am 2081fda6: Merge "Only look up A records if the system has IPv4." into gingerbread
* commit '2081fda69a68505c914324797400b1b798516904':
Only look up A records if the system has IPv4.
diff --git a/libc/Android.mk b/libc/Android.mk
index 9e6bdfb..d940753 100644
--- a/libc/Android.mk
+++ b/libc/Android.mk
@@ -187,7 +187,6 @@
string/strcat.c \
string/strchr.c \
string/strcoll.c \
- string/strcpy.c \
string/strcspn.c \
string/strdup.c \
string/strerror.c \
@@ -230,6 +229,7 @@
wchar/wcsstr.c \
wchar/wcstok.c \
wchar/wcswidth.c \
+ wchar/wcsxfrm.c \
wchar/wmemchr.c \
wchar/wmemcmp.c \
wchar/wmemcpy.c \
@@ -241,13 +241,14 @@
inet/inet_ntoa.c \
inet/inet_ntop.c \
inet/inet_pton.c \
+ inet/ether_aton.c \
+ inet/ether_ntoa.c \
tzcode/asctime.c \
tzcode/difftime.c \
tzcode/localtime.c \
tzcode/strftime.c \
tzcode/strptime.c \
bionic/__set_errno.c \
- bionic/_rand48.c \
bionic/cpuacct.c \
bionic/arc4random.c \
bionic/basename.c \
@@ -270,6 +271,10 @@
bionic/md5.c \
bionic/pututline.c \
bionic/realpath.c \
+ bionic/sched_getaffinity.c \
+ bionic/sched_getcpu.c \
+ bionic/sched_cpualloc.c \
+ bionic/sched_cpucount.c \
bionic/semaphore.c \
bionic/sha1.c \
bionic/ssp.c \
@@ -354,6 +359,7 @@
arch-arm/bionic/setjmp.S \
arch-arm/bionic/sigsetjmp.S \
arch-arm/bionic/strlen.c.arm \
+ arch-arm/bionic/strcpy.S \
arch-arm/bionic/syscall.S \
string/memmove.c.arm \
string/bcopy.c \
@@ -365,6 +371,7 @@
# can set breakpoints in them without messing
# up any thumb code.
libc_common_src_files += \
+ bionic/pthread-atfork.c.arm \
bionic/pthread-rwlocks.c.arm \
bionic/pthread-timers.c.arm \
bionic/ptrace.c.arm
@@ -391,6 +398,7 @@
arch-x86/bionic/_exit_with_stack_teardown.S \
arch-x86/bionic/setjmp.S \
arch-x86/bionic/_setjmp.S \
+ arch-x86/bionic/sigsetjmp.S \
arch-x86/bionic/vfork.S \
arch-x86/bionic/syscall.S \
arch-x86/string/bcopy_wrapper.S \
@@ -401,7 +409,9 @@
arch-x86/string/memset_wrapper.S \
arch-x86/string/strcmp_wrapper.S \
arch-x86/string/strncmp_wrapper.S \
- arch-x86/string/strlen.S \
+ arch-x86/string/strlen_wrapper.S \
+ string/strcpy.c \
+ bionic/pthread-atfork.c \
bionic/pthread-rwlocks.c \
bionic/pthread-timers.c \
bionic/ptrace.c
@@ -441,6 +451,8 @@
string/strncmp.c \
string/memcmp.c \
string/strlen.c \
+ string/strcpy.c \
+ bionic/pthread-atfork.c \
bionic/pthread-rwlocks.c \
bionic/pthread-timers.c \
bionic/ptrace.c \
@@ -495,13 +507,7 @@
libc_common_cflags += -DHAVE_ARM_TLS_REGISTER
endif
else # !arm
- ifeq ($(TARGET_ARCH),x86)
- libc_crt_target_cflags := -m32
-
- # Enable recent IA friendly memory routines (such as for Atom)
- # These will not work on the earlier x86 machines
- libc_common_cflags += -mtune=i686 -DUSE_SSSE3 -DUSE_SSE2
- endif # x86
+ libc_crt_target_cflags :=
endif # !arm
# Define ANDROID_SMP appropriately.
@@ -523,6 +529,10 @@
$(LOCAL_PATH)/string \
$(LOCAL_PATH)/stdio
+# Needed to access private/__dso_handle.S from
+# crtbegin_xxx.S and crtend_xxx.S
+#
+libc_crt_target_cflags += -I$(LOCAL_PATH)/private
# Define the libc run-time (crt) support object files that must be built,
# which are needed to build all other objects (shared/static libs and
@@ -703,6 +713,7 @@
LOCAL_SHARED_LIBRARIES := libc
LOCAL_WHOLE_STATIC_LIBRARIES := libc_common
LOCAL_SYSTEM_SHARED_LIBRARIES :=
+LOCAL_ALLOW_UNDEFINED_SYMBOLS := true
# Don't prelink
LOCAL_PRELINK_MODULE := false
# Don't install on release build
diff --git a/libc/NOTICE b/libc/NOTICE
index e8076b5..d9e6818 100644
--- a/libc/NOTICE
+++ b/libc/NOTICE
@@ -1,5 +1,5 @@
-Copyright (c) 2005-2008, The Android Open Source Project
+Copyright (c) 2005-2010, The Android Open Source Project
All rights reserved.
Redistribution and use in source and binary forms, with or without
diff --git a/libc/SYSCALLS.TXT b/libc/SYSCALLS.TXT
index 0850b82..5653c3c 100644
--- a/libc/SYSCALLS.TXT
+++ b/libc/SYSCALLS.TXT
@@ -85,8 +85,8 @@
# file descriptors
ssize_t read (int, void*, size_t) 3
ssize_t write (int, const void*, size_t) 4
-ssize_t __pread64:pread64 (int, void *, size_t, off_t, off_t) 180
-ssize_t __pwrite64:pwrite64 (int, void *, size_t, off_t, off_t) 181
+ssize_t pread64 (int, void *, size_t, off64_t) 180
+ssize_t pwrite64 (int, void *, size_t, off64_t) 181
int __open:open (const char*, int, mode_t) 5
int __openat:openat (int, const char*, int, mode_t) 322,295
int close (int) 6
@@ -116,6 +116,7 @@
int dup2(int, int) 63
int select:_newselect(int, struct fd_set *, struct fd_set *, struct fd_set *, struct timeval *) 142
int ftruncate(int, off_t) 93
+int ftruncate64(int, off64_t) 194
int getdents:getdents64(unsigned int, struct dirent *, unsigned int) 217,220
int fsync(int) 118
int fdatasync(int) 148
@@ -229,6 +230,9 @@
int sched_get_priority_max(int policy) 159
int sched_get_priority_min(int policy) 160
int sched_rr_get_interval(pid_t pid, struct timespec *interval) 161
+int sched_setaffinity(pid_t pid, size_t setsize, const cpu_set_t* set) 241
+int __sched_getaffinity:sched_getaffinity(pid_t pid, size_t setsize, cpu_set_t* set) 242
+int __getcpu:getcpu(unsigned *cpu, unsigned *node, void *unused) 345,318,318
# io priorities
int ioprio_set(int which, int who, int ioprio) 314,289,288
diff --git a/libc/arch-arm/bionic/strcpy.S b/libc/arch-arm/bionic/strcpy.S
new file mode 100644
index 0000000..70c353f
--- /dev/null
+++ b/libc/arch-arm/bionic/strcpy.S
@@ -0,0 +1,138 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ * Copyright (c) 2008 ARM Ltd
+ * All rights reserved.
+ *
+ * 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. The name of the company may not be used to endorse or promote
+ * products derived from this software without specific prior written
+ * permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY ARM LTD ``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 ARM LTD 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.
+ *
+ * Android adaptation and tweak by Jim Huang <jserv@0xlab.org>.
+ */
+
+#include <machine/cpu-features.h>
+
+ .text
+
+ .global strcpy
+ .type strcpy, %function
+ .align 4
+
+strcpy:
+ .fnstart
+ PLD(r1, #0)
+ eor r2, r0, r1
+ mov ip, r0
+ tst r2, #3
+ bne 4f
+ tst r1, #3
+ bne 3f
+5:
+ str r5, [sp, #-4]!
+ mov r5, #0x01
+ orr r5, r5, r5, lsl #8
+ orr r5, r5, r5, lsl #16
+
+ str r4, [sp, #-4]!
+ tst r1, #4
+ ldr r3, [r1], #4
+ beq 2f
+ sub r2, r3, r5
+ bics r2, r2, r3
+ tst r2, r5, lsl #7
+ itt eq
+ streq r3, [ip], #4
+ ldreq r3, [r1], #4
+ bne 1f
+ /* Inner loop. We now know that r1 is 64-bit aligned, so we
+ can safely fetch up to two words. This allows us to avoid
+ load stalls. */
+ .p2align 2
+2:
+ PLD(r1, #8)
+ ldr r4, [r1], #4
+ sub r2, r3, r5
+ bics r2, r2, r3
+ tst r2, r5, lsl #7
+ sub r2, r4, r5
+ bne 1f
+ str r3, [ip], #4
+ bics r2, r2, r4
+ tst r2, r5, lsl #7
+ itt eq
+ ldreq r3, [r1], #4
+ streq r4, [ip], #4
+ beq 2b
+ mov r3, r4
+1:
+#ifdef __ARMEB__
+ rors r3, r3, #24
+#endif
+ strb r3, [ip], #1
+ tst r3, #0xff
+#ifdef __ARMEL__
+ ror r3, r3, #8
+#endif
+ bne 1b
+ ldr r4, [sp], #4
+ ldr r5, [sp], #4
+ bx lr
+
+ /* Strings have the same offset from word alignment, but it's
+ not zero. */
+3:
+ tst r1, #1
+ beq 1f
+ ldrb r2, [r1], #1
+ strb r2, [ip], #1
+ cmp r2, #0
+ it eq
+ bxeq lr
+1:
+ tst r1, #2
+ beq 5b
+ ldrh r2, [r1], #2
+#ifdef __ARMEB__
+ tst r2, #0xff00
+ iteet ne
+ strneh r2, [ip], #2
+ lsreq r2, r2, #8
+ streqb r2, [ip]
+ tstne r2, #0xff
+#else
+ tst r2, #0xff
+ itet ne
+ strneh r2, [ip], #2
+ streqb r2, [ip]
+ tstne r2, #0xff00
+#endif
+ bne 5b
+ bx lr
+
+ /* src and dst do not have a common word-alignement. Fall back to
+ byte copying. */
+4:
+ ldrb r2, [r1], #1
+ strb r2, [ip], #1
+ cmp r2, #0
+ bne 4b
+ bx lr
diff --git a/libc/arch-arm/include/endian.h b/libc/arch-arm/include/endian.h
index 04204ed..6de0889 100644
--- a/libc/arch-arm/include/endian.h
+++ b/libc/arch-arm/include/endian.h
@@ -1,10 +1,89 @@
/* $OpenBSD: endian.h,v 1.3 2005/12/13 00:35:23 millert Exp $ */
+/*
+ * Copyright (C) 2010 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.
+ */
+
+#ifndef _ARM_ENDIAN_H_
+#define _ARM_ENDIAN_H_
+
+#ifdef __GNUC__
+
+/*
+ * REV and REV16 weren't available on ARM5 or ARM4.
+ * We don't include <machine/cpu-features.h> because it pollutes the
+ * namespace with macros like PLD.
+ */
+#if !defined __ARM_ARCH_5__ && !defined __ARM_ARCH_5T__ && \
+ !defined __ARM_ARCH_5TE__ && !defined __ARM_ARCH_5TEJ__ && \
+ !defined __ARM_ARCH_4T__ && !defined __ARM_ARCH_4__
+
+/* According to RealView Assembler User's Guide, REV and REV16 are available
+ * in Thumb code and 16-bit instructions when used in Thumb-2 code.
+ *
+ * REV Rd, Rm
+ * Rd and Rm must both be Lo registers.
+ *
+ * REV16 Rd, Rm
+ * Rd and Rm must both be Lo registers.
+ *
+ * The +l constraint takes care of this without constraining us in ARM mode.
+ */
+#define __swap16md(x) ({ \
+ register u_int16_t _x = (x); \
+ __asm volatile ("rev16 %0, %0" : "+l" (_x)); \
+ _x; \
+})
+
+#define __swap32md(x) ({ \
+ register u_int32_t _x = (x); \
+ __asm volatile ("rev %0, %0" : "+l" (_x)); \
+ _x; \
+})
+
+#define __swap64md(x) ({ \
+ u_int64_t _swap64md_x = (x); \
+ (u_int64_t) __swap32md(_swap64md_x >> 32) | \
+ (u_int64_t) __swap32md(_swap64md_x & 0xffffffff) << 32; \
+})
+
+/* Tell sys/endian.h we have MD variants of the swap macros. */
+#define MD_SWAP
+
+#endif /* __ARM_ARCH__ */
+#endif /* __GNUC__ */
+
#ifdef __ARMEB__
#define _BYTE_ORDER _BIG_ENDIAN
#else
#define _BYTE_ORDER _LITTLE_ENDIAN
#endif
-#define __STRICT_ALIGNMENT
+#define __STRICT_ALIGNMENT
#include <sys/types.h>
#include <sys/endian.h>
+
+#endif /* !_ARM_ENDIAN_H_ */
diff --git a/libc/arch-arm/include/machine/cpu-features.h b/libc/arch-arm/include/machine/cpu-features.h
index 39c1db3..80d3fda 100644
--- a/libc/arch-arm/include/machine/cpu-features.h
+++ b/libc/arch-arm/include/machine/cpu-features.h
@@ -185,6 +185,7 @@
#endif
/* Assembly-only macros */
+#ifdef __ASSEMBLY__
/* define a handy PLD(address) macro since the cache preload
* is an optional opcode
@@ -195,4 +196,6 @@
# define PLD(reg,offset) /* nothing */
#endif
+#endif /* ! __ASSEMBLY__ */
+
#endif /* _ARM_MACHINE_CPU_FEATURES_H */
diff --git a/libc/arch-arm/syscalls.mk b/libc/arch-arm/syscalls.mk
index ba78c18..5210d6c 100644
--- a/libc/arch-arm/syscalls.mk
+++ b/libc/arch-arm/syscalls.mk
@@ -41,8 +41,8 @@
syscall_src += arch-arm/syscalls/acct.S
syscall_src += arch-arm/syscalls/read.S
syscall_src += arch-arm/syscalls/write.S
-syscall_src += arch-arm/syscalls/__pread64.S
-syscall_src += arch-arm/syscalls/__pwrite64.S
+syscall_src += arch-arm/syscalls/pread64.S
+syscall_src += arch-arm/syscalls/pwrite64.S
syscall_src += arch-arm/syscalls/__open.S
syscall_src += arch-arm/syscalls/__openat.S
syscall_src += arch-arm/syscalls/close.S
@@ -70,6 +70,7 @@
syscall_src += arch-arm/syscalls/dup2.S
syscall_src += arch-arm/syscalls/select.S
syscall_src += arch-arm/syscalls/ftruncate.S
+syscall_src += arch-arm/syscalls/ftruncate64.S
syscall_src += arch-arm/syscalls/getdents.S
syscall_src += arch-arm/syscalls/fsync.S
syscall_src += arch-arm/syscalls/fdatasync.S
@@ -153,6 +154,9 @@
syscall_src += arch-arm/syscalls/sched_get_priority_max.S
syscall_src += arch-arm/syscalls/sched_get_priority_min.S
syscall_src += arch-arm/syscalls/sched_rr_get_interval.S
+syscall_src += arch-arm/syscalls/sched_setaffinity.S
+syscall_src += arch-arm/syscalls/__sched_getaffinity.S
+syscall_src += arch-arm/syscalls/__getcpu.S
syscall_src += arch-arm/syscalls/ioprio_set.S
syscall_src += arch-arm/syscalls/ioprio_get.S
syscall_src += arch-arm/syscalls/uname.S
diff --git a/libc/arch-arm/syscalls/__getcpu.S b/libc/arch-arm/syscalls/__getcpu.S
new file mode 100644
index 0000000..ed6927a
--- /dev/null
+++ b/libc/arch-arm/syscalls/__getcpu.S
@@ -0,0 +1,19 @@
+/* autogenerated by gensyscalls.py */
+#include <sys/linux-syscalls.h>
+
+ .text
+ .type __getcpu, #function
+ .globl __getcpu
+ .align 4
+ .fnstart
+
+__getcpu:
+ .save {r4, r7}
+ stmfd sp!, {r4, r7}
+ ldr r7, =__NR_getcpu
+ swi #0
+ ldmfd sp!, {r4, r7}
+ movs r0, r0
+ bxpl lr
+ b __set_syscall_errno
+ .fnend
diff --git a/libc/arch-arm/syscalls/__sched_getaffinity.S b/libc/arch-arm/syscalls/__sched_getaffinity.S
new file mode 100644
index 0000000..71f2b1d
--- /dev/null
+++ b/libc/arch-arm/syscalls/__sched_getaffinity.S
@@ -0,0 +1,19 @@
+/* autogenerated by gensyscalls.py */
+#include <sys/linux-syscalls.h>
+
+ .text
+ .type __sched_getaffinity, #function
+ .globl __sched_getaffinity
+ .align 4
+ .fnstart
+
+__sched_getaffinity:
+ .save {r4, r7}
+ stmfd sp!, {r4, r7}
+ ldr r7, =__NR_sched_getaffinity
+ swi #0
+ ldmfd sp!, {r4, r7}
+ movs r0, r0
+ bxpl lr
+ b __set_syscall_errno
+ .fnend
diff --git a/libc/arch-arm/syscalls/ftruncate64.S b/libc/arch-arm/syscalls/ftruncate64.S
new file mode 100644
index 0000000..37b4744
--- /dev/null
+++ b/libc/arch-arm/syscalls/ftruncate64.S
@@ -0,0 +1,19 @@
+/* autogenerated by gensyscalls.py */
+#include <sys/linux-syscalls.h>
+
+ .text
+ .type ftruncate64, #function
+ .globl ftruncate64
+ .align 4
+ .fnstart
+
+ftruncate64:
+ .save {r4, r7}
+ stmfd sp!, {r4, r7}
+ ldr r7, =__NR_ftruncate64
+ swi #0
+ ldmfd sp!, {r4, r7}
+ movs r0, r0
+ bxpl lr
+ b __set_syscall_errno
+ .fnend
diff --git a/libc/arch-arm/syscalls/__pread64.S b/libc/arch-arm/syscalls/pread64.S
similarity index 85%
rename from libc/arch-arm/syscalls/__pread64.S
rename to libc/arch-arm/syscalls/pread64.S
index ea645e1..a54084c 100644
--- a/libc/arch-arm/syscalls/__pread64.S
+++ b/libc/arch-arm/syscalls/pread64.S
@@ -2,12 +2,12 @@
#include <sys/linux-syscalls.h>
.text
- .type __pread64, #function
- .globl __pread64
+ .type pread64, #function
+ .globl pread64
.align 4
.fnstart
-__pread64:
+pread64:
mov ip, sp
.save {r4, r5, r6, r7}
stmfd sp!, {r4, r5, r6, r7}
diff --git a/libc/arch-arm/syscalls/__pwrite64.S b/libc/arch-arm/syscalls/pwrite64.S
similarity index 85%
rename from libc/arch-arm/syscalls/__pwrite64.S
rename to libc/arch-arm/syscalls/pwrite64.S
index d1263be..f9d56b2 100644
--- a/libc/arch-arm/syscalls/__pwrite64.S
+++ b/libc/arch-arm/syscalls/pwrite64.S
@@ -2,12 +2,12 @@
#include <sys/linux-syscalls.h>
.text
- .type __pwrite64, #function
- .globl __pwrite64
+ .type pwrite64, #function
+ .globl pwrite64
.align 4
.fnstart
-__pwrite64:
+pwrite64:
mov ip, sp
.save {r4, r5, r6, r7}
stmfd sp!, {r4, r5, r6, r7}
diff --git a/libc/arch-arm/syscalls/sched_setaffinity.S b/libc/arch-arm/syscalls/sched_setaffinity.S
new file mode 100644
index 0000000..aedf8f3
--- /dev/null
+++ b/libc/arch-arm/syscalls/sched_setaffinity.S
@@ -0,0 +1,19 @@
+/* autogenerated by gensyscalls.py */
+#include <sys/linux-syscalls.h>
+
+ .text
+ .type sched_setaffinity, #function
+ .globl sched_setaffinity
+ .align 4
+ .fnstart
+
+sched_setaffinity:
+ .save {r4, r7}
+ stmfd sp!, {r4, r7}
+ ldr r7, =__NR_sched_setaffinity
+ swi #0
+ ldmfd sp!, {r4, r7}
+ movs r0, r0
+ bxpl lr
+ b __set_syscall_errno
+ .fnend
diff --git a/libc/arch-sh/syscalls.mk b/libc/arch-sh/syscalls.mk
index a87419d..9575905 100644
--- a/libc/arch-sh/syscalls.mk
+++ b/libc/arch-sh/syscalls.mk
@@ -45,8 +45,8 @@
syscall_src += arch-sh/syscalls/acct.S
syscall_src += arch-sh/syscalls/read.S
syscall_src += arch-sh/syscalls/write.S
-syscall_src += arch-sh/syscalls/__pread64.S
-syscall_src += arch-sh/syscalls/__pwrite64.S
+syscall_src += arch-sh/syscalls/pread64.S
+syscall_src += arch-sh/syscalls/pwrite64.S
syscall_src += arch-sh/syscalls/__open.S
syscall_src += arch-sh/syscalls/__openat.S
syscall_src += arch-sh/syscalls/close.S
@@ -73,6 +73,7 @@
syscall_src += arch-sh/syscalls/dup2.S
syscall_src += arch-sh/syscalls/select.S
syscall_src += arch-sh/syscalls/ftruncate.S
+syscall_src += arch-sh/syscalls/ftruncate64.S
syscall_src += arch-sh/syscalls/getdents.S
syscall_src += arch-sh/syscalls/fsync.S
syscall_src += arch-sh/syscalls/fdatasync.S
@@ -142,6 +143,9 @@
syscall_src += arch-sh/syscalls/sched_get_priority_max.S
syscall_src += arch-sh/syscalls/sched_get_priority_min.S
syscall_src += arch-sh/syscalls/sched_rr_get_interval.S
+syscall_src += arch-sh/syscalls/sched_setaffinity.S
+syscall_src += arch-sh/syscalls/__sched_getaffinity.S
+syscall_src += arch-sh/syscalls/__getcpu.S
syscall_src += arch-sh/syscalls/ioprio_set.S
syscall_src += arch-sh/syscalls/ioprio_get.S
syscall_src += arch-sh/syscalls/uname.S
diff --git a/libc/arch-sh/syscalls/__pwrite64.S b/libc/arch-sh/syscalls/__getcpu.S
similarity index 63%
copy from libc/arch-sh/syscalls/__pwrite64.S
copy to libc/arch-sh/syscalls/__getcpu.S
index a722242..125387b 100644
--- a/libc/arch-sh/syscalls/__pwrite64.S
+++ b/libc/arch-sh/syscalls/__getcpu.S
@@ -2,22 +2,19 @@
#include <sys/linux-syscalls.h>
.text
- .type __pwrite64, @function
- .globl __pwrite64
+ .type __getcpu, @function
+ .globl __getcpu
.align 4
-__pwrite64:
-
- /* get ready for additonal arg */
- mov.l @r15, r0
+__getcpu:
/* invoke trap */
mov.l 0f, r3 /* trap num */
- trapa #(5 + 0x10)
+ trapa #(3 + 0x10)
/* check return value */
cmp/pz r0
- bt __NR_pwrite64_end
+ bt __NR_getcpu_end
/* keep error number */
sts.l pr, @-r15
@@ -26,10 +23,10 @@
mov r0, r4
lds.l @r15+, pr
-__NR_pwrite64_end:
+__NR_getcpu_end:
rts
nop
.align 2
-0: .long __NR_pwrite64
+0: .long __NR_getcpu
1: .long __set_syscall_errno
diff --git a/libc/arch-sh/syscalls/__pwrite64.S b/libc/arch-sh/syscalls/__sched_getaffinity.S
similarity index 63%
copy from libc/arch-sh/syscalls/__pwrite64.S
copy to libc/arch-sh/syscalls/__sched_getaffinity.S
index a722242..7e8be6a 100644
--- a/libc/arch-sh/syscalls/__pwrite64.S
+++ b/libc/arch-sh/syscalls/__sched_getaffinity.S
@@ -2,22 +2,19 @@
#include <sys/linux-syscalls.h>
.text
- .type __pwrite64, @function
- .globl __pwrite64
+ .type __sched_getaffinity, @function
+ .globl __sched_getaffinity
.align 4
-__pwrite64:
-
- /* get ready for additonal arg */
- mov.l @r15, r0
+__sched_getaffinity:
/* invoke trap */
mov.l 0f, r3 /* trap num */
- trapa #(5 + 0x10)
+ trapa #(3 + 0x10)
/* check return value */
cmp/pz r0
- bt __NR_pwrite64_end
+ bt __NR_sched_getaffinity_end
/* keep error number */
sts.l pr, @-r15
@@ -26,10 +23,10 @@
mov r0, r4
lds.l @r15+, pr
-__NR_pwrite64_end:
+__NR_sched_getaffinity_end:
rts
nop
.align 2
-0: .long __NR_pwrite64
+0: .long __NR_sched_getaffinity
1: .long __set_syscall_errno
diff --git a/libc/arch-sh/syscalls/__pwrite64.S b/libc/arch-sh/syscalls/ftruncate64.S
similarity index 63%
copy from libc/arch-sh/syscalls/__pwrite64.S
copy to libc/arch-sh/syscalls/ftruncate64.S
index a722242..f4c7c1e 100644
--- a/libc/arch-sh/syscalls/__pwrite64.S
+++ b/libc/arch-sh/syscalls/ftruncate64.S
@@ -2,22 +2,19 @@
#include <sys/linux-syscalls.h>
.text
- .type __pwrite64, @function
- .globl __pwrite64
+ .type ftruncate64, @function
+ .globl ftruncate64
.align 4
-__pwrite64:
-
- /* get ready for additonal arg */
- mov.l @r15, r0
+ftruncate64:
/* invoke trap */
mov.l 0f, r3 /* trap num */
- trapa #(5 + 0x10)
+ trapa #(3 + 0x10)
/* check return value */
cmp/pz r0
- bt __NR_pwrite64_end
+ bt __NR_ftruncate64_end
/* keep error number */
sts.l pr, @-r15
@@ -26,10 +23,10 @@
mov r0, r4
lds.l @r15+, pr
-__NR_pwrite64_end:
+__NR_ftruncate64_end:
rts
nop
.align 2
-0: .long __NR_pwrite64
+0: .long __NR_ftruncate64
1: .long __set_syscall_errno
diff --git a/libc/arch-sh/syscalls/__pread64.S b/libc/arch-sh/syscalls/pread64.S
similarity index 89%
rename from libc/arch-sh/syscalls/__pread64.S
rename to libc/arch-sh/syscalls/pread64.S
index 474add3..702a402 100644
--- a/libc/arch-sh/syscalls/__pread64.S
+++ b/libc/arch-sh/syscalls/pread64.S
@@ -2,11 +2,11 @@
#include <sys/linux-syscalls.h>
.text
- .type __pread64, @function
- .globl __pread64
+ .type pread64, @function
+ .globl pread64
.align 4
-__pread64:
+pread64:
/* get ready for additonal arg */
mov.l @r15, r0
diff --git a/libc/arch-sh/syscalls/__pwrite64.S b/libc/arch-sh/syscalls/pwrite64.S
similarity index 89%
rename from libc/arch-sh/syscalls/__pwrite64.S
rename to libc/arch-sh/syscalls/pwrite64.S
index a722242..3f6c192 100644
--- a/libc/arch-sh/syscalls/__pwrite64.S
+++ b/libc/arch-sh/syscalls/pwrite64.S
@@ -2,11 +2,11 @@
#include <sys/linux-syscalls.h>
.text
- .type __pwrite64, @function
- .globl __pwrite64
+ .type pwrite64, @function
+ .globl pwrite64
.align 4
-__pwrite64:
+pwrite64:
/* get ready for additonal arg */
mov.l @r15, r0
diff --git a/libc/arch-sh/syscalls/__pwrite64.S b/libc/arch-sh/syscalls/sched_setaffinity.S
similarity index 63%
copy from libc/arch-sh/syscalls/__pwrite64.S
copy to libc/arch-sh/syscalls/sched_setaffinity.S
index a722242..9dda3b4 100644
--- a/libc/arch-sh/syscalls/__pwrite64.S
+++ b/libc/arch-sh/syscalls/sched_setaffinity.S
@@ -2,22 +2,19 @@
#include <sys/linux-syscalls.h>
.text
- .type __pwrite64, @function
- .globl __pwrite64
+ .type sched_setaffinity, @function
+ .globl sched_setaffinity
.align 4
-__pwrite64:
-
- /* get ready for additonal arg */
- mov.l @r15, r0
+sched_setaffinity:
/* invoke trap */
mov.l 0f, r3 /* trap num */
- trapa #(5 + 0x10)
+ trapa #(3 + 0x10)
/* check return value */
cmp/pz r0
- bt __NR_pwrite64_end
+ bt __NR_sched_setaffinity_end
/* keep error number */
sts.l pr, @-r15
@@ -26,10 +23,10 @@
mov r0, r4
lds.l @r15+, pr
-__NR_pwrite64_end:
+__NR_sched_setaffinity_end:
rts
nop
.align 2
-0: .long __NR_pwrite64
+0: .long __NR_sched_setaffinity
1: .long __set_syscall_errno
diff --git a/libc/arch-x86/bionic/clone.S b/libc/arch-x86/bionic/clone.S
index 3b50cc3..44fce1e 100644
--- a/libc/arch-x86/bionic/clone.S
+++ b/libc/arch-x86/bionic/clone.S
@@ -52,4 +52,4 @@
/* XXX: TODO: Add __bionic_clone here
* See bionic/bionic_clone.c and arch-arm/bionic/clone.S
* for more details...
- */
\ No newline at end of file
+ */
diff --git a/libc/arch-x86/bionic/sigsetjmp.S b/libc/arch-x86/bionic/sigsetjmp.S
new file mode 100644
index 0000000..c990a05
--- /dev/null
+++ b/libc/arch-x86/bionic/sigsetjmp.S
@@ -0,0 +1,92 @@
+/* $OpenBSD: sigsetjmp.S,v 1.7 2005/08/07 11:30:38 espie Exp $ */
+/*-
+ * Copyright (c) 1990 The Regents of the University of California.
+ * All rights reserved.
+ *
+ * This code is derived from software contributed to Berkeley by
+ * William Jolitz.
+ *
+ * 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>
+
+ENTRY(sigsetjmp)
+ movl 4(%esp),%ecx
+ movl 8(%esp),%eax
+ movl %eax,28(%ecx)
+ testl %eax,%eax
+ jz 1f
+
+ PIC_PROLOGUE
+ pushl $0
+#ifdef PIC
+ call PIC_PLT(_C_LABEL(sigblock))
+#else
+ call _C_LABEL(sigblock)
+#endif
+ addl $4,%esp
+ PIC_EPILOGUE
+
+ movl 4(%esp),%ecx
+ movl %eax,24(%ecx)
+1: movl 0(%esp),%edx
+ movl %edx, 0(%ecx)
+ movl %ebx, 4(%ecx)
+ movl %esp, 8(%ecx)
+ movl %ebp,12(%ecx)
+ movl %esi,16(%ecx)
+ movl %edi,20(%ecx)
+ xorl %eax,%eax
+ ret
+
+ENTRY(siglongjmp)
+ movl 4(%esp),%edx
+ cmpl $0,28(%edx)
+ jz 1f
+
+ PIC_PROLOGUE
+ pushl 24(%edx)
+#ifdef PIC
+ call PIC_PLT(_C_LABEL(sigsetmask))
+#else
+ call _C_LABEL(sigsetmask)
+#endif
+ addl $4,%esp
+ PIC_EPILOGUE
+
+1: movl 4(%esp),%edx
+ movl 8(%esp),%eax
+ movl 0(%edx),%ecx
+ movl 4(%edx),%ebx
+ movl 8(%edx),%esp
+ movl 12(%edx),%ebp
+ movl 16(%edx),%esi
+ movl 20(%edx),%edi
+ testl %eax,%eax
+ jnz 2f
+ incl %eax
+2: movl %ecx,0(%esp)
+ ret
diff --git a/libc/arch-x86/include/endian.h b/libc/arch-x86/include/endian.h
index ad37919..4a70536 100644
--- a/libc/arch-x86/include/endian.h
+++ b/libc/arch-x86/include/endian.h
@@ -31,14 +31,14 @@
#if defined(_KERNEL) && !defined(I386_CPU)
#define __swap32md(x) ({ \
- u_int32_t __swap32md_x = (x); \
+ uint32_t __swap32md_x = (x); \
\
__asm ("bswap %1" : "+r" (__swap32md_x)); \
__swap32md_x; \
})
#else
#define __swap32md(x) ({ \
- u_int32_t __swap32md_x = (x); \
+ uint32_t __swap32md_x = (x); \
\
__asm ("rorw $8, %w1; rorl $16, %1; rorw $8, %w1" : \
"+r" (__swap32md_x)); \
@@ -47,13 +47,13 @@
#endif /* _KERNEL && !I386_CPU */
#define __swap64md(x) ({ \
- u_int64_t __swap64md_x = (x); \
+ uint64_t __swap64md_x = (x); \
\
- (u_int64_t)__swap32md(__swap64md_x >> 32) | \
- (u_int64_t)__swap32md(__swap64md_x & 0xffffffff) << 32; \
+ (uint64_t)__swap32md(__swap64md_x >> 32) | \
+ (uint64_t)__swap32md(__swap64md_x & 0xffffffff) << 32; \
})
#define __swap16md(x) ({ \
- u_int16_t __swap16md_x = (x); \
+ uint16_t __swap16md_x = (x); \
\
__asm ("rorw $8, %w1" : "+r" (__swap16md_x)); \
__swap16md_x; \
diff --git a/libc/arch-x86/include/machine/_types.h b/libc/arch-x86/include/machine/_types.h
index be4f6e4..e9280a5 100644
--- a/libc/arch-x86/include/machine/_types.h
+++ b/libc/arch-x86/include/machine/_types.h
@@ -36,8 +36,8 @@
#define _I386__TYPES_H_
/* the kernel defines size_t as unsigned int, but g++ wants it to be unsigned long */
-#ifndef _SIZE_T
-# define _SIZE_T
+#ifndef _SIZE_T_DEFINED_
+# define _SIZE_T_DEFINED_
# ifdef ANDROID
typedef unsigned int size_t;
# else
@@ -54,9 +54,6 @@
typedef long ptrdiff_t;
#endif
-#define _OFF_T_DEFINED_
-#define _SIZE_T_DEFINED_
-
#include <linux/types.h>
/* 7.18.1.1 Exact-width integer types */
diff --git a/libc/arch-x86/string/memcmp_wrapper.S b/libc/arch-x86/string/memcmp_wrapper.S
index 7e28c1e..fa0c672 100644
--- a/libc/arch-x86/string/memcmp_wrapper.S
+++ b/libc/arch-x86/string/memcmp_wrapper.S
@@ -31,7 +31,7 @@
#if defined(USE_SSSE3)
# define MEMCMP memcmp
-# include "ssse3-memcmp3.S"
+# include "ssse3-memcmp3-new.S"
#else
diff --git a/libc/arch-x86/string/sse2-memset5-atom.S b/libc/arch-x86/string/sse2-memset5-atom.S
index 59a598c..4b7f71b 100644
--- a/libc/arch-x86/string/sse2-memset5-atom.S
+++ b/libc/arch-x86/string/sse2-memset5-atom.S
@@ -49,7 +49,7 @@
#endif
#ifndef cfi_restore
-# define cfi_restore(reg) .cfi_restore (reg)
+# define cfi_restore(reg) .cfi_restore reg
#endif
#ifndef cfi_adjust_cfa_offset
@@ -285,7 +285,6 @@
pxor %xmm0, %xmm0
#else
movd %eax, %xmm0
- punpcklbw %xmm0, %xmm0
pshufd $0, %xmm0, %xmm0
#endif
testl $0xf, %edx
@@ -329,14 +328,17 @@
#ifdef DATA_CACHE_SIZE
POP (%ebx)
+# define RESTORE_EBX_STATE CFI_PUSH (%ebx)
cmp $DATA_CACHE_SIZE, %ecx
#else
# ifdef SHARED
+# define RESTORE_EBX_STATE
call __i686.get_pc_thunk.bx
add $_GLOBAL_OFFSET_TABLE_, %ebx
cmp __x86_data_cache_size@GOTOFF(%ebx), %ecx
# else
POP (%ebx)
+# define RESTORE_EBX_STATE CFI_PUSH (%ebx)
cmp __x86_data_cache_size, %ecx
# endif
#endif
@@ -370,7 +372,7 @@
jae L(128bytesormore_normal)
L(128bytesless_normal):
- lea 128(%ecx), %ecx
+ add $128, %ecx
BRANCH_TO_JMPTBL_ENTRY (L(table_16_128bytes))
ALIGN (4)
@@ -393,8 +395,13 @@
L(128bytesless_L2_normal):
BRANCH_TO_JMPTBL_ENTRY (L(table_16_128bytes))
+ RESTORE_EBX_STATE
L(128bytesormore_nt_start):
sub %ebx, %ecx
+ mov %ebx, %eax
+ and $0x7f, %eax
+ add %eax, %ecx
+ movd %xmm0, %eax
ALIGN (4)
L(128bytesormore_shared_cache_loop):
prefetcht0 0x3c0(%edx)
diff --git a/libc/arch-x86/string/sse2-strlen-atom.S b/libc/arch-x86/string/sse2-strlen-atom.S
new file mode 100644
index 0000000..8911868
--- /dev/null
+++ b/libc/arch-x86/string/sse2-strlen-atom.S
@@ -0,0 +1,369 @@
+#define STRLEN sse2_strlen_atom
+
+#ifndef L
+# define L(label) .L##label
+#endif
+
+#ifndef cfi_startproc
+# define cfi_startproc .cfi_startproc
+#endif
+
+#ifndef cfi_endproc
+# define cfi_endproc .cfi_endproc
+#endif
+
+#ifndef cfi_rel_offset
+# define cfi_rel_offset(reg, off) .cfi_rel_offset reg, off
+#endif
+
+#ifndef cfi_restore
+# define cfi_restore(reg) .cfi_restore reg
+#endif
+
+#ifndef cfi_adjust_cfa_offset
+# define cfi_adjust_cfa_offset(off) .cfi_adjust_cfa_offset off
+#endif
+
+#ifndef cfi_remember_state
+# define cfi_remember_state .cfi_remember_state
+#endif
+
+#ifndef cfi_restore_state
+# define cfi_restore_state .cfi_restore_state
+#endif
+
+#ifndef ENTRY
+# define ENTRY(name) \
+ .type name, @function; \
+ .globl name; \
+ .p2align 4; \
+name: \
+ cfi_startproc
+#endif
+
+#ifndef END
+# define END(name) \
+ cfi_endproc; \
+ .size name, .-name
+#endif
+
+#define CFI_PUSH(REG) \
+ cfi_adjust_cfa_offset (4); \
+ cfi_rel_offset (REG, 0)
+
+#define CFI_POP(REG) \
+ cfi_adjust_cfa_offset (-4); \
+ cfi_restore (REG)
+
+#define PUSH(REG) pushl REG; CFI_PUSH (REG)
+#define POP(REG) popl REG; CFI_POP (REG)
+#define PARMS 4
+#define STR PARMS
+#define ENTRANCE
+#define RETURN ret
+
+ .text
+ENTRY (STRLEN)
+ ENTRANCE
+ mov STR(%esp), %edx
+ xor %eax, %eax
+ cmpb $0, (%edx)
+ jz L(exit_tail0)
+ cmpb $0, 1(%edx)
+ jz L(exit_tail1)
+ cmpb $0, 2(%edx)
+ jz L(exit_tail2)
+ cmpb $0, 3(%edx)
+ jz L(exit_tail3)
+ cmpb $0, 4(%edx)
+ jz L(exit_tail4)
+ cmpb $0, 5(%edx)
+ jz L(exit_tail5)
+ cmpb $0, 6(%edx)
+ jz L(exit_tail6)
+ cmpb $0, 7(%edx)
+ jz L(exit_tail7)
+ cmpb $0, 8(%edx)
+ jz L(exit_tail8)
+ cmpb $0, 9(%edx)
+ jz L(exit_tail9)
+ cmpb $0, 10(%edx)
+ jz L(exit_tail10)
+ cmpb $0, 11(%edx)
+ jz L(exit_tail11)
+ cmpb $0, 12(%edx)
+ jz L(exit_tail12)
+ cmpb $0, 13(%edx)
+ jz L(exit_tail13)
+ cmpb $0, 14(%edx)
+ jz L(exit_tail14)
+ cmpb $0, 15(%edx)
+ jz L(exit_tail15)
+ pxor %xmm0, %xmm0
+ mov %edx, %eax
+ mov %edx, %ecx
+ and $-16, %eax
+ add $16, %ecx
+ add $16, %eax
+
+ pcmpeqb (%eax), %xmm0
+ pmovmskb %xmm0, %edx
+ pxor %xmm1, %xmm1
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm1
+ pmovmskb %xmm1, %edx
+ pxor %xmm2, %xmm2
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+
+ pcmpeqb (%eax), %xmm2
+ pmovmskb %xmm2, %edx
+ pxor %xmm3, %xmm3
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm3
+ pmovmskb %xmm3, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm0
+ pmovmskb %xmm0, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm1
+ pmovmskb %xmm1, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm2
+ pmovmskb %xmm2, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm3
+ pmovmskb %xmm3, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm0
+ pmovmskb %xmm0, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm1
+ pmovmskb %xmm1, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm2
+ pmovmskb %xmm2, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm3
+ pmovmskb %xmm3, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm0
+ pmovmskb %xmm0, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm1
+ pmovmskb %xmm1, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm2
+ pmovmskb %xmm2, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ pcmpeqb (%eax), %xmm3
+ pmovmskb %xmm3, %edx
+ test %edx, %edx
+ lea 16(%eax), %eax
+ jnz L(exit)
+
+ and $-0x40, %eax
+ PUSH (%esi)
+ PUSH (%edi)
+ PUSH (%ebx)
+ PUSH (%ebp)
+ xor %ebp, %ebp
+L(aligned_64):
+ pcmpeqb (%eax), %xmm0
+ pcmpeqb 16(%eax), %xmm1
+ pcmpeqb 32(%eax), %xmm2
+ pcmpeqb 48(%eax), %xmm3
+ pmovmskb %xmm0, %edx
+ pmovmskb %xmm1, %esi
+ pmovmskb %xmm2, %edi
+ pmovmskb %xmm3, %ebx
+ or %edx, %ebp
+ or %esi, %ebp
+ or %edi, %ebp
+ or %ebx, %ebp
+ lea 64(%eax), %eax
+ jz L(aligned_64)
+L(48leave):
+ test %edx, %edx
+ jnz L(aligned_64_exit_16)
+ test %esi, %esi
+ jnz L(aligned_64_exit_32)
+ test %edi, %edi
+ jnz L(aligned_64_exit_48)
+ mov %ebx, %edx
+ lea (%eax), %eax
+ jmp L(aligned_64_exit)
+L(aligned_64_exit_48):
+ lea -16(%eax), %eax
+ mov %edi, %edx
+ jmp L(aligned_64_exit)
+L(aligned_64_exit_32):
+ lea -32(%eax), %eax
+ mov %esi, %edx
+ jmp L(aligned_64_exit)
+L(aligned_64_exit_16):
+ lea -48(%eax), %eax
+L(aligned_64_exit):
+ POP (%ebp)
+ POP (%ebx)
+ POP (%edi)
+ POP (%esi)
+L(exit):
+ sub %ecx, %eax
+ test %dl, %dl
+ jz L(exit_high)
+ test $0x01, %dl
+ jnz L(exit_tail0)
+
+ test $0x02, %dl
+ jnz L(exit_tail1)
+
+ test $0x04, %dl
+ jnz L(exit_tail2)
+
+ test $0x08, %dl
+ jnz L(exit_tail3)
+
+ test $0x10, %dl
+ jnz L(exit_tail4)
+
+ test $0x20, %dl
+ jnz L(exit_tail5)
+
+ test $0x40, %dl
+ jnz L(exit_tail6)
+ add $7, %eax
+L(exit_tail0):
+ RETURN
+
+L(exit_high):
+ add $8, %eax
+ test $0x01, %dh
+ jnz L(exit_tail0)
+
+ test $0x02, %dh
+ jnz L(exit_tail1)
+
+ test $0x04, %dh
+ jnz L(exit_tail2)
+
+ test $0x08, %dh
+ jnz L(exit_tail3)
+
+ test $0x10, %dh
+ jnz L(exit_tail4)
+
+ test $0x20, %dh
+ jnz L(exit_tail5)
+
+ test $0x40, %dh
+ jnz L(exit_tail6)
+ add $7, %eax
+ RETURN
+
+ .p2align 4
+L(exit_tail1):
+ add $1, %eax
+ RETURN
+
+L(exit_tail2):
+ add $2, %eax
+ RETURN
+
+L(exit_tail3):
+ add $3, %eax
+ RETURN
+
+L(exit_tail4):
+ add $4, %eax
+ RETURN
+
+L(exit_tail5):
+ add $5, %eax
+ RETURN
+
+L(exit_tail6):
+ add $6, %eax
+ RETURN
+
+L(exit_tail7):
+ add $7, %eax
+ RETURN
+
+L(exit_tail8):
+ add $8, %eax
+ RETURN
+
+L(exit_tail9):
+ add $9, %eax
+ RETURN
+
+L(exit_tail10):
+ add $10, %eax
+ RETURN
+
+L(exit_tail11):
+ add $11, %eax
+ RETURN
+
+L(exit_tail12):
+ add $12, %eax
+ RETURN
+
+L(exit_tail13):
+ add $13, %eax
+ RETURN
+
+L(exit_tail14):
+ add $14, %eax
+ RETURN
+
+L(exit_tail15):
+ add $15, %eax
+ ret
+
+END (STRLEN)
diff --git a/libc/arch-x86/string/ssse3-memcmp3.S b/libc/arch-x86/string/ssse3-memcmp3-new.S
similarity index 95%
rename from libc/arch-x86/string/ssse3-memcmp3.S
rename to libc/arch-x86/string/ssse3-memcmp3-new.S
index a7ce819..5ad8791 100644
--- a/libc/arch-x86/string/ssse3-memcmp3.S
+++ b/libc/arch-x86/string/ssse3-memcmp3-new.S
@@ -53,13 +53,21 @@
#endif
#ifndef cfi_restore
-# define cfi_restore(reg) .cfi_restore (reg)
+# define cfi_restore(reg) .cfi_restore reg
#endif
#ifndef cfi_adjust_cfa_offset
# define cfi_adjust_cfa_offset(off) .cfi_adjust_cfa_offset off
#endif
+#ifndef cfi_remember_state
+# define cfi_remember_state .cfi_remember_state
+#endif
+
+#ifndef cfi_restore_state
+# define cfi_restore_state .cfi_restore_state
+#endif
+
#ifndef ENTRY
# define ENTRY(name) \
.type name, @function; \
@@ -91,8 +99,7 @@
#define BLK2 BLK1+4
#define LEN BLK2+4
#define RETURN_END POP (%edi); POP (%esi); POP (%ebx); ret
-#define RETURN RETURN_END; CFI_PUSH (%ebx); CFI_PUSH (%edi); \
- CFI_PUSH (%esi)
+#define RETURN RETURN_END; cfi_restore_state; cfi_remember_state
.section .text.ssse3,"ax",@progbits
ENTRY (MEMCMP)
@@ -131,6 +138,7 @@
PUSH (%ebx)
PUSH (%esi)
PUSH (%edi)
+ cfi_remember_state
movdqu (%eax), %xmm3
movdqu (%edx), %xmm0
movl %eax, %edi
@@ -211,8 +219,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_0_gobble):
lea -48(%ecx), %ecx
@@ -257,8 +265,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_1):
cmp $80, %ecx
@@ -287,8 +295,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_1_gobble):
sub $32, %ecx
@@ -340,8 +348,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_2):
cmp $80, %ecx
@@ -370,8 +378,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_2_gobble):
sub $32, %ecx
@@ -423,8 +431,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_3):
cmp $80, %ecx
@@ -453,8 +461,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_3_gobble):
sub $32, %ecx
@@ -506,8 +514,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_4):
cmp $80, %ecx
@@ -536,8 +544,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_4_gobble):
sub $32, %ecx
@@ -589,8 +597,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_5):
cmp $80, %ecx
@@ -619,8 +627,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_5_gobble):
sub $32, %ecx
@@ -672,8 +680,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_6):
cmp $80, %ecx
@@ -702,8 +710,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_6_gobble):
sub $32, %ecx
@@ -755,8 +763,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_7):
cmp $80, %ecx
@@ -785,8 +793,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_7_gobble):
sub $32, %ecx
@@ -838,8 +846,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_8):
cmp $80, %ecx
@@ -868,8 +876,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_8_gobble):
sub $32, %ecx
@@ -921,8 +929,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_9):
cmp $80, %ecx
@@ -951,8 +959,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_9_gobble):
sub $32, %ecx
@@ -1004,8 +1012,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_10):
cmp $80, %ecx
@@ -1034,8 +1042,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_10_gobble):
sub $32, %ecx
@@ -1087,8 +1095,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_11):
cmp $80, %ecx
@@ -1117,8 +1125,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_11_gobble):
sub $32, %ecx
@@ -1170,8 +1178,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_12):
cmp $80, %ecx
@@ -1200,8 +1208,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_12_gobble):
sub $32, %ecx
@@ -1253,8 +1261,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_13):
cmp $80, %ecx
@@ -1283,8 +1291,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_13_gobble):
sub $32, %ecx
@@ -1336,8 +1344,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_14):
cmp $80, %ecx
@@ -1366,8 +1374,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_14_gobble):
sub $32, %ecx
@@ -1419,8 +1427,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_15):
cmp $80, %ecx
@@ -1449,8 +1457,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shr_15_gobble):
sub $32, %ecx
@@ -1502,8 +1510,8 @@
POP (%esi)
jmp L(less48bytes)
- CFI_PUSH (%esi)
- CFI_PUSH (%edi)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(exit):
pmovmskb %xmm1, %ebx
diff --git a/libc/arch-x86/string/ssse3-memcpy5.S b/libc/arch-x86/string/ssse3-memcpy5.S
index 6b90402..b4773df 100644
--- a/libc/arch-x86/string/ssse3-memcpy5.S
+++ b/libc/arch-x86/string/ssse3-memcpy5.S
@@ -53,13 +53,21 @@
#endif
#ifndef cfi_restore
-# define cfi_restore(reg) .cfi_restore (reg)
+# define cfi_restore(reg) .cfi_restore reg
#endif
#ifndef cfi_adjust_cfa_offset
# define cfi_adjust_cfa_offset(off) .cfi_adjust_cfa_offset off
#endif
+#ifndef cfi_remember_state
+# define cfi_remember_state .cfi_remember_state
+#endif
+
+#ifndef cfi_restore_state
+# define cfi_restore_state .cfi_restore_state
+#endif
+
#ifndef ENTRY
# define ENTRY(name) \
.type name, @function; \
@@ -118,8 +126,8 @@
jmp *%ebx
# define BRANCH_TO_JMPTBL_ENTRY_VALUE(TABLE) \
- addl $(TABLE - .), %ebx
-
+ addl $(TABLE - .), %ebx
+
# define BRANCH_TO_JMPTBL_ENTRY_TAIL(TABLE, INDEX, SCALE) \
addl (%ebx,INDEX,SCALE), %ebx; \
/* We loaded the jump table. Go. */ \
@@ -146,7 +154,7 @@
# define BRANCH_TO_JMPTBL_ENTRY(TABLE, INDEX, SCALE) \
jmp *TABLE(,INDEX,SCALE)
-# define BRANCH_TO_JMPTBL_ENTRY_VALUE(TABLE)
+# define BRANCH_TO_JMPTBL_ENTRY_VALUE(TABLE)
# define BRANCH_TO_JMPTBL_ENTRY_TAIL(TABLE, INDEX, SCALE) \
jmp *TABLE(,INDEX,SCALE)
@@ -198,6 +206,7 @@
movl %edx, %edi
and $-16, %edx
PUSH (%esi)
+ cfi_remember_state
add $16, %edx
movl %edi, %esi
sub %edx, %edi
@@ -223,6 +232,8 @@
BRANCH_TO_JMPTBL_ENTRY (L(shl_table), %edi, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_0):
movdqu %xmm0, (%esi)
@@ -270,6 +281,7 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY (L(table_48bytes_fwd), %ecx, 4)
+ CFI_PUSH (%edi)
L(shl_0_gobble):
#ifdef DATA_CACHE_SIZE_HALF
@@ -419,7 +431,8 @@
add %ecx, %eax
BRANCH_TO_JMPTBL_ENTRY (L(table_48bytes_fwd), %ecx, 4)
-
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_1):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -463,6 +476,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_2):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -506,6 +521,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_3):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -549,6 +566,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_4):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -592,6 +611,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_5):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -635,7 +656,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
-
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_6):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -679,6 +701,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_7):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -722,6 +746,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_8):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -765,6 +791,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_9):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -808,6 +836,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_10):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -851,6 +881,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_11):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -894,6 +926,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_12):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -937,6 +971,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_13):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -980,6 +1016,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_14):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -1023,7 +1061,8 @@
POP (%edi)
BRANCH_TO_JMPTBL_ENTRY_TAIL(L(table_48bytes_fwd), %ecx, 4)
-
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(shl_15):
BRANCH_TO_JMPTBL_ENTRY_VALUE(L(table_48bytes_fwd))
@@ -1264,8 +1303,10 @@
movl DEST(%esp), %eax
# endif
#endif
- RETURN
+ RETURN_END
+ cfi_restore_state
+ cfi_remember_state
ALIGN (4)
L(large_page):
movdqu (%eax), %xmm1
@@ -1688,6 +1729,7 @@
L(bk_write_less32bytes_2):
BRANCH_TO_JMPTBL_ENTRY (L(table_48_bytes_bwd), %ecx, 4)
+ CFI_PUSH (%esi)
ALIGN (4)
L(bk_align):
cmp $8, %ecx
diff --git a/libc/arch-x86/string/ssse3-strcmp.S b/libc/arch-x86/string/ssse3-strcmp-latest.S
similarity index 98%
rename from libc/arch-x86/string/ssse3-strcmp.S
rename to libc/arch-x86/string/ssse3-strcmp-latest.S
index cfb2e9f..69c6425 100644
--- a/libc/arch-x86/string/ssse3-strcmp.S
+++ b/libc/arch-x86/string/ssse3-strcmp-latest.S
@@ -45,13 +45,21 @@
#endif
#ifndef cfi_restore
-# define cfi_restore(reg) .cfi_restore (reg)
+# define cfi_restore(reg) .cfi_restore reg
#endif
#ifndef cfi_adjust_cfa_offset
# define cfi_adjust_cfa_offset(off) .cfi_adjust_cfa_offset off
#endif
+#ifndef cfi_remember_state
+# define cfi_remember_state .cfi_remember_state
+#endif
+
+#ifndef cfi_restore_state
+# define cfi_restore_state .cfi_restore_state
+#endif
+
#ifndef ENTRY
# define ENTRY(name) \
.type name, @function; \
@@ -201,6 +209,9 @@
PUSH (%ebx)
PUSH (%edi)
PUSH (%esi)
+#ifdef USE_AS_STRNCMP
+ cfi_remember_state
+#endif
movl %edx, %edi
movl %eax, %ecx
@@ -1521,17 +1532,18 @@
sub $0xffff, %esi
jnz L(exit)
+#ifdef USE_AS_STRNCMP
+ cmp $16, %ebp
+ lea -16(%ebp), %ebp
+ jbe L(more8byteseq)
+#endif
+
add $16, %ecx
movdqa %xmm4, %xmm3
add $16, %edi
jg L(nibble_ashr_12)
-#ifdef USE_AS_STRNCMP
- cmp $16, %ebp
- lea -16(%ebp), %ebp
- jbe L(more8byteseq)
-#endif
movdqa (%eax, %ecx), %xmm1
movdqa (%edx, %ecx), %xmm2
movdqa %xmm2, %xmm4
@@ -2087,10 +2099,7 @@
RETURN
#ifdef USE_AS_STRNCMP
- CFI_PUSH (%ebx)
- CFI_PUSH (%edi)
- CFI_PUSH (%esi)
-
+ cfi_restore_state
.p2align 4
L(more8byteseq):
POP (%esi)
diff --git a/libc/arch-x86/string/strcmp_wrapper.S b/libc/arch-x86/string/strcmp_wrapper.S
index 69b7f0b..20f3064 100644
--- a/libc/arch-x86/string/strcmp_wrapper.S
+++ b/libc/arch-x86/string/strcmp_wrapper.S
@@ -31,7 +31,7 @@
#if defined(USE_SSSE3)
# define ssse3_strcmp_latest strcmp
-# include "ssse3-strcmp.S"
+# include "ssse3-strcmp-latest.S"
#else
diff --git a/libc/arch-x86/string/strlen_wrapper.S b/libc/arch-x86/string/strlen_wrapper.S
new file mode 100644
index 0000000..e62786b
--- /dev/null
+++ b/libc/arch-x86/string/strlen_wrapper.S
@@ -0,0 +1,40 @@
+/*
+Copyright (c) 2010, Intel Corporation
+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.
+
+ * Neither the name of Intel Corporation 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 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.
+*/
+
+#if defined(USE_SSE2)
+
+# define sse2_strlen_atom strlen
+# include "sse2-strlen-atom.S"
+
+#else
+
+# include "strlen.S"
+
+#endif
diff --git a/libc/arch-x86/string/strncmp_wrapper.S b/libc/arch-x86/string/strncmp_wrapper.S
index 2050184..191d755 100644
--- a/libc/arch-x86/string/strncmp_wrapper.S
+++ b/libc/arch-x86/string/strncmp_wrapper.S
@@ -32,7 +32,7 @@
# define USE_AS_STRNCMP
# define ssse3_strcmp_latest strncmp
-# include "ssse3-strcmp.S"
+# include "ssse3-strcmp-latest.S"
#else
diff --git a/libc/arch-x86/syscalls.mk b/libc/arch-x86/syscalls.mk
index 420a91e..e8c6a77 100644
--- a/libc/arch-x86/syscalls.mk
+++ b/libc/arch-x86/syscalls.mk
@@ -44,8 +44,8 @@
syscall_src += arch-x86/syscalls/acct.S
syscall_src += arch-x86/syscalls/read.S
syscall_src += arch-x86/syscalls/write.S
-syscall_src += arch-x86/syscalls/__pread64.S
-syscall_src += arch-x86/syscalls/__pwrite64.S
+syscall_src += arch-x86/syscalls/pread64.S
+syscall_src += arch-x86/syscalls/pwrite64.S
syscall_src += arch-x86/syscalls/__open.S
syscall_src += arch-x86/syscalls/__openat.S
syscall_src += arch-x86/syscalls/close.S
@@ -73,6 +73,7 @@
syscall_src += arch-x86/syscalls/dup2.S
syscall_src += arch-x86/syscalls/select.S
syscall_src += arch-x86/syscalls/ftruncate.S
+syscall_src += arch-x86/syscalls/ftruncate64.S
syscall_src += arch-x86/syscalls/getdents.S
syscall_src += arch-x86/syscalls/fsync.S
syscall_src += arch-x86/syscalls/fdatasync.S
@@ -156,6 +157,9 @@
syscall_src += arch-x86/syscalls/sched_get_priority_max.S
syscall_src += arch-x86/syscalls/sched_get_priority_min.S
syscall_src += arch-x86/syscalls/sched_rr_get_interval.S
+syscall_src += arch-x86/syscalls/sched_setaffinity.S
+syscall_src += arch-x86/syscalls/__sched_getaffinity.S
+syscall_src += arch-x86/syscalls/__getcpu.S
syscall_src += arch-x86/syscalls/ioprio_set.S
syscall_src += arch-x86/syscalls/ioprio_get.S
syscall_src += arch-x86/syscalls/uname.S
diff --git a/libc/arch-x86/syscalls/__getcpu.S b/libc/arch-x86/syscalls/__getcpu.S
new file mode 100644
index 0000000..0381799
--- /dev/null
+++ b/libc/arch-x86/syscalls/__getcpu.S
@@ -0,0 +1,29 @@
+/* autogenerated by gensyscalls.py */
+#include <sys/linux-syscalls.h>
+
+ .text
+ .type __getcpu, @function
+ .globl __getcpu
+ .align 4
+
+__getcpu:
+ pushl %ebx
+ pushl %ecx
+ pushl %edx
+ mov 16(%esp), %ebx
+ mov 20(%esp), %ecx
+ mov 24(%esp), %edx
+ movl $__NR_getcpu, %eax
+ int $0x80
+ cmpl $-129, %eax
+ jb 1f
+ negl %eax
+ pushl %eax
+ call __set_errno
+ addl $4, %esp
+ orl $-1, %eax
+1:
+ popl %edx
+ popl %ecx
+ popl %ebx
+ ret
diff --git a/libc/arch-x86/syscalls/__sched_getaffinity.S b/libc/arch-x86/syscalls/__sched_getaffinity.S
new file mode 100644
index 0000000..43bfa50
--- /dev/null
+++ b/libc/arch-x86/syscalls/__sched_getaffinity.S
@@ -0,0 +1,29 @@
+/* autogenerated by gensyscalls.py */
+#include <sys/linux-syscalls.h>
+
+ .text
+ .type __sched_getaffinity, @function
+ .globl __sched_getaffinity
+ .align 4
+
+__sched_getaffinity:
+ pushl %ebx
+ pushl %ecx
+ pushl %edx
+ mov 16(%esp), %ebx
+ mov 20(%esp), %ecx
+ mov 24(%esp), %edx
+ movl $__NR_sched_getaffinity, %eax
+ int $0x80
+ cmpl $-129, %eax
+ jb 1f
+ negl %eax
+ pushl %eax
+ call __set_errno
+ addl $4, %esp
+ orl $-1, %eax
+1:
+ popl %edx
+ popl %ecx
+ popl %ebx
+ ret
diff --git a/libc/arch-x86/syscalls/ftruncate64.S b/libc/arch-x86/syscalls/ftruncate64.S
new file mode 100644
index 0000000..66835ab
--- /dev/null
+++ b/libc/arch-x86/syscalls/ftruncate64.S
@@ -0,0 +1,29 @@
+/* autogenerated by gensyscalls.py */
+#include <sys/linux-syscalls.h>
+
+ .text
+ .type ftruncate64, @function
+ .globl ftruncate64
+ .align 4
+
+ftruncate64:
+ pushl %ebx
+ pushl %ecx
+ pushl %edx
+ mov 16(%esp), %ebx
+ mov 20(%esp), %ecx
+ mov 24(%esp), %edx
+ movl $__NR_ftruncate64, %eax
+ int $0x80
+ cmpl $-129, %eax
+ jb 1f
+ negl %eax
+ pushl %eax
+ call __set_errno
+ addl $4, %esp
+ orl $-1, %eax
+1:
+ popl %edx
+ popl %ecx
+ popl %ebx
+ ret
diff --git a/libc/arch-x86/syscalls/__pread64.S b/libc/arch-x86/syscalls/pread64.S
similarity index 90%
rename from libc/arch-x86/syscalls/__pread64.S
rename to libc/arch-x86/syscalls/pread64.S
index 3114673..eb004a9 100644
--- a/libc/arch-x86/syscalls/__pread64.S
+++ b/libc/arch-x86/syscalls/pread64.S
@@ -2,11 +2,11 @@
#include <sys/linux-syscalls.h>
.text
- .type __pread64, @function
- .globl __pread64
+ .type pread64, @function
+ .globl pread64
.align 4
-__pread64:
+pread64:
pushl %ebx
pushl %ecx
pushl %edx
diff --git a/libc/arch-x86/syscalls/__pwrite64.S b/libc/arch-x86/syscalls/pwrite64.S
similarity index 90%
rename from libc/arch-x86/syscalls/__pwrite64.S
rename to libc/arch-x86/syscalls/pwrite64.S
index 28f6536..01389f8 100644
--- a/libc/arch-x86/syscalls/__pwrite64.S
+++ b/libc/arch-x86/syscalls/pwrite64.S
@@ -2,11 +2,11 @@
#include <sys/linux-syscalls.h>
.text
- .type __pwrite64, @function
- .globl __pwrite64
+ .type pwrite64, @function
+ .globl pwrite64
.align 4
-__pwrite64:
+pwrite64:
pushl %ebx
pushl %ecx
pushl %edx
diff --git a/libc/arch-x86/syscalls/sched_setaffinity.S b/libc/arch-x86/syscalls/sched_setaffinity.S
new file mode 100644
index 0000000..5fa51ef
--- /dev/null
+++ b/libc/arch-x86/syscalls/sched_setaffinity.S
@@ -0,0 +1,29 @@
+/* autogenerated by gensyscalls.py */
+#include <sys/linux-syscalls.h>
+
+ .text
+ .type sched_setaffinity, @function
+ .globl sched_setaffinity
+ .align 4
+
+sched_setaffinity:
+ pushl %ebx
+ pushl %ecx
+ pushl %edx
+ mov 16(%esp), %ebx
+ mov 20(%esp), %ecx
+ mov 24(%esp), %edx
+ movl $__NR_sched_setaffinity, %eax
+ int $0x80
+ cmpl $-129, %eax
+ jb 1f
+ negl %eax
+ pushl %eax
+ call __set_errno
+ addl $4, %esp
+ orl $-1, %eax
+1:
+ popl %edx
+ popl %ecx
+ popl %ebx
+ ret
diff --git a/libc/bionic/__set_errno.c b/libc/bionic/__set_errno.c
index c72d4f7..163d404 100644
--- a/libc/bionic/__set_errno.c
+++ b/libc/bionic/__set_errno.c
@@ -40,6 +40,7 @@
* (tail-called in the case of 0-4 arg versions)
*/
+__LIBC_HIDDEN__
int __set_syscall_errno(int n)
{
/* some syscalls, mmap() for example, have valid return
diff --git a/libc/bionic/_rand48.c b/libc/bionic/_rand48.c
deleted file mode 100644
index e422781..0000000
--- a/libc/bionic/_rand48.c
+++ /dev/null
@@ -1,47 +0,0 @@
-/*
- * Copyright (c) 1993 Martin Birgmeier
- * All rights reserved.
- *
- * You may redistribute unmodified or modified versions of this source
- * code provided that the above copyright notice and this and the
- * following conditions are retained.
- *
- * This software is provided ``as is'', and comes with no warranties
- * of any kind. I shall in no event be liable for anything that happens
- * to anyone/anything when using this software.
- */
-
-#include <sys/cdefs.h>
-#include "rand48.h"
-
-unsigned short _rand48_seed[3] = {
- RAND48_SEED_0,
- RAND48_SEED_1,
- RAND48_SEED_2
-};
-unsigned short _rand48_mult[3] = {
- RAND48_MULT_0,
- RAND48_MULT_1,
- RAND48_MULT_2
-};
-unsigned short _rand48_add = RAND48_ADD;
-
-void
-_dorand48(unsigned short xseed[3])
-{
- unsigned long accu;
- unsigned short temp[2];
-
- accu = (unsigned long) _rand48_mult[0] * (unsigned long) xseed[0] +
- (unsigned long) _rand48_add;
- temp[0] = (unsigned short) accu; /* lower 16 bits */
- accu >>= sizeof(unsigned short) * 8;
- accu += (unsigned long) _rand48_mult[0] * (unsigned long) xseed[1] +
- (unsigned long) _rand48_mult[1] * (unsigned long) xseed[0];
- temp[1] = (unsigned short) accu; /* middle 16 bits */
- accu >>= sizeof(unsigned short) * 8;
- accu += _rand48_mult[0] * xseed[2] + _rand48_mult[1] * xseed[1] + _rand48_mult[2] * xseed[0];
- xseed[0] = temp[0];
- xseed[1] = temp[1];
- xseed[2] = (unsigned short) accu;
-}
diff --git a/libc/bionic/drand48.c b/libc/bionic/drand48.c
index fd48196..93272cf 100644
--- a/libc/bionic/drand48.c
+++ b/libc/bionic/drand48.c
@@ -15,10 +15,10 @@
#include "rand48.h"
-extern unsigned short _rand48_seed[3];
+extern unsigned short __rand48_seed[3];
double
drand48(void)
{
- return erand48(_rand48_seed);
+ return erand48(__rand48_seed);
}
diff --git a/libc/bionic/erand48.c b/libc/bionic/erand48.c
index 843ff34..4ecbead 100644
--- a/libc/bionic/erand48.c
+++ b/libc/bionic/erand48.c
@@ -18,7 +18,7 @@
double
erand48(unsigned short xseed[3])
{
- _dorand48(xseed);
+ __dorand48(xseed);
return ldexp((double) xseed[0], -48) +
ldexp((double) xseed[1], -32) +
ldexp((double) xseed[2], -16);
diff --git a/libc/bionic/fork.c b/libc/bionic/fork.c
index 79b8fff..0eedb01 100644
--- a/libc/bionic/fork.c
+++ b/libc/bionic/fork.c
@@ -41,9 +41,12 @@
* of error, or in the parent process
*/
__timer_table_start_stop(1);
+ __bionic_atfork_run_prepare();
+
ret = __fork();
if (ret != 0) { /* not a child process */
__timer_table_start_stop(0);
+ __bionic_atfork_run_parent();
} else {
/*
* Newly created process must update cpu accounting.
@@ -52,6 +55,7 @@
* as a parameter.
*/
cpuacct_add(getuid());
+ __bionic_atfork_run_child();
}
return ret;
}
diff --git a/libc/bionic/libc_init_common.c b/libc/bionic/libc_init_common.c
index f7579bd..b6a6379 100644
--- a/libc/bionic/libc_init_common.c
+++ b/libc/bionic/libc_init_common.c
@@ -62,7 +62,7 @@
static pthread_internal_t thread;
static void* tls_area[BIONIC_TLS_SLOTS];
- /* setup pthread runtime and maint thread descriptor */
+ /* setup pthread runtime and main thread descriptor */
unsigned stacktop = (__get_sp() & ~(PAGE_SIZE - 1)) + PAGE_SIZE;
unsigned stacksize = 128 * 1024;
unsigned stackbottom = stacktop - stacksize;
diff --git a/libc/bionic/libc_init_dynamic.c b/libc/bionic/libc_init_dynamic.c
index f64b6f2..4bb2a81 100644
--- a/libc/bionic/libc_init_dynamic.c
+++ b/libc/bionic/libc_init_dynamic.c
@@ -61,7 +61,7 @@
void __libc_preinit(void)
{
- /* Read the ELF data pointer form a special slot of the
+ /* Read the ELF data pointer from a special slot of the
* TLS area, then call __libc_init_common with it.
*
* Note that:
diff --git a/libc/bionic/malloc_debug_common.c b/libc/bionic/malloc_debug_common.c
index f05576c..ebf0006 100644
--- a/libc/bionic/malloc_debug_common.c
+++ b/libc/bionic/malloc_debug_common.c
@@ -120,6 +120,7 @@
totalMemory == NULL || backtraceSize == NULL) {
return;
}
+ *totalMemory = 0;
pthread_mutex_lock(&gAllocationsMutex);
@@ -127,7 +128,6 @@
*info = NULL;
*overallSize = 0;
*infoSize = 0;
- *totalMemory = 0;
*backtraceSize = 0;
goto done;
}
diff --git a/libc/bionic/pthread-atfork.c b/libc/bionic/pthread-atfork.c
new file mode 100644
index 0000000..3a5189d
--- /dev/null
+++ b/libc/bionic/pthread-atfork.c
@@ -0,0 +1,123 @@
+/*
+ * 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 <stdlib.h>
+#include <errno.h>
+#include <pthread.h>
+#include <sys/queue.h>
+
+static pthread_mutex_t handler_mutex = PTHREAD_RECURSIVE_MUTEX_INITIALIZER;
+
+struct atfork_t
+{
+ CIRCLEQ_ENTRY(atfork_t) entries;
+
+ void (*prepare)(void);
+ void (*child)(void);
+ void (*parent)(void);
+};
+static CIRCLEQ_HEAD(atfork_head_t, atfork_t) atfork_head = \
+ CIRCLEQ_HEAD_INITIALIZER(atfork_head);
+
+void __bionic_atfork_run_prepare()
+{
+ struct atfork_t *cursor;
+
+ /* We will lock this here, and unlock it in the parent and child functions.
+ * This ensures that nobody can modify the handler array between the calls
+ * to the prepare and parent/child handlers.
+ *
+ * TODO: If a handler mucks with the list, it could cause problems. Right
+ * now it's ok because all they can do is add new items to the end
+ * of the list, but if/when we implement cleanup in dlclose() things
+ * will get more interesting...
+ */
+ pthread_mutex_lock(&handler_mutex);
+
+ /* Call pthread_atfork() prepare handlers. Posix states that the prepare
+ * handlers should be called in the reverse order of the parent/child
+ * handlers, so we iterate backwards.
+ */
+ for (cursor = atfork_head.cqh_last;
+ cursor != (void*)&atfork_head;
+ cursor = cursor->entries.cqe_prev) {
+ if (cursor->prepare != NULL) {
+ cursor->prepare();
+ }
+ }
+}
+
+void __bionic_atfork_run_child()
+{
+ struct atfork_t *cursor;
+
+ /* Call pthread_atfork() child handlers */
+ for (cursor = atfork_head.cqh_first;
+ cursor != (void*)&atfork_head;
+ cursor = cursor->entries.cqe_next) {
+ if (cursor->child != NULL) {
+ cursor->child();
+ }
+ }
+
+ pthread_mutex_unlock(&handler_mutex);
+}
+
+void __bionic_atfork_run_parent()
+{
+ struct atfork_t *cursor;
+
+ /* Call pthread_atfork() parent handlers */
+ for (cursor = atfork_head.cqh_first;
+ cursor != (void*)&atfork_head;
+ cursor = cursor->entries.cqe_next) {
+ if (cursor->parent != NULL) {
+ cursor->parent();
+ }
+ }
+
+ pthread_mutex_unlock(&handler_mutex);
+}
+
+int pthread_atfork(void (*prepare)(void), void (*parent)(void), void(*child)(void))
+{
+ struct atfork_t *entry = malloc(sizeof(struct atfork_t));
+
+ if (entry == NULL) {
+ return ENOMEM;
+ }
+
+ entry->prepare = prepare;
+ entry->parent = parent;
+ entry->child = child;
+
+ pthread_mutex_lock(&handler_mutex);
+ CIRCLEQ_INSERT_TAIL(&atfork_head, entry, entries);
+ pthread_mutex_unlock(&handler_mutex);
+
+ return 0;
+}
diff --git a/libc/bionic/pthread-timers.c b/libc/bionic/pthread-timers.c
index 7b9c99e..ae04029 100644
--- a/libc/bionic/pthread-timers.c
+++ b/libc/bionic/pthread-timers.c
@@ -260,7 +260,7 @@
** requirements: the timers of fork child processes must be
** disarmed but not deleted.
**/
-void
+__LIBC_HIDDEN__ void
__timer_table_start_stop( int stop )
{
if (__timer_table != NULL) {
diff --git a/libc/bionic/pthread.c b/libc/bionic/pthread.c
index b28cd9f..34909fb 100644
--- a/libc/bionic/pthread.c
+++ b/libc/bionic/pthread.c
@@ -196,6 +196,9 @@
// Wait for our creating thread to release us. This lets it have time to
// notify gdb about this thread before it starts doing anything.
+ //
+ // This also provides the memory barrier needed to ensure that all memory
+ // accesses previously made by the creating thread are visible to us.
pthread_mutex_t * start_mutex = (pthread_mutex_t *)&tls[TLS_SLOT_SELF];
pthread_mutex_lock(start_mutex);
pthread_mutex_destroy(start_mutex);
@@ -264,7 +267,7 @@
}
/*
- * Create a new thread. The thread's stack is layed out like so:
+ * Create a new thread. The thread's stack is laid out like so:
*
* +---------------------------+
* | pthread_internal_t |
@@ -334,6 +337,10 @@
// Create a mutex for the thread in TLS_SLOT_SELF to wait on once it starts so we can keep
// it from doing anything until after we notify the debugger about it
+ //
+ // This also provides the memory barrier we need to ensure that all
+ // memory accesses previously performed by this thread are visible to
+ // the new thread.
start_mutex = (pthread_mutex_t *) &tls[TLS_SLOT_SELF];
pthread_mutex_init(start_mutex, NULL);
pthread_mutex_lock(start_mutex);
@@ -1421,6 +1428,18 @@
break;
}
+ /*
+ * Ensure that all memory accesses previously made by this thread are
+ * visible to the woken thread(s). On the other side, the "wait"
+ * code will issue any necessary barriers when locking the mutex.
+ *
+ * This may not strictly be necessary -- if the caller follows
+ * recommended practice and holds the mutex before signaling the cond
+ * var, the mutex ops will provide correct semantics. If they don't
+ * hold the mutex, they're subject to race conditions anyway.
+ */
+ ANDROID_MEMBAR_FULL();
+
__futex_wake_ex(&cond->value, COND_IS_SHARED(cond), counter);
return 0;
}
@@ -1839,7 +1858,13 @@
*/
int ret, old_errno = errno;
- ret = __rt_sigprocmask(how, set, oset, _NSIG / 8);
+ /* Use NSIG which corresponds to the number of signals in
+ * our 32-bit sigset_t implementation. As such, this function, or
+ * anything that deals with sigset_t cannot manage real-time signals
+ * (signo >= 32). We might want to introduce sigset_rt_t as an
+ * extension to do so in the future.
+ */
+ ret = __rt_sigprocmask(how, set, oset, NSIG / 8);
if (ret < 0)
ret = errno;
@@ -1867,12 +1892,16 @@
int pthread_once( pthread_once_t* once_control, void (*init_routine)(void) )
{
static pthread_mutex_t once_lock = PTHREAD_RECURSIVE_MUTEX_INITIALIZER;
+ volatile pthread_once_t* ocptr = once_control;
- if (*once_control == PTHREAD_ONCE_INIT) {
+ pthread_once_t tmp = *ocptr;
+ ANDROID_MEMBAR_FULL();
+ if (tmp == PTHREAD_ONCE_INIT) {
pthread_mutex_lock( &once_lock );
- if (*once_control == PTHREAD_ONCE_INIT) {
+ if (*ocptr == PTHREAD_ONCE_INIT) {
(*init_routine)();
- *once_control = ~PTHREAD_ONCE_INIT;
+ ANDROID_MEMBAR_FULL();
+ *ocptr = ~PTHREAD_ONCE_INIT;
}
pthread_mutex_unlock( &once_lock );
}
diff --git a/libc/bionic/pthread_internal.h b/libc/bionic/pthread_internal.h
index eb4e80c..655b8f3 100644
--- a/libc/bionic/pthread_internal.h
+++ b/libc/bionic/pthread_internal.h
@@ -109,6 +109,9 @@
/* needed by fork.c */
extern void __timer_table_start_stop(int stop);
+extern void __bionic_atfork_run_prepare();
+extern void __bionic_atfork_run_child();
+extern void __bionic_atfork_run_parent();
__END_DECLS
diff --git a/libc/bionic/rand48.h b/libc/bionic/rand48.h
deleted file mode 100644
index 0a3d83d..0000000
--- a/libc/bionic/rand48.h
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * Copyright (c) 1993 Martin Birgmeier
- * All rights reserved.
- *
- * You may redistribute unmodified or modified versions of this source
- * code provided that the above copyright notice and this and the
- * following conditions are retained.
- *
- * This software is provided ``as is'', and comes with no warranties
- * of any kind. I shall in no event be liable for anything that happens
- * to anyone/anything when using this software.
- *
- * $FreeBSD: src/lib/libc/gen/rand48.h,v 1.2 2002/02/01 01:32:19 obrien Exp $
- */
-
-#ifndef _RAND48_H_
-#define _RAND48_H_
-
-#include <math.h>
-#include <stdlib.h>
-
-void _dorand48(unsigned short[3]);
-
-#define RAND48_SEED_0 (0x330e)
-#define RAND48_SEED_1 (0xabcd)
-#define RAND48_SEED_2 (0x1234)
-#define RAND48_MULT_0 (0xe66d)
-#define RAND48_MULT_1 (0xdeec)
-#define RAND48_MULT_2 (0x0005)
-#define RAND48_ADD (0x000b)
-
-#endif /* _RAND48_H_ */
diff --git a/libc/bionic/realpath.c b/libc/bionic/realpath.c
index 274a3a0..4cb847b 100644
--- a/libc/bionic/realpath.c
+++ b/libc/bionic/realpath.c
@@ -1,9 +1,6 @@
+/* $OpenBSD: realpath.c,v 1.13 2005/08/08 08:05:37 espie Exp $ */
/*
- * Copyright (c) 1994
- * The Regents of the University of California. All rights reserved.
- *
- * This code is derived from software contributed to Berkeley by
- * Jan-Simon Pendry.
+ * Copyright (c) 2003 Constantin S. Svintsoff <kostik@iclub.nsu.ru>
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
@@ -13,18 +10,14 @@
* 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. All advertising materials mentioning features or use of this software
- * must display the following acknowledgement:
- * This product includes software developed by the University of
- * California, Berkeley and its contributors.
- * 4. 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.
+ * 3. The names of the authors may not 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
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR 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
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR 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)
@@ -34,133 +27,164 @@
* SUCH DAMAGE.
*/
-#if defined(LIBC_SCCS) && !defined(lint)
-static char sccsid[] = "@(#)realpath.c 8.1 (Berkeley) 2/16/94";
-static char rcsid[] =
-"$FreeBSD: /repoman/r/ncvs/src/lib/libc/stdlib/realpath.c,v 1.6.2.1 2003/08/03 23:47:39 nectar Exp $";
-#endif /* LIBC_SCCS and not lint */
-
#include <sys/param.h>
#include <sys/stat.h>
#include <errno.h>
-#include <fcntl.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
/*
- * char *realpath(const char *path, char resolved_path[MAXPATHLEN]);
+ * char *realpath(const char *path, char resolved[PATH_MAX]);
*
* Find the real name of path, by removing all ".", ".." and symlink
* components. Returns (resolved) on success, or (NULL) on failure,
* in which case the path which caused trouble is left in (resolved).
*/
char *
-realpath(path, resolved)
- const char *path;
- char *resolved;
+realpath(const char *path, char resolved[PATH_MAX])
{
struct stat sb;
- int fd, n, rootd, serrno;
- char *p, *q, wbuf[MAXPATHLEN];
- int symlinks = 0;
+ char *p, *q, *s;
+ size_t left_len, resolved_len;
+ unsigned symlinks;
+ int serrno, slen;
+ char left[PATH_MAX], next_token[PATH_MAX], symlink[PATH_MAX];
- /* Save the starting point. */
- if ((fd = open(".", O_RDONLY)) < 0) {
- (void)strcpy(resolved, ".");
+ serrno = errno;
+ symlinks = 0;
+ if (path[0] == '/') {
+ resolved[0] = '/';
+ resolved[1] = '\0';
+ if (path[1] == '\0')
+ return (resolved);
+ resolved_len = 1;
+ left_len = strlcpy(left, path + 1, sizeof(left));
+ } else {
+ if (getcwd(resolved, PATH_MAX) == NULL) {
+ strlcpy(resolved, ".", PATH_MAX);
+ return (NULL);
+ }
+ resolved_len = strlen(resolved);
+ left_len = strlcpy(left, path, sizeof(left));
+ }
+ if (left_len >= sizeof(left) || resolved_len >= PATH_MAX) {
+ errno = ENAMETOOLONG;
return (NULL);
}
/*
- * Find the dirname and basename from the path to be resolved.
- * Change directory to the dirname component.
- * lstat the basename part.
- * if it is a symlink, read in the value and loop.
- * if it is a directory, then change to that directory.
- * get the current directory name and append the basename.
+ * Iterate over path components in `left'.
*/
- (void)strncpy(resolved, path, MAXPATHLEN - 1);
- resolved[MAXPATHLEN - 1] = '\0';
-loop:
- q = strrchr(resolved, '/');
- if (q != NULL) {
- p = q + 1;
- if (q == resolved)
- q = "/";
- else {
- do {
- --q;
- } while (q > resolved && *q == '/');
- q[1] = '\0';
- q = resolved;
- }
- if (chdir(q) < 0)
- goto err1;
- } else
- p = resolved;
-
- /* Deal with the last component. */
- if (*p != '\0' && lstat(p, &sb) == 0) {
- if (S_ISLNK(sb.st_mode)) {
- if (++symlinks > MAXSYMLINKS) {
- errno = ELOOP;
- goto err1;
- }
- n = readlink(p, resolved, MAXPATHLEN - 1);
- if (n < 0)
- goto err1;
- resolved[n] = '\0';
- goto loop;
- }
- if (S_ISDIR(sb.st_mode)) {
- if (chdir(p) < 0)
- goto err1;
- p = "";
- }
- }
-
- /*
- * Save the last component name and get the full pathname of
- * the current directory.
- */
- (void)strcpy(wbuf, p);
- if (getcwd(resolved, MAXPATHLEN) == 0)
- goto err1;
-
- /*
- * Join the two strings together, ensuring that the right thing
- * happens if the last component is empty, or the dirname is root.
- */
- if (resolved[0] == '/' && resolved[1] == '\0')
- rootd = 1;
- else
- rootd = 0;
-
- if (*wbuf) {
- if (strlen(resolved) + strlen(wbuf) + (1-rootd) + 1 >
- MAXPATHLEN) {
+ while (left_len != 0) {
+ /*
+ * Extract the next path component and adjust `left'
+ * and its length.
+ */
+ p = strchr(left, '/');
+ s = p ? p : left + left_len;
+ if (s - left >= sizeof(next_token)) {
errno = ENAMETOOLONG;
- goto err1;
+ return (NULL);
}
- if (rootd == 0)
- (void)strcat(resolved, "/");
- (void)strcat(resolved, wbuf);
+ memcpy(next_token, left, s - left);
+ next_token[s - left] = '\0';
+ left_len -= s - left;
+ if (p != NULL)
+ memmove(left, s + 1, left_len + 1);
+ if (resolved[resolved_len - 1] != '/') {
+ if (resolved_len + 1 >= PATH_MAX) {
+ errno = ENAMETOOLONG;
+ return (NULL);
+ }
+ resolved[resolved_len++] = '/';
+ resolved[resolved_len] = '\0';
+ }
+ if (next_token[0] == '\0')
+ continue;
+ else if (strcmp(next_token, ".") == 0)
+ continue;
+ else if (strcmp(next_token, "..") == 0) {
+ /*
+ * Strip the last path component except when we have
+ * single "/"
+ */
+ if (resolved_len > 1) {
+ resolved[resolved_len - 1] = '\0';
+ q = strrchr(resolved, '/') + 1;
+ *q = '\0';
+ resolved_len = q - resolved;
+ }
+ continue;
+ }
+
+ /*
+ * Append the next path component and lstat() it. If
+ * lstat() fails we still can return successfully if
+ * there are no more path components left.
+ */
+ resolved_len = strlcat(resolved, next_token, PATH_MAX);
+ if (resolved_len >= PATH_MAX) {
+ errno = ENAMETOOLONG;
+ return (NULL);
+ }
+ if (lstat(resolved, &sb) != 0) {
+ if (errno == ENOENT && p == NULL) {
+ errno = serrno;
+ return (resolved);
+ }
+ return (NULL);
+ }
+ if (S_ISLNK(sb.st_mode)) {
+ if (symlinks++ > MAXSYMLINKS) {
+ errno = ELOOP;
+ return (NULL);
+ }
+ slen = readlink(resolved, symlink, sizeof(symlink) - 1);
+ if (slen < 0)
+ return (NULL);
+ symlink[slen] = '\0';
+ if (symlink[0] == '/') {
+ resolved[1] = 0;
+ resolved_len = 1;
+ } else if (resolved_len > 1) {
+ /* Strip the last path component. */
+ resolved[resolved_len - 1] = '\0';
+ q = strrchr(resolved, '/') + 1;
+ *q = '\0';
+ resolved_len = q - resolved;
+ }
+
+ /*
+ * If there are any path components left, then
+ * append them to symlink. The result is placed
+ * in `left'.
+ */
+ if (p != NULL) {
+ if (symlink[slen - 1] != '/') {
+ if (slen + 1 >= sizeof(symlink)) {
+ errno = ENAMETOOLONG;
+ return (NULL);
+ }
+ symlink[slen] = '/';
+ symlink[slen + 1] = 0;
+ }
+ left_len = strlcat(symlink, left, sizeof(left));
+ if (left_len >= sizeof(left)) {
+ errno = ENAMETOOLONG;
+ return (NULL);
+ }
+ }
+ left_len = strlcpy(left, symlink, sizeof(left));
+ }
}
- /* Go back to where we came from. */
- if (fchdir(fd) < 0) {
- serrno = errno;
- goto err2;
- }
-
- /* It's okay if the close fails, what's an fd more or less? */
- (void)close(fd);
+ /*
+ * Remove trailing slash except when the resolved pathname
+ * is a single "/".
+ */
+ if (resolved_len > 1 && resolved[resolved_len - 1] == '/')
+ resolved[resolved_len - 1] = '\0';
return (resolved);
-
-err1: serrno = errno;
- (void)fchdir(fd);
-err2: (void)close(fd);
- errno = serrno;
- return (NULL);
}
diff --git a/libc/bionic/sched_cpualloc.c b/libc/bionic/sched_cpualloc.c
new file mode 100644
index 0000000..30964bc
--- /dev/null
+++ b/libc/bionic/sched_cpualloc.c
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2010 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.
+ */
+#define _GNU_SOURCE 1
+#include <sched.h>
+#include <stdlib.h>
+
+cpu_set_t* __sched_cpualloc(size_t count)
+{
+ return (cpu_set_t*) malloc(CPU_ALLOC_SIZE(count));
+}
+
+void __sched_cpufree(cpu_set_t* set)
+{
+ free(set);
+}
diff --git a/libc/bionic/sched_cpucount.c b/libc/bionic/sched_cpucount.c
new file mode 100644
index 0000000..9458dc8
--- /dev/null
+++ b/libc/bionic/sched_cpucount.c
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2010 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.
+ */
+#define _GNU_SOURCE 1
+#include <sched.h>
+
+int __sched_cpucount(size_t setsize, cpu_set_t* set)
+{
+ int nn = 0, nn_max = setsize / sizeof(__CPU_BITTYPE);
+ int count = 0;
+
+ for ( ; nn < nn_max; nn++ )
+ count += __builtin_popcount(set->__bits[nn]);
+
+ return count;
+}
diff --git a/libc/bionic/sched_getaffinity.c b/libc/bionic/sched_getaffinity.c
new file mode 100644
index 0000000..7313822
--- /dev/null
+++ b/libc/bionic/sched_getaffinity.c
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2010 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.
+ */
+#define _GNU_SOURCE 1
+#include <sched.h>
+
+int sched_getaffinity(pid_t pid, size_t setsize, cpu_set_t* set)
+{
+ int ret = __sched_getaffinity(pid, setsize, set);
+ if (ret >= 0) {
+ if ((size_t)ret < setsize) {
+ memset((char*)set + ret, '\0', setsize - (size_t)ret);
+ }
+ ret = 0;
+ }
+ return ret;
+}
diff --git a/libc/bionic/sched_getcpu.c b/libc/bionic/sched_getcpu.c
new file mode 100644
index 0000000..954df37
--- /dev/null
+++ b/libc/bionic/sched_getcpu.c
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2010 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.
+ */
+#define _GNU_SOURCE 1
+#include <sched.h>
+
+extern int __getcpu(unsigned *cpu, unsigned *node, void* unused);
+
+int sched_getcpu(void)
+{
+ unsigned cpu;
+ if (__getcpu(&cpu, NULL, NULL) < 0)
+ return 0;
+
+ return (int)cpu;
+}
diff --git a/libc/bionic/stubs.c b/libc/bionic/stubs.c
index d495674..a01d64c 100644
--- a/libc/bionic/stubs.c
+++ b/libc/bionic/stubs.c
@@ -40,8 +40,8 @@
/** Thread-specific state for the stubs functions
**/
-pthread_once_t the_once = PTHREAD_ONCE_INIT;
-pthread_key_t the_key;
+static pthread_once_t the_once = PTHREAD_ONCE_INIT;
+static pthread_key_t the_key;
typedef struct {
struct passwd passwd;
diff --git a/libc/bionic/time64.c b/libc/bionic/time64.c
index 1e1f881..9aa5d4f 100644
--- a/libc/bionic/time64.c
+++ b/libc/bionic/time64.c
@@ -364,7 +364,7 @@
}
-void copy_tm_to_TM(const struct tm *src, struct TM *dest) {
+static void copy_tm_to_TM(const struct tm *src, struct TM *dest) {
if( src == NULL ) {
memset(dest, 0, sizeof(*dest));
}
@@ -396,7 +396,7 @@
}
-void copy_TM_to_tm(const struct TM *src, struct tm *dest) {
+static void copy_TM_to_tm(const struct TM *src, struct tm *dest) {
if( src == NULL ) {
memset(dest, 0, sizeof(*dest));
}
@@ -735,14 +735,14 @@
}
-int valid_tm_wday( const struct TM* date ) {
+static int valid_tm_wday( const struct TM* date ) {
if( 0 <= date->tm_wday && date->tm_wday <= 6 )
return 1;
else
return 0;
}
-int valid_tm_mon( const struct TM* date ) {
+static int valid_tm_mon( const struct TM* date ) {
if( 0 <= date->tm_mon && date->tm_mon <= 11 )
return 1;
else
diff --git a/libc/bionic/time64_config.h b/libc/bionic/time64_config.h
index 53bcecf..1385045 100644
--- a/libc/bionic/time64_config.h
+++ b/libc/bionic/time64_config.h
@@ -33,7 +33,7 @@
*/
#define HAS_GMTIME_R
#define HAS_LOCALTIME_R
-/*#define HAS_TIMEGM */
+#define HAS_TIMEGM
/* Details of non-standard tm struct elements.
diff --git a/libc/docs/CHANGES.TXT b/libc/docs/CHANGES.TXT
index 4d094d0..98b7fcf 100644
--- a/libc/docs/CHANGES.TXT
+++ b/libc/docs/CHANGES.TXT
@@ -1,7 +1,26 @@
Bionic ChangeLog:
-----------------
-Differences between current and Android 2.2:
+Differences between current and Android 2.3:
+
+- <android/api-level.h>: Added new header to define __ANDROID_API__ to
+ a constant integer corresponding to the native API level. This header
+ also exists in the NDK's platform headers.
+
+- <sys/cdefs.h>: Include <android/api-level.h>
+
+- <time.h>: Add timegm(), timelocal(), time2posix() and posix2time()
+
+- <sched.h>: Add sched_getcpu(), sched_getaffinity(), sched_setaffinity(),
+ cpu_set_t and related macros (e.g. CPU_SETSIZE, CPU_ZERO, CPU_SET, ...)
+
+- <unistd.h>: Add ftruncate64().
+
+- <signal.h>: Changed the definition of SIGRTMAX to 64. However, note that
+ sigset_t is only 32-bit and cannot deal with real-time signals.
+
+-------------------------------------------------------------------------------
+Differences between Android 2.3 and Android 2.2:
- <pthread.h>: Add reader/writer locks implementation. Add sanity
checking to pthread_mutex_destroy() (e.g. a locked mutex will return
@@ -70,6 +89,8 @@
- <sys/vfs.h>: fixed implementation of fstatfs() (also fixes fpathconf()
which uses it).
+- Added an implementation of pthread_atfork()
+
- <dlfcn.h>: fixed dlopen() implementation to support dlopen(NULL, ...).
This allows one to look at the dynamic symbols exported by an executable.
diff --git a/libc/include/android/api-level.h b/libc/include/android/api-level.h
new file mode 100644
index 0000000..611fdfb
--- /dev/null
+++ b/libc/include/android/api-level.h
@@ -0,0 +1,33 @@
+/*
+ * 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.
+ */
+#ifndef ANDROID_API_LEVEL_H
+#define ANDROID_API_LEVEL_H
+
+#define __ANDROID_API__ 10
+
+#endif /* ANDROID_API_LEVEL_H */
diff --git a/libc/include/byteswap.h b/libc/include/byteswap.h
index 16d2ad4..74b0e91 100644
--- a/libc/include/byteswap.h
+++ b/libc/include/byteswap.h
@@ -28,7 +28,8 @@
#ifndef _BYTESWAP_H_
#define _BYTESWAP_H_
-#include <sys/endian.h>
+/* endian.h rather than sys/endian.h so we get the machine-specific file. */
+#include <endian.h>
#define bswap_16(x) swap16(x)
#define bswap_32(x) swap32(x)
diff --git a/libc/include/net/if_ether.h b/libc/include/net/if_ether.h
index 121f9ac..8daa16b 100644
--- a/libc/include/net/if_ether.h
+++ b/libc/include/net/if_ether.h
@@ -34,6 +34,8 @@
#ifndef _NET_IF_ETHER_H_
#define _NET_IF_ETHER_H_
+#include <sys/types.h>
+
#ifdef _KERNEL
#ifdef _KERNEL_OPT
#include "opt_mbuftrace.h"
diff --git a/libc/include/netinet/in.h b/libc/include/netinet/in.h
index 0ebd926..7a4b6c7 100644
--- a/libc/include/netinet/in.h
+++ b/libc/include/netinet/in.h
@@ -38,6 +38,8 @@
#define IPPORT_RESERVED 1024
+#define INET_ADDRSTRLEN 16
+
extern int bindresvport (int sd, struct sockaddr_in *sin);
static const struct in6_addr in6addr_any = IN6ADDR_ANY_INIT;
diff --git a/libc/include/netinet/in6.h b/libc/include/netinet/in6.h
index efd5c0a..580a510 100644
--- a/libc/include/netinet/in6.h
+++ b/libc/include/netinet/in6.h
@@ -78,6 +78,9 @@
#define IPV6_ADDR_MC_SCOPE(a) \
((a)->s6_addr[1] & 0x0f)
+#define IN6_IS_ADDR_MC_NODELOCAL(a) \
+ (IN6_IS_ADDR_MULTICAST(a) && \
+ (IPV6_ADDR_MC_SCOPE(a) == IPV6_ADDR_SCOPE_NODELOCAL))
#define IN6_IS_ADDR_MC_LINKLOCAL(a) \
(IN6_IS_ADDR_MULTICAST(a) && \
(IPV6_ADDR_MC_SCOPE(a) == IPV6_ADDR_SCOPE_LINKLOCAL))
@@ -87,7 +90,9 @@
#define IN6_IS_ADDR_MC_ORGLOCAL(a) \
(IN6_IS_ADDR_MULTICAST(a) && \
(IPV6_ADDR_MC_SCOPE(a) == IPV6_ADDR_SCOPE_ORGLOCAL))
-
+#define IN6_IS_ADDR_MC_GLOBAL(a) \
+ (IN6_IS_ADDR_MULTICAST(a) && \
+ (IPV6_ADDR_MC_SCOPE(a) == IPV6_ADDR_SCOPE_GLOBAL))
#define IN6_ARE_ADDR_EQUAL(a, b) \
(memcmp(&(a)->s6_addr[0], &(b)->s6_addr[0], sizeof(struct in6_addr)) == 0)
diff --git a/libc/include/pthread.h b/libc/include/pthread.h
index 99e747a..a43e47c 100644
--- a/libc/include/pthread.h
+++ b/libc/include/pthread.h
@@ -268,6 +268,8 @@
int pthread_setname_np(pthread_t thid, const char *thname);
+int pthread_atfork(void (*prepare)(void), void (*parent)(void), void(*child)(void));
+
typedef void (*__pthread_cleanup_func_t)(void*);
typedef struct __pthread_cleanup_t {
diff --git a/libc/include/sched.h b/libc/include/sched.h
index e702470..ca72da7 100644
--- a/libc/include/sched.h
+++ b/libc/include/sched.h
@@ -73,6 +73,162 @@
extern int clone(int (*fn)(void *), void *child_stack, int flags, void* arg, ...);
#endif
+/* Support for cpu thread affinity */
+#ifdef _GNU_SOURCE
+
+extern int sched_getcpu(void);
+
+
+/* Our implementation supports up to 32 independent CPUs, which is also
+ * the maximum supported by the kernel at the moment. GLibc uses 1024 by
+ * default.
+ *
+ * If you want to use more than that, you should use CPU_ALLOC() / CPU_FREE()
+ * and the CPU_XXX_S() macro variants.
+ */
+#define CPU_SETSIZE 32
+
+#define __CPU_BITTYPE unsigned long int /* mandated by the kernel */
+#define __CPU_BITSHIFT 5 /* should be log2(BITTYPE) */
+#define __CPU_BITS (1 << __CPU_BITSHIFT)
+#define __CPU_ELT(x) ((x) >> __CPU_BITSHIFT)
+#define __CPU_MASK(x) ((__CPU_BITTYPE)1 << ((x) & (__CPU_BITS-1)))
+
+typedef struct {
+ __CPU_BITTYPE __bits[ CPU_SETSIZE / __CPU_BITS ];
+} cpu_set_t;
+
+extern int sched_setaffinity(pid_t pid, size_t setsize, const cpu_set_t* set);
+
+extern int sched_getaffinity(pid_t pid, size_t setsize, cpu_set_t* set);
+
+/* Provide optimized implementation for 32-bit cpu_set_t */
+#if CPU_SETSIZE == __CPU_BITS
+
+# define CPU_ZERO(set_) \
+ do{ \
+ (set_)->__bits[0] = 0; \
+ }while(0)
+
+# define CPU_SET(cpu_,set_) \
+ do {\
+ size_t __cpu = (cpu_); \
+ if (__cpu < CPU_SETSIZE) \
+ (set_)->__bits[0] |= __CPU_MASK(__cpu); \
+ }while (0)
+
+# define CPU_CLR(cpu_,set_) \
+ do {\
+ size_t __cpu = (cpu_); \
+ if (__cpu < CPU_SETSIZE) \
+ (set_)->__bits[0] &= ~__CPU_MASK(__cpu); \
+ }while (0)
+
+# define CPU_ISSET(cpu_, set_) \
+ (__extension__({\
+ size_t __cpu = (cpu_); \
+ (cpu_ < CPU_SETSIZE) \
+ ? ((set_)->__bits[0] & __CPU_MASK(__cpu)) != 0 \
+ : 0; \
+ }))
+
+# define CPU_EQUAL(set1_, set2_) \
+ ((set1_)->__bits[0] == (set2_)->__bits[0])
+
+# define __CPU_OP(dst_, set1_, set2_, op_) \
+ do { \
+ (dst_)->__bits[0] = (set1_)->__bits[0] op_ (set2_)->__bits[0]; \
+ } while (0)
+
+# define CPU_COUNT(set_) __builtin_popcountl((set_)->__bits[0])
+
+#else /* CPU_SETSIZE != __CPU_BITS */
+
+# define CPU_ZERO(set_) CPU_ZERO_S(sizeof(cpu_set_t), set_)
+# define CPU_SET(cpu_,set_) CPU_SET_S(cpu_,sizeof(cpu_set_t),set_)
+# define CPU_CLR(cpu_,set_) CPU_CLR_S(cpu_,sizeof(cpu_set_t),set_)
+# define CPU_ISSET(cpu_,set_) CPU_ISSET_S(cpu_,sizeof(cpu_set_t),set_)
+# define CPU_COUNT(set_) CPU_COUNT_S(sizeof(cpu_set_t),set_)
+# define CPU_EQUAL(set1_,set2_) CPU_EQUAL_S(sizeof(cpu_set_t),set1_,set2_)
+
+# define __CPU_OP(dst_,set1_,set2_,op_) __CPU_OP_S(sizeof(cpu_set_t),dst_,set1_,set2_,op_)
+
+#endif /* CPU_SETSIZE != __CPU_BITS */
+
+#define CPU_AND(set1_,set2_) __CPU_OP(set1_,set2_,&)
+#define CPU_OR(set1_,set2_) __CPU_OP(set1_,set2_,|)
+#define CPU_XOR(set1_,set2_) __CPU_OP(set1_,set2_,^)
+
+/* Support for dynamically-allocated cpu_set_t */
+
+#define CPU_ALLOC_SIZE(count) \
+ __CPU_ELT((count) + (__CPU_BITS-1))*sizeof(__CPU_BITTYPE)
+
+#define CPU_ALLOC(count) __sched_cpualloc((count));
+#define CPU_FREE(set) __sched_cpufree((set))
+
+extern cpu_set_t* __sched_cpualloc(size_t count);
+extern void __sched_cpufree(cpu_set_t* set);
+
+#define CPU_ZERO_S(setsize_,set_) \
+ do { \
+ size_t __nn = 0; \
+ size_t __nn_max = (setsize_)/sizeof(__CPU_BITTYPE); \
+ for (; __nn < __nn_max; __nn++) \
+ (set_)->__bits[__nn] = 0; \
+ } while (0)
+
+#define CPU_SET_S(cpu_,setsize_,set_) \
+ do { \
+ size_t __cpu = (cpu_); \
+ if (__cpu < 8*(setsize_)) \
+ (set_)->__bits[__CPU_ELT(__cpu)] |= __CPU_MASK(__cpu); \
+ } while (0)
+
+#define CPU_CLR_S(cpu_,setsize_,set_) \
+ do { \
+ size_t __cpu = (cpu_); \
+ if (__cpu < 8*(setsize_)) \
+ (set_)->__bits[__CPU_ELT(__cpu)] &= ~__CPU_MASK(__cpu); \
+ } while (0)
+
+#define CPU_ISSET_S(cpu_, setsize_, set_) \
+ (__extension__ ({ \
+ size_t __cpu = (cpu_); \
+ (__cpu < 8*(setsize_)) \
+ ? ((set_)->__bits[__CPU_ELT(__cpu)] & __CPU_MASK(__cpu)) != 0 \
+ : 0; \
+ }))
+
+#define CPU_EQUAL_S(setsize_, set1_, set2_) \
+ (__extension__ ({ \
+ __const __CPU_BITTYPE* __src1 = (set1_)->__bits; \
+ __const __CPU_BITTYPE* __src2 = (set2_)->__bits; \
+ size_t __nn = 0, __nn_max = (setsize_)/sizeof(__CPU_BITTYPE); \
+ for (; __nn < __nn_max; __nn++) { \
+ if (__src1[__nn] != __src2[__nn]) \
+ break; \
+ } \
+ __nn == __nn_max; \
+ }))
+
+#define __CPU_OP_S(setsize_, dstset_, srcset1_, srcset2_, op) \
+ do { \
+ cpu_set_t* __dst = (dstset); \
+ const __CPU_BITTYPE* __src1 = (srcset1)->__bits; \
+ const __CPU_BITTYPE* __src2 = (srcset2)->__bits; \
+ size_t __nn = 0, __nn_max = (setsize_)/sizeof(__CPU_BITTYPE); \
+ for (; __nn < __nn_max; __nn++) \
+ (__dst)->__bits[__nn] = __src1[__nn] op __src2[__nn]; \
+ } while (0)
+
+#define CPU_COUNT_S(setsize_, set_) \
+ __sched_cpucount((setsize_), (set_))
+
+extern int __sched_cpucount(size_t setsize, cpu_set_t* set);
+
+#endif /* _GNU_SOURCE */
+
__END_DECLS
#endif /* _SCHED_H_ */
diff --git a/libc/include/signal.h b/libc/include/signal.h
index 4401164..91c3b00 100644
--- a/libc/include/signal.h
+++ b/libc/include/signal.h
@@ -42,12 +42,15 @@
typedef int sig_atomic_t;
-/* crepy NIG / _NSIG handling, just to be safe */
-#ifndef NSIG
-# define NSIG _NSIG
-#endif
+/* _NSIG is used by the SIGRTMAX definition under <asm/signal.h>, however
+ * its definition is part of a #if __KERNEL__ .. #endif block in the original
+ * kernel headers and is thus not part of our cleaned-up versions.
+ *
+ * Looking at the current kernel sources, it is defined as 64 for all
+ * architectures except for the 'mips' one which set it to 128.
+ */
#ifndef _NSIG
-# define _NSIG NSIG
+# define _NSIG 64
#endif
extern const char * const sys_siglist[];
diff --git a/libc/include/stdlib.h b/libc/include/stdlib.h
index 97d8e46..5dc8a87 100644
--- a/libc/include/stdlib.h
+++ b/libc/include/stdlib.h
@@ -57,6 +57,7 @@
extern int unsetenv(const char *);
extern int clearenv(void);
+extern char *mkdtemp(char *);
extern char *mktemp (char *);
extern int mkstemp (char *);
diff --git a/libc/include/sys/cdefs.h b/libc/include/sys/cdefs.h
index 849e2b8..9b6da31 100644
--- a/libc/include/sys/cdefs.h
+++ b/libc/include/sys/cdefs.h
@@ -497,5 +497,6 @@
#endif
#define __BIONIC__ 1
+#include <android/api-level.h>
#endif /* !_SYS_CDEFS_H_ */
diff --git a/libc/include/sys/cdefs_elf.h b/libc/include/sys/cdefs_elf.h
index e051b1d..1e57470 100644
--- a/libc/include/sys/cdefs_elf.h
+++ b/libc/include/sys/cdefs_elf.h
@@ -95,6 +95,10 @@
__asm__(".section _sec\n\t.asciz _str\n\t.previous")
#endif
+/* GCC visibility helper macro */
+#define __LIBC_HIDDEN__ \
+ __attribute__ ((visibility ("hidden")))
+
#define __IDSTRING(_n,_s) __SECTIONSTRING(.ident,_s)
#define __RCSID(_s) __IDSTRING(rcsid,_s)
diff --git a/libc/include/sys/linux-syscalls.h b/libc/include/sys/linux-syscalls.h
index 9702a7a..cb4d5e5 100644
--- a/libc/include/sys/linux-syscalls.h
+++ b/libc/include/sys/linux-syscalls.h
@@ -71,6 +71,7 @@
#define __NR_dup2 (__NR_SYSCALL_BASE + 63)
#define __NR__newselect (__NR_SYSCALL_BASE + 142)
#define __NR_ftruncate (__NR_SYSCALL_BASE + 93)
+#define __NR_ftruncate64 (__NR_SYSCALL_BASE + 194)
#define __NR_fsync (__NR_SYSCALL_BASE + 118)
#define __NR_fdatasync (__NR_SYSCALL_BASE + 148)
#define __NR_fchown32 (__NR_SYSCALL_BASE + 207)
@@ -120,6 +121,8 @@
#define __NR_sched_get_priority_max (__NR_SYSCALL_BASE + 159)
#define __NR_sched_get_priority_min (__NR_SYSCALL_BASE + 160)
#define __NR_sched_rr_get_interval (__NR_SYSCALL_BASE + 161)
+#define __NR_sched_setaffinity (__NR_SYSCALL_BASE + 241)
+#define __NR_sched_getaffinity (__NR_SYSCALL_BASE + 242)
#define __NR_uname (__NR_SYSCALL_BASE + 122)
#define __NR_wait4 (__NR_SYSCALL_BASE + 114)
#define __NR_umask (__NR_SYSCALL_BASE + 60)
@@ -174,6 +177,7 @@
#define __NR_getsockopt (__NR_SYSCALL_BASE + 295)
#define __NR_sendmsg (__NR_SYSCALL_BASE + 296)
#define __NR_recvmsg (__NR_SYSCALL_BASE + 297)
+#define __NR_getcpu (__NR_SYSCALL_BASE + 345)
#define __NR_ioprio_set (__NR_SYSCALL_BASE + 314)
#define __NR_ioprio_get (__NR_SYSCALL_BASE + 315)
#define __NR_epoll_create (__NR_SYSCALL_BASE + 250)
@@ -218,6 +222,7 @@
#define __NR_timer_delete (__NR_SYSCALL_BASE + 263)
#define __NR_utimes (__NR_SYSCALL_BASE + 271)
#define __NR_socketcall (__NR_SYSCALL_BASE + 102)
+#define __NR_getcpu (__NR_SYSCALL_BASE + 318)
#define __NR_ioprio_set (__NR_SYSCALL_BASE + 289)
#define __NR_ioprio_get (__NR_SYSCALL_BASE + 290)
#define __NR_epoll_create (__NR_SYSCALL_BASE + 254)
@@ -276,6 +281,7 @@
#define __NR_socketcall (__NR_SYSCALL_BASE + 102)
#define __NR_socketcall (__NR_SYSCALL_BASE + 102)
#define __NR___socketcall (__NR_SYSCALL_BASE + 102)
+#define __NR_getcpu (__NR_SYSCALL_BASE + 318)
#define __NR_ioprio_set (__NR_SYSCALL_BASE + 288)
#define __NR_ioprio_get (__NR_SYSCALL_BASE + 289)
#define __NR_epoll_create (__NR_SYSCALL_BASE + 254)
diff --git a/libc/include/sys/linux-unistd.h b/libc/include/sys/linux-unistd.h
index 23853da..f706d00 100644
--- a/libc/include/sys/linux-unistd.h
+++ b/libc/include/sys/linux-unistd.h
@@ -52,8 +52,8 @@
int acct (const char* filepath);
ssize_t read (int, void*, size_t);
ssize_t write (int, const void*, size_t);
-ssize_t __pread64 (int, void *, size_t, off_t, off_t);
-ssize_t __pwrite64 (int, void *, size_t, off_t, off_t);
+ssize_t pread64 (int, void *, size_t, off64_t);
+ssize_t pwrite64 (int, void *, size_t, off64_t);
int __open (const char*, int, mode_t);
int __openat (int, const char*, int, mode_t);
int close (int);
@@ -83,6 +83,7 @@
int dup2 (int, int);
int select (int, struct fd_set *, struct fd_set *, struct fd_set *, struct timeval *);
int ftruncate (int, off_t);
+int ftruncate64 (int, off64_t);
int getdents (unsigned int, struct dirent *, unsigned int);
int fsync (int);
int fdatasync (int);
@@ -183,6 +184,9 @@
int sched_get_priority_max (int policy);
int sched_get_priority_min (int policy);
int sched_rr_get_interval (pid_t pid, struct timespec *interval);
+int sched_setaffinity (pid_t pid, size_t setsize, const cpu_set_t* set);
+int __sched_getaffinity (pid_t pid, size_t setsize, cpu_set_t* set);
+int __getcpu (unsigned *cpu, unsigned *node, void *unused);
int ioprio_set (int which, int who, int ioprio);
int ioprio_get (int which, int who);
int uname (struct utsname *);
diff --git a/libc/include/time.h b/libc/include/time.h
index 5d1a0e2..4ad4f7b 100644
--- a/libc/include/time.h
+++ b/libc/include/time.h
@@ -128,6 +128,11 @@
extern int timer_gettime(timer_t timerid, struct itimerspec *value);
extern int timer_getoverrun(timer_t timerid);
+extern time_t timelocal(struct tm *tm);
+extern time_t timegm(struct tm* tm);
+extern time_t time2posix(time_t ti);
+extern time_t posix2time(time_t ti);
+
__END_DECLS
#endif /* _TIME_H_ */
diff --git a/libc/include/unistd.h b/libc/include/unistd.h
index 29154a2..4534fb9 100644
--- a/libc/include/unistd.h
+++ b/libc/include/unistd.h
@@ -128,12 +128,14 @@
extern int close(int);
extern off_t lseek(int, off_t, int);
-extern loff_t lseek64(int, loff_t, int);
+extern off64_t lseek64(int, off64_t, int);
extern ssize_t read(int, void *, size_t);
extern ssize_t write(int, const void *, size_t);
extern ssize_t pread(int, void *, size_t, off_t);
-extern ssize_t pwrite(int, void *, size_t, off_t);
+extern ssize_t pread64(int, void *, size_t, off64_t);
+extern ssize_t pwrite(int, const void *, size_t, off_t);
+extern ssize_t pwrite64(int, const void *, size_t, off64_t);
extern int dup(int);
extern int dup2(int, int);
@@ -143,6 +145,7 @@
extern int fsync(int);
extern int fdatasync(int);
extern int ftruncate(int, off_t);
+extern int ftruncate64(int, off64_t);
extern int pause(void);
extern unsigned int alarm(unsigned int);
diff --git a/libc/include/wchar.h b/libc/include/wchar.h
index 9b744a5..1361ff5 100644
--- a/libc/include/wchar.h
+++ b/libc/include/wchar.h
@@ -112,6 +112,7 @@
extern int vwprintf(const wchar_t *, va_list);
extern int vswprintf(wchar_t *, size_t, const wchar_t *, va_list);
extern size_t wcrtomb(char *, wchar_t, mbstate_t *);
+extern int wcscasecmp(const wchar_t *, const wchar_t *);
extern wchar_t *wcscat(wchar_t *, const wchar_t *);
extern wchar_t *wcschr(const wchar_t *, wchar_t);
extern int wcscmp(const wchar_t *, const wchar_t *);
@@ -120,6 +121,7 @@
extern size_t wcscspn(const wchar_t *, const wchar_t *);
extern size_t wcsftime(wchar_t *, size_t, const wchar_t *, const struct tm *);
extern size_t wcslen(const wchar_t *);
+extern int wcsncasecmp(const wchar_t *, const wchar_t *, size_t);
extern wchar_t *wcsncat(wchar_t *, const wchar_t *, size_t);
extern int wcsncmp(const wchar_t *, const wchar_t *, size_t);
extern wchar_t *wcsncpy(wchar_t *, const wchar_t *, size_t);
diff --git a/libc/inet/ether_aton.c b/libc/inet/ether_aton.c
new file mode 100644
index 0000000..6540c07
--- /dev/null
+++ b/libc/inet/ether_aton.c
@@ -0,0 +1,89 @@
+/*
+ * Copyright (C) 2010 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 <stdio.h>
+#include <stdlib.h>
+#include <sys/types.h>
+#include <net/if_ether.h>
+#include <ctype.h>
+
+static inline int
+xdigit (char c) {
+ unsigned d;
+ d = (unsigned)(c-'0');
+ if (d < 10) return (int)d;
+ d = (unsigned)(c-'a');
+ if (d < 6) return (int)(10+d);
+ d = (unsigned)(c-'A');
+ if (d < 6) return (int)(10+d);
+ return -1;
+}
+
+/*
+ * Convert Ethernet address in the standard hex-digits-and-colons to binary
+ * representation.
+ * Re-entrant version (GNU extensions)
+ */
+struct ether_addr *
+ether_aton_r (const char *asc, struct ether_addr * addr)
+{
+ int i, val0, val1;
+ for (i = 0; i < ETHER_ADDR_LEN; ++i) {
+ val0 = xdigit(*asc);
+ asc++;
+ if (val0 < 0)
+ return NULL;
+
+ val1 = xdigit(*asc);
+ asc++;
+ if (val1 < 0)
+ return NULL;
+
+ addr->ether_addr_octet[i] = (u_int8_t)((val0 << 4) + val1);
+
+ if (i < ETHER_ADDR_LEN - 1) {
+ if (*asc != ':')
+ return NULL;
+ asc++;
+ }
+ }
+ if (*asc != '\0')
+ return NULL;
+ return addr;
+}
+
+/*
+ * Convert Ethernet address in the standard hex-digits-and-colons to binary
+ * representation.
+ */
+struct ether_addr *
+ether_aton (const char *asc)
+{
+ static struct ether_addr addr;
+ return ether_aton_r(asc, &addr);
+}
diff --git a/libc/inet/ether_ntoa.c b/libc/inet/ether_ntoa.c
new file mode 100644
index 0000000..f56e48b
--- /dev/null
+++ b/libc/inet/ether_ntoa.c
@@ -0,0 +1,55 @@
+/*
+ * Copyright (C) 2010 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 <stdio.h>
+#include <sys/types.h>
+#include <net/if_ether.h>
+
+/*
+ * Convert Ethernet address to standard hex-digits-and-colons printable form.
+ * Re-entrant version (GNU extensions).
+ */
+char *
+ether_ntoa_r (const struct ether_addr *addr, char * buf)
+{
+ snprintf(buf, 18, "%02x:%02x:%02x:%02x:%02x:%02x",
+ addr->ether_addr_octet[0], addr->ether_addr_octet[1],
+ addr->ether_addr_octet[2], addr->ether_addr_octet[3],
+ addr->ether_addr_octet[4], addr->ether_addr_octet[5]);
+ return buf;
+}
+
+/*
+ * Convert Ethernet address to standard hex-digits-and-colons printable form.
+ */
+char *
+ether_ntoa (const struct ether_addr *addr)
+{
+ static char buf[18];
+ return ether_ntoa_r(addr, buf);
+}
diff --git a/libc/kernel/arch-arm/asm/byteorder.h b/libc/kernel/arch-arm/asm/byteorder.h
index 4da37bf..b869695 100644
--- a/libc/kernel/arch-arm/asm/byteorder.h
+++ b/libc/kernel/arch-arm/asm/byteorder.h
@@ -22,7 +22,7 @@
#ifndef __thumb__
if (!__builtin_constant_p(x)) {
- asm ("eor\t%0, %1, %1, ror #16" : "=r" (t) : "r" (x));
+ __asm__ ("eor\t%0, %1, %1, ror #16" : "=r" (t) : "r" (x));
} else
#endif
t = x ^ ((x << 16) | (x >> 16));
diff --git a/libc/kernel/arch-arm/asm/ptrace.h b/libc/kernel/arch-arm/asm/ptrace.h
index b6be08c..3faf738 100644
--- a/libc/kernel/arch-arm/asm/ptrace.h
+++ b/libc/kernel/arch-arm/asm/ptrace.h
@@ -30,6 +30,7 @@
#define PTRACE_SETCRUNCHREGS 26
#define PTRACE_GETVFPREGS 27
+#define PTRACE_SETVFPREGS 28
#define USR26_MODE 0x00000000
#define FIQ26_MODE 0x00000001
diff --git a/libc/kernel/common/linux/akm8975.h b/libc/kernel/common/linux/akm8975.h
new file mode 100644
index 0000000..1815f75
--- /dev/null
+++ b/libc/kernel/common/linux/akm8975.h
@@ -0,0 +1,72 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef AKM8975_H
+#define AKM8975_H
+
+#include <linux/ioctl.h>
+
+#define AK8975_MODE_SNG_MEASURE 0x01
+#define AK8975_MODE_SELF_TEST 0x08
+#define AK8975_MODE_FUSE_ACCESS 0x0F
+#define AK8975_MODE_POWER_DOWN 0x00
+
+#define RBUFF_SIZE 8
+
+#define AK8975_REG_WIA 0x00
+#define AK8975_REG_INFO 0x01
+#define AK8975_REG_ST1 0x02
+#define AK8975_REG_HXL 0x03
+#define AK8975_REG_HXH 0x04
+#define AK8975_REG_HYL 0x05
+#define AK8975_REG_HYH 0x06
+#define AK8975_REG_HZL 0x07
+#define AK8975_REG_HZH 0x08
+#define AK8975_REG_ST2 0x09
+#define AK8975_REG_CNTL 0x0A
+#define AK8975_REG_RSV 0x0B
+#define AK8975_REG_ASTC 0x0C
+#define AK8975_REG_TS1 0x0D
+#define AK8975_REG_TS2 0x0E
+#define AK8975_REG_I2CDIS 0x0F
+
+#define AK8975_FUSE_ASAX 0x10
+#define AK8975_FUSE_ASAY 0x11
+#define AK8975_FUSE_ASAZ 0x12
+
+#define AKMIO 0xA1
+
+#define ECS_IOCTL_WRITE _IOW(AKMIO, 0x02, char[5])
+#define ECS_IOCTL_READ _IOWR(AKMIO, 0x03, char[5])
+#define ECS_IOCTL_GETDATA _IOR(AKMIO, 0x08, char[RBUFF_SIZE])
+#define ECS_IOCTL_SET_YPR _IOW(AKMIO, 0x0C, short[12])
+#define ECS_IOCTL_GET_OPEN_STATUS _IOR(AKMIO, 0x0D, int)
+#define ECS_IOCTL_GET_CLOSE_STATUS _IOR(AKMIO, 0x0E, int)
+#define ECS_IOCTL_GET_DELAY _IOR(AKMIO, 0x30, short)
+
+#define ECS_IOCTL_APP_SET_MFLAG _IOW(AKMIO, 0x11, short)
+#define ECS_IOCTL_APP_GET_MFLAG _IOW(AKMIO, 0x12, short)
+#define ECS_IOCTL_APP_SET_AFLAG _IOW(AKMIO, 0x13, short)
+#define ECS_IOCTL_APP_GET_AFLAG _IOR(AKMIO, 0x14, short)
+#define ECS_IOCTL_APP_SET_DELAY _IOW(AKMIO, 0x18, short)
+#define ECS_IOCTL_APP_GET_DELAY ECS_IOCTL_GET_DELAY
+#define ECS_IOCTL_APP_SET_MVFLAG _IOW(AKMIO, 0x19, short)
+#define ECS_IOCTL_APP_GET_MVFLAG _IOR(AKMIO, 0x1A, short)
+#define ECS_IOCTL_APP_SET_TFLAG _IOR(AKMIO, 0x15, short)
+
+#define ECS_INTR 140
+
+struct akm8975_platform_data {
+ int intr;
+};
+
+#endif
+
diff --git a/libc/kernel/common/linux/bmp085.h b/libc/kernel/common/linux/bmp085.h
new file mode 100644
index 0000000..650cb88
--- /dev/null
+++ b/libc/kernel/common/linux/bmp085.h
@@ -0,0 +1,29 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __BMP085_H__
+#define __BMP085_H__
+
+#include <linux/ioctl.h>
+
+#define BMP085_NAME "bmp085"
+
+#define BMP085_IOCTL_BASE 78
+
+#define BMP085_IOCTL_SET_DELAY _IOW(BMP085_IOCTL_BASE, 0, int)
+#define BMP085_IOCTL_GET_DELAY _IOR(BMP085_IOCTL_BASE, 1, int)
+#define BMP085_IOCTL_SET_ENABLE _IOW(BMP085_IOCTL_BASE, 2, int)
+#define BMP085_IOCTL_GET_ENABLE _IOR(BMP085_IOCTL_BASE, 3, int)
+#define BMP085_IOCTL_ACCURACY _IOW(BMP085_IOCTL_BASE, 4, int)
+
+#endif
+
+
diff --git a/libc/kernel/common/linux/cpcap_audio.h b/libc/kernel/common/linux/cpcap_audio.h
new file mode 100644
index 0000000..a59550f
--- /dev/null
+++ b/libc/kernel/common/linux/cpcap_audio.h
@@ -0,0 +1,65 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef _CPCAP_AUDIO_H
+#define _CPCAP_AUDIO_H
+
+#include <linux/ioctl.h>
+
+#define CPCAP_AUDIO_MAGIC 'c'
+
+#define CPCAP_AUDIO_OUT_SPEAKER 0
+#define CPCAP_AUDIO_OUT_HEADSET 1
+#define CPCAP_AUDIO_OUT_HEADSET_AND_SPEAKER 2
+#define CPCAP_AUDIO_OUT_STANDBY 3
+#define CPCAP_AUDIO_OUT_ANLG_DOCK_HEADSET 4
+#define CPCAP_AUDIO_OUT_MAX 4
+
+struct cpcap_audio_stream {
+ unsigned id;
+ int on;
+};
+
+#define CPCAP_AUDIO_OUT_SET_OUTPUT _IOW(CPCAP_AUDIO_MAGIC, 0, const struct cpcap_audio_stream *)
+
+#define CPCAP_AUDIO_OUT_VOL_MIN 0
+#define CPCAP_AUDIO_OUT_VOL_MAX 15
+
+#define CPCAP_AUDIO_OUT_SET_VOLUME _IOW(CPCAP_AUDIO_MAGIC, 1, unsigned int)
+
+#define CPCAP_AUDIO_OUT_GET_OUTPUT _IOR(CPCAP_AUDIO_MAGIC, 2, struct cpcap_audio_stream *)
+#define CPCAP_AUDIO_OUT_GET_VOLUME _IOR(CPCAP_AUDIO_MAGIC, 3, unsigned int *)
+
+#define CPCAP_AUDIO_IN_MIC1 0
+#define CPCAP_AUDIO_IN_MIC2 1
+#define CPCAP_AUDIO_IN_STANDBY 2
+#define CPCAP_AUDIO_IN_MAX 2
+
+#define CPCAP_AUDIO_IN_SET_INPUT _IOW(CPCAP_AUDIO_MAGIC, 4, const struct cpcap_audio_stream *)
+
+#define CPCAP_AUDIO_IN_GET_INPUT _IOR(CPCAP_AUDIO_MAGIC, 5, struct cpcap_audio_stream *)
+
+#define CPCAP_AUDIO_IN_VOL_MIN 0
+#define CPCAP_AUDIO_IN_VOL_MAX 31
+
+#define CPCAP_AUDIO_IN_SET_VOLUME _IOW(CPCAP_AUDIO_MAGIC, 6, unsigned int)
+
+#define CPCAP_AUDIO_IN_GET_VOLUME _IOR(CPCAP_AUDIO_MAGIC, 7, unsigned int *)
+
+#define CPCAP_AUDIO_OUT_GET_RATE _IOR(CPCAP_AUDIO_MAGIC, 8, unsigned int *)
+#define CPCAP_AUDIO_OUT_SET_RATE _IOW(CPCAP_AUDIO_MAGIC, 9, unsigned int)
+#define CPCAP_AUDIO_IN_GET_RATE _IOR(CPCAP_AUDIO_MAGIC, 10, unsigned int *)
+#define CPCAP_AUDIO_IN_SET_RATE _IOW(CPCAP_AUDIO_MAGIC, 11, unsigned int)
+
+#define CPCAP_AUDIO_SET_BLUETOOTH_BYPASS _IOW(CPCAP_AUDIO_MAGIC, 12, unsigned int)
+
+#endif
+
diff --git a/libc/kernel/common/linux/hid.h b/libc/kernel/common/linux/hid.h
new file mode 100644
index 0000000..450db19
--- /dev/null
+++ b/libc/kernel/common/linux/hid.h
@@ -0,0 +1,36 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __HID_H
+#define __HID_H
+
+#define USB_INTERFACE_CLASS_HID 3
+
+#define USB_INTERFACE_SUBCLASS_BOOT 1
+#define USB_INTERFACE_PROTOCOL_KEYBOARD 1
+#define USB_INTERFACE_PROTOCOL_MOUSE 2
+
+#define HID_REQ_GET_REPORT 0x01
+#define HID_REQ_GET_IDLE 0x02
+#define HID_REQ_GET_PROTOCOL 0x03
+#define HID_REQ_SET_REPORT 0x09
+#define HID_REQ_SET_IDLE 0x0A
+#define HID_REQ_SET_PROTOCOL 0x0B
+
+#define HID_DT_HID (USB_TYPE_CLASS | 0x01)
+#define HID_DT_REPORT (USB_TYPE_CLASS | 0x02)
+#define HID_DT_PHYSICAL (USB_TYPE_CLASS | 0x03)
+
+#define HID_MAX_DESCRIPTOR_SIZE 4096
+
+#endif
+
+
diff --git a/libc/kernel/common/linux/hidraw.h b/libc/kernel/common/linux/hidraw.h
new file mode 100644
index 0000000..0681ece
--- /dev/null
+++ b/libc/kernel/common/linux/hidraw.h
@@ -0,0 +1,41 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef _HIDRAW_H
+#define _HIDRAW_H
+
+#include <linux/hid.h>
+#include <linux/types.h>
+
+struct hidraw_report_descriptor {
+ __u32 size;
+ __u8 value[HID_MAX_DESCRIPTOR_SIZE];
+};
+
+struct hidraw_devinfo {
+ __u32 bustype;
+ __s16 vendor;
+ __s16 product;
+};
+
+#define HIDIOCGRDESCSIZE _IOR('H', 0x01, int)
+#define HIDIOCGRDESC _IOR('H', 0x02, struct hidraw_report_descriptor)
+#define HIDIOCGRAWINFO _IOR('H', 0x03, struct hidraw_devinfo)
+#define HIDIOCGRAWNAME(len) _IOC(_IOC_READ, 'H', 0x04, len)
+#define HIDIOCGRAWPHYS(len) _IOC(_IOC_READ, 'H', 0x05, len)
+
+#define HIDRAW_FIRST_MINOR 0
+#define HIDRAW_MAX_DEVICES 64
+
+#define HIDRAW_BUFFER_SIZE 64
+
+#endif
+
diff --git a/libc/kernel/common/linux/if.h b/libc/kernel/common/linux/if.h
index 47c29d9..7db4888 100644
--- a/libc/kernel/common/linux/if.h
+++ b/libc/kernel/common/linux/if.h
@@ -17,6 +17,7 @@
#include <linux/compiler.h>
#define IFNAMSIZ 16
+#define IFALIASZ 256
#include <linux/hdlc/ioctl.h>
#define IFF_UP 0x1
@@ -42,13 +43,24 @@
#define IFF_LOWER_UP 0x10000
#define IFF_DORMANT 0x20000
-#define IFF_VOLATILE (IFF_LOOPBACK|IFF_POINTOPOINT|IFF_BROADCAST| IFF_MASTER|IFF_SLAVE|IFF_RUNNING|IFF_LOWER_UP|IFF_DORMANT)
+#define IFF_ECHO 0x40000
+
+#define IFF_VOLATILE (IFF_LOOPBACK|IFF_POINTOPOINT|IFF_BROADCAST|IFF_ECHO| IFF_MASTER|IFF_SLAVE|IFF_RUNNING|IFF_LOWER_UP|IFF_DORMANT)
#define IFF_802_1Q_VLAN 0x1
#define IFF_EBRIDGE 0x2
#define IFF_SLAVE_INACTIVE 0x4
#define IFF_MASTER_8023AD 0x8
#define IFF_MASTER_ALB 0x10
+#define IFF_BONDING 0x20
+#define IFF_SLAVE_NEEDARP 0x40
+#define IFF_ISATAP 0x80
+#define IFF_MASTER_ARPMON 0x100
+#define IFF_WAN_HDLC 0x200
+#define IFF_XMIT_DST_RELEASE 0x400
+#define IFF_DONT_BRIDGE 0x800
+#define IFF_IN_NETPOLL 0x1000
+#define IFF_DISABLE_NETPOLL 0x2000
#define IF_GET_IFACE 0x0001
#define IF_GET_PROTO 0x0002
@@ -90,8 +102,7 @@
IF_LINK_MODE_DORMANT,
};
-struct ifmap
-{
+struct ifmap {
unsigned long mem_start;
unsigned long mem_end;
unsigned short base_addr;
@@ -101,8 +112,7 @@
};
-struct if_settings
-{
+struct if_settings {
unsigned int type;
unsigned int size;
union {
@@ -118,8 +128,7 @@
} ifs_ifsu;
};
-struct ifreq
-{
+struct ifreq {
#define IFHWADDRLEN 6
union
{
@@ -161,11 +170,9 @@
#define ifr_newname ifr_ifru.ifru_newname
#define ifr_settings ifr_ifru.ifru_settings
-struct ifconf
-{
+struct ifconf {
int ifc_len;
- union
- {
+ union {
char __user *ifcu_buf;
struct ifreq __user *ifcu_req;
} ifc_ifcu;
@@ -174,3 +181,4 @@
#define ifc_req ifc_ifcu.ifcu_req
#endif
+
diff --git a/libc/kernel/common/linux/if_ether.h b/libc/kernel/common/linux/if_ether.h
index 1ba7a99..7e235a5 100644
--- a/libc/kernel/common/linux/if_ether.h
+++ b/libc/kernel/common/linux/if_ether.h
@@ -84,6 +84,7 @@
#define ETH_P_TRAILER 0x001C
#define ETH_P_PHONET 0x00F5
#define ETH_P_IEEE802154 0x00F6
+#define ETH_P_CAIF 0x00F7
struct ethhdr {
unsigned char h_dest[ETH_ALEN];
diff --git a/libc/kernel/common/linux/if_vlan.h b/libc/kernel/common/linux/if_vlan.h
index d3d2df2..ab3b174 100644
--- a/libc/kernel/common/linux/if_vlan.h
+++ b/libc/kernel/common/linux/if_vlan.h
@@ -25,6 +25,12 @@
GET_VLAN_VID_CMD
};
+enum vlan_flags {
+ VLAN_FLAG_REORDER_HDR = 0x1,
+ VLAN_FLAG_GVRP = 0x2,
+ VLAN_FLAG_LOOSE_BINDING = 0x4,
+};
+
enum vlan_name_types {
VLAN_NAME_TYPE_PLUS_VID,
VLAN_NAME_TYPE_RAW_PLUS_VID,
@@ -50,3 +56,4 @@
};
#endif
+
diff --git a/libc/kernel/common/linux/in_route.h b/libc/kernel/common/linux/in_route.h
new file mode 100644
index 0000000..34e14d6
--- /dev/null
+++ b/libc/kernel/common/linux/in_route.h
@@ -0,0 +1,41 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef _LINUX_IN_ROUTE_H
+#define _LINUX_IN_ROUTE_H
+
+#define RTCF_DEAD RTNH_F_DEAD
+#define RTCF_ONLINK RTNH_F_ONLINK
+
+#define RTCF_NOPMTUDISC RTM_F_NOPMTUDISC
+
+#define RTCF_NOTIFY 0x00010000
+#define RTCF_DIRECTDST 0x00020000
+#define RTCF_REDIRECTED 0x00040000
+#define RTCF_TPROXY 0x00080000
+
+#define RTCF_FAST 0x00200000
+#define RTCF_MASQ 0x00400000
+#define RTCF_SNAT 0x00800000
+#define RTCF_DOREDIRECT 0x01000000
+#define RTCF_DIRECTSRC 0x04000000
+#define RTCF_DNAT 0x08000000
+#define RTCF_BROADCAST 0x10000000
+#define RTCF_MULTICAST 0x20000000
+#define RTCF_REJECT 0x40000000
+#define RTCF_LOCAL 0x80000000
+
+#define RTCF_NAT (RTCF_DNAT|RTCF_SNAT)
+
+#define RT_TOS(tos) ((tos)&IPTOS_TOS_MASK)
+
+#endif
+
diff --git a/libc/kernel/common/linux/ipv6_route.h b/libc/kernel/common/linux/ipv6_route.h
new file mode 100644
index 0000000..3791e87
--- /dev/null
+++ b/libc/kernel/common/linux/ipv6_route.h
@@ -0,0 +1,55 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef _LINUX_IPV6_ROUTE_H
+#define _LINUX_IPV6_ROUTE_H
+
+#include <linux/types.h>
+
+#define RTF_DEFAULT 0x00010000
+#define RTF_ALLONLINK 0x00020000
+#define RTF_ADDRCONF 0x00040000
+#define RTF_PREFIX_RT 0x00080000
+#define RTF_ANYCAST 0x00100000
+
+#define RTF_NONEXTHOP 0x00200000
+#define RTF_EXPIRES 0x00400000
+
+#define RTF_ROUTEINFO 0x00800000
+
+#define RTF_CACHE 0x01000000
+#define RTF_FLOW 0x02000000
+#define RTF_POLICY 0x04000000
+
+#define RTF_PREF(pref) ((pref) << 27)
+#define RTF_PREF_MASK 0x18000000
+
+#define RTF_LOCAL 0x80000000
+
+struct in6_rtmsg {
+ struct in6_addr rtmsg_dst;
+ struct in6_addr rtmsg_src;
+ struct in6_addr rtmsg_gateway;
+ __u32 rtmsg_type;
+ __u16 rtmsg_dst_len;
+ __u16 rtmsg_src_len;
+ __u32 rtmsg_metric;
+ unsigned long rtmsg_info;
+ __u32 rtmsg_flags;
+ int rtmsg_ifindex;
+};
+
+#define RTMSG_NEWDEVICE 0x11
+#define RTMSG_DELDEVICE 0x12
+#define RTMSG_NEWROUTE 0x21
+#define RTMSG_DELROUTE 0x22
+
+#endif
diff --git a/libc/kernel/common/linux/kxtf9.h b/libc/kernel/common/linux/kxtf9.h
new file mode 100644
index 0000000..9141364
--- /dev/null
+++ b/libc/kernel/common/linux/kxtf9.h
@@ -0,0 +1,70 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __KXTF9_H__
+#define __KXTF9_H__
+
+#include <linux/ioctl.h>
+
+#define KXTF9_IOCTL_BASE 77
+
+#define KXTF9_IOCTL_SET_DELAY _IOW(KXTF9_IOCTL_BASE, 0, int)
+#define KXTF9_IOCTL_GET_DELAY _IOR(KXTF9_IOCTL_BASE, 1, int)
+#define KXTF9_IOCTL_SET_ENABLE _IOW(KXTF9_IOCTL_BASE, 2, int)
+#define KXTF9_IOCTL_GET_ENABLE _IOR(KXTF9_IOCTL_BASE, 3, int)
+#define KXTF9_IOCTL_SET_G_RANGE _IOW(KXTF9_IOCTL_BASE, 4, int)
+
+#define KXTF9_IOCTL_SET_TILT_ENABLE _IOW(KXTF9_IOCTL_BASE, 5, int)
+#define KXTF9_IOCTL_SET_TAP_ENABLE _IOW(KXTF9_IOCTL_BASE, 6, int)
+#define KXTF9_IOCTL_SET_WAKE_ENABLE _IOW(KXTF9_IOCTL_BASE, 7, int)
+#define KXTF9_IOCTL_SET_PM_MODE _IOW(KXTF9_IOCTL_BASE, 8, int)
+#define KXTF9_IOCTL_SELF_TEST _IOW(KXTF9_IOCTL_BASE, 9, int)
+#define KXTF9_IOCTL_SET_SENSITIVITY _IOW(KXTF9_IOCTL_BASE, 10, int)
+
+#define RES_12BIT 0x40
+#define KXTF9_G_2G 0x00
+#define KXTF9_G_4G 0x08
+#define KXTF9_G_8G 0x10
+#define TPE 0x01
+#define WUFE 0x02
+#define TDTE 0x04
+
+#define OTP1_6 0x00
+#define OTP6_3 0x20
+#define OTP12_5 0x40
+#define OTP50 0x60
+#define OWUF25 0x00
+#define OWUF50 0x01
+#define OWUF100 0x02
+#define OWUF200 0x03
+#define OTDT50 0x00
+#define OTDT100 0x04
+#define OTDT200 0x08
+#define OTDT400 0x0C
+
+#define IEN 0x20
+#define IEA 0x10
+#define IEL 0x08
+#define IEU 0x04
+
+#define ODR800 0x06
+#define ODR400 0x05
+#define ODR200 0x04
+#define ODR100 0x03
+#define ODR50 0x02
+#define ODR25 0x01
+#define ODR12_5 0x00
+
+#define SENSITIVITY_REGS 0x07
+
+#endif
+
+
diff --git a/libc/kernel/common/linux/l3g4200d.h b/libc/kernel/common/linux/l3g4200d.h
new file mode 100644
index 0000000..0a0f8cd
--- /dev/null
+++ b/libc/kernel/common/linux/l3g4200d.h
@@ -0,0 +1,27 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __L3G4200D_H__
+#define __L3G4200D_H__
+
+#include <linux/ioctl.h>
+
+#define L3G4200D_NAME "l3g4200d"
+
+#define L3G4200D_IOCTL_BASE 77
+
+#define L3G4200D_IOCTL_SET_DELAY _IOW(L3G4200D_IOCTL_BASE, 0, int)
+#define L3G4200D_IOCTL_GET_DELAY _IOR(L3G4200D_IOCTL_BASE, 1, int)
+#define L3G4200D_IOCTL_SET_ENABLE _IOW(L3G4200D_IOCTL_BASE, 2, int)
+#define L3G4200D_IOCTL_GET_ENABLE _IOR(L3G4200D_IOCTL_BASE, 3, int)
+
+#endif
+
diff --git a/libc/kernel/common/linux/max9635.h b/libc/kernel/common/linux/max9635.h
new file mode 100644
index 0000000..e696fa9
--- /dev/null
+++ b/libc/kernel/common/linux/max9635.h
@@ -0,0 +1,23 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef _LINUX_MAX9635_H__
+#define _LINUX_MAX9635_H__
+
+#define MAX9635_NAME "MAX9635_als"
+#define FOPS_MAX9635_NAME "MAX9635"
+
+#define MAX9635_IO 0xA3
+
+#define MAX9635_IOCTL_GET_ENABLE _IOR(MAX9635_IO, 0x00, char)
+#define MAX9635_IOCTL_SET_ENABLE _IOW(MAX9635_IO, 0x01, char)
+
+#endif
diff --git a/libc/kernel/common/linux/netfilter_ipv6/ip6_tables.h b/libc/kernel/common/linux/netfilter_ipv6/ip6_tables.h
index 1687e4f..d76a529 100644
--- a/libc/kernel/common/linux/netfilter_ipv6/ip6_tables.h
+++ b/libc/kernel/common/linux/netfilter_ipv6/ip6_tables.h
@@ -173,6 +173,15 @@
#define IP6T_ERROR_TARGET XT_ERROR_TARGET
+static __inline__ struct ip6t_entry_target *
+ip6t_get_target(struct ip6t_entry *e)
+{
+ return (void *)e + e->target_offset;
+}
+
#define IP6T_MATCH_ITERATE(e, fn, args...) ({ unsigned int __i; int __ret = 0; struct ip6t_entry_match *__m; for (__i = sizeof(struct ip6t_entry); __i < (e)->target_offset; __i += __m->u.match_size) { __m = (void *)(e) + __i; __ret = fn(__m , ## args); if (__ret != 0) break; } __ret; })
+
#define IP6T_ENTRY_ITERATE(entries, size, fn, args...) ({ unsigned int __i; int __ret = 0; struct ip6t_entry *__e; for (__i = 0; __i < (size); __i += __e->next_offset) { __e = (void *)(entries) + __i; __ret = fn(__e , ## args); if (__ret != 0) break; } __ret; })
+
#endif
+
diff --git a/libc/kernel/common/linux/perf_event.h b/libc/kernel/common/linux/perf_event.h
new file mode 100644
index 0000000..9d3cd14
--- /dev/null
+++ b/libc/kernel/common/linux/perf_event.h
@@ -0,0 +1,240 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef _LINUX_PERF_EVENT_H
+#define _LINUX_PERF_EVENT_H
+
+#include <linux/types.h>
+#include <linux/ioctl.h>
+#include <asm/byteorder.h>
+
+enum perf_type_id {
+ PERF_TYPE_HARDWARE = 0,
+ PERF_TYPE_SOFTWARE = 1,
+ PERF_TYPE_TRACEPOINT = 2,
+ PERF_TYPE_HW_CACHE = 3,
+ PERF_TYPE_RAW = 4,
+ PERF_TYPE_BREAKPOINT = 5,
+
+ PERF_TYPE_MAX,
+};
+
+enum perf_hw_id {
+
+ PERF_COUNT_HW_CPU_CYCLES = 0,
+ PERF_COUNT_HW_INSTRUCTIONS = 1,
+ PERF_COUNT_HW_CACHE_REFERENCES = 2,
+ PERF_COUNT_HW_CACHE_MISSES = 3,
+ PERF_COUNT_HW_BRANCH_INSTRUCTIONS = 4,
+ PERF_COUNT_HW_BRANCH_MISSES = 5,
+ PERF_COUNT_HW_BUS_CYCLES = 6,
+
+ PERF_COUNT_HW_MAX,
+};
+
+enum perf_hw_cache_id {
+ PERF_COUNT_HW_CACHE_L1D = 0,
+ PERF_COUNT_HW_CACHE_L1I = 1,
+ PERF_COUNT_HW_CACHE_LL = 2,
+ PERF_COUNT_HW_CACHE_DTLB = 3,
+ PERF_COUNT_HW_CACHE_ITLB = 4,
+ PERF_COUNT_HW_CACHE_BPU = 5,
+
+ PERF_COUNT_HW_CACHE_MAX,
+};
+
+enum perf_hw_cache_op_id {
+ PERF_COUNT_HW_CACHE_OP_READ = 0,
+ PERF_COUNT_HW_CACHE_OP_WRITE = 1,
+ PERF_COUNT_HW_CACHE_OP_PREFETCH = 2,
+
+ PERF_COUNT_HW_CACHE_OP_MAX,
+};
+
+enum perf_hw_cache_op_result_id {
+ PERF_COUNT_HW_CACHE_RESULT_ACCESS = 0,
+ PERF_COUNT_HW_CACHE_RESULT_MISS = 1,
+
+ PERF_COUNT_HW_CACHE_RESULT_MAX,
+};
+
+enum perf_sw_ids {
+ PERF_COUNT_SW_CPU_CLOCK = 0,
+ PERF_COUNT_SW_TASK_CLOCK = 1,
+ PERF_COUNT_SW_PAGE_FAULTS = 2,
+ PERF_COUNT_SW_CONTEXT_SWITCHES = 3,
+ PERF_COUNT_SW_CPU_MIGRATIONS = 4,
+ PERF_COUNT_SW_PAGE_FAULTS_MIN = 5,
+ PERF_COUNT_SW_PAGE_FAULTS_MAJ = 6,
+ PERF_COUNT_SW_ALIGNMENT_FAULTS = 7,
+ PERF_COUNT_SW_EMULATION_FAULTS = 8,
+
+ PERF_COUNT_SW_MAX,
+};
+
+enum perf_event_sample_format {
+ PERF_SAMPLE_IP = 1U << 0,
+ PERF_SAMPLE_TID = 1U << 1,
+ PERF_SAMPLE_TIME = 1U << 2,
+ PERF_SAMPLE_ADDR = 1U << 3,
+ PERF_SAMPLE_READ = 1U << 4,
+ PERF_SAMPLE_CALLCHAIN = 1U << 5,
+ PERF_SAMPLE_ID = 1U << 6,
+ PERF_SAMPLE_CPU = 1U << 7,
+ PERF_SAMPLE_PERIOD = 1U << 8,
+ PERF_SAMPLE_STREAM_ID = 1U << 9,
+ PERF_SAMPLE_RAW = 1U << 10,
+
+ PERF_SAMPLE_MAX = 1U << 11,
+};
+
+enum perf_event_read_format {
+ PERF_FORMAT_TOTAL_TIME_ENABLED = 1U << 0,
+ PERF_FORMAT_TOTAL_TIME_RUNNING = 1U << 1,
+ PERF_FORMAT_ID = 1U << 2,
+ PERF_FORMAT_GROUP = 1U << 3,
+
+ PERF_FORMAT_MAX = 1U << 4,
+};
+
+#define PERF_ATTR_SIZE_VER0 64
+
+struct perf_event_attr {
+
+ __u32 type;
+
+ __u32 size;
+
+ __u64 config;
+
+ union {
+ __u64 sample_period;
+ __u64 sample_freq;
+ };
+
+ __u64 sample_type;
+ __u64 read_format;
+
+ __u64 disabled : 1,
+ inherit : 1,
+ pinned : 1,
+ exclusive : 1,
+ exclude_user : 1,
+ exclude_kernel : 1,
+ exclude_hv : 1,
+ exclude_idle : 1,
+ mmap : 1,
+ comm : 1,
+ freq : 1,
+ inherit_stat : 1,
+ enable_on_exec : 1,
+ task : 1,
+ watermark : 1,
+
+ precise_ip : 2,
+
+ __reserved_1 : 47;
+
+ union {
+ __u32 wakeup_events;
+ __u32 wakeup_watermark;
+ };
+
+ __u32 bp_type;
+ __u64 bp_addr;
+ __u64 bp_len;
+};
+
+#define PERF_EVENT_IOC_ENABLE _IO ('$', 0)
+#define PERF_EVENT_IOC_DISABLE _IO ('$', 1)
+#define PERF_EVENT_IOC_REFRESH _IO ('$', 2)
+#define PERF_EVENT_IOC_RESET _IO ('$', 3)
+#define PERF_EVENT_IOC_PERIOD _IOW('$', 4, __u64)
+#define PERF_EVENT_IOC_SET_OUTPUT _IO ('$', 5)
+#define PERF_EVENT_IOC_SET_FILTER _IOW('$', 6, char *)
+
+enum perf_event_ioc_flags {
+ PERF_IOC_FLAG_GROUP = 1U << 0,
+};
+
+struct perf_event_mmap_page {
+ __u32 version;
+ __u32 compat_version;
+
+ __u32 lock;
+ __u32 index;
+ __s64 offset;
+ __u64 time_enabled;
+ __u64 time_running;
+
+ __u64 __reserved[123];
+
+ __u64 data_head;
+ __u64 data_tail;
+};
+
+#define PERF_RECORD_MISC_CPUMODE_MASK (7 << 0)
+#define PERF_RECORD_MISC_CPUMODE_UNKNOWN (0 << 0)
+#define PERF_RECORD_MISC_KERNEL (1 << 0)
+#define PERF_RECORD_MISC_USER (2 << 0)
+#define PERF_RECORD_MISC_HYPERVISOR (3 << 0)
+#define PERF_RECORD_MISC_GUEST_KERNEL (4 << 0)
+#define PERF_RECORD_MISC_GUEST_USER (5 << 0)
+
+#define PERF_RECORD_MISC_EXACT_IP (1 << 14)
+
+#define PERF_RECORD_MISC_EXT_RESERVED (1 << 15)
+
+struct perf_event_header {
+ __u32 type;
+ __u16 misc;
+ __u16 size;
+};
+
+enum perf_event_type {
+
+ PERF_RECORD_MMAP = 1,
+
+ PERF_RECORD_LOST = 2,
+
+ PERF_RECORD_COMM = 3,
+
+ PERF_RECORD_EXIT = 4,
+
+ PERF_RECORD_THROTTLE = 5,
+ PERF_RECORD_UNTHROTTLE = 6,
+
+ PERF_RECORD_FORK = 7,
+
+ PERF_RECORD_READ = 8,
+
+ PERF_RECORD_SAMPLE = 9,
+
+ PERF_RECORD_MAX,
+};
+
+enum perf_callchain_context {
+ PERF_CONTEXT_HV = (__u64)-32,
+ PERF_CONTEXT_KERNEL = (__u64)-128,
+ PERF_CONTEXT_USER = (__u64)-512,
+
+ PERF_CONTEXT_GUEST = (__u64)-2048,
+ PERF_CONTEXT_GUEST_KERNEL = (__u64)-2176,
+ PERF_CONTEXT_GUEST_USER = (__u64)-2560,
+
+ PERF_CONTEXT_MAX = (__u64)-4095,
+};
+
+#define PERF_FLAG_FD_NO_GROUP (1U << 0)
+#define PERF_FLAG_FD_OUTPUT (1U << 1)
+
+#endif
+
diff --git a/libc/kernel/common/linux/socket.h b/libc/kernel/common/linux/socket.h
index b578df9..c30dae0 100644
--- a/libc/kernel/common/linux/socket.h
+++ b/libc/kernel/common/linux/socket.h
@@ -138,7 +138,8 @@
#define AF_LLC 26
#define AF_TIPC 30
#define AF_BLUETOOTH 31
-#define AF_MAX 32
+#define AF_CAIF 38
+#define AF_MAX 39
#define PF_UNSPEC AF_UNSPEC
#define PF_UNIX AF_UNIX
@@ -170,6 +171,7 @@
#define PF_LLC AF_LLC
#define PF_TIPC AF_TIPC
#define PF_BLUETOOTH AF_BLUETOOTH
+#define PF_CAIF AF_CAIF
#define PF_MAX AF_MAX
#define SOMAXCONN 128
diff --git a/libc/kernel/common/linux/spi/cpcap.h b/libc/kernel/common/linux/spi/cpcap.h
new file mode 100644
index 0000000..24bc918
--- /dev/null
+++ b/libc/kernel/common/linux/spi/cpcap.h
@@ -0,0 +1,587 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef _LINUX_SPI_CPCAP_H
+#define _LINUX_SPI_CPCAP_H
+
+#include <linux/ioctl.h>
+
+#define CPCAP_DEV_NAME "cpcap"
+#define CPCAP_NUM_REG_CPCAP (CPCAP_REG_END - CPCAP_REG_START + 1)
+
+#define CPCAP_IRQ_INT1_INDEX 0
+#define CPCAP_IRQ_INT2_INDEX 16
+#define CPCAP_IRQ_INT3_INDEX 32
+#define CPCAP_IRQ_INT4_INDEX 48
+#define CPCAP_IRQ_INT5_INDEX 64
+
+#define CPCAP_HWCFG_NUM 2
+
+#define CPCAP_HWCFG0_SEC_STBY_SW1 0x0001
+#define CPCAP_HWCFG0_SEC_STBY_SW2 0x0002
+#define CPCAP_HWCFG0_SEC_STBY_SW3 0x0004
+#define CPCAP_HWCFG0_SEC_STBY_SW4 0x0008
+#define CPCAP_HWCFG0_SEC_STBY_SW5 0x0010
+#define CPCAP_HWCFG0_SEC_STBY_VAUDIO 0x0020
+#define CPCAP_HWCFG0_SEC_STBY_VCAM 0x0040
+#define CPCAP_HWCFG0_SEC_STBY_VCSI 0x0080
+#define CPCAP_HWCFG0_SEC_STBY_VDAC 0x0100
+#define CPCAP_HWCFG0_SEC_STBY_VDIG 0x0200
+#define CPCAP_HWCFG0_SEC_STBY_VHVIO 0x0400
+#define CPCAP_HWCFG0_SEC_STBY_VPLL 0x0800
+#define CPCAP_HWCFG0_SEC_STBY_VRF1 0x1000
+#define CPCAP_HWCFG0_SEC_STBY_VRF2 0x2000
+#define CPCAP_HWCFG0_SEC_STBY_VRFREF 0x4000
+#define CPCAP_HWCFG0_SEC_STBY_VSDIO 0x8000
+
+#define CPCAP_HWCFG1_SEC_STBY_VWLAN1 0x0001
+#define CPCAP_HWCFG1_SEC_STBY_VWLAN2 0x0002
+#define CPCAP_HWCFG1_SEC_STBY_VSIM 0x0004
+#define CPCAP_HWCFG1_SEC_STBY_VSIMCARD 0x0008
+
+#define CPCAP_WHISPER_MODE_PU 0x00000001
+#define CPCAP_WHISPER_ENABLE_UART 0x00000002
+#define CPCAP_WHISPER_ACCY_MASK 0xF8000000
+#define CPCAP_WHISPER_ACCY_SHFT 27
+#define CPCAP_WHISPER_ID_SIZE 16
+#define CPCAP_WHISPER_PROP_SIZE 7
+
+enum cpcap_regulator_id {
+ CPCAP_SW2,
+ CPCAP_SW4,
+ CPCAP_SW5,
+ CPCAP_VCAM,
+ CPCAP_VCSI,
+ CPCAP_VDAC,
+ CPCAP_VDIG,
+ CPCAP_VFUSE,
+ CPCAP_VHVIO,
+ CPCAP_VSDIO,
+ CPCAP_VPLL,
+ CPCAP_VRF1,
+ CPCAP_VRF2,
+ CPCAP_VRFREF,
+ CPCAP_VWLAN1,
+ CPCAP_VWLAN2,
+ CPCAP_VSIM,
+ CPCAP_VSIMCARD,
+ CPCAP_VVIB,
+ CPCAP_VUSB,
+ CPCAP_VAUDIO,
+ CPCAP_NUM_REGULATORS
+};
+
+enum cpcap_reg {
+ CPCAP_REG_START,
+
+ CPCAP_REG_INT1 = CPCAP_REG_START,
+ CPCAP_REG_INT2,
+ CPCAP_REG_INT3,
+ CPCAP_REG_INT4,
+ CPCAP_REG_INTM1,
+ CPCAP_REG_INTM2,
+ CPCAP_REG_INTM3,
+ CPCAP_REG_INTM4,
+ CPCAP_REG_INTS1,
+ CPCAP_REG_INTS2,
+ CPCAP_REG_INTS3,
+ CPCAP_REG_INTS4,
+ CPCAP_REG_ASSIGN1,
+ CPCAP_REG_ASSIGN2,
+ CPCAP_REG_ASSIGN3,
+ CPCAP_REG_ASSIGN4,
+ CPCAP_REG_ASSIGN5,
+ CPCAP_REG_ASSIGN6,
+ CPCAP_REG_VERSC1,
+ CPCAP_REG_VERSC2,
+
+ CPCAP_REG_MI1,
+ CPCAP_REG_MIM1,
+ CPCAP_REG_MI2,
+ CPCAP_REG_MIM2,
+ CPCAP_REG_UCC1,
+ CPCAP_REG_UCC2,
+ CPCAP_REG_PC1,
+ CPCAP_REG_PC2,
+ CPCAP_REG_BPEOL,
+ CPCAP_REG_PGC,
+ CPCAP_REG_MT1,
+ CPCAP_REG_MT2,
+ CPCAP_REG_MT3,
+ CPCAP_REG_PF,
+
+ CPCAP_REG_SCC,
+ CPCAP_REG_SW1,
+ CPCAP_REG_SW2,
+ CPCAP_REG_UCTM,
+ CPCAP_REG_TOD1,
+ CPCAP_REG_TOD2,
+ CPCAP_REG_TODA1,
+ CPCAP_REG_TODA2,
+ CPCAP_REG_DAY,
+ CPCAP_REG_DAYA,
+ CPCAP_REG_VAL1,
+ CPCAP_REG_VAL2,
+
+ CPCAP_REG_SDVSPLL,
+ CPCAP_REG_SI2CC1,
+ CPCAP_REG_Si2CC2,
+ CPCAP_REG_S1C1,
+ CPCAP_REG_S1C2,
+ CPCAP_REG_S2C1,
+ CPCAP_REG_S2C2,
+ CPCAP_REG_S3C,
+ CPCAP_REG_S4C1,
+ CPCAP_REG_S4C2,
+ CPCAP_REG_S5C,
+ CPCAP_REG_S6C,
+ CPCAP_REG_VCAMC,
+ CPCAP_REG_VCSIC,
+ CPCAP_REG_VDACC,
+ CPCAP_REG_VDIGC,
+ CPCAP_REG_VFUSEC,
+ CPCAP_REG_VHVIOC,
+ CPCAP_REG_VSDIOC,
+ CPCAP_REG_VPLLC,
+ CPCAP_REG_VRF1C,
+ CPCAP_REG_VRF2C,
+ CPCAP_REG_VRFREFC,
+ CPCAP_REG_VWLAN1C,
+ CPCAP_REG_VWLAN2C,
+ CPCAP_REG_VSIMC,
+ CPCAP_REG_VVIBC,
+ CPCAP_REG_VUSBC,
+ CPCAP_REG_VUSBINT1C,
+ CPCAP_REG_VUSBINT2C,
+ CPCAP_REG_URT,
+ CPCAP_REG_URM1,
+ CPCAP_REG_URM2,
+
+ CPCAP_REG_VAUDIOC,
+ CPCAP_REG_CC,
+ CPCAP_REG_CDI,
+ CPCAP_REG_SDAC,
+ CPCAP_REG_SDACDI,
+ CPCAP_REG_TXI,
+ CPCAP_REG_TXMP,
+ CPCAP_REG_RXOA,
+ CPCAP_REG_RXVC,
+ CPCAP_REG_RXCOA,
+ CPCAP_REG_RXSDOA,
+ CPCAP_REG_RXEPOA,
+ CPCAP_REG_RXLL,
+ CPCAP_REG_A2LA,
+ CPCAP_REG_MIPIS1,
+ CPCAP_REG_MIPIS2,
+ CPCAP_REG_MIPIS3,
+ CPCAP_REG_LVAB,
+
+ CPCAP_REG_CCC1,
+ CPCAP_REG_CRM,
+ CPCAP_REG_CCCC2,
+ CPCAP_REG_CCS1,
+ CPCAP_REG_CCS2,
+ CPCAP_REG_CCA1,
+ CPCAP_REG_CCA2,
+ CPCAP_REG_CCM,
+ CPCAP_REG_CCO,
+ CPCAP_REG_CCI,
+
+ CPCAP_REG_ADCC1,
+ CPCAP_REG_ADCC2,
+ CPCAP_REG_ADCD0,
+ CPCAP_REG_ADCD1,
+ CPCAP_REG_ADCD2,
+ CPCAP_REG_ADCD3,
+ CPCAP_REG_ADCD4,
+ CPCAP_REG_ADCD5,
+ CPCAP_REG_ADCD6,
+ CPCAP_REG_ADCD7,
+ CPCAP_REG_ADCAL1,
+ CPCAP_REG_ADCAL2,
+
+ CPCAP_REG_USBC1,
+ CPCAP_REG_USBC2,
+ CPCAP_REG_USBC3,
+ CPCAP_REG_UVIDL,
+ CPCAP_REG_UVIDH,
+ CPCAP_REG_UPIDL,
+ CPCAP_REG_UPIDH,
+ CPCAP_REG_UFC1,
+ CPCAP_REG_UFC2,
+ CPCAP_REG_UFC3,
+ CPCAP_REG_UIC1,
+ CPCAP_REG_UIC2,
+ CPCAP_REG_UIC3,
+ CPCAP_REG_USBOTG1,
+ CPCAP_REG_USBOTG2,
+ CPCAP_REG_USBOTG3,
+ CPCAP_REG_UIER1,
+ CPCAP_REG_UIER2,
+ CPCAP_REG_UIER3,
+ CPCAP_REG_UIEF1,
+ CPCAP_REG_UIEF2,
+ CPCAP_REG_UIEF3,
+ CPCAP_REG_UIS,
+ CPCAP_REG_UIL,
+ CPCAP_REG_USBD,
+ CPCAP_REG_SCR1,
+ CPCAP_REG_SCR2,
+ CPCAP_REG_SCR3,
+ CPCAP_REG_VMC,
+ CPCAP_REG_OWDC,
+ CPCAP_REG_GPIO0,
+ CPCAP_REG_GPIO1,
+ CPCAP_REG_GPIO2,
+ CPCAP_REG_GPIO3,
+ CPCAP_REG_GPIO4,
+ CPCAP_REG_GPIO5,
+ CPCAP_REG_GPIO6,
+
+ CPCAP_REG_MDLC,
+ CPCAP_REG_KLC,
+ CPCAP_REG_ADLC,
+ CPCAP_REG_REDC,
+ CPCAP_REG_GREENC,
+ CPCAP_REG_BLUEC,
+ CPCAP_REG_CFC,
+ CPCAP_REG_ABC,
+ CPCAP_REG_BLEDC,
+ CPCAP_REG_CLEDC,
+
+ CPCAP_REG_OW1C,
+ CPCAP_REG_OW1D,
+ CPCAP_REG_OW1I,
+ CPCAP_REG_OW1IE,
+ CPCAP_REG_OW1,
+ CPCAP_REG_OW2C,
+ CPCAP_REG_OW2D,
+ CPCAP_REG_OW2I,
+ CPCAP_REG_OW2IE,
+ CPCAP_REG_OW2,
+ CPCAP_REG_OW3C,
+ CPCAP_REG_OW3D,
+ CPCAP_REG_OW3I,
+ CPCAP_REG_OW3IE,
+ CPCAP_REG_OW3,
+ CPCAP_REG_GCAIC,
+ CPCAP_REG_GCAIM,
+ CPCAP_REG_LGDIR,
+ CPCAP_REG_LGPU,
+ CPCAP_REG_LGPIN,
+ CPCAP_REG_LGMASK,
+ CPCAP_REG_LDEB,
+ CPCAP_REG_LGDET,
+ CPCAP_REG_LMISC,
+ CPCAP_REG_LMACE,
+
+ CPCAP_REG_END = CPCAP_REG_LMACE,
+
+ CPCAP_REG_MAX
+ = CPCAP_REG_END,
+
+ CPCAP_REG_SIZE = CPCAP_REG_MAX + 1,
+ CPCAP_REG_UNUSED = CPCAP_REG_MAX + 2,
+};
+
+enum {
+ CPCAP_IOCTL_NUM_TEST__START,
+ CPCAP_IOCTL_NUM_TEST_READ_REG,
+ CPCAP_IOCTL_NUM_TEST_WRITE_REG,
+ CPCAP_IOCTL_NUM_TEST__END,
+
+ CPCAP_IOCTL_NUM_ADC__START,
+ CPCAP_IOCTL_NUM_ADC_PHASE,
+ CPCAP_IOCTL_NUM_ADC__END,
+
+ CPCAP_IOCTL_NUM_BATT__START,
+ CPCAP_IOCTL_NUM_BATT_DISPLAY_UPDATE,
+ CPCAP_IOCTL_NUM_BATT_ATOD_ASYNC,
+ CPCAP_IOCTL_NUM_BATT_ATOD_SYNC,
+ CPCAP_IOCTL_NUM_BATT_ATOD_READ,
+ CPCAP_IOCTL_NUM_BATT__END,
+
+ CPCAP_IOCTL_NUM_UC__START,
+ CPCAP_IOCTL_NUM_UC_MACRO_START,
+ CPCAP_IOCTL_NUM_UC_MACRO_STOP,
+ CPCAP_IOCTL_NUM_UC_GET_VENDOR,
+ CPCAP_IOCTL_NUM_UC_SET_TURBO_MODE,
+ CPCAP_IOCTL_NUM_UC__END,
+
+ CPCAP_IOCTL_NUM_ACCY__START,
+ CPCAP_IOCTL_NUM_ACCY_WHISPER,
+ CPCAP_IOCTL_NUM_ACCY__END,
+};
+
+enum cpcap_irqs {
+ CPCAP_IRQ__START,
+ CPCAP_IRQ_HSCLK = CPCAP_IRQ_INT1_INDEX,
+ CPCAP_IRQ_PRIMAC,
+ CPCAP_IRQ_SECMAC,
+ CPCAP_IRQ_LOWBPL,
+ CPCAP_IRQ_SEC2PRI,
+ CPCAP_IRQ_LOWBPH,
+ CPCAP_IRQ_EOL,
+ CPCAP_IRQ_TS,
+ CPCAP_IRQ_ADCDONE,
+ CPCAP_IRQ_HS,
+ CPCAP_IRQ_MB2,
+ CPCAP_IRQ_VBUSOV,
+ CPCAP_IRQ_RVRS_CHRG,
+ CPCAP_IRQ_CHRG_DET,
+ CPCAP_IRQ_IDFLOAT,
+ CPCAP_IRQ_IDGND,
+
+ CPCAP_IRQ_SE1 = CPCAP_IRQ_INT2_INDEX,
+ CPCAP_IRQ_SESSEND,
+ CPCAP_IRQ_SESSVLD,
+ CPCAP_IRQ_VBUSVLD,
+ CPCAP_IRQ_CHRG_CURR1,
+ CPCAP_IRQ_CHRG_CURR2,
+ CPCAP_IRQ_RVRS_MODE,
+ CPCAP_IRQ_ON,
+ CPCAP_IRQ_ON2,
+ CPCAP_IRQ_CLK,
+ CPCAP_IRQ_1HZ,
+ CPCAP_IRQ_PTT,
+ CPCAP_IRQ_SE0CONN,
+ CPCAP_IRQ_CHRG_SE1B,
+ CPCAP_IRQ_UART_ECHO_OVERRUN,
+ CPCAP_IRQ_EXTMEMHD,
+
+ CPCAP_IRQ_WARM = CPCAP_IRQ_INT3_INDEX,
+ CPCAP_IRQ_SYSRSTR,
+ CPCAP_IRQ_SOFTRST,
+ CPCAP_IRQ_DIEPWRDWN,
+ CPCAP_IRQ_DIETEMPH,
+ CPCAP_IRQ_PC,
+ CPCAP_IRQ_OFLOWSW,
+ CPCAP_IRQ_TODA,
+ CPCAP_IRQ_OPT_SEL_DTCH,
+ CPCAP_IRQ_OPT_SEL_STATE,
+ CPCAP_IRQ_ONEWIRE1,
+ CPCAP_IRQ_ONEWIRE2,
+ CPCAP_IRQ_ONEWIRE3,
+ CPCAP_IRQ_UCRESET,
+ CPCAP_IRQ_PWRGOOD,
+ CPCAP_IRQ_USBDPLLCLK,
+
+ CPCAP_IRQ_DPI = CPCAP_IRQ_INT4_INDEX,
+ CPCAP_IRQ_DMI,
+ CPCAP_IRQ_UCBUSY,
+ CPCAP_IRQ_GCAI_CURR1,
+ CPCAP_IRQ_GCAI_CURR2,
+ CPCAP_IRQ_SB_MAX_RETRANSMIT_ERR,
+ CPCAP_IRQ_BATTDETB,
+ CPCAP_IRQ_PRIHALT,
+ CPCAP_IRQ_SECHALT,
+ CPCAP_IRQ_CC_CAL,
+
+ CPCAP_IRQ_UC_PRIROMR = CPCAP_IRQ_INT5_INDEX,
+ CPCAP_IRQ_UC_PRIRAMW,
+ CPCAP_IRQ_UC_PRIRAMR,
+ CPCAP_IRQ_UC_USEROFF,
+ CPCAP_IRQ_UC_PRIMACRO_4,
+ CPCAP_IRQ_UC_PRIMACRO_5,
+ CPCAP_IRQ_UC_PRIMACRO_6,
+ CPCAP_IRQ_UC_PRIMACRO_7,
+ CPCAP_IRQ_UC_PRIMACRO_8,
+ CPCAP_IRQ_UC_PRIMACRO_9,
+ CPCAP_IRQ_UC_PRIMACRO_10,
+ CPCAP_IRQ_UC_PRIMACRO_11,
+ CPCAP_IRQ_UC_PRIMACRO_12,
+ CPCAP_IRQ_UC_PRIMACRO_13,
+ CPCAP_IRQ_UC_PRIMACRO_14,
+ CPCAP_IRQ_UC_PRIMACRO_15,
+ CPCAP_IRQ__NUM
+};
+
+enum cpcap_adc_bank0 {
+ CPCAP_ADC_AD0_BATTDETB,
+ CPCAP_ADC_BATTP,
+ CPCAP_ADC_VBUS,
+ CPCAP_ADC_AD3,
+ CPCAP_ADC_BPLUS_AD4,
+ CPCAP_ADC_CHG_ISENSE,
+ CPCAP_ADC_BATTI_ADC,
+ CPCAP_ADC_USB_ID,
+
+ CPCAP_ADC_BANK0_NUM,
+};
+
+enum cpcap_adc_bank1 {
+ CPCAP_ADC_AD8,
+ CPCAP_ADC_AD9,
+ CPCAP_ADC_LICELL,
+ CPCAP_ADC_HV_BATTP,
+ CPCAP_ADC_TSX1_AD12,
+ CPCAP_ADC_TSX2_AD13,
+ CPCAP_ADC_TSY1_AD14,
+ CPCAP_ADC_TSY2_AD15,
+
+ CPCAP_ADC_BANK1_NUM,
+};
+
+enum cpcap_adc_format {
+ CPCAP_ADC_FORMAT_RAW,
+ CPCAP_ADC_FORMAT_PHASED,
+ CPCAP_ADC_FORMAT_CONVERTED,
+};
+
+enum cpcap_adc_timing {
+ CPCAP_ADC_TIMING_IMM,
+ CPCAP_ADC_TIMING_IN,
+ CPCAP_ADC_TIMING_OUT,
+};
+
+enum cpcap_adc_type {
+ CPCAP_ADC_TYPE_BANK_0,
+ CPCAP_ADC_TYPE_BANK_1,
+ CPCAP_ADC_TYPE_BATT_PI,
+};
+
+enum cpcap_macro {
+ CPCAP_MACRO_ROMR,
+ CPCAP_MACRO_RAMW,
+ CPCAP_MACRO_RAMR,
+ CPCAP_MACRO_USEROFF,
+ CPCAP_MACRO_4,
+ CPCAP_MACRO_5,
+ CPCAP_MACRO_6,
+ CPCAP_MACRO_7,
+ CPCAP_MACRO_8,
+ CPCAP_MACRO_9,
+ CPCAP_MACRO_10,
+ CPCAP_MACRO_11,
+ CPCAP_MACRO_12,
+ CPCAP_MACRO_13,
+ CPCAP_MACRO_14,
+ CPCAP_MACRO_15,
+
+ CPCAP_MACRO__END,
+};
+
+enum cpcap_vendor {
+ CPCAP_VENDOR_ST,
+ CPCAP_VENDOR_TI,
+};
+
+enum cpcap_revision {
+ CPCAP_REVISION_1_0 = 0x08,
+ CPCAP_REVISION_1_1 = 0x09,
+ CPCAP_REVISION_2_0 = 0x10,
+ CPCAP_REVISION_2_1 = 0x11,
+};
+
+enum cpcap_batt_usb_model {
+ CPCAP_BATT_USB_MODEL_NONE,
+ CPCAP_BATT_USB_MODEL_USB,
+ CPCAP_BATT_USB_MODEL_FACTORY,
+};
+
+struct cpcap_spi_init_data {
+ enum cpcap_reg reg;
+ unsigned short data;
+};
+
+struct cpcap_adc_ato {
+ unsigned short ato_in;
+ unsigned short atox_in;
+ unsigned short adc_ps_factor_in;
+ unsigned short atox_ps_factor_in;
+ unsigned short ato_out;
+ unsigned short atox_out;
+ unsigned short adc_ps_factor_out;
+ unsigned short atox_ps_factor_out;
+};
+
+struct cpcap_batt_data {
+ int status;
+ int health;
+ int present;
+ int capacity;
+ int batt_volt;
+ int batt_temp;
+};
+
+struct cpcap_batt_ac_data {
+ int online;
+};
+
+struct cpcap_batt_usb_data {
+ int online;
+ int current_now;
+ enum cpcap_batt_usb_model model;
+};
+
+struct cpcap_device;
+
+struct cpcap_adc_us_request {
+ enum cpcap_adc_format format;
+ enum cpcap_adc_timing timing;
+ enum cpcap_adc_type type;
+ int status;
+ int result[CPCAP_ADC_BANK0_NUM];
+};
+
+struct cpcap_adc_phase {
+ signed char offset_batti;
+ unsigned char slope_batti;
+ signed char offset_chrgi;
+ unsigned char slope_chrgi;
+ signed char offset_battp;
+ unsigned char slope_battp;
+ signed char offset_bp;
+ unsigned char slope_bp;
+ signed char offset_battt;
+ unsigned char slope_battt;
+ signed char offset_chrgv;
+ unsigned char slope_chrgv;
+};
+
+struct cpcap_regacc {
+ unsigned short reg;
+ unsigned short value;
+ unsigned short mask;
+};
+
+struct cpcap_whisper_request {
+ unsigned int cmd;
+ char dock_id[CPCAP_WHISPER_ID_SIZE];
+ char dock_prop[CPCAP_WHISPER_PROP_SIZE];
+};
+
+#define CPCAP_IOCTL_TEST_READ_REG _IOWR(0, CPCAP_IOCTL_NUM_TEST_READ_REG, struct cpcap_regacc*)
+
+#define CPCAP_IOCTL_TEST_WRITE_REG _IOWR(0, CPCAP_IOCTL_NUM_TEST_WRITE_REG, struct cpcap_regacc*)
+
+#define CPCAP_IOCTL_ADC_PHASE _IOWR(0, CPCAP_IOCTL_NUM_ADC_PHASE, struct cpcap_adc_phase*)
+
+#define CPCAP_IOCTL_BATT_DISPLAY_UPDATE _IOW(0, CPCAP_IOCTL_NUM_BATT_DISPLAY_UPDATE, struct cpcap_batt_data*)
+
+#define CPCAP_IOCTL_BATT_ATOD_ASYNC _IOW(0, CPCAP_IOCTL_NUM_BATT_ATOD_ASYNC, struct cpcap_adc_us_request*)
+
+#define CPCAP_IOCTL_BATT_ATOD_SYNC _IOWR(0, CPCAP_IOCTL_NUM_BATT_ATOD_SYNC, struct cpcap_adc_us_request*)
+
+#define CPCAP_IOCTL_BATT_ATOD_READ _IOWR(0, CPCAP_IOCTL_NUM_BATT_ATOD_READ, struct cpcap_adc_us_request*)
+
+#define CPCAP_IOCTL_UC_MACRO_START _IOWR(0, CPCAP_IOCTL_NUM_UC_MACRO_START, enum cpcap_macro)
+
+#define CPCAP_IOCTL_UC_MACRO_STOP _IOWR(0, CPCAP_IOCTL_NUM_UC_MACRO_STOP, enum cpcap_macro)
+
+#define CPCAP_IOCTL_UC_GET_VENDOR _IOWR(0, CPCAP_IOCTL_NUM_UC_GET_VENDOR, enum cpcap_vendor)
+
+#define CPCAP_IOCTL_UC_SET_TURBO_MODE _IOW(0, CPCAP_IOCTL_NUM_UC_SET_TURBO_MODE, unsigned short)
+
+#define CPCAP_IOCTL_ACCY_WHISPER _IOW(0, CPCAP_IOCTL_NUM_ACCY_WHISPER, struct cpcap_whisper_request*)
+
+#endif
+
diff --git a/libc/kernel/common/linux/tegra_audio.h b/libc/kernel/common/linux/tegra_audio.h
new file mode 100644
index 0000000..e18ce11
--- /dev/null
+++ b/libc/kernel/common/linux/tegra_audio.h
@@ -0,0 +1,43 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef _TEGRA_AUDIO_H
+#define _TEGRA_AUDIO_H
+
+#include <linux/ioctl.h>
+
+#define TEGRA_AUDIO_MAGIC 't'
+
+#define TEGRA_AUDIO_IN_START _IO(TEGRA_AUDIO_MAGIC, 0)
+#define TEGRA_AUDIO_IN_STOP _IO(TEGRA_AUDIO_MAGIC, 1)
+
+struct tegra_audio_in_config {
+ int rate;
+ int stereo;
+};
+
+#define TEGRA_AUDIO_IN_SET_CONFIG _IOW(TEGRA_AUDIO_MAGIC, 2, const struct tegra_audio_in_config *)
+#define TEGRA_AUDIO_IN_GET_CONFIG _IOR(TEGRA_AUDIO_MAGIC, 3, struct tegra_audio_in_config *)
+
+#define TEGRA_AUDIO_IN_SET_NUM_BUFS _IOW(TEGRA_AUDIO_MAGIC, 4, const unsigned int *)
+#define TEGRA_AUDIO_IN_GET_NUM_BUFS _IOW(TEGRA_AUDIO_MAGIC, 5, unsigned int *)
+#define TEGRA_AUDIO_OUT_SET_NUM_BUFS _IOW(TEGRA_AUDIO_MAGIC, 6, const unsigned int *)
+#define TEGRA_AUDIO_OUT_GET_NUM_BUFS _IOW(TEGRA_AUDIO_MAGIC, 7, unsigned int *)
+
+#define TEGRA_AUDIO_OUT_FLUSH _IO(TEGRA_AUDIO_MAGIC, 10)
+
+#define TEGRA_AUDIO_BIT_FORMAT_DEFAULT 0
+#define TEGRA_AUDIO_BIT_FORMAT_DSP 1
+#define TEGRA_AUDIO_SET_BIT_FORMAT _IOW(TEGRA_AUDIO_MAGIC, 11, const unsigned int *)
+#define TEGRA_AUDIO_GET_BIT_FORMAT _IOR(TEGRA_AUDIO_MAGIC, 12, unsigned int *)
+
+#endif
+
diff --git a/libc/kernel/common/linux/tegra_avp.h b/libc/kernel/common/linux/tegra_avp.h
new file mode 100644
index 0000000..c4a0cbd
--- /dev/null
+++ b/libc/kernel/common/linux/tegra_avp.h
@@ -0,0 +1,38 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __LINUX_TEGRA_AVP_H
+#define __LINUX_TEGRA_AVP_H
+
+#include <linux/ioctl.h>
+#include <linux/types.h>
+
+#define TEGRA_AVP_LIB_MAX_NAME 32
+#define TEGRA_AVP_LIB_MAX_ARGS 220
+
+struct tegra_avp_lib {
+ char name[TEGRA_AVP_LIB_MAX_NAME];
+ void __user *args;
+ size_t args_len;
+ int greedy;
+ unsigned long handle;
+};
+
+#define TEGRA_AVP_IOCTL_MAGIC 'r'
+
+#define TEGRA_AVP_IOCTL_LOAD_LIB _IOWR(TEGRA_AVP_IOCTL_MAGIC, 0x40, struct tegra_avp_lib)
+#define TEGRA_AVP_IOCTL_UNLOAD_LIB _IOW(TEGRA_AVP_IOCTL_MAGIC, 0x41, unsigned long)
+
+#define TEGRA_AVP_IOCTL_MIN_NR _IOC_NR(TEGRA_AVP_IOCTL_LOAD_LIB)
+#define TEGRA_AVP_IOCTL_MAX_NR _IOC_NR(TEGRA_AVP_IOCTL_UNLOAD_LIB)
+
+#endif
+
diff --git a/libc/kernel/common/linux/tegra_rpc.h b/libc/kernel/common/linux/tegra_rpc.h
new file mode 100644
index 0000000..e3c8bf2
--- /dev/null
+++ b/libc/kernel/common/linux/tegra_rpc.h
@@ -0,0 +1,35 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __LINUX_TEGRA_RPC_H
+#define __LINUX_TEGRA_RPC_H
+
+#define TEGRA_RPC_MAX_MSG_LEN 256
+
+#define TEGRA_RPC_MAX_NAME_LEN 17
+
+struct tegra_rpc_port_desc {
+ char name[TEGRA_RPC_MAX_NAME_LEN];
+ int notify_fd;
+};
+
+#define TEGRA_RPC_IOCTL_MAGIC 'r'
+
+#define TEGRA_RPC_IOCTL_PORT_CREATE _IOW(TEGRA_RPC_IOCTL_MAGIC, 0x20, struct tegra_rpc_port_desc)
+#define TEGRA_RPC_IOCTL_PORT_GET_NAME _IOR(TEGRA_RPC_IOCTL_MAGIC, 0x21, char *)
+#define TEGRA_RPC_IOCTL_PORT_CONNECT _IOR(TEGRA_RPC_IOCTL_MAGIC, 0x22, long)
+#define TEGRA_RPC_IOCTL_PORT_LISTEN _IOR(TEGRA_RPC_IOCTL_MAGIC, 0x23, long)
+
+#define TEGRA_RPC_IOCTL_MIN_NR _IOC_NR(TEGRA_RPC_IOCTL_PORT_CREATE)
+#define TEGRA_RPC_IOCTL_MAX_NR _IOC_NR(TEGRA_RPC_IOCTL_PORT_LISTEN)
+
+#endif
+
diff --git a/libc/kernel/common/linux/tegra_sema.h b/libc/kernel/common/linux/tegra_sema.h
new file mode 100644
index 0000000..bb11298
--- /dev/null
+++ b/libc/kernel/common/linux/tegra_sema.h
@@ -0,0 +1,24 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __LINUX_TEGRA_SEMA_H
+#define __LINUX_TEGRA_SEMA_H
+
+#define TEGRA_SEMA_IOCTL_MAGIC 'r'
+
+#define TEGRA_SEMA_IOCTL_WAIT _IOW(TEGRA_SEMA_IOCTL_MAGIC, 0x30, long *)
+#define TEGRA_SEMA_IOCTL_SIGNAL _IO(TEGRA_SEMA_IOCTL_MAGIC, 0x31)
+
+#define TEGRA_SEMA_IOCTL_MIN_NR _IOC_NR(TEGRA_SEMA_IOCTL_WAIT)
+#define TEGRA_SEMA_IOCTL_MAX_NR _IOC_NR(TEGRA_SEMA_IOCTL_SIGNAL)
+
+#endif
+
diff --git a/libc/kernel/common/linux/tegrafb.h b/libc/kernel/common/linux/tegrafb.h
new file mode 100644
index 0000000..b8e79ae
--- /dev/null
+++ b/libc/kernel/common/linux/tegrafb.h
@@ -0,0 +1,87 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef _LINUX_TEGRAFB_H_
+#define _LINUX_TEGRAFB_H_
+
+#include <linux/fb.h>
+#include <linux/types.h>
+#include <asm/ioctl.h>
+
+#define TEGRA_FB_WIN_FMT_P1 0
+#define TEGRA_FB_WIN_FMT_P2 1
+#define TEGRA_FB_WIN_FMT_P4 2
+#define TEGRA_FB_WIN_FMT_P8 3
+#define TEGRA_FB_WIN_FMT_B4G4R4A4 4
+#define TEGRA_FB_WIN_FMT_B5G5R5A 5
+#define TEGRA_FB_WIN_FMT_B5G6R5 6
+#define TEGRA_FB_WIN_FMT_AB5G5R5 7
+#define TEGRA_FB_WIN_FMT_B8G8R8A8 12
+#define TEGRA_FB_WIN_FMT_R8G8B8A8 13
+#define TEGRA_FB_WIN_FMT_B6x2G6x2R6x2A8 14
+#define TEGRA_FB_WIN_FMT_R6x2G6x2B6x2A8 15
+#define TEGRA_FB_WIN_FMT_YCbCr422 16
+#define TEGRA_FB_WIN_FMT_YUV422 17
+#define TEGRA_FB_WIN_FMT_YCbCr420P 18
+#define TEGRA_FB_WIN_FMT_YUV420P 19
+#define TEGRA_FB_WIN_FMT_YCbCr422P 20
+#define TEGRA_FB_WIN_FMT_YUV422P 21
+#define TEGRA_FB_WIN_FMT_YCbCr422R 22
+#define TEGRA_FB_WIN_FMT_YUV422R 23
+#define TEGRA_FB_WIN_FMT_YCbCr422RA 24
+#define TEGRA_FB_WIN_FMT_YUV422RA 25
+
+#define TEGRA_FB_WIN_BLEND_NONE 0
+#define TEGRA_FB_WIN_BLEND_PREMULT 1
+#define TEGRA_FB_WIN_BLEND_COVERAGE 2
+
+struct tegra_fb_windowattr {
+ __s32 index;
+ __u32 buff_id;
+ __u32 blend;
+ __u32 offset;
+ __u32 offset_u;
+ __u32 offset_v;
+ __u32 stride;
+ __u32 stride_uv;
+ __u32 pixformat;
+ __u32 x;
+ __u32 y;
+ __u32 w;
+ __u32 h;
+ __u32 out_x;
+ __u32 out_y;
+ __u32 out_w;
+ __u32 out_h;
+ __u32 z;
+ __u32 pre_syncpt_id;
+ __u32 pre_syncpt_val;
+};
+
+#define TEGRA_FB_FLIP_N_WINDOWS 3
+
+struct tegra_fb_flip_args {
+ struct tegra_fb_windowattr win[TEGRA_FB_FLIP_N_WINDOWS];
+ __u32 post_syncpt_id;
+ __u32 post_syncpt_val;
+};
+
+struct tegra_fb_modedb {
+ struct fb_var_screeninfo *modedb;
+ __u32 modedb_len;
+};
+
+#define FBIO_TEGRA_SET_NVMAP_FD _IOW('F', 0x40, __u32)
+#define FBIO_TEGRA_FLIP _IOW('F', 0x41, struct tegra_fb_flip_args)
+#define FBIO_TEGRA_GET_MODEDB _IOWR('F', 0x42, struct tegra_fb_modedb)
+
+#endif
+
diff --git a/libc/kernel/common/linux/tty.h b/libc/kernel/common/linux/tty.h
index b28791c..b1f2eab 100644
--- a/libc/kernel/common/linux/tty.h
+++ b/libc/kernel/common/linux/tty.h
@@ -12,4 +12,6 @@
#ifndef _LINUX_TTY_H
#define _LINUX_TTY_H
+#define N_CAIF 20
+
#endif
diff --git a/libc/kernel/common/linux/ublock.h b/libc/kernel/common/linux/ublock.h
new file mode 100644
index 0000000..aa19a81
--- /dev/null
+++ b/libc/kernel/common/linux/ublock.h
@@ -0,0 +1,81 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __UBLOCK_H_
+#define __UBLOCK_H_
+
+#include <linux/types.h>
+
+#define UBLOCK_VERSION 0
+
+enum {
+ UBLOCK_INIT_IN = 0,
+ UBLOCK_INIT_OUT = 1,
+ UBLOCK_READY_IN = 2,
+ UBLOCK_READY_OUT = 3,
+ UBLOCK_READ_IN = 4,
+ UBLOCK_READ_OUT = 5,
+ UBLOCK_WRITE_IN = 6,
+ UBLOCK_WRITE_OUT = 7,
+};
+
+struct ublock_in_header {
+ __u32 seq;
+ __u32 opcode;
+};
+
+struct ublock_out_header {
+ __u32 seq;
+ __u32 opcode;
+};
+
+struct ublock_init_in {
+ __u32 version;
+ __u32 max_buf;
+ __u32 index;
+};
+
+struct ublock_init_out {
+ __u32 version;
+ __u32 max_buf;
+ __u64 size;
+};
+
+struct ublock_ready_in {
+ __u32 _unused;
+};
+
+struct ublock_ready_out {
+ __u32 _unused;
+};
+
+struct ublock_read_in {
+ __u64 offset;
+ __u64 length;
+};
+
+struct ublock_read_out {
+ __s32 status;
+ __u8 data[];
+};
+
+struct ublock_write_in {
+ __u64 offset;
+ __u64 length;
+ __u8 data[];
+};
+
+struct ublock_write_out {
+ __s32 status;
+};
+
+#endif
+
diff --git a/libc/kernel/common/linux/usb/f_mtp.h b/libc/kernel/common/linux/usb/f_mtp.h
new file mode 100644
index 0000000..a9e37c2
--- /dev/null
+++ b/libc/kernel/common/linux/usb/f_mtp.h
@@ -0,0 +1,42 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __LINUX_USB_F_MTP_H
+#define __LINUX_USB_F_MTP_H
+
+#define MTP_INTERFACE_MODE_MTP 0
+#define MTP_INTERFACE_MODE_PTP 1
+
+struct mtp_file_range {
+
+ int fd;
+
+ loff_t offset;
+
+ int64_t length;
+};
+
+struct mtp_event {
+
+ size_t length;
+
+ void *data;
+};
+
+#define MTP_SEND_FILE _IOW('M', 0, struct mtp_file_range)
+
+#define MTP_RECEIVE_FILE _IOW('M', 1, struct mtp_file_range)
+
+#define MTP_SET_INTERFACE_MODE _IOW('M', 2, int)
+
+#define MTP_SEND_EVENT _IOW('M', 3, struct mtp_event)
+
+#endif
diff --git a/libc/kernel/common/media/ov5650.h b/libc/kernel/common/media/ov5650.h
new file mode 100644
index 0000000..3603dc2
--- /dev/null
+++ b/libc/kernel/common/media/ov5650.h
@@ -0,0 +1,63 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __OV5650_H__
+#define __OV5650_H__
+
+#include <linux/ioctl.h>
+
+#define OV5650_IOCTL_SET_MODE _IOW('o', 1, struct ov5650_mode)
+#define OV5650_IOCTL_SET_FRAME_LENGTH _IOW('o', 2, __u32)
+#define OV5650_IOCTL_SET_COARSE_TIME _IOW('o', 3, __u32)
+#define OV5650_IOCTL_SET_GAIN _IOW('o', 4, __u16)
+#define OV5650_IOCTL_GET_STATUS _IOR('o', 5, __u8)
+#define OV5650_IOCTL_GET_OTP _IOR('o', 6, struct ov5650_otp_data)
+#define OV5650_IOCTL_TEST_PATTERN _IOW('o', 7, enum ov5650_test_pattern)
+
+enum ov5650_test_pattern {
+ TEST_PATTERN_NONE,
+ TEST_PATTERN_COLORBARS,
+ TEST_PATTERN_CHECKERBOARD
+};
+
+struct ov5650_otp_data {
+
+ __u8 sensor_serial_num[6];
+ __u8 part_num[8];
+ __u8 lens_id[1];
+ __u8 manufacture_id[2];
+ __u8 factory_id[2];
+ __u8 manufacture_date[9];
+ __u8 manufacture_line[2];
+
+ __u32 module_serial_num;
+ __u8 focuser_liftoff[2];
+ __u8 focuser_macro[2];
+ __u8 reserved1[12];
+ __u8 shutter_cal[16];
+ __u8 reserved2[183];
+
+ __u16 crc;
+ __u8 reserved3[3];
+ __u8 auto_load[2];
+} __attribute__ ((packed));
+
+struct ov5650_mode {
+ int xres;
+ int yres;
+ __u32 frame_length;
+ __u32 coarse_time;
+ __u16 gain;
+};
+
+#endif
+
+
diff --git a/libc/kernel/common/media/soc2030.h b/libc/kernel/common/media/soc2030.h
new file mode 100644
index 0000000..ad0ddfc
--- /dev/null
+++ b/libc/kernel/common/media/soc2030.h
@@ -0,0 +1,86 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __SOC2030_H__
+#define __SOC2030_H__
+
+#include <linux/ioctl.h>
+
+#define SOC2030_IOCTL_SET_MODE _IOWR('o', 1, struct soc2030_mode)
+#define SOC2030_IOCTL_GET_STATUS _IOC(_IOC_READ, 'o', 2, 10)
+#define SOC2030_IOCTL_SET_PRIVATE _IOWR('o', 3, struct soc2030_regs)
+#define SOC2030_IOCTL_GET_MODES _IO('o', 4)
+#define SOC2030_IOCTL_GET_NUM_MODES _IOR('o', 5, unsigned int)
+#define SOC2030_IOCTL_SET_EFFECT _IOWR('o', 6, unsigned int)
+#define SOC2030_IOCTL_SET_WHITEBALANCE _IOWR('o', 7, unsigned int)
+#define SOC2030_IOCTL_SET_EXP_COMP _IOWR('o', 8, int)
+
+#define SOC2030_POLL_WAITMS 50
+#define SOC2030_MAX_RETRIES 3
+#define SOC2030_POLL_RETRIES 5
+
+#define SOC2030_MAX_PRIVATE_SIZE 1024
+#define SOC2030_MAX_NUM_MODES 6
+
+#define SOC_EV_MAX 2
+#define SOC_EV_MIN -2
+#define EXP_TARGET 0x32
+
+enum {
+ REG_TABLE_END,
+ WRITE_REG_DATA,
+ WRITE_REG_BIT_H,
+ WRITE_REG_BIT_L,
+ POLL_REG_DATA,
+ POLL_REG_BIT_H,
+ POLL_REG_BIT_L,
+ WRITE_VAR_DATA,
+ POLL_VAR_DATA,
+ DELAY_MS,
+};
+
+enum {
+ EFFECT_NONE,
+ EFFECT_BW,
+ EFFECT_NEGATIVE,
+ EFFECT_POSTERIZE,
+ EFFECT_SEPIA,
+ EFFECT_SOLARIZE,
+ EFFECT_AQUA,
+ EFFECT_MAX,
+};
+
+enum {
+ WB_AUTO,
+ WB_INCANDESCENT,
+ WB_FLUORESCENT,
+ WB_DAYLIGHT,
+ WB_CLOUDYDAYLIGHT,
+ WB_NIGHT,
+ WB_MAX,
+};
+
+struct soc2030_regs {
+ __u8 op;
+ __u16 addr;
+ __u16 val;
+};
+
+struct soc2030_mode {
+ int xres;
+ int yres;
+ int fps;
+ struct soc2030_regs *regset;
+};
+
+#endif
+
+
diff --git a/libc/kernel/common/media/tegra_camera.h b/libc/kernel/common/media/tegra_camera.h
new file mode 100644
index 0000000..0f63035
--- /dev/null
+++ b/libc/kernel/common/media/tegra_camera.h
@@ -0,0 +1,33 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ *** This header was automatically generated from a Linux kernel header
+ *** of the same name, to make information necessary for userspace to
+ *** call into the kernel available to libc. It contains only constants,
+ *** structures, and macros generated from the original header, and thus,
+ *** contains no copyrightable information.
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+enum {
+ TEGRA_CAMERA_MODULE_ISP = 0,
+ TEGRA_CAMERA_MODULE_VI,
+ TEGRA_CAMERA_MODULE_CSI,
+};
+
+enum {
+ TEGRA_CAMERA_VI_CLK,
+ TEGRA_CAMERA_VI_SENSOR_CLK,
+};
+
+struct tegra_camera_clk_info {
+ uint id;
+ uint clk_id;
+ unsigned long rate;
+};
+
+#define TEGRA_CAMERA_IOCTL_ENABLE _IOWR('i', 1, uint)
+#define TEGRA_CAMERA_IOCTL_DISABLE _IOWR('i', 2, uint)
+#define TEGRA_CAMERA_IOCTL_CLK_SET_RATE _IOWR('i', 3, struct tegra_camera_clk_info)
+#define TEGRA_CAMERA_IOCTL_RESET _IOWR('i', 4, uint)
+
diff --git a/libc/kernel/tools/clean_header.py b/libc/kernel/tools/clean_header.py
index 28cb05e..dad9120 100755
--- a/libc/kernel/tools/clean_header.py
+++ b/libc/kernel/tools/clean_header.py
@@ -71,6 +71,7 @@
list.removeEmptyLines()
list.removeMacroDefines( kernel_ignored_macros )
list.insertDisclaimer( kernel.kernel_disclaimer )
+ list.replaceTokens( kernel_token_replacements )
out = StringOutput()
list.write(out)
diff --git a/libc/kernel/tools/cpp.py b/libc/kernel/tools/cpp.py
index 4b4bd38..8828a5d 100644
--- a/libc/kernel/tools/cpp.py
+++ b/libc/kernel/tools/cpp.py
@@ -1863,6 +1863,16 @@
tokens = tokens[:-1] # remove trailing tokLN
self.blocks = [ Block(tokens) ] + self.blocks
+ def replaceTokens(self,replacements=dict()):
+ """replace tokens according to the given dict
+ """
+ for b in self.blocks:
+ if not b.isDirective():
+ for tok in b.tokens:
+ if tok.id == tokIDENT:
+ if tok.value in replacements:
+ tok.value = replacements[tok.value]
+
class BlockParser:
"""a class used to convert an input source file into a BlockList object"""
diff --git a/libc/kernel/tools/defaults.py b/libc/kernel/tools/defaults.py
index 4227de7..ca7e6bb 100644
--- a/libc/kernel/tools/defaults.py
+++ b/libc/kernel/tools/defaults.py
@@ -43,6 +43,11 @@
"x86": {"__i386__": "1"},
}
+# Replace tokens in the output according to this mapping
+kernel_token_replacements = {
+ {"asm": "__asm__"},
+ }
+
# this is the set of known static inline functions that we want to keep
# in the final ARM headers. this is only used to keep optimized byteswapping
# static functions and stuff like that.
@@ -71,6 +76,7 @@
"__cmsg_nxthdr", # linux/socket.h
"cmsg_nxthdr", # linux/socket.h
"ipt_get_target",
+ "ip6t_get_target",
]
)
diff --git a/libc/netbsd/gethnamaddr.c b/libc/netbsd/gethnamaddr.c
index 1c219b2..3ebe53e 100644
--- a/libc/netbsd/gethnamaddr.c
+++ b/libc/netbsd/gethnamaddr.c
@@ -104,9 +104,9 @@
static void map_v4v6_hostent(struct hostent *, char **, char *);
static void addrsort(char **, int, res_state);
-void _sethtent(int);
-void _endhtent(void);
-struct hostent *_gethtent(void);
+static void _sethtent(int);
+static void _endhtent(void);
+static struct hostent *_gethtent(void);
void ht_sethostent(int);
void ht_endhostent(void);
struct hostent *ht_gethostbyname(char *);
@@ -114,11 +114,11 @@
void dns_service(void);
#undef dn_skipname
int dn_skipname(const u_char *, const u_char *);
-int _gethtbyaddr(void *, void *, va_list);
-int _gethtbyname(void *, void *, va_list);
-struct hostent *_gethtbyname2(const char *, int);
-int _dns_gethtbyaddr(void *, void *, va_list);
-int _dns_gethtbyname(void *, void *, va_list);
+static int _gethtbyaddr(void *, void *, va_list);
+static int _gethtbyname(void *, void *, va_list);
+static struct hostent *_gethtbyname2(const char *, int);
+static int _dns_gethtbyaddr(void *, void *, va_list);
+static int _dns_gethtbyname(void *, void *, va_list);
static struct hostent *gethostbyname_internal(const char *, int, res_state);
@@ -692,7 +692,7 @@
return hp;
}
-void
+static void
_sethtent(int f)
{
res_static rs = __res_get_static();
@@ -704,7 +704,7 @@
rs->stayopen = f;
}
-void
+static void
_endhtent(void)
{
res_static rs = __res_get_static();
@@ -716,7 +716,7 @@
}
}
-struct hostent *
+static struct hostent *
_gethtent(void)
{
char *p;
@@ -829,7 +829,7 @@
return NS_SUCCESS;
}
-struct hostent *
+static struct hostent *
_gethtbyname2(const char *name, int af)
{
struct hostent *p;
@@ -920,7 +920,7 @@
}
/*ARGSUSED*/
-int
+static int
_gethtbyaddr(void *rv, void *cb_data, va_list ap)
{
struct hostent *p;
@@ -1053,7 +1053,7 @@
}
/*ARGSUSED*/
-int
+static int
_dns_gethtbyname(void *rv, void *cb_data, va_list ap)
{
querybuf *buf;
@@ -1113,7 +1113,7 @@
}
/*ARGSUSED*/
-int
+static int
_dns_gethtbyaddr(void *rv, void *cb_data, va_list ap)
{
char qbuf[MAXDNAME + 1], *qp, *ep;
diff --git a/libc/netbsd/net/getaddrinfo.c b/libc/netbsd/net/getaddrinfo.c
index e4d8c56..bb6645c 100644
--- a/libc/netbsd/net/getaddrinfo.c
+++ b/libc/netbsd/net/getaddrinfo.c
@@ -77,10 +77,13 @@
* friends.
*/
+#include <fcntl.h>
#include <sys/cdefs.h>
#include <sys/types.h>
+#include <sys/stat.h>
#include <sys/param.h>
#include <sys/socket.h>
+#include <sys/un.h>
#include <net/if.h>
#include <netinet/in.h>
#include <arpa/inet.h>
@@ -100,6 +103,10 @@
#include <stdarg.h>
#include "nsswitch.h"
+#ifdef ANDROID_CHANGES
+#include <sys/system_properties.h>
+#endif /* ANDROID_CHANGES */
+
typedef union sockaddr_union {
struct sockaddr generic;
struct sockaddr_in in;
@@ -391,6 +398,190 @@
return _test_connect(PF_INET, &addr.generic, sizeof(addr.in));
}
+// Returns 0 on success, else returns non-zero on error (in which case
+// getaddrinfo should continue as normal)
+static int
+android_getaddrinfo_proxy(
+ const char *hostname, const char *servname,
+ const struct addrinfo *hints, struct addrinfo **res)
+{
+ int sock;
+ const int one = 1;
+ struct sockaddr_un proxy_addr;
+ const char* cache_mode = getenv("ANDROID_DNS_MODE");
+ FILE* proxy = NULL;
+ int success = 0;
+
+ // Clear this at start, as we use its non-NULLness later (in the
+ // error path) to decide if we have to free up any memory we
+ // allocated in the process (before failing).
+ *res = NULL;
+
+ if (cache_mode != NULL && strcmp(cache_mode, "local") == 0) {
+ // Don't use the proxy in local mode. This is used by the
+ // proxy itself.
+ return -1;
+ }
+
+ // Temporary cautious hack to disable the DNS proxy for processes
+ // requesting special treatment. Ideally the DNS proxy should
+ // accomodate these apps, though.
+ char propname[PROP_NAME_MAX];
+ char propvalue[PROP_VALUE_MAX];
+ snprintf(propname, sizeof(propname), "net.dns1.%d", getpid());
+ if (__system_property_get(propname, propvalue) > 0) {
+ return -1;
+ }
+
+ // Bogus things we can't serialize. Don't use the proxy.
+ if ((hostname != NULL &&
+ strcspn(hostname, " \n\r\t^'\"") != strlen(hostname)) ||
+ (servname != NULL &&
+ strcspn(servname, " \n\r\t^'\"") != strlen(servname))) {
+ return -1;
+ }
+
+ sock = socket(AF_UNIX, SOCK_STREAM, 0);
+ if (sock < 0) {
+ return -1;
+ }
+
+ setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &one, sizeof(one));
+ memset(&proxy_addr, 0, sizeof(proxy_addr));
+ proxy_addr.sun_family = AF_UNIX;
+ strlcpy(proxy_addr.sun_path, "/dev/socket/dnsproxyd",
+ sizeof(proxy_addr.sun_path));
+ if (TEMP_FAILURE_RETRY(connect(sock,
+ (const struct sockaddr*) &proxy_addr,
+ sizeof(proxy_addr))) != 0) {
+ close(sock);
+ return -1;
+ }
+
+ // Send the request.
+ proxy = fdopen(sock, "r+");
+ if (fprintf(proxy, "getaddrinfo %s %s %d %d %d %d",
+ hostname == NULL ? "^" : hostname,
+ servname == NULL ? "^" : servname,
+ hints == NULL ? -1 : hints->ai_flags,
+ hints == NULL ? -1 : hints->ai_family,
+ hints == NULL ? -1 : hints->ai_socktype,
+ hints == NULL ? -1 : hints->ai_protocol) < 0) {
+ goto exit;
+ }
+ // literal NULL byte at end, required by FrameworkListener
+ if (fputc(0, proxy) == EOF ||
+ fflush(proxy) != 0) {
+ goto exit;
+ }
+
+ int remote_rv;
+ if (fread(&remote_rv, sizeof(int), 1, proxy) != 1) {
+ goto exit;
+ }
+
+ if (remote_rv != 0) {
+ goto exit;
+ }
+
+ struct addrinfo* ai = NULL;
+ struct addrinfo** nextres = res;
+ while (1) {
+ uint32_t addrinfo_len;
+ if (fread(&addrinfo_len, sizeof(addrinfo_len),
+ 1, proxy) != 1) {
+ break;
+ }
+ addrinfo_len = ntohl(addrinfo_len);
+ if (addrinfo_len == 0) {
+ success = 1;
+ break;
+ }
+
+ if (addrinfo_len < sizeof(struct addrinfo)) {
+ break;
+ }
+ struct addrinfo* ai = calloc(1, addrinfo_len +
+ sizeof(struct sockaddr_storage));
+ if (ai == NULL) {
+ break;
+ }
+
+ if (fread(ai, addrinfo_len, 1, proxy) != 1) {
+ // Error; fall through.
+ break;
+ }
+
+ // Zero out the pointer fields we copied which aren't
+ // valid in this address space.
+ ai->ai_addr = NULL;
+ ai->ai_canonname = NULL;
+ ai->ai_next = NULL;
+
+ // struct sockaddr
+ uint32_t addr_len;
+ if (fread(&addr_len, sizeof(addr_len), 1, proxy) != 1) {
+ break;
+ }
+ addr_len = ntohl(addr_len);
+ if (addr_len != 0) {
+ if (addr_len > sizeof(struct sockaddr_storage)) {
+ // Bogus; too big.
+ break;
+ }
+ struct sockaddr* addr = (struct sockaddr*)(ai + 1);
+ if (fread(addr, addr_len, 1, proxy) != 1) {
+ break;
+ }
+ ai->ai_addr = addr;
+ }
+
+ // cannonname
+ uint32_t name_len;
+ if (fread(&name_len, sizeof(name_len), 1, proxy) != 1) {
+ break;
+ }
+ if (name_len != 0) {
+ ai->ai_canonname = (char*) malloc(name_len);
+ if (fread(ai->ai_canonname, name_len, 1, proxy) != 1) {
+ break;
+ }
+ if (ai->ai_canonname[name_len - 1] != '\0') {
+ // The proxy should be returning this
+ // NULL-terminated.
+ break;
+ }
+ }
+
+ *nextres = ai;
+ nextres = &ai->ai_next;
+ ai = NULL;
+ }
+
+ if (ai != NULL) {
+ // Clean up partially-built addrinfo that we never ended up
+ // attaching to the response.
+ freeaddrinfo(ai);
+ }
+exit:
+ if (proxy != NULL) {
+ fclose(proxy);
+ }
+
+ if (success) {
+ return 0;
+ }
+
+ // Proxy failed; fall through to local
+ // resolver case. But first clean up any
+ // memory we might've allocated.
+ if (*res) {
+ freeaddrinfo(*res);
+ *res = NULL;
+ }
+ return -1;
+}
+
int
getaddrinfo(const char *hostname, const char *servname,
const struct addrinfo *hints, struct addrinfo **res)
@@ -537,6 +728,13 @@
if (pai->ai_flags & AI_NUMERICHOST)
ERR(EAI_NONAME);
+ /*
+ * BEGIN ANDROID CHANGES; proxying to the cache
+ */
+ if (android_getaddrinfo_proxy(hostname, servname, hints, res) == 0) {
+ return 0;
+ }
+
/*
* hostname as alphabetical name.
* we would like to prefer AF_INET6 than AF_INET, so we'll make a
diff --git a/libc/netbsd/resolv/res_cache.c b/libc/netbsd/resolv/res_cache.c
index 2621a7b..84194c2 100644
--- a/libc/netbsd/resolv/res_cache.c
+++ b/libc/netbsd/resolv/res_cache.c
@@ -1143,7 +1143,7 @@
"*************************");
}
-struct resolv_cache*
+static struct resolv_cache*
_resolv_cache_create( void )
{
struct resolv_cache* cache;
diff --git a/libc/netbsd/resolv/res_data.c b/libc/netbsd/resolv/res_data.c
index e60ecfd..014c99b 100644
--- a/libc/netbsd/resolv/res_data.c
+++ b/libc/netbsd/resolv/res_data.c
@@ -46,6 +46,7 @@
#include <unistd.h>
+__LIBC_HIDDEN__
const char * const _res_opcodes[] = {
"QUERY",
"IQUERY",
@@ -82,7 +83,7 @@
int res_ourserver_p(const res_state, const struct sockaddr *);
#ifdef ANDROID_CHANGES
-int res_need_init() {
+static int res_need_init() {
return ((_nres.options & RES_INIT) == 0U) || res_get_dns_changed();
}
#else
diff --git a/libc/netbsd/resolv/res_debug.c b/libc/netbsd/resolv/res_debug.c
index 84c6afc..721e015 100644
--- a/libc/netbsd/resolv/res_debug.c
+++ b/libc/netbsd/resolv/res_debug.c
@@ -385,7 +385,7 @@
/*
* Names of message sections.
*/
-const struct res_sym __p_default_section_syms[] = {
+static const struct res_sym __p_default_section_syms[] = {
{ns_s_qd, "QUERY", (char *)0},
{ns_s_an, "ANSWER", (char *)0},
{ns_s_ns, "AUTHORITY", (char *)0},
@@ -393,7 +393,7 @@
{0, (char *)0, (char *)0}
};
-const struct res_sym __p_update_section_syms[] = {
+static const struct res_sym __p_update_section_syms[] = {
{S_ZONE, "ZONE", (char *)0},
{S_PREREQ, "PREREQUISITE", (char *)0},
{S_UPDATE, "UPDATE", (char *)0},
diff --git a/libc/netbsd/resolv/res_init.c b/libc/netbsd/resolv/res_init.c
index 81e570f..2158f20 100644
--- a/libc/netbsd/resolv/res_init.c
+++ b/libc/netbsd/resolv/res_init.c
@@ -113,8 +113,8 @@
#define DNS_PROP_NAME_PREFIX "net.dns"
#define DNS_CHANGE_PROP_NAME "net.dnschange"
#define DNS_SEARCH_PROP_NAME "net.dns.search"
-const prop_info *dns_change_prop;
-int dns_last_change_counter;
+static const prop_info *dns_change_prop;
+static int dns_last_change_counter;
static int _get_dns_change_count();
#else
#include <resolv.h>
@@ -170,7 +170,7 @@
}
#ifdef ANDROID_CHANGES
-int load_domain_search_list(res_state statp) {
+static int load_domain_search_list(res_state statp) {
char propvalue[PROP_VALUE_MAX];
register char *cp, **pp;
diff --git a/libc/netbsd/resolv/res_send.c b/libc/netbsd/resolv/res_send.c
index 696f8cf..b118956 100644
--- a/libc/netbsd/resolv/res_send.c
+++ b/libc/netbsd/resolv/res_send.c
@@ -222,7 +222,7 @@
* author:
* paul vixie, 29may94
*/
-int
+__LIBC_HIDDEN__ int
res_ourserver_p(const res_state statp, const struct sockaddr *sa) {
const struct sockaddr_in *inp, *srv;
const struct sockaddr_in6 *in6p, *srv6;
diff --git a/libc/netbsd/resolv/res_state.c b/libc/netbsd/resolv/res_state.c
index 3a2301d..3209b6f 100644
--- a/libc/netbsd/resolv/res_state.c
+++ b/libc/netbsd/resolv/res_state.c
@@ -134,6 +134,7 @@
return rt;
}
+__LIBC_HIDDEN__
struct __res_state _nres;
#if 0
diff --git a/libc/stdio/fgetln.c b/libc/stdio/fgetln.c
index 946e1b7..95a5b31 100644
--- a/libc/stdio/fgetln.c
+++ b/libc/stdio/fgetln.c
@@ -43,7 +43,7 @@
* so we add 1 here.
#endif
*/
-int
+static int
__slbexpand(FILE *fp, size_t newsize)
{
void *p;
diff --git a/libc/stdio/findfp.c b/libc/stdio/findfp.c
index 039293f..1d0f9c5 100644
--- a/libc/stdio/findfp.c
+++ b/libc/stdio/findfp.c
@@ -55,7 +55,7 @@
static struct __sfileext usualext[FOPEN_MAX - 3];
static struct glue uglue = { 0, FOPEN_MAX - 3, usual };
-struct __sfileext __sFext[3];
+static struct __sfileext __sFext[3];
FILE __sF[3] = {
std(__SRD, STDIN_FILENO), /* stdin */
std(__SWR, STDOUT_FILENO), /* stdout */
diff --git a/libc/stdio/flockfile.c b/libc/stdio/flockfile.c
index bfb081c..e8c74c5 100644
--- a/libc/stdio/flockfile.c
+++ b/libc/stdio/flockfile.c
@@ -191,7 +191,7 @@
/* called from fclose() to remove the file lock */
-void
+__LIBC_HIDDEN__ void
__fremovelock(FILE* fp)
{
LockTable* t = lock_table_lock();
diff --git a/libc/stdio/fvwrite.c b/libc/stdio/fvwrite.c
index ee39400..57a57e6 100644
--- a/libc/stdio/fvwrite.c
+++ b/libc/stdio/fvwrite.c
@@ -44,7 +44,7 @@
* This routine is large and unsightly, but most of the ugliness due
* to the three different kinds of output buffering is handled here.
*/
-int
+__LIBC_HIDDEN__ int
__sfvwrite(FILE *fp, struct __suio *uio)
{
size_t len;
diff --git a/libc/stdio/mktemp.c b/libc/stdio/mktemp.c
index 951f803..aaa5640 100644
--- a/libc/stdio/mktemp.c
+++ b/libc/stdio/mktemp.c
@@ -65,7 +65,7 @@
char *_mktemp(char *);
-char *
+__LIBC_HIDDEN__ char *
_mktemp(char *path)
{
return(_gettemp(path, (int *)NULL, 0, 0) ? path : (char *)NULL);
diff --git a/libc/stdlib/sha1hash.c b/libc/stdlib/sha1hash.c
deleted file mode 100644
index 1c7aaf3..0000000
--- a/libc/stdlib/sha1hash.c
+++ /dev/null
@@ -1,316 +0,0 @@
-/*
-SHA-1 in C
-By Steve Reid <sreid@sea-to-sky.net>
-100% Public Domain
-
------------------
-Modified 7/98
-By James H. Brown <jbrown@burgoyne.com>
-Still 100% Public Domain
-
-Corrected a problem which generated improper hash values on 16 bit machines
-Routine SHA1Update changed from
- void SHA1Update(SHA1_CTX* context, unsigned char* data, unsigned int
-len)
-to
- void SHA1Update(SHA1_CTX* context, unsigned char* data, unsigned
-long len)
-
-The 'len' parameter was declared an int which works fine on 32 bit machines.
-However, on 16 bit machines an int is too small for the shifts being done
-against
-it. This caused the hash function to generate incorrect values if len was
-greater than 8191 (8K - 1) due to the 'len << 3' on line 3 of SHA1Update().
-
-Since the file IO in main() reads 16K at a time, any file 8K or larger would
-be guaranteed to generate the wrong hash (e.g. Test Vector #3, a million
-"a"s).
-
-I also changed the declaration of variables i & j in SHA1Update to
-unsigned long from unsigned int for the same reason.
-
-These changes should make no difference to any 32 bit implementations since
-an
-int and a long are the same size in those environments.
-
---
-I also corrected a few compiler warnings generated by Borland C.
-1. Added #include <process.h> for exit() prototype
-2. Removed unused variable 'j' in SHA1Final
-3. Changed exit(0) to return(0) at end of main.
-
-ALL changes I made can be located by searching for comments containing 'JHB'
------------------
-Modified 8/98
-By Steve Reid <sreid@sea-to-sky.net>
-Still 100% public domain
-
-1- Removed #include <process.h> and used return() instead of exit()
-2- Fixed overwriting of finalcount in SHA1Final() (discovered by Chris Hall)
-3- Changed email address from steve@edmweb.com to sreid@sea-to-sky.net
-
------------------
-Modified 4/01
-By Saul Kravitz <Saul.Kravitz@celera.com>
-Still 100% PD
-Modified to run on Compaq Alpha hardware.
-
------------------
-Modified 2/03
-By H. Peter Anvin <hpa@zytor.com>
-Still 100% PD
-Modified to run on any hardware with <inttypes.h> and <netinet/in.h>
-Changed the driver program
-
-*/
-
-/*
-Test Vectors (from FIPS PUB 180-1)
-"abc"
- A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D
-"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq"
- 84983E44 1C3BD26E BAAE4AA1 F95129E5 E54670F1
-A million repetitions of "a"
- 34AA973C D4C4DAA4 F61EEB2B DBAD2731 6534016F
-*/
-
-/* #define SHA1HANDSOFF */
-
-#include <stdio.h>
-#include <string.h>
-#include <inttypes.h>
-#include <netinet/in.h> /* For htonl/ntohl/htons/ntohs */
-
-/* #include <process.h> */ /* prototype for exit() - JHB */
-/* Using return() instead of exit() - SWR */
-
-typedef struct {
- uint32_t state[5];
- uint32_t count[2];
- unsigned char buffer[64];
-} SHA1_CTX;
-
-void SHA1Transform(uint32_t state[5], unsigned char buffer[64]);
-void SHA1Init(SHA1_CTX* context);
-void SHA1Update(SHA1_CTX* context, unsigned char* data, uint32_t len); /*
-JHB */
-void SHA1Final(unsigned char digest[20], SHA1_CTX* context);
-
-#define rol(value, bits) (((value) << (bits)) | ((value) >> (32 - (bits))))
-
-/* blk0() and blk() perform the initial expand. */
-/* I got the idea of expanding during the round function from SSLeay */
-#define blk0(i) (block->l[i] = ntohl(block->l[i]))
-#define blk(i) (block->l[i&15] = rol(block->l[(i+13)&15]^block->l[(i+8)&15] \
- ^block->l[(i+2)&15]^block->l[i&15],1))
-
-/* (R0+R1), R2, R3, R4 are the different operations used in SHA1 */
-#define R0(v,w,x,y,z,i) z+=((w&(x^y))^y)+blk0(i)+0x5A827999+rol(v,5);w=rol(w,30);
-#define R1(v,w,x,y,z,i) z+=((w&(x^y))^y)+blk(i)+0x5A827999+rol(v,5);w=rol(w,30);
-#define R2(v,w,x,y,z,i) z+=(w^x^y)+blk(i)+0x6ED9EBA1+rol(v,5);w=rol(w,30);
-#define R3(v,w,x,y,z,i) z+=(((w|x)&y)|(w&x))+blk(i)+0x8F1BBCDC+rol(v,5);w=rol(w,30);
-#define R4(v,w,x,y,z,i) z+=(w^x^y)+blk(i)+0xCA62C1D6+rol(v,5);w=rol(w,30);
-
-
-#ifdef VERBOSE /* SAK */
-void SHAPrintContext(SHA1_CTX *context, char *msg){
- printf("%s (%d,%d) %x %x %x %x %x\n",
- msg,
- context->count[0], context->count[1],
- context->state[0],
- context->state[1],
- context->state[2],
- context->state[3],
- context->state[4]);
-}
-#endif
-
-/* Hash a single 512-bit block. This is the core of the algorithm. */
-
-void SHA1Transform(uint32_t state[5], unsigned char buffer[64])
-{
-uint32_t a, b, c, d, e;
-typedef union {
- unsigned char c[64];
- uint32_t l[16];
-} CHAR64LONG16;
-CHAR64LONG16* block;
-#ifdef SHA1HANDSOFF
-static unsigned char workspace[64];
- block = (CHAR64LONG16*)workspace;
- memcpy(block, buffer, 64);
-#else
- block = (CHAR64LONG16*)buffer;
-#endif
- /* Copy context->state[] to working vars */
- a = state[0];
- b = state[1];
- c = state[2];
- d = state[3];
- e = state[4];
- /* 4 rounds of 20 operations each. Loop unrolled. */
- R0(a,b,c,d,e, 0); R0(e,a,b,c,d, 1); R0(d,e,a,b,c, 2); R0(c,d,e,a,b, 3);
- R0(b,c,d,e,a, 4); R0(a,b,c,d,e, 5); R0(e,a,b,c,d, 6); R0(d,e,a,b,c, 7);
- R0(c,d,e,a,b, 8); R0(b,c,d,e,a, 9); R0(a,b,c,d,e,10); R0(e,a,b,c,d,11);
- R0(d,e,a,b,c,12); R0(c,d,e,a,b,13); R0(b,c,d,e,a,14); R0(a,b,c,d,e,15);
- R1(e,a,b,c,d,16); R1(d,e,a,b,c,17); R1(c,d,e,a,b,18); R1(b,c,d,e,a,19);
- R2(a,b,c,d,e,20); R2(e,a,b,c,d,21); R2(d,e,a,b,c,22); R2(c,d,e,a,b,23);
- R2(b,c,d,e,a,24); R2(a,b,c,d,e,25); R2(e,a,b,c,d,26); R2(d,e,a,b,c,27);
- R2(c,d,e,a,b,28); R2(b,c,d,e,a,29); R2(a,b,c,d,e,30); R2(e,a,b,c,d,31);
- R2(d,e,a,b,c,32); R2(c,d,e,a,b,33); R2(b,c,d,e,a,34); R2(a,b,c,d,e,35);
- R2(e,a,b,c,d,36); R2(d,e,a,b,c,37); R2(c,d,e,a,b,38); R2(b,c,d,e,a,39);
- R3(a,b,c,d,e,40); R3(e,a,b,c,d,41); R3(d,e,a,b,c,42); R3(c,d,e,a,b,43);
- R3(b,c,d,e,a,44); R3(a,b,c,d,e,45); R3(e,a,b,c,d,46); R3(d,e,a,b,c,47);
- R3(c,d,e,a,b,48); R3(b,c,d,e,a,49); R3(a,b,c,d,e,50); R3(e,a,b,c,d,51);
- R3(d,e,a,b,c,52); R3(c,d,e,a,b,53); R3(b,c,d,e,a,54); R3(a,b,c,d,e,55);
- R3(e,a,b,c,d,56); R3(d,e,a,b,c,57); R3(c,d,e,a,b,58); R3(b,c,d,e,a,59);
- R4(a,b,c,d,e,60); R4(e,a,b,c,d,61); R4(d,e,a,b,c,62); R4(c,d,e,a,b,63);
- R4(b,c,d,e,a,64); R4(a,b,c,d,e,65); R4(e,a,b,c,d,66); R4(d,e,a,b,c,67);
- R4(c,d,e,a,b,68); R4(b,c,d,e,a,69); R4(a,b,c,d,e,70); R4(e,a,b,c,d,71);
- R4(d,e,a,b,c,72); R4(c,d,e,a,b,73); R4(b,c,d,e,a,74); R4(a,b,c,d,e,75);
- R4(e,a,b,c,d,76); R4(d,e,a,b,c,77); R4(c,d,e,a,b,78); R4(b,c,d,e,a,79);
- /* Add the working vars back into context.state[] */
- state[0] += a;
- state[1] += b;
- state[2] += c;
- state[3] += d;
- state[4] += e;
- /* Wipe variables */
- a = b = c = d = e = 0;
-}
-
-
-/* SHA1Init - Initialize new context */
-
-void SHA1Init(SHA1_CTX* context)
-{
- /* SHA1 initialization constants */
- context->state[0] = 0x67452301;
- context->state[1] = 0xEFCDAB89;
- context->state[2] = 0x98BADCFE;
- context->state[3] = 0x10325476;
- context->state[4] = 0xC3D2E1F0;
- context->count[0] = context->count[1] = 0;
-}
-
-
-/* Run your data through this. */
-
-void SHA1Update(SHA1_CTX* context, unsigned char* data, uint32_t len) /*
-JHB */
-{
-uint32_t i, j; /* JHB */
-
-#ifdef VERBOSE
- SHAPrintContext(context, "before");
-#endif
- j = (context->count[0] >> 3) & 63;
- if ((context->count[0] += len << 3) < (len << 3)) context->count[1]++;
- context->count[1] += (len >> 29);
- if ((j + len) > 63) {
- memcpy(&context->buffer[j], data, (i = 64-j));
- SHA1Transform(context->state, context->buffer);
- for ( ; i + 63 < len; i += 64) {
- SHA1Transform(context->state, &data[i]);
- }
- j = 0;
- }
- else i = 0;
- memcpy(&context->buffer[j], &data[i], len - i);
-#ifdef VERBOSE
- SHAPrintContext(context, "after ");
-#endif
-}
-
-
-/* Add padding and return the message digest. */
-
-void SHA1Final(unsigned char digest[20], SHA1_CTX* context)
-{
-uint32_t i; /* JHB */
-unsigned char finalcount[8];
-
- for (i = 0; i < 8; i++) {
- finalcount[i] = (unsigned char)((context->count[(i >= 4 ? 0 : 1)]
- >> ((3-(i & 3)) * 8) ) & 255); /* Endian independent */
- }
- SHA1Update(context, (unsigned char *)"\200", 1);
- while ((context->count[0] & 504) != 448) {
- SHA1Update(context, (unsigned char *)"\0", 1);
- }
- SHA1Update(context, finalcount, 8); /* Should cause a SHA1Transform() */
- for (i = 0; i < 20; i++) {
- digest[i] = (unsigned char)
- ((context->state[i>>2] >> ((3-(i & 3)) * 8) ) & 255);
- }
- /* Wipe variables */
- i = 0; /* JHB */
- memset(context->buffer, 0, 64);
- memset(context->state, 0, 20);
- memset(context->count, 0, 8);
- memset(finalcount, 0, 8); /* SWR */
-#ifdef SHA1HANDSOFF /* make SHA1Transform overwrite it's own static vars */
- SHA1Transform(context->state, context->buffer);
-#endif
-}
-
-/*************************************************************/
-
-/* This is not quite the MIME base64 algorithm: it uses _ instead of /,
- and instead of padding the output with = characters we just make the
- output shorter. */
-char *mybase64(uint8_t digest[20])
-{
- static const char charz[] =
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_";
- uint8_t input[21];
- static char output[28];
- int i, j;
- uint8_t *p;
- char *q;
- uint32_t bv;
-
- memcpy(input, digest, 20);
- input[20] = 0; /* Pad to multiple of 3 bytes */
-
- p = input; q = output;
- for ( i = 0 ; i < 7 ; i++ ) {
- bv = (p[0] << 16) | (p[1] << 8) | p[2];
- p += 3;
- for ( j = 0 ; j < 4 ; j++ ) {
- *q++ = charz[(bv >> 18) & 0x3f];
- bv <<= 6;
- }
- }
- *--q = '\0'; /* The last character is not significant */
- return output;
-}
-
-int main(int argc, char** argv)
-{
- int i;
- SHA1_CTX context;
- uint8_t digest[20], buffer[16384];
- FILE* file;
-
- if (argc < 2) {
- file = stdin;
- }
- else {
- if (!(file = fopen(argv[1], "rb"))) {
- fputs("Unable to open file.", stderr);
- return(-1);
- }
- }
- SHA1Init(&context);
- while (!feof(file)) { /* note: what if ferror(file) */
- i = fread(buffer, 1, 16384, file);
- SHA1Update(&context, buffer, i);
- }
- SHA1Final(digest, &context);
- fclose(file);
-
- puts(mybase64(digest));
-
- return 0;
-}
diff --git a/libc/stdlib/strtod.c b/libc/stdlib/strtod.c
index 9d599b0..2851506 100644
--- a/libc/stdlib/strtod.c
+++ b/libc/stdlib/strtod.c
@@ -2062,7 +2062,7 @@
* calculation.
*/
- char *
+__LIBC_HIDDEN__ char *
__dtoa
#ifdef KR_headers
(_d, mode, ndigits, decpt, sign, rve)
diff --git a/libc/stdlib/wchar.c b/libc/stdlib/wchar.c
index 1480212..d83613a 100644
--- a/libc/stdlib/wchar.c
+++ b/libc/stdlib/wchar.c
@@ -302,12 +302,6 @@
return (wchar_t*) strstr( (const char*)ws1, (const char*)ws2 );
}
-size_t wcsxfrm(wchar_t *ws1, const wchar_t *ws2, size_t n)
-{
- memcpy( (char*)ws1, (const char*)ws2, n );
- return n;
-}
-
int wctob(wint_t c)
{
return c;
diff --git a/libc/tools/gensyscalls.py b/libc/tools/gensyscalls.py
index 41c9500..0535e56 100755
--- a/libc/tools/gensyscalls.py
+++ b/libc/tools/gensyscalls.py
@@ -245,6 +245,59 @@
"""
+def param_uses_64bits(param):
+ """Returns True iff a syscall parameter description corresponds
+ to a 64-bit type."""
+ param = param.strip()
+ # First, check that the param type begins with one of the known
+ # 64-bit types.
+ if not ( \
+ param.startswith("int64_t") or param.startswith("uint64_t") or \
+ param.startswith("loff_t") or param.startswith("off64_t") or \
+ param.startswith("long long") or param.startswith("unsigned long long") or
+ param.startswith("signed long long") ):
+ return False
+
+ # Second, check that there is no pointer type here
+ if param.find("*") >= 0:
+ return False
+
+ # Ok
+ return True
+
+def count_arm_param_registers(params):
+ """This function is used to count the number of register used
+ to pass parameters when invoking a thumb or ARM system call.
+ This is because the ARM EABI mandates that 64-bit quantities
+ must be passed in an even+odd register pair. So, for example,
+ something like:
+
+ foo(int fd, off64_t pos)
+
+ would actually need 4 registers:
+ r0 -> int
+ r1 -> unused
+ r2-r3 -> pos
+ """
+ count = 0
+ for param in params:
+ if param_uses_64bits(param):
+ if (count & 1) != 0:
+ count += 1
+ count += 2
+ else:
+ count += 1
+ return count
+
+def count_generic_param_registers(params):
+ count = 0
+ for param in params:
+ if param_uses_64bits(param):
+ count += 2
+ else:
+ count += 1
+ return count
+
class State:
def __init__(self):
self.old_stubs = []
@@ -370,25 +423,28 @@
syscall_name = t["name"]
if t["id"] >= 0:
+ num_regs = count_arm_param_registers(syscall_params)
if gen_thumb_stubs:
- t["asm-thumb"] = self.thumb_genstub(syscall_func,len(syscall_params),"__NR_"+syscall_name)
+ t["asm-thumb"] = self.thumb_genstub(syscall_func,num_regs,"__NR_"+syscall_name)
else:
if gen_eabi_stubs:
- t["asm-arm"] = self.arm_eabi_genstub(syscall_func,len(syscall_params),"__NR_"+syscall_name)
+ t["asm-arm"] = self.arm_eabi_genstub(syscall_func,num_regs,"__NR_"+syscall_name)
else:
- t["asm-arm"] = self.arm_genstub(syscall_func,len(syscall_params),"__NR_"+syscall_name)
+ t["asm-arm"] = self.arm_genstub(syscall_func,num_regs,"__NR_"+syscall_name)
if t["id2"] >= 0:
+ num_regs = count_generic_param_registers(syscall_params)
if t["cid"] >= 0:
- t["asm-x86"] = self.x86_genstub_cid(syscall_func, len(syscall_params), "__NR_"+syscall_name, t["cid"])
+ t["asm-x86"] = self.x86_genstub_cid(syscall_func, num_regs, "__NR_"+syscall_name, t["cid"])
else:
- t["asm-x86"] = self.x86_genstub(syscall_func,len(syscall_params),"__NR_"+syscall_name)
+ t["asm-x86"] = self.x86_genstub(syscall_func, num_regs, "__NR_"+syscall_name)
elif t["cid"] >= 0:
E("cid for dispatch syscalls is only supported for x86 in "
"'%s'" % syscall_name)
return
if t["id3"] >= 0:
- t["asm-sh"] = self.superh_genstub(syscall_func,len(syscall_params),"__NR_"+syscall_name)
+ num_regs = count_generic_param_registers(syscall_params)
+ t["asm-sh"] = self.superh_genstub(syscall_func,num_regs,"__NR_"+syscall_name)
diff --git a/libc/tzcode/localtime.c b/libc/tzcode/localtime.c
index 85a913e..e442a03 100644
--- a/libc/tzcode/localtime.c
+++ b/libc/tzcode/localtime.c
@@ -60,6 +60,14 @@
# define XLOG(x) do{}while (0)
#endif
+/* Add the following function implementations:
+ * timelocal()
+ * timegm()
+ * time2posix()
+ * posix2time()
+ */
+#define STD_INSPIRED 1
+
/* THREAD-SAFETY SUPPORT GOES HERE */
static pthread_mutex_t _tzMutex = PTHREAD_MUTEX_INITIALIZER;
@@ -1509,7 +1517,7 @@
}
#ifdef STD_INSPIRED
-
+#if 0 /* disabled because there is no good documentation for this function */
struct tm *
offtime(timep, offset)
const time_t * const timep;
@@ -1517,7 +1525,7 @@
{
return gmtsub(timep, offset, &tmGlobal);
}
-
+#endif /* 0 */
#endif /* defined STD_INSPIRED */
/*
@@ -2106,6 +2114,7 @@
return result;
}
+#if 0 /* disable due to lack of clear documentation on this function */
time_t
timeoff(tmp, offset)
struct tm * const tmp;
@@ -2120,6 +2129,7 @@
return result;
}
+#endif /* 0 */
#endif /* defined STD_INSPIRED */
diff --git a/libc/unistd/abort.c b/libc/unistd/abort.c
index 3e3aab0..8b8659b 100644
--- a/libc/unistd/abort.c
+++ b/libc/unistd/abort.c
@@ -40,7 +40,7 @@
__libc_android_log_print(ANDROID_LOG_DEBUG, "libc-abort", (format), ##__VA_ARGS__ )
#ifdef __arm__
-void
+__LIBC_HIDDEN__ void
__libc_android_abort(void)
#else
void
diff --git a/libc/unistd/lseek64.c b/libc/unistd/lseek64.c
index 017b331..db0c413 100644
--- a/libc/unistd/lseek64.c
+++ b/libc/unistd/lseek64.c
@@ -29,7 +29,7 @@
extern int __llseek(int fd, unsigned long offset_hi, unsigned long offset_lo, loff_t* result, int whence);
-loff_t lseek64(int fd, loff_t off, int whence)
+off64_t lseek64(int fd, off64_t off, int whence)
{
loff_t result;
diff --git a/libc/unistd/pread.c b/libc/unistd/pread.c
index b55623e..42fc3bc 100644
--- a/libc/unistd/pread.c
+++ b/libc/unistd/pread.c
@@ -11,24 +11,25 @@
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
- * 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.
- * * Neither the name of Google Inc. 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 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 <sys/types.h>
#include <unistd.h>
-extern int __pread64(int fd, void *buf, size_t nbytes, loff_t offset);
-
ssize_t pread(int fd, void *buf, size_t nbytes, off_t offset)
{
- return __pread64(fd, buf, nbytes, offset);
+ return pread64(fd, buf, nbytes, (off64_t)offset);
}
diff --git a/libc/unistd/pwrite.c b/libc/unistd/pwrite.c
index ea080d2..f106cb3 100644
--- a/libc/unistd/pwrite.c
+++ b/libc/unistd/pwrite.c
@@ -28,10 +28,8 @@
#include <sys/types.h>
#include <unistd.h>
-extern int __pwrite64(int fd, void *buf, size_t nbytes, loff_t offset);
-
-ssize_t pwrite(int fd, void *buf, size_t nbytes, off_t offset)
+ssize_t pwrite(int fd, const void *buf, size_t nbytes, off_t offset)
{
- return __pwrite64(fd, buf, nbytes, offset);
+ return pwrite64(fd, buf, nbytes, (off64_t)offset);
}
diff --git a/libc/unistd/raise.c b/libc/unistd/raise.c
index de099da..7b03a7a 100644
--- a/libc/unistd/raise.c
+++ b/libc/unistd/raise.c
@@ -30,5 +30,5 @@
int raise(int signum)
{
- return kill(getpid(), signum);
+ return kill(gettid(), signum);
}
diff --git a/libc/unistd/sigsetmask.c b/libc/unistd/sigsetmask.c
index b987595..4f46458 100644
--- a/libc/unistd/sigsetmask.c
+++ b/libc/unistd/sigsetmask.c
@@ -38,6 +38,8 @@
sigset_t the_sigset;
} in, out;
+ in.the_mask = mask;
+
n = sigprocmask(SIG_SETMASK, &in.the_sigset, &out.the_sigset);
if (n)
return n;
diff --git a/libm/i387/fenv.c b/libm/i387/fenv.c
index 2794faf..aabe270 100644
--- a/libm/i387/fenv.c
+++ b/libm/i387/fenv.c
@@ -153,7 +153,8 @@
int
feupdateenv(const fenv_t *envp)
{
- int mxcsr, status;
+ int mxcsr;
+ short status;
__fnstsw(&status);
if (__HAS_SSE())
diff --git a/libm/i387/fenv.h b/libm/i387/fenv.h
deleted file mode 100644
index b124366..0000000
--- a/libm/i387/fenv.h
+++ /dev/null
@@ -1,240 +0,0 @@
-/*-
- * Copyright (c) 2004-2005 David Schultz <das@FreeBSD.ORG>
- * All rights reserved.
- *
- * 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.
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR 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 AUTHOR 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.
- *
- * $FreeBSD: src/lib/msun/i387/fenv.h,v 1.4 2005/03/17 22:21:46 das Exp $
- */
-
-#ifndef _FENV_H_
-#define _FENV_H_
-
-#include <sys/cdefs.h>
-#include <sys/_types.h>
-
-/*
- * To preserve binary compatibility with FreeBSD 5.3, we pack the
- * mxcsr into some reserved fields, rather than changing sizeof(fenv_t).
- */
-typedef struct {
- __uint16_t __control;
- __uint16_t __mxcsr_hi;
- __uint16_t __status;
- __uint16_t __mxcsr_lo;
- __uint32_t __tag;
- char __other[16];
-} fenv_t;
-
-#define __get_mxcsr(env) (((env).__mxcsr_hi << 16) | \
- ((env).__mxcsr_lo))
-#define __set_mxcsr(env, x) do { \
- (env).__mxcsr_hi = (__uint32_t)(x) >> 16; \
- (env).__mxcsr_lo = (__uint16_t)(x); \
-} while (0)
-
-typedef __uint16_t fexcept_t;
-
-/* Exception flags */
-#define FE_INVALID 0x01
-#define FE_DENORMAL 0x02
-#define FE_DIVBYZERO 0x04
-#define FE_OVERFLOW 0x08
-#define FE_UNDERFLOW 0x10
-#define FE_INEXACT 0x20
-#define FE_ALL_EXCEPT (FE_DIVBYZERO | FE_DENORMAL | FE_INEXACT | \
- FE_INVALID | FE_OVERFLOW | FE_UNDERFLOW)
-
-/* Rounding modes */
-#define FE_TONEAREST 0x0000
-#define FE_DOWNWARD 0x0400
-#define FE_UPWARD 0x0800
-#define FE_TOWARDZERO 0x0c00
-#define _ROUND_MASK (FE_TONEAREST | FE_DOWNWARD | \
- FE_UPWARD | FE_TOWARDZERO)
-
-/*
- * As compared to the x87 control word, the SSE unit's control word
- * has the rounding control bits offset by 3 and the exception mask
- * bits offset by 7.
- */
-#define _SSE_ROUND_SHIFT 3
-#define _SSE_EMASK_SHIFT 7
-
-/* After testing for SSE support once, we cache the result in __has_sse. */
-enum __sse_support { __SSE_YES, __SSE_NO, __SSE_UNK };
-extern enum __sse_support __has_sse;
-int __test_sse(void);
-#ifdef __SSE__
-#define __HAS_SSE() 1
-#else
-#define __HAS_SSE() (__has_sse == __SSE_YES || \
- (__has_sse == __SSE_UNK && __test_sse()))
-#endif
-
-__BEGIN_DECLS
-
-/* Default floating-point environment */
-extern const fenv_t __fe_dfl_env;
-#define FE_DFL_ENV (&__fe_dfl_env)
-
-#define __fldcw(__cw) __asm __volatile("fldcw %0" : : "m" (__cw))
-#define __fldenv(__env) __asm __volatile("fldenv %0" : : "m" (__env))
-#define __fnclex() __asm __volatile("fnclex")
-#define __fnstenv(__env) __asm __volatile("fnstenv %0" : "=m" (*(__env)))
-#define __fnstcw(__cw) __asm __volatile("fnstcw %0" : "=m" (*(__cw)))
-#define __fnstsw(__sw) __asm __volatile("fnstsw %0" : "=am" (*(__sw)))
-#define __fwait() __asm __volatile("fwait")
-#define __ldmxcsr(__csr) __asm __volatile("ldmxcsr %0" : : "m" (__csr))
-#define __stmxcsr(__csr) __asm __volatile("stmxcsr %0" : "=m" (*(__csr)))
-
-static __inline int
-feclearexcept(int __excepts)
-{
- fenv_t __env;
- int __mxcsr;
-
- if (__excepts == FE_ALL_EXCEPT) {
- __fnclex();
- } else {
- __fnstenv(&__env);
- __env.__status &= ~__excepts;
- __fldenv(__env);
- }
- if (__HAS_SSE()) {
- __stmxcsr(&__mxcsr);
- __mxcsr &= ~__excepts;
- __ldmxcsr(__mxcsr);
- }
- return (0);
-}
-
-static __inline int
-fegetexceptflag(fexcept_t *__flagp, int __excepts)
-{
- int __mxcsr, __status;
-
- __fnstsw(&__status);
- if (__HAS_SSE())
- __stmxcsr(&__mxcsr);
- else
- __mxcsr = 0;
- *__flagp = (__mxcsr | __status) & __excepts;
- return (0);
-}
-
-int fesetexceptflag(const fexcept_t *__flagp, int __excepts);
-int feraiseexcept(int __excepts);
-
-static __inline int
-fetestexcept(int __excepts)
-{
- int __mxcsr, __status;
-
- __fnstsw(&__status);
- if (__HAS_SSE())
- __stmxcsr(&__mxcsr);
- else
- __mxcsr = 0;
- return ((__status | __mxcsr) & __excepts);
-}
-
-static __inline int
-fegetround(void)
-{
- int __control;
-
- /*
- * We assume that the x87 and the SSE unit agree on the
- * rounding mode. Reading the control word on the x87 turns
- * out to be about 5 times faster than reading it on the SSE
- * unit on an Opteron 244.
- */
- __fnstcw(&__control);
- return (__control & _ROUND_MASK);
-}
-
-static __inline int
-fesetround(int __round)
-{
- int __mxcsr, __control;
-
- if (__round & ~_ROUND_MASK)
- return (-1);
-
- __fnstcw(&__control);
- __control &= ~_ROUND_MASK;
- __control |= __round;
- __fldcw(__control);
-
- if (__HAS_SSE()) {
- __stmxcsr(&__mxcsr);
- __mxcsr &= ~(_ROUND_MASK << _SSE_ROUND_SHIFT);
- __mxcsr |= __round << _SSE_ROUND_SHIFT;
- __ldmxcsr(__mxcsr);
- }
-
- return (0);
-}
-
-int fegetenv(fenv_t *__envp);
-int feholdexcept(fenv_t *__envp);
-
-static __inline int
-fesetenv(const fenv_t *__envp)
-{
- fenv_t __env = *__envp;
- int __mxcsr;
-
- __mxcsr = __get_mxcsr(__env);
- __set_mxcsr(__env, 0xffffffff);
- __fldenv(__env);
- if (__HAS_SSE())
- __ldmxcsr(__mxcsr);
- return (0);
-}
-
-int feupdateenv(const fenv_t *__envp);
-
-#if __BSD_VISIBLE
-
-int feenableexcept(int __mask);
-int fedisableexcept(int __mask);
-
-static __inline int
-fegetexcept(void)
-{
- int __control;
-
- /*
- * We assume that the masks for the x87 and the SSE unit are
- * the same.
- */
- __fnstcw(&__control);
- return (~__control & FE_ALL_EXCEPT);
-}
-
-#endif /* __BSD_VISIBLE */
-
-__END_DECLS
-
-#endif /* !_FENV_H_ */
diff --git a/libm/include/i387/fenv.h b/libm/include/i387/fenv.h
index b124366..5fe64e2 100644
--- a/libm/include/i387/fenv.h
+++ b/libm/include/i387/fenv.h
@@ -102,7 +102,7 @@
#define __fnclex() __asm __volatile("fnclex")
#define __fnstenv(__env) __asm __volatile("fnstenv %0" : "=m" (*(__env)))
#define __fnstcw(__cw) __asm __volatile("fnstcw %0" : "=m" (*(__cw)))
-#define __fnstsw(__sw) __asm __volatile("fnstsw %0" : "=am" (*(__sw)))
+#define __fnstsw(__sw) __asm __volatile("fnstsw %0" : "=a" (*(__sw)))
#define __fwait() __asm __volatile("fwait")
#define __ldmxcsr(__csr) __asm __volatile("ldmxcsr %0" : : "m" (__csr))
#define __stmxcsr(__csr) __asm __volatile("stmxcsr %0" : "=m" (*(__csr)))
@@ -131,7 +131,8 @@
static __inline int
fegetexceptflag(fexcept_t *__flagp, int __excepts)
{
- int __mxcsr, __status;
+ int __mxcsr;
+ short __status;
__fnstsw(&__status);
if (__HAS_SSE())
@@ -148,7 +149,8 @@
static __inline int
fetestexcept(int __excepts)
{
- int __mxcsr, __status;
+ int __mxcsr;
+ short __status;
__fnstsw(&__status);
if (__HAS_SSE())
diff --git a/libthread_db/Android.mk b/libthread_db/Android.mk
index 3091bbc..922b9cf 100644
--- a/libthread_db/Android.mk
+++ b/libthread_db/Android.mk
@@ -21,7 +21,7 @@
LOCAL_WHOLE_STATIC_LIBRARIES := libthread_db
LOCAL_MODULE:=libthread_db
-LOCAL_SHARED_LIBRARIES := libdl
+LOCAL_SHARED_LIBRARIES := libdl libc
# NOTE: Using --no-undefined results in a missing symbol that is defined inside
# gdbserver and is resolved at runtime. Since there is no library containing
diff --git a/linker/Android.mk b/linker/Android.mk
index 27a6677..da311cd 100644
--- a/linker/Android.mk
+++ b/linker/Android.mk
@@ -4,6 +4,7 @@
LOCAL_SRC_FILES:= \
arch/$(TARGET_ARCH)/begin.S \
linker.c \
+ linker_environ.c \
linker_format.c \
rt.c \
dlfcn.c \
@@ -93,6 +94,6 @@
# just for this module
$(LOCAL_BUILT_MODULE): TARGET_CRTBEGIN_STATIC_O :=
# This line is not strictly necessary because the dynamic linker is built
-# as a static executable, but it won't hurt if in the future we start
+# as a static executable, but it won't hurt if in the future we start
# building the linker as a dynamic one.
$(LOCAL_BUILT_MODULE): TARGET_CRTBEGIN_DYNAMIC_O :=
diff --git a/linker/linker.c b/linker/linker.c
index 42a5205..c4f54f7 100644
--- a/linker/linker.c
+++ b/linker/linker.c
@@ -48,6 +48,7 @@
#include "linker.h"
#include "linker_debug.h"
+#include "linker_environ.h"
#include "linker_format.h"
#include "ba.h"
@@ -123,6 +124,9 @@
int debug_verbosity;
static int pid;
+/* This boolean is set if the program being loaded is setuid */
+static int program_is_setuid;
+
#if STATS
struct _link_stats linker_stats;
#endif
@@ -286,7 +290,7 @@
/* Make sure we get a clean block of soinfo */
memset(si, 0, sizeof(soinfo));
- strcpy((char*) si->name, name);
+ strlcpy((char*) si->name, name, sizeof(si->name));
sonext->next = si;
si->ba_index = -1; /* by default, prelinked */
si->next = NULL;
@@ -314,7 +318,7 @@
return;
}
- /* prev will never be NULL, because the first entry in solist is
+ /* prev will never be NULL, because the first entry in solist is
always the static libdl_info.
*/
prev->next = si->next;
@@ -1232,8 +1236,8 @@
return init_library(si);
}
-/* TODO:
- * notify gdb of unload
+/* TODO:
+ * notify gdb of unload
* for non-prelinked libraries, find a way to decrement libbase
*/
static void call_destructors(soinfo *si);
@@ -1765,14 +1769,14 @@
}
#endif
if (phdr->p_type == PT_LOAD) {
- /* For the executable, we use the si->size field only in
- dl_unwind_find_exidx(), so the meaning of si->size
- is not the size of the executable; it is the last
+ /* For the executable, we use the si->size field only in
+ dl_unwind_find_exidx(), so the meaning of si->size
+ is not the size of the executable; it is the last
virtual address of the loadable part of the executable;
since si->base == 0 for an executable, we use the
- range [0, si->size) to determine whether a PC value
+ range [0, si->size) to determine whether a PC value
falls within the executable section. Of course, if
- a value is below phdr->p_vaddr, it's not in the
+ a value is below phdr->p_vaddr, it's not in the
executable section, but a) we shouldn't be asking for
such a value anyway, and b) if we have to provide
an EXIDX for such a value, then the executable's
@@ -1927,7 +1931,7 @@
}
}
- DEBUG("%5d si->base = 0x%08x, si->strtab = %p, si->symtab = %p\n",
+ DEBUG("%5d si->base = 0x%08x, si->strtab = %p, si->symtab = %p\n",
pid, si->base, si->strtab, si->symtab);
if((si->strtab == 0) || (si->symtab == 0)) {
@@ -2033,7 +2037,7 @@
ftp://ftp.freebsd.org/pub/FreeBSD/CERT/advisories/FreeBSD-SA-02:23.stdio.asc
*/
- if (getuid() != geteuid() || getgid() != getegid())
+ if (program_is_setuid)
nullify_closed_stdio ();
call_constructors(si);
notify_gdb_of_load(si);
@@ -2045,7 +2049,7 @@
return -1;
}
-static void parse_library_path(char *path, char *delim)
+static void parse_library_path(const char *path, char *delim)
{
size_t len;
char *ldpaths_bufp = ldpaths_buf;
@@ -2068,7 +2072,7 @@
}
}
-static void parse_preloads(char *path, char *delim)
+static void parse_preloads(const char *path, char *delim)
{
size_t len;
char *ldpreloads_bufp = ldpreloads_buf;
@@ -2110,8 +2114,8 @@
unsigned *vecs = (unsigned*) (argv + argc + 1);
soinfo *si;
struct link_map * map;
- char *ldpath_env = NULL;
- char *ldpreload_env = NULL;
+ const char *ldpath_env = NULL;
+ const char *ldpreload_env = NULL;
/* Setup a temporary TLS area that is used to get a working
* errno for system calls.
@@ -2135,20 +2139,32 @@
*/
__tls_area[TLS_SLOT_BIONIC_PREINIT] = elfdata;
+ /* Are we setuid? */
+ program_is_setuid = (getuid() != geteuid()) || (getgid() != getegid());
+
+ /* Initialize environment functions, and get to the ELF aux vectors table */
+ vecs = linker_env_init(vecs);
+
+ /* Sanitize environment if we're loading a setuid program */
+ if (program_is_setuid)
+ linker_env_secure();
+
debugger_init();
- /* skip past the environment */
- while(vecs[0] != 0) {
- if(!strncmp((char*) vecs[0], "DEBUG=", 6)) {
- debug_verbosity = atoi(((char*) vecs[0]) + 6);
- } else if(!strncmp((char*) vecs[0], "LD_LIBRARY_PATH=", 16)) {
- ldpath_env = (char*) vecs[0] + 16;
- } else if(!strncmp((char*) vecs[0], "LD_PRELOAD=", 11)) {
- ldpreload_env = (char*) vecs[0] + 11;
+ /* Get a few environment variables */
+ {
+ const char* env;
+ env = linker_env_get("DEBUG"); /* XXX: TODO: Change to LD_DEBUG */
+ if (env)
+ debug_verbosity = atoi(env);
+
+ /* Normally, these are cleaned by linker_env_secure, but the test
+ * against program_is_setuid doesn't cost us anything */
+ if (!program_is_setuid) {
+ ldpath_env = linker_env_get("LD_LIBRARY_PATH");
+ ldpreload_env = linker_env_get("LD_PRELOAD");
}
- vecs++;
}
- vecs++;
INFO("[ android linker & debugger ]\n");
DEBUG("%5d elfdata @ 0x%08x\n", pid, (unsigned)elfdata);
@@ -2176,7 +2192,7 @@
* is. Don't use alloc_info(), because the linker shouldn't
* be on the soinfo list.
*/
- strcpy((char*) linker_soinfo.name, "/system/bin/linker");
+ strlcpy((char*) linker_soinfo.name, "/system/bin/linker", sizeof linker_soinfo.name);
linker_soinfo.flags = 0;
linker_soinfo.base = 0; // This is the important part; must be zero.
insert_soinfo_into_debug_map(&linker_soinfo);
@@ -2206,10 +2222,10 @@
si->refcount = 1;
/* Use LD_LIBRARY_PATH if we aren't setuid/setgid */
- if (ldpath_env && getuid() == geteuid() && getgid() == getegid())
+ if (ldpath_env)
parse_library_path(ldpath_env, ":");
- if (ldpreload_env && getuid() == geteuid() && getgid() == getegid()) {
+ if (ldpreload_env) {
parse_preloads(ldpreload_env, " :");
}
diff --git a/linker/linker_environ.c b/linker/linker_environ.c
new file mode 100644
index 0000000..b71dd80
--- /dev/null
+++ b/linker/linker_environ.c
@@ -0,0 +1,204 @@
+/*
+ * Copyright (C) 2010 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 "linker_environ.h"
+#include <stddef.h>
+
+static char** _envp;
+
+/* Returns 1 if 'str' points to a valid environment variable definition.
+ * For now, we check that:
+ * - It is smaller than MAX_ENV_LEN (to detect non-zero terminated strings)
+ * - It contains at least one equal sign that is not the first character
+ */
+static int
+_is_valid_definition(const char* str)
+{
+ int pos = 0;
+ int first_equal_pos = -1;
+
+ /* According to its sources, the kernel uses 32*PAGE_SIZE by default
+ * as the maximum size for an env. variable definition.
+ */
+ const int MAX_ENV_LEN = 32*4096;
+
+ if (str == NULL)
+ return 0;
+
+ /* Parse the string, looking for the first '=' there, and its size */
+ do {
+ if (str[pos] == '\0')
+ break;
+ if (str[pos] == '=' && first_equal_pos < 0)
+ first_equal_pos = pos;
+ pos++;
+ } while (pos < MAX_ENV_LEN);
+
+ if (pos >= MAX_ENV_LEN) /* Too large */
+ return 0;
+
+ if (first_equal_pos < 1) /* No equal sign, or it is the first character */
+ return 0;
+
+ return 1;
+}
+
+unsigned*
+linker_env_init(unsigned* vecs)
+{
+ /* Store environment pointer - can't be NULL */
+ _envp = (char**) vecs;
+
+ /* Skip over all definitions */
+ while (vecs[0] != 0)
+ vecs++;
+ /* The end of the environment block is marked by two NULL pointers */
+ vecs++;
+
+ /* As a sanity check, we're going to remove all invalid variable
+ * definitions from the environment array.
+ */
+ {
+ char** readp = _envp;
+ char** writep = _envp;
+ for ( ; readp[0] != NULL; readp++ ) {
+ if (!_is_valid_definition(readp[0]))
+ continue;
+ writep[0] = readp[0];
+ writep++;
+ }
+ writep[0] = NULL;
+ }
+
+ /* Return the address of the aux vectors table */
+ return vecs;
+}
+
+/* Check if the environment variable definition at 'envstr'
+ * starts with '<name>=', and if so return the address of the
+ * first character after the equal sign. Otherwise return NULL.
+ */
+static char*
+env_match(char* envstr, const char* name)
+{
+ size_t cnt = 0;
+
+ while (envstr[cnt] == name[cnt] && name[cnt] != '\0')
+ cnt++;
+
+ if (name[cnt] == '\0' && envstr[cnt] == '=')
+ return envstr + cnt + 1;
+
+ return NULL;
+}
+
+#define MAX_ENV_LEN (16*4096)
+
+const char*
+linker_env_get(const char* name)
+{
+ char** readp = _envp;
+
+ if (name == NULL || name[0] == '\0')
+ return NULL;
+
+ for ( ; readp[0] != NULL; readp++ ) {
+ char* val = env_match(readp[0], name);
+ if (val != NULL) {
+ /* Return NULL for empty strings, or if it is too large */
+ if (val[0] == '\0')
+ val = NULL;
+ return val;
+ }
+ }
+ return NULL;
+}
+
+
+void
+linker_env_unset(const char* name)
+{
+ char** readp = _envp;
+ char** writep = readp;
+
+ if (name == NULL || name[0] == '\0')
+ return;
+
+ for ( ; readp[0] != NULL; readp++ ) {
+ if (env_match(readp[0], name))
+ continue;
+ writep[0] = readp[0];
+ writep++;
+ }
+ /* end list with a NULL */
+ writep[0] = NULL;
+}
+
+
+
+/* Remove unsafe environment variables. This should be used when
+ * running setuid programs. */
+void
+linker_env_secure(void)
+{
+ /* The same list than GLibc at this point */
+ static const char* const unsec_vars[] = {
+ "GCONV_PATH",
+ "GETCONF_DIR",
+ "HOSTALIASES",
+ "LD_AUDIT",
+ "LD_DEBUG",
+ "LD_DEBUG_OUTPUT",
+ "LD_DYNAMIC_WEAK",
+ "LD_LIBRARY_PATH",
+ "LD_ORIGIN_PATH",
+ "LD_PRELOAD",
+ "LD_PROFILE",
+ "LD_SHOW_AUXV",
+ "LD_USE_LOAD_BIAS",
+ "LOCALDOMAIN",
+ "LOCPATH",
+ "MALLOC_TRACE",
+ "MALLOC_CHECK_",
+ "NIS_PATH",
+ "NLSPATH",
+ "RESOLV_HOST_CONF",
+ "RES_OPTIONS",
+ "TMPDIR",
+ "TZDIR",
+ "LD_AOUT_LIBRARY_PATH",
+ "LD_AOUT_PRELOAD",
+ };
+
+ const char* const* cp = unsec_vars;
+ const char* const* endp = cp + sizeof(unsec_vars)/sizeof(unsec_vars[0]);
+
+ while (cp < endp) {
+ linker_env_unset(*cp);
+ cp++;
+ }
+}
diff --git a/linker/linker_environ.h b/linker/linker_environ.h
new file mode 100644
index 0000000..98ad1de
--- /dev/null
+++ b/linker/linker_environ.h
@@ -0,0 +1,54 @@
+/*
+ * Copyright (C) 2010 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.
+ */
+#ifndef LINKER_ENVIRON_H
+#define LINKER_ENVIRON_H
+
+/* Call this function before anything else. 'vecs' must be the pointer
+ * to the environment block in the ELF data block. The function returns
+ * the start of the aux vectors after the env block.
+ */
+extern unsigned* linker_env_init(unsigned* vecs);
+
+/* Unset a given environment variable. In case the variable is defined
+ * multiple times, unset all instances. This modifies the environment
+ * block, so any pointer returned by linker_env_get() after this call
+ * might become invalid */
+extern void linker_env_unset(const char* name);
+
+
+/* Returns the value of environment variable 'name' if defined and not
+ * empty, or NULL otherwise. Note that the returned pointer may become
+ * invalid if linker_env_unset() or linker_env_secure() are called
+ * after this function. */
+extern const char* linker_env_get(const char* name);
+
+/* Remove unsecure environment variables. This should be used when
+ * running setuid programs. */
+extern void linker_env_secure(void);
+
+#endif /* LINKER_ENVIRON_H */