...

Text file src/runtime/sys_darwin_arm64.s

Documentation: runtime

     1// Copyright 2015 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// System calls and other sys.stuff for ARM64, Darwin
     6// System calls are implemented in libSystem, this file contains
     7// trampolines that convert from Go to C calling convention.
     8
     9#include "go_asm.h"
    10#include "go_tls.h"
    11#include "textflag.h"
    12#include "cgo/abi_arm64.h"
    13
    14#define CLOCK_REALTIME		0
    15
    16TEXT notok<>(SB),NOSPLIT,$0
    17	MOVD	$0, R8
    18	MOVD	R8, (R8)
    19	B	0(PC)
    20
    21TEXT runtime·open_trampoline(SB),NOSPLIT,$0
    22	SUB	$16, RSP
    23	MOVW	8(R0), R1	// arg 2 flags
    24	MOVW	12(R0), R2	// arg 3 mode
    25	MOVW	R2, (RSP)	// arg 3 is variadic, pass on stack
    26	MOVD	0(R0), R0	// arg 1 pathname
    27	BL	libc_open(SB)
    28	ADD	$16, RSP
    29	RET
    30
    31TEXT runtime·close_trampoline(SB),NOSPLIT,$0
    32	MOVW	0(R0), R0	// arg 1 fd
    33	BL	libc_close(SB)
    34	RET
    35
    36TEXT runtime·write_trampoline(SB),NOSPLIT,$0
    37	MOVD	8(R0), R1	// arg 2 buf
    38	MOVW	16(R0), R2	// arg 3 count
    39	MOVW	0(R0), R0	// arg 1 fd
    40	BL	libc_write(SB)
    41	MOVD	$-1, R1
    42	CMP	R0, R1
    43	BNE	noerr
    44	BL	libc_error(SB)
    45	MOVW	(R0), R0
    46	NEG	R0, R0		// caller expects negative errno value
    47noerr:
    48	RET
    49
    50TEXT runtime·read_trampoline(SB),NOSPLIT,$0
    51	MOVD	8(R0), R1	// arg 2 buf
    52	MOVW	16(R0), R2	// arg 3 count
    53	MOVW	0(R0), R0	// arg 1 fd
    54	BL	libc_read(SB)
    55	MOVD	$-1, R1
    56	CMP	R0, R1
    57	BNE	noerr
    58	BL	libc_error(SB)
    59	MOVW	(R0), R0
    60	NEG	R0, R0		// caller expects negative errno value
    61noerr:
    62	RET
    63
    64TEXT runtime·pipe_trampoline(SB),NOSPLIT,$0
    65	BL	libc_pipe(SB)	// pointer already in R0
    66	CMP	$0, R0
    67	BEQ	3(PC)
    68	BL	libc_error(SB)	// return negative errno value
    69	NEG	R0, R0
    70	RET
    71
    72TEXT runtime·exit_trampoline(SB),NOSPLIT|NOFRAME,$0
    73	MOVW	0(R0), R0
    74	BL	libc_exit(SB)
    75	MOVD	$1234, R0
    76	MOVD	$1002, R1
    77	MOVD	R0, (R1)	// fail hard
    78
    79TEXT runtime·raiseproc_trampoline(SB),NOSPLIT,$0
    80	MOVD	0(R0), R19	// signal
    81	BL	libc_getpid(SB)
    82	// arg 1 pid already in R0 from getpid
    83	MOVD	R19, R1	// arg 2 signal
    84	BL	libc_kill(SB)
    85	RET
    86
    87TEXT runtime·mmap_trampoline(SB),NOSPLIT,$0
    88	MOVD	R0, R19
    89	MOVD	0(R19), R0	// arg 1 addr
    90	MOVD	8(R19), R1	// arg 2 len
    91	MOVW	16(R19), R2	// arg 3 prot
    92	MOVW	20(R19), R3	// arg 4 flags
    93	MOVW	24(R19), R4	// arg 5 fd
    94	MOVW	28(R19), R5	// arg 6 off
    95	BL	libc_mmap(SB)
    96	MOVD	$0, R1
    97	MOVD	$-1, R2
    98	CMP	R0, R2
    99	BNE	ok
   100	BL	libc_error(SB)
   101	MOVW	(R0), R1
   102	MOVD	$0, R0
   103ok:
   104	MOVD	R0, 32(R19) // ret 1 p
   105	MOVD	R1, 40(R19)	// ret 2 err
   106	RET
   107
   108TEXT runtime·munmap_trampoline(SB),NOSPLIT,$0
   109	MOVD	8(R0), R1	// arg 2 len
   110	MOVD	0(R0), R0	// arg 1 addr
   111	BL	libc_munmap(SB)
   112	CMP	$0, R0
   113	BEQ	2(PC)
   114	BL	notok<>(SB)
   115	RET
   116
   117TEXT runtime·madvise_trampoline(SB),NOSPLIT,$0
   118	MOVD	8(R0), R1	// arg 2 len
   119	MOVW	16(R0), R2	// arg 3 advice
   120	MOVD	0(R0), R0	// arg 1 addr
   121	BL	libc_madvise(SB)
   122	RET
   123
   124TEXT runtime·mlock_trampoline(SB),NOSPLIT,$0
   125	MOVD	8(R0), R1	// arg 2 len
   126	MOVD	0(R0), R0	// arg 1 addr
   127	BL	libc_mlock(SB)
   128	RET
   129
   130TEXT runtime·setitimer_trampoline(SB),NOSPLIT,$0
   131	MOVD	8(R0), R1	// arg 2 new
   132	MOVD	16(R0), R2	// arg 3 old
   133	MOVW	0(R0), R0	// arg 1 which
   134	BL	libc_setitimer(SB)
   135	RET
   136
   137TEXT runtime·walltime_trampoline(SB),NOSPLIT,$0
   138	MOVD	R0, R1			// arg 2 timespec
   139	MOVW	$CLOCK_REALTIME, R0 	// arg 1 clock_id
   140	BL	libc_clock_gettime(SB)
   141	RET
   142
   143GLOBL timebase<>(SB),NOPTR,$(machTimebaseInfo__size)
   144
   145TEXT runtime·nanotime_trampoline(SB),NOSPLIT,$40
   146	MOVD	R0, R19
   147	BL	libc_mach_absolute_time(SB)
   148	MOVD	R0, 0(R19)
   149	MOVW	timebase<>+machTimebaseInfo_numer(SB), R20
   150	MOVD	$timebase<>+machTimebaseInfo_denom(SB), R21
   151	LDARW	(R21), R21	// atomic read
   152	CMP	$0, R21
   153	BNE	initialized
   154
   155	SUB	$(machTimebaseInfo__size+15)/16*16, RSP
   156	MOVD	RSP, R0
   157	BL	libc_mach_timebase_info(SB)
   158	MOVW	machTimebaseInfo_numer(RSP), R20
   159	MOVW	machTimebaseInfo_denom(RSP), R21
   160	ADD	$(machTimebaseInfo__size+15)/16*16, RSP
   161
   162	MOVW	R20, timebase<>+machTimebaseInfo_numer(SB)
   163	MOVD	$timebase<>+machTimebaseInfo_denom(SB), R22
   164	STLRW	R21, (R22)	// atomic write
   165
   166initialized:
   167	MOVW	R20, 8(R19)
   168	MOVW	R21, 12(R19)
   169	RET
   170
   171TEXT runtime·sigfwd(SB),NOSPLIT,$0-32
   172	MOVW	sig+8(FP), R0
   173	MOVD	info+16(FP), R1
   174	MOVD	ctx+24(FP), R2
   175	MOVD	fn+0(FP), R11
   176	BL	(R11)
   177	RET
   178
   179TEXT runtime·sigtramp(SB),NOSPLIT|TOPFRAME,$176
   180	// Save callee-save registers in the case of signal forwarding.
   181	// Please refer to https://golang.org/issue/31827 .
   182	SAVE_R19_TO_R28(8*4)
   183	SAVE_F8_TO_F15(8*14)
   184
   185	// Save arguments.
   186	MOVW	R0, (8*1)(RSP)	// sig
   187	MOVD	R1, (8*2)(RSP)	// info
   188	MOVD	R2, (8*3)(RSP)	// ctx
   189
   190	// this might be called in external code context,
   191	// where g is not set.
   192	BL	runtime·load_g(SB)
   193
   194#ifdef GOOS_ios
   195	MOVD	RSP, R6
   196	CMP	$0, g
   197	BEQ	nog
   198	// iOS always use the main stack to run the signal handler.
   199	// We need to switch to gsignal ourselves.
   200	MOVD	g_m(g), R11
   201	MOVD	m_gsignal(R11), R5
   202	MOVD	(g_stack+stack_hi)(R5), R6
   203
   204nog:
   205	// Restore arguments.
   206	MOVW	(8*1)(RSP), R0
   207	MOVD	(8*2)(RSP), R1
   208	MOVD	(8*3)(RSP), R2
   209
   210	// Reserve space for args and the stack pointer on the
   211	// gsignal stack.
   212	SUB	$48, R6
   213	// Save stack pointer.
   214	MOVD	RSP, R4
   215	MOVD	R4, (8*4)(R6)
   216	// Switch to gsignal stack.
   217	MOVD	R6, RSP
   218
   219	// Save arguments.
   220	MOVW	R0, (8*1)(RSP)
   221	MOVD	R1, (8*2)(RSP)
   222	MOVD	R2, (8*3)(RSP)
   223#endif
   224
   225	// Call sigtrampgo.
   226	MOVD	$runtime·sigtrampgo(SB), R11
   227	BL	(R11)
   228
   229#ifdef GOOS_ios
   230	// Switch to old stack.
   231	MOVD	(8*4)(RSP), R5
   232	MOVD	R5, RSP
   233#endif
   234
   235	// Restore callee-save registers.
   236	RESTORE_R19_TO_R28(8*4)
   237	RESTORE_F8_TO_F15(8*14)
   238
   239	RET
   240
   241TEXT runtime·cgoSigtramp(SB),NOSPLIT,$0
   242	JMP	runtime·sigtramp(SB)
   243
   244TEXT runtime·sigprocmask_trampoline(SB),NOSPLIT,$0
   245	MOVD	8(R0), R1	// arg 2 new
   246	MOVD	16(R0), R2	// arg 3 old
   247	MOVW	0(R0), R0	// arg 1 how
   248	BL	libc_pthread_sigmask(SB)
   249	CMP	$0, R0
   250	BEQ	2(PC)
   251	BL	notok<>(SB)
   252	RET
   253
   254TEXT runtime·sigaction_trampoline(SB),NOSPLIT,$0
   255	MOVD	8(R0), R1	// arg 2 new
   256	MOVD	16(R0), R2	// arg 3 old
   257	MOVW	0(R0), R0	// arg 1 how
   258	BL	libc_sigaction(SB)
   259	CMP	$0, R0
   260	BEQ	2(PC)
   261	BL	notok<>(SB)
   262	RET
   263
   264TEXT runtime·usleep_trampoline(SB),NOSPLIT,$0
   265	MOVW	0(R0), R0	// arg 1 usec
   266	BL	libc_usleep(SB)
   267	RET
   268
   269TEXT runtime·sysctl_trampoline(SB),NOSPLIT,$0
   270	MOVW	8(R0), R1	// arg 2 miblen
   271	MOVD	16(R0), R2	// arg 3 oldp
   272	MOVD	24(R0), R3	// arg 4 oldlenp
   273	MOVD	32(R0), R4	// arg 5 newp
   274	MOVD	40(R0), R5	// arg 6 newlen
   275	MOVD	0(R0), R0	// arg 1 mib
   276	BL	libc_sysctl(SB)
   277	RET
   278
   279TEXT runtime·sysctlbyname_trampoline(SB),NOSPLIT,$0
   280	MOVD	8(R0), R1	// arg 2 oldp
   281	MOVD	16(R0), R2	// arg 3 oldlenp
   282	MOVD	24(R0), R3	// arg 4 newp
   283	MOVD	32(R0), R4	// arg 5 newlen
   284	MOVD	0(R0), R0	// arg 1 name
   285	BL	libc_sysctlbyname(SB)
   286	RET
   287
   288
   289TEXT runtime·kqueue_trampoline(SB),NOSPLIT,$0
   290	BL	libc_kqueue(SB)
   291	RET
   292
   293TEXT runtime·kevent_trampoline(SB),NOSPLIT,$0
   294	MOVD	8(R0), R1	// arg 2 keventt
   295	MOVW	16(R0), R2	// arg 3 nch
   296	MOVD	24(R0), R3	// arg 4 ev
   297	MOVW	32(R0), R4	// arg 5 nev
   298	MOVD	40(R0), R5	// arg 6 ts
   299	MOVW	0(R0), R0	// arg 1 kq
   300	BL	libc_kevent(SB)
   301	MOVD	$-1, R2
   302	CMP	R0, R2
   303	BNE	ok
   304	BL	libc_error(SB)
   305	MOVW	(R0), R0	// errno
   306	NEG	R0, R0	// caller wants it as a negative error code
   307ok:
   308	RET
   309
   310TEXT runtime·fcntl_trampoline(SB),NOSPLIT,$0
   311	SUB	$16, RSP
   312	MOVD	R0, R19
   313	MOVW	0(R19), R0	// arg 1 fd
   314	MOVW	4(R19), R1	// arg 2 cmd
   315	MOVW	8(R19), R2	// arg 3 arg
   316	MOVW	R2, (RSP)	// arg 3 is variadic, pass on stack
   317	BL	libc_fcntl(SB)
   318	MOVD	$0, R1
   319	MOVD	$-1, R2
   320	CMP	R0, R2
   321	BNE	noerr
   322	BL	libc_error(SB)
   323	MOVW	(R0), R1
   324	MOVW	$-1, R0
   325noerr:
   326	MOVW	R0, 12(R19)
   327	MOVW	R1, 16(R19)
   328	ADD	$16, RSP
   329	RET
   330
   331TEXT runtime·sigaltstack_trampoline(SB),NOSPLIT,$0
   332#ifdef GOOS_ios
   333	// sigaltstack on iOS is not supported and will always
   334	// run the signal handler on the main stack, so our sigtramp has
   335	// to do the stack switch ourselves.
   336	MOVW	$43, R0
   337	BL	libc_exit(SB)
   338#else
   339	MOVD	8(R0), R1		// arg 2 old
   340	MOVD	0(R0), R0		// arg 1 new
   341	CALL	libc_sigaltstack(SB)
   342	CBZ	R0, 2(PC)
   343	BL	notok<>(SB)
   344#endif
   345	RET
   346
   347// Thread related functions
   348
   349// mstart_stub is the first function executed on a new thread started by pthread_create.
   350// It just does some low-level setup and then calls mstart.
   351// Note: called with the C calling convention.
   352TEXT runtime·mstart_stub(SB),NOSPLIT,$160
   353	// R0 points to the m.
   354	// We are already on m's g0 stack.
   355
   356	// Save callee-save registers.
   357	SAVE_R19_TO_R28(8)
   358	SAVE_F8_TO_F15(88)
   359
   360	MOVD	m_g0(R0), g
   361	BL	·save_g(SB)
   362
   363	BL	runtime·mstart(SB)
   364
   365	// Restore callee-save registers.
   366	RESTORE_R19_TO_R28(8)
   367	RESTORE_F8_TO_F15(88)
   368
   369	// Go is all done with this OS thread.
   370	// Tell pthread everything is ok (we never join with this thread, so
   371	// the value here doesn't really matter).
   372	MOVD	$0, R0
   373
   374	RET
   375
   376TEXT runtime·pthread_attr_init_trampoline(SB),NOSPLIT,$0
   377	MOVD	0(R0), R0	// arg 1 attr
   378	BL	libc_pthread_attr_init(SB)
   379	RET
   380
   381TEXT runtime·pthread_attr_getstacksize_trampoline(SB),NOSPLIT,$0
   382	MOVD	8(R0), R1	// arg 2 size
   383	MOVD	0(R0), R0	// arg 1 attr
   384	BL	libc_pthread_attr_getstacksize(SB)
   385	RET
   386
   387TEXT runtime·pthread_attr_setdetachstate_trampoline(SB),NOSPLIT,$0
   388	MOVD	8(R0), R1	// arg 2 state
   389	MOVD	0(R0), R0	// arg 1 attr
   390	BL	libc_pthread_attr_setdetachstate(SB)
   391	RET
   392
   393TEXT runtime·pthread_create_trampoline(SB),NOSPLIT,$0
   394	SUB	$16, RSP
   395	MOVD	0(R0), R1	// arg 2 state
   396	MOVD	8(R0), R2	// arg 3 start
   397	MOVD	16(R0), R3	// arg 4 arg
   398	MOVD	RSP, R0 	// arg 1 &threadid (which we throw away)
   399	BL	libc_pthread_create(SB)
   400	ADD	$16, RSP
   401	RET
   402
   403TEXT runtime·raise_trampoline(SB),NOSPLIT,$0
   404	MOVW	0(R0), R0	// arg 1 sig
   405	BL	libc_raise(SB)
   406	RET
   407
   408TEXT runtime·pthread_mutex_init_trampoline(SB),NOSPLIT,$0
   409	MOVD	8(R0), R1	// arg 2 attr
   410	MOVD	0(R0), R0	// arg 1 mutex
   411	BL	libc_pthread_mutex_init(SB)
   412	RET
   413
   414TEXT runtime·pthread_mutex_lock_trampoline(SB),NOSPLIT,$0
   415	MOVD	0(R0), R0	// arg 1 mutex
   416	BL	libc_pthread_mutex_lock(SB)
   417	RET
   418
   419TEXT runtime·pthread_mutex_unlock_trampoline(SB),NOSPLIT,$0
   420	MOVD	0(R0), R0	// arg 1 mutex
   421	BL	libc_pthread_mutex_unlock(SB)
   422	RET
   423
   424TEXT runtime·pthread_cond_init_trampoline(SB),NOSPLIT,$0
   425	MOVD	8(R0), R1	// arg 2 attr
   426	MOVD	0(R0), R0	// arg 1 cond
   427	BL	libc_pthread_cond_init(SB)
   428	RET
   429
   430TEXT runtime·pthread_cond_wait_trampoline(SB),NOSPLIT,$0
   431	MOVD	8(R0), R1	// arg 2 mutex
   432	MOVD	0(R0), R0	// arg 1 cond
   433	BL	libc_pthread_cond_wait(SB)
   434	RET
   435
   436TEXT runtime·pthread_cond_timedwait_relative_np_trampoline(SB),NOSPLIT,$0
   437	MOVD	8(R0), R1	// arg 2 mutex
   438	MOVD	16(R0), R2	// arg 3 timeout
   439	MOVD	0(R0), R0	// arg 1 cond
   440	BL	libc_pthread_cond_timedwait_relative_np(SB)
   441	RET
   442
   443TEXT runtime·pthread_cond_signal_trampoline(SB),NOSPLIT,$0
   444	MOVD	0(R0), R0	// arg 1 cond
   445	BL	libc_pthread_cond_signal(SB)
   446	RET
   447
   448TEXT runtime·pthread_self_trampoline(SB),NOSPLIT,$0
   449	MOVD	R0, R19		// R19 is callee-save
   450	BL	libc_pthread_self(SB)
   451	MOVD	R0, 0(R19)	// return value
   452	RET
   453
   454TEXT runtime·pthread_kill_trampoline(SB),NOSPLIT,$0
   455	MOVD	8(R0), R1	// arg 2 sig
   456	MOVD	0(R0), R0	// arg 1 thread
   457	BL	libc_pthread_kill(SB)
   458	RET
   459
   460TEXT runtime·pthread_key_create_trampoline(SB),NOSPLIT,$0
   461	MOVD	8(R0), R1	// arg 2 destructor
   462	MOVD	0(R0), R0	// arg 1 *key
   463	BL	libc_pthread_key_create(SB)
   464	RET
   465
   466TEXT runtime·pthread_setspecific_trampoline(SB),NOSPLIT,$0
   467	MOVD	8(R0), R1	// arg 2 value
   468	MOVD	0(R0), R0	// arg 1 key
   469	BL	libc_pthread_setspecific(SB)
   470	RET
   471
   472TEXT runtime·osinit_hack_trampoline(SB),NOSPLIT,$0
   473	MOVD	$0, R0	// arg 1 val
   474	BL	libc_notify_is_valid_token(SB)
   475	BL	libc_xpc_date_create_from_current(SB)
   476	RET
   477
   478TEXT runtime·arc4random_buf_trampoline(SB),NOSPLIT,$0
   479	MOVW	8(R0), R1	// arg 2 nbytes
   480	MOVD	0(R0), R0	// arg 1 buf
   481	BL	libc_arc4random_buf(SB)
   482	RET
   483
   484// syscall calls a function in libc on behalf of the syscall package.
   485// syscall takes a pointer to a struct like:
   486// struct {
   487//	fn    uintptr
   488//	a1    uintptr
   489//	a2    uintptr
   490//	a3    uintptr
   491//	r1    uintptr
   492//	r2    uintptr
   493//	err   uintptr
   494// }
   495// syscall must be called on the g0 stack with the
   496// C calling convention (use libcCall).
   497TEXT runtime·syscall(SB),NOSPLIT,$0
   498	SUB	$16, RSP	// push structure pointer
   499	MOVD	R0, 8(RSP)
   500
   501	MOVD	0(R0), R12	// fn
   502	MOVD	16(R0), R1	// a2
   503	MOVD	24(R0), R2	// a3
   504	MOVD	8(R0), R0	// a1
   505
   506	// If fn is declared as vararg, we have to pass the vararg arguments on the stack.
   507	// (Because ios decided not to adhere to the standard arm64 calling convention, sigh...)
   508	// The only libSystem calls we support that are vararg are open, fcntl, and ioctl,
   509	// which are all of the form fn(x, y, ...). So we just need to put the 3rd arg
   510	// on the stack as well.
   511	// If we ever have other vararg libSystem calls, we might need to handle more cases.
   512	MOVD	R2, (RSP)
   513
   514	BL	(R12)
   515
   516	MOVD	8(RSP), R2	// pop structure pointer
   517	ADD	$16, RSP
   518	MOVD	R0, 32(R2)	// save r1
   519	MOVD	R1, 40(R2)	// save r2
   520	CMPW	$-1, R0
   521	BNE	ok
   522	SUB	$16, RSP	// push structure pointer
   523	MOVD	R2, 8(RSP)
   524	BL	libc_error(SB)
   525	MOVW	(R0), R0
   526	MOVD	8(RSP), R2	// pop structure pointer
   527	ADD	$16, RSP
   528	MOVD	R0, 48(R2)	// save err
   529ok:
   530	RET
   531
   532// syscallX calls a function in libc on behalf of the syscall package.
   533// syscallX takes a pointer to a struct like:
   534// struct {
   535//	fn    uintptr
   536//	a1    uintptr
   537//	a2    uintptr
   538//	a3    uintptr
   539//	r1    uintptr
   540//	r2    uintptr
   541//	err   uintptr
   542// }
   543// syscallX must be called on the g0 stack with the
   544// C calling convention (use libcCall).
   545TEXT runtime·syscallX(SB),NOSPLIT,$0
   546	SUB	$16, RSP	// push structure pointer
   547	MOVD	R0, (RSP)
   548
   549	MOVD	0(R0), R12	// fn
   550	MOVD	16(R0), R1	// a2
   551	MOVD	24(R0), R2	// a3
   552	MOVD	8(R0), R0	// a1
   553	BL	(R12)
   554
   555	MOVD	(RSP), R2	// pop structure pointer
   556	ADD	$16, RSP
   557	MOVD	R0, 32(R2)	// save r1
   558	MOVD	R1, 40(R2)	// save r2
   559	CMP	$-1, R0
   560	BNE	ok
   561	SUB	$16, RSP	// push structure pointer
   562	MOVD	R2, (RSP)
   563	BL	libc_error(SB)
   564	MOVW	(R0), R0
   565	MOVD	(RSP), R2	// pop structure pointer
   566	ADD	$16, RSP
   567	MOVD	R0, 48(R2)	// save err
   568ok:
   569	RET
   570
   571// syscallPtr is like syscallX except that the libc function reports an
   572// error by returning NULL and setting errno.
   573TEXT runtime·syscallPtr(SB),NOSPLIT,$0
   574	SUB	$16, RSP	// push structure pointer
   575	MOVD	R0, (RSP)
   576
   577	MOVD	0(R0), R12	// fn
   578	MOVD	16(R0), R1	// a2
   579	MOVD	24(R0), R2	// a3
   580	MOVD	8(R0), R0	// a1
   581	BL	(R12)
   582
   583	MOVD	(RSP), R2	// pop structure pointer
   584	ADD	$16, RSP
   585	MOVD	R0, 32(R2)	// save r1
   586	MOVD	R1, 40(R2)	// save r2
   587	CMP	$0, R0
   588	BNE	ok
   589	SUB	$16, RSP	// push structure pointer
   590	MOVD	R2, (RSP)
   591	BL	libc_error(SB)
   592	MOVW	(R0), R0
   593	MOVD	(RSP), R2	// pop structure pointer
   594	ADD	$16, RSP
   595	MOVD	R0, 48(R2)	// save err
   596ok:
   597	RET
   598
   599// syscall6 calls a function in libc on behalf of the syscall package.
   600// syscall6 takes a pointer to a struct like:
   601// struct {
   602//	fn    uintptr
   603//	a1    uintptr
   604//	a2    uintptr
   605//	a3    uintptr
   606//	a4    uintptr
   607//	a5    uintptr
   608//	a6    uintptr
   609//	r1    uintptr
   610//	r2    uintptr
   611//	err   uintptr
   612// }
   613// syscall6 must be called on the g0 stack with the
   614// C calling convention (use libcCall).
   615TEXT runtime·syscall6(SB),NOSPLIT,$0
   616	SUB	$16, RSP	// push structure pointer
   617	MOVD	R0, 8(RSP)
   618
   619	MOVD	0(R0), R12	// fn
   620	MOVD	16(R0), R1	// a2
   621	MOVD	24(R0), R2	// a3
   622	MOVD	32(R0), R3	// a4
   623	MOVD	40(R0), R4	// a5
   624	MOVD	48(R0), R5	// a6
   625	MOVD	8(R0), R0	// a1
   626
   627	// If fn is declared as vararg, we have to pass the vararg arguments on the stack.
   628	// See syscall above. The only function this applies to is openat, for which the 4th
   629	// arg must be on the stack.
   630	MOVD	R3, (RSP)
   631
   632	BL	(R12)
   633
   634	MOVD	8(RSP), R2	// pop structure pointer
   635	ADD	$16, RSP
   636	MOVD	R0, 56(R2)	// save r1
   637	MOVD	R1, 64(R2)	// save r2
   638	CMPW	$-1, R0
   639	BNE	ok
   640	SUB	$16, RSP	// push structure pointer
   641	MOVD	R2, 8(RSP)
   642	BL	libc_error(SB)
   643	MOVW	(R0), R0
   644	MOVD	8(RSP), R2	// pop structure pointer
   645	ADD	$16, RSP
   646	MOVD	R0, 72(R2)	// save err
   647ok:
   648	RET
   649
   650// syscall6X calls a function in libc on behalf of the syscall package.
   651// syscall6X takes a pointer to a struct like:
   652// struct {
   653//	fn    uintptr
   654//	a1    uintptr
   655//	a2    uintptr
   656//	a3    uintptr
   657//	a4    uintptr
   658//	a5    uintptr
   659//	a6    uintptr
   660//	r1    uintptr
   661//	r2    uintptr
   662//	err   uintptr
   663// }
   664// syscall6X must be called on the g0 stack with the
   665// C calling convention (use libcCall).
   666TEXT runtime·syscall6X(SB),NOSPLIT,$0
   667	SUB	$16, RSP	// push structure pointer
   668	MOVD	R0, (RSP)
   669
   670	MOVD	0(R0), R12	// fn
   671	MOVD	16(R0), R1	// a2
   672	MOVD	24(R0), R2	// a3
   673	MOVD	32(R0), R3	// a4
   674	MOVD	40(R0), R4	// a5
   675	MOVD	48(R0), R5	// a6
   676	MOVD	8(R0), R0	// a1
   677	BL	(R12)
   678
   679	MOVD	(RSP), R2	// pop structure pointer
   680	ADD	$16, RSP
   681	MOVD	R0, 56(R2)	// save r1
   682	MOVD	R1, 64(R2)	// save r2
   683	CMP	$-1, R0
   684	BNE	ok
   685	SUB	$16, RSP	// push structure pointer
   686	MOVD	R2, (RSP)
   687	BL	libc_error(SB)
   688	MOVW	(R0), R0
   689	MOVD	(RSP), R2	// pop structure pointer
   690	ADD	$16, RSP
   691	MOVD	R0, 72(R2)	// save err
   692ok:
   693	RET
   694
   695// syscall9 calls a function in libc on behalf of the syscall package.
   696// syscall9 takes a pointer to a struct like:
   697// struct {
   698//	fn    uintptr
   699//	a1    uintptr
   700//	a2    uintptr
   701//	a3    uintptr
   702//	a4    uintptr
   703//	a5    uintptr
   704//	a6    uintptr
   705//	a7    uintptr
   706//	a8    uintptr
   707//	a9    uintptr
   708//	r1    uintptr
   709//	r2    uintptr
   710//	err   uintptr
   711// }
   712// syscall9 must be called on the g0 stack with the
   713// C calling convention (use libcCall).
   714TEXT runtime·syscall9(SB),NOSPLIT,$0
   715	SUB	$16, RSP	// push structure pointer
   716	MOVD	R0, 8(RSP)
   717
   718	MOVD	0(R0), R12	// fn
   719	MOVD	16(R0), R1	// a2
   720	MOVD	24(R0), R2	// a3
   721	MOVD	32(R0), R3	// a4
   722	MOVD	40(R0), R4	// a5
   723	MOVD	48(R0), R5	// a6
   724	MOVD	56(R0), R6	// a7
   725	MOVD	64(R0), R7	// a8
   726	MOVD	72(R0), R8	// a9
   727	MOVD	8(R0), R0	// a1
   728
   729	// If fn is declared as vararg, we have to pass the vararg arguments on the stack.
   730	// See syscall above. The only function this applies to is openat, for which the 4th
   731	// arg must be on the stack.
   732	MOVD	R3, (RSP)
   733
   734	BL	(R12)
   735
   736	MOVD	8(RSP), R2	// pop structure pointer
   737	ADD	$16, RSP
   738	MOVD	R0, 80(R2)	// save r1
   739	MOVD	R1, 88(R2)	// save r2
   740	CMPW	$-1, R0
   741	BNE	ok
   742	SUB	$16, RSP	// push structure pointer
   743	MOVD	R2, 8(RSP)
   744	BL	libc_error(SB)
   745	MOVW	(R0), R0
   746	MOVD	8(RSP), R2	// pop structure pointer
   747	ADD	$16, RSP
   748	MOVD	R0, 96(R2)	// save err
   749ok:
   750	RET
   751
   752// syscall_x509 is for crypto/x509. It is like syscall6 but does not check for errors,
   753// takes 5 uintptrs and 1 float64, and only returns one value,
   754// for use with standard C ABI functions.
   755TEXT runtime·syscall_x509(SB),NOSPLIT,$0
   756	SUB	$16, RSP	// push structure pointer
   757	MOVD	R0, (RSP)
   758
   759	MOVD	0(R0), R12	// fn
   760	MOVD	16(R0), R1	// a2
   761	MOVD	24(R0), R2	// a3
   762	MOVD	32(R0), R3	// a4
   763	MOVD	40(R0), R4	// a5
   764	FMOVD	48(R0), F0	// f1
   765	MOVD	8(R0), R0	// a1
   766	BL	(R12)
   767
   768	MOVD	(RSP), R2	// pop structure pointer
   769	ADD	$16, RSP
   770	MOVD	R0, 56(R2)	// save r1
   771	RET
   772
   773TEXT runtime·issetugid_trampoline(SB),NOSPLIT,$0
   774	BL	libc_issetugid(SB)
   775	RET
   776
   777// mach_vm_region_trampoline calls mach_vm_region from libc.
   778TEXT runtime·mach_vm_region_trampoline(SB),NOSPLIT,$0
   779	MOVD	0(R0), R1	// address
   780	MOVD	8(R0), R2	// size
   781	MOVW	16(R0), R3	// flavor
   782	MOVD	24(R0), R4	// info
   783	MOVD	32(R0), R5	// count
   784	MOVD	40(R0), R6  // object_name
   785	MOVD	$libc_mach_task_self_(SB), R0
   786	MOVW	0(R0), R0
   787	BL	libc_mach_vm_region(SB)
   788	RET
   789
   790// proc_regionfilename_trampoline calls proc_regionfilename for
   791// the current process.
   792TEXT runtime·proc_regionfilename_trampoline(SB),NOSPLIT,$0
   793	MOVD	8(R0), R1	// address
   794	MOVD	16(R0), R2	// buffer
   795	MOVD	24(R0), R3	// buffer_size
   796	MOVD	0(R0), R0 // pid
   797	BL	libc_proc_regionfilename(SB)
   798	RET

View as plain text