Text file src/runtime/secret/asm_loong64.s

     1  // Copyright 2026 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  
     5  //go:build goexperiment.runtimesecret
     6  
     7  // Note: this assembly file is used for testing only.
     8  // We need to access registers directly to properly test
     9  // that secrets are erased and go test doesn't like to conditionally
    10  // include assembly files.
    11  // These functions defined in the package proper and we
    12  // rely on the linker to prune these away in regular builds
    13  
    14  #include "go_asm.h"
    15  #include "funcdata.h"
    16  
    17  #define REGTMP1	R27
    18  #define REGTMP2	R28
    19  
    20  #define dirtyReg(dstReg)		\
    21  	ADDV	$0x1, REGTMP1		\
    22  	MOVV	REGTMP1, dstReg		\
    23  
    24  
    25  #define dirtyVReg(dstReg)		\
    26  	ADDV	$0x1, REGTMP1		\
    27  	VMOVQ	REGTMP1, dstReg.V2	\
    28  
    29  
    30  #define dirtyXReg(dstReg)		\
    31  	ADDV	$0x1, REGTMP1		\
    32  	XVMOVQ	REGTMP1, dstReg.V4	\
    33  
    34  
    35  // func loadRegisters(p unsafe.Pointer)
    36  TEXT ·loadRegisters(SB),0,$0-8
    37  	MOVV	p+0(FP), R4
    38  
    39  	MOVV	(R4), R16
    40  	MOVV	(R4), R17
    41  	MOVV	(R4), R18
    42  	MOVV	(R4), R19
    43  
    44  	MOVD	(R4), F20
    45  	MOVD	(R4), F21
    46  	MOVD	(R4), F22
    47  	MOVD	(R4), F23
    48  
    49  	MOVBU	internal∕cpu·Loong64+const_offsetLOONG64HasLSX(SB), R5
    50  	BEQ	R5, return
    51  	VMOVQ	(R4), V24
    52  	VMOVQ	(R4), V25
    53  	VMOVQ	(R4), V26
    54  	VMOVQ	(R4), V27
    55  
    56  	MOVBU	internal∕cpu·Loong64+const_offsetLOONG64HasLASX(SB), R5
    57  	BEQ	R5, return
    58  	XVMOVQ	(R4), X28
    59  	XVMOVQ	(R4), X29
    60  	XVMOVQ	(R4), X30
    61  	XVMOVQ	(R4), X31
    62  return:
    63  	RET
    64  
    65  // func spillRegisters(p unsafe.Pointer) uintptr
    66  TEXT ·spillRegisters(SB),0,$0-16
    67  	MOVV	p+0(FP), R4
    68  	MOVV	$0, R5
    69  
    70  	MOVV	R16, 0(R4)
    71  	MOVV	R17, 8(R4)
    72  	MOVV	R18, 16(R4)
    73  	MOVV	R19, 24(R4)
    74  
    75  	MOVD	F20, 32(R4)
    76  	MOVD	F21, 40(R4)
    77  	MOVD	F22, 48(R4)
    78  	MOVD	F23, 56(R4)
    79  	ADDV	$64, R4
    80  	ADDV	$64, R5
    81  
    82  	MOVBU	internal∕cpu·Loong64+const_offsetLOONG64HasLSX(SB), R6
    83  	BEQ	R6, return
    84  	VMOVQ	V24, 0(R4)
    85  	VMOVQ	V25, 16(R4)
    86  	VMOVQ	V26, 32(R4)
    87  	VMOVQ	V27, 48(R4)
    88  	ADDV	$64, R4
    89  	ADDV	$64, R5
    90  
    91  	MOVBU	internal∕cpu·Loong64+const_offsetLOONG64HasLASX(SB), R6
    92  	BEQ	R6, return
    93  	XVMOVQ	X28, 0(R4)
    94  	XVMOVQ	X29, 32(R4)
    95  	XVMOVQ	X30, 64(R4)
    96  	XVMOVQ	X31, 96(R4)
    97  	ADDV	$128, R4
    98  	ADDV	$128, R5
    99  return:
   100  	MOVV	R5, ret+8(FP)
   101  	RET
   102  
   103  TEXT ·useSecret(SB),0,$0-24
   104  	NO_LOCAL_POINTERS
   105  
   106  	// Load secret into R27
   107  	MOVV	secret_base+0(FP), REGTMP2
   108  	MOVV	(REGTMP2), REGTMP1
   109  
   110  	MOVBU	internal∕cpu·Loong64+const_offsetLOONG64HasLASX(SB), REGTMP2
   111  	BNE	REGTMP2, dirtyLASX
   112  
   113  	MOVBU	internal∕cpu·Loong64+const_offsetLOONG64HasLSX(SB), REGTMP2
   114  	BNE	REGTMP2, dirtyLSX
   115  
   116  	// Dirty the floating point registers
   117  	dirtyReg(F0)
   118  	dirtyReg(F1)
   119  	dirtyReg(F2)
   120  	dirtyReg(F3)
   121  	dirtyReg(F4)
   122  	dirtyReg(F5)
   123  	dirtyReg(F6)
   124  	dirtyReg(F7)
   125  	dirtyReg(F8)
   126  	dirtyReg(F9)
   127  	dirtyReg(F10)
   128  	dirtyReg(F11)
   129  	dirtyReg(F12)
   130  	dirtyReg(F13)
   131  	dirtyReg(F14)
   132  	dirtyReg(F15)
   133  	dirtyReg(F16)
   134  	dirtyReg(F17)
   135  	dirtyReg(F18)
   136  	dirtyReg(F19)
   137  	dirtyReg(F20)
   138  	dirtyReg(F21)
   139  	dirtyReg(F22)
   140  	dirtyReg(F23)
   141  	dirtyReg(F24)
   142  	dirtyReg(F25)
   143  	dirtyReg(F26)
   144  	dirtyReg(F27)
   145  	dirtyReg(F28)
   146  	dirtyReg(F29)
   147  	dirtyReg(F30)
   148  	dirtyReg(F31)
   149  	JMP	dirtyInt
   150  
   151  	// Dirty the lsx registers
   152  dirtyLSX:
   153  	dirtyVReg(V0)
   154  	dirtyVReg(V1)
   155  	dirtyVReg(V2)
   156  	dirtyVReg(V3)
   157  	dirtyVReg(V4)
   158  	dirtyVReg(V5)
   159  	dirtyVReg(V6)
   160  	dirtyVReg(V7)
   161  	dirtyVReg(V8)
   162  	dirtyVReg(V9)
   163  	dirtyVReg(V10)
   164  	dirtyVReg(V11)
   165  	dirtyVReg(V12)
   166  	dirtyVReg(V13)
   167  	dirtyVReg(V14)
   168  	dirtyVReg(V15)
   169  	dirtyVReg(V16)
   170  	dirtyVReg(V17)
   171  	dirtyVReg(V18)
   172  	dirtyVReg(V19)
   173  	dirtyVReg(V20)
   174  	dirtyVReg(V21)
   175  	dirtyVReg(V22)
   176  	dirtyVReg(V23)
   177  	dirtyVReg(V24)
   178  	dirtyVReg(V25)
   179  	dirtyVReg(V26)
   180  	dirtyVReg(V27)
   181  	dirtyVReg(V28)
   182  	dirtyVReg(V29)
   183  	dirtyVReg(V30)
   184  	dirtyVReg(V31)
   185  	JMP	dirtyInt
   186  
   187  	// Dirty the lasx registers
   188  dirtyLASX:
   189  	dirtyXReg(X0)
   190  	dirtyXReg(X1)
   191  	dirtyXReg(X2)
   192  	dirtyXReg(X3)
   193  	dirtyXReg(X4)
   194  	dirtyXReg(X5)
   195  	dirtyXReg(X6)
   196  	dirtyXReg(X7)
   197  	dirtyXReg(X8)
   198  	dirtyXReg(X9)
   199  	dirtyXReg(X10)
   200  	dirtyXReg(X11)
   201  	dirtyXReg(X12)
   202  	dirtyXReg(X13)
   203  	dirtyXReg(X14)
   204  	dirtyXReg(X15)
   205  	dirtyXReg(X16)
   206  	dirtyXReg(X17)
   207  	dirtyXReg(X18)
   208  	dirtyXReg(X19)
   209  	dirtyXReg(X20)
   210  	dirtyXReg(X21)
   211  	dirtyXReg(X22)
   212  	dirtyXReg(X23)
   213  	dirtyXReg(X24)
   214  	dirtyXReg(X25)
   215  	dirtyXReg(X26)
   216  	dirtyXReg(X27)
   217  	dirtyXReg(X28)
   218  	dirtyXReg(X29)
   219  	dirtyXReg(X30)
   220  	dirtyXReg(X31)
   221  
   222  dirtyInt:
   223  	// Scatter secret across registers.
   224  	// Increment low byte so we can tell which register
   225  	// a leaking secret came from.
   226  	dirtyReg(R4)
   227  	dirtyReg(R5)
   228  	dirtyReg(R6)
   229  	dirtyReg(R7)
   230  	dirtyReg(R8)
   231  	dirtyReg(R9)
   232  	dirtyReg(R10)
   233  	dirtyReg(R11)
   234  	dirtyReg(R12)
   235  	dirtyReg(R13)
   236  	dirtyReg(R14)
   237  	dirtyReg(R15)
   238  	dirtyReg(R16)
   239  	dirtyReg(R17)
   240  	dirtyReg(R18)
   241  	dirtyReg(R19)
   242  	RET
   243  

View as plain text