aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorlemon <lsof@mailbox.org>2025-09-08 22:01:28 +0200
committerlemon <lsof@mailbox.org>2025-09-08 22:01:28 +0200
commita0691e6b4d631c09f2be80d34a9bd8c24f66b6d1 (patch)
tree0a1875866d431a8336f607614f95aa67bfa792ce
parentf02fb99340edd86848794dd9b85088998458a70d (diff)
amd64: bugfix
-rw-r--r--amd64/emit.c13
-rw-r--r--amd64/sysv.c1
2 files changed, 9 insertions, 5 deletions
diff --git a/amd64/emit.c b/amd64/emit.c
index ffee31f..6494df4 100644
--- a/amd64/emit.c
+++ b/amd64/emit.c
@@ -71,7 +71,7 @@ addmemoper(struct oper *mem, struct oper add)
static inline struct oper
mkregoper(union ref r)
{
- assert(r.t == RREG || (r.t == RTMP && ioper[r.i].t == RREG));
+ assert(r.t == RREG || (r.t == RTMP && ioper[r.i].t == OREG));
return r.t == RREG ? reg2oper(r.i) : ioper[r.i];
}
@@ -344,6 +344,10 @@ encode(uchar **pcode, const struct desc *tab, int ntab, enum irclass k, struct o
case EN_R: case EN_RI32: case EN_RI8:
rex |= (dst.reg >> 3) << 0; /* REX.B */
if (rex) B(0x40 | rex);
+ else if (en->r8 && in_range(dst.reg, RSP, RDI)) {
+ /* /r8 needs REX to encode SP,BP,SI,DI (otherwise -> AH..BH) */
+ B(0x40);
+ }
D(opc, nopc);
B(0300 | en->ext << 3 | (dst.reg & 7));
if (en->operenc == EN_RI32)
@@ -657,7 +661,7 @@ static void
Xpush(uchar **pcode, enum reg reg)
{
assert(in_range(reg, RAX, R15));
- if (reg >> 3) B(0x44); /* REX.R */
+ if (reg >> 3) B(0x41); /* REX.B */
B(0x50 + (reg & 7));
}
@@ -665,7 +669,7 @@ static void
Xpop(uchar **pcode, enum reg reg)
{
assert(in_range(reg, RAX, R15));
- if (reg >> 3) B(0x44); /* REX.R */
+ if (reg >> 3) B(0x41); /* REX.B */
B(0x58 + (reg & 7));
}
@@ -1038,8 +1042,9 @@ emitbin(struct function *fn)
calleesave(&npush, pcode, fn);
/* ensure stack is 16-byte aligned for function calls */
- if (!fn->isleaf && ((fn->stksiz + npush*8) & 0xF) != 0x8)
+ if (!fn->isleaf && ((fn->stksiz + npush*8) & 0xF) != 0x8) {
fn->stksiz += 8;
+ }
if (fn->stksiz != 0) {
/* sub rsp, <stack size> */
diff --git a/amd64/sysv.c b/amd64/sysv.c
index 6c5b67c..9ecc09f 100644
--- a/amd64/sysv.c
+++ b/amd64/sysv.c
@@ -1,6 +1,5 @@
#include "all.h"
-
static int classify(uchar cls[2], const struct typedata *td, uint off);
static int
classifyarr(uchar cls[2], union type ty, uint off)