xref: /openbsd-src/gnu/llvm/compiler-rt/lib/sanitizer_common/sanitizer_solaris.cpp (revision 810390e339a5425391477d5d41c78d7cab2424ac)
13cab2bb3Spatrick //===-- sanitizer_solaris.cpp ---------------------------------------------===//
23cab2bb3Spatrick //
33cab2bb3Spatrick // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
43cab2bb3Spatrick // See https://llvm.org/LICENSE.txt for license information.
53cab2bb3Spatrick // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
63cab2bb3Spatrick //
73cab2bb3Spatrick //===----------------------------------------------------------------------===//
83cab2bb3Spatrick //
93cab2bb3Spatrick // This file is shared between various sanitizers' runtime libraries and
103cab2bb3Spatrick // implements Solaris-specific functions.
113cab2bb3Spatrick //===----------------------------------------------------------------------===//
123cab2bb3Spatrick 
133cab2bb3Spatrick #include "sanitizer_platform.h"
143cab2bb3Spatrick #if SANITIZER_SOLARIS
153cab2bb3Spatrick 
163cab2bb3Spatrick #include <stdio.h>
173cab2bb3Spatrick 
183cab2bb3Spatrick #include "sanitizer_common.h"
193cab2bb3Spatrick #include "sanitizer_flags.h"
203cab2bb3Spatrick #include "sanitizer_internal_defs.h"
213cab2bb3Spatrick #include "sanitizer_libc.h"
223cab2bb3Spatrick #include "sanitizer_placement_new.h"
233cab2bb3Spatrick #include "sanitizer_platform_limits_posix.h"
243cab2bb3Spatrick #include "sanitizer_procmaps.h"
253cab2bb3Spatrick 
263cab2bb3Spatrick #include <fcntl.h>
273cab2bb3Spatrick #include <pthread.h>
283cab2bb3Spatrick #include <sched.h>
293cab2bb3Spatrick #include <thread.h>
303cab2bb3Spatrick #include <synch.h>
313cab2bb3Spatrick #include <signal.h>
323cab2bb3Spatrick #include <sys/mman.h>
333cab2bb3Spatrick #include <sys/resource.h>
343cab2bb3Spatrick #include <sys/stat.h>
353cab2bb3Spatrick #include <sys/types.h>
363cab2bb3Spatrick #include <dirent.h>
373cab2bb3Spatrick #include <unistd.h>
383cab2bb3Spatrick #include <errno.h>
393cab2bb3Spatrick #include <stdlib.h>
403cab2bb3Spatrick 
413cab2bb3Spatrick namespace __sanitizer {
423cab2bb3Spatrick 
433cab2bb3Spatrick //#include "sanitizer_syscall_generic.inc"
443cab2bb3Spatrick 
453cab2bb3Spatrick #define _REAL(func) _ ## func
463cab2bb3Spatrick #define DECLARE__REAL(ret_type, func, ...) \
473cab2bb3Spatrick   extern "C" ret_type _REAL(func)(__VA_ARGS__)
483cab2bb3Spatrick #define DECLARE__REAL_AND_INTERNAL(ret_type, func, ...) \
493cab2bb3Spatrick   DECLARE__REAL(ret_type, func, __VA_ARGS__); \
503cab2bb3Spatrick   ret_type internal_ ## func(__VA_ARGS__)
513cab2bb3Spatrick 
523cab2bb3Spatrick #if !defined(_LP64) && _FILE_OFFSET_BITS == 64
533cab2bb3Spatrick #define _REAL64(func) _ ## func ## 64
543cab2bb3Spatrick #else
553cab2bb3Spatrick #define _REAL64(func) _REAL(func)
563cab2bb3Spatrick #endif
573cab2bb3Spatrick #define DECLARE__REAL64(ret_type, func, ...) \
583cab2bb3Spatrick   extern "C" ret_type _REAL64(func)(__VA_ARGS__)
593cab2bb3Spatrick #define DECLARE__REAL_AND_INTERNAL64(ret_type, func, ...) \
603cab2bb3Spatrick   DECLARE__REAL64(ret_type, func, __VA_ARGS__); \
613cab2bb3Spatrick   ret_type internal_ ## func(__VA_ARGS__)
623cab2bb3Spatrick 
633cab2bb3Spatrick // ---------------------- sanitizer_libc.h
DECLARE__REAL_AND_INTERNAL64(uptr,mmap,void * addr,uptr length,int prot,int flags,int fd,OFF_T offset)643cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL64(uptr, mmap, void *addr, uptr /*size_t*/ length,
653cab2bb3Spatrick                              int prot, int flags, int fd, OFF_T offset) {
663cab2bb3Spatrick   return (uptr)_REAL64(mmap)(addr, length, prot, flags, fd, offset);
673cab2bb3Spatrick }
683cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,munmap,void * addr,uptr length)693cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, munmap, void *addr, uptr length) {
703cab2bb3Spatrick   return _REAL(munmap)(addr, length);
713cab2bb3Spatrick }
723cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(int,mprotect,void * addr,uptr length,int prot)733cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(int, mprotect, void *addr, uptr length, int prot) {
743cab2bb3Spatrick   return _REAL(mprotect)(addr, length, prot);
753cab2bb3Spatrick }
763cab2bb3Spatrick 
77*d89ec533Spatrick // Illumos' declaration of madvise cannot be made visible if _XOPEN_SOURCE
78*d89ec533Spatrick // is defined as g++ does on Solaris.
79*d89ec533Spatrick //
80*d89ec533Spatrick // This declaration is consistent with Solaris 11.4. Both Illumos and Solaris
81*d89ec533Spatrick // versions older than 11.4 declared madvise with a caddr_t as the first
82*d89ec533Spatrick // argument, but we don't currently support Solaris versions older than 11.4,
83*d89ec533Spatrick // and as mentioned above the declaration is not visible on Illumos so we can
84*d89ec533Spatrick // use any declaration we like on Illumos.
85*d89ec533Spatrick extern "C" int madvise(void *, size_t, int);
86*d89ec533Spatrick 
internal_madvise(uptr addr,uptr length,int advice)87*d89ec533Spatrick int internal_madvise(uptr addr, uptr length, int advice) {
88*d89ec533Spatrick   return madvise((void *)addr, length, advice);
89*d89ec533Spatrick }
90*d89ec533Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,close,fd_t fd)913cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, close, fd_t fd) {
923cab2bb3Spatrick   return _REAL(close)(fd);
933cab2bb3Spatrick }
943cab2bb3Spatrick 
953cab2bb3Spatrick extern "C" int _REAL64(open)(const char *, int, ...);
963cab2bb3Spatrick 
internal_open(const char * filename,int flags)973cab2bb3Spatrick uptr internal_open(const char *filename, int flags) {
983cab2bb3Spatrick   return _REAL64(open)(filename, flags);
993cab2bb3Spatrick }
1003cab2bb3Spatrick 
internal_open(const char * filename,int flags,u32 mode)1013cab2bb3Spatrick uptr internal_open(const char *filename, int flags, u32 mode) {
1023cab2bb3Spatrick   return _REAL64(open)(filename, flags, mode);
1033cab2bb3Spatrick }
1043cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,read,fd_t fd,void * buf,uptr count)1053cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, read, fd_t fd, void *buf, uptr count) {
1063cab2bb3Spatrick   return _REAL(read)(fd, buf, count);
1073cab2bb3Spatrick }
1083cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,write,fd_t fd,const void * buf,uptr count)1093cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, write, fd_t fd, const void *buf, uptr count) {
1103cab2bb3Spatrick   return _REAL(write)(fd, buf, count);
1113cab2bb3Spatrick }
1123cab2bb3Spatrick 
1133cab2bb3Spatrick // FIXME: There's only _ftruncate64 beginning with Solaris 11.
DECLARE__REAL_AND_INTERNAL(uptr,ftruncate,fd_t fd,uptr size)1143cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, ftruncate, fd_t fd, uptr size) {
1153cab2bb3Spatrick   return ftruncate(fd, size);
1163cab2bb3Spatrick }
1173cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL64(uptr,stat,const char * path,void * buf)1183cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL64(uptr, stat, const char *path, void *buf) {
1193cab2bb3Spatrick   return _REAL64(stat)(path, (struct stat *)buf);
1203cab2bb3Spatrick }
1213cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL64(uptr,lstat,const char * path,void * buf)1223cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL64(uptr, lstat, const char *path, void *buf) {
1233cab2bb3Spatrick   return _REAL64(lstat)(path, (struct stat *)buf);
1243cab2bb3Spatrick }
1253cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL64(uptr,fstat,fd_t fd,void * buf)1263cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL64(uptr, fstat, fd_t fd, void *buf) {
1273cab2bb3Spatrick   return _REAL64(fstat)(fd, (struct stat *)buf);
1283cab2bb3Spatrick }
1293cab2bb3Spatrick 
internal_filesize(fd_t fd)1303cab2bb3Spatrick uptr internal_filesize(fd_t fd) {
1313cab2bb3Spatrick   struct stat st;
1323cab2bb3Spatrick   if (internal_fstat(fd, &st))
1333cab2bb3Spatrick     return -1;
1343cab2bb3Spatrick   return (uptr)st.st_size;
1353cab2bb3Spatrick }
1363cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,dup,int oldfd)1373cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, dup, int oldfd) {
1383cab2bb3Spatrick   return _REAL(dup)(oldfd);
1393cab2bb3Spatrick }
1403cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,dup2,int oldfd,int newfd)1413cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, dup2, int oldfd, int newfd) {
1423cab2bb3Spatrick   return _REAL(dup2)(oldfd, newfd);
1433cab2bb3Spatrick }
1443cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,readlink,const char * path,char * buf,uptr bufsize)1453cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, readlink, const char *path, char *buf,
1463cab2bb3Spatrick                            uptr bufsize) {
1473cab2bb3Spatrick   return _REAL(readlink)(path, buf, bufsize);
1483cab2bb3Spatrick }
1493cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,unlink,const char * path)1503cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, unlink, const char *path) {
1513cab2bb3Spatrick   return _REAL(unlink)(path);
1523cab2bb3Spatrick }
1533cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,rename,const char * oldpath,const char * newpath)1543cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, rename, const char *oldpath,
1553cab2bb3Spatrick                            const char *newpath) {
1563cab2bb3Spatrick   return _REAL(rename)(oldpath, newpath);
1573cab2bb3Spatrick }
1583cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,sched_yield,void)1593cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, sched_yield, void) {
1603cab2bb3Spatrick   return sched_yield();
1613cab2bb3Spatrick }
1623cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(void,usleep,u64 useconds)163*d89ec533Spatrick DECLARE__REAL_AND_INTERNAL(void, usleep, u64 useconds) {
164*d89ec533Spatrick   struct timespec ts;
165*d89ec533Spatrick   ts.tv_sec = useconds / 1000000;
166*d89ec533Spatrick   ts.tv_nsec = (useconds % 1000000) * 1000;
167*d89ec533Spatrick   nanosleep(&ts, nullptr);
1683cab2bb3Spatrick }
1693cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,execve,const char * filename,char * const argv[],char * const envp[])1703cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, execve, const char *filename,
1713cab2bb3Spatrick                            char *const argv[], char *const envp[]) {
1723cab2bb3Spatrick   return _REAL(execve)(filename, argv, envp);
1733cab2bb3Spatrick }
1743cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,waitpid,int pid,int * status,int options)1753cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, waitpid, int pid, int *status, int options) {
1763cab2bb3Spatrick   return _REAL(waitpid)(pid, status, options);
1773cab2bb3Spatrick }
1783cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(uptr,getpid,void)1793cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, getpid, void) {
1803cab2bb3Spatrick   return _REAL(getpid)();
1813cab2bb3Spatrick }
1823cab2bb3Spatrick 
1833cab2bb3Spatrick // FIXME: This might be wrong: _getdents doesn't take a struct linux_dirent *.
DECLARE__REAL_AND_INTERNAL64(uptr,getdents,fd_t fd,struct linux_dirent * dirp,unsigned int count)1843cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL64(uptr, getdents, fd_t fd, struct linux_dirent *dirp,
1853cab2bb3Spatrick                              unsigned int count) {
1863cab2bb3Spatrick   return _REAL64(getdents)(fd, dirp, count);
1873cab2bb3Spatrick }
1883cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL64(uptr,lseek,fd_t fd,OFF_T offset,int whence)1893cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL64(uptr, lseek, fd_t fd, OFF_T offset, int whence) {
1903cab2bb3Spatrick   return _REAL64(lseek)(fd, offset, whence);
1913cab2bb3Spatrick }
1923cab2bb3Spatrick 
1933cab2bb3Spatrick // FIXME: This might be wrong: _sigfillset doesn't take a
1943cab2bb3Spatrick // __sanitizer_sigset_t *.
DECLARE__REAL_AND_INTERNAL(void,sigfillset,__sanitizer_sigset_t * set)1953cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(void, sigfillset, __sanitizer_sigset_t *set) {
1963cab2bb3Spatrick   _REAL(sigfillset)(set);
1973cab2bb3Spatrick }
1983cab2bb3Spatrick 
1993cab2bb3Spatrick // FIXME: This might be wrong: _sigprocmask doesn't take __sanitizer_sigset_t *.
DECLARE__REAL_AND_INTERNAL(uptr,sigprocmask,int how,__sanitizer_sigset_t * set,__sanitizer_sigset_t * oldset)2003cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(uptr, sigprocmask, int how,
2013cab2bb3Spatrick                            __sanitizer_sigset_t *set,
2023cab2bb3Spatrick                            __sanitizer_sigset_t *oldset) {
2033cab2bb3Spatrick   return _REAL(sigprocmask)(how, set, oldset);
2043cab2bb3Spatrick }
2053cab2bb3Spatrick 
DECLARE__REAL_AND_INTERNAL(int,fork,void)2063cab2bb3Spatrick DECLARE__REAL_AND_INTERNAL(int, fork, void) {
2073cab2bb3Spatrick   // TODO(glider): this may call user's pthread_atfork() handlers which is bad.
2083cab2bb3Spatrick   return _REAL(fork)();
2093cab2bb3Spatrick }
2103cab2bb3Spatrick 
NanoTime()2113cab2bb3Spatrick u64 NanoTime() {
2123cab2bb3Spatrick   return gethrtime();
2133cab2bb3Spatrick }
2143cab2bb3Spatrick 
internal_clock_gettime(__sanitizer_clockid_t clk_id,void * tp)2153cab2bb3Spatrick uptr internal_clock_gettime(__sanitizer_clockid_t clk_id, void *tp) {
2163cab2bb3Spatrick   // FIXME: No internal variant.
2173cab2bb3Spatrick   return clock_gettime(clk_id, (timespec *)tp);
2183cab2bb3Spatrick }
2193cab2bb3Spatrick 
2203cab2bb3Spatrick // ----------------- sanitizer_common.h
FutexWait(atomic_uint32_t * p,u32 cmp)221*d89ec533Spatrick void FutexWait(atomic_uint32_t *p, u32 cmp) {
222*d89ec533Spatrick   // FIXME: implement actual blocking.
223*d89ec533Spatrick   sched_yield();
224*d89ec533Spatrick }
225*d89ec533Spatrick 
FutexWake(atomic_uint32_t * p,u32 count)226*d89ec533Spatrick void FutexWake(atomic_uint32_t *p, u32 count) {}
227*d89ec533Spatrick 
2283cab2bb3Spatrick }  // namespace __sanitizer
2293cab2bb3Spatrick 
2303cab2bb3Spatrick #endif  // SANITIZER_SOLARIS
231