Только в avrdude-5.11.1/: avrdude.spec diff -B -u -r avrdude-5.11.1/avrpart.h avrdude-5.11.1.new/avrpart.h --- avrdude-5.11.1/avrpart.h 2011-09-15 18:57:51.000000000 +0400 +++ avrdude-5.11.1.new/avrpart.h 2013-07-25 19:01:28.000000000 +0400 @@ -170,6 +170,7 @@ int page_size; /* size of memory page (if page addressed) */ int num_pages; /* number of pages (if page addressed) */ unsigned int offset; /* offset in IO memory (ATxmega) */ + int start_address; /* start address of programming region */ int min_write_delay; /* microseconds */ int max_write_delay; /* microseconds */ int pwroff_after_write; /* after this memory type is written to, diff -B -u -r avrdude-5.11.1/config_gram.y avrdude-5.11.1.new/config_gram.y --- avrdude-5.11.1/config_gram.y 2011-09-15 18:57:51.000000000 +0400 +++ avrdude-5.11.1.new/config_gram.y 2013-07-25 19:14:14.000000000 +0400 @@ -336,6 +336,7 @@ */ for (ln=lfirst(current_part->mem); ln; ln=lnext(ln)) { m = ldata(ln); + m->start_address = -1; if (m->paged) { if (m->page_size == 0) { fprintf(stderr, Только в avrdude-5.11.1/doc: avrdude.info Только в avrdude-5.11.1/doc: stamp-vti Только в avrdude-5.11.1/doc: version.texi diff -B -u -r avrdude-5.11.1/fileio.c avrdude-5.11.1.new/fileio.c --- avrdude-5.11.1/fileio.c 2011-09-15 18:37:05.000000000 +0400 +++ avrdude-5.11.1.new/fileio.c 2013-07-26 12:37:16.000000000 +0400 @@ -51,14 +51,14 @@ int recsize, int startaddr, char * outfile, FILE * outf); -static int ihex2b(char * infile, FILE * inf, +static int ihex2b(char * infile, FILE * inf, unsigned int * startaddr, unsigned char * outbuf, int bufsize); static int b2srec(unsigned char * inbuf, int bufsize, int recsize, int startaddr, char * outfile, FILE * outf); -static int srec2b(char * infile, FILE * inf, +static int srec2b(char * infile, FILE * inf, unsigned int * startaddr, unsigned char * outbuf, int bufsize); static int ihex_readrec(struct ihexrec * ihex, char * rec); @@ -261,7 +261,7 @@ * If an error occurs, return -1. * * */ -static int ihex2b(char * infile, FILE * inf, +static int ihex2b(char * infile, FILE * inf, unsigned int *start, unsigned char * outbuf, int bufsize) { char buffer [ MAX_LINE_LEN ]; @@ -272,6 +272,7 @@ int len; struct ihexrec ihex; int rc; + unsigned int startaddr; lineno = 0; buf = outbuf; @@ -279,6 +280,7 @@ maxaddr = 0; offsetaddr = 0; nextaddr = 0; + startaddr = 0xffffffff; while (fgets((char *)buffer,MAX_LINE_LEN,inf)!=NULL) { lineno++; @@ -304,6 +306,8 @@ switch (ihex.rectyp) { case 0: /* data record */ nextaddr = ihex.loadofs + baseaddr; + if (nextaddr-offsetaddr < startaddr) + startaddr = nextaddr; if ((nextaddr + ihex.reclen) > (bufsize+offsetaddr)) { fprintf(stderr, "%s: ERROR: address 0x%04x out of range at line %d of %s\n", @@ -318,6 +322,8 @@ break; case 1: /* end of file record */ + if (start) + *start = startaddr; return maxaddr-offsetaddr; break; @@ -353,7 +359,8 @@ "%s: WARNING: no end of file record found for Intel Hex " "file \"%s\"\n", progname, infile); - + if (start) + *start = startaddr; return maxaddr-offsetaddr; } @@ -539,7 +546,7 @@ } -static int srec2b(char * infile, FILE * inf, +static int srec2b(char * infile, FILE * inf, unsigned int * start, unsigned char * outbuf, int bufsize) { char buffer [ MAX_LINE_LEN ]; @@ -552,6 +559,7 @@ int rc; int reccount; unsigned char datarec; + unsigned int startaddr; char * msg = 0; @@ -560,6 +568,7 @@ baseaddr = 0; maxaddr = 0; reccount = 0; + startaddr = 0xffffffff; while (fgets((char *)buffer,MAX_LINE_LEN,inf)!=NULL) { lineno++; @@ -626,6 +635,8 @@ case 0x37: /* S7 Record - end record for 32 bit address data */ case 0x38: /* S8 Record - end record for 24 bit address data */ case 0x39: /* S9 Record - end record for 16 bit address data */ + if (start) + *start = startaddr; return maxaddr; default: @@ -638,6 +649,8 @@ if (datarec == 1) { nextaddr = srec.loadofs + baseaddr; + if (nextaddr < startaddr) + startaddr = nextaddr; if (nextaddr + srec.reclen > bufsize) { fprintf(stderr, msg, progname, nextaddr+srec.reclen, lineno, infile); return -1; @@ -655,7 +668,8 @@ "%s: WARNING: no end of file record found for Motorola S-Records " "file \"%s\"\n", progname, infile); - + if (start) + *start = startaddr; return maxaddr; } @@ -776,8 +790,8 @@ } -static int fileio_ihex(struct fioparms * fio, - char * filename, FILE * f, unsigned char * buf, int size) +static int fileio_ihex(struct fioparms * fio, char * filename, + FILE * f, unsigned char * buf, int size) { int rc; @@ -790,7 +804,7 @@ break; case FIO_READ: - rc = ihex2b(filename, f, buf, size); + rc = ihex2b(filename, f, &fio->startaddr, buf, size); if (rc < 0) return -1; break; @@ -820,7 +834,7 @@ break; case FIO_READ: - rc = srec2b(filename, f, buf, size); + rc = srec2b(filename, f, &fio->startaddr, buf, size); if (rc < 0) return -1; break; @@ -1037,7 +1051,11 @@ /* point at the requested memory buffer */ buf = mem->buf; if (fio.op == FIO_READ) + { + fio.startaddr = 0xffffffff; + mem->start_address = -1; size = mem->size; + } if (fio.op == FIO_READ) { /* 0xff fill unspecified memory */ @@ -1114,10 +1132,20 @@ switch (format) { case FMT_IHEX: rc = fileio_ihex(&fio, fname, f, buf, size); + if (fio.op == FIO_READ && fio.startaddr != 0xffffffff && mem->paged) + { + mem->start_address = (int)fio.startaddr; + mem->start_address = mem->start_address - (mem->start_address % mem->page_size); + } break; case FMT_SREC: rc = fileio_srec(&fio, fname, f, buf, size); + if (fio.op == FIO_READ && fio.startaddr != 0xffffffff && mem->paged) + { + mem->start_address = (int)fio.startaddr; + mem->start_address = mem->start_address - (mem->start_address % mem->page_size); + } break; case FMT_RBIN: diff -B -u -r avrdude-5.11.1/fileio.h avrdude-5.11.1.new/fileio.h --- avrdude-5.11.1/fileio.h 2011-09-15 18:37:05.000000000 +0400 +++ avrdude-5.11.1.new/fileio.h 2013-07-26 12:12:04.000000000 +0400 @@ -40,6 +40,7 @@ char * iodesc; char * dir; char * rw; + unsigned int startaddr; }; enum { Только в avrdude-5.11.1.new/: paged_write Только в avrdude-5.11.1.new/: page_size diff -B -u -r avrdude-5.11.1/update.c avrdude-5.11.1.new/update.c --- avrdude-5.11.1/update.c 2011-09-15 18:37:05.000000000 +0400 +++ avrdude-5.11.1.new/update.c 2013-07-26 11:30:10.000000000 +0400 @@ -332,6 +332,9 @@ } report_progress (0,1,"Reading"); + // copy start_address for upd->memtype from p to v + AVRMEM *vmem = avr_locate_mem(v,upd->memtype); + vmem->start_address = mem->start_address; rc = avr_read(pgm, v, upd->memtype, size, 1); if (rc < 0) { fprintf(stderr, "%s: failed to read all of %s memory, rc=%d\n", diff -B -u -r avrdude-5.11.1/usbasp.c avrdude-5.11.1.new/usbasp.c --- avrdude-5.11.1/usbasp.c 2011-09-15 18:37:05.000000000 +0400 +++ avrdude-5.11.1.new/usbasp.c 2013-07-26 16:45:17.000000000 +0400 @@ -615,6 +615,9 @@ return -2; } + int to_read = 0; + if ( m->start_address == -1 ) + to_read = 1; /* set blocksize depending on sck frequency */ if ((PDATA(pgm)->sckfreq_hz > 0) && (PDATA(pgm)->sckfreq_hz < 10000)) { blocksize = USBASP_READBLOCKSIZE / 10; @@ -623,10 +626,31 @@ } while (wbytes) { + if (!to_read) + { + if (address >= m->start_address) + { + to_read = 1; + if (address > m->start_address) + { + wbytes += address - m->start_address; + buffer -= address - m->start_address; + address -= address - m->start_address; + } + } + } if (wbytes <= blocksize) { blocksize = wbytes; } wbytes -= blocksize; + if (!to_read) + { + buffer += blocksize; + address += blocksize; + + report_progress (address, n_bytes, NULL); + continue; + } /* set address (new mode) - if firmware on usbasp support newmode, then they use address from this command */ unsigned char temp[4]; @@ -682,6 +706,9 @@ return -2; } + int to_write = 0; + if ( m->start_address == -1 ) + to_write = 1; /* set blocksize depending on sck frequency */ if ((PDATA(pgm)->sckfreq_hz > 0) && (PDATA(pgm)->sckfreq_hz < 10000)) { blocksize = USBASP_WRITEBLOCKSIZE / 10; @@ -688,14 +715,33 @@ } else { blocksize = USBASP_WRITEBLOCKSIZE; } - while (wbytes) { - + if (!to_write) + { + if (address >= m->start_address) + { + to_write = 1; + if (address > m->start_address) + { + wbytes += address - m->start_address; + buffer -= address - m->start_address; + address -= address - m->start_address; + } + } + } if (wbytes <= blocksize) { blocksize = wbytes; blockflags |= USBASP_BLOCKFLAG_LAST; } wbytes -= blocksize; + if (!to_write) + { + buffer += blocksize; + address += blocksize; + + report_progress (address, n_bytes, NULL); + continue; + } /* set address (new mode) - if firmware on usbasp support newmode, then