mac: propagate and filter -ETIME error

Filter llhw to avoid triggering useless DeviceStateError

Bug: 241137690
Change-Id: Ic476f1cc9da39eb1afc71edd0188a3ad0abc5259
Signed-off-by: Clément Viel <clement.viel@qorvo.com>
diff --git a/mac/fira_access.c b/mac/fira_access.c
index ac7c50a..dc9c99f 100644
--- a/mac/fira_access.c
+++ b/mac/fira_access.c
@@ -846,6 +846,9 @@
 
 	trace_region_fira_access_done(local, session, access->duration_dtu,
 				      error);
+
+	/* propagate llhw error to fira session */
+	session->last_error = access->error;
 	fira_session_fsm_access_done(local, session, error);
 	fira_diagnostic_free(local);
 	if (!error)
diff --git a/mac/fira_session.h b/mac/fira_session.h
index 7a2241e..4f02596 100644
--- a/mac/fira_session.h
+++ b/mac/fira_session.h
@@ -368,6 +368,10 @@
 		 */
 		u32 last_rotation_block_index;
 	} sts;
+	/*
+	 * @last_error: last error that occurred during the active session.
+	 */
+	int last_error;
 };
 
 /**
diff --git a/mac/fira_session_fsm_active.c b/mac/fira_session_fsm_active.c
index feff6c9..2ba014c 100644
--- a/mac/fira_session_fsm_active.c
+++ b/mac/fira_session_fsm_active.c
@@ -780,7 +780,7 @@
 	/* Update local. */
 	local->current_session = NULL;
 
-	if (error) {
+	if ((error) && (session->last_error != -ETIME)) {
 		/*
 		 * FIXME:
 		 * Why corrupt all status, the last slot_index is not
diff --git a/mac/fproc.c b/mac/fproc.c
index 68ec4c0..a9a5372 100644
--- a/mac/fproc.c
+++ b/mac/fproc.c
@@ -55,7 +55,6 @@
 			     u32 next_timestamp_dtu)
 {
 	struct mcps802154_access *access;
-	int r;
 
 	if (!local->start_stop_request) {
 		mcps802154_fproc_stopped_handle(local);
@@ -73,30 +72,30 @@
 
 	switch (access->method) {
 	case MCPS802154_ACCESS_METHOD_NOTHING:
-		r = mcps802154_fproc_nothing_handle(local, access);
+		access->error = mcps802154_fproc_nothing_handle(local, access);
 		break;
 	case MCPS802154_ACCESS_METHOD_IDLE:
-		r = mcps802154_fproc_idle_handle(local, access);
+		access->error = mcps802154_fproc_idle_handle(local, access);
 		break;
 	case MCPS802154_ACCESS_METHOD_IMMEDIATE_RX:
-		r = mcps802154_fproc_rx_handle(local, access);
+		access->error = mcps802154_fproc_rx_handle(local, access);
 		break;
 	case MCPS802154_ACCESS_METHOD_IMMEDIATE_TX:
-		r = mcps802154_fproc_tx_handle(local, access);
+		access->error = mcps802154_fproc_tx_handle(local, access);
 		break;
 	case MCPS802154_ACCESS_METHOD_MULTI:
-		r = mcps802154_fproc_multi_handle(local, access);
+		access->error = mcps802154_fproc_multi_handle(local, access);
 		break;
 	case MCPS802154_ACCESS_METHOD_VENDOR:
-		r = mcps802154_fproc_vendor_handle(local, access);
+		access->error = mcps802154_fproc_vendor_handle(local, access);
 		break;
 	default:
-		r = -1;
+		access->error = -1;
 	}
 
-	if (r) {
+	if (access->error) {
 		mcps802154_fproc_access_done(local, true);
-		if (r == -ETIME)
+		if (access->error == -ETIME)
 			mcps802154_fproc_access_now(local);
 		else
 			mcps802154_fproc_broken_handle(local);
diff --git a/mac/fproc_multi.c b/mac/fproc_multi.c
index ea1f8a6..af3edc3 100644
--- a/mac/fproc_multi.c
+++ b/mac/fproc_multi.c
@@ -107,15 +107,13 @@
 					struct mcps802154_access *access,
 					size_t frame_idx)
 {
-	int r;
-
 	frame_idx++;
 	if (access->ops->access_extend && frame_idx == access->n_frames) {
 		frame_idx = 0;
 		access->n_frames = 0;
 		access->ops->access_extend(access);
-		r = mcps802154_fproc_multi_check_frames(local, access, 0);
-		if (r) {
+		access->error = mcps802154_fproc_multi_check_frames(local, access, 0);
+		if (access->error) {
 			mcps802154_fproc_access_done(local, true);
 			mcps802154_fproc_broken_handle(local);
 			return;
@@ -123,19 +121,19 @@
 	}
 	if (frame_idx < access->n_frames) {
 		/* Next frame. */
-		r = mcps802154_fproc_multi_handle_frame(local, access,
+		access->error = mcps802154_fproc_multi_handle_frame(local, access,
 							frame_idx);
-		if (r) {
+		if (access->error) {
 			mcps802154_fproc_access_done(local, true);
-			if (r == -ETIME)
+			if (access->error == -ETIME)
 				mcps802154_fproc_access_now(local);
 			else
 				mcps802154_fproc_broken_handle(local);
 		}
 	} else {
-		r = mcps802154_fproc_multi_restore(local, access);
-		mcps802154_fproc_access_done(local, !!r);
-		if (r) {
+		access->error = mcps802154_fproc_multi_restore(local, access);
+		mcps802154_fproc_access_done(local, !!access->error);
+		if (access->error) {
 			mcps802154_fproc_broken_handle(local);
 			return;
 		}
@@ -155,19 +153,18 @@
 	struct mcps802154_access *access = local->fproc.access;
 	size_t frame_idx = local->fproc.frame_idx;
 	struct mcps802154_access_frame *frame = &access->frames[frame_idx];
-	int r;
 
 	/* Read frame. */
 	struct sk_buff *skb = NULL;
 	struct mcps802154_rx_frame_info info = {
 		.flags = frame->rx.frame_info_flags_request,
 	};
-	r = llhw_rx_get_frame(local, &skb, &info);
-	if (!r)
+	access->error =  llhw_rx_get_frame(local, &skb, &info);
+	if (!access->error)
 		access->ops->rx_frame(access, frame_idx, skb, &info,
 				      MCPS802154_RX_ERROR_NONE);
 
-	if (r && r != -EBUSY) {
+	if (access->error && access->error != -EBUSY) {
 		mcps802154_fproc_access_done(local, true);
 		mcps802154_fproc_broken_handle(local);
 	} else {
@@ -215,16 +212,15 @@
 
 	if (frame->rx.frame_config.timeout_dtu == -1) {
 		/* Disable RX. */
-		int r = llhw_rx_disable(local);
-
-		if (r == -EBUSY)
+		access->error = llhw_rx_disable(local);
+		if (access->error == -EBUSY)
 			/* Wait for RX result. */
 			return;
 
 		access->ops->rx_frame(access, frame_idx, NULL, NULL,
 				      MCPS802154_RX_ERROR_TIMEOUT);
-		if (r) {
-			mcps802154_fproc_access_done(local, r);
+		if (access->error) {
+			mcps802154_fproc_access_done(local, access->error);
 			mcps802154_fproc_broken_handle(local);
 		} else {
 			/* Next. */
diff --git a/mac/fproc_rx.c b/mac/fproc_rx.c
index 1e45a7c..d92fb87 100644
--- a/mac/fproc_rx.c
+++ b/mac/fproc_rx.c
@@ -48,15 +48,14 @@
 static void mcps802154_fproc_rx_rx_frame(struct mcps802154_local *local)
 {
 	struct mcps802154_access *access = local->fproc.access;
-	int r;
 
 	/* Read frame. */
 	struct sk_buff *skb = NULL;
 	struct mcps802154_rx_frame_info info = {
 		.flags = MCPS802154_RX_FRAME_INFO_LQI,
 	};
-	r = llhw_rx_get_frame(local, &skb, &info);
-	if (!r) {
+	access->error = llhw_rx_get_frame(local, &skb, &info);
+	if (!access->error) {
 		access->ops->rx_frame(access, 0, skb, &info,
 				      MCPS802154_RX_ERROR_NONE);
 		/* If auto-ack was sent, wait for tx_done. */
@@ -66,9 +65,9 @@
 			return;
 		}
 	}
-	mcps802154_fproc_access_done(local, !!r);
+	mcps802154_fproc_access_done(local, !!access->error);
 
-	if (r && r != -EBUSY)
+	if (access->error && access->error != -EBUSY)
 		mcps802154_fproc_broken_handle(local);
 	else
 		/* Next access. */
@@ -79,23 +78,21 @@
 					 enum mcps802154_rx_error_type error)
 {
 	mcps802154_fproc_access_done(local, true);
-
 	/* Next access. */
 	mcps802154_fproc_access_now(local);
 }
 
 static void mcps802154_fproc_rx_schedule_change(struct mcps802154_local *local)
 {
-	int r;
-
+	struct mcps802154_access *access = local->fproc.access;
 	/* Disable RX. */
-	r = llhw_rx_disable(local);
-	if (r == -EBUSY)
+	access->error = llhw_rx_disable(local);
+	if (access->error == -EBUSY)
 		/* Wait for RX result. */
 		return;
 
-	mcps802154_fproc_access_done(local, !!r);
-	if (r)
+	mcps802154_fproc_access_done(local, !!access->error);
+	if (access->error)
 		mcps802154_fproc_broken_handle(local);
 	else
 		/* Next access. */
@@ -112,14 +109,13 @@
 int mcps802154_fproc_rx_handle(struct mcps802154_local *local,
 			       struct mcps802154_access *access)
 {
-	int r;
 	struct mcps802154_rx_frame_config rx_config = {
 		.flags = MCPS802154_RX_FRAME_CONFIG_AACK,
 		.timeout_dtu = -1,
 	};
-	r = llhw_rx_enable(local, &rx_config, 0, 0);
-	if (r)
-		return r;
+	access->error = llhw_rx_enable(local, &rx_config, 0, 0);
+	if (access->error)
+		return access->error;
 
 	mcps802154_fproc_change_state(local, &mcps802154_fproc_rx);
 
diff --git a/mac/fproc_vendor.c b/mac/fproc_vendor.c
index 8723a0b..f067e16 100644
--- a/mac/fproc_vendor.c
+++ b/mac/fproc_vendor.c
@@ -40,6 +40,7 @@
 	if (!r)
 		return;
 
+	access->error = r;
 	mcps802154_fproc_access_done(local, error);
 	if (error) {
 		mcps802154_fproc_broken_handle(local);
diff --git a/mac/include/net/mcps802154_schedule.h b/mac/include/net/mcps802154_schedule.h
index 485be5b..7355742 100644
--- a/mac/include/net/mcps802154_schedule.h
+++ b/mac/include/net/mcps802154_schedule.h
@@ -218,6 +218,10 @@
 	 * start of a multiple frames access.
 	 */
 	const struct mcps802154_hrp_uwb_params *hrp_uwb_params;
+	/**
+	 * @error: contain the error from the llhw in order to propagate it to upper regions.
+	 */
+	int error;
 };
 
 /**