c44c6c079ec6576660e058f5af7652ac286f3f5a
[fw/sdcc] / support / makebin / makebin.c
1 /** @name makebin - turn a .ihx file into a binary image.
2  */
3 #include <stdio.h>
4 #include <unistd.h>
5 #include <stdlib.h>
6
7 typedef unsigned char BYTE;
8
9 #define FILL_BYTE 0xFF
10
11 int getnibble(char **p)
12 {
13   int ret = *((*p)++) - '0';
14   if (ret > 9) {
15     ret -= 'A' - '9' - 1;
16   }
17   return ret;
18 }
19
20 int getbyte(char **p)
21 {
22   return (getnibble(p) << 4) | getnibble(p);
23 }
24
25 int main(int argc, char **argv)
26 {
27     int opt;
28     int size = 32768, pack = 0, real_size = 0;
29     BYTE *rom;
30     char line[256];
31     char *p;
32
33     while ((opt = getopt(argc, argv, "ps:h"))!=-1) {
34         switch (opt) {
35         case 's':
36             size = atoi(optarg);
37             break;
38         case 'h':
39             printf("makebin: convert a Intel IHX file to binary.\n"
40                    "Usage: %s [-p] [-s romsize] [-h]\n", argv[0]);
41             return 0;
42         case 'p':
43             pack = 1;
44             break;
45         default:
46             return 1;
47         }
48     }
49     rom = malloc(size);
50     if (rom == NULL) {
51         fprintf(stderr, "error: couldn't allocate room for the image.\n");
52         return -1;
53     }
54     memset(rom, FILL_BYTE, size);
55     while (fgets(line, 256, stdin) != NULL) {
56         int nbytes;
57         int addr;
58
59         if (*line != ':') {
60             fprintf(stderr, "error: invalid IHX line.\n");
61             return -2;
62         }
63         p = line+1;
64         nbytes = getbyte(&p);
65         addr = getbyte(&p)<<8 | getbyte(&p);
66         getbyte(&p);
67
68         while (nbytes--) {
69             if (addr < size)
70                 rom[addr++] = getbyte(&p);
71         }
72
73         if (addr > real_size)
74             real_size = addr;
75     }
76
77     if (pack)
78         fwrite(rom, 1, real_size, stdout);
79     else
80         fwrite(rom, 1, size, stdout);
81     
82     return 0;
83 }