linux-arm-kernel.lists.infradead.org archive mirror
 help / color / mirror / Atom feed
From: Hector Martin <marcan@marcan.st>
To: Will Deacon <will@kernel.org>
Cc: linux-arm-kernel@lists.infradead.org,
	Marc Zyngier <maz@kernel.org>, Rob Herring <robh@kernel.org>,
	Arnd Bergmann <arnd@kernel.org>, Olof Johansson <olof@lixom.net>,
	Krzysztof Kozlowski <krzk@kernel.org>,
	Mark Kettenis <mark.kettenis@xs4all.nl>,
	Tony Lindgren <tony@atomide.com>,
	Mohamed Mediouni <mohamed.mediouni@caramail.com>,
	Stan Skowronek <stan@corellium.com>,
	Alexander Graf <graf@amazon.com>,
	Linus Walleij <linus.walleij@linaro.org>,
	Mark Rutland <mark.rutland@arm.com>,
	Andy Shevchenko <andy.shevchenko@gmail.com>,
	Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
	Jonathan Corbet <corbet@lwn.net>,
	Catalin Marinas <catalin.marinas@arm.com>,
	Christoph Hellwig <hch@infradead.org>,
	"David S. Miller" <davem@davemloft.net>,
	devicetree@vger.kernel.org, linux-serial@vger.kernel.org,
	linux-doc@vger.kernel.org, linux-samsung-soc@vger.kernel.org,
	linux-arch@vger.kernel.org, linux-kernel@vger.kernel.org
Subject: Re: [RFT PATCH v3 16/27] irqchip/apple-aic: Add support for the Apple Interrupt Controller
Date: Fri, 26 Mar 2021 17:58:15 +0900	[thread overview]
Message-ID: <3564ed98-6ad6-7ddd-01d2-36d7f5af90e0@marcan.st> (raw)
In-Reply-To: <20210324195742.GA13474@willie-the-truck>

Hi Will,

No worries, I was busy until a couple days ago anyway.

On 25/03/2021 04.57, Will Deacon wrote:
>> +#define pr_fmt(fmt) "%s: " fmt, __func__
> 
> General nit: but I suspect many of the prints in here probably want to be
> using the *_ratelimited variants.

You're right, everything complaining about spurious/unsupported stuff is 
probably safer rate-limited. I also made them all pr_err_ratelimited, 
since nothing should be trying to use that hardware before we get around 
to supporting it in this driver.

>> +static void __exception_irq_entry aic_handle_irq(struct pt_regs *regs)
>> +{
>> +	struct aic_irq_chip *ic = aic_irqc;
>> +	u32 event, type, irq;
>> +
>> +	do {
>> +		/*
>> +		 * We cannot use a relaxed read here, as DMA needs to be
>> +		 * ordered with respect to the IRQ firing.
>> +		 */
> 
> I think this could be a bit clearer: the readl() doesn't order any DMA
> accesses, but instead means that subsequent reads by the CPU are ordered
> (which may be from a buffer which was DMA'd to) are ordered after the
> read of the MMIO register.

Good point, reworded it for v4:

/*
  * We cannot use a relaxed read here, as reads from DMA buffers
  * need to be ordered after the IRQ fires.
  */

> 
>> +		event = readl(ic->base + AIC_EVENT);
>> +		type = FIELD_GET(AIC_EVENT_TYPE, event);
>> +		irq = FIELD_GET(AIC_EVENT_NUM, event);
>> +
>> +		if (type == AIC_EVENT_TYPE_HW)
>> +			handle_domain_irq(aic_irqc->hw_domain, irq, regs);
>> +		else if (type == AIC_EVENT_TYPE_IPI && irq == 1)
>> +			aic_handle_ipi(regs);
>> +		else if (event != 0)
>> +			pr_err("Unknown IRQ event %d, %d\n", type, irq);
>> +	} while (event);
>> +
>> +	/*
>> +	 * vGIC maintenance interrupts end up here too, so we need to check
>> +	 * for them separately. Just report and disable vGIC for now, until
>> +	 * we implement this properly.
>> +	 */
>> +	if ((read_sysreg_s(SYS_ICH_HCR_EL2) & ICH_HCR_EN) &&
>> +		read_sysreg_s(SYS_ICH_MISR_EL2) != 0) {
>> +		pr_err("vGIC IRQ fired, disabling.\n");
>> +		sysreg_clear_set_s(SYS_ICH_HCR_EL2, ICH_HCR_EN, 0);
>> +	}
> 
> What prevents all these system register accesses being speculated up before
> the handler?

Nothing, but that's not a problem, is it? If the condition is met, it 
means the vGIC IRQ *is* firing and needs clearing. We don't particularly 
care if this happens before, after, or during the rest of the IRQ handling.

I changed the message to this, because we actually should never hit this 
path with correctly-working KVM code (it takes care of it before this 
handler runs):

pr_err_ratelimited("vGIC IRQ fired and not handled by KVM, disabling.\n");

>> +static struct irq_chip aic_chip = {
>> +	.name = "AIC",
>> +	.irq_mask = aic_irq_mask,
>> +	.irq_unmask = aic_irq_unmask,
> 
> I know these are driven by the higher-level irq chip code, but I'm a bit
> confused as to what provides ordering if, e.g. something ends up calling:
> 
> 	aic_chip.irq_mask(d);
> 	...
> 	aic_chip.irq_unmask(d);
> 
> I can't see any ISBs in here and they're writing to two different registers,
> so can we end up with the IRQ masked after this sequence?

Wait, aren't MMIO writes to the same peripheral using device-nGnRnE 
memory modes always ordered with respect to each other? I thought the 
_relaxed versions were only trouble when mixed with memory/DMA buffers, 
and MMIO for any given peripheral always takes effect in program order.

>> +static void aic_ipi_mask(struct irq_data *d)
>> +{
>> +	u32 irq_bit = BIT(irqd_to_hwirq(d));
>> +	int this_cpu = smp_processor_id();
>> +
>> +	/* No specific ordering requirements needed here. */
>> +	atomic_andnot(irq_bit, &aic_vipi_enable[this_cpu]);
>> +}
> 
> Why not use a per-cpu variable here instead of an array of atomics? The pcpu
> API has things for atomic updates (e.g. or, and, xchg).

One CPU still needs to be able to mutate the flags of another CPU to 
fire an IPI; AIUI the per-cpu ops are *not* atomic for concurrent access 
by multiple CPUs, and in fact there is no API for that, only for "this CPU".

>> +static void aic_ipi_unmask(struct irq_data *d)
>> +{
>> +	struct aic_irq_chip *ic = irq_data_get_irq_chip_data(d);
>> +	u32 irq_bit = BIT(irqd_to_hwirq(d));
>> +	int this_cpu = smp_processor_id();
>> +
>> +	/*
>> +	 * This must complete before the atomic_read_acquire() below to avoid
>> +	 * racing aic_ipi_send_mask(). Use a dummy fetch op with release
>> +	 * semantics for this. This is arch-specific: ARMv8 B2.3.3 specifies
>> +	 * that writes with Release semantics are Barrier-ordered-before reads
>> +	 * with Acquire semantics, even though the Linux arch-independent
>> +	 * definition of these atomic ops does not.
>> +	 */
> 
> I think a more idiomatic (and portable) way to do this would be to use
> the relaxed accessors, but with smp_mb__after_atomic() between them. Do you
> have a good reason for _not_ doing it like that?

Not particularly, other than symmetry with the case below.

>> +		/*
>> +		 * This sequence is the mirror of the one in aic_ipi_unmask();
>> +		 * see the comment there. Additionally, release semantics
>> +		 * ensure that the vIPI flag set is ordered after any shared
>> +		 * memory accesses that precede it. This therefore also pairs
>> +		 * with the atomic_fetch_andnot in aic_handle_ipi().
>> +		 */
>> +		pending = atomic_fetch_or_release(irq_bit, &aic_vipi_flag[cpu]);

We do need the return data here, and the release semantics (or another 
barrier before it). But the read below can be made relaxed and a barrier 
used instead, and then the same patern above except with a plain 
atomic_or().

>> +		if (!(pending & irq_bit) && (atomic_read_acquire(&aic_vipi_enable[cpu]) & irq_bit))
>> +			send |= AIC_IPI_SEND_CPU(cpu);
>> +	}

[...]

>> +	/*
>> +	 * Clear the IPIs we are about to handle. This pairs with the
>> +	 * atomic_fetch_or_release() in aic_ipi_send_mask(), and needs to be
>> +	 * ordered after the aic_ic_write() above (to avoid dropping vIPIs) and
>> +	 * before IPI handling code (to avoid races handling vIPIs before they
>> +	 * are signaled). The former is taken care of by the release semantics
>> +	 * of the write portion, while the latter is taken care of by the
>> +	 * acquire semantics of the read portion.
>> +	 */
>> +	firing = atomic_fetch_andnot(enabled, &aic_vipi_flag[this_cpu]) & enabled;
> 
> Does this also need to be ordered after the Ack? For example, if we have
> something like:
> 
> CPU 0						CPU 1
> 						<some other IPI>
> aic_ipi_send_mask()
> 						atomic_fetch_andnot(flag)
> 	atomic_fetch_or_release(flag)
> 	aic_ic_write(AIC_IPI_SEND)
> 						aic_ic_write(AIC_IPI_ACK)
> 
> sorry if it's a stupid question, I'm just not sure about the cases in which
> the hardware will pend things for you.

It is ordered, right? As the comment says, it "needs to be ordered after 
the aic_ic_write() above". atomic_fetch_andnot() is *supposed* to be 
fully ordered and that should include against the writel_relaxed() on 
AIC_IPI_FLAG. On ARM it turns out it's not quite fully ordered, but the 
acquire semantics of the read half are sufficient for this case, as they 
guarantee the flags are always read after the FIQ has been ACKed.

Cheeers,
-- 
Hector Martin (marcan@marcan.st)
Public Key: https://mrcn.st/pub

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

  reply	other threads:[~2021-03-26  9:00 UTC|newest]

Thread overview: 139+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-03-04 21:38 [RFT PATCH v3 00/27] Apple M1 SoC platform bring-up Hector Martin
2021-03-04 21:38 ` [RFT PATCH v3 01/27] arm64: Cope with CPUs stuck in VHE mode Hector Martin
2021-03-24 18:05   ` Will Deacon
2021-03-24 20:00     ` Marc Zyngier
2021-03-26  7:54       ` Hector Martin
2021-03-04 21:38 ` [RFT PATCH v3 02/27] dt-bindings: vendor-prefixes: Add apple prefix Hector Martin
2021-03-08 20:26   ` Rob Herring
2021-03-04 21:38 ` [RFT PATCH v3 03/27] dt-bindings: arm: apple: Add bindings for Apple ARM platforms Hector Martin
2021-03-05 10:16   ` Linus Walleij
2021-03-08 20:27   ` Rob Herring
2021-03-04 21:38 ` [RFT PATCH v3 04/27] dt-bindings: arm: cpus: Add apple, firestorm & icestorm compatibles Hector Martin
2021-03-08 20:27   ` Rob Herring
2021-03-04 21:38 ` [RFT PATCH v3 05/27] arm64: cputype: Add CPU implementor & types for the Apple M1 cores Hector Martin
2021-03-24 18:13   ` Will Deacon
2021-03-04 21:38 ` [RFT PATCH v3 06/27] dt-bindings: timer: arm, arch_timer: Add interrupt-names support Hector Martin
2021-03-05 10:18   ` [RFT PATCH v3 06/27] dt-bindings: timer: arm,arch_timer: " Linus Walleij
2021-03-08 11:12   ` [RFT PATCH v3 06/27] dt-bindings: timer: arm, arch_timer: " Marc Zyngier
2021-03-08 17:14   ` [RFT PATCH v3 06/27] dt-bindings: timer: arm,arch_timer: " Tony Lindgren
2021-03-08 20:38   ` Rob Herring
2021-03-08 22:42     ` [RFT PATCH v3 06/27] dt-bindings: timer: arm, arch_timer: " Marc Zyngier
2021-03-09 16:11       ` [RFT PATCH v3 06/27] dt-bindings: timer: arm,arch_timer: " Rob Herring
2021-03-09 20:28         ` Hector Martin
2021-03-04 21:38 ` [RFT PATCH v3 07/27] arm64: arch_timer: implement support for interrupt-names Hector Martin
2021-03-05 10:19   ` Linus Walleij
2021-03-08 11:13   ` Marc Zyngier
2021-03-04 21:38 ` [RFT PATCH v3 08/27] asm-generic/io.h: Add a non-posted variant of ioremap() Hector Martin
2021-03-05 14:45   ` Andy Shevchenko
2021-03-05 15:19     ` Hector Martin
2021-03-08 11:20   ` Marc Zyngier
2021-03-24 18:12   ` Will Deacon
2021-03-24 19:09     ` Arnd Bergmann
2021-03-25 14:07       ` Hector Martin
2021-03-25 14:49         ` Will Deacon
2021-03-04 21:38 ` [RFT PATCH v3 09/27] docs: driver-api: device-io: Document I/O access functions Hector Martin
2021-03-05 10:22   ` Linus Walleij
2021-03-04 21:38 ` [RFT PATCH v3 10/27] docs: driver-api: device-io: Document ioremap() variants & access funcs Hector Martin
2021-03-05 10:25   ` Linus Walleij
2021-03-05 15:09     ` Andy Shevchenko
2021-03-05 15:51       ` Arnd Bergmann
2021-03-09 20:29         ` Hector Martin
2021-03-04 21:38 ` [RFT PATCH v3 11/27] arm64: Implement ioremap_np() to map MMIO as nGnRnE Hector Martin
2021-03-08 11:22   ` Marc Zyngier
2021-03-24 18:18   ` Will Deacon
2021-03-04 21:38 ` [RFT PATCH v3 12/27] of/address: Add infrastructure to declare MMIO as non-posted Hector Martin
2021-03-05 10:28   ` Linus Walleij
2021-03-05 15:13   ` Andy Shevchenko
2021-03-05 15:55     ` Hector Martin
2021-03-05 16:08       ` Andy Shevchenko
2021-03-05 16:43         ` Arnd Bergmann
2021-03-05 17:19           ` Hector Martin
2021-03-05 16:05     ` Rob Herring
2021-03-05 17:39   ` Rob Herring
2021-03-05 18:18     ` Hector Martin
2021-03-05 21:17       ` Arnd Bergmann
2021-03-08 15:56         ` Rob Herring
2021-03-08 20:29           ` Arnd Bergmann
2021-03-08 21:13             ` Rob Herring
2021-03-08 21:56               ` Arnd Bergmann
2021-03-09 15:48                 ` Rob Herring
2021-03-09 20:23                   ` Hector Martin
2021-03-09 22:06                     ` Rob Herring
2021-03-10  8:26                       ` Hector Martin
2021-03-10 17:01                         ` Rob Herring
2021-03-11  9:12                           ` Arnd Bergmann
2021-03-11 12:11                             ` Hector Martin
2021-03-11 13:35                               ` Arnd Bergmann
2021-03-11 16:07                             ` Rob Herring
2021-03-11 16:48                               ` Arnd Bergmann
2021-03-11 18:10                                 ` Rob Herring
2021-03-12 10:20                                   ` Arnd Bergmann
2021-03-09 11:14               ` Linus Walleij
2021-03-09 12:41                 ` Arnd Bergmann
2021-03-09 15:40                   ` Linus Walleij
2021-03-04 21:38 ` [RFT PATCH v3 13/27] arm64: Add Apple vendor-specific system registers Hector Martin
2021-03-24 18:38   ` Will Deacon
2021-03-24 18:59     ` Mark Rutland
2021-03-24 19:04       ` Will Deacon
2021-03-26  6:23         ` Hector Martin
2021-03-04 21:38 ` [RFT PATCH v3 14/27] arm64: move ICH_ sysreg bits from arm-gic-v3.h to sysreg.h Hector Martin
2021-03-08 11:39   ` Marc Zyngier
2021-03-24 18:23   ` Will Deacon
2021-03-04 21:38 ` [RFT PATCH v3 15/27] dt-bindings: interrupt-controller: Add DT bindings for apple-aic Hector Martin
2021-03-08 21:16   ` Rob Herring
2021-03-04 21:38 ` [RFT PATCH v3 16/27] irqchip/apple-aic: Add support for the Apple Interrupt Controller Hector Martin
2021-03-05 15:05   ` Andy Shevchenko
2021-03-08 11:50     ` Marc Zyngier
2021-03-08 12:02       ` Andy Shevchenko
2021-03-26 13:40     ` Hector Martin
2021-03-08 13:31   ` Marc Zyngier
2021-03-26  7:57     ` Hector Martin
2021-03-24 19:57   ` Will Deacon
2021-03-26  8:58     ` Hector Martin [this message]
2021-03-29 12:04       ` Will Deacon
2021-04-01 13:16         ` Hector Martin
2021-03-04 21:38 ` [RFT PATCH v3 17/27] arm64: Kconfig: Introduce CONFIG_ARCH_APPLE Hector Martin
2021-03-08 15:35   ` Marc Zyngier
2021-03-09 20:30     ` Hector Martin
2021-03-04 21:38 ` [RFT PATCH v3 18/27] tty: serial: samsung_tty: Separate S3C64XX ops structure Hector Martin
2021-03-05 10:30   ` Krzysztof Kozlowski
2021-03-04 21:38 ` [RFT PATCH v3 19/27] tty: serial: samsung_tty: Add ucon_mask parameter Hector Martin
2021-03-05 10:34   ` Krzysztof Kozlowski
2021-03-04 21:38 ` [RFT PATCH v3 20/27] tty: serial: samsung_tty: Add s3c24xx_port_type Hector Martin
2021-03-05 10:49   ` Krzysztof Kozlowski
2021-03-04 21:38 ` [RFT PATCH v3 21/27] tty: serial: samsung_tty: IRQ rework Hector Martin
2021-03-05 10:51   ` Krzysztof Kozlowski
2021-03-05 15:17   ` Andy Shevchenko
2021-03-05 16:16     ` Hector Martin
2021-03-05 16:20       ` Andy Shevchenko
2021-03-05 16:29         ` Hector Martin
2021-03-07 11:34           ` Krzysztof Kozlowski
2021-03-07 16:01             ` Arnd Bergmann
2021-03-07 19:51               ` Krzysztof Kozlowski
2021-03-04 21:38 ` [RFT PATCH v3 22/27] tty: serial: samsung_tty: Use devm_ioremap_resource Hector Martin
2021-03-05 10:54   ` Krzysztof Kozlowski
2021-03-05 15:19     ` Andy Shevchenko
2021-03-04 21:38 ` [RFT PATCH v3 23/27] dt-bindings: serial: samsung: Add apple, s5l-uart compatible Hector Martin
2021-03-08 21:17   ` [RFT PATCH v3 23/27] dt-bindings: serial: samsung: Add apple,s5l-uart compatible Rob Herring
2021-03-04 21:38 ` [RFT PATCH v3 24/27] tty: serial: samsung_tty: Add support for Apple UARTs Hector Martin
2021-03-05 10:58   ` Krzysztof Kozlowski
2021-03-05 15:28   ` Andy Shevchenko
2021-03-05 17:04     ` Hector Martin
2021-03-07 11:40       ` Krzysztof Kozlowski
2021-03-04 21:39 ` [RFT PATCH v3 25/27] tty: serial: samsung_tty: Add earlycon " Hector Martin
2021-03-05 10:55   ` Krzysztof Kozlowski
2021-03-10 23:11   ` Linus Walleij
2021-03-04 21:39 ` [RFT PATCH v3 26/27] dt-bindings: display: Add apple, simple-framebuffer Hector Martin
2021-03-08 21:18   ` [RFT PATCH v3 26/27] dt-bindings: display: Add apple,simple-framebuffer Rob Herring
2021-03-09 16:37   ` [RFT PATCH v3 26/27] dt-bindings: display: Add apple, simple-framebuffer Linus Walleij
2021-03-09 20:35     ` [RFT PATCH v3 26/27] dt-bindings: display: Add apple,simple-framebuffer Hector Martin
2021-03-04 21:39 ` [RFT PATCH v3 27/27] arm64: apple: Add initial Apple Mac mini (M1, 2020) devicetree Hector Martin
2021-03-05 11:03   ` Krzysztof Kozlowski
2021-03-05 11:14     ` Hector Martin
2021-03-05 11:45       ` Krzysztof Kozlowski
2021-03-05 15:59       ` Mark Kettenis
2021-03-05 16:50         ` Hector Martin
2021-03-13 20:22   ` Konrad Dybcio
2021-04-05  5:50     ` Hector Martin
2021-04-06  7:14       ` Arnd Bergmann
2021-03-05 10:11 ` [RFT PATCH v3 00/27] Apple M1 SoC platform bring-up Hector Martin

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=3564ed98-6ad6-7ddd-01d2-36d7f5af90e0@marcan.st \
    --to=marcan@marcan.st \
    --cc=andy.shevchenko@gmail.com \
    --cc=arnd@kernel.org \
    --cc=catalin.marinas@arm.com \
    --cc=corbet@lwn.net \
    --cc=davem@davemloft.net \
    --cc=devicetree@vger.kernel.org \
    --cc=graf@amazon.com \
    --cc=gregkh@linuxfoundation.org \
    --cc=hch@infradead.org \
    --cc=krzk@kernel.org \
    --cc=linus.walleij@linaro.org \
    --cc=linux-arch@vger.kernel.org \
    --cc=linux-arm-kernel@lists.infradead.org \
    --cc=linux-doc@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-samsung-soc@vger.kernel.org \
    --cc=linux-serial@vger.kernel.org \
    --cc=mark.kettenis@xs4all.nl \
    --cc=mark.rutland@arm.com \
    --cc=maz@kernel.org \
    --cc=mohamed.mediouni@caramail.com \
    --cc=olof@lixom.net \
    --cc=robh@kernel.org \
    --cc=stan@corellium.com \
    --cc=tony@atomide.com \
    --cc=will@kernel.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;
as well as URLs for NNTP newsgroup(s).