1 // cmdlib.c
2
3 #include "cmdlib.h"
4 #include "qcc.h"
5
6 #ifdef WIN32
7 #ifdef WIN32GUI
8 #include <windows.h>
9 #endif
10
11 #else
12 #include <sys/time.h>
13 #endif
14
15 #define PATHSEPERATOR '\\'
16
17
18 // set these before calling CheckParm
19 int myargc;
20 char **myargv;
21
22 char com_token[1024];
23 int com_eof;
24 /*
25 ============
26 va
27
28 does a varargs printf into a temp buffer, so I don't need to have
29 varargs versions of all text functions.
30 FIXME: make this buffer size safe someday
31 ============
32 */
va(char * format,...)33 char *va(char *format, ...)
34 {
35 va_list argptr;
36 static char string[1024];
37
38 va_start (argptr, format);
39 vsprintf (string, format,argptr);
40 va_end (argptr);
41
42 return string;
43 }
44 /*
45 ================
46 I_FloatTime
47 ================
48 */
49 #include <time.h>
50
I_FloatTime(void)51 time_t I_FloatTime (void)
52 {
53 time_t t;
54
55 time(&t);
56
57 return t;
58
59
60 }
61
62
63 /*
64 ==============
65 COM_Parse
66
67 Parse a token out of a string
68 ==============
69 */
COM_Parse(char * data)70 char *COM_Parse (char *data)
71 {
72 int c;
73 int len;
74
75 len = 0;
76 com_token[0] = 0;
77
78 if (!data)
79 return NULL;
80
81 // skip whitespace
82 skipwhite:
83 while ( (c = *data) <= ' ')
84 {
85 if (c == 0)
86 {
87 com_eof = true;
88 return NULL; // end of file;
89 }
90 data++;
91 }
92
93 // skip // comments
94 if (c=='/' && data[1] == '/')
95 {
96 while (*data && *data != '\n')
97 data++;
98 if (!*data)
99 {
100 com_eof = true;
101 return NULL; // end of file;
102 }
103 goto skipwhite;
104 }
105 // skip /* */ comments
106 if (c=='/' && data[1] == '*')
107 {
108 data+= 2; // don't fall for /*/
109 while (*data && !(*data == '*' && data[1] == '/'))
110 data++;
111 if (!*data)
112 {
113 com_eof = true;
114 return NULL; // end of file;
115 }
116 data+=2;
117 goto skipwhite;
118 }
119 // handle quoted strings specially
120 if (c == '\"')
121 {
122 data++;
123 do
124 {
125 c = *data++;
126 if (c=='\"')
127 {
128 com_token[len] = 0;
129 return data;
130 }
131 com_token[len] = c;
132 len++;
133 } while (1);
134 }
135
136 // parse single characters
137 if (c=='{' || c=='}'|| c==')'|| c=='(' || c=='\'' || c==':')
138 {
139 com_token[len] = c;
140 len++;
141 com_token[len] = 0;
142 return data+1;
143 }
144
145 // parse a regular word
146 do
147 {
148 com_token[len] = c;
149 data++;
150 len++;
151 c = *data;
152 if (c=='{' || c=='}'|| c==')'|| c=='(' || c=='\'' || c==':')
153 break;
154 } while (c>32);
155
156 com_token[len] = 0;
157 return data;
158 }
159
160
161
162
163 /*
164 ================
165 filelength
166 ================
167 */
168 #ifndef WIN32
filelength(int handle)169 int filelength (int handle)
170 {
171 struct stat fileinfo;
172
173 if (fstat (handle,&fileinfo) == -1)
174 {
175 Sys_Error ("Error fstating");
176 }
177
178 return fileinfo.st_size;
179 }
180
tell(int handle)181 int tell (int handle)
182 {
183 return lseek (handle, 0, SEEK_CUR);
184 }
185 #endif
186
strupr(char * start)187 char *strupr (char *start)
188 {
189 char *in;
190 in = start;
191 while (*in)
192 {
193 *in = toupper(*in);
194 in++;
195 }
196 return start;
197 }
198
strlower(char * start)199 char *strlower (char *start)
200 {
201 char *in;
202 in = start;
203 while (*in)
204 {
205 *in = tolower(*in);
206 in++;
207 }
208 return start;
209 }
210
211
212 /*
213 =============================================================================
214
215 MISC FUNCTIONS
216
217 =============================================================================
218 */
219
220 #ifdef WIN32GUI
221 extern HWND main_hWnd;
222 char summary_buf[4096];
223 extern int compiled;
224
225 #endif
226
227
228 /*
229 =================
230 Sys_Error
231
232 For abnormal program terminations
233 =================
234 */
235
236
Sys_Error(char * error,...)237 void Sys_Error (char *error, ...)
238 {
239 va_list argptr;
240 char text[1024];
241 va_start (argptr, error);
242 vsprintf (text, error,argptr);
243 va_end (argptr);
244 #ifdef macintosh
245 Error(text);
246 exit(0);
247 #endif
248 #ifdef WIN32GUI
249 MessageBox(main_hWnd, text, "FrikDec Error", MB_OK | MB_SETFOREGROUND | MB_ICONSTOP);
250 exit(0);
251 #else
252 printf ("************ ERROR ***********\n");
253 printf("%s\n", text);
254 exit(0);
255 #endif
256 }
257
Q_strcmp(char * s1,char * s2)258 int Q_strcmp (char *s1, char *s2)
259 {
260 while (1)
261 {
262 if (*s1 != *s2)
263 return -1; // strings not equal
264 if (!*s1)
265 return 0; // strings are equal
266 s1++;
267 s2++;
268 }
269
270 return -1;
271 }
272 /*
273 =================
274 CheckParm
275
276 Checks for the given parameter in the program's command line arguments
277 Returns the argument number (1 to argc-1) or 0 if not present
278 =================
279 */
CheckParm(char * check)280 int CheckParm (char *check)
281 {
282 int i;
283
284 for (i = 1;i<myargc;i++)
285 {
286
287 if ( !Q_strcmp(check, myargv[i]) )
288 return i;
289
290 }
291
292 return 0;
293 }
294
295
296
SafeOpenWrite(char * filename)297 int SafeOpenWrite (char *filename)
298 {
299 int handle;
300
301 umask (0);
302
303 handle = open(filename,O_WRONLY | O_CREAT | O_TRUNC | O_BINARY
304 , 0666);
305
306 if (handle == -1)
307 Sys_Error ("Error opening %s: %s",filename,strerror(errno));
308
309 return handle;
310 }
311
SafeOpenRead(char * filename)312 int SafeOpenRead (char *filename)
313 {
314 int handle;
315
316 handle = open(filename,O_RDONLY | O_BINARY);
317
318 if (handle <= 0)
319 Sys_Error ("Error opening %s: %s",filename,strerror(errno));
320
321 return handle;
322 }
323
324
SafeRead(int handle,void * buffer,long count)325 void SafeRead (int handle, void *buffer, long count)
326 {
327 if (read (handle,buffer,count) != count)
328 Sys_Error ("File read failure");
329 }
330
331
SafeWrite(int handle,void * buffer,long count)332 void SafeWrite (int handle, void *buffer, long count)
333 {
334 if (write (handle,buffer,count) != count)
335 Sys_Error ("File write failure");
336 }
337
338
339
340 /*
341 ==============
342 LoadFile
343 ==============
344 */
LoadFile(char * filename,void ** bufferptr)345 long LoadFile (char *filename, void **bufferptr)
346 {
347 int handle;
348 long length;
349 void *buffer;
350
351 handle = SafeOpenRead (filename);
352 length = filelength (handle);
353 buffer = malloc(length+1);
354 ((byte *)buffer)[length] = 0;
355 SafeRead (handle, buffer, length);
356 close (handle);
357
358 *bufferptr = buffer;
359 return length;
360 }
361
362
363 /*
364 ==============
365 SaveFile
366 ==============
367 */
SaveFile(char * filename,void * buffer,long count)368 void SaveFile (char *filename, void *buffer, long count)
369 {
370 int handle;
371
372 handle = SafeOpenWrite (filename);
373 SafeWrite (handle, buffer, count);
374 close (handle);
375 }
376
377
378
DefaultExtension(char * path,char * extension)379 void DefaultExtension (char *path, char *extension)
380 {
381 char *src;
382 //
383 // if path doesn't have a .EXT, append extension
384 // (extension should include the .)
385 //
386 src = path + strlen(path) - 1;
387
388 while (*src != PATHSEPERATOR && src != path)
389 {
390 if (*src == '.')
391 return; // it has an extension
392 src--;
393 }
394
395 strcat (path, extension);
396 }
397
398
DefaultPath(char * path,char * basepath)399 void DefaultPath (char *path, char *basepath)
400 {
401 char temp[128];
402
403 if (path[0] == PATHSEPERATOR)
404 return; // absolute path location
405 strcpy (temp,path);
406 strcpy (path,basepath);
407 strcat (path,temp);
408 }
409
410
StripFilename(char * path)411 void StripFilename (char *path)
412 {
413 int length;
414
415 length = strlen(path)-1;
416 while (length > 0 && path[length] != PATHSEPERATOR)
417 length--;
418 path[length] = 0;
419 }
420
StripExtension(char * path)421 void StripExtension (char *path)
422 {
423 int length;
424
425 length = strlen(path)-1;
426 while (length > 0 && path[length] != '.')
427 {
428 length--;
429 if (path[length] == '/')
430 return; // no extension
431 }
432 if (length)
433 path[length] = 0;
434 }
435
436
ExtractFilename(char * path,char * dest)437 void ExtractFilename (char *path, char *dest)
438 {
439 char *src;
440
441 src = path + strlen(path) - 1;
442
443 //
444 // back up until a \ or the start
445 //
446 while (src > path && *(src-1) != PATHSEPERATOR)
447 src--;
448
449
450 strcpy (dest,src);
451 }
452
453
454
455 /*
456 ==============
457 ParseNum / ParseHex
458 ==============
459 */
ParseHex(char * hex)460 long ParseHex (char *hex)
461 {
462 char *str;
463 long num;
464
465 num = 0;
466 str = hex;
467
468 while (*str)
469 {
470 num <<= 4;
471 if (*str >= '0' && *str <= '9')
472 num += *str-'0';
473 else if (*str >= 'a' && *str <= 'f')
474 num += 10 + *str-'a';
475 else if (*str >= 'A' && *str <= 'F')
476 num += 10 + *str-'A';
477 else
478 Sys_Error ("Bad hex number: %s",hex);
479 str++;
480 }
481
482 return num;
483 }
484
485
ParseNum(char * str)486 long ParseNum (char *str)
487 {
488 if (str[0] == '$')
489 return ParseHex (str+1);
490 if (str[0] == '0' && str[1] == 'x')
491 return ParseHex (str+2);
492 return atol (str);
493 }
494
495
496
497 /*
498 ============================================================================
499
500 BYTE ORDER FUNCTIONS
501
502 ============================================================================
503 */
504
505 #ifndef INLINE
506
507 #ifdef __BIG_ENDIAN__
508
LittleShort(short l)509 short LittleShort (short l)
510 {
511 byte b1,b2;
512
513 b1 = l&255;
514 b2 = (l>>8)&255;
515
516 return (b1<<8) + b2;
517 }
518
BigShort(short l)519 short BigShort (short l)
520 {
521 return l;
522 }
523
LittleLong(long l)524 long LittleLong (long l)
525 {
526 byte b1,b2,b3,b4;
527
528 b1 = l&255;
529 b2 = (l>>8)&255;
530 b3 = (l>>16)&255;
531 b4 = (l>>24)&255;
532
533 return ((long)b1<<24) + ((long)b2<<16) + ((long)b3<<8) + b4;
534 }
535
BigLong(long l)536 long BigLong (long l)
537 {
538 return l;
539 }
540
541
LittleFloat(float l)542 float LittleFloat (float l)
543 {
544 union {byte b[4]; float f;} in, out;
545
546 in.f = l;
547 out.b[0] = in.b[3];
548 out.b[1] = in.b[2];
549 out.b[2] = in.b[1];
550 out.b[3] = in.b[0];
551
552 return out.f;
553 }
554
BigFloat(float l)555 float BigFloat (float l)
556 {
557 return l;
558 }
559
560
561 #else
562
563
BigShort(short l)564 short BigShort (short l)
565 {
566 byte b1,b2;
567
568 b1 = l&255;
569 b2 = (l>>8)&255;
570
571 return (b1<<8) + b2;
572 }
573
LittleShort(short l)574 short LittleShort (short l)
575 {
576 return l;
577 }
578
579
BigLong(long l)580 long BigLong (long l)
581 {
582 byte b1,b2,b3,b4;
583
584 b1 = l&255;
585 b2 = (l>>8)&255;
586 b3 = (l>>16)&255;
587 b4 = (l>>24)&255;
588
589 return ((long)b1<<24) + ((long)b2<<16) + ((long)b3<<8) + b4;
590 }
591
LittleLong(long l)592 long LittleLong (long l)
593 {
594 return l;
595 }
596
BigFloat(float l)597 float BigFloat (float l)
598 {
599 union {byte b[4]; float f;} in, out;
600
601 in.f = l;
602 out.b[0] = in.b[3];
603 out.b[1] = in.b[2];
604 out.b[2] = in.b[1];
605 out.b[3] = in.b[0];
606
607 return out.f;
608 }
609
LittleFloat(float l)610 float LittleFloat (float l)
611 {
612 return l;
613 }
614
615 #endif
616
617 #endif
618