From 0f5af86c9f6373e0251b803a1148c6f255557453 Mon Sep 17 00:00:00 2001
From: Joerg Wunsch <j@uriah.heep.sax.de>
Date: Tue, 3 Sep 2013 21:24:16 +0000
Subject: [PATCH] Submitted by Fred (magister): bug #38951: AVR109 use byte
 offset instead of word offset patch #8045: AVR109 butterfly failing *
 butterfly.c (butterfly_paged_load, butterfly_paged_write): fix calculation of
 'A' address when operating on flash memory. It must be given in terms of
 16-bit words rather than bytes.

git-svn-id: svn://svn.savannah.nongnu.org/avrdude/trunk/avrdude@1205 81a1dc3b-b13d-400b-aceb-764788c761c2
---
 ChangeLog   | 11 ++++++++++-
 NEWS        |  1 +
 butterfly.c | 18 +++++++++++-------
 3 files changed, 22 insertions(+), 8 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index c9220ebe..e6ad1c8a 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,6 +1,15 @@
+2013-09-03  Joerg Wunsch <j.gnu@uriah.heep.sax.de>
+
+	Submitted by Fred (magister):
+	bug #38951: AVR109 use byte offset instead of word offset
+	patch #8045: AVR109 butterfly failing
+	* butterfly.c (butterfly_paged_load, butterfly_paged_write):
+	fix calculation of 'A' address when operating on flash memory.
+	It must be given in terms of 16-bit words rather than bytes.
+
 2013-09-03  Rene Liebscher <R.Liebscher@gmx.de>
 
-	* avrftdi.c, avrftdi_private.h: added tx buffer size, and use 
+	* avrftdi.c, avrftdi_private.h: added tx buffer size, and use
 	smaller block sizes as larger sometimes hang
 
 2013-09-03  Joerg Wunsch <j.gnu@uriah.heep.sax.de>
diff --git a/NEWS b/NEWS
index c48ef402..c1f22ffc 100644
--- a/NEWS
+++ b/NEWS
@@ -89,6 +89,7 @@ Current:
       - bug #38307: Can't write usersig of an xmega256a3
       - bug #38580 Current svn head, xmega and fuses, all fuses tied to fuse0
       - bug #39691 Buffer overrun when reading EEPROM byte with JTAGICE3
+      - bug #38951: AVR109 use byte offset instead of word offset
 
   * Keep track of input file contents
 
diff --git a/butterfly.c b/butterfly.c
index 9628e54b..b114ab19 100644
--- a/butterfly.c
+++ b/butterfly.c
@@ -589,17 +589,18 @@ static int butterfly_paged_write(PROGRAMMER * pgm, AVRPART * p, AVRMEM * m,
   char *cmd;
   unsigned int blocksize = PDATA(pgm)->buffersize;
   int use_ext_addr = m->op[AVR_OP_LOAD_EXT_ADDR] != NULL;
+  unsigned int wr_size = 2;
 
   if (strcmp(m->desc, "flash") && strcmp(m->desc, "eeprom")) 
     return -2;
 
   if (m->desc[0] == 'e')
-    blocksize = 1;		/* Write to eeprom single bytes only */
+    wr_size = blocksize = 1;		/* Write to eeprom single bytes only */
 
   if (use_ext_addr) {
-    butterfly_set_extaddr(pgm, addr);
+    butterfly_set_extaddr(pgm, addr / wr_size);
   } else {
-    butterfly_set_addr(pgm, addr);
+    butterfly_set_addr(pgm, addr / wr_size);
   }
 
 #if 0
@@ -638,24 +639,27 @@ static int butterfly_paged_load(PROGRAMMER * pgm, AVRPART * p, AVRMEM * m,
                                 unsigned int addr, unsigned int n_bytes)
 {
   unsigned int max_addr = addr + n_bytes;
-  int rd_size = 1;
+  int rd_size = 2;
+  int blocksize = PDATA(pgm)->buffersize;
   int use_ext_addr = m->op[AVR_OP_LOAD_EXT_ADDR] != NULL;
 
   /* check parameter syntax: only "flash" or "eeprom" is allowed */
   if (strcmp(m->desc, "flash") && strcmp(m->desc, "eeprom")) 
     return -2;
 
+  if (m->desc[0] == 'e')
+    rd_size = blocksize = 1;		/* Read from eeprom single bytes only */
+
   {		/* use buffered mode */
     char cmd[4];
-    int blocksize = PDATA(pgm)->buffersize;
 
     cmd[0] = 'g';
     cmd[3] = toupper((int)(m->desc[0]));
 
     if (use_ext_addr) {
-      butterfly_set_extaddr(pgm, addr);
+      butterfly_set_extaddr(pgm, addr / rd_size);
     } else {
-      butterfly_set_addr(pgm, addr);
+      butterfly_set_addr(pgm, addr / rd_size);
     }
     while (addr < max_addr) {
       if ((max_addr - addr) < blocksize) {