소스 검색

msm: camera: reqmgr: Handle flash properly

Apply the flash at EOF and apply the other devices
at the EPOCH of next frame, then the flash can
cover all the exposure zone of current request.
Add the inject delay for SOF and EOF separate,
then we can use inject delay for more flexible
frame skip control.

CRs-Fixed: 2820683
Change-Id: Ic6a58327a0ae44c54190884ba42ea7926ec7c90e
Signed-off-by: Depeng Shao <[email protected]>
Depeng Shao 4 년 전
부모
커밋
a8fce31f3f

+ 2 - 3
drivers/cam_cust/cam_custom_context.c

@@ -1,6 +1,6 @@
 // SPDX-License-Identifier: GPL-2.0-only
 /*
- * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2019-2021, The Linux Foundation. All rights reserved.
  */
 
 #include <linux/debugfs.h>
@@ -1266,10 +1266,10 @@ static int __cam_custom_ctx_config_dev(struct cam_context *ctx,
 		if ((ctx->state != CAM_CTX_FLUSHED) &&
 			(ctx->state >= CAM_CTX_READY) &&
 			(ctx->ctx_crm_intf->add_req)) {
+			memset(&add_req, 0, sizeof(add_req));
 			add_req.link_hdl = ctx->link_hdl;
 			add_req.dev_hdl  = ctx->dev_hdl;
 			add_req.req_id   = req->request_id;
-			add_req.skip_before_applying = 0;
 			rc = ctx->ctx_crm_intf->add_req(&add_req);
 			if (rc) {
 				CAM_ERR(CAM_CUSTOM,
@@ -1375,7 +1375,6 @@ static int __cam_custom_ctx_link_in_acquired(struct cam_context *ctx,
 
 	ctx->link_hdl = link->link_hdl;
 	ctx->ctx_crm_intf = link->crm_cb;
-	ctx_custom->subscribe_event = link->subscribe_event;
 
 	/* change state only if we had the init config */
 	if (ctx_custom->init_received)

+ 1 - 4
drivers/cam_cust/cam_custom_context.h

@@ -1,6 +1,6 @@
 /* SPDX-License-Identifier: GPL-2.0-only
  *
- * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2019-2021, The Linux Foundation. All rights reserved.
  */
 
 #ifndef _CAM_CUSTOM_CONTEXT_H_
@@ -94,8 +94,6 @@ struct cam_custom_dev_ctx_req {
  * @state: Common context state
  * @hw_ctx: HW object returned by the acquire device command
  * @init_received: Indicate whether init config packet is received
- * @subscribe_event: The irq event mask that CRM subscribes to,
- *                   custom HW will invoke CRM cb at those event.
  * @active_req_cnt: Counter for the active request
  * @frame_id: Frame id tracking for the custom context
  * @hw_acquired: Flag to indicate if HW is acquired for this context
@@ -113,7 +111,6 @@ struct cam_custom_context {
 	uint32_t                       state;
 	void                          *hw_ctx;
 	bool                           init_received;
-	uint32_t                       subscribe_event;
 	uint32_t                       active_req_cnt;
 	int64_t                        frame_id;
 	bool                           hw_acquired;

+ 1 - 2
drivers/cam_isp/cam_isp_context.c

@@ -4608,11 +4608,10 @@ static int __cam_isp_ctx_config_dev_in_top_state(
 		} else if ((ctx->state != CAM_CTX_FLUSHED) &&
 			(ctx->state >= CAM_CTX_READY) &&
 			ctx->ctx_crm_intf->add_req) {
+			memset(&add_req, 0, sizeof(add_req));
 			add_req.link_hdl = ctx->link_hdl;
 			add_req.dev_hdl  = ctx->dev_hdl;
 			add_req.req_id   = req->request_id;
-			add_req.skip_before_applying = 0;
-			add_req.trigger_eof = false;
 			rc = ctx->ctx_crm_intf->add_req(&add_req);
 			if (rc) {
 				CAM_ERR(CAM_ISP, "Add req failed: req id=%llu",

+ 241 - 141
drivers/cam_req_mgr/cam_req_mgr_core.c

@@ -38,15 +38,15 @@ void cam_req_mgr_core_link_reset(struct cam_req_mgr_core_link *link)
 	link->watchdog = NULL;
 	link->state = CAM_CRM_LINK_STATE_AVAILABLE;
 	link->parent = NULL;
-	link->subscribe_event = 0;
-	link->trigger_mask = 0;
 	link->sync_link_sof_skip = false;
 	link->open_req_cnt = 0;
 	link->last_flush_id = 0;
 	link->initial_sync_req = -1;
 	link->dual_trigger = false;
-	link->trigger_cnt[0] = 0;
-	link->trigger_cnt[1] = 0;
+	link->trigger_cnt[0][0] = 0;
+	link->trigger_cnt[0][1] = 0;
+	link->trigger_cnt[1][0] = 0;
+	link->trigger_cnt[1][1] = 0;
 	link->in_msync_mode = false;
 	link->retry_cnt = 0;
 	link->is_shutdown = false;
@@ -162,25 +162,34 @@ static void __cam_req_mgr_dec_idx(int32_t *val, int32_t step, int32_t max_val)
 /**
  * __cam_req_mgr_inject_delay()
  *
- * @brief    : Check if any pd device is injecting delay
- * @tbl      : cam_req_mgr_req_tbl
- * @curr_idx : slot idx
+ * @brief         : Check if any pd device is injecting delay
+ * @tbl           : cam_req_mgr_req_tbl
+ * @curr_idx      : slot idx
+ * @trigger       : Trigger point
  *
  * @return   : 0 for success, negative for failure
  */
 static int __cam_req_mgr_inject_delay(
-	struct cam_req_mgr_req_tbl  *tbl,
-	int32_t curr_idx)
+	struct cam_req_mgr_req_tbl *tbl,
+	int32_t curr_idx, uint32_t trigger)
 {
 	struct cam_req_mgr_tbl_slot *slot = NULL;
 	int rc = 0;
 
 	while (tbl) {
 		slot = &tbl->slot[curr_idx];
-		if (slot->inject_delay > 0) {
-			slot->inject_delay--;
+		if ((trigger == CAM_TRIGGER_POINT_SOF) &&
+			(slot->inject_delay_at_sof > 0)) {
+			slot->inject_delay_at_sof--;
+			CAM_DBG(CAM_CRM,
+				"Delay injected by pd %d device at SOF",
+				tbl->pd);
+			rc = -EAGAIN;
+		} else if ((trigger == CAM_TRIGGER_POINT_EOF) &&
+			(slot->inject_delay_at_eof > 0)) {
+			slot->inject_delay_at_eof--;
 			CAM_DBG(CAM_CRM,
-				"Delay injected by pd %d device",
+				"Delay injected by pd %d device at EOF",
 				tbl->pd);
 			rc = -EAGAIN;
 		}
@@ -557,7 +566,6 @@ static void __cam_req_mgr_flush_req_slot(
 			tbl->slot[idx].req_ready_map = 0;
 			tbl->slot[idx].state = CRM_REQ_STATE_EMPTY;
 			tbl->slot[idx].ops.apply_at_eof = false;
-			tbl->slot[idx].ops.skip_next_frame = false;
 			tbl->slot[idx].ops.dev_hdl = -1;
 			tbl->slot[idx].ops.is_applied = false;
 			tbl = tbl->next;
@@ -567,10 +575,10 @@ static void __cam_req_mgr_flush_req_slot(
 	atomic_set(&link->eof_event_cnt, 0);
 	in_q->wr_idx = 0;
 	in_q->rd_idx = 0;
-	link->trigger_cnt[0] = 0;
-	link->trigger_cnt[1] = 0;
-	link->trigger_mask = 0;
-	link->subscribe_event &= ~CAM_TRIGGER_POINT_EOF;
+	link->trigger_cnt[0][0] = 0;
+	link->trigger_cnt[0][1] = 0;
+	link->trigger_cnt[1][0] = 0;
+	link->trigger_cnt[1][1] = 0;
 }
 
 /**
@@ -611,8 +619,9 @@ static void __cam_req_mgr_reset_req_slot(struct cam_req_mgr_core_link *link,
 			tbl->pd, idx, tbl->slot[idx].state);
 		tbl->slot[idx].req_ready_map = 0;
 		tbl->slot[idx].state = CRM_REQ_STATE_EMPTY;
+		tbl->slot[idx].inject_delay_at_sof = 0;
+		tbl->slot[idx].inject_delay_at_eof = 0;
 		tbl->slot[idx].ops.apply_at_eof = false;
-		tbl->slot[idx].ops.skip_next_frame = false;
 		tbl->slot[idx].ops.dev_hdl = -1;
 		tbl->slot[idx].ops.is_applied = false;
 		tbl = tbl->next;
@@ -820,7 +829,8 @@ static int __cam_req_mgr_send_req(struct cam_req_mgr_core_link *link,
 
 		if (slot->ops.dev_hdl < 0) {
 			CAM_DBG(CAM_CRM,
-				"No special ops detected for this table slot");
+				"No special ops detected for slot %d dev %s",
+				idx, dev->dev_info.name);
 			continue;
 		}
 
@@ -831,6 +841,23 @@ static int __cam_req_mgr_send_req(struct cam_req_mgr_core_link *link,
 			continue;
 		}
 
+		if (apply_data[pd].skip_idx ||
+			(apply_data[pd].req_id < 0)) {
+			CAM_DBG(CAM_CRM,
+				"dev %s skip %d req_id %lld",
+				dev->dev_info.name,
+				apply_data[pd].skip_idx,
+				apply_data[pd].req_id);
+			apply_req.dev_hdl = dev->dev_hdl;
+			apply_req.request_id =
+				link->req.prev_apply_data[pd].req_id;
+			apply_req.trigger_point = 0;
+			apply_req.report_if_bubble = 0;
+			if ((dev->ops) && (dev->ops->notify_frame_skip))
+				dev->ops->notify_frame_skip(&apply_req);
+			continue;
+		}
+
 		/* This one is to prevent EOF request to apply on SOF*/
 		if ((trigger == CAM_TRIGGER_POINT_SOF) &&
 			(slot->ops.apply_at_eof)) {
@@ -858,31 +885,24 @@ static int __cam_req_mgr_send_req(struct cam_req_mgr_core_link *link,
 					trigger);
 				return rc;
 			}
+		} else {
+			CAM_DBG(CAM_REQ,
+				"link_hdl: %x pd: %d req_id %lld has applied",
+				link->link_hdl, pd, apply_req.request_id);
+			break;
 		}
 
 		CAM_DBG(CAM_REQ,
-			"SEND: link_hdl: %x pd: %d req_id %lld",
-			link->link_hdl, pd, apply_req.request_id);
+			"SEND: link_hdl %x dev %s pd %d req_id %lld",
+			link->link_hdl, dev->dev_info.name,
+			pd, apply_req.request_id);
 
-		if (trigger == CAM_TRIGGER_POINT_SOF &&
-			slot->ops.skip_next_frame) {
-			slot->ops.skip_next_frame = false;
-			slot->ops.is_applied = true;
-			CAM_DBG(CAM_REQ,
-				"SEND: link_hdl: %x pd: %d req_id %lld",
-				link->link_hdl, pd, apply_req.request_id);
-			__cam_req_mgr_notify_frame_skip(link,
-				trigger);
-			return -EAGAIN;
-		} else if ((trigger == CAM_TRIGGER_POINT_EOF) &&
+		if ((trigger == CAM_TRIGGER_POINT_EOF) &&
 			(slot->ops.apply_at_eof)) {
+			slot->ops.is_applied = true;
 			slot->ops.apply_at_eof = false;
 			if (atomic_read(&link->eof_event_cnt) > 0)
 				atomic_dec(&link->eof_event_cnt);
-			CAM_DBG(CAM_REQ,
-				"Req_id: %llu eof_event_cnt : %d",
-				apply_data[pd].req_id,
-				link->eof_event_cnt);
 			return 0;
 		}
 	}
@@ -964,8 +984,9 @@ static int __cam_req_mgr_send_req(struct cam_req_mgr_core_link *link,
 
 			apply_req.trigger_point = trigger;
 			CAM_DBG(CAM_REQ,
-				"SEND:  link_hdl: %x pd %d req_id %lld",
-				link->link_hdl, pd, apply_req.request_id);
+				"SEND: link_hdl %x dev %s pd %d req_id %lld",
+				link->link_hdl, dev->dev_info.name,
+				pd, apply_req.request_id);
 			if (dev->ops && dev->ops->apply_req) {
 				rc = dev->ops->apply_req(&apply_req);
 				if (rc < 0) {
@@ -1163,7 +1184,6 @@ static int __cam_req_mgr_check_sync_for_mslave(
 			"No req applied on corresponding SOF on sync link: %x",
 				sync_link->link_hdl);
 		sync_link->sync_link_sof_skip = false;
-		__cam_req_mgr_inject_delay(link->req.l_tbl, slot->idx);
 		return -EAGAIN;
 	}
 
@@ -1181,15 +1201,6 @@ static int __cam_req_mgr_check_sync_for_mslave(
 	}
 
 	if (link->is_master) {
-		rc = __cam_req_mgr_inject_delay(link->req.l_tbl, slot->idx);
-		if (rc) {
-			CAM_DBG(CAM_CRM,
-				"Skip Process Req: %lld on link: %x",
-				req_id, link->link_hdl);
-			link->sync_link_sof_skip = true;
-			return rc;
-		}
-
 		if (sync_link->initial_skip) {
 			CAM_DBG(CAM_CRM,  "Link 0x%x [slave] not streamed on",
 				sync_link->link_hdl);
@@ -1253,15 +1264,6 @@ static int __cam_req_mgr_check_sync_for_mslave(
 		if (link->initial_skip)
 			link->initial_skip = false;
 
-		rc = __cam_req_mgr_inject_delay(link->req.l_tbl, slot->idx);
-		if (rc) {
-			CAM_DBG(CAM_CRM,
-				"Skip Process Req: %lld on link: %x",
-				req_id, link->link_hdl);
-			link->sync_link_sof_skip = true;
-			return rc;
-		}
-
 		rc = __cam_req_mgr_check_link_is_ready(link, slot->idx, true);
 		if (rc) {
 			CAM_DBG(CAM_CRM,
@@ -1374,7 +1376,6 @@ static int __cam_req_mgr_check_sync_req_is_ready(
 
 	if (sync_link->initial_skip) {
 		link->initial_skip = false;
-		__cam_req_mgr_inject_delay(link->req.l_tbl, slot->idx);
 		CAM_DBG(CAM_CRM,
 			"sync link %x not streamed on",
 			sync_link->link_hdl);
@@ -1408,7 +1409,6 @@ static int __cam_req_mgr_check_sync_req_is_ready(
 			 * link, then we need to skip this frame, since the
 			 * previous frame of sync link is also skipped.
 			 */
-			__cam_req_mgr_inject_delay(link->req.l_tbl, slot->idx);
 			CAM_DBG(CAM_CRM,
 				"This frame sync with previous sync_link %x frame",
 				sync_link->link_hdl);
@@ -1421,7 +1421,6 @@ static int __cam_req_mgr_check_sync_req_is_ready(
 			 * we need to skip this SOF event since the sync
 			 * link's SOF event is also skipped.
 			 */
-			__cam_req_mgr_inject_delay(link->req.l_tbl, slot->idx);
 			CAM_DBG(CAM_CRM,
 				"The previous frame of sync link is skipped");
 			return -EAGAIN;
@@ -1433,18 +1432,9 @@ static int __cam_req_mgr_check_sync_req_is_ready(
 			"No req applied on corresponding SOF on sync link: %x",
 			sync_link->link_hdl);
 		sync_link->sync_link_sof_skip = false;
-		__cam_req_mgr_inject_delay(link->req.l_tbl, slot->idx);
 		return -EAGAIN;
 	}
 
-	rc = __cam_req_mgr_inject_delay(link->req.l_tbl, slot->idx);
-	if (rc) {
-		CAM_DBG(CAM_CRM,
-			"Skip Process Req: %lld on link: %x",
-			req_id, link->link_hdl);
-		ready = false;
-	}
-
 	sync_slot_idx = __cam_req_mgr_find_slot_for_req(
 		sync_link->req.in_q, req_id);
 	if (sync_slot_idx == -1) {
@@ -1564,7 +1554,8 @@ static int __cam_req_mgr_check_sync_req_is_ready(
 
 static int __cam_req_mgr_check_multi_sync_link_ready(
 	struct cam_req_mgr_core_link *link,
-	struct cam_req_mgr_slot *slot)
+	struct cam_req_mgr_slot *slot,
+	uint32_t trigger)
 {
 	int i, rc = 0;
 
@@ -1618,6 +1609,16 @@ static int __cam_req_mgr_check_multi_sync_link_ready(
 		}
 	}
 
+	rc = __cam_req_mgr_inject_delay(link->req.l_tbl,
+		slot->idx, trigger);
+	if (rc < 0) {
+		CAM_DBG(CAM_CRM,
+			"Req: %lld needs to inject delay at %s",
+			slot->req_id,
+			(trigger == CAM_TRIGGER_POINT_SOF) ? "SOF" : "EOF");
+		return -EINVAL;
+	}
+
 	/*
 	 *  At this point all validation is successfully done
 	 *  and we can proceed to apply the given request.
@@ -1630,6 +1631,57 @@ static int __cam_req_mgr_check_multi_sync_link_ready(
 	return 0;
 }
 
+/**
+ * __cam_req_mgr_check_for_eof()
+ *
+ * @brief    : Checks for eof trigger type
+ * @link     : pointer to link whose input queue and req tbl are
+ *             traversed through
+ *
+ * @return   : eof trigger type
+ *
+ */
+enum crm_req_eof_trigger_type __cam_req_mgr_check_for_eof(
+	struct cam_req_mgr_core_link *link)
+{
+	int32_t                        curr_idx;
+	struct cam_req_mgr_req_queue  *in_q;
+	enum crm_req_eof_trigger_type  eof_trigger_type;
+	struct cam_req_mgr_tbl_slot   *slot = NULL;
+	struct cam_req_mgr_req_tbl    *tbl;
+
+	in_q = link->req.in_q;
+	tbl = link->req.l_tbl;
+	curr_idx = in_q->rd_idx;
+	eof_trigger_type = CAM_REQ_EOF_TRIGGER_NONE;
+
+	while (tbl != NULL) {
+		slot = &tbl->slot[curr_idx];
+
+		if (slot->ops.is_applied) {
+			eof_trigger_type = CAM_REQ_EOF_TRIGGER_APPLIED;
+			break;
+		} else if (slot->ops.apply_at_eof) {
+			eof_trigger_type = CAM_REQ_EOF_TRIGGER_NOT_APPLY;
+			break;
+		}
+
+		if (tbl->next)
+			__cam_req_mgr_dec_idx(&curr_idx, tbl->pd_delta,
+				tbl->num_slots);
+
+		tbl = tbl->next;
+	}
+
+	CAM_DBG(CAM_REQ,
+		"Req[%lld] idx %d req_status %d link_hdl %x eof_trigger_type %x",
+		in_q->slot[in_q->rd_idx].req_id, in_q->rd_idx,
+		in_q->slot[in_q->rd_idx].status, link->link_hdl,
+		eof_trigger_type);
+
+	return eof_trigger_type;
+}
+
 /**
  * __cam_req_mgr_process_req()
  *
@@ -1652,6 +1704,7 @@ static int __cam_req_mgr_process_req(struct cam_req_mgr_core_link *link,
 	struct cam_req_mgr_connected_device *dev = NULL;
 	struct cam_req_mgr_core_link        *tmp_link = NULL;
 	uint32_t                             max_retry = 0;
+	enum crm_req_eof_trigger_type        eof_trigger_type;
 
 	session = (struct cam_req_mgr_core_session *)link->parent;
 	if (!session) {
@@ -1669,10 +1722,11 @@ static int __cam_req_mgr_process_req(struct cam_req_mgr_core_link *link,
 	 * - if in no_req state, no new req
 	 */
 	CAM_DBG(CAM_REQ,
-		"SOF Req[%lld] idx %d req_status %d link_hdl %x wd_timeout %d ms",
+		"%s Req[%lld] idx %d req_status %d link_hdl %x wd_timeout %d ms trigger:%d",
+		((trigger == CAM_TRIGGER_POINT_SOF) ? "SOF" : "EOF"),
 		in_q->slot[in_q->rd_idx].req_id, in_q->rd_idx,
 		in_q->slot[in_q->rd_idx].status, link->link_hdl,
-		in_q->slot[in_q->rd_idx].additional_timeout);
+		in_q->slot[in_q->rd_idx].additional_timeout, trigger);
 
 	slot = &in_q->slot[in_q->rd_idx];
 
@@ -1680,10 +1734,11 @@ static int __cam_req_mgr_process_req(struct cam_req_mgr_core_link *link,
 		(trigger != CAM_TRIGGER_POINT_EOF))
 		goto end;
 
+	eof_trigger_type = __cam_req_mgr_check_for_eof(link);
+
 	if ((trigger == CAM_TRIGGER_POINT_EOF) &&
-		(!(link->trigger_mask & CAM_TRIGGER_POINT_SOF))) {
-		CAM_DBG(CAM_CRM, "Applying for last SOF fails");
-		rc = -EINVAL;
+		(eof_trigger_type == CAM_REQ_EOF_TRIGGER_NONE)) {
+		CAM_DBG(CAM_CRM, "Not any request to schedule at EOF");
 		goto end;
 	}
 
@@ -1711,17 +1766,12 @@ static int __cam_req_mgr_process_req(struct cam_req_mgr_core_link *link,
 			link->wq_congestion = true;
 		else
 			link->wq_congestion = false;
+	}
 
-		if (link->trigger_mask) {
-			CAM_ERR_RATE_LIMIT(CAM_CRM,
-				"Applying for last EOF fails");
-			rc = -EINVAL;
-			goto end;
-		}
-
+	if (slot->status != CRM_SLOT_STATUS_REQ_READY) {
 		if (slot->sync_mode == CAM_REQ_MGR_SYNC_MODE_SYNC) {
 			rc = __cam_req_mgr_check_multi_sync_link_ready(
-				link, slot);
+				link, slot, trigger);
 		} else {
 			if (link->in_msync_mode) {
 				CAM_DBG(CAM_CRM,
@@ -1738,11 +1788,34 @@ static int __cam_req_mgr_process_req(struct cam_req_mgr_core_link *link,
 				}
 			}
 
-			rc = __cam_req_mgr_inject_delay(link->req.l_tbl,
-				slot->idx);
-			if (!rc)
-				rc = __cam_req_mgr_check_link_is_ready(link,
-					slot->idx, false);
+			/*
+			 * Validate that if the req is ready to apply before
+			 * checking the inject delay.
+			 */
+			rc = __cam_req_mgr_check_link_is_ready(link,
+				slot->idx, true);
+
+			if (!rc) {
+				rc = __cam_req_mgr_inject_delay(link->req.l_tbl,
+					slot->idx, trigger);
+				if (rc < 0)
+					CAM_DBG(CAM_CRM,
+						"Req: %lld needs to inject delay at %s",
+						slot->req_id,
+						(trigger == CAM_TRIGGER_POINT_SOF) ? "SOF" : "EOF");
+
+				if (!rc)
+					rc = __cam_req_mgr_check_link_is_ready(link,
+						slot->idx, false);
+			}
+		}
+
+		if (!rc) {
+			if ((trigger == CAM_TRIGGER_POINT_SOF) &&
+				(eof_trigger_type == CAM_REQ_EOF_TRIGGER_NOT_APPLY)) {
+				CAM_DBG(CAM_CRM, "EOF apply first");
+				rc = -EAGAIN;
+			}
 		}
 
 		if (rc < 0) {
@@ -1769,6 +1842,12 @@ static int __cam_req_mgr_process_req(struct cam_req_mgr_core_link *link,
 			__cam_req_mgr_notify_frame_skip(link, trigger);
 			__cam_req_mgr_validate_crm_wd_timer(link);
 			goto end;
+		} else {
+			slot->status = CRM_SLOT_STATUS_REQ_READY;
+			CAM_DBG(CAM_REQ,
+				"linx_hdl %x Req[%lld] idx %d ready to apply",
+				link->link_hdl, in_q->slot[in_q->rd_idx].req_id,
+				in_q->rd_idx);
 		}
 	}
 
@@ -1808,8 +1887,6 @@ static int __cam_req_mgr_process_req(struct cam_req_mgr_core_link *link,
 		if (link->retry_cnt)
 			link->retry_cnt = 0;
 
-		link->trigger_mask |= trigger;
-
 		/* Check for any long exposure settings */
 		__cam_req_mgr_validate_crm_wd_timer(link);
 
@@ -1826,16 +1903,17 @@ static int __cam_req_mgr_process_req(struct cam_req_mgr_core_link *link,
 		if (link->sync_link_sof_skip)
 			link->sync_link_sof_skip = false;
 
-		if (link->trigger_mask == link->subscribe_event) {
+		/*
+		 * Below two cases can move slot to APPLIED status,
+		 * 1# there is no eof trigger request
+		 * 2# eof trigger is applied and the devcies which need to
+		 * be applied at SOF are also applied.
+		 */
+		if (((eof_trigger_type == CAM_REQ_EOF_TRIGGER_NONE) ||
+			(eof_trigger_type == CAM_REQ_EOF_TRIGGER_APPLIED)) &&
+			(trigger == CAM_TRIGGER_POINT_SOF)) {
 			slot->status = CRM_SLOT_STATUS_REQ_APPLIED;
-			link->trigger_mask = 0;
-			if (!(atomic_read(&link->eof_event_cnt)) &&
-				(trigger == CAM_TRIGGER_POINT_EOF)) {
-				link->subscribe_event &= ~CAM_TRIGGER_POINT_EOF;
-				CAM_DBG(CAM_CRM,
-					"Update link subscribe_event: %d",
-					link->subscribe_event);
-			}
+
 			CAM_DBG(CAM_CRM, "req %d is applied on link %x",
 				slot->req_id,
 				link->link_hdl);
@@ -1937,7 +2015,6 @@ static struct cam_req_mgr_req_tbl *__cam_req_mgr_create_pd_tbl(int32_t delay)
 		CAM_DBG(CAM_CRM, "pd= %d slots= %d", delay, tbl->num_slots);
 		for (i = 0; i < MAX_REQ_SLOTS; i++) {
 			tbl->slot[i].ops.apply_at_eof = false;
-			tbl->slot[i].ops.skip_next_frame = false;
 			tbl->slot[i].ops.dev_hdl = -1;
 			tbl->slot[i].ops.is_applied = false;
 		}
@@ -2217,7 +2294,6 @@ static int __cam_req_mgr_disconnect_link(struct cam_req_mgr_core_link *link)
 	link_data.link_enable = 0;
 	link_data.link_hdl = link->link_hdl;
 	link_data.crm_cb = NULL;
-	link_data.subscribe_event = 0;
 
 	/* Using device ops unlink devices */
 	for (i = 0; i < link->num_devs; i++) {
@@ -2659,23 +2735,31 @@ int cam_req_mgr_process_add_req(void *priv, void *data)
 
 	slot = &tbl->slot[idx];
 	slot->ops.is_applied = false;
-	if ((add_req->skip_before_applying & 0xFF) > slot->inject_delay) {
-		slot->inject_delay = (add_req->skip_before_applying & 0xFF);
-		if (add_req->skip_before_applying & SKIP_NEXT_FRAME) {
-			slot->ops.skip_next_frame = true;
-			slot->ops.dev_hdl = add_req->dev_hdl;
-		}
-		CAM_DBG(CAM_CRM, "Req_id %llu injecting delay %llu",
+
+	if ((add_req->skip_at_sof & 0xFF) > slot->inject_delay_at_sof) {
+		slot->inject_delay_at_sof = (add_req->skip_at_sof & 0xFF);
+		CAM_DBG(CAM_CRM,
+			"Req_id %llu injecting delay %llu frame at SOF by %s",
+			add_req->req_id,
+			slot->inject_delay_at_sof,
+			device->dev_info.name);
+	}
+
+	if ((add_req->skip_at_eof & 0xFF) > slot->inject_delay_at_eof) {
+		slot->inject_delay_at_eof = (add_req->skip_at_eof & 0xFF);
+		CAM_DBG(CAM_CRM,
+			"Req_id %llu injecting delay %llu frame at EOF by %s",
 			add_req->req_id,
-			(add_req->skip_before_applying & 0xFF));
+			slot->inject_delay_at_eof,
+			device->dev_info.name);
 	}
 
 	if (add_req->trigger_eof) {
 		slot->ops.apply_at_eof = true;
 		slot->ops.dev_hdl = add_req->dev_hdl;
 		CAM_DBG(CAM_REQ,
-			"Req_id %llu added for EOF tigger for Device: %s",
-			add_req->req_id, device->dev_info.name);
+			"Req_id %llu slot:%d added for EOF tigger for Device: %s",
+			add_req->req_id, idx, device->dev_info.name);
 	}
 
 	if (slot->state != CRM_REQ_STATE_PENDING &&
@@ -2804,7 +2888,7 @@ int cam_req_mgr_process_error(void *priv, void *data)
 					evt_data.dev_hdl = device->dev_hdl;
 					evt_data.evt_type =
 						CAM_REQ_MGR_LINK_EVT_ERR;
-					evt_data.link_hdl =  link->link_hdl;
+					evt_data.link_hdl = link->link_hdl;
 					evt_data.req_id = err_info->req_id;
 					evt_data.u.error = err_info->error;
 					if (device->ops &&
@@ -2936,6 +3020,10 @@ static int cam_req_mgr_process_trigger(void *priv, void *data)
 
 	spin_unlock_bh(&link->link_state_spin_lock);
 
+	/*
+	 * Move to next req at SOF only in case
+	 * the rd_idx is updated at EOF.
+	 */
 	if (in_q->slot[in_q->rd_idx].status == CRM_SLOT_STATUS_REQ_APPLIED) {
 		/*
 		 * Do NOT reset req q slot data here, it can not be done
@@ -3061,15 +3149,13 @@ static int cam_req_mgr_cb_add_req(struct cam_req_mgr_add_request *add_req)
 	dev_req->req_id = add_req->req_id;
 	dev_req->link_hdl = add_req->link_hdl;
 	dev_req->dev_hdl = add_req->dev_hdl;
-	dev_req->skip_before_applying = add_req->skip_before_applying;
 	dev_req->trigger_eof = add_req->trigger_eof;
+	dev_req->skip_at_sof = add_req->skip_at_sof;
+	dev_req->skip_at_eof = add_req->skip_at_eof;
 	if (dev_req->trigger_eof) {
-		link->subscribe_event |= CAM_TRIGGER_POINT_EOF;
 		atomic_inc(&link->eof_event_cnt);
-		CAM_DBG(CAM_REQ,
-			"Req_id: %llu, eof_event_cnt: %d, link subscribe event: %d",
-			dev_req->req_id, link->eof_event_cnt,
-			link->subscribe_event);
+		CAM_DBG(CAM_REQ, "Req_id: %llu, eof_event_cnt: %d",
+			dev_req->req_id, link->eof_event_cnt);
 	}
 
 	task->process_cb = &cam_req_mgr_process_add_req;
@@ -3147,35 +3233,38 @@ end:
 }
 
 static int __cam_req_mgr_check_for_dual_trigger(
-	struct cam_req_mgr_core_link    *link)
+	struct cam_req_mgr_core_link    *link,
+	uint32_t                         trigger)
 {
 	int rc  = -EAGAIN;
 
-	CAM_DBG(CAM_CRM, "trigger_cnt [%u: %u]",
-		link->trigger_cnt[0], link->trigger_cnt[1]);
+	CAM_DBG(CAM_CRM, "%s trigger_cnt [%u: %u]",
+		(trigger == CAM_TRIGGER_POINT_SOF) ? "SOF" : "EOF",
+		link->trigger_cnt[0][trigger], link->trigger_cnt[1][trigger]);
 
-	if (link->trigger_cnt[0] == link->trigger_cnt[1]) {
-		link->trigger_cnt[0] = 0;
-		link->trigger_cnt[1] = 0;
+	if (link->trigger_cnt[0][trigger] == link->trigger_cnt[1][trigger]) {
+		link->trigger_cnt[0][trigger] = 0;
+		link->trigger_cnt[1][trigger] = 0;
 		rc = 0;
 		return rc;
 	}
 
-	if ((link->trigger_cnt[0] &&
-		(link->trigger_cnt[0] - link->trigger_cnt[1] > 1)) ||
-		(link->trigger_cnt[1] &&
-		(link->trigger_cnt[1] - link->trigger_cnt[0] > 1))) {
+	if ((link->trigger_cnt[0][trigger] &&
+		(link->trigger_cnt[0][trigger] - link->trigger_cnt[1][trigger] > 1)) ||
+		(link->trigger_cnt[1][trigger] &&
+		(link->trigger_cnt[1][trigger] - link->trigger_cnt[0][trigger] > 1))) {
 
 		CAM_WARN(CAM_CRM,
 			"One of the devices could not generate trigger");
 
-		link->trigger_cnt[0] = 0;
-		link->trigger_cnt[1] = 0;
+		link->trigger_cnt[0][trigger] = 0;
+		link->trigger_cnt[1][trigger] = 0;
 		CAM_DBG(CAM_CRM, "Reset the trigger cnt");
 		return rc;
 	}
 
-	CAM_DBG(CAM_CRM, "Only one device has generated trigger");
+	CAM_DBG(CAM_CRM, "Only one device has generated trigger for %s",
+		(trigger == CAM_TRIGGER_POINT_SOF) ? "SOF" : "EOF");
 
 	return rc;
 }
@@ -3308,13 +3397,14 @@ static int cam_req_mgr_cb_notify_trigger(
 	struct cam_req_mgr_trigger_notify *trigger_data)
 {
 	int32_t                          rc = 0, trigger_id = 0;
+	uint32_t                         trigger;
 	struct crm_workq_task           *task = NULL;
 	struct cam_req_mgr_core_link    *link = NULL;
 	struct cam_req_mgr_trigger_notify   *notify_trigger;
 	struct crm_task_payload         *task_data;
 
 	if (!trigger_data) {
-		CAM_ERR(CAM_CRM, "sof_data is NULL");
+		CAM_ERR(CAM_CRM, "trigger_data is NULL");
 		rc = -EINVAL;
 		goto end;
 	}
@@ -3327,10 +3417,20 @@ static int cam_req_mgr_cb_notify_trigger(
 		goto end;
 	}
 
+	CAM_DBG(CAM_REQ, "link_hdl %x frame_id %lld, trigger %x\n",
+		trigger_data->link_hdl,
+		trigger_data->frame_id,
+		trigger_data->trigger);
+
 	trigger_id = trigger_data->trigger_id;
+	trigger = trigger_data->trigger;
 
+	/*
+	 * Reduce the workq overhead when there is
+	 * not any eof event found.
+	 */
 	if ((!atomic_read(&link->eof_event_cnt)) &&
-		(trigger_data->trigger == CAM_TRIGGER_POINT_EOF)) {
+		(trigger == CAM_TRIGGER_POINT_EOF)) {
 		CAM_DBG(CAM_CRM, "Not any request to schedule at EOF");
 		goto end;
 	}
@@ -3344,14 +3444,14 @@ static int cam_req_mgr_cb_notify_trigger(
 	}
 
 	if ((link->watchdog) && (link->watchdog->pause_timer) &&
-		(trigger_data->trigger == CAM_TRIGGER_POINT_SOF))
+		(trigger == CAM_TRIGGER_POINT_SOF))
 		link->watchdog->pause_timer = false;
 
 	if (link->dual_trigger) {
 		if ((trigger_id >= 0) && (trigger_id <
 			CAM_REQ_MGR_MAX_TRIGGERS)) {
-			link->trigger_cnt[trigger_id]++;
-			rc = __cam_req_mgr_check_for_dual_trigger(link);
+			link->trigger_cnt[trigger_id][trigger]++;
+			rc = __cam_req_mgr_check_for_dual_trigger(link, trigger);
 			if (rc) {
 				spin_unlock_bh(&link->link_state_spin_lock);
 				goto end;
@@ -3424,7 +3524,6 @@ static int __cam_req_mgr_setup_link_info(struct cam_req_mgr_core_link *link,
 	struct cam_req_mgr_connected_device    *dev;
 	struct cam_req_mgr_req_tbl             *pd_tbl;
 	enum cam_pipeline_delay                 max_delay;
-	uint32_t                                subscribe_event = 0;
 	uint32_t num_trigger_devices = 0;
 	if (link_info->version == VERSION_1) {
 		if (link_info->u.link_info_v1.num_devices >
@@ -3512,8 +3611,6 @@ static int __cam_req_mgr_setup_link_info(struct cam_req_mgr_core_link *link,
 				}
 			if (dev->dev_info.p_delay > max_delay)
 				max_delay = dev->dev_info.p_delay;
-
-			subscribe_event |= (uint32_t)dev->dev_info.trigger;
 		}
 
 		if (dev->dev_info.trigger_on)
@@ -3528,12 +3625,10 @@ static int __cam_req_mgr_setup_link_info(struct cam_req_mgr_core_link *link,
 		goto error;
 	}
 
-	link->subscribe_event = subscribe_event;
 	link_data.link_enable = 1;
 	link_data.link_hdl = link->link_hdl;
 	link_data.crm_cb = &cam_req_mgr_ops;
 	link_data.max_delay = max_delay;
-	link_data.subscribe_event = subscribe_event;
 	if (num_trigger_devices == CAM_REQ_MGR_MAX_TRIGGERS)
 		link->dual_trigger = true;
 
@@ -3968,6 +4063,11 @@ int cam_req_mgr_link_v2(struct cam_req_mgr_ver_info *link_info)
 		goto setup_failed;
 	}
 
+	link->trigger_cnt[0][0] = 0;
+	link->trigger_cnt[0][1] = 0;
+	link->trigger_cnt[1][0] = 0;
+	link->trigger_cnt[1][1] = 0;
+
 	mutex_unlock(&link->lock);
 	mutex_unlock(&g_crm_core_dev->crm_lock);
 	return rc;

+ 26 - 19
drivers/cam_req_mgr/cam_req_mgr_core.h

@@ -1,6 +1,6 @@
 /* SPDX-License-Identifier: GPL-2.0-only */
 /*
- * Copyright (c) 2016-2020, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2021, The Linux Foundation. All rights reserved.
  */
 #ifndef _CAM_REQ_MGR_CORE_H_
 #define _CAM_REQ_MGR_CORE_H_
@@ -42,6 +42,16 @@
 #define VERSION_2  2
 #define CAM_REQ_MGR_MAX_TRIGGERS   2
 
+/**
+ * enum crm_req_eof_trigger_type
+ * @codes: to identify which type of eof trigger for next slot
+ */
+enum crm_req_eof_trigger_type {
+	CAM_REQ_EOF_TRIGGER_NONE,
+	CAM_REQ_EOF_TRIGGER_NOT_APPLY,
+	CAM_REQ_EOF_TRIGGER_APPLIED,
+};
+
 /**
  * enum crm_workq_task_type
  * @codes: to identify which type of task is present
@@ -105,6 +115,7 @@ enum crm_req_state {
  * NO_REQ     : empty slot
  * REQ_ADDED  : new entry in slot
  * REQ_PENDING    : waiting for next trigger to apply
+ * REQ_READY      : req has ready
  * REQ_APPLIED    : req is sent to all devices
  * INVALID    : invalid state
  */
@@ -112,6 +123,7 @@ enum crm_slot_status {
 	CRM_SLOT_STATUS_NO_REQ,
 	CRM_SLOT_STATUS_REQ_ADDED,
 	CRM_SLOT_STATUS_REQ_PENDING,
+	CRM_SLOT_STATUS_REQ_READY,
 	CRM_SLOT_STATUS_REQ_APPLIED,
 	CRM_SLOT_STATUS_INVALID,
 };
@@ -186,34 +198,34 @@ struct cam_req_mgr_apply {
  * struct crm_tbl_slot_special_ops
  * @dev_hdl         : Device handle who requested for special ops
  * @apply_at_eof    : Boolean Identifier for request to be applied at EOF
- * @skip_next_frame : Flag to drop the frame after skip_before_apply frame
  * @is_applied      : Flag to identify if request is already applied to device
  *                    in previous frame
  */
 struct crm_tbl_slot_special_ops {
 	int32_t dev_hdl;
 	bool apply_at_eof;
-	bool skip_next_frame;
 	bool is_applied;
 };
 
 /**
  * struct cam_req_mgr_tbl_slot
- * @idx             : slot index
- * @req_ready_map   : mask tracking which all devices have request ready
- * @state           : state machine for life cycle of a slot
- * @inject_delay    : insert extra bubbling for flash type of use cases
- * @ops             : special operation for the table slot
- *                    e.g.
- *                    skip_next frame: in case of applying one device
- *                    and skip others
- *                    apply_at_eof: device that needs to apply at EOF
+ * @idx                 : slot index
+ * @req_ready_map       : mask tracking which all devices have request ready
+ * @state               : state machine for life cycle of a slot
+ * @inject_delay_at_sof : insert extra bubbling for flash type of use cases
+ * @inject_delay_at_eof : insert extra bubbling for flash type of use cases
+ * @ops                 : special operation for the table slot
+ *                        e.g.
+ *                        skip_next frame: in case of applying one device
+ *                        and skip others
+ *                        apply_at_eof: device that needs to apply at EOF
  */
 struct cam_req_mgr_tbl_slot {
 	int32_t                                idx;
 	uint32_t                               req_ready_map;
 	enum crm_req_state                     state;
-	uint32_t                               inject_delay;
+	uint32_t                               inject_delay_at_sof;
+	uint32_t                               inject_delay_at_eof;
 	struct  crm_tbl_slot_special_ops       ops;
 };
 
@@ -342,9 +354,6 @@ struct cam_req_mgr_connected_device {
  * @parent               : pvt data - link's parent is session
  * @lock                 : mutex lock to guard link data operations
  * @link_state_spin_lock : spin lock to protect link state variable
- * @subscribe_event      : irqs that link subscribes, IFE should send
- *                         notification to CRM at those hw events.
- * @trigger_mask         : mask on which irq the req is already applied
  * @sync_link            : array of pointer to the sync link for synchronization
  * @num_sync_links       : num of links sync associated with this link
  * @sync_link_sof_skip   : flag determines if a pkt is not available for a given
@@ -390,8 +399,6 @@ struct cam_req_mgr_core_link {
 	void                                *parent;
 	struct mutex                         lock;
 	spinlock_t                           link_state_spin_lock;
-	uint32_t                             subscribe_event;
-	uint32_t                             trigger_mask;
 	struct cam_req_mgr_core_link
 			*sync_link[MAXIMUM_LINKS_PER_SESSION - 1];
 	int32_t                              num_sync_links;
@@ -408,7 +415,7 @@ struct cam_req_mgr_core_link {
 	uint64_t                             sof_timestamp;
 	uint64_t                             prev_sof_timestamp;
 	bool                                 dual_trigger;
-	uint32_t    trigger_cnt[CAM_REQ_MGR_MAX_TRIGGERS];
+	uint32_t trigger_cnt[CAM_REQ_MGR_MAX_TRIGGERS][CAM_TRIGGER_MAX_POINTS];
 	atomic_t                             eof_event_cnt;
 	bool                                 skip_init_frame;
 	uint64_t                             last_sof_trigger_jiffies;

+ 8 - 7
drivers/cam_req_mgr/cam_req_mgr_interface.h

@@ -1,6 +1,6 @@
 /* SPDX-License-Identifier: GPL-2.0-only */
 /*
- * Copyright (c) 2016-2020, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2021, The Linux Foundation. All rights reserved.
  */
 
 #ifndef _CAM_REQ_MGR_INTERFACE_H
@@ -23,8 +23,6 @@ struct cam_req_mgr_flush_request;
 struct cam_req_mgr_link_evt_data;
 struct cam_req_mgr_dump_info;
 
-#define SKIP_NEXT_FRAME 0x100
-
 /* Request Manager -- camera device driver interface */
 /**
  * @brief: camera kernel drivers to cam req mgr communication
@@ -119,9 +117,11 @@ enum cam_pipeline_delay {
 /**
  * @CAM_TRIGGER_POINT_SOF   : Trigger point for Start Of Frame
  * @CAM_TRIGGER_POINT_EOF   : Trigger point for End Of Frame
+ * @CAM_TRIGGER_MAX_POINTS  : Maximum number of trigger point
  */
 #define CAM_TRIGGER_POINT_SOF     (1 << 0)
 #define CAM_TRIGGER_POINT_EOF     (1 << 1)
+#define CAM_TRIGGER_MAX_POINTS    2
 
 /**
  * enum cam_req_status
@@ -266,7 +266,9 @@ struct cam_req_mgr_error_notify {
  * @link_hdl             : link identifier
  * @dev_hdl              : device handle which has sent this req id
  * @req_id               : req id which device is ready to process
- * @skip_before_applying : before applying req mgr introduce bubble
+ * @skip_at_sof          : before applying req mgr introduce bubble
+ *                         by not sending request to devices. ex: IFE and Flash
+ * @skip_at_eof          : before applying req mgr introduce bubble
  *                         by not sending request to devices. ex: IFE and Flash
  * @trigger_eof          : to identify that one of the device at this slot needs
  *                         to be apply at EOF
@@ -275,7 +277,8 @@ struct cam_req_mgr_add_request {
 	int32_t  link_hdl;
 	int32_t  dev_hdl;
 	uint64_t req_id;
-	uint32_t skip_before_applying;
+	uint32_t skip_at_sof;
+	uint32_t skip_at_eof;
 	bool     trigger_eof;
 };
 
@@ -316,7 +319,6 @@ struct cam_req_mgr_device_info {
  * @dev_hdl         : device handle for reference
  * @max_delay       : max pipeline delay on this link
  * @crm_cb          : callback funcs to communicate with req mgr
- * @subscribe_event : the mask of trigger points this link subscribes
  * @trigger_id      : Unique ID provided to the triggering device
  */
 struct cam_req_mgr_core_dev_link_setup {
@@ -325,7 +327,6 @@ struct cam_req_mgr_core_dev_link_setup {
 	int32_t                    dev_hdl;
 	enum cam_pipeline_delay    max_delay;
 	struct cam_req_mgr_crm_cb *crm_cb;
-	uint32_t                   subscribe_event;
 	int32_t                    trigger_id;
 };
 

+ 2 - 3
drivers/cam_sensor_module/cam_actuator/cam_actuator_core.c

@@ -1,6 +1,6 @@
 // SPDX-License-Identifier: GPL-2.0-only
 /*
- * Copyright (c) 2017-2020, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2017-2021, The Linux Foundation. All rights reserved.
  */
 
 #include <linux/module.h>
@@ -374,11 +374,10 @@ static int cam_actuator_update_req_mgr(
 	int rc = 0;
 	struct cam_req_mgr_add_request add_req;
 
+	memset(&add_req, 0, sizeof(add_req));
 	add_req.link_hdl = a_ctrl->bridge_intf.link_hdl;
 	add_req.req_id = csl_packet->header.request_id;
 	add_req.dev_hdl = a_ctrl->bridge_intf.device_hdl;
-	add_req.skip_before_applying = 0;
-	add_req.trigger_eof = false;
 
 	if (a_ctrl->bridge_intf.crm_cb &&
 		a_ctrl->bridge_intf.crm_cb->add_req) {

+ 38 - 27
drivers/cam_sensor_module/cam_flash/cam_flash_core.c

@@ -1263,26 +1263,30 @@ update_req_mgr:
 		CAM_PKT_NOP_OPCODE) ||
 		((csl_packet->header.op_code & 0xFFFFF) ==
 		CAM_FLASH_PACKET_OPCODE_SET_OPS)) {
+		memset(&add_req, 0, sizeof(add_req));
 		add_req.link_hdl = fctrl->bridge_intf.link_hdl;
 		add_req.req_id = csl_packet->header.request_id;
 		add_req.dev_hdl = fctrl->bridge_intf.device_hdl;
 
 		if ((csl_packet->header.op_code & 0xFFFFF) ==
-			CAM_FLASH_PACKET_OPCODE_SET_OPS)
-			add_req.skip_before_applying = 1;
-		else
-			add_req.skip_before_applying = 0;
+			CAM_FLASH_PACKET_OPCODE_SET_OPS) {
+			add_req.trigger_eof = true;
+			add_req.skip_at_sof = 1;
+		}
 
 		if (fctrl->bridge_intf.crm_cb &&
-			fctrl->bridge_intf.crm_cb->add_req)
+			fctrl->bridge_intf.crm_cb->add_req) {
 			rc = fctrl->bridge_intf.crm_cb->add_req(&add_req);
-		if (rc) {
-			CAM_ERR(CAM_FLASH,
-				"Failed in adding request: %llu to request manager",
-				csl_packet->header.request_id);
-			return rc;
+			if  (rc) {
+				CAM_ERR(CAM_FLASH,
+					"Failed in adding request: %llu to request manager",
+					csl_packet->header.request_id);
+				return rc;
+			}
+			CAM_DBG(CAM_FLASH,
+				"add req %lld to req_mgr, trigger_eof %d",
+				add_req.req_id, add_req.trigger_eof);
 		}
-		CAM_DBG(CAM_FLASH, "add req to req_mgr= %lld", add_req.req_id);
 	}
 	return rc;
 }
@@ -1507,7 +1511,8 @@ int cam_flash_pmic_pkt_parser(struct cam_flash_ctrl *fctrl, void *arg)
 		switch (cmn_hdr->cmd_type) {
 		case CAMERA_SENSOR_FLASH_CMD_TYPE_FIRE: {
 			CAM_DBG(CAM_FLASH,
-				"CAMERA_SENSOR_FLASH_CMD_TYPE_FIRE cmd called");
+				"CAMERA_SENSOR_FLASH_CMD_TYPE_FIRE cmd called, req:%lld",
+				csl_packet->header.request_id);
 			if ((fctrl->flash_state == CAM_FLASH_STATE_INIT) ||
 				(fctrl->flash_state ==
 					CAM_FLASH_STATE_ACQUIRE)) {
@@ -1545,7 +1550,8 @@ int cam_flash_pmic_pkt_parser(struct cam_flash_ctrl *fctrl, void *arg)
 				= flash_operation_info->led_current_ma[i];
 
 			CAM_DBG(CAM_FLASH,
-				"FLASH_CMD_TYPE op:%d", flash_data->opcode);
+				"FLASH_CMD_TYPE op:%d, req:%lld",
+				flash_data->opcode, csl_packet->header.request_id);
 
 			if (flash_data->opcode ==
 				CAMERA_SENSOR_FLASH_OP_FIREDURATION) {
@@ -1739,29 +1745,34 @@ int cam_flash_pmic_pkt_parser(struct cam_flash_ctrl *fctrl, void *arg)
 		CAM_PKT_NOP_OPCODE) ||
 		((csl_packet->header.op_code & 0xFFFFF) ==
 		CAM_FLASH_PACKET_OPCODE_SET_OPS)) {
+		memset(&add_req, 0, sizeof(add_req));
 		add_req.link_hdl = fctrl->bridge_intf.link_hdl;
 		add_req.req_id = csl_packet->header.request_id;
 		add_req.dev_hdl = fctrl->bridge_intf.device_hdl;
 
 		if ((csl_packet->header.op_code & 0xFFFFF) ==
 			CAM_FLASH_PACKET_OPCODE_SET_OPS) {
-			add_req.skip_before_applying |= SKIP_NEXT_FRAME;
 			add_req.trigger_eof = true;
-
-			if (flash_data && (flash_data->opcode !=
-				CAMERA_SENSOR_FLASH_OP_FIREDURATION))
-				add_req.skip_before_applying |= 1;
-			else
-				add_req.skip_before_applying = 0;
-		} else {
-			add_req.skip_before_applying = 0;
+			if (flash_data->opcode == CAMERA_SENSOR_FLASH_OP_OFF) {
+				add_req.skip_at_sof = 1;
+				add_req.skip_at_eof = 1;
+			} else
+				add_req.skip_at_sof = 1;
 		}
-		CAM_DBG(CAM_FLASH,
-			"add req to req_mgr= %lld:: trigger_eof: %d",
-			add_req.req_id, add_req.trigger_eof);
+
 		if (fctrl->bridge_intf.crm_cb &&
-			fctrl->bridge_intf.crm_cb->add_req)
-			fctrl->bridge_intf.crm_cb->add_req(&add_req);
+			fctrl->bridge_intf.crm_cb->add_req) {
+			rc = fctrl->bridge_intf.crm_cb->add_req(&add_req);
+			if  (rc) {
+				CAM_ERR(CAM_FLASH,
+					"Failed in adding request: %llu to request manager",
+					csl_packet->header.request_id);
+				return rc;
+			}
+			CAM_DBG(CAM_FLASH,
+				"add req %lld to req_mgr, trigger_eof %d",
+				add_req.req_id, add_req.trigger_eof);
+		}
 	}
 
 	return rc;

+ 1 - 2
drivers/cam_sensor_module/cam_sensor/cam_sensor_core.c

@@ -20,13 +20,12 @@ static int cam_sensor_update_req_mgr(
 	int rc = 0;
 	struct cam_req_mgr_add_request add_req;
 
+	memset(&add_req, 0, sizeof(add_req));
 	add_req.link_hdl = s_ctrl->bridge_intf.link_hdl;
 	add_req.req_id = csl_packet->header.request_id;
 	CAM_DBG(CAM_SENSOR, " Rxed Req Id: %llu",
 		csl_packet->header.request_id);
 	add_req.dev_hdl = s_ctrl->bridge_intf.device_hdl;
-	add_req.skip_before_applying = 0;
-	add_req.trigger_eof = false;
 	if (s_ctrl->bridge_intf.crm_cb &&
 		s_ctrl->bridge_intf.crm_cb->add_req) {
 		rc = s_ctrl->bridge_intf.crm_cb->add_req(&add_req);