From: Kiran Gunda <kgunda@codeaurora.org>
To: Kiran Gunda <kgunda@codeaurora.org>,
Abhijeet Dharmapurikar <adharmap@codeaurora.org>,
Subbaraman Narayanamurthy <subbaram@codeaurora.org>,
Christophe JAILLET <christophe.jaillet@wanadoo.fr>,
David Collins <collinsd@codeaurora.org>,
linux-kernel@vger.kernel.org
Cc: linux-arm-msm@vger.kernel.org, adharmap@quicinc.com,
aghayal@qti.qualcomm.com, sboyd@codeaurora.org
Subject: [PATCH V1 04/15] spmi: pmic-arb: optimize table lookups
Date: Tue, 30 May 2017 18:08:52 +0530 [thread overview]
Message-ID: <1496147943-25822-5-git-send-email-kgunda@codeaurora.org> (raw)
In-Reply-To: <1496147943-25822-1-git-send-email-kgunda@codeaurora.org>
From: Abhijeet Dharmapurikar <adharmap@codeaurora.org>
The current driver uses a mix of radix tree and a fwd lookup
table to translate between apid and ppid. It is buggy and confusing.
Instead simply use a radix tree for v1 hardware and use the
forward lookup table for v2.
Signed-off-by: Abhijeet Dharmapurikar <adharmap@codeaurora.org>
Signed-off-by: Kiran Gunda <kgunda@codeaurora.org>
---
drivers/spmi/spmi-pmic-arb.c | 144 ++++++++++++++++++++++++++-----------------
1 file changed, 88 insertions(+), 56 deletions(-)
diff --git a/drivers/spmi/spmi-pmic-arb.c b/drivers/spmi/spmi-pmic-arb.c
index 7201611..6320f1f 100644
--- a/drivers/spmi/spmi-pmic-arb.c
+++ b/drivers/spmi/spmi-pmic-arb.c
@@ -164,6 +164,8 @@ struct spmi_pmic_arb {
* on v2 offset of SPMI_PIC_IRQ_CLEARn.
*/
struct pmic_arb_ver_ops {
+ int (*ppid_to_apid)(struct spmi_pmic_arb *pa, u8 sid, u16 addr,
+ u8 *apid);
int (*mode)(struct spmi_pmic_arb *dev, u8 sid, u16 addr,
mode_t *mode);
/* spmi commands (read_cmd, write_cmd, cmd) functionality */
@@ -657,42 +659,6 @@ struct spmi_pmic_arb_irq_spec {
unsigned irq:3;
};
-static int search_mapping_table(struct spmi_pmic_arb *pa,
- struct spmi_pmic_arb_irq_spec *spec,
- u8 *apid)
-{
- u16 ppid = spec->slave << 8 | spec->per;
- u32 *mapping_table = pa->mapping_table;
- int index = 0, i;
- u32 data;
-
- for (i = 0; i < SPMI_MAPPING_TABLE_TREE_DEPTH; ++i) {
- if (!test_and_set_bit(index, pa->mapping_table_valid))
- mapping_table[index] = readl_relaxed(pa->cnfg +
- SPMI_MAPPING_TABLE_REG(index));
-
- data = mapping_table[index];
-
- if (ppid & BIT(SPMI_MAPPING_BIT_INDEX(data))) {
- if (SPMI_MAPPING_BIT_IS_1_FLAG(data)) {
- index = SPMI_MAPPING_BIT_IS_1_RESULT(data);
- } else {
- *apid = SPMI_MAPPING_BIT_IS_1_RESULT(data);
- return 0;
- }
- } else {
- if (SPMI_MAPPING_BIT_IS_0_FLAG(data)) {
- index = SPMI_MAPPING_BIT_IS_0_RESULT(data);
- } else {
- *apid = SPMI_MAPPING_BIT_IS_0_RESULT(data);
- return 0;
- }
- }
- }
-
- return -ENODEV;
-}
-
static int qpnpint_irq_domain_dt_translate(struct irq_domain *d,
struct device_node *controller,
const u32 *intspec,
@@ -702,7 +668,7 @@ static int qpnpint_irq_domain_dt_translate(struct irq_domain *d,
{
struct spmi_pmic_arb *pa = d->host_data;
struct spmi_pmic_arb_irq_spec spec;
- int err;
+ int rc;
u8 apid;
dev_dbg(&pa->spmic->dev,
@@ -720,11 +686,14 @@ static int qpnpint_irq_domain_dt_translate(struct irq_domain *d,
spec.per = intspec[1];
spec.irq = intspec[2];
- err = search_mapping_table(pa, &spec, &apid);
- if (err)
- return err;
-
- pa->apid_to_ppid[apid] = spec.slave << 8 | spec.per;
+ rc = pa->ver_ops->ppid_to_apid(pa, intspec[0],
+ (intspec[1] << 8), &apid);
+ if (rc < 0) {
+ dev_err(&pa->spmic->dev,
+ "failed to xlate sid = 0x%x, periph = 0x%x, irq = %x rc = %d\n",
+ intspec[0], intspec[1], intspec[2], rc);
+ return rc;
+ }
/* Keep track of {max,min}_apid for bounding search during interrupt */
if (apid > pa->max_apid)
@@ -758,6 +727,54 @@ static int qpnpint_irq_domain_map(struct irq_domain *d,
}
static int
+pmic_arb_ppid_to_apid_v1(struct spmi_pmic_arb *pa, u8 sid, u16 addr, u8 *apid)
+{
+ u16 ppid = sid << 8 | ((addr >> 8) & 0xFF);
+ u32 *mapping_table = pa->mapping_table;
+ int index = 0, i;
+ u16 apid_valid;
+ u32 data;
+
+ apid_valid = pa->ppid_to_apid[ppid];
+ if (apid_valid & PMIC_ARB_CHAN_VALID) {
+ *apid = (apid_valid & ~PMIC_ARB_CHAN_VALID);
+ return 0;
+ }
+
+ for (i = 0; i < SPMI_MAPPING_TABLE_TREE_DEPTH; ++i) {
+ if (!test_and_set_bit(index, pa->mapping_table_valid))
+ mapping_table[index] = readl_relaxed(pa->cnfg +
+ SPMI_MAPPING_TABLE_REG(index));
+
+ data = mapping_table[index];
+
+ if (ppid & BIT(SPMI_MAPPING_BIT_INDEX(data))) {
+ if (SPMI_MAPPING_BIT_IS_1_FLAG(data)) {
+ index = SPMI_MAPPING_BIT_IS_1_RESULT(data);
+ } else {
+ *apid = SPMI_MAPPING_BIT_IS_1_RESULT(data);
+ pa->ppid_to_apid[ppid]
+ = *apid | PMIC_ARB_CHAN_VALID;
+ pa->apid_to_ppid[*apid] = ppid;
+ return 0;
+ }
+ } else {
+ if (SPMI_MAPPING_BIT_IS_0_FLAG(data)) {
+ index = SPMI_MAPPING_BIT_IS_0_RESULT(data);
+ } else {
+ *apid = SPMI_MAPPING_BIT_IS_0_RESULT(data);
+ pa->ppid_to_apid[ppid]
+ = *apid | PMIC_ARB_CHAN_VALID;
+ pa->apid_to_ppid[*apid] = ppid;
+ return 0;
+ }
+ }
+ }
+
+ return -ENODEV;
+}
+
+static int
pmic_arb_mode_v1(struct spmi_pmic_arb *pa, u8 sid, u16 addr, mode_t *mode)
{
*mode = S_IRUSR | S_IWUSR;
@@ -797,6 +814,7 @@ static u16 pmic_arb_find_apid(struct spmi_pmic_arb *pa, u16 ppid)
id = (regval >> 8) & PMIC_ARB_PPID_MASK;
pa->ppid_to_apid[id] = apid | PMIC_ARB_CHAN_VALID;
+ pa->apid_to_ppid[apid] = id;
if (id == ppid) {
apid |= PMIC_ARB_CHAN_VALID;
break;
@@ -809,20 +827,35 @@ static u16 pmic_arb_find_apid(struct spmi_pmic_arb *pa, u16 ppid)
static int
-pmic_arb_mode_v2(struct spmi_pmic_arb *pa, u8 sid, u16 addr, mode_t *mode)
+pmic_arb_ppid_to_apid_v2(struct spmi_pmic_arb *pa, u8 sid, u16 addr, u8 *apid)
{
u16 ppid = (sid << 8) | (addr >> 8);
- u16 apid;
- u8 owner;
+ u16 apid_valid;
- apid = pa->ppid_to_apid[ppid];
- if (!(apid & PMIC_ARB_CHAN_VALID))
+ apid_valid = pa->ppid_to_apid[ppid];
+ if (!(apid_valid & PMIC_ARB_CHAN_VALID))
+ apid_valid = pmic_arb_find_apid(pa, ppid);
+ if (!(apid_valid & PMIC_ARB_CHAN_VALID))
return -ENODEV;
+ *apid = (apid_valid & ~PMIC_ARB_CHAN_VALID);
+ return 0;
+}
+
+static int
+pmic_arb_mode_v2(struct spmi_pmic_arb *pa, u8 sid, u16 addr, mode_t *mode)
+{
+ u8 apid;
+ u8 owner;
+ int rc;
+
+ rc = pmic_arb_ppid_to_apid_v2(pa, sid, addr, &apid);
+ if (rc < 0)
+ return rc;
+
*mode = 0;
*mode |= S_IRUSR;
- apid &= ~PMIC_ARB_CHAN_VALID;
owner = pa->apid_to_owner[apid];
if (owner == pa->ee)
*mode |= S_IWUSR;
@@ -833,15 +866,12 @@ static u16 pmic_arb_find_apid(struct spmi_pmic_arb *pa, u16 ppid)
static int
pmic_arb_offset_v2(struct spmi_pmic_arb *pa, u8 sid, u16 addr, u32 *offset)
{
- u16 ppid = (sid << 8) | (addr >> 8);
- u16 apid;
+ u8 apid;
+ int rc;
- apid = pa->ppid_to_apid[ppid];
- if (!(apid & PMIC_ARB_CHAN_VALID))
- apid = pmic_arb_find_apid(pa, ppid);
- if (!(apid & PMIC_ARB_CHAN_VALID))
- return -ENODEV;
- apid &= ~PMIC_ARB_CHAN_VALID;
+ rc = pmic_arb_ppid_to_apid_v2(pa, sid, addr, &apid);
+ if (rc < 0)
+ return rc;
*offset = 0x1000 * pa->ee + 0x8000 * apid;
return 0;
@@ -898,6 +928,7 @@ static u32 pmic_arb_irq_clear_v2(u8 n)
}
static const struct pmic_arb_ver_ops pmic_arb_v1 = {
+ .ppid_to_apid = pmic_arb_ppid_to_apid_v1,
.mode = pmic_arb_mode_v1,
.non_data_cmd = pmic_arb_non_data_cmd_v1,
.offset = pmic_arb_offset_v1,
@@ -909,6 +940,7 @@ static u32 pmic_arb_irq_clear_v2(u8 n)
};
static const struct pmic_arb_ver_ops pmic_arb_v2 = {
+ .ppid_to_apid = pmic_arb_ppid_to_apid_v2,
.mode = pmic_arb_mode_v2,
.non_data_cmd = pmic_arb_non_data_cmd_v2,
.offset = pmic_arb_offset_v2,
--
QUALCOMM INDIA, on behalf of Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by The Linux Foundation
--
next prev parent reply other threads:[~2017-05-30 12:40 UTC|newest]
Thread overview: 60+ messages / expand[flat|nested] mbox.gz Atom feed top
2017-05-30 12:38 [PATCH V1 00/15]: support for spmi_pmic_arb v3/v5 and bug fixes Kiran Gunda
2017-05-30 12:38 ` [PATCH V1 01/15] spmi: pmic_arb: block access of invalid read and writes Kiran Gunda
2017-05-31 0:33 ` Stephen Boyd
2017-06-12 11:26 ` kgunda
2017-06-13 2:09 ` Stephen Boyd
2017-06-14 15:09 ` kgunda
2017-05-30 12:38 ` [PATCH V1 02/15] spmi: pmic-arb: rename spmi_pmic_arb_dev to spmi_pmic_arb Kiran Gunda
2017-05-31 0:46 ` Stephen Boyd
2017-06-01 16:11 ` kgunda
2017-06-02 18:29 ` Stephen Boyd
2017-06-05 6:28 ` kgunda
2017-05-30 12:38 ` [PATCH V1 03/15] spmi: pmic-arb: fix inconsistent use of apid and chan Kiran Gunda
2017-05-31 1:31 ` Stephen Boyd
2017-06-01 16:37 ` kgunda
2017-05-30 12:38 ` Kiran Gunda [this message]
2017-05-31 1:44 ` [PATCH V1 04/15] spmi: pmic-arb: optimize table lookups Stephen Boyd
2017-06-01 16:53 ` kgunda
2017-06-02 18:31 ` Stephen Boyd
2017-06-05 6:33 ` kgunda
2017-05-30 12:38 ` [PATCH V1 05/15] spmi: pmic-arb: cleanup unrequested irqs Kiran Gunda
2017-05-31 1:57 ` Stephen Boyd
2017-06-06 10:50 ` kgunda
2017-06-13 2:11 ` Stephen Boyd
2017-06-14 15:04 ` kgunda
2017-05-30 12:38 ` [PATCH V1 06/15] spmi: pmic-arb: fix missing interrupts Kiran Gunda
2017-05-31 2:00 ` Stephen Boyd
2017-06-01 17:06 ` kgunda
2017-05-30 12:38 ` [PATCH V1 07/15] spmi: pmic-arb: clear the latched status of the interrupt Kiran Gunda
2017-05-31 22:03 ` Stephen Boyd
2017-06-06 10:55 ` kgunda
2017-05-30 12:38 ` [PATCH V1 08/15] spmi: pmic_arb: use appropriate flow handler Kiran Gunda
2017-05-31 19:03 ` Stephen Boyd
2017-06-06 10:57 ` kgunda
2017-05-30 12:38 ` [PATCH V1 09/15] spmi: pmic-arb: check apid enabled before calling the handler Kiran Gunda
2017-05-31 20:39 ` Stephen Boyd
2017-06-14 15:38 ` kgunda
2017-06-16 21:11 ` Stephen Boyd
2017-06-21 5:02 ` kgunda
2017-05-30 12:38 ` [PATCH V1 10/15] spmi: pmic_arb: add support for PMIC bus arbiter v3 Kiran Gunda
2017-05-31 22:18 ` Stephen Boyd
2017-06-06 11:10 ` kgunda
2017-05-30 12:38 ` [PATCH V1 11/15] spmi: spmi-pmic-arb: enable the SPMI interrupt as a wakeup source Kiran Gunda
2017-05-31 17:13 ` Stephen Boyd
2017-06-08 11:30 ` kgunda
2017-05-30 12:39 ` [PATCH V1 12/15] spmi-pmic-arb: fix a possible null pointer dereference Kiran Gunda
2017-05-31 17:29 ` Stephen Boyd
2017-06-02 7:13 ` kgunda
2017-05-30 12:39 ` [PATCH V1 13/15] spmi: pmic-arb: add support for HW version 5 Kiran Gunda
2017-06-01 6:08 ` Stephen Boyd
2017-06-08 11:28 ` kgunda
2017-05-30 12:39 ` [PATCH V1 14/15] spmi: pmic-arb: do not ack and clear peripheral interrupts in cleanup_irq Kiran Gunda
2017-05-30 22:23 ` kbuild test robot
2017-05-31 17:53 ` Stephen Boyd
2017-06-02 7:26 ` kgunda
2017-06-06 11:27 ` kgunda
2017-06-13 2:10 ` Stephen Boyd
2017-07-18 11:53 ` kgunda
2017-05-30 12:39 ` [PATCH V1 15/15] spmi: pmic-arb: instantiate spmi_devices at arch_initcall Kiran Gunda
2017-05-31 22:07 ` Stephen Boyd
2017-07-18 11:49 ` kgunda
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1496147943-25822-5-git-send-email-kgunda@codeaurora.org \
--to=kgunda@codeaurora.org \
--cc=adharmap@codeaurora.org \
--cc=adharmap@quicinc.com \
--cc=aghayal@qti.qualcomm.com \
--cc=christophe.jaillet@wanadoo.fr \
--cc=collinsd@codeaurora.org \
--cc=linux-arm-msm@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=sboyd@codeaurora.org \
--cc=subbaram@codeaurora.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
Powered by JetHome