diff options
-rw-r--r-- | .gitignore | 2 | ||||
-rw-r--r-- | configure.ac | 3 | ||||
-rw-r--r-- | src/misc.c | 26 | ||||
-rw-r--r-- | src/misc.h | 8 | ||||
-rw-r--r-- | tests/Makefile.am | 4 | ||||
-rw-r--r-- | tests/internals/Makefile.am | 8 | ||||
-rw-r--r-- | tests/internals/test_internals.c | 65 | ||||
-rwxr-xr-x | tests/internals/test_internals_valgrind.sh | 3 |
8 files changed, 118 insertions, 1 deletions
@@ -35,4 +35,6 @@ Makefile src/bindfs tests/readdir_inode tests/*.log +tests/internals/test_internals +tests/internals/*.log diff --git a/configure.ac b/configure.ac index 6d3e348..a4c26a0 100644 --- a/configure.ac +++ b/configure.ac @@ -45,6 +45,7 @@ PKG_CHECK_MODULES([fuse], [fuse >= 2.5.3]) AC_CONFIG_FILES([Makefile \ src/Makefile \ - tests/Makefile]) + tests/Makefile \ + tests/internals/Makefile]) AC_OUTPUT @@ -82,6 +82,32 @@ const char *my_basename(const char *path) return path; } +const char *my_dirname(char *path) +{ + if (strcmp(path, ".") == 0) { + return ".."; + } else if (strcmp(path, "/") == 0) { + return "/"; + } else { + int len = strlen(path); + char *p = path + len - 1; + while (p > path) { + if (*p == '/') { + break; + } + --p; + } + if (p > path) { + *p = '\0'; + return path; + } else if (*path == '/') { + return "/"; + } else { + return "."; + } + } +} + void grow_array_impl(void **array, int* capacity, int member_size) { int new_cap = *capacity; @@ -38,6 +38,14 @@ char *strdup_until(const char *s, const char *endchars); Returns NULL if path is NULL. */ const char *my_basename(const char *path); +/* A thread-safe version of dirname, with slightly different behavior. + If path is ".", returns "..". + If path is "/", returns "/". + If path has an initial slash but no other slashes, returns "/". + If path contains a slash, replaces the last slash with a '\0' and returns path. + Otherwise, returns ".". */ +const char *my_dirname(char *path); + /* Reallocs `*array` (may be NULL) to be at least one larger than `*capacity` (may be 0) and stores the new capacity in `*capacity`. */ diff --git a/tests/Makefile.am b/tests/Makefile.am index ce11f95..8210f2b 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -2,4 +2,8 @@ noinst_PROGRAMS = readdir_inode readdir_inode_SOURCES = readdir_inode.c +test_internals_CPPFLAGS = ${my_CPPFLAGS} ${fuse_CFLAGS} +test_internals_CFLAGS = ${my_CFLAGS} + TESTS = test_bindfs.rb +SUBDIRS = internals diff --git a/tests/internals/Makefile.am b/tests/internals/Makefile.am new file mode 100644 index 0000000..7f1568b --- /dev/null +++ b/tests/internals/Makefile.am @@ -0,0 +1,8 @@ + +noinst_PROGRAMS = test_internals +test_internals_SOURCES = test_internals.c $(top_builddir)/src/misc.c + +test_internals_CPPFLAGS = ${my_CPPFLAGS} ${fuse_CFLAGS} -I$(top_builddir)/src +test_internals_CFLAGS = ${my_CFLAGS} + +TESTS = test_internals_valgrind.sh diff --git a/tests/internals/test_internals.c b/tests/internals/test_internals.c new file mode 100644 index 0000000..b388ddb --- /dev/null +++ b/tests/internals/test_internals.c @@ -0,0 +1,65 @@ + +#include "misc.h" +#include <string.h> +#include <stdio.h> +#include <stdlib.h> + +int failures = 0; + +#define TEST_ASSERT(expr) do { if (!(expr)) { printf("Assertion failed: `%s'\n", #expr); failures++; } } while (0); + +void test_my_dirname(char *arg, const char *expected) +{ + char *orig = strdup(arg); + + const char *ret = my_dirname(arg); + if (strcmp(ret, expected) != 0) { + printf("Expected my_dirname(`%s') to return `%s' but got `%s'\n", orig, expected, ret); + failures++; + } + + free(orig); +} + +void my_dirname_suite() +{ + char buf[256]; + + strcpy(buf, "/foo/bar/baz"); + test_my_dirname(buf, "/foo/bar"); + + strcpy(buf, "/foo/bar"); + test_my_dirname(buf, "/foo"); + + strcpy(buf, "/foo"); + test_my_dirname(buf, "/"); + + strcpy(buf, "/foo/"); + test_my_dirname(buf, "/foo"); + + strcpy(buf, "/"); + test_my_dirname(buf, "/"); + + strcpy(buf, "foo"); + test_my_dirname(buf, "."); + + strcpy(buf, "foo/bar"); + test_my_dirname(buf, "foo"); + + strcpy(buf, "./foo/bar"); + test_my_dirname(buf, "./foo"); + + strcpy(buf, "./foo"); + test_my_dirname(buf, "."); + + strcpy(buf, "."); + test_my_dirname(buf, ".."); +} + +int main() +{ + my_dirname_suite(); + + return (failures > 0) ? 1 : 0; +} + diff --git a/tests/internals/test_internals_valgrind.sh b/tests/internals/test_internals_valgrind.sh new file mode 100755 index 0000000..a84c664 --- /dev/null +++ b/tests/internals/test_internals_valgrind.sh @@ -0,0 +1,3 @@ +#!/bin/sh +cd `dirname "$0"` +valgrind --error-exitcode=100 ./test_internals |