1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
|
#include <errno.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include "util.h"
#if !DEBUG
void die(const char* format, ...) {
#else
void _die(const char* file, int line, const char* format, ...) {
fprintf(stderr, "%s:%d: error: ", file, line);
#endif
va_list args;
va_start(args, format);
vfprintf(stderr, format, args);
va_end(args);
fprintf(stderr, "\n");
exit(1);
}
#if !DEBUG
void* emalloc(size_t size, char* alloc_reason) {
void* d = malloc(size);
if (d == NULL) die("failed to allocate '%s': %s", alloc_reason, strerror(errno));
return d;
}
#else
void* _emalloc(const char* file, int line, size_t size, char* alloc_reason) {
void* d = malloc(size);
if (d == NULL) _die(file, line, "failed to allocate '%s': %s", alloc_reason, strerror(errno));
return d;
}
#endif
#if DEBUG
void _failassert(const char* file, int line, char* contents) {
fprintf(stderr, "%s:%d: assertion failed: '%s'", file, line, contents);
exit(1);
}
#endif
void printout(const char* format, ...) {
va_list args;
va_start(args, format);
vfprintf(stdout, format, args);
va_end(args);
}
void print(const char* format, ...) {
va_list args;
va_start(args, format);
vfprintf(stderr, format, args);
va_end(args);
}
char* vastrcat_(int dummy, ...) {
va_list args;
va_list args2;
va_start(args, dummy);
va_copy(args2, args);
// get len of output string
size_t len = 0;
char* arg = NULL;
while ((arg = va_arg(args, char*))) {
len += strlen(arg);
}
va_end(args);
// allocate and build output
char* output = malloc(len + 1);
if (!output) return NULL;
char* p = output;
while ((arg = va_arg(args2, char*))) {
size_t alen = strlen(arg);
memcpy(p, arg, alen);
p += alen;
}
output[len] = '\0';
va_end(args2);
return output;
}
char* join_path_(int dummy, ...) {
va_list args;
va_list args2;
va_start(args, dummy);
va_copy(args2, args);
// note(jqj): some path joining libraries reset if they encounter an
// absolute path, we could implement that easily, but I'm not
// sure about it
// get len of output path
size_t len = 0;
char* arg = NULL;
int i = 0;
while ((arg = va_arg(args, char*))) {
if (i > 0) len += 1;
len += strlen(arg);
++i;
}
va_end(args);
// allocate output string
char* output = malloc(len + 1);
if (!output) {
va_end(args2);
return NULL;
}
// build output string
char* p = output;
while ((arg = va_arg(args2, char*))) {
if (p != output) {
// add slash before every part except the first
*p = '/';
++p;
}
size_t alen = strlen(arg);
memcpy(p, arg, alen);
p += alen;
}
output[len] = '\0';
va_end(args2);
return output;
}
|