shithub: riscv

Download patch

ref: 2b5a7cebc2274c5780e2cf62d3e18d0171773231
parent: 637a770a1698da227bcd296bd5578d978bea6e34
author: cinap_lenrek <cinap_lenrek@localhost>
date: Mon Jun 27 05:45:33 EDT 2011

hgfs: add tree caching

--- a/sys/src/cmd/hgfs/dat.h
+++ b/sys/src/cmd/hgfs/dat.h
@@ -66,10 +66,7 @@
 struct Revtree
 {
 	Ref;
-
 	int	level;
-
-	Revinfo	*info;
 	Revnode	*root;
 };
 
--- a/sys/src/cmd/hgfs/fs.c
+++ b/sys/src/cmd/hgfs/fs.c
@@ -53,6 +53,47 @@
 	return ri;
 }
 
+static Revtree*
+getrevtree(Revtree *(*fn)(Revlog *, Revlog *, Revinfo *), Revinfo *ri)
+{
+	static ulong gen;
+	static struct {
+		ulong g;
+		void *f;
+		Revinfo *i;
+		Revtree *t;
+	} cache[4];
+	Revtree *rt;
+	int i, j;
+
+	for(i=j=0; i<nelem(cache); i++){
+		if(cache[i].t == nil){
+			j = i;
+			continue;
+		}
+		if(cache[i].f == fn && cache[i].i == ri){
+			cache[i].g = ++gen;
+			rt = cache[i].t;
+			goto found;
+		}
+		if(cache[j].t && cache[i].g < cache[j].g)
+			j = i;
+	}
+	if((rt = (*fn)(&changelog, &manifest, ri)) == nil)
+		return nil;
+
+	closerevtree(cache[j].t);
+
+	cache[j].g = ++gen;
+	cache[j].f = fn;
+	cache[j].i = ri;
+	cache[j].t = rt;
+
+found:
+	incref(rt);
+	return rt;
+}
+
 static char*
 fsmkuid(char *s)
 {
@@ -281,6 +322,7 @@
 static char*
 fswalk1(Fid *fid, char *name, Qid *qid)
 {
+	Revtree* (*loadfn)(Revlog *, Revlog *, Revinfo *);
 	Revfile *rf;
 	Revnode *nd;
 	int i;
@@ -329,19 +371,20 @@
 				if(strcmp(name, nametab[i]) == 0)
 					break;
 			}
+			loadfn = nil;
 			switch(i){
 			case Qtree:
 				goto Notfound;
 			case Qfiles:
-				if((rf->tree = loadfilestree(&changelog, &manifest, rf->info)) == nil)
-					goto Notfound;
+				loadfn = loadfilestree;
 				break;
 			case Qchanges:
-				if((rf->tree = loadchangestree(&changelog, &manifest, rf->info)) == nil)
-					goto Notfound;
+				loadfn = loadchangestree;
 				break;
 			}
-			if(rf->tree){
+			if(loadfn){
+				if((rf->tree = getrevtree(loadfn, rf->info)) == nil)
+					goto Notfound;
 				rf->node = rf->tree->root;
 				rf->tree->level = i;
 			}
--- a/sys/src/cmd/hgfs/tree.c
+++ b/sys/src/cmd/hgfs/tree.c
@@ -164,8 +164,6 @@
 	memset(t, 0, sizeof(*t));
 	incref(t);
 
-	t->info = ri;
-
 	t->root = malloc(sizeof(Revnode));
 	t->root->path = 0;
 	t->root->name = 0;