shithub: mpl

Download patch

ref: a754ee9f8591a7773426988e8bbd5d18d0494d03
parent: 7577bfa10f5e2fe386bddff5c52c43d1f992cecd
author: Jacob Moody <[email protected]>
date: Sun Dec 15 22:22:19 EST 2019

Fix traversal bug in mapinsert
Fix failure to runlock on certain map methods
Remove unused hasfn member

--- a/dat.c
+++ b/dat.c
@@ -12,8 +12,8 @@
 	int i;
 	uvlong hash;
 	hash = 7;
-	for(i=0;i<strlen(s);i++)
-		hash = hash*31 + s[i];
+	for(;*s;s++)
+		hash = hash*31 + *s;
 	return hash;
 }
 
@@ -29,31 +29,31 @@
 void
 mapinsert(Hmap *h, char *key, void *val)
 {
-	Hnode *n;
+	Hnode *n, *end;
 
 	wlock(h);
 	n = h->nodes+(string2hash(key)%h->size);
 	assert(n != nil);
-	for(;n->next!=nil || n->key!=nil ;n=n->next)
-		if(strcmp(key, n->key) == 0){
-			/* update value */
-			n->val = val;
-			wunlock(h);
-			return;
-		}
+	do {
+		if(n->key == nil)
+			goto new;
+		else if(strcmp(key, n->key) == 0)
+			goto found;
+		
+		end = n;
+		n = n->next;
+	} while(n != nil);
+	n = end;
 
-	/* Set existing free node */
-	if(n->key == nil){
-		n->key = strdup(key);
-		n->val = val;
-		wunlock(h);
-		return;
-	}
-
 	/* create new node */
 	n->next = emalloc(sizeof(Hnode));
-	n->next->key = strdup(key);
-	n->next->val = val;
+	n = n->next;
+
+new:
+	n->key = strdup(key);
+
+found:
+	n->val = val;
 	wunlock(h);
 }
 
@@ -61,6 +61,7 @@
 mapget(Hmap *h, char *key)
 {
 	Hnode *n;
+
 	rlock(h);
 	n = h->nodes+(string2hash(key)%h->size);
 	for(;n!=nil;n=n->next){
@@ -107,9 +108,10 @@
 	for(i=c=0;i<h->size;i++)
 		for(n=h->nodes+i;n!=nil && n->key!=nil;n=n->next){
 			if(c >= size)
-				return c;
+				goto done;
 			buf[c++] = n->val;
 		}
+done:
 	runlock(h);
 	return c;
 }
@@ -124,9 +126,10 @@
 	for(i=c=0;i<h->size;i++)
 		for(n=h->nodes+i;n!=nil && n->key!=nil;n=n->next){
 			if(c >= size)
-				return c;
+				goto done;
 			buf[c++] = n->key;
 		}
+done:
 	runlock(h);
 	return c;
 }
--- a/dat.h
+++ b/dat.h
@@ -124,7 +124,6 @@
 struct Hmap{
 	RWLock;
 	int size;
-	int (*hashfn)(void*);
 	struct Hnode{
 		char *key;
 		void *val;