main: precompute name hash

Signed-off-by: Giuseppe Scrivano <gscrivan@redhat.com>
This commit is contained in:
Giuseppe Scrivano 2019-07-14 23:19:01 +02:00
parent c95961d9cc
commit 87cd8f34fa
No known key found for this signature in database
GPG Key ID: E4730F97F60286ED

48
main.c
View File

@ -174,6 +174,7 @@ struct ovl_node
int lookups; int lookups;
int hidden_dirfd; int hidden_dirfd;
ino_t ino; ino_t ino;
size_t name_hash;
unsigned int present_lowerdir : 1; unsigned int present_lowerdir : 1;
unsigned int do_unlink : 1; unsigned int do_unlink : 1;
@ -875,7 +876,7 @@ static size_t
node_hasher (const void *p, size_t s) node_hasher (const void *p, size_t s)
{ {
struct ovl_node *n = (struct ovl_node *) p; struct ovl_node *n = (struct ovl_node *) p;
return hash_string (n->name, s); return n->name_hash % s;
} }
static bool static bool
@ -884,6 +885,9 @@ node_compare (const void *n1, const void *n2)
struct ovl_node *node1 = (struct ovl_node *) n1; struct ovl_node *node1 = (struct ovl_node *) n1;
struct ovl_node *node2 = (struct ovl_node *) n2; struct ovl_node *node2 = (struct ovl_node *) n2;
if (node1->name_hash != node2->name_hash)
return false;
return strcmp (node1->name, node2->name) == 0 ? true : false; return strcmp (node1->name, node2->name) == 0 ? true : false;
} }
@ -902,19 +906,31 @@ cleanup_node_initp (struct ovl_node **p)
#define cleanup_node_init __attribute__((cleanup (cleanup_node_initp))) #define cleanup_node_init __attribute__((cleanup (cleanup_node_initp)))
static void
node_set_name (struct ovl_node *node, char *name)
{
node->name = name;
if (name == NULL)
node->name_hash = 0;
else
node->name_hash = hash_string (name, SIZE_MAX);
}
static struct ovl_node * static struct ovl_node *
make_whiteout_node (const char *path, const char *name) make_whiteout_node (const char *path, const char *name)
{ {
struct ovl_node *ret_xchg;
cleanup_node_init struct ovl_node *ret = NULL; cleanup_node_init struct ovl_node *ret = NULL;
struct ovl_node *ret_xchg;
char *new_name;
ret = calloc (1, sizeof (*ret)); ret = calloc (1, sizeof (*ret));
if (ret == NULL) if (ret == NULL)
return NULL; return NULL;
ret->name = strdup (name); new_name = strdup (name);
if (ret->name == NULL) if (new_name == NULL)
return NULL; return NULL;
node_set_name (ret, new_name);
ret->path = strdup (path); ret->path = strdup (path);
if (ret->path == NULL) if (ret->path == NULL)
@ -970,6 +986,7 @@ safe_read_xattr (char **ret, int sfd, const char *name, size_t initial_size)
static struct ovl_node * static struct ovl_node *
make_ovl_node (const char *path, struct ovl_layer *layer, const char *name, ino_t ino, bool dir_p, struct ovl_node *parent) make_ovl_node (const char *path, struct ovl_layer *layer, const char *name, ino_t ino, bool dir_p, struct ovl_node *parent)
{ {
char *new_name;
struct ovl_node *ret_xchg; struct ovl_node *ret_xchg;
cleanup_node_init struct ovl_node *ret = NULL; cleanup_node_init struct ovl_node *ret = NULL;
@ -981,9 +998,11 @@ make_ovl_node (const char *path, struct ovl_layer *layer, const char *name, ino_
ret->layer = layer; ret->layer = layer;
ret->ino = ino; ret->ino = ino;
ret->hidden_dirfd = -1; ret->hidden_dirfd = -1;
ret->name = strdup (name);
if (ret->name == NULL) new_name = strdup (name);
if (new_name == NULL)
return NULL; return NULL;
node_set_name (ret, new_name);
if (has_prefix (path, "./") && path[2]) if (has_prefix (path, "./") && path[2])
path += 2; path += 2;
@ -1175,7 +1194,7 @@ load_dir (struct ovl_data *lo, struct ovl_node *n, struct ovl_layer *layer, char
break; break;
} }
key.name = dent->d_name; node_set_name (&key, dent->d_name);
if ((strcmp (dent->d_name, ".") == 0) || strcmp (dent->d_name, "..") == 0) if ((strcmp (dent->d_name, ".") == 0) || strcmp (dent->d_name, "..") == 0)
continue; continue;
@ -1367,7 +1386,7 @@ do_lookup_file (struct ovl_data *lo, fuse_ino_t parent, const char *name)
return NULL; return NULL;
} }
key.name = (char *) name; node_set_name (&key, (char *) name);
node = hash_lookup (pnode->children, &key); node = hash_lookup (pnode->children, &key);
if (node == NULL) if (node == NULL)
{ {
@ -1655,7 +1674,7 @@ create_missing_whiteouts (struct ovl_data *lo, struct ovl_node *node, const char
if (strcmp (dent->d_name, "..") == 0) if (strcmp (dent->d_name, "..") == 0)
continue; continue;
key.name = (char *) dent->d_name; node_set_name (&key, (char *) dent->d_name);
n = hash_lookup (node->children, &key); n = hash_lookup (node->children, &key);
if (n) if (n)
@ -2418,7 +2437,8 @@ do_rm (fuse_req_t req, fuse_ino_t parent, const char *name, bool dirp)
return; return;
} }
key.name = (char *) name; node_set_name (&key, (char *) name);
rm = hash_delete (pnode->children, &key); rm = hash_delete (pnode->children, &key);
if (rm) if (rm)
{ {
@ -3245,8 +3265,8 @@ ovl_rename_exchange (fuse_req_t req, fuse_ino_t parent, const char *name,
destnode->path = tmp; destnode->path = tmp;
tmp = node->name; tmp = node->name;
node->name = destnode->name; node_set_name (node, destnode->name);
destnode->name = tmp; node_set_name (destnode, tmp);
node = insert_node (destpnode, node, true); node = insert_node (destpnode, node, true);
if (node == NULL) if (node == NULL)
@ -3344,7 +3364,7 @@ ovl_rename_direct (fuse_req_t req, fuse_ino_t parent, const char *name,
goto error; goto error;
destfd = ret; destfd = ret;
key.name = (char *) newname; node_set_name (&key, (char *) newname);
destnode = hash_lookup (destpnode->children, &key); destnode = hash_lookup (destpnode->children, &key);
node = get_node_up (lo, node); node = get_node_up (lo, node);
@ -3453,7 +3473,7 @@ ovl_rename_direct (fuse_req_t req, fuse_ino_t parent, const char *name,
hash_delete (pnode->children, node); hash_delete (pnode->children, node);
free (node->name); free (node->name);
node->name = strdup (newname); node_set_name (node, strdup (newname));
if (node->name == NULL) if (node->name == NULL)
goto error; goto error;