2 * Copyright 1993, 1995 Christopher Seiwald.
4 * This file is part of Jam - see jam.c for Copyright information.
8 * mkjambase.c - turn Jambase into a big C structure
10 * Usage: mkjambase jambase.c Jambase ...
12 * Results look like this:
19 * Handles \'s and "'s specially; knows how to delete blank and comment lines.
21 * 11/04/02 (seiwald) - const-ing for string literals
32 //#define MKJAMBASE_COMPACT
35 ////////////////////////////////////////////////////////////////////////////////
36 static void fatal (const char *msg
) {
37 fprintf(stdout
, "FATAL: %s\n", msg
);
42 static char outdata
[1024*1024];
43 static int outdatalen
= 0;
46 static void outStr (const char *str
) {
47 memmove(outdata
+outdatalen
, str
, strlen(str
));
48 outdatalen
+= strlen(str
);
52 #define EMIT(ch) do { \
53 if (outp-outbuf >= sizeof(outbuf)) fatal("output line too big\n");\
58 static inline void normSlashes (char *s
) {
59 for (; *s
; ++s
) if (*s
== '\\') *s
= '/';
63 static int doDotC
= 0, wasScreen
, dontStrip
= 0, dropSpaces
, doCompress
= 1;
65 static int lineno
= 0;
66 static int inclevel
= 0;
67 static const char *srcfname
= "<cli>";
69 static void processFile (FILE *fout
, const char *fname
) {
71 char *p
, *e
, quoteCh
, *outp
;
72 static char buf
[32768], outbuf
[32768];
74 const char *ofn
= srcfname
;
79 if (++inclevel
> 64) {
81 fprintf(stderr
, "FATAL: too many nested includes, failed in file '%s', line %d\n", ofn
, olno
);
85 printf(": %s\n", fname
);
86 if (!(fin
= fopen(fname
, "r"))) {
88 fprintf(stderr
, "FATAL: can't open file '%s', failed in file '%s', line %d\n", fname
, ofn
, olno
);
92 if (!doCompress
) fprintf(fout
, "/* %s */\n", fname
);
99 while (fgets(buf
, sizeof(buf
), fin
)) {
107 while (*p
&& *((unsigned char *)p
) <= ' ') ++p
;
108 if ((t
= strchr(p
, '#')) != NULL
) *t
= '\0';
109 for (t
= p
+strlen(p
); t
> p
; --t
) if (!isspace(t
[-1])) break;
113 fprintf(stderr
, "FATAL: invalid '.' in file '%s', line %d\n", fname
, lineno
);
116 fn
= malloc(strlen(p
)+strlen(fname
)+64);
119 fprintf(stderr
, "FATAL: out of memory in file '%s', line %d\n", fname
, lineno
);
124 if ((t
= strrchr(fn
, '/')) != NULL
) t
[1] = '\0'; else fn
[0] = '\0';
126 processFile(fout
, fn
);
132 #ifdef MKJAMBASE_COMPACT
133 if (!strncmp(buf
, "#DONT_TOUCH", 11)) {
134 dontStrip
= !dontStrip
;
141 /* strip leading whitespace */
143 while (*p
&& *((unsigned char *)p
) <= ' ') ++p
;
144 /* drop comments and empty lines */
145 if (*p
== '#' || !*p
) continue;
147 /* copy; drop comments if # is not in quotes */
148 outp
= outbuf
; quoteCh
= 0; wasScreen
= 0;
149 if (!doCompress
) EMIT('"');
151 for (; *p
&& *p
!= '\n' && *p
!= '\r'; p
++) {
153 if (!quoteCh
&& !wasScreen
&& *p
== '#') break; /* comment follows; drop it */
157 if (!doCompress
) EMIT('\\');
159 wasScreen
= !wasScreen
;
163 if (!doCompress
) EMIT('\\');
165 if (!wasScreen
) quoteCh
= (quoteCh
==*p
)?0:*p
;
170 if (!wasScreen
) quoteCh
= (quoteCh
==*p
)?0:*p
;
174 if (!dontStrip
&& *((unsigned char *)p
) <= ' ') {
175 if (wasScreen
|| !dropSpaces
|| quoteCh
) EMIT(*p
);
176 dropSpaces
= !quoteCh
;
185 /* terminate output */
188 /* strip ending whitespace */
190 while (e
>= outbuf
&& *((unsigned char *)e
) <= ' ') --e
;
192 /* drop empty line */
193 if (!outbuf
[0]) continue;
199 fprintf(fout
, "%s\\n\",\n", outbuf
);
202 fprintf(fout
, "%s", buf
);
213 int main (int argc
, char *argv
[]) {
218 fprintf(stderr
, "usage: %s jambase.c Jambase ...\n", argv
[0]);
222 if (!(fout
= fopen(argv
[1], "wb"))) {
227 /* if the file ends in .c generate a C source file */
228 if ((p
= strrchr(argv
[1], '.')) && !strcmp(p
, ".c")) ++doDotC
;
230 /* now process the files */
231 argc
-= 2, argv
+= 2;
234 fprintf(fout
, "/* Generated by mkjambase from Jambase */\n");
235 fprintf(fout
, "#include \"jam.h\"\n");
237 fprintf(fout
, "char **jambase = 0;\n");
238 fprintf(fout
, "unsigned char jambasepk[] = {");
240 fprintf(fout
, "const char *jambase[] = {\n");
244 for (; argc
--; ++argv
) processFile(fout
, *argv
);
246 if (outdatalen
> 0) {
252 if (lzCompress(outdata
, outdatalen
, &dest
, &destlen
) != 0) {
253 perror("compression error!");
256 printf("%d bytes packed to %u bytes (%u%%)\n", outdatalen
, (unsigned int)destlen
, (unsigned int)(100*destlen
/outdatalen
));
257 //fwrite(dest, destlen, 1, fout);
258 for (int f
= 0; f
< destlen
; ++f
) {
264 fprintf(fout
, "0x%02x,", dest
[f
]);
266 if (cnt
> 0) fputc('\n', fout
);
270 //fwrite(outdata, outdatalen, 1, fout);
275 if (!doCompress
) fputc('0', fout
);
276 fprintf(fout
, "};\n");
277 if (doCompress
) fprintf(fout
, "\nJAMFA_CONST int jbpksize (void) { return sizeof(jambasepk); }\n");