diff options
-rw-r--r-- | GNUmakefile | 2 | ||||
-rw-r--r-- | hal.h | 15 | ||||
-rw-r--r-- | tests/test-mkmif.c | 149 | ||||
-rw-r--r-- | verilog_constants.h | 15 |
4 files changed, 180 insertions, 1 deletions
diff --git a/GNUmakefile b/GNUmakefile index e7b272d..3dcc9da 100644 --- a/GNUmakefile +++ b/GNUmakefile @@ -38,7 +38,7 @@ INC = hal.h hal_internal.h LIB = libhal.a OBJ = errorstrings.o rsa.o ecdsa.o asn1.o ${CORE_OBJ} ${IO_OBJ} ${RPC_OBJ} ${KS_OBJ} -CORE_OBJ := core.o csprng.o hash.o aes_keywrap.o pbkdf2.o modexp.o +CORE_OBJ := core.o csprng.o hash.o aes_keywrap.o pbkdf2.o modexp.o mkmif.o USAGE = "usage: make [IO_BUS=eim|i2c|fmc] [RPC_CLIENT=local|remote|mixed] [RPC_SERVER=yes] [KS=mmap|volatile|flash]" @@ -93,6 +93,9 @@ #define MODEXPS6_NAME "modexps6" #define MODEXPS6_VERSION "0.10" +#define MKMIF_NAME "mkmif " +#define MKMIF_VERSION "0.10" + /* * C API error codes. Defined in this form so we can keep the tokens * and error strings together. See errorstrings.c. @@ -345,6 +348,18 @@ extern hal_error_t hal_modexp(const hal_core_t *core, const uint8_t * const mod, const size_t mod_len, /* Modulus */ uint8_t * result, const size_t result_len); +/* + * Master Key Memory Interface + */ + +extern hal_error_t hal_mkmif_init(const hal_core_t *core); +extern hal_error_t hal_mkmif_set_clockspeed(const hal_core_t *core, const uint32_t divisor); +extern hal_error_t hal_mkmif_get_clockspeed(const hal_core_t *core, uint32_t *divisor); +extern hal_error_t hal_mkmif_write(const hal_core_t *core, uint32_t addr, const uint8_t *buf, size_t len); +extern hal_error_t hal_mkmif_write_word(const hal_core_t *core, uint32_t addr, const uint32_t data); +extern hal_error_t hal_mkmif_read(const hal_core_t *core, uint32_t addr, uint8_t *buf, size_t len); +extern hal_error_t hal_mkmif_read_word(const hal_core_t *core, uint32_t addr, uint32_t *data); + /* * Key types and curves, used in various places. diff --git a/tests/test-mkmif.c b/tests/test-mkmif.c new file mode 100644 index 0000000..0729628 --- /dev/null +++ b/tests/test-mkmif.c @@ -0,0 +1,149 @@ +/* + * Test Joachim's MKMIF core. + */ + +#include <stdio.h> +#include <stdlib.h> +#include <stdint.h> +#include <string.h> +#include <assert.h> + +#include <sys/time.h> + +#include <hal.h> + +#define SCLK_DIV 0x00000020 + +typedef union { + uint8_t byte[4]; + uint32_t word; +} byteword_t; + +static hal_error_t sclk_test(const hal_core_t *core, const uint32_t divisor) +{ + uint32_t readback; + hal_error_t err; + + printf("Trying to adjust the clockspeed.\n"); + + if ((err = hal_mkmif_set_clockspeed(core, divisor)) != HAL_OK) { + printf("hal_mkmif_set_clockspeed: %s\n", hal_error_string(err)); + return err; + } + if ((err = hal_mkmif_get_clockspeed(core, &readback)) != HAL_OK) { + printf("hal_mkmif_get_clockspeed: %s\n", hal_error_string(err)); + return err; + } + if (readback != divisor) { + printf("expected %x, got %x\n", (unsigned int)divisor, (unsigned int)readback); + return HAL_ERROR_IO_UNEXPECTED; + } + return HAL_OK; +} + +static hal_error_t init_test(const hal_core_t *core) +{ + hal_error_t err; + + printf("Trying to init to the memory in continuous mode.\n"); + + if ((err = hal_mkmif_init(core)) != HAL_OK) { + printf("hal_mkmif_init: %s\n", hal_error_string(err)); + return err; + } + + return HAL_OK; +} + +static hal_error_t write_test(const hal_core_t *core) +{ + uint32_t write_data; + uint32_t write_address; + int i; + hal_error_t err; + + for (write_data = 0x01020304, write_address = 0, i = 0; + i < 0x10; + write_data += 0x01010101, write_address += 4, ++i) { + + printf("Trying to write 0x%08x to memory address 0x%08x.\n", + (unsigned int)write_data, (unsigned int)write_address); + + if ((err = hal_mkmif_write_word(core, write_address, write_data)) != HAL_OK) { + printf("hal_mkmif_write: %s\n", hal_error_string(err)); + return err; + } + } + + return HAL_OK; +} + +static hal_error_t read_test(const hal_core_t *core) +{ + uint32_t read_data; + uint32_t read_address; + int i; + hal_error_t err; + + for (read_address = 0, i = 0; + i < 0x10; + read_address += 4, ++i) { + + printf("Trying to read from memory address 0x%08x.\n", (unsigned int)read_address); + + if ((err = hal_mkmif_read_word(core, read_address, &read_data)) != HAL_OK) { + printf("hal_mkmif_read: %s\n", hal_error_string(err)); + return err; + } + printf("Data read: 0x%08x\n", (unsigned int)read_data); + } + + return HAL_OK; +} + +static hal_error_t write_read_test(const hal_core_t *core) +{ + uint32_t data; + uint32_t readback; + hal_error_t err; + + printf("Trying to write 0xdeadbeef to the memory and then read back.\n"); + + data = 0xdeadbeef; + + if ((err = hal_mkmif_write_word(core, 0x00000000, data)) != HAL_OK) { + printf("write error: %s\n", hal_error_string(err)); + return err; + } + + if ((err = hal_mkmif_read_word(core, 0x00000000, &readback)) != HAL_OK) { + printf("read error: %s\n", hal_error_string(err)); + return err; + } + + if (readback != data) { + printf("read %04x, expected %04x\n", (unsigned int)readback, (unsigned int)data); + return HAL_ERROR_IO_UNEXPECTED; + } + + return HAL_OK; +} + +int main(void) +{ + const hal_core_t *core = hal_core_find(MKMIF_NAME, NULL); + + if (core == NULL) { + printf("MKMIF core not present, not testing.\n"); + return HAL_ERROR_CORE_NOT_FOUND; + } + + hal_io_set_debug(1); + + return + sclk_test(core, SCLK_DIV) || + init_test(core) || + write_read_test(core) || + write_test(core) || + read_test(core); +} diff --git a/verilog_constants.h b/verilog_constants.h index dfd102a..43b7a0c 100644 --- a/verilog_constants.h +++ b/verilog_constants.h @@ -219,6 +219,21 @@ #define MODEXPS6_ADDR_EXPONENT (MODEXPS6_ADDR_OPERANDS + 2 * MODEXPS6_OPERAND_WORDS) #define MODEXPS6_ADDR_RESULT (MODEXPS6_ADDR_OPERANDS + 3 * MODEXPS6_OPERAND_WORDS) +/* + * Utility cores. + */ + +/* + * Master Key Memory Interface core. + */ +#define MKMIF_ADDR_CTRL ADDR_CTRL +#define MKMIF_CTRL_CMD_READ (0x01) +#define MKMIF_CTRL_CMD_WRITE (0x02) +#define MKMIF_CTRL_CMD_INIT (0x04) +#define MKMIF_ADDR_SCLK_DIV (0x0a) +#define MKMIF_ADDR_EMEM_ADDR (0x10) +#define MKMIF_ADDR_EMEM_DATA (0x20) + #endif /* _VERILOG_CONSTANTS_H_ */ /* |