Contributed by dcm@mit.edu: add support for the
AVRISP mkII device. (Savannah patch #4789.) * serial.h: Declare usb_serdev_frame device descriptor. * stk500v2.c: Implementation of the AVRISP mkII handling. * usb_libusb.c: Add USB handling for short-frame delimited AVRISP mkII USB protocol; add distinction of different devices in usbdev_open(). * jtagmkII.c: Tell usbdev_open() to search for the JTAG ICE mkII. * usbdevs.h: (New file.) * Makefile.am: Add usbdevs.h, as well as some other forgotten files "make distcheck" complained about. * avrdude.conf.in: Add more aliases for the AVRISP mkII. * avrdude.1: Document how to use the AVRISP mkII. * doc/avrdude.texi: (Ditto.) git-svn-id: svn://svn.savannah.nongnu.org/avrdude/trunk/avrdude@564 81a1dc3b-b13d-400b-aceb-764788c761c2
This commit is contained in:
parent
655094b681
commit
108793bc7a
17
ChangeLog
17
ChangeLog
|
@ -1,3 +1,20 @@
|
||||||
|
2006-01-13 Joerg Wunsch <j@uriah.heep.sax.de>
|
||||||
|
|
||||||
|
Contributed by dcm@mit.edu: add support for the
|
||||||
|
AVRISP mkII device. (Savannah patch #4789.)
|
||||||
|
* serial.h: Declare usb_serdev_frame device descriptor.
|
||||||
|
* stk500v2.c: Implementation of the AVRISP mkII handling.
|
||||||
|
* usb_libusb.c: Add USB handling for short-frame delimited
|
||||||
|
AVRISP mkII USB protocol; add distinction of different
|
||||||
|
devices in usbdev_open().
|
||||||
|
* jtagmkII.c: Tell usbdev_open() to search for the JTAG ICE mkII.
|
||||||
|
* usbdevs.h: (New file.)
|
||||||
|
* Makefile.am: Add usbdevs.h, as well as some other forgotten
|
||||||
|
files "make distcheck" complained about.
|
||||||
|
* avrdude.conf.in: Add more aliases for the AVRISP mkII.
|
||||||
|
* avrdude.1: Document how to use the AVRISP mkII.
|
||||||
|
* doc/avrdude.texi: (Ditto.)
|
||||||
|
|
||||||
2006-01-12 Joerg Wunsch <j@uriah.heep.sax.de>
|
2006-01-12 Joerg Wunsch <j@uriah.heep.sax.de>
|
||||||
|
|
||||||
* avrdude.conf.in: Add EEPROM page instructions for the
|
* avrdude.conf.in: Add EEPROM page instructions for the
|
||||||
|
|
|
@ -22,6 +22,7 @@
|
||||||
#
|
#
|
||||||
|
|
||||||
EXTRA_DIST = \
|
EXTRA_DIST = \
|
||||||
|
ChangeLog \
|
||||||
ChangeLog-2001 \
|
ChangeLog-2001 \
|
||||||
ChangeLog-2002 \
|
ChangeLog-2002 \
|
||||||
ChangeLog-2003 \
|
ChangeLog-2003 \
|
||||||
|
@ -69,6 +70,7 @@ avrdude_SOURCES = \
|
||||||
crc16.h \
|
crc16.h \
|
||||||
fileio.c \
|
fileio.c \
|
||||||
fileio.h \
|
fileio.h \
|
||||||
|
freebsd_ppi.h \
|
||||||
jtagmkI.c \
|
jtagmkI.c \
|
||||||
jtagmkI.h \
|
jtagmkI.h \
|
||||||
jtagmkI_private.h \
|
jtagmkI_private.h \
|
||||||
|
@ -95,6 +97,7 @@ avrdude_SOURCES = \
|
||||||
serbb_win32.c \
|
serbb_win32.c \
|
||||||
ser_posix.c \
|
ser_posix.c \
|
||||||
ser_win32.c \
|
ser_win32.c \
|
||||||
|
solaris_ecpp.h \
|
||||||
stk500.c \
|
stk500.c \
|
||||||
stk500.h \
|
stk500.h \
|
||||||
stk500_private.h \
|
stk500_private.h \
|
||||||
|
@ -103,6 +106,7 @@ avrdude_SOURCES = \
|
||||||
stk500v2_private.h \
|
stk500v2_private.h \
|
||||||
term.c \
|
term.c \
|
||||||
term.h \
|
term.h \
|
||||||
|
usbdevs.h \
|
||||||
usb_libusb.c
|
usb_libusb.c
|
||||||
|
|
||||||
man_MANS = avrdude.1
|
man_MANS = avrdude.1
|
||||||
|
|
|
@ -55,6 +55,7 @@ is a program for downloading code and data to Atmel AVR
|
||||||
microcontrollers.
|
microcontrollers.
|
||||||
.Nm Avrdude
|
.Nm Avrdude
|
||||||
supports Atmel's STK500 programmer,
|
supports Atmel's STK500 programmer,
|
||||||
|
Atmel's AVRISP and AVRISP mkII devices,
|
||||||
Atmel's JTAG ICE (both mkI and mkII),
|
Atmel's JTAG ICE (both mkI and mkII),
|
||||||
programmers complying to AppNote AVR910 and AVR109 (including the Butterfly),
|
programmers complying to AppNote AVR910 and AVR109 (including the Butterfly),
|
||||||
as well as a simple hard-wired
|
as well as a simple hard-wired
|
||||||
|
@ -352,6 +353,9 @@ from any JTAG ICE mkII found on USB.
|
||||||
The match is done after stripping any existing colons from the given
|
The match is done after stripping any existing colons from the given
|
||||||
serial number, and right-to-left, so only the least significant bytes
|
serial number, and right-to-left, so only the least significant bytes
|
||||||
from the serial number need to be given.
|
from the serial number need to be given.
|
||||||
|
.Pp
|
||||||
|
As the AVRISP mkII device can only be talked to over USB, the very
|
||||||
|
same method of specifying the port is required there.
|
||||||
.It Fl q
|
.It Fl q
|
||||||
Disable (or quell) output of the progress bar while reading or writing
|
Disable (or quell) output of the progress bar while reading or writing
|
||||||
to the device. Specify it a second time for even quieter operation.
|
to the device. Specify it a second time for even quieter operation.
|
||||||
|
|
|
@ -233,6 +233,18 @@ programmer
|
||||||
type = stk500v2;
|
type = stk500v2;
|
||||||
;
|
;
|
||||||
|
|
||||||
|
programmer
|
||||||
|
id = "avrispmkII";
|
||||||
|
desc = "Atmel AVR ISP mkII";
|
||||||
|
type = stk500v2;
|
||||||
|
;
|
||||||
|
|
||||||
|
programmer
|
||||||
|
id = "avrisp2";
|
||||||
|
desc = "Atmel AVR ISP mkII";
|
||||||
|
type = stk500v2;
|
||||||
|
;
|
||||||
|
|
||||||
programmer
|
programmer
|
||||||
id = "stk500";
|
id = "stk500";
|
||||||
desc = "Atmel STK500";
|
desc = "Atmel STK500";
|
||||||
|
|
|
@ -135,7 +135,8 @@ from the contents of a file, while interactive mode is useful for
|
||||||
exploring memory contents, modifing individual bytes of eeprom,
|
exploring memory contents, modifing individual bytes of eeprom,
|
||||||
programming fuse/lock bits, etc.
|
programming fuse/lock bits, etc.
|
||||||
|
|
||||||
AVRDUDE supports six basic programmer types: Atmel's STK500,
|
AVRDUDE supports the following basic programmer types: Atmel's STK500,
|
||||||
|
Atmel's AVRISP and AVRISP mkII devices,
|
||||||
Atmel's JTAG ICE (both mkI and mkII), appnote
|
Atmel's JTAG ICE (both mkI and mkII), appnote
|
||||||
avr910, appnote avr109 (including the AVR Butterfly),
|
avr910, appnote avr109 (including the AVR Butterfly),
|
||||||
serial bit-bang adapters,
|
serial bit-bang adapters,
|
||||||
|
@ -430,7 +431,16 @@ Atmel Low Cost Serial Programmer
|
||||||
Atmel AppNote AVR911 AVROSP (an alias for avr109)
|
Atmel AppNote AVR911 AVROSP (an alias for avr109)
|
||||||
|
|
||||||
@itemx avrisp
|
@itemx avrisp
|
||||||
Atmel AVR ISP
|
Atmel AVR ISP (an alias for stk500)
|
||||||
|
|
||||||
|
@itemx avrispv2
|
||||||
|
Atmel AVR ISP, running a version 2.x firmware (an alias for stk500v2)
|
||||||
|
|
||||||
|
@itemx avrispmkII
|
||||||
|
Atmel AVR ISP mkII (alias for stk500v2)
|
||||||
|
|
||||||
|
@itemx avrispmk2
|
||||||
|
Atmel AVR ISP mkII (alias for stk500v2)
|
||||||
|
|
||||||
@itemx bascom
|
@itemx bascom
|
||||||
Bascom SAMPLE programming cable
|
Bascom SAMPLE programming cable
|
||||||
|
@ -480,7 +490,7 @@ STK200
|
||||||
Atmel STK500
|
Atmel STK500
|
||||||
|
|
||||||
@itemx stk500v2
|
@itemx stk500v2
|
||||||
Atmel STK500, running a verrsion 2.x firmware
|
Atmel STK500, running a version 2.x firmware
|
||||||
|
|
||||||
@end table
|
@end table
|
||||||
|
|
||||||
|
@ -579,6 +589,9 @@ bytes from the serial number need to be given.
|
||||||
For a trick how to find out the serial numbers of all JTAG ICEs
|
For a trick how to find out the serial numbers of all JTAG ICEs
|
||||||
attached to USB, see @ref{Example Command Line Invocations}.
|
attached to USB, see @ref{Example Command Line Invocations}.
|
||||||
|
|
||||||
|
As the AVRISP mkII device can only be talked to over USB, the very
|
||||||
|
same method of specifying the port is required there.
|
||||||
|
|
||||||
@item -q
|
@item -q
|
||||||
Disable (or quell) output of the progress bar while reading or writing
|
Disable (or quell) output of the progress bar while reading or writing
|
||||||
to the device. Specify it a second time for even quieter operation.
|
to the device. Specify it a second time for even quieter operation.
|
||||||
|
|
33
jtagmkII.c
33
jtagmkII.c
|
@ -1,6 +1,6 @@
|
||||||
/*
|
/*
|
||||||
* avrdude - A Downloader/Uploader for AVR device programmers
|
* avrdude - A Downloader/Uploader for AVR device programmers
|
||||||
* Copyright (C) 2005 Joerg Wunsch <j@uriah.heep.sax.de>
|
* Copyright (C) 2005,2006 Joerg Wunsch <j@uriah.heep.sax.de>
|
||||||
*
|
*
|
||||||
* Derived from stk500 code which is:
|
* Derived from stk500 code which is:
|
||||||
* Copyright (C) 2002-2004 Brian S. Dean <bsd@bsdhome.com>
|
* Copyright (C) 2002-2004 Brian S. Dean <bsd@bsdhome.com>
|
||||||
|
@ -43,6 +43,7 @@
|
||||||
#include "pgm.h"
|
#include "pgm.h"
|
||||||
#include "jtagmkII_private.h"
|
#include "jtagmkII_private.h"
|
||||||
#include "serial.h"
|
#include "serial.h"
|
||||||
|
#include "usbdevs.h"
|
||||||
|
|
||||||
|
|
||||||
extern int verbose;
|
extern int verbose;
|
||||||
|
@ -1044,26 +1045,34 @@ static void jtagmkII_enable(PROGRAMMER * pgm)
|
||||||
|
|
||||||
static int jtagmkII_open(PROGRAMMER * pgm, char * port)
|
static int jtagmkII_open(PROGRAMMER * pgm, char * port)
|
||||||
{
|
{
|
||||||
|
long baud;
|
||||||
|
|
||||||
if (verbose >= 2)
|
if (verbose >= 2)
|
||||||
fprintf(stderr, "%s: jtagmkII_open()\n", progname);
|
fprintf(stderr, "%s: jtagmkII_open()\n", progname);
|
||||||
|
|
||||||
#if defined(HAVE_LIBUSB)
|
|
||||||
/*
|
|
||||||
* If the port name starts with "usb", divert the serial routines
|
|
||||||
* to the USB ones.
|
|
||||||
*/
|
|
||||||
if (strncmp(port, "usb", 3) == 0)
|
|
||||||
serdev = &usb_serdev;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
strcpy(pgm->port, port);
|
|
||||||
/*
|
/*
|
||||||
* The JTAG ICE mkII always starts with a baud rate of 19200 Bd upon
|
* The JTAG ICE mkII always starts with a baud rate of 19200 Bd upon
|
||||||
* attaching. If the config file or command-line parameters specify
|
* attaching. If the config file or command-line parameters specify
|
||||||
* a higher baud rate, we switch to it later on, after establishing
|
* a higher baud rate, we switch to it later on, after establishing
|
||||||
* the connection with the ICE.
|
* the connection with the ICE.
|
||||||
*/
|
*/
|
||||||
pgm->fd = serial_open(port, 19200);
|
baud = 19200;
|
||||||
|
|
||||||
|
#if defined(HAVE_LIBUSB)
|
||||||
|
/*
|
||||||
|
* If the port name starts with "usb", divert the serial routines
|
||||||
|
* to the USB ones. The serial_open() function for USB overrides
|
||||||
|
* the meaning of the "baud" parameter to be the USB device ID to
|
||||||
|
* search for.
|
||||||
|
*/
|
||||||
|
if (strncmp(port, "usb", 3) == 0) {
|
||||||
|
serdev = &usb_serdev;
|
||||||
|
baud = USB_DEVICE_JTAGICEMKII;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
strcpy(pgm->port, port);
|
||||||
|
pgm->fd = serial_open(port, baud);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* drain any extraneous input
|
* drain any extraneous input
|
||||||
|
|
2
serial.h
2
serial.h
|
@ -44,7 +44,7 @@ struct serial_device
|
||||||
};
|
};
|
||||||
|
|
||||||
extern struct serial_device *serdev;
|
extern struct serial_device *serdev;
|
||||||
extern struct serial_device serial_serdev, usb_serdev;
|
extern struct serial_device serial_serdev, usb_serdev, usb_serdev_frame;
|
||||||
|
|
||||||
#define serial_open (serdev->open)
|
#define serial_open (serdev->open)
|
||||||
#define serial_setspeed (serdev->setspeed)
|
#define serial_setspeed (serdev->setspeed)
|
||||||
|
|
104
stk500v2.c
104
stk500v2.c
|
@ -2,6 +2,7 @@
|
||||||
* avrdude - A Downloader/Uploader for AVR device programmers
|
* avrdude - A Downloader/Uploader for AVR device programmers
|
||||||
* Copyright (C) 2005 Erik Walthinsen
|
* Copyright (C) 2005 Erik Walthinsen
|
||||||
* Copyright (C) 2002-2004 Brian S. Dean <bsd@bsdhome.com>
|
* Copyright (C) 2002-2004 Brian S. Dean <bsd@bsdhome.com>
|
||||||
|
* Copyright (C) 2006 dcm@mit.edu
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or modify
|
* This program is free software; you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
@ -24,6 +25,10 @@
|
||||||
/*
|
/*
|
||||||
* avrdude interface for Atmel STK500V2 programmer
|
* avrdude interface for Atmel STK500V2 programmer
|
||||||
*
|
*
|
||||||
|
* As the AVRISP mkII device is basically an STK500v2 one that can
|
||||||
|
* only talk across USB, and that misses any kind of framing protocol,
|
||||||
|
* this is handled here as well.
|
||||||
|
*
|
||||||
* Note: most commands use the "universal command" feature of the
|
* Note: most commands use the "universal command" feature of the
|
||||||
* programmer in a "pass through" mode, exceptions are "program
|
* programmer in a "pass through" mode, exceptions are "program
|
||||||
* enable", "paged read", and "paged write".
|
* enable", "paged read", and "paged write".
|
||||||
|
@ -45,6 +50,7 @@
|
||||||
#include "stk500_private.h" // temp until all code converted
|
#include "stk500_private.h" // temp until all code converted
|
||||||
#include "stk500v2_private.h"
|
#include "stk500v2_private.h"
|
||||||
#include "serial.h"
|
#include "serial.h"
|
||||||
|
#include "usbdevs.h"
|
||||||
|
|
||||||
#define STK500V2_XTAL 7372800U
|
#define STK500V2_XTAL 7372800U
|
||||||
|
|
||||||
|
@ -66,6 +72,7 @@ extern char * progname;
|
||||||
extern int do_cycles;
|
extern int do_cycles;
|
||||||
|
|
||||||
static unsigned char command_sequence = 1;
|
static unsigned char command_sequence = 1;
|
||||||
|
static int is_mk2; /* Is the device an AVRISP mkII? */
|
||||||
|
|
||||||
|
|
||||||
static int stk500v2_getparm(PROGRAMMER * pgm, unsigned char parm, unsigned char * value);
|
static int stk500v2_getparm(PROGRAMMER * pgm, unsigned char parm, unsigned char * value);
|
||||||
|
@ -74,12 +81,26 @@ static void stk500v2_print_parms1(PROGRAMMER * pgm, char * p);
|
||||||
static int stk500v2_is_page_empty(unsigned int address, int page_size,
|
static int stk500v2_is_page_empty(unsigned int address, int page_size,
|
||||||
const unsigned char *buf);
|
const unsigned char *buf);
|
||||||
|
|
||||||
|
static int stk500v2_set_sck_period_mk2(PROGRAMMER * pgm, double v);
|
||||||
|
|
||||||
|
static int stk500v2_send_mk2(PROGRAMMER * pgm, unsigned char * data, size_t len)
|
||||||
|
{
|
||||||
|
if (serial_send(pgm->fd, data, len) != 0) {
|
||||||
|
fprintf(stderr,"%s: stk500_send_mk2(): failed to send command to serial port\n",progname);
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
static int stk500v2_send(PROGRAMMER * pgm, unsigned char * data, size_t len)
|
static int stk500v2_send(PROGRAMMER * pgm, unsigned char * data, size_t len)
|
||||||
{
|
{
|
||||||
unsigned char buf[275 + 6]; // max MESSAGE_BODY of 275 bytes, 6 bytes overhead
|
unsigned char buf[275 + 6]; // max MESSAGE_BODY of 275 bytes, 6 bytes overhead
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
|
if (is_mk2)
|
||||||
|
return stk500v2_send_mk2(pgm, data, len);
|
||||||
|
|
||||||
buf[0] = MESSAGE_START;
|
buf[0] = MESSAGE_START;
|
||||||
buf[1] = command_sequence;
|
buf[1] = command_sequence;
|
||||||
buf[2] = len / 256;
|
buf[2] = len / 256;
|
||||||
|
@ -110,6 +131,19 @@ static int stk500v2_drain(PROGRAMMER * pgm, int display)
|
||||||
return serial_drain(pgm->fd, display);
|
return serial_drain(pgm->fd, display);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int stk500v2_recv_mk2(PROGRAMMER * pgm, unsigned char msg[],
|
||||||
|
size_t maxsize)
|
||||||
|
{
|
||||||
|
int rv;
|
||||||
|
|
||||||
|
rv = serial_recv(pgm->fd, msg, maxsize);
|
||||||
|
if (rv < 0) {
|
||||||
|
fprintf(stderr, "%s: stk500v2_recv_mk2: error in USB receive\n", progname);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return rv;
|
||||||
|
}
|
||||||
|
|
||||||
static int stk500v2_recv(PROGRAMMER * pgm, unsigned char msg[], size_t maxsize) {
|
static int stk500v2_recv(PROGRAMMER * pgm, unsigned char msg[], size_t maxsize) {
|
||||||
enum states { sINIT, sSTART, sSEQNUM, sSIZE1, sSIZE2, sTOKEN, sDATA, sCSUM, sDONE } state = sSTART;
|
enum states { sINIT, sSTART, sSEQNUM, sSIZE1, sSIZE2, sTOKEN, sDATA, sCSUM, sDONE } state = sSTART;
|
||||||
|
@ -122,6 +156,9 @@ static int stk500v2_recv(PROGRAMMER * pgm, unsigned char msg[], size_t maxsize)
|
||||||
struct timeval tv;
|
struct timeval tv;
|
||||||
double tstart, tnow;
|
double tstart, tnow;
|
||||||
|
|
||||||
|
if (is_mk2)
|
||||||
|
return stk500v2_recv_mk2(pgm, msg, maxsize);
|
||||||
|
|
||||||
DEBUG("STK500V2: stk500v2_recv(): ");
|
DEBUG("STK500V2: stk500v2_recv(): ");
|
||||||
|
|
||||||
gettimeofday(&tv, NULL);
|
gettimeofday(&tv, NULL);
|
||||||
|
@ -437,13 +474,30 @@ static void stk500v2_enable(PROGRAMMER * pgm)
|
||||||
|
|
||||||
static int stk500v2_open(PROGRAMMER * pgm, char * port)
|
static int stk500v2_open(PROGRAMMER * pgm, char * port)
|
||||||
{
|
{
|
||||||
|
long baud = 115200;
|
||||||
|
|
||||||
DEBUG("STK500V2: stk500v2_open()\n");
|
DEBUG("STK500V2: stk500v2_open()\n");
|
||||||
|
|
||||||
strcpy(pgm->port, port);
|
|
||||||
if (pgm->baudrate)
|
if (pgm->baudrate)
|
||||||
pgm->fd = serial_open(port, pgm->baudrate);
|
baud = pgm->baudrate;
|
||||||
else
|
|
||||||
pgm->fd = serial_open(port, 115200);
|
#if defined(HAVE_LIBUSB)
|
||||||
|
/*
|
||||||
|
* If the port name starts with "usb", divert the serial routines
|
||||||
|
* to the USB ones. The serial_open() function for USB overrides
|
||||||
|
* the meaning of the "baud" parameter to be the USB device ID to
|
||||||
|
* search for.
|
||||||
|
*/
|
||||||
|
if (strncmp(port, "usb", 3) == 0) {
|
||||||
|
serdev = &usb_serdev_frame;
|
||||||
|
baud = USB_DEVICE_AVRISPMKII;
|
||||||
|
is_mk2 = 1;
|
||||||
|
pgm->set_sck_period = stk500v2_set_sck_period_mk2;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
strcpy(pgm->port, port);
|
||||||
|
pgm->fd = serial_open(port, baud);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* drain any extraneous input
|
* drain any extraneous input
|
||||||
|
@ -797,6 +851,44 @@ static int stk500v2_set_fosc(PROGRAMMER * pgm, double v)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* The list of SCK frequencies supported by the AVRISP mkII, as listed
|
||||||
|
* in AVR069 */
|
||||||
|
double avrispmkIIfreqs[] = {
|
||||||
|
8000000, 4000000, 2000000, 1000000, 500000, 250000, 125000,
|
||||||
|
96386, 89888, 84211, 79208, 74767, 70797, 67227, 64000,
|
||||||
|
61069, 58395, 55945, 51613, 49690, 47905, 46243, 43244,
|
||||||
|
41885, 39409, 38278, 36200, 34335, 32654, 31129, 29740,
|
||||||
|
28470, 27304, 25724, 24768, 23461, 22285, 21221, 20254,
|
||||||
|
19371, 18562, 17583, 16914, 16097, 15356, 14520, 13914,
|
||||||
|
13224, 12599, 12031, 11511, 10944, 10431, 9963, 9468,
|
||||||
|
9081, 8612, 8239, 7851, 7498, 7137, 6809, 6478, 6178,
|
||||||
|
5879, 5607, 5359, 5093, 4870, 4633, 4418, 4209, 4019,
|
||||||
|
3823, 3645, 3474, 3310, 3161, 3011, 2869, 2734, 2611,
|
||||||
|
2484, 2369, 2257, 2152, 2052, 1956, 1866, 1779, 1695,
|
||||||
|
1615, 1539, 1468, 1398, 1333, 1271, 1212, 1155, 1101,
|
||||||
|
1049, 1000, 953, 909, 866, 826, 787, 750, 715, 682,
|
||||||
|
650, 619, 590, 563, 536, 511, 487, 465, 443, 422,
|
||||||
|
402, 384, 366, 349, 332, 317, 302, 288, 274, 261,
|
||||||
|
249, 238, 226, 216, 206, 196, 187, 178, 170, 162,
|
||||||
|
154, 147, 140, 134, 128, 122, 116, 111, 105, 100,
|
||||||
|
95.4, 90.9, 86.6, 82.6, 78.7, 75.0, 71.5, 68.2,
|
||||||
|
65.0, 61.9, 59.0, 56.3, 53.6, 51.1
|
||||||
|
};
|
||||||
|
|
||||||
|
static int stk500v2_set_sck_period_mk2(PROGRAMMER * pgm, double v)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for (i = 0; i < sizeof(avrispmkIIfreqs); i++) {
|
||||||
|
if (1 / avrispmkIIfreqs[i] >= v)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
fprintf(stderr, "Using p = %.2f us for SCK (param = %d)\n",
|
||||||
|
1000000 / avrispmkIIfreqs[i], i);
|
||||||
|
|
||||||
|
return stk500v2_setparm(pgm, PARAM_SCK_DURATION, i);
|
||||||
|
}
|
||||||
|
|
||||||
/* This code assumes that each count of the SCK duration parameter
|
/* This code assumes that each count of the SCK duration parameter
|
||||||
represents 8/f, where f is the clock frequency of the STK500V2 master
|
represents 8/f, where f is the clock frequency of the STK500V2 master
|
||||||
|
@ -938,6 +1030,10 @@ static void stk500v2_print_parms1(PROGRAMMER * pgm, char * p)
|
||||||
unit = "Hz";
|
unit = "Hz";
|
||||||
fprintf(stderr, "%.3f %s\n", f, unit);
|
fprintf(stderr, "%.3f %s\n", f, unit);
|
||||||
}
|
}
|
||||||
|
if (is_mk2)
|
||||||
|
fprintf(stderr, "%sSCK period : %.2f us\n", p,
|
||||||
|
(float) 1000000 / avrispmkIIfreqs[sck_duration]);
|
||||||
|
else
|
||||||
fprintf(stderr, "%sSCK period : %.1f us\n", p,
|
fprintf(stderr, "%sSCK period : %.1f us\n", p,
|
||||||
sck_duration * 8.0e6 / STK500V2_XTAL + 0.05);
|
sck_duration * 8.0e6 / STK500V2_XTAL + 0.05);
|
||||||
|
|
||||||
|
|
170
usb_libusb.c
170
usb_libusb.c
|
@ -1,6 +1,7 @@
|
||||||
/*
|
/*
|
||||||
* avrdude - A Downloader/Uploader for AVR device programmers
|
* avrdude - A Downloader/Uploader for AVR device programmers
|
||||||
* Copyright (C) 2005 Joerg Wunsch
|
* Copyright (C) 2005,2006 Joerg Wunsch
|
||||||
|
* Copyright (C) 2006 dcm@mit.edu
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or modify
|
* This program is free software; you can redistribute it and/or modify
|
||||||
* it under the terms of the GNU General Public License as published by
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
@ -38,28 +39,24 @@
|
||||||
#include <usb.h>
|
#include <usb.h>
|
||||||
|
|
||||||
#include "serial.h"
|
#include "serial.h"
|
||||||
|
#include "usbdevs.h"
|
||||||
|
|
||||||
extern char *progname;
|
extern char *progname;
|
||||||
extern int verbose;
|
extern int verbose;
|
||||||
|
|
||||||
#define USB_VENDOR_ATMEL 1003
|
static char usbbuf[USBDEV_MAX_XFER];
|
||||||
#define USB_DEVICE_JTAGICEMKII 0x2103
|
|
||||||
/*
|
|
||||||
* Should we query the endpoint number and max transfer size from USB?
|
|
||||||
* After all, the JTAG ICE mkII docs document these values.
|
|
||||||
*/
|
|
||||||
#define JTAGICE_BULK_EP_WRITE 0x02
|
|
||||||
#define JTAGICE_BULK_EP_READ 0x82
|
|
||||||
#define JTAGICE_MAX_XFER 64
|
|
||||||
|
|
||||||
static char usbbuf[JTAGICE_MAX_XFER];
|
|
||||||
static int buflen = -1, bufptr;
|
static int buflen = -1, bufptr;
|
||||||
|
|
||||||
static int usb_interface;
|
static int usb_interface;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* The "baud" parameter is meaningless for USB devices, so we reuse it
|
||||||
|
* to pass the desired USB device ID.
|
||||||
|
*/
|
||||||
static int usbdev_open(char * port, long baud)
|
static int usbdev_open(char * port, long baud)
|
||||||
{
|
{
|
||||||
char string[256];
|
char string[256];
|
||||||
|
char product[256];
|
||||||
struct usb_bus *bus;
|
struct usb_bus *bus;
|
||||||
struct usb_device *dev;
|
struct usb_device *dev;
|
||||||
usb_dev_handle *udev;
|
usb_dev_handle *udev;
|
||||||
|
@ -110,7 +107,7 @@ static int usbdev_open(char * port, long baud)
|
||||||
if (udev)
|
if (udev)
|
||||||
{
|
{
|
||||||
if (dev->descriptor.idVendor == USB_VENDOR_ATMEL &&
|
if (dev->descriptor.idVendor == USB_VENDOR_ATMEL &&
|
||||||
dev->descriptor.idProduct == USB_DEVICE_JTAGICEMKII)
|
dev->descriptor.idProduct == (unsigned short)baud)
|
||||||
{
|
{
|
||||||
/* yeah, we found something */
|
/* yeah, we found something */
|
||||||
if (usb_get_string_simple(udev,
|
if (usb_get_string_simple(udev,
|
||||||
|
@ -133,10 +130,20 @@ static int usbdev_open(char * port, long baud)
|
||||||
strcpy(string, "[unknown]");
|
strcpy(string, "[unknown]");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (usb_get_string_simple(udev,
|
||||||
|
dev->descriptor.iProduct,
|
||||||
|
product, sizeof(product)) < 0)
|
||||||
|
{
|
||||||
|
fprintf(stderr,
|
||||||
|
"%s: usb_open(): cannot read product name \"%s\"\n",
|
||||||
|
progname, usb_strerror());
|
||||||
|
strcpy(product, "[unnamed product]");
|
||||||
|
}
|
||||||
|
|
||||||
if (verbose)
|
if (verbose)
|
||||||
fprintf(stderr,
|
fprintf(stderr,
|
||||||
"%s: usbdev_open(): Found JTAG ICE, serno: %s\n",
|
"%s: usbdev_open(): Found %s, serno: %s\n",
|
||||||
progname, string);
|
progname, product, string);
|
||||||
if (serno != NULL)
|
if (serno != NULL)
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
|
@ -205,6 +212,13 @@ static void usbdev_close(int fd)
|
||||||
usb_dev_handle *udev = (usb_dev_handle *)fd;
|
usb_dev_handle *udev = (usb_dev_handle *)fd;
|
||||||
|
|
||||||
(void)usb_release_interface(udev, usb_interface);
|
(void)usb_release_interface(udev, usb_interface);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Without this reset, the AVRISP mkII seems to stall the second
|
||||||
|
* time we try to connect to it.
|
||||||
|
*/
|
||||||
|
usb_reset(udev);
|
||||||
|
|
||||||
usb_close(udev);
|
usb_close(udev);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -213,14 +227,49 @@ static int usbdev_send(int fd, unsigned char *bp, size_t mlen)
|
||||||
{
|
{
|
||||||
usb_dev_handle *udev = (usb_dev_handle *)fd;
|
usb_dev_handle *udev = (usb_dev_handle *)fd;
|
||||||
size_t rv;
|
size_t rv;
|
||||||
|
int i = mlen;
|
||||||
|
unsigned char * p = bp;
|
||||||
|
int tx_size;
|
||||||
|
|
||||||
rv = usb_bulk_write(udev, JTAGICE_BULK_EP_WRITE, (char *)bp, mlen, 5000);
|
/*
|
||||||
if (rv != mlen)
|
* Split the frame into multiple packets. It's important to make
|
||||||
|
* sure we finish with a short packet, or else the device won't know
|
||||||
|
* the frame is finished. For example, if we need to send 64 bytes,
|
||||||
|
* we must send a packet of length 64 followed by a packet of length
|
||||||
|
* 0.
|
||||||
|
*/
|
||||||
|
do {
|
||||||
|
tx_size = (mlen < USBDEV_MAX_XFER)? mlen: USBDEV_MAX_XFER;
|
||||||
|
rv = usb_bulk_write(udev, USBDEV_BULK_EP_WRITE, (char *)bp, tx_size, 5000);
|
||||||
|
if (rv != tx_size)
|
||||||
{
|
{
|
||||||
fprintf(stderr, "%s: usbdev_send(): wrote %d out of %d bytes, err = %s\n",
|
fprintf(stderr, "%s: usbdev_send(): wrote %d out of %d bytes, err = %s\n",
|
||||||
progname, rv, mlen, usb_strerror());
|
progname, rv, tx_size, usb_strerror());
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
bp += tx_size;
|
||||||
|
mlen -= tx_size;
|
||||||
|
} while (tx_size == USBDEV_MAX_XFER);
|
||||||
|
|
||||||
|
if (verbose > 3)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "%s: Sent: ", progname);
|
||||||
|
|
||||||
|
while (i) {
|
||||||
|
unsigned char c = *p;
|
||||||
|
if (isprint(c)) {
|
||||||
|
fprintf(stderr, "%c ", c);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
fprintf(stderr, ". ");
|
||||||
|
}
|
||||||
|
fprintf(stderr, "[%02x] ", c);
|
||||||
|
|
||||||
|
p++;
|
||||||
|
i--;
|
||||||
|
}
|
||||||
|
fprintf(stderr, "\n");
|
||||||
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -237,7 +286,7 @@ usb_fill_buf(usb_dev_handle *udev)
|
||||||
{
|
{
|
||||||
int rv;
|
int rv;
|
||||||
|
|
||||||
rv = usb_bulk_read(udev, JTAGICE_BULK_EP_READ, usbbuf, JTAGICE_MAX_XFER, 5000);
|
rv = usb_bulk_read(udev, USBDEV_BULK_EP_READ, usbbuf, USBDEV_MAX_XFER, 5000);
|
||||||
if (rv < 0)
|
if (rv < 0)
|
||||||
{
|
{
|
||||||
if (verbose > 1)
|
if (verbose > 1)
|
||||||
|
@ -295,6 +344,71 @@ static int usbdev_recv(int fd, unsigned char *buf, size_t nbytes)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This version of recv keeps reading packets until we receive a short
|
||||||
|
* packet. Then, the entire frame is assembled and returned to the
|
||||||
|
* user. The length will be unknown in advance, so we return the
|
||||||
|
* length as the return value of this function, or -1 in case of an
|
||||||
|
* error.
|
||||||
|
*
|
||||||
|
* This is used for the AVRISP mkII device.
|
||||||
|
*/
|
||||||
|
static int usbdev_recv_frame(int fd, unsigned char *buf, size_t nbytes)
|
||||||
|
{
|
||||||
|
usb_dev_handle *udev = (usb_dev_handle *)fd;
|
||||||
|
int rv, n;
|
||||||
|
int i;
|
||||||
|
unsigned char * p = buf;
|
||||||
|
|
||||||
|
n = 0;
|
||||||
|
do
|
||||||
|
{
|
||||||
|
rv = usb_bulk_read(udev, USBDEV_BULK_EP_READ, usbbuf,
|
||||||
|
USBDEV_MAX_XFER, 10000);
|
||||||
|
if (rv < 0)
|
||||||
|
{
|
||||||
|
if (verbose > 1)
|
||||||
|
fprintf(stderr, "%s: usbdev_recv_frame(): usb_bulk_read(): %s\n",
|
||||||
|
progname, usb_strerror());
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (rv <= nbytes)
|
||||||
|
{
|
||||||
|
memcpy (buf, usbbuf, rv);
|
||||||
|
buf += rv;
|
||||||
|
}
|
||||||
|
|
||||||
|
n += rv;
|
||||||
|
nbytes -= rv;
|
||||||
|
}
|
||||||
|
while (rv == USBDEV_MAX_XFER);
|
||||||
|
|
||||||
|
if (nbytes < 0)
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
if (verbose > 3)
|
||||||
|
{
|
||||||
|
i = n;
|
||||||
|
fprintf(stderr, "%s: Recv: ", progname);
|
||||||
|
|
||||||
|
while (i) {
|
||||||
|
unsigned char c = *p;
|
||||||
|
if (isprint(c)) {
|
||||||
|
fprintf(stderr, "%c ", c);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
fprintf(stderr, ". ");
|
||||||
|
}
|
||||||
|
fprintf(stderr, "[%02x] ", c);
|
||||||
|
|
||||||
|
p++;
|
||||||
|
i--;
|
||||||
|
}
|
||||||
|
fprintf(stderr, "\n");
|
||||||
|
}
|
||||||
|
return n;
|
||||||
|
}
|
||||||
|
|
||||||
static int usbdev_drain(int fd, int display)
|
static int usbdev_drain(int fd, int display)
|
||||||
{
|
{
|
||||||
|
@ -302,7 +416,7 @@ static int usbdev_drain(int fd, int display)
|
||||||
int rv;
|
int rv;
|
||||||
|
|
||||||
do {
|
do {
|
||||||
rv = usb_bulk_read(udev, JTAGICE_BULK_EP_READ, usbbuf, JTAGICE_MAX_XFER, 100);
|
rv = usb_bulk_read(udev, USBDEV_BULK_EP_READ, usbbuf, USBDEV_MAX_XFER, 100);
|
||||||
if (rv > 0 && verbose >= 4)
|
if (rv > 0 && verbose >= 4)
|
||||||
fprintf(stderr, "%s: usbdev_drain(): flushed %d characters\n",
|
fprintf(stderr, "%s: usbdev_drain(): flushed %d characters\n",
|
||||||
progname, rv);
|
progname, rv);
|
||||||
|
@ -311,6 +425,9 @@ static int usbdev_drain(int fd, int display)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Device descriptor for the JTAG ICE mkII.
|
||||||
|
*/
|
||||||
struct serial_device usb_serdev =
|
struct serial_device usb_serdev =
|
||||||
{
|
{
|
||||||
.open = usbdev_open,
|
.open = usbdev_open,
|
||||||
|
@ -321,4 +438,17 @@ struct serial_device usb_serdev =
|
||||||
.drain = usbdev_drain,
|
.drain = usbdev_drain,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Device descriptor for the AVRISP mkII.
|
||||||
|
*/
|
||||||
|
struct serial_device usb_serdev_frame =
|
||||||
|
{
|
||||||
|
.open = usbdev_open,
|
||||||
|
.setspeed = usbdev_setspeed,
|
||||||
|
.close = usbdev_close,
|
||||||
|
.send = usbdev_send,
|
||||||
|
.recv = usbdev_recv_frame,
|
||||||
|
.drain = usbdev_drain,
|
||||||
|
};
|
||||||
|
|
||||||
#endif /* HAVE_LIBUSB */
|
#endif /* HAVE_LIBUSB */
|
||||||
|
|
|
@ -0,0 +1,40 @@
|
||||||
|
/*
|
||||||
|
* avrdude - A Downloader/Uploader for AVR device programmers
|
||||||
|
* Copyright (C) 2006 Joerg Wunsch
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation; either version 2 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* $Id$ */
|
||||||
|
|
||||||
|
/*
|
||||||
|
* defines for the USB interface
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef usbdevs_h
|
||||||
|
#define usbdevs_h
|
||||||
|
|
||||||
|
#define USB_VENDOR_ATMEL 1003
|
||||||
|
#define USB_DEVICE_JTAGICEMKII 0x2103
|
||||||
|
#define USB_DEVICE_AVRISPMKII 0x2104
|
||||||
|
/*
|
||||||
|
* Should we query the endpoint number and max transfer size from USB?
|
||||||
|
* After all, the JTAG ICE mkII docs document these values.
|
||||||
|
*/
|
||||||
|
#define USBDEV_BULK_EP_WRITE 0x02
|
||||||
|
#define USBDEV_BULK_EP_READ 0x82
|
||||||
|
#define USBDEV_MAX_XFER 64
|
||||||
|
|
||||||
|
#endif /* usbdevs_h */
|
Loading…
Reference in New Issue