am f44de270: add personality() system call.
* commit 'f44de270bba32c9b1b5eff8a34be07b10ddff238':
add personality() system call.
diff --git a/libc/Android.mk b/libc/Android.mk
index 49c8731..225d14f 100644
--- a/libc/Android.mk
+++ b/libc/Android.mk
@@ -510,11 +510,8 @@
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
+ libc_crt_target_cflags :=
+ # TARGET_GLOBAL_CFLAGS from build/core/combo/TARGET_linux-x86.mk sets all required flags.
endif # x86
endif # !arm
diff --git a/libc/SYSCALLS.TXT b/libc/SYSCALLS.TXT
index d72d129..7ac5198 100644
--- a/libc/SYSCALLS.TXT
+++ b/libc/SYSCALLS.TXT
@@ -50,6 +50,7 @@
uid_t getresuid:getresuid32 () 209
gid_t getresgid:getresgid32 () 211
pid_t gettid() 224
+ssize_t readahead(int, off64_t, size_t) 225
int getgroups:getgroups32(int, gid_t *) 205
pid_t getpgid(pid_t) 132
pid_t getppid() 64
diff --git a/libc/arch-arm/syscalls.mk b/libc/arch-arm/syscalls.mk
index 861cabf..b7a4532 100644
--- a/libc/arch-arm/syscalls.mk
+++ b/libc/arch-arm/syscalls.mk
@@ -14,6 +14,7 @@
syscall_src += arch-arm/syscalls/getresuid.S
syscall_src += arch-arm/syscalls/getresgid.S
syscall_src += arch-arm/syscalls/gettid.S
+syscall_src += arch-arm/syscalls/readahead.S
syscall_src += arch-arm/syscalls/getgroups.S
syscall_src += arch-arm/syscalls/getpgid.S
syscall_src += arch-arm/syscalls/getppid.S
diff --git a/libc/arch-arm/syscalls/readahead.S b/libc/arch-arm/syscalls/readahead.S
new file mode 100644
index 0000000..6aa8265
--- /dev/null
+++ b/libc/arch-arm/syscalls/readahead.S
@@ -0,0 +1,16 @@
+/* autogenerated by gensyscalls.py */
+#include <machine/asm.h>
+#include <sys/linux-syscalls.h>
+
+ENTRY(readahead)
+ mov ip, sp
+ .save {r4, r5, r6, r7}
+ stmfd sp!, {r4, r5, r6, r7}
+ ldmfd ip, {r4, r5, r6}
+ ldr r7, =__NR_readahead
+ swi #0
+ ldmfd sp!, {r4, r5, r6, r7}
+ movs r0, r0
+ bxpl lr
+ b __set_syscall_errno
+END(readahead)
diff --git a/libc/arch-sh/syscalls.mk b/libc/arch-sh/syscalls.mk
index 6666431..8bed77c 100644
--- a/libc/arch-sh/syscalls.mk
+++ b/libc/arch-sh/syscalls.mk
@@ -15,6 +15,7 @@
syscall_src += arch-sh/syscalls/getresuid.S
syscall_src += arch-sh/syscalls/getresgid.S
syscall_src += arch-sh/syscalls/gettid.S
+syscall_src += arch-sh/syscalls/readahead.S
syscall_src += arch-sh/syscalls/getgroups.S
syscall_src += arch-sh/syscalls/getpgid.S
syscall_src += arch-sh/syscalls/getppid.S
diff --git a/libc/arch-sh/syscalls/readahead.S b/libc/arch-sh/syscalls/readahead.S
new file mode 100644
index 0000000..df64b5f
--- /dev/null
+++ b/libc/arch-sh/syscalls/readahead.S
@@ -0,0 +1,32 @@
+/* autogenerated by gensyscalls.py */
+#include <sys/linux-syscalls.h>
+
+ .text
+ .type readahead, @function
+ .globl readahead
+ .align 4
+
+readahead:
+
+ /* invoke trap */
+ mov.l 0f, r3 /* trap num */
+ trapa #(4 + 0x10)
+
+ /* check return value */
+ cmp/pz r0
+ bt __NR_readahead_end
+
+ /* keep error number */
+ sts.l pr, @-r15
+ mov.l 1f, r1
+ jsr @r1
+ mov r0, r4
+ lds.l @r15+, pr
+
+__NR_readahead_end:
+ rts
+ nop
+
+ .align 2
+0: .long __NR_readahead
+1: .long __set_syscall_errno
diff --git a/libc/arch-x86/bionic/__set_tls.c b/libc/arch-x86/bionic/__set_tls.c
index 48b55f0..e5e43b5 100755
--- a/libc/arch-x86/bionic/__set_tls.c
+++ b/libc/arch-x86/bionic/__set_tls.c
@@ -60,6 +60,8 @@
0
};
+static pthread_mutex_t _tls_desc_lock = PTHREAD_MUTEX_INITIALIZER;
+
struct _thread_area_head {
void *self;
};
@@ -71,6 +73,7 @@
{
int rc, segment;
+ pthread_mutex_lock(&_tls_desc_lock);
_tls_desc.base_addr = (unsigned long)ptr;
/* We also need to write the location of the tls to ptr[0] */
@@ -88,6 +91,8 @@
asm __volatile__ (
" movw %w0, %%gs" :: "q"(segment)
);
+ pthread_mutex_unlock(&_tls_desc_lock);
+
return 0;
}
diff --git a/libc/arch-x86/bionic/clone.S b/libc/arch-x86/bionic/clone.S
index b9b0957..8abb7c8 100644
--- a/libc/arch-x86/bionic/clone.S
+++ b/libc/arch-x86/bionic/clone.S
@@ -22,6 +22,7 @@
movl %eax, -8(%ecx)
movl %ecx, -4(%ecx)
+ subl $16, %ecx
movl $__NR_clone, %eax
int $0x80
test %eax, %eax
@@ -39,7 +40,6 @@
# we're in the child thread now, call __thread_entry
# with the appropriate arguments on the child stack
# we already placed most of them
- subl $16, %esp
jmp __thread_entry
hlt
diff --git a/libc/arch-x86/syscalls.mk b/libc/arch-x86/syscalls.mk
index ba85907..c9ccc39 100644
--- a/libc/arch-x86/syscalls.mk
+++ b/libc/arch-x86/syscalls.mk
@@ -15,6 +15,7 @@
syscall_src += arch-x86/syscalls/getresuid.S
syscall_src += arch-x86/syscalls/getresgid.S
syscall_src += arch-x86/syscalls/gettid.S
+syscall_src += arch-x86/syscalls/readahead.S
syscall_src += arch-x86/syscalls/getgroups.S
syscall_src += arch-x86/syscalls/getpgid.S
syscall_src += arch-x86/syscalls/getppid.S
diff --git a/libc/arch-x86/syscalls/readahead.S b/libc/arch-x86/syscalls/readahead.S
new file mode 100644
index 0000000..b89314f
--- /dev/null
+++ b/libc/arch-x86/syscalls/readahead.S
@@ -0,0 +1,32 @@
+/* autogenerated by gensyscalls.py */
+#include <sys/linux-syscalls.h>
+
+ .text
+ .type readahead, @function
+ .globl readahead
+ .align 4
+
+readahead:
+ pushl %ebx
+ pushl %ecx
+ pushl %edx
+ pushl %esi
+ mov 20(%esp), %ebx
+ mov 24(%esp), %ecx
+ mov 28(%esp), %edx
+ mov 32(%esp), %esi
+ movl $__NR_readahead, %eax
+ int $0x80
+ cmpl $-129, %eax
+ jb 1f
+ negl %eax
+ pushl %eax
+ call __set_errno
+ addl $4, %esp
+ orl $-1, %eax
+1:
+ popl %esi
+ popl %edx
+ popl %ecx
+ popl %ebx
+ ret
diff --git a/libc/bionic/cpuacct.c b/libc/bionic/cpuacct.c
index 7317073..1321d0e 100644
--- a/libc/bionic/cpuacct.c
+++ b/libc/bionic/cpuacct.c
@@ -30,16 +30,19 @@
#include <errno.h>
#include <sys/stat.h>
#include "cpuacct.h"
+#include <fcntl.h>
int cpuacct_add(uid_t uid)
{
int count;
- FILE *fp;
+ int fd;
char buf[80];
+ ssize_t n;
+ int ret = 0;
count = snprintf(buf, sizeof(buf), "/acct/uid/%d/tasks", uid);
- fp = fopen(buf, "w+");
- if (!fp) {
+ fd = open(buf, O_RDWR | O_CREAT, 0666);
+ if (fd == -1) {
/* Note: sizeof("tasks") returns 6, which includes the NULL char */
buf[count - sizeof("tasks")] = 0;
if (mkdir(buf, 0775) < 0)
@@ -47,14 +50,19 @@
/* Note: sizeof("tasks") returns 6, which includes the NULL char */
buf[count - sizeof("tasks")] = '/';
- fp = fopen(buf, "w+");
+ fd = open(buf, O_RDWR | O_CREAT, 0666);
}
- if (!fp)
+ if (fd == -1)
return -errno;
- fprintf(fp, "0");
- if (fclose(fp))
+ n = TEMP_FAILURE_RETRY(write(fd, "0", 1));
+ if (n < 0)
+ ret = -errno;
+ else if (n == 0)
+ ret = -EIO;
+
+ if (TEMP_FAILURE_RETRY(close(fd)) == -1)
return -errno;
- return 0;
+ return ret;
}
diff --git a/libc/bionic/malloc_debug_leak.c b/libc/bionic/malloc_debug_leak.c
index 0a3a68d..e0bcee9 100644
--- a/libc/bionic/malloc_debug_leak.c
+++ b/libc/bionic/malloc_debug_leak.c
@@ -263,7 +263,7 @@
// =============================================================================
#define CHK_FILL_FREE 0xef
-#define CHK_SENTINEL_VALUE 0xeb
+#define CHK_SENTINEL_VALUE (char)0xeb
#define CHK_SENTINEL_HEAD_SIZE 16
#define CHK_SENTINEL_TAIL_SIZE 16
#define CHK_OVERHEAD_SIZE ( CHK_SENTINEL_HEAD_SIZE + \
diff --git a/libc/bionic/pthread.c b/libc/bionic/pthread.c
index 1da2ec9..3435d21 100644
--- a/libc/bionic/pthread.c
+++ b/libc/bionic/pthread.c
@@ -571,6 +571,7 @@
void* stack_base = thread->attr.stack_base;
int stack_size = thread->attr.stack_size;
int user_stack = (thread->attr.flags & PTHREAD_ATTR_FLAG_USER_STACK) != 0;
+ sigset_t mask;
// call the cleanup handlers first
while (thread->cleanup_stack) {
@@ -613,6 +614,10 @@
pthread_mutex_unlock(&gThreadListLock);
}
+ sigfillset(&mask);
+ sigdelset(&mask, SIGSEGV);
+ (void)sigprocmask(SIG_SETMASK, &mask, (sigset_t *)NULL);
+
// destroy the thread stack
if (user_stack)
_exit_thread((int)retval);
@@ -1856,7 +1861,21 @@
return ret;
}
-extern int __rt_sigprocmask(int, const sigset_t *, sigset_t *, size_t);
+/* Despite the fact that our kernel headers define sigset_t explicitly
+ * as a 32-bit integer, the kernel system call really expects a 64-bit
+ * bitmap for the signal set, or more exactly an array of two-32-bit
+ * values (see $KERNEL/arch/$ARCH/include/asm/signal.h for details).
+ *
+ * Unfortunately, we cannot fix the sigset_t definition without breaking
+ * the C library ABI, so perform a little runtime translation here.
+ */
+typedef union {
+ sigset_t bionic;
+ uint32_t kernel[2];
+} kernel_sigset_t;
+
+/* this is a private syscall stub */
+extern int __rt_sigprocmask(int, const kernel_sigset_t *, kernel_sigset_t *, size_t);
int pthread_sigmask(int how, const sigset_t *set, sigset_t *oset)
{
@@ -1865,16 +1884,31 @@
*/
int ret, old_errno = errno;
- /* 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);
+ /* We must convert *set into a kernel_sigset_t */
+ kernel_sigset_t in_set, *in_set_ptr;
+ kernel_sigset_t out_set;
+
+ in_set.kernel[0] = in_set.kernel[1] = 0;
+ out_set.kernel[0] = out_set.kernel[1] = 0;
+
+ /* 'in_set_ptr' is the second parameter to __rt_sigprocmask. It must be NULL
+ * if 'set' is NULL to ensure correct semantics (which in this case would
+ * be to ignore 'how' and return the current signal set into 'oset'.
+ */
+ if (set == NULL) {
+ in_set_ptr = NULL;
+ } else {
+ in_set.bionic = *set;
+ in_set_ptr = &in_set;
+ }
+
+ ret = __rt_sigprocmask(how, in_set_ptr, &out_set, sizeof(kernel_sigset_t));
if (ret < 0)
ret = errno;
+ if (oset)
+ *oset = out_set.bionic;
+
errno = old_errno;
return ret;
}
diff --git a/libc/include/sys/linux-syscalls.h b/libc/include/sys/linux-syscalls.h
index e33e916..b6b7008 100644
--- a/libc/include/sys/linux-syscalls.h
+++ b/libc/include/sys/linux-syscalls.h
@@ -20,6 +20,7 @@
#define __NR_getresuid32 (__NR_SYSCALL_BASE + 209)
#define __NR_getresgid32 (__NR_SYSCALL_BASE + 211)
#define __NR_gettid (__NR_SYSCALL_BASE + 224)
+#define __NR_readahead (__NR_SYSCALL_BASE + 225)
#define __NR_getgroups32 (__NR_SYSCALL_BASE + 205)
#define __NR_getpgid (__NR_SYSCALL_BASE + 132)
#define __NR_getppid (__NR_SYSCALL_BASE + 64)
diff --git a/libc/include/sys/linux-unistd.h b/libc/include/sys/linux-unistd.h
index da57f55..d0aff93 100644
--- a/libc/include/sys/linux-unistd.h
+++ b/libc/include/sys/linux-unistd.h
@@ -20,6 +20,7 @@
uid_t getresuid (void);
gid_t getresgid (void);
pid_t gettid (void);
+ssize_t readahead (int, off64_t, size_t);
int getgroups (int, gid_t *);
pid_t getpgid (pid_t);
pid_t getppid (void);
diff --git a/libc/string/index.c b/libc/string/index.c
index fb0492f..81bfba4 100644
--- a/libc/string/index.c
+++ b/libc/string/index.c
@@ -34,7 +34,7 @@
index(const char *p, int ch)
{
for (;; ++p) {
- if (*p == ch)
+ if (*p == (char) ch)
return((char *)p);
if (!*p)
return((char *)NULL);
diff --git a/libc/string/memrchr.c b/libc/string/memrchr.c
index a533fef..aeb5643 100644
--- a/libc/string/memrchr.c
+++ b/libc/string/memrchr.c
@@ -35,10 +35,10 @@
const char* q = p + n;
while (1) {
- q--; if (q < p || q[0] == c) break;
- q--; if (q < p || q[0] == c) break;
- q--; if (q < p || q[0] == c) break;
- q--; if (q < p || q[0] == c) break;
+ q--; if (q < p || q[0] == (char) c) break;
+ q--; if (q < p || q[0] == (char) c) break;
+ q--; if (q < p || q[0] == (char) c) break;
+ q--; if (q < p || q[0] == (char) c) break;
}
if (q >= p)
return (void*)q;
diff --git a/libc/string/strchr.c b/libc/string/strchr.c
index 31ba4e2..9b4332c 100644
--- a/libc/string/strchr.c
+++ b/libc/string/strchr.c
@@ -34,7 +34,7 @@
strchr(const char *p, int ch)
{
for (;; ++p) {
- if (*p == ch)
+ if (*p == (char) ch)
return((char *)p);
if (!*p)
return((char *)NULL);
diff --git a/libc/string/strrchr.c b/libc/string/strrchr.c
index 4918f82..10c07e6 100644
--- a/libc/string/strrchr.c
+++ b/libc/string/strrchr.c
@@ -36,7 +36,7 @@
char *save;
for (save = NULL;; ++p) {
- if (*p == ch)
+ if (*p == (char) ch)
save = (char *)p;
if (!*p)
return(save);
diff --git a/libc/unistd/opendir.c b/libc/unistd/opendir.c
index afa3ea0..f178bc6 100644
--- a/libc/unistd/opendir.c
+++ b/libc/unistd/opendir.c
@@ -92,6 +92,9 @@
_readdir_unlocked(DIR* dir)
{
struct dirent* entry;
+#ifndef NDEBUG
+ unsigned reclen;
+#endif
if ( !dir->_DIR_avail )
{
@@ -115,15 +118,18 @@
if (((long)(void*)entry & 3) != 0)
return NULL;
- if ( (unsigned)entry->d_reclen > sizeof(*entry) ||
- entry->d_reclen <= offsetof(struct dirent, d_name) )
+#ifndef NDEBUG
+ // paranoid testing of the interface with the kernel getdents64 system call
+ reclen = offsetof(struct dirent, d_name) + strlen(entry->d_name) + 1;
+ if ( reclen > sizeof(*entry) || reclen <= offsetof(struct dirent, d_name) )
goto Bad;
- if ( (char*)entry + entry->d_reclen > (char*)dir->_DIR_buff + sizeof(dir->_DIR_buff) )
+ if ( (char*)entry + reclen > (char*)dir->_DIR_buff + sizeof(dir->_DIR_buff) )
goto Bad;
- if ( !memchr( entry->d_name, 0, entry->d_reclen - offsetof(struct dirent, d_name)) )
+ if ( !memchr( entry->d_name, 0, reclen - offsetof(struct dirent, d_name)) )
goto Bad;
+#endif
dir->_DIR_next = (struct dirent*)((char*)entry + entry->d_reclen);
dir->_DIR_avail -= entry->d_reclen;
diff --git a/libc/unistd/pathconf.c b/libc/unistd/pathconf.c
index 032f918..26b580f 100644
--- a/libc/unistd/pathconf.c
+++ b/libc/unistd/pathconf.c
@@ -70,13 +70,12 @@
};
int nn = 0;
- for (;;) {
- if ( known64[nn] == EOL_MAGIC )
- return 32;
-
- if ( known64[nn] == s->f_type )
+ for (; known64[nn] != EOL_MAGIC; ++nn) {
+ if (known64[nn] == s->f_type) {
return 64;
+ }
}
+ return 32;
}
@@ -99,12 +98,10 @@
};
int nn = 0;
- for (;;) {
- if ( knownMax[nn].type == EOL_MAGIC )
- return LINK_MAX;
-
- if ( knownMax[nn].type == s->f_type )
+ for (; knownMax[nn].type != EOL_MAGIC; ++nn) {
+ if (knownMax[nn].type == s->f_type) {
return knownMax[nn].max;
+ }
}
return LINK_MAX;
}
@@ -121,12 +118,12 @@
};
int nn = 0;
- for (;;) {
- if (knownNoSymlinks[nn] == 0)
- return 1;
- if (knownNoSymlinks[nn] == s->f_type)
+ for (; knownNoSymlinks[nn] != EOL_MAGIC; ++nn) {
+ if (knownNoSymlinks[nn] == s->f_type) {
return 0;
+ }
}
+ return 1;
}
static long
diff --git a/linker/linker.c b/linker/linker.c
index e0a8a18..17008f8 100644
--- a/linker/linker.c
+++ b/linker/linker.c
@@ -707,7 +707,11 @@
if (hdr->e_ident[EI_MAG3] != ELFMAG3) return -1;
/* TODO: Should we verify anything else in the header? */
-
+#ifdef ANDROID_ARM_LINKER
+ if (hdr->e_machine != EM_ARM) return -1;
+#elif defined(ANDROID_X86_LINKER)
+ if (hdr->e_machine != EM_386) return -1;
+#endif
return 0;
}