[lvm-devel] master - lvmetad: unlock vg on out-of-memory path

Zdenek Kabelac zkabelac at fedoraproject.org
Sat Dec 15 16:25:28 UTC 2012


Gitweb:        http://git.fedorahosted.org/git/?p=lvm2.git;a=commitdiff;h=a4269aadf320f36d3d6fa3a3b66dda98855e7bc3
Commit:        a4269aadf320f36d3d6fa3a3b66dda98855e7bc3
Parent:        788ac7fa547fb98f0edd38685d40b80609f298dc
Author:        Zdenek Kabelac <zkabelac at redhat.com>
AuthorDate:    Fri Dec 14 16:35:26 2012 +0100
Committer:     Zdenek Kabelac <zkabelac at redhat.com>
CommitterDate: Sat Dec 15 17:23:26 2012 +0100

lvmetad: unlock vg on out-of-memory path

If we fail to get memory for mutex, hash the mutex
or fail somewhere along pthread function calls
return allocated resources back and unlock vg_lock_map mutex.
---
 WHATS_NEW                      |    1 +
 daemons/lvmetad/lvmetad-core.c |   24 ++++++++++++++----------
 2 files changed, 15 insertions(+), 10 deletions(-)

diff --git a/WHATS_NEW b/WHATS_NEW
index e0ce819..dd8ae68 100644
--- a/WHATS_NEW
+++ b/WHATS_NEW
@@ -1,5 +1,6 @@
 Version 2.02.99 - 
 ===================================
+  Unlock vg mutex in error path when lvmetad tries to lock_vg.
   Add check for key string duplication in config_make_nodes_v.
   Add check for created fid in _scan_file.
   Log output also to syslog when abort_on_internal_error is set.
diff --git a/daemons/lvmetad/lvmetad-core.c b/daemons/lvmetad/lvmetad-core.c
index e1cb583..6c00146 100644
--- a/daemons/lvmetad/lvmetad-core.c
+++ b/daemons/lvmetad/lvmetad-core.c
@@ -121,19 +121,18 @@ static response reply_unknown(const char *reason)
 static struct dm_config_tree *lock_vg(lvmetad_state *s, const char *id) {
 	pthread_mutex_t *vg;
 	struct dm_config_tree *cft;
+	pthread_mutexattr_t rec;
 
 	pthread_mutex_lock(&s->lock.vg_lock_map);
-	vg = dm_hash_lookup(s->lock.vg, id);
-	if (!vg) {
-		pthread_mutexattr_t rec;
-		pthread_mutexattr_init(&rec);
-		pthread_mutexattr_settype(&rec, PTHREAD_MUTEX_RECURSIVE_NP);
-		if (!(vg = malloc(sizeof(pthread_mutex_t))))
-                        return NULL;
-		pthread_mutex_init(vg, &rec);
+	if (!(vg = dm_hash_lookup(s->lock.vg, id))) {
+		if (!(vg = malloc(sizeof(pthread_mutex_t))) ||
+		    pthread_mutexattr_init(&rec) ||
+		    pthread_mutexattr_settype(&rec, PTHREAD_MUTEX_RECURSIVE_NP) ||
+		    pthread_mutex_init(vg, &rec))
+			goto bad;
 		if (!dm_hash_insert(s->lock.vg, id, vg)) {
-			free(vg);
-			return NULL;
+			pthread_mutex_destroy(vg);
+			goto bad;
 		}
 	}
 	/* We never remove items from s->lock.vg => the pointer remains valid. */
@@ -147,6 +146,11 @@ static struct dm_config_tree *lock_vg(lvmetad_state *s, const char *id) {
 	cft = dm_hash_lookup(s->vgid_to_metadata, id);
 	unlock_vgid_to_metadata(s);
 	return cft;
+bad:
+	pthread_mutex_unlock(&s->lock.vg_lock_map);
+	free(vg);
+	ERROR(s, "Out of memory");
+	return NULL;
 }
 
 static void unlock_vg(lvmetad_state *s, const char *id) {




More information about the lvm-devel mailing list