summaryrefslogtreecommitdiffstats
path: root/src/runtime/cgo/asm_ppc64x.s
diff options
context:
space:
mode:
Diffstat (limited to 'src/runtime/cgo/asm_ppc64x.s')
-rw-r--r--src/runtime/cgo/asm_ppc64x.s134
1 files changed, 134 insertions, 0 deletions
diff --git a/src/runtime/cgo/asm_ppc64x.s b/src/runtime/cgo/asm_ppc64x.s
new file mode 100644
index 0000000..f4efc1e
--- /dev/null
+++ b/src/runtime/cgo/asm_ppc64x.s
@@ -0,0 +1,134 @@
+// Copyright 2014 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+// +build ppc64 ppc64le
+
+#include "textflag.h"
+#include "asm_ppc64x.h"
+
+// Called by C code generated by cmd/cgo.
+// func crosscall2(fn, a unsafe.Pointer, n int32, ctxt uintptr)
+// Saves C callee-saved registers and calls cgocallback with three arguments.
+// fn is the PC of a func(a unsafe.Pointer) function.
+TEXT crosscall2(SB),NOSPLIT|NOFRAME,$0
+ // Start with standard C stack frame layout and linkage
+ MOVD LR, R0
+ MOVD R0, 16(R1) // Save LR in caller's frame
+ MOVW CR, R0 // Save CR in caller's frame
+ MOVD R0, 8(R1)
+ MOVD R2, 24(R1) // Save TOC in caller's frame
+
+ BL saveregs2<>(SB)
+
+ MOVDU R1, (-288-3*8-FIXED_FRAME)(R1)
+
+ // Initialize Go ABI environment
+ BL runtime·reginit(SB)
+ BL runtime·load_g(SB)
+
+#ifdef GOARCH_ppc64
+ // ppc64 use elf ABI v1. we must get the real entry address from
+ // first slot of the function descriptor before call.
+ // Same for AIX.
+ MOVD 8(R3), R2
+ MOVD (R3), R3
+#endif
+ MOVD R3, FIXED_FRAME+0(R1) // fn unsafe.Pointer
+ MOVD R4, FIXED_FRAME+8(R1) // a unsafe.Pointer
+ // Skip R5 = n uint32
+ MOVD R6, FIXED_FRAME+16(R1) // ctxt uintptr
+ BL runtime·cgocallback(SB)
+
+ ADD $(288+3*8+FIXED_FRAME), R1
+
+ BL restoreregs2<>(SB)
+
+ MOVD 24(R1), R2
+ MOVD 8(R1), R0
+ MOVFL R0, $0xff
+ MOVD 16(R1), R0
+ MOVD R0, LR
+ RET
+
+TEXT saveregs2<>(SB),NOSPLIT|NOFRAME,$0
+ // O=-288; for R in R{14..31}; do echo "\tMOVD\t$R, $O(R1)"|sed s/R30/g/; ((O+=8)); done; for F in F{14..31}; do echo "\tFMOVD\t$F, $O(R1)"; ((O+=8)); done
+ MOVD R14, -288(R1)
+ MOVD R15, -280(R1)
+ MOVD R16, -272(R1)
+ MOVD R17, -264(R1)
+ MOVD R18, -256(R1)
+ MOVD R19, -248(R1)
+ MOVD R20, -240(R1)
+ MOVD R21, -232(R1)
+ MOVD R22, -224(R1)
+ MOVD R23, -216(R1)
+ MOVD R24, -208(R1)
+ MOVD R25, -200(R1)
+ MOVD R26, -192(R1)
+ MOVD R27, -184(R1)
+ MOVD R28, -176(R1)
+ MOVD R29, -168(R1)
+ MOVD g, -160(R1)
+ MOVD R31, -152(R1)
+ FMOVD F14, -144(R1)
+ FMOVD F15, -136(R1)
+ FMOVD F16, -128(R1)
+ FMOVD F17, -120(R1)
+ FMOVD F18, -112(R1)
+ FMOVD F19, -104(R1)
+ FMOVD F20, -96(R1)
+ FMOVD F21, -88(R1)
+ FMOVD F22, -80(R1)
+ FMOVD F23, -72(R1)
+ FMOVD F24, -64(R1)
+ FMOVD F25, -56(R1)
+ FMOVD F26, -48(R1)
+ FMOVD F27, -40(R1)
+ FMOVD F28, -32(R1)
+ FMOVD F29, -24(R1)
+ FMOVD F30, -16(R1)
+ FMOVD F31, -8(R1)
+
+ RET
+
+TEXT restoreregs2<>(SB),NOSPLIT|NOFRAME,$0
+ // O=-288; for R in R{14..31}; do echo "\tMOVD\t$O(R1), $R"|sed s/R30/g/; ((O+=8)); done; for F in F{14..31}; do echo "\tFMOVD\t$O(R1), $F"; ((O+=8)); done
+ MOVD -288(R1), R14
+ MOVD -280(R1), R15
+ MOVD -272(R1), R16
+ MOVD -264(R1), R17
+ MOVD -256(R1), R18
+ MOVD -248(R1), R19
+ MOVD -240(R1), R20
+ MOVD -232(R1), R21
+ MOVD -224(R1), R22
+ MOVD -216(R1), R23
+ MOVD -208(R1), R24
+ MOVD -200(R1), R25
+ MOVD -192(R1), R26
+ MOVD -184(R1), R27
+ MOVD -176(R1), R28
+ MOVD -168(R1), R29
+ MOVD -160(R1), g
+ MOVD -152(R1), R31
+ FMOVD -144(R1), F14
+ FMOVD -136(R1), F15
+ FMOVD -128(R1), F16
+ FMOVD -120(R1), F17
+ FMOVD -112(R1), F18
+ FMOVD -104(R1), F19
+ FMOVD -96(R1), F20
+ FMOVD -88(R1), F21
+ FMOVD -80(R1), F22
+ FMOVD -72(R1), F23
+ FMOVD -64(R1), F24
+ FMOVD -56(R1), F25
+ FMOVD -48(R1), F26
+ FMOVD -40(R1), F27
+ FMOVD -32(R1), F28
+ FMOVD -24(R1), F29
+ FMOVD -16(R1), F30
+ FMOVD -8(R1), F31
+
+ RET