Part Number: J721S2XSOMXEVM
Tool/software:
How to flash Keywriter image over JTAG ?
This thread has been locked.
If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.
In order to run the keywriter over a JTAG we need to have a way where the secure ROM need to wait for the firmware and R5 should be On.
That is possible in the Dev boot mode and the configuration as follows:
During the Development boot (BOOTMODE[4] = 0), the SMS ROM code will act as if boot of the primary image
has completed, and the SMS ROM then will be waiting for a firmware load message from MCU R5. Thus user
you can load a standard u-boot/SPL image to the R5 RAM. U-boot/SPL will then load the SMS firmware and
complete the full boot.
On EVM you can configure DIP switches as:
We will load the xref using the CCS and then we will load the keywriter certificate at keywr_end + 1 (0x41C7F004).
load below js using ccs, you will be able to load the keywriter image using JTAG
/*
* Copyright (c) 2024, Texas Instruments Incorporated
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of Texas Instruments Incorporated nor the names of
* its contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
* EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/*
Description: Load and run keywriter executable on MCU R5F core on the SOC
Usage:
======
1. Adjust variables in Script
1a. Modify "pdkPath" (search for EDIT THESE) to point to the absolute path of the PDK in SDK
- On windows make sure to use '/' or '\\' as path separator
1b. Modify "kw_elf_file" and "kw_cert_file" to point to the KeyWriter firmware image and KeyWriter certificate
- On windows make sure to use '/' or '\\' as path separator
- Typical paths for these are
<ti-processor-sdk-rtos-j721s2-evm-09_01_00_06>/<pdk_j721s2_09_01_00_22>/packages/ti/boot/keywriter/binary/j721s2/keywriter_img_j721s2_release.xer5f
<ti-processor-sdk-rtos-j721s2-evm-09_01_00_06>/<pdk_j721s2_09_01_00_22>/packages/ti/boot/keywriter/x509cert/final_certificate.bin
1c. Modify "fileCcxml" to point to the desired CCS Target Configuration, created in Step 3
- Optional for Step 4, required if using alternate Step 5
2. Board Setup
2a. Configure the Board to "Dev-Boot" to allow KeyWriter TIFS binary to be processed by Secure ROM
- Please refer to Device TRM and your Board User Guide for the relevant settings of BOOTMODE pins
- Following are the settings on TI J721S2 EVM
SW8: 1000 0000
SW9: 0111 0000
This is a slight variation from "No-Boot" mode documented in 6.1.3.1 No Boot Mode of the RTOS SDK documentation
https://software-dl.ti.com/jacinto7/esd/processor-sdk-rtos-j721s2/09_01_00_06/exports/docs/psdk_rtos/docs/user_guide/evm_setup_j721s2.html#no-boot-mode
2b. Connect to MCU UART and WKUP UARTs using TeraTerm, minicom or picocom for KeyWriter logs
3. Create a CCS Target Configuration (if not done previously) following the HLOS-like environment setup
- See Section 7.4 Debugging with HLOS running on A72 (Linux/QNX) of the RTOS SDK documentation
https://software-dl.ti.com/jacinto7/esd/processor-sdk-rtos-j721s2/09_01_00_06/exports/docs/psdk_rtos/docs/user_guide/ccs_setup_j721s2.html#debugging-with-hlos-running-on-a72-linux-qnx
4. Run KeyWriter (GUI-based)
4a. Launch target connection in CCS, however DO NOT connect to any core
- Optional if this is the default target configuration and launched previously
4b. From CCS Scripting console do (CCS Tool Bar > View > Scripting Console)
js:> loadJSFile "<pdkPath>/packages/ti/drv/sciclient/tools/ccsLoadDmsc/j721s2/kw_launch.js"
4c. After successful execution you should see a log like below
Prepare the MCU R5F target...
Loading the KW certificate: /nhome/sdk/ti-processor-sdk-rtos-j721s2-evm-09_01_00_06/pdk_j721s2_09_01_00_22/packages/ti/boot/keywriter/binary/j721s2/test_images/test1/cert-kw_test03.bin
Loading the KW firmware: /nhome/sdk/ti-processor-sdk-rtos-j721s2-evm-09_01_00_06/pdk_j721s2_09_01_00_22/packages/ti/boot/keywriter/binary/j721s2/test_images/test1/kw_test03.xer5f
Running the KeyWriter image on MCU R5F...
Script Done!!!
4d. Stop the debug session from CCS.
5. Run KeyWriter (Alternate: CCS Scripting without launching CCS)
5a. See CCS Debug Server Scripting (DSS) documentation for details
https://software-dl.ti.com/ccs/esd/documents/users_guide/sdto_dss_handbook.html
5b. Change to CCS Scripting bin folder
Eg:
$ cd /home/<uname>/ti/ccs1240/ccs/ccs_base/scripting/bin
5c. Run the kw_launch.js script
Eg:
$ ./dss.sh /nhome/sdk/ti-processor-sdk-rtos-j721s2-evm-09_01_00_06/pdk_j721s2_09_01_00_22/packages/ti/drv/sciclient/tools/ccsLoadDmsc/j721s2/kw_launch.js
5d. Similar output as 4c will be seen directly in the terminal
Prepare the MCU R5F target...
Loading the KW certificate: /nhome/sdk/ti-processor-sdk-rtos-j721s2-evm-09_01_00_06/pdk_j721s2_09_01_00_22/packages/ti/boot/keywriter/binary/j721s2/test_images/test1/cert-kw_test03.bin
WARNING: MCU_Cortex_R5_0: Unexpected end of file: /nhome/sdk/ti-processor-sdk-rtos-j721s2-evm-09_01_00_06/pdk_j721s2_09_01_00_22/packages/ti/boot/keywriter/binary/j721s2/test_images/test1/
cert-kw_test03.bin. Only 3996 bytes are loaded from the file into the memory and the remaining bytes are set to zero.
Loading the KW firmware: /nhome/sdk/ti-processor-sdk-rtos-j721s2-evm-09_01_00_06/pdk_j721s2_09_01_00_22/packages/ti/boot/keywriter/binary/j721s2/test_images/test1/kw_test03.xer5f
Running the KeyWriter image on MCU R5F...
Script Done!!!
6. If any of the logs in step 4 show "fail" or "error" messages then
check your EVM, CCS, SDK setup, Executables path and try again.
*/
importPackage(Packages.java.lang)
importPackage(Packages.java.io);
/* EDIT THESE: 'pdkPath', 'kw_elf_file' and 'kw_cert_file' to match the deployment environment */
/* Example below runs MSV override certificate from keywriter_cfg_test_gen generated test images */
pdkPath = "/nhome/sdk/ti-processor-sdk-rtos-j721s2-evm-09_01_00_06/pdk_j721s2_09_01_00_22"
kw_elf_file = pdkPath + "/packages/ti/boot/keywriter/binary/j721s2/test_images/test1/kw_test03.xer5f";
kw_cert_file = pdkPath + "/packages/ti/boot/keywriter/binary/j721s2/test_images/test1/cert-kw_test03.bin";
/* Update this path */
fileCcxml = "/home/<uname>/ti/CCSTargetConfigurations/j721s2_hlos.ccxml"
/* KeyWriter certificate starts from keywr_end + 1, which is placed in section ".keywr_bin_end"
* Please look up map file or the linker command file */
kw_cert_addr = 0x41C7F004;
function updateScriptVars()
{
/* Open a debug session */
dsMCU = debugServer.openSession( ".*MCU_Cortex_R5_0" );
}
function connectTargets()
{
updateScriptVars();
print("Prepare the MCU R5F target...");
dsMCU.target.connect();
dsMCU.target.halt();
dsMCU.target.reset();
}
function disconnectTargets()
{
updateScriptVars();
dsMCU.target.disconnect();
}
function runKeywriter()
{
updateScriptVars();
/* Set timeout of in units of msecs for 20 seconds */
script.setScriptTimeout(20 * 1000);
connectTargets();
/* Load the keywriter executable and certificate files to MCU SRAM */
if (File(kw_elf_file).isFile() && File(kw_cert_file).isFile())
{
print("Loading the KW Certificate: "+ kw_cert_file);
dsMCU.memory.loadRaw(0, kw_cert_addr, kw_cert_file, 32, false);
print("Loading the KW Firmware: " + kw_elf_file);
dsMCU.memory.loadProgram(kw_elf_file);
}
else
{
print("Script failed, either of KW Certificate of KW firmware paths do not exist!! ");
print(" KW Certificate: " + kw_cert_file);
print(" KW Firmware: " + kw_elf_file);
disconnectTargets();
return;
}
/* Halt the R5F and re-run */
dsMCU.target.halt();
/* Run asynchronously for the executable to finish */
print("Running the KeyWriter image on MCU R5F...");
/* Comment this line if debugging is required */
dsMCU.target.runAsynch();
disconnectTargets();
print("Script Done!!!");
}
var ds;
var debugServer;
var script;
/* Check to see if running from within CCS Scripting Console */
var withinCCS = (ds !== undefined);
/* Create scripting environment and get debug server if running standalone */
if (!withinCCS)
{
/* Import the DSS packages into our namespace to save on typing */
importPackage(Packages.com.ti.debug.engine.scripting)
importPackage(Packages.com.ti.ccstudio.scripting.environment)
/* Create our scripting environment object - which is the main entry point into any script and
* the factory for creating other Scriptable ervers and Sessions */
script = ScriptingEnvironment.instance();
/* Get the Debug Server and start a Debug Session */
debugServer = script.getServer("DebugServer.1");
debugServer.setConfig(fileCcxml);
}
else /* otherwise leverage existing scripting environment and debug server */
{
debugServer = ds;
script = env;
}
runKeywriter();
Load single keywriter image without the need of loading cert and keywriter app separately.
In order to run the keywriter over JTAG, we need development boot mode where secure ROM waits for firmware and R5 is ON.
Configuration:
MCU_BOOTMODE[5:3] = 111
BOOTMODE[0] = 1
BOOTMODE[4] = 0
EVM DIP Switch Settings:
SW8[1:8] 1000_0000
SW9[1:8] 0111_0000
Prerequisites:
- CCS installed and launch the target configuration for J722S soc.
- PDK installed at known path
- Generated Keywriter binary available at: boot/keywriter/binary/j721s2/keywriter_img_j721s2_release.bin
Steps:
Step 1: Download the updated launch script
- Attachment: launch_keywriter.js
Step 2: Edit the script for your environment
- Open launch_keywriter.js in a text editor
- Line 50: Update pdkPath to your PDK installation path:
pdkPath = "/nhome/sdk/ti-processor-sdk-rtos-j721s2-evm-10_01_00_04/pdk_j721s2_10_01_00_25";
Step 3: Load and run the script from CCS Scripting Console:
loadJSFile "C:\\path\\to\\launch_keywriter.js"
What the script does:
1. Connects to MCU Cortex R5F Core 0
2. Resets the R5F core to clean state
3. Loads keywriter binary at address 0x41C00100
4. Sets Program Counter (PC) to 0x41C00100
5. Automatically runs the keywriter
/*
* Copyright (c) 2018-2022, Texas Instruments Incorporated
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of Texas Instruments Incorporated nor the names of
* its contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
* EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
//
//File Name: launch_keywriter.js
//Description:
// Load and run the keywriter binary on MCU R5F from CCS.
//
//Usage:
//
//From CCS Scripting console
// 1. loadJSFile "C:\\ti\\launch_keywriter.js"
//
//Note:
// 1. Search for "edit this" to look at changes that need to be edited
// for your usage.
//
//<!!!!!! EDIT THIS !!!!!>
//PDK path. Edit this
pdkPath = "/nhome/sdk/ti-processor-sdk-rtos-j721s2-evm-10_01_00_04/pdk_j721s2_10_01_00_25";
//path to keywriter binary
keywriter_bin = pdkPath + "/packages/ti/boot/keywriter/binary/j721s2/keywriter_img_j721s2_release.bin";
//Keywriter load address
keywriter_load_address = 0x41c00100;
//<!!!!!! EDIT THIS !!!!!>
// Import the DSS packages into our namespace to save on typing
importPackage(Packages.com.ti.debug.engine.scripting)
importPackage(Packages.com.ti.ccstudio.scripting.environment)
importPackage(Packages.java.lang);
importPackage(Packages.java.io);
function updateScriptVars()
{
//Open a debug session
dsMCU1_0 = debugServer.openSession( ".*MCU_Cortex_R5_0" );
}
function connectTargets()
{
/* Set timeout of 200 seconds */
script.setScriptTimeout(2000000);
updateScriptVars();
print("Connecting to MCU Cortex_R5_0!");
// Connect the MCU R5F
dsMCU1_0.target.connect();
// Reset the R5F to be in clean state
print("Resetting MCU R5F Core 0...");
dsMCU1_0.target.reset();
print("Loading Keywriter Binary... " + keywriter_bin);
print("Load Address: 0x" + keywriter_load_address.toString(16));
// Load the keywriter binary at specified address
dsMCU1_0.memory.loadRaw(0, keywriter_load_address, keywriter_bin, 32, false);
print("Keywriter Binary Load Done...");
// Set Program Counter to the load address
print("Setting PC to 0x" + keywriter_load_address.toString(16));
dsMCU1_0.memory.writeRegister("PC", keywriter_load_address);
print("Keywriter is ready to run.");
}
function runKeywriter()
{
updateScriptVars();
print("Running Keywriter...");
dsMCU1_0.target.runAsynch();
}
function haltKeywriter()
{
updateScriptVars();
print("Halting Keywriter...");
dsMCU1_0.target.halt();
}
function disconnectTargets()
{
updateScriptVars();
// Disconnect targets
dsMCU1_0.target.disconnect();
print("Disconnected from MCU R5F.");
}
function doEverything()
{
connectTargets();
runKeywriter();
disconnectTargets();
print("====================================================================");
print("Keywriter is loaded and ready!");
print("To run: runKeywriter()");
print("To halt: haltKeywriter()");
print("To disconnect: disconnectTargets()");
print("====================================================================");
}
var ds;
var debugServer;
var script;
// Check to see if running from within CCS Scripting Console
var withinCCS = (ds !== undefined);
// Create scripting environment and get debug server if running standalone
if (!withinCCS)
{
// Import the DSS packages into our namespace to save on typing
importPackage(Packages.com.ti.debug.engine.scripting);
importPackage(Packages.com.ti.ccstudio.scripting.environment);
importPackage(Packages.java.lang);
// Create our scripting environment object - which is the main entry point into any script and
// the factory for creating other Scriptable ervers and Sessions
script = ScriptingEnvironment.instance();
// Get the Debug Server and start a Debug Session
debugServer = script.getServer("DebugServer.1");
}
else // otherwise leverage existing scripting environment and debug server
{
debugServer = ds;
script = env;
}
doEverything();