source: rtems/c/src/lib/libbsp/i386/pc386/tools/bin2boot.c @ f05b2ac

4.104.114.84.9
Last change on this file since f05b2ac was f05b2ac, checked in by Ralf Corsepius <ralf.corsepius@…>, on Apr 21, 2004 at 4:01:48 PM

Remove duplicate white lines.

  • Property mode set to 100644
File size: 8.3 KB
Line 
1
2/*
3 * Simplyfied version of original bin2boot
4 */
5
6#include <stdio.h>
7#include <stdlib.h>
8#include <unistd.h>
9#include <string.h>
10
11static unsigned char buf[512];
12
13static void usage(void)
14{
15  printf("usage: bin2boot [-h][-v] <outFile> <headerAddr> \n");
16  printf("<imFile1> <imAddr1> <imSize1> [<imFile2> <imAddr2> <imSize2>]\n");
17  printf("this function makes image bootable by netboot\n");
18  printf("from one or two binary images\n");
19  printf("-h         - prints this message\n");
20  printf("-v         - verbose output\n");
21  printf("outFile    - output file\n");
22  printf("headerAddr - address to place header in memory\n");
23  printf("             it should be below or equal 0x97e00\n");
24  printf("imFile1    - first image\n");
25  printf("imAddr1    - its start address, image has to be placed whole\n");
26  printf("             below 0x98000 and should not overlap with header\n");
27  printf("imSize1    - actual size of compressed image, 0 for uncompressed\n");
28  printf("imFile2    - second image\n");
29  printf("imAddr2    - its start address\n");
30  printf("imSize2    - actual size of compressed image, 0 for uncompressed\n");
31
32  return;
33}
34
35int main(int argc, char* argv[])
36{
37  int      c, verbose;
38  extern   int optind;
39  FILE     *ofp, *ifp;
40  unsigned long headerAddr, addr1, addr2;
41  int      size1, size2, len1, len2, len, imageCnt, cnt;
42  char     *ofile, *ifile, *end;
43
44  verbose = 0;
45
46  /* parse command line options */
47  while ((c = getopt(argc, argv, "hv")) >= 0)
48    {
49      switch (c)
50        {
51        case 'v':
52          verbose = 1;
53          break;
54        case 'h':
55          usage();
56          return 0;
57        default:
58          usage();
59          return 1;
60        }
61    }
62
63  if((argc - optind) != 8 && (argc - optind) != 5)
64    {
65      usage();
66      return 1;
67    }
68
69  ofile = argv[optind];
70  ofp   = fopen(ofile, "wb");
71  if(ofp == NULL)
72    {
73      fprintf(stderr, "unable to open file %s\n", ofile);
74      return 1;
75    }
76
77  /*
78   * Layout is very simple first 512 is header shared by all
79   * images, then images at 512 bytes border
80   */
81
82  /* Fill buffer with 0's */
83  memset(buf, 0, sizeof(buf));
84
85  fwrite(buf, 1, sizeof(buf), ofp);
86
87  optind++;
88  headerAddr = strtoul(argv[optind], &end, 0);
89  if(end == argv[optind])
90    {
91      fprintf(stderr, "bad headerAddr %s\n", argv[optind]);
92      fclose(ofp);
93      return 1;
94    }
95
96  if(headerAddr > 0x97e00)
97    {
98      fprintf(stderr, "headerAddr is too high 0x%08lx\n", headerAddr);
99      fclose(ofp);
100      return 1;
101    }
102
103  /* Copy the first image */
104  optind++;
105  ifile = argv[optind];
106  ifp   = fopen(ifile,"rb");
107  if(ifp == NULL)
108    {
109      fprintf(stderr, "unable to open output file %s\n", ifile);
110      fclose(ofp);
111      return 1;
112    }
113
114  optind++;
115  addr1 = strtoul(argv[optind], &end, 0);
116  if(end == argv[optind])
117    {
118      fprintf(stderr, "bad image address %s\n", argv[optind]);
119      fclose(ofp);
120      return 1;
121    }
122
123  optind++;
124  size1 = strtoul(argv[optind], &end, 0);
125  if(end == argv[optind])
126    {
127      fprintf(stderr, "bad image size %s\n", argv[optind]);
128      fclose(ofp);
129      return 1;
130    }
131
132  /* Copy first image out and remember its length */
133  cnt  = 0;
134  for(;;)
135    {
136      len = fread(buf, 1, sizeof(buf), ifp);
137
138      if(len != 0)
139        {
140          fwrite(buf, 1, len, ofp);
141          cnt += sizeof(buf);
142
143          if(len != sizeof(buf))
144            {
145              memset(buf, 0, sizeof(buf) - len);
146              fwrite(buf, 1, sizeof(buf) - len, ofp);
147              break;
148            }
149
150        }
151      else
152        {
153          break;
154        }
155    }
156
157  fclose(ifp);
158
159  len1 = cnt;
160
161  if(size1 == 0)
162    {
163      size1 = cnt;
164    }
165  else
166    {
167      memset(buf, 0, sizeof(buf));
168
169      while(cnt < size1)
170        {
171          fwrite(buf, 1, sizeof(buf), ofp);
172          cnt += sizeof(buf);
173        }
174
175      size1 = cnt;
176    }
177
178  /* Let us check agains overlapping */
179  if(!(addr1 >= (headerAddr + sizeof(buf)) || (headerAddr >= addr1+size1)))
180    {
181      /* Areas overlapped */
182      printf("area overlapping: \n");
183      printf("header address      0x%08lx, its memory size 0x%08x\n",
184             headerAddr, sizeof(buf));
185      printf("first image address 0x%08lx, its memory size 0x%08x\n",
186             addr1, size1);
187
188      fclose(ofp);
189      return 1;
190    }
191
192  if((addr1 + size1) > 0x98000)
193    {
194      fprintf(stderr, "imAddr1 is too high 0x%08lx\n", addr1);
195      fclose(ofp);
196      return 1;
197    }
198
199  if(optind == (argc - 1))
200    {
201      imageCnt = 1;
202      goto writeHeader;
203    }
204
205  imageCnt = 2;
206
207  /* Copy Second Image */
208  optind++;
209  ifile = argv[optind];
210  ifp   = fopen(ifile,"rb");
211  if(ifp == NULL)
212    {
213      fprintf(stderr, "unable to open output file %s\n", ifile);
214      fclose(ofp);
215      return 1;
216    }
217
218  optind++;
219  addr2 = strtoul(argv[optind], &end, 0);
220  if(end == argv[optind])
221    {
222      fprintf(stderr, "bad image address %s\n", argv[optind]);
223      fclose(ofp);
224      return 1;
225    }
226
227  optind++;
228  size2 = strtoul(argv[optind], &end, 0);
229  if(end == argv[optind])
230    {
231      fprintf(stderr, "bad image size %s\n", argv[optind]);
232      fclose(ofp);
233      return 1;
234    }
235
236  /* Copy second image out and remember its length */
237  cnt  = 0;
238  for(;;)
239    {
240      len = fread(buf, 1, sizeof(buf), ifp);
241
242      if(len != 0)
243        {
244          fwrite(buf, len, 1, ofp);
245          cnt  += sizeof(buf);
246
247          if(len != sizeof(buf))
248            {
249              memset(buf, 0, sizeof(buf) - len);
250              fwrite(buf, 1, sizeof(buf) - len, ofp);
251              break;
252            }
253        }
254      else
255        {
256          break;
257        }
258    }
259
260  fclose(ifp);
261
262  len2 = cnt;
263
264  if(size2 == 0)
265    {
266      size2 = cnt;
267    }
268  else
269    {
270      memset(buf, 0, sizeof(buf));
271
272      while(cnt < size2)
273        {
274          fwrite(buf, 1, sizeof(buf), ofp);
275          cnt += sizeof(buf);
276        }
277
278      size2 = cnt;
279    }
280
281  /* Let us check against overlapping */
282  if(!((addr2 >= (addr1 + size1) && addr2 >= (headerAddr + sizeof(buf))) ||
283       (addr2 < addr1 && addr2 < headerAddr) ||
284       (addr1 > headerAddr && addr2 > (headerAddr + sizeof(buf)) &&
285        (addr2 + size2) <= addr1) ||
286       (addr1 < headerAddr && addr2 > (addr1 + size1) &&
287        (addr2 + size2) <= headerAddr)))
288
289    {
290      /* Areas overlapped */
291      printf("area overlapping: \n");
292      printf("header address       0x%08lx, its memory size 0x%08x\n",
293             headerAddr, sizeof(buf));
294      printf("first  image address 0x%08lx, its memory size 0x%08x\n",
295             addr1, size1);
296      printf("second image address 0x%08lx, its memory size 0x%08x\n",
297             addr2, size2);
298
299      fclose(ofp);
300      return 1;
301    }
302
303writeHeader:
304
305  /* We know everything so it is time to write buffer */
306  memset(buf, 0, 0x30);
307
308  buf[0x0]  = 0x36;
309  buf[0x1]  = 0x13;
310  buf[0x2]  = 0x03;
311  buf[0x3]  = 0x1b;
312
313  buf[0x4]  = 4;
314
315  /* Header address in ds:bx format */
316  buf[0x8]  = headerAddr & 0xf;
317  buf[0x9]  = 0;
318  buf[0xa]  = (headerAddr >> 4) & 0xff;
319  buf[0xb]  = (headerAddr >> 12) & 0xff;
320
321  /*
322   * Execute address in cs:ip format, which addr1
323   */
324  buf[0xc] = addr1 & 0xf;
325  buf[0xd] = 0;
326  buf[0xe] = (addr1 >> 4) & 0xff;
327  buf[0xf] = (addr1 >> 12) & 0xff;
328
329  /* Flags, tags and lengths */
330  buf[0x10] = 4;
331
332  if(imageCnt == 1)
333    {
334      buf[0x13] = 4;
335    }
336
337  /* Load address */
338  buf[0x14] = addr1 & 0xff;
339  buf[0x15] = (addr1 >> 8) & 0xff;
340  buf[0x16] = (addr1 >> 16) & 0xff;
341  buf[0x17] = (addr1 >> 24) & 0xff;
342
343  /* Image Length */
344  buf[0x18] = len1 & 0xff;
345  buf[0x19] = (len1 >> 8) & 0xff;
346  buf[0x1a] = (len1 >> 16) & 0xff;
347  buf[0x1b] = (len1 >> 24) & 0xff;
348
349  /* Memory Size */
350  buf[0x1c] = size1 & 0xff;
351  buf[0x1d] = (size1 >> 8) & 0xff;
352  buf[0x1e] = (size1 >> 16) & 0xff;
353  buf[0x1f] = (size1 >> 24) & 0xff;
354
355  if(imageCnt != 1)
356    {
357
358      /* Flags, tags and lengths */
359      buf[0x20] = 4;
360
361      buf[0x23] = 4;
362
363      /* Load address */
364      buf[0x24] = addr2 & 0xff;
365      buf[0x25] = (addr2 >> 8) & 0xff;
366      buf[0x26] = (addr2 >> 16) & 0xff;
367      buf[0x27] = (addr2 >> 24) & 0xff;
368
369      /* Image Length */
370      buf[0x28] = len2 & 0xff;
371      buf[0x29] = (len2 >> 8) & 0xff;
372      buf[0x2a] = (len2 >> 16) & 0xff;
373      buf[0x2b] = (len2 >> 24) & 0xff;
374
375      /* Memory Size */
376      buf[0x2c] = size2 & 0xff;
377      buf[0x2d] = (size2 >> 8) & 0xff;
378      buf[0x2e] = (size2 >> 16) & 0xff;
379      buf[0x2f] = (size2 >> 24) & 0xff;
380    }
381
382  rewind(ofp);
383
384  fwrite(buf, 1, 0x30, ofp);
385
386  fclose(ofp);
387
388  if(verbose)
389    {
390      printf("header address       0x%08lx, its memory size 0x%08x\n",
391             headerAddr, sizeof(buf));
392      printf("first  image address 0x%08lx, its memory size 0x%08x\n",
393             addr1, size1);
394      printf("second image address 0x%08lx, its memory size 0x%08x\n",
395             addr2, size2);
396    }
397
398  return 0;
399}
Note: See TracBrowser for help on using the repository browser.