e2f6816100
Now that we've updated the prototypes of the basename(3) and dirname(3) functions to conform to POSIX, let's go ahead and reimplement dirname(3) in such a way that it's thread-safe, but also guaranteed to succeed. C libraries like glibc, musl and the one that's part of Solaris already follow such an approach. Move the existing implementation to another source file, freebsd11_dirname.c to keep existing users of the API that pass in a constant string happy, using symbol versioning. Put a new version of the function in dirname.c, obtained from CloudABI's C library. This version scans through the pathname string from left to right, normalizing it, while discarding the last pathname component. Reviewed by: emaste, jilles Differential Revision: https://reviews.freebsd.org/D7355
552 lines
8.5 KiB
Plaintext
552 lines
8.5 KiB
Plaintext
/*
|
|
* $FreeBSD$
|
|
*/
|
|
|
|
FBSD_1.0 {
|
|
__xuname;
|
|
pthread_atfork;
|
|
pthread_attr_destroy;
|
|
pthread_attr_getdetachstate;
|
|
pthread_attr_getguardsize;
|
|
pthread_attr_getinheritsched;
|
|
pthread_attr_getschedparam;
|
|
pthread_attr_getschedpolicy;
|
|
pthread_attr_getscope;
|
|
pthread_attr_getstackaddr;
|
|
pthread_attr_getstacksize;
|
|
pthread_attr_init;
|
|
pthread_attr_setdetachstate;
|
|
pthread_attr_setguardsize;
|
|
pthread_attr_setinheritsched;
|
|
pthread_attr_setschedparam;
|
|
pthread_attr_setschedpolicy;
|
|
pthread_attr_setscope;
|
|
pthread_attr_setstackaddr;
|
|
pthread_attr_setstacksize;
|
|
pthread_cancel;
|
|
pthread_cleanup_pop;
|
|
pthread_cleanup_push;
|
|
pthread_cond_broadcast;
|
|
pthread_cond_destroy;
|
|
pthread_cond_init;
|
|
pthread_cond_signal;
|
|
pthread_cond_timedwait;
|
|
pthread_cond_wait;
|
|
pthread_detach;
|
|
pthread_equal;
|
|
pthread_exit;
|
|
pthread_getspecific;
|
|
pthread_join;
|
|
pthread_key_create;
|
|
pthread_key_delete;
|
|
pthread_kill;
|
|
pthread_main_np;
|
|
pthread_mutex_destroy;
|
|
pthread_mutex_init;
|
|
pthread_mutex_lock;
|
|
pthread_mutex_trylock;
|
|
pthread_mutex_unlock;
|
|
pthread_mutexattr_destroy;
|
|
pthread_mutexattr_init;
|
|
pthread_mutexattr_settype;
|
|
pthread_once;
|
|
pthread_rwlock_destroy;
|
|
pthread_rwlock_init;
|
|
pthread_rwlock_rdlock;
|
|
pthread_rwlock_tryrdlock;
|
|
pthread_rwlock_trywrlock;
|
|
pthread_rwlock_unlock;
|
|
pthread_rwlock_wrlock;
|
|
pthread_self;
|
|
pthread_setcancelstate;
|
|
pthread_setcanceltype;
|
|
pthread_setspecific;
|
|
pthread_sigmask;
|
|
pthread_testcancel;
|
|
alarm;
|
|
arc4random;
|
|
arc4random_addrandom;
|
|
arc4random_stir;
|
|
__assert;
|
|
basename;
|
|
check_utility_compat;
|
|
clock;
|
|
closedir;
|
|
confstr;
|
|
encrypt;
|
|
des_setkey;
|
|
des_cipher;
|
|
setkey;
|
|
ctermid;
|
|
ctermid_r;
|
|
daemon;
|
|
devname;
|
|
devname_r;
|
|
getdiskbyname;
|
|
dladdr;
|
|
dlclose;
|
|
dlerror;
|
|
dlfunc;
|
|
dllockinit;
|
|
dlopen;
|
|
dlsym;
|
|
dlvsym;
|
|
dlinfo;
|
|
dl_iterate_phdr;
|
|
drand48;
|
|
erand48;
|
|
err_set_file;
|
|
err_set_exit;
|
|
err;
|
|
verr;
|
|
errc;
|
|
verrc;
|
|
errx;
|
|
verrx;
|
|
warn;
|
|
vwarn;
|
|
warnc;
|
|
vwarnc;
|
|
warnx;
|
|
vwarnx;
|
|
sys_errlist;
|
|
sys_nerr;
|
|
errno;
|
|
execl;
|
|
execle;
|
|
execlp;
|
|
execv;
|
|
execvp;
|
|
execvP;
|
|
fmtcheck;
|
|
fmtmsg;
|
|
fnmatch;
|
|
__fpclassifyf;
|
|
__fpclassifyd;
|
|
__fpclassifyl;
|
|
frexp;
|
|
setfstab;
|
|
getfstab;
|
|
getfsent;
|
|
getfsspec;
|
|
getfsfile;
|
|
setfsent;
|
|
endfsent;
|
|
ftok;
|
|
ftw;
|
|
glob;
|
|
globfree;
|
|
getbootfile;
|
|
getbsize;
|
|
cgetset;
|
|
cgetcap;
|
|
cgetent;
|
|
cgetmatch;
|
|
cgetfirst;
|
|
cgetclose;
|
|
cgetnext;
|
|
cgetstr;
|
|
cgetustr;
|
|
cgetnum;
|
|
getcwd;
|
|
getdomainname;
|
|
setgrent;
|
|
setgroupent;
|
|
endgrent;
|
|
getgrent_r;
|
|
getgrnam_r;
|
|
getgrgid_r;
|
|
getgrnam;
|
|
getgrgid;
|
|
getgrent;
|
|
/*
|
|
* Why are __gr_parse_entry() and __gr_match_entry() not static in
|
|
* gen/getgrent.c?
|
|
*/
|
|
getgrouplist;
|
|
gethostname;
|
|
getloadavg;
|
|
getlogin;
|
|
getlogin_r;
|
|
getmntinfo;
|
|
setnetgrent;
|
|
getnetgrent;
|
|
endnetgrent;
|
|
innetgr;
|
|
getosreldate;
|
|
getpagesize;
|
|
getpeereid;
|
|
_getprogname;
|
|
getprogname;
|
|
setpwent;
|
|
setpassent;
|
|
endpwent;
|
|
getpwent_r;
|
|
getpwnam_r;
|
|
getpwuid_r;
|
|
getpwnam;
|
|
getpwuid;
|
|
getpwent;
|
|
getttynam;
|
|
getttyent;
|
|
setttyent;
|
|
endttyent;
|
|
isdialuptty;
|
|
isnettty;
|
|
getusershell;
|
|
endusershell;
|
|
setusershell;
|
|
getvfsbyname;
|
|
__isnan;
|
|
isnan;
|
|
__isnanf;
|
|
isnanf;
|
|
__isinf;
|
|
isinf;
|
|
__isinff;
|
|
__isinfl;
|
|
isatty;
|
|
initgroups;
|
|
jrand48;
|
|
lcong48;
|
|
ldexp;
|
|
lockf;
|
|
lrand48;
|
|
modf;
|
|
mrand48;
|
|
nftw;
|
|
nice;
|
|
nlist;
|
|
nrand48;
|
|
opendir;
|
|
pause;
|
|
posix_madvise;
|
|
popen;
|
|
pclose;
|
|
psignal;
|
|
raise;
|
|
readdir;
|
|
readdir_r;
|
|
readpassphrase;
|
|
getpass;
|
|
rewinddir;
|
|
scandir;
|
|
alphasort;
|
|
seed48;
|
|
seekdir;
|
|
user_from_uid;
|
|
group_from_gid;
|
|
setdomainname;
|
|
sethostname;
|
|
longjmperror;
|
|
getmode;
|
|
setmode;
|
|
setproctitle;
|
|
setprogname;
|
|
siginterrupt;
|
|
sys_signame;
|
|
sys_siglist;
|
|
sys_nsig;
|
|
signal;
|
|
sigaddset;
|
|
sigdelset;
|
|
sigemptyset;
|
|
sigfillset;
|
|
sigismember;
|
|
sleep;
|
|
srand48;
|
|
fstatvfs;
|
|
statvfs;
|
|
sl_init;
|
|
sl_add;
|
|
sl_free;
|
|
sl_find;
|
|
fflagstostr;
|
|
strtofflags;
|
|
sysconf;
|
|
sysctl;
|
|
sysctlbyname;
|
|
sysctlnametomib;
|
|
syslog;
|
|
vsyslog;
|
|
openlog;
|
|
closelog;
|
|
setlogmask;
|
|
ttyname_r;
|
|
ttyname;
|
|
timezone;
|
|
times;
|
|
time;
|
|
telldir;
|
|
tcgetattr;
|
|
tcsetattr;
|
|
tcsetpgrp;
|
|
tcgetpgrp;
|
|
cfgetospeed;
|
|
cfgetispeed;
|
|
cfsetospeed;
|
|
cfsetispeed;
|
|
cfsetspeed;
|
|
cfmakeraw;
|
|
tcsendbreak;
|
|
_init_tls;
|
|
__tls_get_addr;
|
|
tcdrain;
|
|
tcflush;
|
|
tcflow;
|
|
ualarm;
|
|
ulimit;
|
|
uname;
|
|
strunvis;
|
|
strunvisx;
|
|
usleep;
|
|
utime;
|
|
valloc;
|
|
vis;
|
|
strvis;
|
|
strvisx;
|
|
wait;
|
|
wait3;
|
|
waitpid;
|
|
wordexp;
|
|
wordfree;
|
|
};
|
|
|
|
FBSD_1.1 {
|
|
arc4random_buf;
|
|
arc4random_uniform;
|
|
fdevname;
|
|
fdevname_r;
|
|
fdopendir;
|
|
feature_present;
|
|
fts_children;
|
|
fts_close;
|
|
fts_get_clientptr;
|
|
fts_get_stream;
|
|
fts_open;
|
|
fts_read;
|
|
fts_set;
|
|
fts_set_clientptr;
|
|
posix_spawn;
|
|
posix_spawn_file_actions_addclose;
|
|
posix_spawn_file_actions_adddup2;
|
|
posix_spawn_file_actions_addopen;
|
|
posix_spawn_file_actions_destroy;
|
|
posix_spawn_file_actions_init;
|
|
posix_spawnattr_destroy;
|
|
posix_spawnattr_getflags;
|
|
posix_spawnattr_getpgroup;
|
|
posix_spawnattr_getschedparam;
|
|
posix_spawnattr_getschedpolicy;
|
|
posix_spawnattr_getsigdefault;
|
|
posix_spawnattr_getsigmask;
|
|
posix_spawnattr_init;
|
|
posix_spawnattr_setflags;
|
|
posix_spawnattr_setpgroup;
|
|
posix_spawnattr_setschedparam;
|
|
posix_spawnattr_setschedpolicy;
|
|
posix_spawnattr_setsigdefault;
|
|
posix_spawnattr_setsigmask;
|
|
posix_spawnp;
|
|
semctl;
|
|
tcgetsid;
|
|
tcsetsid;
|
|
__pthread_cleanup_pop_imp;
|
|
__pthread_cleanup_push_imp;
|
|
};
|
|
|
|
FBSD_1.2 {
|
|
basename_r;
|
|
cfmakesane;
|
|
endutxent;
|
|
getpagesizes;
|
|
getutxent;
|
|
getutxid;
|
|
getutxline;
|
|
getutxuser;
|
|
pututxline;
|
|
sem_close;
|
|
sem_destroy;
|
|
sem_getvalue;
|
|
sem_init;
|
|
sem_open;
|
|
sem_post;
|
|
sem_timedwait;
|
|
sem_trywait;
|
|
sem_unlink;
|
|
sem_wait;
|
|
setutxdb;
|
|
setutxent;
|
|
};
|
|
|
|
FBSD_1.3 {
|
|
clock_getcpuclockid;
|
|
dirfd;
|
|
dup3;
|
|
fdclosedir;
|
|
fdlopen;
|
|
__FreeBSD_libc_enter_restricted_mode;
|
|
getcontextx;
|
|
gid_from_group;
|
|
nvis;
|
|
pwcache_userdb;
|
|
pwcache_groupdb;
|
|
snvis;
|
|
strenvisx;
|
|
strnunvis;
|
|
strnunvisx;
|
|
strnvis;
|
|
strnvisx;
|
|
strsenvisx;
|
|
strsnvis;
|
|
strsnvisx;
|
|
strsvis;
|
|
strsvisx;
|
|
svis;
|
|
uid_from_user;
|
|
unvis;
|
|
waitid;
|
|
};
|
|
|
|
FBSD_1.4 {
|
|
getnetgrent_r;
|
|
pthread_mutex_consistent;
|
|
pthread_mutexattr_getrobust;
|
|
pthread_mutexattr_setrobust;
|
|
scandir_b;
|
|
stravis;
|
|
};
|
|
|
|
FBSD_1.5 {
|
|
dirname;
|
|
};
|
|
|
|
FBSDprivate_1.0 {
|
|
/* needed by thread libraries */
|
|
__thr_jtable;
|
|
|
|
_pthread_atfork;
|
|
_pthread_attr_destroy;
|
|
_pthread_attr_getdetachstate;
|
|
_pthread_attr_getguardsize;
|
|
_pthread_attr_getinheritsched;
|
|
_pthread_attr_getschedparam;
|
|
_pthread_attr_getschedpolicy;
|
|
_pthread_attr_getscope;
|
|
_pthread_attr_getstackaddr;
|
|
_pthread_attr_getstacksize;
|
|
_pthread_attr_init;
|
|
_pthread_attr_setdetachstate;
|
|
_pthread_attr_setguardsize;
|
|
_pthread_attr_setinheritsched;
|
|
_pthread_attr_setschedparam;
|
|
_pthread_attr_setschedpolicy;
|
|
_pthread_attr_setscope;
|
|
_pthread_attr_setstackaddr;
|
|
_pthread_attr_setstacksize;
|
|
_pthread_cancel;
|
|
_pthread_cancel_enter;
|
|
_pthread_cancel_leave;
|
|
_pthread_cleanup_pop;
|
|
_pthread_cleanup_push;
|
|
_pthread_cond_broadcast;
|
|
_pthread_cond_destroy;
|
|
_pthread_cond_init;
|
|
_pthread_cond_signal;
|
|
_pthread_cond_timedwait;
|
|
_pthread_cond_wait;
|
|
_pthread_detach;
|
|
_pthread_equal;
|
|
_pthread_exit;
|
|
_pthread_getspecific;
|
|
_pthread_join;
|
|
_pthread_key_create;
|
|
_pthread_key_delete;
|
|
_pthread_kill;
|
|
_pthread_main_np;
|
|
_pthread_mutex_destroy;
|
|
_pthread_mutex_init_calloc_cb;
|
|
_pthread_mutex_init;
|
|
_pthread_mutex_lock;
|
|
_pthread_mutex_trylock;
|
|
_pthread_mutex_unlock;
|
|
_pthread_mutexattr_destroy;
|
|
_pthread_mutexattr_init;
|
|
_pthread_mutexattr_settype;
|
|
_pthread_once;
|
|
_pthread_rwlock_destroy;
|
|
_pthread_rwlock_init;
|
|
_pthread_rwlock_rdlock;
|
|
_pthread_rwlock_tryrdlock;
|
|
_pthread_rwlock_trywrlock;
|
|
_pthread_rwlock_unlock;
|
|
_pthread_rwlock_wrlock;
|
|
_pthread_self;
|
|
_pthread_setcancelstate;
|
|
_pthread_setcanceltype;
|
|
_pthread_setspecific;
|
|
_pthread_sigmask;
|
|
_pthread_testcancel;
|
|
_spinlock;
|
|
_spinlock_debug;
|
|
_spinunlock;
|
|
_rtld_addr_phdr;
|
|
_rtld_atfork_pre;
|
|
_rtld_atfork_post;
|
|
_rtld_error; /* for private use */
|
|
_rtld_get_stack_prot;
|
|
_rtld_is_dlopened;
|
|
_rtld_thread_init; /* for private use */
|
|
__elf_phdr_match_addr;
|
|
_err;
|
|
_warn;
|
|
__fmtcheck;
|
|
/* __pw_match_entry; */
|
|
/* __pw_parse_entry; */
|
|
__fdnlist; /* used by libkvm */
|
|
/* __aout_fdnlist; */
|
|
/* __elf_is_okay__; */
|
|
/* __elf_fdnlist; */
|
|
__opendir2;
|
|
__pause;
|
|
_pause;
|
|
__pw_scan; /* Used by (at least) libutil */
|
|
__raise;
|
|
_raise;
|
|
__sleep;
|
|
_sleep;
|
|
_rtld_allocate_tls;
|
|
_rtld_free_tls;
|
|
#if defined(i386)
|
|
___libc_tls_get_addr; /* x86 only */
|
|
#endif
|
|
__libc_tls_get_addr;
|
|
__tcdrain;
|
|
_tcdrain;
|
|
__usleep;
|
|
_usleep;
|
|
__wait;
|
|
_wait;
|
|
__waitpid;
|
|
_waitpid;
|
|
|
|
_libc_sem_init_compat;
|
|
_libc_sem_destroy_compat;
|
|
_libc_sem_open_compat;
|
|
_libc_sem_close_compat;
|
|
_libc_sem_unlink_compat;
|
|
_libc_sem_wait_compat;
|
|
_libc_sem_trywait_compat;
|
|
_libc_sem_timedwait_compat;
|
|
_libc_sem_post_compat;
|
|
_libc_sem_getvalue_compat;
|
|
|
|
__libc_tcdrain;
|
|
|
|
__elf_aux_vector;
|
|
__pthread_map_stacks_exec;
|
|
__fillcontextx;
|
|
__fillcontextx2;
|
|
__getcontextx_size;
|
|
};
|