Improve cosmo's conformance to libc-test

This change addresses various open source compatibility issues, so that
we pass 313/411 of the tests in https://github.com/jart/libc-test where
earlier today we were passing about 30/411 of them, due to header toil.
Please note that Glibc only passes 341/411 so 313 today is pretty good!

- Make the conformance of libc/isystem/ headers nearly perfect
- Import more of the remaining math library routines from Musl
- Fix inconsistencies with type signatures of calls like umask
- Write tests for getpriority/setpriority which work great now
- conform to `struct sockaddr *` on remaining socket functions
- Import a bunch of uninteresting stdlib functions e.g. rand48
- Introduce readdir_r, scandir, pthread_kill, sigsetjmp, etc..

Follow the instructions in our `tool/scripts/cosmocc` toolchain to run
these tests yourself. You use `make CC=cosmocc` on the test repository
This commit is contained in:
Justine Tunney 2022-10-10 17:52:41 -07:00
parent 467a332e38
commit e557058ac8
No known key found for this signature in database
GPG key ID: BE714B4575D6E328
189 changed files with 5091 additions and 884 deletions

View file

@ -85,7 +85,7 @@ int execve(const char *, char *const[], char *const[]);
int execvp(const char *, char *const[]);
int execvpe(const char *, char *const[], char *const[]);
int fexecve(int, char *const[], char *const[]);
int faccessat(int, const char *, int, uint32_t);
int faccessat(int, const char *, int, int);
int fadvise(int, uint64_t, uint64_t, int);
int fchdir(int);
int fchmod(int, uint32_t) dontthrow;
@ -95,6 +95,7 @@ int fchownat(int, const char *, uint32_t, uint32_t, int);
int fcntl(int, int, ...);
int fdatasync(int);
int flock(int, int);
int lockf(int, int, int64_t);
int fork(void);
int fsync(int);
int ftruncate(int, int64_t);
@ -148,7 +149,7 @@ int pipe(int[hasatleast 2]);
int pipe2(int[hasatleast 2], int);
int pivot_root(const char *, const char *);
int pledge(const char *, const char *);
int posix_fadvise(int, uint64_t, uint64_t, int);
int posix_fadvise(int, int64_t, int64_t, int);
int posix_madvise(void *, uint64_t, int);
int prctl(int, ...);
int raise(int);
@ -162,10 +163,10 @@ int sched_yield(void);
int seccomp(unsigned, unsigned, void *);
int setegid(uint32_t);
int seteuid(uint32_t);
int setfsgid(int);
int setfsuid(int);
int setgid(int);
int setgroups(size_t size, const uint32_t list[]);
int setfsgid(unsigned);
int setfsuid(unsigned);
int setgid(unsigned);
int setgroups(size_t, const uint32_t[]);
int setpgid(int, int);
int setpgrp(void);
int setpriority(int, unsigned, int);
@ -174,7 +175,7 @@ int setresgid(uint32_t, uint32_t, uint32_t);
int setresuid(uint32_t, uint32_t, uint32_t);
int setreuid(uint32_t, uint32_t);
int setsid(void);
int setuid(int);
int setuid(unsigned);
int sigignore(int);
int siginterrupt(int, int);
int symlink(const char *, const char *);
@ -187,9 +188,9 @@ int tgkill(int, int, int);
int tkill(int, int);
int tmpfd(void);
int touch(const char *, uint32_t);
int truncate(const char *, uint64_t);
int truncate(const char *, int64_t);
int ttyname_r(int, char *, size_t);
int umask(int);
unsigned umask(unsigned);
int unlink(const char *);
int unlink_s(const char **);
int unlinkat(int, const char *, int);
@ -204,7 +205,7 @@ long ptrace(int, ...);
ssize_t copy_file_range(int, long *, int, long *, size_t, uint32_t);
ssize_t copyfd(int, int64_t *, int, int64_t *, size_t, uint32_t);
ssize_t getfiledescriptorsize(int);
ssize_t lseek(int, int64_t, unsigned);
ssize_t lseek(int, int64_t, int);
ssize_t pread(int, void *, size_t, int64_t);
ssize_t pwrite(int, const void *, size_t, int64_t);
ssize_t read(int, void *, size_t);

View file

@ -19,7 +19,7 @@
#include "libc/calls/termios.h"
#include "libc/sysv/errfuns.h"
int cfsetispeed(struct termios *t, int speed) {
int cfsetispeed(struct termios *t, unsigned speed) {
if (speed) {
if (CBAUD) {
if (speed & ~CBAUD) return einval();

View file

@ -20,7 +20,7 @@
#include "libc/sysv/consts/termios.h"
#include "libc/sysv/errfuns.h"
int cfsetospeed(struct termios *t, int speed) {
int cfsetospeed(struct termios *t, unsigned speed) {
if (CBAUD) {
if (!(speed & ~CBAUD)) {
t->c_cflag &= ~CBAUD;

View file

@ -48,7 +48,7 @@
* @note on Linux `flags` is only supported on Linux 5.8+
* @asyncsignalsafe
*/
int faccessat(int dirfd, const char *path, int amode, uint32_t flags) {
int faccessat(int dirfd, const char *path, int amode, int flags) {
int e, rc;
struct ZiposUri zipname;
if (!path || (IsAsan() && !__asan_is_valid(path, 1))) {

View file

@ -16,28 +16,67 @@
TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/calls/kntprioritycombos.internal.h"
#include "libc/calls/calls.h"
#include "libc/calls/internal.h"
#include "libc/calls/struct/fd.internal.h"
#include "libc/calls/syscall-nt.internal.h"
#include "libc/calls/syscall_support-nt.internal.h"
#include "libc/nexgen32e/ffs.h"
#include "libc/nt/enum/processaccess.h"
#include "libc/nt/enum/processcreationflags.h"
#include "libc/nt/process.h"
#include "libc/nt/runtime.h"
#include "libc/nt/thread.h"
#include "libc/runtime/runtime.h"
#include "libc/sysv/consts/prio.h"
#include "libc/sysv/errfuns.h"
textwindows int sys_getpriority_nt(int ignored) {
size_t i;
uint32_t tier, lg2tier, wut;
if ((tier = GetPriorityClass(GetCurrentProcess())) != 0 &&
(wut = GetThreadPriority(GetCurrentThread())) != -1u) {
lg2tier = ffs(tier);
for (i = 0; i < kNtPriorityCombosLen; ++i) {
if (kNtPriorityCombos[i].lg2tier == lg2tier &&
kNtPriorityCombos[i].wut == wut) {
return kNtPriorityCombos[i].nice;
}
}
abort();
} else {
return __winerr();
textwindows int sys_getpriority_nt(int which, unsigned pid) {
int rc;
uint32_t tier;
int64_t h, closeme = -1;
if (which != PRIO_PROCESS) {
return einval();
}
if (!pid || pid == getpid()) {
h = GetCurrentProcess();
} else if (__isfdkind(pid, kFdProcess)) {
h = g_fds.p[pid].handle;
} else {
h = OpenProcess(kNtProcessQueryInformation, false, pid);
if (!h) return __winerr();
closeme = h;
}
if ((tier = GetPriorityClass(h))) {
switch (tier) {
case kNtRealtimePriorityClass:
rc = -16;
break;
case kNtHighPriorityClass:
rc = -10;
break;
case kNtAboveNormalPriorityClass:
rc = -5;
break;
case kNtNormalPriorityClass:
rc = 0;
break;
case kNtBelowNormalPriorityClass:
rc = 5;
break;
case kNtIdlePriorityClass:
rc = 15;
break;
default:
notpossible;
}
} else {
rc = __winerr();
}
if (closeme != -1) {
CloseHandle(closeme);
}
return rc;
}

View file

@ -17,10 +17,13 @@
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/calls/calls.h"
#include "libc/intrin/strace.internal.h"
#include "libc/calls/syscall-nt.internal.h"
#include "libc/calls/syscall-sysv.internal.h"
#include "libc/dce.h"
#include "libc/errno.h"
#include "libc/intrin/asmflag.h"
#include "libc/intrin/describeflags.internal.h"
#include "libc/intrin/strace.internal.h"
#include "libc/limits.h"
/**
* Returns nice value of thing.
@ -29,20 +32,47 @@
* to clear `errno` beforehand and see if it changed, in order to truly
* determine if an error happened.
*
* @param which can be PRIO_PROCESS, PRIO_PGRP, PRIO_USER
* On Windows, there's only six priority classes. We define them as -16
* (realtime), -10 (high), -5 (above), 0 (normal), 5 (below), 15 (idle)
* which are the only values that'll roundtrip getpriority/setpriority.
*
* @param which can be one of:
* - `PRIO_PROCESS` is supported universally
* - `PRIO_PGRP` is supported on unix
* - `PRIO_USER` is supported on unix
* @param who is the pid, pgid, or uid (0 means current)
* @return value [-NZERO,NZERO) or -1 w/ errno
* @see setpriority(), nice()
* @raise EINVAL if `which` was invalid or unsupported
* @raise EPERM if access to process was denied
* @raise ESRCH if no such process existed
* @see setpriority()
*/
int getpriority(int which, unsigned who) {
privileged int getpriority(int which, unsigned who) {
int rc;
if (!IsWindows()) {
if ((rc = sys_getpriority(which, who)) != -1) {
rc = 20 - rc;
char cf;
if (IsLinux()) {
asm volatile("syscall"
: "=a"(rc)
: "0"(140), "D"(which), "S"(who)
: "rcx", "r11", "memory");
if (rc >= 0) {
rc = NZERO - rc;
} else {
errno = -rc;
rc = -1;
}
} else if (IsBsd()) {
asm volatile(CFLAG_ASM("syscall")
: CFLAG_CONSTRAINT(cf), "=a"(rc)
: "1"((IsXnu() ? 0x2000000 : 0) | 100), "D"(which), "S"(who)
: "rcx", "rdx", "r8", "r9", "r10", "r11", "memory");
if (cf) {
errno = rc;
rc = -1;
}
} else {
rc = sys_getsetpriority_nt(which, who, 0, sys_getpriority_nt);
rc = sys_getpriority_nt(which, who);
}
STRACE("getpriority(%d, %u) → %d% m", which, who, rc);
STRACE("getpriority(%s, %u) → %d% m", DescribeWhichPrio(which), who, rc);
return rc;
}

View file

@ -1,29 +0,0 @@
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi
Copyright 2020 Justine Alexandra Roberts Tunney
Permission to use, copy, modify, and/or distribute this software for
any purpose with or without fee is hereby granted, provided that the
above copyright notice and this permission notice appear in all copies.
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/calls/calls.h"
#include "libc/fmt/conv.h"
#include "libc/sysv/consts/prio.h"
#include "libc/sysv/errfuns.h"
textwindows int sys_getsetpriority_nt(int which, unsigned who, int value,
int (*impl)(int)) {
if (which != PRIO_PROCESS && which != PRIO_PGRP) return einval();
if (who && who != getpid() && who != gettid()) return esrch();
return impl(value);
}

View file

@ -1,56 +0,0 @@
/*-*- mode:c;indent-tabs-mode:nil;c-basic-offset:2;tab-width:8;coding:utf-8 -*-│
vi: set net ft=c ts=2 sts=2 sw=2 fenc=utf-8 :vi
Copyright 2020 Justine Alexandra Roberts Tunney
Permission to use, copy, modify, and/or distribute this software for
any purpose with or without fee is hereby granted, provided that the
above copyright notice and this permission notice appear in all copies.
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/intrin/bits.h"
#include "libc/calls/kntprioritycombos.internal.h"
#include "libc/limits.h"
#include "libc/macros.internal.h"
#include "libc/nexgen32e/ffs.h"
#include "libc/nt/enum/processcreationflags.h"
#include "libc/nt/enum/threadpriority.h"
hidden const struct NtPriorityCombo kNtPriorityCombos[] = {
{-20, ffs(kNtHighPriorityClass), kNtThreadPriorityHighest, 15},
{-18, ffs(kNtHighPriorityClass), kNtThreadPriorityTimeCritical, 15},
{-17, ffs(kNtNormalPriorityClass), kNtThreadPriorityTimeCritical, 15},
{-15, ffs(kNtIdlePriorityClass), kNtThreadPriorityTimeCritical, 15},
{-13, ffs(kNtHighPriorityClass), kNtThreadPriorityAboveNormal, 14},
{-11, ffs(kNtHighPriorityClass), kNtThreadPriorityNormal, 13},
{-9, ffs(kNtHighPriorityClass), kNtThreadPriorityBelowNormal, 12},
{-7, ffs(kNtNormalPriorityClass), kNtThreadPriorityHighest, 11},
{-5, ffs(kNtHighPriorityClass), kNtThreadPriorityLowest, 11},
{-3, ffs(kNtNormalPriorityClass), kNtThreadPriorityAboveNormal, 10},
{-1, ffs(kNtNormalPriorityClass), kNtThreadPriorityHighest, 9},
{0, ffs(kNtNormalPriorityClass), kNtThreadPriorityNormal, 9},
{1, ffs(kNtNormalPriorityClass), kNtThreadPriorityAboveNormal, 8},
{2, ffs(kNtNormalPriorityClass), kNtThreadPriorityBelowNormal, 8},
{3, ffs(kNtNormalPriorityClass), kNtThreadPriorityNormal, 7},
{4, ffs(kNtNormalPriorityClass), kNtThreadPriorityLowest, 7},
{5, ffs(kNtIdlePriorityClass), kNtThreadPriorityHighest, 6},
{6, ffs(kNtNormalPriorityClass), kNtThreadPriorityBelowNormal, 6},
{7, ffs(kNtIdlePriorityClass), kNtThreadPriorityAboveNormal, 5},
{9, ffs(kNtNormalPriorityClass), kNtThreadPriorityLowest, 5},
{11, ffs(kNtIdlePriorityClass), kNtThreadPriorityNormal, 4},
{13, ffs(kNtIdlePriorityClass), kNtThreadPriorityBelowNormal, 3},
{15, ffs(kNtIdlePriorityClass), kNtThreadPriorityLowest, 2},
{17, ffs(kNtHighPriorityClass), kNtThreadPriorityIdle, 1},
{18, ffs(kNtNormalPriorityClass), kNtThreadPriorityIdle, 1},
{19, ffs(kNtIdlePriorityClass), kNtThreadPriorityIdle, 1},
};
hidden const unsigned kNtPriorityCombosLen = ARRAYLEN(kNtPriorityCombos);

18
libc/calls/kntprioritycombos.internal.h Normal file → Executable file
View file

@ -1,18 +0,0 @@
#ifndef COSMOPOLITAN_LIBC_CALLS_KNTPRIORITYCOMBOS_H_
#define COSMOPOLITAN_LIBC_CALLS_KNTPRIORITYCOMBOS_H_
#if !(__ASSEMBLER__ + __LINKER__ + 0)
COSMOPOLITAN_C_START_
struct NtPriorityCombo {
int8_t nice; /* sorted by this */
int8_t lg2tier;
int8_t wut;
int8_t prio;
};
hidden extern const unsigned kNtPriorityCombosLen;
hidden extern const struct NtPriorityCombo kNtPriorityCombos[];
COSMOPOLITAN_C_END_
#endif /* !(__ASSEMBLER__ + __LINKER__ + 0) */
#endif /* COSMOPOLITAN_LIBC_CALLS_KNTPRIORITYCOMBOS_H_ */

View file

@ -74,7 +74,7 @@
* @threadsafe
* @vforksafe
*/
int64_t lseek(int fd, int64_t offset, unsigned whence) {
int64_t lseek(int fd, int64_t offset, int whence) {
int64_t rc;
if (fd < g_fds.n && g_fds.p[fd].kind == kFdZip) {
rc = _weaken(__zipos_lseek)(

View file

@ -18,6 +18,7 @@
*/
#include "libc/calls/calls.h"
#include "libc/fmt/conv.h"
#include "libc/limits.h"
#include "libc/macros.internal.h"
#include "libc/sysv/consts/prio.h"

View file

@ -44,7 +44,7 @@ int sys_fadvise_netbsd(int, int, int64_t, int64_t, int) asm("sys_fadvise");
* @returnserrno
* @threadsafe
*/
errno_t posix_fadvise(int fd, uint64_t offset, uint64_t len, int advice) {
errno_t posix_fadvise(int fd, int64_t offset, int64_t len, int advice) {
int rc, e = errno;
if (IsLinux()) {
rc = sys_fadvise(fd, offset, len, advice);

View file

@ -16,6 +16,7 @@
TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/calls/calls.h"
#include "libc/calls/internal.h"
#include "libc/calls/sched-sysv.internal.h"
#include "libc/calls/struct/cpuset.h"
@ -32,7 +33,7 @@ static dontinline textwindows int sys_sched_setaffinity_nt(
int rc;
int64_t h, closeme = -1;
if (!pid /* || pid == getpid() */) {
if (!pid || pid == getpid()) {
h = GetCurrentProcess();
} else if (__isfdkind(pid, kFdProcess)) {
h = g_fds.p[pid].handle;

View file

@ -17,15 +17,15 @@
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/calls/calls.h"
#include "libc/intrin/strace.internal.h"
#include "libc/calls/syscall-sysv.internal.h"
#include "libc/dce.h"
#include "libc/intrin/strace.internal.h"
/**
* Sets user id of current process for file system ops.
* @return previous filesystem gid
*/
int setfsgid(int gid) {
int setfsgid(unsigned gid) {
int rc;
if (IsLinux()) {
rc = sys_setfsgid(gid);

View file

@ -17,15 +17,15 @@
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/calls/calls.h"
#include "libc/intrin/strace.internal.h"
#include "libc/calls/syscall-sysv.internal.h"
#include "libc/dce.h"
#include "libc/intrin/strace.internal.h"
/**
* Sets user id of current process for file system ops.
* @return previous filesystem uid
*/
int setfsuid(int uid) {
int setfsuid(unsigned uid) {
int rc;
if (IsLinux()) {
rc = sys_setfsuid(uid);

View file

@ -17,9 +17,9 @@
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/calls/calls.h"
#include "libc/intrin/strace.internal.h"
#include "libc/calls/syscall-sysv.internal.h"
#include "libc/dce.h"
#include "libc/intrin/strace.internal.h"
/**
* Sets group id of current process.
@ -28,7 +28,7 @@
* @raise EINVAL if gid not in legal range
* @raise EPERM if lack privileges
*/
int setgid(int gid) {
int setgid(unsigned gid) {
int rc;
if (IsWindows() && gid == getgid()) {
rc = 0;

View file

@ -16,37 +16,60 @@
TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/intrin/safemacros.internal.h"
#include "libc/calls/kntprioritycombos.internal.h"
#include "libc/calls/calls.h"
#include "libc/calls/internal.h"
#include "libc/calls/syscall-nt.internal.h"
#include "libc/calls/syscall_support-nt.internal.h"
#include "libc/nt/enum/processaccess.h"
#include "libc/nt/enum/processcreationflags.h"
#include "libc/nt/process.h"
#include "libc/nt/runtime.h"
#include "libc/nt/thread.h"
#include "libc/sysv/consts/prio.h"
#include "libc/sysv/errfuns.h"
static textwindows struct NtPriorityCombo findntprio(int nice) {
size_t l, r, m;
l = 0;
r = kNtPriorityCombosLen;
while (l < r) {
m = (l + r) >> 1;
if (kNtPriorityCombos[m].nice > nice) {
r = m;
} else {
l = m + 1;
}
}
return kNtPriorityCombos[max(0, l - 1)];
}
textwindows int sys_setpriority_nt(int nice) {
textwindows int sys_setpriority_nt(int which, unsigned pid, int nice) {
int rc;
uint32_t tier;
struct NtPriorityCombo p;
p = findntprio(nice);
tier = 1 << (p.lg2tier - 1);
if (SetPriorityClass(GetCurrentProcess(), tier) &&
SetThreadPriority(GetCurrentThread(), p.wut)) {
return p.nice;
} else {
return __winerr();
int64_t h, closeme = -1;
if (which != PRIO_PROCESS) {
return einval();
}
if (!pid || pid == getpid()) {
h = GetCurrentProcess();
} else if (__isfdkind(pid, kFdProcess)) {
h = g_fds.p[pid].handle;
} else {
h = OpenProcess(kNtProcessSetInformation | kNtProcessQueryInformation,
false, pid);
if (!h) return __winerr();
closeme = h;
}
if (nice <= -15) {
tier = kNtRealtimePriorityClass;
} else if (nice <= -9) {
tier = kNtHighPriorityClass;
} else if (nice <= -3) {
tier = kNtAboveNormalPriorityClass;
} else if (nice <= 3) {
tier = kNtNormalPriorityClass;
} else if (nice <= 12) {
tier = kNtBelowNormalPriorityClass;
} else {
tier = kNtIdlePriorityClass;
}
if (SetPriorityClass(h, tier)) {
rc = 0;
} else {
rc = __winerr();
}
if (closeme != -1) {
CloseHandle(closeme);
}
return rc;
}

View file

@ -20,22 +20,38 @@
#include "libc/calls/syscall-nt.internal.h"
#include "libc/calls/syscall-sysv.internal.h"
#include "libc/dce.h"
#include "libc/intrin/describeflags.internal.h"
#include "libc/intrin/strace.internal.h"
/**
* Sets nice value of thing.
*
* @param which can be PRIO_PROCESS, PRIO_PGRP, PRIO_USER
* On Windows, there's only six priority classes. We define them as -16
* (realtime), -10 (high), -5 (above), 0 (normal), 5 (below), 15 (idle)
* which are the only values that'll roundtrip getpriority/setpriority.
*
* @param which can be one of:
* - `PRIO_PROCESS` is supported universally
* - `PRIO_PGRP` is supported on unix
* - `PRIO_USER` is supported on unix
* @param who is the pid, pgid, or uid, 0 meaning current
* @param value [-NZERO,NZERO) which is clamped automatically
* @return 0 on success or -1 w/ errno
* @error EACCES if lower that RLIMIT_NICE
* @error EACCES on Linux without CAP_SYS_NICE
* @see getpriority(), nice()
* @return 0 on success, or -1 w/ errno
* @raise EINVAL if `which` was invalid or unsupported
* @error EACCES if `value` lower that `RLIMIT_NICE`
* @error EACCES on Linux without `CAP_SYS_NICE`
* @raise EPERM if access to process was denied
* @raise ESRCH if the process didn't exist
* @see getpriority()
*/
int setpriority(int which, unsigned who, int value) {
int rc;
if (!IsWindows()) {
return sys_setpriority(which, who, value);
rc = sys_setpriority(which, who, value);
} else {
return sys_getsetpriority_nt(which, who, value, sys_setpriority_nt);
rc = sys_setpriority_nt(which, who, value);
}
STRACE("setpriority(%s, %u, %d) → %d% m", DescribeWhichPrio(which), who,
value, rc);
return rc;
}

View file

@ -17,9 +17,9 @@
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/calls/calls.h"
#include "libc/intrin/strace.internal.h"
#include "libc/calls/syscall-sysv.internal.h"
#include "libc/dce.h"
#include "libc/intrin/strace.internal.h"
/**
* Sets user id of current process.
@ -30,7 +30,7 @@
* @raise EAGAIN change would cause `RLIMIT_NPROC` to be exceeded
* @raise EPERM if lack privileges
*/
int setuid(int uid) {
int setuid(unsigned uid) {
int rc;
if (IsWindows() && uid == getuid()) {
rc = 0;

View file

@ -16,7 +16,6 @@
TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/intrin/strace.internal.h"
#include "libc/calls/struct/metasigaltstack.h"
#include "libc/calls/struct/sigaltstack.h"
#include "libc/calls/struct/sigaltstack.internal.h"
@ -24,6 +23,8 @@
#include "libc/dce.h"
#include "libc/intrin/asan.internal.h"
#include "libc/intrin/describeflags.internal.h"
#include "libc/intrin/strace.internal.h"
#include "libc/sysv/consts/ss.h"
#include "libc/sysv/errfuns.h"
static void sigaltstack2bsd(struct sigaltstack_bsd *bsd,
@ -76,6 +77,8 @@ static void sigaltstack2linux(struct sigaltstack *linux,
* @param neu if non-null will install new signal alt stack
* @param old if non-null will receive current signal alt stack
* @return 0 on success, or -1 w/ errno
* @raise EFAULT if bad memory was supplied
* @raise ENOMEM if `neu->ss_size` is less than `MINSIGSTKSZ`
*/
int sigaltstack(const struct sigaltstack *neu, struct sigaltstack *old) {
int rc;
@ -86,6 +89,8 @@ int sigaltstack(const struct sigaltstack *neu, struct sigaltstack *old) {
(neu && (__asan_check(neu, sizeof(*neu)).kind ||
__asan_check(neu->ss_sp, neu->ss_size).kind)))) {
rc = efault();
} else if (neu && neu->ss_size < MINSIGSTKSZ) {
rc = enomem();
} else if (IsLinux() || IsBsd()) {
if (IsLinux()) {
a = neu;

View file

@ -20,8 +20,13 @@ int closedir(DIR *);
int dirfd(DIR *);
long telldir(DIR *);
struct dirent *readdir(DIR *);
int readdir_r(DIR *, struct dirent *, struct dirent **);
void rewinddir(DIR *);
void seekdir(DIR *, long);
int alphasort(const struct dirent **, const struct dirent **);
int versionsort(const struct dirent **, const struct dirent **);
int scandir(const char *, struct dirent ***, int (*)(const struct dirent *),
int (*)(const struct dirent **, const struct dirent **));
COSMOPOLITAN_C_END_
#endif /* !(__ASSEMBLER__ + __LINKER__ + 0) */

View file

@ -20,8 +20,7 @@ int sys_fork_nt(void) hidden;
int sys_ftruncate_nt(int64_t, uint64_t) hidden;
int sys_getloadavg_nt(double *, int) hidden;
int sys_getppid_nt(void) hidden;
int sys_getpriority_nt(int) hidden;
int sys_getsetpriority_nt(int, int, int, int (*)(int));
int sys_getpriority_nt(int, unsigned) hidden;
int sys_kill_nt(int, int) hidden;
int sys_linkat_nt(int, const char *, int, const char *) hidden;
int sys_madvise_nt(void *, size_t, int) hidden;
@ -31,7 +30,7 @@ int sys_open_nt(int, const char *, uint32_t, int32_t) dontdiscard hidden;
int sys_pipe_nt(int[hasatleast 2], unsigned) hidden;
int sys_renameat_nt(int, const char *, int, const char *) hidden;
int sys_sched_yield_nt(void) hidden;
int sys_setpriority_nt(int) hidden;
int sys_setpriority_nt(int, unsigned, int) hidden;
int sys_symlinkat_nt(const char *, int, const char *) hidden;
int sys_sync_nt(void) hidden;
int sys_truncate_nt(const char *, uint64_t) hidden;

View file

@ -31,8 +31,8 @@ int tcflow(int, int);
int tcflush(int, int);
int tcsendbreak(int, int);
void cfmakeraw(struct termios *);
int cfsetospeed(struct termios *, int);
int cfsetispeed(struct termios *, int);
int cfsetospeed(struct termios *, unsigned);
int cfsetispeed(struct termios *, unsigned);
uint32_t cfgetospeed(const struct termios *);
uint32_t cfgetispeed(const struct termios *);

View file

@ -48,6 +48,10 @@ static textwindows int sys_tkill_nt(int tid, int sig) {
* @param tid is thread id
* @param sig does nothing on xnu
* @return 0 on success, or -1 w/ errno
* @raise ESRCH if `tid` was valid but no such thread existed
* @raise EAGAIN if `RLIMIT_SIGPENDING` was exceeded
* @raise EINVAL if `tid` or `sig` was invalid
* @raise EPERM if permission was denied
* @asyncsignalsafe
*/
int tkill(int tid, int sig) {

View file

@ -61,7 +61,7 @@
* @see ftruncate()
* @threadsafe
*/
int truncate(const char *path, uint64_t length) {
int truncate(const char *path, int64_t length) {
int rc;
struct ZiposUri zipname;
if (IsMetal()) {

View file

@ -17,9 +17,9 @@
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/calls/calls.h"
#include "libc/intrin/strace.internal.h"
#include "libc/calls/syscall-sysv.internal.h"
#include "libc/dce.h"
#include "libc/intrin/strace.internal.h"
/**
* Sets file mode creation mask.
@ -27,7 +27,7 @@
* @return previous mask
* @note always succeeds
*/
int umask(int newmask) {
unsigned umask(unsigned newmask) {
int oldmask;
if (!IsWindows()) {
oldmask = sys_umask(newmask);

View file

@ -11,7 +11,7 @@
#define cc_t uint8_t
#define clock_t int64_t /* uint64_t on xnu */
#define dev_t uint64_t /* int32_t on xnu */
#define fsblkcnt_t int64_t
#define fsblkcnt_t uint64_t
#define fsfilcnt_t int64_t /* uint32_t on xnu */
#define gid_t uint32_t
#define id_t uint32_t /* int32_t on linux/freebsd/etc. */
@ -36,6 +36,8 @@
#define timer_t void*
#define uid_t uint32_t
#define rlim_t uint64_t /* int64_t on bsd */
#define clockid_t int32_t
#define nlink_t uint64_t
#define TIME_T_MAX __INT64_MAX__
#define TIME_T_MIN (-TIME_T_MAX - 1)