All of lore.kernel.org
 help / color / mirror / Atom feed
From: will.deacon@arm.com (Will Deacon)
To: linux-arm-kernel@lists.infradead.org
Subject: [PATCH v4 20/20] arm64: KVM: vgic: add GICv3 world switch
Date: Wed, 28 May 2014 20:11:10 +0100	[thread overview]
Message-ID: <20140528191110.GF20523@arm.com> (raw)
In-Reply-To: <1400176719-31275-21-git-send-email-marc.zyngier@arm.com>

On Thu, May 15, 2014 at 06:58:39PM +0100, Marc Zyngier wrote:
> Introduce the GICv3 world switch code and helper functions, enabling
> GICv2 emulation on GICv3 hardware.
> 
> Acked-by: Catalin Marinas <catalin.marinas@arm.com>
> Reviewed-by: Christoffer Dall <christoffer.dall@linaro.org>
> Signed-off-by: Marc Zyngier <marc.zyngier@arm.com>

[...]

> diff --git a/arch/arm64/kvm/vgic-v3-switch.S b/arch/arm64/kvm/vgic-v3-switch.S
> new file mode 100644
> index 0000000..791a9ab
> --- /dev/null
> +++ b/arch/arm64/kvm/vgic-v3-switch.S
> @@ -0,0 +1,271 @@
> +/*
> + * Copyright (C) 2012,2013 - ARM Ltd
> + * Author: Marc Zyngier <marc.zyngier@arm.com>
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License version 2 as
> + * published by the Free Software Foundation.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program.  If not, see <http://www.gnu.org/licenses/>.
> + */
> +
> +#include <linux/linkage.h>
> +#include <linux/irqchip/arm-gic-v3.h>
> +
> +#include <asm/assembler.h>
> +#include <asm/memory.h>
> +#include <asm/asm-offsets.h>
> +#include <asm/kvm.h>
> +#include <asm/kvm_asm.h>
> +#include <asm/kvm_arm.h>
> +
> +	.text
> +	.pushsection	.hyp.text, "ax"
> +
> +/*
> + * Save the VGIC CPU state into memory
> + * x0: Register pointing to VCPU struct
> + * Do not corrupt x1!!!
> + */
> +.macro	save_vgic_v3_state
> +	// Compute the address of struct vgic_cpu
> +	add	x3, x0, #VCPU_VGIC_CPU
> +
> +	// Make sure stores to the GIC via the memory mapped interface
> +	// are now visible to the system register interface
> +	dsb	sy

Stores you say? There's an option for that (-st).

> +	// Save all interesting registers
> +	mrs	x4, ICH_HCR_EL2
> +	mrs	x5, ICH_VMCR_EL2
> +	mrs	x6, ICH_MISR_EL2
> +	mrs	x7, ICH_EISR_EL2
> +	mrs	x8, ICH_ELSR_EL2
> +
> +	str	w4, [x3, #VGIC_V3_CPU_HCR]
> +	str	w5, [x3, #VGIC_V3_CPU_VMCR]
> +	str	w6, [x3, #VGIC_V3_CPU_MISR]
> +	str	w7, [x3, #VGIC_V3_CPU_EISR]
> +	str	w8, [x3, #VGIC_V3_CPU_ELRSR]
> +
> +	msr	ICH_HCR_EL2, xzr
> +
> +	mrs	x21, ICH_VTR_EL2
> +	and	w22, w21, #0xf
> +	mov	w23, #0xf
> +	sub	w23, w23, w22	// How many regs we have to skip

	mvn	w22, w21
	ubfiz	w23, w22, 2, 4

> +	adr	x24, 1f
> +	add	x24, x24, x23, lsl #2

... then you don't need this lsl.

> +	br	x24
> +
> +1:
> +	mrs	x20, ICH_LR15_EL2
> +	mrs	x19, ICH_LR14_EL2
> +	mrs	x18, ICH_LR13_EL2
> +	mrs	x17, ICH_LR12_EL2
> +	mrs	x16, ICH_LR11_EL2
> +	mrs	x15, ICH_LR10_EL2
> +	mrs	x14, ICH_LR9_EL2
> +	mrs	x13, ICH_LR8_EL2
> +	mrs	x12, ICH_LR7_EL2
> +	mrs	x11, ICH_LR6_EL2
> +	mrs	x10, ICH_LR5_EL2
> +	mrs	x9, ICH_LR4_EL2
> +	mrs	x8, ICH_LR3_EL2
> +	mrs	x7, ICH_LR2_EL2
> +	mrs	x6, ICH_LR1_EL2
> +	mrs	x5, ICH_LR0_EL2
> +
> +	adr	x24, 1f
> +	add	x24, x24, x23, lsl #2	// adr(1f) + unimp_nr*4

Same here (you can drop the shift with the above)

> +	br	x24
> +
> +1:
> +	str	x20, [x3, #(VGIC_V3_CPU_LR + 15*8)]
> +	str	x19, [x3, #(VGIC_V3_CPU_LR + 14*8)]
> +	str	x18, [x3, #(VGIC_V3_CPU_LR + 13*8)]
> +	str	x17, [x3, #(VGIC_V3_CPU_LR + 12*8)]
> +	str	x16, [x3, #(VGIC_V3_CPU_LR + 11*8)]
> +	str	x15, [x3, #(VGIC_V3_CPU_LR + 10*8)]
> +	str	x14, [x3, #(VGIC_V3_CPU_LR + 9*8)]
> +	str	x13, [x3, #(VGIC_V3_CPU_LR + 8*8)]
> +	str	x12, [x3, #(VGIC_V3_CPU_LR + 7*8)]
> +	str	x11, [x3, #(VGIC_V3_CPU_LR + 6*8)]
> +	str	x10, [x3, #(VGIC_V3_CPU_LR + 5*8)]
> +	str	x9, [x3, #(VGIC_V3_CPU_LR + 4*8)]
> +	str	x8, [x3, #(VGIC_V3_CPU_LR + 3*8)]
> +	str	x7, [x3, #(VGIC_V3_CPU_LR + 2*8)]
> +	str	x6, [x3, #(VGIC_V3_CPU_LR + 1*8)]
> +	str	x5, [x3, #VGIC_V3_CPU_LR]

Do you have to store these backwards? I worry that it could defect some CPU
optimisations detecting streaming stores.

> +
> +	lsr	w22, w21, #29	// Get PRIbits
> +	cmp	w22, #4		// 5 bits
> +	b.eq	5f

Can you lsr by 33 and use cbz for the 5 bits case?

> +	cmp	w22, #5		// 6 bits
> +	b.eq	6f
> +				// 7 bits
> +	mrs	x20, ICH_AP0R3_EL2
> +	str	w20, [x3, #(VGIC_V3_CPU_AP0R + 3*4)]
> +	mrs	x19, ICH_AP0R2_EL2
> +	str	w19, [x3, #(VGIC_V3_CPU_AP0R + 2*4)]

I'm slightly confused here... Why do we access ICH_AP0R3_EL2 when we have 7
bits of priority? Shouldn't we have a check for 8 bits?

> +1:
> +	msr	ICH_LR15_EL2, x20
> +	msr	ICH_LR14_EL2, x19
> +	msr	ICH_LR13_EL2, x18
> +	msr	ICH_LR12_EL2, x17
> +	msr	ICH_LR11_EL2, x16
> +	msr	ICH_LR10_EL2, x15
> +	msr	ICH_LR9_EL2,  x14
> +	msr	ICH_LR8_EL2,  x13
> +	msr	ICH_LR7_EL2,  x12
> +	msr	ICH_LR6_EL2,  x11
> +	msr	ICH_LR5_EL2,  x10
> +	msr	ICH_LR4_EL2,   x9
> +	msr	ICH_LR3_EL2,   x8
> +	msr	ICH_LR2_EL2,   x7
> +	msr	ICH_LR1_EL2,   x6
> +	msr	ICH_LR0_EL2,   x5
> +
> +	// Ensure that the above will be visible via the memory-mapped
> +	// view of the CPU interface (GICV).
> +	isb
> +	dsb	sy

Bah, I'm sure I asked this before, but what is that dsb doing? I can't see
any memory accesses or cache maintenance that need to be completed.

Will

  reply	other threads:[~2014-05-28 19:11 UTC|newest]

Thread overview: 49+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2014-05-15 17:58 [PATCH v4 00/20] arm64: GICv3 support Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 01/20] ARM: GIC: move some bits of GICv2 to a library-type file Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 02/20] arm64: initial support for GICv3 Marc Zyngier
2014-05-23 16:40   ` Jean-Philippe Brucker
2014-05-27  8:17     ` Marc Zyngier
2014-06-05  7:47   ` Abel
2014-06-05  8:44     ` Marc Zyngier
2014-06-09  4:10       ` Abel
2014-06-09  8:41         ` Marc Zyngier
2014-06-10  3:57           ` Abel
2014-06-10 10:43             ` Marc Zyngier
2014-06-11  1:15               ` Abel
2014-05-15 17:58 ` [PATCH v4 03/20] arm64: GICv3 device tree binding documentation Marc Zyngier
2014-05-20 14:58   ` Andre Przywara
2014-05-20 15:32     ` Marc Zyngier
2014-05-20 16:21       ` Andre Przywara
2014-05-15 17:58 ` [PATCH v4 04/20] arm64: boot protocol documentation update for GICv3 Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 05/20] KVM: arm/arm64: vgic: move GICv2 registers to their own structure Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 06/20] KVM: ARM: vgic: introduce vgic_ops and LR manipulation primitives Marc Zyngier
2014-05-20 12:33   ` Christoffer Dall
2014-05-15 17:58 ` [PATCH v4 07/20] KVM: ARM: vgic: abstract access to the ELRSR bitmap Marc Zyngier
2014-05-20 12:35   ` Christoffer Dall
2014-05-15 17:58 ` [PATCH v4 08/20] KVM: ARM: vgic: abstract EISR bitmap access Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 09/20] KVM: ARM: vgic: abstract MISR decoding Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 10/20] KVM: ARM: vgic: move underflow handling to vgic_ops Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 11/20] KVM: ARM: vgic: abstract VMCR access Marc Zyngier
2014-05-20 12:41   ` Christoffer Dall
2014-05-15 17:58 ` [PATCH v4 12/20] KVM: ARM: vgic: introduce vgic_enable Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 13/20] KVM: ARM: introduce vgic_params structure Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 14/20] KVM: ARM: vgic: split GICv2 backend from the main vgic code Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 15/20] KVM: ARM: vgic: revisit implementation of irqchip_in_kernel Marc Zyngier
2014-05-20 12:50   ` Christoffer Dall
2014-05-15 17:58 ` [PATCH v4 16/20] arm64: KVM: remove __kvm_hyp_code_{start, end} from hyp.S Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 17/20] arm64: KVM: split GICv2 world switch from hyp code Marc Zyngier
2014-05-20 12:53   ` Christoffer Dall
2014-05-15 17:58 ` [PATCH v4 18/20] arm64: KVM: move HCR_EL2.{IMO, FMO} manipulation into the vgic switch code Marc Zyngier
2014-05-20 12:58   ` Christoffer Dall
2014-05-15 17:58 ` [PATCH v4 19/20] KVM: ARM: vgic: add the GICv3 backend Marc Zyngier
2014-05-20 13:09   ` Christoffer Dall
2014-05-20 13:29     ` Marc Zyngier
2014-05-15 17:58 ` [PATCH v4 20/20] arm64: KVM: vgic: add GICv3 world switch Marc Zyngier
2014-05-28 19:11   ` Will Deacon [this message]
2014-06-02 15:09     ` Marc Zyngier
2014-05-30 23:06 ` [PATCH v4 00/20] arm64: GICv3 support Radha Mohan
2014-05-31  1:14   ` Chalamarla, Tirumalesh
2014-06-02 12:59     ` Marc Zyngier
2014-06-02 12:57   ` Marc Zyngier
2014-06-11  1:49 ` Abel
2014-06-11  2:58   ` Abel

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=20140528191110.GF20523@arm.com \
    --to=will.deacon@arm.com \
    --cc=linux-arm-kernel@lists.infradead.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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.