Skip to content

Commit

Permalink
Add fdo-sim support for Client-SDK
Browse files Browse the repository at this point in the history
Implement fdo.download and fdo.command fsim modules.

Signed-off-by: Shrikant Temburwar <[email protected]>
  • Loading branch information
shrikant1407 committed Jan 2, 2024
1 parent ed6e092 commit 2e570dd
Show file tree
Hide file tree
Showing 11 changed files with 1,664 additions and 11 deletions.
18 changes: 18 additions & 0 deletions app/main.c
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,24 @@ static fdo_sdk_service_info_module *fdo_sv_info_modules_init(void)
}
module_info[0].service_info_callback = fdo_sys;

/* module#2: fdo.download */
if (strncpy_s(module_info[1].module_name, FDO_MODULE_NAME_LEN,
"fdo.download", FDO_MODULE_NAME_LEN) != 0) {
LOG(LOG_ERROR, "Strcpy failed");
fdo_free(module_info);
return NULL;
}
module_info[1].service_info_callback = fdo_sim_download;

/* module#3: fdo.command */
if (strncpy_s(module_info[2].module_name, FDO_MODULE_NAME_LEN,
"fdo.command", FDO_MODULE_NAME_LEN) != 0) {
LOG(LOG_ERROR, "Strcpy failed");
fdo_free(module_info);
return NULL;
}
module_info[2].service_info_callback = fdo_sim_command;

return module_info;
}

Expand Down
5 changes: 5 additions & 0 deletions device_modules/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,16 @@

client_sdk_include_directories(
fdo_sys
fdo_sim
)

client_sdk_sources(
fdo_sys/fdo_sys.c
fdo_sys/sys_utils_linux.c
fdo_sim/fdo_sim.c
fdo_sim/fdo_sim_download.c
fdo_sim/fdo_sim_command.c
fdo_sim/sim_utils_linux.c
)


Expand Down
214 changes: 214 additions & 0 deletions device_modules/fdo_sim/fdo_sim.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,214 @@
/*
* Copyright 2023 Intel Corporation
* SPDX-License-Identifier: Apache 2.0
*/

#include "util.h"
#include "fdo_sim.h"
#include "safe_lib.h"
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include "fdo_sim_utils.h"

// position/offset on the file from which data will be read
static size_t file_seek_pos = 0;
// size of the file from which data will be read
static size_t file_sz = 0;
// EOT value whose value is 0 for 'fetch-data'success, and 1 for failure
static int fetch_data_status = 1;
// local isMore flag that represents whether the module has data/response to
// send in the NEXT messege SHOULD be 'true' if there is data to send, 'false'
// otherwise For simplicity, it is 'false' always (also a valid value)
static bool ismore = false;

/**
* List of helper functions used in switch case
*
* fdo_si_start
* fdo_si_failure
* fdo_si_has_more_dsi
* fdo_si_is_more_dsi
* fdo_si_get_dsi_count
* fdo_si_get_dsi
* fdo_end
*/

int fdo_si_start(fdor_t **fdor, fdow_t **fdow)
{
int result = FDO_SI_INTERNAL_ERROR;

// Initialize module's CBOR Reader/Writer objects.
*fdow = ModuleAlloc(sizeof(fdow_t));
if (!fdow_init(*fdow) ||
!fdo_block_alloc_with_size(&(*fdow)->b, 8192)) {
LOG(LOG_ERROR, "Module fdo_sim - FDOW "
"Initialization/Allocation failed!\n");
result = FDO_SI_CONTENT_ERROR;
goto end;
}

*fdor = ModuleAlloc(sizeof(fdor_t));
if (!fdor_init(*fdor) ||
!fdo_block_alloc_with_size(&(*fdor)->b, 8192)) {
LOG(LOG_ERROR, "Module fdo_sim - FDOR "
"Initialization/Allocation failed!\n");
goto end;
}
result = FDO_SI_SUCCESS;
end:
return result;
}

int fdo_si_failure(fdor_t **fdor, fdow_t **fdow)
{
// perform clean-ups as needed
if (!process_data(FDO_SIM_MOD_MSG_EXIT, NULL, 0, NULL, NULL, NULL, NULL,
NULL)) {
LOG(LOG_ERROR, "Module fdo_sim - Failed to perform "
"clean-up operations\n");
return FDO_SI_INTERNAL_ERROR;
}

if (*fdow) {
fdow_flush(*fdow);
ModuleFree(*fdow);
}
if (*fdor) {
fdor_flush(*fdor);
ModuleFree(*fdor);
}
return FDO_SI_SUCCESS;
}

int fdo_si_has_more_dsi(bool *has_more, bool hasmore)
{
// calculate whether there is ServiceInfo to send NOW and update
// 'has_more'. For testing purposes, set this to true here, and
// false once first write is done.
if (!has_more) {
return FDO_SI_CONTENT_ERROR;
}

*has_more = hasmore;
if (*has_more) {
LOG(LOG_INFO,
"Module fdo_sim - There is ServiceInfo to send\n");
}
return FDO_SI_SUCCESS;
}

int fdo_si_is_more_dsi(bool *is_more)
{
// calculate whether there is ServiceInfo to send in the NEXT
// iteration and update 'is_more'.
if (!is_more) {
LOG(LOG_ERROR, "is_more is NULL\n");
return FDO_SI_CONTENT_ERROR;
}

// sending either true or false is valid
// for simplicity, setting this to 'false' always,
// since managing 'ismore' by looking-ahead can be error-prone
*is_more = ismore;
return FDO_SI_SUCCESS;
}

int fdo_si_get_dsi_count(uint16_t *num_module_messages)
{
// calculate the number of ServiceInfo items to send NOW and update
// 'num_module_messages'. For testing purposes, set this to 1 here, and
// 0 once first write is done.
if (!num_module_messages) {
return FDO_SI_CONTENT_ERROR;
}
*num_module_messages = 1;
return FDO_SI_SUCCESS;
}

int fdo_si_get_dsi(fdow_t **fdow, size_t mtu, char *module_message,
uint8_t *module_val, size_t *module_val_sz, size_t bin_len,
uint8_t *bin_data, size_t temp_module_val_sz, bool *hasmore,
fdoSimModMsg *write_type, char *filename)
{
// write Device ServiceInfo using 'fdow' by partitioning the
// messages as per MTU, here.
if (mtu == 0 || !module_message || !module_val || !module_val_sz) {
return FDO_SI_CONTENT_ERROR;
}

int result = FDO_SI_INTERNAL_ERROR;

(void)bin_len;
(void)filename;

// reset and initialize FDOW's encoder for usage
fdo_block_reset(&(*fdow)->b);
if (!fdow_encoder_init(*fdow)) {
LOG(LOG_ERROR, "Module fdo_sim - Failed to initialize "
"FDOW encoder\n");
goto end;
}

if (!*hasmore || *write_type == FDO_SIM_MOD_MSG_EXIT) {
LOG(LOG_ERROR, "Module fdo_sim - Invalid state\n");
goto end;
}

// TO-DO: Imlement functionality

if (!fdow_encoded_length(*fdow, &temp_module_val_sz)) {
LOG(LOG_ERROR,
"Module fdo_sim - Failed to get encoded length\n");
goto end;
}
*module_val_sz = temp_module_val_sz;
if (memcpy_s(module_val, *module_val_sz, (*fdow)->b.block,
*module_val_sz) != 0) {
LOG(LOG_ERROR, "Module fdo_sim - Failed to copy "
"CBOR-encoded module value\n");
goto end;
}
result = FDO_SI_SUCCESS;
end:
result =
fdo_end(NULL, fdow, result, bin_data, NULL, 0, hasmore, write_type);
return result;
}

int fdo_end(fdor_t **fdor, fdow_t **fdow, int result, uint8_t *bin_data,
uint8_t **exec_instr, size_t total_exec_array_length, bool *hasmore,
fdoSimModMsg *write_type)
{
// End of function, clean-up state variables/objects
if (bin_data) {
ModuleFree(bin_data);
}
if (exec_instr && total_exec_array_length > 0) {
int exec_counter = total_exec_array_length - 1;
while (exec_counter >= 0) {
ModuleFree(exec_instr[exec_counter]);
--exec_counter;
}
ModuleFree(exec_instr);
total_exec_array_length = 0;
}
if (result != FDO_SI_SUCCESS) {
// clean-up state variables/objects
*hasmore = false;
file_sz = 0;
file_seek_pos = 0;
fetch_data_status = 1;
*write_type = FDO_SIM_MOD_MSG_EXIT;

if (*fdow) {
fdow_flush(*fdow);
ModuleFree(*fdow);
}
if (*fdor) {
fdor_flush(*fdor);
ModuleFree(*fdor);
}
}
return result;
}
128 changes: 128 additions & 0 deletions device_modules/fdo_sim/fdo_sim.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,128 @@
/*
* Copyright 2023 Intel Corporation
* SPDX-License-Identifier: Apache 2.0
*/

#ifndef __FDO_SYS_H__
#define __FDO_SYS_H__

#include <stdint.h>
#include <stddef.h>
#include "fdomodules.h"
#include "fdo_sim_utils.h"

// Maximum buffer size to be used for reading/writing CBOR data
#define MOD_MAX_BUFF_SIZE 8192

// file path could also be supplied
#define FILE_NAME_LEN 150

#define MOD_ACTIVE_TAG "active"
#define MOD_ACTIVE_STATUS "1"

// maximum length of exec command after combining all arguments of received exec
// array
#define MOD_MAX_EXEC_LEN 1024
// maximum length of the individual text arguments in the received exec array
#define MOD_MAX_EXEC_ARG_LEN 100

/**
* The registered callback method for 'fdo_sim' ServiceInfo module.
* The implementation is responsible for handling the received Owner
* ServiceInfo, and for generating the Device ServiceInfo to send.
*
* When module_message, module_val and module_val_sz are used as inputs in type
* 'FDO_SI_SET_OSI', these represent the moduleMessage, CBOR-encoded
* (bstr-unwrapped) module value i.e ServiceInfoVal cbor.bytes, as received in
* TO2.OwnerServiceInfo (Type 69), and its length. The implementation must parse
* and process the input module value depending on the given module message, and
* return.
*
* However, the same set of variables are used as output parameters in type
* 'FDO_SI_GET_DSI', wherein, module_message stores the current moduleMessage,
* module_val stores the response CBOR-encoded module value (ServiceInfoVal),
* and module_val_sz stores the corresponding length. The implementation is
* responsible for generating the CBOR-encoded module value using any
* mechanisms/third-party library. In the current implementation, the
* CBOR-encoder/decoder from 'lib/fdoblockio.c' is used. These 3 parameters are
* then, used to generate ServiceInfoKV at TO2.DeviceServiceInfo (Type 68), and
* sent to the Owner.
*
* The input FDOW object to be used to write the desired 'ServiceInfo' structure
* as per the specification, that will be sent to the Owner. The FDOW can also
* be used for other purposes such as ServiceInfo message partitioning (fit
* within MTU), or, determining has_more/is_more etc. The module implemenation
* is responsible for maintaining any internal state information, as needed.
*
* The input fdo_sdk_si_type can be used to do specific tasks depending on the
* use-case. (The types could be updated in the future)
*
* @param type - [IN] enum value to describe the operation to be done.
* @param module_message - [IN/OUT] moduleMessage that decides how
* ServiceInfoVal is processed.
* @param module_val - [IN/OUT] bstr-unwrapped ServiceInfoVal corresponding to
* the moduleMessage.
* @param module_val_sz - [IN/OUT] ServiceInfoVal length corresponding to the
* moduleMessage.
* @param num_module_messages - [OUT] Number of ServiceInfoKVs to be sent.
* Currently UNUSED.
* @param has_more - [OUT] pointer to bool whose value must be set to
* 'true' if there is Device ServiceInfo to send NOW/immediately, OR,
* 'false' if there is no Device ServiceInfo to send NOW/immediately.
* @param is_more - [OUT] pointer to bool whose value must be set to
* 'true' if there is Device ServiceInfo to send in the NEXT ietration, OR,
* 'false' if there is no Device ServiceInfo to send in the NEXT iteration.
* @param mtu - [IN] MTU value to be used as the upper bound for the ServiceInfo
* length.
* @return integer value FDO_SI_CONTENT_ERROR (0), FDO_SI_INTERNAL_ERROR (1),
* FDO_SI_SUCCESS (2).
*/
int fdo_sim_download(fdo_sdk_si_type type, char *module_message,
uint8_t *module_val, size_t *module_val_sz,
uint16_t *num_module_messages, bool *has_more,
bool *is_more, size_t mtu);

int fdo_sim_command(fdo_sdk_si_type type, char *module_message,
uint8_t *module_val, size_t *module_val_sz,
uint16_t *num_module_messages, bool *has_more,
bool *is_more, size_t mtu);

// Prototype definitions for functions that are implemented in the module
int fdo_si_start(fdor_t **fdor, fdow_t **fdow);
int fdo_si_failure(fdor_t **fdor, fdow_t **fdow);
int fdo_si_has_more_dsi(bool *has_more, bool hasmore);
int fdo_si_is_more_dsi(bool *is_more);
int fdo_si_get_dsi_count(uint16_t *num_module_messages);
int fdo_si_get_dsi(fdow_t **fdow, size_t mtu, char *module_message,
uint8_t *module_val, size_t *module_val_sz, size_t bin_len,
uint8_t *bin_data, size_t temp_module_val_sz, bool *hasmore,
fdoSimModMsg *write_type, char *filename);

int fdo_si_set_osi_download(char *module_message, uint8_t *module_val,
size_t *module_val_sz, int *strcmp_filedesc,
int *strcmp_length, int *strcmp_sha_384,
int *strcmp_write);

int fdo_si_set_osi_command(char *module_message, uint8_t *module_val,
size_t *module_val_sz, int *strcmp_cmd,
int *strcmp_args, int *strcmp_may_fail,
int *strcmp_return_stdout, int *strcmp_return_stderr,
int *strcmp_sig, int *strcmp_exec);

int fdo_si_set_osi_strcmp(size_t bin_len, uint8_t *bin_data);
int fdo_si_set_osi_sha_384(size_t bin_len, uint8_t *bin_data);
int fdo_si_set_osi_length(size_t bin_len);
int fdo_si_set_osi_write(size_t bin_len, uint8_t *bin_data);
int fdo_si_set_osi_may_fail(void);
int fdo_si_set_osi_return_stdout(void);
int fdo_si_set_osi_return_stderr(void);
int fdo_si_set_osi_cmd(size_t bin_len, uint8_t *bin_data);
int fdo_si_set_osi_sig(size_t sigValue);
int fdo_si_set_osi_args(int exec_array_index, size_t *exec_instructions_sz);
int fdo_si_set_osi_exec(uint8_t **exec_instr);
int fdo_si_set_osi_status_cb(size_t *status_cb_array_length);
int fdo_si_set_osi_fetch(size_t bin_len);
int fdo_end(fdor_t **fdor, fdow_t **fdow, int result, uint8_t *bin_data,
uint8_t **exec_instr, size_t total_exec_array_length, bool *hasmore,
fdoSimModMsg *write_type);
#endif /* __FDO_SYS_H__ */
Loading

0 comments on commit 2e570dd

Please sign in to comment.