On Fri, 19 Feb 2016 17:45:48 +0100, Aurelien Jarno said: > On 2016-02-19 12:11, Aurelien Jarno wrote: > Actually the same patch with a bit more context shows the issue: > > > diff --git a/arch/x86/kvm/emulate.c b/arch/x86/kvm/emulate.c > > index e7a4fde..b372a75 100644 > > --- a/arch/x86/kvm/emulate.c > > +++ b/arch/x86/kvm/emulate.c > > @@ -647,12 +647,13 @@ static __always_inline int __linearize(struct x86_emu late_ctxt *ctxt, > > bool usable; > > ulong la; > > u32 lim; > > u16 sel; > > > > la = seg_base(ctxt, addr.seg) + addr.ea; > > + *linear = la; > > The assignation is moved here... > > > *max_size = 0; > > switch (mode) { > > case X86EMUL_MODE_PROT64: > > if (is_noncanonical_address(la)) > > goto bad; > > > > @@ -690,13 +691,12 @@ static __always_inline int __linearize(struct x86_emulate_ctxt *ctxt, > > } > > la &= (u32)-1; > > ... while the value of la might be modified in between. (trying to reconstruct my thought process from 6 months ago. I remember staring at that, and I convinced myself it was still OK to move the assignment.) la can get changed here - but there's 2 cases to consider. If it's in a 32-bit kernel, anding with -1 is a no-op. Now if we're on a 64-bit kernel, the 'and' clears the high 32 bits. But under what conditions is 'la' a 64-bit quantity that has any bits set in the high 32 bits (meaning it's a pointer to something over the 4G line) - but it's still valid to smash those bits?
Attachment:
pgpPzbFhjnWcc.pgp
Description: PGP signature