diff options
Diffstat (limited to 'REORG.TODO/io')
152 files changed, 13214 insertions, 0 deletions
diff --git a/REORG.TODO/io/Makefile b/REORG.TODO/io/Makefile new file mode 100644 index 0000000000..16365e581a --- /dev/null +++ b/REORG.TODO/io/Makefile @@ -0,0 +1,117 @@ +# Copyright (C) 1992-2017 Free Software Foundation, Inc. +# This file is part of the GNU C Library. + +# The GNU C Library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. + +# The GNU C Library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. + +# You should have received a copy of the GNU Lesser General Public +# License along with the GNU C Library; if not, see +# <http://www.gnu.org/licenses/>. + +# +# Sub-makefile for I/O portion of the library. +# +subdir := io + +include ../Makeconfig + +headers := sys/stat.h bits/stat.h sys/statfs.h bits/statfs.h sys/vfs.h \ + sys/statvfs.h bits/statvfs.h fcntl.h sys/fcntl.h bits/fcntl.h \ + poll.h sys/poll.h bits/poll.h bits/fcntl2.h bits/poll2.h \ + utime.h ftw.h fts.h sys/sendfile.h + +routines := \ + utime \ + mkfifo mkfifoat \ + stat fstat lstat stat64 fstat64 lstat64 fstatat fstatat64 \ + xstat fxstat lxstat xstat64 fxstat64 lxstat64 \ + mknod mknodat xmknod xmknodat \ + fxstatat fxstatat64 \ + statfs fstatfs statfs64 fstatfs64 \ + statvfs fstatvfs statvfs64 fstatvfs64 \ + umask chmod fchmod lchmod fchmodat \ + mkdir mkdirat \ + open open_2 open64 open64_2 openat openat_2 openat64 openat64_2 \ + read write lseek lseek64 access euidaccess faccessat \ + fcntl flock lockf lockf64 \ + close dup dup2 dup3 pipe pipe2 \ + creat creat64 \ + chdir fchdir \ + getcwd getwd getdirname \ + chown fchown lchown fchownat \ + ttyname ttyname_r isatty \ + link linkat symlink symlinkat readlink readlinkat \ + unlink unlinkat rmdir \ + ftw ftw64 fts fts64 poll ppoll \ + posix_fadvise posix_fadvise64 \ + posix_fallocate posix_fallocate64 \ + sendfile sendfile64 \ + utimensat futimens + +# These routines will be omitted from the libc shared object. +# Instead the static object files will be included in a special archive +# linked against when the shared library will be used. +static-only-routines = stat fstat lstat stat64 fstat64 lstat64 \ + fstatat fstatat64 mknod mknodat + +others := pwd +test-srcs := ftwtest +tests := test-utime test-stat test-stat2 test-lfs tst-getcwd \ + tst-fcntl bug-ftw1 bug-ftw2 bug-ftw3 bug-ftw4 tst-statvfs \ + tst-openat tst-unlinkat tst-fstatat tst-futimesat \ + tst-renameat tst-fchownat tst-fchmodat tst-faccessat \ + tst-symlinkat tst-linkat tst-readlinkat tst-mkdirat \ + tst-mknodat tst-mkfifoat tst-ttyname_r bug-ftw5 \ + tst-posix_fallocate tst-posix_fallocate64 \ + tst-fts tst-fts-lfs tst-open-tmpfile + +ifeq ($(run-built-tests),yes) +tests-special += $(objpfx)ftwtest.out +endif + +include ../Rules + +CFLAGS-open.c = -fexceptions -fasynchronous-unwind-tables +CFLAGS-open64.c = -fexceptions -fasynchronous-unwind-tables +CFLAGS-creat.c = -fexceptions -fasynchronous-unwind-tables +CFLAGS-creat64.c = -fexceptions -fasynchronous-unwind-tables +CFLAGS-fcntl.c = -fexceptions -fasynchronous-unwind-tables +CFLAGS-poll.c = -fexceptions -fasynchronous-unwind-tables +CFLAGS-ppoll.c = -fexceptions -fasynchronous-unwind-tables +CFLAGS-lockf.c = -fexceptions +CFLAGS-statfs.c = -fexceptions +CFLAGS-fstatfs.c = -fexceptions +CFLAGS-statvfs.c = -fexceptions +CFLAGS-fstatvfs.c = -fexceptions +CFLAGS-fts.c = -Wno-uninitialized $(uses-callbacks) -fexceptions +CFLAGS-fts64.c = -Wno-uninitialized $(uses-callbacks) -fexceptions +CFLAGS-ftw.c = $(uses-callbacks) -fexceptions +CFLAGS-ftw64.c = $(uses-callbacks) -fexceptions +CFLAGS-lockf.c = -fexceptions +CFLAGS-posix_fallocate.c = -fexceptions +CFLAGS-posix_fallocate64.c = -fexceptions +CFLAGS-fallocate.c = -fexceptions +CFLAGS-fallocate64.c = -fexceptions +CFLAGS-sync_file_range.c = -fexceptions +CFLAGS-read.c = -fexceptions +CFLAGS-write.c = -fexceptions + +CFLAGS-test-stat.c = -D_FILE_OFFSET_BITS=64 -D_LARGEFILE64_SOURCE +CFLAGS-test-lfs.c = -D_LARGEFILE64_SOURCE + +test-stat2-ARGS = Makefile . $(objpfx)test-stat2 + +tst-statvfs-ARGS = $(objpfx)tst-statvfs tst-statvfs.c /tmp + +ifeq ($(run-built-tests),yes) +$(objpfx)ftwtest.out: ftwtest-sh $(objpfx)ftwtest + $(SHELL) $< $(common-objpfx) '$(test-program-cmd)' > $@; \ + $(evaluate-test) +endif diff --git a/REORG.TODO/io/Versions b/REORG.TODO/io/Versions new file mode 100644 index 0000000000..64316cd025 --- /dev/null +++ b/REORG.TODO/io/Versions @@ -0,0 +1,128 @@ +libc { + GLIBC_2.0 { + # functions used in inline functions or macros + __xstat; __fxstat; __lxstat; __xmknod; __write; __close; __fcntl; + __lseek; __open; __read; + + # functions used by libstdc++ 2.7.2 + __dup2; __pipe; + + # a* + access; + + # c* + chdir; chmod; chown; close; creat; + + # d* + dup; dup2; + + # e* + euidaccess; + + # f* + fchdir; fchmod; fchown; fcntl; flock; fstatfs; fts_children; fts_close; + fts_open; fts_read; fts_set; ftw; + + # g* + get_current_dir_name; getcwd; getwd; + + # i* + isatty; + + # l* + lchown; link; lockf; lseek; + + # m* + mkdir; mkfifo; + + # o* + open; + + # p* + pipe; poll; + + # r* + read; readlink; rmdir; + + # s* + statfs; symlink; + + # t* + ttyname; ttyname_r; + + # u* + umask; unlink; utime; + + # w* + write; + } + GLIBC_2.1 { + # functions used in other libraries + __xstat64; __fxstat64; __lxstat64; __poll; + + # c* + creat64; + + # f* + fstatfs64; fstatvfs; fstatvfs64; ftw64; + + # l* + lockf64; lseek64; + + # n* + nftw; nftw64; + + # o* + open64; + + # s* + sendfile; + statfs64; statvfs; statvfs64; + } + GLIBC_2.2 { + # p* + posix_fadvise; posix_fadvise64; posix_fallocate; posix_fallocate64; + + __open64; + } + GLIBC_2.3 { + # s* + sendfile64; + } + GLIBC_2.3.2 { + # l* + lchmod; + } + GLIBC_2.3.3 { + # n* + nftw; nftw64; + } + GLIBC_2.4 { + eaccess; + + faccessat; + fchmodat; + fchownat; + __fxstatat; __fxstatat64; + linkat; + mkdirat; mkfifoat; __xmknodat; + openat; openat64; + readlinkat; + symlinkat; + unlinkat; + + ppoll; + } + GLIBC_2.6 { + utimensat; futimens; + } + GLIBC_2.7 { + __open_2; __open64_2; __openat_2; __openat64_2; + } + GLIBC_2.9 { + dup3; pipe2; + } + GLIBC_2.23 { + fts64_children; fts64_close; fts64_open; fts64_read; fts64_set; + } +} diff --git a/REORG.TODO/io/access.c b/REORG.TODO/io/access.c new file mode 100644 index 0000000000..72eba36e3f --- /dev/null +++ b/REORG.TODO/io/access.c @@ -0,0 +1,44 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> + +/* Test for access to FILE without setting errno. */ +int +__access_noerrno (const char *file, int type) +{ + return -1; +} + +/* Test for access to FILE. */ +int +__access (const char *file, int type) +{ + if (file == NULL || (type & ~(R_OK|W_OK|X_OK|F_OK)) != 0) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (access) + +weak_alias (__access, access) diff --git a/REORG.TODO/io/bits/fcntl2.h b/REORG.TODO/io/bits/fcntl2.h new file mode 100644 index 0000000000..4109ead9a8 --- /dev/null +++ b/REORG.TODO/io/bits/fcntl2.h @@ -0,0 +1,172 @@ +/* Checking macros for fcntl functions. + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#ifndef _FCNTL_H +# error "Never include <bits/fcntl2.h> directly; use <fcntl.h> instead." +#endif + +/* Check that calls to open and openat with O_CREAT or O_TMPFILE set have an + appropriate third/fourth parameter. */ +#ifndef __USE_FILE_OFFSET64 +extern int __open_2 (const char *__path, int __oflag) __nonnull ((1)); +extern int __REDIRECT (__open_alias, (const char *__path, int __oflag, ...), + open) __nonnull ((1)); +#else +extern int __REDIRECT (__open_2, (const char *__path, int __oflag), + __open64_2) __nonnull ((1)); +extern int __REDIRECT (__open_alias, (const char *__path, int __oflag, ...), + open64) __nonnull ((1)); +#endif +__errordecl (__open_too_many_args, + "open can be called either with 2 or 3 arguments, not more"); +__errordecl (__open_missing_mode, + "open with O_CREAT or O_TMPFILE in second argument needs 3 arguments"); + +__fortify_function int +open (const char *__path, int __oflag, ...) +{ + if (__va_arg_pack_len () > 1) + __open_too_many_args (); + + if (__builtin_constant_p (__oflag)) + { + if (__OPEN_NEEDS_MODE (__oflag) && __va_arg_pack_len () < 1) + { + __open_missing_mode (); + return __open_2 (__path, __oflag); + } + return __open_alias (__path, __oflag, __va_arg_pack ()); + } + + if (__va_arg_pack_len () < 1) + return __open_2 (__path, __oflag); + + return __open_alias (__path, __oflag, __va_arg_pack ()); +} + + +#ifdef __USE_LARGEFILE64 +extern int __open64_2 (const char *__path, int __oflag) __nonnull ((1)); +extern int __REDIRECT (__open64_alias, (const char *__path, int __oflag, + ...), open64) __nonnull ((1)); +__errordecl (__open64_too_many_args, + "open64 can be called either with 2 or 3 arguments, not more"); +__errordecl (__open64_missing_mode, + "open64 with O_CREAT or O_TMPFILE in second argument needs 3 arguments"); + +__fortify_function int +open64 (const char *__path, int __oflag, ...) +{ + if (__va_arg_pack_len () > 1) + __open64_too_many_args (); + + if (__builtin_constant_p (__oflag)) + { + if (__OPEN_NEEDS_MODE (__oflag) && __va_arg_pack_len () < 1) + { + __open64_missing_mode (); + return __open64_2 (__path, __oflag); + } + return __open64_alias (__path, __oflag, __va_arg_pack ()); + } + + if (__va_arg_pack_len () < 1) + return __open64_2 (__path, __oflag); + + return __open64_alias (__path, __oflag, __va_arg_pack ()); +} +#endif + + +#ifdef __USE_ATFILE +# ifndef __USE_FILE_OFFSET64 +extern int __openat_2 (int __fd, const char *__path, int __oflag) + __nonnull ((2)); +extern int __REDIRECT (__openat_alias, (int __fd, const char *__path, + int __oflag, ...), openat) + __nonnull ((2)); +# else +extern int __REDIRECT (__openat_2, (int __fd, const char *__path, + int __oflag), __openat64_2) + __nonnull ((2)); +extern int __REDIRECT (__openat_alias, (int __fd, const char *__path, + int __oflag, ...), openat64) + __nonnull ((2)); +# endif +__errordecl (__openat_too_many_args, + "openat can be called either with 3 or 4 arguments, not more"); +__errordecl (__openat_missing_mode, + "openat with O_CREAT or O_TMPFILE in third argument needs 4 arguments"); + +__fortify_function int +openat (int __fd, const char *__path, int __oflag, ...) +{ + if (__va_arg_pack_len () > 1) + __openat_too_many_args (); + + if (__builtin_constant_p (__oflag)) + { + if (__OPEN_NEEDS_MODE (__oflag) && __va_arg_pack_len () < 1) + { + __openat_missing_mode (); + return __openat_2 (__fd, __path, __oflag); + } + return __openat_alias (__fd, __path, __oflag, __va_arg_pack ()); + } + + if (__va_arg_pack_len () < 1) + return __openat_2 (__fd, __path, __oflag); + + return __openat_alias (__fd, __path, __oflag, __va_arg_pack ()); +} + + +# ifdef __USE_LARGEFILE64 +extern int __openat64_2 (int __fd, const char *__path, int __oflag) + __nonnull ((2)); +extern int __REDIRECT (__openat64_alias, (int __fd, const char *__path, + int __oflag, ...), openat64) + __nonnull ((2)); +__errordecl (__openat64_too_many_args, + "openat64 can be called either with 3 or 4 arguments, not more"); +__errordecl (__openat64_missing_mode, + "openat64 with O_CREAT or O_TMPFILE in third argument needs 4 arguments"); + +__fortify_function int +openat64 (int __fd, const char *__path, int __oflag, ...) +{ + if (__va_arg_pack_len () > 1) + __openat64_too_many_args (); + + if (__builtin_constant_p (__oflag)) + { + if (__OPEN_NEEDS_MODE (__oflag) && __va_arg_pack_len () < 1) + { + __openat64_missing_mode (); + return __openat64_2 (__fd, __path, __oflag); + } + return __openat64_alias (__fd, __path, __oflag, __va_arg_pack ()); + } + + if (__va_arg_pack_len () < 1) + return __openat64_2 (__fd, __path, __oflag); + + return __openat64_alias (__fd, __path, __oflag, __va_arg_pack ()); +} +# endif +#endif diff --git a/REORG.TODO/io/bits/poll2.h b/REORG.TODO/io/bits/poll2.h new file mode 100644 index 0000000000..0fbba4f325 --- /dev/null +++ b/REORG.TODO/io/bits/poll2.h @@ -0,0 +1,81 @@ +/* Checking macros for poll functions. + Copyright (C) 2012-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#ifndef _SYS_POLL_H +# error "Never include <bits/poll2.h> directly; use <sys/poll.h> instead." +#endif + + +__BEGIN_DECLS + +extern int __REDIRECT (__poll_alias, (struct pollfd *__fds, nfds_t __nfds, + int __timeout), poll); +extern int __poll_chk (struct pollfd *__fds, nfds_t __nfds, int __timeout, + __SIZE_TYPE__ __fdslen); +extern int __REDIRECT (__poll_chk_warn, (struct pollfd *__fds, nfds_t __nfds, + int __timeout, __SIZE_TYPE__ __fdslen), + __poll_chk) + __warnattr ("poll called with fds buffer too small file nfds entries"); + +__fortify_function int +poll (struct pollfd *__fds, nfds_t __nfds, int __timeout) +{ + if (__bos (__fds) != (__SIZE_TYPE__) -1) + { + if (! __builtin_constant_p (__nfds)) + return __poll_chk (__fds, __nfds, __timeout, __bos (__fds)); + else if (__bos (__fds) / sizeof (*__fds) < __nfds) + return __poll_chk_warn (__fds, __nfds, __timeout, __bos (__fds)); + } + + return __poll_alias (__fds, __nfds, __timeout); +} + + +#ifdef __USE_GNU +extern int __REDIRECT (__ppoll_alias, (struct pollfd *__fds, nfds_t __nfds, + const struct timespec *__timeout, + const __sigset_t *__ss), ppoll); +extern int __ppoll_chk (struct pollfd *__fds, nfds_t __nfds, + const struct timespec *__timeout, + const __sigset_t *__ss, __SIZE_TYPE__ __fdslen); +extern int __REDIRECT (__ppoll_chk_warn, (struct pollfd *__fds, nfds_t __nfds, + const struct timespec *__timeout, + const __sigset_t *__ss, + __SIZE_TYPE__ __fdslen), + __ppoll_chk) + __warnattr ("ppoll called with fds buffer too small file nfds entries"); + +__fortify_function int +ppoll (struct pollfd *__fds, nfds_t __nfds, const struct timespec *__timeout, + const __sigset_t *__ss) +{ + if (__bos (__fds) != (__SIZE_TYPE__) -1) + { + if (! __builtin_constant_p (__nfds)) + return __ppoll_chk (__fds, __nfds, __timeout, __ss, __bos (__fds)); + else if (__bos (__fds) / sizeof (*__fds) < __nfds) + return __ppoll_chk_warn (__fds, __nfds, __timeout, __ss, + __bos (__fds)); + } + + return __ppoll_alias (__fds, __nfds, __timeout, __ss); +} +#endif + +__END_DECLS diff --git a/REORG.TODO/io/bug-ftw1.c b/REORG.TODO/io/bug-ftw1.c new file mode 100644 index 0000000000..29c3f7d531 --- /dev/null +++ b/REORG.TODO/io/bug-ftw1.c @@ -0,0 +1,77 @@ +/* Test for ftw function searching in root directory. + Copyright (C) 2001-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper <drepper@cygnus.com>, 2001. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <ftw.h> +#include <mcheck.h> +#include <stdio.h> +#include <string.h> + + +int result; +int cnt; +int sawroot; + + +static int +callback (const char *fname, const struct stat *st, int flag) +{ + if (++cnt >= 10) + return 1; + + printf ("%d: \"%s\" -> ", cnt, fname); + if (strcmp (fname, "/") == 0 && sawroot) + { + puts ("root directory reported twice"); + result = 1; + } + else if (fname[0] != '/') + { + puts ("missing '/' as first character"); + result = 1; + } + else if (fname[1] == '/') + { + puts ("double '/' at beginning"); + result = 1; + } + else + { + puts ("OK"); + sawroot |= strcmp (fname, "/") == 0; + } + + return 0; +} + + +int +main (void) +{ + mtrace (); + + ftw ("/", callback, 10); + + if (! sawroot) + { + puts ("root directory wasn't reported"); + result = 1; + } + + return result; +} diff --git a/REORG.TODO/io/bug-ftw2.c b/REORG.TODO/io/bug-ftw2.c new file mode 100644 index 0000000000..ce8823d28e --- /dev/null +++ b/REORG.TODO/io/bug-ftw2.c @@ -0,0 +1,87 @@ +/* Test for ftw function searching in current directory. + Copyright (C) 2001-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper <drepper@cygnus.com>, 2001. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <ftw.h> +#include <mcheck.h> +#include <stdio.h> +#include <string.h> + + +int cnt; +int result; +int sawown; +int sawcur; + + +static int +callback (const char *fname, const struct stat *st, int flag) +{ + printf ("%d: \"%s\" -> ", ++cnt, fname); + if (strcmp (fname, ".") == 0 && sawcur) + { + puts ("current directory reported twice"); + result = 1; + } + else if (strcmp (fname, "./bug-ftw2.c") == 0 && sawown) + { + puts ("source file reported twice"); + result = 1; + } + else if (fname[0] != '.') + { + puts ("missing '.' as first character"); + result = 1; + } + else if (fname[1] != '\0' && fname[1] != '/') + { + puts ("no '/' in second position"); + result = 1; + } + else + { + puts ("OK"); + sawcur |= strcmp (fname, ".") == 0; + sawown |= strcmp (fname, "./bug-ftw2.c") == 0; + } + + return 0; +} + + +int +main (void) +{ + mtrace (); + + ftw (".", callback, 10); + + if (! sawcur) + { + puts ("current directory wasn't reported"); + result = 1; + } + + if (! sawown) + { + puts ("source file wasn't reported"); + result = 1; + } + + return result; +} diff --git a/REORG.TODO/io/bug-ftw3.c b/REORG.TODO/io/bug-ftw3.c new file mode 100644 index 0000000000..19740f49f3 --- /dev/null +++ b/REORG.TODO/io/bug-ftw3.c @@ -0,0 +1,69 @@ +#include <errno.h> +#include <ftw.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + +static int cb_called; + +static int +cb (const char *fname, const struct stat *st, int flag) +{ + printf ("%s %d\n", fname, flag); + cb_called = 1; + return 0; +} + +int +main (void) +{ + char tmp[] = "/tmp/ftwXXXXXX"; + char tmp2[] = "/tmp/ftwXXXXXX/ftwXXXXXX"; + char *dname; + char *dname2; + int r; + int e; + + if (getuid () == 0) + { + puts ("this test needs to be run by ordinary user"); + exit (0); + } + + dname = mkdtemp (tmp); + if (dname == NULL) + { + printf ("mkdtemp: %m\n"); + exit (1); + } + + memcpy (tmp2, tmp, strlen (tmp)); + dname2 = mkdtemp (tmp2); + if (dname2 == NULL) + { + printf ("mkdtemp: %m\n"); + rmdir (dname); + exit (1); + } + + if (chmod (dname, S_IWUSR|S_IWGRP|S_IWOTH) != 0) + { + printf ("chmod: %m\n"); + rmdir (dname); + exit (1); + } + + r = ftw (dname2, cb, 10); + e = errno; + printf ("r = %d", r); + if (r != 0) + printf (", errno = %d", errno); + puts (""); + + chmod (dname, S_IRWXU|S_IRWXG|S_IRWXO); + rmdir (dname2); + rmdir (dname); + + return (r != -1 && e == EACCES) || cb_called; +} diff --git a/REORG.TODO/io/bug-ftw4.c b/REORG.TODO/io/bug-ftw4.c new file mode 100644 index 0000000000..9fca638937 --- /dev/null +++ b/REORG.TODO/io/bug-ftw4.c @@ -0,0 +1,124 @@ +/* Test if ftw function doesn't leak fds. + Copyright (C) 2003-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Jakub Jelinek <jakub@redhat.com>, 2003. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <fcntl.h> +#include <ftw.h> +#include <stdlib.h> +#include <stdio.h> +#include <string.h> +#include <sys/stat.h> +#include <unistd.h> + +static int cb_called; + +static int +cb (const char *name, const struct stat64 *st, int type) +{ + return cb_called++ & 1; +} + +int +main (void) +{ + char name[32] = "/tmp/ftwXXXXXX", *p; + int ret, i, result = 0, fd, fd1, fd2; + + if (mkdtemp (name) == NULL) + { + printf ("Couldn't make temporary directory: %m\n"); + exit (EXIT_FAILURE); + } + p = strchr (name, '\0'); + strcpy (p, "/1"); + if (mkdir (name, 0755) < 0) + { + printf ("Couldn't make temporary subdirectory: %m\n"); + exit (EXIT_FAILURE); + } + *p = '\0'; + + ret = ftw64 (name, cb, 20); + if (ret != 1) + { + printf ("ftw64 returned %d instead of 1", ret); + result = 1; + } + + fd = open (name, O_RDONLY); + if (fd < 0) + { + printf ("open failed: %m\n"); + result = 1; + } + fd1 = open (name, O_RDONLY); + if (fd1 < 0) + { + printf ("open failed: %m\n"); + result = 1; + } + else + close (fd1); + if (fd >= 0) + close (fd); + + for (i = 0; i < 128; ++i) + { + ret = ftw64 (name, cb, 20); + if (ret != 1) + { + printf ("ftw64 returned %d instead of 1", ret); + result = 1; + } + } + + fd = open (name, O_RDONLY); + if (fd < 0) + { + printf ("open failed: %m\n"); + result = 1; + } + fd2 = open (name, O_RDONLY); + if (fd2 < 0) + { + printf ("open failed: %m\n"); + result = 1; + } + else + close (fd2); + if (fd >= 0) + close (fd); + + if (fd2 >= fd1 + 128) + { + printf ("ftw64 leaking fds: %d -> %d\n", fd1, fd2); + result = 1; + } + + if (cb_called != 129 * 2) + { + printf ("callback called %d times\n", cb_called); + result = 1; + } + + strcpy (p, "/1"); + rmdir (name); + *p = '\0'; + rmdir (name); + return result; +} diff --git a/REORG.TODO/io/bug-ftw5.c b/REORG.TODO/io/bug-ftw5.c new file mode 100644 index 0000000000..c1cd81d30e --- /dev/null +++ b/REORG.TODO/io/bug-ftw5.c @@ -0,0 +1,25 @@ +#include <errno.h> +#include <ftw.h> +#include <stdio.h> + +static int +fn (const char *file, const struct stat *sb, int flag, struct FTW *s) +{ + puts (file); + return FTW_STOP; +} + +static int +do_test (void) +{ + if (nftw ("/", fn, 0, FTW_CHDIR | FTW_ACTIONRETVAL) < 0) + { + printf ("nftw / FTW_CHDIR: %m\n"); + return 1; + } + + return 0; +} + +#define TEST_FUNCTION do_test () +#include "../test-skeleton.c" diff --git a/REORG.TODO/io/chdir.c b/REORG.TODO/io/chdir.c new file mode 100644 index 0000000000..7e11ed72cb --- /dev/null +++ b/REORG.TODO/io/chdir.c @@ -0,0 +1,37 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> + +/* Change the current directory to PATH. */ +int +__chdir (const char *path) +{ + if (path == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (chdir) + +weak_alias (__chdir, chdir) diff --git a/REORG.TODO/io/chmod.c b/REORG.TODO/io/chmod.c new file mode 100644 index 0000000000..0b85565ec2 --- /dev/null +++ b/REORG.TODO/io/chmod.c @@ -0,0 +1,38 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <sys/stat.h> +#include <sys/types.h> + +/* Change the protections of FILE to MODE. */ +int +__chmod (const char *file, mode_t mode) +{ + if (file == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (chmod) + +weak_alias (__chmod, chmod) diff --git a/REORG.TODO/io/chown.c b/REORG.TODO/io/chown.c new file mode 100644 index 0000000000..88712f43b0 --- /dev/null +++ b/REORG.TODO/io/chown.c @@ -0,0 +1,39 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> +#include <sys/types.h> + +/* Change the owner and group of FILE. */ +int +__chown (const char *file, uid_t owner, gid_t group) +{ + if (file == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__chown) +stub_warning (chown) + +weak_alias (__chown, chown) diff --git a/REORG.TODO/io/close.c b/REORG.TODO/io/close.c new file mode 100644 index 0000000000..f4f41086fd --- /dev/null +++ b/REORG.TODO/io/close.c @@ -0,0 +1,37 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <unistd.h> + +/* Close the file descriptor FD. */ +int +__close (int fd) +{ + if (fd < 0) + { + __set_errno (EBADF); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__close) +stub_warning (close) + +weak_alias (__close, close) diff --git a/REORG.TODO/io/creat.c b/REORG.TODO/io/creat.c new file mode 100644 index 0000000000..4e095d6877 --- /dev/null +++ b/REORG.TODO/io/creat.c @@ -0,0 +1,32 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <fcntl.h> +#include <sys/types.h> +#include <sysdep-cancel.h> + +#undef creat + +/* Create FILE with protections MODE. */ +int +creat (const char *file, mode_t mode) +{ + return __open (file, O_WRONLY|O_CREAT|O_TRUNC, mode); +} + +/* __open handles cancellation. */ +LIBC_CANCEL_HANDLED (); diff --git a/REORG.TODO/io/creat64.c b/REORG.TODO/io/creat64.c new file mode 100644 index 0000000000..6bdbcb7e45 --- /dev/null +++ b/REORG.TODO/io/creat64.c @@ -0,0 +1,28 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <fcntl.h> +#include <sys/types.h> + +#undef creat + +/* Create FILE with protections MODE. */ +int +creat64 (const char *file, mode_t mode) +{ + return __open64 (file, O_WRONLY|O_CREAT|O_TRUNC, mode); +} diff --git a/REORG.TODO/io/dup.c b/REORG.TODO/io/dup.c new file mode 100644 index 0000000000..9bb58a94ab --- /dev/null +++ b/REORG.TODO/io/dup.c @@ -0,0 +1,31 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <unistd.h> + +/* Duplicate FD, returning a new file descriptor open on the same file. */ +int +__dup (int fd) +{ + __set_errno (ENOSYS); + return -1; +} +stub_warning (dup) + +weak_alias (__dup, dup) diff --git a/REORG.TODO/io/dup2.c b/REORG.TODO/io/dup2.c new file mode 100644 index 0000000000..cb17affc26 --- /dev/null +++ b/REORG.TODO/io/dup2.c @@ -0,0 +1,44 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <unistd.h> + + +/* Duplicate FD to FD2, closing the old FD2 and making FD2 be + open the same file as FD is. Return FD2 or -1. */ +int +__dup2 (int fd, int fd2) +{ + if (fd < 0 || fd2 < 0) + { + __set_errno (EBADF); + return -1; + } + + if (fd == fd2) + /* No way to check that they are valid. */ + return fd2; + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__dup2) +stub_warning (dup2) + +weak_alias (__dup2, dup2) diff --git a/REORG.TODO/io/dup3.c b/REORG.TODO/io/dup3.c new file mode 100644 index 0000000000..ae4fe4b2ba --- /dev/null +++ b/REORG.TODO/io/dup3.c @@ -0,0 +1,44 @@ +/* Copyright (C) 2008-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <unistd.h> + + +/* Duplicate FD to FD2, closing the old FD2 and making FD2 be + open the same file as FD is which setting flags according to + FLAGS. Return FD2 or -1. */ +int +__dup3 (int fd, int fd2, int flags) +{ + if (fd < 0 || fd2 < 0) + { + __set_errno (EBADF); + return -1; + } + + if (fd == fd2) + /* No way to check that they are valid. */ + return fd2; + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__dup3) +weak_alias (__dup3, dup3) +stub_warning (dup3) diff --git a/REORG.TODO/io/euidaccess.c b/REORG.TODO/io/euidaccess.c new file mode 100644 index 0000000000..38112f7c5b --- /dev/null +++ b/REORG.TODO/io/euidaccess.c @@ -0,0 +1,38 @@ +/* Test for access to FILE using effective UID and GID. Stub version. + Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> + +int +__euidaccess (const char *file, int type) +{ + if (file == NULL || (type & ~(R_OK|W_OK|X_OK|F_OK)) != 0) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +weak_alias (__euidaccess, euidaccess) +weak_alias (__euidaccess, eaccess) +stub_warning (euidaccess) +stub_warning (eaccess) diff --git a/REORG.TODO/io/faccessat.c b/REORG.TODO/io/faccessat.c new file mode 100644 index 0000000000..da6649048c --- /dev/null +++ b/REORG.TODO/io/faccessat.c @@ -0,0 +1,44 @@ +/* Test for access to file, relative to open directory. Stub version. + Copyright (C) 2006-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stddef.h> +#include <unistd.h> +#include <sys/types.h> + +int +faccessat (int fd, const char *file, int type, int flag) +{ + if (file == NULL || (flag & ~(AT_SYMLINK_NOFOLLOW | AT_EACCESS)) != 0 + || (type & ~(R_OK|W_OK|X_OK|F_OK)) != 0) + { + __set_errno (EINVAL); + return -1; + } + + if (fd < 0 && fd != AT_FDCWD) + { + __set_errno (EBADF); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (faccessat) diff --git a/REORG.TODO/io/fchdir.c b/REORG.TODO/io/fchdir.c new file mode 100644 index 0000000000..1599b5a141 --- /dev/null +++ b/REORG.TODO/io/fchdir.c @@ -0,0 +1,31 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> + +/* Change the current directory to FD. */ +int +__fchdir (int fd) +{ + __set_errno (ENOSYS); + return -1; +} +weak_alias (__fchdir, fchdir) + +stub_warning (fchdir) diff --git a/REORG.TODO/io/fchmod.c b/REORG.TODO/io/fchmod.c new file mode 100644 index 0000000000..05900f42dd --- /dev/null +++ b/REORG.TODO/io/fchmod.c @@ -0,0 +1,38 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <sys/stat.h> +#include <sys/types.h> + +/* Change the permissions of the file referenced by FD to MODE. */ +int +__fchmod (int fd, mode_t mode) +{ + if (fd < 0) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (fchmod) + +weak_alias (__fchmod, fchmod) diff --git a/REORG.TODO/io/fchmodat.c b/REORG.TODO/io/fchmodat.c new file mode 100644 index 0000000000..8bf05285c4 --- /dev/null +++ b/REORG.TODO/io/fchmodat.c @@ -0,0 +1,44 @@ +/* Change the protections of file relative to open directory. Stub version. + Copyright (C) 2006-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stddef.h> +#include <unistd.h> +#include <sys/types.h> +#include <sys/stat.h> + +int +fchmodat (int fd, const char *file, mode_t mode, int flag) +{ + if (file == NULL || (flag & ~AT_SYMLINK_NOFOLLOW) != 0) + { + __set_errno (EINVAL); + return -1; + } + + if (fd < 0 && fd != AT_FDCWD) + { + __set_errno (EBADF); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (fchmodat) diff --git a/REORG.TODO/io/fchown.c b/REORG.TODO/io/fchown.c new file mode 100644 index 0000000000..d3b96911e8 --- /dev/null +++ b/REORG.TODO/io/fchown.c @@ -0,0 +1,38 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> +#include <sys/types.h> + +/* Change the owner and group of the file referred to by FD. */ +int +__fchown (int fd, uid_t owner, gid_t group) +{ + if (fd < 0) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (fchown) + +weak_alias (__fchown, fchown) diff --git a/REORG.TODO/io/fchownat.c b/REORG.TODO/io/fchownat.c new file mode 100644 index 0000000000..cf87ad676d --- /dev/null +++ b/REORG.TODO/io/fchownat.c @@ -0,0 +1,43 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stddef.h> +#include <unistd.h> +#include <sys/types.h> + +/* Change the owner and group of FILE. */ +int +fchownat (int fd, const char *file, uid_t owner, gid_t group, int flag) +{ + if (file == NULL || (flag & ~AT_SYMLINK_NOFOLLOW) != 0) + { + __set_errno (EINVAL); + return -1; + } + + if (fd < 0 && fd != AT_FDCWD) + { + __set_errno (EBADF); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (fchownat) diff --git a/REORG.TODO/io/fcntl.c b/REORG.TODO/io/fcntl.c new file mode 100644 index 0000000000..d067650c43 --- /dev/null +++ b/REORG.TODO/io/fcntl.c @@ -0,0 +1,37 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> + +/* Perform file control operations on FD. */ +int +__fcntl (int fd, int cmd, ...) +{ + if (fd < 0) + { + __set_errno (EBADF); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__fcntl) +stub_warning (fcntl) + +weak_alias (__fcntl, fcntl) diff --git a/REORG.TODO/io/fcntl.h b/REORG.TODO/io/fcntl.h new file mode 100644 index 0000000000..a6ccb90a15 --- /dev/null +++ b/REORG.TODO/io/fcntl.h @@ -0,0 +1,318 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +/* + * POSIX Standard: 6.5 File Control Operations <fcntl.h> + */ + +#ifndef _FCNTL_H +#define _FCNTL_H 1 + +#include <features.h> + +/* This must be early so <bits/fcntl.h> can define types winningly. */ +__BEGIN_DECLS + +/* Get __mode_t, __dev_t and __off_t .*/ +#include <bits/types.h> + +/* Get the definitions of O_*, F_*, FD_*: all the + numbers and flag bits for `open', `fcntl', et al. */ +#include <bits/fcntl.h> + +/* Detect if open needs mode as a third argument (or for openat as a fourth + argument). */ +#ifdef __O_TMPFILE +# define __OPEN_NEEDS_MODE(oflag) \ + (((oflag) & O_CREAT) != 0 || ((oflag) & __O_TMPFILE) == __O_TMPFILE) +#else +# define __OPEN_NEEDS_MODE(oflag) (((oflag) & O_CREAT) != 0) +#endif + +/* POSIX.1-2001 specifies that these types are defined by <fcntl.h>. + Earlier POSIX standards permitted any type ending in `_t' to be defined + by any POSIX header, so we don't conditionalize the definitions here. */ +#ifndef __mode_t_defined +typedef __mode_t mode_t; +# define __mode_t_defined +#endif + +#ifndef __off_t_defined +# ifndef __USE_FILE_OFFSET64 +typedef __off_t off_t; +# else +typedef __off64_t off_t; +# endif +# define __off_t_defined +#endif + +#if defined __USE_LARGEFILE64 && !defined __off64_t_defined +typedef __off64_t off64_t; +# define __off64_t_defined +#endif + +#ifndef __pid_t_defined +typedef __pid_t pid_t; +# define __pid_t_defined +#endif + +/* For XPG all symbols from <sys/stat.h> should also be available. */ +#ifdef __USE_XOPEN2K8 +# include <bits/types/struct_timespec.h> +#endif +#if defined __USE_XOPEN || defined __USE_XOPEN2K8 +# include <bits/stat.h> + +# define S_IFMT __S_IFMT +# define S_IFDIR __S_IFDIR +# define S_IFCHR __S_IFCHR +# define S_IFBLK __S_IFBLK +# define S_IFREG __S_IFREG +# ifdef __S_IFIFO +# define S_IFIFO __S_IFIFO +# endif +# ifdef __S_IFLNK +# define S_IFLNK __S_IFLNK +# endif +# if (defined __USE_UNIX98 || defined __USE_XOPEN2K8) && defined __S_IFSOCK +# define S_IFSOCK __S_IFSOCK +# endif + +/* Protection bits. */ + +# define S_ISUID __S_ISUID /* Set user ID on execution. */ +# define S_ISGID __S_ISGID /* Set group ID on execution. */ + +# if defined __USE_MISC || defined __USE_XOPEN +/* Save swapped text after use (sticky bit). This is pretty well obsolete. */ +# define S_ISVTX __S_ISVTX +# endif + +# define S_IRUSR __S_IREAD /* Read by owner. */ +# define S_IWUSR __S_IWRITE /* Write by owner. */ +# define S_IXUSR __S_IEXEC /* Execute by owner. */ +/* Read, write, and execute by owner. */ +# define S_IRWXU (__S_IREAD|__S_IWRITE|__S_IEXEC) + +# define S_IRGRP (S_IRUSR >> 3) /* Read by group. */ +# define S_IWGRP (S_IWUSR >> 3) /* Write by group. */ +# define S_IXGRP (S_IXUSR >> 3) /* Execute by group. */ +/* Read, write, and execute by group. */ +# define S_IRWXG (S_IRWXU >> 3) + +# define S_IROTH (S_IRGRP >> 3) /* Read by others. */ +# define S_IWOTH (S_IWGRP >> 3) /* Write by others. */ +# define S_IXOTH (S_IXGRP >> 3) /* Execute by others. */ +/* Read, write, and execute by others. */ +# define S_IRWXO (S_IRWXG >> 3) +#endif + +#ifdef __USE_MISC +# ifndef R_OK /* Verbatim from <unistd.h>. Ugh. */ +/* Values for the second argument to access. + These may be OR'd together. */ +# define R_OK 4 /* Test for read permission. */ +# define W_OK 2 /* Test for write permission. */ +# define X_OK 1 /* Test for execute permission. */ +# define F_OK 0 /* Test for existence. */ +# endif +#endif /* Use misc. */ + +/* XPG wants the following symbols. <stdio.h> has the same definitions. */ +#if defined __USE_XOPEN || defined __USE_XOPEN2K8 +# define SEEK_SET 0 /* Seek from beginning of file. */ +# define SEEK_CUR 1 /* Seek from current position. */ +# define SEEK_END 2 /* Seek from end of file. */ +#endif /* XPG */ + +/* The constants AT_REMOVEDIR and AT_EACCESS have the same value. AT_EASSESS + is meaningful only to faccessat, while AT_REMOVEDIR is meaningful only to + unlinkat. The two functions do completely different things and therefore, + the flags can be allowed to overlap. For example, passing AT_REMOVEDIR to + faccessat would be undefined behavior and thus treating it equivalent to + AT_EACCESS is valid undefined behavior. */ +#ifdef __USE_ATFILE +# define AT_FDCWD -100 /* Special value used to indicate + the *at functions should use the + current working directory. */ +# define AT_SYMLINK_NOFOLLOW 0x100 /* Do not follow symbolic links. */ +# define AT_REMOVEDIR 0x200 /* Remove directory instead of + unlinking file. */ +# define AT_SYMLINK_FOLLOW 0x400 /* Follow symbolic links. */ +# ifdef __USE_GNU +# define AT_NO_AUTOMOUNT 0x800 /* Suppress terminal automount + traversal. */ +# define AT_EMPTY_PATH 0x1000 /* Allow empty relative pathname. */ +# endif +# define AT_EACCESS 0x200 /* Test access permitted for + effective IDs, not real IDs. */ +#endif + +/* Do the file control operation described by CMD on FD. + The remaining arguments are interpreted depending on CMD. + + This function is a cancellation point and therefore not marked with + __THROW. */ +extern int fcntl (int __fd, int __cmd, ...); + +/* Open FILE and return a new file descriptor for it, or -1 on error. + OFLAG determines the type of access used. If O_CREAT or O_TMPFILE is set + in OFLAG, the third argument is taken as a `mode_t', the mode of the + created file. + + This function is a cancellation point and therefore not marked with + __THROW. */ +#ifndef __USE_FILE_OFFSET64 +extern int open (const char *__file, int __oflag, ...) __nonnull ((1)); +#else +# ifdef __REDIRECT +extern int __REDIRECT (open, (const char *__file, int __oflag, ...), open64) + __nonnull ((1)); +# else +# define open open64 +# endif +#endif +#ifdef __USE_LARGEFILE64 +extern int open64 (const char *__file, int __oflag, ...) __nonnull ((1)); +#endif + +#ifdef __USE_ATFILE +/* Similar to `open' but a relative path name is interpreted relative to + the directory for which FD is a descriptor. + + NOTE: some other `openat' implementation support additional functionality + through this interface, especially using the O_XATTR flag. This is not + yet supported here. + + This function is a cancellation point and therefore not marked with + __THROW. */ +# ifndef __USE_FILE_OFFSET64 +extern int openat (int __fd, const char *__file, int __oflag, ...) + __nonnull ((2)); +# else +# ifdef __REDIRECT +extern int __REDIRECT (openat, (int __fd, const char *__file, int __oflag, + ...), openat64) __nonnull ((2)); +# else +# define openat openat64 +# endif +# endif +# ifdef __USE_LARGEFILE64 +extern int openat64 (int __fd, const char *__file, int __oflag, ...) + __nonnull ((2)); +# endif +#endif + +/* Create and open FILE, with mode MODE. This takes an `int' MODE + argument because that is what `mode_t' will be widened to. + + This function is a cancellation point and therefore not marked with + __THROW. */ +#ifndef __USE_FILE_OFFSET64 +extern int creat (const char *__file, mode_t __mode) __nonnull ((1)); +#else +# ifdef __REDIRECT +extern int __REDIRECT (creat, (const char *__file, mode_t __mode), + creat64) __nonnull ((1)); +# else +# define creat creat64 +# endif +#endif +#ifdef __USE_LARGEFILE64 +extern int creat64 (const char *__file, mode_t __mode) __nonnull ((1)); +#endif + +#if !defined F_LOCK && (defined __USE_MISC || (defined __USE_XOPEN_EXTENDED \ + && !defined __USE_POSIX)) +/* NOTE: These declarations also appear in <unistd.h>; be sure to keep both + files consistent. Some systems have them there and some here, and some + software depends on the macros being defined without including both. */ + +/* `lockf' is a simpler interface to the locking facilities of `fcntl'. + LEN is always relative to the current file position. + The CMD argument is one of the following. */ + +# define F_ULOCK 0 /* Unlock a previously locked region. */ +# define F_LOCK 1 /* Lock a region for exclusive use. */ +# define F_TLOCK 2 /* Test and lock a region for exclusive use. */ +# define F_TEST 3 /* Test a region for other processes locks. */ + +# ifndef __USE_FILE_OFFSET64 +extern int lockf (int __fd, int __cmd, off_t __len); +# else +# ifdef __REDIRECT +extern int __REDIRECT (lockf, (int __fd, int __cmd, __off64_t __len), lockf64); +# else +# define lockf lockf64 +# endif +# endif +# ifdef __USE_LARGEFILE64 +extern int lockf64 (int __fd, int __cmd, off64_t __len); +# endif +#endif + +#ifdef __USE_XOPEN2K +/* Advice the system about the expected behaviour of the application with + respect to the file associated with FD. */ +# ifndef __USE_FILE_OFFSET64 +extern int posix_fadvise (int __fd, off_t __offset, off_t __len, + int __advise) __THROW; +# else + # ifdef __REDIRECT_NTH +extern int __REDIRECT_NTH (posix_fadvise, (int __fd, __off64_t __offset, + __off64_t __len, int __advise), + posix_fadvise64); +# else +# define posix_fadvise posix_fadvise64 +# endif +# endif +# ifdef __USE_LARGEFILE64 +extern int posix_fadvise64 (int __fd, off64_t __offset, off64_t __len, + int __advise) __THROW; +# endif + + +/* Reserve storage for the data of the file associated with FD. + + This function is a possible cancellation point and therefore not + marked with __THROW. */ +# ifndef __USE_FILE_OFFSET64 +extern int posix_fallocate (int __fd, off_t __offset, off_t __len); +# else + # ifdef __REDIRECT +extern int __REDIRECT (posix_fallocate, (int __fd, __off64_t __offset, + __off64_t __len), + posix_fallocate64); +# else +# define posix_fallocate posix_fallocate64 +# endif +# endif +# ifdef __USE_LARGEFILE64 +extern int posix_fallocate64 (int __fd, off64_t __offset, off64_t __len); +# endif +#endif + + +/* Define some inlines helping to catch common problems. */ +#if __USE_FORTIFY_LEVEL > 0 && defined __fortify_function \ + && defined __va_arg_pack_len +# include <bits/fcntl2.h> +#endif + +__END_DECLS + +#endif /* fcntl.h */ diff --git a/REORG.TODO/io/flock.c b/REORG.TODO/io/flock.c new file mode 100644 index 0000000000..9ead1304f1 --- /dev/null +++ b/REORG.TODO/io/flock.c @@ -0,0 +1,32 @@ +/* Copyright (C) 1992-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/file.h> + +/* Apply or remove an advisory lock, according to OPERATION, + on the file FD refers to. */ +int +__flock (int fd, int operation) +{ + __set_errno (ENOSYS); + return -1; +} + +weak_alias (__flock, flock) + +stub_warning (flock) diff --git a/REORG.TODO/io/fstat.c b/REORG.TODO/io/fstat.c new file mode 100644 index 0000000000..1d8c85d7dc --- /dev/null +++ b/REORG.TODO/io/fstat.c @@ -0,0 +1,55 @@ +/* Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file with other + programs, and to distribute those programs without any restriction + coming from the use of this file. (The GNU Lesser General Public + License restrictions do apply in other respects; for example, they + cover modification of the file, and distribution when not linked + into another program.) + + Note that people who make modified versions of this file are not + obligated to grant this special exception for their modified + versions; it is their choice whether to do so. The GNU Lesser + General Public License gives permission to release a modified + version without this exception; this exception also makes it + possible to release a modified version which carries forward this + exception. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/stat.h> + +/* This definition is only used if inlining fails for this function; see + the last page of <sys/stat.h>. The real work is done by the `x' + function which is passed a version number argument. We arrange in the + makefile that when not inlined this function is always statically + linked; that way a dynamically-linked executable always encodes the + version number corresponding to the data structures it uses, so the `x' + functions in the shared library can adapt without needing to recompile + all callers. */ + +#undef fstat +#undef __fstat +int +attribute_hidden +__fstat (int fd, struct stat *buf) +{ + return __fxstat (_STAT_VER, fd, buf); +} + +weak_hidden_alias (__fstat, fstat) diff --git a/REORG.TODO/io/fstat64.c b/REORG.TODO/io/fstat64.c new file mode 100644 index 0000000000..69c80e5e45 --- /dev/null +++ b/REORG.TODO/io/fstat64.c @@ -0,0 +1,52 @@ +/* Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file with other + programs, and to distribute those programs without any restriction + coming from the use of this file. (The GNU Lesser General Public + License restrictions do apply in other respects; for example, they + cover modification of the file, and distribution when not linked + into another program.) + + Note that people who make modified versions of this file are not + obligated to grant this special exception for their modified + versions; it is their choice whether to do so. The GNU Lesser + General Public License gives permission to release a modified + version without this exception; this exception also makes it + possible to release a modified version which carries forward this + exception. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/stat.h> + +/* This definition is only used if inlining fails for this function; see + the last page of <sys/stat.h>. The real work is done by the `x' + function which is passed a version number argument. We arrange in the + makefile that when not inlined this function is always statically + linked; that way a dynamically-linked executable always encodes the + version number corresponding to the data structures it uses, so the `x' + functions in the shared library can adapt without needing to recompile + all callers. */ + +#undef fstat64 +int +attribute_hidden +fstat64 (int fd, struct stat64 *buf) +{ + return __fxstat64 (_STAT_VER, fd, buf); +} diff --git a/REORG.TODO/io/fstatat.c b/REORG.TODO/io/fstatat.c new file mode 100644 index 0000000000..4b2060e590 --- /dev/null +++ b/REORG.TODO/io/fstatat.c @@ -0,0 +1,52 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file with other + programs, and to distribute those programs without any restriction + coming from the use of this file. (The GNU Lesser General Public + License restrictions do apply in other respects; for example, they + cover modification of the file, and distribution when not linked + into another program.) + + Note that people who make modified versions of this file are not + obligated to grant this special exception for their modified + versions; it is their choice whether to do so. The GNU Lesser + General Public License gives permission to release a modified + version without this exception; this exception also makes it + possible to release a modified version which carries forward this + exception. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/stat.h> + +/* This definition is only used if inlining fails for this function; see + the last page of <sys/stat.h>. The real work is done by the `x' + function which is passed a version number argument. We arrange in the + makefile that when not inlined this function is always statically + linked; that way a dynamically-linked executable always encodes the + version number corresponding to the data structures it uses, so the `x' + functions in the shared library can adapt without needing to recompile + all callers. */ + +#undef fstatat +int +attribute_hidden +fstatat (int fd, const char *file, struct stat *buf, int flag) +{ + return __fxstatat (_STAT_VER, fd, file, buf, flag); +} diff --git a/REORG.TODO/io/fstatat64.c b/REORG.TODO/io/fstatat64.c new file mode 100644 index 0000000000..13a9ebc870 --- /dev/null +++ b/REORG.TODO/io/fstatat64.c @@ -0,0 +1,52 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file with other + programs, and to distribute those programs without any restriction + coming from the use of this file. (The GNU Lesser General Public + License restrictions do apply in other respects; for example, they + cover modification of the file, and distribution when not linked + into another program.) + + Note that people who make modified versions of this file are not + obligated to grant this special exception for their modified + versions; it is their choice whether to do so. The GNU Lesser + General Public License gives permission to release a modified + version without this exception; this exception also makes it + possible to release a modified version which carries forward this + exception. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/stat.h> + +/* This definition is only used if inlining fails for this function; see + the last page of <sys/stat.h>. The real work is done by the `x' + function which is passed a version number argument. We arrange in the + makefile that when not inlined this function is always statically + linked; that way a dynamically-linked executable always encodes the + version number corresponding to the data structures it uses, so the `x' + functions in the shared library can adapt without needing to recompile + all callers. */ + +#undef fstatat64 +int +attribute_hidden +fstatat64 (int fd, const char *file, struct stat64 *buf, int flag) +{ + return __fxstatat64 (_STAT_VER, fd, file, buf, flag); +} diff --git a/REORG.TODO/io/fstatfs.c b/REORG.TODO/io/fstatfs.c new file mode 100644 index 0000000000..f0a537a9fa --- /dev/null +++ b/REORG.TODO/io/fstatfs.c @@ -0,0 +1,32 @@ +/* Return information about the filesystem on which FD resides. + Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/statfs.h> +#include <stddef.h> + +/* Return information about the filesystem on which FD resides. */ +int +__fstatfs (int fd, struct statfs *buf) +{ + __set_errno (ENOSYS); + return -1; +} +stub_warning (fstatfs) + +weak_alias (__fstatfs, fstatfs) diff --git a/REORG.TODO/io/fstatfs64.c b/REORG.TODO/io/fstatfs64.c new file mode 100644 index 0000000000..be05550368 --- /dev/null +++ b/REORG.TODO/io/fstatfs64.c @@ -0,0 +1,30 @@ +/* Copyright (C) 1998-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/statfs.h> + +/* Return information about the filesystem on which FD resides. */ +int +__fstatfs64 (int fd, struct statfs64 *buf) +{ + __set_errno (ENOSYS); + return -1; +} +weak_alias (__fstatfs64, fstatfs64) + +stub_warning (fstatfs64) diff --git a/REORG.TODO/io/fstatvfs.c b/REORG.TODO/io/fstatvfs.c new file mode 100644 index 0000000000..344aee229d --- /dev/null +++ b/REORG.TODO/io/fstatvfs.c @@ -0,0 +1,31 @@ +/* Return information about the filesystem on which FD resides. + Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/statvfs.h> + +/* Return information about the filesystem on which FD resides. */ +int +__fstatvfs (int fd, struct statvfs *buf) +{ + __set_errno (ENOSYS); + return -1; +} +stub_warning (fstatvfs) +weak_alias (__fstatvfs, fstatvfs) +libc_hidden_weak (fstatvfs) diff --git a/REORG.TODO/io/fstatvfs64.c b/REORG.TODO/io/fstatvfs64.c new file mode 100644 index 0000000000..cbc78bd88b --- /dev/null +++ b/REORG.TODO/io/fstatvfs64.c @@ -0,0 +1,30 @@ +/* Copyright (C) 1998-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/statvfs.h> + +/* Return information about the filesystem on which FD resides. */ +int +__fstatvfs64 (int fd, struct statvfs64 *buf) +{ + __set_errno (ENOSYS); + return -1; +} +weak_alias (__fstatvfs64, fstatvfs64) + +stub_warning (fstatvfs64) diff --git a/REORG.TODO/io/fts.c b/REORG.TODO/io/fts.c new file mode 100644 index 0000000000..b68a51f333 --- /dev/null +++ b/REORG.TODO/io/fts.c @@ -0,0 +1,1146 @@ +/* File tree traversal functions. + Copyright (C) 1994-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +/*- + * Copyright (c) 1990, 1993, 1994 + * The Regents of the University of California. 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. + * 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. + * + * 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. + */ + +#if defined(LIBC_SCCS) && !defined(lint) +static char sccsid[] = "@(#)fts.c 8.6 (Berkeley) 8/14/94"; +#endif /* LIBC_SCCS and not lint */ + +#include <sys/param.h> +#include <include/sys/stat.h> +#include <fcntl.h> +#include <dirent.h> +#include <errno.h> +#include <fts.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + + +/* Largest alignment size needed, minus one. + Usually long double is the worst case. */ +#ifndef ALIGNBYTES +#define ALIGNBYTES (__alignof__ (long double) - 1) +#endif +/* Align P to that size. */ +#ifndef ALIGN +#define ALIGN(p) (((unsigned long int) (p) + ALIGNBYTES) & ~ALIGNBYTES) +#endif + + +/* Support for the LFS API version. */ +#ifndef FTS_OPEN +#define FTS_OPEN fts_open +#define FTS_CLOSE fts_close +#define FTS_READ fts_read +#define FTS_SET fts_set +#define FTS_CHILDREN fts_children +# define FTSOBJ FTS +# define FTSENTRY FTSENT +# define INO_T ino_t +# define STAT stat +# define LSTAT lstat +#endif + +static FTSENTRY *fts_alloc (FTSOBJ *, const char *, size_t) internal_function; +static FTSENTRY *fts_build (FTSOBJ *, int) internal_function; +static void fts_lfree (FTSENTRY *) internal_function; +static void fts_load (FTSOBJ *, FTSENTRY *) internal_function; +static size_t fts_maxarglen (char * const *) internal_function; +static void fts_padjust (FTSOBJ *, FTSENTRY *) internal_function; +static int fts_palloc (FTSOBJ *, size_t) internal_function; +static FTSENTRY *fts_sort (FTSOBJ *, FTSENTRY *, int) internal_function; +static u_short fts_stat (FTSOBJ *, FTSENTRY *, int) internal_function; +static int fts_safe_changedir (FTSOBJ *, FTSENTRY *, int, const char *) + internal_function; + +#ifndef MAX +#define MAX(a, b) ({ __typeof__ (a) _a = (a); \ + __typeof__ (b) _b = (b); \ + _a > _b ? _a : _b; }) +#endif + +#define ISDOT(a) (a[0] == '.' && (!a[1] || (a[1] == '.' && !a[2]))) + +#define CLR(opt) (sp->fts_options &= ~(opt)) +#define ISSET(opt) (sp->fts_options & (opt)) +#define SET(opt) (sp->fts_options |= (opt)) + +#define FCHDIR(sp, fd) (!ISSET(FTS_NOCHDIR) && __fchdir(fd)) + +/* fts_build flags */ +#define BCHILD 1 /* fts_children */ +#define BNAMES 2 /* fts_children, names only */ +#define BREAD 3 /* fts_read */ + +FTSOBJ * +FTS_OPEN (char * const *argv, int options, + int (*compar) (const FTSENTRY **, const FTSENTRY **)) +{ + FTSOBJ *sp; + FTSENTRY *p, *root; + int nitems; + FTSENTRY *parent = NULL; + FTSENTRY *tmp; + + /* Options check. */ + if (options & ~FTS_OPTIONMASK) { + __set_errno (EINVAL); + return (NULL); + } + + /* Allocate/initialize the stream */ + if ((sp = malloc((u_int)sizeof(FTSOBJ))) == NULL) + return (NULL); + memset(sp, 0, sizeof(FTSOBJ)); + sp->fts_compar = (int (*) (const void *, const void *)) compar; + sp->fts_options = options; + + /* Logical walks turn on NOCHDIR; symbolic links are too hard. */ + if (ISSET(FTS_LOGICAL)) + SET(FTS_NOCHDIR); + + /* + * Start out with 1K of path space, and enough, in any case, + * to hold the user's paths. + */ +#ifndef MAXPATHLEN +#define MAXPATHLEN 1024 +#endif + size_t maxarglen = fts_maxarglen(argv); + if (fts_palloc(sp, MAX(maxarglen, MAXPATHLEN))) + goto mem1; + + /* Allocate/initialize root's parent. */ + if (*argv != NULL) { + if ((parent = fts_alloc(sp, "", 0)) == NULL) + goto mem2; + parent->fts_level = FTS_ROOTPARENTLEVEL; + } + + /* Allocate/initialize root(s). */ + for (root = NULL, nitems = 0; *argv != NULL; ++argv, ++nitems) { + /* Don't allow zero-length paths. */ + size_t len = strlen(*argv); + if (len == 0) { + __set_errno (ENOENT); + goto mem3; + } + + p = fts_alloc(sp, *argv, len); + p->fts_level = FTS_ROOTLEVEL; + p->fts_parent = parent; + p->fts_accpath = p->fts_name; + p->fts_info = fts_stat(sp, p, ISSET(FTS_COMFOLLOW)); + + /* Command-line "." and ".." are real directories. */ + if (p->fts_info == FTS_DOT) + p->fts_info = FTS_D; + + /* + * If comparison routine supplied, traverse in sorted + * order; otherwise traverse in the order specified. + */ + if (compar) { + p->fts_link = root; + root = p; + } else { + p->fts_link = NULL; + if (root == NULL) + tmp = root = p; + else { + tmp->fts_link = p; + tmp = p; + } + } + } + if (compar && nitems > 1) + root = fts_sort(sp, root, nitems); + + /* + * Allocate a dummy pointer and make fts_read think that we've just + * finished the node before the root(s); set p->fts_info to FTS_INIT + * so that everything about the "current" node is ignored. + */ + if ((sp->fts_cur = fts_alloc(sp, "", 0)) == NULL) + goto mem3; + sp->fts_cur->fts_link = root; + sp->fts_cur->fts_info = FTS_INIT; + + /* + * If using chdir(2), grab a file descriptor pointing to dot to ensure + * that we can get back here; this could be avoided for some paths, + * but almost certainly not worth the effort. Slashes, symbolic links, + * and ".." are all fairly nasty problems. Note, if we can't get the + * descriptor we run anyway, just more slowly. + */ + if (!ISSET(FTS_NOCHDIR) + && (sp->fts_rfd = __open(".", O_RDONLY, 0)) < 0) + SET(FTS_NOCHDIR); + + return (sp); + +mem3: fts_lfree(root); + free(parent); +mem2: free(sp->fts_path); +mem1: free(sp); + return (NULL); +} + +static void +internal_function +fts_load (FTSOBJ *sp, FTSENTRY *p) +{ + int len; + char *cp; + + /* + * Load the stream structure for the next traversal. Since we don't + * actually enter the directory until after the preorder visit, set + * the fts_accpath field specially so the chdir gets done to the right + * place and the user can access the first node. From fts_open it's + * known that the path will fit. + */ + len = p->fts_pathlen = p->fts_namelen; + memmove(sp->fts_path, p->fts_name, len + 1); + if ((cp = strrchr(p->fts_name, '/')) && (cp != p->fts_name || cp[1])) { + len = strlen(++cp); + memmove(p->fts_name, cp, len + 1); + p->fts_namelen = len; + } + p->fts_accpath = p->fts_path = sp->fts_path; + sp->fts_dev = p->fts_dev; +} + +int +FTS_CLOSE (FTSOBJ *sp) +{ + FTSENTRY *freep, *p; + int saved_errno; + + /* + * This still works if we haven't read anything -- the dummy structure + * points to the root list, so we step through to the end of the root + * list which has a valid parent pointer. + */ + if (sp->fts_cur) { + for (p = sp->fts_cur; p->fts_level >= FTS_ROOTLEVEL;) { + freep = p; + p = p->fts_link != NULL ? p->fts_link : p->fts_parent; + free(freep); + } + free(p); + } + + /* Free up child linked list, sort array, path buffer. */ + if (sp->fts_child) + fts_lfree(sp->fts_child); + free(sp->fts_array); + free(sp->fts_path); + + /* Return to original directory, save errno if necessary. */ + if (!ISSET(FTS_NOCHDIR)) { + saved_errno = __fchdir(sp->fts_rfd) ? errno : 0; + (void)__close(sp->fts_rfd); + + /* Set errno and return. */ + if (saved_errno != 0) { + /* Free up the stream pointer. */ + free(sp); + __set_errno (saved_errno); + return (-1); + } + } + + /* Free up the stream pointer. */ + free(sp); + return (0); +} + +/* + * Special case of "/" at the end of the path so that slashes aren't + * appended which would cause paths to be written as "....//foo". + */ +#define NAPPEND(p) \ + (p->fts_path[p->fts_pathlen - 1] == '/' \ + ? p->fts_pathlen - 1 : p->fts_pathlen) + +FTSENTRY * +FTS_READ (FTSOBJ *sp) +{ + FTSENTRY *p, *tmp; + int instr; + char *t; + int saved_errno; + + /* If finished or unrecoverable error, return NULL. */ + if (sp->fts_cur == NULL || ISSET(FTS_STOP)) + return (NULL); + + /* Set current node pointer. */ + p = sp->fts_cur; + + /* Save and zero out user instructions. */ + instr = p->fts_instr; + p->fts_instr = FTS_NOINSTR; + + /* Any type of file may be re-visited; re-stat and re-turn. */ + if (instr == FTS_AGAIN) { + p->fts_info = fts_stat(sp, p, 0); + return (p); + } + + /* + * Following a symlink -- SLNONE test allows application to see + * SLNONE and recover. If indirecting through a symlink, have + * keep a pointer to current location. If unable to get that + * pointer, follow fails. + */ + if (instr == FTS_FOLLOW && + (p->fts_info == FTS_SL || p->fts_info == FTS_SLNONE)) { + p->fts_info = fts_stat(sp, p, 1); + if (p->fts_info == FTS_D && !ISSET(FTS_NOCHDIR)) { + if ((p->fts_symfd = __open(".", O_RDONLY, 0)) < 0) { + p->fts_errno = errno; + p->fts_info = FTS_ERR; + } else + p->fts_flags |= FTS_SYMFOLLOW; + } + return (p); + } + + /* Directory in pre-order. */ + if (p->fts_info == FTS_D) { + /* If skipped or crossed mount point, do post-order visit. */ + if (instr == FTS_SKIP || + (ISSET(FTS_XDEV) && p->fts_dev != sp->fts_dev)) { + if (p->fts_flags & FTS_SYMFOLLOW) + (void)__close(p->fts_symfd); + if (sp->fts_child) { + fts_lfree(sp->fts_child); + sp->fts_child = NULL; + } + p->fts_info = FTS_DP; + return (p); + } + + /* Rebuild if only read the names and now traversing. */ + if (sp->fts_child != NULL && ISSET(FTS_NAMEONLY)) { + CLR(FTS_NAMEONLY); + fts_lfree(sp->fts_child); + sp->fts_child = NULL; + } + + /* + * Cd to the subdirectory. + * + * If have already read and now fail to chdir, whack the list + * to make the names come out right, and set the parent errno + * so the application will eventually get an error condition. + * Set the FTS_DONTCHDIR flag so that when we logically change + * directories back to the parent we don't do a chdir. + * + * If haven't read do so. If the read fails, fts_build sets + * FTS_STOP or the fts_info field of the node. + */ + if (sp->fts_child != NULL) { + if (fts_safe_changedir(sp, p, -1, p->fts_accpath)) { + p->fts_errno = errno; + p->fts_flags |= FTS_DONTCHDIR; + for (p = sp->fts_child; p != NULL; + p = p->fts_link) + p->fts_accpath = + p->fts_parent->fts_accpath; + } + } else if ((sp->fts_child = fts_build(sp, BREAD)) == NULL) { + if (ISSET(FTS_STOP)) + return (NULL); + return (p); + } + p = sp->fts_child; + sp->fts_child = NULL; + sp->fts_cur = p; + goto name; + } + + /* Move to the next node on this level. */ +next: tmp = p; + if ((p = p->fts_link) != NULL) { + sp->fts_cur = p; + free(tmp); + + /* + * If reached the top, return to the original directory (or + * the root of the tree), and load the paths for the next root. + */ + if (p->fts_level == FTS_ROOTLEVEL) { + if (FCHDIR(sp, sp->fts_rfd)) { + SET(FTS_STOP); + return (NULL); + } + fts_load(sp, p); + return p; + } + + /* + * User may have called fts_set on the node. If skipped, + * ignore. If followed, get a file descriptor so we can + * get back if necessary. + */ + if (p->fts_instr == FTS_SKIP) + goto next; + if (p->fts_instr == FTS_FOLLOW) { + p->fts_info = fts_stat(sp, p, 1); + if (p->fts_info == FTS_D && !ISSET(FTS_NOCHDIR)) { + if ((p->fts_symfd = + __open(".", O_RDONLY, 0)) < 0) { + p->fts_errno = errno; + p->fts_info = FTS_ERR; + } else + p->fts_flags |= FTS_SYMFOLLOW; + } + p->fts_instr = FTS_NOINSTR; + } + +name: t = sp->fts_path + NAPPEND(p->fts_parent); + *t++ = '/'; + memmove(t, p->fts_name, p->fts_namelen + 1); + return p; + } + + /* Move up to the parent node. */ + p = tmp->fts_parent; + sp->fts_cur = p; + free(tmp); + + if (p->fts_level == FTS_ROOTPARENTLEVEL) { + /* + * Done; free everything up and set errno to 0 so the user + * can distinguish between error and EOF. + */ + free(p); + __set_errno (0); + return (sp->fts_cur = NULL); + } + + /* NUL terminate the pathname. */ + sp->fts_path[p->fts_pathlen] = '\0'; + + /* + * Return to the parent directory. If at a root node or came through + * a symlink, go back through the file descriptor. Otherwise, cd up + * one directory. + */ + if (p->fts_level == FTS_ROOTLEVEL) { + if (FCHDIR(sp, sp->fts_rfd)) { + SET(FTS_STOP); + return (NULL); + } + } else if (p->fts_flags & FTS_SYMFOLLOW) { + if (FCHDIR(sp, p->fts_symfd)) { + saved_errno = errno; + (void)__close(p->fts_symfd); + __set_errno (saved_errno); + SET(FTS_STOP); + return (NULL); + } + (void)__close(p->fts_symfd); + } else if (!(p->fts_flags & FTS_DONTCHDIR) && + fts_safe_changedir(sp, p->fts_parent, -1, "..")) { + SET(FTS_STOP); + return (NULL); + } + p->fts_info = p->fts_errno ? FTS_ERR : FTS_DP; + return p; +} + +/* + * Fts_set takes the stream as an argument although it's not used in this + * implementation; it would be necessary if anyone wanted to add global + * semantics to fts using fts_set. An error return is allowed for similar + * reasons. + */ +/* ARGSUSED */ +int +FTS_SET (FTSOBJ *sp, FTSENTRY *p, int instr) +{ + if (instr != 0 && instr != FTS_AGAIN && instr != FTS_FOLLOW && + instr != FTS_NOINSTR && instr != FTS_SKIP) { + __set_errno (EINVAL); + return (1); + } + p->fts_instr = instr; + return (0); +} + +FTSENTRY * +FTS_CHILDREN(FTSOBJ *sp, int instr) +{ + FTSENTRY *p; + int fd; + + if (instr != 0 && instr != FTS_NAMEONLY) { + __set_errno (EINVAL); + return (NULL); + } + + /* Set current node pointer. */ + p = sp->fts_cur; + + /* + * Errno set to 0 so user can distinguish empty directory from + * an error. + */ + __set_errno (0); + + /* Fatal errors stop here. */ + if (ISSET(FTS_STOP)) + return (NULL); + + /* Return logical hierarchy of user's arguments. */ + if (p->fts_info == FTS_INIT) + return (p->fts_link); + + /* + * If not a directory being visited in pre-order, stop here. Could + * allow FTS_DNR, assuming the user has fixed the problem, but the + * same effect is available with FTS_AGAIN. + */ + if (p->fts_info != FTS_D /* && p->fts_info != FTS_DNR */) + return (NULL); + + /* Free up any previous child list. */ + if (sp->fts_child != NULL) + fts_lfree(sp->fts_child); + + if (instr == FTS_NAMEONLY) { + SET(FTS_NAMEONLY); + instr = BNAMES; + } else + instr = BCHILD; + + /* + * If using chdir on a relative path and called BEFORE fts_read does + * its chdir to the root of a traversal, we can lose -- we need to + * chdir into the subdirectory, and we don't know where the current + * directory is, so we can't get back so that the upcoming chdir by + * fts_read will work. + */ + if (p->fts_level != FTS_ROOTLEVEL || p->fts_accpath[0] == '/' || + ISSET(FTS_NOCHDIR)) + return (sp->fts_child = fts_build(sp, instr)); + + if ((fd = __open(".", O_RDONLY, 0)) < 0) + return (NULL); + sp->fts_child = fts_build(sp, instr); + if (__fchdir(fd)) + return (NULL); + (void)__close(fd); + return (sp->fts_child); +} + +static inline int +dirent_not_directory(const struct dirent *dp) +{ +#if defined DT_DIR && defined _DIRENT_HAVE_D_TYPE + return dp->d_type != DT_DIR && dp->d_type != DT_UNKNOWN; +#else + return 0; +#endif +} + +/* + * This is the tricky part -- do not casually change *anything* in here. The + * idea is to build the linked list of entries that are used by fts_children + * and fts_read. There are lots of special cases. + * + * The real slowdown in walking the tree is the stat calls. If FTS_NOSTAT is + * set and it's a physical walk (so that symbolic links can't be directories), + * we can do things quickly. First, if it's a 4.4BSD file system, the type + * of the file is in the directory entry. Otherwise, we assume that the number + * of subdirectories in a node is equal to the number of links to the parent. + * The former skips all stat calls. The latter skips stat calls in any leaf + * directories and for any files after the subdirectories in the directory have + * been found, cutting the stat calls by about 2/3. + */ +static FTSENTRY * +internal_function +fts_build (FTSOBJ *sp, int type) +{ + struct dirent *dp; + FTSENTRY *p, *head; + int nitems; + FTSENTRY *cur, *tail; + DIR *dirp; + void *oldaddr; + int cderrno, descend, len, level, nlinks, saved_errno, + nostat, doadjust; + size_t maxlen; + char *cp; + + /* Set current node pointer. */ + cur = sp->fts_cur; + + /* + * Open the directory for reading. If this fails, we're done. + * If being called from fts_read, set the fts_info field. + */ +#if defined FTS_WHITEOUT && 0 + if (ISSET(FTS_WHITEOUT)) + oflag = DTF_NODUP|DTF_REWIND; + else + oflag = DTF_HIDEW|DTF_NODUP|DTF_REWIND; +#else +# define __opendir2(path, flag) __opendir(path) +#endif + if ((dirp = __opendir2(cur->fts_accpath, oflag)) == NULL) { + if (type == BREAD) { + cur->fts_info = FTS_DNR; + cur->fts_errno = errno; + } + return (NULL); + } + + /* + * Nlinks is the number of possible entries of type directory in the + * directory if we're cheating on stat calls, 0 if we're not doing + * any stat calls at all, -1 if we're doing stats on everything. + */ + if (type == BNAMES) { + nlinks = 0; + /* Be quiet about nostat, GCC. */ + nostat = 0; + } else if (ISSET(FTS_NOSTAT) && ISSET(FTS_PHYSICAL)) { + nlinks = cur->fts_nlink - (ISSET(FTS_SEEDOT) ? 0 : 2); + nostat = 1; + } else { + nlinks = -1; + nostat = 0; + } + +#ifdef notdef + (void)printf("nlinks == %d (cur: %d)\n", nlinks, cur->fts_nlink); + (void)printf("NOSTAT %d PHYSICAL %d SEEDOT %d\n", + ISSET(FTS_NOSTAT), ISSET(FTS_PHYSICAL), ISSET(FTS_SEEDOT)); +#endif + /* + * If we're going to need to stat anything or we want to descend + * and stay in the directory, chdir. If this fails we keep going, + * but set a flag so we don't chdir after the post-order visit. + * We won't be able to stat anything, but we can still return the + * names themselves. Note, that since fts_read won't be able to + * chdir into the directory, it will have to return different path + * names than before, i.e. "a/b" instead of "b". Since the node + * has already been visited in pre-order, have to wait until the + * post-order visit to return the error. There is a special case + * here, if there was nothing to stat then it's not an error to + * not be able to stat. This is all fairly nasty. If a program + * needed sorted entries or stat information, they had better be + * checking FTS_NS on the returned nodes. + */ + cderrno = 0; + if (nlinks || type == BREAD) { + if (fts_safe_changedir(sp, cur, dirfd(dirp), NULL)) { + if (nlinks && type == BREAD) + cur->fts_errno = errno; + cur->fts_flags |= FTS_DONTCHDIR; + descend = 0; + cderrno = errno; + (void)__closedir(dirp); + dirp = NULL; + } else + descend = 1; + } else + descend = 0; + + /* + * Figure out the max file name length that can be stored in the + * current path -- the inner loop allocates more path as necessary. + * We really wouldn't have to do the maxlen calculations here, we + * could do them in fts_read before returning the path, but it's a + * lot easier here since the length is part of the dirent structure. + * + * If not changing directories set a pointer so that can just append + * each new name into the path. + */ + len = NAPPEND(cur); + if (ISSET(FTS_NOCHDIR)) { + cp = sp->fts_path + len; + *cp++ = '/'; + } else { + /* GCC, you're too verbose. */ + cp = NULL; + } + len++; + maxlen = sp->fts_pathlen - len; + + level = cur->fts_level + 1; + + /* Read the directory, attaching each entry to the `link' pointer. */ + doadjust = 0; + for (head = tail = NULL, nitems = 0; dirp && (dp = __readdir(dirp));) { + if (!ISSET(FTS_SEEDOT) && ISDOT(dp->d_name)) + continue; + + if ((p = fts_alloc(sp, dp->d_name, _D_EXACT_NAMLEN (dp))) == NULL) + goto mem1; + if (_D_EXACT_NAMLEN (dp) >= maxlen) {/* include space for NUL */ + oldaddr = sp->fts_path; + if (fts_palloc(sp, _D_EXACT_NAMLEN (dp) + len + 1)) { + /* + * No more memory for path or structures. Save + * errno, free up the current structure and the + * structures already allocated. + */ +mem1: saved_errno = errno; + free(p); + fts_lfree(head); + (void)__closedir(dirp); + cur->fts_info = FTS_ERR; + SET(FTS_STOP); + __set_errno (saved_errno); + return (NULL); + } + /* Did realloc() change the pointer? */ + if (oldaddr != sp->fts_path) { + doadjust = 1; + if (ISSET(FTS_NOCHDIR)) + cp = sp->fts_path + len; + } + maxlen = sp->fts_pathlen - len; + } + + if (len + _D_EXACT_NAMLEN (dp) >= USHRT_MAX) { + /* + * In an FTSENT, fts_pathlen is a u_short so it is + * possible to wraparound here. If we do, free up + * the current structure and the structures already + * allocated, then error out with ENAMETOOLONG. + */ + free(p); + fts_lfree(head); + (void)__closedir(dirp); + cur->fts_info = FTS_ERR; + SET(FTS_STOP); + __set_errno (ENAMETOOLONG); + return (NULL); + } + p->fts_level = level; + p->fts_parent = sp->fts_cur; + p->fts_pathlen = len + _D_EXACT_NAMLEN (dp); + +#if defined FTS_WHITEOUT && 0 + if (dp->d_type == DT_WHT) + p->fts_flags |= FTS_ISW; +#endif + + /* Unreachable code. cderrno is only ever set to a nonnull + value if dirp is closed at the same time. But then we + cannot enter this loop. */ + if (0 && cderrno) { + if (nlinks) { + p->fts_info = FTS_NS; + p->fts_errno = cderrno; + } else + p->fts_info = FTS_NSOK; + p->fts_accpath = cur->fts_accpath; + } else if (nlinks == 0 + || (nostat && dirent_not_directory(dp))) { + p->fts_accpath = + ISSET(FTS_NOCHDIR) ? p->fts_path : p->fts_name; + p->fts_info = FTS_NSOK; + } else { + /* Build a file name for fts_stat to stat. */ + if (ISSET(FTS_NOCHDIR)) { + p->fts_accpath = p->fts_path; + memmove(cp, p->fts_name, p->fts_namelen + 1); + } else + p->fts_accpath = p->fts_name; + /* Stat it. */ + p->fts_info = fts_stat(sp, p, 0); + + /* Decrement link count if applicable. */ + if (nlinks > 0 && (p->fts_info == FTS_D || + p->fts_info == FTS_DC || p->fts_info == FTS_DOT)) + --nlinks; + } + + /* We walk in directory order so "ls -f" doesn't get upset. */ + p->fts_link = NULL; + if (head == NULL) + head = tail = p; + else { + tail->fts_link = p; + tail = p; + } + ++nitems; + } + if (dirp) + (void)__closedir(dirp); + + /* + * If realloc() changed the address of the path, adjust the + * addresses for the rest of the tree and the dir list. + */ + if (doadjust) + fts_padjust(sp, head); + + /* + * If not changing directories, reset the path back to original + * state. + */ + if (ISSET(FTS_NOCHDIR)) { + if (len == sp->fts_pathlen || nitems == 0) + --cp; + *cp = '\0'; + } + + /* + * If descended after called from fts_children or after called from + * fts_read and nothing found, get back. At the root level we use + * the saved fd; if one of fts_open()'s arguments is a relative path + * to an empty directory, we wind up here with no other way back. If + * can't get back, we're done. + */ + if (descend && (type == BCHILD || !nitems) && + (cur->fts_level == FTS_ROOTLEVEL ? + FCHDIR(sp, sp->fts_rfd) : + fts_safe_changedir(sp, cur->fts_parent, -1, ".."))) { + cur->fts_info = FTS_ERR; + SET(FTS_STOP); + fts_lfree(head); + return (NULL); + } + + /* If didn't find anything, return NULL. */ + if (!nitems) { + if (type == BREAD) + cur->fts_info = FTS_DP; + fts_lfree(head); + return (NULL); + } + + /* Sort the entries. */ + if (sp->fts_compar && nitems > 1) + head = fts_sort(sp, head, nitems); + return (head); +} + +static u_short +internal_function +fts_stat (FTSOBJ *sp, FTSENTRY *p, int follow) +{ + FTSENTRY *t; + dev_t dev; + INO_T ino; + struct STAT *sbp, sb; + int saved_errno; + + /* If user needs stat info, stat buffer already allocated. */ + sbp = ISSET(FTS_NOSTAT) ? &sb : p->fts_statp; + +#if defined FTS_WHITEOUT && 0 + /* check for whiteout */ + if (p->fts_flags & FTS_ISW) { + if (sbp != &sb) { + memset(sbp, '\0', sizeof (*sbp)); + sbp->st_mode = S_IFWHT; + } + return (FTS_W); + } +#endif + + /* + * If doing a logical walk, or application requested FTS_FOLLOW, do + * a stat(2). If that fails, check for a non-existent symlink. If + * fail, set the errno from the stat call. + */ + if (ISSET(FTS_LOGICAL) || follow) { + if (STAT(p->fts_accpath, sbp)) { + saved_errno = errno; + if (!LSTAT(p->fts_accpath, sbp)) { + __set_errno (0); + return (FTS_SLNONE); + } + p->fts_errno = saved_errno; + goto err; + } + } else if (LSTAT(p->fts_accpath, sbp)) { + p->fts_errno = errno; +err: memset(sbp, 0, sizeof(struct STAT)); + return (FTS_NS); + } + + if (S_ISDIR(sbp->st_mode)) { + /* + * Set the device/inode. Used to find cycles and check for + * crossing mount points. Also remember the link count, used + * in fts_build to limit the number of stat calls. It is + * understood that these fields are only referenced if fts_info + * is set to FTS_D. + */ + dev = p->fts_dev = sbp->st_dev; + ino = p->fts_ino = sbp->st_ino; + p->fts_nlink = sbp->st_nlink; + + if (ISDOT(p->fts_name)) + return (FTS_DOT); + + /* + * Cycle detection is done by brute force when the directory + * is first encountered. If the tree gets deep enough or the + * number of symbolic links to directories is high enough, + * something faster might be worthwhile. + */ + for (t = p->fts_parent; + t->fts_level >= FTS_ROOTLEVEL; t = t->fts_parent) + if (ino == t->fts_ino && dev == t->fts_dev) { + p->fts_cycle = t; + return (FTS_DC); + } + return (FTS_D); + } + if (S_ISLNK(sbp->st_mode)) + return (FTS_SL); + if (S_ISREG(sbp->st_mode)) + return (FTS_F); + return (FTS_DEFAULT); +} + +static FTSENTRY * +internal_function +fts_sort (FTSOBJ *sp, FTSENTRY *head, int nitems) +{ + FTSENTRY **ap, *p; + + /* + * Construct an array of pointers to the structures and call qsort(3). + * Reassemble the array in the order returned by qsort. If unable to + * sort for memory reasons, return the directory entries in their + * current order. Allocate enough space for the current needs plus + * 40 so don't realloc one entry at a time. + */ + if (nitems > sp->fts_nitems) { + FTSENTRY **a; + + sp->fts_nitems = nitems + 40; + if ((a = realloc(sp->fts_array, + (size_t)(sp->fts_nitems * sizeof(FTSENTRY *)))) == NULL) { + free(sp->fts_array); + sp->fts_array = NULL; + sp->fts_nitems = 0; + return (head); + } + sp->fts_array = a; + } + for (ap = sp->fts_array, p = head; p; p = p->fts_link) + *ap++ = p; + qsort((void *)sp->fts_array, nitems, sizeof(FTSENTRY *), sp->fts_compar); + for (head = *(ap = sp->fts_array); --nitems; ++ap) + ap[0]->fts_link = ap[1]; + ap[0]->fts_link = NULL; + return (head); +} + +static FTSENTRY * +internal_function +fts_alloc (FTSOBJ *sp, const char *name, size_t namelen) +{ + FTSENTRY *p; + size_t len; + + /* + * The file name is a variable length array and no stat structure is + * necessary if the user has set the nostat bit. Allocate the FTSENT + * structure, the file name and the stat structure in one chunk, but + * be careful that the stat structure is reasonably aligned. Since the + * fts_name field is declared to be of size 1, the fts_name pointer is + * namelen + 2 before the first possible address of the stat structure. + */ + len = sizeof(FTSENTRY) + namelen; + if (!ISSET(FTS_NOSTAT)) + len += sizeof(struct STAT) + ALIGNBYTES; + if ((p = malloc(len)) == NULL) + return (NULL); + + /* Copy the name and guarantee NUL termination. */ + memmove(p->fts_name, name, namelen); + p->fts_name[namelen] = '\0'; + + if (!ISSET(FTS_NOSTAT)) + p->fts_statp = (struct STAT *)ALIGN(p->fts_name + namelen + 2); + p->fts_namelen = namelen; + p->fts_path = sp->fts_path; + p->fts_errno = 0; + p->fts_flags = 0; + p->fts_instr = FTS_NOINSTR; + p->fts_number = 0; + p->fts_pointer = NULL; + return (p); +} + +static void +internal_function +fts_lfree (FTSENTRY *head) +{ + FTSENTRY *p; + + /* Free a linked list of structures. */ + while ((p = head)) { + head = head->fts_link; + free(p); + } +} + +/* + * Allow essentially unlimited paths; find, rm, ls should all work on any tree. + * Most systems will allow creation of paths much longer than MAXPATHLEN, even + * though the kernel won't resolve them. Add the size (not just what's needed) + * plus 256 bytes so don't realloc the path 2 bytes at a time. + */ +static int +internal_function +fts_palloc (FTSOBJ *sp, size_t more) +{ + char *p; + + sp->fts_pathlen += more + 256; + /* + * Check for possible wraparound. In an FTS, fts_pathlen is + * a signed int but in an FTSENT it is an unsigned short. + * We limit fts_pathlen to USHRT_MAX to be safe in both cases. + */ + if (sp->fts_pathlen < 0 || sp->fts_pathlen >= USHRT_MAX) { + free(sp->fts_path); + sp->fts_path = NULL; + __set_errno (ENAMETOOLONG); + return (1); + } + p = realloc(sp->fts_path, sp->fts_pathlen); + if (p == NULL) { + free(sp->fts_path); + sp->fts_path = NULL; + return 1; + } + sp->fts_path = p; + return 0; +} + +/* + * When the path is realloc'd, have to fix all of the pointers in structures + * already returned. + */ +static void +internal_function +fts_padjust (FTSOBJ *sp, FTSENTRY *head) +{ + FTSENTRY *p; + char *addr = sp->fts_path; + +#define ADJUST(p) do { \ + if ((p)->fts_accpath != (p)->fts_name) { \ + (p)->fts_accpath = \ + (char *)addr + ((p)->fts_accpath - (p)->fts_path); \ + } \ + (p)->fts_path = addr; \ +} while (0) + /* Adjust the current set of children. */ + for (p = sp->fts_child; p; p = p->fts_link) + ADJUST(p); + + /* Adjust the rest of the tree, including the current level. */ + for (p = head; p->fts_level >= FTS_ROOTLEVEL;) { + ADJUST(p); + p = p->fts_link ? p->fts_link : p->fts_parent; + } +} + +static size_t +internal_function +fts_maxarglen (char * const *argv) +{ + size_t len, max; + + for (max = 0; *argv; ++argv) + if ((len = strlen(*argv)) > max) + max = len; + return (max + 1); +} + +/* + * Change to dir specified by fd or p->fts_accpath without getting + * tricked by someone changing the world out from underneath us. + * Assumes p->fts_dev and p->fts_ino are filled in. + */ +static int +internal_function +fts_safe_changedir (FTSOBJ *sp, FTSENTRY *p, int fd, const char *path) +{ + int ret, oerrno, newfd; + struct stat64 sb; + + newfd = fd; + if (ISSET(FTS_NOCHDIR)) + return (0); + if (fd < 0 && (newfd = __open(path, O_RDONLY, 0)) < 0) + return (-1); + if (__fxstat64(_STAT_VER, newfd, &sb)) { + ret = -1; + goto bail; + } + if (p->fts_dev != sb.st_dev || p->fts_ino != sb.st_ino) { + __set_errno (ENOENT); /* disinformation */ + ret = -1; + goto bail; + } + ret = __fchdir(newfd); +bail: + oerrno = errno; + if (fd < 0) + (void)__close(newfd); + __set_errno (oerrno); + return (ret); +} diff --git a/REORG.TODO/io/fts.h b/REORG.TODO/io/fts.h new file mode 100644 index 0000000000..ab15567001 --- /dev/null +++ b/REORG.TODO/io/fts.h @@ -0,0 +1,215 @@ +/* File tree traversal functions declarations. + Copyright (C) 1994-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +/* + * Copyright (c) 1989, 1993 + * The Regents of the University of California. 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. + * 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. + * + * 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. + * + * @(#)fts.h 8.3 (Berkeley) 8/14/94 + */ + +#ifndef _FTS_H +#define _FTS_H 1 + +#include <features.h> +#include <sys/types.h> + + +typedef struct { + struct _ftsent *fts_cur; /* current node */ + struct _ftsent *fts_child; /* linked list of children */ + struct _ftsent **fts_array; /* sort array */ + dev_t fts_dev; /* starting device # */ + char *fts_path; /* path for this descent */ + int fts_rfd; /* fd for root */ + int fts_pathlen; /* sizeof(path) */ + int fts_nitems; /* elements in the sort array */ + int (*fts_compar) (const void *, const void *); /* compare fn */ + +#define FTS_COMFOLLOW 0x0001 /* follow command line symlinks */ +#define FTS_LOGICAL 0x0002 /* logical walk */ +#define FTS_NOCHDIR 0x0004 /* don't change directories */ +#define FTS_NOSTAT 0x0008 /* don't get stat info */ +#define FTS_PHYSICAL 0x0010 /* physical walk */ +#define FTS_SEEDOT 0x0020 /* return dot and dot-dot */ +#define FTS_XDEV 0x0040 /* don't cross devices */ +#define FTS_WHITEOUT 0x0080 /* return whiteout information */ +#define FTS_OPTIONMASK 0x00ff /* valid user option mask */ + +#define FTS_NAMEONLY 0x0100 /* (private) child names only */ +#define FTS_STOP 0x0200 /* (private) unrecoverable error */ + int fts_options; /* fts_open options, global flags */ +} FTS; + +#ifdef __USE_LARGEFILE64 +typedef struct { + struct _ftsent64 *fts_cur; /* current node */ + struct _ftsent64 *fts_child; /* linked list of children */ + struct _ftsent64 **fts_array; /* sort array */ + dev_t fts_dev; /* starting device # */ + char *fts_path; /* path for this descent */ + int fts_rfd; /* fd for root */ + int fts_pathlen; /* sizeof(path) */ + int fts_nitems; /* elements in the sort array */ + int (*fts_compar) (const void *, const void *); /* compare fn */ + int fts_options; /* fts_open options, global flags */ +} FTS64; +#endif + +typedef struct _ftsent { + struct _ftsent *fts_cycle; /* cycle node */ + struct _ftsent *fts_parent; /* parent directory */ + struct _ftsent *fts_link; /* next file in directory */ + long fts_number; /* local numeric value */ + void *fts_pointer; /* local address value */ + char *fts_accpath; /* access path */ + char *fts_path; /* root path */ + int fts_errno; /* errno for this node */ + int fts_symfd; /* fd for symlink */ + unsigned short fts_pathlen; /* strlen(fts_path) */ + unsigned short fts_namelen; /* strlen(fts_name) */ + + ino_t fts_ino; /* inode */ + dev_t fts_dev; /* device */ + nlink_t fts_nlink; /* link count */ + +#define FTS_ROOTPARENTLEVEL -1 +#define FTS_ROOTLEVEL 0 + short fts_level; /* depth (-1 to N) */ + +#define FTS_D 1 /* preorder directory */ +#define FTS_DC 2 /* directory that causes cycles */ +#define FTS_DEFAULT 3 /* none of the above */ +#define FTS_DNR 4 /* unreadable directory */ +#define FTS_DOT 5 /* dot or dot-dot */ +#define FTS_DP 6 /* postorder directory */ +#define FTS_ERR 7 /* error; errno is set */ +#define FTS_F 8 /* regular file */ +#define FTS_INIT 9 /* initialized only */ +#define FTS_NS 10 /* stat(2) failed */ +#define FTS_NSOK 11 /* no stat(2) requested */ +#define FTS_SL 12 /* symbolic link */ +#define FTS_SLNONE 13 /* symbolic link without target */ +#define FTS_W 14 /* whiteout object */ + unsigned short fts_info; /* user flags for FTSENT structure */ + +#define FTS_DONTCHDIR 0x01 /* don't chdir .. to the parent */ +#define FTS_SYMFOLLOW 0x02 /* followed a symlink to get here */ + unsigned short fts_flags; /* private flags for FTSENT structure */ + +#define FTS_AGAIN 1 /* read node again */ +#define FTS_FOLLOW 2 /* follow symbolic link */ +#define FTS_NOINSTR 3 /* no instructions */ +#define FTS_SKIP 4 /* discard node */ + unsigned short fts_instr; /* fts_set() instructions */ + + struct stat *fts_statp; /* stat(2) information */ + char fts_name[1]; /* file name */ +} FTSENT; + +#ifdef __USE_LARGEFILE64 +typedef struct _ftsent64 { + struct _ftsent64 *fts_cycle; /* cycle node */ + struct _ftsent64 *fts_parent; /* parent directory */ + struct _ftsent64 *fts_link; /* next file in directory */ + long fts_number; /* local numeric value */ + void *fts_pointer; /* local address value */ + char *fts_accpath; /* access path */ + char *fts_path; /* root path */ + int fts_errno; /* errno for this node */ + int fts_symfd; /* fd for symlink */ + unsigned short fts_pathlen; /* strlen(fts_path) */ + unsigned short fts_namelen; /* strlen(fts_name) */ + + ino64_t fts_ino; /* inode */ + dev_t fts_dev; /* device */ + nlink_t fts_nlink; /* link count */ + + short fts_level; /* depth (-1 to N) */ + + unsigned short fts_info; /* user flags for FTSENT structure */ + + unsigned short fts_flags; /* private flags for FTSENT structure */ + + unsigned short fts_instr; /* fts_set() instructions */ + + struct stat64 *fts_statp; /* stat(2) information */ + char fts_name[1]; /* file name */ +} FTSENT64; +#endif + +__BEGIN_DECLS +#ifndef __USE_FILE_OFFSET64 +FTSENT *fts_children (FTS *, int); +int fts_close (FTS *); +FTS *fts_open (char * const *, int, + int (*)(const FTSENT **, const FTSENT **)); +FTSENT *fts_read (FTS *); +int fts_set (FTS *, FTSENT *, int) __THROW; +#else +# ifdef __REDIRECT +FTSENT *__REDIRECT (fts_children, (FTS *, int), fts64_children); +int __REDIRECT (fts_close, (FTS *), fts64_close); +FTS *__REDIRECT (fts_open, (char * const *, int, + int (*)(const FTSENT **, const FTSENT **)), + fts64_open); +FTSENT *__REDIRECT (fts_read, (FTS *), fts64_read); +int __REDIRECT_NTH (fts_set, (FTS *, FTSENT *, int), fts64_set); +# else +# define fts_children fts64_children +# define fts_close fts64_close +# define fts_open fts64_open +# define fts_read fts64_read +# define fts_set fts64_set +# endif +#endif +#ifdef __USE_LARGEFILE64 +FTSENT64 *fts64_children (FTS64 *, int); +int fts64_close (FTS64 *); +FTS64 *fts64_open (char * const *, int, + int (*)(const FTSENT64 **, const FTSENT64 **)); +FTSENT64 *fts64_read (FTS64 *); +int fts64_set (FTS64 *, FTSENT64 *, int) __THROW; +#endif +__END_DECLS + +#endif /* fts.h */ diff --git a/REORG.TODO/io/fts64.c b/REORG.TODO/io/fts64.c new file mode 100644 index 0000000000..5e623385f0 --- /dev/null +++ b/REORG.TODO/io/fts64.c @@ -0,0 +1,30 @@ +/* File tree traversal functions LFS version. + Copyright (C) 2015-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#define FTS_OPEN fts64_open +#define FTS_CLOSE fts64_close +#define FTS_READ fts64_read +#define FTS_SET fts64_set +#define FTS_CHILDREN fts64_children +#define FTSOBJ FTS64 +#define FTSENTRY FTSENT64 +#define INO_T ino64_t +#define STAT stat64 +#define LSTAT lstat64 + +#include "fts.c" diff --git a/REORG.TODO/io/ftw.c b/REORG.TODO/io/ftw.c new file mode 100644 index 0000000000..140a237746 --- /dev/null +++ b/REORG.TODO/io/ftw.c @@ -0,0 +1,867 @@ +/* File tree walker functions. + Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper <drepper@cygnus.com>, 1996. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#ifdef HAVE_CONFIG_H +# include <config.h> +#endif + +#if __GNUC__ +# define alloca __builtin_alloca +#else +# if HAVE_ALLOCA_H +# include <alloca.h> +# else +# ifdef _AIX + # pragma alloca +# else +char *alloca (); +# endif +# endif +#endif + +#ifdef _LIBC +# include <dirent.h> +# define NAMLEN(dirent) _D_EXACT_NAMLEN (dirent) +#else +# if HAVE_DIRENT_H +# include <dirent.h> +# define NAMLEN(dirent) strlen ((dirent)->d_name) +# else +# define dirent direct +# define NAMLEN(dirent) (dirent)->d_namlen +# if HAVE_SYS_NDIR_H +# include <sys/ndir.h> +# endif +# if HAVE_SYS_DIR_H +# include <sys/dir.h> +# endif +# if HAVE_NDIR_H +# include <ndir.h> +# endif +# endif +#endif + +#include <errno.h> +#include <fcntl.h> +#include <ftw.h> +#include <limits.h> +#include <search.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <not-cancel.h> +#include <sys/param.h> +#ifdef _LIBC +# include <include/sys/stat.h> +#else +# include <sys/stat.h> +#endif + +#if ! _LIBC && !HAVE_DECL_STPCPY && !defined stpcpy +char *stpcpy (); +#endif + +#if ! _LIBC && ! defined HAVE_MEMPCPY && ! defined mempcpy +/* Be CAREFUL that there are no side effects in N. */ +# define mempcpy(D, S, N) ((void *) ((char *) memcpy (D, S, N) + (N))) +#endif + +/* #define NDEBUG 1 */ +#include <assert.h> + +#ifndef _LIBC +# undef __chdir +# define __chdir chdir +# undef __closedir +# define __closedir closedir +# undef __fchdir +# define __fchdir fchdir +# undef __getcwd +# define __getcwd(P, N) xgetcwd () +extern char *xgetcwd (void); +# undef __mempcpy +# define __mempcpy mempcpy +# undef __opendir +# define __opendir opendir +# undef __readdir64 +# define __readdir64 readdir +# undef __stpcpy +# define __stpcpy stpcpy +# undef __tdestroy +# define __tdestroy tdestroy +# undef __tfind +# define __tfind tfind +# undef __tsearch +# define __tsearch tsearch +# undef internal_function +# define internal_function /* empty */ +# undef dirent64 +# define dirent64 dirent +# undef MAX +# define MAX(a, b) ((a) > (b) ? (a) : (b)) +#endif + +/* Arrange to make lstat calls go through the wrapper function + on systems with an lstat function that does not dereference symlinks + that are specified with a trailing slash. */ +#if ! _LIBC && ! LSTAT_FOLLOWS_SLASHED_SYMLINK +int rpl_lstat (const char *, struct stat *); +# undef lstat +# define lstat(Name, Stat_buf) rpl_lstat(Name, Stat_buf) +#endif + +#ifndef __set_errno +# define __set_errno(Val) errno = (Val) +#endif + +/* Support for the LFS API version. */ +#ifndef FTW_NAME +# define FTW_NAME ftw +# define NFTW_NAME nftw +# define NFTW_OLD_NAME __old_nftw +# define NFTW_NEW_NAME __new_nftw +# define INO_T ino_t +# define STAT stat +# ifdef _LIBC +# define LXSTAT __lxstat +# define XSTAT __xstat +# define FXSTATAT __fxstatat +# else +# define LXSTAT(V,f,sb) lstat (f,sb) +# define XSTAT(V,f,sb) stat (f,sb) +# define FXSTATAT(V,d,f,sb,m) fstatat (d, f, sb, m) +# endif +# define FTW_FUNC_T __ftw_func_t +# define NFTW_FUNC_T __nftw_func_t +#endif + +/* We define PATH_MAX if the system does not provide a definition. + This does not artificially limit any operation. PATH_MAX is simply + used as a guesstimate for the expected maximal path length. + Buffers will be enlarged if necessary. */ +#ifndef PATH_MAX +# define PATH_MAX 1024 +#endif + +struct dir_data +{ + DIR *stream; + int streamfd; + char *content; +}; + +struct known_object +{ + dev_t dev; + INO_T ino; +}; + +struct ftw_data +{ + /* Array with pointers to open directory streams. */ + struct dir_data **dirstreams; + size_t actdir; + size_t maxdir; + + /* Buffer containing name of currently processed object. */ + char *dirbuf; + size_t dirbufsize; + + /* Passed as fourth argument to `nftw' callback. The `base' member + tracks the content of the `dirbuf'. */ + struct FTW ftw; + + /* Flags passed to `nftw' function. 0 for `ftw'. */ + int flags; + + /* Conversion array for flag values. It is the identity mapping for + `nftw' calls, otherwise it maps the values to those known by + `ftw'. */ + const int *cvt_arr; + + /* Callback function. We always use the `nftw' form. */ + NFTW_FUNC_T func; + + /* Device of starting point. Needed for FTW_MOUNT. */ + dev_t dev; + + /* Data structure for keeping fingerprints of already processed + object. This is needed when not using FTW_PHYS. */ + void *known_objects; +}; + + +/* Internally we use the FTW_* constants used for `nftw'. When invoked + as `ftw', map each flag to the subset of values used by `ftw'. */ +static const int nftw_arr[] = +{ + FTW_F, FTW_D, FTW_DNR, FTW_NS, FTW_SL, FTW_DP, FTW_SLN +}; + +static const int ftw_arr[] = +{ + FTW_F, FTW_D, FTW_DNR, FTW_NS, FTW_F, FTW_D, FTW_NS +}; + + +/* Forward declarations of local functions. */ +static int ftw_dir (struct ftw_data *data, struct STAT *st, + struct dir_data *old_dir) internal_function; + + +static int +object_compare (const void *p1, const void *p2) +{ + /* We don't need a sophisticated and useful comparison. We are only + interested in equality. However, we must be careful not to + accidentally compare `holes' in the structure. */ + const struct known_object *kp1 = p1, *kp2 = p2; + int cmp1; + cmp1 = (kp1->ino > kp2->ino) - (kp1->ino < kp2->ino); + if (cmp1 != 0) + return cmp1; + return (kp1->dev > kp2->dev) - (kp1->dev < kp2->dev); +} + + +static int +add_object (struct ftw_data *data, struct STAT *st) +{ + struct known_object *newp = malloc (sizeof (struct known_object)); + if (newp == NULL) + return -1; + newp->dev = st->st_dev; + newp->ino = st->st_ino; + return __tsearch (newp, &data->known_objects, object_compare) ? 0 : -1; +} + + +static inline int +find_object (struct ftw_data *data, struct STAT *st) +{ + struct known_object obj; + obj.dev = st->st_dev; + obj.ino = st->st_ino; + return __tfind (&obj, &data->known_objects, object_compare) != NULL; +} + + +static inline int +__attribute ((always_inline)) +open_dir_stream (int *dfdp, struct ftw_data *data, struct dir_data *dirp) +{ + int result = 0; + + if (data->dirstreams[data->actdir] != NULL) + { + /* Oh, oh. We must close this stream. Get all remaining + entries and store them as a list in the `content' member of + the `struct dir_data' variable. */ + size_t bufsize = 1024; + char *buf = malloc (bufsize); + + if (buf == NULL) + result = -1; + else + { + DIR *st = data->dirstreams[data->actdir]->stream; + struct dirent64 *d; + size_t actsize = 0; + + while ((d = __readdir64 (st)) != NULL) + { + size_t this_len = NAMLEN (d); + if (actsize + this_len + 2 >= bufsize) + { + char *newp; + bufsize += MAX (1024, 2 * this_len); + newp = (char *) realloc (buf, bufsize); + if (newp == NULL) + { + /* No more memory. */ + int save_err = errno; + free (buf); + __set_errno (save_err); + return -1; + } + buf = newp; + } + + *((char *) __mempcpy (buf + actsize, d->d_name, this_len)) + = '\0'; + actsize += this_len + 1; + } + + /* Terminate the list with an additional NUL byte. */ + buf[actsize++] = '\0'; + + /* Shrink the buffer to what we actually need. */ + data->dirstreams[data->actdir]->content = realloc (buf, actsize); + if (data->dirstreams[data->actdir]->content == NULL) + { + int save_err = errno; + free (buf); + __set_errno (save_err); + result = -1; + } + else + { + __closedir (st); + data->dirstreams[data->actdir]->stream = NULL; + data->dirstreams[data->actdir]->streamfd = -1; + data->dirstreams[data->actdir] = NULL; + } + } + } + + /* Open the new stream. */ + if (result == 0) + { + assert (data->dirstreams[data->actdir] == NULL); + + if (dfdp != NULL && *dfdp != -1) + { + int fd = openat64_not_cancel_3 (*dfdp, data->dirbuf + data->ftw.base, + O_RDONLY | O_DIRECTORY | O_NDELAY); + dirp->stream = NULL; + if (fd != -1 && (dirp->stream = __fdopendir (fd)) == NULL) + close_not_cancel_no_status (fd); + } + else + { + const char *name; + + if (data->flags & FTW_CHDIR) + { + name = data->dirbuf + data->ftw.base; + if (name[0] == '\0') + name = "."; + } + else + name = data->dirbuf; + + dirp->stream = __opendir (name); + } + + if (dirp->stream == NULL) + result = -1; + else + { + dirp->streamfd = dirfd (dirp->stream); + dirp->content = NULL; + data->dirstreams[data->actdir] = dirp; + + if (++data->actdir == data->maxdir) + data->actdir = 0; + } + } + + return result; +} + + +static int +internal_function +process_entry (struct ftw_data *data, struct dir_data *dir, const char *name, + size_t namlen, int d_type) +{ + struct STAT st; + int result = 0; + int flag = 0; + size_t new_buflen; + + if (name[0] == '.' && (name[1] == '\0' + || (name[1] == '.' && name[2] == '\0'))) + /* Don't process the "." and ".." entries. */ + return 0; + + new_buflen = data->ftw.base + namlen + 2; + if (data->dirbufsize < new_buflen) + { + /* Enlarge the buffer. */ + char *newp; + + data->dirbufsize = 2 * new_buflen; + newp = (char *) realloc (data->dirbuf, data->dirbufsize); + if (newp == NULL) + return -1; + data->dirbuf = newp; + } + + *((char *) __mempcpy (data->dirbuf + data->ftw.base, name, namlen)) = '\0'; + + int statres; + if (dir->streamfd != -1) + statres = FXSTATAT (_STAT_VER, dir->streamfd, name, &st, + (data->flags & FTW_PHYS) ? AT_SYMLINK_NOFOLLOW : 0); + else + { + if ((data->flags & FTW_CHDIR) == 0) + name = data->dirbuf; + + statres = ((data->flags & FTW_PHYS) + ? LXSTAT (_STAT_VER, name, &st) + : XSTAT (_STAT_VER, name, &st)); + } + + if (statres < 0) + { + if (errno != EACCES && errno != ENOENT) + result = -1; + else if (data->flags & FTW_PHYS) + flag = FTW_NS; + else if (d_type == DT_LNK) + flag = FTW_SLN; + else + { + if (dir->streamfd != -1) + statres = FXSTATAT (_STAT_VER, dir->streamfd, name, &st, + AT_SYMLINK_NOFOLLOW); + else + statres = LXSTAT (_STAT_VER, name, &st); + if (statres == 0 && S_ISLNK (st.st_mode)) + flag = FTW_SLN; + else + flag = FTW_NS; + } + } + else + { + if (S_ISDIR (st.st_mode)) + flag = FTW_D; + else if (S_ISLNK (st.st_mode)) + flag = FTW_SL; + else + flag = FTW_F; + } + + if (result == 0 + && (flag == FTW_NS + || !(data->flags & FTW_MOUNT) || st.st_dev == data->dev)) + { + if (flag == FTW_D) + { + if ((data->flags & FTW_PHYS) + || (!find_object (data, &st) + /* Remember the object. */ + && (result = add_object (data, &st)) == 0)) + result = ftw_dir (data, &st, dir); + } + else + result = (*data->func) (data->dirbuf, &st, data->cvt_arr[flag], + &data->ftw); + } + + if ((data->flags & FTW_ACTIONRETVAL) && result == FTW_SKIP_SUBTREE) + result = 0; + + return result; +} + + +static int +__attribute ((noinline)) +internal_function +ftw_dir (struct ftw_data *data, struct STAT *st, struct dir_data *old_dir) +{ + struct dir_data dir; + struct dirent64 *d; + int previous_base = data->ftw.base; + int result; + char *startp; + + /* Open the stream for this directory. This might require that + another stream has to be closed. */ + result = open_dir_stream (old_dir == NULL ? NULL : &old_dir->streamfd, + data, &dir); + if (result != 0) + { + if (errno == EACCES) + /* We cannot read the directory. Signal this with a special flag. */ + result = (*data->func) (data->dirbuf, st, FTW_DNR, &data->ftw); + + return result; + } + + /* First, report the directory (if not depth-first). */ + if (!(data->flags & FTW_DEPTH)) + { + result = (*data->func) (data->dirbuf, st, FTW_D, &data->ftw); + if (result != 0) + { + int save_err; +fail: + save_err = errno; + __closedir (dir.stream); + dir.streamfd = -1; + __set_errno (save_err); + + if (data->actdir-- == 0) + data->actdir = data->maxdir - 1; + data->dirstreams[data->actdir] = NULL; + return result; + } + } + + /* If necessary, change to this directory. */ + if (data->flags & FTW_CHDIR) + { + if (__fchdir (dirfd (dir.stream)) < 0) + { + result = -1; + goto fail; + } + } + + /* Next, update the `struct FTW' information. */ + ++data->ftw.level; + startp = __rawmemchr (data->dirbuf, '\0'); + /* There always must be a directory name. */ + assert (startp != data->dirbuf); + if (startp[-1] != '/') + *startp++ = '/'; + data->ftw.base = startp - data->dirbuf; + + while (dir.stream != NULL && (d = __readdir64 (dir.stream)) != NULL) + { + int d_type = DT_UNKNOWN; +#ifdef _DIRENT_HAVE_D_TYPE + d_type = d->d_type; +#endif + result = process_entry (data, &dir, d->d_name, NAMLEN (d), d_type); + if (result != 0) + break; + } + + if (dir.stream != NULL) + { + /* The stream is still open. I.e., we did not need more + descriptors. Simply close the stream now. */ + int save_err = errno; + + assert (dir.content == NULL); + + __closedir (dir.stream); + dir.streamfd = -1; + __set_errno (save_err); + + if (data->actdir-- == 0) + data->actdir = data->maxdir - 1; + data->dirstreams[data->actdir] = NULL; + } + else + { + int save_err; + char *runp = dir.content; + + while (result == 0 && *runp != '\0') + { + char *endp = strchr (runp, '\0'); + + // XXX Should store the d_type values as well?! + result = process_entry (data, &dir, runp, endp - runp, DT_UNKNOWN); + + runp = endp + 1; + } + + save_err = errno; + free (dir.content); + __set_errno (save_err); + } + + if ((data->flags & FTW_ACTIONRETVAL) && result == FTW_SKIP_SIBLINGS) + result = 0; + + /* Prepare the return, revert the `struct FTW' information. */ + data->dirbuf[data->ftw.base - 1] = '\0'; + --data->ftw.level; + data->ftw.base = previous_base; + + /* Finally, if we process depth-first report the directory. */ + if (result == 0 && (data->flags & FTW_DEPTH)) + result = (*data->func) (data->dirbuf, st, FTW_DP, &data->ftw); + + if (old_dir + && (data->flags & FTW_CHDIR) + && (result == 0 + || ((data->flags & FTW_ACTIONRETVAL) + && (result != -1 && result != FTW_STOP)))) + { + /* Change back to the parent directory. */ + int done = 0; + if (old_dir->stream != NULL) + if (__fchdir (dirfd (old_dir->stream)) == 0) + done = 1; + + if (!done) + { + if (data->ftw.base == 1) + { + if (__chdir ("/") < 0) + result = -1; + } + else + if (__chdir ("..") < 0) + result = -1; + } + } + + return result; +} + + +static int +__attribute ((noinline)) +internal_function +ftw_startup (const char *dir, int is_nftw, void *func, int descriptors, + int flags) +{ + struct ftw_data data; + struct STAT st; + int result = 0; + int save_err; + int cwdfd = -1; + char *cwd = NULL; + char *cp; + + /* First make sure the parameters are reasonable. */ + if (dir[0] == '\0') + { + __set_errno (ENOENT); + return -1; + } + + data.maxdir = descriptors < 1 ? 1 : descriptors; + data.actdir = 0; + data.dirstreams = (struct dir_data **) alloca (data.maxdir + * sizeof (struct dir_data *)); + memset (data.dirstreams, '\0', data.maxdir * sizeof (struct dir_data *)); + + /* PATH_MAX is always defined when we get here. */ + data.dirbufsize = MAX (2 * strlen (dir), PATH_MAX); + data.dirbuf = (char *) malloc (data.dirbufsize); + if (data.dirbuf == NULL) + return -1; + cp = __stpcpy (data.dirbuf, dir); + /* Strip trailing slashes. */ + while (cp > data.dirbuf + 1 && cp[-1] == '/') + --cp; + *cp = '\0'; + + data.ftw.level = 0; + + /* Find basename. */ + while (cp > data.dirbuf && cp[-1] != '/') + --cp; + data.ftw.base = cp - data.dirbuf; + + data.flags = flags; + + /* This assignment might seem to be strange but it is what we want. + The trick is that the first three arguments to the `ftw' and + `nftw' callback functions are equal. Therefore we can call in + every case the callback using the format of the `nftw' version + and get the correct result since the stack layout for a function + call in C allows this. */ + data.func = (NFTW_FUNC_T) func; + + /* Since we internally use the complete set of FTW_* values we need + to reduce the value range before calling a `ftw' callback. */ + data.cvt_arr = is_nftw ? nftw_arr : ftw_arr; + + /* No object known so far. */ + data.known_objects = NULL; + + /* Now go to the directory containing the initial file/directory. */ + if (flags & FTW_CHDIR) + { + /* We have to be able to go back to the current working + directory. The best way to do this is to use a file + descriptor. */ + cwdfd = __open (".", O_RDONLY | O_DIRECTORY); + if (cwdfd == -1) + { + /* Try getting the directory name. This can be needed if + the current directory is executable but not readable. */ + if (errno == EACCES) + /* GNU extension ahead. */ + cwd = __getcwd (NULL, 0); + + if (cwd == NULL) + goto out_fail; + } + else if (data.maxdir > 1) + /* Account for the file descriptor we use here. */ + --data.maxdir; + + if (data.ftw.base > 0) + { + /* Change to the directory the file is in. In data.dirbuf + we have a writable copy of the file name. Just NUL + terminate it for now and change the directory. */ + if (data.ftw.base == 1) + /* I.e., the file is in the root directory. */ + result = __chdir ("/"); + else + { + char ch = data.dirbuf[data.ftw.base - 1]; + data.dirbuf[data.ftw.base - 1] = '\0'; + result = __chdir (data.dirbuf); + data.dirbuf[data.ftw.base - 1] = ch; + } + } + } + + /* Get stat info for start directory. */ + if (result == 0) + { + const char *name; + + if (data.flags & FTW_CHDIR) + { + name = data.dirbuf + data.ftw.base; + if (name[0] == '\0') + name = "."; + } + else + name = data.dirbuf; + + if (((flags & FTW_PHYS) + ? LXSTAT (_STAT_VER, name, &st) + : XSTAT (_STAT_VER, name, &st)) < 0) + { + if (!(flags & FTW_PHYS) + && errno == ENOENT + && LXSTAT (_STAT_VER, name, &st) == 0 + && S_ISLNK (st.st_mode)) + result = (*data.func) (data.dirbuf, &st, data.cvt_arr[FTW_SLN], + &data.ftw); + else + /* No need to call the callback since we cannot say anything + about the object. */ + result = -1; + } + else + { + if (S_ISDIR (st.st_mode)) + { + /* Remember the device of the initial directory in case + FTW_MOUNT is given. */ + data.dev = st.st_dev; + + /* We know this directory now. */ + if (!(flags & FTW_PHYS)) + result = add_object (&data, &st); + + if (result == 0) + result = ftw_dir (&data, &st, NULL); + } + else + { + int flag = S_ISLNK (st.st_mode) ? FTW_SL : FTW_F; + + result = (*data.func) (data.dirbuf, &st, data.cvt_arr[flag], + &data.ftw); + } + } + + if ((flags & FTW_ACTIONRETVAL) + && (result == FTW_SKIP_SUBTREE || result == FTW_SKIP_SIBLINGS)) + result = 0; + } + + /* Return to the start directory (if necessary). */ + if (cwdfd != -1) + { + int save_err = errno; + __fchdir (cwdfd); + close_not_cancel_no_status (cwdfd); + __set_errno (save_err); + } + else if (cwd != NULL) + { + int save_err = errno; + __chdir (cwd); + free (cwd); + __set_errno (save_err); + } + + /* Free all memory. */ + out_fail: + save_err = errno; + __tdestroy (data.known_objects, free); + free (data.dirbuf); + __set_errno (save_err); + + return result; +} + + + +/* Entry points. */ + +int +FTW_NAME (const char *path, FTW_FUNC_T func, int descriptors) +{ + return ftw_startup (path, 0, func, descriptors, 0); +} + +#ifndef _LIBC +int +NFTW_NAME (const char *path, NFTW_FUNC_T func, int descriptors, int flags) +{ + return ftw_startup (path, 1, func, descriptors, flags); +} +#else + +# include <shlib-compat.h> + +int NFTW_NEW_NAME (const char *, NFTW_FUNC_T, int, int); + +int +NFTW_NEW_NAME (const char *path, NFTW_FUNC_T func, int descriptors, int flags) +{ + if (flags + & ~(FTW_PHYS | FTW_MOUNT | FTW_CHDIR | FTW_DEPTH | FTW_ACTIONRETVAL)) + { + __set_errno (EINVAL); + return -1; + } + return ftw_startup (path, 1, func, descriptors, flags); +} + +versioned_symbol (libc, NFTW_NEW_NAME, NFTW_NAME, GLIBC_2_3_3); + +# if SHLIB_COMPAT(libc, GLIBC_2_1, GLIBC_2_3_3) + +/* Older nftw* version just ignored all unknown flags. */ + +int NFTW_OLD_NAME (const char *, NFTW_FUNC_T, int, int); + +int +attribute_compat_text_section +NFTW_OLD_NAME (const char *path, NFTW_FUNC_T func, int descriptors, int flags) +{ + flags &= (FTW_PHYS | FTW_MOUNT | FTW_CHDIR | FTW_DEPTH); + return ftw_startup (path, 1, func, descriptors, flags); +} + +compat_symbol (libc, NFTW_OLD_NAME, NFTW_NAME, GLIBC_2_1); +# endif +#endif diff --git a/REORG.TODO/io/ftw.h b/REORG.TODO/io/ftw.h new file mode 100644 index 0000000000..842931b8ff --- /dev/null +++ b/REORG.TODO/io/ftw.h @@ -0,0 +1,177 @@ +/* Copyright (C) 1992-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +/* + * X/Open Portability Guide 4.2: ftw.h + */ + +#ifndef _FTW_H +#define _FTW_H 1 + +#include <features.h> + +#include <sys/types.h> +#include <sys/stat.h> + + +__BEGIN_DECLS + +/* Values for the FLAG argument to the user function passed to `ftw' + and 'nftw'. */ +enum +{ + FTW_F, /* Regular file. */ +#define FTW_F FTW_F + FTW_D, /* Directory. */ +#define FTW_D FTW_D + FTW_DNR, /* Unreadable directory. */ +#define FTW_DNR FTW_DNR + FTW_NS, /* Unstatable file. */ +#define FTW_NS FTW_NS + +#if defined __USE_MISC || defined __USE_XOPEN_EXTENDED + + FTW_SL, /* Symbolic link. */ +# define FTW_SL FTW_SL +#endif + +#ifdef __USE_XOPEN_EXTENDED +/* These flags are only passed from the `nftw' function. */ + FTW_DP, /* Directory, all subdirs have been visited. */ +# define FTW_DP FTW_DP + FTW_SLN /* Symbolic link naming non-existing file. */ +# define FTW_SLN FTW_SLN + +#endif /* extended X/Open */ +}; + + +#ifdef __USE_XOPEN_EXTENDED +/* Flags for fourth argument of `nftw'. */ +enum +{ + FTW_PHYS = 1, /* Perform physical walk, ignore symlinks. */ +# define FTW_PHYS FTW_PHYS + FTW_MOUNT = 2, /* Report only files on same file system as the + argument. */ +# define FTW_MOUNT FTW_MOUNT + FTW_CHDIR = 4, /* Change to current directory while processing it. */ +# define FTW_CHDIR FTW_CHDIR + FTW_DEPTH = 8 /* Report files in directory before directory itself.*/ +# define FTW_DEPTH FTW_DEPTH +# ifdef __USE_GNU + , + FTW_ACTIONRETVAL = 16 /* Assume callback to return FTW_* values instead of + zero to continue and non-zero to terminate. */ +# define FTW_ACTIONRETVAL FTW_ACTIONRETVAL +# endif +}; + +#ifdef __USE_GNU +/* Return values from callback functions. */ +enum +{ + FTW_CONTINUE = 0, /* Continue with next sibling or for FTW_D with the + first child. */ +# define FTW_CONTINUE FTW_CONTINUE + FTW_STOP = 1, /* Return from `ftw' or `nftw' with FTW_STOP as return + value. */ +# define FTW_STOP FTW_STOP + FTW_SKIP_SUBTREE = 2, /* Only meaningful for FTW_D: Don't walk through the + subtree, instead just continue with its next + sibling. */ +# define FTW_SKIP_SUBTREE FTW_SKIP_SUBTREE + FTW_SKIP_SIBLINGS = 3,/* Continue with FTW_DP callback for current directory + (if FTW_DEPTH) and then its siblings. */ +# define FTW_SKIP_SIBLINGS FTW_SKIP_SIBLINGS +}; +#endif + +/* Structure used for fourth argument to callback function for `nftw'. */ +struct FTW + { + int base; + int level; + }; +#endif /* extended X/Open */ + + +/* Convenient types for callback functions. */ +typedef int (*__ftw_func_t) (const char *__filename, + const struct stat *__status, int __flag); +#ifdef __USE_LARGEFILE64 +typedef int (*__ftw64_func_t) (const char *__filename, + const struct stat64 *__status, int __flag); +#endif +#ifdef __USE_XOPEN_EXTENDED +typedef int (*__nftw_func_t) (const char *__filename, + const struct stat *__status, int __flag, + struct FTW *__info); +# ifdef __USE_LARGEFILE64 +typedef int (*__nftw64_func_t) (const char *__filename, + const struct stat64 *__status, + int __flag, struct FTW *__info); +# endif +#endif + +/* Call a function on every element in a directory tree. + + This function is a possible cancellation point and therefore not + marked with __THROW. */ +#ifndef __USE_FILE_OFFSET64 +extern int ftw (const char *__dir, __ftw_func_t __func, int __descriptors) + __nonnull ((1, 2)); +#else +# ifdef __REDIRECT +extern int __REDIRECT (ftw, (const char *__dir, __ftw_func_t __func, + int __descriptors), ftw64) __nonnull ((1, 2)); +# else +# define ftw ftw64 +# endif +#endif +#ifdef __USE_LARGEFILE64 +extern int ftw64 (const char *__dir, __ftw64_func_t __func, + int __descriptors) __nonnull ((1, 2)); +#endif + +#ifdef __USE_XOPEN_EXTENDED +/* Call a function on every element in a directory tree. FLAG allows + to specify the behaviour more detailed. + + This function is a possible cancellation point and therefore not + marked with __THROW. */ +# ifndef __USE_FILE_OFFSET64 +extern int nftw (const char *__dir, __nftw_func_t __func, int __descriptors, + int __flag) __nonnull ((1, 2)); +# else +# ifdef __REDIRECT +extern int __REDIRECT (nftw, (const char *__dir, __nftw_func_t __func, + int __descriptors, int __flag), nftw64) + __nonnull ((1, 2)); +# else +# define nftw nftw64 +# endif +# endif +# ifdef __USE_LARGEFILE64 +extern int nftw64 (const char *__dir, __nftw64_func_t __func, + int __descriptors, int __flag) __nonnull ((1, 2)); +# endif +#endif + +__END_DECLS + +#endif /* ftw.h */ diff --git a/REORG.TODO/io/ftw64.c b/REORG.TODO/io/ftw64.c new file mode 100644 index 0000000000..4df9bd822a --- /dev/null +++ b/REORG.TODO/io/ftw64.c @@ -0,0 +1,32 @@ +/* File tree walker functions. LFS version. + Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper <drepper@cygnus.com>, 1996. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#define FTW_NAME ftw64 +#define NFTW_NAME nftw64 +#define NFTW_OLD_NAME __old_nftw64 +#define NFTW_NEW_NAME __new_nftw64 +#define INO_T ino64_t +#define STAT stat64 +#define LXSTAT __lxstat64 +#define XSTAT __xstat64 +#define FXSTATAT __fxstatat64 +#define FTW_FUNC_T __ftw64_func_t +#define NFTW_FUNC_T __nftw64_func_t + +#include "ftw.c" diff --git a/REORG.TODO/io/ftwtest-sh b/REORG.TODO/io/ftwtest-sh new file mode 100644 index 0000000000..ac9cf1c6f4 --- /dev/null +++ b/REORG.TODO/io/ftwtest-sh @@ -0,0 +1,301 @@ +#!/bin/sh +# Test for nftw(3). +# Copyright (C) 1997-2017 Free Software Foundation, Inc. +# This file is part of the GNU C Library. + +# The GNU C Library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. + +# The GNU C Library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. + +# You should have received a copy of the GNU Lesser General Public +# License along with the GNU C Library; if not, see +# <http://www.gnu.org/licenses/>. + +set -e + +# The common objpfx, used to find libraries and the dynamic loader. +objpfx=$1 + +# We expect one parameter which is the test program. This must understand +# a number options: +# --phys use the FTW_PHYS flag +# --chdir use the FTW_CHDIR and print the current directory +# in the callback +# --depth use the FTW_DEPTH flag +# --early-exit print file@2 item only and return non-zero from the +# callback when it is seen +testprogram=$2 + +# We cannot test this as root. +if test `id | sed "s/uid=\([0-9]*\).*/\1/"` = 0; then + exit 0 +fi + +# Since we use `sort' we must make sure to use the same locale everywhere. +LC_ALL=C +export LC_ALL + +# First create our scenario: +tmp=${objpfx}io +tmpdir=$tmp/ftwtest.d + +trap 'chmod -fR a+x $tmpdir; rm -fr $tmpdir $testout' 0 1 2 3 15 + +if test -d $tmpdir; then + chmod -fR a+x $tmpdir + rm -fr $tmpdir +fi +mkdir $tmpdir +mkdir $tmpdir/foo +mkdir $tmpdir/bar +echo > $tmpdir/baz +mkdir $tmpdir/foo/lvl1 +echo > $tmpdir/foo/lvl1/file@1 +mkdir $tmpdir/foo/lvl1/lvl2 +echo > $tmpdir/foo/lvl1/lvl2/file@2 +mkdir $tmpdir/foo/lvl1/lvl2/lvl3 +echo > $tmpdir/foo/lvl1/lvl2/lvl3/file@3 +ln -s $tmpdir $tmpdir/foo/lvl1/lvl2/lvl3/link@3 +ln -s $tmpdir/foo/lvl1/lvl2 $tmpdir/foo/lvl1/lvl2/link@2 +ln -s $tmpdir/foo/lvl1/lvl2/lvl3/lvl4 $tmpdir/foo/lvl1/link@1 +echo > $tmpdir/bar/xo +chmod a-x,a+r $tmpdir/bar + +testout=$tmp/ftwtest-tmp.out + +$testprogram $tmpdir | + sort > $testout + +cat <<EOF | cmp $testout - || exit 1 +base = "$tmp/", file = "ftwtest.d", flag = FTW_D, level = 0 +base = "$tmp/ftwtest.d/", file = "bar", flag = FTW_D, level = 1 +base = "$tmp/ftwtest.d/", file = "baz", flag = FTW_F, level = 1 +base = "$tmp/ftwtest.d/", file = "foo", flag = FTW_D, level = 1 +base = "$tmp/ftwtest.d/bar/", file = "xo", flag = FTW_NS, level = 2 +base = "$tmp/ftwtest.d/foo/", file = "lvl1", flag = FTW_D, level = 2 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "file@1", flag = FTW_F, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "link@1", flag = FTW_SLN, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "lvl2", flag = FTW_D, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "file@2", flag = FTW_F, level = 4 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "lvl3", flag = FTW_D, level = 4 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/lvl3/", file = "file@3", flag = FTW_F, level = 5 +EOF +rm $testout + +$testprogram --depth $tmpdir | + sort > $testout + +cat <<EOF | cmp $testout - || exit 1 +base = "$tmp/", file = "ftwtest.d", flag = FTW_DP, level = 0 +base = "$tmp/ftwtest.d/", file = "bar", flag = FTW_DP, level = 1 +base = "$tmp/ftwtest.d/", file = "baz", flag = FTW_F, level = 1 +base = "$tmp/ftwtest.d/", file = "foo", flag = FTW_DP, level = 1 +base = "$tmp/ftwtest.d/bar/", file = "xo", flag = FTW_NS, level = 2 +base = "$tmp/ftwtest.d/foo/", file = "lvl1", flag = FTW_DP, level = 2 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "file@1", flag = FTW_F, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "link@1", flag = FTW_SLN, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "lvl2", flag = FTW_DP, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "file@2", flag = FTW_F, level = 4 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "lvl3", flag = FTW_DP, level = 4 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/lvl3/", file = "file@3", flag = FTW_F, level = 5 +EOF +rm $testout + +$testprogram --phys $tmpdir | + sort > $testout + +cat <<EOF | cmp $testout - || exit 1 +base = "$tmp/", file = "ftwtest.d", flag = FTW_D, level = 0 +base = "$tmp/ftwtest.d/", file = "bar", flag = FTW_D, level = 1 +base = "$tmp/ftwtest.d/", file = "baz", flag = FTW_F, level = 1 +base = "$tmp/ftwtest.d/", file = "foo", flag = FTW_D, level = 1 +base = "$tmp/ftwtest.d/bar/", file = "xo", flag = FTW_NS, level = 2 +base = "$tmp/ftwtest.d/foo/", file = "lvl1", flag = FTW_D, level = 2 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "file@1", flag = FTW_F, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "link@1", flag = FTW_SL, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "lvl2", flag = FTW_D, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "file@2", flag = FTW_F, level = 4 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "link@2", flag = FTW_SL, level = 4 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "lvl3", flag = FTW_D, level = 4 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/lvl3/", file = "file@3", flag = FTW_F, level = 5 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/lvl3/", file = "link@3", flag = FTW_SL, level = 5 +EOF +rm $testout + +# For the next test everything must be readable. +chmod -fR a+x $tmpdir + +$testprogram --chdir $tmpdir | + sort > $testout + +# perhaps $tmp involves some symlinks... +tmpreal=`cd $tmp; pwd -P 2>/dev/null` + +cat <<EOF | cmp $testout - || exit 1 +base = "$tmp/", file = "ftwtest.d", flag = FTW_D, cwd = $tmpreal, level = 0 +base = "$tmp/ftwtest.d/", file = "bar", flag = FTW_D, cwd = $tmpreal/ftwtest.d, level = 1 +base = "$tmp/ftwtest.d/", file = "baz", flag = FTW_F, cwd = $tmpreal/ftwtest.d, level = 1 +base = "$tmp/ftwtest.d/", file = "foo", flag = FTW_D, cwd = $tmpreal/ftwtest.d, level = 1 +base = "$tmp/ftwtest.d/bar/", file = "xo", flag = FTW_F, cwd = $tmpreal/ftwtest.d/bar, level = 2 +base = "$tmp/ftwtest.d/foo/", file = "lvl1", flag = FTW_D, cwd = $tmpreal/ftwtest.d/foo, level = 2 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "file@1", flag = FTW_F, cwd = $tmpreal/ftwtest.d/foo/lvl1, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "link@1", flag = FTW_SLN, cwd = $tmpreal/ftwtest.d/foo/lvl1, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "lvl2", flag = FTW_D, cwd = $tmpreal/ftwtest.d/foo/lvl1, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "file@2", flag = FTW_F, cwd = $tmpreal/ftwtest.d/foo/lvl1/lvl2, level = 4 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "lvl3", flag = FTW_D, cwd = $tmpreal/ftwtest.d/foo/lvl1/lvl2, level = 4 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/lvl3/", file = "file@3", flag = FTW_F, cwd = $tmpreal/ftwtest.d/foo/lvl1/lvl2/lvl3, level = 5 +EOF +rm $testout + +curwd=`pwd -P 2>/dev/null` +cd "$tmp" +$testprogram --chdir ftwtest.d | + sort > $testout +cd "$curwd" + +cat <<EOF | diff -u $testout - || exit 1 +base = "", file = "ftwtest.d", flag = FTW_D, cwd = $tmpreal, level = 0 +base = "ftwtest.d/", file = "bar", flag = FTW_D, cwd = $tmpreal/ftwtest.d, level = 1 +base = "ftwtest.d/", file = "baz", flag = FTW_F, cwd = $tmpreal/ftwtest.d, level = 1 +base = "ftwtest.d/", file = "foo", flag = FTW_D, cwd = $tmpreal/ftwtest.d, level = 1 +base = "ftwtest.d/bar/", file = "xo", flag = FTW_F, cwd = $tmpreal/ftwtest.d/bar, level = 2 +base = "ftwtest.d/foo/", file = "lvl1", flag = FTW_D, cwd = $tmpreal/ftwtest.d/foo, level = 2 +base = "ftwtest.d/foo/lvl1/", file = "file@1", flag = FTW_F, cwd = $tmpreal/ftwtest.d/foo/lvl1, level = 3 +base = "ftwtest.d/foo/lvl1/", file = "link@1", flag = FTW_SLN, cwd = $tmpreal/ftwtest.d/foo/lvl1, level = 3 +base = "ftwtest.d/foo/lvl1/", file = "lvl2", flag = FTW_D, cwd = $tmpreal/ftwtest.d/foo/lvl1, level = 3 +base = "ftwtest.d/foo/lvl1/lvl2/", file = "file@2", flag = FTW_F, cwd = $tmpreal/ftwtest.d/foo/lvl1/lvl2, level = 4 +base = "ftwtest.d/foo/lvl1/lvl2/", file = "lvl3", flag = FTW_D, cwd = $tmpreal/ftwtest.d/foo/lvl1/lvl2, level = 4 +base = "ftwtest.d/foo/lvl1/lvl2/lvl3/", file = "file@3", flag = FTW_F, cwd = $tmpreal/ftwtest.d/foo/lvl1/lvl2/lvl3, level = 5 +EOF +rm $testout + +curwd=`pwd -P` +cd "$tmp" +$testprogram --chdir ftwtest.d/. | + sort > $testout +cd "$curwd" + +cat <<EOF | diff -u $testout - || exit 1 +base = "ftwtest.d/", file = ".", flag = FTW_D, cwd = $tmpreal/ftwtest.d, level = 0 +base = "ftwtest.d/./", file = "bar", flag = FTW_D, cwd = $tmpreal/ftwtest.d, level = 1 +base = "ftwtest.d/./", file = "baz", flag = FTW_F, cwd = $tmpreal/ftwtest.d, level = 1 +base = "ftwtest.d/./", file = "foo", flag = FTW_D, cwd = $tmpreal/ftwtest.d, level = 1 +base = "ftwtest.d/./bar/", file = "xo", flag = FTW_F, cwd = $tmpreal/ftwtest.d/bar, level = 2 +base = "ftwtest.d/./foo/", file = "lvl1", flag = FTW_D, cwd = $tmpreal/ftwtest.d/foo, level = 2 +base = "ftwtest.d/./foo/lvl1/", file = "file@1", flag = FTW_F, cwd = $tmpreal/ftwtest.d/foo/lvl1, level = 3 +base = "ftwtest.d/./foo/lvl1/", file = "link@1", flag = FTW_SLN, cwd = $tmpreal/ftwtest.d/foo/lvl1, level = 3 +base = "ftwtest.d/./foo/lvl1/", file = "lvl2", flag = FTW_D, cwd = $tmpreal/ftwtest.d/foo/lvl1, level = 3 +base = "ftwtest.d/./foo/lvl1/lvl2/", file = "file@2", flag = FTW_F, cwd = $tmpreal/ftwtest.d/foo/lvl1/lvl2, level = 4 +base = "ftwtest.d/./foo/lvl1/lvl2/", file = "lvl3", flag = FTW_D, cwd = $tmpreal/ftwtest.d/foo/lvl1/lvl2, level = 4 +base = "ftwtest.d/./foo/lvl1/lvl2/lvl3/", file = "file@3", flag = FTW_F, cwd = $tmpreal/ftwtest.d/foo/lvl1/lvl2/lvl3, level = 5 +EOF +rm $testout + +curwd=`pwd -P 2>/dev/null` +cd "$tmp" +$testprogram --chdir ftwtest.d/foo/lvl1/link@1 | + sort > $testout +cd "$curwd" + +cat <<EOF | diff -u $testout - || exit 1 +base = "ftwtest.d/foo/lvl1/", file = "link@1", flag = FTW_SLN, cwd = $tmpreal/ftwtest.d/foo/lvl1, level = 0 +EOF +rm $testout + +$testprogram --early-exit $tmpdir | + sort > $testout + +cat <<EOF | cmp $testout - || exit 1 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "file@2", flag = FTW_F, level = 4 +succeeded +EOF +rm $testout + +mkdir $tmpdir/foo/lvl1b +echo > $tmpdir/foo/lvl1b/file@1b +echo > $tmpdir/foo/lvl1b/file2@1b +echo > $tmpdir/foo/lvl1b/file3@1b + +$testprogram --skip-subtree=lvl1 $tmpdir | + sort > $testout + +cat <<EOF | diff -u $testout - || exit 1 +base = "$tmp/", file = "ftwtest.d", flag = FTW_D, level = 0 +base = "$tmp/ftwtest.d/", file = "bar", flag = FTW_D, level = 1 +base = "$tmp/ftwtest.d/", file = "baz", flag = FTW_F, level = 1 +base = "$tmp/ftwtest.d/", file = "foo", flag = FTW_D, level = 1 +base = "$tmp/ftwtest.d/bar/", file = "xo", flag = FTW_F, level = 2 +base = "$tmp/ftwtest.d/foo/", file = "lvl1", flag = FTW_D, level = 2 +base = "$tmp/ftwtest.d/foo/", file = "lvl1b", flag = FTW_D, level = 2 +base = "$tmp/ftwtest.d/foo/lvl1b/", file = "file2@1b", flag = FTW_F, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1b/", file = "file3@1b", flag = FTW_F, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1b/", file = "file@1b", flag = FTW_F, level = 3 +EOF +rm $testout + +$testprogram --skip-siblings=lvl1 $tmpdir | + sort > $testout + +# The filesystem is not required to put lvl1 before lvl1b. +# If lvl1b comes after lvl1, it shouldn't be printed, while if it +# comes before, it should. +catcmd=cat +[ -n "`ls -U $tmpdir/foo/ | sed -n '/lvl1$/,${/lvl1b$/p;}'`" ] \ + && catcmd="grep -v lvl1b" + +$catcmd <<EOF | diff -u $testout - || exit 1 +base = "$tmp/", file = "ftwtest.d", flag = FTW_D, level = 0 +base = "$tmp/ftwtest.d/", file = "bar", flag = FTW_D, level = 1 +base = "$tmp/ftwtest.d/", file = "baz", flag = FTW_F, level = 1 +base = "$tmp/ftwtest.d/", file = "foo", flag = FTW_D, level = 1 +base = "$tmp/ftwtest.d/bar/", file = "xo", flag = FTW_F, level = 2 +base = "$tmp/ftwtest.d/foo/", file = "lvl1", flag = FTW_D, level = 2 +base = "$tmp/ftwtest.d/foo/", file = "lvl1b", flag = FTW_D, level = 2 +base = "$tmp/ftwtest.d/foo/lvl1b/", file = "file2@1b", flag = FTW_F, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1b/", file = "file3@1b", flag = FTW_F, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1b/", file = "file@1b", flag = FTW_F, level = 3 +EOF +rm $testout + +$testprogram --skip-siblings=file@1b $tmpdir | + sort > $testout + +# The filesystem is not required to put file2@1b and file3@1b after file@1b. +# If file[23]@1b come after file@1b, it shouldn't be printed, while if they +# come before, they should. +regexp=`echo $(ls -U $tmp/ftwtest.d/foo/lvl1b \ + | sed -n '/file@1b$/,${/file[23]@1b$/p;}') | sed 's, ,|,'` +catcmd=cat +[ -n "$regexp" ] && catcmd="egrep -v $regexp" + +$catcmd <<EOF | diff -u $testout - || exit 1 +base = "$tmp/", file = "ftwtest.d", flag = FTW_D, level = 0 +base = "$tmp/ftwtest.d/", file = "bar", flag = FTW_D, level = 1 +base = "$tmp/ftwtest.d/", file = "baz", flag = FTW_F, level = 1 +base = "$tmp/ftwtest.d/", file = "foo", flag = FTW_D, level = 1 +base = "$tmp/ftwtest.d/bar/", file = "xo", flag = FTW_F, level = 2 +base = "$tmp/ftwtest.d/foo/", file = "lvl1", flag = FTW_D, level = 2 +base = "$tmp/ftwtest.d/foo/", file = "lvl1b", flag = FTW_D, level = 2 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "file@1", flag = FTW_F, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "link@1", flag = FTW_SLN, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/", file = "lvl2", flag = FTW_D, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "file@2", flag = FTW_F, level = 4 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/", file = "lvl3", flag = FTW_D, level = 4 +base = "$tmp/ftwtest.d/foo/lvl1/lvl2/lvl3/", file = "file@3", flag = FTW_F, level = 5 +base = "$tmp/ftwtest.d/foo/lvl1b/", file = "file2@1b", flag = FTW_F, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1b/", file = "file3@1b", flag = FTW_F, level = 3 +base = "$tmp/ftwtest.d/foo/lvl1b/", file = "file@1b", flag = FTW_F, level = 3 +EOF +rm $testout + +rm -fr $tmpdir + +trap '' 0 + +exit 0 diff --git a/REORG.TODO/io/ftwtest.c b/REORG.TODO/io/ftwtest.c new file mode 100644 index 0000000000..77debd2805 --- /dev/null +++ b/REORG.TODO/io/ftwtest.c @@ -0,0 +1,120 @@ +#include <ftw.h> +#include <getopt.h> +#include <mcheck.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +int do_depth; +int do_chdir; +int do_phys; +int do_exit; +char *skip_subtree; +char *skip_siblings; + +struct option options[] = +{ + { "depth", no_argument, &do_depth, 1 }, + { "chdir", no_argument, &do_chdir, 1 }, + { "phys", no_argument, &do_phys, 1 }, + { "skip-subtree", required_argument, NULL, 't' }, + { "skip-siblings", required_argument, NULL, 's' }, + { "early-exit", no_argument, &do_exit, 1 }, + { NULL, 0, NULL, 0 } +}; + +const char *flag2name[] = +{ + [FTW_F] = "FTW_F", + [FTW_D] = "FTW_D", + [FTW_DNR] = "FTW_DNR", + [FTW_NS] = "FTW_NS", + [FTW_SL] = "FTW_SL", + [FTW_DP] = "FTW_DP", + [FTW_SLN] = "FTW_SLN" +}; + + +static int +cb (const char *name, const struct stat *st, int flag, struct FTW *f) +{ + if (do_exit && strcmp (name + f->base, "file@2")) + return FTW_CONTINUE; + + printf ("base = \"%.*s\", file = \"%s\", flag = %s", + f->base, name, name + f->base, flag2name[flag]); + if (do_chdir) + { + char *cwd = getcwd (NULL, 0); + printf (", cwd = %s", cwd); + free (cwd); + } + printf (", level = %d\n", f->level); + + if (skip_siblings && strcmp (name + f->base, skip_siblings) == 0) + return FTW_SKIP_SIBLINGS; + + if (skip_subtree && strcmp (name + f->base, skip_subtree) == 0) + return FTW_SKIP_SUBTREE; + + return do_exit ? 26 : FTW_CONTINUE; +} + +int +main (int argc, char *argv[]) +{ + int opt; + int r; + int flag = 0; + mtrace (); + + while ((opt = getopt_long_only (argc, argv, "", options, NULL)) != -1) + { + if (opt == 't') + skip_subtree = optarg; + else if (opt == 's') + skip_siblings = optarg; + } + + if (do_chdir) + flag |= FTW_CHDIR; + if (do_depth) + flag |= FTW_DEPTH; + if (do_phys) + flag |= FTW_PHYS; + if (skip_subtree || skip_siblings) + { + flag |= FTW_ACTIONRETVAL; + if (do_exit) + { + printf ("--early-exit cannot be used together with --skip-{siblings,subtree}"); + exit (1); + } + } + + char *cw1 = getcwd (NULL, 0); + + r = nftw (optind < argc ? argv[optind] : ".", cb, do_exit ? 1 : 3, flag); + if (r < 0) + perror ("nftw"); + + char *cw2 = getcwd (NULL, 0); + + if (strcmp (cw1, cw2) != 0) + { + printf ("current working directory before and after nftw call differ:\n" + "before: %s\n" + "after: %s\n", cw1, cw2); + exit (1); + } + + if (do_exit) + { + puts (r == 26 ? "succeeded" : "failed"); + return r == 26 ? 0 : 1; + } + return r; +} diff --git a/REORG.TODO/io/futimens.c b/REORG.TODO/io/futimens.c new file mode 100644 index 0000000000..27fc1ae6ef --- /dev/null +++ b/REORG.TODO/io/futimens.c @@ -0,0 +1,34 @@ +/* Change access and modification times of open file. Linux version. + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <string.h> +#include <time.h> +#include <sysdep.h> + + +/* Change the access time of the file associated with FD to TSP[0] and + the modification time of FILE to TSP[1]. */ +int +futimens (int fd, const struct timespec tsp[2]) +{ + __set_errno (ENOSYS); + return -1; +} +stub_warning (futimens) diff --git a/REORG.TODO/io/fxstat.c b/REORG.TODO/io/fxstat.c new file mode 100644 index 0000000000..d1b548daf7 --- /dev/null +++ b/REORG.TODO/io/fxstat.c @@ -0,0 +1,48 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <sys/stat.h> + +/* Get information about the file descriptor FD in BUF. */ +int +__fxstat (int vers, int fd, struct stat *buf) +{ + if (vers != _STAT_VER) + { + __set_errno (EINVAL); + return -1; + } + + if (fd < 0) + { + __set_errno (EBADF); + return -1; + } + else if (buf == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (fstat) +hidden_def (__fxstat) +weak_alias (__fxstat, _fxstat) diff --git a/REORG.TODO/io/fxstat64.c b/REORG.TODO/io/fxstat64.c new file mode 100644 index 0000000000..c1878e5744 --- /dev/null +++ b/REORG.TODO/io/fxstat64.c @@ -0,0 +1,47 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <sys/stat.h> + +/* Get information about the file descriptor FD in BUF. */ +int +__fxstat64 (int vers, int fd, struct stat64 *buf) +{ + if (vers != _STAT_VER) + { + __set_errno (EINVAL); + return -1; + } + + if (fd < 0) + { + __set_errno (EBADF); + return -1; + } + else if (buf == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +hidden_def (__fxstat64) +stub_warning (fstat64) diff --git a/REORG.TODO/io/fxstatat.c b/REORG.TODO/io/fxstatat.c new file mode 100644 index 0000000000..68a4e34f13 --- /dev/null +++ b/REORG.TODO/io/fxstatat.c @@ -0,0 +1,48 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stddef.h> +#include <sys/stat.h> + +/* Get information about the file descriptor FD in BUF. */ +int +__fxstatat (int vers, int fd, const char *filename, struct stat *buf, int flag) +{ + if (vers != _STAT_VER) + { + __set_errno (EINVAL); + return -1; + } + + if (fd < 0 && fd != AT_FDCWD) + { + __set_errno (EBADF); + return -1; + } + if (buf == NULL || (flag & ~AT_SYMLINK_NOFOLLOW) != 0) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__fxstatat) +stub_warning (fstatat) diff --git a/REORG.TODO/io/fxstatat64.c b/REORG.TODO/io/fxstatat64.c new file mode 100644 index 0000000000..c39ef84bba --- /dev/null +++ b/REORG.TODO/io/fxstatat64.c @@ -0,0 +1,49 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stddef.h> +#include <sys/stat.h> + +/* Get information about the file descriptor FD in BUF. */ +int +__fxstatat64 (int vers, int fd, const char *filename, struct stat64 *buf, + int flag) +{ + if (vers != _STAT_VER) + { + __set_errno (EINVAL); + return -1; + } + + if (fd < 0 && fd != AT_FDCWD) + { + __set_errno (EBADF); + return -1; + } + if (buf == NULL || (flag & ~AT_SYMLINK_NOFOLLOW) != 0) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__fxstatat64) +stub_warning (fstatat64) diff --git a/REORG.TODO/io/getcwd.c b/REORG.TODO/io/getcwd.c new file mode 100644 index 0000000000..def80309f2 --- /dev/null +++ b/REORG.TODO/io/getcwd.c @@ -0,0 +1,38 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <unistd.h> +#include <stddef.h> + +/* Get the pathname of the current working directory, + and put it in SIZE bytes of BUF. Returns NULL if the + directory couldn't be determined or SIZE was too small. + If successful, returns BUF. In GNU, if BUF is NULL, + an array is allocated with `malloc'; the array is SIZE + bytes long, unless SIZE <= 0, in which case it is as + big as necessary. */ +char * +__getcwd (char *buf, size_t size) +{ + __set_errno (ENOSYS); + return NULL; +} +weak_alias (__getcwd, getcwd) + +stub_warning (__getcwd) +stub_warning (getcwd) diff --git a/REORG.TODO/io/getdirname.c b/REORG.TODO/io/getdirname.c new file mode 100644 index 0000000000..e2e449fd16 --- /dev/null +++ b/REORG.TODO/io/getdirname.c @@ -0,0 +1,43 @@ +/* Copyright (C) 1992-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <unistd.h> +#include <include/sys/stat.h> +#include <stdlib.h> +#include <string.h> + +/* Return a malloc'd string containing the current directory name. + If the environment variable `PWD' is set, and its value is correct, + that value is used. */ + +char * +get_current_dir_name (void) +{ + char *pwd; + struct stat64 dotstat, pwdstat; + + pwd = getenv ("PWD"); + if (pwd != NULL + && stat64 (".", &dotstat) == 0 + && stat64 (pwd, &pwdstat) == 0 + && pwdstat.st_dev == dotstat.st_dev + && pwdstat.st_ino == dotstat.st_ino) + /* The PWD value is correct. Use it. */ + return __strdup (pwd); + + return __getcwd ((char *) NULL, 0); +} diff --git a/REORG.TODO/io/getwd.c b/REORG.TODO/io/getwd.c new file mode 100644 index 0000000000..1aa0e1e5b3 --- /dev/null +++ b/REORG.TODO/io/getwd.c @@ -0,0 +1,54 @@ +/* Obsolete function to get current working directory. + Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <limits.h> +#include <string.h> +#include <unistd.h> + + +char * +getwd (char *buf) +{ +#ifndef PATH_MAX +#define PATH_MAX 1024 +#endif + char tmpbuf[PATH_MAX]; + + if (buf == NULL) + { + __set_errno (EINVAL); + return NULL; + } + + if (__getcwd (tmpbuf, PATH_MAX) == NULL) + { + /* We use 1024 here since it should really be enough and because + this is a safe value. */ + __strerror_r (errno, buf, 1024); + return NULL; + } + + /* This is completely unsafe. Nobody can say how big the user + provided buffer is. Perhaps the application and the libc + disagree about the value of PATH_MAX. */ + return strcpy (buf, tmpbuf); +} + +link_warning (getwd, + "the `getwd' function is dangerous and should not be used.") diff --git a/REORG.TODO/io/isatty.c b/REORG.TODO/io/isatty.c new file mode 100644 index 0000000000..8eeb06352e --- /dev/null +++ b/REORG.TODO/io/isatty.c @@ -0,0 +1,31 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <unistd.h> + +/* Return 1 if FD is a terminal, 0 if not. */ +int +__isatty (int fd) +{ + __set_errno (ENOSYS); + return -1; +} + +weak_alias (__isatty, isatty) + +stub_warning (isatty) diff --git a/REORG.TODO/io/lchmod.c b/REORG.TODO/io/lchmod.c new file mode 100644 index 0000000000..21c56adcf8 --- /dev/null +++ b/REORG.TODO/io/lchmod.c @@ -0,0 +1,31 @@ +/* lchmod -- Change the protections of a file or symbolic link. Stub version. + Copyright (C) 2002-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/stat.h> +#include <sys/types.h> + +/* Change the protections of FILE to MODE. */ +int +lchmod (const char *file, mode_t mode) +{ + __set_errno (ENOSYS); + return -1; +} + +stub_warning (lchmod) diff --git a/REORG.TODO/io/lchown.c b/REORG.TODO/io/lchown.c new file mode 100644 index 0000000000..56890b6ace --- /dev/null +++ b/REORG.TODO/io/lchown.c @@ -0,0 +1,38 @@ +/* Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> +#include <sys/types.h> + +/* Change the owner and group of FILE. */ +int +__lchown (const char *file, uid_t owner, gid_t group) +{ + if (file == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (lchown) + +weak_alias (__lchown, lchown) diff --git a/REORG.TODO/io/link.c b/REORG.TODO/io/link.c new file mode 100644 index 0000000000..68d183009c --- /dev/null +++ b/REORG.TODO/io/link.c @@ -0,0 +1,38 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> + + +/* Make a link to FROM called TO. */ +int +__link (const char *from, const char *to) +{ + if (from == NULL || to == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (link) + +weak_alias (__link, link) diff --git a/REORG.TODO/io/linkat.c b/REORG.TODO/io/linkat.c new file mode 100644 index 0000000000..295a2141d4 --- /dev/null +++ b/REORG.TODO/io/linkat.c @@ -0,0 +1,44 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stddef.h> +#include <unistd.h> + + +/* Make a link to FROM relative to FROMFD called TO relative to TOFD. */ +int +linkat (int fromfd, const char *from, int tofd, const char *to, int flags) +{ + if (from == NULL || to == NULL) + { + __set_errno (EINVAL); + return -1; + } + + if ((tofd != AT_FDCWD && tofd < 0 && *to != '/') + || (fromfd != AT_FDCWD && fromfd < 0 && *from != '/')) + { + __set_errno (EBADF); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (linkat) diff --git a/REORG.TODO/io/lockf.c b/REORG.TODO/io/lockf.c new file mode 100644 index 0000000000..4ab7e9357f --- /dev/null +++ b/REORG.TODO/io/lockf.c @@ -0,0 +1,85 @@ +/* Copyright (C) 1994-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +/* We need to avoid the header declaration of lockf64, because + the types don't match lockf and then the compiler will + complain about the mismatch when we do the alias below. */ +#define lockf64 __renamed_lockf64 + +#include <fcntl.h> + +#undef lockf64 + +#include <sys/types.h> +#include <unistd.h> +#include <errno.h> +#include <string.h> + +/* lockf is a simplified interface to fcntl's locking facilities. */ + +int +lockf (int fd, int cmd, off_t len) +{ + struct flock fl; + + memset ((char *) &fl, '\0', sizeof (fl)); + + /* lockf is always relative to the current file position. */ + fl.l_whence = SEEK_CUR; + fl.l_start = 0; + fl.l_len = len; + + switch (cmd) + { + case F_TEST: + /* Test the lock: return 0 if FD is unlocked or locked by this process; + return -1, set errno to EACCES, if another process holds the lock. */ + fl.l_type = F_RDLCK; + if (__fcntl (fd, F_GETLK, &fl) < 0) + return -1; + if (fl.l_type == F_UNLCK || fl.l_pid == __getpid ()) + return 0; + __set_errno (EACCES); + return -1; + + case F_ULOCK: + fl.l_type = F_UNLCK; + cmd = F_SETLK; + break; + case F_LOCK: + fl.l_type = F_WRLCK; + cmd = F_SETLKW; + break; + case F_TLOCK: + fl.l_type = F_WRLCK; + cmd = F_SETLK; + break; + + default: + __set_errno (EINVAL); + return -1; + } + + /* lockf() is a cancellation point but so is fcntl() if F_SETLKW is + used. Therefore we don't have to care about cancellation here, + the fcntl() function will take care of it. */ + return __fcntl (fd, cmd, &fl); +} + +#ifdef __OFF_T_MATCHES_OFF64_T +weak_alias (lockf, lockf64) +#endif diff --git a/REORG.TODO/io/lockf64.c b/REORG.TODO/io/lockf64.c new file mode 100644 index 0000000000..504ce562e5 --- /dev/null +++ b/REORG.TODO/io/lockf64.c @@ -0,0 +1,83 @@ +/* Copyright (C) 1994-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/types.h> +#include <unistd.h> +#include <fcntl.h> +#include <errno.h> +#include <string.h> + +/* lockf.c defines lockf64 as an alias if __OFF_T_MATCHES_OFF64_T. */ +#ifndef __OFF_T_MATCHES_OFF64_T + +/* lockf is a simplified interface to fcntl's locking facilities. */ + +int +lockf64 (int fd, int cmd, off64_t len64) +{ + struct flock fl; + off_t len = (off_t) len64; + + if (len64 != (off64_t) len) + { + /* We can't represent the length. */ + __set_errno (EOVERFLOW); + return -1; + } + + memset ((char *) &fl, '\0', sizeof (fl)); + + /* lockf is always relative to the current file position. */ + fl.l_whence = SEEK_CUR; + fl.l_start = 0; + fl.l_len = len; + + switch (cmd) + { + case F_TEST: + /* Test the lock: return 0 if FD is unlocked or locked by this process; + return -1, set errno to EACCES, if another process holds the lock. */ + fl.l_type = F_RDLCK; + if (__fcntl (fd, F_GETLK, &fl) < 0) + return -1; + if (fl.l_type == F_UNLCK || fl.l_pid == __getpid ()) + return 0; + __set_errno (EACCES); + return -1; + + case F_ULOCK: + fl.l_type = F_UNLCK; + cmd = F_SETLK; + break; + case F_LOCK: + fl.l_type = F_WRLCK; + cmd = F_SETLKW; + break; + case F_TLOCK: + fl.l_type = F_WRLCK; + cmd = F_SETLK; + break; + + default: + __set_errno (EINVAL); + return -1; + } + + return __fcntl (fd, cmd, &fl); +} + +#endif diff --git a/REORG.TODO/io/lseek.c b/REORG.TODO/io/lseek.c new file mode 100644 index 0000000000..4c562a8e9b --- /dev/null +++ b/REORG.TODO/io/lseek.c @@ -0,0 +1,49 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <unistd.h> +#include <sys/types.h> + +/* Seek to OFFSET on FD, starting from WHENCE. */ +off_t +__libc_lseek (int fd, off_t offset, int whence) +{ + if (fd < 0) + { + __set_errno (EBADF); + return -1; + } + switch (whence) + { + case SEEK_SET: + case SEEK_CUR: + case SEEK_END: + break; + default: + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +weak_alias (__libc_lseek, __lseek) +weak_alias (__libc_lseek, lseek) +stub_warning (lseek) + +libc_hidden_def (__lseek) diff --git a/REORG.TODO/io/lseek64.c b/REORG.TODO/io/lseek64.c new file mode 100644 index 0000000000..b4cf09cf5b --- /dev/null +++ b/REORG.TODO/io/lseek64.c @@ -0,0 +1,47 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <unistd.h> +#include <sys/types.h> + +/* Seek to OFFSET on FD, starting from WHENCE. */ +off64_t +__libc_lseek64 (int fd, off64_t offset, int whence) +{ + if (fd < 0) + { + __set_errno (EBADF); + return -1; + } + switch (whence) + { + case SEEK_SET: + case SEEK_CUR: + case SEEK_END: + break; + default: + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +weak_alias (__libc_lseek64, __lseek64) +weak_alias (__libc_lseek64, lseek64) +stub_warning (lseek64) diff --git a/REORG.TODO/io/lstat.c b/REORG.TODO/io/lstat.c new file mode 100644 index 0000000000..8ae18d1339 --- /dev/null +++ b/REORG.TODO/io/lstat.c @@ -0,0 +1,55 @@ +/* Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file with other + programs, and to distribute those programs without any restriction + coming from the use of this file. (The GNU Lesser General Public + License restrictions do apply in other respects; for example, they + cover modification of the file, and distribution when not linked + into another program.) + + Note that people who make modified versions of this file are not + obligated to grant this special exception for their modified + versions; it is their choice whether to do so. The GNU Lesser + General Public License gives permission to release a modified + version without this exception; this exception also makes it + possible to release a modified version which carries forward this + exception. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/stat.h> + +/* This definition is only used if inlining fails for this function; see + the last page of <sys/stat.h>. The real work is done by the `x' + function which is passed a version number argument. We arrange in the + makefile that when not inlined this function is always statically + linked; that way a dynamically-linked executable always encodes the + version number corresponding to the data structures it uses, so the `x' + functions in the shared library can adapt without needing to recompile + all callers. */ + +#undef lstat +#undef __lstat +int +attribute_hidden +__lstat (const char *file, struct stat *buf) +{ + return __lxstat (_STAT_VER, file, buf); +} + +weak_hidden_alias (__lstat, lstat) diff --git a/REORG.TODO/io/lstat64.c b/REORG.TODO/io/lstat64.c new file mode 100644 index 0000000000..c29492aa9f --- /dev/null +++ b/REORG.TODO/io/lstat64.c @@ -0,0 +1,52 @@ +/* Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file with other + programs, and to distribute those programs without any restriction + coming from the use of this file. (The GNU Lesser General Public + License restrictions do apply in other respects; for example, they + cover modification of the file, and distribution when not linked + into another program.) + + Note that people who make modified versions of this file are not + obligated to grant this special exception for their modified + versions; it is their choice whether to do so. The GNU Lesser + General Public License gives permission to release a modified + version without this exception; this exception also makes it + possible to release a modified version which carries forward this + exception. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/stat.h> + +/* This definition is only used if inlining fails for this function; see + the last page of <sys/stat.h>. The real work is done by the `x' + function which is passed a version number argument. We arrange in the + makefile that when not inlined this function is always statically + linked; that way a dynamically-linked executable always encodes the + version number corresponding to the data structures it uses, so the `x' + functions in the shared library can adapt without needing to recompile + all callers. */ + +#undef lstat64 +int +attribute_hidden +lstat64 (const char *file, struct stat64 *buf) +{ + return __lxstat64 (_STAT_VER, file, buf); +} diff --git a/REORG.TODO/io/lxstat.c b/REORG.TODO/io/lxstat.c new file mode 100644 index 0000000000..e2d93f2055 --- /dev/null +++ b/REORG.TODO/io/lxstat.c @@ -0,0 +1,26 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/stat.h> + +int +__lxstat (int version, const char *file, struct stat *buf) +{ + return __xstat (version, file, buf); +} +hidden_def (__lxstat) +weak_alias (__lxstat, _lxstat) diff --git a/REORG.TODO/io/lxstat64.c b/REORG.TODO/io/lxstat64.c new file mode 100644 index 0000000000..1fd227747c --- /dev/null +++ b/REORG.TODO/io/lxstat64.c @@ -0,0 +1,30 @@ +/* lxstat64 -- get file metadata, not following symlinks. Stub version. + Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <sys/stat.h> + +/* Get file information about FILE in BUF. + If FILE is a symbolic link, do not follow it. */ +int +__lxstat64 (int vers, const char *file, struct stat64 *buf) +{ + return __xstat64 (vers, file, buf); +} +hidden_def (__lxstat64) diff --git a/REORG.TODO/io/mkdir.c b/REORG.TODO/io/mkdir.c new file mode 100644 index 0000000000..0b8499a707 --- /dev/null +++ b/REORG.TODO/io/mkdir.c @@ -0,0 +1,39 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <sys/stat.h> +#include <sys/types.h> + + +/* Create a directory named PATH with protections MODE. */ +int +__mkdir (const char *path, mode_t mode) +{ + if (path == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (mkdir) + +weak_alias (__mkdir, mkdir) diff --git a/REORG.TODO/io/mkdirat.c b/REORG.TODO/io/mkdirat.c new file mode 100644 index 0000000000..1541d625d2 --- /dev/null +++ b/REORG.TODO/io/mkdirat.c @@ -0,0 +1,52 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stddef.h> +#include <sys/stat.h> +#include <sys/types.h> + + +/* Create a directory named PATH relative to FD with protections MODE. */ +int +mkdirat (int fd, const char *path, mode_t mode) +{ + if (path == NULL) + { + __set_errno (EINVAL); + return -1; + } + + if (fd != AT_FDCWD && path[0] != '/') + { + /* Check FD is associated with a directory. */ + struct stat64 st; + if (__fxstat64 (_STAT_VER, fd, &st) != 0) + return -1; + + if (!S_ISDIR (st.st_mode)) + { + __set_errno (ENOTDIR); + return -1; + } + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (mkdirat) diff --git a/REORG.TODO/io/mkfifo.c b/REORG.TODO/io/mkfifo.c new file mode 100644 index 0000000000..d00183e4d0 --- /dev/null +++ b/REORG.TODO/io/mkfifo.c @@ -0,0 +1,39 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <sys/stat.h> +#include <sys/types.h> + + +/* Create a named pipe (FIFO) named PATH with protections MODE. */ +int +mkfifo (const char *path, mode_t mode) +{ + if (path == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} + + +stub_warning (mkfifo) diff --git a/REORG.TODO/io/mkfifoat.c b/REORG.TODO/io/mkfifoat.c new file mode 100644 index 0000000000..bcbea75470 --- /dev/null +++ b/REORG.TODO/io/mkfifoat.c @@ -0,0 +1,55 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stddef.h> +#include <sys/stat.h> +#include <sys/types.h> + + +/* Create a named pipe (FIFO) named PATH relative to FD with + protections MODE. */ +int +mkfifoat (int fd, const char *path, mode_t mode) +{ + if (path == NULL) + { + __set_errno (EINVAL); + return -1; + } + + if (fd != AT_FDCWD && path[0] != '/') + { + /* Check FD is associated with a directory. */ + struct stat64 st; + if (__fxstat64 (_STAT_VER, fd, &st) != 0) + return -1; + + if (!S_ISDIR (st.st_mode)) + { + __set_errno (ENOTDIR); + return -1; + } + } + + __set_errno (ENOSYS); + return -1; +} + + +stub_warning (mkfifoat) diff --git a/REORG.TODO/io/mknod.c b/REORG.TODO/io/mknod.c new file mode 100644 index 0000000000..4db51d0ada --- /dev/null +++ b/REORG.TODO/io/mknod.c @@ -0,0 +1,55 @@ +/* Copyright (C) 1995-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file with other + programs, and to distribute those programs without any restriction + coming from the use of this file. (The GNU Lesser General Public + License restrictions do apply in other respects; for example, they + cover modification of the file, and distribution when not linked + into another program.) + + Note that people who make modified versions of this file are not + obligated to grant this special exception for their modified + versions; it is their choice whether to do so. The GNU Lesser + General Public License gives permission to release a modified + version without this exception; this exception also makes it + possible to release a modified version which carries forward this + exception. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + + +#include <sys/types.h> +#include <sys/stat.h> + +/* This definition is only used if inlining fails for this function; see + the last page of <sys/stat.h>. The real work is done by the `x' + function which is passed a version number argument. We arrange in the + makefile that when not inlined this function is always statically + linked; that way a dynamically-linked executable always encodes the + version number corresponding to the data structures it uses, so the `x' + functions in the shared library can adapt without needing to recompile + all callers. */ + +int +attribute_hidden +__mknod (const char *path, mode_t mode, dev_t dev) +{ + return __xmknod (_MKNOD_VER, path, mode, &dev); +} + +weak_hidden_alias (__mknod, mknod) diff --git a/REORG.TODO/io/mknodat.c b/REORG.TODO/io/mknodat.c new file mode 100644 index 0000000000..1e3a4b1f1d --- /dev/null +++ b/REORG.TODO/io/mknodat.c @@ -0,0 +1,53 @@ +/* Copyright (C) 1995-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file with other + programs, and to distribute those programs without any restriction + coming from the use of this file. (The GNU Lesser General Public + License restrictions do apply in other respects; for example, they + cover modification of the file, and distribution when not linked + into another program.) + + Note that people who make modified versions of this file are not + obligated to grant this special exception for their modified + versions; it is their choice whether to do so. The GNU Lesser + General Public License gives permission to release a modified + version without this exception; this exception also makes it + possible to release a modified version which carries forward this + exception. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + + +#include <sys/types.h> +#include <sys/stat.h> + +/* This definition is only used if inlining fails for this function; see + the last page of <sys/stat.h>. The real work is done by the `x' + function which is passed a version number argument. We arrange in the + makefile that when not inlined this function is always statically + linked; that way a dynamically-linked executable always encodes the + version number corresponding to the data structures it uses, so the `x' + functions in the shared library can adapt without needing to recompile + all callers. */ + +int +attribute_hidden +mknodat (int fd, const char *path, mode_t mode, dev_t dev) +{ + return __xmknodat (_MKNOD_VER, fd, path, mode, &dev); +} diff --git a/REORG.TODO/io/open.c b/REORG.TODO/io/open.c new file mode 100644 index 0000000000..47013f65f4 --- /dev/null +++ b/REORG.TODO/io/open.c @@ -0,0 +1,59 @@ +/* Open a file by name. Stub version. + Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stdarg.h> +#include <stddef.h> +#include <stdio.h> + + +/* Open FILE with access OFLAG. If O_CREAT or O_TMPFILE is in OFLAG, + a third argument is the file protection. */ +int +__libc_open (const char *file, int oflag) +{ + int mode; + + if (file == NULL) + { + __set_errno (EINVAL); + return -1; + } + + if (__OPEN_NEEDS_MODE (oflag)) + { + va_list arg; + va_start(arg, oflag); + mode = va_arg(arg, int); + va_end(arg); + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__libc_open) +weak_alias (__libc_open, __open) +libc_hidden_weak (__open) +weak_alias (__libc_open, open) + +stub_warning (open) + +/* __open_2 is a generic wrapper that calls __open. + So give a stub warning for that symbol too. */ +stub_warning (__open_2) diff --git a/REORG.TODO/io/open64.c b/REORG.TODO/io/open64.c new file mode 100644 index 0000000000..46439a5aac --- /dev/null +++ b/REORG.TODO/io/open64.c @@ -0,0 +1,56 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stdarg.h> +#include <stddef.h> +#include <stdio.h> + +/* Open FILE with access OFLAG. If O_CREAT or O_TMPFILE is in OFLAG, + a third argument is the file protection. */ +int +__libc_open64 (const char *file, int oflag) +{ + int mode; + + if (file == NULL) + { + __set_errno (EINVAL); + return -1; + } + + if (__OPEN_NEEDS_MODE (oflag)) + { + va_list arg; + va_start (arg, oflag); + mode = va_arg (arg, int); + va_end (arg); + } + + __set_errno (ENOSYS); + return -1; +} +strong_alias (__libc_open64, __open64) +libc_hidden_def (__open64) +weak_alias (__libc_open64, open64) + +stub_warning (open64) + +/* __open64_2 is a generic wrapper that calls __open64. + So give a stub warning for that symbol too. */ +stub_warning (__open64_2) diff --git a/REORG.TODO/io/open64_2.c b/REORG.TODO/io/open64_2.c new file mode 100644 index 0000000000..138817260d --- /dev/null +++ b/REORG.TODO/io/open64_2.c @@ -0,0 +1,29 @@ +/* _FORTIFY_SOURCE wrapper for open64. + Copyright (C) 2013-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <fcntl.h> +#include <stdio.h> + +int +__open64_2 (const char *file, int oflag) +{ + if (__OPEN_NEEDS_MODE (oflag)) + __fortify_fail ("invalid open64 call: O_CREAT or O_TMPFILE without mode"); + + return __open64 (file, oflag); +} diff --git a/REORG.TODO/io/open_2.c b/REORG.TODO/io/open_2.c new file mode 100644 index 0000000000..b42f493ad8 --- /dev/null +++ b/REORG.TODO/io/open_2.c @@ -0,0 +1,29 @@ +/* _FORTIFY_SOURCE wrapper for open. + Copyright (C) 2013-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <fcntl.h> +#include <stdio.h> + +int +__open_2 (const char *file, int oflag) +{ + if (__OPEN_NEEDS_MODE (oflag)) + __fortify_fail ("invalid open call: O_CREAT or O_TMPFILE without mode"); + + return __open (file, oflag); +} diff --git a/REORG.TODO/io/openat.c b/REORG.TODO/io/openat.c new file mode 100644 index 0000000000..529f418da2 --- /dev/null +++ b/REORG.TODO/io/openat.c @@ -0,0 +1,79 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stdarg.h> +#include <stddef.h> +#include <stdio.h> +#include <sys/stat.h> +#include <kernel-features.h> + +/* Some mostly-generic code (e.g. sysdeps/posix/getcwd.c) uses this variable + if __ASSUME_ATFCTS is not defined. */ +#ifndef __ASSUME_ATFCTS +int __have_atfcts; +#endif + +/* Open FILE with access OFLAG. Interpret relative paths relative to + the directory associated with FD. If O_CREAT or O_TMPFILE is in OFLAG, a + third argument is the file protection. */ +int +__openat (int fd, const char *file, int oflag, ...) +{ + int mode; + + if (file == NULL) + { + __set_errno (EINVAL); + return -1; + } + + if (fd != AT_FDCWD && file[0] != '/') + { + /* Check FD is associated with a directory. */ + struct stat64 st; + if (__fxstat64 (_STAT_VER, fd, &st) != 0) + return -1; + + if (!S_ISDIR (st.st_mode)) + { + __set_errno (ENOTDIR); + return -1; + } + } + + if (__OPEN_NEEDS_MODE (oflag)) + { + va_list arg; + va_start (arg, oflag); + mode = va_arg (arg, int); + va_end (arg); + + ignore_value (mode); + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__openat) +weak_alias (__openat, openat) +stub_warning (openat) + +/* __openat_2 is a generic wrapper that calls __openat. + So give a stub warning for that symbol too. */ +stub_warning (__openat_2) diff --git a/REORG.TODO/io/openat64.c b/REORG.TODO/io/openat64.c new file mode 100644 index 0000000000..116becda98 --- /dev/null +++ b/REORG.TODO/io/openat64.c @@ -0,0 +1,72 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stdarg.h> +#include <stddef.h> +#include <stdio.h> +#include <sys/stat.h> + +/* Open FILE with access OFLAG. Interpret relative paths relative to + the directory associated with FD. If O_CREAT or O_TMPFILE is in OFLAG, a + third argument is the file protection. */ +int +__openat64 (int fd, const char *file, int oflag, ...) +{ + int mode; + + if (file == NULL) + { + __set_errno (EINVAL); + return -1; + } + + if (fd != AT_FDCWD && file[0] != '/') + { + /* Check FD is associated with a directory. */ + struct stat64 st; + if (__fxstat64 (_STAT_VER, fd, &st) != 0) + return -1; + + if (!S_ISDIR (st.st_mode)) + { + __set_errno (ENOTDIR); + return -1; + } + } + + if (__OPEN_NEEDS_MODE (oflag)) + { + va_list arg; + va_start (arg, oflag); + mode = va_arg (arg, int); + va_end (arg); + + ignore_value (mode); + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__openat64) +weak_alias (__openat64, openat64) +stub_warning (openat64) + +/* __openat64_2 is a generic wrapper that calls __openat64. + So give a stub warning for that symbol too. */ +stub_warning (__openat_2) diff --git a/REORG.TODO/io/openat64_2.c b/REORG.TODO/io/openat64_2.c new file mode 100644 index 0000000000..95ff739041 --- /dev/null +++ b/REORG.TODO/io/openat64_2.c @@ -0,0 +1,29 @@ +/* _FORTIFY_SOURCE wrapper for openat64. + Copyright (C) 2013-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <fcntl.h> +#include <stdio.h> + +int +__openat64_2 (int fd, const char *file, int oflag) +{ + if (__OPEN_NEEDS_MODE (oflag)) + __fortify_fail ("invalid openat64 call: O_CREAT or O_TMPFILE without mode"); + + return __openat64 (fd, file, oflag); +} diff --git a/REORG.TODO/io/openat_2.c b/REORG.TODO/io/openat_2.c new file mode 100644 index 0000000000..6911c83411 --- /dev/null +++ b/REORG.TODO/io/openat_2.c @@ -0,0 +1,29 @@ +/* _FORTIFY_SOURCE wrapper for openat. + Copyright (C) 2013-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <fcntl.h> +#include <stdio.h> + +int +__openat_2 (int fd, const char *file, int oflag) +{ + if (__OPEN_NEEDS_MODE (oflag)) + __fortify_fail ("invalid openat call: O_CREAT or O_TMPFILE without mode"); + + return __openat (fd, file, oflag); +} diff --git a/REORG.TODO/io/pipe.c b/REORG.TODO/io/pipe.c new file mode 100644 index 0000000000..7e8b478cfe --- /dev/null +++ b/REORG.TODO/io/pipe.c @@ -0,0 +1,41 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <unistd.h> +#include <stddef.h> + +/* Create a one-way communication channel (__pipe). + If successful, two file descriptors are stored in PIPEDES; + bytes written on PIPEDES[1] can be read from PIPEDES[0]. + Returns 0 if successful, -1 if not. */ +int +__pipe (int __pipedes[2]) +{ + if (__pipedes == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__pipe) +stub_warning (pipe) + +weak_alias (__pipe, pipe) diff --git a/REORG.TODO/io/pipe2.c b/REORG.TODO/io/pipe2.c new file mode 100644 index 0000000000..ec210ee4a3 --- /dev/null +++ b/REORG.TODO/io/pipe2.c @@ -0,0 +1,39 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <unistd.h> +#include <stddef.h> + +/* Create a one-way communication channel (__pipe). If successful, + two file descriptors are stored in PIPEDES; bytes written on + PIPEDES[1] can be read from PIPEDES[0]. Apply FLAGS to the new + file descriptors. Returns 0 if successful, -1 if not. */ +int +__pipe2 (int pipedes[2], int flags) +{ + if (pipedes == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +weak_alias (__pipe2, pipe2) +stub_warning (pipe2) diff --git a/REORG.TODO/io/poll.c b/REORG.TODO/io/poll.c new file mode 100644 index 0000000000..15ed631c46 --- /dev/null +++ b/REORG.TODO/io/poll.c @@ -0,0 +1,37 @@ +/* Poll (or wait) for file descriptor I/O availability. Stub version. + Copyright (C) 1994-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/poll.h> +#include <errno.h> + +/* Poll the file descriptors described by the NFDS structures starting at + FDS. If TIMEOUT is nonzero and not -1, allow TIMEOUT milliseconds for + an event to occur; if TIMEOUT is -1, block until an event occurs. + Returns the number of file descriptors with events, zero if timed out, + or -1 for errors. */ + +int +__poll (struct pollfd *fds, nfds_t nfds, int timeout) +{ + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__poll) +weak_alias (__poll, poll) + +stub_warning (poll) diff --git a/REORG.TODO/io/poll.h b/REORG.TODO/io/poll.h new file mode 100644 index 0000000000..06fb41ab89 --- /dev/null +++ b/REORG.TODO/io/poll.h @@ -0,0 +1 @@ +#include <sys/poll.h> diff --git a/REORG.TODO/io/posix_fadvise.c b/REORG.TODO/io/posix_fadvise.c new file mode 100644 index 0000000000..bad1ed024f --- /dev/null +++ b/REORG.TODO/io/posix_fadvise.c @@ -0,0 +1,29 @@ +/* Copyright (C) 2000-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> + +/* Advice the system about the expected behaviour of the application with + respect to the file associated with FD. */ + +int +posix_fadvise (int fd, __off_t offset, __off_t len, int advise) +{ + return ENOSYS; +} +stub_warning (posix_fadvise) diff --git a/REORG.TODO/io/posix_fadvise64.c b/REORG.TODO/io/posix_fadvise64.c new file mode 100644 index 0000000000..4dd072b6ec --- /dev/null +++ b/REORG.TODO/io/posix_fadvise64.c @@ -0,0 +1,29 @@ +/* Copyright (C) 2000-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> + +/* Advice the system about the expected behaviour of the application with + respect to the file associated with FD. */ + +int +posix_fadvise64 (int fd, __off64_t offset, __off64_t len, int advise) +{ + return ENOSYS; +} +stub_warning (posix_fadvise64) diff --git a/REORG.TODO/io/posix_fallocate.c b/REORG.TODO/io/posix_fallocate.c new file mode 100644 index 0000000000..b35e3e9611 --- /dev/null +++ b/REORG.TODO/io/posix_fallocate.c @@ -0,0 +1,28 @@ +/* Copyright (C) 2000-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> + +/* Reserve storage for the data of the file associated with FD. */ + +int +posix_fallocate (int fd, __off_t offset, __off_t len) +{ + return ENOSYS; +} +stub_warning (posix_fallocate) diff --git a/REORG.TODO/io/posix_fallocate64.c b/REORG.TODO/io/posix_fallocate64.c new file mode 100644 index 0000000000..eb9d95cc53 --- /dev/null +++ b/REORG.TODO/io/posix_fallocate64.c @@ -0,0 +1,28 @@ +/* Copyright (C) 2000-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> + +/* Reserve storage for the data of the file associated with FD. */ + +int +posix_fallocate64 (int fd, __off64_t offset, __off64_t len) +{ + return ENOSYS; +} +stub_warning (posix_fallocate64) diff --git a/REORG.TODO/io/ppoll.c b/REORG.TODO/io/ppoll.c new file mode 100644 index 0000000000..e2919a7098 --- /dev/null +++ b/REORG.TODO/io/ppoll.c @@ -0,0 +1,76 @@ +/* Copyright (C) 2006-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper <drepper@redhat.com>, 2006. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <limits.h> +#include <signal.h> +#include <stddef.h> /* For NULL. */ +#include <sys/poll.h> +#include <sysdep-cancel.h> + + +int +ppoll (struct pollfd *fds, nfds_t nfds, const struct timespec *timeout, + const sigset_t *sigmask) +{ + int tval = -1; + + /* poll uses a simple millisecond value. Convert it. */ + if (timeout != NULL) + { + if (timeout->tv_sec < 0 + || timeout->tv_nsec < 0 || timeout->tv_nsec >= 1000000000) + { + __set_errno (EINVAL); + return -1; + } + + if (timeout->tv_sec > INT_MAX / 1000 + || (timeout->tv_sec == INT_MAX / 1000 + && ((timeout->tv_nsec + 999999) / 1000000 > INT_MAX % 1000))) + /* We cannot represent the timeout in an int value. Wait + forever. */ + tval = -1; + else + tval = (timeout->tv_sec * 1000 + + (timeout->tv_nsec + 999999) / 1000000); + } + + /* The setting and restoring of the signal mask and the select call + should be an atomic operation. This can't be done without kernel + help. */ + sigset_t savemask; + if (sigmask != NULL) + __sigprocmask (SIG_SETMASK, sigmask, &savemask); + + /* Note the ppoll() is a cancellation point. But since we call + poll() which itself is a cancellation point we do not have + to do anything here. */ + int retval = __poll (fds, nfds, tval); + + if (sigmask != NULL) + __sigprocmask (SIG_SETMASK, &savemask, NULL); + + return retval; +} + +#ifndef ppoll +/* __poll handles cancellation. */ +LIBC_CANCEL_HANDLED (); +libc_hidden_def (ppoll); +#endif diff --git a/REORG.TODO/io/pwd.c b/REORG.TODO/io/pwd.c new file mode 100644 index 0000000000..8883447b3e --- /dev/null +++ b/REORG.TODO/io/pwd.c @@ -0,0 +1,42 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <mcheck.h> +#include <stdio.h> +#include <stdlib.h> +#include <unistd.h> + +int +main (void) +{ + char *dir; + + /* Let this program be used for debugging. */ + mtrace (); + + dir = getcwd ((char *) NULL, 0); + + if (dir == NULL) + perror ("getcwd"); + else + { + puts (dir); + free (dir); + } + + return (dir == NULL ? EXIT_FAILURE : EXIT_SUCCESS); +} diff --git a/REORG.TODO/io/read.c b/REORG.TODO/io/read.c new file mode 100644 index 0000000000..2f7b6743f7 --- /dev/null +++ b/REORG.TODO/io/read.c @@ -0,0 +1,47 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <unistd.h> +#include <stddef.h> + +/* Read NBYTES into BUF from FD. Return the number read or -1. */ +ssize_t +__libc_read (int fd, void *buf, size_t nbytes) +{ + if (nbytes == 0) + return 0; + if (fd < 0) + { + __set_errno (EBADF); + return -1; + } + if (buf == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__libc_read) +stub_warning (read) + +weak_alias (__libc_read, __read) +libc_hidden_weak (__read) +weak_alias (__libc_read, read) diff --git a/REORG.TODO/io/readlink.c b/REORG.TODO/io/readlink.c new file mode 100644 index 0000000000..07e35ae807 --- /dev/null +++ b/REORG.TODO/io/readlink.c @@ -0,0 +1,32 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <unistd.h> + +/* Read the contents of the symbolic link PATH into no more than + LEN bytes of BUF. The contents are not null-terminated. + Returns the number of characters read, or -1 for errors. */ +ssize_t +__readlink (const char *path, char *buf, size_t len) +{ + __set_errno (ENOSYS); + return -1; +} +stub_warning (readlink) + +weak_alias (__readlink, readlink) diff --git a/REORG.TODO/io/readlinkat.c b/REORG.TODO/io/readlinkat.c new file mode 100644 index 0000000000..ef40297199 --- /dev/null +++ b/REORG.TODO/io/readlinkat.c @@ -0,0 +1,44 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <unistd.h> + +/* Read the contents of the symbolic link PATH relative to FD into no + more than LEN bytes of BUF. The contents are not null-terminated. + Returns the number of characters read, or -1 for errors. */ +ssize_t +readlinkat (int fd, const char *path, char *buf, size_t len) +{ + if (path == NULL) + { + __set_errno (EINVAL); + return -1; + } + + if (fd != AT_FDCWD && fd < 0 && *path != '/') + { + __set_errno (EBADF); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (readlinkat) +libc_hidden_def (readlinkat) diff --git a/REORG.TODO/io/rmdir.c b/REORG.TODO/io/rmdir.c new file mode 100644 index 0000000000..63ab144b73 --- /dev/null +++ b/REORG.TODO/io/rmdir.c @@ -0,0 +1,38 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> + + +/* Remove the directory PATH. */ +int +__rmdir (const char *path) +{ + if (path == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (rmdir) + +weak_alias (__rmdir, rmdir) diff --git a/REORG.TODO/io/sendfile.c b/REORG.TODO/io/sendfile.c new file mode 100644 index 0000000000..09c4f5acb7 --- /dev/null +++ b/REORG.TODO/io/sendfile.c @@ -0,0 +1,30 @@ +/* sendfile -- copy data directly from one file descriptor to another + Copyright (C) 2002-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/sendfile.h> +#include <errno.h> + +/* Send COUNT bytes from file associated with IN_FD starting at OFFSET to + descriptor OUT_FD. */ +ssize_t +sendfile (int out_fd, int in_fd, off_t *offset, size_t count) +{ + __set_errno (ENOSYS); + return -1; +} +stub_warning (sendfile) diff --git a/REORG.TODO/io/sendfile64.c b/REORG.TODO/io/sendfile64.c new file mode 100644 index 0000000000..766ddf9fa6 --- /dev/null +++ b/REORG.TODO/io/sendfile64.c @@ -0,0 +1,30 @@ +/* sendfile -- copy data directly from one file descriptor to another + Copyright (C) 2002-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/sendfile.h> +#include <errno.h> + +/* Send COUNT bytes from file associated with IN_FD starting at OFFSET to + descriptor OUT_FD. */ +ssize_t +sendfile64 (int out_fd, int in_fd, off64_t *offset, size_t count) +{ + __set_errno (ENOSYS); + return -1; +} +stub_warning (sendfile64) diff --git a/REORG.TODO/io/stat.c b/REORG.TODO/io/stat.c new file mode 100644 index 0000000000..a51278bc64 --- /dev/null +++ b/REORG.TODO/io/stat.c @@ -0,0 +1,54 @@ +/* Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file with other + programs, and to distribute those programs without any restriction + coming from the use of this file. (The GNU Lesser General Public + License restrictions do apply in other respects; for example, they + cover modification of the file, and distribution when not linked + into another program.) + + Note that people who make modified versions of this file are not + obligated to grant this special exception for their modified + versions; it is their choice whether to do so. The GNU Lesser + General Public License gives permission to release a modified + version without this exception; this exception also makes it + possible to release a modified version which carries forward this + exception. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/stat.h> + +/* This definition is only used if inlining fails for this function; see + the last page of <sys/stat.h>. The real work is done by the `x' + function which is passed a version number argument. We arrange in the + makefile that when not inlined this function is always statically + linked; that way a dynamically-linked executable always encodes the + version number corresponding to the data structures it uses, so the `x' + functions in the shared library can adapt without needing to recompile + all callers. */ + +#undef stat +int +attribute_hidden +__stat (const char *file, struct stat *buf) +{ + return __xstat (_STAT_VER, file, buf); +} + +weak_hidden_alias (__stat, stat) diff --git a/REORG.TODO/io/stat64.c b/REORG.TODO/io/stat64.c new file mode 100644 index 0000000000..704cbb34a6 --- /dev/null +++ b/REORG.TODO/io/stat64.c @@ -0,0 +1,52 @@ +/* Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + In addition to the permissions in the GNU Lesser General Public + License, the Free Software Foundation gives you unlimited + permission to link the compiled version of this file with other + programs, and to distribute those programs without any restriction + coming from the use of this file. (The GNU Lesser General Public + License restrictions do apply in other respects; for example, they + cover modification of the file, and distribution when not linked + into another program.) + + Note that people who make modified versions of this file are not + obligated to grant this special exception for their modified + versions; it is their choice whether to do so. The GNU Lesser + General Public License gives permission to release a modified + version without this exception; this exception also makes it + possible to release a modified version which carries forward this + exception. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/stat.h> + +/* This definition is only used if inlining fails for this function; see + the last page of <sys/stat.h>. The real work is done by the `x' + function which is passed a version number argument. We arrange in the + makefile that when not inlined this function is always statically + linked; that way a dynamically-linked executable always encodes the + version number corresponding to the data structures it uses, so the `x' + functions in the shared library can adapt without needing to recompile + all callers. */ + +#undef stat64 +int +attribute_hidden +stat64 (const char *file, struct stat64 *buf) +{ + return __xstat64 (_STAT_VER, file, buf); +} diff --git a/REORG.TODO/io/statfs.c b/REORG.TODO/io/statfs.c new file mode 100644 index 0000000000..28f9ad81c5 --- /dev/null +++ b/REORG.TODO/io/statfs.c @@ -0,0 +1,33 @@ +/* statfs -- Return information about the filesystem on which FILE resides. + Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/statfs.h> +#include <stddef.h> + +/* Return information about the filesystem on which FILE resides. */ +int +__statfs (const char *file, struct statfs *buf) +{ + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__statfs) +weak_alias (__statfs, statfs) + +stub_warning (statfs) diff --git a/REORG.TODO/io/statfs64.c b/REORG.TODO/io/statfs64.c new file mode 100644 index 0000000000..b3974b610e --- /dev/null +++ b/REORG.TODO/io/statfs64.c @@ -0,0 +1,30 @@ +/* Copyright (C) 1998-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/statfs.h> + +/* Return information about the filesystem on which FILE resides. */ +int +__statfs64 (const char *file, struct statfs64 *buf) +{ + __set_errno (ENOSYS); + return -1; +} +weak_alias (__statfs64, statfs64) + +stub_warning (statfs64) diff --git a/REORG.TODO/io/statvfs.c b/REORG.TODO/io/statvfs.c new file mode 100644 index 0000000000..8daf80ba6c --- /dev/null +++ b/REORG.TODO/io/statvfs.c @@ -0,0 +1,32 @@ +/* Return information about the filesystem on which FILE resides. + Copyright (C) 1998-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/statvfs.h> +#include <stddef.h> + +/* Return information about the filesystem on which FILE resides. */ +int +__statvfs (const char *file, struct statvfs *buf) +{ + __set_errno (ENOSYS); + return -1; +} +weak_alias (__statvfs, statvfs) +libc_hidden_weak (statvfs) +stub_warning (statvfs) diff --git a/REORG.TODO/io/statvfs64.c b/REORG.TODO/io/statvfs64.c new file mode 100644 index 0000000000..c3f67c918e --- /dev/null +++ b/REORG.TODO/io/statvfs64.c @@ -0,0 +1,30 @@ +/* Copyright (C) 1998-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/statvfs.h> + +/* Return information about the filesystem on which FILE resides. */ +int +__statvfs64 (const char *file, struct statvfs64 *buf) +{ + __set_errno (ENOSYS); + return -1; +} +weak_alias (__statvfs64, statvfs64) + +stub_warning (statvfs64) diff --git a/REORG.TODO/io/symlink.c b/REORG.TODO/io/symlink.c new file mode 100644 index 0000000000..a8f7001710 --- /dev/null +++ b/REORG.TODO/io/symlink.c @@ -0,0 +1,38 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> + + +/* Make a link to FROM called TO. */ +int +__symlink (const char *from, const char *to) +{ + if (from == NULL || to == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (symlink) + +weak_alias (__symlink, symlink) diff --git a/REORG.TODO/io/symlinkat.c b/REORG.TODO/io/symlinkat.c new file mode 100644 index 0000000000..83a56f89f2 --- /dev/null +++ b/REORG.TODO/io/symlinkat.c @@ -0,0 +1,43 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stddef.h> +#include <unistd.h> + + +/* Make a link to FROM called TO relative to FD. */ +int +symlinkat (const char *from, int fd, const char *to) +{ + if (from == NULL || to == NULL) + { + __set_errno (EINVAL); + return -1; + } + + if (fd != AT_FDCWD && fd < 0 && *to != '/') + { + __set_errno (EBADF); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (symlinkat) diff --git a/REORG.TODO/io/sys/fcntl.h b/REORG.TODO/io/sys/fcntl.h new file mode 100644 index 0000000000..cd304557e7 --- /dev/null +++ b/REORG.TODO/io/sys/fcntl.h @@ -0,0 +1 @@ +#include <fcntl.h> diff --git a/REORG.TODO/io/sys/poll.h b/REORG.TODO/io/sys/poll.h new file mode 100644 index 0000000000..e34c2db5a9 --- /dev/null +++ b/REORG.TODO/io/sys/poll.h @@ -0,0 +1,76 @@ +/* Compatibility definitions for System V `poll' interface. + Copyright (C) 1994-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#ifndef _SYS_POLL_H +#define _SYS_POLL_H 1 + +#include <features.h> + +/* Get the platform dependent bits of `poll'. */ +#include <bits/poll.h> +#ifdef __USE_GNU +# include <bits/types/__sigset_t.h> +# include <bits/types/struct_timespec.h> +#endif + + +/* Type used for the number of file descriptors. */ +typedef unsigned long int nfds_t; + +/* Data structure describing a polling request. */ +struct pollfd + { + int fd; /* File descriptor to poll. */ + short int events; /* Types of events poller cares about. */ + short int revents; /* Types of events that actually occurred. */ + }; + + +__BEGIN_DECLS + +/* Poll the file descriptors described by the NFDS structures starting at + FDS. If TIMEOUT is nonzero and not -1, allow TIMEOUT milliseconds for + an event to occur; if TIMEOUT is -1, block until an event occurs. + Returns the number of file descriptors with events, zero if timed out, + or -1 for errors. + + This function is a cancellation point and therefore not marked with + __THROW. */ +extern int poll (struct pollfd *__fds, nfds_t __nfds, int __timeout); + +#ifdef __USE_GNU +/* Like poll, but before waiting the threads signal mask is replaced + with that specified in the fourth parameter. For better usability, + the timeout value is specified using a TIMESPEC object. + + This function is a cancellation point and therefore not marked with + __THROW. */ +extern int ppoll (struct pollfd *__fds, nfds_t __nfds, + const struct timespec *__timeout, + const __sigset_t *__ss); +#endif + +__END_DECLS + + +/* Define some inlines helping to catch common problems. */ +#if __USE_FORTIFY_LEVEL > 0 && defined __fortify_function +# include <bits/poll2.h> +#endif + +#endif /* sys/poll.h */ diff --git a/REORG.TODO/io/sys/sendfile.h b/REORG.TODO/io/sys/sendfile.h new file mode 100644 index 0000000000..1811227b35 --- /dev/null +++ b/REORG.TODO/io/sys/sendfile.h @@ -0,0 +1,51 @@ +/* sendfile -- copy data directly from one file descriptor to another + Copyright (C) 1998-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#ifndef _SYS_SENDFILE_H +#define _SYS_SENDFILE_H 1 + +#include <features.h> +#include <sys/types.h> + +__BEGIN_DECLS + +/* Send up to COUNT bytes from file associated with IN_FD starting at + *OFFSET to descriptor OUT_FD. Set *OFFSET to the IN_FD's file position + following the read bytes. If OFFSET is a null pointer, use the normal + file position instead. Return the number of written bytes, or -1 in + case of error. */ +#ifndef __USE_FILE_OFFSET64 +extern ssize_t sendfile (int __out_fd, int __in_fd, off_t *__offset, + size_t __count) __THROW; +#else +# ifdef __REDIRECT_NTH +extern ssize_t __REDIRECT_NTH (sendfile, + (int __out_fd, int __in_fd, __off64_t *__offset, + size_t __count), sendfile64); +# else +# define sendfile sendfile64 +# endif +#endif +#ifdef __USE_LARGEFILE64 +extern ssize_t sendfile64 (int __out_fd, int __in_fd, __off64_t *__offset, + size_t __count) __THROW; +#endif + +__END_DECLS + +#endif /* sys/sendfile.h */ diff --git a/REORG.TODO/io/sys/stat.h b/REORG.TODO/io/sys/stat.h new file mode 100644 index 0000000000..ac7ef1f572 --- /dev/null +++ b/REORG.TODO/io/sys/stat.h @@ -0,0 +1,533 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +/* + * POSIX Standard: 5.6 File Characteristics <sys/stat.h> + */ + +#ifndef _SYS_STAT_H +#define _SYS_STAT_H 1 + +#include <features.h> + +#include <bits/types.h> /* For __mode_t and __dev_t. */ + +#ifdef __USE_XOPEN2K8 +# include <bits/types/struct_timespec.h> +#endif + +#if defined __USE_XOPEN || defined __USE_XOPEN2K +/* The Single Unix specification says that some more types are + available here. */ + +# include <bits/types/time_t.h> + +# ifndef __dev_t_defined +typedef __dev_t dev_t; +# define __dev_t_defined +# endif + +# ifndef __gid_t_defined +typedef __gid_t gid_t; +# define __gid_t_defined +# endif + +# ifndef __ino_t_defined +# ifndef __USE_FILE_OFFSET64 +typedef __ino_t ino_t; +# else +typedef __ino64_t ino_t; +# endif +# define __ino_t_defined +# endif + +# ifndef __mode_t_defined +typedef __mode_t mode_t; +# define __mode_t_defined +# endif + +# ifndef __nlink_t_defined +typedef __nlink_t nlink_t; +# define __nlink_t_defined +# endif + +# ifndef __off_t_defined +# ifndef __USE_FILE_OFFSET64 +typedef __off_t off_t; +# else +typedef __off64_t off_t; +# endif +# define __off_t_defined +# endif + +# ifndef __uid_t_defined +typedef __uid_t uid_t; +# define __uid_t_defined +# endif +#endif /* X/Open */ + +#ifdef __USE_UNIX98 +# ifndef __blkcnt_t_defined +# ifndef __USE_FILE_OFFSET64 +typedef __blkcnt_t blkcnt_t; +# else +typedef __blkcnt64_t blkcnt_t; +# endif +# define __blkcnt_t_defined +# endif + +# ifndef __blksize_t_defined +typedef __blksize_t blksize_t; +# define __blksize_t_defined +# endif +#endif /* Unix98 */ + +__BEGIN_DECLS + +#include <bits/stat.h> + +#if defined __USE_MISC || defined __USE_XOPEN +# define S_IFMT __S_IFMT +# define S_IFDIR __S_IFDIR +# define S_IFCHR __S_IFCHR +# define S_IFBLK __S_IFBLK +# define S_IFREG __S_IFREG +# ifdef __S_IFIFO +# define S_IFIFO __S_IFIFO +# endif +# ifdef __S_IFLNK +# define S_IFLNK __S_IFLNK +# endif +# if (defined __USE_MISC || defined __USE_XOPEN_EXTENDED) \ + && defined __S_IFSOCK +# define S_IFSOCK __S_IFSOCK +# endif +#endif + +/* Test macros for file types. */ + +#define __S_ISTYPE(mode, mask) (((mode) & __S_IFMT) == (mask)) + +#define S_ISDIR(mode) __S_ISTYPE((mode), __S_IFDIR) +#define S_ISCHR(mode) __S_ISTYPE((mode), __S_IFCHR) +#define S_ISBLK(mode) __S_ISTYPE((mode), __S_IFBLK) +#define S_ISREG(mode) __S_ISTYPE((mode), __S_IFREG) +#ifdef __S_IFIFO +# define S_ISFIFO(mode) __S_ISTYPE((mode), __S_IFIFO) +#endif +#ifdef __S_IFLNK +# define S_ISLNK(mode) __S_ISTYPE((mode), __S_IFLNK) +#endif + +#if defined __USE_MISC && !defined __S_IFLNK +# define S_ISLNK(mode) 0 +#endif + +#if (defined __USE_XOPEN_EXTENDED || defined __USE_XOPEN2K) \ + && defined __S_IFSOCK +# define S_ISSOCK(mode) __S_ISTYPE((mode), __S_IFSOCK) +#elif defined __USE_XOPEN2K +# define S_ISSOCK(mode) 0 +#endif + +/* These are from POSIX.1b. If the objects are not implemented using separate + distinct file types, the macros always will evaluate to zero. Unlike the + other S_* macros the following three take a pointer to a `struct stat' + object as the argument. */ +#ifdef __USE_POSIX199309 +# define S_TYPEISMQ(buf) __S_TYPEISMQ(buf) +# define S_TYPEISSEM(buf) __S_TYPEISSEM(buf) +# define S_TYPEISSHM(buf) __S_TYPEISSHM(buf) +#endif + + +/* Protection bits. */ + +#define S_ISUID __S_ISUID /* Set user ID on execution. */ +#define S_ISGID __S_ISGID /* Set group ID on execution. */ + +#if defined __USE_MISC || defined __USE_XOPEN +/* Save swapped text after use (sticky bit). This is pretty well obsolete. */ +# define S_ISVTX __S_ISVTX +#endif + +#define S_IRUSR __S_IREAD /* Read by owner. */ +#define S_IWUSR __S_IWRITE /* Write by owner. */ +#define S_IXUSR __S_IEXEC /* Execute by owner. */ +/* Read, write, and execute by owner. */ +#define S_IRWXU (__S_IREAD|__S_IWRITE|__S_IEXEC) + +#ifdef __USE_MISC +# define S_IREAD S_IRUSR +# define S_IWRITE S_IWUSR +# define S_IEXEC S_IXUSR +#endif + +#define S_IRGRP (S_IRUSR >> 3) /* Read by group. */ +#define S_IWGRP (S_IWUSR >> 3) /* Write by group. */ +#define S_IXGRP (S_IXUSR >> 3) /* Execute by group. */ +/* Read, write, and execute by group. */ +#define S_IRWXG (S_IRWXU >> 3) + +#define S_IROTH (S_IRGRP >> 3) /* Read by others. */ +#define S_IWOTH (S_IWGRP >> 3) /* Write by others. */ +#define S_IXOTH (S_IXGRP >> 3) /* Execute by others. */ +/* Read, write, and execute by others. */ +#define S_IRWXO (S_IRWXG >> 3) + + +#ifdef __USE_MISC +/* Macros for common mode bit masks. */ +# define ACCESSPERMS (S_IRWXU|S_IRWXG|S_IRWXO) /* 0777 */ +# define ALLPERMS (S_ISUID|S_ISGID|S_ISVTX|S_IRWXU|S_IRWXG|S_IRWXO)/* 07777 */ +# define DEFFILEMODE (S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH|S_IWOTH)/* 0666*/ + +# define S_BLKSIZE 512 /* Block size for `st_blocks'. */ +#endif + + +#ifndef __USE_FILE_OFFSET64 +/* Get file attributes for FILE and put them in BUF. */ +extern int stat (const char *__restrict __file, + struct stat *__restrict __buf) __THROW __nonnull ((1, 2)); + +/* Get file attributes for the file, device, pipe, or socket + that file descriptor FD is open on and put them in BUF. */ +extern int fstat (int __fd, struct stat *__buf) __THROW __nonnull ((2)); +#else +# ifdef __REDIRECT_NTH +extern int __REDIRECT_NTH (stat, (const char *__restrict __file, + struct stat *__restrict __buf), stat64) + __nonnull ((1, 2)); +extern int __REDIRECT_NTH (fstat, (int __fd, struct stat *__buf), fstat64) + __nonnull ((2)); +# else +# define stat stat64 +# define fstat fstat64 +# endif +#endif +#ifdef __USE_LARGEFILE64 +extern int stat64 (const char *__restrict __file, + struct stat64 *__restrict __buf) __THROW __nonnull ((1, 2)); +extern int fstat64 (int __fd, struct stat64 *__buf) __THROW __nonnull ((2)); +#endif + +#ifdef __USE_ATFILE +/* Similar to stat, get the attributes for FILE and put them in BUF. + Relative path names are interpreted relative to FD unless FD is + AT_FDCWD. */ +# ifndef __USE_FILE_OFFSET64 +extern int fstatat (int __fd, const char *__restrict __file, + struct stat *__restrict __buf, int __flag) + __THROW __nonnull ((2, 3)); +# else +# ifdef __REDIRECT_NTH +extern int __REDIRECT_NTH (fstatat, (int __fd, const char *__restrict __file, + struct stat *__restrict __buf, + int __flag), + fstatat64) __nonnull ((2, 3)); +# else +# define fstatat fstatat64 +# endif +# endif + +# ifdef __USE_LARGEFILE64 +extern int fstatat64 (int __fd, const char *__restrict __file, + struct stat64 *__restrict __buf, int __flag) + __THROW __nonnull ((2, 3)); +# endif +#endif + +#if defined __USE_XOPEN_EXTENDED || defined __USE_XOPEN2K +# ifndef __USE_FILE_OFFSET64 +/* Get file attributes about FILE and put them in BUF. + If FILE is a symbolic link, do not follow it. */ +extern int lstat (const char *__restrict __file, + struct stat *__restrict __buf) __THROW __nonnull ((1, 2)); +# else +# ifdef __REDIRECT_NTH +extern int __REDIRECT_NTH (lstat, + (const char *__restrict __file, + struct stat *__restrict __buf), lstat64) + __nonnull ((1, 2)); +# else +# define lstat lstat64 +# endif +# endif +# ifdef __USE_LARGEFILE64 +extern int lstat64 (const char *__restrict __file, + struct stat64 *__restrict __buf) + __THROW __nonnull ((1, 2)); +# endif +#endif + +/* Set file access permissions for FILE to MODE. + If FILE is a symbolic link, this affects its target instead. */ +extern int chmod (const char *__file, __mode_t __mode) + __THROW __nonnull ((1)); + +#ifdef __USE_MISC +/* Set file access permissions for FILE to MODE. + If FILE is a symbolic link, this affects the link itself + rather than its target. */ +extern int lchmod (const char *__file, __mode_t __mode) + __THROW __nonnull ((1)); +#endif + +/* Set file access permissions of the file FD is open on to MODE. */ +#if defined __USE_POSIX199309 || defined __USE_XOPEN_EXTENDED +extern int fchmod (int __fd, __mode_t __mode) __THROW; +#endif + +#ifdef __USE_ATFILE +/* Set file access permissions of FILE relative to + the directory FD is open on. */ +extern int fchmodat (int __fd, const char *__file, __mode_t __mode, + int __flag) + __THROW __nonnull ((2)) __wur; +#endif /* Use ATFILE. */ + + + +/* Set the file creation mask of the current process to MASK, + and return the old creation mask. */ +extern __mode_t umask (__mode_t __mask) __THROW; + +#ifdef __USE_GNU +/* Get the current `umask' value without changing it. + This function is only available under the GNU Hurd. */ +extern __mode_t getumask (void) __THROW; +#endif + +/* Create a new directory named PATH, with permission bits MODE. */ +extern int mkdir (const char *__path, __mode_t __mode) + __THROW __nonnull ((1)); + +#ifdef __USE_ATFILE +/* Like mkdir, create a new directory with permission bits MODE. But + interpret relative PATH names relative to the directory associated + with FD. */ +extern int mkdirat (int __fd, const char *__path, __mode_t __mode) + __THROW __nonnull ((2)); +#endif + +/* Create a device file named PATH, with permission and special bits MODE + and device number DEV (which can be constructed from major and minor + device numbers with the `makedev' macro above). */ +#if defined __USE_MISC || defined __USE_XOPEN_EXTENDED +extern int mknod (const char *__path, __mode_t __mode, __dev_t __dev) + __THROW __nonnull ((1)); + +# ifdef __USE_ATFILE +/* Like mknod, create a new device file with permission bits MODE and + device number DEV. But interpret relative PATH names relative to + the directory associated with FD. */ +extern int mknodat (int __fd, const char *__path, __mode_t __mode, + __dev_t __dev) __THROW __nonnull ((2)); +# endif +#endif + + +/* Create a new FIFO named PATH, with permission bits MODE. */ +extern int mkfifo (const char *__path, __mode_t __mode) + __THROW __nonnull ((1)); + +#ifdef __USE_ATFILE +/* Like mkfifo, create a new FIFO with permission bits MODE. But + interpret relative PATH names relative to the directory associated + with FD. */ +extern int mkfifoat (int __fd, const char *__path, __mode_t __mode) + __THROW __nonnull ((2)); +#endif + +#ifdef __USE_ATFILE +/* Set file access and modification times relative to directory file + descriptor. */ +extern int utimensat (int __fd, const char *__path, + const struct timespec __times[2], + int __flags) + __THROW __nonnull ((2)); +#endif + +#ifdef __USE_XOPEN2K8 +/* Set file access and modification times of the file associated with FD. */ +extern int futimens (int __fd, const struct timespec __times[2]) __THROW; +#endif + +/* To allow the `struct stat' structure and the file type `mode_t' + bits to vary without changing shared library major version number, + the `stat' family of functions and `mknod' are in fact inline + wrappers around calls to `xstat', `fxstat', `lxstat', and `xmknod', + which all take a leading version-number argument designating the + data structure and bits used. <bits/stat.h> defines _STAT_VER with + the version number corresponding to `struct stat' as defined in + that file; and _MKNOD_VER with the version number corresponding to + the S_IF* macros defined therein. It is arranged that when not + inlined these function are always statically linked; that way a + dynamically-linked executable always encodes the version number + corresponding to the data structures it uses, so the `x' functions + in the shared library can adapt without needing to recompile all + callers. */ + +#ifndef _STAT_VER +# define _STAT_VER 0 +#endif +#ifndef _MKNOD_VER +# define _MKNOD_VER 0 +#endif + +/* Wrappers for stat and mknod system calls. */ +#ifndef __USE_FILE_OFFSET64 +extern int __fxstat (int __ver, int __fildes, struct stat *__stat_buf) + __THROW __nonnull ((3)); +extern int __xstat (int __ver, const char *__filename, + struct stat *__stat_buf) __THROW __nonnull ((2, 3)); +extern int __lxstat (int __ver, const char *__filename, + struct stat *__stat_buf) __THROW __nonnull ((2, 3)); +extern int __fxstatat (int __ver, int __fildes, const char *__filename, + struct stat *__stat_buf, int __flag) + __THROW __nonnull ((3, 4)); +#else +# ifdef __REDIRECT_NTH +extern int __REDIRECT_NTH (__fxstat, (int __ver, int __fildes, + struct stat *__stat_buf), __fxstat64) + __nonnull ((3)); +extern int __REDIRECT_NTH (__xstat, (int __ver, const char *__filename, + struct stat *__stat_buf), __xstat64) + __nonnull ((2, 3)); +extern int __REDIRECT_NTH (__lxstat, (int __ver, const char *__filename, + struct stat *__stat_buf), __lxstat64) + __nonnull ((2, 3)); +extern int __REDIRECT_NTH (__fxstatat, (int __ver, int __fildes, + const char *__filename, + struct stat *__stat_buf, int __flag), + __fxstatat64) __nonnull ((3, 4)); + +# else +# define __fxstat __fxstat64 +# define __xstat __xstat64 +# define __lxstat __lxstat64 +# endif +#endif + +#ifdef __USE_LARGEFILE64 +extern int __fxstat64 (int __ver, int __fildes, struct stat64 *__stat_buf) + __THROW __nonnull ((3)); +extern int __xstat64 (int __ver, const char *__filename, + struct stat64 *__stat_buf) __THROW __nonnull ((2, 3)); +extern int __lxstat64 (int __ver, const char *__filename, + struct stat64 *__stat_buf) __THROW __nonnull ((2, 3)); +extern int __fxstatat64 (int __ver, int __fildes, const char *__filename, + struct stat64 *__stat_buf, int __flag) + __THROW __nonnull ((3, 4)); +#endif +extern int __xmknod (int __ver, const char *__path, __mode_t __mode, + __dev_t *__dev) __THROW __nonnull ((2, 4)); + +extern int __xmknodat (int __ver, int __fd, const char *__path, + __mode_t __mode, __dev_t *__dev) + __THROW __nonnull ((3, 5)); + +#ifdef __USE_EXTERN_INLINES +/* Inlined versions of the real stat and mknod functions. */ + +__extern_inline int +__NTH (stat (const char *__path, struct stat *__statbuf)) +{ + return __xstat (_STAT_VER, __path, __statbuf); +} + +# if defined __USE_MISC || defined __USE_XOPEN_EXTENDED +__extern_inline int +__NTH (lstat (const char *__path, struct stat *__statbuf)) +{ + return __lxstat (_STAT_VER, __path, __statbuf); +} +# endif + +__extern_inline int +__NTH (fstat (int __fd, struct stat *__statbuf)) +{ + return __fxstat (_STAT_VER, __fd, __statbuf); +} + +# ifdef __USE_ATFILE +__extern_inline int +__NTH (fstatat (int __fd, const char *__filename, struct stat *__statbuf, + int __flag)) +{ + return __fxstatat (_STAT_VER, __fd, __filename, __statbuf, __flag); +} +# endif + +# ifdef __USE_MISC +__extern_inline int +__NTH (mknod (const char *__path, __mode_t __mode, __dev_t __dev)) +{ + return __xmknod (_MKNOD_VER, __path, __mode, &__dev); +} +# endif + +# ifdef __USE_ATFILE +__extern_inline int +__NTH (mknodat (int __fd, const char *__path, __mode_t __mode, + __dev_t __dev)) +{ + return __xmknodat (_MKNOD_VER, __fd, __path, __mode, &__dev); +} +# endif + +# if defined __USE_LARGEFILE64 \ + && (! defined __USE_FILE_OFFSET64 \ + || (defined __REDIRECT_NTH && defined __OPTIMIZE__)) +__extern_inline int +__NTH (stat64 (const char *__path, struct stat64 *__statbuf)) +{ + return __xstat64 (_STAT_VER, __path, __statbuf); +} + +# if defined __USE_MISC || defined __USE_XOPEN_EXTENDED +__extern_inline int +__NTH (lstat64 (const char *__path, struct stat64 *__statbuf)) +{ + return __lxstat64 (_STAT_VER, __path, __statbuf); +} +# endif + +__extern_inline int +__NTH (fstat64 (int __fd, struct stat64 *__statbuf)) +{ + return __fxstat64 (_STAT_VER, __fd, __statbuf); +} + +# ifdef __USE_ATFILE +__extern_inline int +__NTH (fstatat64 (int __fd, const char *__filename, struct stat64 *__statbuf, + int __flag)) +{ + return __fxstatat64 (_STAT_VER, __fd, __filename, __statbuf, __flag); +} +# endif + +# endif + +#endif + +__END_DECLS + + +#endif /* sys/stat.h */ diff --git a/REORG.TODO/io/sys/statfs.h b/REORG.TODO/io/sys/statfs.h new file mode 100644 index 0000000000..8b78141460 --- /dev/null +++ b/REORG.TODO/io/sys/statfs.h @@ -0,0 +1,67 @@ +/* Definitions for getting information about a filesystem. + Copyright (C) 1996-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#ifndef _SYS_STATFS_H +#define _SYS_STATFS_H 1 + +#include <features.h> + +/* Get the system-specific definition of `struct statfs'. */ +#include <bits/statfs.h> + +__BEGIN_DECLS + +/* Return information about the filesystem on which FILE resides. */ +#ifndef __USE_FILE_OFFSET64 +extern int statfs (const char *__file, struct statfs *__buf) + __THROW __nonnull ((1, 2)); +#else +# ifdef __REDIRECT_NTH +extern int __REDIRECT_NTH (statfs, + (const char *__file, struct statfs *__buf), + statfs64) __nonnull ((1, 2)); +# else +# define statfs statfs64 +# endif +#endif +#ifdef __USE_LARGEFILE64 +extern int statfs64 (const char *__file, struct statfs64 *__buf) + __THROW __nonnull ((1, 2)); +#endif + +/* Return information about the filesystem containing the file FILDES + refers to. */ +#ifndef __USE_FILE_OFFSET64 +extern int fstatfs (int __fildes, struct statfs *__buf) + __THROW __nonnull ((2)); +#else +# ifdef __REDIRECT_NTH +extern int __REDIRECT_NTH (fstatfs, (int __fildes, struct statfs *__buf), + fstatfs64) __nonnull ((2)); +# else +# define fstatfs fstatfs64 +# endif +#endif +#ifdef __USE_LARGEFILE64 +extern int fstatfs64 (int __fildes, struct statfs64 *__buf) + __THROW __nonnull ((2)); +#endif + +__END_DECLS + +#endif /* sys/statfs.h */ diff --git a/REORG.TODO/io/sys/statvfs.h b/REORG.TODO/io/sys/statvfs.h new file mode 100644 index 0000000000..19ac18f6e0 --- /dev/null +++ b/REORG.TODO/io/sys/statvfs.h @@ -0,0 +1,90 @@ +/* Definitions for getting information about a filesystem. + Copyright (C) 1998-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#ifndef _SYS_STATVFS_H +#define _SYS_STATVFS_H 1 + +#include <features.h> + +/* Get the system-specific definition of `struct statfs'. */ +#include <bits/statvfs.h> + +#ifndef __USE_FILE_OFFSET64 +# ifndef __fsblkcnt_t_defined +typedef __fsblkcnt_t fsblkcnt_t; /* Type to count file system blocks. */ +# define __fsblkcnt_t_defined +# endif +# ifndef __fsfilcnt_t_defined +typedef __fsfilcnt_t fsfilcnt_t; /* Type to count file system inodes. */ +# define __fsfilcnt_t_defined +# endif +#else +# ifndef __fsblkcnt_t_defined +typedef __fsblkcnt64_t fsblkcnt_t; /* Type to count file system blocks. */ +# define __fsblkcnt_t_defined +# endif +# ifndef __fsfilcnt_t_defined +typedef __fsfilcnt64_t fsfilcnt_t; /* Type to count file system inodes. */ +# define __fsfilcnt_t_defined +# endif +#endif + +__BEGIN_DECLS + +/* Return information about the filesystem on which FILE resides. */ +#ifndef __USE_FILE_OFFSET64 +extern int statvfs (const char *__restrict __file, + struct statvfs *__restrict __buf) + __THROW __nonnull ((1, 2)); +#else +# ifdef __REDIRECT_NTH +extern int __REDIRECT_NTH (statvfs, + (const char *__restrict __file, + struct statvfs *__restrict __buf), statvfs64) + __nonnull ((1, 2)); +# else +# define statvfs statvfs64 +# endif +#endif +#ifdef __USE_LARGEFILE64 +extern int statvfs64 (const char *__restrict __file, + struct statvfs64 *__restrict __buf) + __THROW __nonnull ((1, 2)); +#endif + +/* Return information about the filesystem containing the file FILDES + refers to. */ +#ifndef __USE_FILE_OFFSET64 +extern int fstatvfs (int __fildes, struct statvfs *__buf) + __THROW __nonnull ((2)); +#else +# ifdef __REDIRECT_NTH +extern int __REDIRECT_NTH (fstatvfs, (int __fildes, struct statvfs *__buf), + fstatvfs64) __nonnull ((2)); +# else +# define fstatvfs fstatvfs64 +# endif +#endif +#ifdef __USE_LARGEFILE64 +extern int fstatvfs64 (int __fildes, struct statvfs64 *__buf) + __THROW __nonnull ((2)); +#endif + +__END_DECLS + +#endif /* sys/statvfs.h */ diff --git a/REORG.TODO/io/sys/vfs.h b/REORG.TODO/io/sys/vfs.h new file mode 100644 index 0000000000..fa22d31c4c --- /dev/null +++ b/REORG.TODO/io/sys/vfs.h @@ -0,0 +1,4 @@ +/* Other systems declare `struct statfs' et al in <sys/vfs.h>, + so we have this file to be compatible with programs expecting it. */ + +#include <sys/statfs.h> diff --git a/REORG.TODO/io/test-lfs.c b/REORG.TODO/io/test-lfs.c new file mode 100644 index 0000000000..14773544da --- /dev/null +++ b/REORG.TODO/io/test-lfs.c @@ -0,0 +1,241 @@ +/* Some basic tests for LFS. + Copyright (C) 2000-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Andreas Jaeger <aj@suse.de>, 2000. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <unistd.h> +#include <stdlib.h> +#include <sys/types.h> +#include <sys/stat.h> +#include <fcntl.h> +#include <error.h> +#include <errno.h> +#include <sys/resource.h> + +/* Prototype for our test function. */ +extern void do_prepare (int argc, char *argv[]); +extern int do_test (int argc, char *argv[]); + +/* We have a preparation function. */ +#define PREPARE do_prepare + +/* We might need a bit longer timeout. */ +#define TIMEOUT 20 /* sec */ + +/* This defines the `main' function and some more. */ +#include <test-skeleton.c> + +/* These are for the temporary file we generate. */ +char *name; +int fd; + +/* 2^31 = 2GB. */ +#define TWO_GB 2147483648LL + +void +do_prepare (int argc, char *argv[]) +{ + size_t name_len; + struct rlimit64 rlim; + + name_len = strlen (test_dir); + name = xmalloc (name_len + sizeof ("/lfsXXXXXX")); + mempcpy (mempcpy (name, test_dir, name_len), + "/lfsXXXXXX", sizeof ("/lfsXXXXXX")); + + /* Open our test file. */ + fd = mkstemp64 (name); + if (fd == -1) + { + if (errno == ENOSYS) + { + /* Fail silently. */ + error (0, 0, "open64 is not supported"); + exit (EXIT_SUCCESS); + } + else + error (EXIT_FAILURE, errno, "cannot create temporary file"); + } + add_temp_file (name); + + if (getrlimit64 (RLIMIT_FSIZE, &rlim) != 0) + { + error (0, errno, "cannot get resource limit"); + exit (0); + } + if (rlim.rlim_cur < TWO_GB + 200) + { + rlim.rlim_cur = TWO_GB + 200; + if (setrlimit64 (RLIMIT_FSIZE, &rlim) != 0) + { + error (0, errno, "cannot reset file size limits"); + exit (0); + } + } +} + +static void +test_ftello (void) +{ + FILE *f; + int ret; + off64_t pos; + + f = fopen64 (name, "w"); + + ret = fseeko64 (f, TWO_GB+100, SEEK_SET); + if (ret == -1 && errno == ENOSYS) + { + error (0, 0, "fseeko64 is not supported."); + exit (EXIT_SUCCESS); + } + if (ret == -1 && errno == EINVAL) + { + error (0, 0, "LFS seems not to be supported"); + exit (EXIT_SUCCESS); + } + if (ret == -1) + { + error (0, errno, "fseeko64 failed with error"); + exit (EXIT_FAILURE); + } + + ret = fwrite ("Hello", 1, 5, f); + if (ret == -1 && errno == EFBIG) + { + error (0, errno, "LFS seems not to be supported"); + exit (EXIT_SUCCESS); + } + + if (ret == -1 && errno == ENOSPC) + { + error (0, 0, "Not enough space to write file."); + exit (EXIT_SUCCESS); + } + + if (ret != 5) + error (EXIT_FAILURE, errno, "Cannot write test string to large file"); + + pos = ftello64 (f); + + if (pos != TWO_GB+105) + { + error (0, 0, "ftello64 gives wrong result."); + exit (EXIT_FAILURE); + } + + fclose (f); +} + +int +do_test (int argc, char *argv[]) +{ + int ret, fd2; + struct stat64 statbuf; + + ret = lseek64 (fd, TWO_GB+100, SEEK_SET); + if (ret == -1 && errno == ENOSYS) + { + error (0, 0, "lseek64 is not supported."); + exit (EXIT_SUCCESS); + } + if (ret == -1 && errno == EINVAL) + { + error (0, 0, "LFS seems not to be supported."); + exit (EXIT_SUCCESS); + } + if (ret == -1) + { + error (0, errno, "lseek64 failed with error"); + exit (EXIT_FAILURE); + } + off64_t offset64 = lseek64 (fd, 0, SEEK_CUR); + if (offset64 != TWO_GB + 100) + { + error (0, 0, "lseek64 did not return expected offset"); + exit (EXIT_FAILURE); + } + off_t offset = lseek (fd, 0, SEEK_CUR); + if (sizeof (off_t) < sizeof (off64_t)) + { + if (offset != -1 || errno != EOVERFLOW) + { + error (0, 0, "lseek did not fail with EOVERFLOW"); + exit (EXIT_FAILURE); + } + } + else + if (offset != TWO_GB + 100) + { + error (0, 0, "lseek did not return expected offset"); + exit (EXIT_FAILURE); + } + + ret = write (fd, "Hello", 5); + if (ret == -1 && errno == EFBIG) + { + error (0, 0, "LFS seems not to be supported."); + exit (EXIT_SUCCESS); + } + + if (ret == -1 && errno == ENOSPC) + { + error (0, 0, "Not enough space to write file."); + exit (EXIT_SUCCESS); + } + + if (ret != 5) + error (EXIT_FAILURE, errno, "cannot write test string to large file"); + + ret = close (fd); + + if (ret == -1) + error (EXIT_FAILURE, errno, "error closing file"); + + ret = stat64 (name, &statbuf); + + if (ret == -1 && (errno == ENOSYS || errno == EOVERFLOW)) + error (0, 0, "stat64 is not supported."); + else if (ret == -1) + error (EXIT_FAILURE, errno, "cannot stat file `%s'", name); + else if (statbuf.st_size != (TWO_GB + 100 + 5)) + error (EXIT_FAILURE, 0, "stat reported size %lld instead of %lld.", + (long long int) statbuf.st_size, (TWO_GB + 100 + 5)); + + fd2 = openat64 (AT_FDCWD, name, O_RDWR); + if (fd2 == -1) + { + if (errno == ENOSYS) + { + /* Silently ignore this test. */ + error (0, 0, "openat64 is not supported"); + } + else + error (EXIT_FAILURE, errno, "openat64 failed to open big file"); + } + else + { + ret = close (fd2); + + if (ret == -1) + error (EXIT_FAILURE, errno, "error closing file"); + } + + test_ftello (); + + return 0; +} diff --git a/REORG.TODO/io/test-stat.c b/REORG.TODO/io/test-stat.c new file mode 100644 index 0000000000..e0ff992da7 --- /dev/null +++ b/REORG.TODO/io/test-stat.c @@ -0,0 +1,70 @@ +/* Copyright (C) 2000-2017 Free Software Foundation, Inc. + Contributed by Maciej W. Rozycki <macro@ds2.pg.gda.pl>, 2000. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +/* We need to define: +#define _FILE_OFFSET_BITS 64 +#define _LARGEFILE64_SOURCE 1 +*/ + +#include <assert.h> +#include <stddef.h> +#include <sys/stat.h> + +static int +do_test (void) +{ + /* With _FILE_OFFSET_BITS=64 struct stat and struct stat64 should + be identical. */ + assert (sizeof (struct stat) + == sizeof (struct stat64)); + assert (offsetof (struct stat, st_dev) + == offsetof (struct stat64, st_dev)); + assert (offsetof (struct stat, st_ino) + == offsetof (struct stat64, st_ino)); + assert (offsetof (struct stat, st_mode) + == offsetof (struct stat64, st_mode)); + assert (offsetof (struct stat, st_nlink) + == offsetof (struct stat64, st_nlink)); + assert (offsetof (struct stat, st_uid) + == offsetof (struct stat64, st_uid)); + assert (offsetof (struct stat, st_gid) + == offsetof (struct stat64, st_gid)); + assert (offsetof (struct stat, st_rdev) + == offsetof (struct stat64, st_rdev)); + assert (offsetof (struct stat, st_size) + == offsetof (struct stat64, st_size)); + assert (offsetof (struct stat, st_atime) + == offsetof (struct stat64, st_atime)); + assert (offsetof (struct stat, st_mtime) + == offsetof (struct stat64, st_mtime)); + assert (offsetof (struct stat, st_ctime) + == offsetof (struct stat64, st_ctime)); + assert (offsetof (struct stat, st_blksize) + == offsetof (struct stat64, st_blksize)); + assert (offsetof (struct stat, st_blocks) + == offsetof (struct stat64, st_blocks)); +#if 0 + /* Some systems have st_fstype but not all. Don't check it for now. */ + assert (offsetof (struct stat, st_fstype) + == offsetof (struct stat64, st_fstype)); +#endif + return 0; +} + +#define TEST_FUNCTION do_test () +#include "../test-skeleton.c" diff --git a/REORG.TODO/io/test-stat2.c b/REORG.TODO/io/test-stat2.c new file mode 100644 index 0000000000..247a6e0e39 --- /dev/null +++ b/REORG.TODO/io/test-stat2.c @@ -0,0 +1,87 @@ +/* Test consistence of results of stat and stat64. + Copyright (C) 2000-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper <drepper@redhat.com>, 2000. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stdint.h> +#include <stdio.h> +#include <sys/stat.h> + +int +main (int argc, char *argv[]) +{ + int i; + int result = 0; + + for (i = 1; i < argc; ++i) + { + struct stat st; + struct stat64 st64; + int same; + + if (stat (argv[i], &st) != 0) + { + if (errno != EOVERFLOW) + { + /* Something is wrong. */ + printf ("stat(\"%s\",....) failed: %m", argv[i]); + result = 1; + } + continue; + } + + if (stat64 (argv[i], &st64) != 0) + { + if (errno != ENOSYS) + { + /* Something is wrong. */ + printf ("stat64(\"%s\",....) failed: %m", argv[i]); + result = 1; + } + continue; + } + + printf ("\nName: %s\n", argv[i]); + +#define TEST(name) \ + same = st.name == st64.name; \ + printf (#name ": %jd vs %jd %s\n", \ + (intmax_t) st.name, (intmax_t) st64.name, \ + same ? "OK" : "FAIL"); \ + result |= ! same + + TEST (st_dev); + TEST (st_ino); + TEST (st_mode); + TEST (st_nlink); + TEST (st_uid); + TEST (st_gid); +#ifdef _STATBUF_ST_RDEV + TEST (st_rdev); +#endif +#ifdef _STATBUF_ST_BLKSIZE + TEST (st_blksize); +#endif + TEST (st_blocks); + TEST (st_atime); + TEST (st_mtime); + TEST (st_ctime); + } + + return result; +} diff --git a/REORG.TODO/io/test-utime.c b/REORG.TODO/io/test-utime.c new file mode 100644 index 0000000000..3e7583c9c0 --- /dev/null +++ b/REORG.TODO/io/test-utime.c @@ -0,0 +1,141 @@ +/* Copyright (C) 1994-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <fcntl.h> +#include <stdint.h> +#include <stdio.h> +#include <stdlib.h> +#include <sys/stat.h> +#include <unistd.h> +#include <utime.h> +#include <time.h> + +int +main (int argc, char *argv[]) +{ + char file[L_tmpnam]; + struct utimbuf ut; + struct stat st; + struct stat stnow; + time_t now1, now2; + int fd; + + if (tmpnam (file) == 0) + { + perror ("tmpnam"); + return 1; + } + + fd = creat (file, 0666); + if (fd < 0) + { + perror ("creat"); + return 1; + } + close (fd); + + /* Test utime with arg */ + ut.actime = 500000000; + ut.modtime = 500000001; + if (utime (file, &ut)) + { + perror ("utime"); + remove (file); + return 1; + } + + if (stat (file, &st)) + { + perror ("stat"); + remove (file); + return 1; + } + + /* Test utime with NULL. + Since there's a race condition possible here, we check + the time before and after the call to utime. */ + now1 = time (NULL); + if (now1 == (time_t)-1) + { + perror ("time"); + remove (file); + return 1; + } + + /* The clocks used to set the modification time and that used in the + time() call need not be the same. They need not have the same + precision. Therefore we delay the following operation by one + second which makes sure we can compare with second precision. */ + sleep (1); + + if (utime (file, NULL)) + { + perror ("utime NULL"); + remove (file); + return 1; + } + + sleep (1); + + now2 = time (NULL); + if (now2 == (time_t)-1) + { + perror ("time"); + remove (file); + return 1; + } + + if (stat (file, &stnow)) + { + perror ("stat"); + remove (file); + return 1; + } + + remove (file); + + if (st.st_mtime != ut.modtime) + { + printf ("modtime %jd != %jd\n", + (intmax_t) st.st_mtime, (intmax_t) ut.modtime); + return 1; + } + + if (st.st_atime != ut.actime) + { + printf ("actime %jd != %jd\n", + (intmax_t) st.st_atime, (intmax_t) ut.actime); + return 1; + } + + if (stnow.st_mtime < now1 || stnow.st_mtime > now2) + { + printf ("modtime %jd <%jd >%jd\n", + (intmax_t) stnow.st_mtime, (intmax_t) now1, (intmax_t) now2); + return 1; + } + + if (stnow.st_atime < now1 || stnow.st_atime > now2) + { + printf ("actime %jd <%jd >%jd\n", + (intmax_t) stnow.st_atime, (intmax_t) now1, (intmax_t) now2); + return 1; + } + + puts ("Test succeeded."); + return 0; +} diff --git a/REORG.TODO/io/tst-faccessat.c b/REORG.TODO/io/tst-faccessat.c new file mode 100644 index 0000000000..7bdeed008c --- /dev/null +++ b/REORG.TODO/io/tst-faccessat.c @@ -0,0 +1,213 @@ +/* Test for faccessat function. */ + +#include <dirent.h> +#include <fcntl.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-faccessat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty save the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Try to create a file. */ + int fd = openat (dir_fd, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("file creation failed"); + return 1; + } + write (fd, "hello", 5); + puts ("file created"); + + /* Before closing the file, try using this file descriptor to open + another file. This must fail. */ + if (faccessat (fd, "should-not-work", F_OK, AT_EACCESS) != -1) + { + puts ("faccessat using descriptor for normal file worked"); + return 1; + } + if (errno != ENOTDIR) + { + puts ("\ +error for faccessat using descriptor for normal file not ENOTDIR "); + return 1; + } + + close (fd); + + int result = 0; + + if (faccessat (dir_fd, "some-file", F_OK, AT_EACCESS)) + { + printf ("faccessat F_OK: %m\n"); + result = 1; + } + if (faccessat (dir_fd, "some-file", W_OK, AT_EACCESS)) + { + printf ("faccessat W_OK: %m\n"); + result = 1; + } + + errno = 0; + if (faccessat (dir_fd, "some-file", X_OK, AT_EACCESS) == 0 + || errno != EACCES) + { + printf ("faccessat X_OK on nonexecutable: %m\n"); + result = 1; + } + + if (fchmodat (dir_fd, "some-file", 0400, 0) != 0) + { + printf ("fchownat failed: %m\n"); + return 1; + } + + if (faccessat (dir_fd, "some-file", R_OK, AT_EACCESS)) + { + printf ("faccessat R_OK: %m\n"); + result = 1; + } + + errno = 0; + if (faccessat (dir_fd, "some-file", W_OK, AT_EACCESS) == 0 + ? (geteuid () != 0) : (errno != EACCES)) + { + printf ("faccessat W_OK on unwritable file: %m\n"); + result = 1; + } + + /* Create a file descriptor which is closed again right away. */ + int dir_fd2 = dup (dir_fd); + if (dir_fd2 == -1) + { + puts ("dup failed"); + return 1; + } + close (dir_fd2); + + /* With the file descriptor closed the next call must fail. */ + if (faccessat (dir_fd2, "some-file", F_OK, AT_EACCESS) != -1) + { + puts ("faccessat using closed descriptor succeeded"); + return 1; + } + if (errno != EBADF) + { + puts ("faccessat using closed descriptor did not set EBADF"); + return 1; + } + + /* Same with a non-existing file. */ + if (faccessat (dir_fd2, "non-existing-file", F_OK, AT_EACCESS) != -1) + { + puts ("2nd faccessat using closed descriptor succeeded"); + return 1; + } + if (errno != EBADF) + { + puts ("2nd faccessat using closed descriptor did not set EBADF"); + return 1; + } + + if (unlinkat (dir_fd, "some-file", 0) != 0) + { + puts ("unlinkat failed"); + result = 1; + } + + close (dir_fd); + + fd = faccessat (-1, "some-file", F_OK, AT_EACCESS); + if (fd != -1) + { + puts ("faccessat using -1 descriptor succeeded"); + return 1; + } + if (errno != EBADF) + { + puts ("faccessat using -1 descriptor did not set EBADF"); + return 1; + } + + return result; +} diff --git a/REORG.TODO/io/tst-fchmodat.c b/REORG.TODO/io/tst-fchmodat.c new file mode 100644 index 0000000000..7d4a8717ff --- /dev/null +++ b/REORG.TODO/io/tst-fchmodat.c @@ -0,0 +1,192 @@ +/* Test for fchmodat function. */ + +#include <dirent.h> +#include <fcntl.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-fchmodat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty save the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + umask (022); + + /* Try to create a file. */ + int fd = openat (dir_fd, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("file creation failed"); + return 1; + } + write (fd, "hello", 5); + puts ("file created"); + + struct stat64 st1; + if (fstat64 (fd, &st1) != 0) + { + puts ("fstat64 failed"); + return 1; + } + + /* Before closing the file, try using this file descriptor to open + another file. This must fail. */ + if (fchmodat (fd, "some-file", 0400, 0) != -1) + { + puts ("fchmodat using descriptor for normal file worked"); + return 1; + } + if (errno != ENOTDIR) + { + puts ("\ +error for fchmodat using descriptor for normal file not ENOTDIR "); + return 1; + } + + close (fd); + + if ((st1.st_mode & 0777) != 0644) + { + printf ("openat created mode %04o, not 0644\n", (st1.st_mode & 0777)); + return 1; + } + + if (fchmodat (dir_fd, "some-file", 0400, 0) != 0) + { + puts ("fchownat failed"); + return 1; + } + + struct stat64 st2; + if (fstatat64 (dir_fd, "some-file", &st2, 0) != 0) + { + puts ("fstatat64 failed"); + return 1; + } + + if ((st2.st_mode & 0777) != 0400) + { + puts ("mode change failed"); + return 1; + } + + if (unlinkat (dir_fd, "some-file", 0) != 0) + { + puts ("unlinkat failed"); + return 1; + } + + /* Create a file descriptor which is closed again right away. */ + int dir_fd2 = dup (dir_fd); + if (dir_fd2 == -1) + { + puts ("dup failed"); + return 1; + } + close (dir_fd2); + + if (fchmodat (dir_fd2, "some-file", 0400, 0) != -1) + { + puts ("fchmodat using closed descriptor worked"); + return 1; + } + if (errno != EBADF) + { + puts ("error for fchmodat using closed descriptor not EBADF "); + return 1; + } + + close (dir_fd); + + if (fchmodat (-1, "some-file", 0400, 0) != -1) + { + puts ("fchmodat using invalid descriptor worked"); + return 1; + } + if (errno != EBADF) + { + puts ("error for fchmodat using invalid descriptor not EBADF "); + return 1; + } + + return 0; +} diff --git a/REORG.TODO/io/tst-fchownat.c b/REORG.TODO/io/tst-fchownat.c new file mode 100644 index 0000000000..e8adf6229f --- /dev/null +++ b/REORG.TODO/io/tst-fchownat.c @@ -0,0 +1,194 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ +#if _POSIX_CHOWN_RESTRICTED == 0 + if (pathconf (test_dir, _PC_CHOWN_RESTRICTED) != 0) +#endif + { + uid_t uid = getuid (); + if (uid != 0) + { + puts ("need root privileges"); + exit (0); + } + } + + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-fchownat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Try to create a file. */ + int fd = openat (dir_fd, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("file creation failed"); + return 1; + } + write (fd, "hello", 5); + puts ("file created"); + + struct stat64 st1; + if (fstat64 (fd, &st1) != 0) + { + puts ("fstat64 failed"); + return 1; + } + + /* Before closing the file, try using this file descriptor to open + another file. This must fail. */ + if (fchownat (fd, "some-file", 1, 1, 0) != -1) + { + puts ("fchownat using descriptor for normal file worked"); + return 1; + } + if (errno != ENOTDIR) + { + puts ("\ +error for fchownat using descriptor for normal file not ENOTDIR "); + return 1; + } + + close (fd); + + if (fchownat (dir_fd, "some-file", st1.st_uid + 1, st1.st_gid + 1, 0) != 0) + { + puts ("fchownat failed"); + return 1; + } + + struct stat64 st2; + if (fstatat64 (dir_fd, "some-file", &st2, 0) != 0) + { + puts ("fstatat64 failed"); + return 1; + } + + if (st1.st_uid + 1 != st2.st_uid || st1.st_gid + 1 != st2.st_gid) + { + puts ("owner change failed"); + return 1; + } + + if (unlinkat (dir_fd, "some-file", 0) != 0) + { + puts ("unlinkat failed"); + return 1; + } + + /* Create a file descriptor which is closed again right away. */ + int dir_fd2 = dup (dir_fd); + if (dir_fd2 == -1) + { + puts ("dup failed"); + return 1; + } + close (dir_fd2); + + if (fchownat (dir_fd2, "some-file", 1, 1, 0) != -1) + { + puts ("fchownat using closed descriptor worked"); + return 1; + } + if (errno != EBADF) + { + puts ("error for fchownat using closed descriptor not EBADF "); + return 1; + } + + close (dir_fd); + + if (fchownat (-1, "some-file", 1, 1, 0) != -1) + { + puts ("fchownat using invalid descriptor worked"); + return 1; + } + if (errno != EBADF) + { + puts ("error for fchownat using invalid descriptor not EBADF "); + return 1; + } + + return 0; +} diff --git a/REORG.TODO/io/tst-fcntl.c b/REORG.TODO/io/tst-fcntl.c new file mode 100644 index 0000000000..b7ea288e6c --- /dev/null +++ b/REORG.TODO/io/tst-fcntl.c @@ -0,0 +1,198 @@ +/* Tests for fcntl. + Copyright (C) 2000-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper <drepper@cygnus.com>, 2000. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <paths.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +/* Prototype for our test function. */ +extern void do_prepare (int argc, char *argv[]); +extern int do_test (int argc, char *argv[]); + +/* We have a preparation function. */ +#define PREPARE do_prepare + +#include "../test-skeleton.c" + + +/* Name of the temporary files. */ +static char *name; + +/* File descriptor to temporary file. */ +static int fd; + +void +do_prepare (int argc, char *argv[]) +{ + size_t name_len; + + name_len = strlen (test_dir); + name = xmalloc (name_len + sizeof ("/fcntlXXXXXX")); + mempcpy (mempcpy (name, test_dir, name_len), + "/fcntlXXXXXX", sizeof ("/fcntlXXXXXX")); + /* Create the temporary file. */ + fd = mkstemp (name); + if (fd == -1) + { + printf ("cannot open temporary file: %m\n"); + exit (1); + } + add_temp_file (name); +} + + +int +do_test (int argc, char *argv[]) +{ + int fd2; + int fd3; + struct stat64 st; + int val; + int result = 0; + + if (fstat64 (fd, &st) != 0) + { + printf ("cannot stat test file: %m\n"); + return 1; + } + if (! S_ISREG (st.st_mode) || st.st_size != 0) + { + puts ("file not created correctly"); + return 1; + } + + /* Get the flags with fcntl(). */ + val = fcntl (fd, F_GETFL); + if (val == -1) + { + printf ("fcntl(fd, F_GETFL) failed: %m\n"); + result = 1; + } + else if ((val & O_ACCMODE) != O_RDWR) + { + puts ("temporary file not opened for read and write"); + result = 1; + } + + /* Set the flags to something else. */ + if (fcntl (fd, F_SETFL, O_RDONLY) == -1) + { + printf ("fcntl(fd, F_SETFL, O_RDONLY) failed: %m\n"); + result = 1; + } + + val = fcntl (fd, F_GETFL); + if (val == -1) + { + printf ("fcntl(fd, F_GETFL) after F_SETFL failed: %m\n"); + result = 1; + } + else if ((val & O_ACCMODE) != O_RDWR) + { + puts ("temporary file access mode changed"); + result = 1; + } + + /* Set the flags to something else. */ + if (fcntl (fd, F_SETFL, O_APPEND) == -1) + { + printf ("fcntl(fd, F_SETFL, O_APPEND) failed: %m\n"); + result = 1; + } + + val = fcntl (fd, F_GETFL); + if (val == -1) + { + printf ("fcntl(fd, F_GETFL) after second F_SETFL failed: %m\n"); + result = 1; + } + else if ((val & O_APPEND) == 0) + { + puts ("O_APPEND not set"); + result = 1; + } + + val = fcntl (fd, F_GETFD); + if (val == -1) + { + printf ("fcntl(fd, F_GETFD) failed: %m\n"); + result = 1; + } + else if (fcntl (fd, F_SETFD, val | FD_CLOEXEC) == -1) + { + printf ("fcntl(fd, F_SETFD, FD_CLOEXEC) failed: %m\n"); + result = 1; + } + else + { + val = fcntl (fd, F_GETFD); + if (val == -1) + { + printf ("fcntl(fd, F_GETFD) after F_SETFD failed: %m\n"); + result = 1; + } + else if ((val & FD_CLOEXEC) == 0) + { + puts ("FD_CLOEXEC not set"); + result = 1; + } + } + + /* Get a number of a free descriptor. If /dev/null is not available + don't continue testing. */ + fd2 = open (_PATH_DEVNULL, O_RDWR); + if (fd2 == -1) + return result; + close (fd2); + + fd3 = fcntl (fd, F_DUPFD, fd2 + 1); + if (fd3 == -1) + { + printf ("fcntl(fd, F_DUPFD, %d) failed: %m\n", fd2 + 1); + result = 1; + } + else if (fd3 <= fd2) + { + printf ("F_DUPFD returned %d which is not larger than %d\n", fd3, fd2); + result = 1; + } + + if (fd3 != -1) + { + val = fcntl (fd3, F_GETFD); + if (val == -1) + { + printf ("fcntl(fd3, F_GETFD) after F_DUPFD failed: %m\n"); + result = 1; + } + else if ((val & FD_CLOEXEC) != 0) + { + puts ("FD_CLOEXEC still set"); + result = 1; + } + + close (fd3); + } + + return result; +} diff --git a/REORG.TODO/io/tst-fstatat.c b/REORG.TODO/io/tst-fstatat.c new file mode 100644 index 0000000000..4766bb2e71 --- /dev/null +++ b/REORG.TODO/io/tst-fstatat.c @@ -0,0 +1,189 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-fstatat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Try to create a file. */ + int fd = openat (dir_fd, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("file creation failed"); + return 1; + } + write (fd, "hello", 5); + puts ("file created"); + + struct stat64 st1; + + /* Before closing the file, try using this file descriptor to open + another file. This must fail. */ + if (fstatat64 (fd, "some-file", &st1, 0) != -1) + { + puts ("fstatatat using descriptor for normal file worked"); + return 1; + } + if (errno != ENOTDIR) + { + puts ("error for fstatat using descriptor for normal file not ENOTDIR "); + return 1; + } + + if (fstat64 (fd, &st1) != 0) + { + puts ("fstat64 failed"); + return 1; + } + + close (fd); + + struct stat64 st2; + if (fstatat64 (dir_fd, "some-file", &st2, 0) != 0) + { + puts ("fstatat64 failed"); + return 1; + } + + if (st1.st_dev != st2.st_dev + || st1.st_ino != st2.st_ino + || st1.st_size != st2.st_size) + { + puts ("stat results do not match"); + return 1; + } + + if (unlinkat (dir_fd, "some-file", 0) != 0) + { + puts ("unlinkat failed"); + return 1; + } + + if (fstatat64 (dir_fd, "some-file", &st2, 0) == 0) + { + puts ("second fstatat64 succeeded"); + return 1; + } + if (errno != ENOENT) + { + puts ("second fstatat64 did not fail with ENOENT"); + return 1; + } + + /* Create a file descriptor which is closed again right away. */ + int dir_fd2 = dup (dir_fd); + if (dir_fd2 == -1) + { + puts ("dup failed"); + return 1; + } + close (dir_fd2); + + if (fstatat64 (dir_fd2, "some-file", &st1, 0) != -1) + { + puts ("fstatat64 using closed descriptor worked"); + return 1; + } + if (errno != EBADF) + { + puts ("error for fstatat using closed descriptor not EBADF "); + return 1; + } + + close (dir_fd); + + if (fstatat64 (-1, "some-file", &st1, 0) != -1) + { + puts ("fstatat64 using invalid descriptor worked"); + return 1; + } + if (errno != EBADF) + { + puts ("error for fstatat using invalid descriptor not EBADF "); + return 1; + } + + return 0; +} diff --git a/REORG.TODO/io/tst-fts-lfs.c b/REORG.TODO/io/tst-fts-lfs.c new file mode 100644 index 0000000000..bc169342f8 --- /dev/null +++ b/REORG.TODO/io/tst-fts-lfs.c @@ -0,0 +1,2 @@ +#define _FILE_OFFSET_BITS 64 +#include "tst-fts.c" diff --git a/REORG.TODO/io/tst-fts.c b/REORG.TODO/io/tst-fts.c new file mode 100644 index 0000000000..648b402caf --- /dev/null +++ b/REORG.TODO/io/tst-fts.c @@ -0,0 +1,231 @@ +/* Simple test for some fts functions. + Copyright (C) 2015-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/types.h> +#include <sys/stat.h> +#include <fts.h> + +#include <errno.h> +#include <error.h> +#include <string.h> +#include <stdio.h> +#include <stdlib.h> +#include <unistd.h> + +static void prepare (void); +static int do_test (void); +#define PREPARE(argc, argv) prepare () +#define TEST_FUNCTION do_test () +#include "../test-skeleton.c" + +static char *fts_test_dir; + +static void +make_dir (const char *dirname) +{ + char *name; + if (asprintf (&name, "%s/%s", fts_test_dir, dirname) < 0) + { + puts ("out of memory"); + exit (1); + } + + if (mkdir (name, 0700) < 0) + { + printf ("cannot create dir \"%s\": %m\n", name); + exit (1); + } + + add_temp_file (name); +} + +static void +make_file (const char *filename) +{ + char *name; + if (asprintf (&name, "%s/%s", fts_test_dir, filename) < 0) + { + puts ("out of memory"); + exit (1); + } + + int fd = open (name, O_WRONLY | O_CREAT | O_EXCL, 0600); + if (fd < 0) + { + printf ("cannot create file \"%s\": %m\n", name); + exit (1); + } + close (fd); + + add_temp_file (name); +} + +static void +prepare (void) +{ + char *dirbuf; + char dir_name[] = "/tst-fts.XXXXXX"; + + if (asprintf (&dirbuf, "%s%s", test_dir, dir_name) < 0) + { + puts ("out of memory"); + exit (1); + } + + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + fts_test_dir = dirbuf; + + make_file ("12"); + make_file ("345"); + make_file ("6789"); + + make_dir ("aaa"); + make_file ("aaa/1234"); + make_file ("aaa/5678"); + + make_dir ("bbb"); + make_file ("bbb/1234"); + make_file ("bbb/5678"); + make_file ("bbb/90ab"); +} + +/* Largest name wins, otherwise strcmp. */ +static int +compare_ents (const FTSENT **ent1, const FTSENT **ent2) +{ + short len1 = (*ent1)->fts_namelen; + short len2 = (*ent2)->fts_namelen; + if (len1 != len2) + return len1 - len2; + else + { + const char *name1 = (*ent1)->fts_name; + const char *name2 = (*ent2)->fts_name; + return strcmp (name1, name2); + } +} + +/* Count the number of files seen as children. */ +static int files = 0; + +static void +children (FTS *fts) +{ + FTSENT *child = fts_children (fts, 0); + if (child == NULL && errno != 0) + { + printf ("FAIL: fts_children: %m\n"); + exit (1); + } + + while (child != NULL) + { + short level = child->fts_level; + const char *name = child->fts_name; + if (child->fts_info == FTS_F || child->fts_info == FTS_NSOK) + { + files++; + printf ("%*s%s\n", 2 * level, "", name); + } + child = child->fts_link; + } +} + +/* Count the number of dirs seen in the test. */ +static int dirs = 0; + +static int +do_test (void) +{ + char *paths[2] = { fts_test_dir, NULL }; + FTS *fts; + fts = fts_open (paths, FTS_LOGICAL, &compare_ents); + if (fts == NULL) + { + printf ("FAIL: fts_open: %m\n"); + exit (1); + } + + FTSENT *ent; + while ((ent = fts_read (fts)) != NULL) + { + const char *name = ent->fts_name; + short level = ent->fts_level; + switch (ent->fts_info) + { + case FTS_F: + /* Don't show anything, children will have on parent dir. */ + break; + + case FTS_D: + printf ("%*s%s =>\n", 2 * level, "", name); + children (fts); + break; + + case FTS_DP: + dirs++; + printf ("%*s<= %s\n", 2 * level, "", name); + break; + + case FTS_NS: + case FTS_ERR: + printf ("FAIL: fts_read ent: %s\n", strerror (ent->fts_errno)); + exit (1); + break; + + default: + printf ("FAIL: unexpected fts_read ent %s\n", name); + exit (1); + break; + } + } + /* fts_read returns NULL when done (and clears errno) + or when an error occured (with errno set). */ + if (errno != 0) + { + printf ("FAIL: fts_read: %m\n"); + exit (1); + } + + if (fts_close (fts) != 0) + { + printf ("FAIL: fts_close: %m\n"); + exit (1); + } + + if (files != 8) + { + printf ("FAIL: Unexpected number of files: %d\n", files); + return 1; + } + + if (dirs != 3) + { + printf ("FAIL: Unexpected number of dirs: %d\n", dirs); + return 1; + } + + puts ("PASS"); + return 0; +} diff --git a/REORG.TODO/io/tst-futimesat.c b/REORG.TODO/io/tst-futimesat.c new file mode 100644 index 0000000000..af58ad06dd --- /dev/null +++ b/REORG.TODO/io/tst-futimesat.c @@ -0,0 +1,148 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> +#include <sys/time.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-futimesat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Try to create a file. */ + int fd = openat (dir_fd, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("file creation failed"); + return 1; + } + write (fd, "hello", 5); + puts ("file created"); + + struct stat64 st1; + if (fstat64 (fd, &st1) != 0) + { + puts ("fstat64 failed"); + return 1; + } + + close (fd); + + struct timeval tv[2]; + tv[0].tv_sec = st1.st_atime + 1; + tv[0].tv_usec = 0; + tv[1].tv_sec = st1.st_mtime + 1; + tv[1].tv_usec = 0; + if (futimesat (dir_fd, "some-file", tv) != 0) + { + puts ("futimesat failed"); + return 1; + } + + struct stat64 st2; + if (fstatat64 (dir_fd, "some-file", &st2, 0) != 0) + { + puts ("fstatat64 failed"); + return 1; + } + + if (st2.st_mtime != tv[1].tv_sec +#ifdef _STATBUF_ST_NSEC + || st2.st_mtim.tv_nsec != 0 +#endif + ) + { + puts ("stat shows different mtime"); + return 1; + } + + + if (unlinkat (dir_fd, "some-file", 0) != 0) + { + puts ("unlinkat failed"); + return 1; + } + + close (dir_fd); + + return 0; +} diff --git a/REORG.TODO/io/tst-getcwd.c b/REORG.TODO/io/tst-getcwd.c new file mode 100644 index 0000000000..726758bb51 --- /dev/null +++ b/REORG.TODO/io/tst-getcwd.c @@ -0,0 +1,163 @@ +/* Test of getcwd function. + Copyright (C) 2000-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Ulrich Drepper <drepper@cygnus.com>, 2000. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/param.h> + + +#define TEST_FUNCTION do_test () +static int +do_test (void) +{ + char thepath[4096]; /* Yes, this limits the environment this test + can run it but I honestly don't care about + people which have this problem. */ + char *bufs[10]; + size_t lens[10]; + size_t sbs; + size_t len, i; + + if (getcwd (thepath, sizeof thepath) == NULL) + { + if (errno == ERANGE) + /* The path is too long, skip all tests. */ + return 0; + + puts ("getcwd (thepath, sizeof thepath) failed"); + return 1; + } + len = strlen (thepath); + + sbs = 1; + while (sbs < len + 1) + sbs <<= 1; + + for (i = 0; i < 4; ++i) + { + lens[i] = sbs; + bufs[i] = (char *) malloc (sbs); + } + + bufs[i] = getcwd (NULL, sbs); + lens[i] = sbs; + if (bufs[i] == NULL) + { + puts ("getcwd (NULL, sbs) failed"); + return 1; + } + ++i; + + for (; i < 10; sbs >>= 1, ++i) + { + bufs[i] = (char *) malloc (MAX (1, sbs)); + lens[i] = sbs; + } + + /* Before we test the result write something in the memory to see + whether the allocation went right. */ + for (i = 0; i < 10; ++i) + if (i != 4 && bufs[i] != NULL) + memset (bufs[i], '\xff', lens[i]); + + if (strcmp (thepath, bufs[4]) != 0) + { + printf ("\ +getcwd (NULL, sbs) = \"%s\", getcwd (thepath, sizeof thepath) = \"%s\"\n", + bufs[4], thepath); + return 1; + } + + /* Now overwrite all buffers to see that getcwd allocated the buffer + of right size. */ + for (i = 0; i < 10; ++i) + memset (bufs[i], i, lens[i]); + + for (i = 0; i < 10; ++i) + free (bufs[i]); + + /* Test whether the function signals success despite the buffer + being too small. */ + if (getcwd (NULL, len) != NULL) + { + puts ("getcwd (NULL, len) didn't failed"); + return 1; + } + + bufs[0] = malloc (len); + bufs[1] = malloc (len); + bufs[2] = malloc (len); + if (bufs[1] != NULL) + { + if (getcwd (bufs[1], len) != NULL) + { + puts ("getcwd (bufs[1], len) didn't failed"); + return 1; + } + free (bufs[0]); + free (bufs[1]); + free (bufs[2]); + } + + memset (thepath, '\xfe', sizeof (thepath)); + if (getcwd (thepath, len) != NULL) + { + puts ("getcwd (thepath, len) didn't failed"); + return 1; + } + + for (i = len; i < sizeof thepath; ++i) + if (thepath[i] != '\xfe') + { + puts ("thepath[i] != '\xfe'"); + return 1; + } + + /* Now test handling of correctly sized buffers. */ + bufs[0] = getcwd (NULL, len + 1); + if (bufs[0] == NULL) + { + puts ("getcwd (NULL, len + 1) failed"); + return 1; + } + free (bufs[0]); + + memset (thepath, '\xff', sizeof thepath); + if (getcwd (thepath, len + 1) == NULL) + { + puts ("getcwd (thepath, len + 1) failed"); + return 1; + } + + for (i = len + 1; i < sizeof thepath; ++i) + if (thepath[i] != '\xff') + { + printf ("thepath[%zd] != '\xff'\n", i); + return 1; + } + + puts ("everything OK"); + + return 0; +} + +#include "../test-skeleton.c" diff --git a/REORG.TODO/io/tst-linkat.c b/REORG.TODO/io/tst-linkat.c new file mode 100644 index 0000000000..97445b7954 --- /dev/null +++ b/REORG.TODO/io/tst-linkat.c @@ -0,0 +1,172 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-linkat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Try to create a file. */ + int fd = openat (dir_fd, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("file creation failed"); + return 1; + } + write (fd, "hello", 5); + puts ("file created"); + + struct stat64 st1; + if (fstat64 (fd, &st1) != 0) + { + puts ("fstat64 failed"); + return 1; + } + + close (fd); + + if (linkat (dir_fd, "some-file", dir_fd, "another-file", 0) != 0) + { + puts ("symlinkat failed"); + return 1; + } + + struct stat64 st2; + if (fstatat64 (dir_fd, "some-file", &st2, 0) != 0) + { + puts ("fstatat64 failed"); + return 1; + } + if (st1.st_dev != st2.st_dev || st1.st_ino != st2.st_ino) + { + puts ("file changed after symlinkat"); + return 1; + } + + if (fstatat64 (dir_fd, "another-file", &st2, AT_SYMLINK_NOFOLLOW) != 0) + { + puts ("2nd fstatat64 failed"); + return 1; + } + if (S_ISLNK (st2.st_mode)) + { + puts ("2nd fstatat64 shows file is a symlink"); + return 1; + } + if (st1.st_dev != st2.st_dev + || st1.st_ino != st2.st_ino + || st1.st_size != st2.st_size) + { + puts ("stat results for linked file do not match"); + return 1; + } + + if (fstatat64 (dir_fd, "another-file", &st2, 0) != 0) + { + puts ("3rd fstatat64 failed"); + return 1; + } + if (st1.st_dev != st2.st_dev + || st1.st_ino != st2.st_ino + || st1.st_size != st2.st_size) + { + puts ("stat results do not match"); + return 1; + } + + if (unlinkat (dir_fd, "another-file", 0) != 0) + { + puts ("unlinkat failed"); + return 1; + } + if (unlinkat (dir_fd, "some-file", 0) != 0) + { + puts ("2nd unlinkat failed"); + return 1; + } + + close (dir_fd); + + return 0; +} diff --git a/REORG.TODO/io/tst-mkdirat.c b/REORG.TODO/io/tst-mkdirat.c new file mode 100644 index 0000000000..a960c6651d --- /dev/null +++ b/REORG.TODO/io/tst-mkdirat.c @@ -0,0 +1,164 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdbool.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-mkdirat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Create a new directory. */ + int e = mkdirat (dir_fd, "some-dir", 0777); + if (e == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("directory creation failed"); + return 1; + } + + struct stat64 st1; + if (fstatat64 (dir_fd, "some-dir", &st1, 0) != 0) + { + puts ("fstat64 failed"); + return 1; + } + if (!S_ISDIR (st1.st_mode)) + { + puts ("mkdirat did not create a directory"); + return 1; + } + + dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("2nd fdopendir failed"); + return 1; + } + bool has_some_dir = false; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, "some-dir") == 0) + { + has_some_dir = true; +#ifdef _DIRENT_HAVE_D_TYPE + if (d->d_type != DT_UNKNOWN && d->d_type != DT_DIR) + { + puts ("d_type for some-dir wrong"); + return 1; + } +#endif + } + else if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + if (!has_some_dir) + { + puts ("some-dir not in directory list"); + return 1; + } + + if (unlinkat (dir_fd, "some-dir", AT_REMOVEDIR) != 0) + { + puts ("unlinkat failed"); + return 1; + } + + close (dir_fd); + + return 0; +} diff --git a/REORG.TODO/io/tst-mkfifoat.c b/REORG.TODO/io/tst-mkfifoat.c new file mode 100644 index 0000000000..d87b587384 --- /dev/null +++ b/REORG.TODO/io/tst-mkfifoat.c @@ -0,0 +1,164 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdbool.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-mkfifoat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Create a new directory. */ + int e = mkfifoat (dir_fd, "some-fifo", 0777); + if (e == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("fifo creation failed"); + return 1; + } + + struct stat64 st1; + if (fstatat64 (dir_fd, "some-fifo", &st1, 0) != 0) + { + puts ("fstat64 failed"); + return 1; + } + if (!S_ISFIFO (st1.st_mode)) + { + puts ("mkfifoat did not create FIFO"); + return 1; + } + + dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("2nd fdopendir failed"); + return 1; + } + bool has_some_fifo = false; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, "some-fifo") == 0) + { + has_some_fifo = true; +#ifdef _DIRENT_HAVE_D_TYPE + if (d->d_type != DT_UNKNOWN && d->d_type != DT_FIFO) + { + puts ("d_type for some-fifo wrong"); + return 1; + } +#endif + } + else if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + if (!has_some_fifo) + { + puts ("some-fifo not in directory list"); + return 1; + } + + if (unlinkat (dir_fd, "some-fifo", 0) != 0) + { + puts ("unlinkat failed"); + return 1; + } + + close (dir_fd); + + return 0; +} diff --git a/REORG.TODO/io/tst-mknodat.c b/REORG.TODO/io/tst-mknodat.c new file mode 100644 index 0000000000..9d58fdbe3a --- /dev/null +++ b/REORG.TODO/io/tst-mknodat.c @@ -0,0 +1,164 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdbool.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-mknodat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Create a new fifo. */ + int e = mknodat (dir_fd, "some-fifo", 0777 | S_IFIFO, 0); + if (e == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("fifo creation failed"); + return 1; + } + + struct stat64 st1; + if (fstatat64 (dir_fd, "some-fifo", &st1, 0) != 0) + { + puts ("fstat64 failed"); + return 1; + } + if (!S_ISFIFO (st1.st_mode)) + { + puts ("mknodat did not create a fifo"); + return 1; + } + + dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("2nd fdopendir failed"); + return 1; + } + bool has_some_fifo = false; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, "some-fifo") == 0) + { + has_some_fifo = true; +#ifdef _DIRENT_HAVE_D_TYPE + if (d->d_type != DT_UNKNOWN && d->d_type != DT_FIFO) + { + puts ("d_type for some-fifo wrong"); + return 1; + } +#endif + } + else if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + if (!has_some_fifo) + { + puts ("some-fifo not in directory list"); + return 1; + } + + if (unlinkat (dir_fd, "some-fifo", 0) != 0) + { + puts ("unlinkat failed"); + return 1; + } + + close (dir_fd); + + return 0; +} diff --git a/REORG.TODO/io/tst-open-tmpfile.c b/REORG.TODO/io/tst-open-tmpfile.c new file mode 100644 index 0000000000..485109706f --- /dev/null +++ b/REORG.TODO/io/tst-open-tmpfile.c @@ -0,0 +1,318 @@ +/* Test open and openat with O_TMPFILE. + Copyright (C) 2016-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +/* This test verifies that open and openat work as expected, i.e. they + create a deleted file with the requested file mode. */ + +#include <errno.h> +#include <fcntl.h> +#include <stdbool.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <sys/stat.h> +#include <unistd.h> + +#include <support/support.h> + +#ifdef O_TMPFILE +typedef int (*wrapper_func) (const char *, int, mode_t); + +/* Error-checking wrapper for the open function, compatible with the + wrapper_func type. */ +static int +wrap_open (const char *path, int flags, mode_t mode) +{ + int ret = open (path, flags, mode); + if (ret < 0) + { + printf ("error: open (\"%s\", 0x%x, 0%03o): %m\n", path, flags, mode); + exit (1); + } + return ret; +} + +/* Error-checking wrapper for the openat function, compatible with the + wrapper_func type. */ +static int +wrap_openat (const char *path, int flags, mode_t mode) +{ + int ret = openat (AT_FDCWD, path, flags, mode); + if (ret < 0) + { + printf ("error: openat (\"%s\", 0x%x, 0%03o): %m\n", path, flags, mode); + exit (1); + } + return ret; +} + +/* Error-checking wrapper for the open64 function, compatible with the + wrapper_func type. */ +static int +wrap_open64 (const char *path, int flags, mode_t mode) +{ + int ret = open64 (path, flags, mode); + if (ret < 0) + { + printf ("error: open64 (\"%s\", 0x%x, 0%03o): %m\n", path, flags, mode); + exit (1); + } + return ret; +} + +/* Error-checking wrapper for the openat64 function, compatible with the + wrapper_func type. */ +static int +wrap_openat64 (const char *path, int flags, mode_t mode) +{ + int ret = openat64 (AT_FDCWD, path, flags, mode); + if (ret < 0) + { + printf ("error: openat64 (\"%s\", 0x%x, 0%03o): %m\n", path, flags, mode); + exit (1); + } + return ret; +} + +/* Return true if FD is flagged as deleted in /proc/self/fd, false if + not. */ +static bool +is_file_deteted (int fd) +{ + char *proc_fd_path = xasprintf ("/proc/self/fd/%d", fd); + char file_path[4096]; + ssize_t file_path_length + = readlink (proc_fd_path, file_path, sizeof (file_path)); + if (file_path_length < 0) + { + printf ("error: readlink (\"%s\"): %m", proc_fd_path); + free (proc_fd_path); + exit (1); + } + free (proc_fd_path); + if (file_path_length == sizeof (file_path)) + { + printf ("error: path in /proc resolves to overlong file name: %.*s\n", + (int) file_path_length, file_path); + exit (1); + } + const char *deleted = " (deleted)"; + if (file_path_length < strlen (deleted)) + { + printf ("error: path in /proc is too short: %.*s\n", + (int) file_path_length, file_path); + exit (1); + } + return memcmp (file_path + file_path_length - strlen (deleted), + deleted, strlen (deleted)) == 0; +} + +/* Obtain a file name which is difficult to guess. */ +static char * +get_random_name (void) +{ + unsigned long long bytes[2]; + int random_device = open ("/dev/urandom", O_RDONLY); + if (random_device < 0) + { + printf ("error: open (\"/dev/urandom\"): %m\n"); + exit (1); + } + ssize_t ret = read (random_device, bytes, sizeof (bytes)); + if (ret < 0) + { + printf ("error: read (\"/dev/urandom\"): %m\n"); + exit (1); + } + if (ret != sizeof (bytes)) + { + printf ("error: short read from /dev/urandom: %zd\n", ret); + exit (1); + } + close (random_device); + return xasprintf ("tst-open-tmpfile-%08llx%08llx.tmp", bytes[0], bytes[1]); +} + +/* Check open/openat (as specified by OP and WRAPPER) with a specific + PATH/FLAGS/MODE combination. */ +static void +check_wrapper_flags_mode (const char *op, wrapper_func wrapper, + const char *path, int flags, mode_t mode) +{ + int fd = wrapper (path, flags | O_TMPFILE, mode); + struct stat64 st; + if (fstat64 (fd, &st) != 0) + { + printf ("error: fstat64: %m\n"); + exit (1); + } + + /* Verify that the mode was correctly processed. */ + int actual_mode = st.st_mode & 0777; + if (actual_mode != mode) + { + printf ("error: unexpected mode; expected 0%03o, actual 0%03o\n", + mode, actual_mode); + exit (1); + } + + /* Check that the file is marked as deleted in /proc. */ + if (!is_file_deteted (fd)) + { + printf ("error: path in /proc is not marked as deleted\n"); + exit (1); + } + + /* Check that the file can be turned into a regular file with + linkat. Open a file descriptor for the directory at PATH. Use + AT_FDCWD if PATH is ".", to exercise that functionality as + well. */ + int path_fd; + if (strcmp (path, ".") == 0) + path_fd = AT_FDCWD; + else + { + path_fd = open (path, O_RDONLY | O_DIRECTORY); + if (path_fd < 0) + { + printf ("error: open (\"%s\"): %m\n", path); + exit (1); + } + } + + /* Use a hard-to-guess name for the new directory entry. */ + char *new_name = get_random_name (); + + /* linkat does not require privileges if the path in /proc/self/fd + is used. */ + char *proc_fd_path = xasprintf ("/proc/self/fd/%d", fd); + if (linkat (AT_FDCWD, proc_fd_path, path_fd, new_name, + AT_SYMLINK_FOLLOW) == 0) + { + if (unlinkat (path_fd, new_name, 0) != 0 && errno != ENOENT) + { + printf ("error: unlinkat (\"%s/%s\"): %m\n", path, new_name); + exit (1); + } + } + else + { + /* linkat failed. This is expected if O_EXCL was specified. */ + if ((flags & O_EXCL) == 0) + { + printf ("error: linkat failed after %s (\"%s\", 0x%x, 0%03o): %m\n", + op, path, flags, mode); + exit (1); + } + } + + free (proc_fd_path); + free (new_name); + if (path_fd != AT_FDCWD) + close (path_fd); + close (fd); +} + +/* Check OP/WRAPPER with various flags at a specific PATH and + MODE. */ +static void +check_wrapper_mode (const char *op, wrapper_func wrapper, + const char *path, mode_t mode) +{ + check_wrapper_flags_mode (op, wrapper, path, O_WRONLY, mode); + check_wrapper_flags_mode (op, wrapper, path, O_WRONLY | O_EXCL, mode); + check_wrapper_flags_mode (op, wrapper, path, O_RDWR, mode); + check_wrapper_flags_mode (op, wrapper, path, O_RDWR | O_EXCL, mode); +} + +/* Check open/openat with varying permissions. */ +static void +check_wrapper (const char *op, wrapper_func wrapper, + const char *path) +{ + printf ("info: testing %s at: %s\n", op, path); + check_wrapper_mode (op, wrapper, path, 0); + check_wrapper_mode (op, wrapper, path, 0640); + check_wrapper_mode (op, wrapper, path, 0600); + check_wrapper_mode (op, wrapper, path, 0755); + check_wrapper_mode (op, wrapper, path, 0750); +} + +/* Verify that the directory at PATH supports O_TMPFILE. Exit with + status 77 (unsupported) if the kernel does not support O_TMPFILE. + Even with kernel support, not all file systems O_TMPFILE, so return + true if the directory supports O_TMPFILE, false if not. */ +static bool +probe_path (const char *path) +{ + int fd = openat (AT_FDCWD, path, O_TMPFILE | O_RDWR, 0); + if (fd < 0) + { + if (errno == EISDIR) + /* The system does not support O_TMPFILE. */ + { + printf ("info: kernel does not support O_TMPFILE\n"); + exit (77); + } + if (errno == EOPNOTSUPP) + { + printf ("info: path does not support O_TMPFILE: %s\n", path); + return false; + } + printf ("error: openat (\"%s\", O_TMPFILE | O_RDWR): %m\n", path); + exit (1); + } + close (fd); + return true; +} + +static int +do_test (void) +{ + umask (0); + const char *paths[] = { ".", "/dev/shm", "/tmp", + getenv ("TEST_TMPFILE_PATH"), + NULL }; + bool supported = false; + for (int i = 0; paths[i] != NULL; ++i) + if (probe_path (paths[i])) + { + supported = true; + check_wrapper ("open", wrap_open, paths[i]); + check_wrapper ("openat", wrap_openat, paths[i]); + check_wrapper ("open64", wrap_open64, paths[i]); + check_wrapper ("openat64", wrap_openat64, paths[i]); + } + + if (!supported) + return 77; + + return 0; +} + +#else /* !O_TMPFILE */ + +static int +do_test (void) +{ + return 77; +} + +#endif /* O_TMPFILE */ + +#include <support/test-driver.c> diff --git a/REORG.TODO/io/tst-openat.c b/REORG.TODO/io/tst-openat.c new file mode 100644 index 0000000000..741b8d0ad2 --- /dev/null +++ b/REORG.TODO/io/tst-openat.c @@ -0,0 +1,210 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdbool.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-openat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Try to create a file. */ + int fd = openat (dir_fd, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("file creation failed"); + return 1; + } + write (fd, "hello", 5); + + /* Before closing the file, try using this file descriptor to open + another file. This must fail. */ + int fd2 = openat (fd, "should-not-work", O_CREAT|O_RDWR, 0666); + if (fd2 != -1) + { + puts ("openat using descriptor for normal file worked"); + return 1; + } + if (errno != ENOTDIR) + { + puts ("error for openat using descriptor for normal file not ENOTDIR "); + return 1; + } + + close (fd); + puts ("file created"); + + /* fdopendir takes over the descriptor, make a copy. */ + dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("2nd lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + bool seen_file = false; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + if (strcmp (d->d_name, "some-file") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + + seen_file = true; + } + closedir (dir); + + if (!seen_file) + { + puts ("file not created in correct directory"); + return 1; + } + + int cwdfd = open (".", O_RDONLY | O_DIRECTORY); + if (cwdfd == -1) + { + puts ("cannot get descriptor for cwd"); + return 1; + } + + if (fchdir (dir_fd) != 0) + { + puts ("1st fchdir failed"); + return 1; + } + + if (unlink ("some-file") != 0) + { + puts ("unlink failed"); + return 1; + } + + if (fchdir (cwdfd) != 0) + { + puts ("2nd fchdir failed"); + return 1; + } + + close (dir_fd); + close (cwdfd); + + /* With the file descriptor closed the next call must fail. */ + fd = openat (dir_fd, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd != -1) + { + puts ("openat using closed descriptor succeeded"); + return 1; + } + if (errno != EBADF) + { + puts ("openat using closed descriptor did not set EBADF"); + return 1; + } + + fd = openat (-1, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd != -1) + { + puts ("openat using -1 descriptor succeeded"); + return 1; + } + if (errno != EBADF) + { + puts ("openat using -1 descriptor did not set EBADF"); + return 1; + } + + return 0; +} diff --git a/REORG.TODO/io/tst-posix_fallocate-common.c b/REORG.TODO/io/tst-posix_fallocate-common.c new file mode 100644 index 0000000000..d5a302aa9c --- /dev/null +++ b/REORG.TODO/io/tst-posix_fallocate-common.c @@ -0,0 +1,85 @@ +/* Common posix_fallocate tests definitions. + Copyright (C) 2016-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <fcntl.h> +#include <limits.h> +#include <stdint.h> +#include <sys/stat.h> +#include <sys/types.h> +#include <unistd.h> + +#include <support/support.h> +#include <support/check.h> +#include <support/temp_file.h> + +static char *temp_filename; +static int temp_fd; + +static void +do_prepare (int argc, char **argv) +{ + temp_fd = create_temp_file ("tst-posix_fallocate.", &temp_filename); + if (temp_fd == -1) + FAIL_EXIT1 ("cannot create temporary file: %m\n"); +} +#define PREPARE do_prepare + +static int +do_test_with_offset (off_t offset) +{ + struct stat st; + + if (posix_fallocate (temp_fd, offset, 768) != 0) + FAIL_EXIT1 ("1st posix_fallocate call failed"); + + if (fstat (temp_fd, &st) != 0) + FAIL_EXIT1 ("2nd fstat failed"); + + if (st.st_size != (offset + 768)) + FAIL_EXIT1 ("file size after first posix_fallocate call is %lu, " + "expected %lu", + (unsigned long int) st.st_size, 512lu + 768lu); + + if (posix_fallocate (temp_fd, 0, 1024) != 0) + FAIL_EXIT1 ("2nd posix_fallocate call failed"); + + if (fstat (temp_fd, &st) != 0) + FAIL_EXIT1 ("3rd fstat failed"); + + if (st.st_size != (offset) + 768) + FAIL_EXIT1 ("file size changed in second posix_fallocate"); + + offset += 2048; + if (posix_fallocate (temp_fd, offset, 64) != 0) + FAIL_EXIT1 ("3rd posix_fallocate call failed"); + + if (fstat (temp_fd, &st) != 0) + FAIL_EXIT1 ("4th fstat failed"); + + if (st.st_size != (offset + 64)) + FAIL_EXIT1 ("file size after first posix_fallocate call is %llu, " + "expected %u", + (unsigned long long int) st.st_size, 2048u + 64u); + + return 0; +} + +/* This function is defined by the individual tests. */ +static int do_test (void); + +#include <support/test-driver.c> diff --git a/REORG.TODO/io/tst-posix_fallocate.c b/REORG.TODO/io/tst-posix_fallocate.c new file mode 100644 index 0000000000..b695d17afa --- /dev/null +++ b/REORG.TODO/io/tst-posix_fallocate.c @@ -0,0 +1,33 @@ +/* Basic posix_fallocate tests. + Copyright (C) 2016-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include "tst-posix_fallocate-common.c" + +static int +do_test (void) +{ + struct stat st; + + if (fstat (temp_fd, &st) != 0) + FAIL_EXIT1 ("1st fstat failed"); + + if (st.st_size != 0) + FAIL_EXIT1 ("file not created with size 0"); + + return do_test_with_offset (512); +} diff --git a/REORG.TODO/io/tst-posix_fallocate64.c b/REORG.TODO/io/tst-posix_fallocate64.c new file mode 100644 index 0000000000..3b380d7bcb --- /dev/null +++ b/REORG.TODO/io/tst-posix_fallocate64.c @@ -0,0 +1,44 @@ +/* Basic posix_fallocate tests (with _FILE_OFFSET_BITS). + Copyright (C) 2016-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#define _FILE_OFFSET_BITS 64 +#include "tst-posix_fallocate-common.c" + +static int +do_test (void) +{ + struct stat st; + int ret; + + if (fstat (temp_fd, &st) != 0) + FAIL_EXIT1 ("1st fstat failed"); + + if (st.st_size != 0) + FAIL_EXIT1 ("file not created with size 0"); + + ret = do_test_with_offset (512); + if (ret == 1) + return 1; + + off_t base_offset = UINT32_MAX + 512LL; + ret = do_test_with_offset (base_offset); + if (ret == 1) + return 1; + + return 0; +} diff --git a/REORG.TODO/io/tst-readlinkat.c b/REORG.TODO/io/tst-readlinkat.c new file mode 100644 index 0000000000..51fafc92d3 --- /dev/null +++ b/REORG.TODO/io/tst-readlinkat.c @@ -0,0 +1,137 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-symlinkat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + static const char symlinkcontent[] = "some-file"; + if (symlinkat (symlinkcontent, dir_fd, "another-file") != 0) + { + puts ("symlinkat failed"); + return 1; + } + + struct stat64 st2; + if (fstatat64 (dir_fd, "another-file", &st2, AT_SYMLINK_NOFOLLOW) != 0) + { + puts ("fstatat64 failed"); + return 1; + } + if (!S_ISLNK (st2.st_mode)) + { + puts ("2nd fstatat64 does not show file is a symlink"); + return 1; + } + + if (fstatat64 (dir_fd, symlinkcontent, &st2, AT_SYMLINK_NOFOLLOW) == 0) + { + puts ("2nd fstatat64 succeeded"); + return 1; + } + + char buf[100]; + int n = readlinkat (dir_fd, "another-file", buf, sizeof (buf)); + if (n == -1) + { + puts ("readlinkat failed"); + return 1; + } + if (n != sizeof (symlinkcontent) - 1) + { + printf ("readlinkat returned %d, expected %zu\n", + n, sizeof (symlinkcontent) - 1); + return 1; + } + if (strncmp (buf, symlinkcontent, n) != 0) + { + puts ("readlinkat retrieved wrong link content"); + return 1; + } + + if (unlinkat (dir_fd, "another-file", 0) != 0) + { + puts ("unlinkat failed"); + return 1; + } + + close (dir_fd); + + return 0; +} diff --git a/REORG.TODO/io/tst-renameat.c b/REORG.TODO/io/tst-renameat.c new file mode 100644 index 0000000000..435302b52b --- /dev/null +++ b/REORG.TODO/io/tst-renameat.c @@ -0,0 +1,226 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-renameat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Try to create a file. */ + int fd = openat (dir_fd, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("file creation failed"); + return 1; + } + write (fd, "hello", 5); + puts ("file created"); + + struct stat64 st1; + if (fstat64 (fd, &st1) != 0) + { + puts ("fstat64 failed"); + return 1; + } + + /* Using a descriptor for a normal file must fail. */ + if (renameat (fd, "some-file", dir_fd, "another-file") == 0) + { + puts ("renameat with normal file descriptor succeeded"); + return 1; + } + if (errno != ENOTDIR) + { + puts ("error for renameat with normal file descriptor not ENOTDIR"); + return 1; + } + + if (renameat (dir_fd, "some-file", fd, "another-file") == 0) + { + puts ("2nd renameat with normal file descriptor succeeded"); + return 1; + } + if (errno != ENOTDIR) + { + puts ("error for 2nd renameat with normal file descriptor not ENOTDIR"); + return 1; + } + + close (fd); + + if (renameat (dir_fd, "some-file", dir_fd, "another-file") != 0) + { + puts ("renameat failed"); + return 1; + } + + struct stat64 st2; + if (fstatat64 (dir_fd, "some-file", &st2, 0) == 0) + { + puts ("fstatat64 succeeded"); + return 1; + } + if (errno != ENOENT) + { + puts ("fstatat64 did not fail with ENOENT"); + return 1; + } + + if (fstatat64 (dir_fd, "another-file", &st2, 0) != 0) + { + puts ("2nd fstatat64 failed"); + return 1; + } + + if (st1.st_dev != st2.st_dev + || st1.st_ino != st2.st_ino + || st1.st_size != st2.st_size) + { + puts ("stat results do not match"); + return 1; + } + + /* Create a file descriptor which is closed again right away. */ + int dir_fd2 = dup (dir_fd); + if (dir_fd2 == -1) + { + puts ("dup failed"); + return 1; + } + close (dir_fd2); + + if (renameat (dir_fd2, "another-file", dir_fd, "some-file") == 0) + { + puts ("renameat with closed file descriptor succeeded"); + return 1; + } + if (errno != EBADF) + { + puts ("error for renameat with closed file descriptor not EBADF"); + return 1; + } + + if (renameat (dir_fd, "another-file", dir_fd2, "some-file") == 0) + { + puts ("2nd renameat with closed file descriptor succeeded"); + return 1; + } + if (errno != EBADF) + { + puts ("error for 2nd renameat with closed file descriptor not EBADF"); + return 1; + } + + if (unlinkat (dir_fd, "another-file", 0) != 0) + { + puts ("unlinkat failed"); + return 1; + } + + if (renameat (-1, "another-file", dir_fd, "some-file") == 0) + { + puts ("renameat with invalid file descriptor succeeded"); + return 1; + } + if (errno != EBADF) + { + puts ("error for renameat with invalid file descriptor not EBADF"); + return 1; + } + + if (renameat (dir_fd, "another-file", -1, "some-file") == 0) + { + puts ("2nd renameat with invalid file descriptor succeeded"); + return 1; + } + if (errno != EBADF) + { + puts ("error for 2nd renameat with invalid file descriptor not EBADF"); + return 1; + } + + close (dir_fd); + + return 0; +} diff --git a/REORG.TODO/io/tst-statvfs.c b/REORG.TODO/io/tst-statvfs.c new file mode 100644 index 0000000000..227c62d7da --- /dev/null +++ b/REORG.TODO/io/tst-statvfs.c @@ -0,0 +1,30 @@ +#include <stdio.h> +#include <sys/statvfs.h> + + +/* This test cannot detect many errors. But it will fail if the + statvfs is completely hosed and it'll detect a missing export. So + it is better than nothing. */ +static int +do_test (int argc, char *argv[]) +{ + for (int i = 1; i < argc; ++i) + { + struct statvfs st; + if (statvfs (argv[i], &st) != 0) + printf ("%s: failed (%m)\n", argv[i]); + else + printf ("%s: free: %llu, mandatory: %s\n", argv[i], + (unsigned long long int) st.f_bfree, +#ifdef ST_MANDLOCK + (st.f_flag & ST_MANDLOCK) ? "yes" : "no" +#else + "no" +#endif + ); + } + return 0; +} + +#define TEST_FUNCTION do_test (argc, argv) +#include "../test-skeleton.c" diff --git a/REORG.TODO/io/tst-symlinkat.c b/REORG.TODO/io/tst-symlinkat.c new file mode 100644 index 0000000000..214a8e348e --- /dev/null +++ b/REORG.TODO/io/tst-symlinkat.c @@ -0,0 +1,165 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <sys/stat.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-symlinkat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Try to create a file. */ + int fd = openat (dir_fd, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("file creation failed"); + return 1; + } + write (fd, "hello", 5); + puts ("file created"); + + struct stat64 st1; + if (fstat64 (fd, &st1) != 0) + { + puts ("fstat64 failed"); + return 1; + } + + close (fd); + + if (symlinkat ("some-file", dir_fd, "another-file") != 0) + { + puts ("symlinkat failed"); + return 1; + } + + struct stat64 st2; + if (fstatat64 (dir_fd, "some-file", &st2, 0) != 0) + { + puts ("fstatat64 failed"); + return 1; + } + if (st1.st_dev != st2.st_dev || st1.st_ino != st2.st_ino) + { + puts ("file changed after symlinkat"); + return 1; + } + + if (fstatat64 (dir_fd, "another-file", &st2, AT_SYMLINK_NOFOLLOW) != 0) + { + puts ("2nd fstatat64 failed"); + return 1; + } + if (!S_ISLNK (st2.st_mode)) + { + puts ("2nd fstatat64 does not show file is a symlink"); + return 1; + } + + if (fstatat64 (dir_fd, "another-file", &st2, 0) != 0) + { + puts ("3rd fstatat64 failed"); + return 1; + } + if (st1.st_dev != st2.st_dev + || st1.st_ino != st2.st_ino + || st1.st_size != st2.st_size) + { + puts ("stat results do not match"); + return 1; + } + + if (unlinkat (dir_fd, "another-file", 0) != 0) + { + puts ("unlinkat failed"); + return 1; + } + if (unlinkat (dir_fd, "some-file", 0) != 0) + { + puts ("2nd unlinkat failed"); + return 1; + } + + close (dir_fd); + + return 0; +} diff --git a/REORG.TODO/io/tst-ttyname_r.c b/REORG.TODO/io/tst-ttyname_r.c new file mode 100644 index 0000000000..8e2f30c972 --- /dev/null +++ b/REORG.TODO/io/tst-ttyname_r.c @@ -0,0 +1,42 @@ +#include <errno.h> +#include <error.h> +#include <fcntl.h> +#include <stdio.h> +#include <unistd.h> + +static void do_prepare (void); +#define PREPARE(argc, argv) do_prepare () +static int do_test (void); +#define TEST_FUNCTION do_test () +#include <test-skeleton.c> + +static int temp_fd; + +static void +do_prepare (void) +{ + char *temp_file; + temp_fd = create_temp_file ("tst-ttyname_r.", &temp_file); + if (temp_fd == -1) + error (1, errno, "cannot create temporary file"); +} + +static int +do_test (void) +{ + int ret = 0; + char buf[sysconf (_SC_TTY_NAME_MAX) + 1]; + int res = ttyname_r (-1, buf, sizeof (buf)); + if (res != EBADF) + { + printf ("1st ttyname_r returned with res %d\n", res); + ret++; + } + res = ttyname_r (temp_fd, buf, sizeof (buf)); + if (res != ENOTTY) + { + printf ("2nd ttyname_r returned with res %d\n", res); + ret++; + } + return ret; +} diff --git a/REORG.TODO/io/tst-unlinkat.c b/REORG.TODO/io/tst-unlinkat.c new file mode 100644 index 0000000000..e21d56f9f7 --- /dev/null +++ b/REORG.TODO/io/tst-unlinkat.c @@ -0,0 +1,179 @@ +#include <dirent.h> +#include <fcntl.h> +#include <stdbool.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + + +static void prepare (void); +#define PREPARE(argc, argv) prepare () + +static int do_test (void); +#define TEST_FUNCTION do_test () + +#include "../test-skeleton.c" + +static int dir_fd; + +static void +prepare (void) +{ + size_t test_dir_len = strlen (test_dir); + static const char dir_name[] = "/tst-unlinkat.XXXXXX"; + + size_t dirbuflen = test_dir_len + sizeof (dir_name); + char *dirbuf = malloc (dirbuflen); + if (dirbuf == NULL) + { + puts ("out of memory"); + exit (1); + } + + snprintf (dirbuf, dirbuflen, "%s%s", test_dir, dir_name); + if (mkdtemp (dirbuf) == NULL) + { + puts ("cannot create temporary directory"); + exit (1); + } + + add_temp_file (dirbuf); + + dir_fd = open (dirbuf, O_RDONLY | O_DIRECTORY); + if (dir_fd == -1) + { + puts ("cannot open directory"); + exit (1); + } +} + + +static int +do_test (void) +{ + /* fdopendir takes over the descriptor, make a copy. */ + int dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("1st lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + DIR *dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("fdopendir failed"); + return 1; + } + struct dirent64 *d; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + closedir (dir); + + /* Try to create a file. */ + int fd = openat (dir_fd, "some-file", O_CREAT|O_RDWR|O_EXCL, 0666); + if (fd == -1) + { + if (errno == ENOSYS) + { + puts ("*at functions not supported"); + return 0; + } + + puts ("file creation failed"); + return 1; + } + write (fd, "hello", 5); + close (fd); + puts ("file created"); + + /* fdopendir takes over the descriptor, make a copy. */ + dupfd = dup (dir_fd); + if (dupfd == -1) + { + puts ("2nd dup failed"); + return 1; + } + if (lseek (dupfd, 0, SEEK_SET) != 0) + { + puts ("2nd lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + dir = fdopendir (dupfd); + if (dir == NULL) + { + puts ("2nd fdopendir failed"); + return 1; + } + bool seen_file = false; + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + if (strcmp (d->d_name, "some-file") != 0) + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + + seen_file = true; + } + closedir (dir); + + if (!seen_file) + { + puts ("file not created in correct directory"); + return 1; + } + + /* Remove the file now. */ + if (unlinkat (dir_fd, "some-file", 0) != 0) + { + puts ("unlinkat failed"); + return 1; + } + + /* We won't need dir_fd anymore after this, so use it. */ + if (lseek (dir_fd, 0, SEEK_SET) != 0) + { + puts ("3rd lseek failed"); + return 1; + } + + /* The directory should be empty safe the . and .. files. */ + dir = fdopendir (dir_fd); + if (dir == NULL) + { + puts ("3rd fdopendir failed"); + return 1; + } + while ((d = readdir64 (dir)) != NULL) + if (strcmp (d->d_name, ".") != 0 && strcmp (d->d_name, "..") != 0) + { + if (strcmp (d->d_name, "some-file") == 0) + { + puts ("some-file not removed"); + return 1; + } + else + { + printf ("temp directory contains file \"%s\"\n", d->d_name); + return 1; + } + } + closedir (dir); + + return 0; +} diff --git a/REORG.TODO/io/ttyname.c b/REORG.TODO/io/ttyname.c new file mode 100644 index 0000000000..dc4f11890f --- /dev/null +++ b/REORG.TODO/io/ttyname.c @@ -0,0 +1,35 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> + + +char *__ttyname = NULL; + +/* Return the pathname of the terminal FD is open on, or NULL on errors. + The returned storage is good only until the next call to this function. */ +char * +ttyname (int fd) +{ + __set_errno (ENOSYS); + return NULL; +} + + +stub_warning (ttyname) diff --git a/REORG.TODO/io/ttyname_r.c b/REORG.TODO/io/ttyname_r.c new file mode 100644 index 0000000000..a5f5311b09 --- /dev/null +++ b/REORG.TODO/io/ttyname_r.c @@ -0,0 +1,32 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <unistd.h> + + +/* Store at most BUFLEN characters the pathname of the terminal FD is + open on in BUF. Return 0 on success, otherwise an error number. */ +int +__ttyname_r (int fd, char *buf, size_t buflen) +{ + __set_errno (ENOSYS); + return ENOSYS; +} +weak_alias (__ttyname_r, ttyname_r) + +stub_warning (ttyname_r) diff --git a/REORG.TODO/io/umask.c b/REORG.TODO/io/umask.c new file mode 100644 index 0000000000..d40e06c3f2 --- /dev/null +++ b/REORG.TODO/io/umask.c @@ -0,0 +1,31 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sys/stat.h> +#include <errno.h> +#include <sys/types.h> + +/* Set the file creation mask to MASK, returning the old mask. */ +mode_t +__umask (mode_t mask) +{ + __set_errno (ENOSYS); + return -1; +} +stub_warning (umask) + +weak_alias (__umask, umask) diff --git a/REORG.TODO/io/unlink.c b/REORG.TODO/io/unlink.c new file mode 100644 index 0000000000..54f2c9c77f --- /dev/null +++ b/REORG.TODO/io/unlink.c @@ -0,0 +1,38 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <unistd.h> + + +/* Remove the link named NAME. */ +int +__unlink (const char *name) +{ + if (name == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (unlink) + +weak_alias (__unlink, unlink) diff --git a/REORG.TODO/io/unlinkat.c b/REORG.TODO/io/unlinkat.c new file mode 100644 index 0000000000..aeed80edd4 --- /dev/null +++ b/REORG.TODO/io/unlinkat.c @@ -0,0 +1,43 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stddef.h> +#include <unistd.h> + + +/* Remove the link named NAME. */ +int +unlinkat (int fd, const char *name, int flag) +{ + if (name == NULL || (flag & AT_REMOVEDIR) != 0) + { + __set_errno (EINVAL); + return -1; + } + + if (fd < 0 && fd != AT_FDCWD) + { + __set_errno (EBADF); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (unlinkat) diff --git a/REORG.TODO/io/utime.c b/REORG.TODO/io/utime.c new file mode 100644 index 0000000000..242ccd120a --- /dev/null +++ b/REORG.TODO/io/utime.c @@ -0,0 +1,39 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <stddef.h> +#include <utime.h> + + +/* Set the access and modification times of FILE to those given in TIMES. + If TIMES is NULL, set them to the current time. */ +int +utime (const char *file, const struct utimbuf *times) +{ + if (file == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (utime) + +stub_warning (utime) diff --git a/REORG.TODO/io/utime.h b/REORG.TODO/io/utime.h new file mode 100644 index 0000000000..44a4e9cddd --- /dev/null +++ b/REORG.TODO/io/utime.h @@ -0,0 +1,50 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +/* + * POSIX Standard: 5.6.6 Set File Access and Modification Times <utime.h> + */ + +#ifndef _UTIME_H +#define _UTIME_H 1 + +#include <features.h> + +__BEGIN_DECLS + +#include <bits/types.h> + +#if defined __USE_XOPEN || defined __USE_XOPEN2K +# include <bits/types/time_t.h> +#endif + +/* Structure describing file times. */ +struct utimbuf + { + __time_t actime; /* Access time. */ + __time_t modtime; /* Modification time. */ + }; + +/* Set the access and modification times of FILE to those given in + *FILE_TIMES. If FILE_TIMES is NULL, set them to the current time. */ +extern int utime (const char *__file, + const struct utimbuf *__file_times) + __THROW __nonnull ((1)); + +__END_DECLS + +#endif /* utime.h */ diff --git a/REORG.TODO/io/utimensat.c b/REORG.TODO/io/utimensat.c new file mode 100644 index 0000000000..f45eb73b93 --- /dev/null +++ b/REORG.TODO/io/utimensat.c @@ -0,0 +1,32 @@ +/* Change access and modification times of open file. Stub version. + Copyright (C) 2007-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/stat.h> + + +/* Change the access time of FILE to TSP[0] and + the modification time of FILE to TSP[1]. */ +int +utimensat (int fd, const char *file, const struct timespec tsp[2], + int flags) +{ + __set_errno (ENOSYS); + return -1; +} +stub_warning (utimensat) diff --git a/REORG.TODO/io/write.c b/REORG.TODO/io/write.c new file mode 100644 index 0000000000..cb413c76f9 --- /dev/null +++ b/REORG.TODO/io/write.c @@ -0,0 +1,48 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <sysdep.h> +#include <errno.h> +#include <unistd.h> +#include <stddef.h> + +/* Write NBYTES of BUF to FD. Return the number written, or -1. */ +ssize_t +__libc_write (int fd, const void *buf, size_t nbytes) +{ + if (nbytes == 0) + return 0; + if (fd < 0) + { + __set_errno (EBADF); + return -1; + } + if (buf == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +libc_hidden_def (__libc_write) +stub_warning (write) + +weak_alias (__libc_write, __write) +libc_hidden_weak (__write) +weak_alias (__libc_write, write) diff --git a/REORG.TODO/io/xmknod.c b/REORG.TODO/io/xmknod.c new file mode 100644 index 0000000000..1daade187f --- /dev/null +++ b/REORG.TODO/io/xmknod.c @@ -0,0 +1,40 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/types.h> +#include <sys/stat.h> + +/* Create a device file named PATH, with permission and special bits MODE + and device number DEV (which can be constructed from major and minor + device numbers with the `makedev' macro above). */ +int +__xmknod (int vers, const char *path, mode_t mode, dev_t *dev) +{ + if (vers != _MKNOD_VER) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (__xmknod) + +weak_alias (__xmknod, _xmknod) +libc_hidden_def (__xmknod) diff --git a/REORG.TODO/io/xmknodat.c b/REORG.TODO/io/xmknodat.c new file mode 100644 index 0000000000..060c0ef074 --- /dev/null +++ b/REORG.TODO/io/xmknodat.c @@ -0,0 +1,62 @@ +/* Copyright (C) 2005-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <fcntl.h> +#include <stddef.h> +#include <sys/types.h> +#include <sys/stat.h> + +/* Create a device file named PATH relative to FD, with permission and + special bits MODE and device number DEV (which can be constructed + from major and minor device numbers with the `makedev' macro + above). */ +int +__xmknodat (int vers, int fd, const char *path, mode_t mode, dev_t *dev) +{ + if (vers != _MKNOD_VER) + { + __set_errno (EINVAL); + return -1; + } + + if (path == NULL) + { + __set_errno (EINVAL); + return -1; + } + + if (fd != AT_FDCWD && path[0] != '/') + { + /* Check FD is associated with a directory. */ + struct stat64 st; + if (__fxstat64 (_STAT_VER, fd, &st) != 0) + return -1; + + if (!S_ISDIR (st.st_mode)) + { + __set_errno (ENOTDIR); + return -1; + } + } + + __set_errno (ENOSYS); + return -1; +} +stub_warning (__xmknodat) + +libc_hidden_def (__xmknodat) diff --git a/REORG.TODO/io/xstat.c b/REORG.TODO/io/xstat.c new file mode 100644 index 0000000000..5a4de7cd76 --- /dev/null +++ b/REORG.TODO/io/xstat.c @@ -0,0 +1,37 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/stat.h> +#include <stddef.h> + +/* Get file information about FILE in BUF. */ +int +__xstat (int vers, const char *file, struct stat *buf) +{ + if (vers != _STAT_VER || file == NULL || buf == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +hidden_def (__xstat) +stub_warning (stat) +weak_alias (__xstat, _xstat) diff --git a/REORG.TODO/io/xstat64.c b/REORG.TODO/io/xstat64.c new file mode 100644 index 0000000000..12b9549f74 --- /dev/null +++ b/REORG.TODO/io/xstat64.c @@ -0,0 +1,36 @@ +/* Copyright (C) 1991-2017 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; if not, see + <http://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <sys/stat.h> +#include <stddef.h> + +/* Get file information about FILE in BUF. */ +int +__xstat64 (int vers, const char *file, struct stat64 *buf) +{ + if (vers != _STAT_VER || file == NULL || buf == NULL) + { + __set_errno (EINVAL); + return -1; + } + + __set_errno (ENOSYS); + return -1; +} +hidden_def (__xstat64) +stub_warning (stat64) |