Zsh Mailing List Archive
Messages sorted by: Reverse Date, Date, Thread, Author

Re: Improving zcompdump (Re: A patch with hashtable optimization, which doesn't work)




On 4 czerwca 2017 at 02:54:57, Bart Schaefer (schaefer@xxxxxxxxxxxxxxxx) wrote:
> On Jun 3, 4:11pm, Sebastian Gniazdowski wrote:
> } Subject: Re: Improving zcompdump (Re: A patch with hashtable optimization,
> }
> } On 20 maja 2017 at 19:08:09, Bart Schaefer (schaefer@xxxxxxxxxxxxxxxx) wrote:
> } > How much does zcompdump actually help? Have you compared startup with
> } > and without it?
> 
> Haven't seen that yet (nor tried it myself, tho).

It wasn't me in the "How does .."

> } > One lesson learned with Completion/Base/Utility/_store_cache is that
> } > parsing array assignments is expensive.
> }
> } Results seem to confirm what you said
> 
> I also tried something similar ... using the just the default set of
> completions, more wall-clock time is spent restoring the autoloads
> than loading the _comps array, at least on my system.

Could you try patch with single-allocation in mkautofn()? Chances are low, but who knows. The patch spans also to other non-heap Eprog allocation places.

--
Sebastian Gniazdowski
psprint /at/ zdharma.org
diff --git a/Src/builtin.c b/Src/builtin.c
index 063644e..680b19a 100644
--- a/Src/builtin.c
+++ b/Src/builtin.c
@@ -3483,15 +3483,15 @@ mkautofn(Shfunc shf)
 {
     Eprog p;
 
-    p = (Eprog) zalloc(sizeof(*p));
+    p = (Eprog) zalloc(sizeof(*p) + 5 * sizeof(wordcode));
     p->len = 5 * sizeof(wordcode);
-    p->prog = (Wordcode) zalloc(p->len);
+    p->prog = (Wordcode) (((char*)p)+sizeof(*p));
     p->strs = NULL;
     p->shf = shf;
     p->npats = 0;
     p->nref = 1; /* allocated from permanent storage */
     p->pats = (Patprog *) p->prog;
-    p->flags = EF_REAL;
+    p->flags = EF_REAL_SINGLE; /* no allocation for p->prog */
     p->dump = NULL;
 
     p->prog[0] = WCB_LIST((Z_SYNC | Z_END), 0);
diff --git a/Src/exec.c b/Src/exec.c
index debb0ae..088080b 100644
--- a/Src/exec.c
+++ b/Src/exec.c
@@ -4973,7 +4973,13 @@ execfuncdef(Estate state, Eprog redir_prog)
 	    prog = (Eprog) zhalloc(sizeof(*prog));
 	    prog->nref = -1; /* on the heap */
 	} else {
-	    prog = (Eprog) zalloc(sizeof(*prog));
+            if (state->prog->dump || !names) {
+                prog = (Eprog) zalloc(sizeof(*prog));
+            } else {
+                /* The EF_REAL path below */
+                prog = (Eprog) zalloc(sizeof(*prog) + len);
+                prog->pats = pp = (Patprog *) (((char*)prog)+sizeof(*prog));
+            }
 	    prog->nref = 1; /* allocated from permanent storage */
 	}
 	prog->npats = npats;
@@ -4992,8 +4998,11 @@ execfuncdef(Estate state, Eprog redir_prog)
 	    prog->prog = state->pc;
 	    prog->strs = state->strs + sbeg;
 	} else {
-	    prog->flags = EF_REAL;
-	    prog->pats = pp = (Patprog *) zalloc(len);
+            /* The EF_REAL path */
+	    prog->flags = EF_REAL_SINGLE;
+	    // prog->pats = pp = (Patprog *) zalloc(len);
+            // -->
+            // prog->pats = pp = (((char*)prog)+sizeof(*prog));
 	    prog->prog = (Wordcode) (prog->pats + npats);
 	    prog->strs = (char *) (prog->prog + nprg);
 	    prog->dump = NULL;
diff --git a/Src/parse.c b/Src/parse.c
index 8769baa..1e1c528 100644
--- a/Src/parse.c
+++ b/Src/parse.c
@@ -504,18 +504,28 @@ bld_eprog(int heap)
 
     ecadd(WCB_END());
 
-    ret = heap ? (Eprog) zhalloc(sizeof(*ret)) : (Eprog) zalloc(sizeof(*ret));
-    ret->len = ((ecnpats * sizeof(Patprog)) +
-		(ecused * sizeof(wordcode)) +
-		ecsoffs);
-    ret->npats = ecnpats;
-    ret->nref = heap ? -1 : 1;
-    ret->pats = heap ? (Patprog *) zhalloc(ret->len) :
-	(Patprog *) zshcalloc(ret->len);
+    if ( heap ) {
+        ret = (Eprog) zhalloc(sizeof(*ret));
+        ret->len = ((ecnpats * sizeof(Patprog)) +
+                (ecused * sizeof(wordcode)) +
+                ecsoffs);
+        ret->npats = ecnpats;
+        ret->nref = -1;
+        ret->pats = (Patprog *) zhalloc(ret->len);
+    } else {
+        int len = ((ecnpats * sizeof(Patprog)) +
+                (ecused * sizeof(wordcode)) +
+                ecsoffs);
+        ret = (Eprog) zalloc(sizeof(*ret) + len);
+        ret->len = len;
+        ret->npats = ecnpats;
+        ret->nref = 1;
+        ret->pats = (Patprog *) (((char*)ret)+sizeof(*ret));
+    }
     ret->prog = (Wordcode) (ret->pats + ecnpats);
     ret->strs = (char *) (ret->prog + ecused);
     ret->shf = NULL;
-    ret->flags = heap ? EF_HEAP : EF_REAL;
+    ret->flags = heap ? EF_HEAP : EF_REAL_SINGLE;
     ret->dump = NULL;
     for (l = 0; l < ecnpats; l++)
 	ret->pats[l] = dummy_patprog1;
@@ -2709,9 +2719,14 @@ freeeprog(Eprog p)
 	    if (p->dump) {
 		decrdumpcount(p->dump);
 		zfree(p->pats, p->npats * sizeof(Patprog));
-	    } else
-		zfree(p->pats, p->len);
-	    zfree(p, sizeof(*p));
+	    } else {
+                if ( (p->flags & EF_REAL_SINGLE) == 0 )
+                    zfree(p->pats, p->len);
+            }
+            if ( (p->flags & EF_REAL_SINGLE) )
+                zfree(p, sizeof(*p) + p->len);
+            else
+                zfree(p, sizeof(*p));
 	}
     }
 }
diff --git a/Src/zsh.h b/Src/zsh.h
index 22f73f8..ab70cb7 100644
--- a/Src/zsh.h
+++ b/Src/zsh.h
@@ -797,6 +797,7 @@ struct eprog {
 #define EF_HEAP 2
 #define EF_MAP  4
 #define EF_RUN  8
+#define EF_REAL_SINGLE 16
 
 typedef struct estate *Estate;
 


Messages sorted by: Reverse Date, Date, Thread, Author