github.com/primecitizens/pcz/std@v0.2.1/core/reflect/call_amd64.s (about)

     1  // SPDX-License-Identifier: Apache-2.0
     2  // Copyright 2023 The Prime Citizens
     3  //
     4  // Copyright 2018 The Go Authors. All rights reserved.
     5  // Use of this source code is governed by a BSD-style
     6  // license that can be found in the LICENSE file.
     7  
     8  //go:build pcz && amd64
     9  
    10  #include "textflag.h"
    11  #include "funcdata.h" // for NO_LOCAL_POINTERS
    12  
    13  // spillArgs stores return values from registers to a *core/abi.RegArgs in R12.
    14  TEXT ·spillArgs(SB),NOSPLIT,$0-0
    15  	MOVQ AX, 0(R12)
    16  	MOVQ BX, 8(R12)
    17  	MOVQ CX, 16(R12)
    18  	MOVQ DI, 24(R12)
    19  	MOVQ SI, 32(R12)
    20  	MOVQ R8, 40(R12)
    21  	MOVQ R9, 48(R12)
    22  	MOVQ R10, 56(R12)
    23  	MOVQ R11, 64(R12)
    24  	MOVQ X0, 72(R12)
    25  	MOVQ X1, 80(R12)
    26  	MOVQ X2, 88(R12)
    27  	MOVQ X3, 96(R12)
    28  	MOVQ X4, 104(R12)
    29  	MOVQ X5, 112(R12)
    30  	MOVQ X6, 120(R12)
    31  	MOVQ X7, 128(R12)
    32  	MOVQ X8, 136(R12)
    33  	MOVQ X9, 144(R12)
    34  	MOVQ X10, 152(R12)
    35  	MOVQ X11, 160(R12)
    36  	MOVQ X12, 168(R12)
    37  	MOVQ X13, 176(R12)
    38  	MOVQ X14, 184(R12)
    39  	RET
    40  
    41  // unspillArgs loads args into registers from a *core/abi.RegArgs in R12.
    42  TEXT ·unspillArgs(SB),NOSPLIT,$0-0
    43  	MOVQ 0(R12), AX
    44  	MOVQ 8(R12), BX
    45  	MOVQ 16(R12), CX
    46  	MOVQ 24(R12), DI
    47  	MOVQ 32(R12), SI
    48  	MOVQ 40(R12), R8
    49  	MOVQ 48(R12), R9
    50  	MOVQ 56(R12), R10
    51  	MOVQ 64(R12), R11
    52  	MOVQ 72(R12), X0
    53  	MOVQ 80(R12), X1
    54  	MOVQ 88(R12), X2
    55  	MOVQ 96(R12), X3
    56  	MOVQ 104(R12), X4
    57  	MOVQ 112(R12), X5
    58  	MOVQ 120(R12), X6
    59  	MOVQ 128(R12), X7
    60  	MOVQ 136(R12), X8
    61  	MOVQ 144(R12), X9
    62  	MOVQ 152(R12), X10
    63  	MOVQ 160(R12), X11
    64  	MOVQ 168(R12), X12
    65  	MOVQ 176(R12), X13
    66  	MOVQ 184(R12), X14
    67  	RET
    68  
    69  // reflectcall: call a function with the given argument list
    70  // func call(stackArgsType *_type, f *FuncVal, stackArgs *byte, stackArgsSize, stackRetOffset, frameSize uint32, regArgs *abi.RegArgs).
    71  // we don't have variable-sized frames, so we use a small number
    72  // of constant-sized-frame functions to encode a few bits of size in the pc.
    73  // Caution: ugly multiline assembly macros in your future!
    74  
    75  #define DISPATCH(NAME,MAXSIZE)		\
    76  	CMPQ CX, $MAXSIZE;		\
    77  	JA 3(PC);			\
    78  	MOVQ $NAME(SB), AX;		\
    79  	JMP AX
    80  // Note: can't just "JMP NAME(SB)" - bad inlining results.
    81  
    82  TEXT ·Call(SB), NOSPLIT, $0-48
    83  	MOVLQZX frameSize+32(FP), CX
    84  	DISPATCH(·call16, 16)
    85  	DISPATCH(·call32, 32)
    86  	DISPATCH(·call64, 64)
    87  	DISPATCH(·call128, 128)
    88  	DISPATCH(·call256, 256)
    89  	DISPATCH(·call512, 512)
    90  	DISPATCH(·call1024, 1024)
    91  	DISPATCH(·call2048, 2048)
    92  	DISPATCH(·call4096, 4096)
    93  	DISPATCH(·call8192, 8192)
    94  	DISPATCH(·call16384, 16384)
    95  	DISPATCH(·call32768, 32768)
    96  	DISPATCH(·call65536, 65536)
    97  	DISPATCH(·call131072, 131072)
    98  	DISPATCH(·call262144, 262144)
    99  	DISPATCH(·call524288, 524288)
   100  	DISPATCH(·call1048576, 1048576)
   101  	DISPATCH(·call2097152, 2097152)
   102  	DISPATCH(·call4194304, 4194304)
   103  	DISPATCH(·call8388608, 8388608)
   104  	DISPATCH(·call16777216, 16777216)
   105  	DISPATCH(·call33554432, 33554432)
   106  	DISPATCH(·call67108864, 67108864)
   107  	DISPATCH(·call134217728, 134217728)
   108  	DISPATCH(·call268435456, 268435456)
   109  	DISPATCH(·call536870912, 536870912)
   110  	DISPATCH(·call1073741824, 1073741824)
   111  	MOVQ $·badreflectcall(SB), AX
   112  	JMP AX
   113  
   114  #define CALLFN(NAME,MAXSIZE)			\
   115  TEXT NAME(SB), WRAPPER, $MAXSIZE-48;		\
   116  	NO_LOCAL_POINTERS;			\
   117  	/* copy arguments to stack */		\
   118  	MOVQ stackArgs+16(FP), SI;		\
   119  	MOVLQZX stackArgsSize+24(FP), CX;		\
   120  	MOVQ SP, DI;				\
   121  	REP;MOVSB;				\
   122  	/* set up argument registers */		\
   123  	MOVQ    regArgs+40(FP), R12;		\
   124  	CALL    ·unspillArgs(SB);		\
   125  	/* call function */			\
   126  	MOVQ f+8(FP), DX;			\
   127  	PCDATA  $PCDATA_StackMapIndex, $0;	\
   128  	MOVQ (DX), R12;			\
   129  	CALL R12;				\
   130  	/* copy register return values back */		\
   131  	MOVQ    regArgs+40(FP), R12;		\
   132  	CALL    ·spillArgs(SB);		\
   133  	MOVLQZX stackArgsSize+24(FP), CX;		\
   134  	MOVLQZX stackRetOffset+28(FP), BX;		\
   135  	MOVQ stackArgs+16(FP), DI;		\
   136  	MOVQ stackArgsType+0(FP), DX;		\
   137  	MOVQ SP, SI;				\
   138  	ADDQ BX, DI;				\
   139  	ADDQ BX, SI;				\
   140  	SUBQ BX, CX;				\
   141  	CALL callRet<>(SB);			\
   142  	RET
   143  
   144  // callRet copies return values back at the end of call*. This is a
   145  // separate function so it can allocate stack space for the arguments
   146  // to reflectcallmove. It does not follow the Go ABI; it expects its
   147  // arguments in registers.
   148  TEXT callRet<>(SB), NOSPLIT, $40-0
   149  	NO_LOCAL_POINTERS
   150  	MOVQ DX, 0(SP)
   151  	MOVQ DI, 8(SP)
   152  	MOVQ SI, 16(SP)
   153  	MOVQ CX, 24(SP)
   154  	MOVQ R12, 32(SP)
   155  	CALL ·reflectcallmove(SB)
   156  	RET
   157  
   158  CALLFN(·call16, 16)
   159  CALLFN(·call32, 32)
   160  CALLFN(·call64, 64)
   161  CALLFN(·call128, 128)
   162  CALLFN(·call256, 256)
   163  CALLFN(·call512, 512)
   164  CALLFN(·call1024, 1024)
   165  CALLFN(·call2048, 2048)
   166  CALLFN(·call4096, 4096)
   167  CALLFN(·call8192, 8192)
   168  CALLFN(·call16384, 16384)
   169  CALLFN(·call32768, 32768)
   170  CALLFN(·call65536, 65536)
   171  CALLFN(·call131072, 131072)
   172  CALLFN(·call262144, 262144)
   173  CALLFN(·call524288, 524288)
   174  CALLFN(·call1048576, 1048576)
   175  CALLFN(·call2097152, 2097152)
   176  CALLFN(·call4194304, 4194304)
   177  CALLFN(·call8388608, 8388608)
   178  CALLFN(·call16777216, 16777216)
   179  CALLFN(·call33554432, 33554432)
   180  CALLFN(·call67108864, 67108864)
   181  CALLFN(·call134217728, 134217728)
   182  CALLFN(·call268435456, 268435456)
   183  CALLFN(·call536870912, 536870912)
   184  CALLFN(·call1073741824, 1073741824)