aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorAyke van Laethem <[email protected]>2020-06-14 19:07:30 +0200
committerJaden Weiss <[email protected]>2020-06-14 14:44:22 -0400
commite2bf7bbb4991298d3596384bcbdf2b7c566c92f3 (patch)
treea5e0967665aa520beccde267fae8cb3ee0d3b01a
parent4d1d0c2d3bbd7dbacc74c445c6adc00219bae49a (diff)
downloadtinygo-e2bf7bbb4991298d3596384bcbdf2b7c566c92f3.tar.gz
tinygo-e2bf7bbb4991298d3596384bcbdf2b7c566c92f3.zip
device: add new cross-arch Asm and AsmFull functions
This is necessary to avoid a circular dependency between the device/avr and runtime/interrupts package in the next commit. It may be worth replacing existing calls like device/arm.Asm to device.Asm, to have a single place where these are defined.
-rw-r--r--compiler/compiler.go4
-rw-r--r--src/device/asm.go21
2 files changed, 23 insertions, 2 deletions
diff --git a/compiler/compiler.go b/compiler/compiler.go
index 677128d0e..fe45eb3fc 100644
--- a/compiler/compiler.go
+++ b/compiler/compiler.go
@@ -1327,9 +1327,9 @@ func (b *builder) createFunctionCall(instr *ssa.CallCommon) (llvm.Value, error)
return b.createMemoryCopyCall(fn, instr.Args)
case name == "runtime.memzero":
return b.createMemoryZeroCall(instr.Args)
- case name == "device/arm.Asm" || name == "device/avr.Asm" || name == "device/riscv.Asm":
+ case name == "device.Asm" || name == "device/arm.Asm" || name == "device/avr.Asm" || name == "device/riscv.Asm":
return b.createInlineAsm(instr.Args)
- case name == "device/arm.AsmFull" || name == "device/avr.AsmFull" || name == "device/riscv.AsmFull":
+ case name == "device.AsmFull" || name == "device/arm.AsmFull" || name == "device/avr.AsmFull" || name == "device/riscv.AsmFull":
return b.createInlineAsmFull(instr)
case strings.HasPrefix(name, "device/arm.SVCall"):
return b.emitSVCall(instr.Args)
diff --git a/src/device/asm.go b/src/device/asm.go
new file mode 100644
index 000000000..f441b6ae2
--- /dev/null
+++ b/src/device/asm.go
@@ -0,0 +1,21 @@
+package device
+
+// Run the given assembly code. The code will be marked as having side effects,
+// as it doesn't produce output and thus would normally be eliminated by the
+// optimizer.
+func Asm(asm string)
+
+// Run the given inline assembly. The code will be marked as having side
+// effects, as it would otherwise be optimized away. The inline assembly string
+// recognizes template values in the form {name}, like so:
+//
+// arm.AsmFull(
+// "str {value}, {result}",
+// map[string]interface{}{
+// "value": 1
+// "result": &dest,
+// })
+//
+// You can use {} in the asm string (which expands to a register) to set the
+// return value.
+func AsmFull(asm string, regs map[string]interface{}) uintptr