Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
169 changes: 144 additions & 25 deletions cli/mfg.c
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,8 @@
#define PING_SPI_CLK_SEL_MASK 0x30000
#define PING_SPI_CLK_SEL_OFFSET 16
#define PING_SPI_BUS_RATE_MASK 0xFFFF
#define MIN_PORT 1
#define MAX_PORT 65535

static const struct argconfig_choice recovery_mode_choices[] = {
{"I2C", SWITCHTEC_BL2_RECOVERY_I2C, "I2C"},
Expand Down Expand Up @@ -2307,33 +2309,67 @@ static int sjtag_unlock(int argc, char **argv)
struct switchtec_sn_ver_info sn_info = {};
uint8_t sjtag_hr[SJTAG_HR_LEN];
struct sjtag_debug_token debug_token;
FILE *debug_token_bin_file;
char dir_path[1024];
const char *port_str;
unsigned long temp;
char *endptr = NULL;

int ret;
static struct {
struct switchtec_dev *dev;
FILE *sjtag_debug_token;
const char *sjtag_debug_token_file;
int out_fd;
const char *out_filename;
const char *sjtag_server_ip;
uint16_t sjtag_server_port;
bool verbose;
bool force_hr;
} cfg = {
.verbose = false,
.force_hr = false};
.out_fd = -1,
.sjtag_server_ip = NULL,
.sjtag_server_port = 0,
.verbose = false,
.force_hr = false};

const struct argconfig_options opts[] = {
DEVICE_OPTION_MFG,
{"sjtag_debug_token_file",
.cfg_type=CFG_FILE_R,
.value_addr=&cfg.sjtag_debug_token,
.argument_type=optional_positional,
.help="Optional Argument. If not provided, the Debug Token will be generated\n"\
"SJTAG Debug Token File(.bin)\n" \
"Generated by the HSM Server\n"},
{"verbose", 'v', "", CFG_NONE, &cfg.verbose, no_argument,
"print additional sjtag-unlock information"},
{"force_hr", 'f', "", CFG_NONE, &cfg.force_hr, no_argument,
"send HR for all SJTAG mode"},
{
"debug_token_input_file", 'i',
.cfg_type=CFG_FILE_R,
.value_addr=&cfg.sjtag_debug_token,
.argument_type=required_argument,
.help="Optional Argument. If provided the input debug token file will be used for SJTAG Unlocking. If not provided, HSM server will be used for SJTAG Unlocking and the Debug Token (.bin) will be generated\n" \
"Note: When both -i and -o are provided, -i overides -o\n"
},
{
"debug_token_output_file", 'o',
.cfg_type=CFG_FD_WR,
.value_addr=&cfg.out_fd,
.argument_type=required_argument,
.help="Optional Argument. If not provided, the HSM generated Debug Token File will be named sjtag_debug_token.bin\n"
},
{
"sjtag_server_ip", 's',
.cfg_type=CFG_STRING,
.value_addr=&cfg.sjtag_server_ip,
.argument_type=required_argument,
.help="SJTAG HSM Server IP. Can also set via HSM_SERVER_IP environment variable."
},
{
"sjtag_server_port", 'p',
.cfg_type=CFG_SHORT,
.value_addr=&cfg.sjtag_server_port,
.argument_type=required_argument,
.help="SJTAG HSM Server Port. Can also set via HSM_SERVER_PORT environment variable."
},
{
"verbose", 'v', "", CFG_NONE, &cfg.verbose, no_argument,
"print additional sjtag-unlock information"
},
{
"force_hr", 'f', "", CFG_NONE, &cfg.force_hr, no_argument,
"send HR for all SJTAG mode"
},
{NULL}
};

Expand All @@ -2349,7 +2385,7 @@ static int sjtag_unlock(int argc, char **argv)
break;
}

if(true == cfg.verbose)
if (true == cfg.verbose)
{
printf("SJTAG Mode: %x\n", (status.data & 0x03));
}
Expand All @@ -2365,8 +2401,22 @@ static int sjtag_unlock(int argc, char **argv)
}
else
{
/* Open default output file only if no input file is provided */
if (!cfg.sjtag_debug_token_file && cfg.out_fd < 0)
{
cfg.out_filename = "sjtag_debug_token.bin";
cfg.out_fd = open(cfg.out_filename, O_WRONLY | O_CREAT | O_TRUNC, 0644);
if (cfg.out_fd < 0)
{
perror("Failed to open default output file");
ret = -1;
break;
}
}

if (cfg.sjtag_debug_token_file)
{
printf("HSM not used for Debug Token Generation. Using provided Debug Token(-i) for Unlocking.\n");
ret = switchtec_read_sjtag_debug_token_file(cfg.sjtag_debug_token, &debug_token);
fclose(cfg.sjtag_debug_token);
if (ret)
Expand All @@ -2378,11 +2428,56 @@ static int sjtag_unlock(int argc, char **argv)
}
else
{
/* If SJTAG IP and Port are not provided fetch it from environment variables*/
if (cfg.sjtag_server_ip == NULL)
{
cfg.sjtag_server_ip = getenv("HSM_SERVER_IP");
}

if (cfg.sjtag_server_port == 0)
{
/* Environment variables are always strings. convert the string to integer */
port_str = getenv("HSM_SERVER_PORT");
if (port_str != NULL)
{
errno = 0;
temp = strtoul(port_str, &endptr, 10);

if ((errno != 0) || temp > MAX_PORT || temp < MIN_PORT || endptr == port_str || *endptr != '\0')
{
fprintf(stderr, "Error: Invalid port number in HSM_SERVER_PORT environment variable\n");
ret = -1;
if (cfg.out_fd > 0)
{
close(cfg.out_fd);
}
break;
}
cfg.sjtag_server_port = (uint16_t)temp;
}
}

/* Check for Invalid IP and Port */
if((cfg.sjtag_server_ip == NULL) || (cfg.sjtag_server_port == 0))
{
fprintf(stderr, "Error: SJTAG server IP and Port are required when generating token from HSM server.\n");
ret = -1;
if (cfg.out_fd > 0)
{
close(cfg.out_fd);
}
break;
}

ret = switchtec_sjtag_get_uuid_idcode(cfg.dev, uuid.uuid, sjtag_unlock.idcode);
if (ret)
{
switchtec_perror("Failed to retrive the UUID/IDCODE from the device");
ret = -1;
if (cfg.out_fd > 0)
{
close(cfg.out_fd);
}
break;
}

Expand All @@ -2391,28 +2486,51 @@ static int sjtag_unlock(int argc, char **argv)
{
switchtec_perror("Failed to retrive the SUV from the device");
ret = -1;
if (cfg.out_fd > 0)
{
close(cfg.out_fd);
}
break;
}

ret = sjtag_debug_token_gen(sjtag_unlock.idcode, uuid.uuid, (uint8_t *)&sn_info.ver_sec_unlock, debug_token.debug_token, cfg.verbose);
ret = sjtag_debug_token_gen(sjtag_unlock.idcode,
uuid.uuid,
(uint8_t *)&sn_info.ver_sec_unlock,
debug_token.debug_token,
cfg.sjtag_server_ip,
cfg.sjtag_server_port,
cfg.verbose);

if(ret)
{
ret = -1;
if (cfg.out_fd > 0)
{
close(cfg.out_fd);
}
break;
}

debug_token_bin_file = fopen("sjtag_debug_token.bin", "wb");
if (NULL == debug_token_bin_file)
/* Save the generated Debug Token as a binary */
ret = write(cfg.out_fd, debug_token.debug_token, SJTAG_DEBUG_TOKEN_LEN);

close(cfg.out_fd);

if (ret != SJTAG_DEBUG_TOKEN_LEN)
{
switchtec_perror("Error opening file");
if (ret < 0)
{
perror("Error saving the Debug token");
}
else
{
perror("Error: Incomplete Debug Token");
}
ret = -1;
break;
}
}

fwrite(debug_token.debug_token, sizeof(uint8_t), SJTAG_DEBUG_TOKEN_LEN, debug_token_bin_file);
fclose(debug_token_bin_file);
getcwd(dir_path, sizeof(dir_path));
printf("Generated SJTAG Debug Token Path: %s/sjtag_debug_token.bin\n", dir_path);
fprintf(stdout, "\nGenerated SJTAG Debug token saved to %s\n", cfg.out_filename);
}

ret = switchtec_sjtag_get_nonce(cfg.dev, &nonce);
Expand All @@ -2437,6 +2555,7 @@ static int sjtag_unlock(int argc, char **argv)
}
}
}while(false);

return ret;
} /* sjtag_unlock() */

Expand Down
4 changes: 1 addition & 3 deletions inc/switchtec/mfg.h
Original file line number Diff line number Diff line change
Expand Up @@ -60,8 +60,6 @@

#define SKU_NO_OF_BLOCKS 4

#define SJTAG_SERVER_IP "10.40.56.34"
#define SJTAG_SERVER_PORT (5001)
#define SJTAG_SERVER_HEADER_LEN (4)
#define SJTAG_IDCODE_LEN (4)
#define SJTAG_HR_LEN (32)
Expand Down Expand Up @@ -394,7 +392,7 @@ int switchtec_sjtag_hr_send(struct switchtec_dev *dev,

int switchtec_read_sjtag_debug_token_file(FILE *debug_token_file, struct sjtag_debug_token *debug_token);
void sjtag_hr_calc(uint8_t *sjtag_debug_token, uint8_t *sjtag_nonce, uint8_t *digest, bool verbose);
int sjtag_debug_token_gen(uint8_t *idcode_ptr, uint8_t *uuid_ptr, uint8_t *suv_ptr, uint8_t *sjtag_debug_token, bool verbose);
int sjtag_debug_token_gen(uint8_t *idcode_ptr, uint8_t *uuid_ptr, uint8_t *suv_ptr, uint8_t *sjtag_debug_token, const char *server_ip, uint16_t server_port, bool verbose);
void sjtag_hr_compute(uint8_t *sjtag_uuid, uint8_t *sjtag_suv, uint8_t *sjtag_nonce, uint8_t *sjtag_hr);


Expand Down
6 changes: 3 additions & 3 deletions lib/mfg.c
Original file line number Diff line number Diff line change
Expand Up @@ -1001,7 +1001,7 @@ int sjtag_resp_is_success(uint8_t *resp_header)
*
* @return Returns 0 on Success and -1 on Failure
*/
int sjtag_debug_token_gen(uint8_t *idcode_ptr, uint8_t *uuid_ptr, uint8_t *suv_ptr, uint8_t *sjtag_debug_token, bool verbose)
int sjtag_debug_token_gen(uint8_t *idcode_ptr, uint8_t *uuid_ptr, uint8_t *suv_ptr, uint8_t *sjtag_debug_token, const char *server_ip, uint16_t server_port, bool verbose)
{
int ret = 0;
int socket_server;
Expand All @@ -1024,8 +1024,8 @@ int sjtag_debug_token_gen(uint8_t *idcode_ptr, uint8_t *uuid_ptr, uint8_t *suv_p

/* Set port and IP */
server_address.sin_family = AF_INET;
server_address.sin_port = htons(SJTAG_SERVER_PORT);
server_address.sin_addr.s_addr = inet_addr(SJTAG_SERVER_IP);
server_address.sin_port = htons(server_port);
server_address.sin_addr.s_addr = inet_addr(server_ip);

/* Send a connection request to Plugin server */
if(connect(socket_server, (struct sockaddr*)&server_address, sizeof(server_address)) < 0)
Expand Down