FreeCalypso > hg > freecalypso-tools
view loadtools/flprogsrec.c @ 624:7485e75d9477
srec-regions: removed unnecessary prohibition against address going backward
author | Mychaela Falconia <falcon@freecalypso.org> |
---|---|
date | Thu, 27 Feb 2020 08:12:11 +0000 |
parents | 97fe41e9242a |
children | 9c5b0629e346 |
line wrap: on
line source
/* * This module implements the flash program-srec and flash program-m0 commands: * programming flash using S-record files as the data source. */ #include <sys/types.h> #include <stdio.h> #include <stdint.h> #include <stdlib.h> #include <time.h> #include "flash.h" #include "srecreader.h" extern struct flash_bank_info flash_bank_info[2]; flashcmd_progsrec_gen(bank, imgfile, is_m0) char *imgfile; { struct flash_bank_info *bi; struct srecreader srr; char *targv[4], shortarg[10], longarg[513]; int resp; unsigned long rec_count; time_t start_time, finish_time; unsigned duration, mm, ss; if (flash_detect(bank, 0) < 0) return(-1); bi = flash_bank_info + bank; srr.filename = imgfile; resp = open_srec_file(&srr); if (resp < 0) return(resp); sprintf(shortarg, "%lx", (u_long) bi->base_addr); targv[0] = bi->ops->loadagent_setbase_cmd; targv[1] = shortarg; targv[2] = 0; printf("Setting flash base address: %s %s\n", targv[0], targv[1]); tpinterf_make_cmd(targv); if (tpinterf_send_cmd() < 0) { fclose(srr.openfile); return(-1); } resp = tpinterf_pass_output(1); if (resp) { fclose(srr.openfile); return(resp); } if (bi->ops->prep_for_program(bi) < 0) { fclose(srr.openfile); return(-1); } targv[0] = bi->ops->loadagent_program_cmd; targv[1] = shortarg; targv[2] = longarg; targv[3] = 0; for (rec_count = 0; ; ) { if (read_s_record(&srr) < 0) { /* error msg already printed */ fclose(srr.openfile); return(-1); } if (srr.record_type == '0') { if (srr.lineno == 1) continue; fprintf(stderr, "Warning: S0 record found in line %d of %s (expected in line 1 only)\n", srr.lineno, srr.filename); continue; } else if (srr.record_type == '7') { time(&finish_time); break; } else if (srr.record_type != '3') { fprintf(stderr, "Warning: unsupported S%c record type in line %d of %s\n", srr.record_type, srr.lineno, srr.filename); continue; } /* must be S3 */ if (s3s7_get_addr_data(&srr) < 0) { /* error msg already printed */ fclose(srr.openfile); return(-1); } if (srr.datalen < 1) { fprintf(stderr, "%s line %d: S3 record of zero data length ignored\n", srr.filename, srr.lineno); continue; } if (srr.addr & 1 || srr.datalen & 1) { fprintf(stderr, "%s line %d: violates word alignment requirement\n", srr.filename, srr.lineno); fclose(srr.openfile); return(-1); } srr.addr &= bi->geom->total_size - 1; if (srr.addr + srr.datalen > bi->geom->total_size) { fprintf(stderr, "%s line %d: goes past the end of the flash bank\n", srr.filename, srr.lineno); fclose(srr.openfile); return(-1); } if (!rec_count) { printf("Programming flash, each \'.\' is 100 S-records\n"); time(&start_time); } sprintf(shortarg, "%lx", (u_long) srr.addr); build_flashw_hex_string(srr.record + 5, longarg, srr.datalen >> 1, is_m0); tpinterf_make_cmd(targv); if (tpinterf_send_cmd() < 0) { fclose(srr.openfile); return(-1); } resp = tpinterf_pass_output(8); /* 8 s timeout */ if (resp) { fclose(srr.openfile); return(resp); } rec_count++; if (rec_count % 100 == 0) { putchar('.'); fflush(stdout); } } /* got S7 */ fclose(srr.openfile); if (!rec_count) { fprintf(stderr, "%s line %d: S7 without any preceding S3 data records\n", srr.filename, srr.lineno); return(-1); } duration = finish_time - start_time; mm = duration / 60; ss = duration - mm * 60; printf("\nOperation completed in %um%us\n", mm, ss); return(0); } flashcmd_program_srec(argc, argv, bank) char **argv; { if (argc != 3) { fprintf(stderr, "usage: %s %s image.srec\n", argv[0], argv[1]); return(-1); } return flashcmd_progsrec_gen(bank, argv[2], 0); } flashcmd_program_m0(argc, argv, bank) char **argv; { if (argc != 3) { fprintf(stderr, "usage: %s %s image.m0\n", argv[0], argv[1]); return(-1); } return flashcmd_progsrec_gen(bank, argv[2], 1); }