| 1 | .set	noreorder |
| 2 | .global	__clone |
| 3 | .hidden __clone |
| 4 | .type	__clone,@function |
| 5 | __clone: |
| 6 | 	# Save function pointer and argument pointer on new thread stack |
| 7 | 	and	$5, $5, -16	# aligning stack to double word |
| 8 | 	dsubu	$5, $5, 16 |
| 9 | 	sd	$4, 0($5)	# save function pointer |
| 10 | 	sd	$7, 8($5)	# save argument pointer |
| 11 | |
| 12 | 	# Shuffle (fn,sp,fl,arg,ptid,tls,ctid) to (fl,sp,ptid,tls,ctid) |
| 13 | 	# sys_clone(u64 flags, u64 ustack_base, u64 parent_tidptr, u64 child_tidptr, u64 tls) |
| 14 | 	move	$4, $6 |
| 15 | 	move	$6, $8 |
| 16 | 	move	$7, $9 |
| 17 | 	move	$8, $10 |
| 18 | 	li	$2, 5055 |
| 19 | 	syscall |
| 20 | 	beq	$7, $0, 1f |
| 21 | 	nop |
| 22 | 	jr	$ra |
| 23 | 	dsubu	$2, $0, $2 |
| 24 | 1:	beq	$2, $0, 1f |
| 25 | 	nop |
| 26 | 	jr	$ra |
| 27 | 	nop |
| 28 | 1:	move	$fp, $0 |
| 29 | 	ld	$25, 0($sp)	# function pointer |
| 30 | 	ld	$4, 8($sp)	# argument pointer |
| 31 | 	jalr	$25		# call the user's function |
| 32 | 	nop |
| 33 | 	move 	$4, $2 |
| 34 | 	li	$2, 5058 |
| 35 | 	syscall |