Added missing \n in TRACE calls.
[wine.git] / tools / bin2res.c
blobe018bc533554813fc22e2752f89c23c94bfb2414
1 /************************************************
3 * Converting binary resources from/to *.rc files
5 * Copyright 1999 Juergen Schmied
7 * 11/99 first release
9 * This library is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU Lesser General Public
11 * License as published by the Free Software Foundation; either
12 * version 2.1 of the License, or (at your option) any later version.
14 * This library is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * Lesser General Public License for more details.
19 * You should have received a copy of the GNU Lesser General Public
20 * License along with this library; if not, write to the Free Software
21 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
24 #include "config.h"
26 #ifdef HAVE_SYS_PARAM_H
27 # include <sys/param.h>
28 #endif
29 #include <sys/types.h>
30 #include <sys/stat.h>
32 #include <ctype.h>
33 #include <string.h>
35 #include <stdio.h>
36 #include <stdlib.h>
38 #include <fcntl.h>
39 #ifdef HAVE_UNISTD_H
40 # include <unistd.h>
41 #endif
42 #ifdef HAVE_SYS_MMAN_H
43 # include <sys/mman.h>
44 #endif
46 #include "windef.h"
47 #include "winbase.h"
48 #include "wingdi.h"
49 #include "winuser.h"
51 extern char* g_lpstrFileName;
53 /* global options */
55 char* g_lpstrFileName = NULL;
56 char* g_lpstrInputFile = NULL;
57 int b_to_binary = 0;
58 int b_force_overwrite = 0;
60 static char* errorOpenFile = "Unable to open file.\n";
61 static char* errorRCFormat = "Unexpexted syntax in rc file line %i\n";
63 void usage(void)
65 printf("Usage: bin2res [-d bin] [input file]\n");
66 printf(" -d bin convert a *.res back to a binary\n");
67 printf(" -f force overwriting newer files\n");
68 exit(-1);
71 void parse_options(int argc, char **argv)
73 int i;
75 switch( argc )
77 case 2:
78 g_lpstrInputFile = argv[1];
79 break;
81 case 3:
82 case 4:
83 case 5:
84 for( i = 1; i < argc - 1; i++ )
86 if( argv[i][0] != '-' ||
87 strlen(argv[i]) != 2 ) break;
89 if( argv[i][1] == 'd')
91 if (strcmp ("bin", argv[i+1])==0)
93 b_to_binary =1;
94 i++;
96 else
98 usage();
102 else if ( argv[i][1] == 'f')
104 b_force_overwrite = 1;
106 else
108 usage();
111 if( i == argc - 1 )
113 g_lpstrInputFile = argv[i];
114 break;
116 default: usage();
120 int insert_hex (char * infile, FILE * outfile)
122 #ifdef HAVE_MMAP
123 unsigned int i;
124 int fd;
125 struct stat st;
126 LPBYTE p_in_file = NULL;
128 if( (fd = open( infile, O_RDONLY))==-1 )
130 fprintf(stderr, errorOpenFile );
131 exit(1);
133 if ((fstat(fd, &st) == -1) || (p_in_file = mmap(NULL, st.st_size, PROT_READ, MAP_PRIVATE, fd, 0)) == (void *)-1)
135 fprintf(stderr, errorOpenFile );
136 close(fd);
137 exit(1);
140 fprintf (outfile, "{\n '");
141 i = 0;
142 while (1)
144 fprintf(outfile, "%02X", p_in_file[i]);
145 if (++i >= st.st_size) break;
146 fprintf(outfile, "%s", (i == (i & 0xfffffff0)) ? "'\n '" :" ");
148 fprintf (outfile, "'\n}");
149 munmap(p_in_file, st.st_size);
150 close(fd);
151 return 1;
152 #else /* HAVE_MMAP */
153 FILE* fp;
154 struct stat st;
155 unsigned int i;
156 int c;
158 fp = fopen( infile, "r" );
159 if ( fp == NULL )
161 fprintf(stderr, errorOpenFile );
162 exit(1);
164 if (fstat(fileno(fp), &st) == -1)
166 fprintf(stderr, errorOpenFile );
167 fclose(fp);
168 exit(1);
171 fprintf (outfile, "{\n '");
172 i = 0;
173 while (1)
175 c = fgetc(fp);
176 if ( c == EOF )
178 fprintf(stderr, errorOpenFile );
179 fclose(fp);
180 exit(1);
182 fprintf(outfile, "%02X", c);
183 if (++i >= st.st_size) break;
184 fprintf(outfile, "%s", (i == (i & 0xfffffff0)) ? "'\n '" :" ");
186 fprintf (outfile, "'\n}");
188 fclose(fp);
189 return 1;
190 #endif /* HAVE_MMAP */
193 int convert_to_res ()
195 FILE *fin, *ftemp;
196 char buffer[255];
197 char infile[255];
198 char tmpfile[255];
199 char *pos;
200 int c, len;
201 struct stat st;
202 int line = 0;
203 time_t tinput;
204 long startpos, endpos;
206 strcpy( tmpfile, g_lpstrInputFile );
207 strcat( tmpfile, "-tmp" );
208 /* FIXME: should use better tmp name and create with O_EXCL */
209 if( (ftemp = fopen( tmpfile, "w")) == NULL ) goto error_open_file;
211 if( (fin = fopen( g_lpstrInputFile, "r")) == NULL || stat(g_lpstrInputFile, &st)) goto error_open_file;
212 tinput = st.st_ctime;
214 while ( NULL != fgets(buffer, 255, fin))
216 fputs(buffer, ftemp);
217 line++;
218 if ( (pos = strstr(buffer, "BINRES")) != NULL)
220 /* get the out-file name */
221 len = 0; pos += 6; startpos=0; endpos=0;
222 while ( *pos == ' ') pos++;
223 while ( pos[len] != ' ') len++;
224 strncpy(infile, pos, len);
225 infile[len]=0;
227 if ( (!stat(infile, &st) && st.st_ctime > tinput) || b_force_overwrite)
229 /* write a output file */
230 printf("[%s:c]", infile);
231 while((c = fgetc(fin))!='{' && c != EOF) fputc(c, ftemp);
232 if (c == EOF ) goto error_rc_format;
233 while((c = fgetc(fin))!='}' && c != EOF);
234 if (c == EOF ) goto error_rc_format;
236 insert_hex(infile, ftemp);
238 else
240 printf("[%s:s]", infile);
245 fclose(fin);
246 fclose(ftemp);
248 if (unlink(g_lpstrInputFile) == -1)
250 perror("unlink");
251 unlink(tmpfile);
252 return 0;
254 if (rename(tmpfile, g_lpstrInputFile) == -1)
256 perror("rename");
257 unlink(tmpfile);
258 return 0;
260 return 1;
262 error_open_file:
263 fprintf(stderr, errorOpenFile );
264 return 0;
266 error_rc_format:
267 fprintf(stderr, errorRCFormat, line);
268 return 0;
271 int convert_to_bin()
273 FILE *fin, *fout;
274 char buffer[255];
275 char outfile[255];
276 char *pos;
277 int len, index, in_resource;
278 unsigned int byte;
279 struct stat st;
280 int line = 0;
281 time_t tinput;
283 if( (fin = fopen( g_lpstrInputFile, "r")) == NULL || stat(g_lpstrInputFile, &st)) goto error_open_file;
284 tinput = st.st_ctime;
286 while ( NULL != fgets(buffer, 255, fin))
288 line++;
289 if ( (pos = strstr(buffer, "BINRES")) != NULL)
291 /* get the out-file name */
292 len = 0; pos += 6;
293 while ( *pos == ' ') pos++;
294 while ( pos[len] != ' ') len++;
295 strncpy(outfile, pos, len);
296 outfile[len]=0;
298 if ( stat(outfile, &st) || st.st_ctime < tinput || b_force_overwrite)
300 /* write a output file */
301 printf("[%s:c]", outfile);
302 if ( (fout = fopen( outfile, "w")) == NULL) goto error_open_file;
304 in_resource = 0;
305 while (1)
307 if ( NULL == fgets(buffer, 255, fin)) goto error_rc_format;
308 line++;
310 /* parse a line */
311 for ( index = 0; buffer[index] != 0; index++ )
313 if ( ! in_resource )
315 if ( buffer[index] == '{' ) in_resource = 1;
316 continue;
319 if ( buffer[index] == ' ' || buffer[index] == '\''|| buffer[index] == '\n' ) continue;
320 if ( buffer[index] == '}' ) goto end_of_resource;
321 if ( ! isxdigit(buffer[index])) goto error_rc_format;
322 index += sscanf(&buffer[index], "%02x", &byte);
323 fputc(byte, fout);
326 fclose(fout);
328 else
330 printf("[%s:s]", outfile);
332 end_of_resource: ;
336 fclose(fin);
337 return 1;
339 error_open_file:
340 fprintf(stderr, errorOpenFile );
341 return 0;
343 error_rc_format:
344 fprintf(stderr, errorRCFormat, line);
345 return 0;
348 int main(int argc, char **argv)
350 parse_options( argc, argv);
352 if (b_to_binary == 0)
354 convert_to_res();
356 else
358 convert_to_bin();
360 printf("\n");
361 return 0;