...

Text file src/runtime/sys_linux_ppc64x.s

Documentation: runtime

     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
     5//go:build linux && (ppc64 || ppc64le)
     6
     7//
     8// System calls and other sys.stuff for ppc64, Linux
     9//
    10
    11#include "go_asm.h"
    12#include "go_tls.h"
    13#include "textflag.h"
    14#include "asm_ppc64x.h"
    15#include "cgo/abi_ppc64x.h"
    16
    17#define SYS_exit		  1
    18#define SYS_read		  3
    19#define SYS_write		  4
    20#define SYS_open		  5
    21#define SYS_close		  6
    22#define SYS_getpid		 20
    23#define SYS_kill		 37
    24#define SYS_brk			 45
    25#define SYS_mmap		 90
    26#define SYS_munmap		 91
    27#define SYS_setitimer		104
    28#define SYS_clone		120
    29#define SYS_sched_yield		158
    30#define SYS_nanosleep		162
    31#define SYS_rt_sigreturn	172
    32#define SYS_rt_sigaction	173
    33#define SYS_rt_sigprocmask	174
    34#define SYS_sigaltstack		185
    35#define SYS_madvise		205
    36#define SYS_mincore		206
    37#define SYS_gettid		207
    38#define SYS_futex		221
    39#define SYS_sched_getaffinity	223
    40#define SYS_exit_group		234
    41#define SYS_timer_create	240
    42#define SYS_timer_settime	241
    43#define SYS_timer_delete	244
    44#define SYS_clock_gettime	246
    45#define SYS_tgkill		250
    46#define SYS_pipe2		317
    47
    48TEXT runtime·exit(SB),NOSPLIT|NOFRAME,$0-4
    49	MOVW	code+0(FP), R3
    50	SYSCALL	$SYS_exit_group
    51	RET
    52
    53// func exitThread(wait *atomic.Uint32)
    54TEXT runtime·exitThread(SB),NOSPLIT|NOFRAME,$0-8
    55	MOVD	wait+0(FP), R1
    56	// We're done using the stack.
    57	MOVW	$0, R2
    58	SYNC
    59	MOVW	R2, (R1)
    60	MOVW	$0, R3	// exit code
    61	SYSCALL	$SYS_exit
    62	JMP	0(PC)
    63
    64TEXT runtime·open(SB),NOSPLIT|NOFRAME,$0-20
    65	MOVD	name+0(FP), R3
    66	MOVW	mode+8(FP), R4
    67	MOVW	perm+12(FP), R5
    68	SYSCALL	$SYS_open
    69	BVC	2(PC)
    70	MOVW	$-1, R3
    71	MOVW	R3, ret+16(FP)
    72	RET
    73
    74TEXT runtime·closefd(SB),NOSPLIT|NOFRAME,$0-12
    75	MOVW	fd+0(FP), R3
    76	SYSCALL	$SYS_close
    77	BVC	2(PC)
    78	MOVW	$-1, R3
    79	MOVW	R3, ret+8(FP)
    80	RET
    81
    82TEXT runtime·write1(SB),NOSPLIT|NOFRAME,$0-28
    83	MOVD	fd+0(FP), R3
    84	MOVD	p+8(FP), R4
    85	MOVW	n+16(FP), R5
    86	SYSCALL	$SYS_write
    87	BVC	2(PC)
    88	NEG	R3	// caller expects negative errno
    89	MOVW	R3, ret+24(FP)
    90	RET
    91
    92TEXT runtime·read(SB),NOSPLIT|NOFRAME,$0-28
    93	MOVW	fd+0(FP), R3
    94	MOVD	p+8(FP), R4
    95	MOVW	n+16(FP), R5
    96	SYSCALL	$SYS_read
    97	BVC	2(PC)
    98	NEG	R3	// caller expects negative errno
    99	MOVW	R3, ret+24(FP)
   100	RET
   101
   102// func pipe2(flags int32) (r, w int32, errno int32)
   103TEXT runtime·pipe2(SB),NOSPLIT|NOFRAME,$0-20
   104	ADD	$FIXED_FRAME+8, R1, R3
   105	MOVW	flags+0(FP), R4
   106	SYSCALL	$SYS_pipe2
   107	MOVW	R3, errno+16(FP)
   108	RET
   109
   110// func usleep(usec uint32)
   111TEXT runtime·usleep(SB),NOSPLIT,$16-4
   112	MOVW	usec+0(FP), R3
   113
   114	// Use magic constant 0x8637bd06 and shift right 51
   115	// to perform usec/1000000.
   116	MOVD	$0x8637bd06, R4
   117	MULLD	R3, R4, R4	// Convert usec to S.
   118	SRD	$51, R4, R4
   119	MOVD	R4, 8(R1)	// Store to tv_sec
   120
   121	MOVD	$1000000, R5
   122	MULLW	R4, R5, R5	// Convert tv_sec back into uS
   123	SUB	R5, R3, R5	// Compute remainder uS.
   124	MULLD	$1000, R5, R5	// Convert to nsec
   125	MOVD	R5, 16(R1)	// Store to tv_nsec
   126
   127	// nanosleep(&ts, 0)
   128	ADD	$8, R1, R3
   129	MOVW	$0, R4
   130	SYSCALL	$SYS_nanosleep
   131	RET
   132
   133TEXT runtime·gettid(SB),NOSPLIT,$0-4
   134	SYSCALL	$SYS_gettid
   135	MOVW	R3, ret+0(FP)
   136	RET
   137
   138TEXT runtime·raise(SB),NOSPLIT|NOFRAME,$0
   139	SYSCALL	$SYS_getpid
   140	MOVW	R3, R14
   141	SYSCALL	$SYS_gettid
   142	MOVW	R3, R4	// arg 2 tid
   143	MOVW	R14, R3	// arg 1 pid
   144	MOVW	sig+0(FP), R5	// arg 3
   145	SYSCALL	$SYS_tgkill
   146	RET
   147
   148TEXT runtime·raiseproc(SB),NOSPLIT|NOFRAME,$0
   149	SYSCALL	$SYS_getpid
   150	MOVW	R3, R3	// arg 1 pid
   151	MOVW	sig+0(FP), R4	// arg 2
   152	SYSCALL	$SYS_kill
   153	RET
   154
   155TEXT ·getpid(SB),NOSPLIT|NOFRAME,$0-8
   156	SYSCALL $SYS_getpid
   157	MOVD	R3, ret+0(FP)
   158	RET
   159
   160TEXT ·tgkill(SB),NOSPLIT|NOFRAME,$0-24
   161	MOVD	tgid+0(FP), R3
   162	MOVD	tid+8(FP), R4
   163	MOVD	sig+16(FP), R5
   164	SYSCALL $SYS_tgkill
   165	RET
   166
   167TEXT runtime·setitimer(SB),NOSPLIT|NOFRAME,$0-24
   168	MOVW	mode+0(FP), R3
   169	MOVD	new+8(FP), R4
   170	MOVD	old+16(FP), R5
   171	SYSCALL	$SYS_setitimer
   172	RET
   173
   174TEXT runtime·timer_create(SB),NOSPLIT,$0-28
   175	MOVW	clockid+0(FP), R3
   176	MOVD	sevp+8(FP), R4
   177	MOVD	timerid+16(FP), R5
   178	SYSCALL	$SYS_timer_create
   179	MOVW	R3, ret+24(FP)
   180	RET
   181
   182TEXT runtime·timer_settime(SB),NOSPLIT,$0-28
   183	MOVW	timerid+0(FP), R3
   184	MOVW	flags+4(FP), R4
   185	MOVD	new+8(FP), R5
   186	MOVD	old+16(FP), R6
   187	SYSCALL	$SYS_timer_settime
   188	MOVW	R3, ret+24(FP)
   189	RET
   190
   191TEXT runtime·timer_delete(SB),NOSPLIT,$0-12
   192	MOVW	timerid+0(FP), R3
   193	SYSCALL	$SYS_timer_delete
   194	MOVW	R3, ret+8(FP)
   195	RET
   196
   197TEXT runtime·mincore(SB),NOSPLIT|NOFRAME,$0-28
   198	MOVD	addr+0(FP), R3
   199	MOVD	n+8(FP), R4
   200	MOVD	dst+16(FP), R5
   201	SYSCALL	$SYS_mincore
   202	NEG	R3		// caller expects negative errno
   203	MOVW	R3, ret+24(FP)
   204	RET
   205
   206// func walltime() (sec int64, nsec int32)
   207TEXT runtime·walltime(SB),NOSPLIT,$16-12
   208	MOVD	R1, R15		// R15 is unchanged by C code
   209	MOVD	g_m(g), R21	// R21 = m
   210
   211	MOVD	$0, R3		// CLOCK_REALTIME
   212
   213	MOVD	runtime·vdsoClockgettimeSym(SB), R12	// Check for VDSO availability
   214	CMP	R12, R0
   215	BEQ	fallback
   216
   217	// Set vdsoPC and vdsoSP for SIGPROF traceback.
   218	// Save the old values on stack and restore them on exit,
   219	// so this function is reentrant.
   220	MOVD	m_vdsoPC(R21), R4
   221	MOVD	m_vdsoSP(R21), R5
   222	MOVD	R4, 32(R1)
   223	MOVD	R5, 40(R1)
   224
   225	MOVD	LR, R14
   226	MOVD	$ret-FIXED_FRAME(FP), R5 // caller's SP
   227	MOVD	R14, m_vdsoPC(R21)
   228	MOVD	R5, m_vdsoSP(R21)
   229
   230	MOVD	m_curg(R21), R6
   231	CMP	g, R6
   232	BNE	noswitch
   233
   234	MOVD	m_g0(R21), R7
   235	MOVD	(g_sched+gobuf_sp)(R7), R1	// Set SP to g0 stack
   236
   237noswitch:
   238	SUB	$16, R1                 // Space for results
   239	RLDICR	$0, R1, $59, R1         // Align for C code
   240	MOVD	R12, CTR
   241	MOVD	R1, R4
   242
   243	// Store g on gsignal's stack, so if we receive a signal
   244	// during VDSO code we can find the g.
   245	// If we don't have a signal stack, we won't receive signal,
   246	// so don't bother saving g.
   247	// When using cgo, we already saved g on TLS, also don't save
   248	// g here.
   249	// Also don't save g if we are already on the signal stack.
   250	// We won't get a nested signal.
   251	MOVBZ	runtime·iscgo(SB), R22
   252	CMP	R22, $0
   253	BNE	nosaveg
   254	MOVD	m_gsignal(R21), R22	// g.m.gsignal
   255	CMP	R22, $0
   256	BEQ	nosaveg
   257
   258	CMP	g, R22
   259	BEQ	nosaveg
   260	MOVD	(g_stack+stack_lo)(R22), R22 // g.m.gsignal.stack.lo
   261	MOVD	g, (R22)
   262
   263	BL	(CTR)	// Call from VDSO
   264
   265	MOVD	$0, (R22)	// clear g slot, R22 is unchanged by C code
   266
   267	JMP	finish
   268
   269nosaveg:
   270	BL	(CTR)	// Call from VDSO
   271
   272finish:
   273	MOVD	$0, R0		// Restore R0
   274	MOVD	0(R1), R3	// sec
   275	MOVD	8(R1), R5	// nsec
   276	MOVD	R15, R1		// Restore SP
   277
   278	// Restore vdsoPC, vdsoSP
   279	// We don't worry about being signaled between the two stores.
   280	// If we are not in a signal handler, we'll restore vdsoSP to 0,
   281	// and no one will care about vdsoPC. If we are in a signal handler,
   282	// we cannot receive another signal.
   283	MOVD	40(R1), R6
   284	MOVD	R6, m_vdsoSP(R21)
   285	MOVD	32(R1), R6
   286	MOVD	R6, m_vdsoPC(R21)
   287
   288return:
   289	MOVD	R3, sec+0(FP)
   290	MOVW	R5, nsec+8(FP)
   291	RET
   292
   293	// Syscall fallback
   294fallback:
   295	ADD	$32, R1, R4
   296	SYSCALL $SYS_clock_gettime
   297	MOVD	32(R1), R3
   298	MOVD	40(R1), R5
   299	JMP	return
   300
   301TEXT runtime·nanotime1(SB),NOSPLIT,$16-8
   302	MOVD	$1, R3		// CLOCK_MONOTONIC
   303
   304	MOVD	R1, R15		// R15 is unchanged by C code
   305	MOVD	g_m(g), R21	// R21 = m
   306
   307	MOVD	runtime·vdsoClockgettimeSym(SB), R12	// Check for VDSO availability
   308	CMP	R12, R0
   309	BEQ	fallback
   310
   311	// Set vdsoPC and vdsoSP for SIGPROF traceback.
   312	// Save the old values on stack and restore them on exit,
   313	// so this function is reentrant.
   314	MOVD	m_vdsoPC(R21), R4
   315	MOVD	m_vdsoSP(R21), R5
   316	MOVD	R4, 32(R1)
   317	MOVD	R5, 40(R1)
   318
   319	MOVD	LR, R14				// R14 is unchanged by C code
   320	MOVD	$ret-FIXED_FRAME(FP), R5	// caller's SP
   321	MOVD	R14, m_vdsoPC(R21)
   322	MOVD	R5, m_vdsoSP(R21)
   323
   324	MOVD	m_curg(R21), R6
   325	CMP	g, R6
   326	BNE	noswitch
   327
   328	MOVD	m_g0(R21), R7
   329	MOVD	(g_sched+gobuf_sp)(R7), R1	// Set SP to g0 stack
   330
   331noswitch:
   332	SUB	$16, R1			// Space for results
   333	RLDICR	$0, R1, $59, R1		// Align for C code
   334	MOVD	R12, CTR
   335	MOVD	R1, R4
   336
   337	// Store g on gsignal's stack, so if we receive a signal
   338	// during VDSO code we can find the g.
   339	// If we don't have a signal stack, we won't receive signal,
   340	// so don't bother saving g.
   341	// When using cgo, we already saved g on TLS, also don't save
   342	// g here.
   343	// Also don't save g if we are already on the signal stack.
   344	// We won't get a nested signal.
   345	MOVBZ	runtime·iscgo(SB), R22
   346	CMP	R22, $0
   347	BNE	nosaveg
   348	MOVD	m_gsignal(R21), R22	// g.m.gsignal
   349	CMP	R22, $0
   350	BEQ	nosaveg
   351
   352	CMP	g, R22
   353	BEQ	nosaveg
   354	MOVD	(g_stack+stack_lo)(R22), R22 // g.m.gsignal.stack.lo
   355	MOVD	g, (R22)
   356
   357	BL	(CTR)	// Call from VDSO
   358
   359	MOVD	$0, (R22)	// clear g slot, R22 is unchanged by C code
   360
   361	JMP	finish
   362
   363nosaveg:
   364	BL	(CTR)	// Call from VDSO
   365
   366finish:
   367	MOVD	$0, R0			// Restore R0
   368	MOVD	0(R1), R3		// sec
   369	MOVD	8(R1), R5		// nsec
   370	MOVD	R15, R1			// Restore SP
   371
   372	// Restore vdsoPC, vdsoSP
   373	// We don't worry about being signaled between the two stores.
   374	// If we are not in a signal handler, we'll restore vdsoSP to 0,
   375	// and no one will care about vdsoPC. If we are in a signal handler,
   376	// we cannot receive another signal.
   377	MOVD	40(R1), R6
   378	MOVD	R6, m_vdsoSP(R21)
   379	MOVD	32(R1), R6
   380	MOVD	R6, m_vdsoPC(R21)
   381
   382return:
   383	// sec is in R3, nsec in R5
   384	// return nsec in R3
   385	MOVD	$1000000000, R4
   386	MULLD	R4, R3
   387	ADD	R5, R3
   388	MOVD	R3, ret+0(FP)
   389	RET
   390
   391	// Syscall fallback
   392fallback:
   393	ADD	$32, R1, R4
   394	SYSCALL $SYS_clock_gettime
   395	MOVD	32(R1), R3
   396	MOVD	40(R1), R5
   397	JMP	return
   398
   399TEXT runtime·rtsigprocmask(SB),NOSPLIT|NOFRAME,$0-28
   400	MOVW	how+0(FP), R3
   401	MOVD	new+8(FP), R4
   402	MOVD	old+16(FP), R5
   403	MOVW	size+24(FP), R6
   404	SYSCALL	$SYS_rt_sigprocmask
   405	BVC	2(PC)
   406	MOVD	R0, 0xf0(R0)	// crash
   407	RET
   408
   409TEXT runtime·rt_sigaction(SB),NOSPLIT|NOFRAME,$0-36
   410	MOVD	sig+0(FP), R3
   411	MOVD	new+8(FP), R4
   412	MOVD	old+16(FP), R5
   413	MOVD	size+24(FP), R6
   414	SYSCALL	$SYS_rt_sigaction
   415	BVC	2(PC)
   416	NEG	R3	// caller expects negative errno
   417	MOVW	R3, ret+32(FP)
   418	RET
   419
   420#ifdef GOARCH_ppc64le
   421// Call the function stored in _cgo_sigaction using the GCC calling convention.
   422TEXT runtime·callCgoSigaction(SB),NOSPLIT,$0
   423	MOVD    sig+0(FP), R3
   424	MOVD    new+8(FP), R4
   425	MOVD    old+16(FP), R5
   426	MOVD     _cgo_sigaction(SB), R12
   427	MOVD    R12, CTR                // R12 should contain the function address
   428	MOVD    R1, R15                 // Save R1
   429	MOVD    R2, 24(R1)              // Save R2
   430	SUB     $48, R1                 // reserve 32 (frame) + 16 bytes for sp-8 where fp may be saved.
   431	RLDICR  $0, R1, $59, R1         // Align to 16 bytes for C code
   432	BL      (CTR)
   433	XOR     R0, R0, R0              // Clear R0 as Go expects
   434	MOVD    R15, R1                 // Restore R1
   435	MOVD    24(R1), R2              // Restore R2
   436	MOVW    R3, ret+24(FP)          // Return result
   437	RET
   438#endif
   439
   440TEXT runtime·sigfwd(SB),NOSPLIT,$0-32
   441	MOVW	sig+8(FP), R3
   442	MOVD	info+16(FP), R4
   443	MOVD	ctx+24(FP), R5
   444	MOVD	fn+0(FP), R12
   445	MOVD	R12, CTR
   446	BL	(CTR)
   447	MOVD	24(R1), R2
   448	RET
   449
   450#ifdef GO_PPC64X_HAS_FUNCDESC
   451DEFINE_PPC64X_FUNCDESC(runtime·sigtramp, sigtramp<>)
   452// cgo isn't supported on ppc64, but we need to supply a cgoSigTramp function.
   453DEFINE_PPC64X_FUNCDESC(runtime·cgoSigtramp, sigtramp<>)
   454TEXT sigtramp<>(SB),NOSPLIT|NOFRAME|TOPFRAME,$0
   455#else
   456// ppc64le doesn't need function descriptors
   457// Save callee-save registers in the case of signal forwarding.
   458// Same as on ARM64 https://golang.org/issue/31827 .
   459//
   460// Note, it is assumed this is always called indirectly (e.g via
   461// a function pointer) as R2 may not be preserved when calling this
   462// function. In those cases, the caller preserves their R2.
   463TEXT runtime·sigtramp(SB),NOSPLIT|NOFRAME,$0
   464#endif
   465	// This is called with ELF calling conventions. Convert to Go.
   466	// Allocate space for argument storage to call runtime.sigtrampgo.
   467	STACK_AND_SAVE_HOST_TO_GO_ABI(32)
   468
   469	// this might be called in external code context,
   470	// where g is not set.
   471	MOVBZ	runtime·iscgo(SB), R6
   472	CMP	R6, $0
   473	BEQ	2(PC)
   474	BL	runtime·load_g(SB)
   475
   476	// R3,R4,R5 already hold the arguments. Forward them on.
   477	// TODO: Indirectly call runtime.sigtrampgo to avoid the linker's static NOSPLIT stack
   478	// overflow detection. It thinks this might be called on a small Go stack, but this is only
   479	// called from a larger pthread or sigaltstack stack. Can the checker be improved to not
   480	// flag a direct call here?
   481	MOVD	$runtime·sigtrampgo<ABIInternal>(SB), R12
   482	MOVD	R12, CTR
   483	BL	(CTR)
   484	// Restore R2 (TOC pointer) in the event it might be used later in this function.
   485	// If this was not compiled as shared code, R2 is undefined, reloading it is harmless.
   486	MOVD	24(R1), R2
   487
   488	UNSTACK_AND_RESTORE_GO_TO_HOST_ABI(32)
   489	RET
   490
   491#ifdef GOARCH_ppc64le
   492TEXT runtime·cgoSigtramp(SB),NOSPLIT|NOFRAME,$0
   493	// The stack unwinder, presumably written in C, may not be able to
   494	// handle Go frame correctly. So, this function is NOFRAME, and we
   495	// save/restore LR manually, and obey ELFv2 calling conventions.
   496	MOVD	LR, R10
   497
   498	// We're coming from C code, initialize R0
   499	MOVD	$0, R0
   500
   501	// If no traceback function, do usual sigtramp.
   502	MOVD	runtime·cgoTraceback(SB), R6
   503	CMP	$0, R6
   504	BEQ	sigtramp
   505
   506	// If no traceback support function, which means that
   507	// runtime/cgo was not linked in, do usual sigtramp.
   508	MOVD	_cgo_callers(SB), R6
   509	CMP	$0, R6
   510	BEQ	sigtramp
   511
   512	// Inspect the g in TLS without clobbering R30/R31 via runtime.load_g.
   513	MOVD	runtime·tls_g(SB), R9
   514	MOVD	0(R9), R9
   515
   516	// Figure out if we are currently in a cgo call.
   517	// If not, just do usual sigtramp.
   518	// compared to ARM64 and others.
   519	CMP	$0, R9
   520	BEQ	sigtrampnog // g == nil
   521
   522	// g is not nil. Check further.
   523	MOVD	g_m(R9), R6
   524	CMP	$0, R6
   525	BEQ	sigtramp    // g.m == nil
   526	MOVW	m_ncgo(R6), R7
   527	CMPW	$0, R7
   528	BEQ	sigtramp    // g.m.ncgo = 0
   529	MOVD	m_curg(R6), R7
   530	CMP	$0, R7
   531	BEQ	sigtramp    // g.m.curg == nil
   532	MOVD	g_syscallsp(R7), R7
   533	CMP	$0, R7
   534	BEQ	sigtramp    // g.m.curg.syscallsp == 0
   535	MOVD	m_cgoCallers(R6), R7 // R7 is the fifth arg in C calling convention.
   536	CMP	$0, R7
   537	BEQ	sigtramp    // g.m.cgoCallers == nil
   538	MOVW	m_cgoCallersUse(R6), R8
   539	CMPW	$0, R8
   540	BNE	sigtramp    // g.m.cgoCallersUse != 0
   541
   542	// Jump to a function in runtime/cgo.
   543	// That function, written in C, will call the user's traceback
   544	// function with proper unwind info, and will then call back here.
   545	// The first three arguments, and the fifth, are already in registers.
   546	// Set the two remaining arguments now.
   547	MOVD	runtime·cgoTraceback(SB), R6
   548	MOVD	$runtime·sigtramp(SB), R8
   549	MOVD	_cgo_callers(SB), R12
   550	MOVD	R12, CTR
   551	MOVD	R10, LR // restore LR
   552	JMP	(CTR)
   553
   554sigtramp:
   555	MOVD	R10, LR // restore LR
   556	JMP	runtime·sigtramp(SB)
   557
   558sigtrampnog:
   559	// Signal arrived on a non-Go thread. If this is SIGPROF, get a
   560	// stack trace.
   561	CMPW	R3, $27 // 27 == SIGPROF
   562	BNE	sigtramp
   563
   564	// Lock sigprofCallersUse (cas from 0 to 1).
   565	MOVW	$1, R7
   566	MOVD	$runtime·sigprofCallersUse(SB), R8
   567	SYNC
   568	LWAR    (R8), R6
   569	CMPW    $0, R6
   570	BNE     sigtramp
   571	STWCCC  R7, (R8)
   572	BNE     -4(PC)
   573	ISYNC
   574
   575	// Jump to the traceback function in runtime/cgo.
   576	// It will call back to sigprofNonGo, which will ignore the
   577	// arguments passed in registers.
   578	// First three arguments to traceback function are in registers already.
   579	MOVD	runtime·cgoTraceback(SB), R6
   580	MOVD	$runtime·sigprofCallers(SB), R7
   581	MOVD	$runtime·sigprofNonGoWrapper<>(SB), R8
   582	MOVD	_cgo_callers(SB), R12
   583	MOVD	R12, CTR
   584	MOVD	R10, LR // restore LR
   585	JMP	(CTR)
   586#endif
   587
   588// Used by cgoSigtramp to inspect without clobbering R30/R31 via runtime.load_g.
   589GLOBL runtime·tls_g+0(SB), TLSBSS+DUPOK, $8
   590
   591TEXT runtime·sigprofNonGoWrapper<>(SB),NOSPLIT|NOFRAME,$0
   592	// This is called from C code. Callee save registers must be saved.
   593	// R3,R4,R5 hold arguments, and allocate argument space to call sigprofNonGo.
   594	STACK_AND_SAVE_HOST_TO_GO_ABI(32)
   595
   596	CALL	runtime·sigprofNonGo<ABIInternal>(SB)
   597
   598	UNSTACK_AND_RESTORE_GO_TO_HOST_ABI(32)
   599	RET
   600
   601TEXT runtime·mmap(SB),NOSPLIT|NOFRAME,$0
   602	MOVD	addr+0(FP), R3
   603	MOVD	n+8(FP), R4
   604	MOVW	prot+16(FP), R5
   605	MOVW	flags+20(FP), R6
   606	MOVW	fd+24(FP), R7
   607	MOVW	off+28(FP), R8
   608
   609	SYSCALL	$SYS_mmap
   610	BVC	ok
   611	MOVD	$0, p+32(FP)
   612	MOVD	R3, err+40(FP)
   613	RET
   614ok:
   615	MOVD	R3, p+32(FP)
   616	MOVD	$0, err+40(FP)
   617	RET
   618
   619TEXT runtime·munmap(SB),NOSPLIT|NOFRAME,$0
   620	MOVD	addr+0(FP), R3
   621	MOVD	n+8(FP), R4
   622	SYSCALL	$SYS_munmap
   623	BVC	2(PC)
   624	MOVD	R0, 0xf0(R0)
   625	RET
   626
   627TEXT runtime·madvise(SB),NOSPLIT|NOFRAME,$0
   628	MOVD	addr+0(FP), R3
   629	MOVD	n+8(FP), R4
   630	MOVW	flags+16(FP), R5
   631	SYSCALL	$SYS_madvise
   632	MOVW	R3, ret+24(FP)
   633	RET
   634
   635// int64 futex(int32 *uaddr, int32 op, int32 val,
   636//	struct timespec *timeout, int32 *uaddr2, int32 val2);
   637TEXT runtime·futex(SB),NOSPLIT|NOFRAME,$0
   638	MOVD	addr+0(FP), R3
   639	MOVW	op+8(FP), R4
   640	MOVW	val+12(FP), R5
   641	MOVD	ts+16(FP), R6
   642	MOVD	addr2+24(FP), R7
   643	MOVW	val3+32(FP), R8
   644	SYSCALL	$SYS_futex
   645	BVC	2(PC)
   646	NEG	R3	// caller expects negative errno
   647	MOVW	R3, ret+40(FP)
   648	RET
   649
   650// int64 clone(int32 flags, void *stk, M *mp, G *gp, void (*fn)(void));
   651TEXT runtime·clone(SB),NOSPLIT|NOFRAME,$0
   652	MOVW	flags+0(FP), R3
   653	MOVD	stk+8(FP), R4
   654
   655	// Copy mp, gp, fn off parent stack for use by child.
   656	// Careful: Linux system call clobbers ???.
   657	MOVD	mp+16(FP), R7
   658	MOVD	gp+24(FP), R8
   659	MOVD	fn+32(FP), R12
   660
   661	MOVD	R7, -8(R4)
   662	MOVD	R8, -16(R4)
   663	MOVD	R12, -24(R4)
   664	MOVD	$1234, R7
   665	MOVD	R7, -32(R4)
   666
   667	SYSCALL $SYS_clone
   668	BVC	2(PC)
   669	NEG	R3	// caller expects negative errno
   670
   671	// In parent, return.
   672	CMP	R3, $0
   673	BEQ	3(PC)
   674	MOVW	R3, ret+40(FP)
   675	RET
   676
   677	// In child, on new stack.
   678	// initialize essential registers
   679	BL	runtime·reginit(SB)
   680	MOVD	-32(R1), R7
   681	CMP	R7, $1234
   682	BEQ	2(PC)
   683	MOVD	R0, 0(R0)
   684
   685	// Initialize m->procid to Linux tid
   686	SYSCALL $SYS_gettid
   687
   688	MOVD	-24(R1), R12       // fn
   689	MOVD	-16(R1), R8        // g
   690	MOVD	-8(R1), R7         // m
   691
   692	CMP	R7, $0
   693	BEQ	nog
   694	CMP	R8, $0
   695	BEQ	nog
   696
   697	MOVD	R3, m_procid(R7)
   698
   699	// TODO: setup TLS.
   700
   701	// In child, set up new stack
   702	MOVD	R7, g_m(R8)
   703	MOVD	R8, g
   704	//CALL	runtime·stackcheck(SB)
   705
   706nog:
   707	// Call fn
   708	MOVD	R12, CTR
   709	BL	(CTR)
   710
   711	// It shouldn't return.	 If it does, exit that thread.
   712	MOVW	$111, R3
   713	SYSCALL	$SYS_exit
   714	BR	-2(PC)	// keep exiting
   715
   716TEXT runtime·sigaltstack(SB),NOSPLIT|NOFRAME,$0
   717	MOVD	new+0(FP), R3
   718	MOVD	old+8(FP), R4
   719	SYSCALL	$SYS_sigaltstack
   720	BVC	2(PC)
   721	MOVD	R0, 0xf0(R0)  // crash
   722	RET
   723
   724TEXT runtime·osyield(SB),NOSPLIT|NOFRAME,$0
   725	SYSCALL	$SYS_sched_yield
   726	RET
   727
   728TEXT runtime·sched_getaffinity(SB),NOSPLIT|NOFRAME,$0
   729	MOVD	pid+0(FP), R3
   730	MOVD	len+8(FP), R4
   731	MOVD	buf+16(FP), R5
   732	SYSCALL	$SYS_sched_getaffinity
   733	BVC	2(PC)
   734	NEG	R3	// caller expects negative errno
   735	MOVW	R3, ret+24(FP)
   736	RET
   737
   738// func sbrk0() uintptr
   739TEXT runtime·sbrk0(SB),NOSPLIT|NOFRAME,$0
   740	// Implemented as brk(NULL).
   741	MOVD	$0, R3
   742	SYSCALL	$SYS_brk
   743	MOVD	R3, ret+0(FP)
   744	RET
   745
   746TEXT runtime·access(SB),$0-20
   747	MOVD	R0, 0(R0) // unimplemented, only needed for android; declared in stubs_linux.go
   748	MOVW	R0, ret+16(FP) // for vet
   749	RET
   750
   751TEXT runtime·connect(SB),$0-28
   752	MOVD	R0, 0(R0) // unimplemented, only needed for android; declared in stubs_linux.go
   753	MOVW	R0, ret+24(FP) // for vet
   754	RET
   755
   756TEXT runtime·socket(SB),$0-20
   757	MOVD	R0, 0(R0) // unimplemented, only needed for android; declared in stubs_linux.go
   758	MOVW	R0, ret+16(FP) // for vet
   759	RET

View as plain text