4
|
1 /*--------------------------------------------------------------------------
|
|
2 NETREK II -- Paradise
|
|
3
|
|
4 Permission to use, copy, modify, and distribute this software and its
|
|
5 documentation, or any derivative works thereof, for any NON-COMMERCIAL
|
|
6 purpose and without fee is hereby granted, provided that this copyright
|
|
7 notice appear in all copies. No representations are made about the
|
|
8 suitability of this software for any purpose. This software is provided
|
|
9 "as is" without express or implied warranty.
|
|
10
|
|
11 Xtrek Copyright 1986 Chris Guthrie
|
|
12 Netrek (Xtrek II) Copyright 1989 Kevin P. Smith
|
|
13 Scott Silvey
|
|
14 Paradise II (Netrek II) Copyright 1993 Larry Denys
|
|
15 Kurt Olsen
|
|
16 Brandon Gillespie
|
|
17 --------------------------------------------------------------------------*/
|
|
18
|
|
19 #include "config.h"
|
|
20 #include <stdio.h>
|
|
21 #include <stdlib.h>
|
|
22 #include <string.h>
|
|
23
|
|
24 #define pm_error(str) {\
|
|
25 fprintf(stderr, "Error in ParseXbmFile(): %s\n", str);\
|
|
26 if(*dataP) { free(*dataP); *dataP = 0; }\
|
|
27 return -1; }
|
|
28
|
|
29 /*
|
|
30 * most of the following function came from xbmtopbm.c in the PBMPLUS library
|
|
31 */
|
|
32
|
|
33 #define MAX_LINE 500
|
|
34
|
|
35 int
|
|
36 ParseXbmFile(stream, widthP, heightP, dataP)
|
|
37 FILE *stream;
|
|
38 int *widthP;
|
|
39 int *heightP;
|
|
40 char **dataP;
|
|
41 {
|
|
42 char line[MAX_LINE], name_and_type[MAX_LINE];
|
|
43 char *ptr;
|
|
44 char *t;
|
|
45 int raster_length, v;
|
|
46 register int bytes, bytes_per_line;
|
|
47 register int c1, c2, value1, value2;
|
|
48 int hex_table[256];
|
|
49
|
|
50 *widthP = *heightP = -1;
|
|
51 *dataP = 0;
|
|
52
|
|
53 for (;;)
|
|
54 {
|
|
55 if (fgets(line, MAX_LINE, stream) == NULL)
|
|
56 pm_error("EOF / read error");
|
|
57 if (strlen(line) == MAX_LINE - 1)
|
|
58 pm_error("line too long");
|
|
59
|
|
60 if (sscanf(line, "#define %s %d", name_and_type, &v) == 2)
|
|
61 {
|
|
62 if ((t = strrchr(name_and_type, '_')) == NULL)
|
|
63 t = name_and_type;
|
|
64 else
|
|
65 ++t;
|
|
66 if (!strcmp("width", t))
|
|
67 *widthP = v;
|
|
68 else if (!strcmp("height", t))
|
|
69 *heightP = v;
|
|
70 continue;
|
|
71 }
|
|
72
|
|
73 if (sscanf(line, "static char %s = {", name_and_type) == 1 ||
|
|
74 sscanf(line, "static unsigned char %s = {", name_and_type) == 1)
|
|
75 break;
|
|
76 }
|
|
77
|
|
78 if (*widthP == -1)
|
|
79 pm_error("invalid width");
|
|
80 if (*heightP == -1)
|
|
81 pm_error("invalid height");
|
|
82
|
|
83 bytes_per_line = (*widthP + 7) / 8;
|
|
84
|
|
85 raster_length = bytes_per_line * *heightP;
|
|
86 *dataP = (char *) malloc(raster_length);
|
|
87 if (*dataP == (char *) 0)
|
|
88 pm_error("out of memory");
|
|
89
|
|
90 /* Initialize hex_table. */
|
|
91 for (c1 = 0; c1 < 256; ++c1)
|
|
92 hex_table[c1] = 256;
|
|
93
|
|
94 hex_table['0'] = 0;
|
|
95 hex_table['1'] = 1;
|
|
96 hex_table['2'] = 2;
|
|
97 hex_table['3'] = 3;
|
|
98 hex_table['4'] = 4;
|
|
99 hex_table['5'] = 5;
|
|
100 hex_table['6'] = 6;
|
|
101 hex_table['7'] = 7;
|
|
102 hex_table['8'] = 8;
|
|
103 hex_table['9'] = 9;
|
|
104 hex_table['A'] = 10;
|
|
105 hex_table['B'] = 11;
|
|
106 hex_table['C'] = 12;
|
|
107 hex_table['D'] = 13;
|
|
108 hex_table['E'] = 14;
|
|
109 hex_table['F'] = 15;
|
|
110 hex_table['a'] = 10;
|
|
111 hex_table['b'] = 11;
|
|
112 hex_table['c'] = 12;
|
|
113 hex_table['d'] = 13;
|
|
114 hex_table['e'] = 14;
|
|
115 hex_table['f'] = 15;
|
|
116
|
|
117 for (bytes = 0, ptr = *dataP; bytes < raster_length; ++bytes)
|
|
118 {
|
|
119 /*
|
|
120 * Skip until digit is found.
|
|
121 */
|
|
122 for (;;)
|
|
123 {
|
|
124 c1 = getc(stream);
|
|
125 if (c1 == EOF)
|
|
126 pm_error("EOF / read error");
|
|
127 value1 = hex_table[c1];
|
|
128 if (value1 != 256)
|
|
129 break;
|
|
130 }
|
|
131 /*
|
|
132 * Loop on digits.
|
|
133 */
|
|
134 for (;;)
|
|
135 {
|
|
136 c2 = getc(stream);
|
|
137 if (c2 == EOF)
|
|
138 pm_error("EOF / read error");
|
|
139 value2 = hex_table[c2];
|
|
140 if (value2 != 256)
|
|
141 {
|
|
142 value1 = (value1 << 4) | value2;
|
|
143 if (value1 >= 256)
|
|
144 pm_error("syntax error");
|
|
145 }
|
|
146 else if (c2 == 'x' || c2 == 'X')
|
|
147 {
|
|
148 if (value1 == 0)
|
|
149 continue;
|
|
150 else
|
|
151 pm_error("syntax error");
|
|
152 }
|
|
153 else
|
|
154 break;
|
|
155 }
|
|
156 *ptr++ = (char) (value1 ^ 0xFF);
|
|
157 }
|
|
158 return (raster_length);
|
|
159 }
|