diff options
author | Ayke van Laethem <[email protected]> | 2023-05-20 17:17:54 +0200 |
---|---|---|
committer | Ron Evans <[email protected]> | 2023-05-20 23:57:20 +0200 |
commit | cf39db36fea07c7b35e50e47f6c76d4c3f15100e (patch) | |
tree | 931049c471ea75376c0b2e169bc3d91e46af1a61 | |
parent | 54c07b7de81d04cda442bee10dabdb8cdb9a1e58 (diff) | |
download | tinygo-cf39db36fea07c7b35e50e47f6c76d4c3f15100e.tar.gz tinygo-cf39db36fea07c7b35e50e47f6c76d4c3f15100e.zip |
interp: fix subtle bug in pointer xor
If a pointer value was xor'ed with a value other than 0, it would not
have been run at runtime but instead would fall through to the generic
integer operations. This would likely result in a "cannot convert
pointer to integer" panic.
This commit fixes this subtle case.
-rw-r--r-- | interp/interpreter.go | 21 |
1 files changed, 8 insertions, 13 deletions
diff --git a/interp/interpreter.go b/interp/interpreter.go index 46aa9d1f4..1ec4597e1 100644 --- a/interp/interpreter.go +++ b/interp/interpreter.go @@ -736,30 +736,25 @@ func (r *runner) run(fn *function, params []value, parentMem *memoryView, indent if err == nil { // The lhs is a pointer. This sometimes happens for particular // pointer tricks. - switch inst.opcode { - case llvm.Add: + if inst.opcode == llvm.Add { // This likely means this is part of a // unsafe.Pointer(uintptr(ptr) + offset) pattern. lhsPtr = lhsPtr.addOffset(int64(rhs.Uint())) locals[inst.localIndex] = lhsPtr - continue - case llvm.Xor: - if rhs.Uint() == 0 { - // Special workaround for strings.noescape, see - // src/strings/builder.go in the Go source tree. This is - // the identity operator, so we can return the input. - locals[inst.localIndex] = lhs - continue - } - default: + } else if inst.opcode == llvm.Xor && rhs.Uint() == 0 { + // Special workaround for strings.noescape, see + // src/strings/builder.go in the Go source tree. This is + // the identity operator, so we can return the input. + locals[inst.localIndex] = lhs + } else { // Catch-all for weird operations that should just be done // at runtime. err := r.runAtRuntime(fn, inst, locals, &mem, indent) if err != nil { return nil, mem, err } - continue } + continue } var result uint64 switch inst.opcode { |