Message ID | 209441398413635@web22g.yandex.ru |
---|---|
State | New |
Headers | show |
On 04/25/2014 01:13 AM, Dmitry Poletaev wrote: > There is a set of test, that checks QEMU CPU for similar behavior with real hardware (http://roberto.greyhats.it/projects/pills.html). Test reg/pill2579.c can detect, that program is execute in emulated environment. It is related with behavior of rcl instruction. If the number of shifted bits more than 1, OF of eflags become undefined. Real CPUs does not change OF, if it is undefined. QEMU do it anyway. > Emulated program can execute that test and after that can understand environment not real. > > Signed-off-by: Dmitry Poletaev <poletaev-qemu@yandex.ru> > > diff --git a/target-i386/shift_helper_template.h b/target-i386/shift_helper_template.h > index cf91a2d..d5bd321 100644 > --- a/target-i386/shift_helper_template.h > +++ b/target-i386/shift_helper_template.h > @@ -64,8 +64,10 @@ target_ulong glue(helper_rcl, SUFFIX)(CPUX86State *env, target_ulong t0, > } > t0 = res; > env->cc_src = (eflags & ~(CC_C | CC_O)) | > - (lshift(src ^ t0, 11 - (DATA_BITS - 1)) & CC_O) | > ((src >> (DATA_BITS - count)) & CC_C); > + if (count == 1) { > + env->cc_src |= (lshift(src ^ t0, 11 - (DATA_BITS - 1)) & CC_O); > + } This doesn't do what you say it does. It doesn't leave O unchanged, it always resets it to 0, and only sets it back to 1 if count == 1. r~
On 25 April 2014 09:13, Dmitry Poletaev <poletaev-qemu@yandex.ru> wrote: > There is a set of test, that checks QEMU CPU for similar behavior with real hardware (http://roberto.greyhats.it/projects/pills.html). Test reg/pill2579.c can detect, that program is execute in emulated environment. It is related with behavior of rcl instruction. If the number of shifted bits more than 1, OF of eflags become undefined. Real CPUs does not change OF, if it is undefined. QEMU do it anyway. It would be helpful if you could be more precise with your subject lines. "improve emulation correctness" is so vague it could apply to almost any part of QEMU. We usually have a format of "area or file: change", so in this case perhaps "target-i386: fix handling of OF in rcl instruction". That said, > Emulated program can execute that test and after that > can understand environment not real. It is always going to be possible to determine that you're running on an emulator rather than real hardware, so changing QEMU behaviour just for this is uninteresting. If QEMU behaves differently from the specification (in this case the x86 hardware and architecture manuals) that's an interesting bug. If we just happen to choose a different undefined behaviour from that which hardware does, that is not in my opinion a problem. thanks -- PMM
25.04.2014 21:24, Peter Maydell wrote: > On 25 April 2014 09:13, Dmitry Poletaev <poletaev-qemu@yandex.ru> wrote: > >> Emulated program can execute that test and after that >> can understand environment not real. > > It is always going to be possible to determine that you're > running on an emulator rather than real hardware, so changing > QEMU behaviour just for this is uninteresting. If QEMU > behaves differently from the specification (in this case > the x86 hardware and architecture manuals) that's an interesting > bug. If we just happen to choose a different undefined > behaviour from that which hardware does, that is not in > my opinion a problem. Actually it might be a problem. We know a ton of examples where hardware had bugs and software had to compensate and actually _expect_ buggy behavour. Or when software depends on (reliable repeating) certain behavour in undocumented parts, and hell breaks when this (undocumented!) behavour changes. Thanks, /mjt
On 27 April 2014 17:46, Michael Tokarev <mjt@tls.msk.ru> wrote: > 25.04.2014 21:24, Peter Maydell wrote: >> It is always going to be possible to determine that you're >> running on an emulator rather than real hardware, so changing >> QEMU behaviour just for this is uninteresting. If QEMU >> behaves differently from the specification (in this case >> the x86 hardware and architecture manuals) that's an interesting >> bug. If we just happen to choose a different undefined >> behaviour from that which hardware does, that is not in >> my opinion a problem. > > Actually it might be a problem. We know a ton of examples where > hardware had bugs and software had to compensate and actually > _expect_ buggy behavour. Or when software depends on (reliable > repeating) certain behavour in undocumented parts, and hell > breaks when this (undocumented!) behavour changes. Yes, sometimes you get that sort of thing. But we should only put that kind of change in when we actually need it (ie when there's real guest code that hits it, not just silly test programs deliberately looking for undefined behaviour), and comment why it's there so people who need to maintain that bit of code in future know that it's deliberate and not just accidental. I should perhaps have said "that is not inherently a problem". thanks -- PMM
27.04.2014, 20:59, "Peter Maydell" <peter.maydell@linaro.org>: > On 27 April 2014 17:46, Michael Tokarev <mjt@tls.msk.ru> wrote: >> 25.04.2014 21:24, Peter Maydell wrote: >>> It is always going to be possible to determine that you're >>> running on an emulator rather than real hardware, so changing >>> QEMU behaviour just for this is uninteresting. If QEMU >>> behaves differently from the specification (in this case >>> the x86 hardware and architecture manuals) that's an interesting >>> bug. If we just happen to choose a different undefined >>> behaviour from that which hardware does, that is not in >>> my opinion a problem. >> Actually it might be a problem. We know a ton of examples where >> hardware had bugs and software had to compensate and actually >> _expect_ buggy behavour. Or when software depends on (reliable >> repeating) certain behavour in undocumented parts, and hell >> breaks when this (undocumented!) behavour changes. > Yes, sometimes you get that sort of thing. But we should only > put that kind of change in when we actually need it (ie when > there's real guest code that hits it, not just silly test programs > deliberately looking for undefined behaviour), and comment > why it's there so people who need to maintain that bit of code > in future know that it's deliberate and not just accidental. > > I should perhaps have said "that is not inherently a problem". > > thanks > -- PMM Let's imagine we analyse a program(may be a malware) and so run it in emulator. Malware can execute that test and understand that it run in an emulator. After that malware can make decision, that someone analyse it and alter its behavior with a view to make analysis more complicated. So it makes sense to apply that patch. Of course that little fix can't absolutely break a chance to detect emulation, but can make it more difficult.
On 28 April 2014 14:41, Dmitry Poletaev <poletaev-qemu@yandex.ru> wrote: > Let's imagine we analyse a program(may be a malware) and so > run it in emulator. Malware can execute that test and understand > that it run in an emulator. After that malware can make decision, > that someone analyse it and alter its behavior with a view to > make analysis more complicated. I understand this theory. I think it's misguided to think that it's possible to avoid the problem. > So it makes sense to apply that patch. I disagree with this, because we can never make QEMU behave exactly identically to the hardware (timing effects, weird choices of QEMU devices, etc). We cannot offer this guarantee, so there is no point in attempting to make changes purely to try to provide the guarantee in some areas. (Just to pick a fairly easy way guest malware can detect QEMU TCG, it can run timing tests that probe for the size of L1 cache by looking for the point where memory access time falls off a cliff. QEMU will never be able to emulate caches with the same sort of memory timing profile.) thanks -- PMM
I'm understand your position. But why in TCG undefined flags obviously change to zero in some cases? For example: af = 0; /* undefined */ It is not a part of Intel specification, what reason was apply that convention? 28.04.2014, 17:49, "Peter Maydell" <peter.maydell@linaro.org>: > On 28 April 2014 14:41, Dmitry Poletaev <poletaev-qemu@yandex.ru> wrote: > >> Let's imagine we analyse a program(may be a malware) and so >> run it in emulator. Malware can execute that test and understand >> that it run in an emulator. After that malware can make decision, >> that someone analyse it and alter its behavior with a view to >> make analysis more complicated. > > I understand this theory. I think it's misguided to think that > it's possible to avoid the problem. > >> So it makes sense to apply that patch. > > I disagree with this, because we can never make QEMU behave > exactly identically to the hardware (timing effects, weird > choices of QEMU devices, etc). We cannot offer this guarantee, > so there is no point in attempting to make changes purely > to try to provide the guarantee in some areas. > > (Just to pick a fairly easy way guest malware can > detect QEMU TCG, it can run timing tests that probe for > the size of L1 cache by looking for the point where memory > access time falls off a cliff. QEMU will never be able to > emulate caches with the same sort of memory timing profile.) > > thanks > -- PMM
On 04/28/2014 07:32 AM, Dmitry Poletaev wrote: > I'm understand your position. > > But why in TCG undefined flags obviously change to zero in some cases? > For example: > af = 0; /* undefined */ > > It is not a part of Intel specification, what reason was apply that convention? Because it's simple, correct, and makes for the smallest fastest qemu binary. r~
diff --git a/target-i386/shift_helper_template.h b/target-i386/shift_helper_template.h index cf91a2d..d5bd321 100644 --- a/target-i386/shift_helper_template.h +++ b/target-i386/shift_helper_template.h @@ -64,8 +64,10 @@ target_ulong glue(helper_rcl, SUFFIX)(CPUX86State *env, target_ulong t0, } t0 = res; env->cc_src = (eflags & ~(CC_C | CC_O)) | - (lshift(src ^ t0, 11 - (DATA_BITS - 1)) & CC_O) | ((src >> (DATA_BITS - count)) & CC_C); + if (count == 1) { + env->cc_src |= (lshift(src ^ t0, 11 - (DATA_BITS - 1)) & CC_O); + } } return t0; }
There is a set of test, that checks QEMU CPU for similar behavior with real hardware (http://roberto.greyhats.it/projects/pills.html). Test reg/pill2579.c can detect, that program is execute in emulated environment. It is related with behavior of rcl instruction. If the number of shifted bits more than 1, OF of eflags become undefined. Real CPUs does not change OF, if it is undefined. QEMU do it anyway. Emulated program can execute that test and after that can understand environment not real. Signed-off-by: Dmitry Poletaev <poletaev-qemu@yandex.ru> This patch improve correctness of emulator behavior.