comparison loadtools/ltdump.c @ 36:65111e6eee9e

loadtool: dump2bin and dump2srec implemented
author Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
date Mon, 06 May 2013 02:04:56 +0000
parents 05af070c4b60
children 1f035187e98f
comparison
equal deleted inserted replaced
35:05af070c4b60 36:65111e6eee9e
8 #include <stdint.h> 8 #include <stdint.h>
9 #include <string.h> 9 #include <string.h>
10 #include <strings.h> 10 #include <strings.h>
11 #include <stdlib.h> 11 #include <stdlib.h>
12 12
13 extern uint32_t crc32_table[];
13 extern char target_response_line[]; 14 extern char target_response_line[];
14 15
15 crc32_on_target(area_base, area_len, retptr) 16 crc32_on_target(area_base, area_len, retptr)
16 u_long area_base, area_len, *retptr; 17 u_long area_base, area_len, *retptr;
17 { 18 {
61 if (stat == 0) 62 if (stat == 0)
62 printf("%08lX\n", crc_result); 63 printf("%08lX\n", crc_result);
63 return(stat); 64 return(stat);
64 } 65 }
65 66
67 /* the actual dump facility */
68
69 static FILE *dump_outfile;
70 static int dump_save_srec;
71 static uint32_t dump_nextaddr, dump_crcaccum;
72 static u_char dump_binrec[0x86];
73
74 static
75 dump_receiver(line)
76 char *line;
77 {
78 int i, b;
79 u_char sr_cksum;
80 uint32_t addr_from_srec;
81
82 if (strncmp(line, "S385", 4)) {
83 fprintf(stderr,
84 "error: target response is not the expected S385...\n");
85 return(-1);
86 }
87 for (i = 0; i < 0x86; i++) {
88 b = decode_hex_byte(line + i*2 + 2);
89 if (b < 0) {
90 fprintf(stderr,
91 "data from target: S-record hex decode error\n");
92 return(-1);
93 }
94 dump_binrec[i] = b;
95 }
96 sr_cksum = 0;
97 for (i = 0; i < 0x86; i++)
98 sr_cksum += dump_binrec[i];
99 if (sr_cksum != 0xFF) {
100 fprintf(stderr, "data from target: bad S-record checksum\n");
101 return(-1);
102 }
103 /* basic S-record format OK; now verify the address */
104 addr_from_srec = ((uint32_t) dump_binrec[1] << 24) |
105 ((uint32_t) dump_binrec[2] << 16) |
106 ((uint32_t) dump_binrec[3] << 8) |
107 (uint32_t) dump_binrec[4];
108 if (addr_from_srec != dump_nextaddr) {
109 fprintf(stderr,
110 "error: S3 record from target has the wrong address\n");
111 return(-1);
112 }
113 /* all checks passed - save it */
114 if (dump_save_srec)
115 fprintf(dump_outfile, "%s\n", line);
116 else
117 fwrite(dump_binrec + 5, 1, 0x80, dump_outfile);
118 /* update running CRC */
119 for (i = 0; i < 0x80; i++)
120 dump_crcaccum = crc32_table[dump_crcaccum & 0xFF ^
121 dump_binrec[i+5]] ^
122 (dump_crcaccum >> 8);
123 /* progress indication */
124 putchar('.');
125 fflush(stdout);
126 dump_nextaddr += 0x80;
127 return(1);
128 }
129
130 loadtool_memdump(start_addr, area_len, filename, fmt_srec)
131 u_long start_addr, area_len;
132 char *filename;
133 {
134 u_long target_crc_init, target_crc_fin;
135 char *target_argv[4], target_arg1[10], target_arg2[10];
136 int stat;
137
138 if (start_addr & 0x7F || area_len & 0x7F) {
139 fprintf(stderr,
140 "error: implementation limit: 128-byte alignment required\n");
141 return(-1);
142 }
143 printf("Requesting initial CRC-32 of the area from target...\n");
144 stat = crc32_on_target(start_addr, area_len, &target_crc_init);
145 if (stat)
146 return(stat);
147 printf("got %08lX\n", target_crc_init);
148 dump_outfile = fopen(filename, "w");
149 if (!dump_outfile) {
150 perror(filename);
151 return(-1);
152 }
153 dump_save_srec = fmt_srec;
154 dump_nextaddr = start_addr;
155 dump_crcaccum = 0xFFFFFFFF;
156
157 printf("Requesting memory dump...\n");
158 sprintf(target_arg1, "%lx", start_addr);
159 sprintf(target_arg2, "%lx", area_len);
160 target_argv[0] = "DUMP";
161 target_argv[1] = target_arg1;
162 target_argv[2] = target_arg2;
163 target_argv[3] = 0;
164 tpinterf_make_cmd(target_argv);
165 stat = tpinterf_send_cmd();
166 if (stat < 0) {
167 fclose(dump_outfile);
168 return(stat);
169 }
170 stat = tpinterf_capture_output(2, dump_receiver);
171 fclose(dump_outfile);
172 if (stat < 0)
173 return(stat);
174 putchar('\n'); /* after lots of dots */
175
176 /* sanity checks */
177 if (dump_nextaddr != start_addr + area_len) {
178 fprintf(stderr,
179 "error: received dump length does not match expected\n");
180 return(-1);
181 }
182 if (dump_crcaccum != (uint32_t) target_crc_init) {
183 fprintf(stderr, "error: CRC mismatch (computed %lX)\n",
184 (u_long) dump_crcaccum);
185 return(-1);
186 }
187 printf("Requesting another CRC-32 of the area from target...\n");
188 stat = crc32_on_target(start_addr, area_len, &target_crc_fin);
189 if (stat)
190 return(stat);
191 if (target_crc_fin == target_crc_init) {
192 printf("match, dump successful\n");
193 return(0);
194 } else {
195 fprintf(stderr, "mismatch: got %lX this time\n",
196 target_crc_fin);
197 return(-1);
198 }
199 }
200
66 cmd_dump2bin(argc, argv) 201 cmd_dump2bin(argc, argv)
67 char **argv; 202 char **argv;
68 { 203 {
69 204 u_long area_base, area_len;
70 205 char *strtoul_endp;
71 } 206
207 area_base = strtoul(argv[1], &strtoul_endp, 16);
208 if (*strtoul_endp) {
209 inv: fprintf(stderr, "usage: dump2bin hex-start hex-len outfile\n");
210 return(-1);
211 }
212 area_len = strtoul(argv[2], &strtoul_endp, 16);
213 if (*strtoul_endp)
214 goto inv;
215 return loadtool_memdump(area_base, area_len, argv[3], 0);
216 }
217
218 cmd_dump2srec(argc, argv)
219 char **argv;
220 {
221 u_long area_base, area_len;
222 char *strtoul_endp;
223
224 area_base = strtoul(argv[1], &strtoul_endp, 16);
225 if (*strtoul_endp) {
226 inv: fprintf(stderr, "usage: dump2srec hex-start hex-len outfile\n");
227 return(-1);
228 }
229 area_len = strtoul(argv[2], &strtoul_endp, 16);
230 if (*strtoul_endp)
231 goto inv;
232 return loadtool_memdump(area_base, area_len, argv[3], 1);
233 }