From: Aurelien Jarno <aurelien@aurel32.net>
To: Torbjorn Granlund <tg@gmplib.org>
Cc: Richard Henderson <rth@twiddle.net>,
qemu-ppc@nongnu.org, Alexander Graf <agraf@suse.de>,
qemu-devel@nongnu.org
Subject: Re: [Qemu-devel] [Qemu-ppc] Incorrect handling of more PPC64 insns (PATCH)
Date: Wed, 8 May 2013 08:50:09 +0200 [thread overview]
Message-ID: <20130508065009.GP5000@ohm.aurel32.net> (raw)
In-Reply-To: <86ppx2oaen.fsf@shell.gmplib.org>
On Tue, May 07, 2013 at 09:30:24PM +0200, Torbjorn Granlund wrote:
> I realised a possible problem with my suggested patch.
>
> What about a 32-bit processor? Then NARROW_MODE macro is identical 0.
>
> The pre-patch behaviour was then to ignore the L bit and decode both
> 32-bit and 64-bit instruction in the same way.
>
> Apparently that is correct behaviour. (The manual is slightly vague,
> but I let hardware decide.)
>
> With my patch, the bit is not ignored, and invalid code will be
> generated for 32-bit targets, if they'd set the L bit.
>
> Here is an uglier but hopefully completely correct patch.
>
> diff --git a/target-ppc/translate.c b/target-ppc/translate.c
> index 1a84653..69d684c 100644
> --- a/target-ppc/translate.c
> +++ b/target-ppc/translate.c
> @@ -675,49 +675,65 @@ static inline void gen_set_Rc0(DisasContext *ctx, TCGv reg)
> /* cmp */
> static void gen_cmp(DisasContext *ctx)
> {
> - if (NARROW_MODE(ctx) || !(ctx->opcode & 0x00200000)) {
> +#if defined(TARGET_PPC64)
> + if (!(ctx->opcode & 0x00200000)) {
> +#endif
> gen_op_cmp32(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
> 1, crfD(ctx->opcode));
> +#if defined(TARGET_PPC64)
> } else {
> gen_op_cmp(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
> 1, crfD(ctx->opcode));
> }
> +#endif
> }
I agree that there is a bug there, and that cmp32 should be used with
when L=0. That said your code is not going to generate and invalid code
on a 32-bit CPU with L=1, but instead just skip the instruction.
Moreover as Alexander pointed, TARGET_PPC64 doesn't mean it's a 64-bit
CPU, but that the resulting qemu binaries support 64-bit CPU.
What about the following patch (only lightly tested).
From: Aurelien Jarno <aurelien@aurel32.net>
target-ppc: fix cmp instructions on 64-bit CPUs
64-bit CPUs check for the L bit of comparison instruction to determine
if the instruction is 32-bit wide, and not to the MSR SF bit.
L=1 on a 32-bit CPU should generate an invalid instruction exception.
Reported-by: Torbjorn Granlund <tg@gmplib.org>
Signed-off-by: Aurelien Jarno <aurelien@aurel32.net>
---
target-ppc/translate.c | 48 ++++++++++++++++++++++++++++++++----------------
1 file changed, 32 insertions(+), 16 deletions(-)
diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 0886f4d..ab41dc1 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -675,48 +675,64 @@ static inline void gen_set_Rc0(DisasContext *ctx, TCGv reg)
/* cmp */
static void gen_cmp(DisasContext *ctx)
{
- if (NARROW_MODE(ctx) || !(ctx->opcode & 0x00200000)) {
+ if (ctx->opcode & 0x00200000) {
+ if (unlikely(!(ctx->insns_flags & PPC_64B))) {
+ gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
+ } else {
+ gen_op_cmp(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
+ 1, crfD(ctx->opcode));
+ }
+ } else {
gen_op_cmp32(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
1, crfD(ctx->opcode));
- } else {
- gen_op_cmp(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
- 1, crfD(ctx->opcode));
}
}
/* cmpi */
static void gen_cmpi(DisasContext *ctx)
{
- if (NARROW_MODE(ctx) || !(ctx->opcode & 0x00200000)) {
+ if (ctx->opcode & 0x00200000) {
+ if (unlikely(!(ctx->insns_flags & PPC_64B))) {
+ gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
+ } else {
+ gen_op_cmpi(cpu_gpr[rA(ctx->opcode)], SIMM(ctx->opcode),
+ 1, crfD(ctx->opcode));
+ }
+ } else {
gen_op_cmpi32(cpu_gpr[rA(ctx->opcode)], SIMM(ctx->opcode),
1, crfD(ctx->opcode));
- } else {
- gen_op_cmpi(cpu_gpr[rA(ctx->opcode)], SIMM(ctx->opcode),
- 1, crfD(ctx->opcode));
}
}
/* cmpl */
static void gen_cmpl(DisasContext *ctx)
{
- if (NARROW_MODE(ctx) || !(ctx->opcode & 0x00200000)) {
+ if (ctx->opcode & 0x00200000) {
+ if (unlikely(!(ctx->insns_flags & PPC_64B))) {
+ gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
+ } else {
+ gen_op_cmp(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
+ 0, crfD(ctx->opcode));
+ }
+ } else {
gen_op_cmp32(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
0, crfD(ctx->opcode));
- } else {
- gen_op_cmp(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)],
- 0, crfD(ctx->opcode));
}
}
/* cmpli */
static void gen_cmpli(DisasContext *ctx)
{
- if (NARROW_MODE(ctx) || !(ctx->opcode & 0x00200000)) {
+ if (ctx->opcode & 0x00200000) {
+ if (unlikely(!(ctx->insns_flags & PPC_64B))) {
+ gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL);
+ } else {
+ gen_op_cmpi(cpu_gpr[rA(ctx->opcode)], UIMM(ctx->opcode),
+ 0, crfD(ctx->opcode));
+ }
+ } else {
gen_op_cmpi32(cpu_gpr[rA(ctx->opcode)], UIMM(ctx->opcode),
0, crfD(ctx->opcode));
- } else {
- gen_op_cmpi(cpu_gpr[rA(ctx->opcode)], UIMM(ctx->opcode),
- 0, crfD(ctx->opcode));
}
}
--
1.7.10.4
--
Aurelien Jarno GPG: 1024D/F1BCDB73
aurelien@aurel32.net http://www.aurel32.net
next prev parent reply other threads:[~2013-05-08 6:50 UTC|newest]
Thread overview: 21+ messages / expand[flat|nested] mbox.gz Atom feed top
2013-05-06 17:00 [Qemu-devel] Incorrect handling of PPC64 rldcl insn Torbjorn Granlund
2013-05-06 17:47 ` Alexander Graf
2013-05-06 18:13 ` Torbjorn Granlund
2013-05-06 22:14 ` Alexander Graf
2013-05-06 23:12 ` Aurelien Jarno
2013-05-07 10:27 ` [Qemu-devel] Incorrect handling of more PPC64 insns Torbjorn Granlund
2013-05-07 10:39 ` Peter Maydell
2013-05-07 11:48 ` Torbjorn Granlund
2013-05-07 11:51 ` Peter Maydell
2013-05-07 15:58 ` [Qemu-devel] Incorrect handling of more PPC64 insns (PATCH) Torbjorn Granlund
2013-05-07 17:12 ` [Qemu-devel] [Qemu-ppc] " Alexander Graf
2013-05-07 18:10 ` Torbjorn Granlund
2013-05-07 19:30 ` Torbjorn Granlund
2013-05-07 22:00 ` Alexander Graf
2013-05-08 6:50 ` Aurelien Jarno [this message]
2013-05-08 6:52 ` Alexander Graf
2013-05-08 9:20 ` Torbjorn Granlund
2013-05-08 9:32 ` Alexander Graf
2013-05-08 9:57 ` Alexander Graf
2013-05-08 10:07 ` Torbjorn Granlund
2013-05-08 10:45 ` Alexander Graf
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=20130508065009.GP5000@ohm.aurel32.net \
--to=aurelien@aurel32.net \
--cc=agraf@suse.de \
--cc=qemu-devel@nongnu.org \
--cc=qemu-ppc@nongnu.org \
--cc=rth@twiddle.net \
--cc=tg@gmplib.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).