Skip to content

Commit

Permalink
[Config] Add in custom CRC function pointer
Browse files Browse the repository at this point in the history
Requested such that a user can implement the crc stream function via configurable function pointer
parameter

Documentation update required explaining the config
  • Loading branch information
sahil-kale committed Nov 27, 2023
1 parent ac3fb3d commit 9cba6c5
Show file tree
Hide file tree
Showing 6 changed files with 72 additions and 6 deletions.
9 changes: 9 additions & 0 deletions inc/voyager.h
Original file line number Diff line number Diff line change
Expand Up @@ -72,9 +72,18 @@ typedef union {
voyager_bootloader_app_size_t app_size;
} voyager_bootloader_nvm_data_t;

/**
* @brief voyager_custom_crc_stream_F Function pointer signature for a custom CRC stream function
* @param byte The byte to process
* @param crc pointer to the current CRC value that is expected to be modified
*/
typedef void (*voyager_custom_crc_stream_F)(const uint8_t byte, voyager_bootloader_app_crc_t *const crc);

typedef struct {
bool jump_to_app_after_dfu_recv_complete; // Controls whether the system jumps to application or to IDLE after completion of
// DFU
voyager_custom_crc_stream_F
custom_crc_stream; // Custom function pointer signature to allow an override of the base CRC method
} voyager_bootloader_config_t;

/** Primary Bootloader Functions **/
Expand Down
6 changes: 5 additions & 1 deletion src/voyager.c
Original file line number Diff line number Diff line change
Expand Up @@ -658,7 +658,11 @@ voyager_bootloader_app_crc_t voyager_private_calculate_crc(const void *buffer, c
}

void voyager_private_calculate_crc_stream(const uint8_t byte, voyager_bootloader_app_crc_t *const crc) {
*crc = (*crc << 8) ^ crc32_table[(((*crc) >> 24) ^ byte) & 255];
if (voyager_data.config->custom_crc_stream != NULL) {
voyager_data.config->custom_crc_stream(byte, crc);
} else {
*crc = (*crc << 8) ^ crc32_table[(((*crc) >> 24) ^ byte) & 255];
}
}

#ifdef VOYAGER_UNIT_TEST
Expand Down
1 change: 1 addition & 0 deletions test/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,5 +4,6 @@
IMPORT_TEST_GROUP(dummy_test);
IMPORT_TEST_GROUP(test_bootloader_state_machine);
IMPORT_TEST_GROUP(test_dfu);
IMPORT_TEST_GROUP(test_bootloader_api);

int main(int ac, char **av) { return CommandLineTestRunner::RunAllTests(ac, av); }
56 changes: 56 additions & 0 deletions test/test_api.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
#include <CppUTestExt/MockSupport.h>

#include "CppUTest/TestHarness.h"
#include "test_defaults.hpp"

extern "C" {
#include "mock_dfu.h"
#include "mock_nvm.h"
#include "voyager.h"
#include "voyager_private.h"
}

extern const voyager_bootloader_config_t default_test_config;

// create a test group
TEST_GROUP(test_bootloader_api){

void setup(){mock().clear();
mock_nvm_data_t *nvm_data = mock_nvm_get_data();

uint8_t *mock_app_start_address = mock_dfu_get_flash();
nvm_data->app_start_address = (uintptr_t)mock_app_start_address;
nvm_data->app_end_address = nvm_data->app_start_address + FAKE_FLASH_SIZE * 2;
nvm_data->app_size = FAKE_FLASH_SIZE;
mock_dfu_init();
}

void teardown() { mock().clear(); }
}
;

// Test that a nullptr'ed config returns an error
TEST(test_bootloader_api, test_init_nullptr_is_rejected) {
CHECK_EQUAL(VOYAGER_ERROR_INVALID_ARGUMENT, voyager_bootloader_init(NULL));
}

// The below is not implemented as a mock due to the function pointer implementation
static const voyager_bootloader_app_crc_t test_crc_constant = 0xDEADBEEF;

void custom_crc_implementation(const uint8_t byte, voyager_bootloader_app_crc_t *const crc) {
(void)byte;
*crc = test_crc_constant;
}

// Test that a custom CRC implementation can be overriden with the function pointer
TEST(test_bootloader_api, test_custom_crc_implementation) {
// Make a struct with a custom CRC function pointer
voyager_bootloader_config_t config_custom_crc{.jump_to_app_after_dfu_recv_complete = true,
.custom_crc_stream = custom_crc_implementation};

voyager_bootloader_init(&config_custom_crc);

voyager_bootloader_app_crc_t test_crc;
voyager_private_calculate_crc_stream(1, &test_crc);
CHECK_EQUAL(test_crc_constant, test_crc);
}
5 changes: 0 additions & 5 deletions test/test_bootloader.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -108,8 +108,3 @@ TEST(test_bootloader_state_machine, test_app_good_crc_verify) {
// Ensure that the voyager data request is set to VOYAGER_REQUEST_KEEP_IDLE
CHECK_EQUAL(VOYAGER_REQUEST_KEEP_IDLE, voyager_private_get_data()->request);
}

// Test that a nullptr'ed config returns an error
TEST(test_bootloader_state_machine, test_init_nullptr_is_rejected) {
CHECK_EQUAL(VOYAGER_ERROR_INVALID_ARGUMENT, voyager_bootloader_init(NULL));
}
1 change: 1 addition & 0 deletions test/test_defaults.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,5 @@

const voyager_bootloader_config_t default_test_config{
.jump_to_app_after_dfu_recv_complete = true,
.custom_crc_stream = NULL,
};

0 comments on commit 9cba6c5

Please sign in to comment.