diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/fenv/mips64/fenv-sf.c | 3 | ||||
-rw-r--r-- | src/fenv/mips64/fenv.S | 71 | ||||
-rw-r--r-- | src/internal/mips64/syscall.s | 19 | ||||
-rw-r--r-- | src/ldso/mips64/dlsym.s | 17 | ||||
-rw-r--r-- | src/setjmp/mips64/longjmp.S | 37 | ||||
-rw-r--r-- | src/setjmp/mips64/setjmp.S | 34 | ||||
-rw-r--r-- | src/signal/mips64/restore.s | 9 | ||||
-rw-r--r-- | src/signal/mips64/sigsetjmp.s | 38 | ||||
-rw-r--r-- | src/thread/mips64/__unmapself.s | 9 | ||||
-rw-r--r-- | src/thread/mips64/clone.s | 30 | ||||
-rw-r--r-- | src/thread/mips64/syscall_cp.s | 52 | ||||
-rw-r--r-- | src/unistd/mips64/pipe.s | 19 |
12 files changed, 338 insertions, 0 deletions
diff --git a/src/fenv/mips64/fenv-sf.c b/src/fenv/mips64/fenv-sf.c new file mode 100644 index 00000000..4aa3dbf1 --- /dev/null +++ b/src/fenv/mips64/fenv-sf.c @@ -0,0 +1,3 @@ +#ifdef __mips_soft_float +#include "../fenv.c" +#endif diff --git a/src/fenv/mips64/fenv.S b/src/fenv/mips64/fenv.S new file mode 100644 index 00000000..3cba3f0f --- /dev/null +++ b/src/fenv/mips64/fenv.S @@ -0,0 +1,71 @@ +#ifndef __mips_soft_float + +.set noreorder + +.global feclearexcept +.type feclearexcept,@function +feclearexcept: + and $4, $4, 0x7c + cfc1 $5, $31 + or $5, $5, $4 + xor $5, $5, $4 + ctc1 $5, $31 + jr $ra + li $2, 0 + +.global feraiseexcept +.type feraiseexcept,@function +feraiseexcept: + and $4, $4, 0x7c + cfc1 $5, $31 + or $5, $5, $4 + ctc1 $5, $31 + jr $ra + li $2, 0 + +.global fetestexcept +.type fetestexcept,@function +fetestexcept: + and $4, $4, 0x7c + cfc1 $2, $31 + jr $ra + and $2, $2, $4 + +.global fegetround +.type fegetround,@function +fegetround: + cfc1 $2, $31 + jr $ra + andi $2, $2, 3 + +.global __fesetround +.type __fesetround,@function +__fesetround: + cfc1 $5, $31 + li $6, -4 + and $5, $5, $6 + or $5, $5, $4 + ctc1 $5, $31 + jr $ra + li $2, 0 + +.global fegetenv +.type fegetenv,@function +fegetenv: + cfc1 $5, $31 + sw $5, 0($4) + jr $ra + li $2, 0 + +.global fesetenv +.type fesetenv,@function +fesetenv: + daddiu $5, $4, 1 + beq $5, $0, 1f + nop + lw $5, 0($4) +1: ctc1 $5, $31 + jr $ra + li $2, 0 + +#endif diff --git a/src/internal/mips64/syscall.s b/src/internal/mips64/syscall.s new file mode 100644 index 00000000..98448667 --- /dev/null +++ b/src/internal/mips64/syscall.s @@ -0,0 +1,19 @@ +.set noreorder +.global __syscall +.hidden __syscall +.type __syscall,@function +__syscall: + move $2, $4 + move $4, $5 + move $5, $6 + move $6, $7 + move $7, $8 + move $8, $9 + move $9, $10 + move $10, $11 + syscall + beq $7, $0, 1f + nop + dsubu $2, $0, $2 +1: jr $ra + nop diff --git a/src/ldso/mips64/dlsym.s b/src/ldso/mips64/dlsym.s new file mode 100644 index 00000000..32e0dddc --- /dev/null +++ b/src/ldso/mips64/dlsym.s @@ -0,0 +1,17 @@ +.set noreorder +.global dlsym +.hidden __dlsym +.type dlsym,@function +dlsym: + lui $3, %hi(%neg(%gp_rel(dlsym))) + daddiu $3, $3, %lo(%neg(%gp_rel(dlsym))) + daddu $3, $3, $25 + move $6, $ra + ld $25, %got_disp(__dlsym)($3) + daddiu $sp, $sp, -32 + sd $ra, 24($sp) + jalr $25 + nop + ld $ra, 24($sp) + jr $ra + daddiu $sp, $sp, 32 diff --git a/src/setjmp/mips64/longjmp.S b/src/setjmp/mips64/longjmp.S new file mode 100644 index 00000000..3db8a883 --- /dev/null +++ b/src/setjmp/mips64/longjmp.S @@ -0,0 +1,37 @@ +.set noreorder +.global _longjmp +.global longjmp +.type _longjmp,@function +.type longjmp,@function +_longjmp: +longjmp: + move $2, $5 + + bne $2, $0, 1f + nop + daddu $2, $2, 1 +1: +#ifndef __mips_soft_float + ldc1 $24, 96($4) + ldc1 $25, 104($4) + ldc1 $26, 112($4) + ldc1 $27, 120($4) + ldc1 $28, 128($4) + ldc1 $29, 136($4) + ldc1 $30, 144($4) + ldc1 $31, 152($4) +#endif + ld $ra, 0($4) + ld $sp, 8($4) + ld $gp, 16($4) + ld $16, 24($4) + ld $17, 32($4) + ld $18, 40($4) + ld $19, 48($4) + ld $20, 56($4) + ld $21, 64($4) + ld $22, 72($4) + ld $23, 80($4) + ld $30, 88($4) + jr $ra + nop diff --git a/src/setjmp/mips64/setjmp.S b/src/setjmp/mips64/setjmp.S new file mode 100644 index 00000000..b9646c2a --- /dev/null +++ b/src/setjmp/mips64/setjmp.S @@ -0,0 +1,34 @@ +.set noreorder +.global __setjmp +.global _setjmp +.global setjmp +.type __setjmp,@function +.type _setjmp,@function +.type setjmp,@function +__setjmp: +_setjmp: +setjmp: + sd $ra, 0($4) + sd $sp, 8($4) + sd $gp, 16($4) + sd $16, 24($4) + sd $17, 32($4) + sd $18, 40($4) + sd $19, 48($4) + sd $20, 56($4) + sd $21, 64($4) + sd $22, 72($4) + sd $23, 80($4) + sd $30, 88($4) +#ifndef __mips_soft_float + sdc1 $24, 96($4) + sdc1 $25, 104($4) + sdc1 $26, 112($4) + sdc1 $27, 120($4) + sdc1 $28, 128($4) + sdc1 $29, 136($4) + sdc1 $30, 144($4) + sdc1 $31, 152($4) +#endif + jr $ra + li $2, 0 diff --git a/src/signal/mips64/restore.s b/src/signal/mips64/restore.s new file mode 100644 index 00000000..e8988369 --- /dev/null +++ b/src/signal/mips64/restore.s @@ -0,0 +1,9 @@ +.set noreorder +.global __restore_rt +.global __restore +.type __restore_rt,@function +.type __restore,@function +__restore_rt: +__restore: + li $2,5211 + syscall diff --git a/src/signal/mips64/sigsetjmp.s b/src/signal/mips64/sigsetjmp.s new file mode 100644 index 00000000..156e70bd --- /dev/null +++ b/src/signal/mips64/sigsetjmp.s @@ -0,0 +1,38 @@ +.set noreorder +.global sigsetjmp +.global __sigsetjmp +.type sigsetjmp,@function +.type __sigsetjmp,@function +sigsetjmp: +__sigsetjmp: + lui $3, %hi(%neg(%gp_rel(sigsetjmp))) + daddiu $3, $3, %lo(%neg(%gp_rel(sigsetjmp))) + + # comparing save mask with 0, if equals to 0 then + # sigsetjmp is equal to setjmp. + beq $5, $0, 1f + daddu $3, $3, $25 + sd $ra, 160($4) + sd $16, 168($4) + + # save base of got so that we can use it later + # once we return from 'longjmp' + sd $3, 176($4) + ld $25, %got_disp(setjmp)($3) + jalr $25 + move $16, $4 + + move $5, $2 # Return from 'setjmp' or 'longjmp' + move $4, $16 # Restore the pointer-to-sigjmp_buf + ld $ra, 160($4) # Restore ra of sigsetjmp + ld $16, 168($4) # Restore $16 of sigsetjmp + ld $3, 176($4) # Restore base of got + +.hidden __sigsetjmp_tail + ld $25, %got_disp(__sigsetjmp_tail)($3) + jr $25 + nop +1: + ld $25, %got_disp(setjmp)($3) + jr $25 + nop diff --git a/src/thread/mips64/__unmapself.s b/src/thread/mips64/__unmapself.s new file mode 100644 index 00000000..f6795cda --- /dev/null +++ b/src/thread/mips64/__unmapself.s @@ -0,0 +1,9 @@ +.set noreorder +.global __unmapself +.type __unmapself, @function +__unmapself: + li $2, 5011 + syscall + li $4, 0 + li $2, 5058 + syscall diff --git a/src/thread/mips64/clone.s b/src/thread/mips64/clone.s new file mode 100644 index 00000000..229d2677 --- /dev/null +++ b/src/thread/mips64/clone.s @@ -0,0 +1,30 @@ +.set noreorder +.global __clone +.type __clone,@function +__clone: + # Save function pointer and argument pointer on new thread stack + and $5, $5, -16 # aligning stack to double word + dsubu $5, $5, 16 + sd $4, 0($5) # save function pointer + sd $7, 8($5) # save argument pointer + + # Shuffle (fn,sp,fl,arg,ptid,tls,ctid) to (fl,sp,ptid,tls,ctid) + # sys_clone(u64 flags, u64 ustack_base, u64 parent_tidptr, u64 child_tidptr, u64 tls) + move $4, $6 + move $6, $8 + move $7, $9 + move $8, $10 + li $2, 5055 + syscall + beq $7, $0, 1f + nop + jr $ra + dsubu $2, $0, $2 +1: beq $2, $0, 1f + nop + jr $ra + nop +1: ld $25, 0($sp) # function pointer + ld $4, 8($sp) # argument pointer + jr $25 # call the user's function + nop diff --git a/src/thread/mips64/syscall_cp.s b/src/thread/mips64/syscall_cp.s new file mode 100644 index 00000000..0d4ede76 --- /dev/null +++ b/src/thread/mips64/syscall_cp.s @@ -0,0 +1,52 @@ +.set noreorder +.global __cp_begin +.hidden __cp_begin +.type __cp_begin,@function +.global __cp_end +.hidden __cp_end +.type __cp_end,@function +.global __cp_cancel +.hidden __cp_cancel +.type __cp_cancel,@function +.global __cp_cancel_data +.hidden __cp_cancel_data +.type __cp_cancel_data,@function +.hidden __cancel +.global __syscall_cp_asm +.hidden __syscall_cp_asm +.type __syscall_cp_asm,@function +__syscall_cp_asm: +__cp_begin: + lw $4, 0($4) + bne $4, $0, __cp_cancel + move $2, $5 + move $4, $6 + move $5, $7 + move $6, $8 + move $7, $9 + move $8, $10 + move $9, $11 + ld $10, 0($sp) + syscall +__cp_end: + beq $7, $0, 1f + nop + dsubu $2, $0, $2 +1: jr $ra + nop + + # if cancellation flag is 1 then call __cancel +__cp_cancel: + move $2, $ra +.align 8 + bal 1f + nop +__cp_cancel_data: + .gpdword __cp_cancel_data + .gpdword __cancel +1: ld $3, ($ra) + dsubu $3, $ra, $3 + ld $25, 8($ra) + daddu $25, $25, $3 + jr $25 + move $ra, $2 diff --git a/src/unistd/mips64/pipe.s b/src/unistd/mips64/pipe.s new file mode 100644 index 00000000..f8a27dcc --- /dev/null +++ b/src/unistd/mips64/pipe.s @@ -0,0 +1,19 @@ +.set noreorder +.global pipe +.type pipe,@function +pipe: + lui $3, %hi(%neg(%gp_rel(pipe))) + daddiu $3, $3, %lo(%neg(%gp_rel(pipe))) + daddu $3, $3, $25 + li $2, 5021 + syscall + beq $7, $0, 1f + nop + ld $25, %got_disp(__syscall_ret)($3) + jr $25 + dsubu $4, $0, $2 +1: sw $2, 0($4) + sw $3, 4($4) + move $2, $0 + jr $ra + nop |