Compare commits

...

195 Commits

Author SHA1 Message Date
David Brownell
a0a1be5cd6 v4.0-rc2 milestone
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-13 14:47:17 -08:00
Spencer Oliver
f7a6e62776 STR9xpec: issue warning when unlocking device
Issue warning to user when unlocking or writing the option bytes.
The new settings will not take effect until a target reset.

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-02-12 10:49:18 +00:00
Spencer Oliver
747a607aef STM32x: issue warning when unlocking device (bug #16)
Issue warning to user when unlocking or writing the option bytes.
The new settings will not take effect until a target reset.

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-02-12 10:49:11 +00:00
Øyvind Harboe
d4d4b11a77 arm720t: virt2phys callback added
This is a copy and paste of arm926ejs. Not tested, but
ready for testing at least. There is a good chance that
it will work if the generic armv4_5 fn's are robust enough...

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-02-12 08:39:56 +01:00
Marc Pignat
ff404da155 arm920: add virt2phys fn
Copy of the 926ejs function. I have tested it only using
my rtems application (where virtual address mapping == physical).

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-02-12 08:31:06 +01:00
Viktar Palstsiuk
32188c5004 target library: configuration files for openocd tested with Atmel SAM-ICE V6 JTAG.
Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-02-11 21:10:51 +01:00
David Brownell
527e073bba User's Guide: "#" in filesystems names is bad
Sometimes MS-Windows users try to use filesystem names which include
the "#" character.  That's generally unwise, since it begins Tcl
comments.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-10 16:42:37 -08:00
Øyvind Harboe
65cc81ddb6 arm11: fix another infinite loop bug
reset init would get stuck in an infinite loop when
e.g. khz was too high. Added timeout. This is a copy
of paste of a number of such bugfixes in the arm11
code.

Arm11 code reviewed for further such infinite loop bugs
and I couldn't find any more. Xing fingers it's the last
one...

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-02-10 22:54:06 +01:00
David Brownell
84ac6bb0d9 User's Guide: clarify jtag_rclk advice
Not all cores and boards support adaptive clocking, so qualify
all advice to use it to depend on core and board support.

It's primarily ARM cores which support this; and many of the
newer ones (like Cortex-M series) don't.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-10 11:27:48 -08:00
Øyvind Harboe
c646b76797 target: add todo in target_write_memory() about alignment
target_write_buffer() does not align "buffer" in host
memory passed to target_write_memory().

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-02-09 21:57:23 +01:00
Spencer Oliver
f899c2aa97 str730.cfg: fix incorrect mem regions
- update str73x mem regions to correct values.

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-02-09 14:49:47 +00:00
David Brownell
885a2f5b96 Re-title Developer's Guide
The Doxygen output was previously titled "OpenOCD Reference Manual",
which was quite misleading ... the User's Guide is the reference
manual which folk should consult about how to use the software.

Just rename it to match how it's been discussed previously, and to
bring out its intended audience:  developers of this software.  As a
rule, Doxygen is only for folk who work with the code it documents.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-06 19:19:25 -08:00
David Brownell
6f262b69f4 ADIv5: doxygen
Provide doxygen for many of the public ADIv5 interfaces (i.e. the ones
called from Cortex core support code).

Add FIXMEs (and a TODO) to help resolve implementation issues which
became more apparent when trying to document this code:

 - Error-prone context-sensitivity (queued/nonqueued) in many procedures.

 - Procedures that lie by ignoring errors and wrongly claiming success.

Also, there was no point in a return from dap_ap_select(); it can't fail,
and no caller checks its return status.  Clean that up, make it void.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-06 19:16:21 -08:00
Øyvind Harboe
41d0901115 zy1000: complete zy1000_uart to jim command switch
Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-02-05 14:38:26 +01:00
David Brownell
ff5deeeeaa ARMv7-M: make DAP commands verify target is an ARMv7-M
Init the ARMv7-M magic number.  Define predicate verifying it.
Use it to resolve a lurking bug/FIXME:  make sure the ARMv7-M
specific DAP ops reject non-ARMv7-M targets.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-04 14:39:51 -08:00
David Brownell
3ea9e62189 Documentation: mention bug database
Have the User's Guide and BUG handling notes both reference
the fact that we now have a bug database at SourceForge.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-04 11:10:15 -08:00
David Brownell
e380930478 JLink: reference protocol documentation
Segger publishes some documentation on this protocol;
reference it, so future maintainers can know it exists.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-04 10:50:24 -08:00
Spencer Oliver
709f08f17a CMD: duplicate cmd error msg
When registering cmds we report duplicate attempts to register a cmd
as a LOG_ERROR.
Some situations need this, such as when registering dual flash banks.
http://www.mail-archive.com/openocd-development@lists.berlios.de/msg11152.html

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-02-04 10:33:33 +00:00
Ethan Eade
8b049fdba5 scripts: Phytec/LPC2350 config scripts
Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-02-04 10:25:44 +01:00
Spencer Oliver
95ed9c4393 JTAG: fix bug when no interface connected
- fix coredump when OpenOCD is started without a jtag interface connected.

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-02-03 13:09:24 +00:00
Harald Kipp
18969466c9 AT91R40008/Ethernut 3 configuration
Moved board specific settings from target/at91r40008.cfg to a new
file board/ethernut3.cfg.

Set correct CPUTAPID.  Reset delay increased, see MIC2775 data sheet.
Increased work area size from 16k to 128k.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-02 11:09:53 -08:00
David Brownell
5750e899e0 NOR: User's Guide updates
Remove long-obsolete text about "erase_check" affecting "flash info" output.
Move parts of that text to "protect_check", where it's still relevant; and
update the "flash info" description to mention the issue.

(This is still awkward.  It might be best to make "protect_check" mirror
"erase_check" by dumping what it finds, so "flash info" doesn't dump any
potentially-stale cache info.)

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-02 10:53:13 -08:00
Edgar Grimberg
cc440ca1d4 tcl/str7x: Reset init unlocks the flash
For STR7x flash, the device cannot be queried for the protect status.
The solution is to remove the protection on reset init. The driver
also initialises the sector protect field to unprotected.

[dbrownell@users.sourceforge.net: line length shrinkage]

Signed-off-by: Edgar Grimberg <edgar.grimberg@zylin.com>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-02 09:30:33 -08:00
Edgar Grimberg
503f6139c7 flash/str7x: After reset init the flash is unlocked
The default state of the STR7 flash after a reset init is unlocked.
The information in the flash driver now reflects this.

The information about the lock status cannot be read from the
flash chip, so the user is informed that flash info might not
contain accurate information.

[dbrownell@users.sourceforge.net: line length shrinkage]

Signed-off-by: Edgar Grimberg <edgar.grimberg@zylin.com>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-02-02 09:30:33 -08:00
Nicolas Pitre
3d2d5dcc9c ARM semihosting: fix EOF handling with SYS_READ
The semihosting interface has a strange convention for read/write where
the unused amount of buffer must be returned.  We failed to return the
total buffer size when the local read() call returned 0.

Signed-off-by: Nicolas Pitre <nico@marvell.com>
2010-02-02 00:05:42 -05:00
Edgar Grimberg
bef37ceba2 Test cases ran on v0.4.0-rc1
Test cases ran on v0.4.0-rc1 for a number of targets:
AT91FR40162
LPC2148
SAM7
STR710
STR912

The goal of the testing session was to prove basic functionality of OpenOCD for different targets.

Signed-off-by: Edgar Grimberg <edgar.grimberg@zylin.com>
2010-02-01 15:44:06 +01:00
Øyvind Harboe
91e3268737 gdb: restore behavior from 0.3.1 for srst_asserted and power_restore
srst_asserted and power_restore can now be overriden to do
nothing. By default they will "reset init" the targets and
halt gdb.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-02-01 13:45:09 +01:00
David Brownell
82f2492138 ADIv5: more messaging cleanup, docs
When the TAR cache was explicitly invalidated, don't bother
printing it; the actual hardware status is more informative.

Provide some doxygen for the MEM-AP setup routine.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-31 14:16:53 -08:00
Øyvind Harboe
02731cf78b build: fix problems with "struct stat" not being defined under eCos
Include <sys/stat.h> according to
http://www.opengroup.org/onlinepubs/000095399/functions/stat.html

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-31 15:48:14 +01:00
Øyvind Harboe
f68dff6690 telnet: fix strage blank spaces at beginning of telnet lines
Sometimes we saw two strange blank spaces at the beginning
of the telnet lines.

progress
  ogress
>

This patch fixes this problem:

progress
progress
>

The code changes are *reasonably* clean, but perhaps it could be
made a bit more elegant, but I didn't want to change things after
I finished diagnosis/testing & submitting the patch.

The problem was that logging can send the text and the newline
separately in two different requests and the telnet code would
incorrectly remove the prompt from the end of a line.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-31 15:06:02 +01:00
David Brownell
e11ce3e6b0 Subject: ADIv5: fix more diagnostics
If the MEM-AP cache is invalid, don't display it; just report that
invalidity as an error.  (This bug has been observed with "mdw 0 32"
after just a "reset halt".  Some code is being wrongly bypassed...)

If it's valid, display that cache at DEBUG level, not ERROR.  Also,
don't assume it's an AHB-AP; it could be another flavor of MEM-AP.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-31 00:26:21 -08:00
David Brownell
695666d294 ADIv5 error checking for Tcl commands
Reject invalid AP numbers (256+) as Tcl operation parameters.
Shrink one of the overlong lines.

Add my copyright to the ADIv5 code (multiple contributions).

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-30 22:46:00 -08:00
David Brownell
46b6d5bfe6 ARM ADIv5: fix diagnostics for block writes
They were reporting "read" errors, not "write" errors.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-30 18:08:19 -08:00
David Brownell
3d3128a8f5 ADIv5: cleanup, rename swjdp_transaction_endcheck()
Make messages reference "DAP" if they're actually transport-agnostic, or
"JTAG-DP" when they're JTAG-specific.  Saying SWJ-DP is often wrong (on
most Cortex-A8 chips) and is confusing even if correct (since we don't
yet support SWD).

Rename a JTAG-specific routine to jtagdp_transaction_endcheck() to highlight
that it's JTAG-specific, and that identify DAP clients undesirably depending
on JTAG.  (They will all need to change for SWD support.)

Shrink a few overlong lines of code.  Copy a comment from code removed
in a previous patch (for the ARMv7-M "dap baseaddr" command).

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-29 14:31:19 -08:00
David Brownell
2248c387f2 ARMv7-M: use command handler for "dap baseaddr".
Make the ARMv7-M DAP code reuse the command handler for "dap baseaddr".
For some reason, this DAP command wasn't converted earlier.

This is a code shrink and simplification; it also removes a needless
transport dependency on JTAG.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-29 14:16:14 -08:00
David Brownell
303b493c22 NOR: cleanup driver decls
Fix goofy struct indents.  Function names *are* their addresses.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-29 13:52:08 -08:00
Alex Austin
cd3017cffa Clang buildfixes
Building with clang took a few very small changes. The change to
helper/log.h is because clang doesn't like an expression where the
result is unused. In helper/system.h, I just defined true and false
since clang doesn't have them builtin.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-29 00:02:12 -08:00
David Brownell
804c0b2ad3 doc clarifications for server flags
The "-f" is a shortcut for "-c" ... and providing any "-c" options
means the "openocd.cfg" file isn't implicitly used.  Both the User's
Guide and the manual page were weak on these points, which has led
to some confusion.

Also update the manual page to include highlights of the search path
mechanism, including the facts that it exists and that "-s" adds to it.
Stop saying only the current directory is involved; the OpenOCD
script library is quite significant.

(Missing: complete manpage coverage of the search path, including a
FILES section listing all components and saying where the script
library is found.)

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-28 14:03:29 -08:00
David Brownell
5dcf7898f6 ARM: reference DPM defn from v6/v7 arch spec
The term "DPM" is probably not well known ("Device Power Management"?),
so identify its source in the current ARM architecture specification.
It's relevant to ARMv6, ARMv7-A, and ARMv7-R ... but not "M" profiles.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-28 13:58:20 -08:00
Spencer Oliver
75cfda4cd1 ARM semihosting: win32 and cygwin fixes
Cygwin would fail to reopen a previously written file if the mode is
not given.

Simplified converting the open flags and made sure the win32 O_BINARY
bit is set.

Added define for systems that do not support O_BINARY.

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-28 21:05:09 +00:00
Spencer Oliver
465a06dfdc ARM semihosting: fix writing to stdout
SYS_FLEN would be called before a write on a descriptor to check its size.
Currently lseek would fail with -1 when given the stdout/stderr descriptor.
Changing to use fstat seems to be the standard way of handling this.

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-28 20:21:31 +00:00
David Brownell
3172be80a3 Cortex-M3: report lockup, and recover
ARMv7-M defines a "lockup" state that's entered in certain double
fault sequences which can't be recovered from without external help.
OpenOCD has previously ignored this.

Issue a diagnostic saying the chip has locked up, and force exit
from this state by halting the core.  It's not clear this is the
best way to handle lockup; but there should now be less confusion.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-27 13:47:48 -08:00
David Brownell
d44f1aaeff ARM ADIv5: messaging tweaks
Add space missing after the invalid ACK value.  On init, say
which AP is being used, and don't assume it's an AHP-AP.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-27 13:40:05 -08:00
David Brownell
2b5c444a32 Cortex-A8: debug messaging tweaks
Make that "TODO" message say what needs to be done.
Say what part of examining failed.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-27 13:24:21 -08:00
David Brownell
30365886da various: don't mention wiki
The openfacts.berlios wiki isn't particularly current, and isn't
publicly editable.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-26 18:13:10 -08:00
David Brownell
9e52957efc cygwin buildfix
isspace() parameter must be an integer, else a 'char' gets
used as an array index (sigh).

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-26 17:54:49 -08:00
simon qian
33fc60befc SVF: all content between parentheses is one parameter
More SVF fixes:

 * Treat all content between parentheses as part of the same
   parameter; don't (wrongly) treat whitespace as a delimiter.

 * Use isspace() to catch that whitespace; it's not all single
   spaces, newlines etc are also valid.

 * When parsing bitstrings, strip leading whitespace too.

So for example, these are equivalent and should (now) be OK:

  "TDI( 1234 )"
  "TDI( 1 2 3 4 )"
  "TDI(00 12 34 )"
  "TDI(
  	00 12
	34)"

[dbrownell@users.sourceforge.net: comment updates; trivial cleanup]

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-25 13:06:46 -08:00
Edgar Grimberg
1dad2ee602 core arm11: Silence logs at level 3 if there is no activity
If the target and openocd are idling, the log should normally
be silent at level 3.  (Given no verbose logging options.)

Signed-off-by: Edgar Grimberg <edgar.grimberg@zylin.com>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-25 12:19:52 -08:00
simon qian
9ff16575d2 SVF: insert space before '(' and after ')'
See http://forum.sparkfun.com/viewtopic.php?p=90983#90983 for discussion;
basically, the SVF parser wrongly expects "TDI (123)" but the space is
optional and it should accept "TDI(123)" too.

In the same way, "TDI(123)TDO(456)" should work too.

Rather than update the command parsing, this just makes sure the expected
spaces are present.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-23 14:24:10 -08:00
David Brownell
718ee762e7 EmbeddedICE - fix Feroceon/Dragonite message
The breakpoint/watchpoint message was wrong for Feroceon and
Dragonite, which have only one working watchpoint unit.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-22 22:54:39 -08:00
David Brownell
82c3c47825 NEWS updates
Summarize most ARM11 and Cortex-A8 updates as "acting much more
like other ARMs", and mention code sharing.

Clarify a few other points, including support for "reset-assert"
on all ARMs except Cortex-M (which doesn't exactly need it).

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-22 22:49:42 -08:00
David Brownell
b7fa16eeac ARM11: fix breakpoints with GDB
This fixes a bug whereby GDB's breakpoints weren't activated.
The root cause is a confused interface to resume().  Fix by
almost ignoring the "handle breakpoints" parameter; it only
seems related to the case of skipping breakpoint-at-PC.

Update a few coments to clarify what's happening.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-22 22:37:15 -08:00
David Brownell
4960c9018f Various doc/comment updates
Doxygen: don't be needlessly verbose; alphabetically sort members
TODO: add random bits; clarify which manuals are referenced
ARM disassembler: mention a few opcodes that still aren't handled

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-21 16:45:00 -08:00
David Brownell
08b0be94b5 User's Guide secton on target hardware setup
Highlight the needs to properly jumper development boards; to
make the OpenOCD configuration match the jumpering; and to have
a usable "reset-init" method when debugging early boot code.

Specific mention of the "ATX Mode" that seems useful on
many i.MX boards, forcing NAND boot.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-21 16:15:41 -08:00
David Brownell
f06148612b ADIv5 header cleanup (+ #defines)
Update the comments about DP registers and some of the bitfields.
Remove inappropriate (and unused) DP_ZERO declaration.

Add some (currently unused) #defines needed for SWD protocol support,
based on previous patches from Andreas Fritiofson and Simon Qian.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-21 13:39:22 -08:00
Øyvind Harboe
98f7c2127b target: print reason why GDB halts
If GDB halts unexpectedly, print reason: srst assert or power
out detected.

If polling fails, then things are a bit trickier. We do not
want to spam telnet or the log with polling failed messages.
Leave that case be w/a comment in a code for now.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-21 16:20:58 +01:00
Edgar Grimberg
dfba7fa949 interface: Changed parport address to LPT1
Changed the parport address to LPT1, since it's the most obvious default value.

Signed-off-by: Edgar Grimberg <edgar.grimberg@zylin.com>
2010-01-21 15:58:59 +01:00
Edgar Grimberg
bc088b302b target: Fixed format problem for mdh
Fixed format problem for mdh. It needs to display 4 chars.

Signed-off-by: Edgar Grimberg <edgar.grimberg@zylin.com>
2010-01-21 15:58:59 +01:00
Øyvind Harboe
1350b6aad0 gdb_server: handle stepi/continue packet while target is running with more grace
Rather than issuing a halt and then stepi/resume, just
wait for target to halt.

Issue a sterner warning via gdb console that any gdb
register changes will be ignored in this case.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-21 15:57:30 +01:00
Øyvind Harboe
60cb5bdd30 ecos: add missing PRId8 definition
Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-21 08:11:39 +01:00
Spencer Oliver
dbecb13b24 BUILD: remove cygwin gcc 3.4.4 build warnings
Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-20 23:11:25 +00:00
David Brownell
2a0c9b08d7 Cortex-M3 vector_catch testing support
The "cm3-ftest.cfg" can be used to verify that OpenOCD handles
certain faults correctly:

 - Test #1: it ignores faults that it wasn't told to catch
 - Test #2: if vector_catch is told to catch, it catches

The "fault.c" generates ASM code to trigger faults, while the
config script loads and runs pre-compiled code.

This covers most, but not all, of the vector_catch options.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-20 11:07:42 -08:00
David Brownell
22d25e6921 board configs -- unique names for flash chips
Don't give the same names to both flash chips on two OMAP boards.

For OSK, enable DCC downloads (removing a warning).

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-20 10:46:53 -08:00
David Brownell
6f2b88448f gdb_server: correctly report flash sector sizes
Report each region of same-size sectors separately, instead of
incorrectly reporting that every sector has the same size.

This is a longstanding bug on NOR flash chips with non-uniform
sector sizes.  It was largely hidden by other bugs in flash
handling.  When some of those were recently fixed, this one was
exposed as a regression on str710.

[oyvind.harboe@zylin.com: update the loop to behave on str7 ]

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-20 10:43:32 -08:00
Michael Grzeschik
d036f17001 tcl/target/at91sam3u4e.cfg: changed case in dependent file
openocd does not start with the target configfile due to the case in the
dependent config file.

Signed-off-by: Michael Grzeschik <m.grzeschik@pengutronix.de>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-20 10:32:53 -08:00
Øyvind Harboe
87cb29dcfe testing: fix str710 test case now builds
Make the test case easily adjustable in size. str710
has very peculiar flash sector layout, nice for testing,
but a larget test_rom.elf is required.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-20 15:12:31 +01:00
Øyvind Harboe
ff976cdb29 arm7/9: add nags upon reset about options to improve performance
arm7_9 fast_memory_access and working area nags added.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-20 14:51:17 +01:00
Spencer Oliver
0c3a4b4d81 ARMV7M: handle bkpt instruction on resume/step
Skip over a bkpt instruction if found on resume/step.
Only software breakpoints known to OpenOCD are currently handled.

So this handles the special case of either a user added bkpt
or library added, eg. semi-hosting support.

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-20 09:07:55 +00:00
David Brownell
20d1ef70e8 User's guide: mention lpc2000 checksum issue
Folk almost certainly want to have OpenOCD compute the checksum
when they modify the vector table.  However, that almost guarantees
that "verify_image" will fail.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-20 00:04:17 -08:00
David Brownell
44aaba3d08 gdb_server -- subroutinize memory map logic
Put the memory map logic into its own subroutine.
This will make it a bit easier to package bugfixes,
and simplifies the query packet handling.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-19 23:32:54 -08:00
David Brownell
bf1e9a83c8 gdb_server -- symbol cleanup
Make most methods static; net minor object code shrink.
Likewise various data symbols; no net change.
Shrink some overlong lines.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-19 23:30:36 -08:00
Andreas Fritiofson
4f310aa0c9 update win32 script search path
The default script search path on Windows is out of date with
the current layout (from installation and documentation), which
makes the standard script library not be found after a normal

	./configure && make && make install

under msys/MinGW. The same should hold true for cygwin native builds
(not verified).

Update search path to ../share/openocd/scripts not ../lib/openocd,
relative to the openocd executable.

Signed-off-by: Andreas Fritiofson <andreas.fritiofson@gmail.com>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-19 15:02:15 -08:00
David Brownell
fb4239866c NOR: fix diagnostic
The "NOR: last_addr also needs correction when checking alignment"
patch omitted a necessary update to the key diagnostic; fix.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-19 13:56:33 -08:00
Øyvind Harboe
924bf27596 zy1000: flush jtag buffer before changing speed
It is conceivable that there could be commands in the
queue when a speed change request comes in. Flush the
hw queue before changing speed. Not observed, found by
inspection.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-19 10:58:48 +01:00
Øyvind Harboe
c795b0d8f1 zy1000: print out PCB revision upon boot
Simplify debugging a bit.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-19 10:58:48 +01:00
Øyvind Harboe
cdcb9b0885 flash: add error messages upon incorrect arguments to flash iteration
According to OpenOCD error handling rules the error is
logged at where it occurs(same site where an exception
would have been thrown).

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-19 10:58:48 +01:00
David Brownell
5ab34b28ce vsllink -- add comment
Previous patch deserved *inline* comment, not just
in git revision history.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-18 13:18:33 -08:00
Øyvind Harboe
56d2c86500 commands: allow scan_chain command to be executed during config
Adding taps and then dumping them is quite reasonable thing
to do in a config script.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-18 21:42:34 +01:00
simon qian
0b641dac71 read target voltage first in vsllink
The very first command after init command should be "read target voltage".

This is a tweak for the Old Versaloon firmware.  Without this, in most
most cases, it works.   Under Ubuntu9.04, there is a chance that the USB
will fail.  The problem disappears if I read target voltage first.

For the lastest Versaloon firmware, it's OK.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-17 23:37:15 -08:00
richard vegh
daa1ff3535 NAND: lpc3180 crashes on LPC3250
The LPC3180 NAND driver was crashing on some large page chips.
Fix:

 - Crash and related functionality (don't memset too much OOB data)
 - Some debug messages
 - Command handling now works

[dbrownell@users.sourceforge.net: whitespace/linelength/message cleanup]

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-16 12:27:45 -08:00
David Brownell
183765707f ADIv5 improved diagnostic
Don't just complain about an invalid ACK; say what the
value was, to help troubleshooting.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-15 13:02:45 -08:00
David Brownell
6c4a643d63 ARM DPM: disable some nyet-ready breakpoint code
Until we manage breakpoints at runtime (patches not ready for 0.4)
the only way this code should touch them is to disable them at server
startup (a previous debug session may have left them active).

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-15 12:53:26 -08:00
David Brownell
187ccb60ee NEWS: include s3c64xx NAND driver
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-15 09:36:01 -08:00
David Brownell
0f7cea2847 jtag.h whitespace/comment cleanup
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-14 14:38:24 -08:00
David Brownell
8e1b5c3138 ARM ADIv5: add comments
Add doxygen and other comments for what's more or less the lowest
level JDAG-DP primitive, to access JTAG_DP_{A,D}PACC registers.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-14 12:58:39 -08:00
David Brownell
1d140c4dcd ARM7/ARM9: improved reset support
Teach most remaining ARM cores how to use the "reset-assert" event.

Same model as elsewhere:  iff a handler is provided for that event,
use that instead of trying to assert SRST (which may be unavailable,
or inappropriate since it resets too much).  Else no change.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-14 12:46:33 -08:00
Peter Korsgaard
000a1cfd01 nand flash support for s3c64xx
Identical to the existing 2412/2443 support except for the base address
and NFCONF value (bit 2 is reserved and should be written as 1 ref UM).

Tested on a s3c6410 board, but controller is identical in 6400/6410
except for 8bit MLC ECC support in 6410 which isn't supported by the
driver.

Signed-off-by: Peter Korsgaard <jacmet@sunsite.dk>
Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-14 21:07:46 +01:00
Laurentiu Cocanu
24653c950a str9x.c: remove optimization when erasing the whole bank
Using the erase bank command will cause a time out error. Replacing
this with the erase sector bank will provide a slower but safer and
stable method to erase the flash.

Signed-off-by: Laurentiu Cocanu <laurentiu.cocanu@zylin.com>
Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-14 15:07:24 +01:00
David Brownell
e1679a29f0 ARM7/9 minor cleanups
Shrink some overlong lines.  Add my 2009 copyright.
Move a declaration to the beginning of its block.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-14 03:16:07 -08:00
Spencer Oliver
e2d3266ff1 GDB: change gdb_breakpoint_override to COMMAND_ANY
- enable gdb_breakpoint_override to be used within config script.

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-14 09:35:33 +00:00
David Brownell
b60dd35e33 User's Guide updates
Capture various bits of useful information that have come up on the
list but haven't yet gotten into the documentation:

 - Watchdog timers firing during JTAG debug need attention;

 - Some chips have special registers to help JTAG debug;

 - Cortex-M3 stepping example with IRQs and maskisr;

 - Clarifications re adaptive clocking:  not all ARMs do it, and
   explain it a bit better.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-13 23:33:53 -08:00
David Brownell
73566405b6 NOR: add optional "flash erase_address" sector padding
Add a NOR flash mechanism where erase_address ranges can be padded
out to sector boundaries, triggering a diagnostic:

  > flash erase_address 0x0001f980 16
  address range 0x0001f980 .. 0x0001f98f is not sector-aligned
  Command handler execution failed
  in procedure 'flash' called at file "command.c", line 647
  called at file "command.c", line 361
  >

  > flash erase_address pad 0x0001f980 16
  Adding extra erase range, 0x0001f800 to 0x0001f97f
  Adding extra erase range, 0x0001f990 to 0x0001fbff
  erased address 0x0001f980 (length 16) in 0.095975s (0.163 kb/s)
  >

This addresses what would otherwise be something of a functional
regression.  An earlier version of the interface had a dangerous
problem:  it would silently erase data outside the range it was
told to erase.  Fixing that bug turned up some folk who relied on
that unsafe behavior.  (The classic problem with interface bugs!)
Now they can get that behavior again.  If they really need it,
just specify "pad".

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-13 23:33:25 -08:00
David Brownell
d91941d5a0 Cortex-M3: improved core exception handling
This updates three aspects of debugger/exception interactions:

 - Save the user's "vector_catch" setting, and restore it after reset.
   Previously, it was obliterated (rather annoyingly) each time.

 - Don't catch BusFault and HardFault exceptions unless the user says
   to do so.  Target firmware may need to handle them.

 - Don't modify SHCSR to prevent escalating BusFault to HardFault.
   Target firmware may expect to handle it as a HardFault.

Those simplifications fix several bugs.  In one annoying case, OpenOCD
would cause the target to lock up on ome faults which triggered after
the debugger disconnected.

NOTE:  a known remaining issue is that OpenOCD can still leave DEMCR
set after an otherwise-clean OpenOCD shutdown.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-13 03:17:23 -08:00
Øyvind Harboe
b8e930e3bf arm7/9: enable check that DCC downloads have been enabled
Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-13 12:00:02 +01:00
Øyvind Harboe
ee519ab356 arm7/9: add fn to check if dcc downloads have been enabled
DCC downloads should be enabled for any self repecting
openocd config file for arm7/9. Print out note about
it otherwise.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-13 12:00:02 +01:00
Øyvind Harboe
dc793455e9 target: add check_reset hook
Allow targets to run checks post reset. Used to check
that e.g. DCC downloads have been enabled.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-13 12:00:02 +01:00
Øyvind Harboe
3e33393078 gdbserver: fix typo that broke read/write watchpoint
It looks like a bugfix from normal breakpoints was not
copied over.

Do not use clever mathematics and assumptions to convert from
GDB enum for break/watchpoints to OpenOCD enum.

Drop connection upon unknown breakpoint type, this code path
was not really considered by the previous code I think.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-13 12:00:02 +01:00
Øyvind Harboe
6c75f5249c debug: make logging of commands terser
one line / command instead of one line per argument.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-13 08:32:15 +01:00
David Brownell
b4a4d5c731 ARM: bugfix for "movt" disassembly
Use the correct bitfield to specify the register whose
top halfword gets replaced.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-12 12:40:39 -08:00
Vladimir Zapolskiy
1de107a5a2 Added Openmoko USB JTAG interface config file.
Added interface config file for JTAG/RS232 debug board originally
integrated to Neo 1973 and Neo FreeRunner phones.
Adapter was tested with i.MX31, S3C2410 and AT91SAM9260 processors.

Signed-off-by: Vladimir Zapolskiy <vzapolskiy@gmail.com>
2010-01-11 15:58:13 +01:00
Øyvind Harboe
e5349bfb49 target: return JIM_OK instead of ERROR_OK
No change in actual binary as JIM_OK == ERROR_OK,
but JIM_OK is correct here.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-11 15:01:02 +01:00
Øyvind Harboe
fb71a0a0dd reset: better error messages
Use correct tcl syntax to throw exception.

the syntax is "return -code error" not "return -error"

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-11 12:58:06 +01:00
Øyvind Harboe
6d8604de37 commands: make error messages a bit more terse
we don't need to know the build path of command.c when
reading normal user level error messages.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-11 12:58:06 +01:00
Øyvind Harboe
c74ca40e09 zy1000: reset bugfix
flush JTAG FIFO before reset. Fixes RCLK problems observed
w/lpc2148, but really fixes a wider range of problems.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-11 10:25:13 +01:00
David Brownell
8c730aaee2 Doxygen file comments
Add file comments to a few files.  Make the GDB server use
more conventional (pointer-free) hex digit conversion.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-11 00:16:57 -08:00
Øyvind Harboe
88907cc7f9 shutdown: more graceful shutdown
Shutdown is not an error condition, do not return error
from main.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-11 08:13:17 +01:00
Spencer Oliver
d746dee833 build: doxygen build
- Fix for building doxygen out of tree

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-10 21:00:48 +00:00
David Brownell
c8267930c7 FreeBSD build fixes
Based on notes from Tomek Cedro <tomek.cedro@gmail.com> and
Steve Franks <bahamasfranks@gmail.com>.

In the User's Guide, sort the list of operating systems reported
through Tcl with $ocd_HOSTOS ... and include FreeBSD.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-10 10:06:58 -08:00
David Brownell
5e221fa3a7 Presto: doxygen fix
Newline needed.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-09 22:24:43 -08:00
David Brownell
ab4307e693 jtag/tcl help/usage fixups
The usual: expand several helptexts to be more correct and to use
full sentences; make the usage messages use the same EBNF as the
User's Guide; use function names for their addresses.

Also add a comment about that odd jtag_command_handlers_to_move[] thing.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-09 22:15:57 -08:00
David Brownell
5cb1dcfad3 ZY1000 help/usage fixups
The usual:  same EBNF as in the User's Guide, full sentence helptext,
function names *are* their addresses.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-09 22:14:08 -08:00
David Brownell
0811f6b192 jtag: presto, parport help/usage updates
Presto: add doxygen file comment.

Parport: note a couple gaps in layout config.

Both: use the uniform EBNF for usage, bugfix helptexts, use function
name as its address not "&name".

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-09 22:09:08 -08:00
David Brownell
ad5fd39063 jtag/gw16012 usage/help updates
Use standard BNF.  Improve/correct helptext for its "parport_port"
command.  Function address is just its name.
2010-01-09 22:05:55 -08:00
David Brownell
ff647e6bb4 parport (mostly) doc fixes
The "parport_port" commands generally don't *require* a port_number;
they're of the "apply any parameter, then print result" variety.  Update
the User's Guide accordingly.

Some of those commands are intended to be write-once: parport_port,
and parport_cable.  Say so.

Use proper EBNF for the parport_write_on_exit parameter.

Parport address 0xc8b8 is evidently mutant.  Say so in the "parport.cfg"
file, to avoid breaking anyone with that mutant config.  But update the
User's Guide to include a sane example for the LP2 port.

Finally document the "presto_serial" command.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-09 21:56:11 -08:00
David Brownell
1dd5277ba3 src/helper: usage/help updates
Make "usage" messages use the same EBNF as the User's Guide;
no angle brackets.  Improve and correct various helptexts.

Don't use "&function"; a function's name is its address.
Fix some whitespace glitches, shrink a few overlong lines.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-09 13:32:08 -08:00
David Brownell
1c5c57ec8e src/flash/nor: usage/help/doc updates
Make "usage" messages use the same EBNF as the User's Guide;
no angle brackets.  Improve and correct various helptexts.

Don't use "&function"; a function's name is its address.
Remove a couple instances of pointless whitespace; shrink a
few overlong lines; fix some bad indents.

Add TODO list entry re full support for NAND/NOR bank names.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-09 10:25:03 -08:00
Spencer Oliver
70738bd75d MIPS: update arch_info access to match other targets
- add target_to_mips32 and target_to_m4k to match test of codebase.
 - mips32_arch_state now shows if processer is running mips16e isa.

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-09 13:37:02 +00:00
David Brownell
fc9a2d0e6f src/server: usage/help/doc updates
Make "usage" messages use the same EBNF as the User's Guide;
no angle brackets.  Improve and correct various helptexts.

Specifically for the port commands, clarify that the number
is optional, and omitting it causes the current number to be
displayed.

Don't use "&function"; a function's name is its address.
Remove a couple instances of pointless whitespace; shrink a
few overlong lines.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-09 00:55:41 -08:00
Masaki Muranaka
aafd3877e6 buildfix on MacOS
Recent Apple gcc versions use __APPLE__ instead of __DARWIN__; accept
that too.

Also use #warning, not #warn; neither is standard, but most CPP versions
require it to be spelled out.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-09 00:10:18 -08:00
David Brownell
973cd9a299 PLD: usage/help updates
Make "usage" messages use the same EBNF as the User's Guide;
no angle brackets.  Improve and correct various helptexts.

Don't use "&function"; a function's name is its address.
Remove a couple instances of pointless whitespace, shrink
a few overlong lines.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-08 23:23:55 -08:00
David Brownell
2a76c1bcf9 NAND: help/usage/doc updates
Usage messages should use the same EBNF as the User's Guide;
no angle brackets.  Be more complete too ... some params were
missing.  Improve and correct various helptexts.

Make user's guide refer to the NAND "driver" name, not the
controller name; that's a bit more precise.

Don't use "&function"; its name is its address.  Line up struct
initializers properly.  Remove some blank lines.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-08 23:18:46 -08:00
David Brownell
ae71005929 Doc/examples: clarify usage messages
Update/bugfix the "hello" example; emphasize using EBNF syntax,
matching the User's Guide.  Correct the Texinfo style guide to
say EBNF, not BNF.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-08 23:13:39 -08:00
David Brownell
b800eb0336 *SVF: help/usage updates
Usage messages should use the same EBNF as the User's Guide;
no angle brackets.  Be more complete too ... some params were
missing.

Don't use "&function"; its name is its address.

Unrelated: fix typo in one "target.c" usage message.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-08 20:16:05 -08:00
David Brownell
1a2c258ed4 MFLASH: help/usage updates
Make "usage" messages use the same EBNF as the User's Guide;
no angle brackets.  Improve and correct various helptexts.

Don't use "&function"; a function's name is its address.
Remove a couple instances of pointless whitespace.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-08 20:12:18 -08:00
David Brownell
c1cb20971e Coexist with quilt: rename PATCHES --> PATCHES.txt
The issues is on Win32, which ignores case in filesystem
and thus doesn't tolerate the quilt "patches" directory.

Rename, and add "patches" to .gitignore so that developers
can choose to use quilt for local patch management.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-08 17:20:47 -08:00
David Brownell
296a011db5 NOR: add FIXMEs for writing ones
It can invalidate ECC codes, and in general is not guaranteed
to work.  (However on some chips it _appears_ to behave.)  Just
don't do it; don't write in those cases.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-08 16:47:58 -08:00
David Brownell
12c143d594 misc ARM help/usage updates
Usage syntax messages have the same EBNF as the User's Guide;
there should be no angle brackets in either place.

Uupdate some helptext to be more accurate.

Don't use "&function"; functions are like arrays, their address
is their name.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-07 16:41:42 -08:00
David Brownell
82c0fb5277 ARM966: help/usage updates
Usage syntax messages have the same EBNF as the User's Guide;
there should be no angle brackets in either place.

Fix the User's Guide to say where the magic CP15 bits are defined;
and add comments in case someone provides mcr/mrc methods.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-07 16:39:32 -08:00
David Brownell
e7965cd3eb Xscale: User's Guide updates
Fix some EBNF goofs ... these commands have *optional* params, etc

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-07 16:34:44 -08:00
David Brownell
a42bea654c ARM720: help/usage updates
Deprecate the "pass an instruction opcode" flavor of cp15
access in favor of the "arm mcr ..." and "arm mrc ..."
commands, which offer fewer ways to break things.

Use the same EBNF syntax in the code as for the user's guide.

Update User's Guide to say where to find those magic values
(which table in the ARM920 TRM).

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-07 16:30:09 -08:00
David Brownell
e0b6e5deef ARM720: help/usage updates
Deprecate the "pass an instruction opcode" flavor of cp15 access
in favor of the "arm mcr ..." and "arm mrc ..." commands, which
offer fewer ways to break things.

Use the same EBNF syntax in the code as for the user's guide.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-07 16:25:03 -08:00
David Brownell
199abf49ea ARM11: help/usage updates
Usage syntax messages have the same EBNF as the User's Guide;
there should be no angle brackets in either place.

Uupdate some helptext to be more accurate.

Fix the User's Guide in a few places to be more consistent (mostly
to use brackets not parentheses) and to recognize that parameter may
be entirely optional (in which case the command just displays output,
and changes nothing).  Also reference NXP, not Philips, for LPC chips.

Don't use "&function"; functions are like arrays, their address
is their name.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-07 16:21:24 -08:00
David Brownell
48d51e1719 ARM7/ARM9: help/usage updates
Provide helptext which was sometimes missing; update some of it
to be more accurate.

Usage syntax messages have the same EBNF as the User's Guide;
there should be no angle brackets in either place.

Fix the User's Guide in a few places to be more consistent (mostly
to use brackets not parentheses) and to recognize that parameter may
be entirely optional (in which case the command just displays output,
and changes nothing).  Also reference NXP, not Philips, for LPC chips.

Don't use "&function"; functions are like arrays, their address
is their name.  Shrink some overlong lines.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-07 16:20:14 -08:00
David Brownell
17921f51ab ARMv7: help/usage updates
Provide helptext which was sometimes missing; update some of it
to be more accurate.

Usage syntax messages have the same EBNF as the User's Guide;
there should be no angle brackets in either place.

Don't use "&function"; functions are like arrays, their address
is their name.  Shrink some overlong lines, remove some empties.

Add a couple comments about things that should change:  those
extra TCK cycles for MEM-AP reads are in the wrong place (that
might explain some problems we've seen); the DAP command tables
should be shared, not copied.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-07 16:18:01 -08:00
David Brownell
e19fe9ad09 ARM ETM/ETB/trace: help/usage updates
Provide helptext which was sometimes missing; update some of it
to be more accurate.

Usage syntax messages have the same EBNF as the User's Guide;
no angle brackets in either place.

Don't use "&function"; functions are like arrays, their address
is their name.  Shrink some overlong lines, remove some empties.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-07 15:22:41 -08:00
David Brownell
dd8f679aa2 target misc: help/usage updates
Provide helptext which was sometimes missing; update some of it
to be more accurate.

Usage syntax messages have the same EBNF as the User's Guide.

Don't use "&function"; functions are like arrays, their address
is their name.  Shrink some overlong lines; remove some empties.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-07 15:05:26 -08:00
David Brownell
7c3aee96b2 XScale: help/usage updates
Provide helptext which was sometimes missing; update some of it
to be more accurate (mostly they display something w/no args).

Usage syntax messages have the same EBNF as the User's Guide.
In some cases, *exactly* what the user's guide shows... e.g.
talking about "offset" not "address" for trace_image.

Don't use "&function"; functions are like arrays, their name
is their address.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-07 14:51:59 -08:00
Spencer Oliver
991d030fcc MIPS: change bulk_write_memory fallback msg to LOG_DEBUG
Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-07 22:39:35 +00:00
Spencer Oliver
c68c2751f3 MIPS: whitespace cleanup
Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-07 20:56:07 +00:00
Spencer Oliver
2d450b9033 MIPS: fastdata bulk write fallback
If fastdata access fails, then fallback to default mips_m4k_write_memory
Remove unnecessary fastdata loader verify check

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-06 20:24:31 +00:00
David Brownell
2bc7446bb8 buildfix with -DNDEBUG
Don't save that state unless its only user, an assertion,
is compiled.  Saving it broke a cygwin build.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-05 14:11:03 -08:00
David Brownell
844b5eb49d don't require 'openocd.cfg' to start
Starting the daemon with with just a bare "openocd" I saw:

	Can't find openocd.cfg

That's not an error; don't treat it as if it were.  There may
be an error later -- like, "no interface set up" -- but let
messages only report real errors, not fake ones.
2010-01-05 13:32:39 -08:00
David Brownell
fccb812f82 ARM: add #defines for JTAG ack codes
JTAG has only two possible JTAG ack codes for APACC and DPACC
register reads/writes.  Define them, and remove empty "else"
clause in the code which now uses those codes.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-05 13:03:27 -08:00
David Brownell
adf2a9a267 ARM: add comments re DAP assumptions
I think some of these assumptions are not well-founded.
Related, that swjdp_transaction_endcheck() is a bit iffy.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-05 12:55:46 -08:00
Spencer Oliver
9d83df72dc MIPS: pracc access tweaks
reorder the pracc access so we can save a few access cycles

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-05 19:54:37 +00:00
Spencer Oliver
ba96fc3e9d PIC32: enable ram execution
add reset-init script to allow ram execution from reset, this is required for ejtag fastdata access.

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-05 19:54:37 +00:00
Spencer Oliver
f6412d9c7b MIPS: optimize pracc access
remove unnecessary nops when accessing ejtag pracc
general fastdata patch cleanup

Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-05 19:54:36 +00:00
Spencer Oliver
faad9e5923 parport: output port as hex rather than dec
Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-05 19:54:36 +00:00
David Claffey
03e8649bc6 MIPS: merge mips fast_data patch from David N. Claffey
Signed-off-by: Spencer Oliver <ntfreak@users.sourceforge.net>
2010-01-05 19:54:35 +00:00
Øyvind Harboe
95f86e8e05 gdb: fix regression in gdb_port command
The gdb_port command can be invoked during normal execution
to report the port used for gdb, whereas it was listed as
CONFIG stage only, which caused an error when excuting
it to return the reported error.

Also in line with the grander goal of making more commands
available during all "modes" (perhaps retiring config mode),
there is no particular reason to limit gdb_port to the
config stage.

Regression was introduced in:

b3bf1d12b2 aka
v0.4.0-rc1-32-gb3bf1d1

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2010-01-05 15:28:23 +01:00
Johannes Stezenbach
6d4abe906f update udev rules for new udev version
New versions of udev (148+) emit the following warnings:

udevd[425]: BUS= will be removed in a future udev version,
  please use SUBSYSTEM= to match the event device, or
  SUBSYSTEMS= to match a parent device, in /lib/udev/rules.d/60-openocd.rules:1
udevd[425]: SYSFS{}= will be removed in a future udev version,
  please use ATTR{}= to match the event device, or
  ATTRS{}= to match a parent device, in /lib/udev/rules.d/60-openocd.rules:4
udevd[425]: SYSFS{}= will be removed in a future udev version,
  please use ATTR{}= to match the event device, or
  ATTRS{}= to match a parent device, in /lib/udev/rules.d/60-openocd.rules:7
...

See also http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=560141

[dbrownell@users.sourceforge.net: add IDs for Stellaris ICDI, Olimex Tiny-H]

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-05 01:54:06 -08:00
David Brownell
1b3f15d51e ARMv7-M: use AP_REG_* symbol
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-04 22:11:34 -08:00
David Brownell
237a707f96 FT2232: fix doc typo
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-03 15:02:51 -08:00
David Brownell
e1258c703b JTAG/drivers: ft2232 docs
Add doxyegen description for this driver.

Correct the helptext (configures *or* displays based on #params),
and usage (use the same BNF as the User's Guide).

Remove superfluous #include

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-03 14:54:52 -08:00
David Brownell
50fb3a5129 JTAG/Drivers: Amontec JTAG accelerator fixes
Remove superfluous #include.

Correct the helptext (configures *or* displays based on #params),
and usage (use the same BNF as the User's Guide).

Add doxygen -- file-level description and a @todo for doing
RTCK correctly.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-03 14:51:01 -08:00
David Brownell
4aedb02fcd JTAG: Amontec JTAG accelerater "rtck" is back
The command processing conversion a while back lost the
"rtck" enable/disable command; restore it.

NOTE that having such a command is wrong; there's a standard
way to enable adaptive clocking ("speed 0").

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-03 13:30:06 -08:00
David Brownell
e0338293b8 JTAG/drivers: cleanup jtag_interface structs
Get rid of excess indents.
Ditto superfluous "&" before function pointers.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-03 13:07:18 -08:00
David Brownell
d9508b30e0 JTAG/drivers: amt_jtagaccel fixes + cleanup
Build fixes:  it failed abysmally with PPDEV enabled.  Swapped
a build-time error with a FIXME comment in the affected macros.

Cleanup: remove "&" before function pointers, and excess indent,
for the interface struct declaration.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-03 12:59:51 -08:00
David Brownell
4ed5b45097 ARM: ADIv5 JTAG symbol cleanup
Rename DAP_IR_* as JTAG_DP_* since those symbols are specifically
for JTAG-DP (or SWJ-DP in JTAG mode), and won't work with SWD.
Define the JTAG ABORT and IDCODE instructions for completeness;
add a comment about where to (someday) use ABORT.

Fix messaging which assumes everything is an SWJ-DP; say "JTAG-DP"
instead, it's at least more appropriate for all JTAG transports.

Shrink the affected lines.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-02 15:53:33 -08:00
David Brownell
858226aae2 ARM: dap info fix + tweaks
Fix: don't print the BASE address except if it's a MEM-AP;
that's an unlikely error, but there's no point getting it wrong.
Tweaks: comments, capitalization.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-02 15:53:18 -08:00
David Brownell
6105f2bc4a ARM: ADIv5 export cleanup
Make some private functions "static".  Remove their public declarations,
and what is now an obviously unused function.  Shrinks this object's size
(about 5% on x86_64) while making the code's scope easier to understand.
Shrink the affected lines.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-02 15:53:06 -08:00
David Brownell
e60c164cdb ARM: ADIv5 symbol and comment cleanup
Instead of magic numbers, use their AP_REG_* constants.  Rename
the ROM address symbol as BASE to match ARM's documentation.

Comment various other symbols in the header; add some missing ones.
Remove an unused struct.  Add some doxygen for stuff including the
DAP structure and initialization.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-02 15:53:03 -08:00
David Brownell
ec88ccc51c Cortex-M3: minor breakpoint cleanup
Shrink some lines, add some comments, simplify some tests.
During debug startup, log the core revision level too.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-02 15:52:52 -08:00
David Brownell
b3bf1d12b2 streamline and document helptext mode displays
Most commands are usable only at runtime; so don't bother saying
that, it's noise.  Moreover, tokens like EXEC are cryptic.  Be
more clear: highlight only the commands which may (also) be used
during the config stage, thus matching the docs more closely.
There are

 - Configuration commands (per documentation)
 - And also some commands that valid at *any* time.

Update the docs to note that "help" now shows this mode info.

This also highlighted a few mistakes in command configuration,
mostly commands listed as "valid at any time" which shouldn't
have been.  This just fixes ones I noted when sanity testing.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-02 15:52:35 -08:00
Dean Glazeski
9d167d62f2 Fix usage/help search for subcommands.
This makes it so that the usage/help command properly uses the whole command,
including subcommand, in the search for help information.  This previously
caused erroneous output from the usage command handler.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-02 02:10:55 -08:00
Dean Glazeski
be01786186 Add the current command to the command information
I wanted to make it so I can be ignorant of a commands invocation string, so
I tried to use CMD_CURRENT (aka cmd->current) which is supposed to house a
pointer to the current command.  It turns out that this wasn't being set.

This patch adds the current command structure to the command invocation
structure before sending it along to the command handler.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-02 01:50:57 -08:00
Antonio Borneo
668f20d0ab Added ST FlashLINK interface config file.
The relevant cable config is already in OpenOCD, but not a config for
the JTAG adapter.  I have tested with FlashLINK on ARM926.

Signed-off-by: Antonio Borneo <borneo.antonio@gmail.com>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2010-01-02 01:50:57 -08:00
David Brownell
384e9193e9 User's Guide: warn about the forum
Namely, that developers don't hang out; it's a users-only club.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-31 03:09:03 -08:00
Dean Glazeski
7cef6d650c Remove some more Eclipse stuff from Git's eyes.
This adds the .settings folder and the .cproject file put down
by Eclipse from the eyes of Git.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-30 23:26:16 -08:00
Antonio Borneo
3ed254c18a ARM7_9: Fix segfaults
Handlers for commands
 - arm7_9 semihosting <enable | disable>
 - $_TARGETNAME arp_reset assert 1
didn't check if target has already been examined, and could
segfault when using the NULL pointer "arm7_9->eice_cache".

Signed-off-by: Antonio Borneo <borneo.antonio@gmail.com>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-30 16:58:27 -08:00
Antonio Borneo
7c5acf8660 whitespace cleanup, mostly for docs
Remove useless space/tab at end of lines.
Remove spaces in indentation and replace with tab.

Signed-off-by: Antonio Borneo <borneo.antonio@gmail.com>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-30 11:51:29 -08:00
Antonio Borneo
17fb7ead4b ARM9TDMI: Fix segfault.
The handler for "arm9tdmi vector_catch ..." did not check
if target has already been examined.  Without this fix it
segfaults when using NULL pointer "arm7_9->eice_cache".

Signed-off-by: Antonio Borneo <borneo.antonio@gmail.com>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-30 11:51:29 -08:00
Antonio Borneo
c116d8f6bc Fix parport_dcl5 config file.
Signed-off-by: Antonio Borneo <borneo.antonio@gmail.com>
2009-12-30 19:07:44 +01:00
Øyvind Harboe
20354a66b9 zy1000: add zy1000_ prefix to uart command
less polution of the general namespace(preventive action,
no problems reported).

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2009-12-30 13:13:31 +01:00
Øyvind Harboe
2cf6d47375 zy1000: unlock flash upon startup for revc
Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2009-12-30 12:36:22 +01:00
Øyvind Harboe
272c33c190 zy1000: reconfigure FPGA upon reset instead of just the CPU
Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2009-12-30 12:12:32 +01:00
Øyvind Harboe
bd3700e89d zy1000: firmware upgrade fixes for revc
Use ecos firmwareutil upgrade utilities

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2009-12-30 12:12:24 +01:00
Øyvind Harboe
12618e4c6d zy1000: less warnings
use inline for static functions in header files to
avoid warnings about fn not being used.

Signed-off-by: Øyvind Harboe <oyvind.harboe@zylin.com>
2009-12-30 12:11:33 +01:00
Piotr Esden-Tempski
d4bef466c3 Added Open-BLDC board config file. 2009-12-29 12:41:43 +01:00
Piotr Esden-Tempski
aa81462618 Added floss-jtag interface config file. 2009-12-29 12:41:43 +01:00
Freddie Chopin
6b1eeb92fe MinGW build fixes
Print "ssize_t" as "%ld" (+ cast to long) not as "%zu".
Official MinGW (gcc 3.4.5) doesn't understand "z" flag.

Signed-off-by: Freddie Chopin <freddie_chopin@op.pl>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-28 13:09:31 -08:00
Freddie Chopin
37cc6c495f stm32x commands get "usage"
Add .usage fields to stm32x command_registration,
so that "help stm32x" shows required parameters.

Signed-off-by: Freddie Chopin <freddie_chopin@op.pl>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-28 13:05:50 -08:00
David Brownell
ec297e4bf1 Fix Luminary FT2232 layout docs/configs
Most of this patch updates documentation and comments for various
Luminary boards, supporting two bug fixes by helping to make sense
of the current mess:

 - Recent rev C lm3s811 eval boards didn't work.  They must use
   the ICDI layout, which sets up some signals that the older
   boards didn't need.  This is actually safe and appropriate
   for *all* recent boards ... so just make "luminary.cfg" use
   the ICDI layout.

 - "luminary-lm3s811.cfg", was previously unusable!  No VID/PID;
   and the wrong vendor string.  Make it work, but reserve it
   for older boards where the ICDI layout is wrong.

 - Default the LM3748 eval board to "luminary.cfg", like the
   other boards.  If someone uses an external JTAG adapter, all
   boards will use the same workaround (override that default).

The difference between the two FT2232 layouts is that eventually
the EVB layout will fail cleanly when asked to enable SWO trace,
but the ICDI layout will as cleanly be able to enable it.  Folk
using "luminary.cfg" with Rev B boards won't see anything going
wrong until SWO support is (someday) added.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-28 12:59:47 -08:00
Piotr Esden-Tempski
cba1813d5c NOR: last_addr also needs correction when checking alignment
Otherwise the new alignment checking algorithm thinks that the
address is not aligned, because it is way beyond the last sector.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-28 12:31:47 -08:00
David Brownell
3ace333663 create tcl/board/dm365evm.cfg
This config is only lightly tested, and doesn't work well yet;
but it's a start.

 * Notably missing is PLL configuration, since each DaVinci
   does that just a bit differently; and thus DDR2 setup.

 * The SRST workaround needed for the goof in the CPLD's VHDL
   depends on at least the not-yet-merged patch letting ARM9
   (and ARM7) chips perform resets that don't use SRST.

So this isn't yet suitable for debugging U-Boot.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-27 12:16:55 -08:00
David Brownell
155a6a2c0b NOR: make flash_write_unlock() pad to sector end
Resolve a regression when using newish automagic "write_image"
modes, by always padding to the end of affected sectors.

Also document some issues associated with those automagic options,
in the User's Guide and also some related code comments.

We might need similar padding at the *beginning* of some sectors,
but this is a minimalist fix for the problems which have currently
been reported (plus doc updates).

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-27 11:34:31 -08:00
Catalin Patulea
84dbf8ab5a Driver for USB-JTAG, Altera USB-Blaster and compatibles
The 10-pin JTAG layout used with these adapters is used by
a variety of platforms including AVR.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-26 15:05:06 -08:00
Dean Glazeski
900d745567 Olimex SAM9-L9260 board configuration update.
This updates the board configuration for the SAM9-L9260 board with the
configuration for the on-board NAND and dataflash.  Included are commands
for configuring the AT91SAM9 NAND flash driver.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-26 13:08:24 -08:00
David Brownell
3a84436afb ARM: add comment re register exports
Modern versions of GDB can understand VFP3 and iwMMXt hardware.
2009-12-26 11:25:44 -08:00
David Brownell
e7f81c11c9 User's Guide: update GDB info
Advise leaving background polling enabled; fix broken URL;
add simple program startup example.
2009-12-26 10:35:24 -08:00
David Brownell
df58812b52 NOR: messaging fix
Fix syntax error:  default to "wrote N bytes"; writing a
single byte is an unusual case, not the normal one.
2009-12-26 10:24:39 -08:00
David Brownell
396b0f3012 NOR: Allocate the right amount of memory
Switch to calloc() to simplify review and initialization.
2009-12-26 10:22:28 -08:00
David Brownell
08a890e4aa cygwin 1.7 build fixes
It's less accepting of signed char ... insisting that e.g. tolower()
not receive one as a parameter.

It's probably good to phase out such usage, given the number of bugs
that lurk in the vicinity (assumptions that char is unsigned), so fix
these even though such usage is actually legal.

Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-26 10:19:19 -08:00
Antonio Borneo
f9d203d1e6 PARPORT code cleanup:
Align elements in array.

Signed-off-by: Antonio Borneo <borneo.antonio@gmail.com>
2009-12-26 10:19:57 +01:00
David Brownell
4e2b15fc93 Restore "-dev" version suffix
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
2009-12-21 14:49:36 -08:00
189 changed files with 11088 additions and 2771 deletions

6
.gitignore vendored
View File

@@ -66,6 +66,10 @@ stamp-vti
INSTALL
NOTES
# coexist with quilt
patches
# Eclipse stuff
.project
.cproject
.settings

14
BUGS
View File

@@ -6,6 +6,12 @@ posting a message with your report:
openocd-development@lists.berlios.de
Also, please check the Trac bug database to see if a ticket for
the bug has already been opened. You might be asked to open
such a ticket, or to update an existing ticket with more data.
https://sourceforge.net/apps/trac/openocd/
To minimize work for OpenOCD developers, you should try to include
all of the information listed below. If you feel that some of the
items below are unnecessary for a clear bug report, you may leave
@@ -22,12 +28,12 @@ that may be important.
- If the report is for a regression:
- Include logs for both working and broken versions.
- Find the precise version that caused the regression by binary search.
You can use "git bisect" to expedite this binary search:
You can use "git bisect" to expedite this binary search:
http://www.kernel.org/pub/software/scm/git/docs/git-bisect.html
If possible, please develop and attach a patch that helps to expose or
solve the reported problem. See the PATCHES file for more information
for that process.
solve the reported problem. See the PATCHES.txt file for information
about that process.
Attach all files directly to your posting. The mailing list knows to
transform attachments to links, but attachments must be less than 300KB
@@ -36,7 +42,7 @@ in total.
@section bugscrashdump Obtaining Crash Backtraces
If OpenOCD is crashing, there are two very effective things you can do to
improve your chances of getting help on the development mailing list.
improve your chances of getting help on the development mailing list.
Try to reproduce the problem using the dummy JTAG interface to allow other developers to replicate
your problem robustly and use GDB to get a trace:@par

View File

@@ -384,7 +384,7 @@ HIDE_SCOPE_NAMES = NO
# will put a list of the files that are included by a file in the documentation
# of that file.
SHOW_INCLUDE_FILES = YES
SHOW_INCLUDE_FILES = NO
# If the INLINE_INFO tag is set to YES (the default) then a tag [inline]
# is inserted in the documentation for inline members.
@@ -403,7 +403,7 @@ SORT_MEMBER_DOCS = YES
# by member name. If set to NO (the default) the members will appear in
# declaration order.
SORT_BRIEF_DOCS = NO
SORT_BRIEF_DOCS = YES
# If the SORT_GROUP_NAMES tag is set to YES then doxygen will sort the
# hierarchy of group names into alphabetical order. If set to NO (the default)
@@ -567,9 +567,9 @@ WARN_LOGFILE =
INPUT = @srcdir@/doc/manual \
@srcdir@/TODO \
@srcdir@/BUGS \
@srcdir@/PATCHES \
@srcdir@/PATCHES.txt \
@srcdir@/src \
@srcdir@/config.h
@builddir@/config.h
# This tag can be used to specify the character encoding of the source files
# that doxygen parses. Internally doxygen uses the UTF-8 encoding, which is
@@ -692,13 +692,13 @@ SOURCE_BROWSER = YES
# Setting the INLINE_SOURCES tag to YES will include the body
# of functions and classes directly in the documentation.
INLINE_SOURCES = YES
INLINE_SOURCES = NO
# Setting the STRIP_CODE_COMMENTS tag to YES (the default) will instruct
# doxygen to hide any special comment blocks from generated source code
# fragments. Normal C and C++ comments will always remain visible.
STRIP_CODE_COMMENTS = NO
STRIP_CODE_COMMENTS = YES
# If the REFERENCED_BY_RELATION tag is set to YES
# then for each documented function all documented

View File

@@ -26,6 +26,7 @@ Doxyfile: $(srcdir)/Doxyfile.in
echo "### @@@ -= DO NOT EDIT THIS FILE =- @@@ ###" && \
echo "### @@@ Make changes to Doxyfile.in @@@ ###" && \
sed -e 's,@srcdir\@,$(srcdir),' \
-e 's,@builddir\@,$(builddir),' \
-e 's,@doxygen_as_html\@,$(doxygen_as_html),' \
-e 's,@doxygen_as_pdf\@,$(doxygen_as_pdf),' $< \
) > $@

42
NEWS
View File

@@ -5,36 +5,46 @@ and other issues not mentioned here.
JTAG Layer:
Support KT-Link JTAG adapter.
Support USB-JTAG, Altera USB-Blaster and compatibles.
Boundary Scan:
Target Layer:
General
- new "reset-assert" event, for systems without SRST
ARM
- supports "reset-assert" event (except on Cortex-M3)
- renamed "armv4_5" command prefix as "arm"
- recognize TrustZone "Secure Monitor" mode
- "arm regs" command output changed
- register names use "sp" not "r13"
- add top-level "mcr" and "mrc" commands, replacing
various core-specific operations
- basic semihosting support
- basic semihosting support (ARM7/ARM9 only, for now)
ARM11
- Preliminary ETM and ETB hookup
- accelerated "flash erase_check"
- accelerated GDB memory checksum
- support "arm regs" command
- can access all core modes and registers
- watchpoint support
- Should act much more like other ARM cores:
* Preliminary ETM and ETB hookup
* accelerated "flash erase_check"
* accelerated GDB memory checksum
* support "arm regs" command
* can access all core modes and registers
* watchpoint support
- Shares some core debug code with Cortex-A8
Cortex-A8
- support "arm regs" command
- can access all core modes and registers
- supports "reset-assert" event (used on OMAP3530)
- watchpoint support
- Should act much more like other ARM cores:
* support "arm regs" command
* can access all core modes and registers
* watchpoint support
- Shares some core debug code with ARM11
Cortex-M3
- Exposed DWT registers like cycle counter
- vector_catch settings not clobbered by resets
- no longer interferes with firmware's fault handling
ETM, ETB
- "trigger_percent" command moved ETM --> ETB
- "etm trigger_debug" command added
MIPS
- use fastdata writes
Freescale DSP563xx cores (partial support)
Flash Layer:
@@ -44,13 +54,19 @@ Flash Layer:
- <driver_name>[.N]: reference the driver's Nth bank
New 'nand verify' command to check bank against an image file.
The "flash erase_address" command now rejects partial sectors;
previously it would silently erase extra data.
previously it would silently erase extra data. If you
want to erase the rest of the first and/or last sectors
instead of failing, you must pass an explicit "pad" flag.
New at91sam9 NAND controller driver.
New s3c64xx NAND controller driver.
Board, Target, and Interface Configuration Scripts:
ARM9
- ETM and ETB hookup for iMX2* targets
Add $HOME/.openocd to the search path.
Handle Rev C of LM3S811 eval boards.
- use "luminary-lm3s811.cfg" for older boards
- use "luminary.cfg" for RevC and newer
Core Jim/TCL Scripting:
New 'usage' command to provide terse command help.
@@ -77,4 +93,4 @@ For older NEWS, see the NEWS files associated with each release
For more information about contributing test reports, bug fixes, or new
features and device support, please read the new Developer Manual (or
the BUGS and PATCHES files in the source archive).
the BUGS and PATCHES.txt files in the source archive).

View File

@@ -9,7 +9,7 @@ must past stricter value checks, and many more error conditions have
been handled correctly. These efforts helped to make the 0.2.0 release
more stable and robust, though some changes may expose latent bugs in
your existing configuration scripts.
This release does not maintain backward compatibility in all respects,
so some target or configuration scripts may need to be updated. In some
cases, you may also see warnings; resolve those, because they indicate
@@ -20,7 +20,7 @@ The following areas of OpenOCD functionality changed in this release:
JTAG Layer:
- Improves modularity: core, TCL, driver commands, and interface have
been separated, encapsulated, and documented for developers. Mostly.
- Improves JTAG TAP transition tables:
- Improves JTAG TAP transition tables:
* Makes TAP paths variable length, rather than being fixed at 7 steps.
* Fixes problems with some targets that did not like longer paths.
- Improves JTAG driver/minidriver modularity and encapsulation.

12
NEWTAPS
View File

@@ -30,7 +30,7 @@ Version Number Changes:
not a big deal. Please do report this information. We'd like to
know about it.
For example
For example
Error: ERROR: Tap: s3c4510.cpu - Expected id: 0x3f0f0f0f, Got: 0x1f0f0f0f
Error: ERROR: expected: mfg: 0x787, part: 0xf0f0, ver: 0x3
@@ -39,7 +39,7 @@ Error: ERROR: got: mfg: 0x787, part: 0xf0f0, ver: 0x1
========================================
Updating the Tap ID number your self
Why do this? You just want the warning to go away. And don't want
to update your version/instance of OpenOCD.
@@ -79,11 +79,11 @@ Examples:
0x3f0f0f0f - is a newer ARM7TDMI
0x3ba00477 - is an ARM cortex M3
Some chips have multiple JTAG taps - be sure to list
Some chips have multiple JTAG taps - be sure to list
each one individually - ORDER is important!
========================================
B) The maker of the part
B) The maker of the part
Examples:
Xilinx, Atmel, ST Micro Systems, Freescale
@@ -94,7 +94,7 @@ C) The family of parts it belongs to
Examples:
"NXP LPC Series"
"Atmel SAM7 Series"
========================================
D) The actual part number on the package
@@ -121,7 +121,7 @@ For example: A consumer GPS unit or a cellphone
ie: Olimex, LogicPD, Freescale(eval board)
========================================
(G) Identifying information on the board.
Not good: "iar red ST eval board"

View File

@@ -32,7 +32,7 @@ in response to feedback.
Add yourself to the GPL copyright for non-trivial changes.
To create a patch from the command line:
@code
@code
git diff >mypatch.txt
@endcode

View File

@@ -27,8 +27,8 @@ based JTAG debuggers.
http://sourceforge.net/projects/libusb-win32/
You need to download the libusb-win32-device-bin-0.1.12.2.tar.gz
package. Extract this file into a temp directory.
You need to download the libusb-win32-device-bin-0.1.12.2.tar.gz
package. Extract this file into a temp directory.
Copy the file libusb-win32-device-bin-0.1.12.2\include\usb.h
to your MinGW include directory.
@@ -59,10 +59,10 @@ released source tarball or the git tree.
If you are using the git tree, the following are the instructions from
README.mingw. You will need to have the cmake utility installed.
- Edit Toolchain-mingw32.cmake to point to the correct MinGW
- Edit Toolchain-mingw32.cmake to point to the correct MinGW
installation.
- Create a build directory like "mkdir build-win32", e.g in ../libftdi/
- cd into that directory and run
- cd into that directory and run
"cmake -DCMAKE_TOOLCHAIN_FILE=../Toolchain-mingw32.cmake .."
- Copy src/ftdi.h to your MinGW include directory.
- Copy build-win32/src/*.a to your MinGW lib directory.

42
TODO
View File

@@ -27,8 +27,8 @@ This section provides possible things to improve with OpenOCD's TCL support.
parameters. Currently variables assigned through one such parameter
command/script are unset before the next one is invoked.
- Isolate all TCL command support:
- Pure C CLI implementations using --disable-builtin-tcl.
- Isolate all TCL command support:
- Pure C CLI implementations using --disable-builtin-tcl.
- Allow developers to build new dongles using OpenOCD's JTAG core.
- At first, provide only low-level JTAG support; target layer and
above rely heavily on scripting event mechanisms.
@@ -112,7 +112,7 @@ TCP/IP packets handled by the server.
@section thelistswd Serial Wire Debug
- implement Serial Wire Debug interface
- implement Serial Wire Debug interface
@section thelistbs Boundary Scan Support
@@ -142,6 +142,8 @@ Once the above are completed:
https://lists.berlios.de/pipermail/openocd-development/2009-May/006590.html
- regression: "reset halt" between 729(works) and 788(fails): @par
https://lists.berlios.de/pipermail/openocd-development/2009-July/009206.html
- registers
- add flush-value operation, call them all on resume/reset
- mcr/mrc target->type support
- missing from ARM920t, ARM966e, XScale.
It's possible that the current syntax is unable to support read-modify-write
@@ -163,17 +165,25 @@ https://lists.berlios.de/pipermail/openocd-development/2009-October/011506.html
use hardware stepping if available.
- mdb can return garbage data if read byte operation fails for
a memory region(16 & 32 byte access modes may be supported). Is this
a bug in the .MX31 PDK init script? Try on i.MX31 PDK:
a bug in the .MX31 PDK init script? Try on i.MX31 PDK:
mdw 0xb80005f0 0x8, mdh 0xb80005f0 0x10, mdb 0xb80005f0 0x20. mdb returns
garabage.
- implement missing functionality (grep FNC_INFO_NOTIMPLEMENTED ...)
- Thumb2 single stepping: ARM1156T2 needs simulator support
- Cortex A8 support (ML)
- add target implementation (ML)
- Cortex M3 support
- when stepping, only write dirtied registers (be faster)
- when connecting to halted core, fetch registers (startup is quirky)
- Generic ARM run_algorithm() interface
- tagged struct wrapping ARM instructions and metadata
- not revision-specific (current: ARMv4+ARMv5 -or- ARMv6 -or- ARMv7)
- usable with at least arm_nandwrite() and generic CFI drivers
- ETM
- don't show FIFOFULL registers if they're not supported
- use comparators to get more breakpoints and watchpoints
- add "etm drivers" command
- trace driver init() via examine() paths only, not setup()/reset
- MC1322x support (JW/DE?)
- integrate and test support from JW (and DE?)
- get working with a known good interface (i.e. not today's jlink)
@@ -197,8 +207,8 @@ https://lists.berlios.de/pipermail/openocd-development/2009-October/011506.html
@section thelistsvf SVF/XSVF
- develop SVF unit tests
- develop XSVF unit tests
- develop SVF unit tests
- develop XSVF unit tests
@section thelistflash Flash Support
@@ -209,6 +219,16 @@ https://lists.berlios.de/pipermail/openocd-development/2009-October/011506.html
- ocl
- str9xpec
- Don't expect writing all-ones to be a safe way to write without
changing bit values. Minimally it loses on flash modules with
internal ECC, where it may change the ECC.
- NOR flash_write_unlock() does that between sectors
- there may be other cases too
- Make sure all commands accept either a bank name or a bank number,
and be sure both identifiers show up in "flash banks" and "nand list".
Right now the user-friendly names are pretty much hidden...
@subsection thelistflashcfi CFI
- finish implementing bus width/chip width handling (suggested by NC)
@@ -328,7 +348,7 @@ at the bottom of the list below. Example, on amd64:
from unaligned memory addresses
- libopenocd support: @par
https://lists.berlios.de/pipermail/openocd-development/2009-May/006405.html
- review and clean up interface/target/flash APIs
- review and clean up interface/target/flash APIs
The following strategic tasks will require ambition, knowledge, and time
to complete:
@@ -346,9 +366,11 @@ to complete:
- Develop milestone and release guidelines, processes, and scripts.
- Develop "style" guidelines (and scripts) for maintainers:
- reviewing patches
- committing to Subversion
- Review The Guide for OpenOCD Users for documentation errors or omissions
- Update The Manual for OpenOCD Developers:
- committing to git
- Review Users' Guide for documentation errors or omissions
- "capture" and "ocd_find" commands
- "ocd_" prefix on various stuff
- Update Developer's Manual (doxygen output)
- Add documentation describing the architecture of each module
- Provide more Technical Primers to bootstrap contributor knowledge

View File

@@ -1,7 +1,7 @@
#!/bin/sh -e
# Run the autotools bootstrap sequence to create the configure script
# Stop execution as soon as we have an unknown command
# Stop execution as soon as we have an unknown command
set -e
if libtoolize --version >/dev/null 2>&1; then

View File

@@ -1,5 +1,5 @@
AC_PREREQ(2.60)
AC_INIT([openocd], [0.4.0-rc1],
AC_INIT([openocd], [0.4.0-rc2],
[OpenOCD Mailing List <openocd-development@lists.berlios.de>])
AC_CONFIG_SRCDIR([src/openocd.c])
@@ -392,6 +392,14 @@ AC_ARG_ENABLE(ft2232_ftd2xx,
AS_HELP_STRING([--enable-ft2232_ftd2xx], [Enable building support for FT2232 based devices using the FTD2XX driver from ftdichip.com]),
[build_ft2232_ftd2xx=$enableval], [build_ft2232_ftd2xx=no])
AC_ARG_ENABLE(usb_blaster_libftdi,
AS_HELP_STRING([--enable-usb_blaster_libftdi], [Enable building support for the Altera USB-Blaster using the libftdi driver, opensource alternate of FTD2XX]),
[build_usb_blaster_libftdi=$enableval], [build_usb_blaster_libftdi=no])
AC_ARG_ENABLE(usb_blaster_ftd2xx,
AS_HELP_STRING([--enable-usb_blaster_ftd2xx], [Enable building support for the Altera USB-Blaster using the FTD2XX driver from ftdichip.com]),
[build_usb_blaster_ftd2xx=$enableval], [build_usb_blaster_ftd2xx=no])
AC_ARG_ENABLE(amtjtagaccel,
AS_HELP_STRING([--enable-amtjtagaccel], [Enable building the Amontec JTAG-Accelerator driver]),
[build_amtjtagaccel=$enableval], [build_amtjtagaccel=no])
@@ -551,7 +559,7 @@ case $host in
AC_MSG_WARN([--disable-parport-giveio is not supported by MinGW32 hosts])
fi
parport_use_giveio=yes
CFLAGS="$CFLAGS -D__USE_MINGW_ANSI_STDIO"
AC_DEFINE(IS_MINGW, 1, [1 if building for MinGW.])
@@ -651,6 +659,20 @@ else
AC_DEFINE(BUILD_FT2232_FTD2XX, 0, [0 if you don't want ftd2xx ft2232.])
fi
if test $build_usb_blaster_libftdi = yes; then
build_bitbang=yes
AC_DEFINE(BUILD_USB_BLASTER_LIBFTDI, 1, [1 if you want libftdi usb_blaster.])
else
AC_DEFINE(BUILD_USB_BLASTER_LIBFTDI, 0, [0 if you don't want libftdi usb_blaster.])
fi
if test $build_usb_blaster_ftd2xx = yes; then
build_bitbang=yes
AC_DEFINE(BUILD_USB_BLASTER_FTD2XX, 1, [1 if you want ftd2xx usb_blaster.])
else
AC_DEFINE(BUILD_USB_BLASTER_FTD2XX, 0, [0 if you don't want ftd2xx usb_blaster.])
fi
if test $build_amtjtagaccel = yes; then
AC_DEFINE(BUILD_AMTJTAGACCEL, 1, [1 if you want the Amontec JTAG-Accelerator driver.])
else
@@ -727,7 +749,7 @@ then
AC_MSG_ERROR([The option: with_ftd2xx_linux_tardir is for LINUX only.])
fi
if test $build_ft2232_ftd2xx = yes -o $build_presto_ftd2xx = yes ; then
if test $build_ft2232_ftd2xx = yes -o $build_presto_ftd2xx = yes -o $build_usb_blaster_ftd2xx = yes ; then
AC_MSG_CHECKING([for ftd2xx.lib exists (win32)])
# if we are given a zipdir...
@@ -1001,6 +1023,8 @@ AM_CONDITIONAL(AT91RM9200, test $build_at91rm9200 = yes)
AM_CONDITIONAL(BITBANG, test $build_bitbang = yes)
AM_CONDITIONAL(FT2232_LIBFTDI, test $build_ft2232_libftdi = yes)
AM_CONDITIONAL(FT2232_DRIVER, test $build_ft2232_ftd2xx = yes -o $build_ft2232_libftdi = yes)
AM_CONDITIONAL(USB_BLASTER_LIBFTDI, test $build_usb_blaster_libftdi = yes)
AM_CONDITIONAL(USB_BLASTER_DRIVER, test $build_usb_blaster_ftd2xx = yes -o $build_usb_blaster_libftdi = yes)
AM_CONDITIONAL(AMTJTAGACCEL, test $build_amtjtagaccel = yes)
AM_CONDITIONAL(GW16012, test $build_gw16012 = yes)
AM_CONDITIONAL(PRESTO_LIBFTDI, test $build_presto_libftdi = yes)

View File

@@ -1,60 +1,68 @@
BUS!="usb", ACTION!="add", SUBSYSTEM!=="usb_device", GOTO="openocd_rules_end"
ACTION!="add|change", GOTO="openocd_rules_end"
SUBSYSTEM!="usb", GOTO="openocd_rules_end"
ENV{DEVTYPE}!="usb_device", GOTO="openocd_rules_end"
# Olimex ARM-USB-OCD
SYSFS{idVendor}=="15ba", SYSFS{idProduct}=="0003", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="15ba", ATTRS{idProduct}=="0003", MODE="664", GROUP="plugdev"
# Olimex ARM-USB-OCD-TINY
SYSFS{idVendor}=="15ba", SYSFS{idProduct}=="0004", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="15ba", ATTRS{idProduct}=="0004", MODE="664", GROUP="plugdev"
# Olimex ARM-JTAG-EW
SYSFS{idVendor}=="15ba", SYSFS{idProduct}=="001e", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="15ba", ATTRS{idProduct}=="001e", MODE="664", GROUP="plugdev"
# Olimex ARM-USB-OCD-TINY-H
ATTRS{idVendor}=="15ba", ATTRS{idProduct}=="002a", MODE="664", GROUP="plugdev"
# USBprog with OpenOCD firmware
SYSFS{idVendor}=="1781", SYSFS{idProduct}=="0c63", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="1781", ATTRS{idProduct}=="0c63", MODE="664", GROUP="plugdev"
# Amontec JTAGkey and JTAGkey-tiny
SYSFS{idVendor}=="0403", SYSFS{idProduct}=="cff8", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="0403", ATTRS{idProduct}=="cff8", MODE="664", GROUP="plugdev"
# Amontec JTAGkey-HiSpeed
SYSFS{idVendor}=="0fbb", SYSFS{idProduct}=="1000", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="0fbb", ATTRS{idProduct}=="1000", MODE="664", GROUP="plugdev"
# Axiom AXM-0432 Link (Symphony SoundBite?)
# Calao Systems USB-A9260-C01
# TinCanTools Flyswatter
# OOCD-Link
# Marvell Sheevaplug (early development versions)
SYSFS{idVendor}=="0403", SYSFS{idProduct}=="6010", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="0403", ATTRS{idProduct}=="6010", MODE="664", GROUP="plugdev"
# Calao Systems USB-A9260-C02
SYSFS{idVendor}=="0403", SYSFS{idProduct}=="6001", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="0403", ATTRS{idProduct}=="6001", MODE="664", GROUP="plugdev"
# IAR J-Link USB
SYSFS{idVendor}=="1366", SYSFS{idProduct}=="0101", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="1366", ATTRS{idProduct}=="0101", MODE="664", GROUP="plugdev"
# Raisonance RLink
SYSFS{idVendor}=="138e", SYSFS{idProduct}=="9000", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="138e", ATTRS{idProduct}=="9000", MODE="664", GROUP="plugdev"
# Hitex STR9-comStick
SYSFS{idVendor}=="0640", SYSFS{idProduct}=="002c", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="0640", ATTRS{idProduct}=="002c", MODE="664", GROUP="plugdev"
# Hitex STM32-PerformanceStick
SYSFS{idVendor}=="0640", SYSFS{idProduct}=="002d", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="0640", ATTRS{idProduct}=="002d", MODE="664", GROUP="plugdev"
# Luminary Micro Stellaris/LM3S811
SYSFS{idVendor}=="0403", SYSFS{idProduct}=="bcd9", MODE="664", GROUP="plugdev"
# TI/Luminary Stellaris Evaluation Board (several)
ATTRS{idVendor}=="0403", ATTRS{idProduct}=="bcd9", MODE="664", GROUP="plugdev"
# TI/Luminary Stellaris In-Circuit Debug Interface (ICDI) Board
ATTRS{idVendor}=="0403", ATTRS{idProduct}=="bcda", MODE="664", GROUP="plugdev"
# Xverve Signalyzer Tool (DT-USB-ST)
SYSFS{idVendor}=="0403", SYSFS{idProduct}=="bca0", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="0403", ATTRS{idProduct}=="bca0", MODE="664", GROUP="plugdev"
# egnite Turtelizer 2
SYSFS{idVendor}=="0403", SYSFS{idProduct}=="bdc8", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="0403", ATTRS{idProduct}=="bdc8", MODE="664", GROUP="plugdev"
# Marvell Sheevaplug
SYSFS{idVendor}=="9e88", SYSFS{idProduct}=="9e8f", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="9e88", ATTRS{idProduct}=="9e8f", MODE="664", GROUP="plugdev"
# Section5 ICEbear
SYSFS{idVendor}=="0403", SYSFS{idProduct}=="c140", MODE="664", GROUP="plugdev"
SYSFS{idVendor}=="0403", SYSFS{idProduct}=="c141", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="0403", ATTRS{idProduct}=="c140", MODE="664", GROUP="plugdev"
ATTRS{idVendor}=="0403", ATTRS{idProduct}=="c141", MODE="664", GROUP="plugdev"
LABEL="openocd_rules_end"

View File

@@ -1,6 +1,6 @@
/** @mainpage OpenOCD Reference Manual
/** @mainpage OpenOCD Developer's Guide
Welcome to the OpenOCD Reference Manual -- the developer's resource for
Welcome to the OpenOCD Developer's Guide -- the developer's resource for
learning about the internal architecture of the OpenOCD project. @par
In addition, this document contains the tactical and strategic plans

View File

@@ -55,7 +55,7 @@ static COMMAND_HELPER(handle_hello_args, const char **sep, const char **name)
@endcode
Of course, you may also call other macros or functions, but that extends
beyond the scope of this tutorial on writing commands.
beyond the scope of this tutorial on writing commands.
@section primercmdreg Command Registration
@@ -68,9 +68,9 @@ static const struct command_registration hello_command_handlers[] = {
{
.name = "hello",
.mode = COMMAND_ANY,
.handler = &handle_hello_command,
.help = "print a warm greetings",
.usage = "[<name>]",
.handler = handle_hello_command,
.help = "print a warm greeting",
.usage = "[name]",
},
{
.chain = foo_command_handlers,
@@ -84,7 +84,12 @@ int hello_register_commands(struct command_context_s *cmd_ctx)
}
@endcode
That's it! The command should now be registered and avaiable to scripts.
Note that the "usage" text should use the same EBNF that's found
in the User's Guide: literals in 'single quotes', sequences of
optional parameters in [square brackets], and alternatives in
(parentheses|with|vertical bars), and so forth. No angle brackets.
That's it! The command should now be registered and available to scripts.
@section primercmdchain Command Chaining

View File

@@ -399,7 +399,7 @@ affect its behavior:
@section releasetutorial Release Tutorials
This section should contain a brief tutorial for using the Release
This section should contain a brief tutorial for using the Release
Script to perform release tasks, but the new script needs to be
used for 0.3.0.

View File

@@ -320,6 +320,6 @@ openocd -s /usr/local/share/openocd -f httpd/httpd.tcl -f interface/dummy.cfg -f
Navigate to: http://localhost:8888/
*/

View File

@@ -308,7 +308,7 @@ For technical reference material:
- Else it's a "Config Command" if it must be used before the
configuration stage completes.
- For a "Driver", list its name.
- Use BNF style regular expressions to define parameters:
- Use EBNF style regular expressions to define parameters:
brackets around zero-or-one choices, parentheses around
exactly-one choices.
- Use \@option, \@file, \@var and other mechanisms where appropriate.

View File

@@ -22,19 +22,23 @@ please check the \fIopenocd\fR info page for the complete list.
.SH "OPTIONS"
.TP
.B "\-f, \-\-file <filename>"
Use configuration file
.BR <filename> .
This is a shortcut for a \fB\-c "[script \fI<filename>\fB]"\fR
command, using a search path to load the configuration file
.IR <filename> .
In order to specify multiple config files, you can use multiple
.B \-\-file
arguments. If this option is omitted, the config file
arguments. If no such \fB\-c\fR
options are included, the first config file
.B openocd.cfg
in the current working directory will be used.
in the search path will be used.
.TP
.B "\-s, \-\-search <dirname>"
Search for config files and scripts in the directory
.BR <dirname> .
If this option is omitted, OpenOCD searches for config files and scripts
in the current directory.
Add
.I <dirname>
to the search path used for config files and scripts.
The search path begins with the current directory,
then includes these additional directories before other
components such as the standard OpenOCD script libraries.
.TP
.B "\-d, \-\-debug <debuglevel>"
Set debug level. Possible values are:
@@ -52,13 +56,17 @@ The default level is
.TP
.B "\-l, \-\-log_output <filename>"
Redirect log output to the file
.BR <filename> .
.IR <filename> .
Per default the log output is printed on
.BR stderr .
.TP
.B "\-c, \-\-command <cmd>"
Run the command
.BR <cmd> .
Add the command
.I <cmd>
to a list of commands executed on server startup.
Note that you will need to explicitly invoke
.I init
if the command requires access to a target or flash.
.TP
.B "\-p, \-\-pipe"
Use pipes when talking to gdb.
@@ -88,9 +96,6 @@ and
programs are properly installed at your site, the command
.B info openocd
should give you access to the complete manual.
.PP
Also, the OpenOCD wiki contains some more information and examples:
.B http://openfacts.berlios.de/index-en.phtml?title=Open_On-Chip_Debugger
.SH "AUTHORS"
Please see the file AUTHORS.
.PP

File diff suppressed because it is too large Load Diff

View File

@@ -1,4 +1,4 @@
Some of these binaries are build & linked using eCos.
Some of these binaries are build & linked using eCos.
For source for the flash drivers, see:

View File

@@ -60,12 +60,16 @@ endif
if FT2232_LIBFTDI
FTDI2232LIB = -lftdi -lusb
else
if USB_BLASTER_LIBFTDI
FTDI2232LIB = -lftdi -lusb
else
if PRESTO_LIBFTDI
FTDI2232LIB = -lftdi -lusb
else
FTDI2232LIB =
endif
endif
endif
if USBPROG
LIBUSB = -lusb

View File

@@ -62,6 +62,7 @@
#include "rom.h"
#ifdef CYGPKG_HAL_NIOS2
#include <cyg/hal/io.h>
#define ZY1000_SER_DEV "/dev/uart_0"
#else
#define ZY1000_SER_DEV "/dev/ser0"
@@ -145,7 +146,14 @@ static void zylinjtag_reboot(cyg_addrword_t data)
diag_printf("Unmounting /config..\n");
umount("/config");
diag_printf("Rebooting..\n");
#ifdef CYGPKG_HAL_NIOS2
/* This will reboot & reconfigure the FPGA from the bootloader
* and on.
*/
IOWR(REMOTE_UPDATE_BASE, 0x20, 0x1);
#else
HAL_PLATFORM_RESET();
#endif
}
static cyg_thread zylinjtag_thread_object;
static cyg_handle_t zylinjtag_thread_handle;
@@ -839,7 +847,7 @@ static int zylinjtag_Jim_Command_uart(Jim_Interp *interp, int argc,
static int current_baud = 38400;
if (argc == 1)
{
command_print(cmd_ctx, "%d", current_baud);
Jim_SetResult(interp, Jim_NewIntObj(interp, current_baud));
return JIM_OK;
}
else if (argc != 2)
@@ -875,8 +883,8 @@ static int zylinjtag_Jim_Command_uart(Jim_Interp *interp, int argc,
baud = CYGNUM_SERIAL_BAUD_230400;
break;
default:
command_print(cmd_ctx, "unsupported baudrate");
return ERROR_INVALID_ARGUMENTS;
Jim_SetResult(interp, Jim_NewStringObj(interp, "unsupported baudrate", -1));
return JIM_ERR;
}
cyg_serial_info_t buf;
@@ -889,7 +897,7 @@ static int zylinjtag_Jim_Command_uart(Jim_Interp *interp, int argc,
err = cyg_io_lookup(ZY1000_SER_DEV, &serial_handle);
if (err != ENOERR)
{
LOG_ERROR("Could not open serial port\n");
Jim_SetResult(interp, Jim_NewStringObj(interp, "Could not open serial port", -1));
return JIM_ERR;
}
@@ -899,7 +907,7 @@ static int zylinjtag_Jim_Command_uart(Jim_Interp *interp, int argc,
&len);
if (err != ENOERR)
{
LOG_ERROR("Failed to get serial port settings %d", err);
Jim_SetResult(interp, Jim_NewStringObj(interp, "Failed to get serial port settings", -1));
return JIM_ERR;
}
buf.baud = baud;
@@ -908,7 +916,7 @@ static int zylinjtag_Jim_Command_uart(Jim_Interp *interp, int argc,
&len);
if (err != ENOERR)
{
LOG_ERROR("Failed to set serial port settings %d", err);
Jim_SetResult(interp, Jim_NewStringObj(interp, "Failed to set serial port settings", -1));
return JIM_ERR;
}
@@ -948,7 +956,11 @@ int main(int argc, char *argv[])
diag_init_putc(_zylinjtag_diag_write_char);
// We want this in the log.
diag_printf("Zylin ZY1000.\n");
#ifdef CYGPKG_HAL_NIOS2
diag_printf("Zylin ZY1000 PCB revc.\n");
#else
diag_printf("Zylin ZY1000 PCB revb.\n");
#endif
err = mount("", "/ram", "ramfs");
if (err < 0)
@@ -987,6 +999,20 @@ int main(int argc, char *argv[])
copydir("/rom", "/ram/cgi");
#ifdef CYGPKG_HAL_NIOS2
cyg_flashaddr_t err_address;
#define UNCACHED_EXT_FLASH_BASE (0x80000000 + EXT_FLASH_BASE)
/* The revc flash is locked upon reset, unlock it */
#ifdef CYGHWR_IO_FLASH_BLOCK_LOCKING
if ((err = flash_unlock((void *) UNCACHED_EXT_FLASH_BASE, EXT_FLASH_SPAN,
(void **) &err_address)) != 0)
{
diag_printf("Error: could not unlock flash\n");
}
#endif
#endif
err = mount("/dev/flash1", "/config", "jffs2");
if (err < 0)
{
@@ -1075,7 +1101,7 @@ int main(int argc, char *argv[])
NULL, NULL);
#endif
Jim_CreateCommand(httpstate.jim_interp, "uart", zylinjtag_Jim_Command_uart, NULL, NULL);
Jim_CreateCommand(httpstate.jim_interp, "zy1000_uart", zylinjtag_Jim_Command_uart, NULL, NULL);
log_init();

View File

@@ -751,8 +751,8 @@ COMMAND_HANDLER(mg_write_cmd)
if (duration_measure(&bench) == ERROR_OK)
{
command_print(CMD_CTX, "wrote %zu byte from file %s "
"in %fs (%0.3f kB/s)", fileio.size, CMD_ARGV[1],
command_print(CMD_CTX, "wrote %ld bytes from file %s "
"in %fs (%0.3f kB/s)", (long)fileio.size, CMD_ARGV[1],
duration_elapsed(&bench), duration_kbps(&bench, fileio.size));
}
@@ -762,7 +762,7 @@ COMMAND_HANDLER(mg_write_cmd)
return ERROR_OK;
mg_write_cmd_err:
free(buffer);
free(buffer);
fileio_close(&fileio);
return ret;
@@ -829,7 +829,7 @@ COMMAND_HANDLER(mg_dump_cmd)
return ERROR_OK;
mg_dump_cmd_err:
free(buffer);
free(buffer);
fileio_close(&fileio);
return ret;
@@ -1271,30 +1271,33 @@ COMMAND_HANDLER(mg_config_cmd)
static const struct command_registration mflash_exec_command_handlers[] = {
{
.name = "probe",
.handler = &mg_probe_cmd,
.handler = mg_probe_cmd,
.mode = COMMAND_EXEC,
.help = "Detect bank configuration information",
},
{
.name = "write",
.handler = &mg_write_cmd,
.handler = mg_write_cmd,
.mode = COMMAND_EXEC,
.usage = "<num> <file> <address>",
.help = "Write a file at the specified address",
/* FIXME bank_num is unused */
.usage = "bank_num filename address",
.help = "Write binary file at the specified address.",
},
{
.name = "dump",
.handler = &mg_dump_cmd,
.handler = mg_dump_cmd,
.mode = COMMAND_EXEC,
.usage = "<num> <file> <address> <size>",
.help = "Dump to a file from the specified address",
/* FIXME bank_num is unused */
.usage = "bank_num filename address size",
.help = "Write specified number of bytes from a binary file "
"to the specified, address.",
},
{
.name = "config",
.handler = &mg_config_cmd,
.handler = mg_config_cmd,
.mode = COMMAND_EXEC,
.usage = "<num> <stage>",
.help = "Dump to a file from the specified address",
.help = "Configure MFLASH options.",
.usage = "('boot'|'storage'|'pll' frequency)",
},
COMMAND_REGISTRATION_DONE
};
@@ -1345,7 +1348,8 @@ COMMAND_HANDLER(mg_bank_cmd)
char *str;
mflash_bank->rst_pin.num = strtoul(CMD_ARGV[2], &str, 0);
if (*str)
mflash_bank->rst_pin.port[0] = (uint16_t)tolower(str[0]);
mflash_bank->rst_pin.port[0] = (uint16_t)
tolower((unsigned)str[0]);
mflash_bank->target = target;
@@ -1366,15 +1370,15 @@ COMMAND_HANDLER(mg_bank_cmd)
static const struct command_registration mflash_config_command_handlers[] = {
{
.name = "bank",
.handler = &mg_bank_cmd,
.handler = mg_bank_cmd,
.mode = COMMAND_CONFIG,
.help = "configure a mflash device bank",
.usage = "<soc> <base> <RST pin> <target #>",
.usage = "soc_type base_addr pin_id target",
},
{
.name = "init",
.mode = COMMAND_CONFIG,
.handler = &handle_mflash_init_command,
.handler = handle_mflash_init_command,
.help = "initialize mflash devices",
},
COMMAND_REGISTRATION_DONE

View File

@@ -25,6 +25,7 @@ NAND_DRIVERS = \
s3c2412.c \
s3c2440.c \
s3c2443.c \
s3c6400.c \
at91sam9.c
noinst_HEADERS = \

View File

@@ -697,28 +697,30 @@ static const struct command_registration at91sam9_sub_command_handlers[] = {
.handler = handle_at91sam9_cle_command,
.mode = COMMAND_CONFIG,
.help = "set command latch enable address line (default is 22)",
.usage = "<device_id> <address_line>",
.usage = "bank_id address_line",
},
{
.name = "ale",
.handler = handle_at91sam9_ale_command,
.mode = COMMAND_CONFIG,
.help = "set address latch enable address line (default is 21)",
.usage = "<device_id> <address_line>",
.usage = "bank_id address_line",
},
{
.name = "rdy_busy",
.handler = handle_at91sam9_rdy_busy_command,
.mode = COMMAND_CONFIG,
.help = "set the input pin connected to RDY/~BUSY signal (no default)",
.usage = "<device_id> <base_pioc> <pin_num>",
.help = "set the GPIO input pin connected to "
"the RDY/~BUSY signal (no default)",
.usage = "bank_id pio_base_addr pin_num",
},
{
.name = "ce",
.handler = handle_at91sam9_ce_command,
.mode = COMMAND_CONFIG,
.help = "set the output pin connected to chip enable signal (no default)",
.usage = "<device_id> <base_pioc> <pin_num>",
.help = "set the GPIO output pin connected to "
"the chip enable signal (no default)",
.usage = "bank_id pio_base_addr pin_num",
},
COMMAND_REGISTRATION_DONE
};

View File

@@ -36,6 +36,7 @@ extern struct nand_flash_controller s3c2410_nand_controller;
extern struct nand_flash_controller s3c2412_nand_controller;
extern struct nand_flash_controller s3c2440_nand_controller;
extern struct nand_flash_controller s3c2443_nand_controller;
extern struct nand_flash_controller s3c6400_nand_controller;
extern struct nand_flash_controller imx31_nand_flash_controller;
extern struct nand_flash_controller at91sam9_nand_controller;
@@ -51,6 +52,7 @@ static struct nand_flash_controller *nand_flash_controllers[] =
&s3c2412_nand_controller,
&s3c2440_nand_controller,
&s3c2443_nand_controller,
&s3c6400_nand_controller,
&imx31_nand_flash_controller,
&at91sam9_nand_controller,
/* &boundary_scan_nand_controller, */

View File

@@ -500,9 +500,10 @@ static int lpc3180_write_page(struct nand_device *nand, uint32_t page, uint8_t *
return ERROR_NAND_OPERATION_NOT_SUPPORTED;
}
if (oob && (oob_size > 6))
if (oob && (oob_size > 24))
{
LOG_ERROR("LPC3180 MLC controller can't write more than 6 bytes of OOB data");
LOG_ERROR("LPC3180 MLC controller can't write more "
"than 6 bytes for each quarter's OOB data");
return ERROR_NAND_OPERATION_NOT_SUPPORTED;
}
@@ -559,10 +560,10 @@ static int lpc3180_write_page(struct nand_device *nand, uint32_t page, uint8_t *
data += thisrun_data_size;
}
memset(oob_buffer, 0xff, (nand->page_size == 512) ? 6 : 24);
memset(oob_buffer, 0xff, 6);
if (oob)
{
memcpy(page_buffer, oob, thisrun_oob_size);
memcpy(oob_buffer, oob, thisrun_oob_size);
oob_size -= thisrun_oob_size;
oob += thisrun_oob_size;
}
@@ -570,8 +571,10 @@ static int lpc3180_write_page(struct nand_device *nand, uint32_t page, uint8_t *
/* write MLC_ECC_ENC_REG to start encode cycle */
target_write_u32(target, 0x200b8008, 0x0);
target_write_memory(target, 0x200a8000, 4, 128, page_buffer + (quarter * 512));
target_write_memory(target, 0x200a8000, 1, 6, oob_buffer + (quarter * 6));
target_write_memory(target, 0x200a8000,
4, 128, page_buffer);
target_write_memory(target, 0x200a8000,
1, 6, oob_buffer);
/* write MLC_ECC_AUTO_ENC_REG to start auto encode */
target_write_u32(target, 0x200b8010, 0x0);
@@ -760,7 +763,6 @@ static int lpc3180_controller_ready(struct nand_device *nand, int timeout)
{
struct lpc3180_nand_controller *lpc3180_info = nand->controller_priv;
struct target *target = lpc3180_info->target;
uint8_t status = 0x0;
if (target->state != TARGET_HALTED)
{
@@ -768,20 +770,35 @@ static int lpc3180_controller_ready(struct nand_device *nand, int timeout)
return ERROR_NAND_OPERATION_FAILED;
}
LOG_DEBUG("lpc3180_controller_ready count start=%d", timeout);
do
{
if (lpc3180_info->selected_controller == LPC3180_MLC_CONTROLLER)
{
uint8_t status;
/* Read MLC_ISR, wait for controller to become ready */
target_read_u8(target, 0x200b8048, &status);
if (status & 2)
if (status & 2) {
LOG_DEBUG("lpc3180_controller_ready count=%d",
timeout);
return 1;
}
}
else if (lpc3180_info->selected_controller == LPC3180_SLC_CONTROLLER)
{
/* we pretend that the SLC controller is always ready */
return 1;
uint32_t status;
/* Read SLC_STAT and check READY bit */
target_read_u32(target, 0x20020018, &status);
if (status & 1) {
LOG_DEBUG("lpc3180_controller_ready count=%d",
timeout);
return 1;
}
}
alive_sleep(1);
@@ -801,6 +818,8 @@ static int lpc3180_nand_ready(struct nand_device *nand, int timeout)
return ERROR_NAND_OPERATION_FAILED;
}
LOG_DEBUG("lpc3180_nand_ready count start=%d", timeout);
do
{
if (lpc3180_info->selected_controller == LPC3180_MLC_CONTROLLER)
@@ -810,8 +829,11 @@ static int lpc3180_nand_ready(struct nand_device *nand, int timeout)
/* Read MLC_ISR, wait for NAND flash device to become ready */
target_read_u8(target, 0x200b8048, &status);
if (status & 1)
if (status & 1) {
LOG_DEBUG("lpc3180_nand_ready count end=%d",
timeout);
return 1;
}
}
else if (lpc3180_info->selected_controller == LPC3180_SLC_CONTROLLER)
{
@@ -820,8 +842,11 @@ static int lpc3180_nand_ready(struct nand_device *nand, int timeout)
/* Read SLC_STAT and check READY bit */
target_read_u32(target, 0x20020018, &status);
if (status & 1)
if (status & 1) {
LOG_DEBUG("lpc3180_nand_ready count end=%d",
timeout);
return 1;
}
}
alive_sleep(1);
@@ -844,7 +869,7 @@ COMMAND_HANDLER(handle_lpc3180_select_command)
}
unsigned num;
COMMAND_PARSE_NUMBER(uint, CMD_ARGV[1], num);
COMMAND_PARSE_NUMBER(uint, CMD_ARGV[0], num);
struct nand_device *nand = get_nand_device_by_num(num);
if (!nand)
{
@@ -878,10 +903,10 @@ COMMAND_HANDLER(handle_lpc3180_select_command)
static const struct command_registration lpc3180_exec_command_handlers[] = {
{
.name = "select",
.handler = &handle_lpc3180_select_command,
.handler = handle_lpc3180_select_command,
.mode = COMMAND_EXEC,
.help = "select <'mlc'|'slc'> controller (default is mlc)",
.usage = "<device_id> (mlc|slc)",
.help = "select MLC or SLC controller (default is MLC)",
.usage = "bank_id ['mlc'|'slc']",
},
COMMAND_REGISTRATION_DONE
};
@@ -896,17 +921,17 @@ static const struct command_registration lpc3180_command_handler[] = {
};
struct nand_flash_controller lpc3180_nand_controller = {
.name = "lpc3180",
.commands = lpc3180_command_handler,
.nand_device_command = lpc3180_nand_device_command,
.init = lpc3180_init,
.reset = lpc3180_reset,
.command = lpc3180_command,
.address = lpc3180_address,
.write_data = lpc3180_write_data,
.read_data = lpc3180_read_data,
.write_page = lpc3180_write_page,
.read_page = lpc3180_read_page,
.controller_ready = lpc3180_controller_ready,
.nand_ready = lpc3180_nand_ready,
};
.name = "lpc3180",
.commands = lpc3180_command_handler,
.nand_device_command = lpc3180_nand_device_command,
.init = lpc3180_init,
.reset = lpc3180_reset,
.command = lpc3180_command,
.address = lpc3180_address,
.write_data = lpc3180_write_data,
.read_data = lpc3180_read_data,
.write_page = lpc3180_write_page,
.read_page = lpc3180_read_page,
.controller_ready = lpc3180_controller_ready,
.nand_ready = lpc3180_nand_ready,
};

76
src/flash/nand/s3c6400.c Normal file
View File

@@ -0,0 +1,76 @@
/***************************************************************************
* Copyright (C) 2010 by Peter Korsgaard <jacmet@sunsite.dk> *
* Heavily based on s3c2412.c by Ben Dooks <ben@fluff.org> *
* *
* 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. *
***************************************************************************/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include "s3c24xx.h"
/* s3c64xx uses another base address for the nand controller than 24xx */
#undef S3C2410_NFREG
#define S3C2410_NFREG(x) ((x) + 0x70200000)
NAND_DEVICE_COMMAND_HANDLER(s3c6400_nand_device_command)
{
struct s3c24xx_nand_controller *info;
CALL_S3C24XX_DEVICE_COMMAND(nand, &info);
/* fill in the address fields for the core device */
info->cmd = S3C2440_NFCMD;
info->addr = S3C2440_NFADDR;
info->data = S3C2440_NFDATA;
info->nfstat = S3C2412_NFSTAT;
return ERROR_OK;
}
static int s3c6400_init(struct nand_device *nand)
{
struct s3c24xx_nand_controller *s3c24xx_info = nand->controller_priv;
struct target *target = s3c24xx_info->target;
target_write_u32(target, S3C2410_NFCONF,
S3C2440_NFCONF_TACLS(3) |
S3C2440_NFCONF_TWRPH0(7) |
S3C2440_NFCONF_TWRPH1(7) | 4);
target_write_u32(target, S3C2440_NFCONT,
S3C2412_NFCONT_INIT_MAIN_ECC |
S3C2440_NFCONT_ENABLE);
return ERROR_OK;
}
struct nand_flash_controller s3c6400_nand_controller = {
.name = "s3c6400",
.nand_device_command = &s3c6400_nand_device_command,
.init = &s3c6400_init,
.reset = &s3c24xx_reset,
.command = &s3c24xx_command,
.address = &s3c24xx_address,
.write_data = &s3c24xx_write_data,
.read_data = &s3c24xx_read_data,
.write_page = s3c24xx_write_page,
.read_page = s3c24xx_read_page,
.write_block_data = &s3c2440_write_block_data,
.read_block_data = &s3c2440_read_block_data,
.controller_ready = &s3c24xx_controller_ready,
.nand_ready = &s3c2440_nand_ready,
};

View File

@@ -409,8 +409,8 @@ COMMAND_HANDLER(handle_nand_dump_command)
if (nand_fileio_finish(&s) == ERROR_OK)
{
command_print(CMD_CTX, "dumped %zu bytes in %fs (%0.3f kb/s)",
s.fileio.size, duration_elapsed(&s.bench),
command_print(CMD_CTX, "dumped %ld bytes in %fs (%0.3f kb/s)",
(long)s.fileio.size, duration_elapsed(&s.bench),
duration_kbps(&s.bench, s.fileio.size));
}
return ERROR_OK;
@@ -446,68 +446,67 @@ COMMAND_HANDLER(handle_nand_raw_access_command)
static const struct command_registration nand_exec_command_handlers[] = {
{
.name = "list",
.handler = &handle_nand_list_command,
.handler = handle_nand_list_command,
.mode = COMMAND_EXEC,
.help = "list configured NAND flash devices",
},
{
.name = "info",
.handler = &handle_nand_info_command,
.handler = handle_nand_info_command,
.mode = COMMAND_EXEC,
.usage = "<bank>",
.help = "print info about a NAND flash device",
.usage = "[banknum | first_bank_num last_bank_num]",
.help = "print info about one or more NAND flash devices",
},
{
.name = "probe",
.handler = &handle_nand_probe_command,
.handler = handle_nand_probe_command,
.mode = COMMAND_EXEC,
.usage = "<bank>",
.help = "identify NAND flash device <num>",
.usage = "bank_id",
.help = "identify NAND flash device",
},
{
.name = "check_bad_blocks",
.handler = &handle_nand_check_bad_blocks_command,
.handler = handle_nand_check_bad_blocks_command,
.mode = COMMAND_EXEC,
.usage = "<bank> [<offset> <length>]",
.help = "check NAND flash device <num> for bad blocks",
.usage = "bank_id [offset length]",
.help = "check all or part of NAND flash device for bad blocks",
},
{
.name = "erase",
.handler = &handle_nand_erase_command,
.handler = handle_nand_erase_command,
.mode = COMMAND_EXEC,
.usage = "<bank> [<offset> <length>]",
.help = "erase blocks on NAND flash device",
.usage = "bank_id [offset length]",
.help = "erase all or subset of blocks on NAND flash device",
},
{
.name = "dump",
.handler = &handle_nand_dump_command,
.handler = handle_nand_dump_command,
.mode = COMMAND_EXEC,
.usage = "<bank> <filename> <offset> <length> "
"[oob_raw | oob_only]",
.usage = "bank_id filename offset length "
"['oob_raw'|'oob_only']",
.help = "dump from NAND flash device",
},
{
.name = "verify",
.handler = &handle_nand_verify_command,
.handler = handle_nand_verify_command,
.mode = COMMAND_EXEC,
.usage = "<bank> <filename> <offset> "
"[oob_raw | oob_only | oob_softecc | oob_softecc_kw]",
.usage = "bank_id filename offset "
"['oob_raw'|'oob_only'|'oob_softecc'|'oob_softecc_kw']",
.help = "verify NAND flash device",
},
{
.name = "write",
.handler = &handle_nand_write_command,
.handler = handle_nand_write_command,
.mode = COMMAND_EXEC,
.usage = "<bank> <filename> <offset> "
"[oob_raw | oob_only | oob_softecc | oob_softecc_kw]",
.usage = "bank_id filename offset "
"['oob_raw'|'oob_only'|'oob_softecc'|'oob_softecc_kw']",
.help = "write to NAND flash device",
},
{
.name = "raw_access",
.handler = &handle_nand_raw_access_command,
.handler = handle_nand_raw_access_command,
.mode = COMMAND_EXEC,
.usage = "<num> ['enable'|'disable']",
.usage = "bank_id ['enable'|'disable']",
.help = "raw access to NAND flash device",
},
COMMAND_REGISTRATION_DONE
@@ -614,6 +613,7 @@ static const struct command_registration nand_config_command_handlers[] = {
.handler = &handle_nand_device_command,
.mode = COMMAND_CONFIG,
.help = "defines a new NAND bank",
.usage = "bank_id driver target [driver_options ...]",
},
{
.name = "drivers",

View File

@@ -412,14 +412,14 @@ static int aduc702x_check_flash_completion(struct target* target, unsigned int t
}
struct flash_driver aduc702x_flash = {
.name = "aduc702x",
.flash_bank_command = &aduc702x_flash_bank_command,
.erase = &aduc702x_erase,
.protect = &aduc702x_protect,
.write = &aduc702x_write,
.probe = &aduc702x_probe,
.auto_probe = &aduc702x_probe,
.erase_check = &default_flash_blank_check,
.protect_check = &aduc702x_protect_check,
.info = &aduc702x_info
};
.name = "aduc702x",
.flash_bank_command = aduc702x_flash_bank_command,
.erase = aduc702x_erase,
.protect = aduc702x_protect,
.write = aduc702x_write,
.probe = aduc702x_probe,
.auto_probe = aduc702x_probe,
.erase_check = default_flash_blank_check,
.protect_check = aduc702x_protect_check,
.info = aduc702x_info
};

View File

@@ -2288,7 +2288,7 @@ COMMAND_HANDLER(sam3_handle_info_command)
return ERROR_FAIL;
}
}
// above garentees the "chip details" structure is valid
// above guarantees the "chip details" structure is valid
// and thus, bank private areas are valid
// and we have a SAM3 chip, what a concept!
@@ -2386,7 +2386,7 @@ COMMAND_HANDLER(sam3_handle_gpnvm_command)
if (0 == strcmp("show", CMD_ARGV[0])) {
if (who == -1) {
showall:
showall:
r = ERROR_OK;
for (x = 0 ; x < pChip->details.n_gpnvms ; x++) {
r = FLASHD_GetGPNVM(&(pChip->details.bank[0]), x, &v);
@@ -2466,24 +2466,27 @@ COMMAND_HANDLER(sam3_handle_slowclk_command)
static const struct command_registration at91sam3_exec_command_handlers[] = {
{
.name = "gpnvm",
.handler = &sam3_handle_gpnvm_command,
.handler = sam3_handle_gpnvm_command,
.mode = COMMAND_EXEC,
.usage = "[(set|clear) [<bit_id>]]",
.help = "Without arguments, shows the gpnvm register; "
"otherwise, sets or clear the specified bit.",
.usage = "[('clr'|'set'|'show') bitnum]",
.help = "Without arguments, shows all bits in the gpnvm "
"register. Otherwise, clears, sets, or shows one "
"General Purpose Non-Volatile Memory (gpnvm) bit.",
},
{
.name = "info",
.handler = &sam3_handle_info_command,
.handler = sam3_handle_info_command,
.mode = COMMAND_EXEC,
.help = "print information about the current sam3 chip",
.help = "Print information about the current at91sam3 chip"
"and its flash configuration.",
},
{
.name = "slowclk",
.handler = &sam3_handle_slowclk_command,
.handler = sam3_handle_slowclk_command,
.mode = COMMAND_EXEC,
.usage = "<value>",
.help = "set the slowclock frequency (default 32768hz)",
.usage = "[clock_hz]",
.help = "Display or set the slowclock frequency "
"(default 32768 Hz).",
},
COMMAND_REGISTRATION_DONE
};
@@ -2498,15 +2501,15 @@ static const struct command_registration at91sam3_command_handlers[] = {
};
struct flash_driver at91sam3_flash = {
.name = "at91sam3",
.commands = at91sam3_command_handlers,
.flash_bank_command = &sam3_flash_bank_command,
.erase = &sam3_erase,
.protect = &sam3_protect,
.write = &sam3_write,
.probe = &sam3_probe,
.auto_probe = &sam3_auto_probe,
.erase_check = &sam3_erase_check,
.protect_check = &sam3_protect_check,
.info = &sam3_info,
};
.name = "at91sam3",
.commands = at91sam3_command_handlers,
.flash_bank_command = sam3_flash_bank_command,
.erase = sam3_erase,
.protect = sam3_protect,
.write = sam3_write,
.probe = sam3_probe,
.auto_probe = sam3_auto_probe,
.erase_check = sam3_erase_check,
.protect_check = sam3_protect_check,
.info = sam3_info,
};

View File

@@ -1182,10 +1182,11 @@ COMMAND_HANDLER(at91sam7_handle_gpnvm_command)
static const struct command_registration at91sam7_exec_command_handlers[] = {
{
.name = "gpnvm",
.handler = &at91sam7_handle_gpnvm_command,
.handler = at91sam7_handle_gpnvm_command,
.mode = COMMAND_EXEC,
.usage = "gpnvm <bit> set | clear, "
"set or clear one gpnvm bit",
.help = "set or clear one General Purpose Non-Volatile Memory "
"(gpnvm) bit",
.usage = "bitnum ('set'|'clear')",
},
COMMAND_REGISTRATION_DONE
};
@@ -1200,15 +1201,15 @@ static const struct command_registration at91sam7_command_handlers[] = {
};
struct flash_driver at91sam7_flash = {
.name = "at91sam7",
.commands = at91sam7_command_handlers,
.flash_bank_command = &at91sam7_flash_bank_command,
.erase = &at91sam7_erase,
.protect = &at91sam7_protect,
.write = &at91sam7_write,
.probe = &at91sam7_probe,
.auto_probe = &at91sam7_probe,
.erase_check = &at91sam7_erase_check,
.protect_check = &at91sam7_protect_check,
.info = &at91sam7_info,
};
.name = "at91sam7",
.commands = at91sam7_command_handlers,
.flash_bank_command = at91sam7_flash_bank_command,
.erase = at91sam7_erase,
.protect = at91sam7_protect,
.write = at91sam7_write,
.probe = at91sam7_probe,
.auto_probe = at91sam7_probe,
.erase_check = at91sam7_erase_check,
.protect_check = at91sam7_protect_check,
.info = at91sam7_info,
};

View File

@@ -452,7 +452,7 @@ COMMAND_HANDLER(avrf_handle_mass_erase_command)
static const struct command_registration avrf_exec_command_handlers[] = {
{
.name = "mass_erase",
.handler = &avrf_handle_mass_erase_command,
.handler = avrf_handle_mass_erase_command,
.mode = COMMAND_EXEC,
.help = "erase entire device",
},
@@ -469,15 +469,15 @@ static const struct command_registration avrf_command_handlers[] = {
};
struct flash_driver avr_flash = {
.name = "avr",
.commands = avrf_command_handlers,
.flash_bank_command = &avrf_flash_bank_command,
.erase = &avrf_erase,
.protect = &avrf_protect,
.write = &avrf_write,
.probe = &avrf_probe,
.auto_probe = &avrf_auto_probe,
.erase_check = &default_flash_mem_blank_check,
.protect_check = &avrf_protect_check,
.info = &avrf_info,
};
.name = "avr",
.commands = avrf_command_handlers,
.flash_bank_command = avrf_flash_bank_command,
.erase = avrf_erase,
.protect = avrf_protect,
.write = avrf_write,
.probe = avrf_probe,
.auto_probe = avrf_auto_probe,
.erase_check = default_flash_mem_blank_check,
.protect_check = avrf_protect_check,
.info = avrf_info,
};

View File

@@ -2618,14 +2618,14 @@ static int cfi_info(struct flash_bank *bank, char *buf, int buf_size)
}
struct flash_driver cfi_flash = {
.name = "cfi",
.flash_bank_command = &cfi_flash_bank_command,
.erase = &cfi_erase,
.protect = &cfi_protect,
.write = &cfi_write,
.probe = &cfi_probe,
.auto_probe = &cfi_auto_probe,
.erase_check = &default_flash_blank_check,
.protect_check = &cfi_protect_check,
.info = &cfi_info,
};
.name = "cfi",
.flash_bank_command = cfi_flash_bank_command,
.erase = cfi_erase,
.protect = cfi_protect,
.write = cfi_write,
.probe = cfi_probe,
.auto_probe = cfi_auto_probe,
.erase_check = default_flash_blank_check,
.protect_check = cfi_protect_check,
.info = cfi_info,
};

View File

@@ -29,6 +29,13 @@
#include <target/image.h>
/**
* @file
* Upper level of NOR flash framework.
* The lower level interfaces are to drivers. These upper level ones
* primarily support access from Tcl scripts or from GDB.
*/
struct flash_bank *flash_banks;
int flash_driver_erase(struct flash_bank *bank, int first, int last)
@@ -280,9 +287,22 @@ int default_flash_blank_check(struct flash_bank *bank)
return ERROR_OK;
}
/* erase given flash region, selects proper bank according to target and address */
/* Manipulate given flash region, selecting the bank according to target
* and address. Maps an address range to a set of sectors, and issues
* the callback() on that set ... e.g. to erase or unprotect its members.
*
* (Note a current bad assumption: that protection operates on the same
* size sectors as erase operations use.)
*
* The "pad_reason" parameter is a kind of boolean: when it's NULL, the
* range must fit those sectors exactly. This is clearly safe; it can't
* erase data which the caller said to leave alone, for example. If it's
* non-NULL, rather than failing, extra data in the first and/or last
* sectors will be added to the range, and that reason string is used when
* warning about those additions.
*/
static int flash_iterate_address_range(struct target *target,
uint32_t addr, uint32_t length,
char *pad_reason, uint32_t addr, uint32_t length,
int (*callback)(struct flash_bank *bank, int first, int last))
{
struct flash_bank *c;
@@ -304,34 +324,76 @@ static int flash_iterate_address_range(struct target *target,
{
/* special case, erase whole bank when length is zero */
if (addr != c->base)
{
LOG_ERROR("Whole bank access must start at beginning of bank.");
return ERROR_FLASH_DST_BREAKS_ALIGNMENT;
}
return callback(c, 0, c->num_sectors - 1);
}
/* check whether it all fits in this bank */
if (addr + length - 1 > c->base + c->size - 1)
{
LOG_ERROR("Flash access does not fit into bank.");
return ERROR_FLASH_DST_BREAKS_ALIGNMENT;
}
/** @todo: handle erasures that cross into adjacent banks */
addr -= c->base;
last_addr -= c->base;
for (i = 0; i < c->num_sectors; i++)
{
struct flash_sector *f = c->sectors + i;
uint32_t end = f->offset + f->size;
/* start only on a sector boundary */
if (first < 0) {
/* scanned past the first sector? */
if (addr < f->offset)
break;
/* is this the first sector? */
if (addr == f->offset)
first = i;
else if (addr < f->offset)
break;
/* Does this need head-padding? If so, pad and warn;
* or else force an error.
*
* Such padding can make trouble, since *WE* can't
* ever know if that data was in use. The warning
* should help users sort out messes later.
*/
else if (addr < end && pad_reason) {
/* FIXME say how many bytes (e.g. 80 KB) */
LOG_WARNING("Adding extra %s range, "
"%#8.8x to %#8.8x",
pad_reason,
(unsigned) f->offset,
(unsigned) addr - 1);
first = i;
} else
continue;
}
/* is this (also?) the last sector? */
if (last_addr == f->offset + f->size) {
if (last_addr == end) {
last = i;
break;
}
/* Does this need tail-padding? If so, pad and warn;
* or else force an error.
*/
if (last_addr < end && pad_reason) {
/* FIXME say how many bytes (e.g. 80 KB) */
LOG_WARNING("Adding extra %s range, "
"%#8.8x to %#8.8x",
pad_reason,
(unsigned) last_addr,
(unsigned) end - 1);
last = i;
break;
}
@@ -346,22 +408,21 @@ static int flash_iterate_address_range(struct target *target,
LOG_ERROR("address range 0x%8.8x .. 0x%8.8x "
"is not sector-aligned",
(unsigned) (c->base + addr),
(unsigned) (last_addr - 1));
(unsigned) (c->base + last_addr - 1));
return ERROR_FLASH_DST_BREAKS_ALIGNMENT;
}
/* The NOR driver may trim this range down, based on
* whether or not a given sector is already erased.
*
* REVISIT should *we* trim it... ?
/* The NOR driver may trim this range down, based on what
* sectors are already erased/unprotected. GDB currently
* blocks such optimizations.
*/
return callback(c, first, last);
}
int flash_erase_address_range(struct target *target,
uint32_t addr, uint32_t length)
bool pad, uint32_t addr, uint32_t length)
{
return flash_iterate_address_range(target,
return flash_iterate_address_range(target, pad ? "erase" : NULL,
addr, length, &flash_driver_erase);
}
@@ -372,7 +433,11 @@ static int flash_driver_unprotect(struct flash_bank *bank, int first, int last)
static int flash_unlock_address_range(struct target *target, uint32_t addr, uint32_t length)
{
return flash_iterate_address_range(target,
/* By default, pad to sector boundaries ... the real issue here
* is that our (only) caller *permanently* removes protection,
* and doesn't restore it.
*/
return flash_iterate_address_range(target, "unprotect",
addr, length, &flash_driver_unprotect);
}
@@ -386,6 +451,12 @@ int flash_write_unlock(struct target *target, struct image *image,
struct flash_bank *c;
int *padding;
/* REVISIT do_pad should perhaps just be another parameter.
* GDB wouldn't ever need it, since it erases separately.
* But "flash write_image" commands might want that option.
*/
bool do_pad = false;
section = 0;
section_offset = 0;
@@ -401,7 +472,7 @@ int flash_write_unlock(struct target *target, struct image *image,
}
/* allocate padding array */
padding = malloc(image->num_sections * sizeof(padding));
padding = calloc(image->num_sections, sizeof(*padding));
/* loop until we reach end of the image */
while (section < image->num_sections)
@@ -439,10 +510,31 @@ int flash_write_unlock(struct target *target, struct image *image,
{
if (image->sections[section_last + 1].base_address < (run_address + run_size))
{
LOG_DEBUG("section %d out of order(very slightly surprising, but supported)", section_last + 1);
LOG_DEBUG("section %d out of order "
"(surprising, but supported)",
section_last + 1);
/* REVISIT this can break with autoerase ...
* clobbering data after it's written.
*/
break;
}
/* if we have multiple sections within our image, flash programming could fail due to alignment issues
/* FIXME This needlessly touches sectors BETWEEN the
* sections it's writing. Without auto erase, it just
* writes ones. That WILL INVALIDATE data in cases
* like Stellaris Tempest chips, corrupting internal
* ECC codes; and at least FreeScale suggests issues
* with that approach (in HC11 documentation).
*
* With auto erase enabled, data in those sectors will
* be needlessly destroyed; and some of the limited
* number of flash erase cycles will be wasted...
*
* In both cases, the extra writes slow things down.
*/
/* if we have multiple sections within our image,
* flash programming could fail due to alignment issues
* attempt to rebuild a consecutive buffer for the flash loader */
pad_bytes = (image->sections[section_last + 1].base_address) - (run_address + run_size);
if ((run_address + run_size + pad_bytes) > (c->base + c->size))
@@ -450,7 +542,6 @@ int flash_write_unlock(struct target *target, struct image *image,
padding[section_last] = pad_bytes;
run_size += image->sections[++section_last].size;
run_size += pad_bytes;
padding[section_last] = 0;
LOG_INFO("Padding image section %d with %d bytes", section_last-1, pad_bytes);
}
@@ -458,11 +549,35 @@ int flash_write_unlock(struct target *target, struct image *image,
/* fit the run into bank constraints */
if (run_address + run_size - 1 > c->base + c->size - 1)
{
/* REVISIT isn't this superfluous, given the while()
* loop conditions above??
*/
LOG_WARNING("writing %d bytes only - as image section is %d bytes and bank is only %d bytes", \
(int)(c->base + c->size - run_address), (int)(run_size), (int)(c->size));
run_size = c->base + c->size - run_address;
}
/* If we're applying any sector automagic, then pad this
* (maybe-combined) segment to the end of its last sector.
*/
if (unlock || erase) {
int sector;
uint32_t offset_start = run_address - c->base;
uint32_t offset_end = offset_start + run_size;
uint32_t end = offset_end, delta;
for (sector = 0; sector < c->num_sectors; sector++) {
end = c->sectors[sector].offset
+ c->sectors[sector].size;
if (offset_end <= end)
break;
}
delta = end - offset_end;
padding[section_last] += delta;
run_size += delta;
}
/* allocate buffer */
buffer = malloc(run_size);
buffer_size = 0;
@@ -509,7 +624,8 @@ int flash_write_unlock(struct target *target, struct image *image,
if (erase)
{
/* calculate and erase sectors */
retval = flash_erase_address_range(target, run_address, run_size);
retval = flash_erase_address_range(target,
do_pad, run_address, run_size);
}
}

View File

@@ -24,6 +24,11 @@
#include <flash/common.h>
/**
* @file
* Upper level NOR flash interfaces.
*/
struct image;
#define FLASH_MAX_ERROR_STR (128)
@@ -97,10 +102,14 @@ int flash_init_drivers(struct command_context *cmd_ctx);
/**
* Erases @a length bytes in the @a target flash, starting at @a addr.
* The range @a addr to @a addr + @a length - 1 must be strictly
* sector aligned, unless @a pad is true. Setting @a pad true extends
* the range, at beginning and/or end, if needed for sector alignment.
* @returns ERROR_OK if successful; otherwise, an error code.
*/
int flash_erase_address_range(struct target *target,
uint32_t addr, uint32_t length);
bool pad, uint32_t addr, uint32_t length);
/**
* Writes @a image into the @a target flash. The @a written parameter
* will contain the

View File

@@ -431,14 +431,14 @@ static int ecosflash_handle_gpnvm_command(struct command_context *cmd_ctx, char
#endif
struct flash_driver ecosflash_flash = {
.name = "ecosflash",
.flash_bank_command = &ecosflash_flash_bank_command,
.erase = &ecosflash_erase,
.protect = &ecosflash_protect,
.write = &ecosflash_write,
.probe = &ecosflash_probe,
.auto_probe = &ecosflash_probe,
.erase_check = &default_flash_blank_check,
.protect_check = &ecosflash_protect_check,
.info = &ecosflash_info
};
.name = "ecosflash",
.flash_bank_command = ecosflash_flash_bank_command,
.erase = ecosflash_erase,
.protect = ecosflash_protect,
.write = ecosflash_write,
.probe = ecosflash_probe,
.auto_probe = ecosflash_probe,
.erase_check = default_flash_blank_check,
.protect_check = ecosflash_protect_check,
.info = ecosflash_info
};

View File

@@ -135,15 +135,15 @@ static const struct command_registration faux_command_handlers[] = {
};
struct flash_driver faux_flash = {
.name = "faux",
.commands = faux_command_handlers,
.flash_bank_command = &faux_flash_bank_command,
.erase = &faux_erase,
.protect = &faux_protect,
.write = &faux_write,
.probe = &faux_probe,
.auto_probe = &faux_probe,
.erase_check = &default_flash_blank_check,
.protect_check = &faux_protect_check,
.info = &faux_info
};
.name = "faux",
.commands = faux_command_handlers,
.flash_bank_command = faux_flash_bank_command,
.erase = faux_erase,
.protect = faux_protect,
.write = faux_write,
.probe = faux_probe,
.auto_probe = faux_probe,
.erase_check = default_flash_blank_check,
.protect_check = faux_protect_check,
.info = faux_info
};

View File

@@ -783,7 +783,7 @@ COMMAND_HANDLER(lpc2000_handle_part_id_command)
static const struct command_registration lpc2000_exec_command_handlers[] = {
{
.name = "part_id",
.handler = &lpc2000_handle_part_id_command,
.handler = lpc2000_handle_part_id_command,
.mode = COMMAND_EXEC,
.help = "print part id of lpc2000 flash bank <num>",
},
@@ -800,17 +800,15 @@ static const struct command_registration lpc2000_command_handlers[] = {
};
struct flash_driver lpc2000_flash = {
.name = "lpc2000",
.commands = lpc2000_command_handlers,
.flash_bank_command = &lpc2000_flash_bank_command,
.erase = &lpc2000_erase,
.protect = &lpc2000_protect,
.write = &lpc2000_write,
.probe = &lpc2000_probe,
.auto_probe = &lpc2000_probe,
.erase_check = &lpc2000_erase_check,
.protect_check = &lpc2000_protect_check,
.info = &lpc2000_info,
};
.name = "lpc2000",
.commands = lpc2000_command_handlers,
.flash_bank_command = lpc2000_flash_bank_command,
.erase = lpc2000_erase,
.protect = lpc2000_protect,
.write = lpc2000_write,
.probe = lpc2000_probe,
.auto_probe = lpc2000_probe,
.erase_check = lpc2000_erase_check,
.protect_check = lpc2000_protect_check,
.info = lpc2000_info,
};

View File

@@ -473,14 +473,14 @@ static int lpc288x_protect(struct flash_bank *bank, int set, int first, int last
}
struct flash_driver lpc288x_flash = {
.name = "lpc288x",
.flash_bank_command = &lpc288x_flash_bank_command,
.erase = &lpc288x_erase,
.protect = &lpc288x_protect,
.write = &lpc288x_write,
.probe = &lpc288x_probe,
.auto_probe = &lpc288x_probe,
.erase_check = &lpc288x_erase_check,
.protect_check = &lpc288x_protect_check,
.info = &lpc288x_info,
};
.name = "lpc288x",
.flash_bank_command = lpc288x_flash_bank_command,
.erase = lpc288x_erase,
.protect = lpc288x_protect,
.write = lpc288x_write,
.probe = lpc288x_probe,
.auto_probe = lpc288x_probe,
.erase_check = lpc288x_erase_check,
.protect_check = lpc288x_protect_check,
.info = lpc288x_info,
};

View File

@@ -951,45 +951,49 @@ COMMAND_HANDLER(lpc2900_handle_secure_jtag_command)
static const struct command_registration lpc2900_exec_command_handlers[] = {
{
.name = "signature",
.handler = &lpc2900_handle_signature_command,
.handler = lpc2900_handle_signature_command,
.mode = COMMAND_EXEC,
.usage = "<bank>",
.help = "print device signature of flash bank",
.usage = "bank_id",
.help = "Calculate and display signature of flash bank.",
},
{
.name = "read_custom",
.handler = &lpc2900_handle_read_custom_command,
.handler = lpc2900_handle_read_custom_command,
.mode = COMMAND_EXEC,
.usage = "<bank> <filename>",
.help = "read customer information from index sector to file",
.usage = "bank_id filename",
.help = "Copies 912 bytes of customer information "
"from index sector into file.",
},
{
.name = "password",
.handler = &lpc2900_handle_password_command,
.handler = lpc2900_handle_password_command,
.mode = COMMAND_EXEC,
.usage = "<bank> <password>",
.help = "enter password to enable 'dangerous' options",
.usage = "bank_id password",
.help = "Enter fixed password to enable 'dangerous' options.",
},
{
.name = "write_custom",
.handler = &lpc2900_handle_write_custom_command,
.handler = lpc2900_handle_write_custom_command,
.mode = COMMAND_EXEC,
.usage = "<bank> <filename> [<type>]",
.help = "write customer info from file to index sector",
.usage = "bank_id filename ('bin'|'ihex'|'elf'|'s19')",
.help = "Copies 912 bytes of customer info from file "
"to index sector.",
},
{
.name = "secure_sector",
.handler = &lpc2900_handle_secure_sector_command,
.handler = lpc2900_handle_secure_sector_command,
.mode = COMMAND_EXEC,
.usage = "<bank> <first> <last>",
.help = "activate sector security for a range of sectors",
.usage = "bank_id first_sector last_sector",
.help = "Activate sector security for a range of sectors. "
"It will be effective after a power cycle.",
},
{
.name = "secure_jtag",
.handler = &lpc2900_handle_secure_jtag_command,
.handler = lpc2900_handle_secure_jtag_command,
.mode = COMMAND_EXEC,
.usage = "<bank> <level>",
.help = "activate JTAG security",
.usage = "bank_id",
.help = "Disable the JTAG port. "
"It will be effective after a power cycle.",
},
COMMAND_REGISTRATION_DONE
};

View File

@@ -348,14 +348,14 @@ static int ocl_auto_probe(struct flash_bank *bank)
}
struct flash_driver ocl_flash = {
.name = "ocl",
.flash_bank_command = &ocl_flash_bank_command,
.erase = &ocl_erase,
.protect = &ocl_protect,
.write = &ocl_write,
.probe = &ocl_probe,
.erase_check = &ocl_erase_check,
.protect_check = &ocl_protect_check,
.info = &ocl_info,
.auto_probe = &ocl_auto_probe,
};
.name = "ocl",
.flash_bank_command = ocl_flash_bank_command,
.erase = ocl_erase,
.protect = ocl_protect,
.write = ocl_write,
.probe = ocl_probe,
.erase_check = ocl_erase_check,
.protect_check = ocl_protect_check,
.info = ocl_info,
.auto_probe = ocl_auto_probe,
};

View File

@@ -886,13 +886,13 @@ COMMAND_HANDLER(pic32mx_handle_pgm_word_command)
static const struct command_registration pic32mx_exec_command_handlers[] = {
{
.name = "chip_erase",
.handler = &pic32mx_handle_chip_erase_command,
.handler = pic32mx_handle_chip_erase_command,
.mode = COMMAND_EXEC,
.help = "erase device",
},
{
.name = "pgm_word",
.handler = &pic32mx_handle_pgm_word_command,
.handler = pic32mx_handle_pgm_word_command,
.mode = COMMAND_EXEC,
.help = "program a word",
},
@@ -909,15 +909,15 @@ static const struct command_registration pic32mx_command_handlers[] = {
};
struct flash_driver pic32mx_flash = {
.name = "pic32mx",
.commands = pic32mx_command_handlers,
.flash_bank_command = &pic32mx_flash_bank_command,
.erase = &pic32mx_erase,
.protect = &pic32mx_protect,
.write = &pic32mx_write,
.probe = &pic32mx_probe,
.auto_probe = &pic32mx_auto_probe,
.erase_check = &default_flash_mem_blank_check,
.protect_check = &pic32mx_protect_check,
.info = &pic32mx_info,
};
.name = "pic32mx",
.commands = pic32mx_command_handlers,
.flash_bank_command = pic32mx_flash_bank_command,
.erase = pic32mx_erase,
.protect = pic32mx_protect,
.write = pic32mx_write,
.probe = pic32mx_probe,
.auto_probe = pic32mx_auto_probe,
.erase_check = default_flash_mem_blank_check,
.protect_check = pic32mx_protect_check,
.info = pic32mx_info,
};

View File

@@ -1173,7 +1173,7 @@ COMMAND_HANDLER(stellaris_handle_mass_erase_command)
static const struct command_registration stellaris_exec_command_handlers[] = {
{
.name = "mass_erase",
.handler = &stellaris_handle_mass_erase_command,
.handler = stellaris_handle_mass_erase_command,
.mode = COMMAND_EXEC,
.help = "erase entire device",
},
@@ -1182,7 +1182,7 @@ static const struct command_registration stellaris_exec_command_handlers[] = {
static const struct command_registration stellaris_command_handlers[] = {
{
.name = "stellaris",
.mode = COMMAND_ANY,
.mode = COMMAND_EXEC,
.help = "Stellaris flash command group",
.chain = stellaris_exec_command_handlers,
},

View File

@@ -978,7 +978,9 @@ COMMAND_HANDLER(stm32x_handle_unlock_command)
return ERROR_OK;
}
command_print(CMD_CTX, "stm32x unlocked");
command_print(CMD_CTX, "stm32x unlocked.\n"
"INFO: a reset or power cycle is required "
"for the new settings to take effect.");
return ERROR_OK;
}
@@ -1066,29 +1068,36 @@ COMMAND_HANDLER(stm32x_handle_options_write_command)
return ERROR_TARGET_NOT_HALTED;
}
/* REVISIT: ignores some options which we will display...
* and doesn't insist on the specified syntax.
*/
/* OPT_RDWDGSW */
if (strcmp(CMD_ARGV[1], "SWWDG") == 0)
{
optionbyte |= (1 << 0);
}
else
else /* REVISIT must be "HWWDG" then ... */
{
optionbyte &= ~(1 << 0);
}
/* OPT_RDRSTSTDBY */
if (strcmp(CMD_ARGV[2], "NORSTSTNDBY") == 0)
{
optionbyte |= (1 << 1);
}
else
else /* REVISIT must be "RSTSTNDBY" then ... */
{
optionbyte &= ~(1 << 1);
}
/* OPT_RDRSTSTOP */
if (strcmp(CMD_ARGV[3], "NORSTSTOP") == 0)
{
optionbyte |= (1 << 2);
}
else
else /* REVISIT must be "RSTSTOP" then ... */
{
optionbyte &= ~(1 << 2);
}
@@ -1107,7 +1116,9 @@ COMMAND_HANDLER(stm32x_handle_options_write_command)
return ERROR_OK;
}
command_print(CMD_CTX, "stm32x write options complete");
command_print(CMD_CTX, "stm32x write options complete.\n"
"INFO: a reset or power cycle is required "
"for the new settings to take effect.");
return ERROR_OK;
}
@@ -1186,33 +1197,40 @@ COMMAND_HANDLER(stm32x_handle_mass_erase_command)
static const struct command_registration stm32x_exec_command_handlers[] = {
{
.name = "lock",
.handler = &stm32x_handle_lock_command,
.handler = stm32x_handle_lock_command,
.mode = COMMAND_EXEC,
.help = "lock device",
.usage = "bank_id",
.help = "Lock entire flash device.",
},
{
.name = "unlock",
.handler = &stm32x_handle_unlock_command,
.handler = stm32x_handle_unlock_command,
.mode = COMMAND_EXEC,
.help = "unlock protected device",
.usage = "bank_id",
.help = "Unlock entire protected flash device.",
},
{
.name = "mass_erase",
.handler = &stm32x_handle_mass_erase_command,
.handler = stm32x_handle_mass_erase_command,
.mode = COMMAND_EXEC,
.help = "mass erase device",
.usage = "bank_id",
.help = "Erase entire flash device.",
},
{
.name = "options_read",
.handler = &stm32x_handle_options_read_command,
.handler = stm32x_handle_options_read_command,
.mode = COMMAND_EXEC,
.help = "read device option bytes",
.usage = "bank_id",
.help = "Read and display device option byte.",
},
{
.name = "options_write",
.handler = &stm32x_handle_options_write_command,
.handler = stm32x_handle_options_write_command,
.mode = COMMAND_EXEC,
.help = "write device option bytes",
.usage = "bank_id ('SWWDG'|'HWWDG') "
"('RSTSTNDBY'|'NORSTSTNDBY') "
"('RSTSTOP'|'NORSTSTOP')",
.help = "Replace bits in device option byte.",
},
COMMAND_REGISTRATION_DONE
};
@@ -1227,15 +1245,15 @@ static const struct command_registration stm32x_command_handlers[] = {
};
struct flash_driver stm32x_flash = {
.name = "stm32x",
.commands = stm32x_command_handlers,
.flash_bank_command = &stm32x_flash_bank_command,
.erase = &stm32x_erase,
.protect = &stm32x_protect,
.write = &stm32x_write,
.probe = &stm32x_probe,
.auto_probe = &stm32x_auto_probe,
.erase_check = &default_flash_mem_blank_check,
.protect_check = &stm32x_protect_check,
.info = &stm32x_info,
};
.name = "stm32x",
.commands = stm32x_command_handlers,
.flash_bank_command = stm32x_flash_bank_command,
.erase = stm32x_erase,
.protect = stm32x_protect,
.write = stm32x_write,
.probe = stm32x_probe,
.auto_probe = stm32x_auto_probe,
.erase_check = default_flash_mem_blank_check,
.protect_check = stm32x_protect_check,
.info = stm32x_info,
};

View File

@@ -93,7 +93,10 @@ static int str7x_build_block_list(struct flash_bank *bank)
bank->sectors[num_sectors].offset = mem_layout_str7bank0[i].sector_start;
bank->sectors[num_sectors].size = mem_layout_str7bank0[i].sector_size;
bank->sectors[num_sectors].is_erased = -1;
bank->sectors[num_sectors].is_protected = 1;
/* the reset_init handler marks all the sectors unprotected,
* matching hardware after reset; keep the driver in sync
*/
bank->sectors[num_sectors].is_protected = 0;
str7x_info->sector_bits[num_sectors++] = mem_layout_str7bank0[i].sector_bit;
}
@@ -102,7 +105,10 @@ static int str7x_build_block_list(struct flash_bank *bank)
bank->sectors[num_sectors].offset = mem_layout_str7bank1[i].sector_start;
bank->sectors[num_sectors].size = mem_layout_str7bank1[i].sector_size;
bank->sectors[num_sectors].is_erased = -1;
bank->sectors[num_sectors].is_protected = 1;
/* the reset_init handler marks all the sectors unprotected,
* matching hardware after reset; keep the driver in sync
*/
bank->sectors[num_sectors].is_protected = 0;
str7x_info->sector_bits[num_sectors++] = mem_layout_str7bank1[i].sector_bit;
}
@@ -600,6 +606,12 @@ COMMAND_HANDLER(str7x_handle_part_id_command)
static int str7x_info(struct flash_bank *bank, char *buf, int buf_size)
{
snprintf(buf, buf_size, "str7x flash driver info");
/* STR7x flash doesn't support sector protection interrogation.
* FLASH_NVWPAR acts as a write only register; its read value
* doesn't reflect the actual protection state of the sectors.
*/
LOG_WARNING("STR7x flash lock information might not be correct "
"due to hardware limitations.");
return ERROR_OK;
}
@@ -676,7 +688,7 @@ COMMAND_HANDLER(str7x_handle_disable_jtag_command)
static const struct command_registration str7x_exec_command_handlers[] = {
{
.name = "disable_jtag",
.handler = &str7x_handle_disable_jtag_command,
.handler = str7x_handle_disable_jtag_command,
.mode = COMMAND_EXEC,
.help = "disable jtag access",
},
@@ -693,15 +705,15 @@ static const struct command_registration str7x_command_handlers[] = {
};
struct flash_driver str7x_flash = {
.name = "str7x",
.commands = str7x_command_handlers,
.flash_bank_command = &str7x_flash_bank_command,
.erase = &str7x_erase,
.protect = &str7x_protect,
.write = &str7x_write,
.probe = &str7x_probe,
.auto_probe = &str7x_probe,
.erase_check = &default_flash_blank_check,
.protect_check = &str7x_protect_check,
.info = &str7x_info,
};
.name = "str7x",
.commands = str7x_command_handlers,
.flash_bank_command = str7x_flash_bank_command,
.erase = str7x_erase,
.protect = str7x_protect,
.write = str7x_write,
.probe = str7x_probe,
.auto_probe = str7x_probe,
.erase_check = default_flash_blank_check,
.protect_check = str7x_protect_check,
.info = str7x_info,
};

View File

@@ -230,17 +230,9 @@ static int str9x_erase(struct flash_bank *bank, int first, int last)
return ERROR_TARGET_NOT_HALTED;
}
/* Check if we erase whole bank */
if ((first == 0) && (last == (bank->num_sectors - 1)))
{
/* Optimize to run erase bank command instead of sector */
erase_cmd = 0x80;
}
else
{
/* Erase sector command */
erase_cmd = 0x20;
}
/*A slower but stable way of erasing*/
/* Erase sector command */
erase_cmd = 0x20;
for (i = first; i <= last; i++)
{
@@ -296,10 +288,6 @@ static int str9x_erase(struct flash_bank *bank, int first, int last)
LOG_ERROR("error erasing flash bank, status: 0x%x", status);
return ERROR_FLASH_OPERATION_FAILED;
}
/* If we ran erase bank command, we are finished */
if (erase_cmd == 0x80)
break;
}
for (i = first; i <= last; i++)
@@ -679,11 +667,12 @@ COMMAND_HANDLER(str9x_handle_flash_config_command)
static const struct command_registration str9x_config_command_handlers[] = {
{
.name = "disable_jtag",
.handler = &str9x_handle_flash_config_command,
.name = "flash_config",
.handler = str9x_handle_flash_config_command,
.mode = COMMAND_EXEC,
.help = "configure str9x flash controller",
.usage = "<bank_id> <BBSR> <NBBSR> <BBADR> <NBBADR>",
.help = "Configure str9x flash controller, prior to "
"programming the flash.",
.usage = "bank_id BBSR NBBSR BBADR NBBADR",
},
COMMAND_REGISTRATION_DONE
};
@@ -698,15 +687,15 @@ static const struct command_registration str9x_command_handlers[] = {
};
struct flash_driver str9x_flash = {
.name = "str9x",
.commands = str9x_command_handlers,
.flash_bank_command = &str9x_flash_bank_command,
.erase = &str9x_erase,
.protect = &str9x_protect,
.write = &str9x_write,
.probe = &str9x_probe,
.auto_probe = &str9x_probe,
.erase_check = &default_flash_blank_check,
.protect_check = &str9x_protect_check,
.info = &str9x_info,
};
.name = "str9x",
.commands = str9x_command_handlers,
.flash_bank_command = str9x_flash_bank_command,
.erase = str9x_erase,
.protect = str9x_protect,
.write = str9x_write,
.probe = str9x_probe,
.auto_probe = str9x_probe,
.erase_check = default_flash_blank_check,
.protect_check = str9x_protect_check,
.info = str9x_info,
};

View File

@@ -915,6 +915,10 @@ COMMAND_HANDLER(str9xpec_handle_flash_options_write_command)
if ((status & ISC_STATUS_ERROR) != STR9XPEC_ISC_SUCCESS)
return ERROR_FLASH_OPERATION_FAILED;
command_print(CMD_CTX, "str9xpec write options complete.\n"
"INFO: a reset or power cycle is required "
"for the new settings to take effect.");
return ERROR_OK;
}
@@ -1077,6 +1081,10 @@ COMMAND_HANDLER(str9xpec_handle_flash_unlock_command)
if ((status & ISC_STATUS_ERROR) != STR9XPEC_ISC_SUCCESS)
return ERROR_FLASH_OPERATION_FAILED;
command_print(CMD_CTX, "str9xpec unlocked.\n"
"INFO: a reset or power cycle is required "
"for the new settings to take effect.");
return ERROR_OK;
}
@@ -1244,15 +1252,15 @@ static const struct command_registration str9xpec_command_handlers[] = {
};
struct flash_driver str9xpec_flash = {
.name = "str9xpec",
.commands = str9xpec_command_handlers,
.flash_bank_command = &str9xpec_flash_bank_command,
.erase = &str9xpec_erase,
.protect = &str9xpec_protect,
.write = &str9xpec_write,
.probe = &str9xpec_probe,
.auto_probe = &str9xpec_probe,
.erase_check = &str9xpec_erase_check,
.protect_check = &str9xpec_protect_check,
.info = &str9xpec_info,
};
.name = "str9xpec",
.commands = str9xpec_command_handlers,
.flash_bank_command = str9xpec_flash_bank_command,
.erase = str9xpec_erase,
.protect = str9xpec_protect,
.write = str9xpec_write,
.probe = str9xpec_probe,
.auto_probe = str9xpec_probe,
.erase_check = str9xpec_erase_check,
.protect_check = str9xpec_protect_check,
.info = str9xpec_info,
};

View File

@@ -26,6 +26,11 @@
#include <helper/time_support.h>
#include <target/image.h>
/**
* @file
* Implements Tcl commands used to access NOR flash facilities.
*/
COMMAND_HELPER(flash_command_get_bank, unsigned name_index,
struct flash_bank **bank)
{
@@ -198,14 +203,29 @@ COMMAND_HANDLER(handle_flash_erase_address_command)
int retval;
int address;
int length;
bool do_pad = false;
struct target *target = get_current_target(CMD_CTX);
if (CMD_ARGC != 2)
switch (CMD_ARGC) {
case 3:
/* Optionally pad out the address range to block/sector
* boundaries. We can't know if there's data in that part
* of the flash; only do padding if we're told to.
*/
if (strcmp("pad", CMD_ARGV[0]) != 0)
return ERROR_COMMAND_SYNTAX_ERROR;
do_pad = true;
CMD_ARGC--;
CMD_ARGV++;
/* FALL THROUGH */
case 2:
COMMAND_PARSE_NUMBER(int, CMD_ARGV[0], address);
COMMAND_PARSE_NUMBER(int, CMD_ARGV[1], length);
break;
default:
return ERROR_COMMAND_SYNTAX_ERROR;
}
COMMAND_PARSE_NUMBER(int, CMD_ARGV[0], address);
COMMAND_PARSE_NUMBER(int, CMD_ARGV[1], length);
if (length <= 0)
{
command_print(CMD_CTX, "Length must be >0");
@@ -224,7 +244,7 @@ COMMAND_HANDLER(handle_flash_erase_address_command)
struct duration bench;
duration_start(&bench);
retval = flash_erase_address_range(target, address, length);
retval = flash_erase_address_range(target, do_pad, address, length);
if ((ERROR_OK == retval) && (duration_measure(&bench) == ERROR_OK))
{
@@ -439,7 +459,7 @@ COMMAND_HANDLER(handle_flash_write_image_command)
if ((ERROR_OK == retval) && (duration_measure(&bench) == ERROR_OK))
{
command_print(CMD_CTX, "wrote %" PRIu32 " byte from file %s "
command_print(CMD_CTX, "wrote %" PRIu32 " bytes from file %s "
"in %fs (%0.3f kb/s)", written, CMD_ARGV[0],
duration_elapsed(&bench), duration_kbps(&bench, written));
}
@@ -625,9 +645,9 @@ COMMAND_HANDLER(handle_flash_write_bank_command)
if ((ERROR_OK == retval) && (duration_measure(&bench) == ERROR_OK))
{
command_print(CMD_CTX, "wrote %zu byte from file %s to flash bank %u"
command_print(CMD_CTX, "wrote %ld bytes from file %s to flash bank %u"
" at offset 0x%8.8" PRIx32 " in %fs (%0.3f kb/s)",
fileio.size, CMD_ARGV[1], p->bank_number, offset,
(long)fileio.size, CMD_ARGV[1], p->bank_number, offset,
duration_elapsed(&bench), duration_kbps(&bench, fileio.size));
}
@@ -654,89 +674,102 @@ void flash_set_dirty(void)
static const struct command_registration flash_exec_command_handlers[] = {
{
.name = "probe",
.handler = &handle_flash_probe_command,
.handler = handle_flash_probe_command,
.mode = COMMAND_EXEC,
.usage = "<bank>",
.help = "identify flash bank",
.usage = "bank_id",
.help = "Identify a flash bank.",
},
{
.name = "info",
.handler = &handle_flash_info_command,
.handler = handle_flash_info_command,
.mode = COMMAND_EXEC,
.usage = "<bank>",
.help = "print bank information",
.usage = "bank_id",
.help = "Print information about a flash bank.",
},
{
.name = "erase_check",
.handler = &handle_flash_erase_check_command,
.handler = handle_flash_erase_check_command,
.mode = COMMAND_EXEC,
.usage = "<bank>",
.help = "check erase state of sectors",
.usage = "bank_id",
.help = "Check erase state of all blocks in a "
"flash bank.",
},
{
.name = "protect_check",
.handler = &handle_flash_protect_check_command,
.handler = handle_flash_protect_check_command,
.mode = COMMAND_EXEC,
.usage = "<bank>",
.help = "check protection state of sectors",
.usage = "bank_id",
.help = "Check protection state of all blocks in a "
"flash bank.",
},
{
.name = "erase_sector",
.handler = &handle_flash_erase_command,
.handler = handle_flash_erase_command,
.mode = COMMAND_EXEC,
.usage = "<bank> <first> <last>",
.help = "erase sectors",
.usage = "bank_id first_sector_num last_sector_num",
.help = "Erase a range of sectors in a flash bank.",
},
{
.name = "erase_address",
.handler = &handle_flash_erase_address_command,
.handler = handle_flash_erase_address_command,
.mode = COMMAND_EXEC,
.usage = "<address> <length>",
.help = "erase address range",
.usage = "['pad'] address length",
.help = "Erase flash sectors starting at address and "
"continuing for length bytes. If 'pad' is specified, "
"data outside that range may also be erased: the start "
"address may be decreased, and length increased, so "
"that all of the first and last sectors are erased.",
},
{
.name = "fillw",
.handler = &handle_flash_fill_command,
.handler = handle_flash_fill_command,
.mode = COMMAND_EXEC,
.usage = "<address> <word_pattern> <count>",
.help = "fill with pattern (no autoerase)",
.usage = "address value n",
.help = "Fill n words with 32-bit value, starting at "
"word address. (No autoerase.)",
},
{
.name = "fillh",
.handler = &handle_flash_fill_command,
.handler = handle_flash_fill_command,
.mode = COMMAND_EXEC,
.usage = "<address> <halfword_pattern> <count>",
.help = "fill with pattern",
.usage = "address value n",
.help = "Fill n halfwords with 16-bit value, starting at "
"word address. (No autoerase.)",
},
{
.name = "fillb",
.handler = &handle_flash_fill_command,
.handler = handle_flash_fill_command,
.mode = COMMAND_EXEC,
.usage = "<address> <byte_pattern> <count>",
.help = "fill with pattern",
.usage = "address value n",
.help = "Fill n bytes with 8-bit value, starting at "
"word address. (No autoerase.)",
},
{
.name = "write_bank",
.handler = &handle_flash_write_bank_command,
.handler = handle_flash_write_bank_command,
.mode = COMMAND_EXEC,
.usage = "<bank> <file> <offset>",
.help = "write binary data",
.usage = "bank_id filename offset",
.help = "Write binary data from file to flash bank, "
"starting at specified byte offset from the "
"beginning of the bank.",
},
{
.name = "write_image",
.handler = &handle_flash_write_image_command,
.handler = handle_flash_write_image_command,
.mode = COMMAND_EXEC,
.usage = "[erase] [unlock] <file> [offset] [type]",
.help = "write an image to flash"
.usage = "[erase] [unlock] filename [offset [file_type]]",
.help = "Write an image to flash. Optionally first unprotect "
"and/or erase the region to be used. Allow optional "
"offset from beginning of bank (defaults to zero)",
},
{
.name = "protect",
.handler = &handle_flash_protect_command,
.handler = handle_flash_protect_command,
.mode = COMMAND_EXEC,
.usage = "<bank> <first> <last> <on | off>",
.help = "set protection of sectors",
.usage = "bank_id first_sector [last_sector|'last'] "
"('on'|'off')",
.help = "Turn protection on or off for a range of sectors "
"in a given flash bank.",
},
COMMAND_REGISTRATION_DONE
};
@@ -891,10 +924,10 @@ COMMAND_HANDLER(handle_flash_init_command)
static const struct command_registration flash_config_command_handlers[] = {
{
.name = "bank",
.handler = &handle_flash_bank_command,
.handler = handle_flash_bank_command,
.mode = COMMAND_CONFIG,
.usage = "<name> <driver> <base> <size> "
"<chip_width> <bus_width> <target> "
.usage = "bank_id driver_name base_address size_bytes "
"chip_width_bytes bus_width_bytes target "
"[driver_options ...]",
.help = "Define a new bank with the given name, "
"using the specified NOR flash driver.",
@@ -902,20 +935,20 @@ static const struct command_registration flash_config_command_handlers[] = {
{
.name = "init",
.mode = COMMAND_CONFIG,
.handler = &handle_flash_init_command,
.help = "initialize flash devices",
.handler = handle_flash_init_command,
.help = "Initialize flash devices.",
},
{
.name = "banks",
.mode = COMMAND_ANY,
.handler = &handle_flash_banks_command,
.help = "return readable information about the flash banks",
.handler = handle_flash_banks_command,
.help = "Display table with information about flash banks.",
},
{
.name = "list",
.mode = COMMAND_ANY,
.jim_handler = &jim_flash_list,
.help = "returns a list of details about the flash banks",
.jim_handler = jim_flash_list,
.help = "Returns a list of details about the flash banks.",
},
COMMAND_REGISTRATION_DONE
};

View File

@@ -821,19 +821,19 @@ static int tms470_erase_sector(struct flash_bank *bank, int sector)
static const struct command_registration tms470_any_command_handlers[] = {
{
.name = "flash_keyset",
.handler = &tms470_handle_flash_keyset_command,
.handler = tms470_handle_flash_keyset_command,
.mode = COMMAND_ANY,
.help = "tms470 flash_keyset <key0> <key1> <key2> <key3>",
},
{
.name = "osc_megahertz",
.handler = &tms470_handle_osc_megahertz_command,
.handler = tms470_handle_osc_megahertz_command,
.mode = COMMAND_ANY,
.help = "tms470 osc_megahertz <MHz>",
},
{
.name = "plldis",
.handler = &tms470_handle_plldis_command,
.handler = tms470_handle_plldis_command,
.mode = COMMAND_ANY,
.help = "tms470 plldis <0/1>",
},
@@ -1258,15 +1258,15 @@ FLASH_BANK_COMMAND_HANDLER(tms470_flash_bank_command)
}
struct flash_driver tms470_flash = {
.name = "tms470",
.commands = tms470_command_handlers,
.flash_bank_command = &tms470_flash_bank_command,
.erase = &tms470_erase,
.protect = &tms470_protect,
.write = &tms470_write,
.probe = &tms470_probe,
.auto_probe = &tms470_auto_probe,
.erase_check = &tms470_erase_check,
.protect_check = &tms470_protect_check,
.info = &tms470_info,
};
.name = "tms470",
.commands = tms470_command_handlers,
.flash_bank_command = tms470_flash_bank_command,
.erase = tms470_erase,
.protect = tms470_protect,
.write = tms470_write,
.probe = tms470_probe,
.auto_probe = tms470_auto_probe,
.erase_check = tms470_erase_check,
.protect_check = tms470_protect_check,
.info = tms470_info,
};

View File

@@ -58,14 +58,14 @@ static const struct command_registration foo_command_handlers[] = {
.name = "bar",
.handler = &handle_foo_command,
.mode = COMMAND_ANY,
.usage = "<address> [enable|disable]",
.usage = "address ['enable'|'disable']",
.help = "an example command",
},
{
.name = "baz",
.handler = &handle_foo_command,
.mode = COMMAND_ANY,
.usage = "<address> [enable|disable]",
.usage = "address ['enable'|'disable']",
.help = "a sample command",
},
{
@@ -107,10 +107,10 @@ COMMAND_HANDLER(handle_hello_command)
const struct command_registration hello_command_handlers[] = {
{
.name = "hello",
.handler = &handle_hello_command,
.handler = handle_hello_command,
.mode = COMMAND_ANY,
.help = "prints a warm welcome",
.usage = "[<name>]",
.usage = "[name]",
},
{
.name = "foo",

View File

@@ -108,10 +108,15 @@ static int command_retval_set(Jim_Interp *interp, int retval)
extern struct command_context *global_cmd_ctx;
/* dump a single line to the log for the command.
* Do nothing in case we are not at debug level 3 */
void script_debug(Jim_Interp *interp, const char *name,
unsigned argc, Jim_Obj *const *argv)
{
LOG_DEBUG("command - %s", name);
if (debug_level < LOG_LVL_DEBUG)
return;
char * dbg = alloc_printf("command - %s", name);
for (unsigned i = 0; i < argc; i++)
{
int len;
@@ -121,8 +126,12 @@ void script_debug(Jim_Interp *interp, const char *name,
if (*w == '#')
break;
LOG_DEBUG("%s - argv[%d]=%s", name, i, w);
char * t = alloc_printf("%s %s", dbg, w);
free (dbg);
dbg = t;
}
LOG_DEBUG("%s", dbg);
free(dbg);
}
static void script_command_args_free(const char **words, unsigned nwords)
@@ -349,7 +358,7 @@ static int register_command_handler(struct command_context *cmd_ctx,
if (NULL == override_name)
return JIM_ERR;
retval = Jim_Eval_Named(interp, override_name, __FILE__, __LINE__);
retval = Jim_Eval_Named(interp, override_name, __THIS__FILE__ , __LINE__);
free((void *)override_name);
return retval;
@@ -366,7 +375,10 @@ struct command* register_command(struct command_context *context,
struct command *c = command_find(*head, name);
if (NULL != c)
{
LOG_ERROR("command '%s' is already registered in '%s' context",
/* TODO: originally we treated attempting to register a cmd twice as an error
* Sometimes we need this behaviour, such as with flash banks.
* http://www.mail-archive.com/openocd-development@lists.berlios.de/msg11152.html */
LOG_DEBUG("command '%s' is already registered in '%s' context",
name, parent ? parent->name : "<global>");
return c;
}
@@ -580,6 +592,7 @@ static int run_command(struct command_context *context,
struct command_invocation cmd = {
.ctx = context,
.current = c,
.name = c->name,
.argc = num_words - 1,
.argv = words + 1,
@@ -913,7 +926,7 @@ static COMMAND_HELPER(command_help_show, struct command *c, unsigned n,
bool is_match = (strstr(cmd_name, match) != NULL) ||
((c->usage != NULL) && (strstr(c->usage, match) != NULL)) ||
((c->help != NULL) && (strstr(c->help, match) != NULL));
if (is_match)
{
command_help_show_indent(n);
@@ -933,15 +946,27 @@ static COMMAND_HELPER(command_help_show, struct command *c, unsigned n,
if (is_match && show_help)
{
const char *stage_msg;
switch (c->mode) {
case COMMAND_CONFIG: stage_msg = "CONFIG"; break;
case COMMAND_EXEC: stage_msg = "EXEC"; break;
case COMMAND_ANY: stage_msg = "CONFIG or EXEC"; break;
default: stage_msg = "***UNKNOWN***"; break;
}
char *msg = alloc_printf("%s%sValid Modes: %s",
c->help ? : "", c->help ? " " : "", stage_msg);
char *msg;
/* Normal commands are runtime-only; highlight exceptions */
if (c->mode != COMMAND_EXEC) {
const char *stage_msg = "";
switch (c->mode) {
case COMMAND_CONFIG:
stage_msg = " (configuration command)";
break;
case COMMAND_ANY:
stage_msg = " (command valid any time)";
break;
default:
stage_msg = " (?mode error?)";
break;
}
msg = alloc_printf("%s%s", c->help ? : "", stage_msg);
} else
msg = alloc_printf("%s", c->help ? : "");
if (NULL != msg)
{
command_help_show_wrap(msg, n + 3, n + 3);
@@ -959,18 +984,45 @@ static COMMAND_HELPER(command_help_show, struct command *c, unsigned n,
COMMAND_HANDLER(handle_help_command)
{
bool full = strcmp(CMD_NAME, "help") == 0;
int retval;
struct command *c = CMD_CTX->commands;
char *match = NULL;
const char *match = "";
if (CMD_ARGC == 0)
match = "";
else if (CMD_ARGC == 1)
match = CMD_ARGV[0];
else
else if (CMD_ARGC >= 1) {
unsigned i;
for (i = 0; i < CMD_ARGC; ++i) {
if (NULL != match) {
char *prev = match;
match = alloc_printf("%s %s", match,
CMD_ARGV[i]);
free(prev);
if (NULL == match) {
LOG_ERROR("unable to build "
"search string");
return -ENOMEM;
}
} else {
match = alloc_printf("%s", CMD_ARGV[i]);
if (NULL == match) {
LOG_ERROR("unable to build "
"search string");
return -ENOMEM;
}
}
}
} else
return ERROR_COMMAND_SYNTAX_ERROR;
return CALL_COMMAND_HANDLER(command_help_show_list, c, 0, full, match);
retval = CALL_COMMAND_HANDLER(command_help_show_list,
c, 0, full, match);
if (CMD_ARGC >= 1)
free(match);
return retval;
}
static int command_unknown_find(unsigned argc, Jim_Obj *const *argv,
@@ -1047,6 +1099,7 @@ static int jim_command_mode(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
{
struct command_context *cmd_ctx = current_command_context(interp);
enum command_mode mode;
if (argc > 1)
{
struct command *c = cmd_ctx->commands;
@@ -1183,7 +1236,7 @@ COMMAND_HANDLER(handle_help_add_command)
return help_add_command(CMD_CTX, c, cmd_name, help, usage);
}
/* sleep command sleeps for <n> miliseconds
/* sleep command sleeps for <n> milliseconds
* this is useful in target startup scripts
*/
COMMAND_HANDLER(handle_sleep_command)
@@ -1223,19 +1276,22 @@ static const struct command_registration command_subcommand_handlers[] = {
{
.name = "mode",
.mode = COMMAND_ANY,
.jim_handler = &jim_command_mode,
.usage = "[<name> ...]",
.jim_handler = jim_command_mode,
.usage = "[command_name ...]",
.help = "Returns the command modes allowed by a command:"
"'any', 'config', or 'exec'. If no command is"
"specified, returns the current command mode.",
"specified, returns the current command mode. "
"Returns 'unknown' if an unknown command is given. "
"Command can be multiple tokens.",
},
{
.name = "type",
.mode = COMMAND_ANY,
.jim_handler = &jim_command_type,
.usage = "<name> ...",
.jim_handler = jim_command_type,
.usage = "command_name [...]",
.help = "Returns the type of built-in command:"
"'native', 'simple', 'group', or 'unknown'",
"'native', 'simple', 'group', or 'unknown'. "
"Command can be multiple tokens.",
},
COMMAND_REGISTRATION_DONE
};
@@ -1243,39 +1299,43 @@ static const struct command_registration command_subcommand_handlers[] = {
static const struct command_registration command_builtin_handlers[] = {
{
.name = "add_help_text",
.handler = &handle_help_add_command,
.handler = handle_help_add_command,
.mode = COMMAND_ANY,
.help = "add new command help text",
.usage = "<command> [...] <help_text>]",
.help = "Add new command help text; "
"Command can be multiple tokens.",
.usage = "command_name helptext_string",
},
{
.name = "add_usage_text",
.handler = &handle_help_add_command,
.handler = handle_help_add_command,
.mode = COMMAND_ANY,
.help = "add new command usage text",
.usage = "<command> [...] <usage_text>]",
.help = "Add new command usage text; "
"command can be multiple tokens.",
.usage = "command_name usage_string",
},
{
.name = "sleep",
.handler = &handle_sleep_command,
.handler = handle_sleep_command,
.mode = COMMAND_ANY,
.help = "sleep for n milliseconds. "
"\"busy\" will busy wait",
.usage = "<n> [busy]",
.help = "Sleep for specified number of milliseconds. "
"\"busy\" will busy wait instead (avoid this).",
.usage = "milliseconds ['busy']",
},
{
.name = "help",
.handler = &handle_help_command,
.handler = handle_help_command,
.mode = COMMAND_ANY,
.help = "show full command help",
.usage = "[<command> ...]",
.help = "Show full command help; "
"command can be multiple tokens.",
.usage = "[command_name]",
},
{
.name = "usage",
.handler = &handle_help_command,
.handler = handle_help_command,
.mode = COMMAND_ANY,
.help = "show basic command usage",
.usage = "[<command> ...]",
.help = "Show basic command usage; "
"command can be multiple tokens.",
.usage = "[command_name]",
},
{
.name = "command",
@@ -1310,6 +1370,7 @@ struct command_context* command_init(const char *startup_tcl, Jim_Interp *interp
#endif
context->interp = interp;
/* Stick to lowercase for HostOS strings. */
#if defined(_MSC_VER)
/* WinXX - is generic, the forward
* looking problem is this:
@@ -1321,7 +1382,7 @@ struct command_context* command_init(const char *startup_tcl, Jim_Interp *interp
HostOs = "winxx";
#elif defined(__linux__)
HostOs = "linux";
#elif defined(__DARWIN__)
#elif defined(__APPLE__) || defined(__DARWIN__)
HostOs = "darwin";
#elif defined(__CYGWIN__)
HostOs = "cygwin";
@@ -1329,8 +1390,10 @@ struct command_context* command_init(const char *startup_tcl, Jim_Interp *interp
HostOs = "mingw32";
#elif defined(__ECOS)
HostOs = "ecos";
#elif defined(__FreeBSD__)
HostOs = "freebsd";
#else
#warn unrecognized host OS...
#warning "Unrecognized host OS..."
HostOs = "other";
#endif
Jim_SetGlobalVariableStr(interp, "ocd_HOSTOS",

View File

@@ -115,8 +115,10 @@ int parse_config_file(struct command_context *cmd_ctx)
int retval;
char **cfg;
if (!config_file_names)
add_config_command ("script openocd.cfg");
if (!config_file_names) {
command_run_line(cmd_ctx, "script openocd.cfg");
return ERROR_OK;
}
cfg = config_file_names;

View File

@@ -191,6 +191,7 @@ COMMAND_HANDLER(handle_append_command)
int retval = ERROR_FAIL;
FILE *config_file = NULL;
config_file = fopen(CMD_ARGV[0], "a");
if (config_file != NULL)
{
@@ -199,7 +200,8 @@ COMMAND_HANDLER(handle_append_command)
unsigned i;
for (i = 1; i < CMD_ARGC; i++)
{
if (fwrite(CMD_ARGV[i], 1, strlen(CMD_ARGV[i]), config_file) != strlen(CMD_ARGV[i]))
if (fwrite(CMD_ARGV[i], 1, strlen(CMD_ARGV[i]),
config_file) != strlen(CMD_ARGV[i]))
break;
if (i != CMD_ARGC - 1)
{
@@ -208,9 +210,8 @@ COMMAND_HANDLER(handle_append_command)
}
}
if ((i == CMD_ARGC) && (fwrite("\n", 1, 1, config_file) == 1))
{
retval = ERROR_OK;
}
fclose(config_file);
}
@@ -619,76 +620,86 @@ static int zylinjtag_Jim_Command_mac(Jim_Interp *interp, int argc,
static const struct command_registration ioutil_command_handlers[] = {
{
.name = "cat",
.handler = &handle_cat_command,
.handler = handle_cat_command,
.mode = COMMAND_ANY,
.help = "display file content",
.usage= "<file_name>",
.help = "display text file content",
.usage= "file_name",
},
{
.name = "trunc",
.handler = &handle_trunc_command,
.handler = handle_trunc_command,
.mode = COMMAND_ANY,
.help = "truncate a file 0 size",
.usage= "<file_name>",
.help = "truncate a file to zero length",
.usage= "file_name",
},
{
.name = "cp",
.handler = &handle_cp_command,
.handler = handle_cp_command,
.mode = COMMAND_ANY,
.help = "copy a file",
.usage = "<src> <dst>",
.usage = "src_file_name dst_file_name",
},
{
.name = "append_file",
.handler = &handle_append_command,
.handler = handle_append_command,
.mode = COMMAND_ANY,
.help = "append a variable number of strings to a file",
.usage= "<file_name> [<string> ...]",
.usage= "file_name [string ...]",
},
{
.name = "meminfo",
.handler = &handle_meminfo_command,
.handler = handle_meminfo_command,
.mode = COMMAND_ANY,
.help = "display available ram memory",
.help = "display free heap space",
},
{
.name = "rm",
.mode = COMMAND_ANY,
.handler = &handle_rm_command,
.help = "remove a file",
.usage = "<file>",
.handler = handle_rm_command,
.help = "remove a directory or file",
.usage = "file_name",
},
/*
* REVISIT shouldn't most, or all, these zylinjtag_*()
* entries be #ifdef ZY1000? If not, why so they have
* those names?
*
* Peek and poke are security holes -- they manipulate
* server-internal addresses.
*/
// jim handlers
{
.name = "peek",
.mode = COMMAND_ANY,
.jim_handler = &zylinjtag_Jim_Command_peek,
.jim_handler = zylinjtag_Jim_Command_peek,
.help = "peek at a memory address",
.usage = "<addr>",
.usage = "address",
},
{
.name = "poke",
.mode = COMMAND_ANY,
.jim_handler = &zylinjtag_Jim_Command_poke,
.jim_handler = zylinjtag_Jim_Command_poke,
.help = "poke at a memory address",
.usage = "<addr> <value>",
.usage = "address value",
},
{
.name = "ls",
.mode = COMMAND_ANY,
.jim_handler = &zylinjtag_Jim_Command_ls,
.jim_handler = zylinjtag_Jim_Command_ls,
.help = "show a listing of files",
.usage = "<dir>",
.usage = "dirname",
},
{
.name = "mac",
.mode = COMMAND_ANY,
.jim_handler = &zylinjtag_Jim_Command_mac,
.jim_handler = zylinjtag_Jim_Command_mac,
.help = "show MAC address",
},
{
.name = "ip",
.jim_handler = &zylinjtag_Jim_Command_ip,
.jim_handler = zylinjtag_Jim_Command_ip,
.mode = COMMAND_ANY,
.help = "show IP address",
},

View File

@@ -2217,7 +2217,7 @@ static Jim_Obj *JimStringToLower(Jim_Interp *interp, Jim_Obj *strObjPtr)
memcpy(buf, strObjPtr->bytes, strObjPtr->length + 1);
for (i = 0; i < strObjPtr->length; i++)
buf[i] = tolower(buf[i]);
buf[i] = tolower((unsigned)buf[i]);
return Jim_NewStringObjNoAlloc(interp, buf, strObjPtr->length);
}
@@ -2233,7 +2233,7 @@ static Jim_Obj *JimStringToUpper(Jim_Interp *interp, Jim_Obj *strObjPtr)
memcpy(buf, strObjPtr->bytes, strObjPtr->length + 1);
for (i = 0; i < strObjPtr->length; i++)
buf[i] = toupper(buf[i]);
buf[i] = toupper((unsigned)buf[i]);
return Jim_NewStringObjNoAlloc(interp, buf, strObjPtr->length);
}
@@ -2347,7 +2347,7 @@ static Jim_Obj *Jim_FormatString_Inner(Jim_Interp *interp, Jim_Obj *fmtObjPtr,
case '8':
case '9':
accum = 0;
while (isdigit(*fmt) && (fmtLen > 0)) {
while (isdigit((unsigned)*fmt) && (fmtLen > 0)) {
accum = (accum * 10) + (*fmt - '0');
fmt++; fmtLen--;
}

View File

@@ -286,13 +286,16 @@ COMMAND_HANDLER(handle_debug_level_command)
if (debug_level >= LOG_LVL_DEBUG && server_use_pipes == 1)
{
/* if we are enabling debug info then we need to write to a log file
* otherwise the pipe will get full and cause issues with gdb */
/* if we are enabling debug info then we need to write to a
* log file otherwise the pipe will get full and cause issues
* with gdb
*/
FILE* file = fopen("openocd.log", "w");
if (file)
{
log_output = file;
LOG_WARNING("enabling log output as we are using pipes");
LOG_WARNING("enabling logfile output because "
"we are using pipes to talk to GDB.");
}
}
@@ -319,17 +322,19 @@ COMMAND_HANDLER(handle_log_output_command)
static struct command_registration log_command_handlers[] = {
{
.name = "log_output",
.handler = &handle_log_output_command,
.handler = handle_log_output_command,
.mode = COMMAND_ANY,
.help = "redirect logging to a file (default: stderr)",
.usage = "<file_name>",
.usage = "file_name",
},
{
.name = "debug_level",
.handler = &handle_debug_level_command,
.handler = handle_debug_level_command,
.mode = COMMAND_ANY,
.help = "sets the verbosity level of debugging output",
.usage = "<level:0-3>",
.help = "Sets the verbosity level of debugging output. "
"0 shows errors only; 1 adds warnings; "
"2 (default) adds other info; 3 adds debugging.",
.usage = "number",
},
COMMAND_REGISTRATION_DONE
};

View File

@@ -111,7 +111,12 @@ extern int debug_level;
#define LOG_LEVEL_IS(FOO) ((debug_level) >= (FOO))
#define LOG_DEBUG(expr ...) \
((debug_level >= LOG_LVL_DEBUG) ? log_printf_lf (LOG_LVL_DEBUG, __FILE__, __LINE__, __FUNCTION__, expr) , 0 : 0)
do { \
if (debug_level >= LOG_LVL_DEBUG) \
log_printf_lf(LOG_LVL_DEBUG, \
__FILE__, __LINE__, __func__, \
expr); \
} while (0)
#define LOG_INFO(expr ...) \
log_printf_lf (LOG_LVL_INFO, __FILE__, __LINE__, __FUNCTION__, expr)

View File

@@ -74,21 +74,21 @@ static void add_default_dirs(void)
add_script_search_dir(strExePath);
}
/*
* Add support for the default (as of 20080121) layout when
* using autotools and cygwin to build native MinGW binary.
* Add support for the default (as of 20091118) layout when
* using autotools and cygwin/MinGW to build native binary.
* Path separator is converted to UNIX style so that MinGW is
* pleased.
*
* bin/openocd.exe
* lib/openocd/event/at91eb40a_reset.cfg
* lib/openocd/target/at91eb40a.cfg
* share/openocd/scripts/interface/dummy.cfg
* share/openocd/scripts/target/at91eb40a.cfg
*/
{
char strExePath [MAX_PATH];
char *p;
GetModuleFileName (NULL, strExePath, MAX_PATH);
*strrchr(strExePath, '\\') = 0;
strcat(strExePath, "/../lib/"PACKAGE);
strcat(strExePath, "/../share/"PACKAGE"/scripts");
for (p = strExePath; *p; p++) {
if (*p == '\\')
*p = '/';

View File

@@ -40,6 +40,12 @@
#define ENOTSUP 134 /* Not supported */
#endif
/* for systems that do not support O_BINARY
* linux being one of them */
#ifndef O_BINARY
#define O_BINARY 0
#endif
#ifndef HAVE_SYS_TIME_H
#ifndef _TIMEVAL_DEFINED

View File

@@ -50,6 +50,8 @@
#ifdef _WIN32
#include <winsock2.h>
#include <ws2tcpip.h>
#include <sys/types.h>
#include <sys/stat.h>
#endif
// --- platform specific headers ---
@@ -83,4 +85,9 @@
#include <fcntl.h>
#endif
#ifndef true
#define true 1
#define false 0
#endif
#endif // SYSTEM_H

View File

@@ -172,6 +172,7 @@ static inline void h_u16_to_be(uint8_t* buf, int val)
#define SCNx32 "x"
#define PRIi32 "i"
#define PRIu32 "u"
#define PRId8 PRId32
typedef CYG_ADDRWORD intptr_t;
typedef int64_t intmax_t;

View File

@@ -530,10 +530,12 @@ int jtag_add_statemove(tap_state_t goal_state)
{
tap_state_t cur_state = cmd_queue_cur_state;
LOG_DEBUG("cur_state=%s goal_state=%s",
tap_state_name(cur_state),
tap_state_name(goal_state));
if (goal_state != cur_state)
{
LOG_DEBUG("cur_state=%s goal_state=%s",
tap_state_name(cur_state),
tap_state_name(goal_state));
}
/* If goal is RESET, be paranoid and force that that transition
* (e.g. five TCK cycles, TMS high). Else trust "cur_state".
@@ -1621,6 +1623,13 @@ bool jtag_will_verify_capture_ir()
int jtag_power_dropout(int *dropout)
{
if (jtag == NULL)
{
/* TODO: as the jtag interface is not valid all
* we can do at the moment is exit OpenOCD */
LOG_ERROR("No Valid JTAG Interface Configured.");
exit(-1);
}
return jtag->power_dropout(dropout);
}

View File

@@ -28,6 +28,9 @@ endif
if FT2232_DRIVER
DRIVERFILES += ft2232.c
endif
if USB_BLASTER_DRIVER
DRIVERFILES += usb_blaster.c
endif
if AMTJTAGACCEL
DRIVERFILES += amt_jtagaccel.c
endif

View File

@@ -22,8 +22,6 @@
#endif
#include <jtag/interface.h>
#include <jtag/commands.h>
#if PARPORT_USE_PPDEV == 1
#include <linux/parport.h>
@@ -41,6 +39,15 @@
#endif
#endif
/**
* @file
* Support the Amontec Chameleon POD with JTAG Accelerator support.
* This is a parallel port JTAG adapter with a CPLD between the
* parallel port and the JTAG connection. VHDL code running in the
* CPLD significantly accelerates JTAG operations compared to the
* bitbanging "Wiggler" style of most parallel port adapters.
*/
/* configuration */
static uint16_t amt_jtagaccel_port;
@@ -55,13 +62,41 @@ static int rtck_enabled = 0;
#if PARPORT_USE_PPDEV == 1
static int device_handle;
static int addr_mode = IEEE1284_MODE_EPP | IEEE1284_ADDR ;
#define AMT_AW(val) do { ioctl(device_handle, PPSETMODE, &addr_mode); write(device_handle, &val, 1); } while (0)
#define AMT_AR(val) do { ioctl(device_handle, PPSETMODE, &addr_mode); read(device_handle, &val, 1); } while (0)
static const int addr_mode = IEEE1284_MODE_EPP | IEEE1284_ADDR;
static int data_mode = IEEE1284_MODE_EPP | IEEE1284_DATA ;
#define AMT_DW(val) do { ioctl(device_handle, PPSETMODE, &data_mode); write(device_handle, &val, 1); } while (0)
#define AMT_DR(val) do { ioctl(device_handle, PPSETMODE, &data_mode); read(device_handle, &val, 1); } while (0)
/* FIXME do something sane when these ioctl/read/write calls fail. */
#define AMT_AW(val) \
do { \
int __retval; \
\
__retval = ioctl(device_handle, PPSETMODE, &addr_mode); \
__retval = write(device_handle, &val, 1); \
} while (0)
#define AMT_AR(val) \
do { \
int __retval; \
\
__retval = ioctl(device_handle, PPSETMODE, &addr_mode); \
__retval = read(device_handle, &val, 1); \
} while (0)
static const int data_mode = IEEE1284_MODE_EPP | IEEE1284_DATA;
#define AMT_DW(val) \
do { \
int __retval; \
\
__retval = ioctl(device_handle, PPSETMODE, &data_mode); \
__retval = write(device_handle, &val, 1); \
} while (0)
#define AMT_DR(val) \
do { \
int __retval; \
\
__retval = ioctl(device_handle, PPSETMODE, &data_mode); \
__retval = read(device_handle, &val, 1); \
} while (0)
#else
@@ -545,24 +580,31 @@ static const struct command_registration amtjtagaccel_command_handlers[] = {
.name = "parport_port",
.handler = &amt_jtagaccel_handle_parport_port_command,
.mode = COMMAND_CONFIG,
.help = "configure the parallel port to use",
.usage = "<port_num>",
.help = "configure or display the parallel port to use",
.usage = "[port_num]",
},
{
.name = "parport_port",
/**
* @todo Remove this "rtck" command; just use the standard
* mechanism to enable/disable adaptive clocking. First
* implement the standard mechanism and deprecate "rtck";
* after a year or so, it'll be safe to remove this.
*/
.name = "rtck",
.handler = &amt_jtagaccel_handle_rtck_command,
.mode = COMMAND_CONFIG,
.help = "enable RTCK",
.usage = "<enable|disable>",
.help = "configure or display RTCK support",
.usage = "[enable|disable]",
},
COMMAND_REGISTRATION_DONE
};
struct jtag_interface amt_jtagaccel_interface = {
.name = "amt_jtagaccel",
.commands = amtjtagaccel_command_handlers,
.init = &amt_jtagaccel_init,
.quit = &amt_jtagaccel_quit,
.speed = &amt_jtagaccel_speed,
.execute_queue = &amt_jtagaccel_execute_queue,
};
.name = "amt_jtagaccel",
.commands = amtjtagaccel_command_handlers,
.init = amt_jtagaccel_init,
.quit = amt_jtagaccel_quit,
.speed = amt_jtagaccel_speed,
.execute_queue = amt_jtagaccel_execute_queue,
};

View File

@@ -513,17 +513,15 @@ static const struct command_registration armjtagew_command_handlers[] = {
};
struct jtag_interface armjtagew_interface = {
.name = "arm-jtag-ew",
.name = "arm-jtag-ew",
.commands = armjtagew_command_handlers,
.commands = armjtagew_command_handlers,
.execute_queue = &armjtagew_execute_queue,
.speed = &armjtagew_speed,
.khz = &armjtagew_khz,
.init = &armjtagew_init,
.quit = &armjtagew_quit,
};
.execute_queue = armjtagew_execute_queue,
.speed = armjtagew_speed,
.khz = armjtagew_khz,
.init = armjtagew_init,
.quit = armjtagew_quit,
};
/***************************************************************************/
/* ARM-JTAG-EW tap functions */

View File

@@ -215,7 +215,10 @@ int interface_jtag_add_dr_scan(int in_num_fields, const struct scan_field *in_fi
if (!tap->bypass)
{
struct scan_field * start_field = field; /* keep initial position for assert() */
#ifndef NDEBUG
/* remember initial position for assert() */
struct scan_field *start_field = field;
#endif /* NDEBUG */
for (int j = 0; j < in_num_fields; j++)
{

View File

@@ -27,13 +27,40 @@
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
/* This code uses information contained in the MPSSE specification which was
/**
* @file
* JTAG adapters based on the FT2232 full and high speed USB parts are
* popular low cost JTAG debug solutions. Many FT2232 based JTAG adapters
* are discrete, but development boards may integrate them as alternatives
* to more capable (and expensive) third party JTAG pods. Since JTAG uses
* only one of the two ports on these devices, on integrated boards the
* second port often serves as a USB-to-serial adapter for the target's
* console UART even when the JTAG port is not in use. (Systems which
* support ARM's SWD in addition to JTAG, or instead of it, may use that
* second port for reading SWV trace data.)
*
* FT2232 based JTAG adapters are "dumb" not "smart", because most JTAG
* request/response interactions involve round trips over the USB link.
* A "smart" JTAG adapter has intelligence close to the scan chain, so it
* can for example poll quickly for a status change (usually taking on the
* order of microseconds not milliseconds) before beginning a queued
* transaction which require the previous one to have completed.
*
* There are dozens of adapters of this type, differing in details which
* this driver needs to understand. Those "layout" details are required
* as part of FT2232 driver configuration.
*
* This code uses information contained in the MPSSE specification which was
* found here:
* http://www.ftdichip.com/Documents/AppNotes/AN2232C-01_MPSSE_Cmnd.pdf
* Hereafter this is called the "MPSSE Spec".
*
* The datasheet for the ftdichip.com's FT2232D part is here:
* http://www.ftdichip.com/Documents/DataSheets/DS_FT2232D.pdf
*
* Also note the issue with code 0x4b (clock data to TMS) noted in
* http://developer.intra2net.com/mailarchive/html/libftdi/2009/msg00292.html
* which can affect longer JTAG state paths.
*/
#ifdef HAVE_CONFIG_H
@@ -42,7 +69,6 @@
/* project specific includes */
#include <jtag/interface.h>
#include <jtag/commands.h>
#include <helper/time_support.h>
#if IS_CYGWIN == 1
@@ -2182,6 +2208,11 @@ static int usbjtag_init(void)
}
else if (strcmp(ft2232_layout, "evb_lm3s811") == 0)
{
/* There are multiple revisions of LM3S811 eval boards:
* - Rev B (and older?) boards have no SWO trace support.
* - Rev C boards add ADBUS_6 DBG_ENn and BDBUS_4 SWO_EN;
* they should use the "luminary_icdi" layout instead.
*/
nTRST = 0x0;
nTRSTnOE = 0x00;
nSRST = 0x20;
@@ -2191,6 +2222,9 @@ static int usbjtag_init(void)
}
else if (strcmp(ft2232_layout, "luminary_icdi") == 0)
{
/* Most Luminary eval boards support SWO trace output,
* and should use this "luminary_icdi" layout.
*/
nTRST = 0x0;
nTRSTnOE = 0x00;
nSRST = 0x20;
@@ -3975,14 +4009,14 @@ static const struct command_registration ft2232_command_handlers[] = {
.handler = &ft2232_handle_device_desc_command,
.mode = COMMAND_CONFIG,
.help = "set the USB device description of the FTDI FT2232 device",
.usage = "<description>",
.usage = "description_string",
},
{
.name = "ft2232_serial",
.handler = &ft2232_handle_serial_command,
.mode = COMMAND_CONFIG,
.help = "set the serial number of the FTDI FT2232 device",
.usage = "<serial#>",
.usage = "serial_string",
},
{
.name = "ft2232_layout",
@@ -3990,32 +4024,33 @@ static const struct command_registration ft2232_command_handlers[] = {
.mode = COMMAND_CONFIG,
.help = "set the layout of the FT2232 GPIO signals used "
"to control output-enables and reset signals",
.usage = "<layout>",
.usage = "layout_name",
},
{
.name = "ft2232_vid_pid",
.handler = &ft2232_handle_vid_pid_command,
.mode = COMMAND_CONFIG,
.help = "the vendor ID and product ID of the FTDI FT2232 device",
.usage = "<vid> <pid> [...]",
.usage = "(vid pid)* ",
},
{
.name = "ft2232_latency",
.handler = &ft2232_handle_latency_command,
.mode = COMMAND_CONFIG,
.help = "set the FT2232 latency timer to a new value",
.usage = "<vid> <pid> [...]",
.usage = "value",
},
COMMAND_REGISTRATION_DONE
};
struct jtag_interface ft2232_interface = {
.name = "ft2232",
.commands = ft2232_command_handlers,
.init = &ft2232_init,
.quit = &ft2232_quit,
.speed = &ft2232_speed,
.speed_div = &ft2232_speed_div,
.khz = &ft2232_khz,
.execute_queue = &ft2232_execute_queue,
};
.name = "ft2232",
.commands = ft2232_command_handlers,
.init = ft2232_init,
.quit = ft2232_quit,
.speed = ft2232_speed,
.speed_div = ft2232_speed_div,
.khz = ft2232_khz,
.execute_queue = ft2232_execute_queue,
};

View File

@@ -565,19 +565,22 @@ COMMAND_HANDLER(gw16012_handle_parport_port_command)
static const struct command_registration gw16012_command_handlers[] = {
{
.name = "parport_port",
.handler = &gw16012_handle_parport_port_command,
.handler = gw16012_handle_parport_port_command,
.mode = COMMAND_CONFIG,
.help = "configure the parallel port to use",
.usage = "<port_num>",
.help = "Display the address of the I/O port (e.g. 0x378) "
"or the number of the '/dev/parport' device used. "
"If a parameter is provided, first change that port.",
.usage = "[port_number]",
},
COMMAND_REGISTRATION_DONE
};
struct jtag_interface gw16012_interface = {
.name = "gw16012",
.commands = gw16012_command_handlers,
.init = &gw16012_init,
.quit = &gw16012_quit,
.speed = &gw16012_speed,
.execute_queue = &gw16012_execute_queue,
};
.name = "gw16012",
.commands = gw16012_command_handlers,
.init = gw16012_init,
.quit = gw16012_quit,
.speed = gw16012_speed,
.execute_queue = gw16012_execute_queue,
};

View File

@@ -29,6 +29,10 @@
#include <jtag/commands.h>
#include "usb_common.h"
/* See Segger's public documentation:
* Reference manual for J-Link USB Protocol
* Document RM08001-R6 Date: June 16, 2009
*/
#define VID 0x1366
#define PID 0x0101
@@ -645,18 +649,16 @@ static const struct command_registration jlink_command_handlers[] = {
};
struct jtag_interface jlink_interface = {
.name = "jlink",
.name = "jlink",
.commands = jlink_command_handlers,
.commands = jlink_command_handlers,
.execute_queue = &jlink_execute_queue,
.speed = &jlink_speed,
.speed_div = &jlink_speed_div,
.khz = &jlink_khz,
.init = &jlink_init,
.quit = &jlink_quit,
};
.execute_queue = jlink_execute_queue,
.speed = jlink_speed,
.speed_div = jlink_speed_div,
.khz = jlink_khz,
.init = jlink_init,
.quit = jlink_quit,
};
/***************************************************************************/
/* J-Link tap functions */

View File

@@ -76,16 +76,15 @@ struct cable {
static struct cable cables[] =
{
/* name tdo trst tms tck tdi srst o_inv i_inv init exit led */
/* name tdo trst tms tck tdi srst o_inv i_inv init exit led */
{ "wiggler", 0x80, 0x10, 0x02, 0x04, 0x08, 0x01, 0x01, 0x80, 0x80, 0x80, 0x00 },
{ "wiggler2", 0x80, 0x10, 0x02, 0x04, 0x08, 0x01, 0x01, 0x80, 0x80, 0x00, 0x20 },
{ "wiggler_ntrst_inverted",
0x80, 0x10, 0x02, 0x04, 0x08, 0x01, 0x11, 0x80, 0x80, 0x80, 0x00 },
{ "old_amt_wiggler", 0x80, 0x01, 0x02, 0x04, 0x08, 0x10, 0x11, 0x80, 0x80, 0x80, 0x00 },
{ "wiggler_ntrst_inverted", 0x80, 0x10, 0x02, 0x04, 0x08, 0x01, 0x11, 0x80, 0x80, 0x80, 0x00 },
{ "old_amt_wiggler", 0x80, 0x01, 0x02, 0x04, 0x08, 0x10, 0x11, 0x80, 0x80, 0x80, 0x00 },
{ "arm-jtag", 0x80, 0x01, 0x02, 0x04, 0x08, 0x10, 0x01, 0x80, 0x80, 0x80, 0x00 },
{ "chameleon", 0x80, 0x00, 0x04, 0x01, 0x02, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00 },
{ "dlc5", 0x10, 0x00, 0x04, 0x02, 0x01, 0x00, 0x00, 0x00, 0x10, 0x10, 0x00 },
{ "triton", 0x80, 0x08, 0x04, 0x01, 0x02, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00 },
{ "dlc5", 0x10, 0x00, 0x04, 0x02, 0x01, 0x00, 0x00, 0x00, 0x10, 0x10, 0x00 },
{ "triton", 0x80, 0x08, 0x04, 0x01, 0x02, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00 },
{ "lattice", 0x40, 0x10, 0x04, 0x02, 0x01, 0x08, 0x00, 0x00, 0x18, 0x18, 0x00 },
{ "flashlink", 0x20, 0x10, 0x02, 0x01, 0x04, 0x20, 0x30, 0x20, 0x00, 0x00, 0x00 },
/* Altium Universal JTAG cable. Set the cable to Xilinx Mode and wire to target as follows:
@@ -425,7 +424,7 @@ COMMAND_HANDLER(parport_handle_parport_port_command)
}
}
command_print(CMD_CTX, "parport port = %u", parport_port);
command_print(CMD_CTX, "parport port = 0x%" PRIx16 "", parport_port);
return ERROR_OK;
}
@@ -438,10 +437,13 @@ COMMAND_HANDLER(parport_handle_parport_cable_command)
/* only if the cable name wasn't overwritten by cmdline */
if (parport_cable == 0)
{
/* REVISIT first verify that it's listed in cables[] ... */
parport_cable = malloc(strlen(CMD_ARGV[0]) + sizeof(char));
strcpy(parport_cable, CMD_ARGV[0]);
}
/* REVISIT it's probably worth returning the current value ... */
return ERROR_OK;
}
@@ -485,49 +487,49 @@ COMMAND_HANDLER(parport_handle_parport_toggling_time_command)
static const struct command_registration parport_command_handlers[] = {
{
.name = "parport_port",
.handler = &parport_handle_parport_port_command,
.handler = parport_handle_parport_port_command,
.mode = COMMAND_CONFIG,
.help = "either the address of the I/O port "
"or the number of the '/dev/parport' device",
.usage = "[<port|devname>]",
.help = "Display the address of the I/O port (e.g. 0x378) "
"or the number of the '/dev/parport' device used. "
"If a parameter is provided, first change that port.",
.usage = "[port_number]",
},
{
.name = "parport_cable",
.handler = &parport_handle_parport_cable_command,
.handler = parport_handle_parport_cable_command,
.mode = COMMAND_CONFIG,
.help = "the layout of the parallel port cable "
"used to connect to the target",
.usage = "[<layout>]",
.help = "Set the layout of the parallel port cable "
"used to connect to the target.",
/* REVISIT there's no way to list layouts we know ... */
.usage = "[layout]",
},
{
.name = "parport_write_on_exit",
.handler = &parport_handle_write_on_exit_command,
.handler = parport_handle_write_on_exit_command,
.mode = COMMAND_CONFIG,
.help = "configure the parallel driver to write "
"a known value to the parallel interface",
.usage = "[<on|off>]",
.help = "Configure the parallel driver to write "
"a known value to the parallel interface on exit.",
.usage = "('on'|'off')",
},
{
.name = "parport_toggling_time",
.handler = &parport_handle_parport_toggling_time_command,
.handler = parport_handle_parport_toggling_time_command,
.mode = COMMAND_CONFIG,
.help = "time <ns> it takes for the hardware to toggle TCK",
.usage = "[<ns>]",
.help = "Displays or assigns how many nanoseconds it "
"takes for the hardware to toggle TCK.",
.usage = "[nanoseconds]",
},
COMMAND_REGISTRATION_DONE
};
struct jtag_interface parport_interface = {
.name = "parport",
.name = "parport",
.commands = parport_command_handlers,
.commands = parport_command_handlers,
.init = &parport_init,
.quit = &parport_quit,
.khz = &parport_khz,
.speed_div = &parport_speed_div,
.speed = &parport_speed,
.execute_queue = &bitbang_execute_queue,
};
.init = parport_init,
.quit = parport_quit,
.khz = parport_khz,
.speed_div = parport_speed_div,
.speed = parport_speed,
.execute_queue = bitbang_execute_queue,
};

View File

@@ -17,6 +17,12 @@
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
/**
* @file
* Holds driver for PRESTO programmer from ASIX.
* http://tools.asix.net/prg_presto.htm
*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
@@ -742,10 +748,10 @@ COMMAND_HANDLER(presto_handle_serial_command)
static const struct command_registration presto_command_handlers[] = {
{
.name = "presto_serial",
.handler = &presto_handle_serial_command,
.handler = presto_handle_serial_command,
.mode = COMMAND_CONFIG,
.help = "configure serial port",
.usage = "<devname>",
.help = "Configure USB serial number of Presto device.",
.usage = "serial_string",
},
COMMAND_REGISTRATION_DONE
};
@@ -786,15 +792,13 @@ static int presto_jtag_quit(void)
}
struct jtag_interface presto_interface = {
.name = "presto",
.name = "presto",
.commands = presto_command_handlers,
.commands = presto_command_handlers,
.execute_queue = &bitq_execute_queue,
.speed = &presto_jtag_speed,
.khz = &presto_jtag_khz,
.speed_div = &presto_jtag_speed_div,
.init = &presto_jtag_init,
.quit = &presto_jtag_quit,
};
.execute_queue = bitq_execute_queue,
.speed = presto_jtag_speed,
.khz = presto_jtag_khz,
.speed_div = presto_jtag_speed_div,
.init = presto_jtag_init,
.quit = presto_jtag_quit,
};

View File

@@ -0,0 +1,589 @@
/***************************************************************************
* Driver for USB-JTAG, Altera USB-Blaster and compatibles *
* Original code from Kolja Waschk's USB-JTAG project *
* (http://www.ixo.de/info/usb_jtag/). *
* Some updates by Anthony Liu (2006). *
* Minor updates and cleanup by Catalin Patulea (2009). *
* *
* Copyright (C) 2009 Catalin Patulea *
* cat@vv.carleton.ca *
* *
* Copyright (C) 2006 Kolja Waschk *
* usbjtag@ixo.de *
* *
* Based on ft2232.c and bitbang.c, *
* Copyright (C) 2004,2006 by Dominic Rath *
* *
* 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. *
***************************************************************************/
/*
* The following information is originally from Kolja Waschk's USB-JTAG,
* where it was obtained by reverse engineering an Altera USB-Blaster.
* See http://www.ixo.de/info/usb_jtag/ for USB-Blaster block diagram and
* usb_jtag-20080705-1200.zip#usb_jtag/host/openocd for protocol.
*
* The same information is also on the UrJTAG mediawiki, with some additional
* notes on bits marked as "unknown" by usb_jtag.
* (http://sourceforge.net/apps/mediawiki/urjtag/index.php?
* title=Cable_Altera_USB-Blaster)
*
* USB-JTAG, Altera USB-Blaster and compatibles are typically implemented as
* an FTDIChip FT245 followed by a CPLD which handles a two-mode protocol:
*
* _________
* | |
* | AT93C46 |
* |_________|
* __|__________ _________
* | | | |
* USB__| FTDI 245BM |__| EPM7064 |__JTAG (B_TDO,B_TDI,B_TMS,B_TCK)
* |_____________| |_________|
* __|__________ _|___________
* | | | |
* | 6 MHz XTAL | | 24 MHz Osc. |
* |_____________| |_____________|
*
* Protocol details are given in the code below.
*
* It is also possible to emulate this configuration using a single-chip USB
* controller like the Cypress FX2 (again, see usb_jtag for details).
*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#if IS_CYGWIN == 1
#include "windows.h"
#undef LOG_ERROR
#endif
/* project specific includes */
#include <jtag/interface.h>
#include <jtag/commands.h>
#include <helper/time_support.h>
/* system includes */
#include <string.h>
#include <stdlib.h>
#include <unistd.h>
#include "bitbang.h"
#if (BUILD_USB_BLASTER_FTD2XX == 1 && BUILD_USB_BLASTER_LIBFTDI == 1)
#error "BUILD_USB_BLASTER_FTD2XX && BUILD_USB_BLASTER_LIBFTDI "
"are mutually exclusive"
#elif (BUILD_USB_BLASTER_FTD2XX != 1 && BUILD_USB_BLASTER_LIBFTDI != 1)
#error "BUILD_USB_BLASTER_FTD2XX || BUILD_USB_BLASTER_LIBFTDI must be chosen"
#endif
/* USB_BLASTER access library includes */
#if BUILD_USB_BLASTER_FTD2XX == 1
#include <ftd2xx.h>
#elif BUILD_USB_BLASTER_LIBFTDI == 1
#include <ftdi.h>
#endif
#include <sys/time.h>
#include <time.h>
static char *usb_blaster_device_desc;
static uint16_t usb_blaster_vid = 0x09fb; /* Altera */
static uint16_t usb_blaster_pid = 0x6001; /* USB-Blaster */
/* last output byte in simple bit banging mode */
static uint8_t out_value;
#if BUILD_USB_BLASTER_FTD2XX == 1
static FT_HANDLE ftdih;
#elif BUILD_USB_BLASTER_LIBFTDI == 1
static struct ftdi_context ftdic;
#endif
static int usb_blaster_buf_write(
uint8_t *buf, int size, uint32_t *bytes_written)
{
#if BUILD_USB_BLASTER_FTD2XX == 1
FT_STATUS status;
DWORD dw_bytes_written;
#ifdef _DEBUG_JTAG_IO_
LOG_DEBUG("usb_blaster_buf_write %02X (%d)\n", buf[0], size);
#endif
status = FT_Write(ftdih, buf, size, &dw_bytes_written);
if (status != FT_OK)
{
*bytes_written = dw_bytes_written;
LOG_ERROR("FT_Write returned: %lu", status);
return ERROR_JTAG_DEVICE_ERROR;
}
*bytes_written = dw_bytes_written;
return ERROR_OK;
#elif BUILD_USB_BLASTER_LIBFTDI == 1
int retval;
#ifdef _DEBUG_JTAG_IO_
LOG_DEBUG("usb_blaster_buf_write %02X (%d)\n", buf[0], size);
#endif
retval = ftdi_write_data(&ftdic, buf, size);
if (retval < 0)
{
*bytes_written = 0;
LOG_ERROR("ftdi_write_data: %s", ftdi_get_error_string(&ftdic));
return ERROR_JTAG_DEVICE_ERROR;
}
*bytes_written = retval;
return ERROR_OK;
#endif
}
static int
usb_blaster_buf_read(uint8_t *buf, unsigned size, uint32_t *bytes_read)
{
#if BUILD_USB_BLASTER_FTD2XX == 1
DWORD dw_bytes_read;
FT_STATUS status;
status = FT_Read(ftdih, buf, size, &dw_bytes_read);
if (status != FT_OK)
{
*bytes_read = dw_bytes_read;
LOG_ERROR("FT_Read returned: %lu", status);
return ERROR_JTAG_DEVICE_ERROR;
}
#ifdef _DEBUG_JTAG_IO_
LOG_DEBUG("usb_blaster_buf_read %02X (%lu)\n", buf[0], dw_bytes_read);
#endif
*bytes_read = dw_bytes_read;
return ERROR_OK;
#elif BUILD_USB_BLASTER_LIBFTDI == 1
int retval;
int timeout = 100;
*bytes_read = 0;
while ((*bytes_read < size) && timeout--)
{
retval = ftdi_read_data(&ftdic, buf + *bytes_read,
size - *bytes_read);
if (retval < 0)
{
*bytes_read = 0;
LOG_ERROR("ftdi_read_data: %s",
ftdi_get_error_string(&ftdic));
return ERROR_JTAG_DEVICE_ERROR;
}
*bytes_read += retval;
}
#ifdef _DEBUG_JTAG_IO_
LOG_DEBUG("usb_blaster_buf_read %02X (%d)\n", buf[0], *bytes_read);
#endif
return ERROR_OK;
#endif
}
/* The following code doesn't fully utilize the possibilities of the
* USB-Blaster. It writes one byte per JTAG pin state change at a time; it
* doesn't even try to buffer data up to the maximum packet size of 64 bytes.
*
* Actually, the USB-Blaster offers a byte-shift mode to transmit up to 504 data
* bits (bidirectional) in a single USB packet. A header byte has to be sent as
* the first byte in a packet with the following meaning:
*
* Bit 7 (0x80): Must be set to indicate byte-shift mode.
* Bit 6 (0x40): If set, the USB-Blaster will also read data, not just write.
* Bit 5..0: Define the number N of following bytes
*
* All N following bytes will then be clocked out serially on TDI. If Bit 6 was
* set, it will afterwards return N bytes with TDO data read while clocking out
* the TDI data. LSB of the first byte after the header byte will appear first
* on TDI.
*/
/* Simple bit banging mode:
*
* Bit 7 (0x80): Must be zero (see byte-shift mode above)
* Bit 6 (0x40): If set, you will receive a byte indicating the state of TDO
* in return.
* Bit 5 (0x20): Output Enable/LED.
* Bit 4 (0x10): TDI Output.
* Bit 3 (0x08): nCS Output (not used in JTAG mode).
* Bit 2 (0x04): nCE Output (not used in JTAG mode).
* Bit 1 (0x02): TMS Output.
* Bit 0 (0x01): TCK Output.
*
* For transmitting a single data bit, you need to write two bytes. Up to 64
* bytes can be combined in a single USB packet (but this is not done in the
* code below). It isn't possible to read a data without transmitting data.
*/
#define TCK (1 << 0)
#define TMS (1 << 1)
#define NCE (1 << 2)
#define NCS (1 << 3)
#define TDI (1 << 4)
#define LED (1 << 5)
#define READ (1 << 6)
#define SHMODE (1 << 7)
#define OTHERS ((1 << 2) | (1 << 3) | (1 << 5))
#define READ_TDO (1 << 0)
static void usb_blaster_write_data(void)
{
uint32_t bytes_written;
usb_blaster_buf_write(&out_value, 1, &bytes_written);
}
static int usb_blaster_read_data(void)
{
int status;
uint8_t buf[1];
uint32_t bytes_read;
out_value |= READ;
usb_blaster_write_data();
out_value &= ~READ;
status = usb_blaster_buf_read(buf, 1, &bytes_read);
if (status < 0)
return 0;
return !!(buf[0] & READ_TDO);
}
static void usb_blaster_write(int tck, int tms, int tdi)
{
#ifdef _DEBUG_JTAG_IO_
LOG_DEBUG("---- usb_blaster_write(%d,%d,%d)\n", tck, tms, tdi);
#endif
out_value &= ~(TCK | TMS | TDI);
if (tck)
out_value |= TCK;
if (tms)
out_value |= TMS;
if (tdi)
out_value |= TDI;
usb_blaster_write_data();
}
static int usb_blaster_speed(int speed)
{
#if BUILD_USB_BLASTER_FTD2XX == 1
LOG_DEBUG("TODO: usb_blaster_speed() isn't implemented for libftd2xx!");
#elif BUILD_USB_BLASTER_LIBFTDI == 1
LOG_DEBUG("TODO: usb_blaster_speed() isn't optimally implemented!");
/* TODO: libftdi's ftdi_set_baudrate chokes on high rates, use lowlevel
* usb function instead! And additionally allow user to throttle.
*/
if (ftdi_set_baudrate(&ftdic, 3000000 / 4) < 0)
{
LOG_ERROR("Can't set baud rate to max: %s",
ftdi_get_error_string(&ftdic));
return ERROR_JTAG_DEVICE_ERROR;
};
#endif
return ERROR_OK;
}
static void usb_blaster_reset(int trst, int srst)
{
LOG_DEBUG("TODO: usb_blaster_reset(%d,%d) isn't implemented!",
trst, srst);
}
static struct bitbang_interface usb_blaster_bitbang = {
.read = usb_blaster_read_data,
.write = usb_blaster_write,
.reset = usb_blaster_reset,
};
static int usb_blaster_init(void)
{
uint8_t latency_timer;
#if BUILD_USB_BLASTER_FTD2XX == 1
FT_STATUS status;
#endif
#if BUILD_USB_BLASTER_FTD2XX == 1
LOG_DEBUG("'usb_blaster' interface using FTD2XX");
#elif BUILD_USB_BLASTER_LIBFTDI == 1
LOG_DEBUG("'usb_blaster' interface using libftdi");
#endif
#if BUILD_USB_BLASTER_FTD2XX == 1
/* Open by device description */
if (usb_blaster_device_desc == NULL)
{
LOG_WARNING("no usb_blaster device description specified, "
"using default 'USB-Blaster'");
usb_blaster_device_desc = "USB-Blaster";
}
#if IS_WIN32 == 0
/* Add non-standard Vid/Pid to the linux driver */
status = FT_SetVIDPID(usb_blaster_vid, usb_blaster_pid);
if (status != FT_OK)
{
LOG_WARNING("couldn't add %4.4x:%4.4x",
usb_blaster_vid, usb_blaster_pid);
}
#endif
status = FT_OpenEx(usb_blaster_device_desc, FT_OPEN_BY_DESCRIPTION,
&ftdih);
if (status != FT_OK)
{
DWORD num_devices;
LOG_ERROR("unable to open ftdi device: %lu", status);
status = FT_ListDevices(&num_devices, NULL,
FT_LIST_NUMBER_ONLY);
if (status == FT_OK)
{
char **desc_array = malloc(sizeof(char *)
* (num_devices + 1));
unsigned int i;
for (i = 0; i < num_devices; i++)
desc_array[i] = malloc(64);
desc_array[num_devices] = NULL;
status = FT_ListDevices(desc_array, &num_devices,
FT_LIST_ALL | FT_OPEN_BY_DESCRIPTION);
if (status == FT_OK)
{
LOG_ERROR("ListDevices: %lu\n", num_devices);
for (i = 0; i < num_devices; i++)
LOG_ERROR("%i: %s", i, desc_array[i]);
}
for (i = 0; i < num_devices; i++)
free(desc_array[i]);
free(desc_array);
}
else
{
printf("ListDevices: NONE\n");
}
return ERROR_JTAG_INIT_FAILED;
}
status = FT_SetLatencyTimer(ftdih, 2);
if (status != FT_OK)
{
LOG_ERROR("unable to set latency timer: %lu", status);
return ERROR_JTAG_INIT_FAILED;
}
status = FT_GetLatencyTimer(ftdih, &latency_timer);
if (status != FT_OK)
{
LOG_ERROR("unable to get latency timer: %lu", status);
return ERROR_JTAG_INIT_FAILED;
}
LOG_DEBUG("current latency timer: %i", latency_timer);
status = FT_SetBitMode(ftdih, 0x00, 0);
if (status != FT_OK)
{
LOG_ERROR("unable to disable bit i/o mode: %lu", status);
return ERROR_JTAG_INIT_FAILED;
}
#elif BUILD_USB_BLASTER_LIBFTDI == 1
if (ftdi_init(&ftdic) < 0)
return ERROR_JTAG_INIT_FAILED;
/* context, vendor id, product id */
if (ftdi_usb_open(&ftdic, usb_blaster_vid, usb_blaster_pid) < 0)
{
LOG_ERROR("unable to open ftdi device: %s", ftdic.error_str);
return ERROR_JTAG_INIT_FAILED;
}
if (ftdi_usb_reset(&ftdic) < 0)
{
LOG_ERROR("unable to reset ftdi device");
return ERROR_JTAG_INIT_FAILED;
}
if (ftdi_set_latency_timer(&ftdic, 2) < 0)
{
LOG_ERROR("unable to set latency timer");
return ERROR_JTAG_INIT_FAILED;
}
if (ftdi_get_latency_timer(&ftdic, &latency_timer) < 0)
{
LOG_ERROR("unable to get latency timer");
return ERROR_JTAG_INIT_FAILED;
}
LOG_DEBUG("current latency timer: %u", latency_timer);
ftdi_disable_bitbang(&ftdic);
#endif
bitbang_interface = &usb_blaster_bitbang;
usb_blaster_speed(jtag_get_speed());
#if 0
#if BUILD_USB_BLASTER_FTD2XX == 1
if ((status = FT_Purge(ftdih, FT_PURGE_RX | FT_PURGE_TX)) != FT_OK)
{
LOG_ERROR("error purging ftd2xx device: %i", status);
return ERROR_JTAG_INIT_FAILED;
}
#elif BUILD_USB_BLASTER_LIBFTDI == 1
if (ftdi_usb_purge_buffers(&ftdic) < 0)
{
LOG_ERROR("ftdi_purge_buffers: %s", ftdic.error_str);
return ERROR_JTAG_INIT_FAILED;
}
#endif
#endif
return ERROR_OK;
}
static int usb_blaster_quit(void)
{
#if BUILD_USB_BLASTER_FTD2XX == 1
FT_STATUS status;
status = FT_Close(ftdih);
#elif BUILD_USB_BLASTER_LIBFTDI == 1
ftdi_usb_close(&ftdic);
ftdi_deinit(&ftdic);
#endif
return ERROR_OK;
}
COMMAND_HANDLER(usb_blaster_handle_device_desc_command)
{
if (CMD_ARGC == 1)
usb_blaster_device_desc = strdup(CMD_ARGV[0]);
else
LOG_ERROR("require exactly one argument to "
"usb_blaster_device_desc <description>");
return ERROR_OK;
}
COMMAND_HANDLER(usb_blaster_handle_vid_pid_command)
{
if (CMD_ARGC > 2)
{
LOG_WARNING("ignoring extra IDs in ft2232_vid_pid "
"(maximum is 1 pair)");
CMD_ARGC = 2;
}
if (CMD_ARGC == 2)
{
COMMAND_PARSE_NUMBER(u16, CMD_ARGV[0], usb_blaster_vid);
COMMAND_PARSE_NUMBER(u16, CMD_ARGV[1], usb_blaster_pid);
}
else
LOG_WARNING("incomplete usb_blaster_vid_pid configuration");
return ERROR_OK;
}
COMMAND_HANDLER(usb_blaster_handle_pin_command)
{
if (CMD_ARGC == 2)
{
const char * const pin_name = CMD_ARGV[0];
uint8_t mask;
unsigned int state;
if (!strcmp(pin_name, "pin6"))
mask = NCE;
else if (!strcmp(pin_name, "pin8"))
mask = NCS;
else
{
LOG_ERROR("%s: pin name must be \"pin6\" or \"pin8\"",
CMD_NAME);
return ERROR_COMMAND_SYNTAX_ERROR;
}
COMMAND_PARSE_NUMBER(uint, CMD_ARGV[1], state);
if (state == 0)
{
out_value &= ~mask;
usb_blaster_write_data();
}
else if (state == 1)
{
out_value |= mask;
usb_blaster_write_data();
}
else
{
LOG_ERROR("%s: pin state must be 0 or 1", CMD_NAME);
return ERROR_COMMAND_SYNTAX_ERROR;
}
return ERROR_OK;
}
else
{
LOG_ERROR("%s takes exactly two arguments", CMD_NAME);
return ERROR_COMMAND_SYNTAX_ERROR;
}
}
static const struct command_registration usb_blaster_command_handlers[] = {
{
.name = "usb_blaster_device_desc",
.handler = usb_blaster_handle_device_desc_command,
.mode = COMMAND_CONFIG,
.help = "set the USB device description of the USB-Blaster",
.usage = "description-string",
},
{
.name = "usb_blaster_vid_pid",
.handler = usb_blaster_handle_vid_pid_command,
.mode = COMMAND_CONFIG,
.help = "the vendor ID and product ID of the USB-Blaster",
.usage = "vid pid",
},
{
.name = "usb_blaster",
.handler = usb_blaster_handle_pin_command,
.mode = COMMAND_ANY,
.help = "set pin state for the unused GPIO pins",
.usage = "(pin6|pin8) (0|1)",
},
COMMAND_REGISTRATION_DONE
};
struct jtag_interface usb_blaster_interface = {
.name = "usb_blaster",
.commands = usb_blaster_command_handlers,
.execute_queue = bitbang_execute_queue,
.speed = usb_blaster_speed,
.init = usb_blaster_init,
.quit = usb_blaster_quit,
};

View File

@@ -652,9 +652,10 @@ static void usbprog_jtag_tms_send(struct usbprog_jtag *usbprog_jtag)
}
struct jtag_interface usbprog_interface = {
.name = "usbprog",
.execute_queue = &usbprog_execute_queue,
.speed = &usbprog_speed,
.init = &usbprog_init,
.quit = &usbprog_quit
};
.name = "usbprog",
.execute_queue = usbprog_execute_queue,
.speed = usbprog_speed,
.init = usbprog_init,
.quit = usbprog_quit
};

View File

@@ -476,6 +476,17 @@ static int vsllink_init(void)
}
VSLLINK_USB_TIMEOUT = to_tmp;
/* Some older firmware versions sometimes fail if the
* voltage isn't read first.
*/
vsllink_simple_command(0x01);
result = vsllink_usb_read(vsllink_handle);
if (result != 2)
LOG_WARNING("Fail to get target voltage");
else
LOG_INFO("Target runs at %d mV", vsllink_usb_in_buffer[0]
+ (vsllink_usb_in_buffer[1] << 8));
// connect to vsllink
vsllink_connect();
// initialize function pointers
@@ -1891,13 +1902,13 @@ static const struct command_registration vsllink_command_handlers[] = {
};
struct jtag_interface vsllink_interface = {
.name = "vsllink",
.commands = vsllink_command_handlers,
.name = "vsllink",
.commands = vsllink_command_handlers,
.init = &vsllink_init,
.quit = &vsllink_quit,
.khz = &vsllink_khz,
.speed = &vsllink_speed,
.speed_div = &vsllink_speed_div,
.execute_queue = &vsllink_execute_queue,
};
.init = vsllink_init,
.quit = vsllink_quit,
.khz = vsllink_khz,
.speed = vsllink_speed,
.speed_div = vsllink_speed_div,
.execute_queue = vsllink_execute_queue,
};

View File

@@ -58,6 +58,9 @@ extern struct jtag_interface ft2232_interface;
#if BUILD_FT2232_LIBFTDI == 1
extern struct jtag_interface ft2232_interface;
#endif
#if BUILD_USB_BLASTER_LIBFTDI == 1 || BUILD_USB_BLASTER_FTD2XX == 1
extern struct jtag_interface usb_blaster_interface;
#endif
#if BUILD_AMTJTAGACCEL == 1
extern struct jtag_interface amt_jtagaccel_interface;
#endif
@@ -115,6 +118,9 @@ struct jtag_interface *jtag_interfaces[] = {
#if BUILD_FT2232_LIBFTDI == 1
&ft2232_interface,
#endif
#if BUILD_USB_BLASTER_LIBFTDI == 1 || BUILD_USB_BLASTER_FTD2XX == 1
&usb_blaster_interface,
#endif
#if BUILD_AMTJTAGACCEL == 1
&amt_jtagaccel_interface,
#endif

View File

@@ -525,8 +525,8 @@ int jtag_add_statemove(tap_state_t goal_state);
* to @a endstate (unless it is also TAP_IDLE).
*
* @param num_cycles Number of cycles in TAP_IDLE state. This argument
* may be 0, in which case this routine will navigate to @a endstate
* via TAP_IDLE.
* may be 0, in which case this routine will navigate to @a endstate
* via TAP_IDLE.
* @param endstate The final state.
*/
void jtag_add_runtest(int num_cycles, tap_state_t endstate);
@@ -563,23 +563,22 @@ void jtag_add_reset(int req_tlr_or_trst, int srst);
* Set a global variable to \a state if \a state != TAP_INVALID.
*
* Return the value of the global variable.
*
**/
*/
tap_state_t jtag_set_end_state(tap_state_t state);
/**
* Function jtag_get_end_state
*
* Return the value of the global variable for end state
*
**/
*/
tap_state_t jtag_get_end_state(void);
void jtag_add_sleep(uint32_t us);
/**
* Function jtag_add_stable_clocks
* Function jtag_add_clocks
* first checks that the state in which the clocks are to be issued is
* stable, then queues up clock_count clocks for transmission.
* stable, then queues up num_cycles clocks for transmission.
*/
void jtag_add_clocks(int num_cycles);

View File

@@ -30,8 +30,18 @@ proc init_reset { mode } {
# documented nor supported except on ZY1000.
proc power_restore {} {
puts "Sensed power restore."
puts "Sensed power restore, running reset init and halting GDB."
reset init
# Halt GDB so user can deal with a detected power restore.
#
# After GDB is halted, then output is no longer forwarded
# to the GDB console.
set targets [target names]
foreach t $targets {
# New event script.
$t invoke-event arp_halt_gdb
}
}
add_help_text power_restore "Overridable procedure run when power restore is detected. Runs 'reset init' by default."
@@ -46,9 +56,20 @@ proc power_dropout {} {
# documented nor supported except on ZY1000.
proc srst_deasserted {} {
puts "Sensed nSRST deasserted."
puts "Sensed nSRST deasserted, running reset init and halting GDB."
reset init
# Halt GDB so user can deal with a detected reset.
#
# After GDB is halted, then output is no longer forwarded
# to the GDB console.
set targets [target names]
foreach t $targets {
# New event script.
$t invoke-event arp_halt_gdb
}
}
add_help_text srst_deasserted "Overridable procedure run when srst deassert is detected. Runs 'reset init' by default."
proc srst_asserted {} {

View File

@@ -269,26 +269,39 @@ static int Jim_Command_flush_count(Jim_Interp *interp, int argc, Jim_Obj *const
return JIM_OK;
}
/* REVISIT Just what about these should "move" ... ?
* These registrations, into the main JTAG table?
*
* There's a minor compatibility issue, these all show up twice;
* that's not desirable:
* - jtag drscan ... NOT DOCUMENTED!
* - drscan ...
*
* The "irscan" command (for example) doesn't show twice.
*/
static const struct command_registration jtag_command_handlers_to_move[] = {
{
.name = "drscan",
.mode = COMMAND_EXEC,
.jim_handler = &Jim_Command_drscan,
.help = "execute DR scan <device> "
"<num_bits> <value> <num_bits1> <value2> ...",
.jim_handler = Jim_Command_drscan,
.help = "Execute Data Register (DR) scan for one TAP. "
"Other TAPs must be in BYPASS mode.",
.usage = "tap_name [num_bits value]* ['-endstate' state_name]",
},
{
.name = "flush_count",
.mode = COMMAND_EXEC,
.jim_handler = &Jim_Command_flush_count,
.help = "returns number of times the JTAG queue has been flushed",
.jim_handler = Jim_Command_flush_count,
.help = "Returns the number of times the JTAG queue "
"has been flushed.",
},
{
.name = "pathmove",
.mode = COMMAND_EXEC,
.jim_handler = &Jim_Command_pathmove,
.usage = "<state1>,<state2>,<state3>... ",
.help = "move JTAG to state1 then to state2, state3, etc.",
.jim_handler = Jim_Command_pathmove,
.usage = "start_state state1 [state2 [state3 ...]]",
.help = "Move JTAG state machine from current state "
"(start_state) to state1, then state2, state3, etc.",
},
COMMAND_REGISTRATION_DONE
};
@@ -610,7 +623,7 @@ static int jim_newtap_cmd(Jim_GetOptInfo *goi)
if (pTap->ir_length != 0)
{
jtag_tap_init(pTap);
return ERROR_OK;
return JIM_OK;
}
Jim_SetResult_sprintf(goi->interp,
@@ -658,7 +671,8 @@ static void jtag_tap_handle_event(struct jtag_tap *tap, enum jtag_event e)
}
}
static int jim_jtag_interface(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
static int
jim_jtag_interface(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
{
Jim_GetOptInfo goi;
Jim_GetOpt_Setup(&goi, interp, argc-1, argv + 1);
@@ -845,73 +859,88 @@ static const struct command_registration jtag_subcommand_handlers[] = {
{
.name = "init",
.mode = COMMAND_ANY,
.handler = &handle_jtag_init_command,
.handler = handle_jtag_init_command,
.help = "initialize jtag scan chain",
},
{
.name = "interface",
.mode = COMMAND_ANY,
.jim_handler = &jim_jtag_interface,
.help = "Returns the selected interface",
.jim_handler = jim_jtag_interface,
.help = "Returns the name of the currently selected interface.",
},
{
.name = "arp_init",
.mode = COMMAND_ANY,
.jim_handler = &jim_jtag_arp_init,
.jim_handler = jim_jtag_arp_init,
.help = "Validates JTAG scan chain against the list of "
"declared TAPs using just the four standard JTAG "
"signals.",
},
{
.name = "arp_init-reset",
.mode = COMMAND_ANY,
.jim_handler = &jim_jtag_arp_init_reset,
.jim_handler = jim_jtag_arp_init_reset,
.help = "Uses TRST and SRST to try resetting everything on "
"the JTAG scan chain, then performs 'jtag arp_init'."
},
{
.name = "newtap",
.mode = COMMAND_CONFIG,
.jim_handler = &jim_jtag_newtap,
.help = "Create a new TAP instance",
.usage = "<name> <type> -irlen <count> [-ircapture <count>] "
"[-irmask <count>] [-enable|-disable]",
.jim_handler = jim_jtag_newtap,
.help = "Create a new TAP instance named basename.tap_type, "
"and appends it to the scan chain.",
.usage = "basename tap_type '-irlen' count "
"['-enable'|'-disable'] "
"['-expected_id' number] "
"['-ignore-version'] "
"['-ircapture' number] "
"['-mask' number] ",
},
{
.name = "tapisenabled",
.mode = COMMAND_EXEC,
.jim_handler = &jim_jtag_tap_enabler,
.help = "Returns a integer indicating TAP state (0/1)",
.usage = "<name>",
.jim_handler = jim_jtag_tap_enabler,
.help = "Returns a Tcl boolean (0/1) indicating whether "
"the TAP is enabled (1) or not (0).",
.usage = "tap_name",
},
{
.name = "tapenable",
.mode = COMMAND_EXEC,
.jim_handler = &jim_jtag_tap_enabler,
.help = "Enable the specified TAP",
.usage = "<name>",
.jim_handler = jim_jtag_tap_enabler,
.help = "Try to enable the specified TAP using the "
"'tap-enable' TAP event.",
.usage = "tap_name",
},
{
.name = "tapdisable",
.mode = COMMAND_EXEC,
.jim_handler = &jim_jtag_tap_enabler,
.help = "Enable the specified TAP",
.usage = "<name>",
.jim_handler = jim_jtag_tap_enabler,
.help = "Try to disable the specified TAP using the "
"'tap-disable' TAP event.",
.usage = "tap_name",
},
{
.name = "configure",
.mode = COMMAND_EXEC,
.jim_handler = &jim_jtag_configure,
.help = "Enable the specified TAP",
.usage = "<name> [<key> <value> ...]",
.jim_handler = jim_jtag_configure,
.help = "Provide a Tcl handler for the specified "
"TAP event.",
.usage = "tap_name '-event' event_name handler",
},
{
.name = "cget",
.mode = COMMAND_EXEC,
.jim_handler = &jim_jtag_configure,
.help = "Enable the specified TAP",
.usage = "<name> [<key> <value> ...]",
.jim_handler = jim_jtag_configure,
.help = "Return any Tcl handler for the specified "
"TAP event.",
.usage = "tap_name '-event' event_name",
},
{
.name = "names",
.mode = COMMAND_ANY,
.jim_handler = &jim_jtag_names,
.help = "Returns list of all JTAG tap names",
.jim_handler = jim_jtag_names,
.help = "Returns list of all JTAG tap names.",
},
{
.chain = jtag_command_handlers_to_move,
@@ -1574,34 +1603,38 @@ COMMAND_HANDLER(handle_tms_sequence_command)
static const struct command_registration jtag_command_handlers[] = {
{
.name = "interface",
.handler = &handle_interface_command,
.handler = handle_interface_command,
.mode = COMMAND_CONFIG,
.help = "select a JTAG interface",
.usage = "<driver_name>",
.help = "Select a JTAG interface",
.usage = "driver_name",
},
{
.name = "interface_list",
.handler = &handle_interface_list_command,
.handler = handle_interface_list_command,
.mode = COMMAND_ANY,
.help = "list all built-in interfaces",
.help = "List all built-in interfaces",
},
{
.name = "jtag_khz",
.handler = &handle_jtag_khz_command,
.handler = handle_jtag_khz_command,
.mode = COMMAND_ANY,
.help = "set maximum jtag speed (if supported)",
.usage = "<khz:0=rtck>",
.help = "With an argument, change to the specified maximum "
"jtag speed. Pass 0 to require adaptive clocking. "
"With or without argument, display current setting.",
.usage = "[khz]",
},
{
.name = "jtag_rclk",
.handler = &handle_jtag_rclk_command,
.handler = handle_jtag_rclk_command,
.mode = COMMAND_ANY,
.help = "set JTAG speed to RCLK or use fallback speed",
.usage = "<fallback_speed_khz>",
.help = "With an argument, change to to use adaptive clocking "
"if possible; else to use the fallback speed. "
"With or without argument, display current setting.",
.usage = "[fallback_speed_khz]",
},
{
.name = "reset_config",
.handler = &handle_reset_config_command,
.handler = handle_reset_config_command,
.mode = COMMAND_ANY,
.help = "configure JTAG reset behavior",
.usage = "[none|trst_only|srst_only|trst_and_srst] "
@@ -1612,79 +1645,87 @@ static const struct command_registration jtag_command_handlers[] = {
},
{
.name = "jtag_nsrst_delay",
.handler = &handle_jtag_nsrst_delay_command,
.handler = handle_jtag_nsrst_delay_command,
.mode = COMMAND_ANY,
.help = "delay after deasserting srst in ms",
.usage = "<ms>",
.usage = "[milliseconds]",
},
{
.name = "jtag_ntrst_delay",
.handler = &handle_jtag_ntrst_delay_command,
.handler = handle_jtag_ntrst_delay_command,
.mode = COMMAND_ANY,
.help = "delay after deasserting trst in ms",
.usage = "<ms>"
.usage = "[milliseconds]",
},
{
.name = "jtag_nsrst_assert_width",
.handler = &handle_jtag_nsrst_assert_width_command,
.handler = handle_jtag_nsrst_assert_width_command,
.mode = COMMAND_ANY,
.help = "delay after asserting srst in ms",
.usage = "<ms>"
.usage = "[milliseconds]",
},
{
.name = "jtag_ntrst_assert_width",
.handler = &handle_jtag_ntrst_assert_width_command,
.handler = handle_jtag_ntrst_assert_width_command,
.mode = COMMAND_ANY,
.help = "delay after asserting trst in ms",
.usage = "<ms>"
.usage = "[milliseconds]",
},
{
.name = "scan_chain",
.handler = &handle_scan_chain_command,
.mode = COMMAND_EXEC,
.handler = handle_scan_chain_command,
.mode = COMMAND_ANY,
.help = "print current scan chain configuration",
},
{
.name = "jtag_reset",
.handler = &handle_jtag_reset_command,
.handler = handle_jtag_reset_command,
.mode = COMMAND_EXEC,
.help = "toggle reset lines",
.usage = "<trst> <srst>",
.help = "Set reset line values. Value '1' is active, "
"value '0' is inactive.",
.usage = "trst_active srst_active",
},
{
.name = "runtest",
.handler = &handle_runtest_command,
.handler = handle_runtest_command,
.mode = COMMAND_EXEC,
.help = "move to Run-Test/Idle, and execute <num_cycles>",
.usage = "<num_cycles>"
.help = "Move to Run-Test/Idle, and issue TCK for num_cycles.",
.usage = "num_cycles"
},
{
.name = "irscan",
.handler = &handle_irscan_command,
.handler = handle_irscan_command,
.mode = COMMAND_EXEC,
.help = "execute IR scan",
.usage = "<device> <instr> [dev2] [instr2] ...",
.help = "Execute Instruction Register (DR) scan. The "
"specified opcodes are put into each TAP's IR, "
"and other TAPs are put in BYPASS.",
.usage = "[tap_name instruction]* ['-endstate' state_name]",
},
{
.name = "verify_ircapture",
.handler = &handle_verify_ircapture_command,
.handler = handle_verify_ircapture_command,
.mode = COMMAND_ANY,
.help = "verify value captured during Capture-IR",
.usage = "<enable | disable>",
.help = "Display or assign flag controlling whether to "
"verify values captured during Capture-IR.",
.usage = "['enable'|'disable']",
},
{
.name = "verify_jtag",
.handler = &handle_verify_jtag_command,
.handler = handle_verify_jtag_command,
.mode = COMMAND_ANY,
.help = "verify value capture",
.usage = "<enable | disable>",
.help = "Display or assign flag controlling whether to "
"verify values captured during IR and DR scans.",
.usage = "['enable'|'disable']",
},
{
.name = "tms_sequence",
.handler = &handle_tms_sequence_command,
.handler = handle_tms_sequence_command,
.mode = COMMAND_ANY,
.help = "choose short(default) or long tms_sequence",
.usage = "<short | long>",
.help = "Display or change what style TMS sequences to use "
"for JTAG state transitions: short (default) or "
"long. Only for working around JTAG bugs.",
/* Specifically for working around DRIVER bugs... */
.usage = "['short'|'long']",
},
{
.name = "jtag",

View File

@@ -50,7 +50,7 @@ static __inline__ void waitQueue(void)
// waitIdle();
}
static void sampleShiftRegister(void)
static __inline__ void sampleShiftRegister(void)
{
#if 0
cyg_uint32 dummy;
@@ -59,8 +59,7 @@ static void sampleShiftRegister(void)
#endif
}
/* -O3 will inline this for us */
static void setCurrentState(enum tap_state state)
static __inline__ void setCurrentState(enum tap_state state)
{
cyg_uint32 a;
a = state;

View File

@@ -55,6 +55,11 @@
#include <time.h>
#ifdef CYGPKG_HAL_NIOS2
#include <cyg/hal/io.h>
#include <cyg/firmwareutil/firmwareutil.h>
#endif
#define ZYLIN_VERSION GIT_ZY1000_VERSION
#define ZYLIN_DATE __DATE__
#define ZYLIN_TIME __TIME__
@@ -127,6 +132,13 @@ static int zy1000_power_dropout(int *dropout)
void zy1000_reset(int trst, int srst)
{
LOG_DEBUG("zy1000 trst=%d, srst=%d", trst, srst);
/* flush the JTAG FIFO. Not flushing the queue before messing with
* reset has such interesting bugs as causing hard to reproduce
* RCLK bugs as RCLK will stop responding when TRST is asserted
*/
waitIdle();
if (!srst)
{
ZY1000_POKE(ZY1000_JTAG_BASE + 0x14, 0x00000001);
@@ -151,7 +163,6 @@ void zy1000_reset(int trst, int srst)
if (trst||(srst && (jtag_get_reset_config() & RESET_SRST_PULLS_TRST)))
{
waitIdle();
/* we're now in the RESET state until trst is deasserted */
ZY1000_POKE(ZY1000_JTAG_BASE + 0x20, TAP_RESET);
} else
@@ -188,6 +199,9 @@ void zy1000_reset(int trst, int srst)
int zy1000_speed(int speed)
{
/* flush JTAG master FIFO before setting speed */
waitIdle();
if (speed == 0)
{
/*0 means RCLK*/
@@ -322,33 +336,57 @@ static int jim_zy1000_version(Jim_Interp *interp, int argc, Jim_Obj *const *argv
#ifdef CYGPKG_HAL_NIOS2
struct info_forward
{
void *data;
struct cyg_upgrade_info *upgraded_file;
};
static void report_info(void *data, const char * format, va_list args)
{
char *s = alloc_vprintf(format, args);
LOG_USER_N("%s", s);
free(s);
}
struct cyg_upgrade_info firmware_info =
{
(cyg_uint8 *)0x84000000,
"/ram/firmware.phi",
"Firmware",
0x0300000,
0x1f00000 -
0x0300000,
"ZylinNiosFirmware\n",
report_info,
};
static int jim_zy1000_writefirmware(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
{
if (argc != 2)
return JIM_ERR;
int length;
int stat;
const char *str = Jim_GetString(argv[1], &length);
/* BUG!!!! skip header! */
void *firmware_address=0x4000000;
int firmware_length=0x100000;
if (length>firmware_length)
/* */
int tmpFile;
if ((tmpFile = open(firmware_info.file, O_RDWR | O_CREAT | O_TRUNC)) <= 0)
{
return JIM_ERR;
}
bool success;
success = write(tmpFile, str, length) == length;
close(tmpFile);
if (!success)
return JIM_ERR;
void *err_addr;
if (!cyg_firmware_upgrade(NULL, firmware_info))
return JIM_ERR;
if ((stat = flash_erase((void *)firmware_address, firmware_length, (void **)&err_addr)) != 0)
{
return JIM_ERR;
}
if ((stat = flash_program(firmware_address, str, length, (void **)&err_addr)) != 0)
return JIM_ERR;
return JIM_OK;
return JIM_OK;
}
#endif
@@ -803,29 +841,32 @@ void embeddedice_write_dcc(struct jtag_tap *tap, int reg_addr, uint8_t *buffer,
static const struct command_registration zy1000_commands[] = {
{
.name = "power",
.handler = &handle_power_command,
.handler = handle_power_command,
.mode = COMMAND_ANY,
.help = "turn power switch to target on/off. No arguments - print status.",
.usage = "power <on/off>",
.help = "Turn power switch to target on/off. "
"With no arguments, prints status.",
.usage = "('on'|'off)",
},
{
.name = "zy1000_version",
.mode = COMMAND_ANY,
.jim_handler = &jim_zy1000_version,
.help = "print version info for zy1000",
.jim_handler = jim_zy1000_version,
.help = "Print version info for zy1000.",
.usage = "['openocd'|'zy1000'|'date'|'time'|'pcb'|'fpga']",
},
{
.name = "powerstatus",
.mode = COMMAND_ANY,
.jim_handler = & zylinjtag_Jim_Command_powerstatus,
.help = "print power status of target",
.jim_handler = zylinjtag_Jim_Command_powerstatus,
.help = "Returns power status of target",
},
#ifdef CYGPKG_HAL_NIOS2
{
.name = "updatezy1000firmware",
.mode = COMMAND_ANY,
.jim_handler = &jim_zy1000_writefirmware,
.jim_handler = jim_zy1000_writefirmware,
.help = "writes firmware to flash",
/* .usage = "some_string", */
},
#endif
COMMAND_REGISTRATION_DONE

View File

@@ -76,7 +76,7 @@ COMMAND_HANDLER(handle_pld_device_command)
/* register pld specific commands */
int retval;
if (pld_drivers[i]->commands) {
retval = register_commands(CMD_CTX, NULL,
retval = register_commands(CMD_CTX, NULL,
pld_drivers[i]->commands);
if (ERROR_OK != retval)
{
@@ -89,10 +89,12 @@ COMMAND_HANDLER(handle_pld_device_command)
c->driver = pld_drivers[i];
c->next = NULL;
retval = CALL_COMMAND_HANDLER(pld_drivers[i]->pld_device_command, c);
retval = CALL_COMMAND_HANDLER(
pld_drivers[i]->pld_device_command, c);
if (ERROR_OK != retval)
{
LOG_ERROR("'%s' driver rejected pld device", CMD_ARGV[0]);
LOG_ERROR("'%s' driver rejected pld device",
CMD_ARGV[0]);
free(c);
return ERROR_OK;
}
@@ -191,16 +193,16 @@ COMMAND_HANDLER(handle_pld_load_command)
static const struct command_registration pld_exec_command_handlers[] = {
{
.name = "devices",
.handler = &handle_pld_devices_command,
.handler = handle_pld_devices_command,
.mode = COMMAND_EXEC,
.help = "list configured pld devices",
},
{
.name = "load",
.handler = &handle_pld_load_command,
.handler = handle_pld_load_command,
.mode = COMMAND_EXEC,
.help = "load configuration file into PLD",
.usage = "<device#> <file>",
.usage = "pld_num filename",
},
COMMAND_REGISTRATION_DONE
};
@@ -234,14 +236,14 @@ static const struct command_registration pld_config_command_handlers[] = {
{
.name = "device",
.mode = COMMAND_CONFIG,
.handler = &handle_pld_device_command,
.handler = handle_pld_device_command,
.help = "configure a PLD device",
.usage = "<driver> ...",
.usage = "driver_name [driver_args ... ]",
},
{
.name = "init",
.mode = COMMAND_CONFIG,
.handler = &handle_pld_init_command,
.handler = handle_pld_init_command,
.help = "initialize PLD devices",
},
COMMAND_REGISTRATION_DONE
@@ -251,7 +253,6 @@ static const struct command_registration pld_command_handler[] = {
.name = "pld",
.mode = COMMAND_ANY,
.help = "programmable logic device commands",
.chain = pld_config_command_handlers,
},
COMMAND_REGISTRATION_DONE

View File

@@ -237,9 +237,9 @@ static const struct command_registration virtex2_exec_command_handlers[] = {
{
.name = "read_stat",
.mode = COMMAND_EXEC,
.handler = &virtex2_handle_read_stat_command,
.handler = virtex2_handle_read_stat_command,
.help = "read status register",
.usage = "<device_id>",
.usage = "pld_num",
},
COMMAND_REGISTRATION_DONE
};

View File

@@ -37,6 +37,15 @@
#include <jtag/jtag.h>
/**
* @file
* GDB server implementation.
*
* This implements the GDB Remote Serial Protocol, over TCP connections,
* giving GDB access to the JTAG or other hardware debugging facilities
* found in most modern embedded processors.
*/
/* private connection data for GDB */
struct gdb_connection
{
@@ -65,10 +74,10 @@ static struct gdb_connection *current_gdb_connection;
static int gdb_breakpoint_override;
static enum breakpoint_type gdb_breakpoint_override_type;
extern int gdb_error(struct connection *connection, int retval);
static int gdb_error(struct connection *connection, int retval);
static unsigned short gdb_port = 3333;
static unsigned short gdb_port_next = 0;
static const char *DIGITS = "0123456789abcdef";
static const char DIGITS[16] = "0123456789abcdef";
static void gdb_log_callback(void *priv, const char *file, unsigned line,
const char *function, const char *string);
@@ -80,15 +89,17 @@ int gdb_actual_connections;
/* set if we are sending a memory map to gdb
* via qXfer:memory-map:read packet */
/* enabled by default*/
int gdb_use_memory_map = 1;
static int gdb_use_memory_map = 1;
/* enabled by default*/
int gdb_flash_program = 1;
static int gdb_flash_program = 1;
/* if set, data aborts cause an error to be reported in memory read packets
* see the code in gdb_read_memory_packet() for further explanations */
int gdb_report_data_abort = 0;
* see the code in gdb_read_memory_packet() for further explanations.
* Disabled by default.
*/
static int gdb_report_data_abort;
int gdb_last_signal(struct target *target)
static int gdb_last_signal(struct target *target)
{
switch (target->debug_reason)
{
@@ -108,7 +119,8 @@ int gdb_last_signal(struct target *target)
}
}
int check_pending(struct connection *connection, int timeout_s, int *got_data)
static int check_pending(struct connection *connection,
int timeout_s, int *got_data)
{
/* a non-blocking socket will block if there is 0 bytes available on the socket,
* but return with as many bytes as are available immediately
@@ -275,14 +287,14 @@ static inline int gdb_get_char_fast(struct connection *connection, int* next_cha
}
int gdb_get_char(struct connection *connection, int* next_char)
static int gdb_get_char(struct connection *connection, int* next_char)
{
struct gdb_connection *gdb_con = connection->priv;
return gdb_get_char_fast(connection, next_char, &gdb_con->buf_p, &gdb_con->buf_cnt);
}
int gdb_putback_char(struct connection *connection, int last_char)
static int gdb_putback_char(struct connection *connection, int last_char)
{
struct gdb_connection *gdb_con = connection->priv;
@@ -302,7 +314,7 @@ int gdb_putback_char(struct connection *connection, int last_char)
/* The only way we can detect that the socket is closed is the first time
* we write to it, we will fail. Subsequent write operations will
* succeed. Shudder! */
int gdb_write(struct connection *connection, void *data, int len)
static int gdb_write(struct connection *connection, void *data, int len)
{
struct gdb_connection *gdb_con = connection->priv;
if (gdb_con->closed)
@@ -327,7 +339,8 @@ int gdb_write(struct connection *connection, void *data, int len)
return ERROR_SERVER_REMOTE_CLOSED;
}
int gdb_put_packet_inner(struct connection *connection, char *buffer, int len)
static int gdb_put_packet_inner(struct connection *connection,
char *buffer, int len)
{
int i;
unsigned char my_checksum = 0;
@@ -350,7 +363,8 @@ int gdb_put_packet_inner(struct connection *connection, char *buffer, int len)
int gotdata;
for (;;)
{
if ((retval = check_pending(connection, 0, &gotdata)) != ERROR_OK)
retval = check_pending(connection, 0, &gotdata);
if (retval != ERROR_OK)
return retval;
if (!gotdata)
break;
@@ -468,7 +482,7 @@ int gdb_put_packet_inner(struct connection *connection, char *buffer, int len)
return ERROR_OK;
}
int gdb_put_packet(struct connection *connection, char *buffer, int len)
static int gdb_put_packet(struct connection *connection, char *buffer, int len)
{
struct gdb_connection *gdb_con = connection->priv;
gdb_con->busy = 1;
@@ -607,7 +621,8 @@ static __inline__ int fetch_packet(struct connection *connection, int *checksum_
return ERROR_OK;
}
int gdb_get_packet_inner(struct connection *connection, char *buffer, int *len)
static int gdb_get_packet_inner(struct connection *connection,
char *buffer, int *len)
{
int character;
int retval;
@@ -682,7 +697,7 @@ int gdb_get_packet_inner(struct connection *connection, char *buffer, int *len)
return ERROR_OK;
}
int gdb_get_packet(struct connection *connection, char *buffer, int *len)
static int gdb_get_packet(struct connection *connection, char *buffer, int *len)
{
struct gdb_connection *gdb_con = connection->priv;
gdb_con->busy = 1;
@@ -691,7 +706,7 @@ int gdb_get_packet(struct connection *connection, char *buffer, int *len)
return retval;
}
int gdb_output_con(struct connection *connection, const char* line)
static int gdb_output_con(struct connection *connection, const char* line)
{
char *hex_buffer;
int i, bin_size;
@@ -713,7 +728,7 @@ int gdb_output_con(struct connection *connection, const char* line)
return retval;
}
int gdb_output(struct command_context *context, const char* line)
static int gdb_output(struct command_context *context, const char* line)
{
/* this will be dumped to the log and also sent as an O packet if possible */
LOG_USER_N("%s", line);
@@ -758,7 +773,8 @@ static void gdb_frontend_halted(struct target *target, struct connection *connec
}
}
int gdb_target_callback_event_handler(struct target *target, enum target_event event, void *priv)
static int gdb_target_callback_event_handler(struct target *target,
enum target_event event, void *priv)
{
int retval;
struct connection *connection = priv;
@@ -786,7 +802,7 @@ int gdb_target_callback_event_handler(struct target *target, enum target_event e
return ERROR_OK;
}
int gdb_new_connection(struct connection *connection)
static int gdb_new_connection(struct connection *connection)
{
struct gdb_connection *gdb_connection = malloc(sizeof(struct gdb_connection));
struct gdb_service *gdb_service = connection->service->priv;
@@ -842,7 +858,7 @@ int gdb_new_connection(struct connection *connection)
return ERROR_OK;
}
int gdb_connection_closed(struct connection *connection)
static int gdb_connection_closed(struct connection *connection)
{
struct gdb_service *gdb_service = connection->service->priv;
struct gdb_connection *gdb_connection = connection->priv;
@@ -889,14 +905,15 @@ int gdb_connection_closed(struct connection *connection)
return ERROR_OK;
}
void gdb_send_error(struct connection *connection, uint8_t the_error)
static void gdb_send_error(struct connection *connection, uint8_t the_error)
{
char err[4];
snprintf(err, 4, "E%2.2X", the_error);
gdb_put_packet(connection, err, 3);
}
int gdb_last_signal_packet(struct connection *connection, struct target *target, char* packet, int packet_size)
static int gdb_last_signal_packet(struct connection *connection,
struct target *target, char* packet, int packet_size)
{
char sig_reply[4];
int signal;
@@ -926,7 +943,8 @@ static int gdb_reg_pos(struct target *target, int pos, int len)
* The format of reg->value is little endian
*
*/
void gdb_str_to_target(struct target *target, char *tstr, struct reg *reg)
static void gdb_str_to_target(struct target *target,
char *tstr, struct reg *reg)
{
int i;
@@ -943,7 +961,7 @@ void gdb_str_to_target(struct target *target, char *tstr, struct reg *reg)
}
}
static int hextoint(char c)
static int hextoint(int c)
{
if (c>='0'&&c<='9')
{
@@ -959,7 +977,8 @@ static int hextoint(char c)
}
/* copy over in register buffer */
void gdb_target_to_reg(struct target *target, char *tstr, int str_len, uint8_t *bin)
static void gdb_target_to_reg(struct target *target,
char *tstr, int str_len, uint8_t *bin)
{
if (str_len % 2)
{
@@ -978,7 +997,8 @@ void gdb_target_to_reg(struct target *target, char *tstr, int str_len, uint8_t *
}
}
int gdb_get_registers_packet(struct connection *connection, struct target *target, char* packet, int packet_size)
static int gdb_get_registers_packet(struct connection *connection,
struct target *target, char* packet, int packet_size)
{
struct reg **reg_list;
int reg_list_size;
@@ -1028,7 +1048,8 @@ int gdb_get_registers_packet(struct connection *connection, struct target *targe
return ERROR_OK;
}
int gdb_set_registers_packet(struct connection *connection, struct target *target, char *packet, int packet_size)
static int gdb_set_registers_packet(struct connection *connection,
struct target *target, char *packet, int packet_size)
{
int i;
struct reg **reg_list;
@@ -1086,7 +1107,8 @@ int gdb_set_registers_packet(struct connection *connection, struct target *targe
return ERROR_OK;
}
int gdb_get_register_packet(struct connection *connection, struct target *target, char *packet, int packet_size)
static int gdb_get_register_packet(struct connection *connection,
struct target *target, char *packet, int packet_size)
{
char *reg_packet;
int reg_num = strtoul(packet + 1, NULL, 16);
@@ -1121,7 +1143,8 @@ int gdb_get_register_packet(struct connection *connection, struct target *target
return ERROR_OK;
}
int gdb_set_register_packet(struct connection *connection, struct target *target, char *packet, int packet_size)
static int gdb_set_register_packet(struct connection *connection,
struct target *target, char *packet, int packet_size)
{
char *separator;
uint8_t *bin_buf;
@@ -1167,7 +1190,7 @@ int gdb_set_register_packet(struct connection *connection, struct target *target
return ERROR_OK;
}
int gdb_error(struct connection *connection, int retval)
static int gdb_error(struct connection *connection, int retval)
{
switch (retval)
{
@@ -1198,7 +1221,8 @@ int gdb_error(struct connection *connection, int retval)
*
* 8191 bytes by the looks of it. Why 8191 bytes instead of 8192?????
*/
int gdb_read_memory_packet(struct connection *connection, struct target *target, char *packet, int packet_size)
static int gdb_read_memory_packet(struct connection *connection,
struct target *target, char *packet, int packet_size)
{
char *separator;
uint32_t addr = 0;
@@ -1272,7 +1296,8 @@ int gdb_read_memory_packet(struct connection *connection, struct target *target,
return retval;
}
int gdb_write_memory_packet(struct connection *connection, struct target *target, char *packet, int packet_size)
static int gdb_write_memory_packet(struct connection *connection,
struct target *target, char *packet, int packet_size)
{
char *separator;
uint32_t addr = 0;
@@ -1329,7 +1354,8 @@ int gdb_write_memory_packet(struct connection *connection, struct target *target
return retval;
}
int gdb_write_memory_binary_packet(struct connection *connection, struct target *target, char *packet, int packet_size)
static int gdb_write_memory_binary_packet(struct connection *connection,
struct target *target, char *packet, int packet_size)
{
char *separator;
uint32_t addr = 0;
@@ -1377,7 +1403,8 @@ int gdb_write_memory_binary_packet(struct connection *connection, struct target
return ERROR_OK;
}
int gdb_step_continue_packet(struct connection *connection, struct target *target, char *packet, int packet_size)
static int gdb_step_continue_packet(struct connection *connection,
struct target *target, char *packet, int packet_size)
{
int current = 0;
uint32_t address = 0x0;
@@ -1410,11 +1437,12 @@ int gdb_step_continue_packet(struct connection *connection, struct target *targe
return retval;
}
int gdb_breakpoint_watchpoint_packet(struct connection *connection, struct target *target, char *packet, int packet_size)
static int gdb_breakpoint_watchpoint_packet(struct connection *connection,
struct target *target, char *packet, int packet_size)
{
int type;
enum breakpoint_type bp_type = BKPT_SOFT /* dummy init to avoid warning */;
enum watchpoint_rw wp_type;
enum watchpoint_rw wp_type = WPT_READ /* dummy init to avoid warning */;
uint32_t address;
uint32_t size;
char *separator;
@@ -1434,6 +1462,12 @@ int gdb_breakpoint_watchpoint_packet(struct connection *connection, struct targe
wp_type = WPT_READ;
else if (type == 4) /* access watchpoint */
wp_type = WPT_ACCESS;
else
{
LOG_ERROR("invalid gdb watch/breakpoint type(%d), dropping connection", type);
return ERROR_SERVER_REMOTE_CLOSED;
}
if (gdb_breakpoint_override && ((bp_type == BKPT_SOFT)||(bp_type == BKPT_HARD)))
{
@@ -1484,7 +1518,7 @@ int gdb_breakpoint_watchpoint_packet(struct connection *connection, struct targe
{
if (packet[0] == 'Z')
{
if ((retval = watchpoint_add(target, address, size, type-2, 0, 0xffffffffu)) != ERROR_OK)
if ((retval = watchpoint_add(target, address, size, wp_type, 0, 0xffffffffu)) != ERROR_OK)
{
if ((retval = gdb_error(connection, retval)) != ERROR_OK)
return retval;
@@ -1508,8 +1542,11 @@ int gdb_breakpoint_watchpoint_packet(struct connection *connection, struct targe
return ERROR_OK;
}
/* print out a string and allocate more space as needed, mainly used for XML at this point */
void xml_printf(int *retval, char **xml, int *pos, int *size, const char *fmt, ...)
/* print out a string and allocate more space as needed,
* mainly used for XML at this point
*/
static void xml_printf(int *retval, char **xml, int *pos, int *size,
const char *fmt, ...)
{
if (*retval != ERROR_OK)
{
@@ -1576,22 +1613,6 @@ static int decode_xfer_read(char *buf, char **annex, int *ofs, unsigned int *len
return 0;
}
int gdb_calc_blocksize(struct flash_bank *bank)
{
uint32_t i;
uint32_t block_size = 0xffffffff;
/* loop through all sectors and return smallest sector size */
for (i = 0; i < (uint32_t)bank->num_sectors; i++)
{
if (bank->sectors[i].size < block_size)
block_size = bank->sectors[i].size;
}
return block_size;
}
static int compare_bank (const void * a, const void * b)
{
struct flash_bank *b1, *b2;
@@ -1610,7 +1631,151 @@ static int compare_bank (const void * a, const void * b)
}
}
int gdb_query_packet(struct connection *connection, struct target *target, char *packet, int packet_size)
static int gdb_memory_map(struct connection *connection,
struct target *target, char *packet, int packet_size)
{
/* We get away with only specifying flash here. Regions that are not
* specified are treated as if we provided no memory map(if not we
* could detect the holes and mark them as RAM).
* Normally we only execute this code once, but no big deal if we
* have to regenerate it a couple of times.
*/
struct flash_bank *p;
char *xml = NULL;
int size = 0;
int pos = 0;
int retval = ERROR_OK;
struct flash_bank **banks;
int offset;
int length;
char *separator;
uint32_t ram_start = 0;
int i;
/* skip command character */
packet += 23;
offset = strtoul(packet, &separator, 16);
length = strtoul(separator + 1, &separator, 16);
xml_printf(&retval, &xml, &pos, &size, "<memory-map>\n");
/* Sort banks in ascending order. We need to report non-flash
* memory as ram (or rather read/write) by default for GDB, since
* it has no concept of non-cacheable read/write memory (i/o etc).
*
* FIXME Most non-flash addresses are *NOT* RAM! Don't lie.
* Current versions of GDB assume unlisted addresses are RAM...
*/
banks = malloc(sizeof(struct flash_bank *)*flash_get_bank_count());
for (i = 0; i < flash_get_bank_count(); i++) {
p = get_flash_bank_by_num(i);
if (p == NULL) {
free(banks);
retval = ERROR_FAIL;
gdb_send_error(connection, retval);
return retval;
}
banks[i] = p;
}
qsort(banks, flash_get_bank_count(), sizeof(struct flash_bank *),
compare_bank);
for (i = 0; i < flash_get_bank_count(); i++) {
int j;
unsigned sector_size = 0;
uint32_t start, end;
p = banks[i];
start = p->base;
end = p->base + p->size;
if (ram_start < p->base)
xml_printf(&retval, &xml, &pos, &size,
"<memory type=\"ram\" start=\"0x%x\" "
"length=\"0x%x\"/>\n",
ram_start, p->base - ram_start);
/* Report adjacent groups of same-size sectors. So for
* example top boot CFI flash will list an initial region
* with several large sectors (maybe 128KB) and several
* smaller ones at the end (maybe 32KB). STR7 will have
* regions with 8KB, 32KB, and 64KB sectors; etc.
*/
for (j = 0; j < p->num_sectors; j++) {
unsigned group_len;
/* Maybe start a new group of sectors. */
if (sector_size == 0) {
start = p->base + p->sectors[j].offset;
xml_printf(&retval, &xml, &pos, &size,
"<memory type=\"flash\" "
"start=\"0x%x\" ",
start);
sector_size = p->sectors[j].size;
}
/* Does this finish a group of sectors?
* If not, continue an already-started group.
*/
if (j == p->num_sectors -1)
group_len = (p->base + p->size) - start;
else if (p->sectors[j + 1].size != sector_size)
group_len = p->base + p->sectors[j + 1].offset
- start;
else
continue;
xml_printf(&retval, &xml, &pos, &size,
"length=\"0x%x\">\n"
"<property name=\"blocksize\">"
"0x%x</property>\n"
"</memory>\n",
group_len,
sector_size);
sector_size = 0;
}
ram_start = p->base + p->size;
}
if (ram_start != 0)
xml_printf(&retval, &xml, &pos, &size,
"<memory type=\"ram\" start=\"0x%x\" "
"length=\"0x%x\"/>\n",
ram_start, 0-ram_start);
/* ELSE a flash chip could be at the very end of the 32 bit address
* space, in which case ram_start will be precisely 0
*/
free(banks);
banks = NULL;
xml_printf(&retval, &xml, &pos, &size, "</memory-map>\n");
if (retval != ERROR_OK) {
gdb_send_error(connection, retval);
return retval;
}
if (offset + length > pos)
length = pos - offset;
char *t = malloc(length + 1);
t[0] = 'l';
memcpy(t + 1, xml + offset, length);
gdb_put_packet(connection, t, length + 1);
free(t);
free(xml);
return ERROR_OK;
}
static int gdb_query_packet(struct connection *connection,
struct target *target, char *packet, int packet_size)
{
struct command_context *cmd_ctx = connection->cmd_ctx;
struct gdb_connection *gdb_connection = connection->priv;
@@ -1709,112 +1874,9 @@ int gdb_query_packet(struct connection *connection, struct target *target, char
return ERROR_OK;
}
else if (strstr(packet, "qXfer:memory-map:read::") && (flash_get_bank_count() > 0))
{
/* We get away with only specifying flash here. Regions that are not
* specified are treated as if we provided no memory map(if not we
* could detect the holes and mark them as RAM).
* Normally we only execute this code once, but no big deal if we
* have to regenerate it a couple of times. */
struct flash_bank *p;
char *xml = NULL;
int size = 0;
int pos = 0;
int retval = ERROR_OK;
int offset;
int length;
char *separator;
int blocksize;
/* skip command character */
packet += 23;
offset = strtoul(packet, &separator, 16);
length = strtoul(separator + 1, &separator, 16);
xml_printf(&retval, &xml, &pos, &size, "<memory-map>\n");
/*
sort banks in ascending order, we need to make non-flash memory be ram(or rather
read/write) by default for GDB.
GDB does not have a concept of non-cacheable read/write memory.
*/
struct flash_bank **banks = malloc(sizeof(struct flash_bank *)*flash_get_bank_count());
int i;
for (i = 0; i < flash_get_bank_count(); i++)
{
p = get_flash_bank_by_num(i);
if (p == NULL)
{
free(banks);
retval = ERROR_FAIL;
gdb_send_error(connection, retval);
return retval;
}
banks[i]=p;
}
qsort(banks, flash_get_bank_count(), sizeof(struct flash_bank *), compare_bank);
uint32_t ram_start = 0;
for (i = 0; i < flash_get_bank_count(); i++)
{
p = banks[i];
if (ram_start < p->base)
{
xml_printf(&retval, &xml, &pos, &size, "<memory type=\"ram\" start=\"0x%x\" length=\"0x%x\"/>\n",
ram_start, p->base-ram_start);
}
/* if device has uneven sector sizes, eg. str7, lpc
* we pass the smallest sector size to gdb memory map */
blocksize = gdb_calc_blocksize(p);
xml_printf(&retval, &xml, &pos, &size, "<memory type=\"flash\" start=\"0x%x\" length=\"0x%x\">\n" \
"<property name=\"blocksize\">0x%x</property>\n" \
"</memory>\n", \
p->base, p->size, blocksize);
ram_start = p->base + p->size;
}
if (ram_start != 0)
{
xml_printf(&retval, &xml, &pos, &size, "<memory type=\"ram\" start=\"0x%x\" length=\"0x%x\"/>\n",
ram_start, 0-ram_start);
} else
{
/* a flash chip could be at the very end of the 32 bit address space, in which case
ram_start will be precisely 0 */
}
free(banks);
banks = NULL;
xml_printf(&retval, &xml, &pos, &size, "</memory-map>\n");
if (retval != ERROR_OK)
{
gdb_send_error(connection, retval);
return retval;
}
if (offset + length > pos)
{
length = pos - offset;
}
char *t = malloc(length + 1);
t[0] = 'l';
memcpy(t + 1, xml + offset, length);
gdb_put_packet(connection, t, length + 1);
free(t);
free(xml);
return ERROR_OK;
}
else if (strstr(packet, "qXfer:memory-map:read::")
&& (flash_get_bank_count() > 0))
return gdb_memory_map(connection, target, packet, packet_size);
else if (strstr(packet, "qXfer:features:read:"))
{
char *xml = NULL;
@@ -1866,7 +1928,8 @@ int gdb_query_packet(struct connection *connection, struct target *target, char
return ERROR_OK;
}
int gdb_v_packet(struct connection *connection, struct target *target, char *packet, int packet_size)
static int gdb_v_packet(struct connection *connection,
struct target *target, char *packet, int packet_size)
{
struct gdb_connection *gdb_connection = connection->priv;
struct gdb_service *gdb_service = connection->service->priv;
@@ -1913,9 +1976,19 @@ int gdb_v_packet(struct connection *connection, struct target *target, char *pac
flash_set_dirty();
/* perform any target specific operations before the erase */
target_call_event_callbacks(gdb_service->target, TARGET_EVENT_GDB_FLASH_ERASE_START);
result = flash_erase_address_range(gdb_service->target, addr, length);
target_call_event_callbacks(gdb_service->target, TARGET_EVENT_GDB_FLASH_ERASE_END);
target_call_event_callbacks(gdb_service->target,
TARGET_EVENT_GDB_FLASH_ERASE_START);
/* vFlashErase:addr,length messages require region start and
* end to be "block" aligned ... if padding is ever needed,
* GDB will have become dangerously confused.
*/
result = flash_erase_address_range(gdb_service->target,
false, addr, length);
/* perform any target specific operations after the erase */
target_call_event_callbacks(gdb_service->target,
TARGET_EVENT_GDB_FLASH_ERASE_END);
/* perform erase */
if (result != ERROR_OK)
@@ -2003,11 +2076,12 @@ int gdb_v_packet(struct connection *connection, struct target *target, char *pac
return ERROR_OK;
}
int gdb_detach(struct connection *connection, struct target *target)
static int gdb_detach(struct connection *connection, struct target *target)
{
struct gdb_service *gdb_service = connection->service->priv;
target_call_event_callbacks(gdb_service->target, TARGET_EVENT_GDB_DETACH);
target_call_event_callbacks(gdb_service->target,
TARGET_EVENT_GDB_DETACH);
return gdb_put_packet(connection, "OK", 2);
}
@@ -2027,9 +2101,6 @@ static void gdb_log_callback(void *priv, const char *file, unsigned line,
gdb_output_con(connection, string);
}
/* Do not allocate this on the stack */
char gdb_packet_buffer[GDB_BUFFER_SIZE];
static void gdb_sig_halted(struct connection *connection)
{
char sig_reply[4];
@@ -2038,8 +2109,11 @@ static void gdb_sig_halted(struct connection *connection)
}
int gdb_input_inner(struct connection *connection)
static int gdb_input_inner(struct connection *connection)
{
/* Do not allocate this on the stack */
static char gdb_packet_buffer[GDB_BUFFER_SIZE];
struct gdb_service *gdb_service = connection->service->priv;
struct target *target = gdb_service->target;
char *packet = gdb_packet_buffer;
@@ -2052,10 +2126,9 @@ int gdb_input_inner(struct connection *connection)
do
{
packet_size = GDB_BUFFER_SIZE-1;
if ((retval = gdb_get_packet(connection, packet, &packet_size)) != ERROR_OK)
{
retval = gdb_get_packet(connection, packet, &packet_size);
if (retval != ERROR_OK)
return retval;
}
/* terminate with zero */
packet[packet_size] = 0;
@@ -2087,32 +2160,48 @@ int gdb_input_inner(struct connection *connection)
break;
case 'q':
case 'Q':
retval = gdb_query_packet(connection, target, packet, packet_size);
retval = gdb_query_packet(connection,
target, packet,
packet_size);
break;
case 'g':
retval = gdb_get_registers_packet(connection, target, packet, packet_size);
retval = gdb_get_registers_packet(
connection, target,
packet, packet_size);
break;
case 'G':
retval = gdb_set_registers_packet(connection, target, packet, packet_size);
retval = gdb_set_registers_packet(
connection, target,
packet, packet_size);
break;
case 'p':
retval = gdb_get_register_packet(connection, target, packet, packet_size);
retval = gdb_get_register_packet(
connection, target,
packet, packet_size);
break;
case 'P':
retval = gdb_set_register_packet(connection, target, packet, packet_size);
retval = gdb_set_register_packet(
connection, target,
packet, packet_size);
break;
case 'm':
retval = gdb_read_memory_packet(connection, target, packet, packet_size);
retval = gdb_read_memory_packet(
connection, target,
packet, packet_size);
break;
case 'M':
retval = gdb_write_memory_packet(connection, target, packet, packet_size);
retval = gdb_write_memory_packet(
connection, target,
packet, packet_size);
break;
case 'z':
case 'Z':
retval = gdb_breakpoint_watchpoint_packet(connection, target, packet, packet_size);
break;
case '?':
gdb_last_signal_packet(connection, target, packet, packet_size);
gdb_last_signal_packet(
connection, target,
packet, packet_size);
break;
case 'c':
case 's':
@@ -2123,12 +2212,13 @@ int gdb_input_inner(struct connection *connection)
log_add_callback(gdb_log_callback, connection);
bool nostep = false;
bool already_running = false;
if (target->state == TARGET_RUNNING)
{
LOG_WARNING("The target is already running. Halt target before stepi/continue.");
retval = target_halt(target);
if (retval == ERROR_OK)
retval = target_wait_state(target, TARGET_HALTED, 100);
LOG_WARNING("WARNING! The target is already running. "
"All changes GDB did to registers will be discarded! "
"Waiting for target to halt.");
already_running = true;
} else if (target->state != TARGET_HALTED)
{
LOG_WARNING("The target is not in the halted nor running stated, stepi/continue ignored.");
@@ -2144,7 +2234,7 @@ int gdb_input_inner(struct connection *connection)
}
gdb_con->sync = false;
if ((retval!=ERROR_OK) || nostep)
if ((retval!=ERROR_OK) || (!already_running && nostep))
{
/* Either the target isn't in the halted state, then we can't
* step/continue. This might be early setup, etc.
@@ -2164,24 +2254,33 @@ int gdb_input_inner(struct connection *connection)
*/
gdb_con->frontend_state = TARGET_RUNNING;
target_call_event_callbacks(target, TARGET_EVENT_GDB_START);
int retval = gdb_step_continue_packet(connection, target, packet, packet_size);
if (retval != ERROR_OK)
if (!already_running)
{
/* we'll never receive a halted condition... issue a false one.. */
gdb_frontend_halted(target, connection);
int retval = gdb_step_continue_packet(connection, target, packet, packet_size);
if (retval != ERROR_OK)
{
/* we'll never receive a halted condition... issue a false one.. */
gdb_frontend_halted(target, connection);
}
}
}
}
break;
case 'v':
retval = gdb_v_packet(connection, target, packet, packet_size);
retval = gdb_v_packet(
connection, target,
packet, packet_size);
break;
case 'D':
retval = gdb_detach(connection, target);
extended_protocol = 0;
break;
case 'X':
if ((retval = gdb_write_memory_binary_packet(connection, target, packet, packet_size)) != ERROR_OK)
retval = gdb_write_memory_binary_packet(
connection, target,
packet, packet_size);
if (retval != ERROR_OK)
return retval;
break;
case 'k':
@@ -2236,7 +2335,7 @@ int gdb_input_inner(struct connection *connection)
return ERROR_OK;
}
int gdb_input(struct connection *connection)
static int gdb_input(struct connection *connection)
{
int retval = gdb_input_inner(connection);
struct gdb_connection *gdb_con = connection->priv;
@@ -2272,7 +2371,7 @@ static int gdb_target_start(struct target *target, uint16_t port)
return ERROR_OK;
}
int gdb_target_add_one(struct target *target)
static int gdb_target_add_one(struct target *target)
{
if (gdb_port == 0 && server_use_pipes == 0)
{
@@ -2411,7 +2510,7 @@ COMMAND_HANDLER(handle_gdb_breakpoint_override_command)
static const struct command_registration gdb_command_handlers[] = {
{
.name = "gdb_sync",
.handler = &handle_gdb_sync_command,
.handler = handle_gdb_sync_command,
.mode = COMMAND_ANY,
.help = "next stepi will return immediately allowing "
"GDB to fetch register state without affecting "
@@ -2419,39 +2518,41 @@ static const struct command_registration gdb_command_handlers[] = {
},
{
.name = "gdb_port",
.handler = &handle_gdb_port_command,
.handler = handle_gdb_port_command,
.mode = COMMAND_ANY,
.help = "daemon configuration command gdb_port",
.usage = "<port>",
.help = "Display or specify base port on which to listen "
"for incoming GDB connections. "
"No arguments reports GDB port; zero disables.",
.usage = "[port_num]",
},
{
.name = "gdb_memory_map",
.handler = &handle_gdb_memory_map_command,
.handler = handle_gdb_memory_map_command,
.mode = COMMAND_CONFIG,
.help = "enable or disable memory map",
.usage = "enable|disable"
.usage = "('enable'|'disable')"
},
{
.name = "gdb_flash_program",
.handler = &handle_gdb_flash_program_command,
.handler = handle_gdb_flash_program_command,
.mode = COMMAND_CONFIG,
.help = "enable or disable flash program",
.usage = "enable|disable"
.usage = "('enable'|'disable')"
},
{
.name = "gdb_report_data_abort",
.handler = &handle_gdb_report_data_abort_command,
.handler = handle_gdb_report_data_abort_command,
.mode = COMMAND_CONFIG,
.help = "enable or disable reporting data aborts",
.usage = "enable|disable"
.usage = "('enable'|'disable')"
},
{
.name = "gdb_breakpoint_override",
.handler = &handle_gdb_breakpoint_override_command,
.mode = COMMAND_EXEC,
.help = "force type of breakpoint "
"used by gdb 'break' commands.",
.usage = "hard|soft|disable",
.handler = handle_gdb_breakpoint_override_command,
.mode = COMMAND_ANY,
.help = "Display or specify type of breakpoint "
"to be used by gdb 'break' commands.",
.usage = "('hard'|'soft'|'disable')"
},
COMMAND_REGISTRATION_DONE
};

View File

@@ -36,7 +36,6 @@ struct gdb_service
struct target *target;
};
int gdb_target_add_one(struct target *target);
int gdb_target_add_all(struct target *target);
int gdb_register_commands(struct command_context *command_context);

View File

@@ -118,11 +118,11 @@ static int httpd_Jim_Command_writeform(Jim_Interp *interp, int argc,
// Find length
const char *data;
int actual;
int retcode;
const char *script = alloc_printf("set dummy_val $httppostdata(%s); set dummy_val",
const char *script = alloc_printf(
"set dummy_val $httppostdata(%s); set dummy_val",
name);
retcode = Jim_Eval_Named(interp, script, __FILE__, __LINE__);
free((void *) script);
if (retcode != JIM_OK)
@@ -154,27 +154,25 @@ httpd_Jim_Command_formfetch(Jim_Interp *interp,
int argc,
Jim_Obj *const *argv)
{
if (argc != 2)
{
Jim_WrongNumArgs(interp, 1, argv, "method ?CMD_ARGV ...?");
return JIM_ERR;
}
char *name = (char*)Jim_GetString(argv[1], NULL);
if (argc != 2)
{
Jim_WrongNumArgs(interp, 1, argv, "method ?CMD_ARGV ...?");
return JIM_ERR;
}
char *name = (char*)Jim_GetString(argv[1], NULL);
const char *script = alloc_printf(
"set dummy_val $httppostdata(%s); set dummy_val",
name);
int retcode = Jim_Eval_Named(interp, script, __FILE__, __LINE__);
const char *script = alloc_printf("set dummy_val $httppostdata(%s); set dummy_val",
name);
int retcode = Jim_Eval_Named(interp, script, __FILE__, __LINE__);
free((void *) script);
if (retcode != JIM_OK)
{
Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
} else
{
Jim_SetResult(interp, Jim_GetResult(interp));
}
free((void *) script);
if (retcode != JIM_OK)
Jim_SetResult(interp, Jim_NewEmptyStringObj(interp));
else
Jim_SetResult(interp, Jim_GetResult(interp));
return JIM_OK;
return JIM_OK;
}
struct httpd_request
@@ -467,16 +465,16 @@ static struct MHD_Daemon * d;
static const struct command_registration httpd_command_handlers[] = {
{
.name = "formfetch",
.jim_handler = &httpd_Jim_Command_formfetch,
.jim_handler = httpd_Jim_Command_formfetch,
.mode = COMMAND_EXEC,
.usage = "<parameter_name>",
.usage = "parameter_name",
.help = "Reads a posted form value.",
},
{
.name = "writeform",
.jim_handler = &httpd_Jim_Command_writeform,
.jim_handler = httpd_Jim_Command_writeform,
.mode = COMMAND_EXEC,
.usage = "<parameter_name> <file>",
.usage = "parameter_name filename",
.help = "Writes a form value to a file.",
},
COMMAND_REGISTRATION_DONE

File diff suppressed because it is too large Load Diff

View File

@@ -2,7 +2,7 @@
<!DOCTYPE xsl:stylesheet [<!ENTITY nbsp "&#160;">]>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns="http://www.w3.org/TR/REC-html40" version="1.0">
<xsl:output method="html" version="4.0" indent="yes" encoding="UTF-8"
media-type="text/plain; charset=UTF-8"/>
<xsl:param name="pagetogenerate" select="UNDEFINED"/>
@@ -16,17 +16,17 @@
<html>
<head>
<title>OpenOCD debugger</title>
<meta http-equiv="Content-Type" content="text/html" charset="utf-8"/>
<link href="menuweb.css" rel="stylesheet" type="text/css"/>
<meta http-equiv="Content-Type" content="text/html" charset="utf-8"/>
<link href="menuweb.css" rel="stylesheet" type="text/css"/>
</head>
<tcl>
set console ""
set upload_filename /ram/upload
</tcl>
<body style="margin:0px;">
<div style="width:974px;height:85px;">
<div style="float:left;position:relative;left:32px;width:478px;">
@@ -92,17 +92,17 @@
</xsl:for-each>
<tr>
<td style="width:140px;height:35px;background-image:url('menu_cuts/v_1.png')">
</td>
</tr>
<tr>
<td style="width:140px;background-image:url('menu_cuts/v_2_tile.png')">
</td>
</tr>
<tr>
<td style="width:140px;height:140px;background-image:url('menu_cuts/v_3.png')">
</td>
</tr>
</table>
@@ -142,96 +142,96 @@
</xsl:for-each>
</tr>
</table>
</td>
</tr>
<tr>
<td colspan="6" style="height:30px;width:535px;background-image:url('menu_cuts/center_top.png');background-repeat: no-repeat;background-position:top right;">
<div style="width:500px;background-color:#ffffff;height:100%;">
&nbsp;
</div>
</td>
</tr>
<tr>
<td colspan="6" style="background-color:#ffffff;text-indent:30px;height:40px;">
<H1><xsl:value-of select="pageheading"/></H1>
</td>
</tr>
<tr style="height:100%;">
<td colspan="6" style="background-color:#ffffff;padding-left:30px;padding-right:30px;width=535px;height:100%;">
</td>
</tr>
<tr>
<td colspan="6" style="height:30px;width:535px;background-image:url('menu_cuts/center_top.png');background-repeat: no-repeat;background-position:top right;">
<div style="width:500px;background-color:#ffffff;height:100%;">
&nbsp;
</div>
</td>
</tr>
<tr>
<td colspan="6" style="background-color:#ffffff;text-indent:30px;height:40px;">
<H1><xsl:value-of select="pageheading"/></H1>
</td>
</tr>
<tr style="height:100%;">
<td colspan="6" style="background-color:#ffffff;padding-left:30px;padding-right:30px;width=535px;height:100%;">
<xsl:value-of disable-output-escaping="yes" select="pagetext/markup_code"/>
</td>
</tr>
<tcl>
<!-- This is the output from any OpenOCD commands -->
set toggle_details [formfetch toggle_details]
if {[string length $toggle_details]==0} {
set toggle_details 0
}
set show_details [load_var show_details]
if {[string length $show_details]==0} {
set show_details 0
}
if {$toggle_details==1} {
set show_details [expr 1-$show_details]
save_var show_details $show_details
}
if {[string length $console]!=0} {
</tcl>
<tr style="height:100%;">
<td colspan="6" style="height:100%;background-color:red;">
</td>
</tr>
<tcl>
<!-- This is the output from any OpenOCD commands -->
set toggle_details [formfetch toggle_details]
if {[string length $toggle_details]==0} {
set toggle_details 0
}
set show_details [load_var show_details]
if {[string length $show_details]==0} {
set show_details 0
}
if {$toggle_details==1} {
set show_details [expr 1-$show_details]
save_var show_details $show_details
}
if {[string length $console]!=0} {
</tcl>
<tr style="height:100%;">
<td colspan="6" style="height:100%;background-color:red;">
<table class="textgray" style="padding:0px;border-collapse:collapse;background-color:#ffffff;width:100%">
<td style="width:25px;">&nbsp;</td>
<tcl>
if {$show_details==1} {
append buffer <xsl:text disable-output-escaping="yes"><![CDATA[<]]></xsl:text>
append buffer {td style="background-color:#dddddd;padding-left:5px;padding-right:5px;padding-top:3px;padding-bottom:3px;"}
append buffer <xsl:text disable-output-escaping="yes"><![CDATA[>]]></xsl:text>
} else {
append buffer <xsl:text disable-output-escaping="yes"><![CDATA[<]]></xsl:text>
append buffer {td style="background-image:url('menu_cuts/h_tab_free.png');width:110px;height:29px;background-repeat: no-repeat;background-position:top left;"}
append buffer <xsl:text disable-output-escaping="yes"><![CDATA[>]]></xsl:text>
}
</tcl>
<a class="openocd">
<td style="width:25px;">&nbsp;</td>
<tcl>
if {$show_details==1} {
append buffer <xsl:text disable-output-escaping="yes"><![CDATA[<]]></xsl:text>
append buffer {td style="background-color:#dddddd;padding-left:5px;padding-right:5px;padding-top:3px;padding-bottom:3px;"}
append buffer <xsl:text disable-output-escaping="yes"><![CDATA[>]]></xsl:text>
} else {
append buffer <xsl:text disable-output-escaping="yes"><![CDATA[<]]></xsl:text>
append buffer {td style="background-image:url('menu_cuts/h_tab_free.png');width:110px;height:29px;background-repeat: no-repeat;background-position:top left;"}
append buffer <xsl:text disable-output-escaping="yes"><![CDATA[>]]></xsl:text>
}
</tcl>
<a class="openocd">
<xsl:attribute name="href"><xsl:value-of select="$pagetogenerate"/>?toggle_details=1</xsl:attribute>
<tcl>
if {$show_details==1} {
append buffer "Hide details"
append buffer <br/>
append buffer <br/>
} else {
append buffer {<div style="position:relative;top:7px;text-align:center;">}
append buffer "Show details"
append buffer {</div>}
}
</tcl>
</a>
<tcl>
if {$show_details==1} {
append buffer $console
}
</tcl>
</a>
<tcl>
if {$show_details==1} {
append buffer $console
}
</tcl>
<xsl:text disable-output-escaping="yes"><![CDATA[<]]></xsl:text>/td<xsl:text disable-output-escaping="yes"><![CDATA[>]]></xsl:text>
<tcl>
if {$show_details!=1} {
append buffer {<td>&nbsp;</td>}
}
if {$show_details!=1} {
append buffer {<td>&nbsp;</td>}
}
</tcl>
<td style="width:25px;">&nbsp;</td>
</table>
</td>
<td style="width:25px;">&nbsp;</td>
</table>
</td>
</tr>
<tcl>
<tcl>
}
</tcl>
<tr>
<td colspan="6" style="height:30px;background-image:url('menu_cuts/center_bottom.png');background-repeat: no-repeat;background-position:top right;">
<div style="width:500px;background-color:#ffffff;height:100%;">
&nbsp;
</div>
</td>
</tr>
</table>
<tr>
<td colspan="6" style="height:30px;background-image:url('menu_cuts/center_bottom.png');background-repeat: no-repeat;background-position:top right;">
<div style="width:500px;background-color:#ffffff;height:100%;">
&nbsp;
</div>
</td>
</tr>
</table>
</td>
<td style="width:6px;">
</td>
@@ -240,56 +240,56 @@
<tr>
<td style="width:103px;height:29px;background-image:url('menu_cuts/h_tab2_selected.png');background-repeat: no-repeat;">
<div class="textgray" style="position:relative;top:7px;;font-weight:bold;text-align:center;width:100px;">
Documentation
Documentation
</div>
</td>
<td width="40px">
&nbsp;
</td>
<td>
</td>
</td>
<td width="40px">
&nbsp;
</td>
<td>
</td>
</tr>
<tr>
<td colspan="3" style="height:10px;width:245px;background-image:url('menu_cuts/right_top_small.png');"></td>
</tr>
<tr>
<td colspan="3" style="background-color:#d8d7d7;width:245px;padding-left:10px;padding-buttom:10px;line-height:17px;">
<a href="http://openocd.berlios.de/doc/openocd.pdf" target="_blank">OpenOCD Manual</a><br/>
</td>
</tr>
<tr><td colspan="3" style="background-color:#d8d7d7;height:15px;"></td></tr>
<tr>
<td colspan="3">
<table style="padding:0px;border-collapse:collapse;">
<td style="background-color:#d8d7d7;width:10px;height:1px"></td>
<td style="background-color:#999999;width:225px; height:1px;"></td>
<td style="background-color:#d8d7d7;width:10px;height:1px"></td>
</table>
</td>
</tr>
<tr><td colspan="3" style="background-color:#d8d7d7;height:15px;"></td></tr>
<tr style="height:100%;">
<td class="textgray" colspan="3" style="height:100%;background-color:#d8d7d7;padding-left:10px;padding-right:10px;">
<tr>
<td colspan="3" style="height:10px;width:245px;background-image:url('menu_cuts/right_top_small.png');"></td>
</tr>
<tr>
<td colspan="3" style="background-color:#d8d7d7;width:245px;padding-left:10px;padding-buttom:10px;line-height:17px;">
<a href="http://openocd.berlios.de/doc/openocd.pdf" target="_blank">OpenOCD Manual</a><br/>
</td>
</tr>
<tr><td colspan="3" style="background-color:#d8d7d7;height:15px;"></td></tr>
<tr>
<td colspan="3">
<table style="padding:0px;border-collapse:collapse;">
<td style="background-color:#d8d7d7;width:10px;height:1px"></td>
<td style="background-color:#999999;width:225px; height:1px;"></td>
<td style="background-color:#d8d7d7;width:10px;height:1px"></td>
</table>
</td>
</tr>
<tr><td colspan="3" style="background-color:#d8d7d7;height:15px;"></td></tr>
<tr style="height:100%;">
<td class="textgray" colspan="3" style="height:100%;background-color:#d8d7d7;padding-left:10px;padding-right:10px;">
<xsl:choose>
<xsl:when test="(pagetext/right_column)">
<xsl:value-of disable-output-escaping="yes" select="pagetext/right_column"/>
</xsl:when>
<xsl:otherwise>
</xsl:otherwise>
</xsl:choose>
</td>
</tr>
<tr>
<td colspan="3" style="height:30px;background-image:url('menu_cuts/right_bottom.png');">
&nbsp;
</td>
</tr>
</td>
</tr>
<tr>
<td colspan="3" style="height:30px;background-image:url('menu_cuts/right_bottom.png');">
&nbsp;
</td>
</tr>
</table>
</td>
</tr>
</table>
</body>
</html>

View File

@@ -70,7 +70,7 @@ body
font-size: 12px;
line-height: 15px;
color : #024d67;
}
h1
@@ -86,7 +86,7 @@ td
{
padding: 0px;
font-size: 12px;
vertical-align:top;
vertical-align:top;
}
@@ -95,7 +95,7 @@ td
color: #cccccc;
padding: 0px;
font-size: 12px;
vertical-align:top;
vertical-align:top;
}

View File

@@ -7,7 +7,7 @@ tcl with embedded html.
sh build.sh
xalan.jar can be gotten from apache.org.
xalan.jar can be gotten from apache.org.
2. libmicrohttpd is a bit tricky to build under Cygwin:

View File

@@ -563,9 +563,11 @@ int server_quit(void)
/* tell the server we want to shut down */
COMMAND_HANDLER(handle_shutdown_command)
{
LOG_USER("shutdown command invoked");
shutdown_openocd = 1;
return ERROR_COMMAND_CLOSE_CONNECTION;
return ERROR_OK;
}
static const struct command_registration server_command_handlers[] = {

View File

@@ -88,7 +88,7 @@ static int tcl_input(struct connection *connection)
const char *result;
int reslen;
struct tcl_connection *tclc;
char in[256];
unsigned char in[256];
rlen = read_socket(connection->fd, &in, sizeof(in));
if (rlen <= 0) {
@@ -181,11 +181,12 @@ COMMAND_HANDLER(handle_tcl_port_command)
static const struct command_registration tcl_command_handlers[] = {
{
.name = "tcl_port",
.handler = &handle_tcl_port_command,
.handler = handle_tcl_port_command,
.mode = COMMAND_CONFIG,
.help = "port on which to listen "
"for incoming TCL syntax",
.usage = "<port>",
.help = "Specify port on which to listen "
"for incoming Tcl syntax. "
"No arguments reports Tcl port; zero disables.",
.usage = "[port_num]",
},
COMMAND_REGISTRATION_DONE
};

View File

@@ -62,7 +62,6 @@ int telnet_prompt(struct connection *connection)
{
struct telnet_connection *t_con = connection->priv;
telnet_write(connection, "\r", 1); /* the prompt is always placed at the line beginning */
return telnet_write(connection, t_con->prompt, strlen(t_con->prompt));
}
@@ -116,10 +115,12 @@ void telnet_log_callback(void *priv, const char *file, unsigned line,
}
/* clear the command line */
telnet_write(connection, "\r", 1);
for (i = strlen(t_con->prompt) + t_con->line_size; i > 0; i -= 16)
telnet_write(connection, "\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b", i > 16 ? 16 : i);
for (i = strlen(t_con->prompt) + t_con->line_size; i > 0; i -= 16)
telnet_write(connection, " ", i > 16 ? 16 : i);
telnet_write(connection, "\r", 1);
for (i = strlen(t_con->prompt) + t_con->line_size; i > 0; i -= 16)
telnet_write(connection, "\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b\b", i > 16 ? 16 : i);
/* output the message */
telnet_outputline(connection, string);
@@ -160,6 +161,7 @@ int telnet_new_connection(struct connection *connection)
telnet_write(connection, "\r\n", 2);
}
telnet_write(connection, "\r", 1); /* the prompt is always placed at the line beginning */
telnet_prompt(connection);
/* initialize history */
@@ -195,8 +197,8 @@ void telnet_clear_line(struct connection *connection, struct telnet_connection *
int telnet_input(struct connection *connection)
{
int bytes_read;
char buffer[TELNET_BUFFER_SIZE];
char *buf_p;
unsigned char buffer[TELNET_BUFFER_SIZE];
unsigned char *buf_p;
struct telnet_connection *t_con = connection->priv;
struct command_context *command_context = connection->cmd_ctx;
@@ -216,7 +218,7 @@ int telnet_input(struct connection *connection)
switch (t_con->state)
{
case TELNET_STATE_DATA:
if (*buf_p == '\xff')
if (*buf_p == 0xff)
{
t_con->state = TELNET_STATE_IAC;
}
@@ -331,6 +333,7 @@ int telnet_input(struct connection *connection)
if (retval == ERROR_COMMAND_CLOSE_CONNECTION)
return ERROR_SERVER_REMOTE_CLOSED;
telnet_write(connection, "\r", 1); /* the prompt is always placed at the line beginning */
retval = telnet_prompt(connection);
if (retval == ERROR_SERVER_REMOTE_CLOSED)
return ERROR_SERVER_REMOTE_CLOSED;
@@ -395,16 +398,16 @@ int telnet_input(struct connection *connection)
case TELNET_STATE_IAC:
switch (*buf_p)
{
case '\xfe':
case 0xfe:
t_con->state = TELNET_STATE_DONT;
break;
case '\xfd':
case 0xfd:
t_con->state = TELNET_STATE_DO;
break;
case '\xfc':
case 0xfc:
t_con->state = TELNET_STATE_WONT;
break;
case '\xfb':
case 0xfb:
t_con->state = TELNET_STATE_WILL;
break;
}
@@ -619,17 +622,18 @@ COMMAND_HANDLER(handle_exit_command)
static const struct command_registration telnet_command_handlers[] = {
{
.name = "exit",
.handler = &handle_exit_command,
.handler = handle_exit_command,
.mode = COMMAND_EXEC,
.help = "exit telnet session",
},
{
.name = "telnet_port",
.handler = &handle_telnet_port_command,
.handler = handle_telnet_port_command,
.mode = COMMAND_ANY,
.help = "port on which to listen "
"for incoming telnet connections",
.usage = "<port>",
.help = "Specify port on which to listen "
"for incoming telnet connections. "
"No arguments reports telnet port; zero disables.",
.usage = "[port_num]",
},
COMMAND_REGISTRATION_DONE
};

View File

@@ -470,7 +470,8 @@ free_all:
#define SVFP_CMD_INC_CNT 1024
static int svf_read_command_from_file(int fd)
{
char ch, *tmp_buffer = NULL;
unsigned char ch;
char *tmp_buffer = NULL;
int cmd_pos = 0, cmd_ok = 0, slash = 0, comment = 0;
while (!cmd_ok && (read(fd, &ch, 1) > 0))
@@ -499,31 +500,55 @@ static int svf_read_command_from_file(int fd)
case '\r':
slash = 0;
comment = 0;
break;
/* Don't save '\r' and '\n' if no data is parsed */
if (!cmd_pos)
break;
default:
if (!comment)
{
if (cmd_pos >= svf_command_buffer_size - 1)
/* The parsing code currently expects a space
* before parentheses -- "TDI (123)". Also a
* space afterwards -- "TDI (123) TDO(456)".
* But such spaces are optional... instead of
* parser updates, cope with that by adding the
* spaces as needed.
*
* Ensure there are 3 bytes available, for:
* - current character
* - added space.
* - terminating NUL ('\0')
*/
if ((cmd_pos + 2) >= svf_command_buffer_size)
{
tmp_buffer = (char*)malloc(svf_command_buffer_size + SVFP_CMD_INC_CNT); // 1 more byte for '\0'
/* REVISIT use realloc(); simpler */
tmp_buffer = malloc(
svf_command_buffer_size
+ SVFP_CMD_INC_CNT);
if (NULL == tmp_buffer)
{
LOG_ERROR("not enough memory");
return ERROR_FAIL;
}
if (svf_command_buffer_size > 0)
{
memcpy(tmp_buffer, svf_command_buffer, svf_command_buffer_size);
}
memcpy(tmp_buffer,
svf_command_buffer,
svf_command_buffer_size);
if (svf_command_buffer != NULL)
{
free(svf_command_buffer);
}
svf_command_buffer = tmp_buffer;
svf_command_buffer_size += SVFP_CMD_INC_CNT;
tmp_buffer = NULL;
}
/* insert a space before '(' */
if ('(' == ch)
svf_command_buffer[cmd_pos++] = ' ';
svf_command_buffer[cmd_pos++] = (char)toupper(ch);
/* insert a space after ')' */
if (')' == ch)
svf_command_buffer[cmd_pos++] = ' ';
}
break;
}
@@ -542,25 +567,30 @@ static int svf_read_command_from_file(int fd)
static int svf_parse_cmd_string(char *str, int len, char **argus, int *num_of_argu)
{
int pos = 0, num = 0, space_found = 1;
int pos = 0, num = 0, space_found = 1, in_bracket = 0;
while (pos < len)
{
switch (str[pos])
{
case '\n':
case '\r':
case '!':
case '/':
LOG_ERROR("fail to parse svf command");
return ERROR_FAIL;
break;
case ' ':
space_found = 1;
str[pos] = '\0';
break;
case '(':
in_bracket = 1;
goto parse_char;
case ')':
in_bracket = 0;
goto parse_char;
default:
if (space_found)
parse_char:
if (!in_bracket && isspace((int) str[pos]))
{
space_found = 1;
str[pos] = '\0';
}
else if (space_found)
{
argus[num++] = &str[pos];
space_found = 0;
@@ -628,6 +658,7 @@ static int svf_copy_hexstring_to_binary(char *str, uint8_t **bin, int orig_bit_l
return ERROR_FAIL;
}
/* fill from LSB (end of str) to MSB (beginning of str) */
for (i = 0; i < str_hbyte_len; i++)
{
ch = 0;
@@ -635,7 +666,13 @@ static int svf_copy_hexstring_to_binary(char *str, uint8_t **bin, int orig_bit_l
{
ch = str[--str_len];
if (!isblank(ch))
/* Skip whitespace. The SVF specification (rev E) is
* deficient in terms of basic lexical issues like
* where whitespace is allowed. Long bitstrings may
* require line ends for correctness, since there is
* a hard limit on line length.
*/
if (!isspace(ch))
{
if ((ch >= '0') && (ch <= '9'))
{
@@ -671,11 +708,12 @@ static int svf_copy_hexstring_to_binary(char *str, uint8_t **bin, int orig_bit_l
}
}
// consume optional leading '0' characters
while (str_len > 0 && str[str_len - 1] == '0')
/* consume optional leading '0' MSBs or whitespace */
while (str_len > 0 && ((str[str_len - 1] == '0')
|| isspace((int) str[str_len - 1])))
str_len--;
// check valid
/* check validity: we must have consumed everything */
if (str_len > 0 || (ch & ~((2 << ((bit_len - 1) % 4)) - 1)) != 0)
{
LOG_ERROR("value execeeds length");
@@ -1460,10 +1498,10 @@ static int svf_run_command(struct command_context *cmd_ctx, char *cmd_str)
static const struct command_registration svf_command_handlers[] = {
{
.name = "svf",
.handler = &handle_svf_command,
.handler = handle_svf_command,
.mode = COMMAND_EXEC,
.help = "Runs a SVF file.",
.usage = "<file>",
.usage = "filename ['quiet']",
},
COMMAND_REGISTRATION_DONE
};

View File

@@ -64,10 +64,10 @@ static int arm11_step(struct target *target, int current,
static int arm11_check_init(struct arm11_common *arm11)
{
CHECK_RETVAL(arm11_read_DSCR(arm11));
LOG_DEBUG("DSCR %08x", (unsigned) arm11->dscr);
if (!(arm11->dscr & DSCR_HALT_DBG_MODE))
{
LOG_DEBUG("DSCR %08x", (unsigned) arm11->dscr);
LOG_DEBUG("Bringing target into debug mode");
arm11->dscr |= DSCR_HALT_DBG_MODE;
@@ -498,12 +498,9 @@ static int arm11_resume(struct target *target, int current,
if (!debug_execution)
target_free_all_working_areas(target);
/* Set up breakpoints */
if (handle_breakpoints)
{
/* check if one matches PC and step over it if necessary */
struct breakpoint * bp;
/* Should we skip over breakpoints matching the PC? */
if (handle_breakpoints) {
struct breakpoint *bp;
for (bp = target->breakpoints; bp; bp = bp->next)
{
@@ -514,9 +511,11 @@ static int arm11_resume(struct target *target, int current,
break;
}
}
}
/* set all breakpoints */
/* activate all breakpoints */
if (true) {
struct breakpoint *bp;
unsigned brp_num = 0;
for (bp = target->breakpoints; bp; bp = bp->next)
@@ -542,7 +541,8 @@ static int arm11_resume(struct target *target, int current,
arm11_sc7_set_vcr(arm11, arm11_vcr);
}
arm11_leave_debug_state(arm11, handle_breakpoints);
/* activate all watchpoints and breakpoints */
arm11_leave_debug_state(arm11, true);
arm11_add_IR(arm11, ARM11_RESTART, TAP_IDLE);
@@ -953,6 +953,7 @@ static int arm11_write_memory_inner(struct target *target,
if (retval != ERROR_OK)
return retval;
/* load r0 with buffer address */
/* MRC p14,0,r0,c0,c5,0 */
retval = arm11_run_instr_data_to_core1(arm11, 0xee100e15, address);
if (retval != ERROR_OK)
@@ -975,11 +976,13 @@ static int arm11_write_memory_inner(struct target *target,
for (size_t i = 0; i < count; i++)
{
/* load r1 from DCC with byte data */
/* MRC p14,0,r1,c0,c5,0 */
retval = arm11_run_instr_data_to_core1(arm11, 0xee101e15, *buffer++);
if (retval != ERROR_OK)
return retval;
/* write r1 to memory */
/* strb r1, [r0], #1 */
/* strb r1, [r0] */
retval = arm11_run_instr_no_data1(arm11,
@@ -1002,11 +1005,13 @@ static int arm11_write_memory_inner(struct target *target,
uint16_t value;
memcpy(&value, buffer + i * sizeof(uint16_t), sizeof(uint16_t));
/* load r1 from DCC with halfword data */
/* MRC p14,0,r1,c0,c5,0 */
retval = arm11_run_instr_data_to_core1(arm11, 0xee101e15, value);
if (retval != ERROR_OK)
return retval;
/* write r1 to memory */
/* strh r1, [r0], #2 */
/* strh r1, [r0] */
retval = arm11_run_instr_no_data1(arm11,
@@ -1021,6 +1026,7 @@ static int arm11_write_memory_inner(struct target *target,
}
case 4: {
/* stream word data through DCC directly to memory */
/* increment: STC p14,c5,[R0],#4 */
/* no increment: STC p14,c5,[R0]*/
uint32_t instr = !no_increment ? 0xeca05e01 : 0xed805e00;
@@ -1318,17 +1324,20 @@ COMMAND_HANDLER(arm11_handle_vcr)
static const struct command_registration arm11_mw_command_handlers[] = {
{
.name = "burst",
.handler = &arm11_handle_bool_memwrite_burst,
.handler = arm11_handle_bool_memwrite_burst,
.mode = COMMAND_ANY,
.help = "Enable/Disable potentially risky fast burst mode"
" (default: enabled)",
.help = "Display or modify flag controlling potentially "
"risky fast burst mode (default: enabled)",
.usage = "['enable'|'disable']",
},
{
.name = "error_fatal",
.handler = &arm11_handle_bool_memwrite_error_fatal,
.handler = arm11_handle_bool_memwrite_error_fatal,
.mode = COMMAND_ANY,
.help = "Terminate program if transfer error was found"
.help = "Display or modify flag controlling transfer "
"termination on transfer errors"
" (default: enabled)",
.usage = "['enable'|'disable']",
},
COMMAND_REGISTRATION_DONE
};
@@ -1338,11 +1347,11 @@ static const struct command_registration arm11_any_command_handlers[] = {
* simulate + breakpoint implementation is broken.
* TEMPORARY! NOT DOCUMENTED! */
.name = "hardware_step",
.handler = &arm11_handle_bool_hardware_step,
.handler = arm11_handle_bool_hardware_step,
.mode = COMMAND_ANY,
.help = "DEBUG ONLY - Hardware single stepping"
" (default: disabled)",
.usage = "(enable|disable)",
.usage = "['enable'|'disable']",
},
{
.name = "memwrite",
@@ -1352,16 +1361,18 @@ static const struct command_registration arm11_any_command_handlers[] = {
},
{
.name = "step_irq_enable",
.handler = &arm11_handle_bool_step_irq_enable,
.handler = arm11_handle_bool_step_irq_enable,
.mode = COMMAND_ANY,
.help = "Enable interrupts while stepping"
" (default: disabled)",
.help = "Display or modify flag controlling interrupt "
"enable while stepping (default: disabled)",
.usage = "['enable'|'disable']",
},
{
.name = "vcr",
.handler = &arm11_handle_vcr,
.handler = arm11_handle_vcr,
.mode = COMMAND_ANY,
.help = "Control (Interrupt) Vector Catch Register",
.help = "Display or modify Vector Catch Register",
.usage = "[value]",
},
COMMAND_REGISTRATION_DONE
};

View File

@@ -854,7 +854,9 @@ int arm11_sc7_run(struct arm11_common * arm11, struct arm11_sc7_action * actions
AddressOut = 0;
}
do
/* Timeout here so we don't get stuck. */
int i = 0;
while (1)
{
JTAG_DEBUG("SC7 <= c%-3d Data %08x %s",
(unsigned) AddressOut,
@@ -866,10 +868,27 @@ int arm11_sc7_run(struct arm11_common * arm11, struct arm11_sc7_action * actions
CHECK_RETVAL(jtag_execute_queue());
if (!Ready)
JTAG_DEBUG("SC7 => !ready");
/* 'nRW' is 'Ready' on read out */
if (Ready)
break;
long long then = 0;
if (i == 1000)
{
then = timeval_ms();
}
if (i >= 1000)
{
if ((timeval_ms()-then) > 1000)
{
LOG_WARNING("Timeout (1000ms) waiting for instructions to complete");
return ERROR_FAIL;
}
}
i++;
}
while (!Ready); /* 'nRW' is 'Ready' on read out */
if (!nRW)
JTAG_DEBUG("SC7 => Data %08x", (unsigned) DataIn);

View File

@@ -255,11 +255,21 @@ static int arm720_mmu(struct target *target, int *enabled)
}
static int arm720_virt2phys(struct target *target,
uint32_t virt, uint32_t *phys)
uint32_t virtual, uint32_t *physical)
{
/** @todo Implement this! */
LOG_ERROR("%s: not implemented", __func__);
return ERROR_FAIL;
int type;
uint32_t cb;
int domain;
uint32_t ap;
struct arm720t_common *arm720t = target_to_arm720(target);
uint32_t ret = armv4_5_mmu_translate_va(target, &arm720t->armv4_5_mmu, virtual, &type, &cb, &domain, &ap);
if (type == -1)
{
return ret;
}
*physical = ret;
return ERROR_OK;
}
static int arm720t_read_memory(struct target *target,
@@ -516,8 +526,10 @@ static const struct command_registration arm720t_exec_command_handlers[] = {
.name = "cp15",
.handler = arm720t_handle_cp15_command,
.mode = COMMAND_EXEC,
.usage = "<opcode> [value]",
.help = "display/modify cp15 register",
/* prefer using less error-prone "arm mcr" or "arm mrc" */
.help = "display/modify cp15 register using ARM opcode"
" (DEPRECATED)",
.usage = "instruction [value]",
},
COMMAND_REGISTRATION_DONE
};
@@ -576,4 +588,5 @@ struct target_type arm720t_target =
.target_create = arm720t_target_create,
.init_target = arm720t_init_target,
.examine = arm7_9_examine,
.check_reset = arm7_9_check_reset,
};

View File

@@ -2,7 +2,7 @@
* Copyright (C) 2005 by Dominic Rath *
* Dominic.Rath@gmx.de *
* *
* Copyright (C) 2007,2008 Øyvind Harboe *
* Copyright (C) 2007-2009 Øyvind Harboe *
* oyvind.harboe@zylin.com *
* *
* Copyright (C) 2008 by Spencer Oliver *
@@ -11,6 +11,8 @@
* Copyright (C) 2008 by Hongtao Zheng *
* hontor@126.com *
* *
* Copyright (C) 2009 by David Brownell *
* *
* 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 *
@@ -941,14 +943,16 @@ int arm7_9_poll(struct target *target)
int arm7_9_assert_reset(struct target *target)
{
struct arm7_9_common *arm7_9 = target_to_arm7_9(target);
enum reset_types jtag_reset_config = jtag_get_reset_config();
bool use_event = false;
LOG_DEBUG("target->state: %s",
target_state_name(target));
enum reset_types jtag_reset_config = jtag_get_reset_config();
if (!(jtag_reset_config & RESET_HAS_SRST))
{
LOG_ERROR("Can't assert SRST");
if (target_has_event_action(target, TARGET_EVENT_RESET_ASSERT))
use_event = true;
else if (!(jtag_reset_config & RESET_HAS_SRST)) {
LOG_ERROR("%s: how to reset?", target_name(target));
return ERROR_FAIL;
}
@@ -963,7 +967,8 @@ int arm7_9_assert_reset(struct target *target)
*/
bool srst_asserted = false;
if (((jtag_reset_config & RESET_SRST_PULLS_TRST) == 0)
if (!use_event
&& !(jtag_reset_config & RESET_SRST_PULLS_TRST)
&& (jtag_reset_config & RESET_SRST_NO_GATING))
{
jtag_add_reset(0, 1);
@@ -973,48 +978,70 @@ int arm7_9_assert_reset(struct target *target)
if (target->reset_halt)
{
/*
* Some targets do not support communication while SRST is asserted. We need to
* set up the reset vector catch here.
* For targets that don't support communication while SRST is
* asserted, we need to set up the reset vector catch first.
*
* If TRST is asserted, then these settings will be reset anyway, so setting them
* here is harmless.
* When we use TRST+SRST and that's equivalent to a power-up
* reset, these settings may well be reset anyway; so setting
* them here won't matter.
*/
if (arm7_9->has_vector_catch)
{
/* program vector catch register to catch reset vector */
embeddedice_write_reg(&arm7_9->eice_cache->reg_list[EICE_VEC_CATCH], 0x1);
/* program vector catch register to catch reset */
embeddedice_write_reg(&arm7_9->eice_cache
->reg_list[EICE_VEC_CATCH], 0x1);
/* extra runtest added as issues were found with certain ARM9 cores (maybe more) - AT91SAM9260 and STR9 */
/* extra runtest added as issues were found with
* certain ARM9 cores (maybe more) - AT91SAM9260
* and STR9
*/
jtag_add_runtest(1, jtag_get_end_state());
}
else
{
/* program watchpoint unit to match on reset vector address */
embeddedice_write_reg(&arm7_9->eice_cache->reg_list[EICE_W0_ADDR_VALUE], 0x0);
embeddedice_write_reg(&arm7_9->eice_cache->reg_list[EICE_W0_ADDR_MASK], 0x3);
embeddedice_write_reg(&arm7_9->eice_cache->reg_list[EICE_W0_DATA_MASK], 0xffffffff);
embeddedice_write_reg(&arm7_9->eice_cache->reg_list[EICE_W0_CONTROL_VALUE], EICE_W_CTRL_ENABLE);
embeddedice_write_reg(&arm7_9->eice_cache->reg_list[EICE_W0_CONTROL_MASK], ~EICE_W_CTRL_nOPC & 0xff);
/* program watchpoint unit to match on reset vector
* address
*/
embeddedice_write_reg(&arm7_9->eice_cache
->reg_list[EICE_W0_ADDR_VALUE], 0x0);
embeddedice_write_reg(&arm7_9->eice_cache
->reg_list[EICE_W0_ADDR_MASK], 0x3);
embeddedice_write_reg(&arm7_9->eice_cache
->reg_list[EICE_W0_DATA_MASK],
0xffffffff);
embeddedice_write_reg(&arm7_9->eice_cache
->reg_list[EICE_W0_CONTROL_VALUE],
EICE_W_CTRL_ENABLE);
embeddedice_write_reg(&arm7_9->eice_cache
->reg_list[EICE_W0_CONTROL_MASK],
~EICE_W_CTRL_nOPC & 0xff);
}
}
/* here we should issue an SRST only, but we may have to assert TRST as well */
if (jtag_reset_config & RESET_SRST_PULLS_TRST)
{
jtag_add_reset(1, 1);
} else if (!srst_asserted)
{
jtag_add_reset(0, 1);
if (use_event) {
target_handle_event(target, TARGET_EVENT_RESET_ASSERT);
} else {
/* If we use SRST ... we'd like to issue just SRST, but the
* board or chip may be set up so we have to assert TRST as
* well. On some chips that combination is equivalent to a
* power-up reset, and generally clobbers EICE state.
*/
if (jtag_reset_config & RESET_SRST_PULLS_TRST)
jtag_add_reset(1, 1);
else if (!srst_asserted)
jtag_add_reset(0, 1);
jtag_add_sleep(50000);
}
target->state = TARGET_RESET;
jtag_add_sleep(50000);
register_cache_invalidate(arm7_9->armv4_5_common.core_cache);
if ((target->reset_halt) && ((jtag_reset_config & RESET_SRST_PULLS_TRST) == 0))
/* REVISIT why isn't standard debug entry logic sufficient?? */
if (target->reset_halt
&& (!(jtag_reset_config & RESET_SRST_PULLS_TRST)
|| use_event))
{
/* debug entry was already prepared in arm7_9_assert_reset() */
/* debug entry was prepared above */
target->debug_reason = DBG_REASON_DBGRQ;
}
@@ -2723,6 +2750,29 @@ int arm7_9_examine(struct target *target)
return retval;
}
int arm7_9_check_reset(struct target *target)
{
struct arm7_9_common *arm7_9 = target_to_arm7_9(target);
if (get_target_reset_nag() && !arm7_9->dcc_downloads)
{
LOG_WARNING("NOTE! DCC downloads have not been enabled, defaulting to slow memory writes. Type 'help dcc'.");
}
if (get_target_reset_nag() && (target->working_area_size == 0))
{
LOG_WARNING("NOTE! Severe performance degradation without working memory enabled.");
}
if (get_target_reset_nag() && !arm7_9->fast_memory_access)
{
LOG_WARNING("NOTE! Severe performance degradation without fast memory access enabled. Type 'help fast'.");
}
return ERROR_OK;
}
COMMAND_HANDLER(handle_arm7_9_dbgrq_command)
{
struct target *target = get_current_target(CMD_CTX);
@@ -2797,6 +2847,12 @@ COMMAND_HANDLER(handle_arm7_9_semihosting_command)
COMMAND_PARSE_ENABLE(CMD_ARGV[0], semihosting);
if (!target_was_examined(target))
{
LOG_ERROR("Target not examined yet");
return ERROR_FAIL;
}
if (arm7_9->has_vector_catch) {
struct reg *vector_catch = &arm7_9->eice_cache
->reg_list[EICE_VEC_CATCH];
@@ -2858,32 +2914,32 @@ int arm7_9_init_arch_info(struct target *target, struct arm7_9_common *arm7_9)
static const struct command_registration arm7_9_any_command_handlers[] = {
{
"dbgrq",
.handler = &handle_arm7_9_dbgrq_command,
.handler = handle_arm7_9_dbgrq_command,
.mode = COMMAND_ANY,
.usage = "<enable|disable>",
.usage = "['enable'|'disable']",
.help = "use EmbeddedICE dbgrq instead of breakpoint "
"for target halt requests",
},
{
"fast_memory_access",
.handler = &handle_arm7_9_fast_memory_access_command,
.handler = handle_arm7_9_fast_memory_access_command,
.mode = COMMAND_ANY,
.usage = "<enable|disable>",
.usage = "['enable'|'disable']",
.help = "use fast memory accesses instead of slower "
"but potentially safer accesses",
},
{
"dcc_downloads",
.handler = &handle_arm7_9_dcc_downloads_command,
.handler = handle_arm7_9_dcc_downloads_command,
.mode = COMMAND_ANY,
.usage = "<enable | disable>",
.usage = "['enable'|'disable']",
.help = "use DCC downloads for larger memory writes",
},
{
"semihosting",
.handler = &handle_arm7_9_semihosting_command,
.handler = handle_arm7_9_semihosting_command,
.mode = COMMAND_EXEC,
.usage = "<enable | disable>",
.usage = "['enable'|'disable']",
.help = "activate support for semihosting operations",
},
COMMAND_REGISTRATION_DONE

View File

@@ -157,5 +157,6 @@ int arm7_9_execute_sys_speed(struct target *target);
int arm7_9_init_arch_info(struct target *target, struct arm7_9_common *arm7_9);
int arm7_9_examine(struct target *target);
int arm7_9_check_reset(struct target *target);
#endif /* ARM7_9_COMMON_H */

View File

@@ -752,4 +752,5 @@ struct target_type arm7tdmi_target =
.target_create = arm7tdmi_target_create,
.init_target = arm7tdmi_init_target,
.examine = arm7_9_examine,
.check_reset = arm7_9_check_reset,
};

Some files were not shown because too many files have changed in this diff Show More