diff options
-rw-r--r-- | .gitignore | 1 | ||||
-rw-r--r-- | Makefile | 4 | ||||
-rwxr-xr-x | tests.sh | 22 | ||||
-rw-r--r-- | tests/mksock.c | 131 | ||||
-rw-r--r-- | tests/test_color.out | 1 | ||||
-rw-r--r-- | tests/test_color_ext.out | 1 | ||||
-rw-r--r-- | tests/test_color_ext0.out | 1 | ||||
-rw-r--r-- | tests/test_color_mh.out | 1 | ||||
-rw-r--r-- | tests/test_color_mh0.out | 1 | ||||
-rw-r--r-- | tests/test_color_mi.out | 1 | ||||
-rw-r--r-- | tests/test_color_missing_colon.out | 1 | ||||
-rw-r--r-- | tests/test_color_or.out | 1 | ||||
-rw-r--r-- | tests/test_color_or0_mi.out | 1 | ||||
-rw-r--r-- | tests/test_color_or_mi.out | 1 | ||||
-rw-r--r-- | tests/test_color_or_mi0.out | 1 |
15 files changed, 156 insertions, 13 deletions
@@ -1,3 +1,4 @@ *.o *.d /bfs +/tests/mksock @@ -94,7 +94,7 @@ tests/mksock: tests/mksock.o %.o: %.c $(CC) $(ALL_CFLAGS) -c $< -o $@ -check: all +check: all tests/mksock ./tests.sh distcheck: @@ -107,7 +107,7 @@ endif +$(MAKE) -Bs check clean: - $(RM) bfs *.o *.d + $(RM) bfs *.[od] tests/mksock tests/*.[od] install: $(MKDIR) $(DESTDIR)$(PREFIX)/bin @@ -22,6 +22,16 @@ umask 022 export LC_ALL=C export TZ=UTC +function _realpath() { + ( + cd "${1%/*}" + echo "$PWD/${1##*/}" + ) +} + +BFS="$(_realpath ./bfs)" +TESTS="$(_realpath ./tests)" + # The temporary directory that will hold our test data TMP="$(mktemp -d "${TMPDIR:-/tmp}"/bfs.XXXXXXXXXX)" chown "$(id -u):$(id -g)" "$TMP" @@ -177,7 +187,7 @@ function make_rainbow() { # TODO: block # TODO: chardev ln -s nowhere "$1/broken" - # TODO: socket + "$TESTS/mksock" "$1/socket" touchp "$1"/s{u,g,ug}id chmod u+s "$1"/su{,g}id chmod g+s "$1"/s{u,}gid @@ -195,16 +205,6 @@ function make_scratch() { } make_scratch "$TMP/scratch" -function _realpath() { - ( - cd "${1%/*}" - echo "$PWD/${1##*/}" - ) -} - -BFS="$(_realpath ./bfs)" -TESTS="$(_realpath ./tests)" - posix_tests=( # General parsing test_basic diff --git a/tests/mksock.c b/tests/mksock.c new file mode 100644 index 0000000..a996d58 --- /dev/null +++ b/tests/mksock.c @@ -0,0 +1,131 @@ +/**************************************************************************** + * bfs * + * Copyright (C) 2019 Tavian Barnes <tavianator@tavianator.com> * + * * + * Permission to use, copy, modify, and/or distribute this software for any * + * purpose with or without fee is hereby granted. * + * * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES * + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF * + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR * + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN * + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF * + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * + ****************************************************************************/ + +/** + * There's no standard Unix utility that creates a socket file, so this small + * program does the job. + */ + +#include <errno.h> +#include <fcntl.h> +#include <libgen.h> +#include <stdio.h> +#include <string.h> +#include <stdlib.h> +#include <sys/socket.h> +#include <sys/stat.h> +#include <sys/types.h> +#include <sys/un.h> +#include <unistd.h> + +/** + * Print an error message. + */ +static void errmsg(const char *cmd, const char *path) { + fprintf(stderr, "%s: '%s': %s.\n", cmd, path, strerror(errno)); +} + +/** + * struct sockaddr_un::sun_path is very short, so we chdir() into the target + * directory before creating sockets in case the full path is too long but the + * file name is not. + */ +static int chdir_parent(const char *path) { + char *copy = strdup(path); + if (!copy) { + return -1; + } + const char *dir = dirname(copy); + + int ret = chdir(dir); + + int error = errno; + free(copy); + errno = error; + + return ret; +} + +/** + * Initialize a struct sockaddr_un with the right filename. + */ +static int init_sun(struct sockaddr_un *sock, const char *path) { + size_t len = strlen(path); + if (len == 0 || path[len - 1] == '/') { + errno = ENOENT; + return -1; + } + + char *copy = strdup(path); + if (!copy) { + return -1; + } + const char *base = basename(copy); + + len = strlen(base); + if (len >= sizeof(sock->sun_path)) { + free(copy); + errno = ENAMETOOLONG; + return -1; + } + + sock->sun_family = AF_UNIX; + memcpy(sock->sun_path, base, len + 1); + free(copy); + return 0; +} + +int main(int argc, char *argv[]) { + const char *cmd = argc > 0 ? argv[0] : "mksock"; + + if (argc != 2) { + fprintf(stderr, "Usage: %s NAME\n", cmd); + return EXIT_FAILURE; + } + + const char *path = argv[1]; + + if (chdir_parent(path) != 0) { + errmsg(cmd, path); + return EXIT_FAILURE; + } + + struct sockaddr_un sock; + if (init_sun(&sock, path) != 0) { + errmsg(cmd, path); + return EXIT_FAILURE; + } + + int fd = socket(AF_UNIX, SOCK_STREAM, 0); + if (fd < 0) { + errmsg(cmd, path); + return EXIT_FAILURE; + } + + int ret = EXIT_SUCCESS; + + if (bind(fd, (struct sockaddr *)&sock, sizeof(sock)) != 0) { + errmsg(cmd, path); + ret = EXIT_FAILURE; + } + + if (close(fd) != 0) { + errmsg(cmd, path); + ret = EXIT_FAILURE; + } + + return ret; +} diff --git a/tests/test_color.out b/tests/test_color.out index e267da8..40e09b4 100644 --- a/tests/test_color.out +++ b/tests/test_color.out @@ -1,5 +1,6 @@ [01;34mrainbow[0m [01;34mrainbow/[0m[01;32mexec.sh[0m +[01;34mrainbow/[0m[01;35msocket[0m [01;34mrainbow/[0m[01;36mlink.txt[0m [01;34mrainbow/[0m[30;42msticky_ow[0m [01;34mrainbow/[0m[30;43msgid[0m diff --git a/tests/test_color_ext.out b/tests/test_color_ext.out index d2e2a70..f8c4d28 100644 --- a/tests/test_color_ext.out +++ b/tests/test_color_ext.out @@ -1,5 +1,6 @@ [01;34mrainbow[0m [01;34mrainbow/[0m[01;32mexec.sh[0m +[01;34mrainbow/[0m[01;35msocket[0m [01;34mrainbow/[0m[01;36mlink.txt[0m [01;34mrainbow/[0m[01mfile.txt[0m [01;34mrainbow/[0m[30;42msticky_ow[0m diff --git a/tests/test_color_ext0.out b/tests/test_color_ext0.out index 3bc8dc1..8710fc8 100644 --- a/tests/test_color_ext0.out +++ b/tests/test_color_ext0.out @@ -1,6 +1,7 @@ [01;34mrainbow[0m [01;34mrainbow/[0m[00mfile.txt[0m [01;34mrainbow/[0m[01;32mexec.sh[0m +[01;34mrainbow/[0m[01;35msocket[0m [01;34mrainbow/[0m[01;36mlink.txt[0m [01;34mrainbow/[0m[30;42msticky_ow[0m [01;34mrainbow/[0m[30;43msgid[0m diff --git a/tests/test_color_mh.out b/tests/test_color_mh.out index 600451e..32e2b95 100644 --- a/tests/test_color_mh.out +++ b/tests/test_color_mh.out @@ -1,5 +1,6 @@ [01;34mrainbow[0m [01;34mrainbow/[0m[01;32mexec.sh[0m +[01;34mrainbow/[0m[01;35msocket[0m [01;34mrainbow/[0m[01;36mlink.txt[0m [01;34mrainbow/[0m[01mmh1[0m [01;34mrainbow/[0m[01mmh2[0m diff --git a/tests/test_color_mh0.out b/tests/test_color_mh0.out index e267da8..40e09b4 100644 --- a/tests/test_color_mh0.out +++ b/tests/test_color_mh0.out @@ -1,5 +1,6 @@ [01;34mrainbow[0m [01;34mrainbow/[0m[01;32mexec.sh[0m +[01;34mrainbow/[0m[01;35msocket[0m [01;34mrainbow/[0m[01;36mlink.txt[0m [01;34mrainbow/[0m[30;42msticky_ow[0m [01;34mrainbow/[0m[30;43msgid[0m diff --git a/tests/test_color_mi.out b/tests/test_color_mi.out index e267da8..40e09b4 100644 --- a/tests/test_color_mi.out +++ b/tests/test_color_mi.out @@ -1,5 +1,6 @@ [01;34mrainbow[0m [01;34mrainbow/[0m[01;32mexec.sh[0m +[01;34mrainbow/[0m[01;35msocket[0m [01;34mrainbow/[0m[01;36mlink.txt[0m [01;34mrainbow/[0m[30;42msticky_ow[0m [01;34mrainbow/[0m[30;43msgid[0m diff --git a/tests/test_color_missing_colon.out b/tests/test_color_missing_colon.out index d2e2a70..f8c4d28 100644 --- a/tests/test_color_missing_colon.out +++ b/tests/test_color_missing_colon.out @@ -1,5 +1,6 @@ [01;34mrainbow[0m [01;34mrainbow/[0m[01;32mexec.sh[0m +[01;34mrainbow/[0m[01;35msocket[0m [01;34mrainbow/[0m[01;36mlink.txt[0m [01;34mrainbow/[0m[01mfile.txt[0m [01;34mrainbow/[0m[30;42msticky_ow[0m diff --git a/tests/test_color_or.out b/tests/test_color_or.out index 6e94bc6..e132546 100644 --- a/tests/test_color_or.out +++ b/tests/test_color_or.out @@ -1,5 +1,6 @@ [01;34mrainbow[0m [01;34mrainbow/[0m[01;32mexec.sh[0m +[01;34mrainbow/[0m[01;35msocket[0m [01;34mrainbow/[0m[01;36mlink.txt[0m [01;34mrainbow/[0m[01mbroken[0m [01;34mrainbow/[0m[30;42msticky_ow[0m diff --git a/tests/test_color_or0_mi.out b/tests/test_color_or0_mi.out index cafa798..8b92ded 100644 --- a/tests/test_color_or0_mi.out +++ b/tests/test_color_or0_mi.out @@ -1,5 +1,6 @@ [01;34mrainbow[0m [01;34mrainbow/[0m[01;32mexec.sh[0m +[01;34mrainbow/[0m[01;35msocket[0m [01;34mrainbow/[0m[01;36mbroken[0m [01;34mrainbow/[0m[01;36mlink.txt[0m [01;34mrainbow/[0m[30;42msticky_ow[0m diff --git a/tests/test_color_or_mi.out b/tests/test_color_or_mi.out index 7e57688..8a095a8 100644 --- a/tests/test_color_or_mi.out +++ b/tests/test_color_or_mi.out @@ -1,6 +1,7 @@ [01;34mrainbow[0m [01;34mrainbow/[0m[01;31mbroken[0m [01;34mrainbow/[0m[01;32mexec.sh[0m +[01;34mrainbow/[0m[01;35msocket[0m [01;34mrainbow/[0m[01;36mlink.txt[0m [01;34mrainbow/[0m[30;42msticky_ow[0m [01;34mrainbow/[0m[30;43msgid[0m diff --git a/tests/test_color_or_mi0.out b/tests/test_color_or_mi0.out index 7e57688..8a095a8 100644 --- a/tests/test_color_or_mi0.out +++ b/tests/test_color_or_mi0.out @@ -1,6 +1,7 @@ [01;34mrainbow[0m [01;34mrainbow/[0m[01;31mbroken[0m [01;34mrainbow/[0m[01;32mexec.sh[0m +[01;34mrainbow/[0m[01;35msocket[0m [01;34mrainbow/[0m[01;36mlink.txt[0m [01;34mrainbow/[0m[30;42msticky_ow[0m [01;34mrainbow/[0m[30;43msgid[0m |