[MIPS64] libc/libm support

libc/libm support for MIPS64 targets

Change-Id: I8271941d418612a286be55495f0e95822f90004f
Signed-off-by: Chris Dearman <chris.dearman@imgtec.com>
Signed-off-by: Raghu Gandham <raghu.gandham@imgtec.com>
diff --git a/libc/arch-mips64/bionic/__bionic_clone.S b/libc/arch-mips64/bionic/__bionic_clone.S
new file mode 100644
index 0000000..2a9a2b0
--- /dev/null
+++ b/libc/arch-mips64/bionic/__bionic_clone.S
@@ -0,0 +1,99 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <machine/asm.h>
+#include <asm/unistd.h>
+#include <linux/errno.h>
+#include <linux/sched.h>
+
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+FRAMESZ		=	MKFSIZ(NARGSAVE,0)
+FRAME_ARG	=	0*REGSZ
+FRAME_FN	=	1*REGSZ
+#else
+FRAMESZ		=	MKFSIZ(0,3)
+FRAME_GP	=	FRAMESZ-1*REGSZ
+FRAME_ARG	=	FRAMESZ-2*REGSZ
+FRAME_FN	=	FRAMESZ-3*REGSZ
+#endif
+
+// pid_t __bionic_clone(int flags, void* child_stack, pid_t* parent_tid, void* tls, pid_t* child_tid, int (*fn)(void*), void* arg);
+	.text
+LEAF(__bionic_clone,FRAMESZ)
+	PTR_SUBU sp, FRAMESZ			# allocate stack frame
+	SETUP_GP64(FRAME_GP,__bionic_clone)
+	SAVE_GP(FRAME_GP)
+
+	# set up child stack
+	PTR_SUBU a1,FRAMESZ
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+	PTR_L	t0,FRAMESZ+5*REGSZ(sp)	# fn
+	PRL_L	t1,FRAMESZ+6*REGSZ(sp)	# arg
+	PTR_S	t0,FRAME_FN(a1)		# fn
+	PTR_S	t1,FRAME_ARG(a1)	# arg
+#else
+	PTR_L	t0,FRAME_GP(sp)		# copy gp to child stack
+	PTR_S	t0,FRAME_GP(a1)
+	PTR_S	a5,FRAME_FN(a1)		# fn
+	PTR_S	a6,FRAME_ARG(a1)	# arg
+# endif
+
+	# remainder of arguments are correct for clone system call
+	LI	v0,__NR_clone
+	syscall
+
+	move    a0,v0
+	bnez	a3,.L__error_bc
+
+	beqz	v0,.L__thread_start_bc
+
+	RESTORE_GP64
+	PTR_ADDU sp,FRAMESZ
+	j	ra
+
+.L__thread_start_bc:
+	# void __bionic_clone_entry(int (*func)(void*), void *arg)
+	PTR_L	a0,FRAME_FN(sp)		#  fn
+	PTR_L	a1,FRAME_ARG(sp)	#  arg
+	LA	t9,__bionic_clone_entry
+	RESTORE_GP64
+	/*
+	 * For O32 etc the child stack must have space for a0..a3 to be stored
+	 * For N64 etc, the child stack can be restored to the original value
+	 */
+#if !((_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32))
+	PTR_ADDU sp,FRAMESZ
+#endif
+	j	t9
+
+.L__error_bc:
+	LA	t9,__set_errno
+	RESTORE_GP64
+	PTR_ADDU sp,FRAMESZ
+	j	t9
+	END(__bionic_clone)
diff --git a/libc/arch-mips64/bionic/__get_sp.S b/libc/arch-mips64/bionic/__get_sp.S
new file mode 100644
index 0000000..834c89d
--- /dev/null
+++ b/libc/arch-mips64/bionic/__get_sp.S
@@ -0,0 +1,39 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+	.text
+
+/* void *__get_sp(void) */
+
+	.type	__get_sp, @function
+	.global	__get_sp
+	.align	4
+	.ent	__get_sp
+__get_sp:
+	move	$v0, $sp
+	j	$ra
+	.end	__get_sp
diff --git a/libc/arch-mips64/bionic/__set_tls.c b/libc/arch-mips64/bionic/__set_tls.c
new file mode 100644
index 0000000..38e3a50
--- /dev/null
+++ b/libc/arch-mips64/bionic/__set_tls.c
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+#include <pthread.h>
+
+extern int __set_thread_area(void *u_info);
+
+int __set_tls(void *ptr)
+{
+    return __set_thread_area(ptr);
+}
diff --git a/libc/arch-mips64/bionic/_exit_with_stack_teardown.S b/libc/arch-mips64/bionic/_exit_with_stack_teardown.S
new file mode 100644
index 0000000..8f624c3
--- /dev/null
+++ b/libc/arch-mips64/bionic/_exit_with_stack_teardown.S
@@ -0,0 +1,48 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <asm/unistd.h>
+
+	.text
+
+// void _exit_with_stack_teardown(void* stackBase, size_t stackSize)
+
+	.type	_exit_with_stack_teardown, @function
+	.global	_exit_with_stack_teardown
+	.align	4
+	.ent	_exit_with_stack_teardown
+_exit_with_stack_teardown:
+	li	$v0, __NR_munmap
+	syscall
+	// If munmap failed, we ignore the failure and exit anyway.
+
+	li	$a0, 0
+	li	$v0, __NR_exit
+	syscall
+        // The exit syscall does not return.
+	.end	_exit_with_stack_teardown
diff --git a/libc/arch-mips64/bionic/_setjmp.S b/libc/arch-mips64/bionic/_setjmp.S
new file mode 100644
index 0000000..e7083ae
--- /dev/null
+++ b/libc/arch-mips64/bionic/_setjmp.S
@@ -0,0 +1,188 @@
+/*	$OpenBSD: _setjmp.S,v 1.4 2005/08/07 16:40:15 espie Exp $ */
+
+/*
+ * Copyright (c) 2002 Opsycon AB  (www.opsycon.se / www.opsycon.com)
+ * 
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Opsycon AB nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ */
+
+#include <machine/asm.h>
+#include <machine/regnum.h>
+#include <machine/signal.h>
+
+/*
+ * _setjmp, _longjmp (not restoring signal state)
+ *
+ * XXX FPSET should probably be taken from SR setting. hmmm...
+ *  GPOFF and FRAMESIZE must be the same for both _setjmp and _longjmp!
+ *
+ */
+
+FRAMESZ= MKFSIZ(0,4)
+GPOFF= FRAMESZ-2*REGSZ
+
+#define FPREG64_S(FPR, OFF, BASE)       \
+        swc1    FPR, OFF(BASE)  ;       \
+        mfhc1   t0, FPR         ;       \
+        sw      t0, OFF+4(BASE) ;
+        
+#define FPREG64_L(FPR, OFF, BASE)       \
+        lw      t0, OFF+4(BASE) ;       \
+        lw      t1, OFF(BASE)   ;       \
+        mtc1    t1, FPR         ;       \
+        mthc1   t0, FPR         ;       \
+        
+LEAF(_setjmp, FRAMESZ)
+	PTR_SUBU sp, FRAMESZ
+	SETUP_GP64(GPOFF, _setjmp)
+	SAVE_GP(GPOFF)
+	.set	noreorder
+#if defined(__mips64)
+	dli	v0, 0xACEDBADE			# sigcontext magic number
+#else
+	li	v0, 0xACEDBADE			# sigcontext magic number
+#endif
+	REG_S	v0, SC_REGS+ZERO*REGSZ(a0)
+	REG_S	s0, SC_REGS+S0*REGSZ(a0)
+	REG_S	s1, SC_REGS+S1*REGSZ(a0)
+	REG_S	s2, SC_REGS+S2*REGSZ(a0)
+	REG_S	s3, SC_REGS+S3*REGSZ(a0)
+	REG_S	s4, SC_REGS+S4*REGSZ(a0)
+	REG_S	s5, SC_REGS+S5*REGSZ(a0)
+	REG_S	s6, SC_REGS+S6*REGSZ(a0)
+	REG_S	s7, SC_REGS+S7*REGSZ(a0)
+	REG_S	s8, SC_REGS+S8*REGSZ(a0)
+	REG_L	v0, GPOFF(sp)
+	REG_S	v0, SC_REGS+GP*REGSZ(a0)
+	PTR_ADDU v0, sp, FRAMESZ
+	REG_S	v0, SC_REGS+SP*REGSZ(a0)
+	REG_S	ra, SC_PC(a0)
+
+#if !defined(SOFTFLOAT)
+	li	v0, 1				# be nice if we could tell
+	REG_S	v0, SC_FPUSED(a0)		# sc_fpused = 1
+	cfc1	v0, $31
+#if _MIPS_FPSET == 32
+        FPREG64_S($f20, SC_FPREGS+((F20-F0)*REGSZ_FP), a0)
+        FPREG64_S($f21, SC_FPREGS+((F21-F0)*REGSZ_FP), a0)
+        FPREG64_S($f22, SC_FPREGS+((F22-F0)*REGSZ_FP), a0)
+        FPREG64_S($f23, SC_FPREGS+((F23-F0)*REGSZ_FP), a0)
+        FPREG64_S($f24, SC_FPREGS+((F24-F0)*REGSZ_FP), a0)
+        FPREG64_S($f25, SC_FPREGS+((F25-F0)*REGSZ_FP), a0)
+        FPREG64_S($f26, SC_FPREGS+((F26-F0)*REGSZ_FP), a0)
+        FPREG64_S($f27, SC_FPREGS+((F27-F0)*REGSZ_FP), a0)
+        FPREG64_S($f28, SC_FPREGS+((F28-F0)*REGSZ_FP), a0)
+        FPREG64_S($f29, SC_FPREGS+((F29-F0)*REGSZ_FP), a0)
+        FPREG64_S($f30, SC_FPREGS+((F30-F0)*REGSZ_FP), a0)
+        FPREG64_S($f31, SC_FPREGS+((F31-F0)*REGSZ_FP), a0)
+#else
+        swc1    $f20, SC_FPREGS+((F20-F0)*REGSZ_FP)(a0)
+        swc1    $f21, SC_FPREGS+((F21-F0)*REGSZ_FP)(a0)
+        swc1    $f22, SC_FPREGS+((F22-F0)*REGSZ_FP)(a0)
+        swc1    $f23, SC_FPREGS+((F23-F0)*REGSZ_FP)(a0)
+        swc1    $f24, SC_FPREGS+((F24-F0)*REGSZ_FP)(a0)
+        swc1    $f25, SC_FPREGS+((F25-F0)*REGSZ_FP)(a0)
+        swc1    $f26, SC_FPREGS+((F26-F0)*REGSZ_FP)(a0)
+        swc1    $f27, SC_FPREGS+((F27-F0)*REGSZ_FP)(a0)
+        swc1    $f28, SC_FPREGS+((F28-F0)*REGSZ_FP)(a0)
+        swc1    $f29, SC_FPREGS+((F29-F0)*REGSZ_FP)(a0)
+        swc1    $f30, SC_FPREGS+((F30-F0)*REGSZ_FP)(a0)
+        swc1    $f31, SC_FPREGS+((F31-F0)*REGSZ_FP)(a0)
+#endif
+	REG_S	v0, SC_FPREGS+((FSR-F0)*REGSZ)(a0)
+#endif /* !SOFTFLOAT */
+	RESTORE_GP64
+	PTR_ADDU sp, FRAMESZ
+	j	ra
+	 move	v0, zero
+END(_setjmp)
+
+LEAF(_longjmp, FRAMESZ)
+	PTR_SUBU sp, FRAMESZ
+	SETUP_GP64(GPOFF, _longjmp)
+	SAVE_GP(GPOFF)
+	.set    noreorder
+	REG_L	v0, SC_REGS+ZERO*REGSZ(a0)
+	bne	v0, 0xACEDBADE, botch		# jump if error
+	REG_L	ra, SC_PC(a0)
+	REG_L	v0, SC_FPREGS+((FSR-F0)*REGSZ)(a0)
+	REG_L	s0, SC_REGS+S0*REGSZ(a0)
+	REG_L	s1, SC_REGS+S1*REGSZ(a0)
+	REG_L	s2, SC_REGS+S2*REGSZ(a0)
+	REG_L	s3, SC_REGS+S3*REGSZ(a0)
+	REG_L	s4, SC_REGS+S4*REGSZ(a0)
+	REG_L	s5, SC_REGS+S5*REGSZ(a0)
+	REG_L	s6, SC_REGS+S6*REGSZ(a0)
+	REG_L	s7, SC_REGS+S7*REGSZ(a0)
+	REG_L	s8, SC_REGS+S8*REGSZ(a0)
+	REG_L	gp, SC_REGS+GP*REGSZ(a0)
+	REG_L	sp, SC_REGS+SP*REGSZ(a0)
+#if !defined(SOFTFLOAT)
+	ctc1	v0, $31
+#if _MIPS_FPSET == 32
+        FPREG64_L($f20, SC_FPREGS+((F20-F0)*REGSZ_FP), a0)
+        FPREG64_L($f21, SC_FPREGS+((F21-F0)*REGSZ_FP), a0)
+        FPREG64_L($f22, SC_FPREGS+((F22-F0)*REGSZ_FP), a0)
+        FPREG64_L($f23, SC_FPREGS+((F23-F0)*REGSZ_FP), a0)
+        FPREG64_L($f24, SC_FPREGS+((F24-F0)*REGSZ_FP), a0)
+        FPREG64_L($f25, SC_FPREGS+((F25-F0)*REGSZ_FP), a0)
+        FPREG64_L($f26, SC_FPREGS+((F26-F0)*REGSZ_FP), a0)
+        FPREG64_L($f27, SC_FPREGS+((F27-F0)*REGSZ_FP), a0)
+        FPREG64_L($f28, SC_FPREGS+((F28-F0)*REGSZ_FP), a0)
+        FPREG64_L($f29, SC_FPREGS+((F29-F0)*REGSZ_FP), a0)
+        FPREG64_L($f30, SC_FPREGS+((F30-F0)*REGSZ_FP), a0)
+        FPREG64_L($f31, SC_FPREGS+((F31-F0)*REGSZ_FP), a0)
+#else
+        lwc1    $f20, SC_FPREGS+((F20-F0)*REGSZ_FP)(a0)
+        lwc1    $f21, SC_FPREGS+((F21-F0)*REGSZ_FP)(a0)
+        lwc1    $f22, SC_FPREGS+((F22-F0)*REGSZ_FP)(a0)
+        lwc1    $f23, SC_FPREGS+((F23-F0)*REGSZ_FP)(a0)
+        lwc1    $f24, SC_FPREGS+((F24-F0)*REGSZ_FP)(a0)
+        lwc1    $f25, SC_FPREGS+((F25-F0)*REGSZ_FP)(a0)
+        lwc1    $f26, SC_FPREGS+((F26-F0)*REGSZ_FP)(a0)
+        lwc1    $f27, SC_FPREGS+((F27-F0)*REGSZ_FP)(a0)
+        lwc1    $f28, SC_FPREGS+((F28-F0)*REGSZ_FP)(a0)
+        lwc1    $f29, SC_FPREGS+((F29-F0)*REGSZ_FP)(a0)
+        lwc1    $f30, SC_FPREGS+((F30-F0)*REGSZ_FP)(a0)
+        lwc1    $f31, SC_FPREGS+((F31-F0)*REGSZ_FP)(a0)
+#endif
+#endif /* !SOFTFLOAT */
+	bne	a1, zero, 1f
+	 nop
+	li	a1, 1			# never return 0!
+1:
+	j	ra
+	 move	v0, a1
+
+botch:
+	jal	longjmperror
+	nop
+	jal	abort
+	nop
+	RESTORE_GP64
+	PTR_ADDU sp, FRAMESZ
+END(_longjmp)
+
diff --git a/libc/arch-mips64/bionic/atexit.h b/libc/arch-mips64/bionic/atexit.h
new file mode 100644
index 0000000..759008c
--- /dev/null
+++ b/libc/arch-mips64/bionic/atexit.h
@@ -0,0 +1,36 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+extern void *__dso_handle;
+extern int __cxa_atexit(void (*func)(void *), void *arg, void *dso);
+
+__attribute__ ((visibility ("hidden")))
+int atexit(void (*func)(void))
+{
+  return (__cxa_atexit((void (*)(void *))func, (void *)0, &__dso_handle));
+}
diff --git a/libc/arch-mips64/bionic/bzero.S b/libc/arch-mips64/bionic/bzero.S
new file mode 100644
index 0000000..d0b5c84
--- /dev/null
+++ b/libc/arch-mips64/bionic/bzero.S
@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+	.text
+
+#include <machine/asm.h>
+
+/*
+ * void bzero(void *s, size_t n);
+ */
+LEAF(bzero,0)
+	SETUP_GP64(t0,bzero)
+	move	a2,a1
+	move	a1,zero
+	LA	t9,memset
+	RESTORE_GP64
+	j	t9
+END(bzero)
+
diff --git a/libc/arch-mips64/bionic/cacheflush.cpp b/libc/arch-mips64/bionic/cacheflush.cpp
new file mode 100644
index 0000000..7955dd6
--- /dev/null
+++ b/libc/arch-mips64/bionic/cacheflush.cpp
@@ -0,0 +1,99 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+#include <unistd.h>
+#include <sys/cachectl.h>
+
+#ifdef DEBUG
+#include "private/libc_logging.h"
+#define  XLOG(...) __libc_format_log(ANDROID_LOG_DEBUG,"libc-cacheflush",__VA_ARGS__)
+#endif
+
+/*
+ * Linux historically defines a cacheflush(3) routine for MIPS
+ * with this signature:
+ * int cacheflush(char *addr, int nbytes, int cache);
+ *
+ * Android defines an alternate cacheflush routine which exposes the
+ * ARM system call interface:
+ * int cacheflush (long start, long end, long flags)
+ *
+ * This is an attempt to maintain compatibility between the historical MIPS
+ * usage for software previously ported to MIPS and Android specific
+ * uses of cacheflush()
+ *
+ * Use the gcc __clear_cache builtin if possible. This will generate inline synci
+ * instructions if available or call _flush_cache(start, len, BCACHE) directly
+ */
+
+#if defined (__GNUC__)
+#define GCC_VERSION ((__GNUC__*10000) + __GNUC_MINOR__*100 + __GNUC_PATCHLEVEL__)
+#endif
+
+/* This is the Android signature */
+int cacheflush (long start, long end, long /*flags*/) {
+	if (end < start) {
+		/*
+		 * It looks like this is really MIPS style cacheflush call
+		 * start => addr
+		 * end => nbytes
+		 */
+#ifdef DEBUG
+		static int warned = 0;
+		if (!warned) {
+			XLOG("called with (start,len) instead of (start,end)");
+			warned = 1;
+		}
+#endif
+		end += start;
+	}
+
+#if !defined(ARCH_MIPS_USE_FLUSHCACHE_SYSCALL) && \
+	defined(GCC_VERSION) && (GCC_VERSION >= 40300)
+
+#if (__mips_isa_rev >= 2) && (GCC_VERSION < 40403)
+	/*
+	 * Modify "start" and "end" to avoid GCC 4.3.0-4.4.2 bug in
+	 * mips_expand_synci_loop that may execute synci one more time.
+	 * "start" points to the first byte of the cache line.
+	 * "end" points to the last byte of the line before the last cache line.
+	 * Because size is always a multiple of 4, this is safe to set
+	 * "end" to the last byte.
+	 */
+	{
+		int lineSize;
+		asm("rdhwr %0, $1" : "=r" (lineSize));
+		start = start & (-lineSize);
+		end = (end & (-lineSize)) - 1;
+	}
+#endif
+	__builtin___clear_cache((char *)start, (char *)end);
+#else
+	_flush_cache((char *)start, end-start, BCACHE);
+#endif
+	return 0;
+}
diff --git a/libc/arch-mips64/bionic/crtbegin.c b/libc/arch-mips64/bionic/crtbegin.c
new file mode 100644
index 0000000..2ea31ad
--- /dev/null
+++ b/libc/arch-mips64/bionic/crtbegin.c
@@ -0,0 +1,94 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include "../../bionic/libc_init_common.h"
+#include <stddef.h>
+#include <stdint.h>
+
+__attribute__ ((section (".preinit_array")))
+void (*__PREINIT_ARRAY__)(void) = (void (*)(void)) -1;
+
+__attribute__ ((section (".init_array")))
+void (*__INIT_ARRAY__)(void) = (void (*)(void)) -1;
+
+__attribute__ ((section (".fini_array")))
+void (*__FINI_ARRAY__)(void) = (void (*)(void)) -1;
+
+
+__LIBC_HIDDEN__  void do_mips_start(void *raw_args) {
+  structors_array_t array;
+  array.preinit_array = &__PREINIT_ARRAY__;
+  array.init_array = &__INIT_ARRAY__;
+  array.fini_array = &__FINI_ARRAY__;
+
+  __libc_init(raw_args, NULL, &main, &array);
+}
+
+/*
+ * This function prepares the return address with a branch-and-link
+ * instruction (bal) and then uses a .cpsetup to compute the Global
+ * Offset Table (GOT) pointer ($gp). The $gp is then used to load
+ * the address of _do_mips_start() into $t9 just before calling it.
+ * Terminating the stack with a NULL return address.
+ */
+__asm__ (
+"       .set push                   \n"
+"                                   \n"
+"       .text                       \n"
+"       .align  4                   \n"
+"       .type __start,@function     \n"
+"       .globl __start              \n"
+"       .globl  _start              \n"
+"                                   \n"
+"       .ent    __start             \n"
+"__start:                           \n"
+" _start:                           \n"
+"       .frame   $sp,32,$0          \n"
+"       .mask   0x80000000,-8       \n"
+"                                   \n"
+"       move    $a0, $sp            \n"
+"       daddiu  $sp, $sp, -32       \n"
+"                                   \n"
+"       .set noreorder              \n"
+"       bal     1f                  \n"
+"       nop                         \n"
+"1:                                 \n"
+"       .cpsetup $ra,16,1b          \n"
+"       .set reorder                \n"
+"                                   \n"
+"       sd      $0, 24($sp)         \n"
+"       jal     do_mips_start       \n"
+"                                   \n"
+"2:     b       2b                  \n"
+"       .end    __start             \n"
+"                                   \n"
+"       .set pop                    \n"
+);
+
+#include "../../arch-common/bionic/__dso_handle.h"
+#include "atexit.h"
diff --git a/libc/arch-mips64/bionic/crtbegin_so.c b/libc/arch-mips64/bionic/crtbegin_so.c
new file mode 100644
index 0000000..d664ce6
--- /dev/null
+++ b/libc/arch-mips64/bionic/crtbegin_so.c
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+extern void __cxa_finalize(void *);
+extern void *__dso_handle;
+
+__attribute__((visibility("hidden"),destructor))
+void __on_dlclose() {
+  __cxa_finalize(&__dso_handle);
+}
+
+#include "../../arch-common/bionic/__dso_handle_so.h"
+#include "atexit.h"
diff --git a/libc/arch-mips64/bionic/futex_mips.S b/libc/arch-mips64/bionic/futex_mips.S
new file mode 100644
index 0000000..1a249a7
--- /dev/null
+++ b/libc/arch-mips64/bionic/futex_mips.S
@@ -0,0 +1,145 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <machine/asm.h>
+#include <private/bionic_asm.h>
+
+#define FUTEX_WAIT 0
+#define FUTEX_WAKE 1
+
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+FRAMESZ		=	MKFSIZ(NARGSAVE+2,0)
+FRAME_A4	=	4*REGSZ
+FRAME_A5	=	5*REGSZ
+#else
+FRAMESZ		=	0
+#endif
+
+// int __futex_wait(volatile void* ftx, int val, const struct timespec* timeout)
+LEAF(__futex_wait, FRAMESZ)
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+	PTR_SUBU sp, FRAMESZ
+	REG_S	$0,FRAME_A5(sp)	/* val3 */
+	REG_S	$0,FRAME_A4(sp)	/* addr2 */
+#else
+	move	a5,$0		/* val3 */
+	move	a4,$0		/* addr2 */
+#endif
+	move	a3,a2		/* timespec */
+	move	a2,a1		/* val */
+	LI	a1,FUTEX_WAIT	/* op */
+#	move	a0,a0		/* ftx */
+	LI	v0,__NR_futex
+	syscall
+	neg	v0		/* Negate errno */
+	bnez	a3,1f		/* Check for error */
+	move	v0,$0		/* Return 0 if no error */
+1:
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+	PTR_ADDU sp,FRAMESZ
+#endif
+	j	ra
+	END(__futex_wait)
+
+// int __futex_wake(volatile void* ftx, int count)
+LEAF(__futex_wake,FRAMESZ)
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+	PTR_SUBU sp, FRAMESZ
+	REG_S	$0,FRAME_A5(sp)	/* val3 */
+	REG_S	$0,FRAME_A4(sp)	/* addr2 */
+#else
+	move	a5,$0		/* val3 */
+	move	a4,$0		/* addr2 */
+#endif
+	move	a3,$0		/* timespec */
+	move	a2,a1		/* val */
+	LI	a1,FUTEX_WAKE	/* op */
+#	move	a0,a0		/* ftx */
+	LI	v0,__NR_futex
+	syscall
+	neg	v0		/* Negate errno */
+	bnez	a3,1f		/* Check for error */
+	move	v0,$0		/* Return 0 if no error */
+1:
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+	PTR_ADDU sp,FRAMESZ
+#endif
+	j	ra
+	END(__futex_wake)
+
+// int __futex_syscall3(volatile void* ftx, int op, int count)
+LEAF(__futex_syscall3,FRAMESZ)
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+	PTR_SUBU sp, FRAMESZ
+	REG_S	$0,FRAME_A5(sp)	/* val3 */
+	REG_S	$0,FRAME_A4(sp)	/* addr2 */
+#else
+	move	a5,$0		/* val3 */
+	move	a4,$0		/* addr2 */
+#endif
+	move	a3,$0		/* timespec */
+#	move	a2,a2		/* val */
+#	move	a1,a1		/* op */
+#	move	a0,a0		/* ftx */
+	LI	v0,__NR_futex
+	syscall
+	neg	v0		/* Negate errno */
+	bnez	a3,1f		/* Check for error */
+	move	v0,$0		/* Return 0 if no error */
+1:
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+	PTR_ADDU sp,FRAMESZ
+#endif
+	j	ra
+	END(__futex_syscall3)
+
+// int __futex_syscall4(volatile void* ftx, int op, int val, const struct timespec* timeout)
+LEAF(__futex_syscall4,FRAMESZ)
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+	PTR_SUBU sp, FRAMESZ
+	REG_S	$0,FRAME_A5(sp)	/* val3 */
+	REG_S	$0,FRAME_A4(sp)	/* addr2 */
+#else
+	move	a5,$0		/* val3 */
+	move	a4,$0		/* addr2 */
+#endif
+#	move	a3,a3		/* timespec */
+#	move	a2,a2		/* val */
+#	move	a1,a1		/* op */
+#	move	a0,a0		/* ftx */
+	LI	v0,__NR_futex
+	syscall
+	neg	v0		/* Negate errno */
+	bnez	a3,1f		/* Check for error */
+	move	v0,$0		/* Return 0 if no error */
+1:
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+	PTR_ADDU sp,FRAMESZ
+#endif
+	j	ra
+	END(__futex_syscall4)
diff --git a/libc/arch-mips64/bionic/getdents.cpp b/libc/arch-mips64/bionic/getdents.cpp
new file mode 100644
index 0000000..66a61ec
--- /dev/null
+++ b/libc/arch-mips64/bionic/getdents.cpp
@@ -0,0 +1,97 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+/*
+ * The MIPS64 getdents64() system call is only present in 3.10+ kernels.
+ * If the getdents64() system call is not available fall back to using
+ * getdents() and modify the result to be compatible with getdents64().
+ */
+
+#include <dirent.h>
+
+#include <errno.h>
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+
+/* The mips_getdents type is 64bit clean */
+struct mips_dirent {
+        uint64_t d_ino;     /* Inode number */
+        uint64_t d_off;     /* Offset to next mips_dirent */
+        uint16_t d_reclen;  /* Length of this mips_dirent */
+        char     d_name[];  /* Filename (null-terminated) */
+                            /* length is actually (d_reclen - 2 -
+                               offsetof(struct mips_dirent, d_name) */
+        // char  pad;       /* Zero padding byte */
+        // char  d_type;    /* File type (only since Linux 2.6.4; offset is (d_reclen - 1)) */
+};
+
+extern "C" int __getdents64(unsigned int fd, struct dirent *dirp, unsigned int count);
+extern "C" int __getdents(unsigned int fd, struct mips_dirent *dirp, unsigned int count);
+int getdents(unsigned int fd, struct dirent *dirp, unsigned int count)
+{
+        int r;
+        int oerrno = errno;
+
+        /* Use getdents64() if it is available */
+        r = __getdents64(fd, dirp, count);
+        if (r >= 0 || errno != ENOSYS)
+                return r;
+
+        /* Fallback to getdents() */
+        errno = oerrno;
+        r = __getdents(fd, (struct mips_dirent *)dirp, count);
+        if (r > 0) {
+                char *p;
+                char type;
+                union dirents {
+                        struct mips_dirent m;
+                        struct dirent d;
+                } *u;
+
+                p = (char *)dirp;
+                do {
+                        u = (union dirents *)p;
+
+                        /* This should not happen, but just in case... */
+                        if (p + u->m.d_reclen > (char *)dirp + r)
+                                break;
+
+                        /* shuffle the dirent */
+                        type = *(p + u->m.d_reclen - 1);
+                        memmove(u->d.d_name, u->m.d_name,
+                                u->m.d_reclen - 2 - offsetof(struct mips_dirent, d_name) + 1);
+                        u->d.d_type = type;
+
+                        p += u->m.d_reclen;
+                } while (p < (char *)dirp + r);
+        }
+        return r;
+}
diff --git a/libc/arch-mips64/bionic/memcmp16.S b/libc/arch-mips64/bionic/memcmp16.S
new file mode 100644
index 0000000..b70c078
--- /dev/null
+++ b/libc/arch-mips64/bionic/memcmp16.S
@@ -0,0 +1,53 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+	.text
+
+#include <machine/asm.h>
+
+/*
+ * u4 __memcmp16(const u2* s0, const u2* s1, size_t count);
+ */
+LEAF(__memcmp16,0)
+	move	t0,$0
+	move	t1,$0
+	beqz	a2,.L_done		/* 0 length string */
+	beq	a0,a1,.L_done		/* strings are identical */
+
+	/* Unoptimised... */
+1:	lhu	t0,0(a0)
+	lhu	t1,0(a1)
+	PTR_ADDU a1,2
+	bne	t0,t1,.L_done
+	PTR_ADDU a0,2
+	SUBU	a2,1
+	bnez	a2,1b
+
+.L_done:
+	SUBU	v0,t0,t1
+	j	ra
+	END(__memcmp16)
diff --git a/libc/arch-mips64/bionic/setjmp.S b/libc/arch-mips64/bionic/setjmp.S
new file mode 100644
index 0000000..7c21195
--- /dev/null
+++ b/libc/arch-mips64/bionic/setjmp.S
@@ -0,0 +1,211 @@
+/*      $OpenBSD: setjmp.S,v 1.5 2005/08/07 16:40:15 espie Exp $ */
+
+/*
+ * Copyright (c) 2001-2002 Opsycon AB  (www.opsycon.se / www.opsycon.com)
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Opsycon AB nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ */
+
+#include <machine/asm.h>
+#include <machine/regnum.h>
+#include <machine/signal.h>
+
+/*
+ * setjmp, longjmp implementation for libc. this code depends
+ * on the layout of the struct sigcontext in machine/signal.h.
+ *
+ */
+
+FRAMESZ= MKFSIZ(2,6)
+A1OFF= FRAMESZ-4*REGSZ
+A0OFF= FRAMESZ-3*REGSZ
+GPOFF= FRAMESZ-2*REGSZ
+RAOFF= FRAMESZ-1*REGSZ
+
+#define FPREG64_S(FPR, OFF, BASE)       \
+        swc1    FPR, OFF(BASE)  ;       \
+        mfhc1   t0, FPR         ;       \
+        sw      t0, OFF+4(BASE) ;
+        
+#define FPREG64_L(FPR, OFF, BASE)       \
+        lw      t0, OFF+4(BASE) ;       \
+        lw      t1, OFF(BASE)   ;       \
+        mtc1    t1, FPR         ;       \
+        mthc1   t0, FPR         ;       \
+        
+NON_LEAF(setjmp, FRAMESZ, ra)
+	.mask	0x80000000, RAOFF
+	PTR_SUBU sp, FRAMESZ			# allocate stack frame
+	SETUP_GP64(GPOFF, setjmp)
+	SAVE_GP(GPOFF)
+	.set	reorder
+	REG_S	ra, RAOFF(sp)			# save state
+	REG_S	a0, A0OFF(sp)
+
+	move	a0, zero			# get current signal mask
+	jal	sigblock
+
+	REG_L	v1, A0OFF(sp)			# v1 = jmpbuf
+	REG_S	v0, SC_MASK(v1)			# save sc_mask = sigblock(0)
+
+	REG_L	a0, A0OFF(sp)			# restore jmpbuf
+	REG_L	ra, RAOFF(sp)
+	REG_S	ra, SC_PC(a0)			# sc_pc = return address
+#if defined(__mips64)
+	dli	v0, 0xACEDBADE			# sigcontext magic number
+#else
+	li	v0, 0xACEDBADE			# sigcontext magic number
+#endif
+	REG_S	v0, SC_REGS+ZERO*REGSZ(a0)
+	REG_S	s0, SC_REGS+S0*REGSZ(a0)
+	REG_S	s1, SC_REGS+S1*REGSZ(a0)
+	REG_S	s2, SC_REGS+S2*REGSZ(a0)
+	REG_S	s3, SC_REGS+S3*REGSZ(a0)
+	REG_S	s4, SC_REGS+S4*REGSZ(a0)
+	REG_S	s5, SC_REGS+S5*REGSZ(a0)
+	REG_S	s6, SC_REGS+S6*REGSZ(a0)
+	REG_S	s7, SC_REGS+S7*REGSZ(a0)
+	REG_S	s8, SC_REGS+S8*REGSZ(a0)
+	REG_L	v0, GPOFF(sp)
+	REG_S	v0, SC_REGS+GP*REGSZ(a0)
+	PTR_ADDU v0, sp, FRAMESZ
+	REG_S	v0, SC_REGS+SP*REGSZ(a0)
+
+#if !defined(SOFTFLOAT)
+	li	v0, 1				# be nice if we could tell
+	REG_S	v0, SC_FPUSED(a0)		# sc_fpused = 1
+	cfc1	v0, $31
+#if _MIPS_FPSET == 32
+        FPREG64_S($f20, SC_FPREGS+((F20-F0)*REGSZ_FP), a0)
+        FPREG64_S($f21, SC_FPREGS+((F21-F0)*REGSZ_FP), a0)
+        FPREG64_S($f22, SC_FPREGS+((F22-F0)*REGSZ_FP), a0)
+        FPREG64_S($f23, SC_FPREGS+((F23-F0)*REGSZ_FP), a0)
+        FPREG64_S($f24, SC_FPREGS+((F24-F0)*REGSZ_FP), a0)
+        FPREG64_S($f25, SC_FPREGS+((F25-F0)*REGSZ_FP), a0)
+        FPREG64_S($f26, SC_FPREGS+((F26-F0)*REGSZ_FP), a0)
+        FPREG64_S($f27, SC_FPREGS+((F27-F0)*REGSZ_FP), a0)
+        FPREG64_S($f28, SC_FPREGS+((F28-F0)*REGSZ_FP), a0)
+        FPREG64_S($f29, SC_FPREGS+((F29-F0)*REGSZ_FP), a0)
+        FPREG64_S($f30, SC_FPREGS+((F30-F0)*REGSZ_FP), a0)
+        FPREG64_S($f31, SC_FPREGS+((F31-F0)*REGSZ_FP), a0)
+#else
+        swc1    $f20, SC_FPREGS+((F20-F0)*REGSZ_FP)(a0)
+        swc1    $f21, SC_FPREGS+((F21-F0)*REGSZ_FP)(a0)
+        swc1    $f22, SC_FPREGS+((F22-F0)*REGSZ_FP)(a0)
+        swc1    $f23, SC_FPREGS+((F23-F0)*REGSZ_FP)(a0)
+        swc1    $f24, SC_FPREGS+((F24-F0)*REGSZ_FP)(a0)
+        swc1    $f25, SC_FPREGS+((F25-F0)*REGSZ_FP)(a0)
+        swc1    $f26, SC_FPREGS+((F26-F0)*REGSZ_FP)(a0)
+        swc1    $f27, SC_FPREGS+((F27-F0)*REGSZ_FP)(a0)
+        swc1    $f28, SC_FPREGS+((F28-F0)*REGSZ_FP)(a0)
+        swc1    $f29, SC_FPREGS+((F29-F0)*REGSZ_FP)(a0)
+        swc1    $f30, SC_FPREGS+((F30-F0)*REGSZ_FP)(a0)
+        swc1    $f31, SC_FPREGS+((F31-F0)*REGSZ_FP)(a0)
+#endif
+	REG_S	v0, SC_FPREGS+((FSR-F0)*REGSZ)(a0)
+#endif /* !SOFTFLOAT */
+	move	v0, zero
+	RESTORE_GP64
+	PTR_ADDU sp, FRAMESZ
+	j	ra
+
+botch:
+	jal	longjmperror
+	jal	abort
+	RESTORE_GP64
+	PTR_ADDU sp, FRAMESZ
+END(setjmp)
+
+
+LEAF(longjmp, FRAMESZ)
+	PTR_SUBU sp, FRAMESZ
+	SETUP_GP64(GPOFF, longjmp)
+	SAVE_GP(GPOFF)
+	.set	reorder
+	sw	a1, A1OFF(sp)
+	sw	a0, A0OFF(sp)
+
+	lw	a0, SC_MASK(a0)
+	jal	sigsetmask
+
+	lw	a0, A0OFF(sp)
+	lw	a1, A1OFF(sp)
+
+	.set	noreorder	
+	REG_L	v0, SC_REGS+ZERO*REGSZ(a0)
+	bne	v0, 0xACEDBADE, botch		# jump if error
+	REG_L	ra, SC_PC(a0)
+	REG_L	s0, SC_REGS+S0*REGSZ(a0)
+	REG_L	s1, SC_REGS+S1*REGSZ(a0)
+	REG_L	s2, SC_REGS+S2*REGSZ(a0)
+	REG_L	s3, SC_REGS+S3*REGSZ(a0)
+	REG_L	s4, SC_REGS+S4*REGSZ(a0)
+	REG_L	s5, SC_REGS+S5*REGSZ(a0)
+	REG_L	s6, SC_REGS+S6*REGSZ(a0)
+	REG_L	s7, SC_REGS+S7*REGSZ(a0)
+	REG_L	s8, SC_REGS+S8*REGSZ(a0)
+	REG_L	gp, SC_REGS+GP*REGSZ(a0)
+	REG_L	sp, SC_REGS+SP*REGSZ(a0)
+	
+#if !defined(SOFTFLOAT)
+	REG_L	v0, SC_FPREGS+((FSR-F0)*REGSZ)(a0)	
+	ctc1	v0, $31
+#if _MIPS_FPSET == 32
+        FPREG64_L($f20, SC_FPREGS+((F20-F0)*REGSZ_FP), a0)
+        FPREG64_L($f21, SC_FPREGS+((F21-F0)*REGSZ_FP), a0)
+        FPREG64_L($f22, SC_FPREGS+((F22-F0)*REGSZ_FP), a0)
+        FPREG64_L($f23, SC_FPREGS+((F23-F0)*REGSZ_FP), a0)
+        FPREG64_L($f24, SC_FPREGS+((F24-F0)*REGSZ_FP), a0)
+        FPREG64_L($f25, SC_FPREGS+((F25-F0)*REGSZ_FP), a0)
+        FPREG64_L($f26, SC_FPREGS+((F26-F0)*REGSZ_FP), a0)
+        FPREG64_L($f27, SC_FPREGS+((F27-F0)*REGSZ_FP), a0)
+        FPREG64_L($f28, SC_FPREGS+((F28-F0)*REGSZ_FP), a0)
+        FPREG64_L($f29, SC_FPREGS+((F29-F0)*REGSZ_FP), a0)
+        FPREG64_L($f30, SC_FPREGS+((F30-F0)*REGSZ_FP), a0)
+        FPREG64_L($f31, SC_FPREGS+((F31-F0)*REGSZ_FP), a0)
+#else
+        lwc1    $f20, SC_FPREGS+((F20-F0)*REGSZ_FP)(a0)
+        lwc1    $f21, SC_FPREGS+((F21-F0)*REGSZ_FP)(a0)
+        lwc1    $f22, SC_FPREGS+((F22-F0)*REGSZ_FP)(a0)
+        lwc1    $f23, SC_FPREGS+((F23-F0)*REGSZ_FP)(a0)
+        lwc1    $f24, SC_FPREGS+((F24-F0)*REGSZ_FP)(a0)
+        lwc1    $f25, SC_FPREGS+((F25-F0)*REGSZ_FP)(a0)
+        lwc1    $f26, SC_FPREGS+((F26-F0)*REGSZ_FP)(a0)
+        lwc1    $f27, SC_FPREGS+((F27-F0)*REGSZ_FP)(a0)
+        lwc1    $f28, SC_FPREGS+((F28-F0)*REGSZ_FP)(a0)
+        lwc1    $f29, SC_FPREGS+((F29-F0)*REGSZ_FP)(a0)
+        lwc1    $f30, SC_FPREGS+((F30-F0)*REGSZ_FP)(a0)
+        lwc1    $f31, SC_FPREGS+((F31-F0)*REGSZ_FP)(a0)
+#endif
+#endif /* !SOFTFLOAT */
+	bne	a1, zero, 1f
+	 nop
+	li	a1, 1			# never return 0!
+1:
+	j	ra
+	 move	v0, a1
+
+END(longjmp)
diff --git a/libc/arch-mips64/bionic/sigsetjmp.S b/libc/arch-mips64/bionic/sigsetjmp.S
new file mode 100644
index 0000000..b05454c
--- /dev/null
+++ b/libc/arch-mips64/bionic/sigsetjmp.S
@@ -0,0 +1,77 @@
+/* $OpenBSD: sigsetjmp.S,v 1.5 2005/08/07 16:40:15 espie Exp $ */
+/*-
+ * Copyright (c) 1991, 1993, 1995,
+ *	The Regents of the University of California.  All rights reserved.
+ *
+ * This code is derived from software contributed to Berkeley by
+ * Havard Eidnes.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the University nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <machine/asm.h>
+#include <machine/regnum.h>
+#include <machine/setjmp.h>
+
+/*
+ * trampolines for sigsetjmp and  siglongjmp save and restore mask.
+ *
+ */
+FRAMESZ= MKFSIZ(1,1)
+GPOFF= FRAMESZ-2*REGSZ
+
+LEAF(sigsetjmp, FRAMESZ)
+	PTR_SUBU sp, FRAMESZ
+	SETUP_GP64(GPOFF, sigsetjmp)
+	.set	reorder
+	REG_S	a1, (_JBLEN*REGSZ)(a0)		# save "savemask"
+	bne	a1, 0x0, 1f			# do saving of signal mask?
+	LA	t9, _setjmp
+	RESTORE_GP64
+	PTR_ADDU sp, FRAMESZ
+	jr t9
+
+1:	LA	t9, setjmp
+	RESTORE_GP64
+	PTR_ADDU sp, FRAMESZ
+	jr t9
+END(sigsetjmp)
+
+LEAF(siglongjmp, FRAMESZ)
+	PTR_SUBU sp, FRAMESZ
+	SETUP_GP64(GPOFF, siglongjmp)
+	.set	reorder
+	REG_L	t0, (_JBLEN*REGSZ)(a0)		# get "savemask"
+	bne	t0, 0x0, 1f			# restore signal mask?
+	LA	t9, _longjmp
+	RESTORE_GP64
+	PTR_ADDU sp, FRAMESZ
+	jr	t9
+1:
+	LA	t9, longjmp
+	RESTORE_GP64
+	PTR_ADDU sp, FRAMESZ
+	jr	t9
+END(siglongjmp)
diff --git a/libc/arch-mips64/bionic/syscall.S b/libc/arch-mips64/bionic/syscall.S
new file mode 100644
index 0000000..08aa705
--- /dev/null
+++ b/libc/arch-mips64/bionic/syscall.S
@@ -0,0 +1,69 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <machine/asm.h>
+#include <asm/unistd.h>
+
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+FRAMESZ		=	MKFSIZ(6,0)
+#else
+FRAMESZ		=	MKFSIZ(0,1)
+FRAME_GP	=	FRAMESZ-1*REGSZ
+#endif
+
+LEAF(syscall,FRAMESZ)
+	PTR_SUBU sp, FRAMESZ	# allocate stack frame
+	SETUP_GP64(FRAME_GP,syscall)
+	SAVE_GP(FRAME_GP)
+	move	v0, a0		# syscall number to v0
+	move	a0, a1		# shift args down
+	move	a1, a2
+	move	a2, a3
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+	REG_L	a3, FRAMESZ+4*REGSZ(sp)
+	REG_L	t0, FRAMESZ+5*REGSZ(sp)
+	REG_L	t1, FRAMESZ+6*REGSZ(sp)
+	REG_S	t0, 4*REGSZ(sp)
+	REG_S	t1, 5*REGSZ(sp)
+#else
+	move	a3, a4
+	move	a4, a5
+	REG_L	a5, FRAMESZ(sp)
+#endif
+	syscall
+	move	a0, v0
+	bnez	a3, 1f
+	RESTORE_GP64
+	PTR_ADDU sp, FRAMESZ
+	j	ra
+1:
+	LA	t9,__set_errno
+	RESTORE_GP64
+	PTR_ADDU sp, FRAMESZ
+	j	t9
+	END(syscall)
diff --git a/libc/arch-mips64/bionic/vfork.S b/libc/arch-mips64/bionic/vfork.S
new file mode 100644
index 0000000..c936945
--- /dev/null
+++ b/libc/arch-mips64/bionic/vfork.S
@@ -0,0 +1,72 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <machine/asm.h>
+#include <asm/unistd.h>
+#include <linux/sched.h>
+
+// TODO: mips' uapi signal.h is missing #ifndef __ASSEMBLY__.
+// #include <asm/signal.h>
+#define SIGCHLD 18
+
+	.text
+
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+FRAMESZ		=	MKFSIZ(5,0)
+#else
+FRAMESZ		=	MKFSIZ(0,0)
+#endif
+
+LEAF(vfork,FRAMESZ)
+#if FRAMESZ!=0
+	PTR_SUBU sp, FRAMESZ
+#endif
+	SETUP_GP64(a5,vfork)
+	LI	a0, (CLONE_VM | CLONE_VFORK | SIGCHLD)
+	move	a1, $0
+	move	a2, $0
+	move	a3, $0
+#if (_MIPS_SIM == _ABIO32) || (_MIPS_SIM == _ABI32)
+	REG_S	$0, 4*REGSZ(sp)
+#else
+	move	a4, $0
+#endif
+	LI	v0, __NR_clone
+	syscall
+#if FRAMESZ!=0
+	PTR_ADDU sp,FRAMESZ
+#endif
+	move	a0, v0
+	bnez	a3, 1f
+	RESTORE_GP64
+	j	ra
+1:
+	LA	t9,__set_errno
+	RESTORE_GP64
+	j	t9
+	END(vfork)