"Fossies" - the Fresh Open Source Software Archive

Member "fuse-3.2.1/lib/fuse.c" (14 Nov 2017, 111108 Bytes) of package /linux/misc/fuse-3.2.1.tar.xz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "fuse.c" see the Fossies "Dox" file reference documentation and the latest Fossies "Diffs" side-by-side code changes report: 3.2.0_vs_3.2.1.

    1 /*
    2   FUSE: Filesystem in Userspace
    3   Copyright (C) 2001-2007  Miklos Szeredi <miklos@szeredi.hu>
    4 
    5   Implementation of the high-level FUSE API on top of the low-level
    6   API.
    7 
    8   This program can be distributed under the terms of the GNU LGPLv2.
    9   See the file COPYING.LIB
   10 */
   11 
   12 
   13 /* For pthread_rwlock_t */
   14 #define _GNU_SOURCE
   15 
   16 #include "config.h"
   17 #include "fuse_i.h"
   18 #include "fuse_lowlevel.h"
   19 #include "fuse_opt.h"
   20 #include "fuse_misc.h"
   21 #include "fuse_kernel.h"
   22 
   23 #include <stdio.h>
   24 #include <string.h>
   25 #include <stdlib.h>
   26 #include <stddef.h>
   27 #include <stdbool.h>
   28 #include <unistd.h>
   29 #include <time.h>
   30 #include <fcntl.h>
   31 #include <limits.h>
   32 #include <errno.h>
   33 #include <signal.h>
   34 #include <dlfcn.h>
   35 #include <assert.h>
   36 #include <poll.h>
   37 #include <sys/param.h>
   38 #include <sys/uio.h>
   39 #include <sys/time.h>
   40 #include <sys/mman.h>
   41 #include <sys/file.h>
   42 
   43 #define FUSE_NODE_SLAB 1
   44 
   45 #ifndef MAP_ANONYMOUS
   46 #undef FUSE_NODE_SLAB
   47 #endif
   48 
   49 #ifndef RENAME_EXCHANGE
   50 #define RENAME_EXCHANGE     (1 << 1)    /* Exchange source and dest */
   51 #endif
   52 
   53 #define FUSE_DEFAULT_INTR_SIGNAL SIGUSR1
   54 
   55 #define FUSE_UNKNOWN_INO 0xffffffff
   56 #define OFFSET_MAX 0x7fffffffffffffffLL
   57 
   58 #define NODE_TABLE_MIN_SIZE 8192
   59 
   60 struct fuse_fs {
   61     struct fuse_operations op;
   62     struct fuse_module *m;
   63     void *user_data;
   64     int debug;
   65 };
   66 
   67 struct fusemod_so {
   68     void *handle;
   69     int ctr;
   70 };
   71 
   72 struct lock_queue_element {
   73     struct lock_queue_element *next;
   74     pthread_cond_t cond;
   75     fuse_ino_t nodeid1;
   76     const char *name1;
   77     char **path1;
   78     struct node **wnode1;
   79     fuse_ino_t nodeid2;
   80     const char *name2;
   81     char **path2;
   82     struct node **wnode2;
   83     int err;
   84     bool first_locked : 1;
   85     bool second_locked : 1;
   86     bool done : 1;
   87 };
   88 
   89 struct node_table {
   90     struct node **array;
   91     size_t use;
   92     size_t size;
   93     size_t split;
   94 };
   95 
   96 #define container_of(ptr, type, member) ({                              \
   97             const typeof( ((type *)0)->member ) *__mptr = (ptr); \
   98             (type *)( (char *)__mptr - offsetof(type,member) );})
   99 
  100 #define list_entry(ptr, type, member)           \
  101     container_of(ptr, type, member)
  102 
  103 struct list_head {
  104     struct list_head *next;
  105     struct list_head *prev;
  106 };
  107 
  108 struct node_slab {
  109     struct list_head list;  /* must be the first member */
  110     struct list_head freelist;
  111     int used;
  112 };
  113 
  114 struct fuse {
  115     struct fuse_session *se;
  116     struct node_table name_table;
  117     struct node_table id_table;
  118     struct list_head lru_table;
  119     fuse_ino_t ctr;
  120     unsigned int generation;
  121     unsigned int hidectr;
  122     pthread_mutex_t lock;
  123     struct fuse_config conf;
  124     int intr_installed;
  125     struct fuse_fs *fs;
  126     struct lock_queue_element *lockq;
  127     int pagesize;
  128     struct list_head partial_slabs;
  129     struct list_head full_slabs;
  130     pthread_t prune_thread;
  131 };
  132 
  133 struct lock {
  134     int type;
  135     off_t start;
  136     off_t end;
  137     pid_t pid;
  138     uint64_t owner;
  139     struct lock *next;
  140 };
  141 
  142 struct node {
  143     struct node *name_next;
  144     struct node *id_next;
  145     fuse_ino_t nodeid;
  146     unsigned int generation;
  147     int refctr;
  148     struct node *parent;
  149     char *name;
  150     uint64_t nlookup;
  151     int open_count;
  152     struct timespec stat_updated;
  153     struct timespec mtime;
  154     off_t size;
  155     struct lock *locks;
  156     unsigned int is_hidden : 1;
  157     unsigned int cache_valid : 1;
  158     int treelock;
  159     char inline_name[32];
  160 };
  161 
  162 #define TREELOCK_WRITE -1
  163 #define TREELOCK_WAIT_OFFSET INT_MIN
  164 
  165 struct node_lru {
  166     struct node node;
  167     struct list_head lru;
  168     struct timespec forget_time;
  169 };
  170 
  171 struct fuse_direntry {
  172     struct stat stat;
  173     char *name;
  174     struct fuse_direntry *next;
  175 };
  176 
  177 struct fuse_dh {
  178     pthread_mutex_t lock;
  179     struct fuse *fuse;
  180     fuse_req_t req;
  181     char *contents;
  182     struct fuse_direntry *first;
  183     struct fuse_direntry **last;
  184     int allocated;
  185     unsigned len;
  186     unsigned size;
  187     unsigned needlen;
  188     int filled;
  189     uint64_t fh;
  190     int error;
  191     fuse_ino_t nodeid;
  192 };
  193 
  194 struct fuse_context_i {
  195     struct fuse_context ctx;
  196     fuse_req_t req;
  197 };
  198 
  199 /* Defined by FUSE_REGISTER_MODULE() in lib/modules/subdir.c and iconv.c.  */
  200 extern fuse_module_factory_t fuse_module_subdir_factory;
  201 #ifdef HAVE_ICONV
  202 extern fuse_module_factory_t fuse_module_iconv_factory;
  203 #endif
  204 
  205 static pthread_key_t fuse_context_key;
  206 static pthread_mutex_t fuse_context_lock = PTHREAD_MUTEX_INITIALIZER;
  207 static int fuse_context_ref;
  208 static struct fuse_module *fuse_modules = NULL;
  209 
  210 static int fuse_register_module(const char *name,
  211                 fuse_module_factory_t factory,
  212                 struct fusemod_so *so)
  213 {
  214     struct fuse_module *mod;
  215 
  216     mod = calloc(1, sizeof(struct fuse_module));
  217     if (!mod) {
  218         fprintf(stderr, "fuse: failed to allocate module\n");
  219         return -1;
  220     }
  221     mod->name = strdup(name);
  222     if (!mod->name) {
  223         fprintf(stderr, "fuse: failed to allocate module name\n");
  224         free(mod);
  225         return -1;
  226     }
  227     mod->factory = factory;
  228     mod->ctr = 0;
  229     mod->so = so;
  230     if (mod->so)
  231         mod->so->ctr++;
  232     mod->next = fuse_modules;
  233     fuse_modules = mod;
  234 
  235     return 0;
  236 }
  237 
  238 
  239 static int fuse_load_so_module(const char *module)
  240 {
  241     int ret = -1;
  242     char *tmp;
  243     struct fusemod_so *so;
  244     fuse_module_factory_t factory;
  245 
  246     tmp = malloc(strlen(module) + 64);
  247     if (!tmp) {
  248         fprintf(stderr, "fuse: memory allocation failed\n");
  249         return -1;
  250     }
  251     sprintf(tmp, "libfusemod_%s.so", module);
  252     so = calloc(1, sizeof(struct fusemod_so));
  253     if (!so) {
  254         fprintf(stderr, "fuse: failed to allocate module so\n");
  255         goto out;
  256     }
  257 
  258     so->handle = dlopen(tmp, RTLD_NOW);
  259     if (so->handle == NULL) {
  260         fprintf(stderr, "fuse: dlopen(%s) failed: %s\n",
  261             tmp, dlerror());
  262         goto out_free_so;
  263     }
  264 
  265     sprintf(tmp, "fuse_module_%s_factory", module);
  266     *(void**)(&factory) = dlsym(so->handle, tmp);
  267     if (factory == NULL) {
  268         fprintf(stderr, "fuse: symbol <%s> not found in module: %s\n",
  269             tmp, dlerror());
  270         goto out_dlclose;
  271     }
  272     ret = fuse_register_module(module, factory, so);
  273     if (ret)
  274         goto out_dlclose;
  275 
  276 out:
  277     free(tmp);
  278     return ret;
  279 
  280 out_dlclose:
  281     dlclose(so->handle);
  282 out_free_so:
  283     free(so);
  284     goto out;
  285 }
  286 
  287 static struct fuse_module *fuse_find_module(const char *module)
  288 {
  289     struct fuse_module *m;
  290     for (m = fuse_modules; m; m = m->next) {
  291         if (strcmp(module, m->name) == 0) {
  292             m->ctr++;
  293             break;
  294         }
  295     }
  296     return m;
  297 }
  298 
  299 static struct fuse_module *fuse_get_module(const char *module)
  300 {
  301     struct fuse_module *m;
  302 
  303     pthread_mutex_lock(&fuse_context_lock);
  304     m = fuse_find_module(module);
  305     if (!m) {
  306         int err = fuse_load_so_module(module);
  307         if (!err)
  308             m = fuse_find_module(module);
  309     }
  310     pthread_mutex_unlock(&fuse_context_lock);
  311     return m;
  312 }
  313 
  314 static void fuse_put_module(struct fuse_module *m)
  315 {
  316     pthread_mutex_lock(&fuse_context_lock);
  317     assert(m->ctr > 0);
  318     m->ctr--;
  319     if (!m->ctr && m->so) {
  320         struct fusemod_so *so = m->so;
  321         assert(so->ctr > 0);
  322         so->ctr--;
  323         if (!so->ctr) {
  324             struct fuse_module **mp;
  325             for (mp = &fuse_modules; *mp;) {
  326                 if ((*mp)->so == so)
  327                     *mp = (*mp)->next;
  328                 else
  329                     mp = &(*mp)->next;
  330             }
  331             dlclose(so->handle);
  332             free(so);
  333         }
  334     }
  335     pthread_mutex_unlock(&fuse_context_lock);
  336 }
  337 
  338 static void init_list_head(struct list_head *list)
  339 {
  340     list->next = list;
  341     list->prev = list;
  342 }
  343 
  344 static int list_empty(const struct list_head *head)
  345 {
  346     return head->next == head;
  347 }
  348 
  349 static void list_add(struct list_head *new, struct list_head *prev,
  350              struct list_head *next)
  351 {
  352     next->prev = new;
  353     new->next = next;
  354     new->prev = prev;
  355     prev->next = new;
  356 }
  357 
  358 static inline void list_add_head(struct list_head *new, struct list_head *head)
  359 {
  360     list_add(new, head, head->next);
  361 }
  362 
  363 static inline void list_add_tail(struct list_head *new, struct list_head *head)
  364 {
  365     list_add(new, head->prev, head);
  366 }
  367 
  368 static inline void list_del(struct list_head *entry)
  369 {
  370     struct list_head *prev = entry->prev;
  371     struct list_head *next = entry->next;
  372 
  373     next->prev = prev;
  374     prev->next = next;
  375 }
  376 
  377 static inline int lru_enabled(struct fuse *f)
  378 {
  379     return f->conf.remember > 0;
  380 }
  381 
  382 static struct node_lru *node_lru(struct node *node)
  383 {
  384     return (struct node_lru *) node;
  385 }
  386 
  387 static size_t get_node_size(struct fuse *f)
  388 {
  389     if (lru_enabled(f))
  390         return sizeof(struct node_lru);
  391     else
  392         return sizeof(struct node);
  393 }
  394 
  395 #ifdef FUSE_NODE_SLAB
  396 static struct node_slab *list_to_slab(struct list_head *head)
  397 {
  398     return (struct node_slab *) head;
  399 }
  400 
  401 static struct node_slab *node_to_slab(struct fuse *f, struct node *node)
  402 {
  403     return (struct node_slab *) (((uintptr_t) node) & ~((uintptr_t) f->pagesize - 1));
  404 }
  405 
  406 static int alloc_slab(struct fuse *f)
  407 {
  408     void *mem;
  409     struct node_slab *slab;
  410     char *start;
  411     size_t num;
  412     size_t i;
  413     size_t node_size = get_node_size(f);
  414 
  415     mem = mmap(NULL, f->pagesize, PROT_READ | PROT_WRITE,
  416            MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
  417 
  418     if (mem == MAP_FAILED)
  419         return -1;
  420 
  421     slab = mem;
  422     init_list_head(&slab->freelist);
  423     slab->used = 0;
  424     num = (f->pagesize - sizeof(struct node_slab)) / node_size;
  425 
  426     start = (char *) mem + f->pagesize - num * node_size;
  427     for (i = 0; i < num; i++) {
  428         struct list_head *n;
  429 
  430         n = (struct list_head *) (start + i * node_size);
  431         list_add_tail(n, &slab->freelist);
  432     }
  433     list_add_tail(&slab->list, &f->partial_slabs);
  434 
  435     return 0;
  436 }
  437 
  438 static struct node *alloc_node(struct fuse *f)
  439 {
  440     struct node_slab *slab;
  441     struct list_head *node;
  442 
  443     if (list_empty(&f->partial_slabs)) {
  444         int res = alloc_slab(f);
  445         if (res != 0)
  446             return NULL;
  447     }
  448     slab = list_to_slab(f->partial_slabs.next);
  449     slab->used++;
  450     node = slab->freelist.next;
  451     list_del(node);
  452     if (list_empty(&slab->freelist)) {
  453         list_del(&slab->list);
  454         list_add_tail(&slab->list, &f->full_slabs);
  455     }
  456     memset(node, 0, sizeof(struct node));
  457 
  458     return (struct node *) node;
  459 }
  460 
  461 static void free_slab(struct fuse *f, struct node_slab *slab)
  462 {
  463     int res;
  464 
  465     list_del(&slab->list);
  466     res = munmap(slab, f->pagesize);
  467     if (res == -1)
  468         fprintf(stderr, "fuse warning: munmap(%p) failed\n", slab);
  469 }
  470 
  471 static void free_node_mem(struct fuse *f, struct node *node)
  472 {
  473     struct node_slab *slab = node_to_slab(f, node);
  474     struct list_head *n = (struct list_head *) node;
  475 
  476     slab->used--;
  477     if (slab->used) {
  478         if (list_empty(&slab->freelist)) {
  479             list_del(&slab->list);
  480             list_add_tail(&slab->list, &f->partial_slabs);
  481         }
  482         list_add_head(n, &slab->freelist);
  483     } else {
  484         free_slab(f, slab);
  485     }
  486 }
  487 #else
  488 static struct node *alloc_node(struct fuse *f)
  489 {
  490     return (struct node *) calloc(1, get_node_size(f));
  491 }
  492 
  493 static void free_node_mem(struct fuse *f, struct node *node)
  494 {
  495     (void) f;
  496     free(node);
  497 }
  498 #endif
  499 
  500 static size_t id_hash(struct fuse *f, fuse_ino_t ino)
  501 {
  502     uint64_t hash = ((uint32_t) ino * 2654435761U) % f->id_table.size;
  503     uint64_t oldhash = hash % (f->id_table.size / 2);
  504 
  505     if (oldhash >= f->id_table.split)
  506         return oldhash;
  507     else
  508         return hash;
  509 }
  510 
  511 static struct node *get_node_nocheck(struct fuse *f, fuse_ino_t nodeid)
  512 {
  513     size_t hash = id_hash(f, nodeid);
  514     struct node *node;
  515 
  516     for (node = f->id_table.array[hash]; node != NULL; node = node->id_next)
  517         if (node->nodeid == nodeid)
  518             return node;
  519 
  520     return NULL;
  521 }
  522 
  523 static struct node *get_node(struct fuse *f, fuse_ino_t nodeid)
  524 {
  525     struct node *node = get_node_nocheck(f, nodeid);
  526     if (!node) {
  527         fprintf(stderr, "fuse internal error: node %llu not found\n",
  528             (unsigned long long) nodeid);
  529         abort();
  530     }
  531     return node;
  532 }
  533 
  534 static void curr_time(struct timespec *now);
  535 static double diff_timespec(const struct timespec *t1,
  536                const struct timespec *t2);
  537 
  538 static void remove_node_lru(struct node *node)
  539 {
  540     struct node_lru *lnode = node_lru(node);
  541     list_del(&lnode->lru);
  542     init_list_head(&lnode->lru);
  543 }
  544 
  545 static void set_forget_time(struct fuse *f, struct node *node)
  546 {
  547     struct node_lru *lnode = node_lru(node);
  548 
  549     list_del(&lnode->lru);
  550     list_add_tail(&lnode->lru, &f->lru_table);
  551     curr_time(&lnode->forget_time);
  552 }
  553 
  554 static void free_node(struct fuse *f, struct node *node)
  555 {
  556     if (node->name != node->inline_name)
  557         free(node->name);
  558     free_node_mem(f, node);
  559 }
  560 
  561 static void node_table_reduce(struct node_table *t)
  562 {
  563     size_t newsize = t->size / 2;
  564     void *newarray;
  565 
  566     if (newsize < NODE_TABLE_MIN_SIZE)
  567         return;
  568 
  569     newarray = realloc(t->array, sizeof(struct node *) * newsize);
  570     if (newarray != NULL)
  571         t->array = newarray;
  572 
  573     t->size = newsize;
  574     t->split = t->size / 2;
  575 }
  576 
  577 static void remerge_id(struct fuse *f)
  578 {
  579     struct node_table *t = &f->id_table;
  580     int iter;
  581 
  582     if (t->split == 0)
  583         node_table_reduce(t);
  584 
  585     for (iter = 8; t->split > 0 && iter; iter--) {
  586         struct node **upper;
  587 
  588         t->split--;
  589         upper = &t->array[t->split + t->size / 2];
  590         if (*upper) {
  591             struct node **nodep;
  592 
  593             for (nodep = &t->array[t->split]; *nodep;
  594                  nodep = &(*nodep)->id_next);
  595 
  596             *nodep = *upper;
  597             *upper = NULL;
  598             break;
  599         }
  600     }
  601 }
  602 
  603 static void unhash_id(struct fuse *f, struct node *node)
  604 {
  605     struct node **nodep = &f->id_table.array[id_hash(f, node->nodeid)];
  606 
  607     for (; *nodep != NULL; nodep = &(*nodep)->id_next)
  608         if (*nodep == node) {
  609             *nodep = node->id_next;
  610             f->id_table.use--;
  611 
  612             if(f->id_table.use < f->id_table.size / 4)
  613                 remerge_id(f);
  614             return;
  615         }
  616 }
  617 
  618 static int node_table_resize(struct node_table *t)
  619 {
  620     size_t newsize = t->size * 2;
  621     void *newarray;
  622 
  623     newarray = realloc(t->array, sizeof(struct node *) * newsize);
  624     if (newarray == NULL)
  625         return -1;
  626 
  627     t->array = newarray;
  628     memset(t->array + t->size, 0, t->size * sizeof(struct node *));
  629     t->size = newsize;
  630     t->split = 0;
  631 
  632     return 0;
  633 }
  634 
  635 static void rehash_id(struct fuse *f)
  636 {
  637     struct node_table *t = &f->id_table;
  638     struct node **nodep;
  639     struct node **next;
  640     size_t hash;
  641 
  642     if (t->split == t->size / 2)
  643         return;
  644 
  645     hash = t->split;
  646     t->split++;
  647     for (nodep = &t->array[hash]; *nodep != NULL; nodep = next) {
  648         struct node *node = *nodep;
  649         size_t newhash = id_hash(f, node->nodeid);
  650 
  651         if (newhash != hash) {
  652             next = nodep;
  653             *nodep = node->id_next;
  654             node->id_next = t->array[newhash];
  655             t->array[newhash] = node;
  656         } else {
  657             next = &node->id_next;
  658         }
  659     }
  660     if (t->split == t->size / 2)
  661         node_table_resize(t);
  662 }
  663 
  664 static void hash_id(struct fuse *f, struct node *node)
  665 {
  666     size_t hash = id_hash(f, node->nodeid);
  667     node->id_next = f->id_table.array[hash];
  668     f->id_table.array[hash] = node;
  669     f->id_table.use++;
  670 
  671     if (f->id_table.use >= f->id_table.size / 2)
  672         rehash_id(f);
  673 }
  674 
  675 static size_t name_hash(struct fuse *f, fuse_ino_t parent,
  676             const char *name)
  677 {
  678     uint64_t hash = parent;
  679     uint64_t oldhash;
  680 
  681     for (; *name; name++)
  682         hash = hash * 31 + (unsigned char) *name;
  683 
  684     hash %= f->name_table.size;
  685     oldhash = hash % (f->name_table.size / 2);
  686     if (oldhash >= f->name_table.split)
  687         return oldhash;
  688     else
  689         return hash;
  690 }
  691 
  692 static void unref_node(struct fuse *f, struct node *node);
  693 
  694 static void remerge_name(struct fuse *f)
  695 {
  696     struct node_table *t = &f->name_table;
  697     int iter;
  698 
  699     if (t->split == 0)
  700         node_table_reduce(t);
  701 
  702     for (iter = 8; t->split > 0 && iter; iter--) {
  703         struct node **upper;
  704 
  705         t->split--;
  706         upper = &t->array[t->split + t->size / 2];
  707         if (*upper) {
  708             struct node **nodep;
  709 
  710             for (nodep = &t->array[t->split]; *nodep;
  711                  nodep = &(*nodep)->name_next);
  712 
  713             *nodep = *upper;
  714             *upper = NULL;
  715             break;
  716         }
  717     }
  718 }
  719 
  720 static void unhash_name(struct fuse *f, struct node *node)
  721 {
  722     if (node->name) {
  723         size_t hash = name_hash(f, node->parent->nodeid, node->name);
  724         struct node **nodep = &f->name_table.array[hash];
  725 
  726         for (; *nodep != NULL; nodep = &(*nodep)->name_next)
  727             if (*nodep == node) {
  728                 *nodep = node->name_next;
  729                 node->name_next = NULL;
  730                 unref_node(f, node->parent);
  731                 if (node->name != node->inline_name)
  732                     free(node->name);
  733                 node->name = NULL;
  734                 node->parent = NULL;
  735                 f->name_table.use--;
  736 
  737                 if (f->name_table.use < f->name_table.size / 4)
  738                     remerge_name(f);
  739                 return;
  740             }
  741         fprintf(stderr,
  742             "fuse internal error: unable to unhash node: %llu\n",
  743             (unsigned long long) node->nodeid);
  744         abort();
  745     }
  746 }
  747 
  748 static void rehash_name(struct fuse *f)
  749 {
  750     struct node_table *t = &f->name_table;
  751     struct node **nodep;
  752     struct node **next;
  753     size_t hash;
  754 
  755     if (t->split == t->size / 2)
  756         return;
  757 
  758     hash = t->split;
  759     t->split++;
  760     for (nodep = &t->array[hash]; *nodep != NULL; nodep = next) {
  761         struct node *node = *nodep;
  762         size_t newhash = name_hash(f, node->parent->nodeid, node->name);
  763 
  764         if (newhash != hash) {
  765             next = nodep;
  766             *nodep = node->name_next;
  767             node->name_next = t->array[newhash];
  768             t->array[newhash] = node;
  769         } else {
  770             next = &node->name_next;
  771         }
  772     }
  773     if (t->split == t->size / 2)
  774         node_table_resize(t);
  775 }
  776 
  777 static int hash_name(struct fuse *f, struct node *node, fuse_ino_t parentid,
  778              const char *name)
  779 {
  780     size_t hash = name_hash(f, parentid, name);
  781     struct node *parent = get_node(f, parentid);
  782     if (strlen(name) < sizeof(node->inline_name)) {
  783         strcpy(node->inline_name, name);
  784         node->name = node->inline_name;
  785     } else {
  786         node->name = strdup(name);
  787         if (node->name == NULL)
  788             return -1;
  789     }
  790 
  791     parent->refctr ++;
  792     node->parent = parent;
  793     node->name_next = f->name_table.array[hash];
  794     f->name_table.array[hash] = node;
  795     f->name_table.use++;
  796 
  797     if (f->name_table.use >= f->name_table.size / 2)
  798         rehash_name(f);
  799 
  800     return 0;
  801 }
  802 
  803 static void delete_node(struct fuse *f, struct node *node)
  804 {
  805     if (f->conf.debug)
  806         fprintf(stderr, "DELETE: %llu\n",
  807             (unsigned long long) node->nodeid);
  808 
  809     assert(node->treelock == 0);
  810     unhash_name(f, node);
  811     if (lru_enabled(f))
  812         remove_node_lru(node);
  813     unhash_id(f, node);
  814     free_node(f, node);
  815 }
  816 
  817 static void unref_node(struct fuse *f, struct node *node)
  818 {
  819     assert(node->refctr > 0);
  820     node->refctr --;
  821     if (!node->refctr)
  822         delete_node(f, node);
  823 }
  824 
  825 static fuse_ino_t next_id(struct fuse *f)
  826 {
  827     do {
  828         f->ctr = (f->ctr + 1) & 0xffffffff;
  829         if (!f->ctr)
  830             f->generation ++;
  831     } while (f->ctr == 0 || f->ctr == FUSE_UNKNOWN_INO ||
  832          get_node_nocheck(f, f->ctr) != NULL);
  833     return f->ctr;
  834 }
  835 
  836 static struct node *lookup_node(struct fuse *f, fuse_ino_t parent,
  837                 const char *name)
  838 {
  839     size_t hash = name_hash(f, parent, name);
  840     struct node *node;
  841 
  842     for (node = f->name_table.array[hash]; node != NULL; node = node->name_next)
  843         if (node->parent->nodeid == parent &&
  844             strcmp(node->name, name) == 0)
  845             return node;
  846 
  847     return NULL;
  848 }
  849 
  850 static void inc_nlookup(struct node *node)
  851 {
  852     if (!node->nlookup)
  853         node->refctr++;
  854     node->nlookup++;
  855 }
  856 
  857 static struct node *find_node(struct fuse *f, fuse_ino_t parent,
  858                   const char *name)
  859 {
  860     struct node *node;
  861 
  862     pthread_mutex_lock(&f->lock);
  863     if (!name)
  864         node = get_node(f, parent);
  865     else
  866         node = lookup_node(f, parent, name);
  867     if (node == NULL) {
  868         node = alloc_node(f);
  869         if (node == NULL)
  870             goto out_err;
  871 
  872         node->nodeid = next_id(f);
  873         node->generation = f->generation;
  874         if (f->conf.remember)
  875             inc_nlookup(node);
  876 
  877         if (hash_name(f, node, parent, name) == -1) {
  878             free_node(f, node);
  879             node = NULL;
  880             goto out_err;
  881         }
  882         hash_id(f, node);
  883         if (lru_enabled(f)) {
  884             struct node_lru *lnode = node_lru(node);
  885             init_list_head(&lnode->lru);
  886         }
  887     } else if (lru_enabled(f) && node->nlookup == 1) {
  888         remove_node_lru(node);
  889     }
  890     inc_nlookup(node);
  891 out_err:
  892     pthread_mutex_unlock(&f->lock);
  893     return node;
  894 }
  895 
  896 static int lookup_path_in_cache(struct fuse *f,
  897         const char *path, fuse_ino_t *inop)
  898 {
  899     char *tmp = strdup(path);
  900     if (!tmp)
  901         return -ENOMEM;
  902 
  903     pthread_mutex_lock(&f->lock);
  904     fuse_ino_t ino = FUSE_ROOT_ID;
  905 
  906     int err = 0;
  907     char *save_ptr;
  908     char *path_element = strtok_r(tmp, "/", &save_ptr);
  909     while (path_element != NULL) {
  910         struct node *node = lookup_node(f, ino, path_element);
  911         if (node == NULL) {
  912             err = -ENOENT;
  913             break;
  914         }
  915         ino = node->nodeid;
  916         path_element = strtok_r(NULL, "/", &save_ptr);
  917     }
  918     pthread_mutex_unlock(&f->lock);
  919     free(tmp);
  920 
  921     if (!err)
  922         *inop = ino;
  923     return err;
  924 }
  925 
  926 static char *add_name(char **buf, unsigned *bufsize, char *s, const char *name)
  927 {
  928     size_t len = strlen(name);
  929 
  930     if (s - len <= *buf) {
  931         unsigned pathlen = *bufsize - (s - *buf);
  932         unsigned newbufsize = *bufsize;
  933         char *newbuf;
  934 
  935         while (newbufsize < pathlen + len + 1) {
  936             if (newbufsize >= 0x80000000)
  937                 newbufsize = 0xffffffff;
  938             else
  939                 newbufsize *= 2;
  940         }
  941 
  942         newbuf = realloc(*buf, newbufsize);
  943         if (newbuf == NULL)
  944             return NULL;
  945 
  946         *buf = newbuf;
  947         s = newbuf + newbufsize - pathlen;
  948         memmove(s, newbuf + *bufsize - pathlen, pathlen);
  949         *bufsize = newbufsize;
  950     }
  951     s -= len;
  952     strncpy(s, name, len);
  953     s--;
  954     *s = '/';
  955 
  956     return s;
  957 }
  958 
  959 static void unlock_path(struct fuse *f, fuse_ino_t nodeid, struct node *wnode,
  960             struct node *end)
  961 {
  962     struct node *node;
  963 
  964     if (wnode) {
  965         assert(wnode->treelock == TREELOCK_WRITE);
  966         wnode->treelock = 0;
  967     }
  968 
  969     for (node = get_node(f, nodeid);
  970          node != end && node->nodeid != FUSE_ROOT_ID; node = node->parent) {
  971         assert(node->treelock != 0);
  972         assert(node->treelock != TREELOCK_WAIT_OFFSET);
  973         assert(node->treelock != TREELOCK_WRITE);
  974         node->treelock--;
  975         if (node->treelock == TREELOCK_WAIT_OFFSET)
  976             node->treelock = 0;
  977     }
  978 }
  979 
  980 static int try_get_path(struct fuse *f, fuse_ino_t nodeid, const char *name,
  981             char **path, struct node **wnodep, bool need_lock)
  982 {
  983     unsigned bufsize = 256;
  984     char *buf;
  985     char *s;
  986     struct node *node;
  987     struct node *wnode = NULL;
  988     int err;
  989 
  990     *path = NULL;
  991 
  992     err = -ENOMEM;
  993     buf = malloc(bufsize);
  994     if (buf == NULL)
  995         goto out_err;
  996 
  997     s = buf + bufsize - 1;
  998     *s = '\0';
  999 
 1000     if (name != NULL) {
 1001         s = add_name(&buf, &bufsize, s, name);
 1002         err = -ENOMEM;
 1003         if (s == NULL)
 1004             goto out_free;
 1005     }
 1006 
 1007     if (wnodep) {
 1008         assert(need_lock);
 1009         wnode = lookup_node(f, nodeid, name);
 1010         if (wnode) {
 1011             if (wnode->treelock != 0) {
 1012                 if (wnode->treelock > 0)
 1013                     wnode->treelock += TREELOCK_WAIT_OFFSET;
 1014                 err = -EAGAIN;
 1015                 goto out_free;
 1016             }
 1017             wnode->treelock = TREELOCK_WRITE;
 1018         }
 1019     }
 1020 
 1021     for (node = get_node(f, nodeid); node->nodeid != FUSE_ROOT_ID;
 1022          node = node->parent) {
 1023         err = -ENOENT;
 1024         if (node->name == NULL || node->parent == NULL)
 1025             goto out_unlock;
 1026 
 1027         err = -ENOMEM;
 1028         s = add_name(&buf, &bufsize, s, node->name);
 1029         if (s == NULL)
 1030             goto out_unlock;
 1031 
 1032         if (need_lock) {
 1033             err = -EAGAIN;
 1034             if (node->treelock < 0)
 1035                 goto out_unlock;
 1036 
 1037             node->treelock++;
 1038         }
 1039     }
 1040 
 1041     if (s[0])
 1042         memmove(buf, s, bufsize - (s - buf));
 1043     else
 1044         strcpy(buf, "/");
 1045 
 1046     *path = buf;
 1047     if (wnodep)
 1048         *wnodep = wnode;
 1049 
 1050     return 0;
 1051 
 1052  out_unlock:
 1053     if (need_lock)
 1054         unlock_path(f, nodeid, wnode, node);
 1055  out_free:
 1056     free(buf);
 1057 
 1058  out_err:
 1059     return err;
 1060 }
 1061 
 1062 static void queue_element_unlock(struct fuse *f, struct lock_queue_element *qe)
 1063 {
 1064     struct node *wnode;
 1065 
 1066     if (qe->first_locked) {
 1067         wnode = qe->wnode1 ? *qe->wnode1 : NULL;
 1068         unlock_path(f, qe->nodeid1, wnode, NULL);
 1069         qe->first_locked = false;
 1070     }
 1071     if (qe->second_locked) {
 1072         wnode = qe->wnode2 ? *qe->wnode2 : NULL;
 1073         unlock_path(f, qe->nodeid2, wnode, NULL);
 1074         qe->second_locked = false;
 1075     }
 1076 }
 1077 
 1078 static void queue_element_wakeup(struct fuse *f, struct lock_queue_element *qe)
 1079 {
 1080     int err;
 1081     bool first = (qe == f->lockq);
 1082 
 1083     if (!qe->path1) {
 1084         /* Just waiting for it to be unlocked */
 1085         if (get_node(f, qe->nodeid1)->treelock == 0)
 1086             pthread_cond_signal(&qe->cond);
 1087 
 1088         return;
 1089     }
 1090 
 1091     if (!qe->first_locked) {
 1092         err = try_get_path(f, qe->nodeid1, qe->name1, qe->path1,
 1093                    qe->wnode1, true);
 1094         if (!err)
 1095             qe->first_locked = true;
 1096         else if (err != -EAGAIN)
 1097             goto err_unlock;
 1098     }
 1099     if (!qe->second_locked && qe->path2) {
 1100         err = try_get_path(f, qe->nodeid2, qe->name2, qe->path2,
 1101                    qe->wnode2, true);
 1102         if (!err)
 1103             qe->second_locked = true;
 1104         else if (err != -EAGAIN)
 1105             goto err_unlock;
 1106     }
 1107 
 1108     if (qe->first_locked && (qe->second_locked || !qe->path2)) {
 1109         err = 0;
 1110         goto done;
 1111     }
 1112 
 1113     /*
 1114      * Only let the first element be partially locked otherwise there could
 1115      * be a deadlock.
 1116      *
 1117      * But do allow the first element to be partially locked to prevent
 1118      * starvation.
 1119      */
 1120     if (!first)
 1121         queue_element_unlock(f, qe);
 1122 
 1123     /* keep trying */
 1124     return;
 1125 
 1126 err_unlock:
 1127     queue_element_unlock(f, qe);
 1128 done:
 1129     qe->err = err;
 1130     qe->done = true;
 1131     pthread_cond_signal(&qe->cond);
 1132 }
 1133 
 1134 static void wake_up_queued(struct fuse *f)
 1135 {
 1136     struct lock_queue_element *qe;
 1137 
 1138     for (qe = f->lockq; qe != NULL; qe = qe->next)
 1139         queue_element_wakeup(f, qe);
 1140 }
 1141 
 1142 static void debug_path(struct fuse *f, const char *msg, fuse_ino_t nodeid,
 1143                const char *name, bool wr)
 1144 {
 1145     if (f->conf.debug) {
 1146         struct node *wnode = NULL;
 1147 
 1148         if (wr)
 1149             wnode = lookup_node(f, nodeid, name);
 1150 
 1151         if (wnode) {
 1152             fprintf(stderr, "%s %llu (w)\n",
 1153                 msg, (unsigned long long) wnode->nodeid);
 1154         } else {
 1155             fprintf(stderr, "%s %llu\n",
 1156                 msg, (unsigned long long) nodeid);
 1157         }
 1158     }
 1159 }
 1160 
 1161 static void queue_path(struct fuse *f, struct lock_queue_element *qe)
 1162 {
 1163     struct lock_queue_element **qp;
 1164 
 1165     qe->done = false;
 1166     qe->first_locked = false;
 1167     qe->second_locked = false;
 1168     pthread_cond_init(&qe->cond, NULL);
 1169     qe->next = NULL;
 1170     for (qp = &f->lockq; *qp != NULL; qp = &(*qp)->next);
 1171     *qp = qe;
 1172 }
 1173 
 1174 static void dequeue_path(struct fuse *f, struct lock_queue_element *qe)
 1175 {
 1176     struct lock_queue_element **qp;
 1177 
 1178     pthread_cond_destroy(&qe->cond);
 1179     for (qp = &f->lockq; *qp != qe; qp = &(*qp)->next);
 1180     *qp = qe->next;
 1181 }
 1182 
 1183 static int wait_path(struct fuse *f, struct lock_queue_element *qe)
 1184 {
 1185     queue_path(f, qe);
 1186 
 1187     do {
 1188         pthread_cond_wait(&qe->cond, &f->lock);
 1189     } while (!qe->done);
 1190 
 1191     dequeue_path(f, qe);
 1192 
 1193     return qe->err;
 1194 }
 1195 
 1196 static int get_path_common(struct fuse *f, fuse_ino_t nodeid, const char *name,
 1197                char **path, struct node **wnode)
 1198 {
 1199     int err;
 1200 
 1201     pthread_mutex_lock(&f->lock);
 1202     err = try_get_path(f, nodeid, name, path, wnode, true);
 1203     if (err == -EAGAIN) {
 1204         struct lock_queue_element qe = {
 1205             .nodeid1 = nodeid,
 1206             .name1 = name,
 1207             .path1 = path,
 1208             .wnode1 = wnode,
 1209         };
 1210         debug_path(f, "QUEUE PATH", nodeid, name, !!wnode);
 1211         err = wait_path(f, &qe);
 1212         debug_path(f, "DEQUEUE PATH", nodeid, name, !!wnode);
 1213     }
 1214     pthread_mutex_unlock(&f->lock);
 1215 
 1216     return err;
 1217 }
 1218 
 1219 static int get_path(struct fuse *f, fuse_ino_t nodeid, char **path)
 1220 {
 1221     return get_path_common(f, nodeid, NULL, path, NULL);
 1222 }
 1223 
 1224 static int get_path_nullok(struct fuse *f, fuse_ino_t nodeid, char **path)
 1225 {
 1226     int err = 0;
 1227 
 1228     if (f->conf.nullpath_ok) {
 1229         *path = NULL;
 1230     } else {
 1231         err = get_path_common(f, nodeid, NULL, path, NULL);
 1232         if (err == -ENOENT)
 1233             err = 0;
 1234     }
 1235 
 1236     return err;
 1237 }
 1238 
 1239 static int get_path_name(struct fuse *f, fuse_ino_t nodeid, const char *name,
 1240              char **path)
 1241 {
 1242     return get_path_common(f, nodeid, name, path, NULL);
 1243 }
 1244 
 1245 static int get_path_wrlock(struct fuse *f, fuse_ino_t nodeid, const char *name,
 1246                char **path, struct node **wnode)
 1247 {
 1248     return get_path_common(f, nodeid, name, path, wnode);
 1249 }
 1250 
 1251 static int try_get_path2(struct fuse *f, fuse_ino_t nodeid1, const char *name1,
 1252              fuse_ino_t nodeid2, const char *name2,
 1253              char **path1, char **path2,
 1254              struct node **wnode1, struct node **wnode2)
 1255 {
 1256     int err;
 1257 
 1258     /* FIXME: locking two paths needs deadlock checking */
 1259     err = try_get_path(f, nodeid1, name1, path1, wnode1, true);
 1260     if (!err) {
 1261         err = try_get_path(f, nodeid2, name2, path2, wnode2, true);
 1262         if (err) {
 1263             struct node *wn1 = wnode1 ? *wnode1 : NULL;
 1264 
 1265             unlock_path(f, nodeid1, wn1, NULL);
 1266             free(*path1);
 1267         }
 1268     }
 1269     return err;
 1270 }
 1271 
 1272 static int get_path2(struct fuse *f, fuse_ino_t nodeid1, const char *name1,
 1273              fuse_ino_t nodeid2, const char *name2,
 1274              char **path1, char **path2,
 1275              struct node **wnode1, struct node **wnode2)
 1276 {
 1277     int err;
 1278 
 1279     pthread_mutex_lock(&f->lock);
 1280     err = try_get_path2(f, nodeid1, name1, nodeid2, name2,
 1281                 path1, path2, wnode1, wnode2);
 1282     if (err == -EAGAIN) {
 1283         struct lock_queue_element qe = {
 1284             .nodeid1 = nodeid1,
 1285             .name1 = name1,
 1286             .path1 = path1,
 1287             .wnode1 = wnode1,
 1288             .nodeid2 = nodeid2,
 1289             .name2 = name2,
 1290             .path2 = path2,
 1291             .wnode2 = wnode2,
 1292         };
 1293 
 1294         debug_path(f, "QUEUE PATH1", nodeid1, name1, !!wnode1);
 1295         debug_path(f, "      PATH2", nodeid2, name2, !!wnode2);
 1296         err = wait_path(f, &qe);
 1297         debug_path(f, "DEQUEUE PATH1", nodeid1, name1, !!wnode1);
 1298         debug_path(f, "        PATH2", nodeid2, name2, !!wnode2);
 1299     }
 1300     pthread_mutex_unlock(&f->lock);
 1301 
 1302     return err;
 1303 }
 1304 
 1305 static void free_path_wrlock(struct fuse *f, fuse_ino_t nodeid,
 1306                  struct node *wnode, char *path)
 1307 {
 1308     pthread_mutex_lock(&f->lock);
 1309     unlock_path(f, nodeid, wnode, NULL);
 1310     if (f->lockq)
 1311         wake_up_queued(f);
 1312     pthread_mutex_unlock(&f->lock);
 1313     free(path);
 1314 }
 1315 
 1316 static void free_path(struct fuse *f, fuse_ino_t nodeid, char *path)
 1317 {
 1318     if (path)
 1319         free_path_wrlock(f, nodeid, NULL, path);
 1320 }
 1321 
 1322 static void free_path2(struct fuse *f, fuse_ino_t nodeid1, fuse_ino_t nodeid2,
 1323                struct node *wnode1, struct node *wnode2,
 1324                char *path1, char *path2)
 1325 {
 1326     pthread_mutex_lock(&f->lock);
 1327     unlock_path(f, nodeid1, wnode1, NULL);
 1328     unlock_path(f, nodeid2, wnode2, NULL);
 1329     wake_up_queued(f);
 1330     pthread_mutex_unlock(&f->lock);
 1331     free(path1);
 1332     free(path2);
 1333 }
 1334 
 1335 static void forget_node(struct fuse *f, fuse_ino_t nodeid, uint64_t nlookup)
 1336 {
 1337     struct node *node;
 1338     if (nodeid == FUSE_ROOT_ID)
 1339         return;
 1340     pthread_mutex_lock(&f->lock);
 1341     node = get_node(f, nodeid);
 1342 
 1343     /*
 1344      * Node may still be locked due to interrupt idiocy in open,
 1345      * create and opendir
 1346      */
 1347     while (node->nlookup == nlookup && node->treelock) {
 1348         struct lock_queue_element qe = {
 1349             .nodeid1 = nodeid,
 1350         };
 1351 
 1352         debug_path(f, "QUEUE PATH (forget)", nodeid, NULL, false);
 1353         queue_path(f, &qe);
 1354 
 1355         do {
 1356             pthread_cond_wait(&qe.cond, &f->lock);
 1357         } while (node->nlookup == nlookup && node->treelock);
 1358 
 1359         dequeue_path(f, &qe);
 1360         debug_path(f, "DEQUEUE_PATH (forget)", nodeid, NULL, false);
 1361     }
 1362 
 1363     assert(node->nlookup >= nlookup);
 1364     node->nlookup -= nlookup;
 1365     if (!node->nlookup) {
 1366         unref_node(f, node);
 1367     } else if (lru_enabled(f) && node->nlookup == 1) {
 1368         set_forget_time(f, node);
 1369     }
 1370     pthread_mutex_unlock(&f->lock);
 1371 }
 1372 
 1373 static void unlink_node(struct fuse *f, struct node *node)
 1374 {
 1375     if (f->conf.remember) {
 1376         assert(node->nlookup > 1);
 1377         node->nlookup--;
 1378     }
 1379     unhash_name(f, node);
 1380 }
 1381 
 1382 static void remove_node(struct fuse *f, fuse_ino_t dir, const char *name)
 1383 {
 1384     struct node *node;
 1385 
 1386     pthread_mutex_lock(&f->lock);
 1387     node = lookup_node(f, dir, name);
 1388     if (node != NULL)
 1389         unlink_node(f, node);
 1390     pthread_mutex_unlock(&f->lock);
 1391 }
 1392 
 1393 static int rename_node(struct fuse *f, fuse_ino_t olddir, const char *oldname,
 1394                fuse_ino_t newdir, const char *newname, int hide)
 1395 {
 1396     struct node *node;
 1397     struct node *newnode;
 1398     int err = 0;
 1399 
 1400     pthread_mutex_lock(&f->lock);
 1401     node  = lookup_node(f, olddir, oldname);
 1402     newnode  = lookup_node(f, newdir, newname);
 1403     if (node == NULL)
 1404         goto out;
 1405 
 1406     if (newnode != NULL) {
 1407         if (hide) {
 1408             fprintf(stderr, "fuse: hidden file got created during hiding\n");
 1409             err = -EBUSY;
 1410             goto out;
 1411         }
 1412         unlink_node(f, newnode);
 1413     }
 1414 
 1415     unhash_name(f, node);
 1416     if (hash_name(f, node, newdir, newname) == -1) {
 1417         err = -ENOMEM;
 1418         goto out;
 1419     }
 1420 
 1421     if (hide)
 1422         node->is_hidden = 1;
 1423 
 1424 out:
 1425     pthread_mutex_unlock(&f->lock);
 1426     return err;
 1427 }
 1428 
 1429 static int exchange_node(struct fuse *f, fuse_ino_t olddir, const char *oldname,
 1430              fuse_ino_t newdir, const char *newname)
 1431 {
 1432     struct node *oldnode;
 1433     struct node *newnode;
 1434     int err;
 1435 
 1436     pthread_mutex_lock(&f->lock);
 1437     oldnode  = lookup_node(f, olddir, oldname);
 1438     newnode  = lookup_node(f, newdir, newname);
 1439 
 1440     if (oldnode)
 1441         unhash_name(f, oldnode);
 1442     if (newnode)
 1443         unhash_name(f, newnode);
 1444 
 1445     err = -ENOMEM;
 1446     if (oldnode) {
 1447         if (hash_name(f, oldnode, newdir, newname) == -1)
 1448             goto out;
 1449     }
 1450     if (newnode) {
 1451         if (hash_name(f, newnode, olddir, oldname) == -1)
 1452             goto out;
 1453     }
 1454     err = 0;
 1455 out:
 1456     pthread_mutex_unlock(&f->lock);
 1457     return err;
 1458 }
 1459 
 1460 static void set_stat(struct fuse *f, fuse_ino_t nodeid, struct stat *stbuf)
 1461 {
 1462     if (!f->conf.use_ino)
 1463         stbuf->st_ino = nodeid;
 1464     if (f->conf.set_mode)
 1465         stbuf->st_mode = (stbuf->st_mode & S_IFMT) |
 1466                  (0777 & ~f->conf.umask);
 1467     if (f->conf.set_uid)
 1468         stbuf->st_uid = f->conf.uid;
 1469     if (f->conf.set_gid)
 1470         stbuf->st_gid = f->conf.gid;
 1471 }
 1472 
 1473 static struct fuse *req_fuse(fuse_req_t req)
 1474 {
 1475     return (struct fuse *) fuse_req_userdata(req);
 1476 }
 1477 
 1478 static void fuse_intr_sighandler(int sig)
 1479 {
 1480     (void) sig;
 1481     /* Nothing to do */
 1482 }
 1483 
 1484 struct fuse_intr_data {
 1485     pthread_t id;
 1486     pthread_cond_t cond;
 1487     int finished;
 1488 };
 1489 
 1490 static void fuse_interrupt(fuse_req_t req, void *d_)
 1491 {
 1492     struct fuse_intr_data *d = d_;
 1493     struct fuse *f = req_fuse(req);
 1494 
 1495     if (d->id == pthread_self())
 1496         return;
 1497 
 1498     pthread_mutex_lock(&f->lock);
 1499     while (!d->finished) {
 1500         struct timeval now;
 1501         struct timespec timeout;
 1502 
 1503         pthread_kill(d->id, f->conf.intr_signal);
 1504         gettimeofday(&now, NULL);
 1505         timeout.tv_sec = now.tv_sec + 1;
 1506         timeout.tv_nsec = now.tv_usec * 1000;
 1507         pthread_cond_timedwait(&d->cond, &f->lock, &timeout);
 1508     }
 1509     pthread_mutex_unlock(&f->lock);
 1510 }
 1511 
 1512 static void fuse_do_finish_interrupt(struct fuse *f, fuse_req_t req,
 1513                      struct fuse_intr_data *d)
 1514 {
 1515     pthread_mutex_lock(&f->lock);
 1516     d->finished = 1;
 1517     pthread_cond_broadcast(&d->cond);
 1518     pthread_mutex_unlock(&f->lock);
 1519     fuse_req_interrupt_func(req, NULL, NULL);
 1520     pthread_cond_destroy(&d->cond);
 1521 }
 1522 
 1523 static void fuse_do_prepare_interrupt(fuse_req_t req, struct fuse_intr_data *d)
 1524 {
 1525     d->id = pthread_self();
 1526     pthread_cond_init(&d->cond, NULL);
 1527     d->finished = 0;
 1528     fuse_req_interrupt_func(req, fuse_interrupt, d);
 1529 }
 1530 
 1531 static inline void fuse_finish_interrupt(struct fuse *f, fuse_req_t req,
 1532                      struct fuse_intr_data *d)
 1533 {
 1534     if (f->conf.intr)
 1535         fuse_do_finish_interrupt(f, req, d);
 1536 }
 1537 
 1538 static inline void fuse_prepare_interrupt(struct fuse *f, fuse_req_t req,
 1539                       struct fuse_intr_data *d)
 1540 {
 1541     if (f->conf.intr)
 1542         fuse_do_prepare_interrupt(req, d);
 1543 }
 1544 
 1545 static const char* file_info_string(struct fuse_file_info *fi,
 1546                   char* buf, size_t len)
 1547 {
 1548     if(fi == NULL)
 1549         return "NULL";
 1550     snprintf(buf, len, "%llu", (unsigned long long) fi->fh);
 1551     return buf;
 1552 }
 1553 
 1554 int fuse_fs_getattr(struct fuse_fs *fs, const char *path, struct stat *buf,
 1555             struct fuse_file_info *fi)
 1556 {
 1557     fuse_get_context()->private_data = fs->user_data;
 1558     if (fs->op.getattr) {
 1559         if (fs->debug) {
 1560             char buf[10];
 1561             fprintf(stderr, "getattr[%s] %s\n",
 1562                 file_info_string(fi, buf, sizeof(buf)),
 1563                 path);
 1564         }
 1565         return fs->op.getattr(path, buf, fi);
 1566     } else {
 1567         return -ENOSYS;
 1568     }
 1569 }
 1570 
 1571 int fuse_fs_rename(struct fuse_fs *fs, const char *oldpath,
 1572            const char *newpath, unsigned int flags)
 1573 {
 1574     fuse_get_context()->private_data = fs->user_data;
 1575     if (fs->op.rename) {
 1576         if (fs->debug)
 1577             fprintf(stderr, "rename %s %s 0x%x\n", oldpath, newpath,
 1578                 flags);
 1579 
 1580         return fs->op.rename(oldpath, newpath, flags);
 1581     } else {
 1582         return -ENOSYS;
 1583     }
 1584 }
 1585 
 1586 int fuse_fs_unlink(struct fuse_fs *fs, const char *path)
 1587 {
 1588     fuse_get_context()->private_data = fs->user_data;
 1589     if (fs->op.unlink) {
 1590         if (fs->debug)
 1591             fprintf(stderr, "unlink %s\n", path);
 1592 
 1593         return fs->op.unlink(path);
 1594     } else {
 1595         return -ENOSYS;
 1596     }
 1597 }
 1598 
 1599 int fuse_fs_rmdir(struct fuse_fs *fs, const char *path)
 1600 {
 1601     fuse_get_context()->private_data = fs->user_data;
 1602     if (fs->op.rmdir) {
 1603         if (fs->debug)
 1604             fprintf(stderr, "rmdir %s\n", path);
 1605 
 1606         return fs->op.rmdir(path);
 1607     } else {
 1608         return -ENOSYS;
 1609     }
 1610 }
 1611 
 1612 int fuse_fs_symlink(struct fuse_fs *fs, const char *linkname, const char *path)
 1613 {
 1614     fuse_get_context()->private_data = fs->user_data;
 1615     if (fs->op.symlink) {
 1616         if (fs->debug)
 1617             fprintf(stderr, "symlink %s %s\n", linkname, path);
 1618 
 1619         return fs->op.symlink(linkname, path);
 1620     } else {
 1621         return -ENOSYS;
 1622     }
 1623 }
 1624 
 1625 int fuse_fs_link(struct fuse_fs *fs, const char *oldpath, const char *newpath)
 1626 {
 1627     fuse_get_context()->private_data = fs->user_data;
 1628     if (fs->op.link) {
 1629         if (fs->debug)
 1630             fprintf(stderr, "link %s %s\n", oldpath, newpath);
 1631 
 1632         return fs->op.link(oldpath, newpath);
 1633     } else {
 1634         return -ENOSYS;
 1635     }
 1636 }
 1637 
 1638 int fuse_fs_release(struct fuse_fs *fs,  const char *path,
 1639             struct fuse_file_info *fi)
 1640 {
 1641     fuse_get_context()->private_data = fs->user_data;
 1642     if (fs->op.release) {
 1643         if (fs->debug)
 1644             fprintf(stderr, "release%s[%llu] flags: 0x%x\n",
 1645                 fi->flush ? "+flush" : "",
 1646                 (unsigned long long) fi->fh, fi->flags);
 1647 
 1648         return fs->op.release(path, fi);
 1649     } else {
 1650         return 0;
 1651     }
 1652 }
 1653 
 1654 int fuse_fs_opendir(struct fuse_fs *fs, const char *path,
 1655             struct fuse_file_info *fi)
 1656 {
 1657     fuse_get_context()->private_data = fs->user_data;
 1658     if (fs->op.opendir) {
 1659         int err;
 1660 
 1661         if (fs->debug)
 1662             fprintf(stderr, "opendir flags: 0x%x %s\n", fi->flags,
 1663                 path);
 1664 
 1665         err = fs->op.opendir(path, fi);
 1666 
 1667         if (fs->debug && !err)
 1668             fprintf(stderr, "   opendir[%llu] flags: 0x%x %s\n",
 1669                 (unsigned long long) fi->fh, fi->flags, path);
 1670 
 1671         return err;
 1672     } else {
 1673         return 0;
 1674     }
 1675 }
 1676 
 1677 int fuse_fs_open(struct fuse_fs *fs, const char *path,
 1678          struct fuse_file_info *fi)
 1679 {
 1680     fuse_get_context()->private_data = fs->user_data;
 1681     if (fs->op.open) {
 1682         int err;
 1683 
 1684         if (fs->debug)
 1685             fprintf(stderr, "open flags: 0x%x %s\n", fi->flags,
 1686                 path);
 1687 
 1688         err = fs->op.open(path, fi);
 1689 
 1690         if (fs->debug && !err)
 1691             fprintf(stderr, "   open[%llu] flags: 0x%x %s\n",
 1692                 (unsigned long long) fi->fh, fi->flags, path);
 1693 
 1694         return err;
 1695     } else {
 1696         return 0;
 1697     }
 1698 }
 1699 
 1700 static void fuse_free_buf(struct fuse_bufvec *buf)
 1701 {
 1702     if (buf != NULL) {
 1703         size_t i;
 1704 
 1705         for (i = 0; i < buf->count; i++)
 1706             free(buf->buf[i].mem);
 1707         free(buf);
 1708     }
 1709 }
 1710 
 1711 int fuse_fs_read_buf(struct fuse_fs *fs, const char *path,
 1712              struct fuse_bufvec **bufp, size_t size, off_t off,
 1713              struct fuse_file_info *fi)
 1714 {
 1715     fuse_get_context()->private_data = fs->user_data;
 1716     if (fs->op.read || fs->op.read_buf) {
 1717         int res;
 1718 
 1719         if (fs->debug)
 1720             fprintf(stderr,
 1721                 "read[%llu] %zu bytes from %llu flags: 0x%x\n",
 1722                 (unsigned long long) fi->fh,
 1723                 size, (unsigned long long) off, fi->flags);
 1724 
 1725         if (fs->op.read_buf) {
 1726             res = fs->op.read_buf(path, bufp, size, off, fi);
 1727         } else {
 1728             struct fuse_bufvec *buf;
 1729             void *mem;
 1730 
 1731             buf = malloc(sizeof(struct fuse_bufvec));
 1732             if (buf == NULL)
 1733                 return -ENOMEM;
 1734 
 1735             mem = malloc(size);
 1736             if (mem == NULL) {
 1737                 free(buf);
 1738                 return -ENOMEM;
 1739             }
 1740             *buf = FUSE_BUFVEC_INIT(size);
 1741             buf->buf[0].mem = mem;
 1742             *bufp = buf;
 1743 
 1744             res = fs->op.read(path, mem, size, off, fi);
 1745             if (res >= 0)
 1746                 buf->buf[0].size = res;
 1747         }
 1748 
 1749         if (fs->debug && res >= 0)
 1750             fprintf(stderr, "   read[%llu] %zu bytes from %llu\n",
 1751                 (unsigned long long) fi->fh,
 1752                 fuse_buf_size(*bufp),
 1753                 (unsigned long long) off);
 1754         if (res >= 0 && fuse_buf_size(*bufp) > size)
 1755             fprintf(stderr, "fuse: read too many bytes\n");
 1756 
 1757         if (res < 0)
 1758             return res;
 1759 
 1760         return 0;
 1761     } else {
 1762         return -ENOSYS;
 1763     }
 1764 }
 1765 
 1766 int fuse_fs_read(struct fuse_fs *fs, const char *path, char *mem, size_t size,
 1767          off_t off, struct fuse_file_info *fi)
 1768 {
 1769     fuse_get_context()->private_data = fs->user_data;
 1770     if (fs->op.read || fs->op.read_buf) {
 1771         int res;
 1772 
 1773         if (fs->debug)
 1774             fprintf(stderr,
 1775                 "read[%llu] %zu bytes from %llu flags: 0x%x\n",
 1776                 (unsigned long long) fi->fh,
 1777                 size, (unsigned long long) off, fi->flags);
 1778 
 1779         if (fs->op.read_buf) {
 1780             struct fuse_bufvec *buf = NULL;
 1781 
 1782             res = fs->op.read_buf(path, &buf, size, off, fi);
 1783             if (res == 0) {
 1784                 struct fuse_bufvec dst = FUSE_BUFVEC_INIT(size);
 1785 
 1786                 dst.buf[0].mem = mem;
 1787                 res = fuse_buf_copy(&dst, buf, 0);
 1788             }
 1789             fuse_free_buf(buf);
 1790         } else {
 1791             res = fs->op.read(path, mem, size, off, fi);
 1792         }
 1793 
 1794         if (fs->debug && res >= 0)
 1795             fprintf(stderr, "   read[%llu] %u bytes from %llu\n",
 1796                 (unsigned long long) fi->fh,
 1797                 res,
 1798                 (unsigned long long) off);
 1799         if (res >= 0 && res > (int) size)
 1800             fprintf(stderr, "fuse: read too many bytes\n");
 1801 
 1802         return res;
 1803     } else {
 1804         return -ENOSYS;
 1805     }
 1806 }
 1807 
 1808 int fuse_fs_write_buf(struct fuse_fs *fs, const char *path,
 1809               struct fuse_bufvec *buf, off_t off,
 1810               struct fuse_file_info *fi)
 1811 {
 1812     fuse_get_context()->private_data = fs->user_data;
 1813     if (fs->op.write_buf || fs->op.write) {
 1814         int res;
 1815         size_t size = fuse_buf_size(buf);
 1816 
 1817         assert(buf->idx == 0 && buf->off == 0);
 1818         if (fs->debug)
 1819             fprintf(stderr,
 1820                 "write%s[%llu] %zu bytes to %llu flags: 0x%x\n",
 1821                 fi->writepage ? "page" : "",
 1822                 (unsigned long long) fi->fh,
 1823                 size,
 1824                 (unsigned long long) off,
 1825                 fi->flags);
 1826 
 1827         if (fs->op.write_buf) {
 1828             res = fs->op.write_buf(path, buf, off, fi);
 1829         } else {
 1830             void *mem = NULL;
 1831             struct fuse_buf *flatbuf;
 1832             struct fuse_bufvec tmp = FUSE_BUFVEC_INIT(size);
 1833 
 1834             if (buf->count == 1 &&
 1835                 !(buf->buf[0].flags & FUSE_BUF_IS_FD)) {
 1836                 flatbuf = &buf->buf[0];
 1837             } else {
 1838                 res = -ENOMEM;
 1839                 mem = malloc(size);
 1840                 if (mem == NULL)
 1841                     goto out;
 1842 
 1843                 tmp.buf[0].mem = mem;
 1844                 res = fuse_buf_copy(&tmp, buf, 0);
 1845                 if (res <= 0)
 1846                     goto out_free;
 1847 
 1848                 tmp.buf[0].size = res;
 1849                 flatbuf = &tmp.buf[0];
 1850             }
 1851 
 1852             res = fs->op.write(path, flatbuf->mem, flatbuf->size,
 1853                        off, fi);
 1854 out_free:
 1855             free(mem);
 1856         }
 1857 out:
 1858         if (fs->debug && res >= 0)
 1859             fprintf(stderr, "   write%s[%llu] %u bytes to %llu\n",
 1860                 fi->writepage ? "page" : "",
 1861                 (unsigned long long) fi->fh, res,
 1862                 (unsigned long long) off);
 1863         if (res > (int) size)
 1864             fprintf(stderr, "fuse: wrote too many bytes\n");
 1865 
 1866         return res;
 1867     } else {
 1868         return -ENOSYS;
 1869     }
 1870 }
 1871 
 1872 int fuse_fs_write(struct fuse_fs *fs, const char *path, const char *mem,
 1873           size_t size, off_t off, struct fuse_file_info *fi)
 1874 {
 1875     struct fuse_bufvec bufv = FUSE_BUFVEC_INIT(size);
 1876 
 1877     bufv.buf[0].mem = (void *) mem;
 1878 
 1879     return fuse_fs_write_buf(fs, path, &bufv, off, fi);
 1880 }
 1881 
 1882 int fuse_fs_fsync(struct fuse_fs *fs, const char *path, int datasync,
 1883           struct fuse_file_info *fi)
 1884 {
 1885     fuse_get_context()->private_data = fs->user_data;
 1886     if (fs->op.fsync) {
 1887         if (fs->debug)
 1888             fprintf(stderr, "fsync[%llu] datasync: %i\n",
 1889                 (unsigned long long) fi->fh, datasync);
 1890 
 1891         return fs->op.fsync(path, datasync, fi);
 1892     } else {
 1893         return -ENOSYS;
 1894     }
 1895 }
 1896 
 1897 int fuse_fs_fsyncdir(struct fuse_fs *fs, const char *path, int datasync,
 1898              struct fuse_file_info *fi)
 1899 {
 1900     fuse_get_context()->private_data = fs->user_data;
 1901     if (fs->op.fsyncdir) {
 1902         if (fs->debug)
 1903             fprintf(stderr, "fsyncdir[%llu] datasync: %i\n",
 1904                 (unsigned long long) fi->fh, datasync);
 1905 
 1906         return fs->op.fsyncdir(path, datasync, fi);
 1907     } else {
 1908         return -ENOSYS;
 1909     }
 1910 }
 1911 
 1912 int fuse_fs_flush(struct fuse_fs *fs, const char *path,
 1913           struct fuse_file_info *fi)
 1914 {
 1915     fuse_get_context()->private_data = fs->user_data;
 1916     if (fs->op.flush) {
 1917         if (fs->debug)
 1918             fprintf(stderr, "flush[%llu]\n",
 1919                 (unsigned long long) fi->fh);
 1920 
 1921         return fs->op.flush(path, fi);
 1922     } else {
 1923         return -ENOSYS;
 1924     }
 1925 }
 1926 
 1927 int fuse_fs_statfs(struct fuse_fs *fs, const char *path, struct statvfs *buf)
 1928 {
 1929     fuse_get_context()->private_data = fs->user_data;
 1930     if (fs->op.statfs) {
 1931         if (fs->debug)
 1932             fprintf(stderr, "statfs %s\n", path);
 1933 
 1934         return fs->op.statfs(path, buf);
 1935     } else {
 1936         buf->f_namemax = 255;
 1937         buf->f_bsize = 512;
 1938         return 0;
 1939     }
 1940 }
 1941 
 1942 int fuse_fs_releasedir(struct fuse_fs *fs, const char *path,
 1943                struct fuse_file_info *fi)
 1944 {
 1945     fuse_get_context()->private_data = fs->user_data;
 1946     if (fs->op.releasedir) {
 1947         if (fs->debug)
 1948             fprintf(stderr, "releasedir[%llu] flags: 0x%x\n",
 1949                 (unsigned long long) fi->fh, fi->flags);
 1950 
 1951         return fs->op.releasedir(path, fi);
 1952     } else {
 1953         return 0;
 1954     }
 1955 }
 1956 
 1957 int fuse_fs_readdir(struct fuse_fs *fs, const char *path, void *buf,
 1958             fuse_fill_dir_t filler, off_t off,
 1959             struct fuse_file_info *fi,
 1960             enum fuse_readdir_flags flags)
 1961 {
 1962     fuse_get_context()->private_data = fs->user_data;
 1963     if (fs->op.readdir) {
 1964         if (fs->debug) {
 1965             fprintf(stderr, "readdir%s[%llu] from %llu\n",
 1966                 (flags & FUSE_READDIR_PLUS) ? "plus" : "",
 1967                 (unsigned long long) fi->fh,
 1968                 (unsigned long long) off);
 1969         }
 1970 
 1971         return fs->op.readdir(path, buf, filler, off, fi, flags);
 1972     } else {
 1973         return -ENOSYS;
 1974     }
 1975 }
 1976 
 1977 int fuse_fs_create(struct fuse_fs *fs, const char *path, mode_t mode,
 1978            struct fuse_file_info *fi)
 1979 {
 1980     fuse_get_context()->private_data = fs->user_data;
 1981     if (fs->op.create) {
 1982         int err;
 1983 
 1984         if (fs->debug)
 1985             fprintf(stderr,
 1986                 "create flags: 0x%x %s 0%o umask=0%03o\n",
 1987                 fi->flags, path, mode,
 1988                 fuse_get_context()->umask);
 1989 
 1990         err = fs->op.create(path, mode, fi);
 1991 
 1992         if (fs->debug && !err)
 1993             fprintf(stderr, "   create[%llu] flags: 0x%x %s\n",
 1994                 (unsigned long long) fi->fh, fi->flags, path);
 1995 
 1996         return err;
 1997     } else {
 1998         return -ENOSYS;
 1999     }
 2000 }
 2001 
 2002 int fuse_fs_lock(struct fuse_fs *fs, const char *path,
 2003          struct fuse_file_info *fi, int cmd, struct flock *lock)
 2004 {
 2005     fuse_get_context()->private_data = fs->user_data;
 2006     if (fs->op.lock) {
 2007         if (fs->debug)
 2008             fprintf(stderr, "lock[%llu] %s %s start: %llu len: %llu pid: %llu\n",
 2009                 (unsigned long long) fi->fh,
 2010                 (cmd == F_GETLK ? "F_GETLK" :
 2011                  (cmd == F_SETLK ? "F_SETLK" :
 2012                   (cmd == F_SETLKW ? "F_SETLKW" : "???"))),
 2013                 (lock->l_type == F_RDLCK ? "F_RDLCK" :
 2014                  (lock->l_type == F_WRLCK ? "F_WRLCK" :
 2015                   (lock->l_type == F_UNLCK ? "F_UNLCK" :
 2016                    "???"))),
 2017                 (unsigned long long) lock->l_start,
 2018                 (unsigned long long) lock->l_len,
 2019                 (unsigned long long) lock->l_pid);
 2020 
 2021         return fs->op.lock(path, fi, cmd, lock);
 2022     } else {
 2023         return -ENOSYS;
 2024     }
 2025 }
 2026 
 2027 int fuse_fs_flock(struct fuse_fs *fs, const char *path,
 2028           struct fuse_file_info *fi, int op)
 2029 {
 2030     fuse_get_context()->private_data = fs->user_data;
 2031     if (fs->op.flock) {
 2032         if (fs->debug) {
 2033             int xop = op & ~LOCK_NB;
 2034 
 2035             fprintf(stderr, "lock[%llu] %s%s\n",
 2036                 (unsigned long long) fi->fh,
 2037                 xop == LOCK_SH ? "LOCK_SH" :
 2038                 (xop == LOCK_EX ? "LOCK_EX" :
 2039                  (xop == LOCK_UN ? "LOCK_UN" : "???")),
 2040                 (op & LOCK_NB) ? "|LOCK_NB" : "");
 2041         }
 2042         return fs->op.flock(path, fi, op);
 2043     } else {
 2044         return -ENOSYS;
 2045     }
 2046 }
 2047 
 2048 int fuse_fs_chown(struct fuse_fs *fs, const char *path, uid_t uid,
 2049           gid_t gid, struct fuse_file_info *fi)
 2050 {
 2051     fuse_get_context()->private_data = fs->user_data;
 2052     if (fs->op.chown) {
 2053         if (fs->debug) {
 2054             char buf[10];
 2055             fprintf(stderr, "chown[%s] %s %lu %lu\n",
 2056                 file_info_string(fi, buf, sizeof(buf)),
 2057                 path, (unsigned long) uid, (unsigned long) gid);
 2058         }
 2059         return fs->op.chown(path, uid, gid, fi);
 2060     } else {
 2061         return -ENOSYS;
 2062     }
 2063 }
 2064 
 2065 int fuse_fs_truncate(struct fuse_fs *fs, const char *path, off_t size,
 2066               struct fuse_file_info *fi)
 2067 {
 2068     fuse_get_context()->private_data = fs->user_data;
 2069     if (fs->op.truncate) {
 2070         if (fs->debug) {
 2071             char buf[10];
 2072             fprintf(stderr, "truncate[%s] %llu\n",
 2073                 file_info_string(fi, buf, sizeof(buf)),
 2074                 (unsigned long long) size);
 2075         }
 2076         return fs->op.truncate(path, size, fi);
 2077     } else {
 2078         return -ENOSYS;
 2079     }
 2080 }
 2081 
 2082 int fuse_fs_utimens(struct fuse_fs *fs, const char *path,
 2083             const struct timespec tv[2], struct fuse_file_info *fi)
 2084 {
 2085     fuse_get_context()->private_data = fs->user_data;
 2086     if (fs->op.utimens) {
 2087         if (fs->debug) {
 2088             char buf[10];
 2089             fprintf(stderr, "utimens[%s] %s %li.%09lu %li.%09lu\n",
 2090                 file_info_string(fi, buf, sizeof(buf)),
 2091                 path, tv[0].tv_sec, tv[0].tv_nsec,
 2092                 tv[1].tv_sec, tv[1].tv_nsec);
 2093         }
 2094         return fs->op.utimens(path, tv, fi);
 2095     } else {
 2096         return -ENOSYS;
 2097     }
 2098 }
 2099 
 2100 int fuse_fs_access(struct fuse_fs *fs, const char *path, int mask)
 2101 {
 2102     fuse_get_context()->private_data = fs->user_data;
 2103     if (fs->op.access) {
 2104         if (fs->debug)
 2105             fprintf(stderr, "access %s 0%o\n", path, mask);
 2106 
 2107         return fs->op.access(path, mask);
 2108     } else {
 2109         return -ENOSYS;
 2110     }
 2111 }
 2112 
 2113 int fuse_fs_readlink(struct fuse_fs *fs, const char *path, char *buf,
 2114              size_t len)
 2115 {
 2116     fuse_get_context()->private_data = fs->user_data;
 2117     if (fs->op.readlink) {
 2118         if (fs->debug)
 2119             fprintf(stderr, "readlink %s %lu\n", path,
 2120                 (unsigned long) len);
 2121 
 2122         return fs->op.readlink(path, buf, len);
 2123     } else {
 2124         return -ENOSYS;
 2125     }
 2126 }
 2127 
 2128 int fuse_fs_mknod(struct fuse_fs *fs, const char *path, mode_t mode,
 2129           dev_t rdev)
 2130 {
 2131     fuse_get_context()->private_data = fs->user_data;
 2132     if (fs->op.mknod) {
 2133         if (fs->debug)
 2134             fprintf(stderr, "mknod %s 0%o 0x%llx umask=0%03o\n",
 2135                 path, mode, (unsigned long long) rdev,
 2136                 fuse_get_context()->umask);
 2137 
 2138         return fs->op.mknod(path, mode, rdev);
 2139     } else {
 2140         return -ENOSYS;
 2141     }
 2142 }
 2143 
 2144 int fuse_fs_mkdir(struct fuse_fs *fs, const char *path, mode_t mode)
 2145 {
 2146     fuse_get_context()->private_data = fs->user_data;
 2147     if (fs->op.mkdir) {
 2148         if (fs->debug)
 2149             fprintf(stderr, "mkdir %s 0%o umask=0%03o\n",
 2150                 path, mode, fuse_get_context()->umask);
 2151 
 2152         return fs->op.mkdir(path, mode);
 2153     } else {
 2154         return -ENOSYS;
 2155     }
 2156 }
 2157 
 2158 int fuse_fs_setxattr(struct fuse_fs *fs, const char *path, const char *name,
 2159              const char *value, size_t size, int flags)
 2160 {
 2161     fuse_get_context()->private_data = fs->user_data;
 2162     if (fs->op.setxattr) {
 2163         if (fs->debug)
 2164             fprintf(stderr, "setxattr %s %s %lu 0x%x\n",
 2165                 path, name, (unsigned long) size, flags);
 2166 
 2167         return fs->op.setxattr(path, name, value, size, flags);
 2168     } else {
 2169         return -ENOSYS;
 2170     }
 2171 }
 2172 
 2173 int fuse_fs_getxattr(struct fuse_fs *fs, const char *path, const char *name,
 2174              char *value, size_t size)
 2175 {
 2176     fuse_get_context()->private_data = fs->user_data;
 2177     if (fs->op.getxattr) {
 2178         if (fs->debug)
 2179             fprintf(stderr, "getxattr %s %s %lu\n",
 2180                 path, name, (unsigned long) size);
 2181 
 2182         return fs->op.getxattr(path, name, value, size);
 2183     } else {
 2184         return -ENOSYS;
 2185     }
 2186 }
 2187 
 2188 int fuse_fs_listxattr(struct fuse_fs *fs, const char *path, char *list,
 2189               size_t size)
 2190 {
 2191     fuse_get_context()->private_data = fs->user_data;
 2192     if (fs->op.listxattr) {
 2193         if (fs->debug)
 2194             fprintf(stderr, "listxattr %s %lu\n",
 2195                 path, (unsigned long) size);
 2196 
 2197         return fs->op.listxattr(path, list, size);
 2198     } else {
 2199         return -ENOSYS;
 2200     }
 2201 }
 2202 
 2203 int fuse_fs_bmap(struct fuse_fs *fs, const char *path, size_t blocksize,
 2204          uint64_t *idx)
 2205 {
 2206     fuse_get_context()->private_data = fs->user_data;
 2207     if (fs->op.bmap) {
 2208         if (fs->debug)
 2209             fprintf(stderr, "bmap %s blocksize: %lu index: %llu\n",
 2210                 path, (unsigned long) blocksize,
 2211                 (unsigned long long) *idx);
 2212 
 2213         return fs->op.bmap(path, blocksize, idx);
 2214     } else {
 2215         return -ENOSYS;
 2216     }
 2217 }
 2218 
 2219 int fuse_fs_removexattr(struct fuse_fs *fs, const char *path, const char *name)
 2220 {
 2221     fuse_get_context()->private_data = fs->user_data;
 2222     if (fs->op.removexattr) {
 2223         if (fs->debug)
 2224             fprintf(stderr, "removexattr %s %s\n", path, name);
 2225 
 2226         return fs->op.removexattr(path, name);
 2227     } else {
 2228         return -ENOSYS;
 2229     }
 2230 }
 2231 
 2232 int fuse_fs_ioctl(struct fuse_fs *fs, const char *path, int cmd, void *arg,
 2233           struct fuse_file_info *fi, unsigned int flags, void *data)
 2234 {
 2235     fuse_get_context()->private_data = fs->user_data;
 2236     if (fs->op.ioctl) {
 2237         if (fs->debug)
 2238             fprintf(stderr, "ioctl[%llu] 0x%x flags: 0x%x\n",
 2239                 (unsigned long long) fi->fh, cmd, flags);
 2240 
 2241         return fs->op.ioctl(path, cmd, arg, fi, flags, data);
 2242     } else
 2243         return -ENOSYS;
 2244 }
 2245 
 2246 int fuse_fs_poll(struct fuse_fs *fs, const char *path,
 2247          struct fuse_file_info *fi, struct fuse_pollhandle *ph,
 2248          unsigned *reventsp)
 2249 {
 2250     fuse_get_context()->private_data = fs->user_data;
 2251     if (fs->op.poll) {
 2252         int res;
 2253 
 2254         if (fs->debug)
 2255             fprintf(stderr, "poll[%llu] ph: %p, events 0x%x\n",
 2256                 (unsigned long long) fi->fh, ph,
 2257                 fi->poll_events);
 2258 
 2259         res = fs->op.poll(path, fi, ph, reventsp);
 2260 
 2261         if (fs->debug && !res)
 2262             fprintf(stderr, "   poll[%llu] revents: 0x%x\n",
 2263                 (unsigned long long) fi->fh, *reventsp);
 2264 
 2265         return res;
 2266     } else
 2267         return -ENOSYS;
 2268 }
 2269 
 2270 int fuse_fs_fallocate(struct fuse_fs *fs, const char *path, int mode,
 2271         off_t offset, off_t length, struct fuse_file_info *fi)
 2272 {
 2273     fuse_get_context()->private_data = fs->user_data;
 2274     if (fs->op.fallocate) {
 2275         if (fs->debug)
 2276             fprintf(stderr, "fallocate %s mode %x, offset: %llu, length: %llu\n",
 2277                 path,
 2278                 mode,
 2279                 (unsigned long long) offset,
 2280                 (unsigned long long) length);
 2281 
 2282         return fs->op.fallocate(path, mode, offset, length, fi);
 2283     } else
 2284         return -ENOSYS;
 2285 }
 2286 
 2287 static int is_open(struct fuse *f, fuse_ino_t dir, const char *name)
 2288 {
 2289     struct node *node;
 2290     int isopen = 0;
 2291     pthread_mutex_lock(&f->lock);
 2292     node = lookup_node(f, dir, name);
 2293     if (node && node->open_count > 0)
 2294         isopen = 1;
 2295     pthread_mutex_unlock(&f->lock);
 2296     return isopen;
 2297 }
 2298 
 2299 static char *hidden_name(struct fuse *f, fuse_ino_t dir, const char *oldname,
 2300              char *newname, size_t bufsize)
 2301 {
 2302     struct stat buf;
 2303     struct node *node;
 2304     struct node *newnode;
 2305     char *newpath;
 2306     int res;
 2307     int failctr = 10;
 2308 
 2309     do {
 2310         pthread_mutex_lock(&f->lock);
 2311         node = lookup_node(f, dir, oldname);
 2312         if (node == NULL) {
 2313             pthread_mutex_unlock(&f->lock);
 2314             return NULL;
 2315         }
 2316         do {
 2317             f->hidectr ++;
 2318             snprintf(newname, bufsize, ".fuse_hidden%08x%08x",
 2319                  (unsigned int) node->nodeid, f->hidectr);
 2320             newnode = lookup_node(f, dir, newname);
 2321         } while(newnode);
 2322 
 2323         res = try_get_path(f, dir, newname, &newpath, NULL, false);
 2324         pthread_mutex_unlock(&f->lock);
 2325         if (res)
 2326             break;
 2327 
 2328         memset(&buf, 0, sizeof(buf));
 2329         res = fuse_fs_getattr(f->fs, newpath, &buf, NULL);
 2330         if (res == -ENOENT)
 2331             break;
 2332         free(newpath);
 2333         newpath = NULL;
 2334     } while(res == 0 && --failctr);
 2335 
 2336     return newpath;
 2337 }
 2338 
 2339 static int hide_node(struct fuse *f, const char *oldpath,
 2340              fuse_ino_t dir, const char *oldname)
 2341 {
 2342     char newname[64];
 2343     char *newpath;
 2344     int err = -EBUSY;
 2345 
 2346     newpath = hidden_name(f, dir, oldname, newname, sizeof(newname));
 2347     if (newpath) {
 2348         err = fuse_fs_rename(f->fs, oldpath, newpath, 0);
 2349         if (!err)
 2350             err = rename_node(f, dir, oldname, dir, newname, 1);
 2351         free(newpath);
 2352     }
 2353     return err;
 2354 }
 2355 
 2356 static int mtime_eq(const struct stat *stbuf, const struct timespec *ts)
 2357 {
 2358     return stbuf->st_mtime == ts->tv_sec &&
 2359         ST_MTIM_NSEC(stbuf) == ts->tv_nsec;
 2360 }
 2361 
 2362 #ifndef CLOCK_MONOTONIC
 2363 #define CLOCK_MONOTONIC CLOCK_REALTIME
 2364 #endif
 2365 
 2366 static void curr_time(struct timespec *now)
 2367 {
 2368     static clockid_t clockid = CLOCK_MONOTONIC;
 2369     int res = clock_gettime(clockid, now);
 2370     if (res == -1 && errno == EINVAL) {
 2371         clockid = CLOCK_REALTIME;
 2372         res = clock_gettime(clockid, now);
 2373     }
 2374     if (res == -1) {
 2375         perror("fuse: clock_gettime");
 2376         abort();
 2377     }
 2378 }
 2379 
 2380 static void update_stat(struct node *node, const struct stat *stbuf)
 2381 {
 2382     if (node->cache_valid && (!mtime_eq(stbuf, &node->mtime) ||
 2383                   stbuf->st_size != node->size))
 2384         node->cache_valid = 0;
 2385     node->mtime.tv_sec = stbuf->st_mtime;
 2386     node->mtime.tv_nsec = ST_MTIM_NSEC(stbuf);
 2387     node->size = stbuf->st_size;
 2388     curr_time(&node->stat_updated);
 2389 }
 2390 
 2391 static int do_lookup(struct fuse *f, fuse_ino_t nodeid, const char *name,
 2392              struct fuse_entry_param *e)
 2393 {
 2394     struct node *node;
 2395 
 2396     node = find_node(f, nodeid, name);
 2397     if (node == NULL)
 2398         return -ENOMEM;
 2399 
 2400     e->ino = node->nodeid;
 2401     e->generation = node->generation;
 2402     e->entry_timeout = f->conf.entry_timeout;
 2403     e->attr_timeout = f->conf.attr_timeout;
 2404     if (f->conf.auto_cache) {
 2405         pthread_mutex_lock(&f->lock);
 2406         update_stat(node, &e->attr);
 2407         pthread_mutex_unlock(&f->lock);
 2408     }
 2409     set_stat(f, e->ino, &e->attr);
 2410     return 0;
 2411 }
 2412 
 2413 static int lookup_path(struct fuse *f, fuse_ino_t nodeid,
 2414                const char *name, const char *path,
 2415                struct fuse_entry_param *e, struct fuse_file_info *fi)
 2416 {
 2417     int res;
 2418 
 2419     memset(e, 0, sizeof(struct fuse_entry_param));
 2420     res = fuse_fs_getattr(f->fs, path, &e->attr, fi);
 2421     if (res == 0) {
 2422         res = do_lookup(f, nodeid, name, e);
 2423         if (res == 0 && f->conf.debug) {
 2424             fprintf(stderr, "   NODEID: %llu\n",
 2425                 (unsigned long long) e->ino);
 2426         }
 2427     }
 2428     return res;
 2429 }
 2430 
 2431 static struct fuse_context_i *fuse_get_context_internal(void)
 2432 {
 2433     return (struct fuse_context_i *) pthread_getspecific(fuse_context_key);
 2434 }
 2435 
 2436 static struct fuse_context_i *fuse_create_context(struct fuse *f)
 2437 {
 2438     struct fuse_context_i *c = fuse_get_context_internal();
 2439     if (c == NULL) {
 2440         c = (struct fuse_context_i *)
 2441             calloc(1, sizeof(struct fuse_context_i));
 2442         if (c == NULL) {
 2443             /* This is hard to deal with properly, so just
 2444                abort.  If memory is so low that the
 2445                context cannot be allocated, there's not
 2446                much hope for the filesystem anyway */
 2447             fprintf(stderr, "fuse: failed to allocate thread specific data\n");
 2448             abort();
 2449         }
 2450         pthread_setspecific(fuse_context_key, c);
 2451     } else {
 2452         memset(c, 0, sizeof(*c));
 2453     }
 2454     c->ctx.fuse = f;
 2455 
 2456     return c;
 2457 }
 2458 
 2459 static void fuse_freecontext(void *data)
 2460 {
 2461     free(data);
 2462 }
 2463 
 2464 static int fuse_create_context_key(void)
 2465 {
 2466     int err = 0;
 2467     pthread_mutex_lock(&fuse_context_lock);
 2468     if (!fuse_context_ref) {
 2469         err = pthread_key_create(&fuse_context_key, fuse_freecontext);
 2470         if (err) {
 2471             fprintf(stderr, "fuse: failed to create thread specific key: %s\n",
 2472                 strerror(err));
 2473             pthread_mutex_unlock(&fuse_context_lock);
 2474             return -1;
 2475         }
 2476     }
 2477     fuse_context_ref++;
 2478     pthread_mutex_unlock(&fuse_context_lock);
 2479     return 0;
 2480 }
 2481 
 2482 static void fuse_delete_context_key(void)
 2483 {
 2484     pthread_mutex_lock(&fuse_context_lock);
 2485     fuse_context_ref--;
 2486     if (!fuse_context_ref) {
 2487         free(pthread_getspecific(fuse_context_key));
 2488         pthread_key_delete(fuse_context_key);
 2489     }
 2490     pthread_mutex_unlock(&fuse_context_lock);
 2491 }
 2492 
 2493 static struct fuse *req_fuse_prepare(fuse_req_t req)
 2494 {
 2495     struct fuse_context_i *c = fuse_create_context(req_fuse(req));
 2496     const struct fuse_ctx *ctx = fuse_req_ctx(req);
 2497     c->req = req;
 2498     c->ctx.uid = ctx->uid;
 2499     c->ctx.gid = ctx->gid;
 2500     c->ctx.pid = ctx->pid;
 2501     c->ctx.umask = ctx->umask;
 2502     return c->ctx.fuse;
 2503 }
 2504 
 2505 static inline void reply_err(fuse_req_t req, int err)
 2506 {
 2507     /* fuse_reply_err() uses non-negated errno values */
 2508     fuse_reply_err(req, -err);
 2509 }
 2510 
 2511 static void reply_entry(fuse_req_t req, const struct fuse_entry_param *e,
 2512             int err)
 2513 {
 2514     if (!err) {
 2515         struct fuse *f = req_fuse(req);
 2516         if (fuse_reply_entry(req, e) == -ENOENT) {
 2517             /* Skip forget for negative result */
 2518             if  (e->ino != 0)
 2519                 forget_node(f, e->ino, 1);
 2520         }
 2521     } else
 2522         reply_err(req, err);
 2523 }
 2524 
 2525 void fuse_fs_init(struct fuse_fs *fs, struct fuse_conn_info *conn,
 2526           struct fuse_config *cfg)
 2527 {
 2528     fuse_get_context()->private_data = fs->user_data;
 2529     if (!fs->op.write_buf)
 2530         conn->want &= ~FUSE_CAP_SPLICE_READ;
 2531     if (!fs->op.lock)
 2532         conn->want &= ~FUSE_CAP_POSIX_LOCKS;
 2533     if (!fs->op.flock)
 2534         conn->want &= ~FUSE_CAP_FLOCK_LOCKS;
 2535     if (fs->op.init)
 2536         fs->user_data = fs->op.init(conn, cfg);
 2537 }
 2538 
 2539 static void fuse_lib_init(void *data, struct fuse_conn_info *conn)
 2540 {
 2541     struct fuse *f = (struct fuse *) data;
 2542 
 2543     fuse_create_context(f);
 2544     if(conn->capable & FUSE_CAP_EXPORT_SUPPORT)
 2545         conn->want |= FUSE_CAP_EXPORT_SUPPORT;
 2546     fuse_fs_init(f->fs, conn, &f->conf);
 2547 }
 2548 
 2549 void fuse_fs_destroy(struct fuse_fs *fs)
 2550 {
 2551     fuse_get_context()->private_data = fs->user_data;
 2552     if (fs->op.destroy)
 2553         fs->op.destroy(fs->user_data);
 2554     if (fs->m)
 2555         fuse_put_module(fs->m);
 2556     free(fs);
 2557 }
 2558 
 2559 static void fuse_lib_destroy(void *data)
 2560 {
 2561     struct fuse *f = (struct fuse *) data;
 2562 
 2563     fuse_create_context(f);
 2564     fuse_fs_destroy(f->fs);
 2565     f->fs = NULL;
 2566 }
 2567 
 2568 static void fuse_lib_lookup(fuse_req_t req, fuse_ino_t parent,
 2569                 const char *name)
 2570 {
 2571     struct fuse *f = req_fuse_prepare(req);
 2572     struct fuse_entry_param e;
 2573     char *path;
 2574     int err;
 2575     struct node *dot = NULL;
 2576 
 2577     if (name[0] == '.') {
 2578         int len = strlen(name);
 2579 
 2580         if (len == 1 || (name[1] == '.' && len == 2)) {
 2581             pthread_mutex_lock(&f->lock);
 2582             if (len == 1) {
 2583                 if (f->conf.debug)
 2584                     fprintf(stderr, "LOOKUP-DOT\n");
 2585                 dot = get_node_nocheck(f, parent);
 2586                 if (dot == NULL) {
 2587                     pthread_mutex_unlock(&f->lock);
 2588                     reply_entry(req, &e, -ESTALE);
 2589                     return;
 2590                 }
 2591                 dot->refctr++;
 2592             } else {
 2593                 if (f->conf.debug)
 2594                     fprintf(stderr, "LOOKUP-DOTDOT\n");
 2595                 parent = get_node(f, parent)->parent->nodeid;
 2596             }
 2597             pthread_mutex_unlock(&f->lock);
 2598             name = NULL;
 2599         }
 2600     }
 2601 
 2602     err = get_path_name(f, parent, name, &path);
 2603     if (!err) {
 2604         struct fuse_intr_data d;
 2605         if (f->conf.debug)
 2606             fprintf(stderr, "LOOKUP %s\n", path);
 2607         fuse_prepare_interrupt(f, req, &d);
 2608         err = lookup_path(f, parent, name, path, &e, NULL);
 2609         if (err == -ENOENT && f->conf.negative_timeout != 0.0) {
 2610             e.ino = 0;
 2611             e.entry_timeout = f->conf.negative_timeout;
 2612             err = 0;
 2613         }
 2614         fuse_finish_interrupt(f, req, &d);
 2615         free_path(f, parent, path);
 2616     }
 2617     if (dot) {
 2618         pthread_mutex_lock(&f->lock);
 2619         unref_node(f, dot);
 2620         pthread_mutex_unlock(&f->lock);
 2621     }
 2622     reply_entry(req, &e, err);
 2623 }
 2624 
 2625 static void do_forget(struct fuse *f, fuse_ino_t ino, uint64_t nlookup)
 2626 {
 2627     if (f->conf.debug)
 2628         fprintf(stderr, "FORGET %llu/%llu\n", (unsigned long long)ino,
 2629             (unsigned long long) nlookup);
 2630     forget_node(f, ino, nlookup);
 2631 }
 2632 
 2633 static void fuse_lib_forget(fuse_req_t req, fuse_ino_t ino, uint64_t nlookup)
 2634 {
 2635     do_forget(req_fuse(req), ino, nlookup);
 2636     fuse_reply_none(req);
 2637 }
 2638 
 2639 static void fuse_lib_forget_multi(fuse_req_t req, size_t count,
 2640                   struct fuse_forget_data *forgets)
 2641 {
 2642     struct fuse *f = req_fuse(req);
 2643     size_t i;
 2644 
 2645     for (i = 0; i < count; i++)
 2646         do_forget(f, forgets[i].ino, forgets[i].nlookup);
 2647 
 2648     fuse_reply_none(req);
 2649 }
 2650 
 2651 
 2652 static void fuse_lib_getattr(fuse_req_t req, fuse_ino_t ino,
 2653                  struct fuse_file_info *fi)
 2654 {
 2655     struct fuse *f = req_fuse_prepare(req);
 2656     struct stat buf;
 2657     char *path;
 2658     int err;
 2659 
 2660     memset(&buf, 0, sizeof(buf));
 2661 
 2662     if (fi != NULL)
 2663         err = get_path_nullok(f, ino, &path);
 2664     else
 2665         err = get_path(f, ino, &path);
 2666     if (!err) {
 2667         struct fuse_intr_data d;
 2668         fuse_prepare_interrupt(f, req, &d);
 2669         err = fuse_fs_getattr(f->fs, path, &buf, fi);
 2670         fuse_finish_interrupt(f, req, &d);
 2671         free_path(f, ino, path);
 2672     }
 2673     if (!err) {
 2674         struct node *node;
 2675 
 2676         pthread_mutex_lock(&f->lock);
 2677         node = get_node(f, ino);
 2678         if (node->is_hidden && buf.st_nlink > 0)
 2679             buf.st_nlink--;
 2680         if (f->conf.auto_cache)
 2681             update_stat(node, &buf);
 2682         pthread_mutex_unlock(&f->lock);
 2683         set_stat(f, ino, &buf);
 2684         fuse_reply_attr(req, &buf, f->conf.attr_timeout);
 2685     } else
 2686         reply_err(req, err);
 2687 }
 2688 
 2689 int fuse_fs_chmod(struct fuse_fs *fs, const char *path, mode_t mode,
 2690           struct fuse_file_info *fi)
 2691 {
 2692     fuse_get_context()->private_data = fs->user_data;
 2693     if (fs->op.chmod) {
 2694         if (fs->debug) {
 2695             char buf[10];
 2696             fprintf(stderr, "chmod[%s] %s %llo\n",
 2697                 file_info_string(fi, buf, sizeof(buf)),
 2698                 path, (unsigned long long) mode);
 2699         }
 2700         return fs->op.chmod(path, mode, fi);
 2701     }
 2702     else
 2703         return -ENOSYS;
 2704 }
 2705 
 2706 static void fuse_lib_setattr(fuse_req_t req, fuse_ino_t ino, struct stat *attr,
 2707                  int valid, struct fuse_file_info *fi)
 2708 {
 2709     struct fuse *f = req_fuse_prepare(req);
 2710     struct stat buf;
 2711     char *path;
 2712     int err;
 2713 
 2714     memset(&buf, 0, sizeof(buf));
 2715     if (fi != NULL)
 2716         err = get_path_nullok(f, ino, &path);
 2717     else
 2718         err = get_path(f, ino, &path);
 2719     if (!err) {
 2720         struct fuse_intr_data d;
 2721         fuse_prepare_interrupt(f, req, &d);
 2722         err = 0;
 2723         if (!err && (valid & FUSE_SET_ATTR_MODE))
 2724             err = fuse_fs_chmod(f->fs, path, attr->st_mode, fi);
 2725         if (!err && (valid & (FUSE_SET_ATTR_UID | FUSE_SET_ATTR_GID))) {
 2726             uid_t uid = (valid & FUSE_SET_ATTR_UID) ?
 2727                 attr->st_uid : (uid_t) -1;
 2728             gid_t gid = (valid & FUSE_SET_ATTR_GID) ?
 2729                 attr->st_gid : (gid_t) -1;
 2730             err = fuse_fs_chown(f->fs, path, uid, gid, fi);
 2731         }
 2732         if (!err && (valid & FUSE_SET_ATTR_SIZE)) {
 2733             err = fuse_fs_truncate(f->fs, path,
 2734                            attr->st_size, fi);
 2735         }
 2736 #ifdef HAVE_UTIMENSAT
 2737         if (!err &&
 2738             (valid & (FUSE_SET_ATTR_ATIME | FUSE_SET_ATTR_MTIME))) {
 2739             struct timespec tv[2];
 2740 
 2741             tv[0].tv_sec = 0;
 2742             tv[1].tv_sec = 0;
 2743             tv[0].tv_nsec = UTIME_OMIT;
 2744             tv[1].tv_nsec = UTIME_OMIT;
 2745 
 2746             if (valid & FUSE_SET_ATTR_ATIME_NOW)
 2747                 tv[0].tv_nsec = UTIME_NOW;
 2748             else if (valid & FUSE_SET_ATTR_ATIME)
 2749                 tv[0] = attr->st_atim;
 2750 
 2751             if (valid & FUSE_SET_ATTR_MTIME_NOW)
 2752                 tv[1].tv_nsec = UTIME_NOW;
 2753             else if (valid & FUSE_SET_ATTR_MTIME)
 2754                 tv[1] = attr->st_mtim;
 2755 
 2756             err = fuse_fs_utimens(f->fs, path, tv, fi);
 2757         } else
 2758 #endif
 2759         if (!err &&
 2760             (valid & (FUSE_SET_ATTR_ATIME | FUSE_SET_ATTR_MTIME)) ==
 2761             (FUSE_SET_ATTR_ATIME | FUSE_SET_ATTR_MTIME)) {
 2762             struct timespec tv[2];
 2763             tv[0].tv_sec = attr->st_atime;
 2764             tv[0].tv_nsec = ST_ATIM_NSEC(attr);
 2765             tv[1].tv_sec = attr->st_mtime;
 2766             tv[1].tv_nsec = ST_MTIM_NSEC(attr);
 2767             err = fuse_fs_utimens(f->fs, path, tv, fi);
 2768         }
 2769         if (!err) {
 2770             err = fuse_fs_getattr(f->fs, path, &buf, fi);
 2771         }
 2772         fuse_finish_interrupt(f, req, &d);
 2773         free_path(f, ino, path);
 2774     }
 2775     if (!err) {
 2776         if (f->conf.auto_cache) {
 2777             pthread_mutex_lock(&f->lock);
 2778             update_stat(get_node(f, ino), &buf);
 2779             pthread_mutex_unlock(&f->lock);
 2780         }
 2781         set_stat(f, ino, &buf);
 2782         fuse_reply_attr(req, &buf, f->conf.attr_timeout);
 2783     } else
 2784         reply_err(req, err);
 2785 }
 2786 
 2787 static void fuse_lib_access(fuse_req_t req, fuse_ino_t ino, int mask)
 2788 {
 2789     struct fuse *f = req_fuse_prepare(req);
 2790     char *path;
 2791     int err;
 2792 
 2793     err = get_path(f, ino, &path);
 2794     if (!err) {
 2795         struct fuse_intr_data d;
 2796 
 2797         fuse_prepare_interrupt(f, req, &d);
 2798         err = fuse_fs_access(f->fs, path, mask);
 2799         fuse_finish_interrupt(f, req, &d);
 2800         free_path(f, ino, path);
 2801     }
 2802     reply_err(req, err);
 2803 }
 2804 
 2805 static void fuse_lib_readlink(fuse_req_t req, fuse_ino_t ino)
 2806 {
 2807     struct fuse *f = req_fuse_prepare(req);
 2808     char linkname[PATH_MAX + 1];
 2809     char *path;
 2810     int err;
 2811 
 2812     err = get_path(f, ino, &path);
 2813     if (!err) {
 2814         struct fuse_intr_data d;
 2815         fuse_prepare_interrupt(f, req, &d);
 2816         err = fuse_fs_readlink(f->fs, path, linkname, sizeof(linkname));
 2817         fuse_finish_interrupt(f, req, &d);
 2818         free_path(f, ino, path);
 2819     }
 2820     if (!err) {
 2821         linkname[PATH_MAX] = '\0';
 2822         fuse_reply_readlink(req, linkname);
 2823     } else
 2824         reply_err(req, err);
 2825 }
 2826 
 2827 static void fuse_lib_mknod(fuse_req_t req, fuse_ino_t parent, const char *name,
 2828                mode_t mode, dev_t rdev)
 2829 {
 2830     struct fuse *f = req_fuse_prepare(req);
 2831     struct fuse_entry_param e;
 2832     char *path;
 2833     int err;
 2834 
 2835     err = get_path_name(f, parent, name, &path);
 2836     if (!err) {
 2837         struct fuse_intr_data d;
 2838 
 2839         fuse_prepare_interrupt(f, req, &d);
 2840         err = -ENOSYS;
 2841         if (S_ISREG(mode)) {
 2842             struct fuse_file_info fi;
 2843 
 2844             memset(&fi, 0, sizeof(fi));
 2845             fi.flags = O_CREAT | O_EXCL | O_WRONLY;
 2846             err = fuse_fs_create(f->fs, path, mode, &fi);
 2847             if (!err) {
 2848                 err = lookup_path(f, parent, name, path, &e,
 2849                           &fi);
 2850                 fuse_fs_release(f->fs, path, &fi);
 2851             }
 2852         }
 2853         if (err == -ENOSYS) {
 2854             err = fuse_fs_mknod(f->fs, path, mode, rdev);
 2855             if (!err)
 2856                 err = lookup_path(f, parent, name, path, &e,
 2857                           NULL);
 2858         }
 2859         fuse_finish_interrupt(f, req, &d);
 2860         free_path(f, parent, path);
 2861     }
 2862     reply_entry(req, &e, err);
 2863 }
 2864 
 2865 static void fuse_lib_mkdir(fuse_req_t req, fuse_ino_t parent, const char *name,
 2866                mode_t mode)
 2867 {
 2868     struct fuse *f = req_fuse_prepare(req);
 2869     struct fuse_entry_param e;
 2870     char *path;
 2871     int err;
 2872 
 2873     err = get_path_name(f, parent, name, &path);
 2874     if (!err) {
 2875         struct fuse_intr_data d;
 2876 
 2877         fuse_prepare_interrupt(f, req, &d);
 2878         err = fuse_fs_mkdir(f->fs, path, mode);
 2879         if (!err)
 2880             err = lookup_path(f, parent, name, path, &e, NULL);
 2881         fuse_finish_interrupt(f, req, &d);
 2882         free_path(f, parent, path);
 2883     }
 2884     reply_entry(req, &e, err);
 2885 }
 2886 
 2887 static void fuse_lib_unlink(fuse_req_t req, fuse_ino_t parent,
 2888                 const char *name)
 2889 {
 2890     struct fuse *f = req_fuse_prepare(req);
 2891     struct node *wnode;
 2892     char *path;
 2893     int err;
 2894 
 2895     err = get_path_wrlock(f, parent, name, &path, &wnode);
 2896     if (!err) {
 2897         struct fuse_intr_data d;
 2898 
 2899         fuse_prepare_interrupt(f, req, &d);
 2900         if (!f->conf.hard_remove && is_open(f, parent, name)) {
 2901             err = hide_node(f, path, parent, name);
 2902         } else {
 2903             err = fuse_fs_unlink(f->fs, path);
 2904             if (!err)
 2905                 remove_node(f, parent, name);
 2906         }
 2907         fuse_finish_interrupt(f, req, &d);
 2908         free_path_wrlock(f, parent, wnode, path);
 2909     }
 2910     reply_err(req, err);
 2911 }
 2912 
 2913 static void fuse_lib_rmdir(fuse_req_t req, fuse_ino_t parent, const char *name)
 2914 {
 2915     struct fuse *f = req_fuse_prepare(req);
 2916     struct node *wnode;
 2917     char *path;
 2918     int err;
 2919 
 2920     err = get_path_wrlock(f, parent, name, &path, &wnode);
 2921     if (!err) {
 2922         struct fuse_intr_data d;
 2923 
 2924         fuse_prepare_interrupt(f, req, &d);
 2925         err = fuse_fs_rmdir(f->fs, path);
 2926         fuse_finish_interrupt(f, req, &d);
 2927         if (!err)
 2928             remove_node(f, parent, name);
 2929         free_path_wrlock(f, parent, wnode, path);
 2930     }
 2931     reply_err(req, err);
 2932 }
 2933 
 2934 static void fuse_lib_symlink(fuse_req_t req, const char *linkname,
 2935                  fuse_ino_t parent, const char *name)
 2936 {
 2937     struct fuse *f = req_fuse_prepare(req);
 2938     struct fuse_entry_param e;
 2939     char *path;
 2940     int err;
 2941 
 2942     err = get_path_name(f, parent, name, &path);
 2943     if (!err) {
 2944         struct fuse_intr_data d;
 2945 
 2946         fuse_prepare_interrupt(f, req, &d);
 2947         err = fuse_fs_symlink(f->fs, linkname, path);
 2948         if (!err)
 2949             err = lookup_path(f, parent, name, path, &e, NULL);
 2950         fuse_finish_interrupt(f, req, &d);
 2951         free_path(f, parent, path);
 2952     }
 2953     reply_entry(req, &e, err);
 2954 }
 2955 
 2956 static void fuse_lib_rename(fuse_req_t req, fuse_ino_t olddir,
 2957                 const char *oldname, fuse_ino_t newdir,
 2958                 const char *newname, unsigned int flags)
 2959 {
 2960     struct fuse *f = req_fuse_prepare(req);
 2961     char *oldpath;
 2962     char *newpath;
 2963     struct node *wnode1;
 2964     struct node *wnode2;
 2965     int err;
 2966 
 2967     err = get_path2(f, olddir, oldname, newdir, newname,
 2968             &oldpath, &newpath, &wnode1, &wnode2);
 2969     if (!err) {
 2970         struct fuse_intr_data d;
 2971         err = 0;
 2972         fuse_prepare_interrupt(f, req, &d);
 2973         if (!f->conf.hard_remove && !(flags & RENAME_EXCHANGE) &&
 2974             is_open(f, newdir, newname))
 2975             err = hide_node(f, newpath, newdir, newname);
 2976         if (!err) {
 2977             err = fuse_fs_rename(f->fs, oldpath, newpath, flags);
 2978             if (!err) {
 2979                 if (flags & RENAME_EXCHANGE) {
 2980                     err = exchange_node(f, olddir, oldname,
 2981                                 newdir, newname);
 2982                 } else {
 2983                     err = rename_node(f, olddir, oldname,
 2984                               newdir, newname, 0);
 2985                 }
 2986             }
 2987         }
 2988         fuse_finish_interrupt(f, req, &d);
 2989         free_path2(f, olddir, newdir, wnode1, wnode2, oldpath, newpath);
 2990     }
 2991     reply_err(req, err);
 2992 }
 2993 
 2994 static void fuse_lib_link(fuse_req_t req, fuse_ino_t ino, fuse_ino_t newparent,
 2995               const char *newname)
 2996 {
 2997     struct fuse *f = req_fuse_prepare(req);
 2998     struct fuse_entry_param e;
 2999     char *oldpath;
 3000     char *newpath;
 3001     int err;
 3002 
 3003     err = get_path2(f, ino, NULL, newparent, newname,
 3004             &oldpath, &newpath, NULL, NULL);
 3005     if (!err) {
 3006         struct fuse_intr_data d;
 3007 
 3008         fuse_prepare_interrupt(f, req, &d);
 3009         err = fuse_fs_link(f->fs, oldpath, newpath);
 3010         if (!err)
 3011             err = lookup_path(f, newparent, newname, newpath,
 3012                       &e, NULL);
 3013         fuse_finish_interrupt(f, req, &d);
 3014         free_path2(f, ino, newparent, NULL, NULL, oldpath, newpath);
 3015     }
 3016     reply_entry(req, &e, err);
 3017 }
 3018 
 3019 static void fuse_do_release(struct fuse *f, fuse_ino_t ino, const char *path,
 3020                 struct fuse_file_info *fi)
 3021 {
 3022     struct node *node;
 3023     int unlink_hidden = 0;
 3024 
 3025     fuse_fs_release(f->fs, path, fi);
 3026 
 3027     pthread_mutex_lock(&f->lock);
 3028     node = get_node(f, ino);
 3029     assert(node->open_count > 0);
 3030     --node->open_count;
 3031     if (node->is_hidden && !node->open_count) {
 3032         unlink_hidden = 1;
 3033         node->is_hidden = 0;
 3034     }
 3035     pthread_mutex_unlock(&f->lock);
 3036 
 3037     if(unlink_hidden) {
 3038         if (path) {
 3039             fuse_fs_unlink(f->fs, path);
 3040         } else if (f->conf.nullpath_ok) {
 3041             char *unlinkpath;
 3042 
 3043             if (get_path(f, ino, &unlinkpath) == 0)
 3044                 fuse_fs_unlink(f->fs, unlinkpath);
 3045 
 3046             free_path(f, ino, unlinkpath);
 3047         }
 3048     }
 3049 }
 3050 
 3051 static void fuse_lib_create(fuse_req_t req, fuse_ino_t parent,
 3052                 const char *name, mode_t mode,
 3053                 struct fuse_file_info *fi)
 3054 {
 3055     struct fuse *f = req_fuse_prepare(req);
 3056     struct fuse_intr_data d;
 3057     struct fuse_entry_param e;
 3058     char *path;
 3059     int err;
 3060 
 3061     err = get_path_name(f, parent, name, &path);
 3062     if (!err) {
 3063         fuse_prepare_interrupt(f, req, &d);
 3064         err = fuse_fs_create(f->fs, path, mode, fi);
 3065         if (!err) {
 3066             err = lookup_path(f, parent, name, path, &e, fi);
 3067             if (err)
 3068                 fuse_fs_release(f->fs, path, fi);
 3069             else if (!S_ISREG(e.attr.st_mode)) {
 3070                 err = -EIO;
 3071                 fuse_fs_release(f->fs, path, fi);
 3072                 forget_node(f, e.ino, 1);
 3073             } else {
 3074                 if (f->conf.direct_io)
 3075                     fi->direct_io = 1;
 3076                 if (f->conf.kernel_cache)
 3077                     fi->keep_cache = 1;
 3078 
 3079             }
 3080         }
 3081         fuse_finish_interrupt(f, req, &d);
 3082     }
 3083     if (!err) {
 3084         pthread_mutex_lock(&f->lock);
 3085         get_node(f, e.ino)->open_count++;
 3086         pthread_mutex_unlock(&f->lock);
 3087         if (fuse_reply_create(req, &e, fi) == -ENOENT) {
 3088             /* The open syscall was interrupted, so it
 3089                must be cancelled */
 3090             fuse_do_release(f, e.ino, path, fi);
 3091             forget_node(f, e.ino, 1);
 3092         }
 3093     } else {
 3094         reply_err(req, err);
 3095     }
 3096 
 3097     free_path(f, parent, path);
 3098 }
 3099 
 3100 static double diff_timespec(const struct timespec *t1,
 3101                 const struct timespec *t2)
 3102 {
 3103     return (t1->tv_sec - t2->tv_sec) +
 3104         ((double) t1->tv_nsec - (double) t2->tv_nsec) / 1000000000.0;
 3105 }
 3106 
 3107 static void open_auto_cache(struct fuse *f, fuse_ino_t ino, const char *path,
 3108                 struct fuse_file_info *fi)
 3109 {
 3110     struct node *node;
 3111 
 3112     pthread_mutex_lock(&f->lock);
 3113     node = get_node(f, ino);
 3114     if (node->cache_valid) {
 3115         struct timespec now;
 3116 
 3117         curr_time(&now);
 3118         if (diff_timespec(&now, &node->stat_updated) >
 3119             f->conf.ac_attr_timeout) {
 3120             struct stat stbuf;
 3121             int err;
 3122             pthread_mutex_unlock(&f->lock);
 3123             err = fuse_fs_getattr(f->fs, path, &stbuf, fi);
 3124             pthread_mutex_lock(&f->lock);
 3125             if (!err)
 3126                 update_stat(node, &stbuf);
 3127             else
 3128                 node->cache_valid = 0;
 3129         }
 3130     }
 3131     if (node->cache_valid)
 3132         fi->keep_cache = 1;
 3133 
 3134     node->cache_valid = 1;
 3135     pthread_mutex_unlock(&f->lock);
 3136 }
 3137 
 3138 static void fuse_lib_open(fuse_req_t req, fuse_ino_t ino,
 3139               struct fuse_file_info *fi)
 3140 {
 3141     struct fuse *f = req_fuse_prepare(req);
 3142     struct fuse_intr_data d;
 3143     char *path;
 3144     int err;
 3145 
 3146     err = get_path(f, ino, &path);
 3147     if (!err) {
 3148         fuse_prepare_interrupt(f, req, &d);
 3149         err = fuse_fs_open(f->fs, path, fi);
 3150         if (!err) {
 3151             if (f->conf.direct_io)
 3152                 fi->direct_io = 1;
 3153             if (f->conf.kernel_cache)
 3154                 fi->keep_cache = 1;
 3155 
 3156             if (f->conf.auto_cache)
 3157                 open_auto_cache(f, ino, path, fi);
 3158         }
 3159         fuse_finish_interrupt(f, req, &d);
 3160     }
 3161     if (!err) {
 3162         pthread_mutex_lock(&f->lock);
 3163         get_node(f, ino)->open_count++;
 3164         pthread_mutex_unlock(&f->lock);
 3165         if (fuse_reply_open(req, fi) == -ENOENT) {
 3166             /* The open syscall was interrupted, so it
 3167                must be cancelled */
 3168             fuse_do_release(f, ino, path, fi);
 3169         }
 3170     } else
 3171         reply_err(req, err);
 3172 
 3173     free_path(f, ino, path);
 3174 }
 3175 
 3176 static void fuse_lib_read(fuse_req_t req, fuse_ino_t ino, size_t size,
 3177               off_t off, struct fuse_file_info *fi)
 3178 {
 3179     struct fuse *f = req_fuse_prepare(req);
 3180     struct fuse_bufvec *buf = NULL;
 3181     char *path;
 3182     int res;
 3183 
 3184     res = get_path_nullok(f, ino, &path);
 3185     if (res == 0) {
 3186         struct fuse_intr_data d;
 3187 
 3188         fuse_prepare_interrupt(f, req, &d);
 3189         res = fuse_fs_read_buf(f->fs, path, &buf, size, off, fi);
 3190         fuse_finish_interrupt(f, req, &d);
 3191         free_path(f, ino, path);
 3192     }
 3193 
 3194     if (res == 0)
 3195         fuse_reply_data(req, buf, FUSE_BUF_SPLICE_MOVE);
 3196     else
 3197         reply_err(req, res);
 3198 
 3199     fuse_free_buf(buf);
 3200 }
 3201 
 3202 static void fuse_lib_write_buf(fuse_req_t req, fuse_ino_t ino,
 3203                    struct fuse_bufvec *buf, off_t off,
 3204                    struct fuse_file_info *fi)
 3205 {
 3206     struct fuse *f = req_fuse_prepare(req);
 3207     char *path;
 3208     int res;
 3209 
 3210     res = get_path_nullok(f, ino, &path);
 3211     if (res == 0) {
 3212         struct fuse_intr_data d;
 3213 
 3214         fuse_prepare_interrupt(f, req, &d);
 3215         res = fuse_fs_write_buf(f->fs, path, buf, off, fi);
 3216         fuse_finish_interrupt(f, req, &d);
 3217         free_path(f, ino, path);
 3218     }
 3219 
 3220     if (res >= 0)
 3221         fuse_reply_write(req, res);
 3222     else
 3223         reply_err(req, res);
 3224 }
 3225 
 3226 static void fuse_lib_fsync(fuse_req_t req, fuse_ino_t ino, int datasync,
 3227                struct fuse_file_info *fi)
 3228 {
 3229     struct fuse *f = req_fuse_prepare(req);
 3230     char *path;
 3231     int err;
 3232 
 3233     err = get_path_nullok(f, ino, &path);
 3234     if (!err) {
 3235         struct fuse_intr_data d;
 3236 
 3237         fuse_prepare_interrupt(f, req, &d);
 3238         err = fuse_fs_fsync(f->fs, path, datasync, fi);
 3239         fuse_finish_interrupt(f, req, &d);
 3240         free_path(f, ino, path);
 3241     }
 3242     reply_err(req, err);
 3243 }
 3244 
 3245 static struct fuse_dh *get_dirhandle(const struct fuse_file_info *llfi,
 3246                      struct fuse_file_info *fi)
 3247 {
 3248     struct fuse_dh *dh = (struct fuse_dh *) (uintptr_t) llfi->fh;
 3249     memset(fi, 0, sizeof(struct fuse_file_info));
 3250     fi->fh = dh->fh;
 3251     return dh;
 3252 }
 3253 
 3254 static void fuse_lib_opendir(fuse_req_t req, fuse_ino_t ino,
 3255                  struct fuse_file_info *llfi)
 3256 {
 3257     struct fuse *f = req_fuse_prepare(req);
 3258     struct fuse_intr_data d;
 3259     struct fuse_dh *dh;
 3260     struct fuse_file_info fi;
 3261     char *path;
 3262     int err;
 3263 
 3264     dh = (struct fuse_dh *) malloc(sizeof(struct fuse_dh));
 3265     if (dh == NULL) {
 3266         reply_err(req, -ENOMEM);
 3267         return;
 3268     }
 3269     memset(dh, 0, sizeof(struct fuse_dh));
 3270     dh->fuse = f;
 3271     dh->contents = NULL;
 3272     dh->first = NULL;
 3273     dh->len = 0;
 3274     dh->filled = 0;
 3275     dh->nodeid = ino;
 3276     fuse_mutex_init(&dh->lock);
 3277 
 3278     llfi->fh = (uintptr_t) dh;
 3279 
 3280     memset(&fi, 0, sizeof(fi));
 3281     fi.flags = llfi->flags;
 3282 
 3283     err = get_path(f, ino, &path);
 3284     if (!err) {
 3285         fuse_prepare_interrupt(f, req, &d);
 3286         err = fuse_fs_opendir(f->fs, path, &fi);
 3287         fuse_finish_interrupt(f, req, &d);
 3288         dh->fh = fi.fh;
 3289     }
 3290     if (!err) {
 3291         if (fuse_reply_open(req, llfi) == -ENOENT) {
 3292             /* The opendir syscall was interrupted, so it
 3293                must be cancelled */
 3294             fuse_fs_releasedir(f->fs, path, &fi);
 3295             pthread_mutex_destroy(&dh->lock);
 3296             free(dh);
 3297         }
 3298     } else {
 3299         reply_err(req, err);
 3300         pthread_mutex_destroy(&dh->lock);
 3301         free(dh);
 3302     }
 3303     free_path(f, ino, path);
 3304 }
 3305 
 3306 static int extend_contents(struct fuse_dh *dh, unsigned minsize)
 3307 {
 3308     if (minsize > dh->size) {
 3309         char *newptr;
 3310         unsigned newsize = dh->size;
 3311         if (!newsize)
 3312             newsize = 1024;
 3313         while (newsize < minsize) {
 3314             if (newsize >= 0x80000000)
 3315                 newsize = 0xffffffff;
 3316             else
 3317                 newsize *= 2;
 3318         }
 3319 
 3320         newptr = (char *) realloc(dh->contents, newsize);
 3321         if (!newptr) {
 3322             dh->error = -ENOMEM;
 3323             return -1;
 3324         }
 3325         dh->contents = newptr;
 3326         dh->size = newsize;
 3327     }
 3328     return 0;
 3329 }
 3330 
 3331 static int fuse_add_direntry_to_dh(struct fuse_dh *dh, const char *name,
 3332                    struct stat *st)
 3333 {
 3334     struct fuse_direntry *de;
 3335 
 3336     de = malloc(sizeof(struct fuse_direntry));
 3337     if (!de) {
 3338         dh->error = -ENOMEM;
 3339         return -1;
 3340     }
 3341     de->name = strdup(name);
 3342     if (!de->name) {
 3343         dh->error = -ENOMEM;
 3344         free(de);
 3345         return -1;
 3346     }
 3347     de->stat = *st;
 3348     de->next = NULL;
 3349 
 3350     *dh->last = de;
 3351     dh->last = &de->next;
 3352 
 3353     return 0;
 3354 }
 3355 
 3356 static fuse_ino_t lookup_nodeid(struct fuse *f, fuse_ino_t parent,
 3357                 const char *name)
 3358 {
 3359     struct node *node;
 3360     fuse_ino_t res = FUSE_UNKNOWN_INO;
 3361 
 3362     pthread_mutex_lock(&f->lock);
 3363     node = lookup_node(f, parent, name);
 3364     if (node)
 3365         res = node->nodeid;
 3366     pthread_mutex_unlock(&f->lock);
 3367 
 3368     return res;
 3369 }
 3370 
 3371 static int fill_dir(void *dh_, const char *name, const struct stat *statp,
 3372             off_t off, enum fuse_fill_dir_flags flags)
 3373 {
 3374     struct fuse_dh *dh = (struct fuse_dh *) dh_;
 3375     struct stat stbuf;
 3376 
 3377     if ((flags & ~FUSE_FILL_DIR_PLUS) != 0) {
 3378         dh->error = -EIO;
 3379         return 1;
 3380     }
 3381 
 3382     if (statp)
 3383         stbuf = *statp;
 3384     else {
 3385         memset(&stbuf, 0, sizeof(stbuf));
 3386         stbuf.st_ino = FUSE_UNKNOWN_INO;
 3387     }
 3388 
 3389     if (!dh->fuse->conf.use_ino) {
 3390         stbuf.st_ino = FUSE_UNKNOWN_INO;
 3391         if (dh->fuse->conf.readdir_ino) {
 3392             stbuf.st_ino = (ino_t)
 3393                 lookup_nodeid(dh->fuse, dh->nodeid, name);
 3394         }
 3395     }
 3396 
 3397     if (off) {
 3398         size_t newlen;
 3399 
 3400         if (dh->first) {
 3401             dh->error = -EIO;
 3402             return 1;
 3403         }
 3404 
 3405         if (extend_contents(dh, dh->needlen) == -1)
 3406             return 1;
 3407 
 3408         dh->filled = 0;
 3409         newlen = dh->len +
 3410             fuse_add_direntry(dh->req, dh->contents + dh->len,
 3411                       dh->needlen - dh->len, name,
 3412                       &stbuf, off);
 3413         if (newlen > dh->needlen)
 3414             return 1;
 3415 
 3416         dh->len = newlen;
 3417     } else {
 3418         if (!dh->filled) {
 3419             dh->error = -EIO;
 3420             return 1;
 3421         }
 3422         if (fuse_add_direntry_to_dh(dh, name, &stbuf) == -1)
 3423             return 1;
 3424     }
 3425     return 0;
 3426 }
 3427 
 3428 static int is_dot_or_dotdot(const char *name)
 3429 {
 3430     return name[0] == '.' && (name[1] == '\0' ||
 3431                   (name[1] == '.' && name[2] == '\0'));
 3432 }
 3433 
 3434 static int fill_dir_plus(void *dh_, const char *name, const struct stat *statp,
 3435              off_t off, enum fuse_fill_dir_flags flags)
 3436 {
 3437     struct fuse_dh *dh = (struct fuse_dh *) dh_;
 3438     struct fuse_entry_param e = {
 3439         /* ino=0 tells the kernel to ignore readdirplus stat info */
 3440         .ino = 0,
 3441     };
 3442     struct fuse *f = dh->fuse;
 3443     int res;
 3444 
 3445     if ((flags & ~FUSE_FILL_DIR_PLUS) != 0) {
 3446         dh->error = -EIO;
 3447         return 1;
 3448     }
 3449 
 3450     if (off && statp && (flags & FUSE_FILL_DIR_PLUS)) {
 3451         e.attr = *statp;
 3452 
 3453         if (!is_dot_or_dotdot(name)) {
 3454             res = do_lookup(f, dh->nodeid, name, &e);
 3455             if (res) {
 3456                 dh->error = res;
 3457                 return 1;
 3458             }
 3459         }
 3460     } else {
 3461         e.attr.st_ino = FUSE_UNKNOWN_INO;
 3462         if (!f->conf.use_ino && f->conf.readdir_ino) {
 3463             e.attr.st_ino = (ino_t)
 3464                 lookup_nodeid(f, dh->nodeid, name);
 3465         }
 3466     }
 3467 
 3468     if (off) {
 3469         size_t newlen;
 3470 
 3471         if (dh->first) {
 3472             dh->error = -EIO;
 3473             return 1;
 3474         }
 3475         if (extend_contents(dh, dh->needlen) == -1)
 3476             return 1;
 3477 
 3478         dh->filled = 0;
 3479         newlen = dh->len +
 3480             fuse_add_direntry_plus(dh->req, dh->contents + dh->len,
 3481                            dh->needlen - dh->len, name,
 3482                            &e, off);
 3483         if (newlen > dh->needlen)
 3484             return 1;
 3485         dh->len = newlen;
 3486     } else {
 3487         if (!dh->filled) {
 3488             dh->error = -EIO;
 3489             return 1;
 3490         }
 3491         if (fuse_add_direntry_to_dh(dh, name, &e.attr) == -1)
 3492             return 1;
 3493     }
 3494 
 3495     return 0;
 3496 }
 3497 
 3498 static void free_direntries(struct fuse_direntry *de)
 3499 {
 3500     while (de) {
 3501         struct fuse_direntry *next = de->next;
 3502         free(de->name);
 3503         free(de);
 3504         de = next;
 3505     }
 3506 }
 3507 
 3508 static int readdir_fill(struct fuse *f, fuse_req_t req, fuse_ino_t ino,
 3509             size_t size, off_t off, struct fuse_dh *dh,
 3510             struct fuse_file_info *fi,
 3511             enum fuse_readdir_flags flags)
 3512 {
 3513     char *path;
 3514     int err;
 3515 
 3516     if (f->fs->op.readdir)
 3517         err = get_path_nullok(f, ino, &path);
 3518     else
 3519         err = get_path(f, ino, &path);
 3520     if (!err) {
 3521         struct fuse_intr_data d;
 3522         fuse_fill_dir_t filler = fill_dir;
 3523 
 3524         if (flags & FUSE_READDIR_PLUS)
 3525             filler = fill_dir_plus;
 3526 
 3527         free_direntries(dh->first);
 3528         dh->first = NULL;
 3529         dh->last = &dh->first;
 3530         dh->len = 0;
 3531         dh->error = 0;
 3532         dh->needlen = size;
 3533         dh->filled = 1;
 3534         dh->req = req;
 3535         fuse_prepare_interrupt(f, req, &d);
 3536         err = fuse_fs_readdir(f->fs, path, dh, filler, off, fi, flags);
 3537         fuse_finish_interrupt(f, req, &d);
 3538         dh->req = NULL;
 3539         if (!err)
 3540             err = dh->error;
 3541         if (err)
 3542             dh->filled = 0;
 3543         free_path(f, ino, path);
 3544     }
 3545     return err;
 3546 }
 3547 
 3548 static int readdir_fill_from_list(fuse_req_t req, struct fuse_dh *dh,
 3549                   off_t off, enum fuse_readdir_flags flags)
 3550 {
 3551     off_t pos;
 3552     struct fuse_direntry *de = dh->first;
 3553 
 3554     dh->len = 0;
 3555 
 3556     if (extend_contents(dh, dh->needlen) == -1)
 3557         return dh->error;
 3558 
 3559     for (pos = 0; pos < off; pos++) {
 3560         if (!de)
 3561             break;
 3562 
 3563         de = de->next;
 3564     }
 3565     while (de) {
 3566         char *p = dh->contents + dh->len;
 3567         unsigned rem = dh->needlen - dh->len;
 3568         unsigned thislen;
 3569         unsigned newlen;
 3570         pos++;
 3571 
 3572         if (flags & FUSE_READDIR_PLUS) {
 3573             struct fuse_entry_param e = {
 3574                 .ino = 0,
 3575                 .attr = de->stat,
 3576             };
 3577             thislen = fuse_add_direntry_plus(req, p, rem,
 3578                              de->name, &e, pos);
 3579         } else {
 3580             thislen = fuse_add_direntry(req, p, rem,
 3581                             de->name, &de->stat, pos);
 3582         }
 3583         newlen = dh->len + thislen;
 3584         if (newlen > dh->needlen)
 3585             break;
 3586         dh->len = newlen;
 3587         de = de->next;
 3588     }
 3589     return 0;
 3590 }
 3591 
 3592 static void fuse_readdir_common(fuse_req_t req, fuse_ino_t ino, size_t size,
 3593                 off_t off, struct fuse_file_info *llfi,
 3594                 enum fuse_readdir_flags flags)
 3595 {
 3596     struct fuse *f = req_fuse_prepare(req);
 3597     struct fuse_file_info fi;
 3598     struct fuse_dh *dh = get_dirhandle(llfi, &fi);
 3599     int err;
 3600 
 3601     pthread_mutex_lock(&dh->lock);
 3602     /* According to SUS, directory contents need to be refreshed on
 3603        rewinddir() */
 3604     if (!off)
 3605         dh->filled = 0;
 3606 
 3607     if (!dh->filled) {
 3608         err = readdir_fill(f, req, ino, size, off, dh, &fi, flags);
 3609         if (err) {
 3610             reply_err(req, err);
 3611             goto out;
 3612         }
 3613     }
 3614     if (dh->filled) {
 3615         dh->needlen = size;
 3616         err = readdir_fill_from_list(req, dh, off, flags);
 3617         if (err) {
 3618             reply_err(req, err);
 3619             goto out;
 3620         }
 3621     }
 3622     fuse_reply_buf(req, dh->contents, dh->len);
 3623 out:
 3624     pthread_mutex_unlock(&dh->lock);
 3625 }
 3626 
 3627 static void fuse_lib_readdir(fuse_req_t req, fuse_ino_t ino, size_t size,
 3628                  off_t off, struct fuse_file_info *llfi)
 3629 {
 3630     fuse_readdir_common(req, ino, size, off, llfi, 0);
 3631 }
 3632 
 3633 static void fuse_lib_readdirplus(fuse_req_t req, fuse_ino_t ino, size_t size,
 3634                   off_t off, struct fuse_file_info *llfi)
 3635 {
 3636     fuse_readdir_common(req, ino, size, off, llfi, FUSE_READDIR_PLUS);
 3637 }
 3638 
 3639 static void fuse_lib_releasedir(fuse_req_t req, fuse_ino_t ino,
 3640                 struct fuse_file_info *llfi)
 3641 {
 3642     struct fuse *f = req_fuse_prepare(req);
 3643     struct fuse_intr_data d;
 3644     struct fuse_file_info fi;
 3645     struct fuse_dh *dh = get_dirhandle(llfi, &fi);
 3646     char *path;
 3647 
 3648     get_path_nullok(f, ino, &path);
 3649 
 3650     fuse_prepare_interrupt(f, req, &d);
 3651     fuse_fs_releasedir(f->fs, path, &fi);
 3652     fuse_finish_interrupt(f, req, &d);
 3653     free_path(f, ino, path);
 3654 
 3655     pthread_mutex_lock(&dh->lock);
 3656     pthread_mutex_unlock(&dh->lock);
 3657     pthread_mutex_destroy(&dh->lock);
 3658     free_direntries(dh->first);
 3659     free(dh->contents);
 3660     free(dh);
 3661     reply_err(req, 0);
 3662 }
 3663 
 3664 static void fuse_lib_fsyncdir(fuse_req_t req, fuse_ino_t ino, int datasync,
 3665                   struct fuse_file_info *llfi)
 3666 {
 3667     struct fuse *f = req_fuse_prepare(req);
 3668     struct fuse_file_info fi;
 3669     char *path;
 3670     int err;
 3671 
 3672     get_dirhandle(llfi, &fi);
 3673 
 3674     err = get_path_nullok(f, ino, &path);
 3675     if (!err) {
 3676         struct fuse_intr_data d;
 3677         fuse_prepare_interrupt(f, req, &d);
 3678         err = fuse_fs_fsyncdir(f->fs, path, datasync, &fi);
 3679         fuse_finish_interrupt(f, req, &d);
 3680         free_path(f, ino, path);
 3681     }
 3682     reply_err(req, err);
 3683 }
 3684 
 3685 static void fuse_lib_statfs(fuse_req_t req, fuse_ino_t ino)
 3686 {
 3687     struct fuse *f = req_fuse_prepare(req);
 3688     struct statvfs buf;
 3689     char *path = NULL;
 3690     int err = 0;
 3691 
 3692     memset(&buf, 0, sizeof(buf));
 3693     if (ino)
 3694         err = get_path(f, ino, &path);
 3695 
 3696     if (!err) {
 3697         struct fuse_intr_data d;
 3698         fuse_prepare_interrupt(f, req, &d);
 3699         err = fuse_fs_statfs(f->fs, path ? path : "/", &buf);
 3700         fuse_finish_interrupt(f, req, &d);
 3701         free_path(f, ino, path);
 3702     }
 3703 
 3704     if (!err)
 3705         fuse_reply_statfs(req, &buf);
 3706     else
 3707         reply_err(req, err);
 3708 }
 3709 
 3710 static void fuse_lib_setxattr(fuse_req_t req, fuse_ino_t ino, const char *name,
 3711                   const char *value, size_t size, int flags)
 3712 {
 3713     struct fuse *f = req_fuse_prepare(req);
 3714     char *path;
 3715     int err;
 3716 
 3717     err = get_path(f, ino, &path);
 3718     if (!err) {
 3719         struct fuse_intr_data d;
 3720         fuse_prepare_interrupt(f, req, &d);
 3721         err = fuse_fs_setxattr(f->fs, path, name, value, size, flags);
 3722         fuse_finish_interrupt(f, req, &d);
 3723         free_path(f, ino, path);
 3724     }
 3725     reply_err(req, err);
 3726 }
 3727 
 3728 static int common_getxattr(struct fuse *f, fuse_req_t req, fuse_ino_t ino,
 3729                const char *name, char *value, size_t size)
 3730 {
 3731     int err;
 3732     char *path;
 3733 
 3734     err = get_path(f, ino, &path);
 3735     if (!err) {
 3736         struct fuse_intr_data d;
 3737         fuse_prepare_interrupt(f, req, &d);
 3738         err = fuse_fs_getxattr(f->fs, path, name, value, size);
 3739         fuse_finish_interrupt(f, req, &d);
 3740         free_path(f, ino, path);
 3741     }
 3742     return err;
 3743 }
 3744 
 3745 static void fuse_lib_getxattr(fuse_req_t req, fuse_ino_t ino, const char *name,
 3746                   size_t size)
 3747 {
 3748     struct fuse *f = req_fuse_prepare(req);
 3749     int res;
 3750 
 3751     if (size) {
 3752         char *value = (char *) malloc(size);
 3753         if (value == NULL) {
 3754             reply_err(req, -ENOMEM);
 3755             return;
 3756         }
 3757         res = common_getxattr(f, req, ino, name, value, size);
 3758         if (res > 0)
 3759             fuse_reply_buf(req, value, res);
 3760         else
 3761             reply_err(req, res);
 3762         free(value);
 3763     } else {
 3764         res = common_getxattr(f, req, ino, name, NULL, 0);
 3765         if (res >= 0)
 3766             fuse_reply_xattr(req, res);
 3767         else
 3768             reply_err(req, res);
 3769     }
 3770 }
 3771 
 3772 static int common_listxattr(struct fuse *f, fuse_req_t req, fuse_ino_t ino,
 3773                 char *list, size_t size)
 3774 {
 3775     char *path;
 3776     int err;
 3777 
 3778     err = get_path(f, ino, &path);
 3779     if (!err) {
 3780         struct fuse_intr_data d;
 3781         fuse_prepare_interrupt(f, req, &d);
 3782         err = fuse_fs_listxattr(f->fs, path, list, size);
 3783         fuse_finish_interrupt(f, req, &d);
 3784         free_path(f, ino, path);
 3785     }
 3786     return err;
 3787 }
 3788 
 3789 static void fuse_lib_listxattr(fuse_req_t req, fuse_ino_t ino, size_t size)
 3790 {
 3791     struct fuse *f = req_fuse_prepare(req);
 3792     int res;
 3793 
 3794     if (size) {
 3795         char *list = (char *) malloc(size);
 3796         if (list == NULL) {
 3797             reply_err(req, -ENOMEM);
 3798             return;
 3799         }
 3800         res = common_listxattr(f, req, ino, list, size);
 3801         if (res > 0)
 3802             fuse_reply_buf(req, list, res);
 3803         else
 3804             reply_err(req, res);
 3805         free(list);
 3806     } else {
 3807         res = common_listxattr(f, req, ino, NULL, 0);
 3808         if (res >= 0)
 3809             fuse_reply_xattr(req, res);
 3810         else
 3811             reply_err(req, res);
 3812     }
 3813 }
 3814 
 3815 static void fuse_lib_removexattr(fuse_req_t req, fuse_ino_t ino,
 3816                  const char *name)
 3817 {
 3818     struct fuse *f = req_fuse_prepare(req);
 3819     char *path;
 3820     int err;
 3821 
 3822     err = get_path(f, ino, &path);
 3823     if (!err) {
 3824         struct fuse_intr_data d;
 3825         fuse_prepare_interrupt(f, req, &d);
 3826         err = fuse_fs_removexattr(f->fs, path, name);
 3827         fuse_finish_interrupt(f, req, &d);
 3828         free_path(f, ino, path);
 3829     }
 3830     reply_err(req, err);
 3831 }
 3832 
 3833 static struct lock *locks_conflict(struct node *node, const struct lock *lock)
 3834 {
 3835     struct lock *l;
 3836 
 3837     for (l = node->locks; l; l = l->next)
 3838         if (l->owner != lock->owner &&
 3839             lock->start <= l->end && l->start <= lock->end &&
 3840             (l->type == F_WRLCK || lock->type == F_WRLCK))
 3841             break;
 3842 
 3843     return l;
 3844 }
 3845 
 3846 static void delete_lock(struct lock **lockp)
 3847 {
 3848     struct lock *l = *lockp;
 3849     *lockp = l->next;
 3850     free(l);
 3851 }
 3852 
 3853 static void insert_lock(struct lock **pos, struct lock *lock)
 3854 {
 3855     lock->next = *pos;
 3856     *pos = lock;
 3857 }
 3858 
 3859 static int locks_insert(struct node *node, struct lock *lock)
 3860 {
 3861     struct lock **lp;
 3862     struct lock *newl1 = NULL;
 3863     struct lock *newl2 = NULL;
 3864 
 3865     if (lock->type != F_UNLCK || lock->start != 0 ||
 3866         lock->end != OFFSET_MAX) {
 3867         newl1 = malloc(sizeof(struct lock));
 3868         newl2 = malloc(sizeof(struct lock));
 3869 
 3870         if (!newl1 || !newl2) {
 3871             free(newl1);
 3872             free(newl2);
 3873             return -ENOLCK;
 3874         }
 3875     }
 3876 
 3877     for (lp = &node->locks; *lp;) {
 3878         struct lock *l = *lp;
 3879         if (l->owner != lock->owner)
 3880             goto skip;
 3881 
 3882         if (lock->type == l->type) {
 3883             if (l->end < lock->start - 1)
 3884                 goto skip;
 3885             if (lock->end < l->start - 1)
 3886                 break;
 3887             if (l->start <= lock->start && lock->end <= l->end)
 3888                 goto out;
 3889             if (l->start < lock->start)
 3890                 lock->start = l->start;
 3891             if (lock->end < l->end)
 3892                 lock->end = l->end;
 3893             goto delete;
 3894         } else {
 3895             if (l->end < lock->start)
 3896                 goto skip;
 3897             if (lock->end < l->start)
 3898                 break;
 3899             if (lock->start <= l->start && l->end <= lock->end)
 3900                 goto delete;
 3901             if (l->end <= lock->end) {
 3902                 l->end = lock->start - 1;
 3903                 goto skip;
 3904             }
 3905             if (lock->start <= l->start) {
 3906                 l->start = lock->end + 1;
 3907                 break;
 3908             }
 3909             *newl2 = *l;
 3910             newl2->start = lock->end + 1;
 3911             l->end = lock->start - 1;
 3912             insert_lock(&l->next, newl2);
 3913             newl2 = NULL;
 3914         }
 3915     skip:
 3916         lp = &l->next;
 3917         continue;
 3918 
 3919     delete:
 3920         delete_lock(lp);
 3921     }
 3922     if (lock->type != F_UNLCK) {
 3923         *newl1 = *lock;
 3924         insert_lock(lp, newl1);
 3925         newl1 = NULL;
 3926     }
 3927 out:
 3928     free(newl1);
 3929     free(newl2);
 3930     return 0;
 3931 }
 3932 
 3933 static void flock_to_lock(struct flock *flock, struct lock *lock)
 3934 {
 3935     memset(lock, 0, sizeof(struct lock));
 3936     lock->type = flock->l_type;
 3937     lock->start = flock->l_start;
 3938     lock->end =
 3939         flock->l_len ? flock->l_start + flock->l_len - 1 : OFFSET_MAX;
 3940     lock->pid = flock->l_pid;
 3941 }
 3942 
 3943 static void lock_to_flock(struct lock *lock, struct flock *flock)
 3944 {
 3945     flock->l_type = lock->type;
 3946     flock->l_start = lock->start;
 3947     flock->l_len =
 3948         (lock->end == OFFSET_MAX) ? 0 : lock->end - lock->start + 1;
 3949     flock->l_pid = lock->pid;
 3950 }
 3951 
 3952 static int fuse_flush_common(struct fuse *f, fuse_req_t req, fuse_ino_t ino,
 3953                  const char *path, struct fuse_file_info *fi)
 3954 {
 3955     struct fuse_intr_data d;
 3956     struct flock lock;
 3957     struct lock l;
 3958     int err;
 3959     int errlock;
 3960 
 3961     fuse_prepare_interrupt(f, req, &d);
 3962     memset(&lock, 0, sizeof(lock));
 3963     lock.l_type = F_UNLCK;
 3964     lock.l_whence = SEEK_SET;
 3965     err = fuse_fs_flush(f->fs, path, fi);
 3966     errlock = fuse_fs_lock(f->fs, path, fi, F_SETLK, &lock);
 3967     fuse_finish_interrupt(f, req, &d);
 3968 
 3969     if (errlock != -ENOSYS) {
 3970         flock_to_lock(&lock, &l);
 3971         l.owner = fi->lock_owner;
 3972         pthread_mutex_lock(&f->lock);
 3973         locks_insert(get_node(f, ino), &l);
 3974         pthread_mutex_unlock(&f->lock);
 3975 
 3976         /* if op.lock() is defined FLUSH is needed regardless
 3977            of op.flush() */
 3978         if (err == -ENOSYS)
 3979             err = 0;
 3980     }
 3981     return err;
 3982 }
 3983 
 3984 static void fuse_lib_release(fuse_req_t req, fuse_ino_t ino,
 3985                  struct fuse_file_info *fi)
 3986 {
 3987     struct fuse *f = req_fuse_prepare(req);
 3988     struct fuse_intr_data d;
 3989     char *path;
 3990     int err = 0;
 3991 
 3992     get_path_nullok(f, ino, &path);
 3993     if (fi->flush) {
 3994         err = fuse_flush_common(f, req, ino, path, fi);
 3995         if (err == -ENOSYS)
 3996             err = 0;
 3997     }
 3998 
 3999     fuse_prepare_interrupt(f, req, &d);
 4000     fuse_do_release(f, ino, path, fi);
 4001     fuse_finish_interrupt(f, req, &d);
 4002     free_path(f, ino, path);
 4003 
 4004     reply_err(req, err);
 4005 }
 4006 
 4007 static void fuse_lib_flush(fuse_req_t req, fuse_ino_t ino,
 4008                struct fuse_file_info *fi)
 4009 {
 4010     struct fuse *f = req_fuse_prepare(req);
 4011     char *path;
 4012     int err;
 4013 
 4014     get_path_nullok(f, ino, &path);
 4015     err = fuse_flush_common(f, req, ino, path, fi);
 4016     free_path(f, ino, path);
 4017 
 4018     reply_err(req, err);
 4019 }
 4020 
 4021 static int fuse_lock_common(fuse_req_t req, fuse_ino_t ino,
 4022                 struct fuse_file_info *fi, struct flock *lock,
 4023                 int cmd)
 4024 {
 4025     struct fuse *f = req_fuse_prepare(req);
 4026     char *path;
 4027     int err;
 4028 
 4029     err = get_path_nullok(f, ino, &path);
 4030     if (!err) {
 4031         struct fuse_intr_data d;
 4032         fuse_prepare_interrupt(f, req, &d);
 4033         err = fuse_fs_lock(f->fs, path, fi, cmd, lock);
 4034         fuse_finish_interrupt(f, req, &d);
 4035         free_path(f, ino, path);
 4036     }
 4037     return err;
 4038 }
 4039 
 4040 static void fuse_lib_getlk(fuse_req_t req, fuse_ino_t ino,
 4041                struct fuse_file_info *fi, struct flock *lock)
 4042 {
 4043     int err;
 4044     struct lock l;
 4045     struct lock *conflict;
 4046     struct fuse *f = req_fuse(req);
 4047 
 4048     flock_to_lock(lock, &l);
 4049     l.owner = fi->lock_owner;
 4050     pthread_mutex_lock(&f->lock);
 4051     conflict = locks_conflict(get_node(f, ino), &l);
 4052     if (conflict)
 4053         lock_to_flock(conflict, lock);
 4054     pthread_mutex_unlock(&f->lock);
 4055     if (!conflict)
 4056         err = fuse_lock_common(req, ino, fi, lock, F_GETLK);
 4057     else
 4058         err = 0;
 4059 
 4060     if (!err)
 4061         fuse_reply_lock(req, lock);
 4062     else
 4063         reply_err(req, err);
 4064 }
 4065 
 4066 static void fuse_lib_setlk(fuse_req_t req, fuse_ino_t ino,
 4067                struct fuse_file_info *fi, struct flock *lock,
 4068                int sleep)
 4069 {
 4070     int err = fuse_lock_common(req, ino, fi, lock,
 4071                    sleep ? F_SETLKW : F_SETLK);
 4072     if (!err) {
 4073         struct fuse *f = req_fuse(req);
 4074         struct lock l;
 4075         flock_to_lock(lock, &l);
 4076         l.owner = fi->lock_owner;
 4077         pthread_mutex_lock(&f->lock);
 4078         locks_insert(get_node(f, ino), &l);
 4079         pthread_mutex_unlock(&f->lock);
 4080     }
 4081     reply_err(req, err);
 4082 }
 4083 
 4084 static void fuse_lib_flock(fuse_req_t req, fuse_ino_t ino,
 4085                struct fuse_file_info *fi, int op)
 4086 {
 4087     struct fuse *f = req_fuse_prepare(req);
 4088     char *path;
 4089     int err;
 4090 
 4091     err = get_path_nullok(f, ino, &path);
 4092     if (err == 0) {
 4093         struct fuse_intr_data d;
 4094         fuse_prepare_interrupt(f, req, &d);
 4095         err = fuse_fs_flock(f->fs, path, fi, op);
 4096         fuse_finish_interrupt(f, req, &d);
 4097         free_path(f, ino, path);
 4098     }
 4099     reply_err(req, err);
 4100 }
 4101 
 4102 static void fuse_lib_bmap(fuse_req_t req, fuse_ino_t ino, size_t blocksize,
 4103               uint64_t idx)
 4104 {
 4105     struct fuse *f = req_fuse_prepare(req);
 4106     struct fuse_intr_data d;
 4107     char *path;
 4108     int err;
 4109 
 4110     err = get_path(f, ino, &path);
 4111     if (!err) {
 4112         fuse_prepare_interrupt(f, req, &d);
 4113         err = fuse_fs_bmap(f->fs, path, blocksize, &idx);
 4114         fuse_finish_interrupt(f, req, &d);
 4115         free_path(f, ino, path);
 4116     }
 4117     if (!err)
 4118         fuse_reply_bmap(req, idx);
 4119     else
 4120         reply_err(req, err);
 4121 }
 4122 
 4123 static void fuse_lib_ioctl(fuse_req_t req, fuse_ino_t ino, int cmd, void *arg,
 4124                struct fuse_file_info *llfi, unsigned int flags,
 4125                const void *in_buf, size_t in_bufsz,
 4126                size_t out_bufsz)
 4127 {
 4128     struct fuse *f = req_fuse_prepare(req);
 4129     struct fuse_intr_data d;
 4130     struct fuse_file_info fi;
 4131     char *path, *out_buf = NULL;
 4132     int err;
 4133 
 4134     err = -EPERM;
 4135     if (flags & FUSE_IOCTL_UNRESTRICTED)
 4136         goto err;
 4137 
 4138     if (flags & FUSE_IOCTL_DIR)
 4139         get_dirhandle(llfi, &fi);
 4140     else
 4141         fi = *llfi;
 4142 
 4143     if (out_bufsz) {
 4144         err = -ENOMEM;
 4145         out_buf = malloc(out_bufsz);
 4146         if (!out_buf)
 4147             goto err;
 4148     }
 4149 
 4150     assert(!in_bufsz || !out_bufsz || in_bufsz == out_bufsz);
 4151     if (out_buf && in_bufsz)
 4152         memcpy(out_buf, in_buf, in_bufsz);
 4153 
 4154     err = get_path_nullok(f, ino, &path);
 4155     if (err)
 4156         goto err;
 4157 
 4158     fuse_prepare_interrupt(f, req, &d);
 4159 
 4160     err = fuse_fs_ioctl(f->fs, path, cmd, arg, &fi, flags,
 4161                 out_buf ?: (void *)in_buf);
 4162 
 4163     fuse_finish_interrupt(f, req, &d);
 4164     free_path(f, ino, path);
 4165 
 4166     fuse_reply_ioctl(req, err, out_buf, out_bufsz);
 4167     goto out;
 4168 err:
 4169     reply_err(req, err);
 4170 out:
 4171     free(out_buf);
 4172 }
 4173 
 4174 static void fuse_lib_poll(fuse_req_t req, fuse_ino_t ino,
 4175               struct fuse_file_info *fi, struct fuse_pollhandle *ph)
 4176 {
 4177     struct fuse *f = req_fuse_prepare(req);
 4178     struct fuse_intr_data d;
 4179     char *path;
 4180     int err;
 4181     unsigned revents = 0;
 4182 
 4183     err = get_path_nullok(f, ino, &path);
 4184     if (!err) {
 4185         fuse_prepare_interrupt(f, req, &d);
 4186         err = fuse_fs_poll(f->fs, path, fi, ph, &revents);
 4187         fuse_finish_interrupt(f, req, &d);
 4188         free_path(f, ino, path);
 4189     }
 4190     if (!err)
 4191         fuse_reply_poll(req, revents);
 4192     else
 4193         reply_err(req, err);
 4194 }
 4195 
 4196 static void fuse_lib_fallocate(fuse_req_t req, fuse_ino_t ino, int mode,
 4197         off_t offset, off_t length, struct fuse_file_info *fi)
 4198 {
 4199     struct fuse *f = req_fuse_prepare(req);
 4200     struct fuse_intr_data d;
 4201     char *path;
 4202     int err;
 4203 
 4204     err = get_path_nullok(f, ino, &path);
 4205     if (!err) {
 4206         fuse_prepare_interrupt(f, req, &d);
 4207         err = fuse_fs_fallocate(f->fs, path, mode, offset, length, fi);
 4208         fuse_finish_interrupt(f, req, &d);
 4209         free_path(f, ino, path);
 4210     }
 4211     reply_err(req, err);
 4212 }
 4213 
 4214 static int clean_delay(struct fuse *f)
 4215 {
 4216     /*
 4217      * This is calculating the delay between clean runs.  To
 4218      * reduce the number of cleans we are doing them 10 times
 4219      * within the remember window.
 4220      */
 4221     int min_sleep = 60;
 4222     int max_sleep = 3600;
 4223     int sleep_time = f->conf.remember / 10;
 4224 
 4225     if (sleep_time > max_sleep)
 4226         return max_sleep;
 4227     if (sleep_time < min_sleep)
 4228         return min_sleep;
 4229     return sleep_time;
 4230 }
 4231 
 4232 int fuse_clean_cache(struct fuse *f)
 4233 {
 4234     struct node_lru *lnode;
 4235     struct list_head *curr, *next;
 4236     struct node *node;
 4237     struct timespec now;
 4238 
 4239     pthread_mutex_lock(&f->lock);
 4240 
 4241     curr_time(&now);
 4242 
 4243     for (curr = f->lru_table.next; curr != &f->lru_table; curr = next) {
 4244         double age;
 4245 
 4246         next = curr->next;
 4247         lnode = list_entry(curr, struct node_lru, lru);
 4248         node = &lnode->node;
 4249 
 4250         age = diff_timespec(&now, &lnode->forget_time);
 4251         if (age <= f->conf.remember)
 4252             break;
 4253 
 4254         assert(node->nlookup == 1);
 4255 
 4256         /* Don't forget active directories */
 4257         if (node->refctr > 1)
 4258             continue;
 4259 
 4260         node->nlookup = 0;
 4261         unhash_name(f, node);
 4262         unref_node(f, node);
 4263     }
 4264     pthread_mutex_unlock(&f->lock);
 4265 
 4266     return clean_delay(f);
 4267 }
 4268 
 4269 static struct fuse_lowlevel_ops fuse_path_ops = {
 4270     .init = fuse_lib_init,
 4271     .destroy = fuse_lib_destroy,
 4272     .lookup = fuse_lib_lookup,
 4273     .forget = fuse_lib_forget,
 4274     .forget_multi = fuse_lib_forget_multi,
 4275     .getattr = fuse_lib_getattr,
 4276     .setattr = fuse_lib_setattr,
 4277     .access = fuse_lib_access,
 4278     .readlink = fuse_lib_readlink,
 4279     .mknod = fuse_lib_mknod,
 4280     .mkdir = fuse_lib_mkdir,
 4281     .unlink = fuse_lib_unlink,
 4282     .rmdir = fuse_lib_rmdir,
 4283     .symlink = fuse_lib_symlink,
 4284     .rename = fuse_lib_rename,
 4285     .link = fuse_lib_link,
 4286     .create = fuse_lib_create,
 4287     .open = fuse_lib_open,
 4288     .read = fuse_lib_read,
 4289     .write_buf = fuse_lib_write_buf,
 4290     .flush = fuse_lib_flush,
 4291     .release = fuse_lib_release,
 4292     .fsync = fuse_lib_fsync,
 4293     .opendir = fuse_lib_opendir,
 4294     .readdir = fuse_lib_readdir,
 4295     .readdirplus = fuse_lib_readdirplus,
 4296     .releasedir = fuse_lib_releasedir,
 4297     .fsyncdir = fuse_lib_fsyncdir,
 4298     .statfs = fuse_lib_statfs,
 4299     .setxattr = fuse_lib_setxattr,
 4300     .getxattr = fuse_lib_getxattr,
 4301     .listxattr = fuse_lib_listxattr,
 4302     .removexattr = fuse_lib_removexattr,
 4303     .getlk = fuse_lib_getlk,
 4304     .setlk = fuse_lib_setlk,
 4305     .flock = fuse_lib_flock,
 4306     .bmap = fuse_lib_bmap,
 4307     .ioctl = fuse_lib_ioctl,
 4308     .poll = fuse_lib_poll,
 4309     .fallocate = fuse_lib_fallocate,
 4310 };
 4311 
 4312 int fuse_notify_poll(struct fuse_pollhandle *ph)
 4313 {
 4314     return fuse_lowlevel_notify_poll(ph);
 4315 }
 4316 
 4317 struct fuse_session *fuse_get_session(struct fuse *f)
 4318 {
 4319     return f->se;
 4320 }
 4321 
 4322 static int fuse_session_loop_remember(struct fuse *f)
 4323 {
 4324     struct fuse_session *se = f->se;
 4325     int res = 0;
 4326     struct timespec now;
 4327     time_t next_clean;
 4328     struct pollfd fds = {
 4329         .fd = se->fd,
 4330         .events = POLLIN
 4331     };
 4332     struct fuse_buf fbuf = {
 4333         .mem = NULL,
 4334     };
 4335 
 4336     curr_time(&now);
 4337     next_clean = now.tv_sec;
 4338     while (!fuse_session_exited(se)) {
 4339         unsigned timeout;
 4340 
 4341         curr_time(&now);
 4342         if (now.tv_sec < next_clean)
 4343             timeout = next_clean - now.tv_sec;
 4344         else
 4345             timeout = 0;
 4346 
 4347         res = poll(&fds, 1, timeout * 1000);
 4348         if (res == -1) {
 4349             if (errno == -EINTR)
 4350                 continue;
 4351             else
 4352                 break;
 4353         } else if (res > 0) {
 4354             res = fuse_session_receive_buf_int(se, &fbuf, NULL);
 4355 
 4356             if (res == -EINTR)
 4357                 continue;
 4358             if (res <= 0)
 4359                 break;
 4360 
 4361             fuse_session_process_buf_int(se, &fbuf, NULL);
 4362         } else {
 4363             timeout = fuse_clean_cache(f);
 4364             curr_time(&now);
 4365             next_clean = now.tv_sec + timeout;
 4366         }
 4367     }
 4368 
 4369     free(fbuf.mem);
 4370     fuse_session_reset(se);
 4371     return res < 0 ? -1 : 0;
 4372 }
 4373 
 4374 int fuse_loop(struct fuse *f)
 4375 {
 4376     if (!f)
 4377         return -1;
 4378 
 4379     if (lru_enabled(f))
 4380         return fuse_session_loop_remember(f);
 4381 
 4382     return fuse_session_loop(f->se);
 4383 }
 4384 
 4385 FUSE_SYMVER(".symver fuse_loop_mt_32,fuse_loop_mt@@FUSE_3.2");
 4386 int fuse_loop_mt_32(struct fuse *f, struct fuse_loop_config *config)
 4387 {
 4388     if (f == NULL)
 4389         return -1;
 4390 
 4391     int res = fuse_start_cleanup_thread(f);
 4392     if (res)
 4393         return -1;
 4394 
 4395     res = fuse_session_loop_mt_32(fuse_get_session(f), config);
 4396     fuse_stop_cleanup_thread(f);
 4397     return res;
 4398 }
 4399 
 4400 int fuse_loop_mt_31(struct fuse *f, int clone_fd);
 4401 FUSE_SYMVER(".symver fuse_loop_mt_31,fuse_loop_mt@FUSE_3.0");
 4402 int fuse_loop_mt_31(struct fuse *f, int clone_fd)
 4403 {
 4404     struct fuse_loop_config config;
 4405     config.clone_fd = clone_fd;
 4406     config.max_idle_threads = 10;
 4407     return fuse_loop_mt_32(f, &config);
 4408 }
 4409 
 4410 void fuse_exit(struct fuse *f)
 4411 {
 4412     fuse_session_exit(f->se);
 4413 }
 4414 
 4415 struct fuse_context *fuse_get_context(void)
 4416 {
 4417     struct fuse_context_i *c = fuse_get_context_internal();
 4418 
 4419     if (c)
 4420         return &c->ctx;
 4421     else
 4422         return NULL;
 4423 }
 4424 
 4425 int fuse_getgroups(int size, gid_t list[])
 4426 {
 4427     struct fuse_context_i *c = fuse_get_context_internal();
 4428     if (!c)
 4429         return -EINVAL;
 4430 
 4431     return fuse_req_getgroups(c->req, size, list);
 4432 }
 4433 
 4434 int fuse_interrupted(void)
 4435 {
 4436     struct fuse_context_i *c = fuse_get_context_internal();
 4437 
 4438     if (c)
 4439         return fuse_req_interrupted(c->req);
 4440     else
 4441         return 0;
 4442 }
 4443 
 4444 int fuse_invalidate_path(struct fuse *f, const char *path) {
 4445     fuse_ino_t ino;
 4446     int err = lookup_path_in_cache(f, path, &ino);
 4447     if (err) {
 4448         return err;
 4449     }
 4450 
 4451     return fuse_lowlevel_notify_inval_inode(f->se, ino, 0, 0);
 4452 }
 4453 
 4454 #define FUSE_LIB_OPT(t, p, v) { t, offsetof(struct fuse_config, p), v }
 4455 
 4456 static const struct fuse_opt fuse_lib_opts[] = {
 4457     FUSE_OPT_KEY("debug",             FUSE_OPT_KEY_KEEP),
 4458     FUSE_OPT_KEY("-d",            FUSE_OPT_KEY_KEEP),
 4459     FUSE_LIB_OPT("debug",             debug, 1),
 4460     FUSE_LIB_OPT("-d",            debug, 1),
 4461     FUSE_LIB_OPT("kernel_cache",          kernel_cache, 1),
 4462     FUSE_LIB_OPT("auto_cache",        auto_cache, 1),
 4463     FUSE_LIB_OPT("noauto_cache",          auto_cache, 0),
 4464     FUSE_LIB_OPT("umask=",            set_mode, 1),
 4465     FUSE_LIB_OPT("umask=%o",          umask, 0),
 4466     FUSE_LIB_OPT("uid=",              set_uid, 1),
 4467     FUSE_LIB_OPT("uid=%d",            uid, 0),
 4468     FUSE_LIB_OPT("gid=",              set_gid, 1),
 4469     FUSE_LIB_OPT("gid=%d",            gid, 0),
 4470     FUSE_LIB_OPT("entry_timeout=%lf",     entry_timeout, 0),
 4471     FUSE_LIB_OPT("attr_timeout=%lf",      attr_timeout, 0),
 4472     FUSE_LIB_OPT("ac_attr_timeout=%lf",   ac_attr_timeout, 0),
 4473     FUSE_LIB_OPT("ac_attr_timeout=",      ac_attr_timeout_set, 1),
 4474     FUSE_LIB_OPT("negative_timeout=%lf",  negative_timeout, 0),
 4475     FUSE_LIB_OPT("noforget",              remember, -1),
 4476     FUSE_LIB_OPT("remember=%u",           remember, 0),
 4477     FUSE_LIB_OPT("modules=%s",        modules, 0),
 4478     FUSE_OPT_END
 4479 };
 4480 
 4481 static int fuse_lib_opt_proc(void *data, const char *arg, int key,
 4482                  struct fuse_args *outargs)
 4483 {
 4484     (void) arg; (void) outargs; (void) data; (void) key;
 4485 
 4486     /* Pass through unknown options */
 4487     return 1;
 4488 }
 4489 
 4490 
 4491 static const struct fuse_opt fuse_help_opts[] = {
 4492     FUSE_LIB_OPT("modules=%s", modules, 1),
 4493     FUSE_OPT_KEY("modules=%s", FUSE_OPT_KEY_KEEP),
 4494     FUSE_OPT_END
 4495 };
 4496 
 4497 static void print_module_help(const char *name,
 4498                   fuse_module_factory_t *fac)
 4499 {
 4500     struct fuse_args a = FUSE_ARGS_INIT(0, NULL);
 4501     if (fuse_opt_add_arg(&a, "") == -1 ||
 4502         fuse_opt_add_arg(&a, "-h") == -1)
 4503         return;
 4504     printf("\nOptions for %s module:\n", name);
 4505     (*fac)(&a, NULL);
 4506 }
 4507 
 4508 void fuse_lib_help(struct fuse_args *args)
 4509 {
 4510     /* These are not all options, but only the ones that
 4511        may be of interest to an end-user */
 4512     printf(
 4513 "    -o kernel_cache        cache files in kernel\n"
 4514 "    -o [no]auto_cache      enable caching based on modification times (off)\n"
 4515 "    -o umask=M             set file permissions (octal)\n"
 4516 "    -o uid=N               set file owner\n"
 4517 "    -o gid=N               set file group\n"
 4518 "    -o entry_timeout=T     cache timeout for names (1.0s)\n"
 4519 "    -o negative_timeout=T  cache timeout for deleted names (0.0s)\n"
 4520 "    -o attr_timeout=T      cache timeout for attributes (1.0s)\n"
 4521 "    -o ac_attr_timeout=T   auto cache timeout for attributes (attr_timeout)\n"
 4522 "    -o noforget            never forget cached inodes\n"
 4523 "    -o remember=T          remember cached inodes for T seconds (0s)\n"
 4524 "    -o modules=M1[:M2...]  names of modules to push onto filesystem stack\n");
 4525 
 4526 
 4527     /* Print low-level help */
 4528     fuse_lowlevel_help();
 4529 
 4530     /* Print help for builtin modules */
 4531     print_module_help("subdir", &fuse_module_subdir_factory);
 4532 #ifdef HAVE_ICONV
 4533     print_module_help("iconv", &fuse_module_iconv_factory);
 4534 #endif
 4535 
 4536     /* Parse command line options in case we need to
 4537        activate more modules */
 4538     struct fuse_config conf = { .modules = NULL };
 4539     if (fuse_opt_parse(args, &conf, fuse_help_opts,
 4540                fuse_lib_opt_proc) == -1
 4541         || !conf.modules)
 4542         return;
 4543     
 4544     char *module;
 4545     char *next;
 4546     struct fuse_module *m;
 4547 
 4548     // Iterate over all modules
 4549     for (module = conf.modules; module; module = next) {
 4550         char *p;
 4551         for (p = module; *p && *p != ':'; p++);
 4552         next = *p ? p + 1 : NULL;
 4553         *p = '\0';
 4554 
 4555         m = fuse_get_module(module);
 4556         if (m)
 4557             print_module_help(module, &m->factory);
 4558     }
 4559 }
 4560 
 4561                       
 4562 
 4563 static int fuse_init_intr_signal(int signum, int *installed)
 4564 {
 4565     struct sigaction old_sa;
 4566 
 4567     if (sigaction(signum, NULL, &old_sa) == -1) {
 4568         perror("fuse: cannot get old signal handler");
 4569         return -1;
 4570     }
 4571 
 4572     if (old_sa.sa_handler == SIG_DFL) {
 4573         struct sigaction sa;
 4574 
 4575         memset(&sa, 0, sizeof(struct sigaction));
 4576         sa.sa_handler = fuse_intr_sighandler;
 4577         sigemptyset(&sa.sa_mask);
 4578 
 4579         if (sigaction(signum, &sa, NULL) == -1) {
 4580             perror("fuse: cannot set interrupt signal handler");
 4581             return -1;
 4582         }
 4583         *installed = 1;
 4584     }
 4585     return 0;
 4586 }
 4587 
 4588 static void fuse_restore_intr_signal(int signum)
 4589 {
 4590     struct sigaction sa;
 4591 
 4592     memset(&sa, 0, sizeof(struct sigaction));
 4593     sa.sa_handler = SIG_DFL;
 4594     sigaction(signum, &sa, NULL);
 4595 }
 4596 
 4597 
 4598 static int fuse_push_module(struct fuse *f, const char *module,
 4599                 struct fuse_args *args)
 4600 {
 4601     struct fuse_fs *fs[2] = { f->fs, NULL };
 4602     struct fuse_fs *newfs;
 4603     struct fuse_module *m = fuse_get_module(module);
 4604 
 4605     if (!m)
 4606         return -1;
 4607 
 4608     newfs = m->factory(args, fs);
 4609     if (!newfs) {
 4610         fuse_put_module(m);
 4611         return -1;
 4612     }
 4613     newfs->m = m;
 4614     f->fs = newfs;
 4615     return 0;
 4616 }
 4617 
 4618 struct fuse_fs *fuse_fs_new(const struct fuse_operations *op, size_t op_size,
 4619                 void *user_data)
 4620 {
 4621     struct fuse_fs *fs;
 4622 
 4623     if (sizeof(struct fuse_operations) < op_size) {
 4624         fprintf(stderr, "fuse: warning: library too old, some operations may not not work\n");
 4625         op_size = sizeof(struct fuse_operations);
 4626     }
 4627 
 4628     fs = (struct fuse_fs *) calloc(1, sizeof(struct fuse_fs));
 4629     if (!fs) {
 4630         fprintf(stderr, "fuse: failed to allocate fuse_fs object\n");
 4631         return NULL;
 4632     }
 4633 
 4634     fs->user_data = user_data;
 4635     if (op)
 4636         memcpy(&fs->op, op, op_size);
 4637     return fs;
 4638 }
 4639 
 4640 static int node_table_init(struct node_table *t)
 4641 {
 4642     t->size = NODE_TABLE_MIN_SIZE;
 4643     t->array = (struct node **) calloc(1, sizeof(struct node *) * t->size);
 4644     if (t->array == NULL) {
 4645         fprintf(stderr, "fuse: memory allocation failed\n");
 4646         return -1;
 4647     }
 4648     t->use = 0;
 4649     t->split = 0;
 4650 
 4651     return 0;
 4652 }
 4653 
 4654 static void *fuse_prune_nodes(void *fuse)
 4655 {
 4656     struct fuse *f = fuse;
 4657     int sleep_time;
 4658 
 4659     while(1) {
 4660         sleep_time = fuse_clean_cache(f);
 4661         sleep(sleep_time);
 4662     }
 4663     return NULL;
 4664 }
 4665 
 4666 int fuse_start_cleanup_thread(struct fuse *f)
 4667 {
 4668     if (lru_enabled(f))
 4669         return fuse_start_thread(&f->prune_thread, fuse_prune_nodes, f);
 4670 
 4671     return 0;
 4672 }
 4673 
 4674 void fuse_stop_cleanup_thread(struct fuse *f)
 4675 {
 4676     if (lru_enabled(f)) {
 4677         pthread_mutex_lock(&f->lock);
 4678         pthread_cancel(f->prune_thread);
 4679         pthread_mutex_unlock(&f->lock);
 4680         pthread_join(f->prune_thread, NULL);
 4681     }
 4682 }
 4683 
 4684 
 4685 FUSE_SYMVER(".symver fuse_new_31,fuse_new@@FUSE_3.1");
 4686 struct fuse *fuse_new_31(struct fuse_args *args,
 4687               const struct fuse_operations *op,
 4688               size_t op_size, void *user_data)
 4689 {
 4690     struct fuse *f;
 4691     struct node *root;
 4692     struct fuse_fs *fs;
 4693     struct fuse_lowlevel_ops llop = fuse_path_ops;
 4694 
 4695     f = (struct fuse *) calloc(1, sizeof(struct fuse));
 4696     if (f == NULL) {
 4697         fprintf(stderr, "fuse: failed to allocate fuse object\n");
 4698         goto out;
 4699     }
 4700 
 4701     f->conf.entry_timeout = 1.0;
 4702     f->conf.attr_timeout = 1.0;
 4703     f->conf.negative_timeout = 0.0;
 4704     f->conf.intr_signal = FUSE_DEFAULT_INTR_SIGNAL;
 4705 
 4706     /* Parse options */
 4707     if (fuse_opt_parse(args, &f->conf, fuse_lib_opts,
 4708                fuse_lib_opt_proc) == -1)
 4709         goto out_free;
 4710 
 4711     pthread_mutex_lock(&fuse_context_lock);
 4712     static int builtin_modules_registered = 0;
 4713     /* Have the builtin modules already been registered? */
 4714     if (builtin_modules_registered == 0) {
 4715         /* If not, register them. */
 4716         fuse_register_module("subdir", fuse_module_subdir_factory, NULL);
 4717 #ifdef HAVE_ICONV
 4718         fuse_register_module("iconv", fuse_module_iconv_factory, NULL);
 4719 #endif
 4720         builtin_modules_registered= 1;
 4721     }
 4722     pthread_mutex_unlock(&fuse_context_lock);
 4723 
 4724     if (fuse_create_context_key() == -1)
 4725         goto out_free;
 4726 
 4727     fs = fuse_fs_new(op, op_size, user_data);
 4728     if (!fs)
 4729         goto out_delete_context_key;
 4730 
 4731     f->fs = fs;
 4732 
 4733     /* Oh f**k, this is ugly! */
 4734     if (!fs->op.lock) {
 4735         llop.getlk = NULL;
 4736         llop.setlk = NULL;
 4737     }
 4738 
 4739     f->pagesize = getpagesize();
 4740     init_list_head(&f->partial_slabs);
 4741     init_list_head(&f->full_slabs);
 4742     init_list_head(&f->lru_table);
 4743 
 4744     if (f->conf.modules) {
 4745         char *module;
 4746         char *next;
 4747 
 4748         for (module = f->conf.modules; module; module = next) {
 4749             char *p;
 4750             for (p = module; *p && *p != ':'; p++);
 4751             next = *p ? p + 1 : NULL;
 4752             *p = '\0';
 4753             if (module[0] &&
 4754                 fuse_push_module(f, module, args) == -1)
 4755                 goto out_free_fs;
 4756         }
 4757     }
 4758 
 4759     if (!f->conf.ac_attr_timeout_set)
 4760         f->conf.ac_attr_timeout = f->conf.attr_timeout;
 4761 
 4762 #if defined(__FreeBSD__) || defined(__NetBSD__)
 4763     /*
 4764      * In FreeBSD, we always use these settings as inode numbers
 4765      * are needed to make getcwd(3) work.
 4766      */
 4767     f->conf.readdir_ino = 1;
 4768 #endif
 4769 
 4770     f->se = fuse_session_new(args, &llop, sizeof(llop), f);
 4771     if (f->se == NULL)
 4772         goto out_free_fs;
 4773 
 4774     if (f->conf.debug) {
 4775         fprintf(stderr, "nullpath_ok: %i\n", f->conf.nullpath_ok);
 4776     }
 4777 
 4778     /* Trace topmost layer by default */
 4779     f->fs->debug = f->conf.debug;
 4780     f->ctr = 0;
 4781     f->generation = 0;
 4782     if (node_table_init(&f->name_table) == -1)
 4783         goto out_free_session;
 4784 
 4785     if (node_table_init(&f->id_table) == -1)
 4786         goto out_free_name_table;
 4787 
 4788     fuse_mutex_init(&f->lock);
 4789 
 4790     root = alloc_node(f);
 4791     if (root == NULL) {
 4792         fprintf(stderr, "fuse: memory allocation failed\n");
 4793         goto out_free_id_table;
 4794     }
 4795     if (lru_enabled(f)) {
 4796         struct node_lru *lnode = node_lru(root);
 4797         init_list_head(&lnode->lru);
 4798     }
 4799 
 4800     strcpy(root->inline_name, "/");
 4801     root->name = root->inline_name;
 4802 
 4803     if (f->conf.intr &&
 4804         fuse_init_intr_signal(f->conf.intr_signal,
 4805                   &f->intr_installed) == -1)
 4806         goto out_free_root;
 4807 
 4808     root->parent = NULL;
 4809     root->nodeid = FUSE_ROOT_ID;
 4810     inc_nlookup(root);
 4811     hash_id(f, root);
 4812 
 4813     return f;
 4814 
 4815 out_free_root:
 4816     free(root);
 4817 out_free_id_table:
 4818     free(f->id_table.array);
 4819 out_free_name_table:
 4820     free(f->name_table.array);
 4821 out_free_session:
 4822     fuse_session_destroy(f->se);
 4823 out_free_fs:
 4824     if (f->fs->m)
 4825         fuse_put_module(f->fs->m);
 4826     free(f->fs);
 4827     free(f->conf.modules);
 4828 out_delete_context_key:
 4829     fuse_delete_context_key();
 4830 out_free:
 4831     free(f);
 4832 out:
 4833     return NULL;
 4834 }
 4835 
 4836 /* Emulates 3.0-style fuse_new(), which processes --help */
 4837 struct fuse *fuse_new_30(struct fuse_args *args, const struct fuse_operations *op,
 4838              size_t op_size, void *private_data);
 4839 FUSE_SYMVER(".symver fuse_new_30,fuse_new@FUSE_3.0");
 4840 struct fuse *fuse_new_30(struct fuse_args *args,
 4841              const struct fuse_operations *op,
 4842              size_t op_size, void *user_data)
 4843 {
 4844     struct fuse_config conf;
 4845     const struct fuse_opt opts[] = {
 4846         FUSE_LIB_OPT("-h", show_help, 1),
 4847         FUSE_LIB_OPT("--help", show_help, 1),
 4848         FUSE_OPT_END
 4849     };
 4850 
 4851     if (fuse_opt_parse(args, &conf, opts,
 4852                fuse_lib_opt_proc) == -1)
 4853         return NULL;
 4854 
 4855     if (conf.show_help) {
 4856         fuse_lib_help(args);
 4857         return NULL;
 4858     } else
 4859         return fuse_new_31(args, op, op_size, user_data);
 4860 }
 4861 
 4862 void fuse_destroy(struct fuse *f)
 4863 {
 4864     size_t i;
 4865 
 4866     if (f->conf.intr && f->intr_installed)
 4867         fuse_restore_intr_signal(f->conf.intr_signal);
 4868 
 4869     if (f->fs) {
 4870         fuse_create_context(f);
 4871 
 4872         for (i = 0; i < f->id_table.size; i++) {
 4873             struct node *node;
 4874 
 4875             for (node = f->id_table.array[i]; node != NULL;
 4876                  node = node->id_next) {
 4877                 if (node->is_hidden) {
 4878                     char *path;
 4879                     if (try_get_path(f, node->nodeid, NULL, &path, NULL, false) == 0) {
 4880                         fuse_fs_unlink(f->fs, path);
 4881                         free(path);
 4882                     }
 4883                 }
 4884             }
 4885         }
 4886     }
 4887     for (i = 0; i < f->id_table.size; i++) {
 4888         struct node *node;
 4889         struct node *next;
 4890 
 4891         for (node = f->id_table.array[i]; node != NULL; node = next) {
 4892             next = node->id_next;
 4893             free_node(f, node);
 4894             f->id_table.use--;
 4895         }
 4896     }
 4897     assert(list_empty(&f->partial_slabs));
 4898     assert(list_empty(&f->full_slabs));
 4899 
 4900     free(f->id_table.array);
 4901     free(f->name_table.array);
 4902     pthread_mutex_destroy(&f->lock);
 4903     fuse_session_destroy(f->se);
 4904     free(f->conf.modules);
 4905     free(f);
 4906     fuse_delete_context_key();
 4907 }
 4908 
 4909 int fuse_mount(struct fuse *f, const char *mountpoint) {
 4910     return fuse_session_mount(fuse_get_session(f), mountpoint);
 4911 }
 4912 
 4913 
 4914 void fuse_unmount(struct fuse *f) {
 4915     return fuse_session_unmount(fuse_get_session(f));
 4916 }
 4917 
 4918 int fuse_version(void)
 4919 {
 4920     return FUSE_VERSION;
 4921 }
 4922 
 4923 const char *fuse_pkgversion(void)
 4924 {
 4925     return PACKAGE_VERSION;
 4926 }