summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorOliver Kiddle <okiddle@yahoo.co.uk>2018-04-12 23:15:04 +0200
committerOliver Kiddle <okiddle@yahoo.co.uk>2018-04-12 23:15:29 +0200
commit65b265f3c0877823b72ffff6ba1083972c49a3a8 (patch)
tree42f54ce498e887dd73d697ee8fe43674bd728709
parent2c4ec9dab0233afa146f0ad99041194c208e23b7 (diff)
downloadzsh-65b265f3c0877823b72ffff6ba1083972c49a3a8.tar.gz
zsh-65b265f3c0877823b72ffff6ba1083972c49a3a8.zip
42624 (plus test): avoid freeing memory that's still needed
This was occurring in a multiple function definition where a function name is duplicated.
-rw-r--r--ChangeLog6
-rw-r--r--Src/exec.c14
-rw-r--r--Test/C04funcdef.ztst10
3 files changed, 25 insertions, 5 deletions
diff --git a/ChangeLog b/ChangeLog
index 926abf3ea..949fdda57 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,9 @@
+2018-04-12 Oliver Kiddle <okiddle@yahoo.co.uk>
+
+ * 42624 (plus test): Src/exec.c, Test/C04funcdef.ztst: avoid
+ freeing memory that's still needed in multiple function
+ definition that has a duplicated function name
+
2018-04-11 Peter Stephenson <p.stephenson@samsung.com>
* 42623: configure.ac: some extra quotes needed (and some
diff --git a/Src/exec.c b/Src/exec.c
index e154d1249..216057aa7 100644
--- a/Src/exec.c
+++ b/Src/exec.c
@@ -5042,7 +5042,7 @@ execfuncdef(Estate state, Eprog redir_prog)
Shfunc shf;
char *s = NULL;
int signum, nprg, sbeg, nstrs, npats, len, plen, i, htok = 0, ret = 0;
- int nfunc = 0, anon_func = 0;
+ int anon_func = 0;
Wordcode beg = state->pc, end;
Eprog prog;
Patprog *pp;
@@ -5118,12 +5118,16 @@ execfuncdef(Estate state, Eprog redir_prog)
/*
* redir_prog is permanently allocated --- but if
* this function has multiple names we need an additional
- * one.
+ * one. Original redir_prog used with the last name
+ * because earlier functions are freed in case of duplicate
+ * names.
*/
- if (nfunc++ && redir_prog)
+ if (names && nonempty(names) && redir_prog)
shf->redir = dupeprog(redir_prog, 0);
- else
+ else {
shf->redir = redir_prog;
+ redir_prog = 0;
+ }
shfunc_set_sticky(shf);
if (!names) {
@@ -5203,7 +5207,7 @@ execfuncdef(Estate state, Eprog redir_prog)
}
if (!anon_func)
setunderscore("");
- if (!nfunc && redir_prog) {
+ if (redir_prog) {
/* For completeness, shouldn't happen */
freeeprog(redir_prog);
}
diff --git a/Test/C04funcdef.ztst b/Test/C04funcdef.ztst
index 5786018e0..3aaf7fb4a 100644
--- a/Test/C04funcdef.ztst
+++ b/Test/C04funcdef.ztst
@@ -43,6 +43,16 @@
0:Function definition without braces
>bar
+ a a b() {
+ read word
+ print $0: $word
+ } <<<redirection
+ b
+ a
+0:Multiple function definition with duplicate name and redirection
+>b: redirection
+>a: redirection
+
functions -M m1
m1() { (( $# )) }
print $(( m1() ))