summaryrefslogtreecommitdiff
path: root/debian/patches/0016-ext2fs-use-librbtree-for-the-nodehash.patch
diff options
context:
space:
mode:
Diffstat (limited to 'debian/patches/0016-ext2fs-use-librbtree-for-the-nodehash.patch')
-rw-r--r--debian/patches/0016-ext2fs-use-librbtree-for-the-nodehash.patch314
1 files changed, 0 insertions, 314 deletions
diff --git a/debian/patches/0016-ext2fs-use-librbtree-for-the-nodehash.patch b/debian/patches/0016-ext2fs-use-librbtree-for-the-nodehash.patch
deleted file mode 100644
index fee4854f..00000000
--- a/debian/patches/0016-ext2fs-use-librbtree-for-the-nodehash.patch
+++ /dev/null
@@ -1,314 +0,0 @@
-From 54e3e8084aad34ddcd74aea215d83eb3f641d248 Mon Sep 17 00:00:00 2001
-From: Justus Winter <4winter@informatik.uni-hamburg.de>
-Date: Wed, 14 May 2014 15:30:19 +0200
-Subject: [PATCH 16/16] ext2fs: use librbtree for the nodehash
-
-Previously, a lookup of a node through nodehash took O(N / INOHSZ).
-With INOHSZ being a constant (512) this is linear in N. Use a
-red-black tree instead, which guarantees a lookup performance in
-O(log N) time.
-
-* ext2fs/inode.c (INOHSZ, INOHASH): Remove.
-(nodehash): Use a red-black tree.
-(node_cmp_lookup, node_cmp_insert, node_get_np): New functions.
-(inode_init): Remove.
-(diskfs_cached_lookup): Adjust accordingly.
-(ifind, diskfs_try_dropping_softrefs, diskfs_node_iterate): Likewise.
-* ext2fs/ext2fs.h (struct disknode): Remove list pointers, add
-red-black tree node. Because we store disknode objects in the tree,
-we also need a pointer to the node object, and the cache_id for
-efficient operations on the rb tree.
-* ext2fs/ext2fs.c (main): Drop inode_init.
----
- ext2fs/Makefile | 2 +-
- ext2fs/ext2fs.c | 2 -
- ext2fs/ext2fs.h | 7 ++--
- ext2fs/inode.c | 124 +++++++++++++++++++++++++++++---------------------------
- 4 files changed, 70 insertions(+), 65 deletions(-)
-
-diff --git a/ext2fs/Makefile b/ext2fs/Makefile
-index 8d2e68c..b075dc0 100644
---- a/ext2fs/Makefile
-+++ b/ext2fs/Makefile
-@@ -23,7 +23,7 @@ target = ext2fs
- SRCS = balloc.c dir.c ext2fs.c getblk.c hyper.c ialloc.c \
- inode.c pager.c pokel.c truncate.c storeinfo.c msg.c xinl.c
- OBJS = $(SRCS:.c=.o)
--HURDLIBS = diskfs pager iohelp fshelp store ports ihash shouldbeinlibc
-+HURDLIBS = diskfs pager iohelp fshelp store ports ihash rbtree shouldbeinlibc
- OTHERLIBS = -lpthread $(and $(HAVE_LIBBZ2),-lbz2) $(and $(HAVE_LIBZ),-lz)
-
- include ../Makeconf
-diff --git a/ext2fs/ext2fs.c b/ext2fs/ext2fs.c
-index 128b6ed..0409dfb 100644
---- a/ext2fs/ext2fs.c
-+++ b/ext2fs/ext2fs.c
-@@ -185,8 +185,6 @@ main (int argc, char **argv)
-
- map_hypermetadata ();
-
-- inode_init ();
--
- /* Set diskfs_root_node to the root inode. */
- err = diskfs_cached_lookup (EXT2_ROOT_INO, &diskfs_root_node);
- if (err)
-diff --git a/ext2fs/ext2fs.h b/ext2fs/ext2fs.h
-index 3422af2..3505bb7 100644
---- a/ext2fs/ext2fs.h
-+++ b/ext2fs/ext2fs.h
-@@ -26,6 +26,7 @@
- #include <hurd/store.h>
- #include <hurd/diskfs.h>
- #include <hurd/ihash.h>
-+#include <hurd/rbtree.h>
- #include <assert.h>
- #include <pthread.h>
- #include <sys/mman.h>
-@@ -155,13 +156,13 @@ clear_bit (unsigned num, char *bitmap)
- /* ext2fs specific per-file data. */
- struct disknode
- {
-+ /* Red-black-tree node for the node cache. */
-+ struct rbtree_node tree_node;
-+
- /* For a directory, this array holds the number of directory entries in
- each DIRBLKSIZE piece of the directory. */
- int *dirents;
-
-- /* Links on hash list. */
-- struct node *hnext, **hprevp;
--
- /* Lock to lock while fiddling with this inode's block allocation info. */
- pthread_rwlock_t alloc_lock;
-
-diff --git a/ext2fs/inode.c b/ext2fs/inode.c
-index 7ec343f..0142bf6 100644
---- a/ext2fs/inode.c
-+++ b/ext2fs/inode.c
-@@ -20,6 +20,7 @@
- Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
-
- #include "ext2fs.h"
-+#include <stddef.h>
- #include <string.h>
- #include <unistd.h>
- #include <stdio.h>
-@@ -39,13 +40,6 @@
- #define UF_IMMUTABLE 0
- #endif
-
--#define INOHSZ 512
--#if ((INOHSZ&(INOHSZ-1)) == 0)
--#define INOHASH(ino) ((ino)&(INOHSZ-1))
--#else
--#define INOHASH(ino) (((unsigned)(ino))%INOHSZ)
--#endif
--
- /* The nodehash is a cache of nodes.
-
- Access to nodehash and nodehash_nr_items is protected by
-@@ -55,23 +49,45 @@
- asked to give up that light reference, we reacquire our lock
- momentarily to check whether someone else reacquired a reference
- through the nodehash. */
--static struct node *nodehash[INOHSZ];
-+static struct rbtree nodehash = RBTREE_INITIALIZER;
- static size_t nodehash_nr_items;
- static pthread_mutex_t nodehash_lock = PTHREAD_MUTEX_INITIALIZER;
-
--static error_t read_node (struct node *np);
-+static inline struct node *
-+node_get_np (const struct rbtree_node *node)
-+{
-+ struct disknode *dn;
-
--pthread_spinlock_t generation_lock = PTHREAD_SPINLOCK_INITIALIZER;
-+ dn = rbtree_entry (node, struct disknode, tree_node);
-
--/* Initialize the inode hash table. */
--void
--inode_init ()
-+ return diskfs_disknode_node (dn);
-+}
-+
-+static inline int
-+node_cmp_lookup (const ino_t inum,
-+ const struct rbtree_node *node)
- {
-- int n;
-- for (n = 0; n < INOHSZ; n++)
-- nodehash[n] = 0;
-+ struct node *np = node_get_np (node);
-+
-+ if (inum == np->cache_id)
-+ return 0;
-+ else if (inum < np->cache_id)
-+ return -1;
-+ else
-+ return 1;
- }
-
-+static inline int
-+node_cmp_insert (const struct rbtree_node *a,
-+ const struct rbtree_node *b)
-+{
-+ return node_cmp_lookup (node_get_np (a)->cache_id, b);
-+}
-+
-+static error_t read_node (struct node *np);
-+
-+pthread_spinlock_t generation_lock = PTHREAD_SPINLOCK_INITIALIZER;
-+
- /* Fetch inode INUM, set *NPP to the node structure;
- gain one user reference and lock the node. */
- error_t
-@@ -79,47 +95,42 @@ diskfs_cached_lookup (ino_t inum, struct node **npp)
- {
- error_t err;
- struct node *np;
-+ struct rbtree_node *node;
-+ unsigned long slot;
- struct disknode *dn;
-
- pthread_mutex_lock (&nodehash_lock);
-- for (np = nodehash[INOHASH(inum)]; np; np = np->dn->hnext)
-- if (np->cache_id == inum)
-- {
-- diskfs_nref (np);
-- pthread_mutex_unlock (&nodehash_lock);
-- pthread_mutex_lock (&np->lock);
-- *npp = np;
-- return 0;
-- }
--
-- /* Format specific data for the new node. */
-- dn = malloc (sizeof (struct disknode));
-- if (! dn)
-+ node = rbtree_lookup_slot (&nodehash, inum, node_cmp_lookup, slot);
-+ if (node != NULL)
-+ {
-+ np = node_get_np (node);
-+ diskfs_nref (np);
-+ pthread_mutex_unlock (&nodehash_lock);
-+ pthread_mutex_lock (&np->lock);
-+ *npp = np;
-+ return 0;
-+ }
-+
-+ /* Create the new node. */
-+ np = diskfs_make_node_alloc (sizeof *dn);
-+ if (np == NULL)
- {
- pthread_mutex_unlock (&nodehash_lock);
- return ENOMEM;
- }
-+ np->cache_id = inum;
-+ dn = diskfs_node_disknode (np);
- dn->dirents = 0;
- dn->dir_idx = 0;
- dn->pager = 0;
- pthread_rwlock_init (&dn->alloc_lock, NULL);
- pokel_init (&dn->indir_pokel, diskfs_disk_pager, disk_cache);
--
-- /* Create the new node. */
-- np = diskfs_make_node (dn);
-- np->cache_id = inum;
--
- pthread_mutex_lock (&np->lock);
-
- /* Put NP in NODEHASH. */
-- dn->hnext = nodehash[INOHASH(inum)];
-- if (dn->hnext)
-- dn->hnext->dn->hprevp = &dn->hnext;
-- dn->hprevp = &nodehash[INOHASH(inum)];
-- nodehash[INOHASH(inum)] = np;
- diskfs_nref_light (np);
-+ rbtree_insert_slot (&nodehash, slot, &dn->tree_node);
- nodehash_nr_items += 1;
--
- pthread_mutex_unlock (&nodehash_lock);
-
- /* Get the contents of NP off disk. */
-@@ -149,16 +160,14 @@ diskfs_cached_lookup (ino_t inum, struct node **npp)
- struct node *
- ifind (ino_t inum)
- {
-- struct node *np;
-+ struct rbtree_node *node;
-
- pthread_mutex_lock (&nodehash_lock);
-- for (np = nodehash[INOHASH(inum)]; np; np = np->dn->hnext)
-+ node = rbtree_lookup (&nodehash, inum, node_cmp_lookup);
-+ if (node != NULL)
- {
-- if (np->cache_id != inum)
-- continue;
--
- pthread_mutex_unlock (&nodehash_lock);
-- return np;
-+ return node_get_np (node);
- }
- assert (0);
- }
-@@ -176,7 +185,6 @@ diskfs_node_norefs (struct node *np)
- pokel_inherit (&global_pokel, &np->dn->indir_pokel);
- pokel_finalize (&np->dn->indir_pokel);
-
-- free (np->dn);
- free (np);
- }
-
-@@ -186,7 +194,7 @@ void
- diskfs_try_dropping_softrefs (struct node *np)
- {
- pthread_mutex_lock (&nodehash_lock);
-- if (np->dn->hnext != NULL)
-+ if (np->cache_id != 0)
- {
- /* Check if someone reacquired a reference through the
- nodehash. */
-@@ -200,11 +208,9 @@ diskfs_try_dropping_softrefs (struct node *np)
- return;
- }
-
-- *np->dn->hprevp = np->dn->hnext;
-- if (np->dn->hnext)
-- np->dn->hnext->dn->hprevp = np->dn->hprevp;
-- np->dn->hnext = NULL;
-+ rbtree_remove (&nodehash, &(diskfs_node_disknode (np))->tree_node);
- nodehash_nr_items -= 1;
-+ np->cache_id = 0;
- diskfs_nrele_light (np);
- }
- pthread_mutex_unlock (&nodehash_lock);
-@@ -581,7 +587,7 @@ error_t
- diskfs_node_iterate (error_t (*fun)(struct node *))
- {
- error_t err = 0;
-- int n;
-+ struct rbtree_node *n;
- size_t num_nodes;
- struct node *node, **node_list, **p;
-
-@@ -605,12 +611,12 @@ diskfs_node_iterate (error_t (*fun)(struct node *))
- }
-
- p = node_list;
-- for (n = 0; n < INOHSZ; n++)
-- for (node = nodehash[n]; node; node = node->dn->hnext)
-- {
-- *p++ = node;
-- diskfs_nref (node);
-- }
-+ for (n = rbtree_first (&nodehash); n; n = rbtree_next (n))
-+ {
-+ node = node_get_np (n);
-+ *p++ = node;
-+ diskfs_nref (node);
-+ }
-
- pthread_mutex_unlock (&nodehash_lock);
-
---
-2.0.0.rc2
-