diff --git a/docs/technical/path.txt b/docs/technical/path.txt index ecada5d..36db655 100644 --- a/docs/technical/path.txt +++ b/docs/technical/path.txt @@ -17,7 +17,12 @@ Functions `is_dir()`:: Returns a non zero value if 'path' is a directory. zero otherwise. - + +`mkpath()`:: + + Formats a "functional correct" path (that works with `open()`, `stat()` etc). + + Returns a staticly allocated string. + `path_normalize`:: Returns a string that contains the normalized full path specified by 'base', 'name' and 'dir'. + diff --git a/src/path.c b/src/path.c index 7e3c26b..7ca8bad 100644 --- a/src/path.c +++ b/src/path.c @@ -67,6 +67,32 @@ int is_dir(const char *path) { return 0; } +const char *mkpath(const char *fmt, ...) { + + static strbuf_t sb = STRBUF_INIT; + va_list va; + int len; + + if (strbuf_avail(&sb)) { + strbuf_reduce(&sb, sb.len); + } else { + strbuf_expand(&sb, 1); + } + + va_start(va, fmt); + len = strbuf_append_va(&sb, fmt, va); + va_end(va); + + if (len > 0) { + strbuf_expand(&sb, len); + va_start(va, fmt); + strbuf_append_va(&sb, fmt, va); + va_end(va); + } + + return sb.buf; +} + static char* expand_home() { char *home = getenv("HOME"); diff --git a/src/path.h b/src/path.h index 6164aa1..054147f 100644 --- a/src/path.h +++ b/src/path.h @@ -20,6 +20,8 @@ int is_file(const char *path); int is_dir(const char *path); +const char* mkpath(const char *fmt, ...); + char* path_normalize(const char *base, const char *name, unsigned dir); #endif /* __PATH_H */ diff --git a/test/t_path.c b/test/t_path.c index c76422b..51fda72 100644 --- a/test/t_path.c +++ b/test/t_path.c @@ -36,6 +36,12 @@ void test_normalize() { free(ptr); } +void test_mkpath() { + + assert_string(mkpath("%s/%s", "/mnt/", "file"), "/mnt//file"); + assert_string(mkpath("%s/%s%i", "/dev", "tty", 2), "/dev/tty2"); +} + void test_isabspath() { assert(is_abspath("file") == 0); @@ -115,6 +121,7 @@ int main(int argc, char *argv[]) { test_isfile(); test_isdir(); test_normalize(); + test_mkpath(); test_basename(); test_dirname();