diff options
| author | Thomas Voss <mail@thomasvoss.com> | 2024-02-13 13:02:28 +0100 | 
|---|---|---|
| committer | Thomas Voss <mail@thomasvoss.com> | 2024-02-13 13:11:47 +0100 | 
| commit | 79e6af86ca526d5fb56af6f6ca3da713e3a5e9f9 (patch) | |
| tree | 752f1c26d1f122dcf58374ac78db109c9578be45 /vendor/librune/make.c | |
Genesis commit
Diffstat (limited to 'vendor/librune/make.c')
| -rw-r--r-- | vendor/librune/make.c | 159 | 
1 files changed, 159 insertions, 0 deletions
| diff --git a/vendor/librune/make.c b/vendor/librune/make.c new file mode 100644 index 0000000..6f59825 --- /dev/null +++ b/vendor/librune/make.c @@ -0,0 +1,159 @@ +#define _GNU_SOURCE +#include <ctype.h> +#include <errno.h> +#include <glob.h> +#include <libgen.h> +#include <stdint.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + +#define CBS_PTHREAD +#include "cbs.h" + +#define CC         "cc" +#define WARNINGS   "-Wall", "-Wextra", "-Wpedantic", "-Werror", "-Wno-attributes" +#define CFLAGS_ALL WARNINGS, "-pipe", "-std=c2x" +#define CFLAGS_DBG CFLAGS_ALL, "-g", "-ggdb3", "-Og" +#ifdef __APPLE__ +#	define CFLAGS_RLS CFLAGS_ALL, "-O3" +#else +#	define CFLAGS_RLS CFLAGS_ALL, "-O3", "-march=native", "-mtune=native" +#endif + +#define _CMDPRC(C, F) \ +	do { \ +		int ec; \ +		F(C); \ +		if ((ec = cmdexec(C)) != EXIT_SUCCESS) \ +			diex("%s terminated with exit-code %d", *(C)._argv, ec); \ +		cmdclr(&(C)); \ +	} while (0) +#define CMDPRC(C)  _CMDPRC(C, cmdput) +#define CMDPRC2(C) _CMDPRC(C, cmdput) + +#define streq(a, b) (!strcmp(a, b)) + +#define flagset(o) (flags & (1 << ((o) - 'a'))) + +static void work(void *); +static int globerr(const char *, int); +static void cmdput2(cmd_t); + +static uint32_t flags; + +int +main(int argc, char **argv) +{ +	int opt; + +	cbsinit(argc, argv); +	rebuild(); + +	while ((opt = getopt(argc, argv, "flr")) != -1) { +		switch (opt) { +		case '?': +			fprintf(stderr, "Usage: %s [-flr]\n", *argv); +			exit(EXIT_FAILURE); +		default: +			flags |= 1 << (opt - 'a'); +		} +	} + +	argc -= optind; +	argv += optind; + +	if (argc >= 1) { +		if (streq(*argv, "clean")) { +			cmd_t c = {0}; +			cmdadd(&c, "find", ".", "-name", "*.[ao]", "-delete"); +			CMDPRC(c); +		} else { +			diex("invalid subcommand -- '%s'", *argv); +			exit(EXIT_FAILURE); +		} +	} else { +		cmd_t c = {0}; +		size_t n; +		glob_t g; +		tpool_t tp; + +		if (glob("lib/*/*.c", 0, globerr, &g)) +			die("glob"); + +		if ((n = nproc()) == -1) { +			if (errno) +				die("nproc"); +			n = 8; +		} + +		tpinit(&tp, n); +		for (size_t i = 0; i < g.gl_pathc; i++) +			tpenq(&tp, work, g.gl_pathv[i], NULL); +		tpwait(&tp); +		tpfree(&tp); + +		for (size_t i = 0; i < g.gl_pathc; i++) +			g.gl_pathv[i][strlen(g.gl_pathv[i]) - 1] = 'o'; + +		if (flagset('f') +		    || foutdatedv("librune.a", (const char **)g.gl_pathv, g.gl_pathc)) +		{ +			c.dst = "librune.a"; +			cmdadd(&c, "ar", "rcs", "librune.a"); +			cmdaddv(&c, g.gl_pathv, g.gl_pathc); +			CMDPRC2(c); +		} + +		globfree(&g); +	} + +	return EXIT_SUCCESS; +} + +void +work(void *p) +{ +	cmd_t c = {0}; +	char *src = p; +	struct strv sv = {0}; + +	if (!(c.dst = strdup(src))) +		die("strdup"); +	c.dst[strlen(c.dst) - 1] = 'o'; + +	if (flagset('f') || foutdated(c.dst, src)) { +		env_or_default(&sv, "CC", CC); +		if (flagset('r')) +			env_or_default(&sv, "CFLAGS", CFLAGS_RLS); +		else +			env_or_default(&sv, "CFLAGS", CFLAGS_DBG); +		cmdaddv(&c, sv.buf, sv.len); +		if (flagset('l')) +			cmdadd(&c, "-flto"); +		cmdadd(&c, "-Iinclude", "-fPIC", "-o", c.dst, "-c", src); +		CMDPRC2(c); +	} + +	free(c.dst); +} + +int +globerr(const char *s, int e) +{ +	errno = e; +	die("glob: %s", s); +} + +void +cmdput2(cmd_t c) +{ +	const char *p; + +	flockfile(stderr); +	for (p = *c._argv; *p; p++) +		fputc(toupper(*p), stderr); +	fprintf(stderr, "\t%s\n", c.dst); +	funlockfile(stderr); +} |