use larger string heap
[rrq/fuse_xattrs.git] / fuse_xattrs.c
index 3d3a5a493abed3208166a44fc4167bc1ea694a4d..a19b1e595ace8198b415b34e06fdf65705a020e5 100644 (file)
 #include "xattrs_config.h"
 #include "utils.h"
 #include "passthrough.h"
-
+#include "stringmem.h"
 #include "binary_storage.h"
 
+struct xattrs_config xattrs_config;
+
 static int xmp_setxattr(const char *path, const char *name, const char *value, size_t size, int flags)
 {
     if (xattrs_config.show_sidecar == 0 && filename_is_sidecar(path) == 1)  {
@@ -64,11 +66,11 @@ static int xmp_setxattr(const char *path, const char *name, const char *value, s
     debug_print("path=%s name=%s value=%s size=%zu XATTR_CREATE=%d XATTR_REPLACE=%d\n",
                 _path, name, sanitized_value, size, flags & XATTR_CREATE, flags & XATTR_REPLACE);
 
-    free(sanitized_value);
+    strfree(sanitized_value);
 #endif
 
     int rtval = binary_storage_write_key(_path, name, value, size, flags);
-    free(_path);
+    strfree(_path);
 
     return rtval;
 }
@@ -91,7 +93,7 @@ static int xmp_getxattr(const char *path, const char *name, char *value, size_t
     char *_path = prepend_source_directory(path);
     debug_print("path=%s name=%s size=%zu\n", _path, name, size);
     int rtval = binary_storage_read_key(_path, name, value, size);
-    free(_path);
+    strfree(_path);
 
     return rtval;
 }
@@ -122,7 +124,7 @@ static int xmp_listxattr(const char *path, char *list, size_t size)
     char *_path = prepend_source_directory(path);
     debug_print("path=%s size=%zu\n", _path, size);
     int rtval = binary_storage_list_keys(_path, list, size);
-    free(_path);
+    strfree(_path);
 
     return rtval;
 }
@@ -145,11 +147,13 @@ static int xmp_removexattr(const char *path, const char *name)
     char *_path = prepend_source_directory(path);
     debug_print("path=%s name=%s\n", _path, name);
     int rtval = binary_storage_remove_key(_path, name);
-    free(_path);
+    strfree(_path);
 
     return rtval;
 }
 
+extern int xmp_utimens(const char *path, const struct timespec ts[2]);
+
 static struct fuse_operations xmp_oper = {
         .getattr     = xmp_getattr,
         .access      = xmp_access,
@@ -190,45 +194,20 @@ static struct fuse_operations xmp_oper = {
 
 /**
  * Check if the path is valid. If it's a relative path,
- * prepend the working path.
+ * prepend the working path. Ensure it ends with /
  * @param path relative or absolute path to eval.
  * @return new string with absolute path
  */
 const char *sanitized_source_directory(const char *path) {
-    char *absolute_path;
-    if (strlen(path) == 0) {
-        return NULL;
+    char *absolute_path = stralloc( PATH_MAX );
+    if ( ( strlen( path ) == 0 ) ||
+        ( realpath( path, absolute_path ) == 0 ) ||
+        ( is_directory( absolute_path ) == -1 ) ) {
+       return NULL; // Path badness
     }
 
-    /* absolute path, we don't do anything */
-    if (path[0] == '/') {
-        if (is_directory(path) == -1) {
-            return NULL;
-        }
-        absolute_path = strdup(path);
-        return absolute_path;
-    }
-
-    static char cwd[MAXPATHLEN];
-    char *pwd = getcwd(cwd, sizeof(cwd));
-    size_t len = strlen(pwd) + 1 + strlen(path) + 1;
-    int has_trailing_backslash = (path[strlen(path)-1] == '/');
-    if (!has_trailing_backslash)
-        len++;
-
-    absolute_path = (char*) malloc(sizeof(char) * len);
-    memset(absolute_path, '\0', len);
-    sprintf(absolute_path, "%s/%s", pwd, path);
-
-    if(!has_trailing_backslash)
-        absolute_path[len-2] = '/';
-
-    if (is_directory(absolute_path) == -1) {
-        free(absolute_path);
-        return NULL;
-    }
-
-    return absolute_path;
+    // Allocate new memory for the string
+    return strdup( absolute_path );
 }
 
 enum {
@@ -241,6 +220,7 @@ enum {
 static struct fuse_opt xattrs_opts[] = {
         FUSE_XATTRS_OPT("show_sidecar",         show_sidecar,       1),
         FUSE_XATTRS_OPT("enable_namespaces",    enable_namespaces,  1),
+       FUSE_XATTRS_OPT("sroot=%s", sidecar_dir, 0 ),
 
         FUSE_OPT_KEY("-V",                 KEY_VERSION),
         FUSE_OPT_KEY("--version",          KEY_VERSION),
@@ -264,16 +244,17 @@ static int xattrs_opt_proc(void *data, const char *arg, int key,
         case KEY_HELP:
             fprintf(stderr,
                     "usage: %s source_dir mountpoint [options]\n"
-                            "\n"
-                            "general options:\n"
-                            "    -o opt,[opt...]  mount options\n"
-                            "    -h   --help      print help\n"
-                            "    -V   --version   print version\n"
-                            "\n"
-                            "FUSE XATTRS options:\n"
-                            "    -o show_sidecar  don't hide sidecar files\n"
-                            "    -o enable_namespaces  enable namespaces checks\n"
-                            "\n", outargs->argv[0]);
+                   "\n"
+                   "general options:\n"
+                   "    -o opt,[opt...]  mount options\n"
+                   "    -h   --help      print help\n"
+                   "    -V   --version   print version\n"
+                   "\n"
+                   "FUSE XATTRS options:\n"
+                   "    -o show_sidecar  don't hide sidecar files\n"
+                   "    -o enable_namespaces  enable namespaces checks\n"
+                   "    -o sroot=path  use other sidecar root path\n"
+                   "\n", outargs->argv[0]);
 
             fuse_opt_add_arg(outargs, "-ho");
             fuse_main(outargs->argc, outargs->argv, &xmp_oper, NULL);
@@ -296,6 +277,12 @@ int main(int argc, char *argv[]) {
         exit(1);
     }
 
+    if ( xattrs_config.sidecar_dir ) {
+       xattrs_config.sidecar_dir =
+           sanitized_source_directory( xattrs_config.sidecar_dir );
+       xattrs_config.sidecar_dir_size = strlen( xattrs_config.sidecar_dir );
+    }
+    
     if (!xattrs_config.source_dir) {
         fprintf(stderr, "missing source directory\n");
         fprintf(stderr, "see `%s -h' for usage\n", argv[0]);