arm/arm64: KVM: vgic: Improve handling of GICD_I{CS}PENDRn
authorChristoffer Dall <christoffer.dall@linaro.org>
Sat, 14 Jun 2014 19:54:51 +0000 (21:54 +0200)
committerChristoffer Dall <christoffer.dall@linaro.org>
Thu, 2 Oct 2014 15:19:20 +0000 (17:19 +0200)
commitfe8a7fe10d123135d9f8fee2eb0b0c14b31d609d
treee909a51b63afadd263a209ec235d977c7a05cfa4
parent520445af8ef7b1e8d17b692c0957b3802b90d98a
arm/arm64: KVM: vgic: Improve handling of GICD_I{CS}PENDRn

Writes to GICD_ISPENDRn and GICD_ICPENDRn are currently not handled
correctly for level-triggered interrupts.  The spec states that for
level-triggered interrupts, writes to the GICD_ISPENDRn activate the
output of a flip-flop which is in turn or'ed with the actual input
interrupt signal.  Correspondingly, writes to GICD_ICPENDRn simply
deactivates the output of that flip-flop, but does not (of course) affect
the external input signal.  Reads from GICC_IAR will also deactivate the
flip-flop output.

This requires us to track the state of the level-input separately from
the state in the flip-flop.  We therefore introduce two new variables on
the distributor struct to track these two states.  Astute readers may
notice that this is introducing more state than required (because an OR
of the two states gives you the pending state), but the remaining vgic
code uses the pending bitmap for optimized operations to figure out, at
the end of the day, if an interrupt is pending or not on the distributor
side.  Refactoring the code to consider the two state variables all the
places where we currently access the precomputed pending value, did not
look pretty.

Signed-off-by: Christoffer Dall <christoffer.dall@linaro.org>
(cherry picked from commit faa1b46c3e9f4d40359aee04ff275eea5f4cae3a)
Signed-off-by: Christoffer Dall <christoffer.dall@linaro.org>
include/kvm/arm_vgic.h
virt/kvm/arm/vgic.c