28 #include <unistd.h>
29 #include <sys/fcntl.h>
30 #include <stdlib.h>
31 #include <libelf.h>
32 #include <gelf.h>
33 #include <sys/mman.h>
34 #include <libgen.h>
35 #include <stdarg.h>
36 #include <limits.h>
37
38 static char *g_progname;
39 static char *g_unique;
40 static char *g_outfile;
41 static uint_t g_nctf;
42
43 #define CTFMERGE_OK 0
44 #define CTFMERGE_FATAL 1
45 #define CTFMERGE_USAGE 2
46
47 #define CTFMERGE_DEFAULT_NTHREADS 8
48 #define CTFMERGE_ALTEXEC "CTFMERGE_ALTEXEC"
49
50 static void __attribute__((__noreturn__))
51 ctfmerge_fatal(const char *fmt, ...)
52 {
53 va_list ap;
54
55 (void) fprintf(stderr, "%s: ", g_progname);
56 va_start(ap, fmt);
57 (void) vfprintf(stderr, fmt, ap);
58 va_end(ap);
59
60 if (g_outfile != NULL)
61 (void) unlink(g_outfile);
62
63 exit(CTFMERGE_FATAL);
64 }
65
66 /*
67 * We failed to find CTF for this file, check if it's OK. If we're not derived
68 * from C, or we have the -m option, we let missing CTF pass.
295 va_list ap;
296
297 (void) fprintf(stderr, "%s: ", g_progname);
298 va_start(ap, fmt);
299 (void) vfprintf(stderr, fmt, ap);
300 va_end(ap);
301 }
302
303 (void) fprintf(stderr, "Usage: %s [-m] [-d uniqfile] [-l label] "
304 "[-L labelenv] [-j nthrs] -o outfile file ...\n"
305 "\n"
306 "\t-d uniquify merged output against uniqfile\n"
307 "\t-j use nthrs threads to perform the merge\n"
308 "\t-l set output container's label to specified value\n"
309 "\t-L set output container's label to value from environment\n"
310 "\t-m allow C-based input files to not have CTF\n"
311 "\t-o file to add CTF data to\n",
312 g_progname);
313 }
314
315 static void
316 ctfmerge_altexec(char **argv)
317 {
318 const char *alt;
319 char *altexec;
320
321 alt = getenv(CTFMERGE_ALTEXEC);
322 if (alt == NULL || *alt == '\0')
323 return;
324
325 altexec = strdup(alt);
326 if (altexec == NULL)
327 ctfmerge_fatal("failed to allocate memory for altexec\n");
328 if (unsetenv(CTFMERGE_ALTEXEC) != 0)
329 ctfmerge_fatal("failed to unset %s from environment: %s\n",
330 CTFMERGE_ALTEXEC, strerror(errno));
331
332 (void) execv(altexec, argv);
333 ctfmerge_fatal("failed to execute alternate program %s: %s",
334 altexec, strerror(errno));
335 }
336
337 int
338 main(int argc, char *argv[])
339 {
340 int err, i, c, ofd;
341 uint_t nthreads = CTFMERGE_DEFAULT_NTHREADS;
342 char *tmpfile = NULL, *label = NULL;
343 int wflags = CTF_ELFWRITE_F_COMPRESS;
344 uint_t flags = 0;
345 ctf_merge_t *cmh;
346 ctf_file_t *ofp;
347 long argj;
348 char *eptr;
349
350 g_progname = basename(argv[0]);
351
352 ctfmerge_altexec(argv);
353
354 /*
355 * We support a subset of the old CTF merge flags, mostly for
356 * compatibility.
357 */
358 while ((c = getopt(argc, argv, ":d:fgj:l:L:mo:t")) != -1) {
359 switch (c) {
360 case 'd':
361 g_unique = optarg;
362 break;
363 case 'f':
364 /* Silently ignored for compatibility */
365 break;
366 case 'g':
367 /* Silently ignored for compatibility */
368 break;
369 case 'j':
370 errno = 0;
371 argj = strtol(optarg, &eptr, 10);
372 if (errno != 0 || argj == LONG_MAX ||
373 argj > 1024 || *eptr != '\0') {
|
28 #include <unistd.h>
29 #include <sys/fcntl.h>
30 #include <stdlib.h>
31 #include <libelf.h>
32 #include <gelf.h>
33 #include <sys/mman.h>
34 #include <libgen.h>
35 #include <stdarg.h>
36 #include <limits.h>
37
38 static char *g_progname;
39 static char *g_unique;
40 static char *g_outfile;
41 static uint_t g_nctf;
42
43 #define CTFMERGE_OK 0
44 #define CTFMERGE_FATAL 1
45 #define CTFMERGE_USAGE 2
46
47 #define CTFMERGE_DEFAULT_NTHREADS 8
48
49 static void __attribute__((__noreturn__))
50 ctfmerge_fatal(const char *fmt, ...)
51 {
52 va_list ap;
53
54 (void) fprintf(stderr, "%s: ", g_progname);
55 va_start(ap, fmt);
56 (void) vfprintf(stderr, fmt, ap);
57 va_end(ap);
58
59 if (g_outfile != NULL)
60 (void) unlink(g_outfile);
61
62 exit(CTFMERGE_FATAL);
63 }
64
65 /*
66 * We failed to find CTF for this file, check if it's OK. If we're not derived
67 * from C, or we have the -m option, we let missing CTF pass.
294 va_list ap;
295
296 (void) fprintf(stderr, "%s: ", g_progname);
297 va_start(ap, fmt);
298 (void) vfprintf(stderr, fmt, ap);
299 va_end(ap);
300 }
301
302 (void) fprintf(stderr, "Usage: %s [-m] [-d uniqfile] [-l label] "
303 "[-L labelenv] [-j nthrs] -o outfile file ...\n"
304 "\n"
305 "\t-d uniquify merged output against uniqfile\n"
306 "\t-j use nthrs threads to perform the merge\n"
307 "\t-l set output container's label to specified value\n"
308 "\t-L set output container's label to value from environment\n"
309 "\t-m allow C-based input files to not have CTF\n"
310 "\t-o file to add CTF data to\n",
311 g_progname);
312 }
313
314 int
315 main(int argc, char *argv[])
316 {
317 int err, i, c, ofd;
318 uint_t nthreads = CTFMERGE_DEFAULT_NTHREADS;
319 char *tmpfile = NULL, *label = NULL;
320 int wflags = CTF_ELFWRITE_F_COMPRESS;
321 uint_t flags = 0;
322 ctf_merge_t *cmh;
323 ctf_file_t *ofp;
324 long argj;
325 char *eptr;
326
327 g_progname = basename(argv[0]);
328
329 /*
330 * We support a subset of the old CTF merge flags, mostly for
331 * compatibility.
332 */
333 while ((c = getopt(argc, argv, ":d:fgj:l:L:mo:t")) != -1) {
334 switch (c) {
335 case 'd':
336 g_unique = optarg;
337 break;
338 case 'f':
339 /* Silently ignored for compatibility */
340 break;
341 case 'g':
342 /* Silently ignored for compatibility */
343 break;
344 case 'j':
345 errno = 0;
346 argj = strtol(optarg, &eptr, 10);
347 if (errno != 0 || argj == LONG_MAX ||
348 argj > 1024 || *eptr != '\0') {
|