-
-
Notifications
You must be signed in to change notification settings - Fork 680
Description
Bug description
As shadow stack will insert stack increase or decrease operations without debug location, but Binaryen debug location strategy is range, that means the offset from previous expression offset to current expression offset, they all be regarded to the debug location of previous expression, here id code from WasmBinaryWriter::writeSourceMapEpilog:
writeBase64VLQ(*sourceMap, int32_t(offset - lastOffset));
writeBase64VLQ(*sourceMap, int32_t(loc->fileIndex - lastLoc.fileIndex));
writeBase64VLQ(*sourceMap, int32_t(loc->lineNumber - lastLoc.lineNumber));
writeBase64VLQ(*sourceMap,
int32_t(loc->columnNumber - lastLoc.columnNumber));so the new inserted shadow stack expressions will attach to previous expression, which will cause Basic Block analysis confusion.
for example:
...
;;@ assert.ts:9:6
(local.set $total
;;@ assert.ts:9:15
(i32.add
;;@ assert.ts:9:6
(local.get $total)
;;@ assert.ts:9:15
(i32.const 1)
)
)
)
)
)
;;@ assert.ts:9:6
(global.set $~lib/memory/__stack_pointer
;;@ assert.ts:9:6
(i32.add
;;@ assert.ts:9:6
(global.get $~lib/memory/__stack_pointer)
;;@ assert.ts:9:6
(i32.const 8)
)
)
;;@ assert.ts:11:2
(return)
)
the stack pointer update will be inserted before return instruction, but from debug location, it inherit from another basic block.
I checked from binaryen side, how can prevent this happened, from current solution of Source map of binaryen, it is hard to do that, and from AssemblyScript side, I think if we can add the specific debug location for the stack update expressions?
Steps to reproduce
1, compile as file:
export function test(result: boolean, value: string, key: string): void
{
let total = 0, failed = 0;
if (!result)
{ failed++;
if (value == key)
{ total += failed; }
else
{ total += 1; }
}
return;
}
2, view debug location with below command:
npx wasm-opt build/debug.wasm -ism build/debug.wasm.map --print
AssemblyScript version
v0.27.2