diff options
| author | Laurent Bercot <ska-skaware@skarnet.org> | 2025-10-28 21:11:11 +0000 |
|---|---|---|
| committer | Laurent Bercot <ska-skaware@skarnet.org> | 2025-10-28 21:11:11 +0000 |
| commit | da11c327290b02537d95dbe6251ade8b76cedde4 (patch) | |
| tree | 8cfa94052976b129e7a106496cec24b34b527d4e /src | |
| parent | af1a9923d1fc79e76197059251d6f54fc0082db5 (diff) | |
| download | execline-da11c327290b02537d95dbe6251ade8b76cedde4.tar.gz | |
Add emptyenv -l, prepare for 2.9.8.0
Diffstat (limited to 'src')
| -rw-r--r-- | src/execline/emptyenv.c | 148 |
1 files changed, 92 insertions, 56 deletions
diff --git a/src/execline/emptyenv.c b/src/execline/emptyenv.c index 3c5b287..ac59697 100644 --- a/src/execline/emptyenv.c +++ b/src/execline/emptyenv.c @@ -2,9 +2,12 @@ #include <string.h> -#include <skalibs/gccattributes.h> +#include <skalibs/uint64.h> +#include <skalibs/types.h> +#include <skalibs/posixplz.h> #include <skalibs/bytestr.h> -#include <skalibs/sgetopt.h> +#include <skalibs/prog.h> +#include <skalibs/gol.h> #include <skalibs/strerr.h> #include <skalibs/stralloc.h> #include <skalibs/env.h> @@ -12,74 +15,85 @@ #include <execline/execline.h> -#define USAGE "emptyenv [ -p | -c | -o | -P ] prog..." +#define USAGE "emptyenv [ -p | -l | -c | -o | -P ] prog..." -static void cleanupenv (char const *const *, char const *const *) gccattr_noreturn ; -static void cleanupenv (char const *const *argv, char const *const *envp) +enum emptyenv_golb_e { - stralloc sa = STRALLOC_ZERO ; - if (!env_mexec("!", 0) || !env_mexec("?", 0)) goto err ; - for (; *envp ; envp++) - { - char const *s = *envp ; - sa.len = 0 ; - if (!strncmp(s, "ELGETOPT_", 9) - || !strncmp(s, "EXECLINE_", 9) - || !strncmp(s, "FD", 2) - || (s[0] == '#') - || ((s[0] >= '0') && (s[0] <= '9'))) - if (!stralloc_catb(&sa, s, str_chr(s, '=')) - || !stralloc_0(&sa) - || !env_mexec(sa.s, 0)) - goto err ; - } - stralloc_free(&sa) ; - xmexec(argv) ; -err: - strerr_diefu1sys(111, "clean up environment") ; -} + GOLB_PATH = 0x01, + GOLB_LIB = 0x02, + GOLB_CLEANUP = 0x04, + GOLB_OPT = 0x08, + GOLB_POS = 0x10 +} ; -int main (int argc, char const *const *argv, char const *const *envp) +int main (int argc, char const *const *argv) { - int flagpath = 0, flagcleanup = 0, flagopt = 0, flagpos = 0 ; + static gol_bool const rgolb[5] = + { + { .so = 'p', .lo = "keep-path", .clear = 0, .set = GOLB_PATH }, + { .so = 'l', .lo = "keep-ld-library-path", .clear = 0, .set = GOLB_LIB }, + { .so = 'c', .lo = "cleanup", .clear = 0, .set = GOLB_CLEANUP }, + { .so = 'o', .lo = "pop-elgetopt", .clear = 0, .set = GOLB_OPT }, + { .so = 'P', .lo = "pop-execline", .clear = 0, .set = GOLB_POS } + } ; + uint64_t wgolb = 0 ; + unsigned int golc ; PROG = "emptyenv" ; + golc = gol_main(argc, argv, rgolb, 5, 0, 0, &wgolb, 0) ; + argc -= golc ; argv += golc ; + if (!argc) strerr_dieusage(100, USAGE) ; + + if (wgolb & GOLB_CLEANUP) { - subgetopt l = SUBGETOPT_ZERO ; - for (;;) + static char const *const onebyte = "!?#0" ; + char *const *envp = environ ; + for (size_t i = 0 ; onebyte[i] ; i++) + { + char s[2] ; + s[0] = onebyte[i] ; + s[1] = 0 ; + if (!env_mexec(s, 0)) goto err ; + } + if (!env_mexec("EXECLINE_STRICT", 0)) goto err ; + for (; *envp ; envp++) { - int opt = subgetopt_r(argc, argv, "pcoP", &l) ; - if (opt == -1) break ; - switch (opt) + size_t l ; + char const *s = *envp ; + if (!strncmp(s, "ELGETOPT_", 9)) goto add ; + if (!strncmp(s, "FD", 2)) { - case 'p' : flagpath = 1 ; break ; - case 'c' : flagcleanup = 1 ; break ; - case 'o' : flagopt = 1 ; break ; - case 'P' : flagpos = 1 ; break ; - default : strerr_dieusage(100, USAGE) ; + unsigned int n ; + l = uint_scan(s + 2, &n) ; + if (l && s[2 + l] == '=') goto add ; + } + if ((s[0] >= '1') && (s[0] <= '9')) + { + unsigned int n ; + l = uint_scan(s, &n) ; + if (l && s[l] == '=') goto add ; + } + continue ; + add: + l = str_chr(s, '=') ; + if (l) + { + char tmp[l+1] ; + memcpy(tmp, s, l) ; + tmp[l] = 0 ; + if (!env_mexec(tmp, 0)) goto err ; } } - argc -= l.ind ; argv += l.ind ; + xmexec(argv) ; + err: + strerr_diefu1sys(111, "clean up environment") ; } - if (!argc) strerr_dieusage(100, USAGE) ; - if (flagcleanup) cleanupenv(argv, envp) ; - else if (!flagopt && !flagpos) - { - char const *newenv[2] = { 0, 0 } ; - if (flagpath) - for (; *envp ; envp++) - if (!strncmp(*envp, "PATH=", 5)) - { - newenv[0] = *envp ; - break ; - } - xexec_e(argv, newenv) ; - } - else + + else if (wgolb & (GOLB_OPT | GOLB_POS)) { static char const *const list[12] = { "0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "#", "ELGETOPT_" } ; stralloc sa = STRALLOC_ZERO ; - size_t envlen = env_len(envp) ; - int n = el_popenv(&sa, envp, envlen, flagpos ? list : list + 11, 11 * flagpos + flagopt) ; + size_t envlen = env_len((char const *const *)environ) ; + int n = el_popenv(&sa, (char const *const *)environ, envlen, wgolb & GOLB_POS ? list : list + 11, (wgolb & GOLB_POS ? 11 : 0) + !!(wgolb & GOLB_OPT)) ; if (n < 0) strerr_diefu1sys(111, "pop current execline environment") ; { char const *v[envlen - n + 1] ; @@ -88,4 +102,26 @@ int main (int argc, char const *const *argv, char const *const *envp) xexec_e(argv, v) ; } } + + else + { + char const *newenv[3] = { 0, 0, 0 } ; + char *const *envp = environ ; + unsigned int m = 0 ; + wgolb &= GOLB_PATH | GOLB_LIB ; + for (; wgolb && *envp ; envp++) + { + if (wgolb & GOLB_PATH && !strncmp(*envp, "PATH=", 5)) + { + newenv[m++] = *envp ; + wgolb &= ~GOLB_PATH ; + } + if (wgolb & GOLB_LIB && !strncmp(*envp, "LD_LIBRARY_PATH=", 16)) + { + newenv[m++] = *envp ; + wgolb &= ~GOLB_LIB ; + } + } + xexec_e(argv, newenv) ; + } } |
