embeddedsw/lib/sw_services/xilskey/examples/xilskey_efuse_example.c
VNSL Durga 5e98df225c Xilskey: Modified efuse example
Added new lines in example prints.
Modified CRC calculation API name and
provided backward compatability.

Signed-off-by: VNSL Durga <vnsldurg@xilinx.com>
Reviewed-by: Harini Katakam <harinik@xilinx.com>
2015-10-12 18:56:09 +05:30

922 lines
31 KiB
C
Raw Blame History

/******************************************************************************
*
* Copyright (C) 2013 - 2015 Xilinx, Inc. All rights reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* Use of the Software is limited solely to applications:
* (a) running on a Xilinx device, or
* (b) that interact with a Xilinx device through a bus or interconnect.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
* XILINX BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*
* Except as contained in this notice, the name of the Xilinx shall not be used
* in advertising or otherwise to promote the sale, use or other dealings in
* this Software without prior written authorization from Xilinx.
*
******************************************************************************/
/*****************************************************************************/
/**
*
* @file
* xilskey_efuse_example.c
* @note
*
* Contains the api functions for the PS & PL eFUSE functionality.
* eFUSE Application project is capable of programming the PS and PL eFUSE
* bits given by the user. PS eFUSE holds the RSA primary key hash bits and
* user feature bits, which will enable/disable some features in ZYNQ.
* In Zynq PL eFUSE holds the AES key, user key and some feature bits and
* and in Ultrascale eFUSE holds AES key, User key, RSA key Hash and
* some feature bits.
* User has the provision to write PS eFUSE & PL eFUSE independently or
* can combine together. This can be selected by using the compilation
* switch provided in xilskey_input.h. XSK_EFUSEPS_DRIVER should be
* defined to enable PS functionality & XSK_EFUSEPL_DRIVER for PL
* functionality.
* However for programming eFuse Ultrascale only XSK_EFUSEPL_DRIVER should be
* enabled.
*
* eFUSE bits are one-time programmable. Once they are burnt, they
* cannot be changed. Make sure you enter the correct information before
* you program eFUSE bits.
*
* POR reset is required for the eFUSE values to become into effect.
* Please do a POR reset after eFUSE writing.
*
* All the user configurable parameters for PS & PL eFUSE writing should be
* defined in xilskey_input.h. By default, all the macros will be defined
* with FALSE values.
*
* For Zynq
* -----------------------------------------------------------------------
* For PL eFUSE writing enabling the caches are necessary if the image is
* executing from DDR. This will be done in BSP by default. User has to
* take care not to disable caches.
*
* eFUSE writing procedure running out of DDR as an application:
* (This sequence is same as the existing flow described below)
*
* 1) After providing the required inputs in xilskey_input.h, compile the
* project.
* 2) Take the latest FSBL (.elf) and stitch the <output>.elf generated
* to it using the bootgen utility and generate a bootable image.
* 3) Write the generated binary image into the flash device.
* (Ex: QSPI,NAND etc)
* 4) Execute image from flash which will write the mentioned eFUSE key
* bits.
*
* eFUSE driver compilation procedure for OCM:
*
* 1) Open the linker script (lscript.ld) in the SDK project.
* 2) Now map all the sections points to <20>ps7_ram_0_S_AXI_BASEADDR<44>
* instead of <20>ps7_ddr_0_S_AXI_BASEADDR<44>.
*
* Example: Click on the <20>Memory Region<6F> tab for .text section & select
* <09>ps7_ram_0_S_AXI_BASEADDR<44> from the drop down list.
*
* 3) Copy the ps7_init.c & ps7_init.h files from the hw_platform folder
* into the example folder.
* 4) Uncomment calling of <20>ps7_init()<29> routine in
* <09>xilskey_efuse_example.c<>
* 5) Compile the project.
* 6) <project name>.elf will be generated. This will be executed
* out of OCM.
*
* SVF File Generation using <output>.elf :
*
* 1) Use the below xmd to create the svf file from the above generated
* elf file. Please note that path to the elf file should be given in opt file.
*
* <09>xmd <20>tcl efuse.tcl <20>opt efuse.opt<70>
*
* 2) Output of the above command will be <O/p file name>.svf.
*
* For Ultrascale
* -----------------------------------------------------------------------
* Accessing Ultrascale microblaze 's eFuse is done by using block RAM
* initialization.
* Master Jtag primitive has to added to design i.e MASTER_JTAG_inst
* instantiation have to performed and AXI GPIO pins has to be connected
* to TDO, TDI, TMS and TCK signals of MASTER_JTAG primitive.
* All Inputs(TDO) and All Outputs(TDI, TMS, TCK) of MASTER_JTAG can be
* connected as
* 1) All Inputs to one channel
* All Outputs to other channel
* Valid example: All Outputs connected to Channel 1
* Input signal TDO also connected to channel 2
* 2) All Inputs and All Outputs to same channel.
* Valid example: All Outputs connected to Channel 1
* Input signal TDO also connected to channel 1
* 3) But some of the Outputs in one channel and some of them in different
* channel is not accepted.
* Invalid example: All Outputs connected to Channel 1
* Input signals (TDI, TMS) connected to Channel 1
* Input signal TCK also connected to channel 2
* The design should only contain AXI bram Ctrl memory mapped(1MB).
* System management wizard should be operated in DRP interface.
* Note: MASTER_JTAG will disable all other JTAGs
*
* Procedure to access efuse of Ultrascale:
* 1) After providing the required inputs in xilskey_input.h, compile the
* project.
* 2) Generate a memory mapped interface file using TCL command
* write_mem_info $Outfilename
* 3) Update memory has to be done using the tcl command updatemem.
* updatemem -meminfo $file.mmi -data $Outfilename.elf -bit $design.bit
* -proc design_1_i/microblaze_0 -out $Final.bit
* 4) Program the board using $Final.bit bitstream
* 5) Output can be seen in UART terminal.
* 6) For calculating CRC of AES key reverse polynomial is 0x82F63B78 or
* one can use the API u32 XilSKey_CrcCalculation(u8 *Key)
*
* MODIFICATION HISTORY:
*
* Ver Who Date Changes
* ----- ---- -------- --------------------------------------------------------
* 1.00a rpoolla 04/26/13 First release
* 1.02a hk 10/28/13 Added use of API's read status and key. PR# 735957.
* 3.00 vns 31/07/15 Modified XSK_EFUSEPL_RSA_KEY_HASH_STRING_SIZE macro
* name to XSK_EFUSEPS_RSA_KEY_HASH_STRING_SIZE.
* Added missing goto statement.
* Modified init function, intialisation of instance is
* done based on the platform and Modified example
* to support both Zynq PL's eFuse and also Ultrascale's
* eFuse.
* 4.00 vns 09/10/15 Added DFT JTAG disable and DFT MODE disable
* programming and reading options for Zynq eFuse PS.
*
****************************************************************************/
/***************************** Include Files *********************************/
#include "stdio.h"
#include "xil_io.h"
#include "xstatus.h"
#include "xilskey_utils.h"
#include "xilskey_eps.h"
#include "xilskey_epl.h"
#include "xilskey_input.h"
/************************** Constant Definitions *****************************/
/**************************** Type Definitions ******************************/
/***************** Macros (Inline Functions) Definitions ********************/
/**
* Address for the Reboot Status Register
*/
#define REBOOT_STATUS_REG_ADDR (0xF8000258)
/**
* PL eFUSE aes key size in characters
*/
#define XSK_EFUSEPL_AES_KEY_STRING_SIZE (64)
/**
* PL eFUSE user low key size in characters
*/
#define XSK_EFUSEPL_USER_LOW_KEY_STRING_SIZE (2)
/**
* PL eFUSE user high key size in characters
*/
#define XSK_EFUSEPL_USER_HIGH_KEY_STRING_SIZE (6)
/**
* User AES Key size in Bytes
*/
#define XSK_EFUSEPL_AES_KEY_SIZE_IN_BITS (256)
/**
* User Low Key size in Bytes
*/
#define XSK_EFUSEPL_USER_LOW_KEY_SIZE_IN_BITS (8)
/**
* User High Key size in Bytes
*/
#define XSK_EFUSEPL_USER_HIGH_KEY_SIZE_IN_BITS (24)
/**
* user key size in bits
*/
#define XSK_EFUSEPL_USER_KEY_SIZE_IN_BITS (32)
/**
* PL eFUSE RSA key size in characters
*/
#define XSK_EFUSEPL_RSA_KEY_HASH_STRING_SIZE (96)
/**
* RSA Key size in Bytes
*/
#define XSK_EFUSEPL_RSA_KEY_SIZE_IN_BITS (384)
/**
* PL eFuse user key size in characters
*/
#define XSK_EFUSEPL_USER_KEY_STRING_SIZE (8)
/**
* Key length definition for RSA KEY Hash
*/
/**
* PS eFUSE RSA key Hash size in characters
*/
#define XSK_EFUSEPS_RSA_KEY_HASH_STRING_SIZE (64)
/*
* PS efuse status bit definitions
*/
#define XSK_EFUSEPS_STATUS_WP_BIT_LOW 0x1000
#define XSK_EFUSEPS_STATUS_WP_BIT_HIGH 0x2000
#define XSK_EFUSEPS_STATUS_RSA_EN 0x400
#define XSK_EFUSEPS_STATUS_ROM_128_CRC 0x800
#define XSK_EFUSEPS_STATUS_DFT_JTAG_DISABLE 0x200
#define XSK_EFUSEPS_STATUS_DFT_MODE_DISABLE 0x100
/*
* PL efuse status bit definitions of Zynq
*/
#define XSK_EFUSEPL_STATUS_FORCE_PCYCLE_RECONFIG 0x002
#define XSK_EFUSEPL_STATUS_DISABLE_KEY_WRITE 0x004
#define XSK_EFUSEPL_STATUS_DISABLE_AES_KEY_READ 0x008
#define XSK_EFUSEPL_STATUS_DISABLE_USER_KEY_READ 0x010
#define XSK_EFUSEPL_STATUS_DISABLE_FUSE_CNTRL_WRITE 0x020
#define XSK_EFUSEPL_STATUS_EFUSE_SEC_ENABLE 0x100
#define XSK_EFUSEPL_STATUS_JTAG_DISABLE 0x200
#define XSK_EFUSEPL_STATUS_BBRAM_KEY_DISABLE 0x400
/************************** Variable Definitions ****************************/
/************************** Function Prototypes *****************************/
/**
* Function used to convert the string to Hex in Little Endian format
*/
u32 XilSKey_Efuse_ConvertStringToHexLE(const char * Str, u8 * Buf, u32 Len);
/**
* Function used to convert the string to Hex in Little Endian format
*/
u32 XilSKey_Efuse_ConvertStringToHexBE(const char * Str, u8 * Buf, u32 Len);
/**
* Function used to validate the AES & RSA key provided as input
*/
u32 XilSKey_Efuse_ValidateKey(const char *Key, u32 Len);
u32 XilSKey_EfusePs_InitData(XilSKey_EPs *PsInstancePtr);
u32 XilSKey_EfusePl_InitData(XilSKey_EPl *PlInstancePtr);
/*extern void ps7_init();*/
/***************************************************************************/
int main()
{
u32 PlStatus = 0xFFFF;
u32 PsStatus = 0xFFFF;
u32 Status = 0;
/*ps7_init();*/
#ifdef XSK_EFUSEPS_DRIVER
XilSKey_EPs PsInstancePtr;
u32 PsStatusBits = 0;
#ifdef XSK_MICROBLAZE_PLATFORM
xil_printf("Kintex ultrascale will not have PS please disable"
"XSK_EFUSEPS_DRIVER\n\r");
goto EFUSE_ERROR;
#endif
/**
* Initialize the PS instance pointer with the data
* populated in xilskey_input.h
*/
PsStatus = XilSKey_EfusePs_InitData(&PsInstancePtr);
if(PsStatus != XST_SUCCESS) {
printf("PS Data Initialization failed\r\n");
goto EFUSE_ERROR;
}
/*
* Read the PS efuse status
* Change in these status bits will only be reflected after POR
*/
PsStatus = XilSKey_EfusePs_ReadStatus(&PsInstancePtr, &PsStatusBits);
if(PsStatus != XST_SUCCESS) {
printf("PS status read failed\r\n");
goto EFUSE_ERROR;
}
/*
* Print Efuse PS status bits
*/
xil_printf("EfusePS status bits : 0x%x \n\r", PsStatusBits);
if((PsStatusBits & XSK_EFUSEPS_STATUS_WP_BIT_LOW) ||
(PsStatusBits & XSK_EFUSEPS_STATUS_WP_BIT_HIGH)) {
xil_printf("EfusePS status bits : Write protect enabled\n\r");
}else {
xil_printf("EfusePS status bits : Write protect disabled\n\r");
}
if(PsStatusBits & XSK_EFUSEPS_STATUS_RSA_EN) {
xil_printf("EfusePS status bits : RSA authentication of "
"fsbl enabled\n\r");
}else {
xil_printf("EfusePS status bits : RSA authentication of "
"fsbl disabled\n\r");
}
if(PsStatusBits & XSK_EFUSEPS_STATUS_ROM_128_CRC) {
xil_printf("EfusePS status bits : 128k CRC check on ROM enabled\n\r");
}else {
xil_printf("EfusePS status bits : 128k CRC check on ROM disabled\n\r");
}
if (PsStatusBits & XSK_EFUSEPS_STATUS_DFT_JTAG_DISABLE) {
xil_printf("EfusePS status bits : DFT JTAG is disabled\n\r");
}
else {
xil_printf("EfusePS status bits : DFT JTAG is enabled\n\r");
}
if (PsStatusBits & XSK_EFUSEPS_STATUS_DFT_MODE_DISABLE) {
xil_printf("EfusePS status bits : DFT mode is disabled\n\r");
}
else {
xil_printf("EfusePS status bits : DFT mode is enabled\n\r");
}
/**
* Write the PS eFUSE as defined in xilskeyinput.h
*/
PsStatus = XilSKey_EfusePs_Write(&PsInstancePtr);
if (PsStatus != XST_SUCCESS) {
printf("PS EFUSE writing failed\n");
goto EFUSE_ERROR;
}
u32 Index;
/**
* Clear the structure element of Rsa Key Hash for reading
*/
for(Index=0;Index<32;Index++){
PsInstancePtr.RsaKeyHashValue[Index]=0;
}
/**
* Read the PS eFUSE RSA Key Hash
*/
PsStatus = XilSKey_EfusePs_Read(&PsInstancePtr);
if (PsStatus != XST_SUCCESS){
printf("PS EFUSE reading failed\n");
goto EFUSE_ERROR;
}
/**
* Print the read PS eFUSE RSA Key Hash
*/
printf("Read RSA Key Hash: \n");
for(Index=0;Index<32;Index++){
printf("%02x",PsInstancePtr.RsaKeyReadback[Index]);
}
printf("\n");
#endif /* XSK_EFUSEPS_DRIVER*/
#ifdef XSK_EFUSEPL_DRIVER
XilSKey_EPl PlInstancePtr;
u32 PlStatusBits = 0;
int KeyCnt;
/**
* Initialize the PL data structure based on the xilskey_input.h values
*/
PlStatus = XilSKey_EfusePl_InitData(&PlInstancePtr);
if( PlStatus != XST_SUCCESS) {
printf("PL Data Initialization Failed\r\n");
goto EFUSE_ERROR;
}
/**
* Call the PL eFUSE programming function to program the eFUSE
* based on the user input
*/
PlStatus = XilSKey_EfusePl_Program(&PlInstancePtr);
if(PlStatus != XST_SUCCESS) {
printf("PL eFUSE programming failed\r\n");
goto EFUSE_ERROR;
}
/*
* Read Efuse PL status bits
*/
PlStatus = XilSKey_EfusePl_ReadStatus(&PlInstancePtr, &PlStatusBits);
if( PlStatus != XST_SUCCESS) {
printf("PL efuse status read failed\r\n");
goto EFUSE_ERROR;
}
/*
* Print Efuse PL status bits
*/
xil_printf("EfusePL status bits : 0x%x \n\r", PlStatusBits);
/* Status bits for Zynq */
if (PlInstancePtr.FpgaFlag == XSK_FPGA_SERIES_ZYNQ) {
if(PlStatusBits & XSK_EFUSEPL_STATUS_FORCE_PCYCLE_RECONFIG) {
xil_printf("EfusePL status bits : Force power cycle for "
"reconfiguration enabled\n\r");
}else {
xil_printf("EfusePL status bits : Force power cycle for "
"reconfiguration disabled\n\r");
}
if(PlStatusBits & XSK_EFUSEPL_STATUS_DISABLE_KEY_WRITE) {
xil_printf("EfusePL status bits : Key write disabled \n\r");
}else {
xil_printf("EfusePL status bits : Key write enabled \n\r");
}
if(PlStatusBits & XSK_EFUSEPL_STATUS_DISABLE_AES_KEY_READ) {
xil_printf("EfusePL status bits : AES Key read disabled \n\r");
}else {
xil_printf("EfusePL status bits : AES Key read enabled \n\r");
}
if(PlStatusBits & XSK_EFUSEPL_STATUS_DISABLE_USER_KEY_READ) {
xil_printf("EfusePL status bits : User Key read disabled \n\r");
}else {
xil_printf("EfusePL status bits : User Key read enabled \n\r");
}
if(PlStatusBits & XSK_EFUSEPL_STATUS_DISABLE_FUSE_CNTRL_WRITE) {
xil_printf("EfusePL status bits : Fuse Control write disabled \n\r");
}else {
xil_printf("EfusePL status bits : Fuse Control write enabled \n\r");
}
if(PlStatusBits & XSK_EFUSEPL_STATUS_EFUSE_SEC_ENABLE) {
xil_printf("EfusePL status bits : Efuse secure boot enabled \n\r");
}else {
xil_printf("EfusePL status bits : Efuse secure boot disabled \n\r");
}
if(PlStatusBits & XSK_EFUSEPL_STATUS_JTAG_DISABLE) {
xil_printf("EfusePL status bits : Jtag disabled \n\r");
}else {
xil_printf("EfusePL status bits : Jtag enabled \n\r");
}
if(PlStatusBits & XSK_EFUSEPL_STATUS_BBRAM_KEY_DISABLE) {
xil_printf("EfusePL status bits : BBRAM key disabled \n\r");
}else {
xil_printf("EfusePL status bits : BBRAM key enabled \n\r");
}
}
else { /* for Ultrascale */
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_DISABLE_KEY_READ_ULTRA)) {
xil_printf("EfusePL status bits : AES key read and programming disabled \n\r");
}else {
xil_printf("EfusePL status bits : AES key read enabled\n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_DISABLE_USER_KEY_READ_ULTRA)) {
xil_printf("EfusePL status bits : User key read and programming disabled \n\r");
}else {
xil_printf("EfusePL status bits : User key read enabled\n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_DISABLE_SECURE_READ_ULTRA)) {
xil_printf("EfusePL status bits : Secure bits read and programming disabled \n\r");
}else {
xil_printf("EfusePL status bits : Secure bits read enabled\n\r");
}
if(PlStatusBits & (1<< XSK_EFUSEPL_STATUS_DISABLE_CNTRL_WRITE_ULTRA)) {
xil_printf("EfusePL status bits : Cntrol bits write disabled \n\r");
}else {
xil_printf("EfusePL status bits : Control bits write enabled\n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_DISABLE_RSA_KEY_READ_ULTRA)) {
xil_printf("EfusePL status bits : RSA key read and programming disabled \n\r");
}else {
xil_printf("EfusePL status bits : RSA key read enabled\n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_DISABLE_KEY_WRITE_ULTRA)) {
xil_printf("EfusePL status bits : AES key programming disabled \n\r");
}else {
xil_printf("EfusePL status bits : AES key programming enabled\n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_DISABLE_USER_KEY_WRITE_ULTRA)) {
xil_printf("EfusePL status bits : User key programming disabled \n\r");
}else {
xil_printf("EfusePL status bits : User key programming enabled\n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_DISABLE_SECURE_WRITE_ULTRA)) {
xil_printf("EfusePL status bits : Secure bits programming disabled \n\r");
}else {
xil_printf("EfusePL status bits : Secure bits programming enabled\n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_DISABLE_RSA_KEY_WRITE_ULTRA)) {
xil_printf("EfusePL status bits : RSA key programming disabled \n\r");
}else {
xil_printf("EfusePL status bits : RSA key programming enabled\n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_FUSE_LOGIC_IS_BUSY_ULTRA)) {
xil_printf("EfusePL status bits : FUSE logic is busy \n\r");
}else {
xil_printf("EfusePL status bits : FUSE logic is free \n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_ALLOW_ENCRYPTED_ONLY_ULTRA)) {
xil_printf("EfusePL status bits : Only allows encrypted bitstreams\n\r");
}else {
xil_printf("EfusePL status bits : Non encrypted bitstream allowed\n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_AES_ONLY_ENABLED_ULTRA)) {
xil_printf("EfusePL status bits : Decryption only by AES of FUSE \n\r");
}else {
xil_printf("EfusePL status bits : Decryption can be AES of FUSE or BBRAM \n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_RSA_AUTH_ENABLED_ULTRA)) {
xil_printf("EfusePL status bits : RSA authentication is enabled \n\r");
}else {
xil_printf("EfusePL status bits : RSA authentication is disabled \n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_DISABLE_JTAG_ULTRA)) {
xil_printf("EfusePL status bits : External Jtag pins are disabled\n\r");
}else {
xil_printf("EfusePL status bits : Jtag is not disabled\n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_DISABLE_TEST_ACCESS_ULTRA)) {
xil_printf("EfusePL status bits : Disables test access\n\r");
}else {
xil_printf("EfusePL status bits : Xilinx test access is enabled\n\r");
}
if(PlStatusBits & (1 << XSK_EFUSEPL_STATUS_DISABLE_DCRPTR_ULTRA)) {
xil_printf("EfusePL status bits : Decryptor disabled \n\r");
}else {
xil_printf("EfusePL status bits : Decryptor enabled\n\r");
}
}
/*
* Read Efuse PL key
*/
PlStatus = XilSKey_EfusePl_ReadKey(&PlInstancePtr);
if( PlStatus != XST_SUCCESS) {
xil_printf("PL efuse key read failed\r\n");
goto EFUSE_ERROR;
}
#ifdef XSK_ARM_PLATFORM
/*
* Print Efuse PL key
*/
xil_printf("EfusePL User key : 0x");
for(KeyCnt = 3; KeyCnt >= 0; KeyCnt--)
{
xil_printf("%02x", PlInstancePtr.UserKeyReadback[KeyCnt]);
}
xil_printf("\n\r");
xil_printf("EfusePL AES key : 0x");
for(KeyCnt = 31; KeyCnt >= 0; KeyCnt--)
{
xil_printf("%02x", PlInstancePtr.AESKeyReadback[KeyCnt]);
}
xil_printf("\n\r");
#else
if (XSK_EFUSEPL_CHECK_AES_KEY_CRC == TRUE){
if (PlInstancePtr.AESKeyMatched == TRUE) {
xil_printf("AES key matched with expected AES Key's CRC\n\r");
}
else {
xil_printf("AES key not matched with expected AES's CRC "
"Please provide key's valid CRC \n\r");
}
}
if (XSK_EFUSEPL_READ_USER_KEY == TRUE) {
xil_printf("\r\nEfusePL User key : 0x");
for(KeyCnt = (XSK_EFUSEPL_USER_KEY_SIZE_IN_BYTES - 1); KeyCnt >= 0; KeyCnt--) {
xil_printf("%02x", PlInstancePtr.UserKeyReadback[KeyCnt]);
}
}
xil_printf("\r\n");
if (XSK_EFUSEPL_READ_RSA_KEY_HASH == TRUE) {
xil_printf("\r\nEfusePL RSA hash value : 0x");
for(KeyCnt = (XSK_EFUSEPL_RSA_KEY_HASH_SIZE_IN_BYTES - 1); KeyCnt >= 0; KeyCnt--) {
xil_printf("%02x", PlInstancePtr.RSAHashReadback[KeyCnt]);
}
}
xil_printf("\r\n");
#endif
#endif /*XSK_EFUSEPL_DRIVER*/
EFUSE_ERROR:
/**
* Write the error returned in the Reboot Status Register
* Eg: If the reboot status register value is 0xYYYYZZZZ
* then
* - YYYY Represents the PS eFUSE Status.
* - ZZZZ Represents the PL eFUSE Status.
*
* - Value 0x0000ZZZZ
* represents PS eFUSE is successful & PL eFUSE process
* returned with error.
* - Value 0xYYYY0000
* represents PL eFUSE is successful & PS eFUSE process
* returned with error.
* - Value 0xFFFF0000
* represents PS eFUSE is not initiated & PL eFUSE is successful.
* - Value 0x0000FFFF
* represents PL eFUSE is not initiated & PS eFUSE is successful.
* - Value 0xFFFFZZZZ
* represents PS eFUSE is not initiated & PL eFUSE is process
* returned with error.
* - Value 0xYYYYFFFF
* represents PL eFUSE is not initiated & PS eFUSE is process
* returned with error.
*/
Status = ((PsStatus << 16) + PlStatus);
xil_printf("\r\neFUSE operations exit status: %08X\r\n", Status);
#ifdef XSK_ARM_PLATFORM
/**
* Writing the Exit Status to Reboot Status Register
*/
Xil_Out32(REBOOT_STATUS_REG_ADDR,Status);
#endif
while(1);
return 0;
}
#ifdef XSK_EFUSEPS_DRIVER
/****************************************************************************/
/**
*
*
* Helper functions to properly initialize the PS eFUSE structure instance
*
*
* @param PsInstancePtr - Structure Address to update the structure elements
*
* @return
*
* - XST_SUCCESS - In case of Success
* - XST_FAILURE - If initialization fails
*
* @note
*
*****************************************************************************/
u32 XilSKey_EfusePs_InitData(XilSKey_EPs *PsInstancePtr)
{
u32 PsStatus;
PsStatus = XST_SUCCESS;
/**
* Copy the xilskeyinput.h values into PS structure elements
*/
PsInstancePtr->EnableWriteProtect = XSK_EFUSEPS_ENABLE_WRITE_PROTECT;
PsInstancePtr->EnableRsaAuth = XSK_EFUSEPS_ENABLE_RSA_AUTH;
PsInstancePtr->EnableRom128Crc = XSK_EFUSEPS_ENABLE_ROM_128K_CRC;
PsInstancePtr->EnableRsaKeyHash = XSK_EFUSEPS_ENABLE_RSA_KEY_HASH;
PsInstancePtr->DisableDftJtag = XSK_EFUSEPS_DISABLE_DFT_JTAG;
PsInstancePtr->DisableDftMode = XSK_EFUSEPS_DISABLE_DFT_MODE;
if (PsInstancePtr->EnableRsaKeyHash == TRUE) {
/**
* Validation of RSA Hash
*/
PsStatus = XilSKey_Efuse_ValidateKey(
(char *)XSK_EFUSEPS_RSA_KEY_HASH_VALUE,
XSK_EFUSEPS_RSA_KEY_HASH_STRING_SIZE);
if(PsStatus != XST_SUCCESS) {
return PsStatus;
}
/**
* Convert the input RSA Key Hash string into Hex buffer
*/
PsStatus = XilSKey_Efuse_ConvertStringToHexBE(
XSK_EFUSEPS_RSA_KEY_HASH_VALUE,
&(PsInstancePtr->RsaKeyHashValue[0]), 64);
if(PsStatus != XST_SUCCESS) {
return PsStatus;
}
}
return PsStatus;
}
#endif /* XSK_EFUSEPS_DRIVER*/
#ifdef XSK_EFUSEPL_DRIVER
/****************************************************************************/
/**
*
*
* Helper functions to properly initialize the PL eFUSE structure instance
*
*
* @param PlInstancePtr - Structure Address to update the structure elements
*
* @return
*
* - XST_SUCCESS - In case of Success
* - XST_FAILURE - If initialization fails
*
* @note
*
*****************************************************************************/
u32 XilSKey_EfusePl_InitData(XilSKey_EPl *PlInstancePtr)
{
u32 PlStatus;
PlStatus = XST_SUCCESS;
/**
* Copy the xilskeyinput.h values into PL eFUSE structure elements
*/
/* For Zynq PL efuse */
/**
* Assign FUSE CNTRL bits[1:5] to the PL eFUSE structure elements.
*/
#ifdef XSK_ARM_PLATFORM
/* Assign FUSE CNTRL bits[1:5] to the PL eFUSE structure elements.*/
PlInstancePtr->ForcePowerCycle = XSK_EFUSEPL_FORCE_PCYCLE_RECONFIG;
PlInstancePtr->KeyWrite = XSK_EFUSEPL_DISABLE_KEY_WRITE;
PlInstancePtr->AESKeyRead = XSK_EFUSEPL_DISABLE_AES_KEY_READ;
PlInstancePtr->UserKeyRead = XSK_EFUSEPL_DISABLE_USER_KEY_READ;
PlInstancePtr->CtrlWrite = XSK_EFUSEPL_DISABLE_FUSE_CNTRL_WRITE;
/**
* Assign the FUSE CNTRL bits[8:10] into the PL eFUSE structure elements
*/
PlInstancePtr->UseAESOnly = XSK_EFUSEPL_FORCE_USE_AES_ONLY;
PlInstancePtr->JtagDisable = XSK_EFUSEPL_DISABLE_JTAG_CHAIN;
PlInstancePtr->AESKeyExclusive = XSK_EFUSEPL_BBRAM_KEY_DISABLE;
PlInstancePtr->JtagMioTDI = XSK_EFUSEPL_MIO_JTAG_TDI;
PlInstancePtr->JtagMioTDO = XSK_EFUSEPL_MIO_JTAG_TDO;
PlInstancePtr->JtagMioTCK = XSK_EFUSEPL_MIO_JTAG_TCK;
PlInstancePtr->JtagMioTMS = XSK_EFUSEPL_MIO_JTAG_TMS;
PlInstancePtr->JtagMioMuxSel = XSK_EFUSEPL_MIO_JTAG_MUX_SELECT;
PlInstancePtr->JtagMuxSelLineDefVal = XSK_EFUSEPL_MIO_MUX_SEL_DEFAULT_VAL;
/*
* Variable to check whether internal system initialization is done.
*/
PlInstancePtr->SystemInitDone = 0;
/**
* Assign the user selection for AES & USER Low Key (or)
* User High Key (or) both
*/
PlInstancePtr->ProgAESandUserLowKey =
XSK_EFUSEPL_PROGRAM_AES_AND_USER_LOW_KEY;
PlInstancePtr->ProgUserHighKey = XSK_EFUSEPL_PROGRAM_USER_HIGH_KEY;
if (PlInstancePtr->ProgAESandUserLowKey == TRUE) {
/**
* Validation of AES Key
*/
PlStatus = XilSKey_Efuse_ValidateKey((char *)XSK_EFUSEPL_AES_KEY,
XSK_EFUSEPL_AES_KEY_STRING_SIZE);
if(PlStatus != XST_SUCCESS) {
goto PL_INIT_ERROR;
}
/**
* Validation of User Low Key
*/
PlStatus = XilSKey_Efuse_ValidateKey((char *)XSK_EFUSEPL_USER_LOW_KEY,
XSK_EFUSEPL_USER_LOW_KEY_STRING_SIZE);
if(PlStatus != XST_SUCCESS) {
goto PL_INIT_ERROR;
}
/**
* Assign the AES Key Value
*/
XilSKey_Efuse_ConvertStringToHexLE((char *)XSK_EFUSEPL_AES_KEY ,
&PlInstancePtr->AESKey[0],
XSK_EFUSEPL_AES_KEY_SIZE_IN_BITS);
/**
* Assign the User Low key [7:0] bits
*/
XilSKey_Efuse_ConvertStringToHexLE((char *)XSK_EFUSEPL_USER_LOW_KEY ,
&PlInstancePtr->UserKey[0],
XSK_EFUSEPL_USER_LOW_KEY_SIZE_IN_BITS);
}
if (PlInstancePtr->ProgUserHighKey == TRUE) {
/**
* Validation of User High Key
*/
PlStatus = XilSKey_Efuse_ValidateKey(
(char *)XSK_EFUSEPL_USER_HIGH_KEY,
XSK_EFUSEPL_USER_HIGH_KEY_STRING_SIZE);
if(PlStatus != XST_SUCCESS) {
goto PL_INIT_ERROR;
}
/**
* Assign the User High key [31:8] bits
*/
XilSKey_Efuse_ConvertStringToHexLE((char *)XSK_EFUSEPL_USER_HIGH_KEY ,
&PlInstancePtr->UserKey[1],
XSK_EFUSEPL_USER_HIGH_KEY_SIZE_IN_BITS);
}
#else
/* For Ultrascle efuse */
/* eFuse control bits [2:0] */
PlInstancePtr->AESKeyRead= XSK_EFUSEPL_DISABLE_AES_KEY_READ;
PlInstancePtr->UserKeyRead = XSK_EFUSEPL_DISABLE_USER_KEY_READ;
PlInstancePtr->SecureRead = XSK_EFUSEPL_DISABLE_SECURE_READ;
/* eFuse Control bits [9:5] */
PlInstancePtr->CtrlWrite = XSK_EFUSEPL_DISABLE_FUSE_CNTRL_WRITE;
PlInstancePtr->RSARead = XSK_EFUSEPL_DISABLE_RSA_KEY_READ;
PlInstancePtr->KeyWrite = XSK_EFUSEPL_DISABLE_KEY_WRITE;
PlInstancePtr->UserKeyWrite = XSK_EFUSEPL_DISABLE_USER_KEY_WRITE;
PlInstancePtr->SecureWrite = XSK_EFUSEPL_DISABLE_SECURE_WRITE;
/* eFuse control bit 15 */
PlInstancePtr->RSAWrite = XSK_EFUSEPL_DISABLE_RSA_HASH_WRITE;
/* eFuse secure bits [5:0] */
PlInstancePtr->EncryptOnly = XSK_EFUSEPL_ALLOW_ENCRYPTED_ONLY;
PlInstancePtr->UseAESOnly = XSK_EFUSEPL_FORCE_USE_FUSE_AES_ONLY;
PlInstancePtr->RSAEnable = XSK_EFUSEPL_ENABLE_RSA_AUTH;
PlInstancePtr->JtagDisable = XSK_EFUSEPL_DISABLE_JTAG_CHAIN;
PlInstancePtr->IntTestAccessDisable = XSK_EFUSEPL_DISABLE_TEST_ACCESS;
PlInstancePtr->DecoderDisable = XSK_EFUSEPL_DISABLE_DECODER;
PlInstancePtr->ProgAESKeyUltra = XSK_EFUSEPL_PROGRAM_AES_KEY;
PlInstancePtr->ProgUserKeyUltra = XSK_EFUSEPL_PROGRAM_USER_KEY;
PlInstancePtr->ProgRSAKeyUltra = XSK_EFUSEPL_PROGRAM_RSA_KEY_HASH;
PlInstancePtr->ReadUserKeyUltra = XSK_EFUSEPL_READ_USER_KEY;
PlInstancePtr->ReadRSAKeyUltra = XSK_EFUSEPL_READ_RSA_KEY_HASH;
PlInstancePtr->CheckAESKeyUltra = XSK_EFUSEPL_CHECK_AES_KEY_CRC;
PlInstancePtr->CrcOfAESKey = XSK_EFUSEPL_CRC_OF_EXPECTED_AES_KEY;
PlInstancePtr->JtagGpioTDI = XSK_EFUSEPL_AXI_GPIO_JTAG_TDI;
PlInstancePtr->JtagGpioTMS = XSK_EFUSEPL_AXI_GPIO_JTAG_TMS;
PlInstancePtr->JtagGpioTCK = XSK_EFUSEPL_AXI_GPIO_JTAG_TCK;
PlInstancePtr->JtagGpioTDO = XSK_EFUSEPL_AXI_GPIO_JTAG_TDO;
PlInstancePtr->GpioInputCh = XSK_EFUSEPL_GPIO_INPUT_CH;
PlInstancePtr->GpioOutPutCh = XSK_EFUSEPL_GPIO_OUTPUT_CH;
if (PlInstancePtr->ProgUserKeyUltra == TRUE) {
/* Validation of User High Key */
PlStatus = XilSKey_Efuse_ValidateKey(
(char *)XSK_EFUSEPL_USER_KEY,
XSK_EFUSEPL_USER_KEY_STRING_SIZE);
if(PlStatus != XST_SUCCESS) {
goto PL_INIT_ERROR;
}
/* Assign the User key [31:0]bits */
XilSKey_Efuse_ConvertStringToHexLE(
(char *)XSK_EFUSEPL_USER_KEY ,
&PlInstancePtr->UserKey[0],
XSK_EFUSEPL_USER_KEY_SIZE_IN_BITS);
}
if (PlInstancePtr->ProgAESKeyUltra == TRUE) {
/* Validation of AES Key */
PlStatus = XilSKey_Efuse_ValidateKey(
(char *)XSK_EFUSEPL_AES_KEY,
XSK_EFUSEPL_AES_KEY_STRING_SIZE);
if(PlStatus != XST_SUCCESS) {
goto PL_INIT_ERROR;
}
/* Assign the AES Key Value */
XilSKey_Efuse_ConvertStringToHexLE(
(char *)XSK_EFUSEPL_AES_KEY,
&PlInstancePtr->AESKey[0],
XSK_EFUSEPL_AES_KEY_SIZE_IN_BITS);
}
if (PlInstancePtr->ProgRSAKeyUltra == TRUE) {
/* Validation of RSA hash */
PlStatus = XilSKey_Efuse_ValidateKey(
(char *)XSK_EFUSEPL_RSA_KEY_HASH_VALUE,
XSK_EFUSEPL_RSA_KEY_HASH_STRING_SIZE);
if(PlStatus != XST_SUCCESS) {
goto PL_INIT_ERROR;
}
/* Assign the RSA hash */
XilSKey_Efuse_ConvertStringToHexLE(
(char *)XSK_EFUSEPL_RSA_KEY_HASH_VALUE,
&PlInstancePtr->RSAKeyHash[0],
XSK_EFUSEPL_RSA_KEY_SIZE_IN_BITS);
}
/* Variable to check whether internal system initialization is done.*/
PlInstancePtr->SystemInitDone = 0;
#endif
PL_INIT_ERROR:
return PlStatus;
}
#endif /*XSK_EFUSEPL_DRIVER*/