commit fefb7e82bdf96801d513e26c28d0679cd10bd3b4 from: Benjamin Stürz date: Thu Dec 12 23:26:05 2024 UTC make: implement :Mpattern and :Npattern modifiers commit - 2534b579b7fcf1f22729331399e0898ff4f52dd7 commit + fefb7e82bdf96801d513e26c28d0679cd10bd3b4 blob - 2916fcba96c1bcd5647ad72330d64fbb0e0ba87a blob + 99c3670c513201155710170e9e69e008121a368d --- make/make.c +++ make/make.c @@ -5,6 +5,7 @@ #include #include #include +#include #include #include #include @@ -904,9 +905,10 @@ struct expand_ctx *ctx; * ${name:H} replace each word with its dirname() equvialent * ${name:T} replace each word with its basename() equvialent * ${name:m1:m2...} multiple modifiers can be combined - * TODO: * ${name:Mpattern} select only words that match pattern * ${name:Npattern} opposite of :Mpattern + * TODO: + * somehow make this function shorter */ subst2 (out, sc, prefix, s, ctx) str_t *out; @@ -920,7 +922,7 @@ struct expand_ctx *ctx; extern subst (); struct macro *m; struct filetime ft; - char *orig = *s, *t, *u, *v, *w; + char *orig = *s, *t, *u, *v, *w, *pattern; str_t name, old, new; /* parse macro name */ @@ -1086,12 +1088,50 @@ struct expand_ctx *ctx; continue; str_puts (&new, basename (w)); + str_putc (&new, ' '); + } + + str_pop (&new); + free (v); + v = str_release (&new); + } else if (str_get (&old)[0] == 'M') { + str_new (&new); + + pattern = str_get (&old) + 1; + + for (t = v; (w = strsep (&t, " \t")) != NULL; ) { + if (*w == '\0') + continue; + + if (fnmatch (pattern, w, 0) != 0) + continue; + + str_puts (&new, w); str_putc (&new, ' '); } str_pop (&new); free (v); v = str_release (&new); + } else if (str_get (&old)[0] == 'N') { + str_new (&new); + + pattern = str_get (&old) + 1; + + for (t = v; (w = strsep (&t, " \t")) != NULL; ) { + if (*w == '\0') + continue; + + if (fnmatch (pattern, w, 0) == 0) + continue; + + str_puts (&new, w); + str_putc (&new, ' '); + } + + str_pop (&new); + free (v); + v = str_release (&new); } else { errx (1, "%s: invalid modifier: ':%s' in '${%s'", sc_path_str (sc), str_get (&old), orig); }