aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--shell/ash.c61
1 files changed, 34 insertions, 27 deletions
diff --git a/shell/ash.c b/shell/ash.c
index 75a72ea0c..e900a425f 100644
--- a/shell/ash.c
+++ b/shell/ash.c
@@ -1250,7 +1250,6 @@ static struct parsefile basepf; /* top level input file */
1250static struct parsefile *g_parsefile = &basepf; /* current input file */ 1250static struct parsefile *g_parsefile = &basepf; /* current input file */
1251static int startlinno; /* line # where last token started */ 1251static int startlinno; /* line # where last token started */
1252static char *commandname; /* currently executing command */ 1252static char *commandname; /* currently executing command */
1253static struct strlist *cmdenviron; /* environment for builtin command */
1254 1253
1255 1254
1256/* ============ Message printing */ 1255/* ============ Message printing */
@@ -2225,15 +2224,9 @@ reinit_unicode_for_ash(void)
2225/* 2224/*
2226 * Search the environment of a builtin command. 2225 * Search the environment of a builtin command.
2227 */ 2226 */
2228static const char * 2227static inline const char *
2229bltinlookup(const char *name) 2228bltinlookup(const char *name)
2230{ 2229{
2231 struct strlist *sp;
2232
2233 for (sp = cmdenviron; sp; sp = sp->next) {
2234 if (varcmp(sp->text, name) == 0)
2235 return var_end(sp->text);
2236 }
2237 return lookupvar(name); 2230 return lookupvar(name);
2238} 2231}
2239 2232
@@ -9179,7 +9172,7 @@ static struct localvar_list *localvar_stack;
9179 * Interrupts must be off. 9172 * Interrupts must be off.
9180 */ 9173 */
9181static void 9174static void
9182poplocalvars(void) 9175poplocalvars(int keep)
9183{ 9176{
9184 struct localvar_list *ll; 9177 struct localvar_list *ll;
9185 struct localvar *lvp, *next; 9178 struct localvar *lvp, *next;
@@ -9196,7 +9189,23 @@ poplocalvars(void)
9196 next = lvp->next; 9189 next = lvp->next;
9197 vp = lvp->vp; 9190 vp = lvp->vp;
9198 TRACE(("poplocalvar %s\n", vp ? vp->var_text : "-")); 9191 TRACE(("poplocalvar %s\n", vp ? vp->var_text : "-"));
9199 if (vp == NULL) { /* $- saved */ 9192 if (keep) {
9193 int bits = VSTRFIXED;
9194
9195 if (lvp->flags != VUNSET) {
9196 if (vp->var_text == lvp->text)
9197 bits |= VTEXTFIXED;
9198 else if (!(lvp->flags & (VTEXTFIXED|VSTACK)))
9199 free((char*)lvp->text);
9200 }
9201
9202 vp->flags &= ~bits;
9203 vp->flags |= (lvp->flags & bits);
9204
9205 if ((vp->flags &
9206 (VEXPORT|VREADONLY|VSTRFIXED|VUNSET)) == VUNSET)
9207 unsetvar(vp->var_text);
9208 } else if (vp == NULL) { /* $- saved */
9200 memcpy(optlist, lvp->text, sizeof(optlist)); 9209 memcpy(optlist, lvp->text, sizeof(optlist));
9201 free((char*)lvp->text); 9210 free((char*)lvp->text);
9202 optschanged(); 9211 optschanged();
@@ -9260,7 +9269,7 @@ evalfun(struct funcnode *func, int argc, char **argv, int flags)
9260#endif 9269#endif
9261 pushlocalvars(); 9270 pushlocalvars();
9262 evaltree(func->n.narg.next, flags & EV_TESTED); 9271 evaltree(func->n.narg.next, flags & EV_TESTED);
9263 poplocalvars(); 9272 poplocalvars(0);
9264 funcdone: 9273 funcdone:
9265 INT_OFF; 9274 INT_OFF;
9266 funcnest--; 9275 funcnest--;
@@ -9631,6 +9640,7 @@ evalcommand(union node *cmd, int flags)
9631 /* First expand the arguments. */ 9640 /* First expand the arguments. */
9632 TRACE(("evalcommand(0x%lx, %d) called\n", (long)cmd, flags)); 9641 TRACE(("evalcommand(0x%lx, %d) called\n", (long)cmd, flags));
9633 setstackmark(&smark); 9642 setstackmark(&smark);
9643 pushlocalvars();
9634 back_exitstatus = 0; 9644 back_exitstatus = 0;
9635 9645
9636 cmdentry.cmdtype = CMDBUILTIN; 9646 cmdentry.cmdtype = CMDBUILTIN;
@@ -9684,6 +9694,8 @@ evalcommand(union node *cmd, int flags)
9684 spp = varlist.lastp; 9694 spp = varlist.lastp;
9685 expandarg(argp, &varlist, EXP_VARTILDE); 9695 expandarg(argp, &varlist, EXP_VARTILDE);
9686 9696
9697 mklocal((*spp)->text);
9698
9687 /* 9699 /*
9688 * Modify the command lookup path, if a PATH= assignment 9700 * Modify the command lookup path, if a PATH= assignment
9689 * is present 9701 * is present
@@ -9815,6 +9827,7 @@ evalcommand(union node *cmd, int flags)
9815 /* parent */ 9827 /* parent */
9816 status = waitforjob(jp); 9828 status = waitforjob(jp);
9817 INT_ON; 9829 INT_ON;
9830 poplocalvars(0);
9818 TRACE(("forked child exited with %d\n", status)); 9831 TRACE(("forked child exited with %d\n", status));
9819 break; 9832 break;
9820 } 9833 }
@@ -9827,17 +9840,10 @@ evalcommand(union node *cmd, int flags)
9827 /* NOTREACHED */ 9840 /* NOTREACHED */
9828 } /* default */ 9841 } /* default */
9829 case CMDBUILTIN: 9842 case CMDBUILTIN:
9830 cmdenviron = varlist.list; 9843 poplocalvars(spclbltin > 0 || argc == 0);
9831 if (cmdenviron) { 9844 if (cmd_is_exec && argc > 1)
9832 struct strlist *list = cmdenviron; 9845 listsetvar(varlist.list, VEXPORT);
9833 int i = VNOSET; 9846
9834 if (spclbltin > 0 || argc == 0) {
9835 i = 0;
9836 if (cmd_is_exec && argc > 1)
9837 i = VEXPORT;
9838 }
9839 listsetvar(list, i);
9840 }
9841 /* Tight loop with builtins only: 9847 /* Tight loop with builtins only:
9842 * "while kill -0 $child; do true; done" 9848 * "while kill -0 $child; do true; done"
9843 * will never exit even if $child died, unless we do this 9849 * will never exit even if $child died, unless we do this
@@ -9855,7 +9861,7 @@ evalcommand(union node *cmd, int flags)
9855 goto readstatus; 9861 goto readstatus;
9856 9862
9857 case CMDFUNCTION: 9863 case CMDFUNCTION:
9858 listsetvar(varlist.list, 0); 9864 poplocalvars(1);
9859 /* See above for the rationale */ 9865 /* See above for the rationale */
9860 dowait(DOWAIT_NONBLOCK, NULL); 9866 dowait(DOWAIT_NONBLOCK, NULL);
9861 if (evalfun(cmdentry.u.func, argc, argv, flags)) 9867 if (evalfun(cmdentry.u.func, argc, argv, flags))
@@ -12714,11 +12720,12 @@ dotcmd(int argc_ UNUSED_PARAM, char **argv_ UNUSED_PARAM)
12714 char *fullname; 12720 char *fullname;
12715 char **argv; 12721 char **argv;
12716 char *args_need_save; 12722 char *args_need_save;
12717 struct strlist *sp;
12718 volatile struct shparam saveparam; 12723 volatile struct shparam saveparam;
12719 12724
12720 for (sp = cmdenviron; sp; sp = sp->next) 12725//???
12721 setvareq(ckstrdup(sp->text), VSTRFIXED | VTEXTFIXED); 12726// struct strlist *sp;
12727// for (sp = cmdenviron; sp; sp = sp->next)
12728// setvareq(ckstrdup(sp->text), VSTRFIXED | VTEXTFIXED);
12722 12729
12723 nextopt(nullstr); /* handle possible "--" */ 12730 nextopt(nullstr); /* handle possible "--" */
12724 argv = argptr; 12731 argv = argptr;
@@ -13601,7 +13608,7 @@ reset(void)
13601 13608
13602 /* from var.c: */ 13609 /* from var.c: */
13603 while (localvar_stack) 13610 while (localvar_stack)
13604 poplocalvars(); 13611 poplocalvars(0);
13605} 13612}
13606 13613
13607#if PROFILE 13614#if PROFILE