Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 73abf3a0 authored by Srinivasarao P's avatar Srinivasarao P
Browse files

Revert rpmh and usb changes



8aafbcb3 usb: dwc3: gadget: Properly handle failed kick_transfer
c6463694 soc: qcom: rpmh: Dirt can only make you dirtier, not cleaner
a91f874f soc: qcom: rpmh-rsc: Allow using free WAKE TCS for active request
c15a40c9 soc: qcom: rpmh-rsc: Clear active mode configuration for wake TCS
8644121c soc: qcom: rpmh: Invalidate SLEEP and WAKE TCSes before flushing new data
d5046990 soc: qcom: rpmh: Update dirty flag only when data changes

Change-Id: I0d919e1b658c8195230444ef118f7f1fe8e63b47
Signed-off-by: default avatarSrinivasarao P <spathi@codeaurora.org>
parent 204dd19a
Loading
Loading
Loading
Loading
+34 −64
Original line number Diff line number Diff line
@@ -148,7 +148,7 @@ int rpmh_rsc_invalidate(struct rsc_drv *drv)
static struct tcs_group *get_tcs_for_msg(struct rsc_drv *drv,
					 const struct tcs_request *msg)
{
	int type;
	int type, ret;
	struct tcs_group *tcs;

	switch (msg->state) {
@@ -169,10 +169,19 @@ static struct tcs_group *get_tcs_for_msg(struct rsc_drv *drv,
	 * If we are making an active request on a RSC that does not have a
	 * dedicated TCS for active state use, then re-purpose a wake TCS to
	 * send active votes.
	 * NOTE: The driver must be aware that this RSC does not have a
	 * dedicated AMC, and therefore would invalidate the sleep and wake
	 * TCSes before making an active state request.
	 */
	tcs = get_tcs_of_type(drv, type);
	if (msg->state == RPMH_ACTIVE_ONLY_STATE && !tcs->num_tcs)
	if (msg->state == RPMH_ACTIVE_ONLY_STATE && !tcs->num_tcs) {
		tcs = get_tcs_of_type(drv, WAKE_TCS);
		if (tcs->num_tcs) {
			ret = rpmh_rsc_invalidate(drv);
			if (ret)
				return ERR_PTR(ret);
		}
	}

	return tcs;
}
@@ -192,42 +201,6 @@ static const struct tcs_request *get_req_from_tcs(struct rsc_drv *drv,
	return NULL;
}

static void __tcs_set_trigger(struct rsc_drv *drv, int tcs_id, bool trigger)
{
	u32 enable;

	/*
	 * HW req: Clear the DRV_CONTROL and enable TCS again
	 * While clearing ensure that the AMC mode trigger is cleared
	 * and then the mode enable is cleared.
	 */
	enable = read_tcs_reg(drv, RSC_DRV_CONTROL, tcs_id, 0);
	enable &= ~TCS_AMC_MODE_TRIGGER;
	write_tcs_reg_sync(drv, RSC_DRV_CONTROL, tcs_id, enable);
	enable &= ~TCS_AMC_MODE_ENABLE;
	write_tcs_reg_sync(drv, RSC_DRV_CONTROL, tcs_id, enable);

	if (trigger) {
		/* Enable the AMC mode on the TCS and then trigger the TCS */
		enable = TCS_AMC_MODE_ENABLE;
		write_tcs_reg_sync(drv, RSC_DRV_CONTROL, tcs_id, enable);
		enable |= TCS_AMC_MODE_TRIGGER;
		write_tcs_reg_sync(drv, RSC_DRV_CONTROL, tcs_id, enable);
	}
}

static void enable_tcs_irq(struct rsc_drv *drv, int tcs_id, bool enable)
{
	u32 data;

	data = read_tcs_reg(drv, RSC_DRV_IRQ_ENABLE, 0, 0);
	if (enable)
		data |= BIT(tcs_id);
	else
		data &= ~BIT(tcs_id);
	write_tcs_reg(drv, RSC_DRV_IRQ_ENABLE, 0, data);
}

/**
 * tcs_tx_done: TX Done interrupt handler
 */
@@ -264,14 +237,6 @@ static irqreturn_t tcs_tx_done(int irq, void *p)
		}

		trace_rpmh_tx_done(drv, i, req, err);

		/*
		 * If wake tcs was re-purposed for sending active
		 * votes, clear AMC trigger & enable modes and
		 * disable interrupt for this TCS
		 */
		if (!drv->tcs[ACTIVE_TCS].num_tcs)
			__tcs_set_trigger(drv, i, false);
skip:
		/* Reclaim the TCS */
		write_tcs_reg(drv, RSC_DRV_CMD_ENABLE, i, 0);
@@ -279,13 +244,6 @@ static irqreturn_t tcs_tx_done(int irq, void *p)
		write_tcs_reg(drv, RSC_DRV_IRQ_CLEAR, 0, BIT(i));
		spin_lock(&drv->lock);
		clear_bit(i, drv->tcs_in_use);
		/*
		 * Disable interrupt for WAKE TCS to avoid being
		 * spammed with interrupts coming when the solver
		 * sends its wake votes.
		 */
		if (!drv->tcs[ACTIVE_TCS].num_tcs)
			enable_tcs_irq(drv, i, false);
		spin_unlock(&drv->lock);
		if (req)
			rpmh_tx_done(req, err);
@@ -327,6 +285,28 @@ static void __tcs_buffer_write(struct rsc_drv *drv, int tcs_id, int cmd_id,
	write_tcs_reg(drv, RSC_DRV_CMD_ENABLE, tcs_id, cmd_enable);
}

static void __tcs_trigger(struct rsc_drv *drv, int tcs_id)
{
	u32 enable;

	/*
	 * HW req: Clear the DRV_CONTROL and enable TCS again
	 * While clearing ensure that the AMC mode trigger is cleared
	 * and then the mode enable is cleared.
	 */
	enable = read_tcs_reg(drv, RSC_DRV_CONTROL, tcs_id, 0);
	enable &= ~TCS_AMC_MODE_TRIGGER;
	write_tcs_reg_sync(drv, RSC_DRV_CONTROL, tcs_id, enable);
	enable &= ~TCS_AMC_MODE_ENABLE;
	write_tcs_reg_sync(drv, RSC_DRV_CONTROL, tcs_id, enable);

	/* Enable the AMC mode on the TCS and then trigger the TCS */
	enable = TCS_AMC_MODE_ENABLE;
	write_tcs_reg_sync(drv, RSC_DRV_CONTROL, tcs_id, enable);
	enable |= TCS_AMC_MODE_TRIGGER;
	write_tcs_reg_sync(drv, RSC_DRV_CONTROL, tcs_id, enable);
}

static int check_for_req_inflight(struct rsc_drv *drv, struct tcs_group *tcs,
				  const struct tcs_request *msg)
{
@@ -397,20 +377,10 @@ static int tcs_write(struct rsc_drv *drv, const struct tcs_request *msg)

	tcs->req[tcs_id - tcs->offset] = msg;
	set_bit(tcs_id, drv->tcs_in_use);
	if (msg->state == RPMH_ACTIVE_ONLY_STATE && tcs->type != ACTIVE_TCS) {
		/*
		 * Clear previously programmed WAKE commands in selected
		 * repurposed TCS to avoid triggering them. tcs->slots will be
		 * cleaned from rpmh_flush() by invoking rpmh_rsc_invalidate()
		 */
		write_tcs_reg_sync(drv, RSC_DRV_CMD_ENABLE, tcs_id, 0);
		write_tcs_reg_sync(drv, RSC_DRV_CMD_WAIT_FOR_CMPL, tcs_id, 0);
		enable_tcs_irq(drv, tcs_id, true);
	}
	spin_unlock(&drv->lock);

	__tcs_buffer_write(drv, tcs_id, 0, msg);
	__tcs_set_trigger(drv, tcs_id, true);
	__tcs_trigger(drv, tcs_id);

done_write:
	spin_unlock_irqrestore(&tcs->lock, flags);
+29 −27
Original line number Diff line number Diff line
@@ -119,7 +119,6 @@ static struct cache_req *cache_rpm_request(struct rpmh_ctrlr *ctrlr,
{
	struct cache_req *req;
	unsigned long flags;
	u32 old_sleep_val, old_wake_val;

	spin_lock_irqsave(&ctrlr->cache_lock, flags);
	req = __find_req(ctrlr, cmd->addr);
@@ -134,27 +133,26 @@ static struct cache_req *cache_rpm_request(struct rpmh_ctrlr *ctrlr,

	req->addr = cmd->addr;
	req->sleep_val = req->wake_val = UINT_MAX;
	INIT_LIST_HEAD(&req->list);
	list_add_tail(&req->list, &ctrlr->cache);

existing:
	old_sleep_val = req->sleep_val;
	old_wake_val = req->wake_val;

	switch (state) {
	case RPMH_ACTIVE_ONLY_STATE:
		if (req->sleep_val != UINT_MAX)
			req->wake_val = cmd->data;
		break;
	case RPMH_WAKE_ONLY_STATE:
		req->wake_val = cmd->data;
		break;
	case RPMH_SLEEP_STATE:
		req->sleep_val = cmd->data;
		break;
	default:
		break;
	}

	ctrlr->dirty |= (req->sleep_val != old_sleep_val ||
			 req->wake_val != old_wake_val) &&
			 req->sleep_val != UINT_MAX &&
			 req->wake_val != UINT_MAX;

	ctrlr->dirty = true;
unlock:
	spin_unlock_irqrestore(&ctrlr->cache_lock, flags);

@@ -290,7 +288,6 @@ static void cache_batch(struct rpmh_ctrlr *ctrlr, struct batch_cache_req *req)

	spin_lock_irqsave(&ctrlr->cache_lock, flags);
	list_add_tail(&req->list, &ctrlr->batch_cache);
	ctrlr->dirty = true;
	spin_unlock_irqrestore(&ctrlr->cache_lock, flags);
}

@@ -318,6 +315,18 @@ static int flush_batch(struct rpmh_ctrlr *ctrlr)
	return ret;
}

static void invalidate_batch(struct rpmh_ctrlr *ctrlr)
{
	struct batch_cache_req *req, *tmp;
	unsigned long flags;

	spin_lock_irqsave(&ctrlr->cache_lock, flags);
	list_for_each_entry_safe(req, tmp, &ctrlr->batch_cache, list)
		kfree(req);
	INIT_LIST_HEAD(&ctrlr->batch_cache);
	spin_unlock_irqrestore(&ctrlr->cache_lock, flags);
}

/**
 * rpmh_write_batch: Write multiple sets of RPMH commands and wait for the
 * batch to finish.
@@ -457,13 +466,6 @@ int rpmh_flush(const struct device *dev)
		return 0;
	}

	/* Invalidate the TCSes first to avoid stale data */
	do {
		ret = rpmh_rsc_invalidate(ctrlr_to_drv(ctrlr));
	} while (ret == -EAGAIN);
	if (ret)
		return ret;

	/* First flush the cached batch requests */
	ret = flush_batch(ctrlr);
	if (ret)
@@ -495,25 +497,25 @@ int rpmh_flush(const struct device *dev)
EXPORT_SYMBOL(rpmh_flush);

/**
 * rpmh_invalidate: Invalidate sleep and wake sets in batch_cache
 * rpmh_invalidate: Invalidate all sleep and active sets
 * sets.
 *
 * @dev: The device making the request
 *
 * Invalidate the sleep and wake values in batch_cache.
 * Invalidate the sleep and active values in the TCS blocks.
 */
int rpmh_invalidate(const struct device *dev)
{
	struct rpmh_ctrlr *ctrlr = get_rpmh_ctrlr(dev);
	struct batch_cache_req *req, *tmp;
	unsigned long flags;
	int ret;

	spin_lock_irqsave(&ctrlr->cache_lock, flags);
	list_for_each_entry_safe(req, tmp, &ctrlr->batch_cache, list)
		kfree(req);
	INIT_LIST_HEAD(&ctrlr->batch_cache);
	invalidate_batch(ctrlr);
	ctrlr->dirty = true;
	spin_unlock_irqrestore(&ctrlr->cache_lock, flags);

	return 0;
	do {
		ret = rpmh_rsc_invalidate(ctrlr_to_drv(ctrlr));
	} while (ret == -EAGAIN);

	return ret;
}
EXPORT_SYMBOL(rpmh_invalidate);
+8 −16
Original line number Diff line number Diff line
@@ -1217,8 +1217,6 @@ static void dwc3_prepare_trbs(struct dwc3_ep *dep)
	}
}

static void dwc3_gadget_ep_cleanup_cancelled_requests(struct dwc3_ep *dep);

static int __dwc3_gadget_kick_transfer(struct dwc3_ep *dep)
{
	struct dwc3_gadget_ep_cmd_params params;
@@ -1255,20 +1253,14 @@ static int __dwc3_gadget_kick_transfer(struct dwc3_ep *dep)

	ret = dwc3_send_gadget_ep_cmd(dep, cmd, &params);
	if (ret < 0) {
		struct dwc3_request *tmp;

		if (ret == -EAGAIN)
			return ret;

		dwc3_stop_active_transfer(dep, true, true);

		list_for_each_entry_safe(req, tmp, &dep->started_list, list)
			dwc3_gadget_move_cancelled_request(req);

		/* If ep isn't started, then there's no end transfer pending */
		if (!(dep->flags & DWC3_EP_END_TRANSFER_PENDING))
			dwc3_gadget_ep_cleanup_cancelled_requests(dep);

		/*
		 * FIXME we need to iterate over the list of requests
		 * here and stop, unmap, free and del each of the linked
		 * requests instead of what we do now.
		 */
		if (req->trb)
			memset(req->trb, 0, sizeof(struct dwc3_trb));
		dwc3_gadget_del_and_unmap_request(dep, req, ret);
		return ret;
	}