Mercurial > hg > octave-lyh > gnulib-hg
changeset 12061:c47da311af77
test-symlinkat: enhance test
* tests/test-readlink.c (main): Move guts...
* tests/test-readlink.h (test_readlink): ...into new file.
* tests/test-symlink.c (main): Move guts...
* tests/test-symlink.h (test_symlink): ...into new file.
* tests/test-symlinkat.c (main): Use new files for further
coverage.
(do_symlink, do_readlink): New helper functions.
* modules/symlink-tests (Files): Ship new file.
(Depends-on): Add stdbool.
* modules/readlink-tests (Files): Ship new file.
(Depends-on): Add stdbool.
* modules/symlinkat-tests (Files): Use new files.
Signed-off-by: Eric Blake <ebb9@byu.net>
author | Eric Blake <ebb9@byu.net> |
---|---|
date | Mon, 21 Sep 2009 14:07:44 -0600 |
parents | 95a12a00ea4f |
children | 00e8f52bdef4 |
files | ChangeLog modules/readlink-tests modules/symlink-tests modules/symlinkat-tests tests/test-readlink.c tests/test-readlink.h tests/test-symlink.c tests/test-symlink.h tests/test-symlinkat.c |
diffstat | 9 files changed, 262 insertions(+), 171 deletions(-) [+] |
line wrap: on
line diff
--- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,19 @@ +2009-09-23 Eric Blake <ebb9@byu.net> + + test-symlinkat: enhance test + * tests/test-readlink.c (main): Move guts... + * tests/test-readlink.h (test_readlink): ...into new file. + * tests/test-symlink.c (main): Move guts... + * tests/test-symlink.h (test_symlink): ...into new file. + * tests/test-symlinkat.c (main): Use new files for further + coverage. + (do_symlink, do_readlink): New helper functions. + * modules/symlink-tests (Files): Ship new file. + (Depends-on): Add stdbool. + * modules/readlink-tests (Files): Ship new file. + (Depends-on): Add stdbool. + * modules/symlinkat-tests (Files): Use new files. + 2009-09-23 Eric Blake <ebb9@byu.net> readlink: document portability issue with symlink length
--- a/modules/readlink-tests +++ b/modules/readlink-tests @@ -1,7 +1,9 @@ Files: +tests/test-readlink.h tests/test-readlink.c Depends-on: +stdbool symlink configure.ac:
--- a/modules/symlink-tests +++ b/modules/symlink-tests @@ -1,7 +1,9 @@ Files: +tests/test-symlink.h tests/test-symlink.c Depends-on: +stdbool configure.ac:
--- a/modules/symlinkat-tests +++ b/modules/symlinkat-tests @@ -1,4 +1,6 @@ Files: +tests/test-readlink.h +tests/test-symlink.h tests/test-symlinkat.c Depends-on:
--- a/tests/test-readlink.c +++ b/tests/test-readlink.c @@ -22,6 +22,7 @@ #include <fcntl.h> #include <errno.h> +#include <stdbool.h> #include <stdio.h> #include <stdlib.h> #include <string.h> @@ -41,89 +42,13 @@ #define BASE "test-readlink.t" +#include "test-readlink.h" + int main () { - char buf[80]; - /* Remove any leftovers from a previous partial run. */ ASSERT (system ("rm -rf " BASE "*") == 0); - /* Sanity checks of failures. Mingw lacks symlink, but readlink can - still distinguish between various errors. */ - memset (buf, 0xff, sizeof buf); - errno = 0; - ASSERT (readlink ("no_such", buf, sizeof buf) == -1); - ASSERT (errno == ENOENT); - errno = 0; - ASSERT (readlink ("no_such/", buf, sizeof buf) == -1); - ASSERT (errno == ENOENT); - errno = 0; - ASSERT (readlink ("", buf, sizeof buf) == -1); - ASSERT (errno == ENOENT); - errno = 0; - ASSERT (readlink (".", buf, sizeof buf) == -1); - ASSERT (errno == EINVAL); - errno = 0; - ASSERT (readlink ("./", buf, sizeof buf) == -1); - ASSERT (errno == EINVAL); - ASSERT (close (creat (BASE "file", 0600)) == 0); - errno = 0; - ASSERT (readlink (BASE "file", buf, sizeof buf) == -1); - ASSERT (errno == EINVAL); - errno = 0; - ASSERT (readlink (BASE "file/", buf, sizeof buf) == -1); - ASSERT (errno == ENOTDIR); - ASSERT (unlink (BASE "file") == 0); - - /* Now test actual symlinks. */ - if (symlink (BASE "dir", BASE "link")) - { - fputs ("skipping test: symlinks not supported on this filesystem\n", - stderr); - return 77; - } - ASSERT (mkdir (BASE "dir", 0700) == 0); - errno = 0; - ASSERT (readlink (BASE "link/", buf, sizeof buf) == -1); - ASSERT (errno == EINVAL); - { - /* Up till now, no readlink has been successful, so buf should be - unchanged. */ - int i; - for (i = 0; i < sizeof buf; i++) - ASSERT (buf[i] == (char) 0xff); - } - { - size_t len = strlen (BASE "dir"); - /* When passing too small of a buffer, expect the truncated - length, or an ERANGE failure. However, a size of 0 is not - portable enough to test. */ - ssize_t result; - errno = 0; - result = readlink (BASE "link", buf, 1); - if (result == -1) - { - ASSERT (errno == ERANGE); - ASSERT (buf[0] == (char) 0xff); - } - else - { - ASSERT (result == 1); - ASSERT (buf[0] == BASE[0]); - } - ASSERT (buf[1] == (char) 0xff); - ASSERT (readlink (BASE "link", buf, len) == len); - ASSERT (strncmp (buf, BASE "dir", len) == 0); - ASSERT (buf[len] == (char) 0xff); - ASSERT (readlink (BASE "link", buf, sizeof buf) == len); - ASSERT (strncmp (buf, BASE "dir", len) == 0); - /* POSIX says rest of buf is unspecified; but in practice, it is - either left alone, or NUL-terminated. */ - ASSERT (buf[len] == '\0' || buf[len] == (char) 0xff); - } - ASSERT (rmdir (BASE "dir") == 0); - ASSERT (unlink (BASE "link") == 0); - - return 0; + return test_readlink (readlink, true); }
new file mode 100644 --- /dev/null +++ b/tests/test-readlink.h @@ -0,0 +1,108 @@ +/* Tests of readlink. + Copyright (C) 2009 Free Software Foundation, Inc. + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + This program 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 General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see <http://www.gnu.org/licenses/>. */ + +/* Written by Eric Blake <ebb9@byu.net>, 2009. */ + +/* This file is designed to test both readlink(a,b,c) and + readlinkat(AT_FDCWD,a,b,c). FUNC is the function to test. Assumes + that BASE and ASSERT are already defined, and that appropriate + headers are already included. If PRINT, warn before skipping + symlink tests with status 77. */ + +static int +test_readlink (ssize_t (*func) (char const *, char *, size_t), bool print) +{ + char buf[80]; + + /* Sanity checks of failures. Mingw lacks symlink, but readlink can + still distinguish between various errors. */ + memset (buf, 0xff, sizeof buf); + errno = 0; + ASSERT (func ("no_such", buf, sizeof buf) == -1); + ASSERT (errno == ENOENT); + errno = 0; + ASSERT (func ("no_such/", buf, sizeof buf) == -1); + ASSERT (errno == ENOENT); + errno = 0; + ASSERT (func ("", buf, sizeof buf) == -1); + ASSERT (errno == ENOENT); + errno = 0; + ASSERT (func (".", buf, sizeof buf) == -1); + ASSERT (errno == EINVAL); + errno = 0; + ASSERT (func ("./", buf, sizeof buf) == -1); + ASSERT (errno == EINVAL); + ASSERT (close (creat (BASE "file", 0600)) == 0); + errno = 0; + ASSERT (func (BASE "file", buf, sizeof buf) == -1); + ASSERT (errno == EINVAL); + errno = 0; + ASSERT (func (BASE "file/", buf, sizeof buf) == -1); + ASSERT (errno == ENOTDIR); + ASSERT (unlink (BASE "file") == 0); + + /* Now test actual symlinks. */ + if (symlink (BASE "dir", BASE "link")) + { + if (print) + fputs ("skipping test: symlinks not supported on this filesystem\n", + stderr); + return 77; + } + ASSERT (mkdir (BASE "dir", 0700) == 0); + errno = 0; + ASSERT (func (BASE "link/", buf, sizeof buf) == -1); + ASSERT (errno == EINVAL); + { + /* Up till now, no readlink has been successful, so buf should be + unchanged. */ + int i; + for (i = 0; i < sizeof buf; i++) + ASSERT (buf[i] == (char) 0xff); + } + { + size_t len = strlen (BASE "dir"); + /* When passing too small of a buffer, expect the truncated + length, or an ERANGE failure. However, a size of 0 is not + portable enough to test. */ + ssize_t result; + errno = 0; + result = readlink (BASE "link", buf, 1); + if (result == -1) + { + ASSERT (errno == ERANGE); + ASSERT (buf[0] == (char) 0xff); + } + else + { + ASSERT (result == 1); + ASSERT (buf[0] == BASE[0]); + } + ASSERT (buf[1] == (char) 0xff); + ASSERT (func (BASE "link", buf, len) == len); + ASSERT (strncmp (buf, BASE "dir", len) == 0); + ASSERT (buf[len] == (char) 0xff); + ASSERT (func (BASE "link", buf, sizeof buf) == len); + ASSERT (strncmp (buf, BASE "dir", len) == 0); + /* POSIX says rest of buf is unspecified; but in practice, it is + either left alone, or NUL-terminated. */ + ASSERT (buf[len] == '\0' || buf[len] == (char) 0xff); + } + ASSERT (rmdir (BASE "dir") == 0); + ASSERT (unlink (BASE "link") == 0); + + return 0; +}
--- a/tests/test-symlink.c +++ b/tests/test-symlink.c @@ -22,6 +22,7 @@ #include <fcntl.h> #include <errno.h> +#include <stdbool.h> #include <stdio.h> #include <stdlib.h> #include <sys/stat.h> @@ -40,58 +41,13 @@ #define BASE "test-symlink.t" +#include "test-symlink.h" + int main () { /* Remove any leftovers from a previous partial run. */ ASSERT (system ("rm -rf " BASE "*") == 0); - if (symlink ("nowhere", BASE "link1")) - { - fputs ("skipping test: symlinks not supported on this filesystem\n", - stderr); - return 77; - } - - /* Some systems allow the creation of 0-length symlinks as a synonym - for "."; but most reject it. */ - errno = 0; - if (symlink ("", BASE "link2") == -1) - ASSERT (errno == ENOENT || errno == EINVAL); - else - ASSERT (unlink (BASE "link2") == 0); - - /* Sanity checks of failures. */ - errno = 0; - ASSERT (symlink ("nowhere", "") == -1); - ASSERT (errno == ENOENT); - errno = 0; - ASSERT (symlink ("nowhere", ".") == -1); - ASSERT (errno == EEXIST || errno == EINVAL); - errno = 0; - ASSERT (symlink ("somewhere", BASE "link1") == -1); - ASSERT (errno == EEXIST); - errno = 0; - ASSERT (symlink ("nowhere", BASE "link2/") == -1); - ASSERT (errno == ENOTDIR || errno == ENOENT); - ASSERT (mkdir (BASE "dir", 0700) == 0); - errno = 0; - ASSERT (symlink ("nowhere", BASE "dir") == -1); - ASSERT (errno == EEXIST); - errno = 0; - ASSERT (symlink ("nowhere", BASE "dir/") == -1); - ASSERT (errno == EEXIST); - ASSERT (close (creat (BASE "file", 0600)) == 0); - errno = 0; - ASSERT (symlink ("nowhere", BASE "file") == -1); - ASSERT (errno == EEXIST); - errno = 0; - ASSERT (symlink ("nowhere", BASE "file/") == -1); - ASSERT (errno == EEXIST || errno == ENOTDIR); - - ASSERT (rmdir (BASE "dir") == 0); - ASSERT (unlink (BASE "file") == 0); - ASSERT (unlink (BASE "link1") == 0); - - return 0; + return test_symlink (symlink, true); }
new file mode 100644 --- /dev/null +++ b/tests/test-symlink.h @@ -0,0 +1,77 @@ +/* Tests of symlink. + Copyright (C) 2009 Free Software Foundation, Inc. + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + This program 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 General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see <http://www.gnu.org/licenses/>. */ + +/* Written by Eric Blake <ebb9@byu.net>, 2009. */ + +/* This file is designed to test both symlink(a,b) and + symlinkat(a,AT_FDCWD,b). FUNC is the function to test. Assumes + that BASE and ASSERT are already defined, and that appropriate + headers are already included. If PRINT, warn before skipping + symlink tests with status 77. */ + +static int +test_symlink (int (*func) (char const *, char const *), bool print) +{ + if (func ("nowhere", BASE "link1")) + { + if (print) + fputs ("skipping test: symlinks not supported on this filesystem\n", + stderr); + return 77; + } + + /* Some systems allow the creation of 0-length symlinks as a synonym + for "."; but most reject it. */ + errno = 0; + if (func ("", BASE "link2") == -1) + ASSERT (errno == ENOENT || errno == EINVAL); + else + ASSERT (unlink (BASE "link2") == 0); + + /* Sanity checks of failures. */ + errno = 0; + ASSERT (func ("nowhere", "") == -1); + ASSERT (errno == ENOENT); + errno = 0; + ASSERT (func ("nowhere", ".") == -1); + ASSERT (errno == EEXIST || errno == EINVAL); + errno = 0; + ASSERT (func ("somewhere", BASE "link1") == -1); + ASSERT (errno == EEXIST); + errno = 0; + ASSERT (func ("nowhere", BASE "link2/") == -1); + ASSERT (errno == ENOTDIR || errno == ENOENT); + ASSERT (mkdir (BASE "dir", 0700) == 0); + errno = 0; + ASSERT (func ("nowhere", BASE "dir") == -1); + ASSERT (errno == EEXIST); + errno = 0; + ASSERT (func ("nowhere", BASE "dir/") == -1); + ASSERT (errno == EEXIST); + ASSERT (close (creat (BASE "file", 0600)) == 0); + errno = 0; + ASSERT (func ("nowhere", BASE "file") == -1); + ASSERT (errno == EEXIST); + errno = 0; + ASSERT (func ("nowhere", BASE "file/") == -1); + ASSERT (errno == EEXIST || errno == ENOTDIR); + + ASSERT (rmdir (BASE "dir") == 0); + ASSERT (unlink (BASE "file") == 0); + ASSERT (unlink (BASE "link1") == 0); + + return 0; +}
--- a/tests/test-symlinkat.c +++ b/tests/test-symlinkat.c @@ -22,6 +22,7 @@ #include <fcntl.h> #include <errno.h> +#include <stdbool.h> #include <stdio.h> #include <stdlib.h> #include <string.h> @@ -43,78 +44,80 @@ } \ while (0) +#define BASE "test-symlinkat.t" + +#include "test-readlink.h" +#include "test-symlink.h" + +static int dfd = AT_FDCWD; + +static int +do_symlink (char const *contents, char const *name) +{ + return symlinkat (contents, dfd, name); +} + +static ssize_t +do_readlink (char const *name, char *buf, size_t len) +{ + return readlinkat (dfd, name, buf, len); +} + int main () { char buf[80]; + int result; - /* Create handle for future use. */ - int dfd = openat (AT_FDCWD, ".", O_RDONLY); - ASSERT (0 <= dfd); + /* Remove any leftovers from a previous partial run. */ + ASSERT (system ("rm -rf " BASE "*") == 0); - /* Sanity checks of failures. Mingw lacks symlinkat, but readlinkat - can still distinguish between various errors. */ - errno = 0; - ASSERT (readlinkat (AT_FDCWD, "no_such", buf, sizeof buf) == -1); - ASSERT (errno == ENOENT); - errno = 0; - ASSERT (readlinkat (dfd, "no_such", buf, sizeof buf) == -1); - ASSERT (errno == ENOENT); - errno = 0; - ASSERT (readlinkat (AT_FDCWD, "", buf, sizeof buf) == -1); - ASSERT (errno == ENOENT); - errno = 0; - ASSERT (readlinkat (dfd, "", buf, sizeof buf) == -1); - ASSERT (errno == ENOENT); - errno = 0; - ASSERT (readlinkat (AT_FDCWD, ".", buf, sizeof buf) == -1); - ASSERT (errno == EINVAL); - errno = 0; - ASSERT (readlinkat (dfd, ".", buf, sizeof buf) == -1); - ASSERT (errno == EINVAL); - errno = 0; - ASSERT (symlinkat ("who cares", AT_FDCWD, "") == -1); - ASSERT (errno == ENOENT || errno == ENOSYS); - errno = 0; - ASSERT (symlinkat ("who cares", dfd, "") == -1); - ASSERT (errno == ENOENT || errno == ENOSYS); + /* Perform same checks as counterpart functions. */ + result = test_readlink (do_readlink, false); + ASSERT (test_symlink (do_symlink, false) == result); + dfd = openat (AT_FDCWD, ".", O_RDONLY); + ASSERT (0 <= dfd); + ASSERT (test_readlink (do_readlink, false) == result); + ASSERT (test_symlink (do_symlink, false) == result); - /* Skip everything else on mingw. */ + /* Now perform some cross-directory checks. Skip everything else on + mingw. */ if (HAVE_SYMLINK) { - const char *linkname = "test-symlinkat.link"; const char *contents = "don't matter!"; - int exp = strlen (contents); + ssize_t exp = strlen (contents); /* Create link while cwd is '.', then read it in '..'. */ - ASSERT (symlinkat (contents, AT_FDCWD, linkname) == 0); + ASSERT (symlinkat (contents, AT_FDCWD, BASE "link") == 0); errno = 0; - ASSERT (symlinkat (contents, dfd, linkname) == -1); + ASSERT (symlinkat (contents, dfd, BASE "link") == -1); ASSERT (errno == EEXIST); ASSERT (chdir ("..") == 0); errno = 0; - ASSERT (readlinkat (AT_FDCWD, linkname, buf, sizeof buf) == -1); + ASSERT (readlinkat (AT_FDCWD, BASE "link", buf, sizeof buf) == -1); ASSERT (errno == ENOENT); - ASSERT (readlinkat (dfd, linkname, buf, sizeof buf) == exp); + ASSERT (readlinkat (dfd, BASE "link", buf, sizeof buf) == exp); ASSERT (strncmp (contents, buf, exp) == 0); - ASSERT (unlinkat (dfd, linkname, 0) == 0); + ASSERT (unlinkat (dfd, BASE "link", 0) == 0); /* Create link while cwd is '..', then read it in '.'. */ - ASSERT (symlinkat (contents, dfd, linkname) == 0); + ASSERT (symlinkat (contents, dfd, BASE "link") == 0); ASSERT (fchdir (dfd) == 0); errno = 0; - ASSERT (symlinkat (contents, AT_FDCWD, linkname) == -1); + ASSERT (symlinkat (contents, AT_FDCWD, BASE "link") == -1); ASSERT (errno == EEXIST); buf[0] = '\0'; - ASSERT (readlinkat (AT_FDCWD, linkname, buf, sizeof buf) == exp); + ASSERT (readlinkat (AT_FDCWD, BASE "link", buf, sizeof buf) == exp); ASSERT (strncmp (contents, buf, exp) == 0); buf[0] = '\0'; - ASSERT (readlinkat (dfd, linkname, buf, sizeof buf) == exp); + ASSERT (readlinkat (dfd, BASE "link", buf, sizeof buf) == exp); ASSERT (strncmp (contents, buf, exp) == 0); - ASSERT (unlink (linkname) == 0); + ASSERT (unlink (BASE "link") == 0); } ASSERT (close (dfd) == 0); - - return 0; + if (result == 77) + fputs ("skipping test: symlinks not supported on this filesystem\n", + stderr); + return result; }