From 60767fa68f5c83bde937e3cab4b963b49b63b0cd Mon Sep 17 00:00:00 2001 From: Marcel Telka Date: Tue, 29 Apr 2003 21:40:29 +0000 Subject: [PATCH] 2003-04-29 Marcel Telka * data/MANUFACTURERS: Added new manufacturer: DEC. * src/jtag.c (jtag_create_jtagdir): Changed permissions for jtag directory. * include/part.h (part_alloc, read_part): Changed return type from `part *' to `part_t *'. (struct parts): Changed parts member type from `part **' to `part_t **'. (parts_alloc): Changed return type from `parts *' to `parts_t *'. * src/bus/ixp425.c (select_flash, unselect_flash, setup_address, set_data_in, setup_data): Changed first parameter type from `part *' to `part_t *'. * src/bus/pxa250.c (setup_address, set_data_in, setup_data): Ditto. * src/bus/sa1110.c (setup_address, set_data_in, setup_data): Ditto. * include/bus.h: Replaced static bus_driver_t architecture with dynamic bus_t. Removed direct chain_t dependency. Added `params' and `prepare' members. All related functions' parameter types changed. * src/bus/ixp425.c (bus_params_t): New structure typedef. (CHAIN, PART): New macros. (ixp425_bus_prepare, ixp425_bus_free, new_ixp425_bus): New functions. (ixp425_bus_driver, ixp425_bus): Renamed `ixp425_bus_driver' to `ixp425_bus' and updated for new bus driver architecture. * src/bus/pxa250.c (bus_params_t): New structure typedef. (CHAIN, PART): New macros. (pxa250_bus_prepare, pxa250_bus_free, new_pxa250_bus): New functions. (pxa250_bus_driver, pxa250_bus): Renamed `pxa250_bus_driver' to `pxa250_bus' and updated for new bus driver architecture. * src/bus/sa1110.c (bus_params_t): New structure typedef. (CHAIN, PART): New macros. (sa1110_bus_prepare, sa1110_bus_free, new_sa1110_bus): New functions. (sa1110_bus_driver, sa1110_bus): Renamed `sa1110_bus_driver' to `sa1110_bus' and updated for new bus driver architecture. * src/readmem.c (detectflash, readmem): Moved JTAG chain initialization to bus->prepare(). * src/flash.c (flashcheck): Ditto. (flashmsbin, flashmem): Removed BYPASS instruction setup. * src/jtag.c (bus_driver, bus): Replaced `bus_driver' with `bus' global variable. (jtag_parse_line, main): Added `bus' deallocation. * src/flash.h (flash_driver_t): Changed parameter type for all function members from `chain_t*' to `bus_t *'. All function callers changed. git-svn-id: https://urjtag.svn.sourceforge.net/svnroot/urjtag/trunk@423 b68d4a1b-bc3d-0410-92ed-d4ac073336b7 --- jtag/ChangeLog | 41 ++++++++++++++ jtag/NEWS | 2 + jtag/data/MANUFACTURERS | 1 + jtag/include/bus.h | 43 +++++++------- jtag/include/part.h | 8 +-- jtag/src/bus/ixp425.c | 108 +++++++++++++++++++++++++++--------- jtag/src/bus/pxa2x0.c | 105 ++++++++++++++++++++++++++--------- jtag/src/bus/sa1110.c | 94 ++++++++++++++++++++++++------- jtag/src/cfi.c | 65 +++++++++++----------- jtag/src/flash-amd.c | 73 ++++++++++++------------ jtag/src/flash-intel.c | 120 ++++++++++++++++++++-------------------- jtag/src/flash.c | 67 ++++++++-------------- jtag/src/flash.h | 15 +++-- jtag/src/jtag.c | 26 ++++++--- jtag/src/jtag.h | 11 ++-- jtag/src/readmem.c | 50 +++++++---------- 16 files changed, 512 insertions(+), 317 deletions(-) diff --git a/jtag/ChangeLog b/jtag/ChangeLog index 9bb21ff8..6a7258e2 100644 --- a/jtag/ChangeLog +++ b/jtag/ChangeLog @@ -1,3 +1,44 @@ +2003-04-29 Marcel Telka + + * data/MANUFACTURERS: Added new manufacturer: DEC. + + * src/jtag.c (jtag_create_jtagdir): Changed permissions for jtag directory. + + * include/part.h (part_alloc, read_part): Changed return type from `part *' to `part_t *'. + (struct parts): Changed parts member type from `part **' to `part_t **'. + (parts_alloc): Changed return type from `parts *' to `parts_t *'. + * src/bus/ixp425.c (select_flash, unselect_flash, setup_address, set_data_in, setup_data): + Changed first parameter type from `part *' to `part_t *'. + * src/bus/pxa250.c (setup_address, set_data_in, setup_data): Ditto. + * src/bus/sa1110.c (setup_address, set_data_in, setup_data): Ditto. + + * include/bus.h: Replaced static bus_driver_t architecture with dynamic bus_t. + Removed direct chain_t dependency. Added `params' and `prepare' members. + All related functions' parameter types changed. + * src/bus/ixp425.c (bus_params_t): New structure typedef. + (CHAIN, PART): New macros. + (ixp425_bus_prepare, ixp425_bus_free, new_ixp425_bus): New functions. + (ixp425_bus_driver, ixp425_bus): Renamed `ixp425_bus_driver' to `ixp425_bus' and updated + for new bus driver architecture. + * src/bus/pxa250.c (bus_params_t): New structure typedef. + (CHAIN, PART): New macros. + (pxa250_bus_prepare, pxa250_bus_free, new_pxa250_bus): New functions. + (pxa250_bus_driver, pxa250_bus): Renamed `pxa250_bus_driver' to `pxa250_bus' and updated + for new bus driver architecture. + * src/bus/sa1110.c (bus_params_t): New structure typedef. + (CHAIN, PART): New macros. + (sa1110_bus_prepare, sa1110_bus_free, new_sa1110_bus): New functions. + (sa1110_bus_driver, sa1110_bus): Renamed `sa1110_bus_driver' to `sa1110_bus' and updated + for new bus driver architecture. + * src/readmem.c (detectflash, readmem): Moved JTAG chain initialization to bus->prepare(). + * src/flash.c (flashcheck): Ditto. + (flashmsbin, flashmem): Removed BYPASS instruction setup. + * src/jtag.c (bus_driver, bus): Replaced `bus_driver' with `bus' global variable. + (jtag_parse_line, main): Added `bus' deallocation. + * src/flash.h (flash_driver_t): Changed parameter type for all function members from + `chain_t*' to `bus_t *'. + All function callers changed. + 2003-04-04 Marcel Telka Version 0.3.2 released. diff --git a/jtag/NEWS b/jtag/NEWS index 237d733d..885074d3 100644 --- a/jtag/NEWS +++ b/jtag/NEWS @@ -1,5 +1,7 @@ $Id$ + * Added new manufacturer: DEC. + jtag-0.3.2 (2003-04-04): * Added driver for Keith & Koep JTAG Cable. diff --git a/jtag/data/MANUFACTURERS b/jtag/data/MANUFACTURERS index 150aa493..25efcea7 100644 --- a/jtag/data/MANUFACTURERS +++ b/jtag/data/MANUFACTURERS @@ -32,5 +32,6 @@ 00000010101 xilinx Xilinx # Philips Semi. (Signetics) 00000011111 atmel Atmel 00000110100 cypress Cypress +00000110101 dec DEC 00001001001 xilinx Xilinx 00101010000 broadcom Broadcom diff --git a/jtag/include/bus.h b/jtag/include/bus.h index f40dd162..0f2e2053 100644 --- a/jtag/include/bus.h +++ b/jtag/include/bus.h @@ -27,28 +27,33 @@ #define BUS_H #include -#include "part.h" #include "chain.h" -typedef struct { - int (*bus_width)( chain_t * ); - void (*bus_read_start)( chain_t *, uint32_t ); - uint32_t (*bus_read_next)( chain_t *, uint32_t ); - uint32_t (*bus_read_end)( chain_t * ); - uint32_t (*bus_read)( chain_t *, uint32_t ); - void (*bus_write)( chain_t *, uint32_t, uint32_t ); -} bus_driver_t; +typedef struct bus bus_t; -extern bus_driver_t *bus_driver; -#define bus_width bus_driver->bus_width -#define bus_read_start bus_driver->bus_read_start -#define bus_read_next bus_driver->bus_read_next -#define bus_read_end bus_driver->bus_read_end -#define bus_read bus_driver->bus_read -#define bus_write bus_driver->bus_write +struct bus { + void *params; + void (*prepare)( bus_t *bus ); + int (*width)( bus_t *bus ); + void (*read_start)( bus_t *bus, uint32_t adr ); + uint32_t (*read_next)( bus_t *bus, uint32_t adr ); + uint32_t (*read_end)( bus_t *bus ); + uint32_t (*read)( bus_t *bus, uint32_t adr ); + void (*write)( bus_t *bus, uint32_t adr, uint32_t data ); + void (*free)( bus_t *bus ); +}; -extern bus_driver_t sa1110_bus_driver; -extern bus_driver_t pxa250_bus_driver; -extern bus_driver_t ixp425_bus_driver; +#define bus_prepare(bus) bus->prepare(bus) +#define bus_width(bus) bus->width(bus) +#define bus_read_start(bus,adr) bus->read_start(bus,adr) +#define bus_read_next(bus,adr) bus->read_next(bus,adr) +#define bus_read_end(bus) bus->read_end(bus) +#define bus_read(bus,adr) bus->read(bus,adr) +#define bus_write(bus,adr,data) bus->write(bus,adr,data) +#define bus_free(bus) bus->free(bus) + +bus_t *new_sa1110_bus( chain_t *chain, int pn ); +bus_t *new_pxa250_bus( chain_t *chain, int pn ); +bus_t *new_ixp425_bus( chain_t *chain, int pn ); #endif /* BUS_H */ diff --git a/jtag/include/part.h b/jtag/include/part.h index 86523187..3833744c 100644 --- a/jtag/include/part.h +++ b/jtag/include/part.h @@ -52,9 +52,9 @@ struct part { bsbit **bsbits; }; -part *part_alloc( void ); +part_t *part_alloc( void ); void part_free( part_t *p ); -part *read_part( FILE *f, tap_register_t *idr ); +part_t *read_part( FILE *f, tap_register_t *idr ); instruction *part_find_instruction( part_t *p, const char *iname ); data_register *part_find_data_register( part_t *p, const char *drname ); void part_set_instruction( part_t *p, const char *iname ); @@ -66,10 +66,10 @@ typedef struct parts parts_t; struct parts { int len; - part **parts; + part_t **parts; }; -parts *parts_alloc( void ); +parts_t *parts_alloc( void ); void parts_free( parts_t *ps ); int parts_add_part( parts_t *ps, part_t *p ); void parts_set_instruction( parts_t *ps, const char *iname ); diff --git a/jtag/src/bus/ixp425.c b/jtag/src/bus/ixp425.c index 4a1e5196..38f223d3 100644 --- a/jtag/src/bus/ixp425.c +++ b/jtag/src/bus/ixp425.c @@ -22,16 +22,24 @@ * */ +#include #include +#include #include "part.h" #include "bus.h" #include "chain.h" -/* IXP425 must be at position 0 in JTAG chain */ +typedef struct { + chain_t *chain; + part_t *part; +} bus_params_t; + +#define CHAIN ((bus_params_t *) bus->params)->chain +#define PART ((bus_params_t *) bus->params)->part static void -select_flash( part *p) +select_flash( part_t *p) { part_set_signal( p, "EX_CS[0]", 1, 0 ); part_set_signal( p, "EX_CS[1]", 1, 1 ); @@ -44,7 +52,7 @@ select_flash( part *p) } static void -unselect_flash( part *p) +unselect_flash( part_t *p) { part_set_signal( p, "EX_CS[0]", 1, 1 ); part_set_signal( p, "EX_CS[1]", 1, 1 ); @@ -57,7 +65,7 @@ unselect_flash( part *p) } static void -setup_address( part *p, uint32_t a ) +setup_address( part_t *p, uint32_t a ) { int i; char buff[15]; @@ -69,7 +77,7 @@ setup_address( part *p, uint32_t a ) } static void -set_data_in( part *p ) +set_data_in( part_t *p ) { int i; char buff[15]; @@ -81,7 +89,7 @@ set_data_in( part *p ) } static void -setup_data( part *p, uint32_t d ) +setup_data( part_t *p, uint32_t d ) { int i; char buff[15]; @@ -92,10 +100,18 @@ setup_data( part *p, uint32_t d ) } } -void -ixp425_bus_read_start( chain_t *chain, uint32_t adr ) +static void +ixp425_bus_prepare( bus_t *bus ) +{ + part_set_instruction( PART, "EXTEST" ); + chain_shift_instructions( CHAIN ); +} + +static void +ixp425_bus_read_start( bus_t *bus, uint32_t adr ) { - part_t *p = chain->parts->parts[0]; + part_t *p = PART; + chain_t *chain = CHAIN; select_flash( p ); part_set_signal( p, "EX_RD", 1, 0 ); @@ -107,10 +123,11 @@ ixp425_bus_read_start( chain_t *chain, uint32_t adr ) chain_shift_data_registers( chain ); } -uint32_t -ixp425_bus_read_next( chain_t *chain, uint32_t adr ) +static uint32_t +ixp425_bus_read_next( bus_t *bus, uint32_t adr ) { - part_t *p = chain->parts->parts[0]; + part_t *p = PART; + chain_t *chain = CHAIN; setup_address( p, adr ); chain_shift_data_registers( chain ); @@ -129,10 +146,11 @@ ixp425_bus_read_next( chain_t *chain, uint32_t adr ) } } -uint32_t -ixp425_bus_read_end( chain_t *chain ) +static uint32_t +ixp425_bus_read_end( bus_t *bus ) { - part_t *p = chain->parts->parts[0]; + part_t *p = PART; + chain_t *chain = CHAIN; unselect_flash( p ); part_set_signal( p, "EX_RD", 1, 1 ); @@ -154,17 +172,18 @@ ixp425_bus_read_end( chain_t *chain ) } } -uint32_t -ixp425_bus_read( chain_t *chain, uint32_t adr ) +static uint32_t +ixp425_bus_read( bus_t *bus, uint32_t adr ) { - ixp425_bus_read_start( chain, adr ); - return ixp425_bus_read_end( chain ); + ixp425_bus_read_start( bus, adr ); + return ixp425_bus_read_end( bus ); } -void -ixp425_bus_write( chain_t *chain, uint32_t adr, uint32_t data ) +static void +ixp425_bus_write( bus_t *bus, uint32_t adr, uint32_t data ) { - part_t *p = chain->parts->parts[0]; + part_t *p = PART; + chain_t *chain = CHAIN; select_flash( p ); part_set_signal( p, "EX_RD", 1, 1 ); @@ -181,17 +200,54 @@ ixp425_bus_write( chain_t *chain, uint32_t adr, uint32_t data ) chain_shift_data_registers( chain ); } -int -ixp425_bus_width( chain_t *chain ) +static int +ixp425_bus_width( bus_t *bus ) { return 16; } -bus_driver_t ixp425_bus_driver = { +static void +ixp425_bus_free( bus_t *bus ) +{ + free( bus->params ); + free( bus ); +} + + +static const bus_t ixp425_bus = { + NULL, + ixp425_bus_prepare, ixp425_bus_width, ixp425_bus_read_start, ixp425_bus_read_next, ixp425_bus_read_end, ixp425_bus_read, - ixp425_bus_write + ixp425_bus_write, + ixp425_bus_free }; + +bus_t * +new_ixp425_bus( chain_t *chain, int pn ) +{ + bus_t *bus; + + if (!chain || !chain->parts || chain->parts->len <= pn || pn < 0) + return NULL; + + bus = malloc( sizeof (bus_t) ); + if (!bus) + return NULL; + + memcpy( bus, &ixp425_bus, sizeof (bus_t) ); + + bus->params = malloc( sizeof (bus_params_t) ); + if (!bus->params) { + free( bus ); + return NULL; + } + + CHAIN = chain; + PART = chain->parts->parts[pn]; + + return bus; +} diff --git a/jtag/src/bus/pxa2x0.c b/jtag/src/bus/pxa2x0.c index 1aaaab2e..a8fd2590 100644 --- a/jtag/src/bus/pxa2x0.c +++ b/jtag/src/bus/pxa2x0.c @@ -26,15 +26,23 @@ * */ +#include #include +#include #include "part.h" #include "bus.h" -/* PXA250 must be at position 0 in JTAG chain */ +typedef struct { + chain_t *chain; + part_t *part; +} bus_params_t; + +#define CHAIN ((bus_params_t *) bus->params)->chain +#define PART ((bus_params_t *) bus->params)->part static void -setup_address( part *p, uint32_t a ) +setup_address( part_t *p, uint32_t a ) { int i; char buff[10]; @@ -46,7 +54,7 @@ setup_address( part *p, uint32_t a ) } static void -set_data_in( part *p ) +set_data_in( part_t *p ) { int i; char buff[10]; @@ -58,7 +66,7 @@ set_data_in( part *p ) } static void -setup_data( part *p, uint32_t d ) +setup_data( part_t *p, uint32_t d ) { int i; char buff[10]; @@ -69,10 +77,18 @@ setup_data( part *p, uint32_t d ) } } -void -pxa250_bus_read_start( chain_t *chain, uint32_t adr ) +static void +pxa250_bus_prepare( bus_t *bus ) +{ + part_set_instruction( PART, "EXTEST" ); + chain_shift_instructions( CHAIN ); +} + +static void +pxa250_bus_read_start( bus_t *bus, uint32_t adr ) { - part_t *p = chain->parts->parts[0]; + chain_t *chain = CHAIN; + part_t *p = PART; /* see Figure 6-13 in [1] */ part_set_signal( p, "nCS[0]", 1, 0 ); @@ -91,10 +107,11 @@ pxa250_bus_read_start( chain_t *chain, uint32_t adr ) chain_shift_data_registers( chain ); } -uint32_t -pxa250_bus_read_next( chain_t *chain, uint32_t adr ) +static uint32_t +pxa250_bus_read_next( bus_t *bus, uint32_t adr ) { - part_t *p = chain->parts->parts[0]; + part_t *p = PART; + chain_t *chain = CHAIN; /* see Figure 6-13 in [1] */ setup_address( p, adr ); @@ -114,10 +131,11 @@ pxa250_bus_read_next( chain_t *chain, uint32_t adr ) } } -uint32_t -pxa250_bus_read_end( chain_t *chain ) +static uint32_t +pxa250_bus_read_end( bus_t *bus ) { - part_t *p = chain->parts->parts[0]; + part_t *p = PART; + chain_t *chain = CHAIN; /* see Figure 6-13 in [1] */ part_set_signal( p, "nCS[0]", 1, 1 ); @@ -140,18 +158,19 @@ pxa250_bus_read_end( chain_t *chain ) } } -uint32_t -pxa250_bus_read( chain_t *chain, uint32_t adr ) +static uint32_t +pxa250_bus_read( bus_t *bus, uint32_t adr ) { - pxa250_bus_read_start( chain, adr ); - return pxa250_bus_read_end( chain ); + pxa250_bus_read_start( bus, adr ); + return pxa250_bus_read_end( bus ); } -void -pxa250_bus_write( chain_t *chain, uint32_t adr, uint32_t data ) +static void +pxa250_bus_write( bus_t *bus, uint32_t adr, uint32_t data ) { /* see Figure 6-17 in [1] */ - part_t *p = chain->parts->parts[0]; + part_t *p = PART; + chain_t *chain = CHAIN; part_set_signal( p, "nCS[0]", 1, 0 ); part_set_signal( p, "DQM[0]", 1, 0 ); @@ -174,10 +193,10 @@ pxa250_bus_write( chain_t *chain, uint32_t adr, uint32_t data ) chain_shift_data_registers( chain ); } -int -pxa250_bus_width( chain_t *chain ) +static int +pxa250_bus_width( bus_t *bus ) { - part_t *p = chain->parts->parts[0]; + part_t *p = PART; uint8_t boot_sel = (part_get_signal( p, "BOOT_SEL[2]" ) << 2) | (part_get_signal( p, "BOOT_SEL[1]" ) << 1) | part_get_signal( p, "BOOT_SEL[0]" ); @@ -204,11 +223,47 @@ pxa250_bus_width( chain_t *chain ) } } -bus_driver_t pxa250_bus_driver = { +static void +pxa250_bus_free( bus_t *bus ) +{ + free( bus->params ); + free( bus ); +} + +static const bus_t pxa250_bus = { + NULL, + pxa250_bus_prepare, pxa250_bus_width, pxa250_bus_read_start, pxa250_bus_read_next, pxa250_bus_read_end, pxa250_bus_read, - pxa250_bus_write + pxa250_bus_write, + pxa250_bus_free }; + +bus_t * +new_pxa250_bus( chain_t *chain, int pn ) +{ + bus_t *bus; + + if (!chain || !chain->parts || chain->parts->len <= pn || pn < 0) + return NULL; + + bus = malloc( sizeof (bus_t) ); + if (!bus) + return NULL; + + memcpy( bus, &pxa250_bus, sizeof (bus_t) ); + + bus->params = malloc( sizeof (bus_params_t) ); + if (!bus->params) { + free( bus ); + return NULL; + } + + CHAIN = chain; + PART = chain->parts->parts[pn]; + + return bus; +} diff --git a/jtag/src/bus/sa1110.c b/jtag/src/bus/sa1110.c index 738bfb5b..4106b1c2 100644 --- a/jtag/src/bus/sa1110.c +++ b/jtag/src/bus/sa1110.c @@ -26,16 +26,24 @@ * */ +#include #include +#include #include "part.h" #include "bus.h" #include "chain.h" -/* SA1110 must be at position 0 in JTAG chain */ +typedef struct { + chain_t *chain; + part_t *part; +} bus_params_t; + +#define CHAIN ((bus_params_t *) bus->params)->chain +#define PART ((bus_params_t *) bus->params)->part static void -setup_address( part *p, uint32_t a ) +setup_address( part_t *p, uint32_t a ) { int i; char buff[10]; @@ -47,7 +55,7 @@ setup_address( part *p, uint32_t a ) } static void -set_data_in( part *p ) +set_data_in( part_t *p ) { int i; char buff[10]; @@ -59,7 +67,7 @@ set_data_in( part *p ) } static void -setup_data( part *p, uint32_t d ) +setup_data( part_t *p, uint32_t d ) { int i; char buff[10]; @@ -71,10 +79,18 @@ setup_data( part *p, uint32_t d ) } static void -sa1110_bus_read_start( chain_t *chain, uint32_t adr ) +sa1110_bus_prepare( bus_t *bus ) +{ + part_set_instruction( PART, "EXTEST" ); + chain_shift_instructions( CHAIN ); +} + +static void +sa1110_bus_read_start( bus_t *bus, uint32_t adr ) { /* see Figure 10-12 in [1] */ - part_t *p = chain->parts->parts[0]; + part_t *p = PART; + chain_t *chain = CHAIN; part_set_signal( p, "nCS0", 1, (adr >> 27) != 0 ); part_set_signal( p, "nCS1", 1, (adr >> 27) != 1 ); @@ -93,10 +109,11 @@ sa1110_bus_read_start( chain_t *chain, uint32_t adr ) } static uint32_t -sa1110_bus_read_next( chain_t *chain, uint32_t adr ) +sa1110_bus_read_next( bus_t *bus, uint32_t adr ) { /* see Figure 10-12 in [1] */ - part_t *p = chain->parts->parts[0]; + part_t *p = PART; + chain_t *chain = CHAIN; setup_address( p, adr ); chain_shift_data_registers( chain ); @@ -116,10 +133,11 @@ sa1110_bus_read_next( chain_t *chain, uint32_t adr ) } static uint32_t -sa1110_bus_read_end( chain_t *chain ) +sa1110_bus_read_end( bus_t *bus ) { /* see Figure 10-12 in [1] */ - part_t *p = chain->parts->parts[0]; + part_t *p = PART; + chain_t *chain = CHAIN; part_set_signal( p, "nCS0", 1, 1 ); part_set_signal( p, "nCS1", 1, 1 ); @@ -145,17 +163,18 @@ sa1110_bus_read_end( chain_t *chain ) } static uint32_t -sa1110_bus_read( chain_t *chain, uint32_t adr ) +sa1110_bus_read( bus_t *bus, uint32_t adr ) { - sa1110_bus_read_start( chain, adr ); - return sa1110_bus_read_end( chain ); + sa1110_bus_read_start( bus, adr ); + return sa1110_bus_read_end( bus ); } static void -sa1110_bus_write( chain_t *chain, uint32_t adr, uint32_t data ) +sa1110_bus_write( bus_t *bus, uint32_t adr, uint32_t data ) { /* see Figure 10-16 in [1] */ - part_t *p = chain->parts->parts[0]; + part_t *p = PART; + chain_t *chain = CHAIN; part_set_signal( p, "nCS0", 1, (adr >> 27) != 0 ); part_set_signal( p, "nCS1", 1, (adr >> 27) != 1 ); @@ -185,9 +204,9 @@ sa1110_bus_write( chain_t *chain, uint32_t adr, uint32_t data ) } static int -sa1110_bus_width( chain_t *chain ) +sa1110_bus_width( bus_t *bus ) { - if (part_get_signal( chain->parts->parts[0], "ROM_SEL" )) { + if (part_get_signal( PART, "ROM_SEL" )) { printf( "ROM_SEL: 32 bits\n" ); return 32; } else { @@ -196,11 +215,48 @@ sa1110_bus_width( chain_t *chain ) } } -bus_driver_t sa1110_bus_driver = { +static void +sa1110_bus_free( bus_t *bus ) +{ + free( bus->params ); + free( bus ); +} + +static const bus_t sa1110_bus = { + NULL, + sa1110_bus_prepare, sa1110_bus_width, sa1110_bus_read_start, sa1110_bus_read_next, sa1110_bus_read_end, sa1110_bus_read, - sa1110_bus_write + sa1110_bus_write, + sa1110_bus_free }; + +bus_t * +new_sa1110_bus( chain_t *chain, int pn ) +{ + bus_t *bus; + + if (!chain || !chain->parts || chain->parts->len <= pn || pn < 0) + return NULL; + + bus = malloc( sizeof (bus_t) ); + if (!bus) + return NULL; + + memcpy( bus, &sa1110_bus, sizeof (bus_t) ); + + bus->params = malloc( sizeof (bus_params_t) ); + if (!bus->params) { + free( bus ); + return NULL; + } + + CHAIN = chain; + PART = chain->parts->parts[pn]; + + return bus; +} + diff --git a/jtag/src/cfi.c b/jtag/src/cfi.c index 36a8fa35..42edb1c3 100644 --- a/jtag/src/cfi.c +++ b/jtag/src/cfi.c @@ -34,42 +34,41 @@ #include "jtag.h" #include "bus.h" -#include "chain.h" /* function to cover 2x16 and 1x16 modes */ -#define BW16(x) ( (bus_width(chain) == 16) ? x : ( (x<<16) | x ) ) +#define BW16(x) ( (bus_width(bus) == 16) ? x : ( (x<<16) | x ) ) static uint16_t -read2( chain_t *chain, uint32_t adr, int o ) +read2( bus_t *bus, uint32_t adr, int o ) { uint16_t r; - bus_read_start( chain, adr << o ); - r = bus_read_next( chain, (adr + 1) << o ); - return ((bus_read_end( chain ) & 0xFF) << 8) | (r & 0xFF); + bus_read_start( bus, adr << o ); + r = bus_read_next( bus, (adr + 1) << o ); + return ((bus_read_end( bus ) & 0xFF) << 8) | (r & 0xFF); } cfi_query_structure_t * -detect_cfi( chain_t *chain ) +detect_cfi( bus_t *bus ) { cfi_query_structure_t *cfi; int o = 2; uint32_t tmp; - if (bus_width( chain ) == 16) + if (bus_width( bus ) == 16) o = 1; /* detect CFI capable devices - see Table 1 in [1] */ - bus_write( chain, CFI_CMD_QUERY_OFFSET << o, BW16(CFI_CMD_QUERY) ); - if (bus_read( chain, CFI_QUERY_ID_OFFSET << o ) != BW16('Q')) { + bus_write( bus, CFI_CMD_QUERY_OFFSET << o, BW16(CFI_CMD_QUERY) ); + if (bus_read( bus, CFI_QUERY_ID_OFFSET << o ) != BW16('Q')) { printf( "No CFI device detected (Q)!\n" ); return NULL; } - if (bus_read( chain, (CFI_QUERY_ID_OFFSET + 1) << o ) != BW16('R')) { + if (bus_read( bus, (CFI_QUERY_ID_OFFSET + 1) << o ) != BW16('R')) { printf( "No CFI device detected (R)!\n" ); return NULL; } - if (bus_read( chain, (CFI_QUERY_ID_OFFSET + 2) << o ) != BW16('Y')) { + if (bus_read( bus, (CFI_QUERY_ID_OFFSET + 2) << o ) != BW16('Y')) { printf( "No CFI device detected (Y)!\n" ); return NULL; } @@ -83,60 +82,60 @@ detect_cfi( chain_t *chain ) /* TODO: Low chip only (bits 15:0) */ /* Identification string - see Table 6 in [1] */ - cfi->identification_string.pri_id_code = read2( chain, PRI_VENDOR_ID_OFFSET, o ); + cfi->identification_string.pri_id_code = read2( bus, PRI_VENDOR_ID_OFFSET, o ); cfi->identification_string.pri_vendor_tbl = NULL; - cfi->identification_string.alt_id_code = read2( chain, ALT_VENDOR_ID_OFFSET, o ); + cfi->identification_string.alt_id_code = read2( bus, ALT_VENDOR_ID_OFFSET, o ); cfi->identification_string.alt_vendor_tbl = NULL; /* System interface information - see Table 7 in [1] */ - tmp = bus_read( chain, VCC_MIN_WEV_OFFSET << o ); + tmp = bus_read( bus, VCC_MIN_WEV_OFFSET << o ); cfi->system_interface_info.vcc_min_wev = ((tmp >> 4) & 0xF) * 1000 + (tmp & 0xF) * 100; - tmp = bus_read( chain, VCC_MAX_WEV_OFFSET << o ); + tmp = bus_read( bus, VCC_MAX_WEV_OFFSET << o ); cfi->system_interface_info.vcc_max_wev = ((tmp >> 4) & 0xF) * 1000 + (tmp & 0xF) * 100; - tmp = bus_read( chain, VPP_MIN_WEV_OFFSET << o ); + tmp = bus_read( bus, VPP_MIN_WEV_OFFSET << o ); cfi->system_interface_info.vpp_min_wev = ((tmp >> 4) & 0xF) * 1000 + (tmp & 0xF) * 100; - tmp = bus_read( chain, VPP_MAX_WEV_OFFSET << o ); + tmp = bus_read( bus, VPP_MAX_WEV_OFFSET << o ); cfi->system_interface_info.vpp_max_wev = ((tmp >> 4) & 0xF) * 1000 + (tmp & 0xF) * 100; /* TODO: Add out of range checks for timeouts */ - tmp = bus_read( chain, TYP_SINGLE_WRITE_TIMEOUT_OFFSET << o ) & 0xFF; + tmp = bus_read( bus, TYP_SINGLE_WRITE_TIMEOUT_OFFSET << o ) & 0xFF; cfi->system_interface_info.typ_single_write_timeout = tmp ? (1 << tmp) : 0; - tmp = bus_read( chain, TYP_BUFFER_WRITE_TIMEOUT_OFFSET << o ) & 0xFF; + tmp = bus_read( bus, TYP_BUFFER_WRITE_TIMEOUT_OFFSET << o ) & 0xFF; cfi->system_interface_info.typ_buffer_write_timeout = tmp ? (1 << tmp) : 0; - tmp = bus_read( chain, TYP_BLOCK_ERASE_TIMEOUT_OFFSET << o ) & 0xFF; + tmp = bus_read( bus, TYP_BLOCK_ERASE_TIMEOUT_OFFSET << o ) & 0xFF; cfi->system_interface_info.typ_block_erase_timeout = tmp ? (1 << tmp) : 0; - tmp = bus_read( chain, TYP_CHIP_ERASE_TIMEOUT_OFFSET << o ) & 0xFF; + tmp = bus_read( bus, TYP_CHIP_ERASE_TIMEOUT_OFFSET << o ) & 0xFF; cfi->system_interface_info.typ_chip_erase_timeout = tmp ? (1 << tmp) : 0; - tmp = bus_read( chain, MAX_SINGLE_WRITE_TIMEOUT_OFFSET << o ) & 0xFF; + tmp = bus_read( bus, MAX_SINGLE_WRITE_TIMEOUT_OFFSET << o ) & 0xFF; cfi->system_interface_info.max_single_write_timeout = (tmp ? (1 << tmp) : 0) * cfi->system_interface_info.typ_single_write_timeout; - tmp = bus_read( chain, MAX_BUFFER_WRITE_TIMEOUT_OFFSET << o ) & 0xFF; + tmp = bus_read( bus, MAX_BUFFER_WRITE_TIMEOUT_OFFSET << o ) & 0xFF; cfi->system_interface_info.max_buffer_write_timeout = (tmp ? (1 << tmp) : 0) * cfi->system_interface_info.typ_buffer_write_timeout; - tmp = bus_read( chain, MAX_BLOCK_ERASE_TIMEOUT_OFFSET << o ) & 0xFF; + tmp = bus_read( bus, MAX_BLOCK_ERASE_TIMEOUT_OFFSET << o ) & 0xFF; cfi->system_interface_info.max_block_erase_timeout = (tmp ? (1 << tmp) : 0) * cfi->system_interface_info.typ_block_erase_timeout; - tmp = bus_read( chain, MAX_CHIP_ERASE_TIMEOUT_OFFSET << o ) & 0xFF; + tmp = bus_read( bus, MAX_CHIP_ERASE_TIMEOUT_OFFSET << o ) & 0xFF; cfi->system_interface_info.max_chip_erase_timeout = (tmp ? (1 << tmp) : 0) * cfi->system_interface_info.typ_chip_erase_timeout; /* Device geometry - see Table 8 in [1] */ /* TODO: Add out of range check */ - cfi->device_geometry.device_size = 1 << (bus_read( chain, DEVICE_SIZE_OFFSET << o ) & 0xFF); + cfi->device_geometry.device_size = 1 << (bus_read( bus, DEVICE_SIZE_OFFSET << o ) & 0xFF); - cfi->device_geometry.device_interface = read2( chain, FLASH_DEVICE_INTERFACE_OFFSET, o ); + cfi->device_geometry.device_interface = read2( bus, FLASH_DEVICE_INTERFACE_OFFSET, o ); /* TODO: Add out of range check */ - cfi->device_geometry.max_bytes_write = 1 << read2( chain, MAX_BYTES_WRITE_OFFSET, o ); + cfi->device_geometry.max_bytes_write = 1 << read2( bus, MAX_BYTES_WRITE_OFFSET, o ); - tmp = bus_read( chain, NUMBER_OF_ERASE_REGIONS_OFFSET << o ) & 0xFF; + tmp = bus_read( bus, NUMBER_OF_ERASE_REGIONS_OFFSET << o ) & 0xFF; cfi->device_geometry.number_of_erase_regions = tmp; cfi->device_geometry.erase_block_regions = malloc( tmp * sizeof (cfi_erase_block_region_t) ); @@ -150,8 +149,8 @@ detect_cfi( chain_t *chain ) int i; for (i = 0, a = ERASE_BLOCK_REGION_OFFSET; i < tmp; i++, a += 4) { - uint32_t y = read2( chain, a, o ); - uint32_t z = read2( chain, a + 2, o ) << 8; + uint32_t y = read2( bus, a, o ); + uint32_t z = read2( bus, a + 2, o ) << 8; if (z == 0) z = 128; cfi->device_geometry.erase_block_regions[i].erase_block_size = z; @@ -162,7 +161,7 @@ detect_cfi( chain_t *chain ) /* TODO: Intel Primary Algorithm Extended Query Table - see Table 5. in [2] */ /* Read Array */ - bus_write( chain, 0, (CFI_CMD_READ_ARRAY1 << 16) | CFI_CMD_READ_ARRAY1 ); + bus_write( bus, 0, (CFI_CMD_READ_ARRAY1 << 16) | CFI_CMD_READ_ARRAY1 ); return cfi; } diff --git a/jtag/src/flash-amd.c b/jtag/src/flash-amd.c index 3b68a9d1..43868bfe 100644 --- a/jtag/src/flash-amd.c +++ b/jtag/src/flash-amd.c @@ -37,18 +37,18 @@ #include #include "flash.h" -#include "chain.h" +#include "bus.h" static int dbg = 0; -static int amd_flash_erase_block( chain_t *chain, uint32_t adr ); -static int amd_flash_unlock_block( chain_t *chain, uint32_t adr ); -static int amd_flash_program( chain_t *chain, uint32_t adr, uint32_t data ); -static void amd_flash_read_array( chain_t *chain ); +static int amd_flash_erase_block( bus_t *bus, uint32_t adr ); +static int amd_flash_unlock_block( bus_t *bus, uint32_t adr ); +static int amd_flash_program( bus_t *bus, uint32_t adr, uint32_t data ); +static void amd_flash_read_array( bus_t *bus ); /* autodetect, we can handle this chip */ static int -amd_flash_autodetect( chain_t *chain, cfi_query_structure_t *cfi ) +amd_flash_autodetect( bus_t *bus, cfi_query_structure_t *cfi ) { return (cfi->identification_string.pri_id_code == CFI_VENDOR_AMD_SCS); } @@ -97,15 +97,15 @@ amdstatus29( parts *ps, uint32_t adr, uint32_t data ) * second implementation: see [1], page 30 */ static int -amdstatus( chain_t *chain, uint32_t adr, int data ) +amdstatus( bus_t *bus, uint32_t adr, int data ) { int timeout; uint32_t togglemask = ((1 << 6) << 16) + (1 << 6); /* DQ 6 */ /* int dq5mask = ((1 << 5) << 16) + (1 << 5); DQ5 */ for (timeout = 0; timeout < 100; timeout++) { - uint32_t data1 = bus_read( chain, adr ); - uint32_t data2 = bus_read( chain, adr ); + uint32_t data1 = bus_read( bus, adr ); + uint32_t data2 = bus_read( bus, adr ); /*printf("amdstatus %d: %04X/%04X %04X/%04X \n", */ /* timeout, data1, data2, (data1 & togglemask), (data2 & togglemask)); */ @@ -143,17 +143,18 @@ amdisprotected( parts *ps, uint32_t adr ) #endif /* 0 */ static void -amd_flash_print_info( chain_t *chain ) +amd_flash_print_info( bus_t *bus ) { int o = 2; int mid, cid, prot; - bus_write( chain, 0x0555 << o, 0x00aa00aa ); /* autoselect p29 */ - bus_write( chain, 0x02aa << o, 0x00550055 ); - bus_write( chain, 0x0555 << o, 0x00900090 ); - mid = bus_read( chain, 0x00 << o ) & 0xFFFF; - cid = bus_read( chain, 0x01 << o ) & 0xFFFF; - prot = bus_read( chain, 0x02 << o ) & 0xFF; - amd_flash_read_array( chain ); /* AMD reset */ + + bus_write( bus, 0x0555 << o, 0x00aa00aa ); /* autoselect p29 */ + bus_write( bus, 0x02aa << o, 0x00550055 ); + bus_write( bus, 0x0555 << o, 0x00900090 ); + mid = bus_read( bus, 0x00 << o ) & 0xFFFF; + cid = bus_read( bus, 0x01 << o ) & 0xFFFF; + prot = bus_read( bus, 0x02 << o ) & 0xFF; + amd_flash_read_array( bus ); /* AMD reset */ printf( "Chip: AMD Flash\n\tManufacturer: " ); switch (mid) { case 0x0001: @@ -176,7 +177,7 @@ amd_flash_print_info( chain_t *chain ) } static int -amd_flash_erase_block( chain_t *chain, uint32_t adr ) +amd_flash_erase_block( bus_t *bus, uint32_t adr ) { int o = 2; @@ -184,34 +185,34 @@ amd_flash_erase_block( chain_t *chain, uint32_t adr ) /* printf("protected: %d\n", amdisprotected(ps, adr)); */ - bus_write( chain, 0x0555 << o, 0x00aa00aa ); /* autoselect p29, sector erase */ - bus_write( chain, 0x02aa << o, 0x00550055 ); - bus_write( chain, 0x0555 << o, 0x00800080 ); - bus_write( chain, 0x0555 << o, 0x00aa00aa ); - bus_write( chain, 0x02aa << o, 0x00550055 ); - bus_write( chain, adr, 0x00300030 ); + bus_write( bus, 0x0555 << o, 0x00aa00aa ); /* autoselect p29, sector erase */ + bus_write( bus, 0x02aa << o, 0x00550055 ); + bus_write( bus, 0x0555 << o, 0x00800080 ); + bus_write( bus, 0x0555 << o, 0x00aa00aa ); + bus_write( bus, 0x02aa << o, 0x00550055 ); + bus_write( bus, adr, 0x00300030 ); - if (amdstatus( chain, adr, 0xffff )) { + if (amdstatus( bus, adr, 0xffff )) { printf( "flash_erase_block 0x%08X DONE\n", adr ); - amd_flash_read_array( chain ); /* AMD reset */ + amd_flash_read_array( bus ); /* AMD reset */ return 0; } printf( "flash_erase_block 0x%08X FAILED\n", adr ); /* Read Array */ - amd_flash_read_array( chain ); /* AMD reset */ + amd_flash_read_array( bus ); /* AMD reset */ return CFI_INTEL_ERROR_UNKNOWN; } static int -amd_flash_unlock_block( chain_t *chain, uint32_t adr ) +amd_flash_unlock_block( bus_t *bus, uint32_t adr ) { printf( "flash_unlock_block 0x%08X IGNORE\n", adr ); return 0; } static int -amd_flash_program( chain_t *chain, uint32_t adr, uint32_t data ) +amd_flash_program( bus_t *bus, uint32_t adr, uint32_t data ) { int o = 2; int status; @@ -219,22 +220,22 @@ amd_flash_program( chain_t *chain, uint32_t adr, uint32_t data ) if (dbg) printf("\nflash_program 0x%08X = 0x%08X\n", adr, data); - bus_write( chain, 0x0555 << o, 0x00aa00aa ); /* autoselect p29, program */ - bus_write( chain, 0x02aa << o, 0x00550055 ); - bus_write( chain, 0x0555 << o, 0x00A000A0 ); + bus_write( bus, 0x0555 << o, 0x00aa00aa ); /* autoselect p29, program */ + bus_write( bus, 0x02aa << o, 0x00550055 ); + bus_write( bus, 0x0555 << o, 0x00A000A0 ); - bus_write( chain, adr, data ); - status = amdstatus( chain, adr, data ); + bus_write( bus, adr, data ); + status = amdstatus( bus, adr, data ); /* amd_flash_read_array(ps); */ return !status; } static void -amd_flash_read_array( chain_t *chain ) +amd_flash_read_array( bus_t *bus ) { /* Read Array */ - bus_write( chain, 0x0, 0x00F000F0 ); /* AMD reset */ + bus_write( bus, 0x0, 0x00F000F0 ); /* AMD reset */ } flash_driver_t amd_32_flash_driver = { diff --git a/jtag/src/flash-intel.c b/jtag/src/flash-intel.c index 534cdb8a..643ba101 100644 --- a/jtag/src/flash-intel.c +++ b/jtag/src/flash-intel.c @@ -41,34 +41,34 @@ #include #include "flash.h" -#include "chain.h" +#include "bus.h" -static int intel_flash_erase_block( chain_t *chain, uint32_t adr ); -static int intel_flash_unlock_block( chain_t *chain, uint32_t adr ); -static int intel_flash_program( chain_t *chain, uint32_t adr, uint32_t data ); -static int intel_flash_erase_block32( chain_t *chain, uint32_t adr ); -static int intel_flash_unlock_block32( chain_t *chain, uint32_t adr ); -static int intel_flash_program32( chain_t *chain, uint32_t adr, uint32_t data ); +static int intel_flash_erase_block( bus_t *bus, uint32_t adr ); +static int intel_flash_unlock_block( bus_t *bus, uint32_t adr ); +static int intel_flash_program( bus_t *bus, uint32_t adr, uint32_t data ); +static int intel_flash_erase_block32( bus_t *bus, uint32_t adr ); +static int intel_flash_unlock_block32( bus_t *bus, uint32_t adr ); +static int intel_flash_program32( bus_t *bus, uint32_t adr, uint32_t data ); /* autodetect, we can handle this chip */ static int -intel_flash_autodetect32( chain_t *chain, cfi_query_structure_t *cfi ) +intel_flash_autodetect32( bus_t *bus, cfi_query_structure_t *cfi ) { - return (cfi->identification_string.pri_id_code == CFI_VENDOR_INTEL_ECS) && (bus_width( chain ) == 32); + return (cfi->identification_string.pri_id_code == CFI_VENDOR_INTEL_ECS) && (bus_width( bus ) == 32); } static int -intel_flash_autodetect( chain_t *chain, cfi_query_structure_t *cfi ) +intel_flash_autodetect( bus_t *bus, cfi_query_structure_t *cfi ) { - return (cfi->identification_string.pri_id_code == CFI_VENDOR_INTEL_ECS) && (bus_width( chain ) == 16); + return (cfi->identification_string.pri_id_code == CFI_VENDOR_INTEL_ECS) && (bus_width( bus ) == 16); } -static -void _intel_flash_print_info( chain_t *chain, int o ) +static void +_intel_flash_print_info( bus_t *bus, int o ) { uint32_t mid, cid; - mid = (bus_read( chain, 0x00 << o ) & 0xFF); + mid = (bus_read( bus, 0x00 << o ) & 0xFF); switch (mid) { case STD_MIC_INTEL: printf( "Manufacturer: %s\n", STD_MICN_INTEL ); @@ -79,7 +79,7 @@ void _intel_flash_print_info( chain_t *chain, int o ) } printf( "Chip: " ); - cid = (bus_read( chain, 0x01 << o ) & 0xFFFF); + cid = (bus_read( bus, 0x01 << o ) & 0xFFFF); switch (cid) { case 0x0016: printf( "28F320J3A\n" ); @@ -114,51 +114,51 @@ void _intel_flash_print_info( chain_t *chain, int o ) } /* Read Array */ - bus_write( chain, 0 << o, 0x00FF00FF ); + bus_write( bus, 0 << o, 0x00FF00FF ); } -static -void intel_flash_print_info( chain_t *chain ) +static void +intel_flash_print_info( bus_t *bus ) { int o = 1; /* Intel Primary Algorithm Extended Query Table - see Table 5. in [3] */ /* TODO */ /* Clear Status Register */ - bus_write( chain, 0 << o, 0x0050 ); + bus_write( bus, 0 << o, 0x0050 ); /* Read Identifier Command */ - bus_write( chain, 0 << 0, 0x0090 ); + bus_write( bus, 0 << 0, 0x0090 ); - _intel_flash_print_info( chain, o ); + _intel_flash_print_info( bus, o ); } -static -void intel_flash_print_info32( chain_t *chain ) +static void +intel_flash_print_info32( bus_t *bus ) { int o = 2; /* Intel Primary Algorithm Extended Query Table - see Table 5. in [3] */ /* TODO */ /* Clear Status Register */ - bus_write( chain, 0 << o, 0x00500050 ); + bus_write( bus, 0 << o, 0x00500050 ); /* Read Identifier Command */ - bus_write( chain, 0 << 0, 0x00900090 ); + bus_write( bus, 0 << 0, 0x00900090 ); - _intel_flash_print_info( chain, o ); + _intel_flash_print_info( bus, o ); } static int -intel_flash_erase_block( chain_t *chain, uint32_t adr ) +intel_flash_erase_block( bus_t *bus, uint32_t adr ) { uint16_t sr; - bus_write( chain, 0, CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); - bus_write( chain, adr, CFI_INTEL_CMD_BLOCK_ERASE ); - bus_write( chain, adr, CFI_INTEL_CMD_CONFIRM ); + bus_write( bus, 0, CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); + bus_write( bus, adr, CFI_INTEL_CMD_BLOCK_ERASE ); + bus_write( bus, adr, CFI_INTEL_CMD_CONFIRM ); - while (!((sr = bus_read( chain, 0 ) & 0xFE) & CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ + while (!((sr = bus_read( bus, 0 ) & 0xFE) & CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ switch (sr & ~CFI_INTEL_SR_READY) { case 0: @@ -180,15 +180,15 @@ intel_flash_erase_block( chain_t *chain, uint32_t adr ) } static int -intel_flash_unlock_block( chain_t *chain, uint32_t adr ) +intel_flash_unlock_block( bus_t *bus, uint32_t adr ) { uint16_t sr; - bus_write( chain, 0, CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); - bus_write( chain, adr, CFI_INTEL_CMD_LOCK_SETUP ); - bus_write( chain, adr, CFI_INTEL_CMD_UNLOCK_BLOCK ); + bus_write( bus, 0, CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); + bus_write( bus, adr, CFI_INTEL_CMD_LOCK_SETUP ); + bus_write( bus, adr, CFI_INTEL_CMD_UNLOCK_BLOCK ); - while (!((sr = bus_read( chain, 0 ) & 0xFE) & CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ + while (!((sr = bus_read( bus, 0 ) & 0xFE) & CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ if (sr != CFI_INTEL_SR_READY) { printf("flash: unknown error while unblocking\n"); @@ -198,15 +198,15 @@ intel_flash_unlock_block( chain_t *chain, uint32_t adr ) } static int -intel_flash_program( chain_t *chain, uint32_t adr, uint32_t data ) +intel_flash_program( bus_t *bus, uint32_t adr, uint32_t data ) { uint16_t sr; - bus_write( chain, 0, CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); - bus_write( chain, adr, CFI_INTEL_CMD_PROGRAM1 ); - bus_write( chain, adr, data ); + bus_write( bus, 0, CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); + bus_write( bus, adr, CFI_INTEL_CMD_PROGRAM1 ); + bus_write( bus, adr, data ); - while (!((sr = bus_read( chain, 0 ) & 0xFE) & CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ + while (!((sr = bus_read( bus, 0 ) & 0xFE) & CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ if (sr != CFI_INTEL_SR_READY) { printf("flash: unknown error while programming\n"); @@ -216,15 +216,15 @@ intel_flash_program( chain_t *chain, uint32_t adr, uint32_t data ) } static int -intel_flash_erase_block32( chain_t *chain, uint32_t adr ) +intel_flash_erase_block32( bus_t *bus, uint32_t adr ) { uint32_t sr; - bus_write( chain, 0, (CFI_INTEL_CMD_CLEAR_STATUS_REGISTER << 16) | CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); - bus_write( chain, adr, (CFI_INTEL_CMD_BLOCK_ERASE << 16) | CFI_INTEL_CMD_BLOCK_ERASE ); - bus_write( chain, adr, (CFI_INTEL_CMD_CONFIRM << 16) | CFI_INTEL_CMD_CONFIRM ); + bus_write( bus, 0, (CFI_INTEL_CMD_CLEAR_STATUS_REGISTER << 16) | CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); + bus_write( bus, adr, (CFI_INTEL_CMD_BLOCK_ERASE << 16) | CFI_INTEL_CMD_BLOCK_ERASE ); + bus_write( bus, adr, (CFI_INTEL_CMD_CONFIRM << 16) | CFI_INTEL_CMD_CONFIRM ); - while (((sr = bus_read( chain, 0 ) & 0x00FE00FE) & ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) != ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ + while (((sr = bus_read( bus, 0 ) & 0x00FE00FE) & ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) != ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ if (sr != ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) { printf( "\nsr = 0x%08X\n", sr ); @@ -234,15 +234,15 @@ intel_flash_erase_block32( chain_t *chain, uint32_t adr ) } static int -intel_flash_unlock_block32( chain_t *chain, uint32_t adr ) +intel_flash_unlock_block32( bus_t *bus, uint32_t adr ) { uint32_t sr; - bus_write( chain, 0, (CFI_INTEL_CMD_CLEAR_STATUS_REGISTER << 16) | CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); - bus_write( chain, adr, (CFI_INTEL_CMD_LOCK_SETUP << 16) | CFI_INTEL_CMD_LOCK_SETUP ); - bus_write( chain, adr, (CFI_INTEL_CMD_UNLOCK_BLOCK << 16) | CFI_INTEL_CMD_UNLOCK_BLOCK ); + bus_write( bus, 0, (CFI_INTEL_CMD_CLEAR_STATUS_REGISTER << 16) | CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); + bus_write( bus, adr, (CFI_INTEL_CMD_LOCK_SETUP << 16) | CFI_INTEL_CMD_LOCK_SETUP ); + bus_write( bus, adr, (CFI_INTEL_CMD_UNLOCK_BLOCK << 16) | CFI_INTEL_CMD_UNLOCK_BLOCK ); - while (((sr = bus_read( chain, 0 ) & 0x00FE00FE) & ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) != ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ + while (((sr = bus_read( bus, 0 ) & 0x00FE00FE) & ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) != ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ if (sr != ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) { printf( "\nsr = 0x%08X\n", sr ); @@ -252,15 +252,15 @@ intel_flash_unlock_block32( chain_t *chain, uint32_t adr ) } static int -intel_flash_program32( chain_t *chain, uint32_t adr, uint32_t data ) +intel_flash_program32( bus_t *bus, uint32_t adr, uint32_t data ) { uint32_t sr; - bus_write( chain, 0, (CFI_INTEL_CMD_CLEAR_STATUS_REGISTER << 16) | CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); - bus_write( chain, adr, (CFI_INTEL_CMD_PROGRAM1 << 16) | CFI_INTEL_CMD_PROGRAM1 ); - bus_write( chain, adr, data ); + bus_write( bus, 0, (CFI_INTEL_CMD_CLEAR_STATUS_REGISTER << 16) | CFI_INTEL_CMD_CLEAR_STATUS_REGISTER ); + bus_write( bus, adr, (CFI_INTEL_CMD_PROGRAM1 << 16) | CFI_INTEL_CMD_PROGRAM1 ); + bus_write( bus, adr, data ); - while (((sr = bus_read( chain, 0 ) & 0x00FE00FE) & ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) != ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ + while (((sr = bus_read( bus, 0 ) & 0x00FE00FE) & ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) != ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) ; /* TODO: add timeout */ if (sr != ((CFI_INTEL_SR_READY << 16) | CFI_INTEL_SR_READY)) { printf( "\nsr = 0x%08X\n", sr ); @@ -270,17 +270,17 @@ intel_flash_program32( chain_t *chain, uint32_t adr, uint32_t data ) } static void -intel_flash_readarray32( chain_t *chain ) +intel_flash_readarray32( bus_t *bus ) { /* Read Array */ - bus_write( chain, 0, 0x00FF00FF ); + bus_write( bus, 0, 0x00FF00FF ); } static void -intel_flash_readarray( chain_t *chain ) +intel_flash_readarray( bus_t *bus ) { /* Read Array */ - bus_write( chain, 0, 0x00FF00FF ); + bus_write( bus, 0, 0x00FF00FF ); } flash_driver_t intel_32_flash_driver = { diff --git a/jtag/src/flash.c b/jtag/src/flash.c index aaea1fa8..dc8145bb 100644 --- a/jtag/src/flash.c +++ b/jtag/src/flash.c @@ -41,7 +41,6 @@ #include /* for ntohs */ -#include "part.h" #include "bus.h" #include "flash.h" @@ -61,13 +60,13 @@ flash_driver_t *flash_drivers[] = { flash_driver_t *flash_driver = NULL; void -set_flash_driver( chain_t *chain, cfi_query_structure_t *cfi ) +set_flash_driver( bus_t *bus, cfi_query_structure_t *cfi ) { int i; flash_driver = NULL; for (i = 0; flash_drivers[i] != NULL; i++) - if (flash_drivers[i]->flash_autodetect( chain, cfi )) { + if (flash_drivers[i]->flash_autodetect( bus, cfi )) { flash_driver = flash_drivers[i]; return; } @@ -79,16 +78,16 @@ set_flash_driver( chain_t *chain, cfi_query_structure_t *cfi ) /* check for flashmem - set driver */ static void -flashcheck( chain_t *chain, cfi_query_structure_t **cfi ) +flashcheck( bus_t *bus, cfi_query_structure_t **cfi ) { - parts_t *ps = chain->parts; - part *p = ps->parts[0]; int o = 0; flash_driver = NULL; + bus_prepare( bus ); + printf( "Note: Supported configuration is 2 x 16 bit or 1 x 16 bit only\n" ); - switch (bus_width( chain )) { + switch (bus_width( bus )) { case 16: o = 1; break; @@ -100,31 +99,26 @@ flashcheck( chain_t *chain, cfi_query_structure_t **cfi ) return; } - /* EXTEST */ - part_set_instruction( p, "EXTEST" ); - chain_shift_instructions( chain ); - - *cfi = detect_cfi( chain ); + *cfi = detect_cfi( bus ); if (!*cfi) { printf( "Flash not found!\n" ); return; } - set_flash_driver( chain, *cfi ); + set_flash_driver( bus, *cfi ); if (!flash_driver) { printf( "Flash not supported!\n" ); return; } - flash_driver->flash_print_info( chain ); + flash_driver->flash_print_info( bus ); } void -flashmsbin( chain_t *chain, FILE *f ) +flashmsbin( bus_t *bus, FILE *f ) { - parts_t *ps = chain->parts; uint32_t adr; - cfi_query_structure_t *cfi = 0; + cfi_query_structure_t *cfi = NULL; - flashcheck( chain, &cfi ); + flashcheck( bus, &cfi ); if (!cfi || !flash_driver) { printf( "no flash driver found\n" ); return; @@ -153,9 +147,9 @@ flashmsbin( chain_t *chain, FILE *f ) last = (start + len - 1) / (cfi->device_geometry.erase_block_regions[0].erase_block_size * 2); for (; first <= last; first++) { adr = first * cfi->device_geometry.erase_block_regions[0].erase_block_size * 2; - flash_unlock_block( chain, adr ); + flash_unlock_block( bus, adr ); printf( "block %d unlocked\n", first ); - printf( "erasing block %d: %d\n", first, flash_erase_block( chain, adr ) ); + printf( "erasing block %d: %d\n", first, flash_erase_block( bus, adr ) ); } } @@ -184,7 +178,7 @@ flashmsbin( chain_t *chain, FILE *f ) printf( "addr: 0x%08X\r", a ); fflush(stdout); fread( &data, sizeof data, 1, f ); - if (flash_program( chain, a, data )) { + if (flash_program( bus, a, data )) { printf( "\nflash error\n" ); return; } @@ -194,7 +188,7 @@ flashmsbin( chain_t *chain, FILE *f ) } printf( "\n" ); - flash_readarray( chain ); + flash_readarray( bus ); fseek( f, 15, SEEK_SET ); printf( "verify:\n" ); @@ -223,7 +217,7 @@ flashmsbin( chain_t *chain, FILE *f ) printf( "addr: 0x%08X\r", a ); fflush( stdout ); fread( &data, sizeof data, 1, f ); - readed = bus_read( chain, a ); + readed = bus_read( bus, a ); if (data != readed) { printf( "\nverify error: 0x%08X vs. 0x%08X at addr %08X\n", readed, data, a ); @@ -235,23 +229,18 @@ flashmsbin( chain_t *chain, FILE *f ) } printf( "\n" ); - /* BYPASS */ - parts_set_instruction( ps, "BYPASS" ); - chain_shift_instructions( chain ); - printf( "Done.\n" ); } void -flashmem( chain_t *chain, FILE *f, uint32_t addr ) +flashmem( bus_t *bus, FILE *f, uint32_t addr ) { - parts_t *ps = chain->parts; uint32_t adr; cfi_query_structure_t *cfi = NULL; int *erased; int i; - flashcheck( chain, &cfi ); + flashcheck( bus, &cfi ); if (!cfi || !flash_driver) { printf( "no flash driver found\n" ); return; @@ -275,9 +264,9 @@ flashmem( chain_t *chain, FILE *f, uint32_t addr ) int block_no = adr / (cfi->device_geometry.erase_block_regions[0].erase_block_size * flash_driver->buswidth / 2); if (!erased[block_no]) { - flash_unlock_block( chain, adr ); + flash_unlock_block( bus, adr ); printf( "\nblock %d unlocked\n", block_no ); - printf( "erasing block %d: %d\n", block_no, flash_erase_block( chain, adr ) ); + printf( "erasing block %d: %d\n", block_no, flash_erase_block( bus, adr ) ); erased[block_no] = 1; } @@ -289,7 +278,7 @@ flashmem( chain_t *chain, FILE *f, uint32_t addr ) data = htons( *((uint16_t *) &b[bc]) ); else data = * ((uint32_t *) &b[bc]); - if (flash_program( chain, adr, data )) { + if (flash_program( bus, adr, data )) { printf( "\nflash error\n" ); return; } @@ -298,7 +287,7 @@ flashmem( chain_t *chain, FILE *f, uint32_t addr ) } printf( "\n" ); - flash_readarray( chain ); + flash_readarray( bus ); if (flash_driver->buswidth == 4) { /* TODO: not available in 1 x 16 bit mode */ fseek( f, 0, SEEK_SET ); @@ -318,7 +307,7 @@ flashmem( chain_t *chain, FILE *f, uint32_t addr ) printf( "addr: 0x%08X\r", adr ); fflush( stdout ); - readed = bus_read( chain, adr ); + readed = bus_read( bus, adr ); if (data != readed) { printf( "\nverify error:\nreaded: 0x%08X\nexpected: 0x%08X\n", readed, data ); return; @@ -329,13 +318,5 @@ flashmem( chain_t *chain, FILE *f, uint32_t addr ) } else printf( "TODO: Verify is not available in 1 x 16 bit mode.\n" ); - /* BYPASS */ - parts_set_instruction( ps, "BYPASS" ); - chain_shift_instructions( chain ); - free( erased ); } - - - - diff --git a/jtag/src/flash.h b/jtag/src/flash.h index 9889486c..faa05b73 100644 --- a/jtag/src/flash.h +++ b/jtag/src/flash.h @@ -31,18 +31,17 @@ #include "part.h" #include "bus.h" -#include "chain.h" typedef struct { int buswidth; /* supported bus width, 1/2/4 bytes */ const char *name; const char *description; - int (*flash_autodetect)( chain_t *, cfi_query_structure_t * ); - void (*flash_print_info)( chain_t * ); - int (*flash_erase_block)( chain_t *, uint32_t ); - int (*flash_unlock_block)( chain_t *, uint32_t ); - int (*flash_program)( chain_t *, uint32_t, uint32_t ); - void (*flash_readarray)( chain_t *chain ); + int (*flash_autodetect)( bus_t *bus, cfi_query_structure_t *cfi ); + void (*flash_print_info)( bus_t *bus ); + int (*flash_erase_block)( bus_t *bus, uint32_t adr ); + int (*flash_unlock_block)( bus_t *bus, uint32_t adr ); + int (*flash_program)( bus_t *bus, uint32_t adr, uint32_t data ); + void (*flash_readarray)( bus_t *bus ); } flash_driver_t; extern flash_driver_t *flash_driver; @@ -54,7 +53,7 @@ extern flash_driver_t *flash_drivers[]; #define flash_program flash_driver->flash_program #define flash_readarray flash_driver->flash_readarray -extern void set_flash_driver( chain_t *chain, cfi_query_structure_t *cfi ); +extern void set_flash_driver( bus_t *bus, cfi_query_structure_t *cfi ); #define CFI_INTEL_ERROR_UNKNOWN 1 #define CFI_INTEL_ERROR_UNSUPPORTED 2 diff --git a/jtag/src/jtag.c b/jtag/src/jtag.c index 738c6b0c..278f782d 100644 --- a/jtag/src/jtag.c +++ b/jtag/src/jtag.c @@ -52,7 +52,7 @@ ssize_t getline( char **lineptr, size_t *n, FILE *stream ); #endif chain_t *chain = NULL; -bus_driver_t *bus_driver = NULL; +bus_t *bus = NULL; static char * get_token( char *buf ) @@ -84,7 +84,7 @@ jtag_create_jtagdir( void ) strcat( jdir, JTAGDIR ); /* Create the directory if it doesn't exists. */ - mkdir( jdir, 0755 ); + mkdir( jdir, S_IRWXU | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH ); free( jdir ); } @@ -269,6 +269,10 @@ jtag_parse_line( char *line ) return 1; } + if (bus) { + bus->free( bus ); + bus = NULL; + } parts_free( chain->parts ); chain->parts = detect_parts( chain, JTAG_DATA_DIR ); if (!chain->parts->len) { @@ -282,11 +286,11 @@ jtag_parse_line( char *line ) parts_set_instruction( chain->parts, "BYPASS" ); chain_shift_instructions( chain ); if (strcmp( chain->parts->parts[0]->part, "SA1110" ) == 0) - bus_driver = &sa1110_bus_driver; + bus = new_sa1110_bus( chain, 0 ); if (strcmp( chain->parts->parts[0]->part, "PXA250" ) == 0) - bus_driver = &pxa250_bus_driver; + bus = new_pxa250_bus( chain, 0 ); if (strcmp( chain->parts->parts[0]->part, "IXP425" ) == 0) - bus_driver = &ixp425_bus_driver; + bus = new_ixp425_bus( chain, 0 ); return 1; } @@ -334,9 +338,9 @@ jtag_parse_line( char *line ) return 1; } if (msbin) - flashmsbin( chain, f ); + flashmsbin( bus, f ); else - flashmem( chain, f, addr ); + flashmem( bus, f, addr ); fclose( f ); return 1; } @@ -392,7 +396,7 @@ jtag_parse_line( char *line ) printf( _("Unable to create file `%s'!\n"), t ); return 1; } - readmem( chain, f, addr, len ); + readmem( bus, f, addr, len ); fclose( f ); return 1; @@ -414,7 +418,7 @@ jtag_parse_line( char *line ) return 1; } - detectflash( chain ); + detectflash( bus ); return 1; } @@ -841,6 +845,10 @@ main( int argc, const char **argv ) } } + if (bus) { + bus->free( bus ); + bus = NULL; + } chain_free( chain ); return 0; diff --git a/jtag/src/jtag.h b/jtag/src/jtag.h index b41d2bea..d7628202 100644 --- a/jtag/src/jtag.h +++ b/jtag/src/jtag.h @@ -32,17 +32,18 @@ #include "part.h" #include "chain.h" +#include "bus.h" parts_t *detect_parts( chain_t* chain, char *db_path ); -void detectflash( chain_t *chain ); -void readmem( chain_t *chain, FILE *f, uint32_t addr, uint32_t len ); -void flashmem( chain_t *chain, FILE *f, uint32_t addr ); -void flashmsbin( chain_t *chain, FILE *f ); +void detectflash( bus_t *bus ); +void readmem( bus_t *bus, FILE *f, uint32_t addr, uint32_t len ); +void flashmem( bus_t *bus, FILE *f, uint32_t addr ); +void flashmsbin( bus_t *bus, FILE *f ); void help( const char *cmd ); void discovery( chain_t *chain, const char *filename ); -cfi_query_structure_t *detect_cfi( chain_t *chain ); +cfi_query_structure_t *detect_cfi( bus_t *bus ); #endif /* JTAG_H */ diff --git a/jtag/src/readmem.c b/jtag/src/readmem.c index 7bda247b..a02665bd 100644 --- a/jtag/src/readmem.c +++ b/jtag/src/readmem.c @@ -43,27 +43,25 @@ #include /* for ntohs */ -#include "part.h" #include "bus.h" #include "flash.h" -#include "chain.h" void -detectflash( chain_t *chain ) +detectflash( bus_t *bus ) { - parts_t *ps = chain->parts; - part *p = ps->parts[0]; int o = 0; cfi_query_structure_t *cfi; - if (!bus_driver) { - printf( "Error: Missing bus_driver!\n" ); + if (!bus) { + printf( "Error: Missing bus driver!\n" ); return; } + bus_prepare( bus ); + printf( "Note: Supported configuration is 2 x 16 bit or 1 x 16 bit only\n" ); - switch (bus_width( chain )) { + switch (bus_width( bus )) { case 16: o = 1; break; @@ -75,11 +73,7 @@ detectflash( chain_t *chain ) return; } - /* EXTEST */ - part_set_instruction( p, "EXTEST" ); - chain_shift_instructions( chain ); - - cfi = detect_cfi( chain ); + cfi = detect_cfi( bus ); if (!cfi) { printf( "Flash not found!\n" ); return; @@ -211,36 +205,32 @@ detectflash( chain_t *chain ) } } - set_flash_driver( chain, cfi ); + set_flash_driver( bus, cfi ); if (flash_driver) - flash_driver->flash_print_info( chain ); + flash_driver->flash_print_info( bus ); } void -readmem( chain_t *chain, FILE *f, uint32_t addr, uint32_t len ) +readmem( bus_t *bus, FILE *f, uint32_t addr, uint32_t len ) { - parts_t *ps = chain->parts; - part *p = ps->parts[0]; int step = 0; uint32_t a; int bc = 0; - if (!bus_driver) { - printf( "Error: Missing bus_driver!\n" ); + if (!bus) { + printf( "Error: Missing bus driver!\n" ); return; } - step = bus_width( chain ) / 8; + bus_prepare( bus ); + + step = bus_width( bus ) / 8; if (step == 0) { printf( "Unknown bus width!\n" ); return; } - /* EXTEST */ - part_set_instruction( p, "EXTEST" ); - chain_shift_instructions( chain ); - addr = addr & (~(step - 1)); len = (len + step - 1) & (~(step - 1)); @@ -253,7 +243,7 @@ readmem( chain_t *chain, FILE *f, uint32_t addr, uint32_t len ) } printf( "reading:\n" ); - bus_read_start( chain, addr ); + bus_read_start( bus, addr ); for (a = addr + step; a <= addr + len; a += step) { uint32_t d = 0; uint16_t d16 = 0; @@ -262,15 +252,15 @@ readmem( chain_t *chain, FILE *f, uint32_t addr, uint32_t len ) if (a < addr + len) { if (step == 2) - d16 = bus_read_next( chain, a ); + d16 = bus_read_next( bus, a ); else - d = bus_read_next( chain, a ); + d = bus_read_next( bus, a ); } else { if (step == 2) - d16 = bus_read_end( chain ); + d16 = bus_read_end( bus ); else - d = bus_read_end( chain ); + d = bus_read_end( bus ); } if (step == 2) *((uint16_t *) &b[bc]) = ntohs(d16);