Blame SOURCES/autofs-5.1.7-add-mapent-tree-implementation.patch

29d2b9
autofs-5.1.7 - add mapent tree implementation
29d2b9
29d2b9
From: Ian Kent <raven@themaw.net>
29d2b9
29d2b9
Add a struct mapent basic tree implementation.
29d2b9
29d2b9
Signed-off-by: Ian Kent <raven@themaw.net>
29d2b9
---
29d2b9
 CHANGELOG           |    1 +
29d2b9
 include/automount.h |    4 ++++
29d2b9
 include/mounts.h    |    8 ++++++++
29d2b9
 lib/cache.c         |    9 ++++++++-
29d2b9
 lib/mounts.c        |   50 ++++++++++++++++++++++++++++++++++++++++++++++++++
29d2b9
 5 files changed, 71 insertions(+), 1 deletion(-)
29d2b9
29d2b9
diff --git a/CHANGELOG b/CHANGELOG
29d2b9
index 74571570..8841f72f 100644
29d2b9
--- a/CHANGELOG
29d2b9
+++ b/CHANGELOG
29d2b9
@@ -32,6 +32,7 @@
29d2b9
 - remove unused functions cache_dump_multi() and cache_dump_cache().
29d2b9
 - add a len field to struct autofs_point.
29d2b9
 - make tree implementation data independent.
29d2b9
+- add mapent tree implementation.
29d2b9
 
29d2b9
 25/01/2021 autofs-5.1.7
29d2b9
 - make bind mounts propagation slave by default.
29d2b9
diff --git a/include/automount.h b/include/automount.h
29d2b9
index 34485859..ebc2007f 100644
29d2b9
--- a/include/automount.h
29d2b9
+++ b/include/automount.h
29d2b9
@@ -166,10 +166,14 @@ struct mapent {
29d2b9
 	struct mapent_cache *mc;
29d2b9
 	struct map_source *source;
29d2b9
 	/* Need to know owner if we're a multi-mount */
29d2b9
+	struct tree_node *mm_root;
29d2b9
+	struct tree_node *mm_parent;
29d2b9
+	struct tree_node node;
29d2b9
 	struct mapent *multi;
29d2b9
 	/* Parent nesting point within multi-mount */
29d2b9
 	struct mapent *parent;
29d2b9
 	char *key;
29d2b9
+	size_t len;
29d2b9
 	char *mapent;
29d2b9
 	struct stack *stack;
29d2b9
 	time_t age;
29d2b9
diff --git a/include/mounts.h b/include/mounts.h
29d2b9
index 71d29566..fd7c6183 100644
29d2b9
--- a/include/mounts.h
29d2b9
+++ b/include/mounts.h
29d2b9
@@ -66,6 +66,13 @@ struct tree_node {
29d2b9
 #define MNT_LIST(n)		(container_of(n, struct mnt_list, node))
29d2b9
 #define MNT_LIST_NODE(ptr)	((struct tree_node *) &((struct mnt_list *) ptr)->node)
29d2b9
 
29d2b9
+#define MAPENT(n)		(container_of(n, struct mapent, node))
29d2b9
+#define MAPENT_NODE(p)		((struct tree_node *) &((struct mapent *) p)->node)
29d2b9
+#define MAPENT_ROOT(p)		((struct tree_node *) ((struct mapent *) p)->mm_root)
29d2b9
+#define MAPENT_PARENT(p)	((struct tree_node *) ((struct mapent *) p)->mm_parent)
29d2b9
+#define MAPENT_SET_ROOT(p, r)	{ (((struct mapent *) p)->mm_root = (struct tree_node *) r); }
29d2b9
+#define MAPENT_SET_PARENT(p, n)	{ (((struct mapent *) p)->mm_parent = (struct tree_node *) n); }
29d2b9
+
29d2b9
 typedef struct tree_node *(*tree_new_t) (void *ptr);
29d2b9
 typedef int  (*tree_cmp_t) (struct tree_node *n, void *ptr);
29d2b9
 typedef void (*tree_free_t) (struct tree_node *n);
29d2b9
@@ -161,6 +168,7 @@ unsigned int mnts_has_mounted_mounts(struct autofs_point *ap);
29d2b9
 void mnts_get_expire_list(struct list_head *mnts, struct autofs_point *ap);
29d2b9
 void mnts_put_expire_list(struct list_head *mnts);
29d2b9
 void mnts_set_mounted_mount(struct autofs_point *ap, const char *name, unsigned int flags);
29d2b9
+struct tree_node *tree_mapent_root(struct mapent *me);
29d2b9
 int unlink_mount_tree(struct autofs_point *ap, const char *mp);
29d2b9
 void free_mnt_list(struct mnt_list *list);
29d2b9
 int is_mounted(const char *mp, unsigned int type);
29d2b9
diff --git a/lib/cache.c b/lib/cache.c
29d2b9
index 629c4d0a..6dfaeff5 100644
29d2b9
--- a/lib/cache.c
29d2b9
+++ b/lib/cache.c
29d2b9
@@ -546,17 +546,21 @@ int cache_add(struct mapent_cache *mc, struct map_source *ms, const char *key, c
29d2b9
 	struct mapent *me, *existing = NULL;
29d2b9
 	char *pkey, *pent;
29d2b9
 	u_int32_t hashval = hash(key, mc->size);
29d2b9
+	size_t len;
29d2b9
 
29d2b9
 	me = (struct mapent *) malloc(sizeof(struct mapent));
29d2b9
 	if (!me)
29d2b9
 		return CHE_FAIL;
29d2b9
 
29d2b9
-	pkey = malloc(strlen(key) + 1);
29d2b9
+	len = strlen(key);
29d2b9
+
29d2b9
+	pkey = malloc(len + 1);
29d2b9
 	if (!pkey) {
29d2b9
 		free(me);
29d2b9
 		return CHE_FAIL;
29d2b9
 	}
29d2b9
 	me->key = strcpy(pkey, key);
29d2b9
+	me->len = len;
29d2b9
 
29d2b9
 	if (mapent) {
29d2b9
 		pent = malloc(strlen(mapent) + 1);
29d2b9
@@ -575,6 +579,9 @@ int cache_add(struct mapent_cache *mc, struct map_source *ms, const char *key, c
29d2b9
 	me->status = 0;
29d2b9
 	me->mc = mc;
29d2b9
 	me->source = ms;
29d2b9
+	me->mm_root = NULL;
29d2b9
+	me->mm_parent = NULL;
29d2b9
+	INIT_TREE_NODE(&me->node);
29d2b9
 	INIT_LIST_HEAD(&me->ino_index);
29d2b9
 	INIT_LIST_HEAD(&me->multi_list);
29d2b9
 	me->multi = NULL;
29d2b9
diff --git a/lib/mounts.c b/lib/mounts.c
29d2b9
index a6d1c5a7..40ebf9cf 100644
29d2b9
--- a/lib/mounts.c
29d2b9
+++ b/lib/mounts.c
29d2b9
@@ -79,6 +79,17 @@ static struct tree_ops mnt_ops = {
29d2b9
 };
29d2b9
 static struct tree_ops *tree_mnt_ops = &mnt_ops;
29d2b9
 
29d2b9
+static struct tree_node *tree_mapent_new(void *ptr);
29d2b9
+static int tree_mapent_cmp(struct tree_node *n, void *ptr);
29d2b9
+static void tree_mapent_free(struct tree_node *n);
29d2b9
+
29d2b9
+static struct tree_ops mapent_ops = {
29d2b9
+	.new = tree_mapent_new,
29d2b9
+	.cmp = tree_mapent_cmp,
29d2b9
+	.free = tree_mapent_free,
29d2b9
+};
29d2b9
+static struct tree_ops *tree_mapent_ops = &mapent_ops;
29d2b9
+
29d2b9
 unsigned int linux_version_code(void)
29d2b9
 {
29d2b9
 	struct utsname my_utsname;
29d2b9
@@ -1431,6 +1442,45 @@ void mnts_put_expire_list(struct list_head *mnts)
29d2b9
 	mnts_hash_mutex_unlock();
29d2b9
 }
29d2b9
 
29d2b9
+struct tree_node *tree_mapent_root(struct mapent *me)
29d2b9
+{
29d2b9
+	return tree_root(tree_mapent_ops, me);
29d2b9
+}
29d2b9
+
29d2b9
+static struct tree_node *tree_mapent_new(void *ptr)
29d2b9
+{
29d2b9
+	struct tree_node *n = MAPENT_NODE(ptr);
29d2b9
+
29d2b9
+	n->ops = tree_mapent_ops;
29d2b9
+	n->left = NULL;
29d2b9
+	n->right = NULL;
29d2b9
+
29d2b9
+	return n;
29d2b9
+}
29d2b9
+
29d2b9
+static int tree_mapent_cmp(struct tree_node *n, void *ptr)
29d2b9
+{
29d2b9
+	struct mapent *n_me = MAPENT(n);
29d2b9
+	size_t n_me_len = n_me->len;
29d2b9
+	struct mapent *me = ptr;
29d2b9
+	size_t me_len = me->len;
29d2b9
+
29d2b9
+	if (strncmp(me->key, n_me->key, n_me_len) == 0) {
29d2b9
+		if (me_len < n_me_len)
29d2b9
+			return -1;
29d2b9
+		else if (me_len > n_me_len)
29d2b9
+			return 1;
29d2b9
+	}
29d2b9
+	return strcmp(me->key, n_me->key);
29d2b9
+}
29d2b9
+
29d2b9
+static void tree_mapent_free(struct tree_node *n)
29d2b9
+{
29d2b9
+	n->ops = NULL;
29d2b9
+	n->left = NULL;
29d2b9
+	n->right = NULL;
29d2b9
+}
29d2b9
+
29d2b9
 /* From glibc decode_name() */
29d2b9
 /* Since the values in a line are separated by spaces, a name cannot
29d2b9
  * contain a space.  Therefore some programs encode spaces in names