There is a possible race condition when debugfs files are concurrently
accessed by multiple threads. Fix this.
CRs-Fixed: 1106842
Change-Id: Ifd092143f428db3cf73c45ec4f0aaa96318ae165
Signed-off-by: ansharma <ansharma@codeaurora.org>
Currently, the SPMI debugfs entries support peek/poke functionality to
access PMIC register directly. This is a possible way to access the PMIC
and change some unexpected setting which is very dangerous. Add a flag
CONFIG_MSM_SPMI_DEBUGFS_RO to make the write operation through debugfs
optional, it can be defined if SPMI debugfs write is not desired.
CRs-Fixed: 1103178
Change-Id: Iedbbf57a4a24a18f755a8b304591cc151b10bd4c
Signed-off-by: Fenglin Wu <fenglinw@codeaurora.org>
Creating devices with the address of the container spmidev is not
indicative of the actual hardware device it represents.
Instead use an unique id to indicate the device it represents.
CRs-Fixed: 1024197
Change-Id: Id18e2a19f4fa1249901a3f275defa8f589270d69
Signed-off-by: Abhijeet Dharmapurikar <adharmap@codeaurora.org>
Signed-off-by: Sivasri Kumar Vanka <sivasri@codeaurora.org>
Creating devices with the address of the container spmidev is not
indicative of the actual hardware device it represents.
Instead use an unique id to indicate the device it represents.
CRs-Fixed: 1024197
Change-Id: Id18e2a19f4fa1249901a3f275defa8f589270d69
Signed-off-by: Abhijeet Dharmapurikar <adharmap@codeaurora.org>
Signed-off-by: Sivasri Kumar Vanka <sivasri@codeaurora.org>
This reverts commit de4413fe458e ("spmi: prevent showing the address of
spmidev")
The above change, although stops displaying the address, fails
to create devices with the same name on the same slave id. That
causes failures to register devices like qpnp-pin and qpnp-regulator
that have multiple instances on the same slave id.
CRs-Fixed: 1024197
Change-Id: I504e454a292c3b8aee9551ac593a8b54f52cf152
Signed-off-by: Abhijeet Dharmapurikar <adharmap@codeaurora.org>
Signed-off-by: Sivasri Kumar Vanka <sivasri@codeaurora.org>
Creating devices with the address of the container spmidev is not
indicative of the actual hardware device it represents.
Instead use the slave id to indicate the device it represents.
CRs-Fixed: 1024197
Change-Id: I254d89ff1058752e523eaae8e27976440858f541
Signed-off-by: Abhijeet Dharmapurikar <adharmap@codeaurora.org>
Signed-off-by: Sivasri Kumar Vanka <sivasri@codeaurora.org>
Currently the accesses to the peripheral data's irq enable count is
unprotected. The ACC bit in the spmi arbiter represents if any of the
eight interrupts in the peripheral is enabled. The counts are used to
ensure that the ACC bit for that peripheral is enabled when
the first interrupt in the peripheral is unmasked and is disabled when
the last interrupt in the peripheral is masked.
A race like this could happen.
Initial condition: Only two interrupts are enabled in the peripheral.
cpu0 cpu1
1. Mask 1st
2. Handle 1st
3. Unmask 1st. Sees that 2nd is
unmasked
3. Mask 2nd. Disables ACC
4. Handle 2nd
5. Unmask 1st continues. Skips
enabling ACC since it sees that
this is not the first interrupt
being unmasked. Although it is,
since 2nd interrupt was masked
after enabled counts were read.
6. Unmask 2nd, sees that 1st is
enabled and skips enabling ACC
bit
7. After this, the ACC bit for that peripheral remains disabled even when
interrupts are in unmasked state at the peripheral.
Fix this by ensuring 3 and 5 happen atomically, i.e. the reading of the
masked state and the action of enabling/disabling ACC bit should be
atomic.
CRs-Fixed: 968643
Change-Id: I02cb7b3350d73c9b24b6445a5008f52cbc32cecf
Signed-off-by: Abhijeet Dharmapurikar <adharmap@codeaurora.org>
The default of maximum number of interrupt should be
the maximum number of all relevant targets.
Change-Id: I20f0e43d06dd51dc84cff5f9c425307dd1c3e715
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
Add the max pmic arb supported channel, interrupts as part
of spmi controller to support varying max channel and
interrupts from target to target with same arbiter version.
Change-Id: I96f146f0c0d2d9a4442a38ca94f131e52f862205
Signed-off-by: Alok Chauhan <alokc@codeaurora.org>
As a workaround for interrupt that got stack at boot
time and could not be cleared by APPS, the driver reads
the interrupt accumulator at probe time and later
masks the corresponding interrupt, thinking that they
are stack.
However, there are valid cases where an interrupt that
is owned by APSS fire at boot time and seen by the probe.
This patch unmasks bits of interrupts that are present
in probe time in case they owned by APSS.
Change-Id: I534e69ee6cf6cc113101cc89823b1784821b4a8b
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
Due to some faulty HW/SW interaction during boot loader
time, the first accumulator bit may be incorectly set.
When the peripheral represented by this bit is not
owned by the application processor, it stays set forever,
confusing the interrupt controller to think that it
get interrupted by that peripheral when it isn't.
To amend this problem, we read the accumulator value
at boot time and compare that value to the accumulator
when new interrupt is handled. If a bit reperesenting
a peripheral was set at probe time, then it is ignored.
Change-Id: Iab3d70d6c63520ac7be1e77aba113cf5f46ec003
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
Dump the stack-trace and the APID to PPID mapping when a client
issue a bad request.
Bad requests include: registering to an unmapped peripheral
interrupt, and attempting to map an already mapped APID.
The stack-trace dump helps in findind the offending caller.
The APID to PPID mapping-dump lists all the correct mapping
known to the driver. This mapping dump helps in understanding
why the client's request is bad.
Change-Id: Id0ce7064767b0406252c30ba93b916473b269b35
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
SPMI protocal irq status register bits are sticky bits which
may show the other EEs status. so read it before starting of
transaction and dump it at the time of issue to get exact
cause of issue.
Change-Id: I2d2faef1a28ac6827cecc53984a26a4fceaff4eb
Signed-off-by: Alok Chauhan <alokc@codeaurora.org>
Add additional information on error return code and
log dump. Introduce a new return code for transient
failures and add to log dump information such as:
slave-id, address, op-code, byte-count, data buffer
content, and values of relevant registers.
Change-Id: I6ac785cf78a84a448f96057b93c94df0b72e39ce
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
Signed-off-by: Alok Chauhan <alokc@codeaurora.org>
Two registers which are used for debugging have different offset
in pmic-arbiter versions 2.2 vs earlier versiosn.
Change-Id: If072e280c2207b07b637b9ed048fd350c541e07d
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
Demote an error msg to dbg one to keep log clean.
Change-Id: Ia704c6ead529805dbc2f66da844a1e86be198a7d
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
Add support for spmi-arb channel I/O protection scheme.
This scheme allows access in per-channel resolution
and each PMIC peripheral has its own channel.
Change-Id: I2c1b8c9fd0c15f18b30513ff10d340c72ba1c2a6
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
Signed-off-by: Alok Chauhan <alokc@codeaurora.org>
Signed-off-by: Kiran Gunda <kgunda@codeaurora.org>
Use pointer and size_t rather then size dependent code
and avoid use of casting.
Change-Id: Ie901c75ff99730830268f385a415b1199a3720a0
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
The original calculation of spmi command in pmic_arb_cmd()function
has wrong opcode bits value.
Change-Id: Ifdddaac4d4a58b71dca8307af002435333af0910
Signed-off-by: Wu Fenglin <fenglinw@codeaurora.org>
The qpnp-int.h header file resides under mach-msm's include directory.
qpnp-int is a irq controller driver and so should reside in
include/linux/irqchip. Move it there.
Change-Id: Ic3e427c44a15132c4d909eb2d4d688634995d30f
Signed-off-by: Abhijeet Dharmapurikar <adharmap@codeaurora.org>
Code does not compile with debugfs disabled. Fix this.
Change-Id: I11fa09401f29e9f2fb65d19668cae455253f6355
Signed-off-by: Olav Haugan <ohaugan@codeaurora.org>
Dump values of core HW debugging registers on an error
in transfer. These values are valuable for root cause
analysis.
Change-Id: I206c4a2232f44480220e795a8d8e946d8352ba19
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
PMIC interrupts each have an internal latched status bit which is
not visible from any register. This status bit is set as soon as
the conditions specified in the interrupt type and polarity
registers are met even if the interrupt is not enabled. When it
is set, nothing else changes within the PMIC and no interrupt
notification packets are sent. If the internal latched status
bit is set when an interrupt is enabled, then the value is
immediately propagated into the interrupt latched status register
and an interrupt notification packet is sent out from the PMIC
over SPMI.
This PMIC hardware behavior can lead to a situation where the
handler for a level triggered interrupt is called immediately
after enable_irq() is called even though the interrupt physically
triggered while it was disabled within the genirq framework.
This situation takes place if the the interrupt fires twice after
calling disable_irq(). The first time it fires, the level flow
handler will mask and disregard it. Unfortunately, the second
time it fires, the internal latched status bit is set within the
PMIC and no further notification is received. When enable_irq()
is called later, the interrupt is unmasked (enabled in the PMIC)
which results in the PMIC immediately sending an interrupt
notification packet out over SPMI. This breaks the semantics
of level triggered interrupts within the genirq framework since
they should be completely ignored while disabled.
The PMIC internal latched status behavior also affects how
interrupts are treated during suspend. While entering suspend,
all interrupts not specified as wakeup mode are masked. Upon
resume, these interrupts are unmasked. Thus if any of the
non-wakeup PMIC interrupts fired while the system was suspended,
then the PMIC will send interrupt notification packets out via
SPMI as soon as they are unmasked during resume. This behavior
violates genirq semantics as well since non-wakeup interrupts
should be completely ignored during suspend.
Modify the qpnpint_irq_unmask() function so that the interrupt
latched status clear register is written immediately before the
interrupt enable register. This clears the internal latched
status bit of the interrupt so that it cannot trigger spuriously
immediately upon being enabled.
Also, before writing these registers, check if the interrupt is
already enabled within the PMIC. If it is enabled, then no
further register writes are required. This condition check
ensures that a valid latched status register bit is not cleared
until it is properly handled.
Change-Id: Ib99a384bfeba440a4ad91cd0e16e8f62e4352f28
Signed-off-by: David Collins <collinsd@codeaurora.org>
The driver uses level flow handler for both edge and level trigger types.
This creates a window where an edge triggered interrupt can be missed.
The following explanation applies for kernel prior to commit
d4dc0f90d2 ("genirq: Allow
check_wakeup_irqs to notice level-triggered interrupts").
The edge flow handler sets the IRQS_PENDING flag if that interrupt was
disabled (IRQD_DISABLED flag set) and the genirq framework uses this
flag to:
1. Resend edge triggered interrupts
2. Abort suspend if it were a wakeup interrupt
The level flow handler does not set this flag as it is expected that a
level triggered interrupt will be active unless handled.
If the level flow handler is used for edge triggered interrupts, then we
miss the opportunity to set IRQS_PENDING flag and so we could miss
resending the interrupt or aborting suspend if the edge triggered
interrupt fires while it is disabled.
Change in commit d4dc0f90d2 ("genirq:
Allow check_wakeup_irqs to notice level-triggered interrupts")
makes level flow handler set the IRQS_PENDING flag and solves this issue.
However, the qpnp-int driver is intended to be run on kernels without this
change.
Hence update the code to use edge flow handler for edge triggered
interrupts.
Change-Id: I9a99ecd1366a614fc372743f150e5a6d508db786
Signed-off-by: Abhijeet Dharmapurikar <adharmap@codeaurora.org>
Add a function into the qpnp-int driver named qpnpint_irq_ack()
which performs the single step required to acknowledge a PMIC
interrupt: clearing the latched status register bit for the
interrupt. At the same time modify the qpnpint_irq_mask_ack()
function so that it simply calls qpnpint_irq_mask() and
qpnpint_irq_ack(). This eliminates redundant code present in
both qpnpint_irq_mask() and qpnpint_irq_mask_ack().
An irq_ack() callback is required in order to utilize the
handle_edge_irq flow handler.
Change-Id: Iacb0edf01fe82f358bb6200cef1b905584eb29e5
Signed-off-by: David Collins <collinsd@codeaurora.org>
Compilation error is seen in spmi_dfs_add_controller
function when debug fs is disabled.
In this patch this function is defined as static
inline to remove this error.
CRs-Fixed: 555022
Change-Id: I66ac9ca9eeb1e25c68c9deff665258f4e036a678
Signed-off-by: Kiran Gunda <kgunda@codeaurora.org>
Add code to print the interrupts that woke up the device from
resume. Use syscore resume operation to print the interrupt
number.
Since most of the systems have only one arbiter control, it is
reasonable to create a file scoped PMIC arbiter pointer for the
syscore resume operation.
CRs-Fixed: 502334
Change-Id: Ib4be9273633a70527a853fb5792543d66c8d2303
Signed-off-by: Abhijeet Dharmapurikar <adharmap@codeaurora.org>
The current driver calls arbiter ops when an interrupt is being
masked or unmasked. However, the arbiter ops were meant to be
called if all interrupts for a peripheral were disabled or
the first enable happens. The driver ends up masking the peripheral
(i.e. all the interrupts in that peripheral) if any one interrupt in
that peripheral is masked. There could be other interrupts enabled
which will not trigger after this.
Fix this by changing the driver to call the arbiter ops only
when all the interrupts in the peripheral are disabled or when
the first enable of an interrupt in that peripheral happens.
Also take this opportunity to clean up the arbiter ops calls to
specifically write to the INT_ACC_ENABLE bit instead of entire
register as specified in the data sheets.
Change-Id: If5835ac125f59d2964242758aa9f9ef145000af7
Signed-off-by: Abhijeet Dharmapurikar <adharmap@codeaurora.org>
Replace the BUG_ON() check with a NULL pointer check and verify that
the controller type is set appropriately. This prevents a system crash
due to invalid input.
Change-Id: I858980ad54ba0d764219049a20b4ca3e9b77f72e
Signed-off-by: Kenneth Heitke <kheitke@codeaurora.org>
This patch is to fix KW errors in drivers. It's
neccessary to check NULL pointer before dereferencing it.
There're 4 issues related to it in qpnp-int.c and
qpnp-pin.c. Fix them by checking before.
CRs-Fixed: 505322
Change-Id: I2f82d1b24c219ef7e6b0977091fc353dac579cbc
Signed-off-by: Zhenhua Huang <zhenhuah@codeaurora.org>
The del_controller function is required to release any client device
resources as well as the debugfs entries. This patch adds that
functionality.
Change-Id: I91c6b840acfe002f096570cbe1867b302c475e60
Signed-off-by: Kenneth Heitke <kheitke@codeaurora.org>
Registered controllers are maintained in a linked list as well as in an
idr (ID management) object which is redundant. This patch removes the
linked list and just uses the idr to manage the controllers.
Change-Id: Ief36e6870b036304e34d4eec4e22e50c6c028d43
Signed-off-by: Kenneth Heitke <kheitke@codeaurora.org>
Implement irq_chip->irq_read_line() callback by returning the
status value read from a peripheral's INT_REG_RT_STS register.
Change-Id: I4c2f54bac497f64efee51ba524db8d0642f2f3d1
Signed-off-by: Jack Pham <jackp@codeaurora.org>
Upon device removal, we should take care to unregister the
controller from qpnp-int so that qpnp-int doesn't make bad
assumptions that the controller is still there.
Change-Id: I06f5994d5f8c457c178edc9b68d92855f48535e3
Signed-off-by: Michael Bohan <mbohan@codeaurora.org>
Devices using SPMI interrupts that map their interrupts before
the MSM SPMI Arbiter has probed will not be able to receive
interrupts. This is since the arbiter callback structure hasn't
been populated due to the missing registration, and thus we
end up unmasking / masking for the interrupt in question on the
arbiter with uninitialized 'priv_data'.
Since the order in which devices are mapped is arbitrary and
nothing we have control over, handle this case by verifying that
each IRQ has been registered with the arbiter before issuing a
mask / unmask request. If it's not registered, then register it
while servicing the interrupt. This amounts to additional latency
when masking / unmasking for the first time, only for
interrupts that are mapped before the SPMI PMIC Arbiter is
registered.
Note that this patch makes no attempt to support devices *using*
interrupts before the SPMI PMIC Arbiter has probed. That is to
say, it's permissible to map an interrupt early, but calling
request_irq() or any other function that results in a qpnp-int
unmask / mask callback being invoked before the arbiter probes
is forbidden. The bus is a very real dependency to servicing
interrupts, and so it's impossible to support this.
Also add better error detection and handling, and introduce a
complementary controller unregistration function for proper
cleanup.
Change-Id: Iba6086887ad81779fec15fa05379b92215f1623b
Signed-off-by: Michael Bohan <mbohan@codeaurora.org>
Add 'mapping' file to the SPMI debugfs which will display the mapping
of PMIC peripheral identifiers (PPID) to the internal identifier (APID).
This mapping is useful to understand what peripheral have registered
for interrupts and how they are mapped in the PMIC Arbiter interrupt
registers.
Change-Id: I236c88268459143e920106238af1ff4e4cec0401
Signed-off-by: Kenneth Heitke <kheitke@codeaurora.org>
Add API function 'spmi_dfs_create_file' for SPMI controller drivers to
create their own implementation specific files under the SPMI debugfs
directory.
Change-Id: Ib4d0557333371a2a29b6dc6ae6ca6a41ebf13c34
Signed-off-by: Kenneth Heitke <kheitke@codeaurora.org>
The APID/PPID mapping data is stored in the device tree and allows the
PMIC Arbiter driver to map the 8-bit hardware identifiers back to the
12-bit identifiers (slave id + peripheral id). This mapping data is
subject to change (and does change for different targets) and therefore
adds maintenance overhead. The same information can be determined at
run-time by using the PMIC Arbiter mapping table to determine the APID
from the PPID at the time that interrupts are being registered.
Therefore, add support to read from the PMIC Arbiter hardware mapping
table.
Change-Id: I72c84a7503f640bc4a9ea7e2dfffb31e472b8a6b
Signed-off-by: Kenneth Heitke <kheitke@codeaurora.org>
It is considered a bug to insert into a radix tree with
preemption enabled. Use radix_tree_preload() to preload resources
for the radix tree and disable preemption.
Change-Id: If518ebfc78630a72e35b6fbd71f4ff9119dc8b0b
Signed-off-by: Michael Bohan <mbohan@codeaurora.org>
Improve readability and maintainability of the PMIC-arbiter
driver, by reading platform memory resources from device tree
by name rather then by index.
Change-Id: I10651e474210f0859d517d2b60fa04acdf77c9a4
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
Signed-off-by: Kenneth Heitke <kheitke@codeaurora.org>
Add user space interface to the SPMI kernel framework that enables
master-read and master-write transactions.
Each SPMI controller is represented as a file under the root directory
of SPMI debug-fs. For each controller, 'address', 'count', and 'data'
files are added. The user may configure the transaction via the
respective files and invoke a master read transaction by reading from
the 'data' file, and a master write transaction by writing a string of
decimal or hexadecimal byte size values to the 'data' file.
Change-Id: I3e760be7796bfb9aa15c8ab758ff616a72240176
Signed-off-by: Gilad Avidov <gavidov@codeaurora.org>
Signed-off-by: Kenneth Heitke <kheitke@codeaurora.org>