github.com/metacubex/gvisor@v0.0.0-20240320004321-933faba989ec/pkg/sentry/platform/ptrace/stub_arm64.s (about)

     1  // Copyright 2019 The gVisor Authors.
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  #include "funcdata.h"
    16  #include "textflag.h"
    17  
    18  #define SYS_GETPID		172
    19  #define SYS_EXIT		93
    20  #define SYS_KILL		129
    21  #define SYS_GETPPID		173
    22  #define SYS_PRCTL		167
    23  
    24  #define SIGKILL			9
    25  #define SIGSTOP			19
    26  
    27  #define PR_SET_PDEATHSIG	1
    28  
    29  // stub bootstraps the child and sends itself SIGSTOP to wait for attach.
    30  //
    31  // R7 contains the expected PPID.
    32  //
    33  // This should not be used outside the context of a new ptrace child (as the
    34  // function is otherwise a bunch of nonsense).
    35  TEXT ·stub(SB),NOSPLIT,$0
    36  begin:
    37  	// N.B. This loop only executes in the context of a single-threaded
    38  	// fork child.
    39  
    40  	MOVD $SYS_PRCTL, R8
    41  	MOVD $PR_SET_PDEATHSIG, R0
    42  	MOVD $SIGKILL, R1
    43  	SVC
    44  
    45  	CMN $4095, R0
    46  	BCS error
    47  
    48  	// If the parent already died before we called PR_SET_DEATHSIG then
    49  	// we'll have an unexpected PPID.
    50  	MOVD $SYS_GETPPID, R8
    51  	SVC
    52  
    53  	CMP R0, R7
    54  	BNE parent_dead
    55  
    56  	MOVD $SYS_GETPID, R8
    57  	SVC
    58  
    59  	CMP $0x0, R0
    60  	BLT error
    61  
    62  	MOVD $0, R9
    63  
    64  	// SIGSTOP to wait for attach.
    65  	//
    66  	// The SYSCALL instruction will be used for future syscall injection by
    67  	// thread.syscall.
    68  	MOVD $SYS_KILL, R8
    69  	MOVD $SIGSTOP, R1
    70  	SVC
    71  
    72  	// The sentry sets R9 to 1 when creating stub process.
    73  	CMP $1, R9
    74  	BEQ clone
    75  
    76  done:
    77  	// Notify the Sentry that syscall exited.
    78  	BRK $3
    79  	B done // Be paranoid.
    80  clone:
    81  	// subprocess.createStub clones a new stub process that is untraced,
    82  	// thus executing this code. We setup the PDEATHSIG before SIGSTOPing
    83  	// ourselves for attach by the tracer.
    84  	//
    85  	// R7 has been updated with the expected PPID.
    86  	CMP $0, R0
    87  	BEQ begin
    88  
    89  	// The clone system call returned a non-zero value.
    90  	B done
    91  
    92  error:
    93  	// Exit with -errno.
    94  	NEG R0, R0
    95  	MOVD $SYS_EXIT, R8
    96  	SVC
    97  	HLT
    98  
    99  parent_dead:
   100  	MOVD $SYS_EXIT, R8
   101  	MOVD $1, R0
   102  	SVC
   103  	HLT
   104  
   105  // func addrOfStub() uintptr
   106  TEXT ·addrOfStub(SB), $0-8
   107  	MOVD	$·stub(SB), R0
   108  	MOVD	R0, ret+0(FP)
   109  	RET
   110  
   111  // stubCall calls the stub function at the given address with the given PPID.
   112  //
   113  // This is a distinct function because stub, above, may be mapped at any
   114  // arbitrary location, and stub has a specific binary API (see above).
   115  TEXT ·stubCall(SB),NOSPLIT,$0-16
   116  	MOVD addr+0(FP), R0
   117  	MOVD pid+8(FP), R7
   118  	B (R0)