wcc: tuple slice-element read loads the full 24B header, both stages
Reading a slice-typed tuple element (t.0) loaded only the pointer word; len and cap took whatever was left in BX/CX — silent garbage in BOTH stages once anything clobbered the registers between build and read. Load all three header words at the tuple-element arm. Review item #28. Both stages move in one commit: one emission contract; splitting would leave the byte-id gates red between the halves.
This commit is contained in:
@@ -26646,7 +26646,14 @@ fn cgdot(c: *cgen, n: *node) void = {
|
||||
};
|
||||
if (tp != nil) {
|
||||
let tpt: *node = tp.lhs;
|
||||
if (isstrtype(c, tpt)) {
|
||||
// str IS []u8, and a slice is the same 24B
|
||||
// {ptr,len,cap} header — load all three words
|
||||
// into (AX, BX, CX). #28: pre-fix the gate was
|
||||
// str-only, so a SLICE tuple element fell to
|
||||
// the scalar tail below (one ptr word; len/cap
|
||||
// took stale registers). base is BP (frame),
|
||||
// so the triple order has no clobber risk.
|
||||
if (isstrtype(c, tpt) || isslicetype(c, tpt)) {
|
||||
emitline("\tMOVQ\t");
|
||||
emitoff((lc.off + foff + 0): i64);
|
||||
emitline("(BP), AX\n");
|
||||
|
||||
@@ -3495,7 +3495,14 @@ fn cgdot(c: *cgen, n: *node) void = {
|
||||
};
|
||||
if (tp != nil) {
|
||||
let tpt: *node = tp.lhs;
|
||||
if (isstrtype(c, tpt)) {
|
||||
// str IS []u8, and a slice is the same 24B
|
||||
// {ptr,len,cap} header — load all three words
|
||||
// into (AX, BX, CX). #28: pre-fix the gate was
|
||||
// str-only, so a SLICE tuple element fell to
|
||||
// the scalar tail below (one ptr word; len/cap
|
||||
// took stale registers). base is BP (frame),
|
||||
// so the triple order has no clobber risk.
|
||||
if (isstrtype(c, tpt) || isslicetype(c, tpt)) {
|
||||
emitline("\tMOVQ\t");
|
||||
emitoff((lc.off + foff + 0): i64);
|
||||
emitline("(BP), AX\n");
|
||||
|
||||
@@ -26646,7 +26646,14 @@ fn cgdot(c: *cgen, n: *node) void = {
|
||||
};
|
||||
if (tp != nil) {
|
||||
let tpt: *node = tp.lhs;
|
||||
if (isstrtype(c, tpt)) {
|
||||
// str IS []u8, and a slice is the same 24B
|
||||
// {ptr,len,cap} header — load all three words
|
||||
// into (AX, BX, CX). #28: pre-fix the gate was
|
||||
// str-only, so a SLICE tuple element fell to
|
||||
// the scalar tail below (one ptr word; len/cap
|
||||
// took stale registers). base is BP (frame),
|
||||
// so the triple order has no clobber risk.
|
||||
if (isstrtype(c, tpt) || isslicetype(c, tpt)) {
|
||||
emitline("\tMOVQ\t");
|
||||
emitoff((lc.off + foff + 0): i64);
|
||||
emitline("(BP), AX\n");
|
||||
|
||||
Reference in New Issue
Block a user