From: Marc Zyngier <maz@kernel.org>
To: Alexandru Elisei <alexandru.elisei@arm.com>
Cc: kvm@vger.kernel.org, pbonzini@redhat.com, drjones@redhat.com,
andre.przywara@arm.com
Subject: Re: [kvm-unit-tests RFC PATCH v3 5/7] lib: arm64: Add support for disabling and re-enabling VHE
Date: Fri, 31 Jan 2020 11:26:30 +0000 [thread overview]
Message-ID: <0ffad077a14887b91eda082ef4893dd5@kernel.org> (raw)
In-Reply-To: <aa243b68-8fb5-d002-2d89-5865fe4dfd3f@arm.com>
Hi Alex,
On 2020-01-31 09:52, Alexandru Elisei wrote:
> Hi,
>
> Thank you for testing the patches!
>
> On 1/30/20 5:40 PM, Marc Zyngier wrote:
>> Hi Alexandru,
>>
>> On 2020-01-02 13:46, Alexandru Elisei wrote:
>>> Add a function to disable VHE and another one to re-enable VHE. Both
>>> functions work under the assumption that the CPU had VHE mode enabled
>>> at
>>> boot.
>>>
>>> Minimal support to run with VHE has been added to the TLB invalidate
>>> functions and to the exception handling code.
>>>
>>> Since we're touch the assembly enable/disable MMU code, let's take
>>> this
>>> opportunity to replace a magic number with the proper define.
>>
>> I've been using this test case to debug my NV code... only to realize
>> after a few hours of banging my head on the wall that it is the test
>> that needed debugging, see below... ;-)
>>
>>>
>>> Signed-off-by: Alexandru Elisei <alexandru.elisei@arm.com>
>>> ---
>>> lib/arm64/asm/mmu.h | 11 ++-
>>> lib/arm64/asm/pgtable-hwdef.h | 53 ++++++++---
>>> lib/arm64/asm/processor.h | 19 +++-
>>> lib/arm64/processor.c | 37 +++++++-
>>> arm/cstart64.S | 204
>>> ++++++++++++++++++++++++++++++++++++++++--
>>> 5 files changed, 300 insertions(+), 24 deletions(-)
>>
>> [...]
>>
>>> --- a/arm/cstart64.S
>>> +++ b/arm/cstart64.S
>>> @@ -104,6 +104,13 @@ exceptions_init:
>>>
>>> .text
>>>
>>> +exceptions_init_nvhe:
>>> + adrp x0, vector_table_nvhe
>>> + add x0, x0, :lo12:vector_table_nvhe
>>> + msr vbar_el2, x0
>>> + isb
>>> + ret
>>> +
>>> .globl get_mmu_off
>>> get_mmu_off:
>>> adrp x0, auxinfo
>>> @@ -203,7 +210,7 @@ asm_mmu_enable:
>>> TCR_IRGN_WBWA | TCR_ORGN_WBWA | \
>>> TCR_SHARED
>>> mrs x2, id_aa64mmfr0_el1
>>> - bfi x1, x2, #32, #3
>>> + bfi x1, x2, #TCR_EL1_IPS_SHIFT, #3
>>> msr tcr_el1, x1
>>>
>>> /* MAIR */
>>> @@ -228,6 +235,41 @@ asm_mmu_enable:
>>>
>>> ret
>>>
>>> +asm_mmu_enable_nvhe:
>>
>> Note the "_nvhe" suffix, which implies that...
>>
>>> + tlbi alle2
>>> + dsb nsh
>>> +
>>> + /* TCR */
>>> + ldr x1, =TCR_EL2_RES1 | \
>>> + TCR_T0SZ(VA_BITS) | \
>>> + TCR_TG0_64K | \
>>> + TCR_IRGN0_WBWA | TCR_ORGN0_WBWA | \
>>> + TCR_SH0_IS
>>> + mrs x2, id_aa64mmfr0_el1
>>> + bfi x1, x2, #TCR_EL2_PS_SHIFT, #3
>>> + msr tcr_el2, x1
>>> +
>>> + /* Same MAIR and TTBR0 as in VHE mode */
>>> + ldr x1, =MAIR(0x00, MT_DEVICE_nGnRnE) | \
>>> + MAIR(0x04, MT_DEVICE_nGnRE) | \
>>> + MAIR(0x0c, MT_DEVICE_GRE) | \
>>> + MAIR(0x44, MT_NORMAL_NC) | \
>>> + MAIR(0xff, MT_NORMAL)
>>> + msr mair_el1, x1
>>
>> ... this should be mair_el2...
>>
>>> +
>>> + msr ttbr0_el1, x0
>>
>> ... and this should be ttbr0_el2.
>
> The code is definitely confusing, but not because it's wrong, but
> because it's
> doing something useless. From DDI 04876E.a, page D13-3374, the
> pseudocode for
> writing to ttbr0_el1:
>
> [..] elsif PSTATE.EL == EL2 then if HCR_EL2.E2H == '1' then
> TTBR0_EL2
> = X[t];
>
> else TTBR0_EL1 = X[t]; [..]
>
> We want to use the same ttbr0_el2 and mair_el2 values that we were
> using when VHE
> was on. We programmed those values when VHE was on, so we actually
> wrote them to
> ttbr0_el2 and mair_el2. We don't need to write them again now, in fact,
> all the
> previous versions of the series didn't even have the above useless
> writes (I
> assume it was a copy-and-paste mistake when I split the fixes from the
> el2 patches).
Fair enough. You're just propagating a dummy value, which is going to
bite you later.
>
>>
>>> + isb
>>> +
>>> + /* SCTLR */
>>> + ldr x1, =SCTLR_EL2_RES1 | \
>>> + SCTLR_EL2_C | \
>>> + SCTLR_EL2_I | \
>>> + SCTLR_EL2_M
>>> + msr sctlr_el2, x1
>>> + isb
>>> +
>>> + ret
>>> +
>>> /* Taken with small changes from arch/arm64/incluse/asm/assembler.h
>>> */
>>> .macro dcache_by_line_op op, domain, start, end, tmp1, tmp2
>>> adrp \tmp1, dcache_line_size
>>> @@ -242,21 +284,61 @@ asm_mmu_enable:
>>> dsb \domain
>>> .endm
>>>
>>> +clean_inval_cache:
>>> + adrp x0, __phys_offset
>>> + ldr x0, [x0, :lo12:__phys_offset]
>>> + adrp x1, __phys_end
>>> + ldr x1, [x1, :lo12:__phys_end]
>>> + dcache_by_line_op civac, sy, x0, x1, x2, x3
>>> + isb
>>> + ret
>>> +
>>> .globl asm_mmu_disable
>>> asm_mmu_disable:
>>> mrs x0, sctlr_el1
>>> bic x0, x0, SCTLR_EL1_M
>>> msr sctlr_el1, x0
>>> isb
>>> + b clean_inval_cache
>>>
>>> - /* Clean + invalidate the entire memory */
>>> - adrp x0, __phys_offset
>>> - ldr x0, [x0, :lo12:__phys_offset]
>>> - adrp x1, __phys_end
>>> - ldr x1, [x1, :lo12:__phys_end]
>>> - dcache_by_line_op civac, sy, x0, x1, x2, x3
>>> +asm_mmu_disable_nvhe:
>>> + mrs x0, sctlr_el2
>>> + bic x0, x0, SCTLR_EL2_M
>>> + msr sctlr_el2, x0
>>> + isb
>>> + b clean_inval_cache
>>> +
>>> +.globl asm_disable_vhe
>>> +asm_disable_vhe:
>>> + str x30, [sp, #-16]!
>>> +
>>> + bl asm_mmu_disable
>>> + msr hcr_el2, xzr
>>> + isb
>>
>> At this stage, VHE is off...
>>
>>> + bl exceptions_init_nvhe
>>> + /* Make asm_mmu_enable_nvhe happy by having TTBR0 value in x0.
>>> */
>>> + mrs x0, ttbr0_el1
>>
>> ... so this is going to sample the wrong TTBR. It really should be
>> TTBR0_EL2!
>
> Not really, asm_mmu_enable has one parameter, the PA for the
> translation tables in
> register x0, and we are going to use the same translation tables with
> VHE off that
> we were using with VHE on. Hence the read.//It could have easily been
> mrs
> x0,ttbr0_el2, since they have the same value, which we want to reuse.
I'm sorry, but if your reasoning that above that VHE's TTBR0_EL1 is the
same as nVHE's TTBR0_EL2 appears correct (they are accessing the same HW
register), this particular read of TTBR0_EL1 is *not* an EL2 register at
all. VHE is off, and you are reading an uninitialized EL1 register (and
it's easy to spot in KVM, as it has the magic poison value).
> I think this confusion stems from the fact that I'm trying to write
> the registers
> again in asm_mmu_enable_nvhe, when we don't have to. And writing to the
> wrong
> registers makes the confusion even worse.
I don't mind the extra writes, or even the confusion. But the above
looks
totally wrong.
Thanks,
M.
--
Jazz is not dead. It just smells funny...
next prev parent reply other threads:[~2020-01-31 11:26 UTC|newest]
Thread overview: 12+ messages / expand[flat|nested] mbox.gz Atom feed top
2020-01-02 13:46 [kvm-unit-tests RFC PATCH v3 0/7] arm64: Run at EL2 Alexandru Elisei
2020-01-02 13:46 ` [kvm-unit-tests RFC PATCH v3 1/7] lib: Add _UL and _ULL definitions to linux/const.h Alexandru Elisei
2020-01-02 13:46 ` [kvm-unit-tests RFC PATCH v3 2/7] lib: arm64: Run existing tests at EL2 Alexandru Elisei
2020-01-02 13:46 ` [kvm-unit-tests RFC PATCH v3 3/7] arm64: timer: Add test for EL2 timers Alexandru Elisei
2020-01-02 13:46 ` [kvm-unit-tests RFC PATCH v3 4/7] arm64: selftest: Add basic test for EL2 Alexandru Elisei
2020-01-02 13:46 ` [kvm-unit-tests RFC PATCH v3 5/7] lib: arm64: Add support for disabling and re-enabling VHE Alexandru Elisei
2020-01-30 17:40 ` Marc Zyngier
2020-01-31 9:52 ` Alexandru Elisei
2020-01-31 11:26 ` Marc Zyngier [this message]
2020-01-31 11:43 ` Alexandru Elisei
2020-01-02 13:46 ` [kvm-unit-tests RFC PATCH v3 6/7] arm64: selftest: Expand EL2 test to disable and re-enable VHE Alexandru Elisei
2020-01-02 13:46 ` [kvm-unit-tests RFC PATCH v3 7/7] arm64: timer: Run tests with VHE disabled Alexandru Elisei
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=0ffad077a14887b91eda082ef4893dd5@kernel.org \
--to=maz@kernel.org \
--cc=alexandru.elisei@arm.com \
--cc=andre.przywara@arm.com \
--cc=drjones@redhat.com \
--cc=kvm@vger.kernel.org \
--cc=pbonzini@redhat.com \
/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