diff --git a/.gitmodules b/.gitmodules
index b28b159..8fde71a 100644
--- a/.gitmodules
+++ b/.gitmodules
@@ -4,3 +4,6 @@
[submodule "tinycbor"]
path = tinycbor
url = https://github.com/intel/tinycbor.git
+[submodule "mlkem"]
+ path = mlkem
+ url = https://github.com/pq-code-package/mlkem-native/
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 0adf96b..42e9437 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -26,7 +26,7 @@ else()
include(pico_sdk_import.cmake)
endif()
- project(picokey C CXX ASM)
+ project(pico_rescue C CXX ASM)
set(CMAKE_C_STANDARD 11)
set(CMAKE_CXX_STANDARD 17)
@@ -38,7 +38,7 @@ else()
add_definitions(-D__FOR_CI)
endif()
- add_executable(picokey)
+ add_executable(pico_rescue)
endif()
set(USB_ITF_CCID 1)
@@ -53,48 +53,48 @@ set(SOURCES ${SOURCES}
${CMAKE_CURRENT_LIST_DIR}/src/version.c
)
-SET_VERSION(ver_major ver_minor "${CMAKE_CURRENT_LIST_DIR}/src/pico_keys_version.h" 2)
+SET_VERSION(ver_major ver_minor "${CMAKE_CURRENT_LIST_DIR}/src/pico_keys_version.h" 3)
if(ESP_PLATFORM)
- project(picokey)
+ project(pico_rescue)
endif()
if(NOT ESP_PLATFORM)
- target_sources(picokey PUBLIC ${SOURCES})
- target_include_directories(picokey PUBLIC ${INCLUDES})
+ target_sources(pico_rescue PUBLIC ${SOURCES})
+ target_include_directories(pico_rescue PUBLIC ${INCLUDES})
- target_compile_options(picokey PUBLIC
+ target_compile_options(pico_rescue PUBLIC
-Wall
)
if(NOT MSVC)
- target_compile_options(picokey PUBLIC
+ target_compile_options(pico_rescue PUBLIC
-Werror
)
endif()
if(ENABLE_EMULATION)
if(NOT MSVC)
- target_compile_options(picokey PUBLIC
+ target_compile_options(pico_rescue PUBLIC
-fdata-sections
-ffunction-sections
)
endif()
if(APPLE)
- target_link_options(picokey PUBLIC
+ target_link_options(pico_rescue PUBLIC
-Wl,-dead_strip
)
elseif(MSVC)
- target_compile_options(picokey PUBLIC
+ target_compile_options(pico_rescue PUBLIC
-WX
)
- target_link_libraries(picokey PUBLIC wsock32 ws2_32 Bcrypt)
+ target_link_libraries(pico_rescue PUBLIC wsock32 ws2_32 Bcrypt)
else()
- target_link_options(picokey PUBLIC
+ target_link_options(pico_rescue PUBLIC
-Wl,--gc-sections
)
endif(APPLE)
- target_link_libraries(picokey PRIVATE pthread m)
+ target_link_libraries(pico_rescue PRIVATE pthread m)
else()
pico_add_extra_outputs(${CMAKE_PROJECT_NAME})
endif()
diff --git a/LICENSE b/LICENSE
index bae94e1..714397f 100644
--- a/LICENSE
+++ b/LICENSE
@@ -1,3 +1,23 @@
+Unless stated otherwise at the top of a file, all the files of this
+project are licensed under the GNU Affero General Public License v3
+(AGPLv3). The full text of this license is reproduced at the bottom of
+this document.
+The copyright holders are indicated at the top of each file.
+
+The project is using the following libraries, sdk or portions of code:
+- mdebtls, licensed under Apache-2.0 and GPL-2.0-or-later licenses,
+ https://github.com/Mbed-TLS/mbedtls
+- tinyUSB, licensed under the MIT License,
+ https://github.com/hathach/tinyusb
+- tinycbor, licensed under the MIT license,
+ https://github.com/intel/tinycbor
+- mlkem-native, the Apache-2.0 license OR the ISC license OR the MIT
+ license, https://github.com/pq-code-package/mlkem-native
+- USB CCID from Raspberry Pi (Trading) Ltd, licensed under the BSD
+ license,
+
+________________________________________________________________________
+
GNU AFFERO GENERAL PUBLIC LICENSE
Version 3, 19 November 2007
@@ -658,4 +678,4 @@ specific requirements.
You should also get your employer (if you work as a programmer) or school,
if any, to sign a "copyright disclaimer" for the program, if necessary.
For more information on this, and how to apply and follow the GNU AGPL, see
-.
\ No newline at end of file
+.
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..e2bf33f
--- /dev/null
+++ b/README.md
@@ -0,0 +1,4 @@
+# Pico Keys SDK
+This is a fork of the community edition of the project located at https://github.com/polhenarejos/pico-keys-sdk
+
+For licensing information and credits, see the LICENSE file
diff --git a/config/esp32/components/mlkem1024/CMakeLists.txt b/config/esp32/components/mlkem1024/CMakeLists.txt
new file mode 100644
index 0000000..22033d4
--- /dev/null
+++ b/config/esp32/components/mlkem1024/CMakeLists.txt
@@ -0,0 +1,23 @@
+set(MLKEM_DIR ${CMAKE_CURRENT_LIST_DIR}/../../../../mlkem/mlkem)
+
+file(GLOB_RECURSE MLKEM_SOURCES
+ ${MLKEM_DIR}/src/*.c
+)
+list(FILTER MLKEM_SOURCES EXCLUDE REGEX "/native/")
+
+idf_component_register(
+ SRCS ${MLKEM_SOURCES}
+ INCLUDE_DIRS ${MLKEM_DIR}
+)
+
+target_compile_definitions(${COMPONENT_LIB} PRIVATE
+ MLK_CONFIG_PARAMETER_SET=1024
+ MLK_CONFIG_MULTILEVEL_NO_SHARED
+ MLK_CONFIG_NAMESPACE_PREFIX=mlkem
+)
+
+target_compile_options(${COMPONENT_LIB} PRIVATE
+ -O2
+ -fno-builtin
+ -fno-strict-aliasing
+)
diff --git a/config/esp32/components/mlkem512/CMakeLists.txt b/config/esp32/components/mlkem512/CMakeLists.txt
new file mode 100644
index 0000000..65357c5
--- /dev/null
+++ b/config/esp32/components/mlkem512/CMakeLists.txt
@@ -0,0 +1,23 @@
+set(MLKEM_DIR ${CMAKE_CURRENT_LIST_DIR}/../../../../mlkem/mlkem)
+
+file(GLOB_RECURSE MLKEM_SOURCES
+ ${MLKEM_DIR}/src/*.c
+)
+list(FILTER MLKEM_SOURCES EXCLUDE REGEX "/native/")
+
+idf_component_register(
+ SRCS ${MLKEM_SOURCES}
+ INCLUDE_DIRS ${MLKEM_DIR}
+)
+
+target_compile_definitions(${COMPONENT_LIB} PRIVATE
+ MLK_CONFIG_PARAMETER_SET=512
+ MLK_CONFIG_MULTILEVEL_WITH_SHARED
+ MLK_CONFIG_NAMESPACE_PREFIX=mlkem
+)
+
+target_compile_options(${COMPONENT_LIB} PRIVATE
+ -O2
+ -fno-builtin
+ -fno-strict-aliasing
+)
diff --git a/config/esp32/components/mlkem768/CMakeLists.txt b/config/esp32/components/mlkem768/CMakeLists.txt
new file mode 100644
index 0000000..0085303
--- /dev/null
+++ b/config/esp32/components/mlkem768/CMakeLists.txt
@@ -0,0 +1,23 @@
+set(MLKEM_DIR ${CMAKE_CURRENT_LIST_DIR}/../../../../mlkem/mlkem)
+
+file(GLOB_RECURSE MLKEM_SOURCES
+ ${MLKEM_DIR}/src/*.c
+)
+list(FILTER MLKEM_SOURCES EXCLUDE REGEX "/native/")
+
+idf_component_register(
+ SRCS ${MLKEM_SOURCES}
+ INCLUDE_DIRS ${MLKEM_DIR}
+)
+
+target_compile_definitions(${COMPONENT_LIB} PRIVATE
+ MLK_CONFIG_PARAMETER_SET=768
+ MLK_CONFIG_MULTILEVEL_NO_SHARED
+ MLK_CONFIG_NAMESPACE_PREFIX=mlkem
+)
+
+target_compile_options(${COMPONENT_LIB} PRIVATE
+ -O2
+ -fno-builtin
+ -fno-strict-aliasing
+)
diff --git a/config/esp32/components/pico-keys-sdk/CMakeLists.txt b/config/esp32/components/pico-keys-sdk/CMakeLists.txt
new file mode 100755
index 0000000..653fd87
--- /dev/null
+++ b/config/esp32/components/pico-keys-sdk/CMakeLists.txt
@@ -0,0 +1,7 @@
+set(PICO_KEYS_SDK_DIR ${CMAKE_CURRENT_LIST_DIR}/../../../..)
+idf_component_register(
+ SRCS ${PICO_KEYS_SOURCES}
+ INCLUDE_DIRS ${PICO_KEYS_SDK_DIR}/src ${PICO_KEYS_SDK_DIR}/src/fs ${PICO_KEYS_SDK_DIR}/src/rng ${PICO_KEYS_SDK_DIR}/src/usb ${PICO_KEYS_SDK_DIR}/src/led ${PICO_KEYS_SDK_DIR}/tinycbor/src ${PICO_KEYS_SDK_DIR}/mlkem/mlkem ${PICO_KEYS_SDK_DIR}/config/mlkem
+ REQUIRES bootloader_support esp_partition esp_tinyusb efuse mbedtls mlkem512 mlkem768 mlkem1024 tinycbor
+)
+idf_component_set_property(${COMPONENT_NAME} WHOLE_ARCHIVE ON)
diff --git a/src/idf_component.yml b/config/esp32/components/pico-keys-sdk/idf_component.yml
similarity index 100%
rename from src/idf_component.yml
rename to config/esp32/components/pico-keys-sdk/idf_component.yml
diff --git a/config/esp32/components/tinycbor/CMakeLists.txt b/config/esp32/components/tinycbor/CMakeLists.txt
new file mode 100755
index 0000000..76ecf22
--- /dev/null
+++ b/config/esp32/components/tinycbor/CMakeLists.txt
@@ -0,0 +1,6 @@
+set(PICO_KEYS_SDK_DIR ${CMAKE_CURRENT_LIST_DIR}/../../../..)
+idf_component_register(
+ SRCS ${CBOR_SOURCES}
+ INCLUDE_DIRS ${PICO_KEYS_SDK_DIR}/tinycbor/src
+)
+idf_component_set_property(${COMPONENT_NAME} WHOLE_ARCHIVE ON)
diff --git a/config/mbedtls_config.h b/config/mbedtls_config.h
index 0311975..6da7bd8 100644
--- a/config/mbedtls_config.h
+++ b/config/mbedtls_config.h
@@ -330,7 +330,7 @@
//#define MBEDTLS_RSA_ALT
//#define MBEDTLS_SHA1_ALT
#ifdef PICO_RP2350
-#define MBEDTLS_SHA256_ALT
+//#define MBEDTLS_SHA256_ALT
#endif
//#define MBEDTLS_SHA512_ALT
diff --git a/config/mlkem/mlkem_native_all.h b/config/mlkem/mlkem_native_all.h
new file mode 100644
index 0000000..5fb5ba5
--- /dev/null
+++ b/config/mlkem/mlkem_native_all.h
@@ -0,0 +1,27 @@
+/*
+ * Copyright (c) The mlkem-native project authors
+ * SPDX-License-Identifier: Apache-2.0 OR ISC OR MIT
+ */
+
+#if !defined(MLK_ALL_H)
+#define MLK_ALL_H
+
+/* API for MLKEM-512 */
+#define MLK_CONFIG_PARAMETER_SET 512
+#include "mlkem_native.h"
+#undef MLK_CONFIG_PARAMETER_SET
+#undef MLK_H
+
+/* API for MLKEM-768 */
+#define MLK_CONFIG_PARAMETER_SET 768
+#include "mlkem_native.h"
+#undef MLK_CONFIG_PARAMETER_SET
+#undef MLK_H
+
+/* API for MLKEM-1024 */
+#define MLK_CONFIG_PARAMETER_SET 1024
+#include "mlkem_native.h"
+#undef MLK_CONFIG_PARAMETER_SET
+#undef MLK_H
+
+#endif /* !MLK_ALL_H */
diff --git a/config/mlkem/mlkem_native_config.h b/config/mlkem/mlkem_native_config.h
new file mode 100644
index 0000000..b75c37a
--- /dev/null
+++ b/config/mlkem/mlkem_native_config.h
@@ -0,0 +1,13 @@
+#pragma once
+
+/* Disable all native/asm backends */
+#define MLK_NO_NATIVE_BACKENDS 1
+
+/* No CBMC */
+#undef CBMC
+
+/* Platform characteristics */
+#define MLK_LITTLE_ENDIAN 1
+
+/* Memory model */
+#define MLK_NO_MALLOC 1
diff --git a/config/rp2350/alt/sha256_alt.c b/config/rp2350/alt/sha256_alt.c
index 17f5517..82bcd4d 100644
--- a/config/rp2350/alt/sha256_alt.c
+++ b/config/rp2350/alt/sha256_alt.c
@@ -286,3 +286,9 @@ int mbedtls_sha256_finish(mbedtls_sha256_context *ctx, unsigned char *output) {
}
return 0;
}
+
+void mbedtls_sha256_clone(mbedtls_sha256_context *dst,
+ const mbedtls_sha256_context *src)
+{
+ *dst = *src;
+}
diff --git a/config/rp2350/alt/sha256_alt.h b/config/rp2350/alt/sha256_alt.h
index 0e1ada4..d480ce6 100644
--- a/config/rp2350/alt/sha256_alt.h
+++ b/config/rp2350/alt/sha256_alt.h
@@ -18,7 +18,6 @@
#ifndef _SHA256_ALT_H_
#define _SHA256_ALT_H_
-#include "pico_keys.h"
#include "pico/sha256.h"
typedef struct mbedtls_sha256_context {
diff --git a/config/rp2350/pt.json b/config/rp2350/pt.json
index a6cf59f..48acfc5 100644
--- a/config/rp2350/pt.json
+++ b/config/rp2350/pt.json
@@ -10,7 +10,7 @@
},
"partitions": [
{
- "name": "Pico Keys Firmware",
+ "name": "PicoKeys Firmware",
"id": 0,
"start": 0,
"size": "1024K",
@@ -22,10 +22,10 @@
}
},
{
- "name": "Pico Keys Data",
+ "name": "PicoKeys Data",
"id": 1,
- "start": "1024K",
- "size": "3072K",
+ "start": "1032K",
+ "size": "3064K",
"families": ["data"],
"permissions": {
"secure": "rw",
@@ -35,6 +35,21 @@
"link": ["owner", 0],
"ignored_during_arm_boot": true,
"ignored_during_riscv_boot": true
+ },
+ {
+ "name": "PicoKeys Binding",
+ "id": 2,
+ "start": "1024K",
+ "size": "8K",
+ "families": ["data"],
+ "permissions": {
+ "secure": "r",
+ "nonsecure": "",
+ "bootloader": "w"
+ },
+ "link": ["owner", 0],
+ "ignored_during_arm_boot": true,
+ "ignored_during_riscv_boot": true
}
]
}
diff --git a/mlkem b/mlkem
new file mode 160000
index 0000000..1453da5
--- /dev/null
+++ b/mlkem
@@ -0,0 +1 @@
+Subproject commit 1453da5cd11ea6be7ae83d619d1a72b21e48ec7d
diff --git a/pico_keys_sdk_import.cmake b/pico_keys_sdk_import.cmake
index 346febf..d1df2e0 100644
--- a/pico_keys_sdk_import.cmake
+++ b/pico_keys_sdk_import.cmake
@@ -64,12 +64,12 @@ if(ESP_PLATFORM)
endif()
if(NOT DEFINED USB_VID)
- set(USB_VID 0xFEFF)
+ set(USB_VID 0x1D50)
endif()
add_definitions(-DUSB_VID=${USB_VID})
if(NOT DEFINED USB_PID)
- set(USB_PID 0xFCFD)
+ set(USB_PID 0x619B)
endif()
add_definitions(-DUSB_PID=${USB_PID})
@@ -126,7 +126,7 @@ if(NOT ESP_PLATFORM)
)
if(ENABLE_EDDSA)
- set(MBEDTLS_ORIGIN "https://github.com/polhenarejos/mbedtls.git")
+ set(MBEDTLS_ORIGIN "https://github.com/librekeys/mbedtls.git")
set(MBEDTLS_REF "mbedtls-3.6-eddsa")
execute_process(
@@ -213,6 +213,14 @@ if(NOT ESP_PLATFORM)
endif()
endif(NOT ESP_PLATFORM)
+option(ENABLE_PQC "Enable/disable PQC support" OFF)
+if(ENABLE_PQC)
+ message(STATUS "PQC support:\t\t\t enabled")
+ add_definitions(-DENABLE_PQC)
+else()
+ message(STATUS "PQC support:\t\t\t disabled")
+endif(ENABLE_PQC)
+
set(MBEDTLS_SOURCES
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/aes.c
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/asn1parse.c
@@ -245,9 +253,12 @@ set(MBEDTLS_SOURCES
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/poly1305.c
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/ripemd160.c
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/des.c
+ ${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/x509write.c
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/x509write_crt.c
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/x509_create.c
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/x509write_csr.c
+ ${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/base64.c
+ ${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/pem.c
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/pk.c
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/pk_wrap.c
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/pkwrite.c
@@ -260,6 +271,54 @@ if (ENABLE_EDDSA)
)
endif()
+if(ENABLE_PQC)
+if (NOT ESP_PLATFORM)
+ file(GLOB_RECURSE MLKEM_SOURCES
+ ${CMAKE_CURRENT_LIST_DIR}/mlkem/mlkem/src/*.c
+ )
+ list(FILTER MLKEM_SOURCES EXCLUDE REGEX "/native/")
+
+ add_library(mlkem512 STATIC ${MLKEM_SOURCES})
+ target_include_directories(mlkem512 PRIVATE
+ ${CMAKE_CURRENT_LIST_DIR}/mlkem/mlkem/src
+ ${CMAKE_CURRENT_LIST_DIR}/config/mlkem
+ )
+ target_compile_definitions(mlkem512 PRIVATE
+ MLK_CONFIG_PARAMETER_SET=512
+ MLK_CONFIG_MULTILEVEL_WITH_SHARED
+ MLK_CONFIG_NAMESPACE_PREFIX=mlkem
+ )
+
+ add_library(mlkem768 STATIC ${MLKEM_SOURCES})
+ target_include_directories(mlkem768 PRIVATE
+ ${CMAKE_CURRENT_LIST_DIR}/mlkem/mlkem/src
+ ${CMAKE_CURRENT_LIST_DIR}/config/mlkem
+ )
+ target_compile_definitions(mlkem768 PRIVATE
+ MLK_CONFIG_PARAMETER_SET=768
+ MLK_CONFIG_MULTILEVEL_NO_SHARED
+ MLK_CONFIG_NAMESPACE_PREFIX=mlkem
+ )
+
+ add_library(mlkem1024 STATIC ${MLKEM_SOURCES})
+ target_include_directories(mlkem1024 PRIVATE
+ ${CMAKE_CURRENT_LIST_DIR}/mlkem/mlkem/src
+ ${CMAKE_CURRENT_LIST_DIR}/config/mlkem
+ )
+ target_compile_definitions(mlkem1024 PRIVATE
+ MLK_CONFIG_PARAMETER_SET=1024
+ MLK_CONFIG_MULTILEVEL_NO_SHARED
+ MLK_CONFIG_NAMESPACE_PREFIX=mlkem
+ )
+endif()
+
+ set(INCLUDES ${INCLUDES}
+ ${CMAKE_CURRENT_LIST_DIR}/mlkem/mlkem
+ ${CMAKE_CURRENT_LIST_DIR}/config/mlkem
+ )
+ add_definitions(-DMLK_CONFIG_NAMESPACE_PREFIX=mlkem -DMLK_CONFIG_MULTILEVEL_BUILD=1)
+endif()
+
set(PICO_KEYS_SOURCES ${PICO_KEYS_SOURCES}
${CMAKE_CURRENT_LIST_DIR}/src/main.c
${CMAKE_CURRENT_LIST_DIR}/src/usb/usb.c
@@ -318,6 +377,9 @@ if(USB_ITF_HID)
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/pk_wrap.c
${CMAKE_CURRENT_LIST_DIR}/mbedtls/library/pkwrite.c
)
+
+endif()
+
set(CBOR_SOURCES
${CMAKE_CURRENT_LIST_DIR}/tinycbor/src/cborencoder.c
${CMAKE_CURRENT_LIST_DIR}/tinycbor/src/cborparser.c
@@ -327,19 +389,41 @@ if(USB_ITF_HID)
set(INCLUDES ${INCLUDES}
${CMAKE_CURRENT_LIST_DIR}/tinycbor/src
)
+set(LIBRARIES
+ mbedtls
+)
+
+if (NOT ESP_PLATFORM)
+ add_library(mbedtls STATIC ${MBEDTLS_SOURCES})
+ target_include_directories(mbedtls PUBLIC ${CMAKE_CURRENT_LIST_DIR}/mbedtls/include)
+ if(USB_ITF_HID)
+ add_library(tinycbor STATIC ${CBOR_SOURCES})
+ target_include_directories(tinycbor PUBLIC ${CMAKE_CURRENT_LIST_DIR}/tinycbor/src)
+ set(LIBRARIES ${LIBRARIES} tinycbor)
+ endif()
endif()
-set(LIBRARIES
- pico_stdlib
- pico_multicore
- pico_rand
- pico_aon_timer
- hardware_flash
- pico_unique_id
- tinyusb_device
- tinyusb_board
- hardware_pio
-)
+if (PICO_PLATFORM)
+ list(APPEND LIBRARIES
+ pico_stdlib
+ pico_multicore
+ pico_rand
+ pico_aon_timer
+ hardware_flash
+ pico_unique_id
+ tinyusb_device
+ tinyusb_board
+ hardware_pio
+ )
+endif()
+
+if (ENABLE_PQC)
+ list(APPEND LIBRARIES
+ mlkem512
+ mlkem768
+ mlkem1024
+ )
+endif()
set(IS_CYW43 0)
if (PICO_PLATFORM)
@@ -403,10 +487,7 @@ else()
${CMAKE_CURRENT_LIST_DIR}/src/usb/usb_descriptors.c
)
endif()
-set(EXTERNAL_SOURCES ${CBOR_SOURCES})
-if(NOT ESP_PLATFORM)
- set(EXTERNAL_SOURCES ${EXTERNAL_SOURCES} ${MBEDTLS_SOURCES})
-endif()
+
if(MSVC)
set(
CMAKE_C_FLAGS
@@ -423,11 +504,6 @@ if(MSVC)
_WIN32_WINNT_WIN10_RS5=0
_STRALIGN_USE_SECURE_CRT=0
NTDDI_WIN11_DT=0)
- set_source_files_properties(
- ${EXTERNAL_SOURCES}
- PROPERTIES
- COMPILE_FLAGS " -W3 -wd4242 -wd4065"
- )
endif()
if(PICO_PLATFORM)
@@ -450,13 +526,17 @@ if(PICO_RP2350)
set(INCLUDES ${INCLUDES}
${CMAKE_CURRENT_LIST_DIR}/config/rp2350/alt
)
+ target_include_directories(mbedtls PRIVATE
+ ${CMAKE_CURRENT_LIST_DIR}/config/rp2350/alt
+ )
+ target_link_libraries(mbedtls PRIVATE pico_sha256)
set(PICO_KEYS_SOURCES ${PICO_KEYS_SOURCES}
${CMAKE_CURRENT_LIST_DIR}/config/rp2350/alt/sha256_alt.c
)
+ add_definitions(-DMBEDTLS_SHA256_ALT=1)
set(LIBRARIES ${LIBRARIES} pico_sha256)
endif()
set(INTERNAL_SOURCES ${PICO_KEYS_SOURCES})
-set(PICO_KEYS_SOURCES ${PICO_KEYS_SOURCES} ${EXTERNAL_SOURCES})
if(NOT TARGET pico_keys_sdk)
if(PICO_PLATFORM)
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
deleted file mode 100755
index 4ccd9f1..0000000
--- a/src/CMakeLists.txt
+++ /dev/null
@@ -1,6 +0,0 @@
-idf_component_register(
- SRCS ${PICO_KEYS_SOURCES}
- INCLUDE_DIRS . fs rng usb led ../tinycbor/src
- REQUIRES bootloader_support esp_partition esp_tinyusb efuse mbedtls
-)
-idf_component_set_property(${COMPONENT_NAME} WHOLE_ARCHIVE ON)
diff --git a/src/apdu.c b/src/apdu.c
index 3eeffd8..8ac596d 100644
--- a/src/apdu.c
+++ b/src/apdu.c
@@ -30,7 +30,7 @@ uint8_t *rdata_gr = NULL;
uint16_t rdata_bk = 0x0;
extern uint32_t timeout;
bool is_chaining = false;
-uint8_t chain_buf[4096];
+uint8_t chain_buf[2038];
uint8_t *chain_ptr = NULL;
int process_apdu() {
diff --git a/src/crypto_utils.c b/src/crypto_utils.c
index 7adba39..84a3213 100644
--- a/src/crypto_utils.c
+++ b/src/crypto_utils.c
@@ -278,3 +278,16 @@ mbedtls_ecp_group_id ec_get_curve_from_prime(const uint8_t *prime, size_t prime_
}
return MBEDTLS_ECP_DP_NONE;
}
+
+#define POLY 0xedb88320
+
+uint32_t crc32c(const uint8_t *buf, size_t len) {
+ uint32_t crc = 0xffffffff;
+ while (len--) {
+ crc ^= *buf++;
+ for (int k = 0; k < 8; k++) {
+ crc = (crc >> 1) ^ (POLY & (0 - (crc & 1)));
+ }
+ }
+ return ~crc;
+}
diff --git a/src/crypto_utils.h b/src/crypto_utils.h
index 83631fb..c2952b9 100644
--- a/src/crypto_utils.h
+++ b/src/crypto_utils.h
@@ -56,5 +56,6 @@ extern int aes_decrypt(const uint8_t *key, const uint8_t *iv, uint16_t key_size,
extern int aes_encrypt_cfb_256(const uint8_t *key, const uint8_t *iv, uint8_t *data, uint16_t len);
extern int aes_decrypt_cfb_256(const uint8_t *key, const uint8_t *iv, uint8_t *data, uint16_t len);
extern mbedtls_ecp_group_id ec_get_curve_from_prime(const uint8_t *prime, size_t prime_len);
+extern uint32_t crc32c(const uint8_t *buf, size_t len);
#endif
diff --git a/src/fs/low_flash.c b/src/fs/low_flash.c
index bfd43d9..3c72333 100644
--- a/src/fs/low_flash.c
+++ b/src/fs/low_flash.c
@@ -22,6 +22,7 @@
#include "pico_keys.h"
#include
+#include "crypto_utils.h"
#ifdef PICO_PLATFORM
#include "pico/stdlib.h"
#include "hardware/flash.h"
@@ -158,8 +159,14 @@ void do_flash() {
sem_release(&sem_flash);
}
+#ifdef PICO_RP2040
+void phymarker_write();
+#endif
//this function has to be called from the core 0
void low_flash_init() {
+#ifdef PICO_RP2040
+ phymarker_write();
+#endif
memset(flash_pages, 0, sizeof(page_flash_t) * TOTAL_FLASH_PAGES);
mutex_init(&mtx_flash);
sem_init(&sem_flash, 0, 1);
@@ -371,3 +378,42 @@ bool flash_check_blank(const uint8_t *p_start, size_t size) {
}
return true;
}
+
+#ifdef PICO_RP2040
+typedef struct {
+ uint64_t magic;
+ uint16_t version;
+ uint16_t flags;
+ uint8_t uid[PICO_UNIQUE_BOARD_ID_SIZE_BYTES];
+ uint32_t crc32;
+} __attribute__ ((packed)) phymarker_t;
+
+uintptr_t __phymarker_start = (uintptr_t)0x10100000;
+
+const uint64_t PHYSICAL_MARKER_MAGIC = 0x5049434F4B455953ULL; // "PICOKEYS"
+
+void phymarker_write() {
+ const uint64_t magic = *(uint64_t *)__phymarker_start;
+ if (magic == PHYSICAL_MARKER_MAGIC) {
+ return;
+ }
+ phymarker_t pm = {
+ .magic = PHYSICAL_MARKER_MAGIC, // "PICOKEYS"
+ .version = 0x0001,
+ .flags = 0x0000,
+ .crc32 = 0x00000000
+ };
+ memcpy(pm.uid, pico_serial.id, PICO_UNIQUE_BOARD_ID_SIZE_BYTES);
+ pm.crc32 = crc32c((const uint8_t *)&pm, sizeof(phymarker_t) - sizeof(uint32_t));
+
+ uint8_t buf[FLASH_PAGE_SIZE] = {0};
+ memcpy(buf, &pm, sizeof(phymarker_t));
+ uint32_t ints = save_and_disable_interrupts();
+
+ flash_range_erase((uint32_t)__phymarker_start - XIP_BASE, FLASH_SECTOR_SIZE);
+ flash_range_program((uint32_t)__phymarker_start - XIP_BASE, (const uint8_t *)buf, sizeof(buf));
+
+ restore_interrupts(ints);
+}
+
+#endif
diff --git a/src/main.c b/src/main.c
index ecdc873..064e622 100644
--- a/src/main.c
+++ b/src/main.c
@@ -235,8 +235,42 @@ bool wait_button() {
req_button_pending = false;
return timeout || cancel_button;
}
+
+__attribute__((weak)) int picokey_init() {
+ return 0;
+}
+
#endif
+bool set_rtc = false;
+
+bool has_set_rtc() {
+ return set_rtc;
+}
+
+void set_rtc_time(time_t t) {
+#ifdef PICO_PLATFORM
+ struct timespec tv = {.tv_sec = t, .tv_nsec = 0};
+ aon_timer_set_time(&tv);
+#else
+ struct timeval tv = {.tv_sec = t, .tv_usec = 0};
+ settimeofday(&tv, NULL);
+#endif
+ set_rtc = true;
+}
+
+time_t get_rtc_time() {
+#ifdef PICO_PLATFORM
+ struct timespec tv;
+ aon_timer_get_time(&tv);
+ return tv.tv_sec;
+#else
+ struct timeval tv;
+ gettimeofday(&tv, NULL);
+ return tv.tv_sec;
+#endif
+}
+
struct apdu apdu;
void init_rtc() {
@@ -247,7 +281,7 @@ void init_rtc() {
#endif
}
-extern void neug_task();
+extern void hwrng_task();
extern void usb_task();
void execute_tasks()
{
@@ -261,7 +295,7 @@ void execute_tasks()
void core0_loop() {
while (1) {
execute_tasks();
- neug_task();
+ hwrng_task();
do_flash();
#ifndef ENABLE_EMULATION
if (button_pressed_cb && board_millis() > 1000 && !is_busy()) { // wait 1 second to boot up
@@ -364,6 +398,10 @@ int main(void) {
#endif
#endif
+#ifndef ENABLE_EMULATION
+ picokey_init();
+#endif
+
#ifdef ESP_PLATFORM
xTaskCreatePinnedToCore(core0_loop, "core0", 4096*ITF_TOTAL*2, NULL, CONFIG_TINYUSB_TASK_PRIORITY - 1, &hcore0, ESP32_CORE0);
#else
diff --git a/src/pico_keys.h b/src/pico_keys.h
index 3859ac2..d9e6bfa 100644
--- a/src/pico_keys.h
+++ b/src/pico_keys.h
@@ -18,6 +18,8 @@
#ifndef _PICO_KEYS_H_
#define _PICO_KEYS_H_
+#define MBEDTLS_ALLOW_PRIVATE_ACCESS
+
#if defined(PICO_RP2040) || defined(PICO_RP2350)
#define PICO_PLATFORM
#endif
@@ -59,6 +61,15 @@
#include "pico/util/queue.h"
#endif
+#ifdef PICO_PLATFORM
+#include "pico/bootrom.h"
+#include "hardware/watchdog.h"
+#include "pico/aon_timer.h"
+#else
+#include
+#include
+#endif
+
extern bool wait_button();
extern void low_flash_init_core1();
@@ -240,4 +251,8 @@ extern uint8_t pico_serial_hash[32];
#define multicore_launch_func_core1(a) multicore_launch_core1((void (*) (void))a)
#endif
+extern bool has_set_rtc();
+extern time_t get_rtc_time();
+extern void set_rtc_time(time_t tv_sec);
+
#endif
diff --git a/src/pico_keys_version.h b/src/pico_keys_version.h
index c803d56..607649d 100644
--- a/src/pico_keys_version.h
+++ b/src/pico_keys_version.h
@@ -18,7 +18,7 @@
#ifndef __VERSION_H_
#define __VERSION_H_
-#define PICO_KEYS_SDK_VERSION 0x0802
+#define PICO_KEYS_SDK_VERSION 0x0805
#define PICO_KEYS_SDK_VERSION_MAJOR ((PICO_KEYS_SDK_VERSION >> 8) & 0xff)
#define PICO_KEYS_SDK_VERSION_MINOR (PICO_KEYS_SDK_VERSION & 0xff)
diff --git a/src/rescue.c b/src/rescue.c
index 603c781..a0cfa73 100644
--- a/src/rescue.c
+++ b/src/rescue.c
@@ -19,17 +19,10 @@
#include "apdu.h"
#include "pico_keys_version.h"
#include "otp.h"
-#ifdef PICO_PLATFORM
-#include "pico/bootrom.h"
-#include "hardware/watchdog.h"
-#include "pico/aon_timer.h"
-#else
-#include
-#include
-#endif
#include "mbedtls/ecdsa.h"
#include "mbedtls/sha256.h"
#include "random.h"
+#include "crypto_utils.h"
#ifdef PICO_PLATFORM
extern char __flash_binary_start;
@@ -38,7 +31,6 @@ extern char __flash_binary_end;
int rescue_process_apdu();
int rescue_unload();
-bool set_rtc = false;
const uint8_t rescue_aid[] = {
8,
@@ -55,6 +47,8 @@ const uint8_t rescue_aid[] = {
#define PICO_MCU 0
#endif
+#define EF_DEVCERT_KEY 0xE0C1
+
extern uint8_t PICO_PRODUCT;
extern uint8_t PICO_VERSION_MAJOR;
extern uint8_t PICO_VERSION_MINOR;
@@ -84,30 +78,69 @@ int rescue_unload() {
return PICOKEY_OK;
}
+static int load_internal_keydev(mbedtls_ecp_keypair *ecp, mbedtls_ecp_group_id ec_id) {
+ file_t *ef_devcert_key = file_new(EF_DEVCERT_KEY);
+ if (!ef_devcert_key) {
+ return SW_FILE_NOT_FOUND();
+ }
+ uint8_t kbase[32] = {0};
+ derive_kbase(kbase);
+ if (file_has_data(ef_devcert_key)) {
+ uint8_t pkey[32] = {0};
+ memcpy(pkey, file_get_data(ef_devcert_key), 32);
+ aes_decrypt(kbase, pico_serial_hash, 32 * 8, PICO_KEYS_AES_MODE_CBC, pkey, 32);
+ int ret = mbedtls_ecp_read_key(ec_id, ecp, pkey, 32);
+ mbedtls_platform_zeroize(pkey, sizeof(pkey));
+ if (ret != 0) {
+ return SW_EXEC_ERROR();
+ }
+ }
+ else {
+ // Generate new key
+ uint8_t pkey[MBEDTLS_ECP_MAX_BYTES] = {0};
+ size_t olen = 0;
+ mbedtls_ecp_gen_key(ec_id, ecp, random_gen, NULL);
+ mbedtls_ecp_write_key_ext(ecp, &olen, pkey, sizeof(pkey));
+
+ aes_encrypt(kbase, pico_serial_hash, 32 * 8, PICO_KEYS_AES_MODE_CBC, pkey, 32);
+ file_put_data(ef_devcert_key, pkey, (uint16_t)olen);
+ mbedtls_platform_zeroize(pkey, sizeof(pkey));
+ low_flash_available();
+ }
+ return PICOKEY_OK;
+}
+
int cmd_keydev_sign() {
uint8_t p1 = P1(apdu);
if (p1 == 0x01) {
if (apdu.nc != 32) {
return SW_WRONG_LENGTH();
}
+ mbedtls_ecp_keypair ecp;
+ mbedtls_ecp_keypair_init(&ecp);
+ mbedtls_ecp_group_id ec_id = MBEDTLS_ECP_DP_SECP256K1;
if (!otp_key_2) {
- return SW_INS_NOT_SUPPORTED();
+ int ret = load_internal_keydev(&ecp, ec_id);
+ if (ret != PICOKEY_OK) {
+ mbedtls_ecp_keypair_free(&ecp);
+ return ret;
+ }
}
- mbedtls_ecdsa_context ecdsa;
- mbedtls_ecdsa_init(&ecdsa);
- int ret = mbedtls_ecp_read_key(MBEDTLS_ECP_DP_SECP256K1, &ecdsa, otp_key_2, 32);
- if (ret != 0) {
- mbedtls_ecdsa_free(&ecdsa);
- return SW_EXEC_ERROR();
+ else {
+ int ret = mbedtls_ecp_read_key(ec_id, &ecp, otp_key_2, 32);
+ if (ret != 0) {
+ mbedtls_ecp_keypair_free(&ecp);
+ return SW_EXEC_ERROR();
+ }
}
- uint16_t key_size = 2 * (int)((mbedtls_ecp_curve_info_from_grp_id(MBEDTLS_ECP_DP_SECP256K1)->bit_size + 7) / 8);
+ uint16_t key_size = 2 * (int)((mbedtls_ecp_curve_info_from_grp_id(ec_id)->bit_size + 7) / 8);
mbedtls_mpi r, s;
mbedtls_mpi_init(&r);
mbedtls_mpi_init(&s);
- ret = mbedtls_ecdsa_sign(&ecdsa.MBEDTLS_PRIVATE(grp), &r, &s, &ecdsa.MBEDTLS_PRIVATE(d), apdu.data, apdu.nc, random_gen, NULL);
+ int ret = mbedtls_ecdsa_sign(&ecp.MBEDTLS_PRIVATE(grp), &r, &s, &ecp.MBEDTLS_PRIVATE(d), apdu.data, apdu.nc, random_gen, NULL);
if (ret != 0) {
- mbedtls_ecdsa_free(&ecdsa);
+ mbedtls_ecp_keypair_free(&ecp);
mbedtls_mpi_free(&r);
mbedtls_mpi_free(&s);
return SW_EXEC_ERROR();
@@ -115,32 +148,39 @@ int cmd_keydev_sign() {
mbedtls_mpi_write_binary(&r, res_APDU, key_size / 2); res_APDU_size = key_size / 2;
mbedtls_mpi_write_binary(&s, res_APDU + res_APDU_size, key_size / 2); res_APDU_size += key_size / 2;
- mbedtls_ecdsa_free(&ecdsa);
+ mbedtls_ecp_keypair_free(&ecp);
mbedtls_mpi_free(&r);
mbedtls_mpi_free(&s);
}
else if (p1 == 0x02) {
// Return public key
- if (!otp_key_2) {
- return SW_INS_NOT_SUPPORTED();
- }
if (apdu.nc != 0) {
return SW_WRONG_LENGTH();
}
mbedtls_ecp_keypair ecp;
mbedtls_ecp_keypair_init(&ecp);
- int ret = mbedtls_ecp_read_key(MBEDTLS_ECP_DP_SECP256K1, &ecp, otp_key_2, 32);
- if (ret != 0) {
- mbedtls_ecp_keypair_free(&ecp);
- return SW_EXEC_ERROR();
+ mbedtls_ecp_group_id ec_id = MBEDTLS_ECP_DP_SECP256K1;
+ if (!otp_key_2) {
+ int ret = load_internal_keydev(&ecp, ec_id);
+ if (ret != PICOKEY_OK) {
+ mbedtls_ecp_keypair_free(&ecp);
+ return ret;
+ }
}
- ret = mbedtls_ecp_mul(&ecp.MBEDTLS_PRIVATE(grp), &ecp.MBEDTLS_PRIVATE(Q), &ecp.MBEDTLS_PRIVATE(d), &ecp.MBEDTLS_PRIVATE(grp).G, random_gen, NULL);
+ else {
+ int ret = mbedtls_ecp_read_key(ec_id, &ecp, otp_key_2, 32);
+ if (ret != 0) {
+ mbedtls_ecp_keypair_free(&ecp);
+ return SW_EXEC_ERROR();
+ }
+ }
+ int ret = mbedtls_ecp_mul(&ecp.MBEDTLS_PRIVATE(grp), &ecp.MBEDTLS_PRIVATE(Q), &ecp.MBEDTLS_PRIVATE(d), &ecp.MBEDTLS_PRIVATE(grp).G, random_gen, NULL);
if (ret != 0) {
mbedtls_ecp_keypair_free(&ecp);
return SW_EXEC_ERROR();
}
size_t olen = 0;
- ret = mbedtls_ecp_point_write_binary(&ecp.MBEDTLS_PRIVATE(grp), &ecp.MBEDTLS_PRIVATE(Q), MBEDTLS_ECP_PF_UNCOMPRESSED, &olen, res_APDU, 4096);
+ ret = mbedtls_ecp_point_write_binary(&ecp.MBEDTLS_PRIVATE(grp), &ecp.MBEDTLS_PRIVATE(Q), MBEDTLS_ECP_PF_UNCOMPRESSED, &olen, res_APDU, 2038);
if (ret != 0) {
mbedtls_ecp_keypair_free(&ecp);
return SW_EXEC_ERROR();
@@ -220,14 +260,7 @@ int cmd_write() {
uint32_t t = (apdu.data[0] << 24) | (apdu.data[1] << 16) | (apdu.data[2] << 8) | apdu.data[3];
tv_sec = (time_t)t;
}
-#ifdef PICO_PLATFORM
- struct timespec tv = {.tv_sec = tv_sec, .tv_nsec = 0};
- aon_timer_set_time(&tv);
-#else
- struct timeval tv = {.tv_sec = tv_sec, .tv_usec = 0};
- settimeofday(&tv, NULL);
-#endif
- set_rtc = true;
+ set_rtc_time(tv_sec);
}
led_3_blinks();
return SW_OK();
@@ -277,16 +310,15 @@ int cmd_read() {
if (p2 != 0x1 && p2 != 0x2) {
return SW_INCORRECT_P1P2();
}
- if (!set_rtc) {
+ if (!has_set_rtc()) {
return SW_CONDITIONS_NOT_SATISFIED();
}
res_APDU_size = 0;
+ time_t tv_sec = get_rtc_time();
#ifdef PICO_PLATFORM
- struct timespec tv;
- aon_timer_get_time(&tv);
+ struct timespec tv = {.tv_sec = tv_sec, .tv_nsec = 0};
#else
- struct timeval tv;
- gettimeofday(&tv, NULL);
+ struct timeval tv = {.tv_sec = tv_sec, .tv_usec = 0};
#endif
if (p2 == 0x1) {
struct tm *tm = localtime(&tv.tv_sec);
diff --git a/src/rng/hwrng.c b/src/rng/hwrng.c
index cec2871..c83c437 100644
--- a/src/rng/hwrng.c
+++ b/src/rng/hwrng.c
@@ -44,17 +44,17 @@ void hwrng_start() {
}
static uint64_t random_word = 0xcbf29ce484222325;
-static uint8_t ep_round = 0;
+static uint8_t hwrng_mix_round = 0;
-static void ep_init() {
+static void hwrng_mix_init() {
random_word = 0xcbf29ce484222325;
- ep_round = 0;
+ hwrng_mix_round = 0;
}
/* Here, we assume a little endian architecture. */
-static int ep_process() {
- if (ep_round == 0) {
- ep_init();
+static int hwrng_mix_process() {
+ if (hwrng_mix_round == 0) {
+ hwrng_mix_init();
}
uint64_t word = 0x0;
@@ -69,14 +69,14 @@ static int ep_process() {
#endif
random_word ^= word ^ board_millis();
random_word *= 0x00000100000001B3;
- if (++ep_round == 8) {
- ep_round = 0;
- return 2; //2 words
+ if (++hwrng_mix_round == 8) {
+ hwrng_mix_round = 0;
+ return sizeof(uint64_t) / sizeof(uint32_t); //2 words
}
return 0;
}
-struct rng_rb {
+struct hwrng_buf {
uint32_t *buf;
uint8_t head, tail;
uint8_t size;
@@ -84,7 +84,7 @@ struct rng_rb {
unsigned int empty : 1;
};
-static void rb_init(struct rng_rb *rb, uint32_t *p, uint8_t size) {
+static void hwrng_buf_init(struct hwrng_buf *rb, uint32_t *p, uint8_t size) {
rb->buf = p;
rb->size = size;
rb->head = rb->tail = 0;
@@ -92,7 +92,7 @@ static void rb_init(struct rng_rb *rb, uint32_t *p, uint8_t size) {
rb->empty = 1;
}
-static void rb_add(struct rng_rb *rb, uint32_t v) {
+static void hwrng_buf_add(struct hwrng_buf *rb, uint32_t v) {
rb->buf[rb->tail++] = v;
if (rb->tail == rb->size) {
rb->tail = 0;
@@ -103,7 +103,7 @@ static void rb_add(struct rng_rb *rb, uint32_t v) {
rb->empty = 0;
}
-static uint32_t rb_del(struct rng_rb *rb) {
+static uint32_t hwrng_buf_del(struct hwrng_buf *rb) {
uint32_t v = rb->buf[rb->head++];
if (rb->head == rb->size) {
@@ -117,19 +117,18 @@ static uint32_t rb_del(struct rng_rb *rb) {
return v;
}
-static struct rng_rb the_ring_buffer;
+static struct hwrng_buf ring_buffer;
-void *neug_task() {
- struct rng_rb *rb = &the_ring_buffer;
+void *hwrng_task() {
+ struct hwrng_buf *rb = &ring_buffer;
int n;
- if ((n = ep_process())) {
- int i;
+ if ((n = hwrng_mix_process())) {
const uint32_t *vp = (const uint32_t *) &random_word;
- for (i = 0; i < n; i++) {
- rb_add(rb, *vp++);
+ for (int i = 0; i < n; i++) {
+ hwrng_buf_add(rb, *vp++);
if (rb->full) {
break;
}
@@ -138,38 +137,37 @@ void *neug_task() {
return NULL;
}
-void neug_init(uint32_t *buf, uint8_t size) {
- struct rng_rb *rb = &the_ring_buffer;
+void hwrng_init(uint32_t *buf, uint8_t size) {
+ struct hwrng_buf *rb = &ring_buffer;
- rb_init(rb, buf, size);
+ hwrng_buf_init(rb, buf, size);
hwrng_start();
- ep_init();
+ hwrng_mix_init();
}
-void neug_flush(void) {
- struct rng_rb *rb = &the_ring_buffer;
-
+void hwrng_flush(void) {
+ struct hwrng_buf *rb = &ring_buffer;
while (!rb->empty) {
- rb_del(rb);
+ hwrng_buf_del(rb);
}
}
-uint32_t neug_get() {
- struct rng_rb *rb = &the_ring_buffer;
+uint32_t hwrng_get() {
+ struct hwrng_buf *rb = &ring_buffer;
uint32_t v;
while (rb->empty) {
- neug_task();
+ hwrng_task();
}
- v = rb_del(rb);
+ v = hwrng_buf_del(rb);
return v;
}
-void neug_wait_full() {
- struct rng_rb *rb = &the_ring_buffer;
+void hwrng_wait_full() {
+ struct hwrng_buf *rb = &ring_buffer;
#ifdef ESP_PLATFORM
uint8_t core = xTaskGetCurrentTaskHandle() == hcore1 ? 1 : 0;
#elif defined(PICO_PLATFORM)
@@ -182,6 +180,6 @@ void neug_wait_full() {
}
else
#endif
- neug_task();
+ hwrng_task();
}
}
diff --git a/src/rng/hwrng.h b/src/rng/hwrng.h
index e510d93..4229eb9 100644
--- a/src/rng/hwrng.h
+++ b/src/rng/hwrng.h
@@ -17,17 +17,11 @@
#ifndef _NEUG_H_
#define _NEUG_H_
+#include
-#define NEUG_PRE_LOOP 32
-
-#include
-#if defined(PICO_PLATFORM)
-#include "pico/stdlib.h"
-#endif
-
-void neug_init(uint32_t *buf, uint8_t size);
-uint32_t neug_get();
-void neug_flush(void);
-void neug_wait_full();
+void hwrng_init(uint32_t *buf, uint8_t size);
+uint32_t hwrng_get();
+void hwrng_flush(void);
+void hwrng_wait_full();
#endif
diff --git a/src/rng/random.c b/src/rng/random.c
index 3c46d81..bc75434 100644
--- a/src/rng/random.c
+++ b/src/rng/random.c
@@ -15,8 +15,12 @@
* along with this program. If not, see .
*/
+#define HWRNG_PRE_LOOP 32
-#include
+#include
+#if defined(PICO_PLATFORM)
+#include "pico/stdlib.h"
+#endif
#include
#include "hwrng.h"
@@ -25,42 +29,38 @@
static uint32_t random_word[RANDOM_BYTES_LENGTH / sizeof(uint32_t)];
void random_init(void) {
- int i;
+ hwrng_init(random_word, RANDOM_BYTES_LENGTH / sizeof(uint32_t));
- neug_init(random_word, RANDOM_BYTES_LENGTH / sizeof(uint32_t));
-
- for (i = 0; i < NEUG_PRE_LOOP; i++) {
- neug_get();
+ for (int i = 0; i < HWRNG_PRE_LOOP; i++) {
+ hwrng_get();
}
}
-/*
- * Return pointer to random 32-byte
- */
-void random_bytes_free(const uint8_t *p);
-#define MAX_RANDOM_BUFFER 1024
-const uint8_t *random_bytes_get(size_t len) {
- if (len > MAX_RANDOM_BUFFER) {
- return NULL;
- }
- static uint32_t return_word[MAX_RANDOM_BUFFER / sizeof(uint32_t)];
- for (size_t ix = 0; ix < len; ix += RANDOM_BYTES_LENGTH) {
- neug_wait_full();
- memcpy(return_word + ix / sizeof(uint32_t), random_word, RANDOM_BYTES_LENGTH);
- random_bytes_free((const uint8_t *) random_word);
- }
- return (const uint8_t *) return_word;
-}
-
/*
* Free pointer to random 32-byte
*/
void random_bytes_free(const uint8_t *p) {
(void) p;
memset(random_word, 0, RANDOM_BYTES_LENGTH);
- neug_flush();
+ hwrng_flush();
}
+/*
+ * Return pointer to random 32-byte
+ */
+#define MAX_RANDOM_BUFFER 1024
+const uint8_t *random_bytes_get(size_t len) {
+ if (len > MAX_RANDOM_BUFFER) {
+ return NULL;
+ }
+ static uint32_t return_word[MAX_RANDOM_BUFFER / sizeof(uint32_t)];
+ for (size_t ix = 0; ix < len; ix += RANDOM_BYTES_LENGTH) {
+ hwrng_wait_full();
+ memcpy(return_word + ix / sizeof(uint32_t), random_word, RANDOM_BYTES_LENGTH);
+ random_bytes_free((const uint8_t *) random_word);
+ }
+ return (const uint8_t *) return_word;
+}
/*
* Random byte iterator
@@ -71,7 +71,7 @@ int random_gen(void *arg, unsigned char *out, size_t out_len) {
uint8_t n;
while (out_len) {
- neug_wait_full();
+ hwrng_wait_full();
n = RANDOM_BYTES_LENGTH - index;
if (n > out_len) {
@@ -85,7 +85,7 @@ int random_gen(void *arg, unsigned char *out, size_t out_len) {
if (index >= RANDOM_BYTES_LENGTH) {
index = 0;
- neug_flush();
+ hwrng_flush();
}
}
@@ -95,3 +95,9 @@ int random_gen(void *arg, unsigned char *out, size_t out_len) {
return 0;
}
+
+#ifdef ENABLE_PQC
+void randombytes(uint8_t *buf, size_t n) {
+ random_gen(NULL, buf, n);
+}
+#endif
diff --git a/src/usb/ccid/ccid.c b/src/usb/ccid/ccid.c
index 4bc4657..fd16ae3 100644
--- a/src/usb/ccid/ccid.c
+++ b/src/usb/ccid/ccid.c
@@ -201,6 +201,20 @@ int driver_process_usb_packet_ccid(uint8_t itf, uint16_t rx_read) {
(void) rx_read;
if (ccid_rx[itf].w_ptr - ccid_rx[itf].r_ptr >= 10) {
driver_init_ccid(itf);
+ if (ccid_header[itf]->dwLength > USB_BUFFER_SIZE - 10) {
+ //Invalid length
+ ccid_rx[itf].r_ptr = ccid_rx[itf].w_ptr = 0;
+
+ ccid_resp_fast[itf]->bMessageType = CCID_DATA_BLOCK_RET;
+ ccid_resp_fast[itf]->dwLength = 2;
+ ccid_resp_fast[itf]->bSlot = 0;
+ ccid_resp_fast[itf]->bSeq = ccid_header[itf]->bSeq;
+ ccid_resp_fast[itf]->abRFU0 = ccid_status;
+ ccid_resp_fast[itf]->abRFU1 = 0;
+ memcpy(&ccid_resp_fast[itf]->apdu, "\x6F\x00", 2);
+ ccid_write_fast(itf, (const uint8_t *)ccid_resp_fast[itf], 12);
+ return 0;
+ }
//printf("ccid_process %ld %d %x %x %d\n",ccid_header[itf]->dwLength,rx_read-10,ccid_header[itf]->bMessageType,ccid_header[itf]->bSeq,ccid_rx[itf].w_ptr - ccid_rx[itf].r_ptr - 10);
if (ccid_header[itf]->dwLength <= (uint32_t)(ccid_rx[itf].w_ptr - ccid_rx[itf].r_ptr - 10)){
ccid_rx[itf].r_ptr += (uint16_t)(ccid_header[itf]->dwLength + 10);
diff --git a/src/usb/usb.c b/src/usb/usb.c
index e040e8b..9bdd08c 100644
--- a/src/usb/usb.c
+++ b/src/usb/usb.c
@@ -73,8 +73,10 @@ queue_t card_to_usb_q = {0};
#ifndef ENABLE_EMULATION
extern tusb_desc_device_t desc_device;
+extern char *string_desc_itf[4], *string_desc_arr[];
#endif
-void usb_init() {
+void usb_init()
+{
#ifndef ENABLE_EMULATION
if (phy_data.vidpid_present) {
desc_device.idVendor = phy_data.vid;
@@ -108,20 +110,32 @@ void usb_init() {
if (enabled_usb_itf & PHY_USB_ITF_HID) {
ITF_HID_CTAP = ITF_HID_TOTAL++;
ITF_HID = ITF_TOTAL++;
+#ifndef ENABLE_EMULATION
+ string_desc_itf[ITF_TOTAL - 1] = string_desc_arr[5];
+#endif
}
if (enabled_usb_itf & PHY_USB_ITF_KB) {
ITF_HID_KB = ITF_HID_TOTAL++;
ITF_KEYBOARD = ITF_TOTAL++;
+#ifndef ENABLE_EMULATION
+ string_desc_itf[ITF_TOTAL - 1] = string_desc_arr[6];
+#endif
}
#endif
#ifdef USB_ITF_CCID
if (enabled_usb_itf & PHY_USB_ITF_CCID) {
ITF_SC_CCID = ITF_SC_TOTAL++;
ITF_CCID = ITF_TOTAL++;
+#ifndef ENABLE_EMULATION
+ string_desc_itf[ITF_TOTAL - 1] = string_desc_arr[7];
+#endif
}
if (enabled_usb_itf & PHY_USB_ITF_WCID) {
ITF_SC_WCID = ITF_SC_TOTAL++;
ITF_WCID = ITF_TOTAL++;
+#ifndef ENABLE_EMULATION
+ string_desc_itf[ITF_TOTAL - 1] = string_desc_arr[8];
+#endif
}
#endif
card_locked_itf = ITF_TOTAL;
diff --git a/src/usb/usb_descriptors.c b/src/usb/usb_descriptors.c
index f2f2734..90e4e16 100644
--- a/src/usb/usb_descriptors.c
+++ b/src/usb/usb_descriptors.c
@@ -28,10 +28,10 @@
#include "usb.h"
#ifndef USB_VID
-#define USB_VID 0xFEFF
+#define USB_VID 0x1D50
#endif
#ifndef USB_PID
-#define USB_PID 0xFCFD
+#define USB_PID 0x619B
#endif
#if defined(PICO_PLATFORM) || defined(ESP_PLATFORM)
@@ -316,20 +316,17 @@ uint8_t const *tud_descriptor_bos_cb(void) {
//--------------------------------------------------------------------+
// array of pointer to string descriptors
+char *string_desc_itf[4] = {0};
char const *string_desc_arr [] = {
(const char[]) { 0x09, 0x04 }, // 0: is supported language is English (0x0409)
"Libre Keys", // 1: Manufacturer
"Pico Key", // 2: Product
"11223344", // 3: Serials, should use chip ID
"Config" // 4: Vendor Interface
-#ifdef USB_ITF_HID
, "HID Interface"
, "HID Keyboard Interface"
-#endif
-#ifdef USB_ITF_CCID
, "CCID OTP FIDO Interface"
, "WebCCID Interface"
-#endif
};
#ifdef ESP_PLATFORM
@@ -369,6 +366,9 @@ uint16_t const *tud_descriptor_string_cb(uint8_t index, uint16_t langid) {
str = phy_data.usb_product;
}
}
+ else if (index >= 5 && string_desc_itf[index - 5] != NULL) {
+ str = string_desc_itf[index - 5];
+ }
uint8_t buff_avail = sizeof(_desc_str) / sizeof(_desc_str[0]) - 1;
if (index >= 4) {