Ticket #20526: patch-avr910.c.diff

File patch-avr910.c.diff, 5.2 KB (added by ranauei@…, 15 years ago)
  • avr910.c

    old new  
    5555  unsigned char use_blockmode;
    5656};
    5757
     58static char is_usb = 0;
     59#define READ_SIZE 64
     60static unsigned char extra_buf[1024+7];
     61
    5862#define PDATA(pgm) ((struct pdata *)(pgm->cookie))
    5963
    6064static void avr910_setup(PROGRAMMER * pgm)
     
    154158  return -1;
    155159}
    156160
     161static int can_cmd = 0;
    157162
    158163/*
    159164 * initialize the AVR device and prepare it to accept commands
     
    175180  avr910_send(pgm, "S", 1);
    176181  memset (id, 0, sizeof(id));
    177182  avr910_recv(pgm, id, sizeof(id)-1);
     183  is_usb = !strncmp(id, "USB910",6);
    178184
    179185  /* Get the HW and SW versions to see if the programmer is present. */
    180186
    181187  avr910_send(pgm, "V", 1);
    182188  avr910_recv(pgm, sw, sizeof(sw));
     189  if (sw[0] == '2') {
     190    can_cmd = 1;
     191  }
    183192
    184193  avr910_send(pgm, "v", 1);
    185194  avr910_recv(pgm, hw, sizeof(hw));
     
    304313{
    305314  char buf[5];
    306315
    307   /* FIXME: Insert version check here */
     316  if (!can_cmd) return -1;
    308317
    309318  buf[0] = '.';                 /* New Universal Command */
    310319  buf[1] = cmd[0];
     
    320329  res[2] = cmd[1];
    321330  res[3] = buf[0];
    322331
    323   return 0;
     332  return (buf[1] == 'Y')?0:-1;
    324333}
    325334
    326335
     
    518527  avr910_set_addr(pgm, addr>>1);
    519528
    520529  while (addr < max_addr) {
    521     page_wr_cmd_pending = 1;
    522     buf[0] = cmd[addr & 0x01];
    523     buf[1] = m->buf[addr];
    524     avr910_send(pgm, buf, sizeof(buf));
    525     avr910_vfy_cmd_sent(pgm, "write byte");
     530    if (is_usb && m->paged) {
     531      int i;
     532      int idx = 0;
     533      extra_buf[idx++] = 'A';
     534      extra_buf[idx++] = (addr>>(8+1)) & 0xff;
     535      extra_buf[idx++] = (addr>>1) & 0xff;
     536      for (i=0; i< page_size; i++) {
     537        extra_buf[idx++] = cmd[(addr+i)&0x01];
     538        extra_buf[idx++] = (addr + i >= max_addr)?0xff:m->buf[addr+i];
     539      }
     540      extra_buf[idx++] = 'A';
     541      extra_buf[idx++] = (addr>>(8+1)) & 0xff;
     542      extra_buf[idx++] = (addr>>1) & 0xff;
     543      extra_buf[idx++] = 'm';
     544      avr910_send(pgm, extra_buf, idx);
     545      avr910_recv(pgm, extra_buf, 3 + page_size);
     546      addr += page_size;
     547      usleep(m->max_write_delay);
     548    } else {
     549      page_wr_cmd_pending = 1;
     550      buf[0] = cmd[addr & 0x01];
     551      buf[1] = m->buf[addr];
     552      avr910_send(pgm, buf, sizeof(buf));
     553      avr910_vfy_cmd_sent(pgm, "write byte");
    526554
    527     addr++;
    528     page_bytes--;
     555      addr++;
     556      page_bytes--;
    529557
    530     if (m->paged && (page_bytes == 0)) {
    531       /* Send the "Issue Page Write" if we have sent a whole page. */
     558      if (m->paged && (page_bytes == 0)) {
     559        /* Send the "Issue Page Write" if we have sent a whole page. */
    532560
    533       avr910_set_addr(pgm, page_addr>>1);
    534       avr910_send(pgm, "m", 1);
    535       avr910_vfy_cmd_sent(pgm, "flush page");
     561        avr910_set_addr(pgm, page_addr>>1);
     562        avr910_send(pgm, "m", 1);
     563        avr910_vfy_cmd_sent(pgm, "flush page");
    536564
    537       page_wr_cmd_pending = 0;
    538       usleep(m->max_write_delay);
    539       avr910_set_addr(pgm, addr>>1);
     565        page_wr_cmd_pending = 0;
     566        usleep(m->max_write_delay);
     567        avr910_set_addr(pgm, addr>>1);
    540568
    541       /* Set page address for next page. */
     569        /* Set page address for next page. */
    542570
    543       page_addr = addr;
    544       page_bytes = page_size;
    545     }
    546     else if ((PDATA(pgm)->has_auto_incr_addr != 'Y') && ((addr & 0x01) == 0)) {
    547       avr910_set_addr(pgm, addr>>1);
     571        page_addr = addr;
     572        page_bytes = page_size;
     573      }
     574      else if ((PDATA(pgm)->has_auto_incr_addr != 'Y') && ((addr & 0x01) == 0)) {
     575        avr910_set_addr(pgm, addr>>1);
     576      }
    548577    }
    549 
    550578    report_progress (addr, max_addr, NULL);
    551579  }
    552580
     
    676704    avr910_set_addr(pgm, addr);
    677705
    678706    while (addr < max_addr) {
    679       avr910_send(pgm, &cmd, 1);
    680       if (cmd == 'R') {
    681         /* The 'R' command returns two bytes, MSB first, we need to put the data
    682            into the memory buffer LSB first. */
    683         avr910_recv(pgm, buf, 2);
    684         m->buf[addr*2]   = buf[1];  /* LSB */
    685         m->buf[addr*2+1] = buf[0];  /* MSB */
    686       }
    687       else {
    688         avr910_recv(pgm, (char *)&m->buf[addr], 1);
     707      if (is_usb && cmd == 'R') {
     708        int i;
     709        for (i=0; i<READ_SIZE/2; i++) {
     710          extra_buf[i] = 'R';
     711        }
     712        avr910_send(pgm, extra_buf, READ_SIZE/2);
     713        avr910_recv(pgm, extra_buf, READ_SIZE);
     714        for (i=0; i< READ_SIZE; i+=2) {
     715          m->buf[addr*2+i]   = extra_buf[i+1];  /* LSB */
     716          m->buf[addr*2+i+1] = extra_buf[i];    /* MSB */
     717        }
     718        addr += READ_SIZE/2;
     719      } else {
     720        avr910_send(pgm, &cmd, 1);
     721        if (cmd == 'R') {
     722          /* The 'R' command returns two bytes, MSB first, we need to put the data
     723             into the memory buffer LSB first. */
     724          avr910_recv(pgm, buf, 2);
     725          m->buf[addr*2]   = buf[1];  /* LSB */
     726          m->buf[addr*2+1] = buf[0];  /* MSB */
     727        } else {
     728          avr910_recv(pgm, (char *)&m->buf[addr], 1);
     729        }
     730
     731        addr++;
     732
     733        if (PDATA(pgm)->has_auto_incr_addr != 'Y') {
     734          avr910_set_addr(pgm, addr);
     735        }
    689736      }
    690 
    691       addr++;
    692 
    693       if (PDATA(pgm)->has_auto_incr_addr != 'Y') {
    694         avr910_set_addr(pgm, addr);
    695       }
    696 
    697737      report_progress (addr, max_addr, NULL);
    698738    }
    699739