J-Run
J-Run is a command line utility for automated tests. It loads an application (elf) file to the device under test, runs it, and captures the application's output.
The origin on J-Run is described in this blog post: https://blog.segger.com/j-run-automating-performance-tests
Test Applications
J-Run supports any ARM and RISC-V device which is supported by J-Link, and elf output from most toolchains.
The test application can do standard printf-style debug output to the debugger. J-Run supports handling of RTT and Semihosting.
When the test application is finished, it can call the Semihosting exit operation or print the wildcard exit string (by default "STOP"), to exit the J-Run test.
The target output is printed to the terminal. It can be redirected to a file or application for further analysis.
Usage
JRun [options] elf-file
Option | Default | Description |
---|---|---|
--usb <SerialNo> | Not set | Connect to J-Link with SN <SerialNo> via USB. |
--ip <str> | Not set | Connect to J-Link with IP <str> via IP. |
--device <str> | STM32F407IE | Set device name to <str>. |
--if SWD/JTAG | SWD | Select SWD or JTAG as target interface. |
-speed <khz> | 4000 | Set interface speed to <khz> kHz. |
--rtt | Auto | Force RTT enabled. |
--nortt | Auto | Force RTT disabled. |
--semihost | Auto | Force semihosting enabled. |
--nosemihost | Auto | Force semihosting disabled. |
--args <args> | Not set | Arguments passed to target application via semihosting and RTT |
--wargs <str> | *ARGS* | Set RTT getargs wildcard to <str>. |
--wexit <str> | *STOP* | Set RTT exit wildcard to <str>". |
--quit | On | Automatically exit J-Run on application exit. |
--wait | Off | Wait for key press on application exit. |
--stderr | Off | Also send target output to stderr. |
--silent | Off | Work silently. |
--verbose | Off | Increase verbosity. |
--dryrun | Off | Dry run. Parse elf-file only. |
--jlinkscriptfile <str> | Not set | Set path of J-Link script file to use to <str>. Further info: J-Link script files |
--pc <mode>/0xXXXXXXXX | vec | Initialize PC before start (according to <mode> or fixed address). <mode>: vec - Vector table, elf - ELF start address, off - do not init. |
--sp <mode>/0xXXXXXXXX | vec | Initialize SP before start (according to <mode> or fixed address). <mode>: vec - Vector table, off - do not init. |
--log <file> | Off | Write output to logfile. |
--fileonly | Off | Write output _only_ to logfile. |
In case some arguments are not available, please consider updating to the latest J-Link version.
Example Output
C:\Work\JLink\JRun\Test>JRun.exe Target\ST_STM32F407_RTT_JRun_Demo.elf
SEGGER J-Run V1.24 (Compiled Sep 16 2024 10:08:12)
Open application...OK
Connecting to J-Link...OK
Connected to J-Trace PRO V3 compiled Jul 3 2024 16:59:08 (S/N 1223000038).
DLL Version: 7.96j
Set target device to STM32F407IE...OK
Select SWD interface...OK
Set interface speed to 4000 kHz...OK
Reset target...OK
Download 0x08000000 - 0x08000FC9...OK
Set RTT control block at 0x20000000...OK
Start RTT...OK
Start target application (SP 0x20020000, PC 0x08000E9F)... OK
Reading output from target until exit command.
==============================================
SEGGER J-Run demo.
Took 8395654 cycles
Target Application exit.
Passing arguments to target application
J-Run can supply arguments to your application via Semihosting and via RTT. Arguments can be passed by using the "--args"option
C:\Work\JLink\Output\Debug_x64>JRun --wait ST_STM32F407_SemihostArgs_Example.elf --args "foo baz --verbose"
Argument passing is support for three implementations that will need counterpart in target code
- Standard Semihosting
- Segger Semihosting
- Segger RTT, device to send *ARGS* and receive <args>
For more information on passing arguments please refer to Passing Command-line arguments in C for Embedded Targets
Returning arguments from target application
J-Run can retrieve return values from target and will exit with the return value received.
Return value retrieval is supported for two implementations that will need counterpart in target code
- Standard Semihosting SYS_EXIT command (SW Reason = ADP_Stopped_ApplicationExit, Subcode = <ret>)
- Segger RTT, device to send *STOP*<ret>
Please note that values <0 are used by J-Run
Return | Value | Comment |
---|---|---|
-1 | JRUN_EXIT_ERR | J-Run error on host side. Check logs. |
0 | JRUN_EXIT_OK | J-Run succeeded |
>0 | <ret> | Application specific return value. |
Initialization of PC/SP on start
In order to start the application properly, J-Run needs to setup the target stack pointer (SP) and program counter (PC). While this is done automatically in Segger GUI products like Ozone, user need to take care in J-Run. J-Run will display what it did right before application start as described in the following.
If the values do not match you target needs, it will result in undefined behaviour.
SP and PC initialized by vector table
This is the default behaviour of J-Run and will work for most devices including our STM32F407 trace reference board. The compiler stores the SP and PC values in the vector table, located at start of the target memory.
C:\Work\JLink\JRun\Test>JRun.exe Target\ST_STM32F407_RTT_JRun_Demo.elf
<...>
Start target application (SP 0x20020000, PC 0x08000E9F)... OK
Reading output from target until exit command.
SP initialized by vector table, PC by ELF entry point address
Some toolchains only store the SP in the vector table. In case the entry point is set correctly in the ELF file, we can get it from there.
For this example, the ELF entry point contains same value as the vector table.
C:\Work\JLink\JRun\Test>JRun.exe Target\ST_STM32F407_RTT_JRun_Demo.elf --pc elf
<...>
Start target application (SP 0x20020000, PC 0x08000E9F)... OK
Reading output from target until exit command.
SP and PC initialized by boot loader
Some target devices use a bootloader approach to copy and start the application on the target. In this case, we should not interfere with and rather leave initialization up to the bootloader.
This example will work due to the target PC after reset and startup code.
C:\Work\JLink\JRun\Test>JRun.exe Target\ST_STM32F407_RTT_JRun_Demo.elf --pc off --sp off
<...>
Start target application (SP <noinit>, PC <noinit>)... OK
Reading output from target until exit command.
User defined value
In case your target environment does not support any of the above methods, you can still provide the initial values to J-Run. If you don't have an idea how to find out these values, you might start your test application using Ozone and simply take over the values.
This example will not work - the user provided values will be set as is, starting the application with an invalid SP and a bogus address.
C:\Work\JLink\JRun\Test>JRun.exe Target\ST_STM32F407_RTT_JRun_Demo.elf --pc 0xdeadbeef --sp 0xf00bad00
<...>
Start target application (SP 0xF00BAD00, PC 0xDEADBEEF)... OK
Reading output from target until exit command.