Introduction#
The XTC Tools are a suite of tools to run on a host PC for working with XMOS target systems.
A target system is typically a single printed circuit board populated with one or more XMOS
devices. A target program, (which is a .xe-suffixed file produced by the xcc
tool),
may be downloaded into the target RAM and executed using the xrun
tool. Symbolic
debugging of a target program may be carried out using the xgdb
tool. A
target program may burned to non-volatile flash using the xflash
tool. These
tools require an XMOS xTAG to connect the target system to the host computer via
a USB 2.0 interface.
Key target-based features#
The following target-related features are provided by the XTC Tools:
Reset the target, download and launch a target program, and optionally support host-IO and xSCOPE operations
Write a target program to a flash device in a target system
Dump the current state of the target (does not reset the target)
Provide symbolic debug of a target (where the program is either downloaded into RAM or booted from flash)
The target may be debugged starting from a system-reset state or the debugger may be attached to a running program
Host-IO and xSCOPE API calls may be left in programs which are deployed. The tools will optionally enable host-IO when a connection is made via an xTAG
Provide an API for a developer to use on the host computer to transfer application data to and from the target
Provide sample-based profiling of a target
Management of all xTAGs attached to the host
List the xTAGs and detect the type of target system attached
For all the tools, an xTAG may be specified by its list index or by unique identifier
If only one xTAG is connected to the host an identifier does not need to be supplied to the tools
Targets#
Two generations of XMOS target system are supported by the tools:
xCORE-200 (XS2A Instruction Set Architecture)
xcore.ai (XS3A Instruction Set Architecture)
Evaluation boards may be obtained from various sources, such as Farnell.
xTAG#
The xTAG is the physical host-to-target interface. Two types are supported by the tools; xTAG v3.0 (https://www.xmos.com/download/xTAG-3-Hardware-Manual(1.0).pdf) and xTAG v4.0. Both xTAG types have a USB 2.0 High Speed (Micro-B) interface for connection to the host which also supplies the power to the xTAG. The xTAG3 has a proprietary xSYS interface to the target board and the xTAG4 has an xSYS2 interface to the target board.
Both xSYS and xSYS2 provide 4-wire IEEE1149.1 JTAG interface and a duplex serial xCONNECT link (xLINK) interface, plus some additional control signals. Note the optional JTAG signal nTRST is not pinned out.
When an xTAG is attached to a host it listens for a connection by certain host
programs (xrun
, xgdb
, xflash
or xburn
). The first connection
will download firmware to the xTAG which will support target-related operations.
The firmware is not downloaded on subsequent connections until the xTAG is
power-cycled.
The elapsed time required to connect to an xTAG is highly variable, due to the possibility of a firmware download occurring, and because the host operating system can introduce delays. This period may extend when multiple xTAGs are attached to the host computer. When a connection is initiated a lock is taken which may pause the execution of other independent host tools each using their own xTAG. The lock is released once the connection is established. Automated test systems should ensure any timeout for an xTAG response is sufficient for the worst case which may need to be determined empirically.
If the xTAG has been used previously with an earlier Tools 15 release the first connection will attempt to install the firmware required for use with this release. The xTAG will automatically reboot as part of this process which will be shown by the xTAG LEDs.
Note 1: If an xTAG has been used with a tools release earlier than Tools 15 it must be manually power cycled prior to making a connection with Tools 15.
Note 2: If the host is rebooted it may fail to enumerate the attached xTAGs. The xTAGs must be power-cycled. Some USB hubs provide a mechanism to power-cycle their downstream ports, and these are recommended for remote lab environments. Note Windows hosts do not support this feature.
xTAG v3.0#
xTAG v3.0 datasheet: https://www.xmos.com/download/xTAG-3-Hardware-Manual(1.0).pdf
The xTAG v3.0 provides the xSYS target interface (IDC 20-pin 0.1”) and supports XCORE-200 target families. It supports only 3v3 target voltage levels.
xTAG v4.0#
The xTAG v4.0 provides the xSYS2 target interface (Amphenol Minitek127 20-pin 0.05”) and supports XCORE-200 and xcore.ai target families. It supports 1v8 and 3v3 target voltages, automatically and independently for JTAG and xLINK interfaces.
The xLINK is optional - if it is not connected a reduced-footprint connector may be employed on the target board. To reduce the connector cost to a minimum, for production programming and testing, a Tag-Connect Plug-Of-Nails may be used. Only the IEEEE1149.1 JTAG signals need to be connected.
Host tools#
The host tools that interface with the target system are xrun
, xgdb
,
xflash
and xburn
.
Unless stated otherwise the following examples in this section assume a single xTAG and target system are attached to the host computer.
xrun#
The program xrun
is used to:
List the xTAGs and target systems attached to the host computer
Download a target program to RAM and launch it
Download a target program to RAM and launch it, managing host-IO
Download a target program to RAM and launch it, and capture xSCOPE data to a file
Download a target program to RAM and launch it, and allow a user-supplied host program capture xSCOPE data from the target and send data to the target
Dump the state of a target either with a
.xe
target program so it may be represented symbolically or without a.xe
to show state as raw data
Launching a target program#
A target program may be launched on the target system with:
$ xrun my_program.xe
xrun
will exit immediately, leaving the target program running
indefinitely. If the target program fails it may be debugged by attaching with xgdb
.
A target program may be launched with host-IO enabled with:
$ xrun --io my_program.xe
or with xSCOPE host-IO enabled:
$ xrun --xscope my_program.xe
xgdb#
The host tool xgdb
is a variant of the open-source tool gdb
. It supports the
standard gdb command line options and commands, plus extra command options and
builtin commands for use with XMOS targets.
It may be used to carry out all the functions supported by xrun
, plus
Interactive, symbolic debug of the downloaded program
Scripted actions with the target
Attaching to a target which is running a program which either booted from flash or was downloaded and launched with xrun or xgdb
Symbolic debug is only available for a source compilation unit (that is, a .c., .cpp or .xc
file) if it is compiled with the -g
option passed to xcc. Reducing the
optimisation level used by xcc
with the -O
option will improve debuggability at
the expense of potential changes in program behaviour.
Debugging a target program#
The following command will start a debug session of the program my_program.xe by connecting to the target, downloading the program and initialising the device based on the target XN used to build the program:
$ xgdb -ex "connect" -ex "load" my_program.xe
Commands supplied with the option -ex
may be entered at the (gdb) prompt if
preferred.
To start the program running the user must enter the command:
(gdb) continue
Before starting the program debugging commands may be supplied. For example,
breakpoints may be set with the break
command.
Once the target program is started the (gdb) prompt will not be available. Host-IO may appear on the console. Once started the target program may be stopped by pressing Ctrl-C which will report the stopped location and provide the (gdb) prompt.
The active logical cores may be listed with:
(gdb) info threads
Each active logical core is assigned a unique “gdb thread” number. Only active logical cores in all tiles in the system are listed. Note the “gdb thread” number assignments are not static and they may vary each time the target stops. A logical core may be selected for further inspection with the thread command. For example:
(gdb) thread 5
The back trace (call stack) for the logical core may be shown with the where command, for example:
(gdb) where
Local and global variables may be inspected with the standard gdb commands. See the gdb documentation for details.
Attaching to a target#
In some cases it may be desirable to inspect the state of a target system
without resetting it. It is possible to attach
to a running target. For example:
$ xgdb -ex attach my_program.xe
xgdb
will stop all the tiles and provide the (gdb) prompt. xgdb
commands
may be issued as illustrated in the previous section.
Target interaction#
The JTAG interface is used by the tools to establish a connection to the target, to reset it and to download programs to RAM. It is used to interact with the target, for example, to extract register state and to set breakpoints. It is used to monitor the target to detect program termination, to detect the target taking a fatal exception and to interrupt the target. It may be used to handle host-IO.
Debug mode#
Each tile will be placed in its debug mode to: download a program, when a
breakpoint is reached, to terminate a target program and when interrupted by a
Ctrl-C operation in the xgdb
console. In some cases it will enter debug mode to
forward host-IO data. When a tile enters debug mode all its logical cores will
be paused.
Exceptions#
The tools xrun
and xgdb
place a breakpoint on the exception handler entry point.
When the target takes a fatal exception (for example, due to arithmetic
divide-by-zero), the tools will report on the occurrence of the exception. xgdb
may be used to debug the cause, symbolically, typically by showing the
back-trace.
Note the message SIGTRAP
is generated if a tile enters debug mode unexpectedly.
This may occur when certain low-level operations are being carried out with the
tiles. The target program has not taken an exception.
Launch with xrun#
If the target program is launched by xrun
without any optional arguments, xrun
loads and runs the program, then exits immediately leaving the target program
running. If the --io
option or any of the --xscope
options are supplied to xrun it
will not exit until the target program terminates - see below.
Termination#
If a tile’s control flow reaches the end of main()
that tile will terminate and
wait. When control flow for all tiles has reached the end of main()
, the
xrun
session will terminate with a successful exit code. If the program was launched
using xgdb
it will report “Program exited normally “ on termination. (If xrun
has
been used to launch a program without either the xrun --io
or xrun --xscope
options, then it will detach after loading, and not await termination.)
If a tile calls exit()
with a non-zero value, this will be returned by xrun
as
the process exit code. One tile calling exit()
terminates the entire system.
If launched by xgdb
, the exit code will be shown
on the console, and the xgdb --return-child-result
option can be used to make
xgdb
return the exit code as its exit code.
Host-IO#
If the target program calls standard library IO functions from stdio.h
such as
printf()
, fprintf()
, fopen()
, fread()
and fwrite()
,
and the program was launched with
xgdb
, or with xrun
and the xrun --io
or xrun --xscope
options, these calls will be
redirected to act on the host computer’s filesystem (or its console, for
stdin, stdout and stderr). This is part of the “semihosting” system which runs
all system calls on the host system when the target is connected via a debug interface.
By default, data is sent to and from the target via the JTAG interface.
Using the JTAG interface, the tile making the call enters debug mode which pauses execution of all its logical cores.
These calls may be left in the program when it is deployed to boot from flash
using xflash
. The system calls will be skipped if a debugger is not connected, however
much of the logic (such as the string formatting of printf) will still execute.
If xrun
or xgdb
is later used with a such a system, the IO will be
redirected to the host computer. There is a deployment penalty in
run-time and memory used; each call will process its arguments before inspecting
internal state to determine whether xrun
or xgdb
is connected.
Note stdio.h
and other headers mentioned in the following sections can be found
under the tools installation in the sub-directory target/include
.
An example xrun command to enable host-IO:
$ xrun --adapter-id DFW7DTYY --io test.xe
An example xgdb command (note IO is enabled by default when using xgdb):
$ xgdb -ex "connect --adapter-id DFW7DTYY" -ex load -ex continue test.xe
Reduced-overhead print functions#
The header print.h
provides a set of reduced overhead print functions such as
printstr()
. These do not perform any memory allocation or any runtime
formatting, making them memory and run-time efficient compared with the standard
library IO functions. For example, the following prints a set of characters
without a new line:
printstr("Starting test 1");
Syscall host-IO#
The header syscall.h
provides the functions _open()
, _close()
, _write()
and
_read()
. These may be used to perform host-IO with a reduced run-time and memory
overhead compared with the standard library IO functions. The standard library
IO functions call these underlying syscall functions. For example:
int fd = _open(path, O_WRONLY | O_CREAT | O_TRUNC, S_IREAD | S_IWRITE);
if (_write(fd, buf, len) != len) { // Handle error }
Host-IO via the xCONNECT link (xSCOPE)#
The IO transfer rate via JTAG is relatively low. Furthermore, each IO call puts the tile in debug mode which is highly intrusive (as it pauses all logical cores). To achieve a significantly higher bandwidth and minimise intrusion into the target program, the xCONNECT link (xLINK) may be used as a transport. This may be configured in a lossy mode where data may be dropped if the host fails to keep pace with the target, or in lossless mode where the logical core emitting the data may be paused while data is being received by the host.
Note the write APIs (printf()
, fprintf()
, fwrite()
and _write()
) will use
xSCOPE exclusively. Other APIs such as fopen()
, fread()
or _read()
always
use the JTAG interface to transport data even if IO has been configured to use xSCOPE.
To use the xSCOPE protocol over xLINK, the following should be provided in a source file from which the target program is built:
#include <xscope.h>
// This user-implemented function will be called just before main()
void xscope_user_init() {
// This enables using xSCOPE for write syscalls (such as when using printf)
xscope_config_io(XSCOPE_IO_BASIC);
}
For full documentation of the xSCOPE runtime library, see xSCOPE target library.
Key points to note:
The program provides the function named
xscope_user_init()
(which is called automatically on program startup by the C-runtime initialisation code as a static constructor)The target program must be built with xSCOPE support, either by passing
xcc -fxscope
or an xSCOPE config file to xccOne of the
--xscope
options must be supplied to xrun or thexgdb
connect
command.
xSCOPE APIs#
A set of target APIs is provided to send packets of data to the host to be visualised as waveforms with a 3rd party graphical tool. A set of virtual channels called ‘probes’ are defined in the target program and each appears as a separate waveform trace.
The xLINK is always used to transport the data sent from the target.
xSCOPE may be configured in lossy mode where data may be dropped if the host fails to keep pace with the target, or in lossless mode where logical core emitting the data may be paused while data is transferred.
Lossy or lossless data delivery may be selected using xscope_mode_lossless()
and xscope_mode_lossy()
.
The APIs are defined in xscope.h. An example to emit float and integer data for two probes is:
void xscope_user_init(void) {
// Register 2 probes. The first implicitly has ID 0, the second has ID 1.
xscope_register(2,
XSCOPE_CONTINUOUS, "Float0", XSCOPE_FLOAT, "mV",
XSCOPE_CONTINUOUS, "Iterations", XSCOPE_UINT, "Steps");
}
void emit(float f, unsigned int i) {
xscope_float(0, f);
xscope_int(1, i);
}
The target program must be built with xSCOPE support, either by passing
xcc -fxscope
or an xSCOPE config file to xcc
The xrun
option xrun --xscope-file
must be supplied to specify a file into
which the data will be written in IEEE 1364-2001 Verilog VCD format.
User-supplied host program#
The user may supply a host program which handles target data while the target program is running. The target can send data to the host program using either the xSCOPE APIs, the semihosting APIs (such as printf) or both sets. The host program can send data back to the target program.
The host program can be written in either the C or C++ programming language. The
header xscope_endpoint.h provides the API for the host program. It must be
linked against the shared library libxscope_endpoint.so
on Linux and Mac hosts
and xscope_endpoint.a
on Windows hosts, using C linkage. These libraries are
provided by the XTC Tools in the lib
sub-directory of the installation root.
See xSCOPE host library for more information.
In this example two consoles are used to launch the xgdb session and the host program.
<PORTNUM>
must be substituted with a free system port number.
Console 1: launch the xgdb session:
$ xgdb -ex "connect --xscope-port --xscope-port localhost:<PORTNUM>"
Console 2: launch the host program:
$ host_example <PORTNUM>
Structure of the host program#
The host program starts by registering callback functions to handle selected
target activities, such as target calls to printf()
or target calls to xSCOPE
APIs. It does this with calls to:
It then connects to the xgdb session using the <PORTNUM>
argument passed to
main()
:
result = xscope_ep_connect("localhost", argv[1]);
If result is zero, the connection was successful. If non-zero the xgdb server
was not ready. The xscope_ep_connect()
API call may be re-tried
until a connection is made.
Once connected the program should sleep in an efficient manner. The callback functions will be called when necessary as a direct result of API calls by the target program.
Example host program and target programs#
In the following example the host program provides a set of call back functions which are called when the target-initiated events occur.
Compile#
$ xcc -g -fxscope -target=XCORE-AI-EXPLORER -o target.xe main.xc target.c
$ gcc -g -I "$(XMOS_TOOL_PATH)/include" ${XMOS_TOOL_PATH}/lib/xscope_endpoint.so -o host host.c
Run#
Open two consoles.
In console 1:
$ xrun --xscope-port : target.xe
XScope Realtime Server Enabled (localhost:37316)
In console 2: Supply the port number printed by xrun following localhost:
above:
$ ./host 37316
Host program#
#include <signal.h>
#include "xscope_endpoint.h"
/* Called when the target calls xscope_register() */
static void xscope_register(unsigned int id,
unsigned int type,
unsigned int r,
unsigned int g,
unsigned int b,
unsigned char *name,
unsigned char *unit,
unsigned int data_type,
unsigned char *data_name)
{
// Handle the registration of the probe with the id 'id'
// For this example, we would expect a registration for:
// - Probe id=0, name = "V"
// - Probe id=1, name = "I"
// See the xscope_register call in the target file below
}
/* Called on each target call to xscope_int() and similar APIs */
static void xscope_record(unsigned int id,
unsigned long long timestamp,
unsigned int length,
unsigned long long dataval,
unsigned char *databytes)
{
/* id is the probe number used by the target in the xSCOPE API call */
switch (id) {
/* handle each probe id */
case 0:
/* do something for probe 0 */
break;
case 1:
/* do something for probe 1 */
break;
}
/* Optional: Send a 2-byte reply to the host : max 256 bytes */
const char* s = "ok";
xscope_ep_request_upload(2, s);
}
static void xscope_print(unsigned long long timestamp,
unsigned int length,
unsigned char *data)
{
for (int i = 0; i<length; i++) {
printf("%c", data[i]);
}
}
static volatile int running;
/* Called when the target program terminates */
static void sigint_handler(int) {
running = 0;
}
int main(int argc, char *argv[])
{
if(argc != 2){
fprintf(stderr, "ERROR missing xscope port number: Usage example %s localhost:12340\n", argv[0]);
exit(-1);
}
xscope_ep_set_print_cb(xscope_print);
xscope_ep_set_register_cb(xscope_register);
xscope_ep_set_record_cb(xscope_record);
signal(SIGINT, &sigint_handler);
int error = 1;
unsigned attempts = 0;
const unsigned MAX_ATTEMPTS = 240;
while (attempts<MAX_ATTEMPTS) {
error = xscope_ep_connect("localhost", argv[1]);
if (0 == error) {
break;
}
sleep(1);
attempts++;
}
if (error) {
fprintf(stderr, "xscope_ep_connect: failed %d attempts\n", attempts);
return 1;
}
running = 1;
while (running) {
sleep(1);
}
xscope_ep_disconnect();
return 0;
}
Target program#
#include <platform.h>
#include <xscope.h>
extern "C" {
void main_tile0(chanend);
}
int main (void)
{
chan xscope_chan;
par
{
xscope_host_data(xscope_chan);
on tile[0]: main_tile0(xscope_chan);
}
return 0;
}
void xscope_user_init(void) {
xscope_register(2,
XSCOPE_CONTINUOUS, "V", XSCOPE_INT, "mV", /* Probe 0 */
XSCOPE_CONTINUOUS, "I", XSCOPE_INT, "mA", /* Probe 1 */
);
}
void main_tile0(chanend_t xscope_end)
{
xscope_mode_lossless();
xscope_connect_data_from_host(xscope_end);
xscope_int(0, 45); /* Send 45 to probe 0 */
// Read response from host
int bytes_read = 0;
SELECT_RES(CASE_THEN(xscope_end, read_host_data)) {
read_host_data: {
xscope_data_from_host(xscope_end, (char *)buffer_ptr, &bytes_read);
}
}
xscope_int(1, 578); /* Send 578 to probe 1 */
// Read response from host
int bytes_read = 0;
SELECT_RES(CASE_THEN(xscope_end, read_host_data)) {
read_host_data: {
xscope_data_from_host(xscope_end, (char *)buffer_ptr, &bytes_read);
}
}
}
Specifying a port number for xgdb and the user host program#
An example of an explicitly chosen port number is:
xgdb -ex "connect --xscope-port-blocking --xscope-port localhost:45678" led-flash.xe
Allow xgdb to choose a port number and bind - avoiding a race condition#
It is often difficult to choose a port number and avoid the race condition where
another program on the host computer binds to that number.
This race can be prevented by allowing xgdb
to choose the port number, and bind to it
(which is an atomic operation and prevents another program from using that number).
xgdb
prints the port number it has used, which is then passed to the host program.
The following example shows the xgdb
this:
$ xgdb -ex "connect --xscope-port-blocking --xscope-port :" led-flash.xe
See xSCOPE performance figures for benchmarks on xSCOPE performance.
Sample-based profiling of the target program#
The tools provide a mechanism to profile a target program and report the time
spent executing its lines and functions, as a flat call graph. It does this
non-intrusively by sampling at a low frequency, which might vary considerably,
the program counter of each logical core. The samples are captured in a set of
gprof data files, and a report generated with the tools xgprof
.
This approach is useful for gaining insight into the behaviour of certain types of program, for example those which carry out a repetitive task. It may be useful for debugging a program which is failing to run as intended.
Capturing the sample data#
Run and capture sample data using the --gprof
option to the connect command to
xgdb
. When xgdb
is quit a set of gprof files (with the extension .gprof) will be
written in the current working directory. The filename of each gprof file
indicates the tile and logical core which it covers. For example, start capture
with:
$ xgdb -ex "connect --gprof" -ex load -ex continue CircularBuffer.xe
Leave xgdb
running for a period to capture samples, interrupt it with Ctrl-C
and exit xgdb with the quit command. On exit the gprof profile data files will
be written to the current working directory.
Analysing the profile data#
Spit the target program (.xe) file using the xobjdump -s
to obtain the Elf files
for each tile. For example:
$ xobjdump -s CircularBuffer.xe
For the next step, the Elf image_n0c0_2.elf
is used for tile 0 analysis, the Elf
image_n0c1_2.elf
is used for tile 1 and so on. Ignore Elf images without the _2
suffix (these are bootstrap images used to provide system initialisation).
Generate a flat profile report for a logical core with the tool xgprof, supplying the Elf for the tile and the gprof file for the logical core of the tile. It is typically necessary use a selection of report levels to understand the behaviour of the target program. For example, a summary report may be shown with:
$ xgprof -b image_n0c0_2.elf tile[0]_core0.gprof
A detailed report at the source line level may be shown with:
$ xgprof -l -b image_n0c0_2.elf tile[0]_core0.gprof
A very detailed report at the address level with hit-counts may be shown with:
$ xgprof -C -l -b image_n0c0_2.elf tile[0]_core0.gprof
Profiling a target program which boots from flash#
The following command may be used to capture profile data for a system which booted from flash:
$ xgdb -ex "attach --gprof" -ex "continue" test.xe
where test.xe
was used to build the flash image (or to build the upgrade image
within the flash device) and is currently executing.
Leave xgdb
running for a period to capture samples, interrupt with Ctrl-C and
exit xgdb
with the quit command. On exit the gprof profile data files will be
written to the current working directory.
Follow the steps described above to analyse the data files.
Target errors and warnings#
xSCOPE not supported#
The following message may be shown when xrun
or xgdb
is launched with the
--xscope
option. This occurs because the application does not make the call
xscope_config_io(XSCOPE_IO_BASIC)
from a function named xscope_user_init()
XScope connection was requested with '--xscope', but support does not appear to be
compiled into program (or symbols are missing). JTAG IO will be used. See -fxscope compiler option.
This implies any host-IO will be transported over the JTAG interface which is highly intrusive to the target program.
Failure to parse XN file#
When xrun or xgdb connects and loads a program to the target it configures the
target using the target XN file (and associated configuration files) supplied to
xcc
with the -target
option.
If the following message is shown the clocks and clock dividers in the target will not be set correctly and the target program may not function:
Warning: could not parse XN file, error /tmp/.xgdb21287-I8WMQBQG/platform.xn:11 Error: XN11101 Configuration file for node type "XTAG4" not found.
, PLL will not be set to expected value
This may be because a local XN file and configuration file was used to build the
target program. In the example above the file XTAG4.cfg
could not be found in
the tools installation. The location of these local XN and configuration files
may be specified by setting the search path environment variables
XCC_TARGET_PATH
and XCC_DEVICE_PATH
respectively. For example, on a Linux host,
the following command adds the current working directory to the paths that will
be searched:
$ XCC_TARGET_PATH=. XCC_DEVICE_PATH=.:${XCC_DEVICE_PATH} xgdb …
Command examples#
XGDB examples#
In the following examples xgdb commands are often supplied as a sequence of -ex
options on the xgdb
command line. But the they may also be supplied in a command
file or typed interactively at the gdb prompt. Commands may be abbreviated for
convenience, but abbreviated forms must not be ambiguous.
Load and run a program#
The following example connects to a target, loads the target program test.xe
into RAM and starts it running. Once launched the program must be interrupted
with a Ctrl-C action if it does not terminate, either to quit xgdb
or to enter
further xgdb
commands. A Ctrl-C action is made by the holding down both the
Ctrl key and the C key on the keyboard:
$ xgdb -ex connect -ex load -ex continue test.xe
Note the load command runs two phases. The first phase loads a setup image (which is automatically generated by the tools) to the target SRAM which is executed to initialise it. The second phase loads the target program which was built from the user’s source code.
Breakpoints#
A breakpoint may be set symbolically or with a numerical address to stop execution of all tiles when the control flow of a logical core reaches that address. The gdb prompt is shown along with a diagnostic message indicating the reason the program stopped.
The xgdb command break
inserts a soft breakpoint in RAM. There is no limit to
the number of soft breakpoints that may be set. A soft breakpoint is implemented
by writing a dcall instruction to the breakpoint address in the RAM of the tile.
For example:
(gdb) break my_func
(gdb) break *0x80402
In some cases a soft breakpoint cannot be used, for example where a program will
be loaded to RAM over an external link after the breakpoint is set. The xgdb
command hbreak
can be used. This will use the hardware emulation debug feature
within the tile to set a breakpoint. A maximum of three hardware breakpoints
may be set:
(gdb) hbreak my_func
Watchpoints#
XGDB may set watchpoints (also known as data breakpoints) to stop all tiles when an access is made to a watched address. Two types of watchpoint command are supported:
watch
<location>
stops execution when a store occurs to the specified location
awatch
<location>
stops execution when store occurs to or a load occurs from the specified location
xgdb
infers the address range to watch based on the type of the argument
<location>
.
For example, if my_counter is declared as type int in the target program the following will watch for write accesses only to its 4-byte range:
(gdb) watch my_counter
The following will watch for write and read accesses only to my_counter:
(gdb) awatch my_counter
A watch may be set on an address with a defined range. The following sets a watch on address 0x80250 with a range of 8 bytes:
(gdb) watch (char [8]) *0x80250
The debug hardware which provides watch support monitors the address issued by a load or store instruction, checking whether it is greater than or equal to the lower bound and less than or equal to the upper bound. If the lower bound is the address of the third byte of a word, and the upper bound is the address of the fourth byte of the word, and a 2-byte store is made to the address of the third byte the watch will trigger. But if a 4-byte store is made to the address of first byte the watch will not trigger (although this store will write to the third and fourth byte which is being watched).
If a watch it is set on a global or static variable before the program is
started it may be triggered when the startup code in the function _start()
performs initialisation.
Attaching to a running target#
It is possible to perform symbolic debugging on a target which already has an application
running. Such as if it has booted from flash, or if XRUN or XGDB had previously started
a program then detached. The attach
command can be used:
xgdb -ex "attach --adapter-id pr1V0_15" led-flash.xe
If the target application was built to perform host-IO over JTAG (for example,
by making a call to printstrln()
) this will be enabled. XSCOPE communication
will not function (See xSCOPE FAQ).
Attaching to a running target and capture data to generate a sample-based profiling report#
The following command can be used to attach to a system which is running and collect profile data without intrusion:
$ xgdb -ex "attach --gprof --adapter-id pr1V0_15" -ex "continue" led-flash.xe
xrun examples#
Dump the target state#
The following will dump the state of the target:
$ xrun --dump-state test.xe
where test.xe
is the target program that was launched on the target by an
invocation of xrun
or was burned to flash with the xflash
tool.
The following will dump the state of the target without a .xe
file:
$ xrun --dump-state-no-xe
Note in both cases all tiles will be put in their debug mode which will stop execution of all logical cores. They will be resumed after the state has been dumped (although, if they have hit an exception, xrun will not take them out of the exception.)
Reboot an xTAG which fails to respond#
The --xtag=reboot
option to the xgdb command connect
will force the xTAG
reboot:
$ xgdb -ex "connect --xtag=reboot"
If the xTAG is flagged in use by xrun -l
the above command will release it.
Note this reboot feature is not available on Windows due to limitations in
the standard Windows USB driver.