Text file src/runtime/rt0_linux_ppc64le.s

     1  // Copyright 2016 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  #include "go_asm.h"
     6  #include "textflag.h"
     7  
     8  TEXT _rt0_ppc64le_linux(SB),NOSPLIT,$0
     9  	XOR R0, R0	  // Make sure R0 is zero before _main
    10  	BR _main<>(SB)
    11  
    12  TEXT _rt0_ppc64le_linux_lib(SB),NOSPLIT,$-8
    13  	// Start with standard C stack frame layout and linkage.
    14  	MOVD	LR, R0
    15  	MOVD	R0, 16(R1) // Save LR in caller's frame.
    16  	MOVW	CR, R0     // Save CR in caller's frame
    17  	MOVD	R0, 8(R1)
    18  	MOVDU	R1, -320(R1) // Allocate frame.
    19  
    20  	// Preserve callee-save registers.
    21  	MOVD	R14, 24(R1)
    22  	MOVD	R15, 32(R1)
    23  	MOVD	R16, 40(R1)
    24  	MOVD	R17, 48(R1)
    25  	MOVD	R18, 56(R1)
    26  	MOVD	R19, 64(R1)
    27  	MOVD	R20, 72(R1)
    28  	MOVD	R21, 80(R1)
    29  	MOVD	R22, 88(R1)
    30  	MOVD	R23, 96(R1)
    31  	MOVD	R24, 104(R1)
    32  	MOVD	R25, 112(R1)
    33  	MOVD	R26, 120(R1)
    34  	MOVD	R27, 128(R1)
    35  	MOVD	R28, 136(R1)
    36  	MOVD	R29, 144(R1)
    37  	MOVD	g, 152(R1) // R30
    38  	MOVD	R31, 160(R1)
    39  	FMOVD	F14, 168(R1)
    40  	FMOVD	F15, 176(R1)
    41  	FMOVD	F16, 184(R1)
    42  	FMOVD	F17, 192(R1)
    43  	FMOVD	F18, 200(R1)
    44  	FMOVD	F19, 208(R1)
    45  	FMOVD	F20, 216(R1)
    46  	FMOVD	F21, 224(R1)
    47  	FMOVD	F22, 232(R1)
    48  	FMOVD	F23, 240(R1)
    49  	FMOVD	F24, 248(R1)
    50  	FMOVD	F25, 256(R1)
    51  	FMOVD	F26, 264(R1)
    52  	FMOVD	F27, 272(R1)
    53  	FMOVD	F28, 280(R1)
    54  	FMOVD	F29, 288(R1)
    55  	FMOVD	F30, 296(R1)
    56  	FMOVD	F31, 304(R1)
    57  
    58  	MOVD	R3, _rt0_ppc64le_linux_lib_argc<>(SB)
    59  	MOVD	R4, _rt0_ppc64le_linux_lib_argv<>(SB)
    60  
    61  	// Synchronous initialization.
    62  	MOVD	$runtime·reginit(SB), R12
    63  	MOVD	R12, CTR
    64  	BL	(CTR)
    65  	MOVD	$runtime·libpreinit(SB), R12
    66  	MOVD	R12, CTR
    67  	BL	(CTR)
    68  
    69  	// Create a new thread to do the runtime initialization and return.
    70  	MOVD	_cgo_sys_thread_create(SB), R12
    71  	CMP	$0, R12
    72  	BEQ	nocgo
    73  	MOVD	$_rt0_ppc64le_linux_lib_go(SB), R3
    74  	MOVD	$0, R4
    75  	MOVD	R12, CTR
    76  	BL	(CTR)
    77  	BR	done
    78  
    79  nocgo:
    80  	MOVD	$0x800000, R12                     // stacksize = 8192KB
    81  	MOVD	R12, 8(R1)
    82  	MOVD	$_rt0_ppc64le_linux_lib_go(SB), R12
    83  	MOVD	R12, 16(R1)
    84  	MOVD	$runtime·newosproc0(SB),R12
    85  	MOVD	R12, CTR
    86  	BL	(CTR)
    87  
    88  done:
    89  	// Restore saved registers.
    90  	MOVD	24(R1), R14
    91  	MOVD	32(R1), R15
    92  	MOVD	40(R1), R16
    93  	MOVD	48(R1), R17
    94  	MOVD	56(R1), R18
    95  	MOVD	64(R1), R19
    96  	MOVD	72(R1), R20
    97  	MOVD	80(R1), R21
    98  	MOVD	88(R1), R22
    99  	MOVD	96(R1), R23
   100  	MOVD	104(R1), R24
   101  	MOVD	112(R1), R25
   102  	MOVD	120(R1), R26
   103  	MOVD	128(R1), R27
   104  	MOVD	136(R1), R28
   105  	MOVD	144(R1), R29
   106  	MOVD	152(R1), g // R30
   107  	MOVD	160(R1), R31
   108  	FMOVD	168(R1), F14
   109  	FMOVD	176(R1), F15
   110  	FMOVD	184(R1), F16
   111  	FMOVD	192(R1), F17
   112  	FMOVD	200(R1), F18
   113  	FMOVD	208(R1), F19
   114  	FMOVD	216(R1), F20
   115  	FMOVD	224(R1), F21
   116  	FMOVD	232(R1), F22
   117  	FMOVD	240(R1), F23
   118  	FMOVD	248(R1), F24
   119  	FMOVD	256(R1), F25
   120  	FMOVD	264(R1), F26
   121  	FMOVD	272(R1), F27
   122  	FMOVD	280(R1), F28
   123  	FMOVD	288(R1), F29
   124  	FMOVD	296(R1), F30
   125  	FMOVD	304(R1), F31
   126  
   127  	ADD	$320, R1
   128  	MOVD	8(R1), R0
   129  	MOVFL	R0, $0xff
   130  	MOVD	16(R1), R0
   131  	MOVD	R0, LR
   132  	RET
   133  
   134  TEXT _rt0_ppc64le_linux_lib_go(SB),NOSPLIT,$0
   135  	MOVD	_rt0_ppc64le_linux_lib_argc<>(SB), R3
   136  	MOVD	_rt0_ppc64le_linux_lib_argv<>(SB), R4
   137  	MOVD	$runtime·rt0_go(SB), R12
   138  	MOVD	R12, CTR
   139  	BR	(CTR)
   140  
   141  DATA _rt0_ppc64le_linux_lib_argc<>(SB)/8, $0
   142  GLOBL _rt0_ppc64le_linux_lib_argc<>(SB),NOPTR, $8
   143  DATA _rt0_ppc64le_linux_lib_argv<>(SB)/8, $0
   144  GLOBL _rt0_ppc64le_linux_lib_argv<>(SB),NOPTR, $8
   145  
   146  TEXT _main<>(SB),NOSPLIT,$-8
   147  	// In a statically linked binary, the stack contains argc,
   148  	// argv as argc string pointers followed by a NULL, envv as a
   149  	// sequence of string pointers followed by a NULL, and auxv.
   150  	// The TLS pointer should be initialized to 0.
   151  	//
   152  	// In an ELFv2 compliant dynamically linked binary, R3 contains argc,
   153  	// R4 contains argv, R5 contains envp, R6 contains auxv, and R13
   154  	// contains the TLS pointer.
   155  	//
   156  	// When loading via glibc, the first doubleword on the stack points
   157  	// to NULL a value. (that is *(uintptr)(R1) == 0). This is used to
   158  	// differentiate static vs dynamicly linked binaries.
   159  	//
   160  	// If loading with the musl loader, it doesn't follow the ELFv2 ABI. It
   161  	// passes argc/argv similar to the linux kernel, R13 (TLS) is
   162  	// initialized, and R3/R4 are undefined.
   163  	MOVD	(R1), R12
   164  	CMP	R0, R12
   165  	BEQ	tls_and_argcv_in_reg
   166  
   167  	// Arguments are passed via the stack (musl loader or a static binary)
   168  	MOVD	0(R1), R3 // argc
   169  	ADD	$8, R1, R4 // argv
   170  
   171  	// Did the TLS pointer get set? If so, don't change it (e.g musl).
   172  	CMP	R0, R13
   173  	BNE	tls_and_argcv_in_reg
   174  
   175  	MOVD	$runtime·m0+m_tls(SB), R13 // TLS
   176  	ADD	$0x7000, R13
   177  
   178  tls_and_argcv_in_reg:
   179  	BR	main(SB)
   180  
   181  TEXT main(SB),NOSPLIT,$-8
   182  	MOVD	$runtime·rt0_go(SB), R12
   183  	MOVD	R12, CTR
   184  	BR	(CTR)
   185  

View as plain text