asm_ppc64le.s 2.0 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182
  1. // Copyright 2014 The Go Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style
  3. // license that can be found in the LICENSE file.
  4. #include "textflag.h"
  5. #include "abi_ppc64x.h"
  6. // Called by C code generated by cmd/cgo.
  7. // func crosscall2(fn, a unsafe.Pointer, n int32, ctxt uintptr)
  8. // Saves C callee-saved registers and calls cgocallback with three arguments.
  9. // fn is the PC of a func(a unsafe.Pointer) function.
  10. //
  11. // This is a simplified version that only saves GPR and FPR registers,
  12. // not vector registers. This keeps the stack frame smaller to avoid
  13. // exceeding the nosplit stack limit.
  14. //
  15. // On PPC64LE ELFv2, callee-save registers are:
  16. // R14-R31 (18 GPRs = 144 bytes)
  17. // F14-F31 (18 FPRs = 144 bytes)
  18. // CR2-CR4 (saved in CR field)
  19. //
  20. // Stack layout (must be 16-byte aligned):
  21. // 32 (FIXED_FRAME) + 24 (args) + 144 (GPR) + 144 (FPR) = 344
  22. // Rounded to 352 for 16-byte alignment.
  23. #define FIXED_FRAME 32
  24. #define SAVE_SIZE 352
  25. #define GPR_OFFSET (FIXED_FRAME+24)
  26. #define FPR_OFFSET (GPR_OFFSET+SAVE_GPR_SIZE)
  27. TEXT crosscall2(SB), NOSPLIT|NOFRAME, $0
  28. // Save LR and CR in caller's frame per ELFv2 ABI
  29. MOVD LR, R0
  30. MOVD R0, 16(R1)
  31. MOVW CR, R0
  32. MOVD R0, 8(R1)
  33. // Allocate our stack frame
  34. MOVDU R1, -SAVE_SIZE(R1)
  35. // Save TOC (R2) in case needed
  36. MOVD R2, 24(R1)
  37. // Save callee-save GPRs
  38. SAVE_GPR(GPR_OFFSET)
  39. // Save callee-save FPRs
  40. SAVE_FPR(FPR_OFFSET)
  41. // Initialize R0 to 0 as expected by Go
  42. MOVD $0, R0
  43. // Load the current g.
  44. BL runtime·load_g(SB)
  45. // Set up arguments for cgocallback
  46. MOVD R3, FIXED_FRAME+0(R1) // fn unsafe.Pointer
  47. MOVD R4, FIXED_FRAME+8(R1) // a unsafe.Pointer
  48. // Skip R5 = n uint32
  49. MOVD R6, FIXED_FRAME+16(R1) // ctxt uintptr
  50. BL runtime·cgocallback(SB)
  51. // Restore callee-save FPRs
  52. RESTORE_FPR(FPR_OFFSET)
  53. // Restore callee-save GPRs
  54. RESTORE_GPR(GPR_OFFSET)
  55. // Restore TOC
  56. MOVD 24(R1), R2
  57. // Deallocate stack frame
  58. ADD $SAVE_SIZE, R1
  59. // Restore LR and CR from caller's frame
  60. MOVD 16(R1), R0
  61. MOVD R0, LR
  62. MOVD 8(R1), R0
  63. MOVW R0, CR
  64. RET