203 lines
4.3 KiB
Diff
203 lines
4.3 KiB
Diff
autofs-5.1.6 - add a hash index to mnt_list
|
|
|
|
From: Ian Kent <raven@themaw.net>
|
|
|
|
Add a hash index (and utility functions) to struct mnt_list.
|
|
|
|
Signed-off-by: Ian Kent <raven@themaw.net>
|
|
---
|
|
CHANGELOG | 1
|
|
include/mounts.h | 8 +++
|
|
lib/mounts.c | 135 +++++++++++++++++++++++++++++++++++++++++++++++++++++++
|
|
3 files changed, 144 insertions(+)
|
|
|
|
--- autofs-5.1.4.orig/CHANGELOG
|
|
+++ autofs-5.1.4/CHANGELOG
|
|
@@ -121,6 +121,7 @@ xx/xx/2018 autofs-5.1.5
|
|
- change mountpoint to mp in struct ext_mount.
|
|
- make external mounts independent of amd_entry.
|
|
- make external mounts use simpler hashtable.
|
|
+- add a hash index to mnt_list.
|
|
|
|
19/12/2017 autofs-5.1.4
|
|
- fix spec file url.
|
|
--- autofs-5.1.4.orig/include/mounts.h
|
|
+++ autofs-5.1.4/include/mounts.h
|
|
@@ -54,10 +54,16 @@ struct mapent;
|
|
struct mnt_list {
|
|
char *mp;
|
|
unsigned int flags;
|
|
+
|
|
+ /* Hash of all mounts */
|
|
+ struct hlist_node hash;
|
|
+ unsigned int ref;
|
|
+
|
|
/*
|
|
* List operations ie. get_mnt_list.
|
|
*/
|
|
struct mnt_list *next;
|
|
+
|
|
/*
|
|
* Tree operations ie. tree_make_tree,
|
|
* tree_get_mnt_list etc.
|
|
@@ -100,6 +106,8 @@ char *make_mnt_name_string(char *path);
|
|
int ext_mount_add(const char *, const char *);
|
|
int ext_mount_remove(const char *);
|
|
int ext_mount_inuse(const char *);
|
|
+struct mnt_list *mnts_lookup_mount(const char *mp);
|
|
+void mnts_put_mount(struct mnt_list *mnt);
|
|
struct mnt_list *get_mnt_list(const char *path, int include);
|
|
int unlink_mount_tree(struct autofs_point *ap, const char *mp);
|
|
void free_mnt_list(struct mnt_list *list);
|
|
--- autofs-5.1.4.orig/lib/mounts.c
|
|
+++ autofs-5.1.4/lib/mounts.c
|
|
@@ -63,6 +63,11 @@ struct ext_mount {
|
|
static DEFINE_HASHTABLE(ext_mounts_hash, EXT_MOUNTS_HASH_BITS);
|
|
static pthread_mutex_t ext_mount_hash_mutex = PTHREAD_MUTEX_INITIALIZER;
|
|
|
|
+#define MNTS_HASH_BITS 7
|
|
+
|
|
+static DEFINE_HASHTABLE(mnts_hash, MNTS_HASH_BITS);
|
|
+static pthread_mutex_t mnts_hash_mutex = PTHREAD_MUTEX_INITIALIZER;
|
|
+
|
|
unsigned int linux_version_code(void)
|
|
{
|
|
struct utsname my_utsname;
|
|
@@ -832,6 +837,136 @@ done:
|
|
return ret;
|
|
}
|
|
|
|
+static void mnts_hash_mutex_lock(void)
|
|
+{
|
|
+ int status = pthread_mutex_lock(&mnts_hash_mutex);
|
|
+ if (status)
|
|
+ fatal(status);
|
|
+}
|
|
+
|
|
+static void mnts_hash_mutex_unlock(void)
|
|
+{
|
|
+ int status = pthread_mutex_unlock(&mnts_hash_mutex);
|
|
+ if (status)
|
|
+ fatal(status);
|
|
+}
|
|
+
|
|
+static struct mnt_list *mnts_lookup(const char *mp)
|
|
+{
|
|
+ uint32_t hval = hash(mp, HASH_SIZE(mnts_hash));
|
|
+ struct mnt_list *this;
|
|
+
|
|
+ if (hlist_empty(&mnts_hash[hval]))
|
|
+ return NULL;
|
|
+
|
|
+ hlist_for_each_entry(this, &mnts_hash[hval], hash) {
|
|
+ if (!strcmp(this->mp, mp) && this->ref)
|
|
+ return this;
|
|
+ }
|
|
+
|
|
+ return NULL;
|
|
+}
|
|
+
|
|
+static struct mnt_list *mnts_alloc_mount(const char *mp)
|
|
+{
|
|
+ struct mnt_list *this;
|
|
+
|
|
+ this = malloc(sizeof(*this));
|
|
+ if (!this)
|
|
+ goto done;
|
|
+ memset(this, 0, sizeof(*this));
|
|
+
|
|
+ this->mp = strdup(mp);
|
|
+ if (!this->mp) {
|
|
+ free(this);
|
|
+ this = NULL;
|
|
+ goto done;
|
|
+ }
|
|
+
|
|
+ this->ref = 1;
|
|
+ INIT_HLIST_NODE(&this->hash);
|
|
+done:
|
|
+ return this;
|
|
+}
|
|
+
|
|
+static void __mnts_get_mount(struct mnt_list *mnt)
|
|
+{
|
|
+ mnt->ref++;
|
|
+}
|
|
+
|
|
+static void __mnts_put_mount(struct mnt_list *mnt)
|
|
+{
|
|
+ mnt->ref--;
|
|
+ if (!mnt->ref) {
|
|
+ hash_del(&mnt->hash);
|
|
+ free(mnt->mp);
|
|
+ free(mnt);
|
|
+ }
|
|
+}
|
|
+
|
|
+static struct mnt_list *mnts_new_mount(const char *mp)
|
|
+{
|
|
+ struct mnt_list *this;
|
|
+
|
|
+ this = mnts_lookup(mp);
|
|
+ if (this) {
|
|
+ __mnts_get_mount(this);
|
|
+ goto done;
|
|
+ }
|
|
+
|
|
+ this = mnts_alloc_mount(mp);
|
|
+ if (!this)
|
|
+ goto done;
|
|
+
|
|
+ hash_add_str(mnts_hash, &this->hash, this->mp);
|
|
+done:
|
|
+ return this;
|
|
+}
|
|
+
|
|
+static struct mnt_list *mnts_get_mount(const char *mp)
|
|
+{
|
|
+ struct mnt_list *this;
|
|
+
|
|
+ this = mnts_lookup(mp);
|
|
+ if (this) {
|
|
+ __mnts_get_mount(this);
|
|
+ return this;
|
|
+ }
|
|
+
|
|
+ return mnts_new_mount(mp);
|
|
+}
|
|
+
|
|
+static struct mnt_list *__mnts_lookup_mount(const char *mp)
|
|
+{
|
|
+ struct mnt_list *this;
|
|
+
|
|
+ this = mnts_lookup(mp);
|
|
+ if (this)
|
|
+ __mnts_get_mount(this);
|
|
+
|
|
+ return this;
|
|
+}
|
|
+
|
|
+struct mnt_list *mnts_lookup_mount(const char *mp)
|
|
+{
|
|
+ struct mnt_list *this;
|
|
+
|
|
+ mnts_hash_mutex_lock();
|
|
+ this = __mnts_lookup_mount(mp);
|
|
+ mnts_hash_mutex_unlock();
|
|
+
|
|
+ return this;
|
|
+}
|
|
+
|
|
+void mnts_put_mount(struct mnt_list *mnt)
|
|
+{
|
|
+ if (!mnt)
|
|
+ return;
|
|
+ mnts_hash_mutex_lock();
|
|
+ __mnts_put_mount(mnt);
|
|
+ mnts_hash_mutex_unlock();
|
|
+}
|
|
+
|
|
/* From glibc decode_name() */
|
|
/* Since the values in a line are separated by spaces, a name cannot
|
|
* contain a space. Therefore some programs encode spaces in names
|