Skip to content

Commit b7735aa

Browse files
committed
Merge commit '0c4272c0'
2 parents fab3ce6 + 0c4272c commit b7735aa

File tree

15 files changed

+781
-25
lines changed

15 files changed

+781
-25
lines changed

CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -386,6 +386,7 @@ if(CMAKE_CROSSCOMPILING)
386386
else()
387387
include(CTest)
388388
add_subdirectory(test/unit-test)
389+
add_subdirectory(test/simulator)
389390
if(COVERAGE)
390391
find_program(GCOVR gcovr)
391392
if(NOT GCOVR STREQUAL "GCOVR-NOTFOUND")

Makefile

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,10 @@ docs: | build
8585
$(MAKE) -C build doc
8686
rust-docs: | build
8787
$(MAKE) -C build rust-docs
88+
simulator: | build-build
89+
$(MAKE) -C build-build simulator
90+
run-simulator: | simulator
91+
./build-build/bin/simulator
8892
unit-test: | build-build
8993
$(MAKE) -C build-build
9094
# Must compile C tests before running them

py/send_message.py

Lines changed: 6 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1573,28 +1573,24 @@ class Simulator(PhysicalLayer):
15731573
def __init__(self) -> None:
15741574
self.client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
15751575
port = 15423
1576-
self.client_socket.bind(("", port))
1577-
self.client_socket.listen(50)
1578-
print(f"Waiting for connection on port {port}")
1579-
self.connection, addr = self.client_socket.accept()
1580-
print(f"Connected to {addr}")
1576+
self.client_socket.connect(("127.0.0.1", port))
1577+
if debug:
1578+
print("Connected to the simulator")
15811579

15821580
def write(self, data: bytes) -> None:
1583-
self.connection.send(data[1:])
1581+
self.client_socket.send(data[1:])
15841582
if debug:
15851583
print(f"Written to the simulator:\n{data.hex()[2:]}")
15861584

15871585
def read(self, size: int, timeout_ms: int) -> bytes:
1588-
res = self.connection.recv(64)
1586+
res = self.client_socket.recv(64)
15891587
if debug:
15901588
print(f"Read from the simulator:\n{res.hex()}")
15911589
return res
15921590

15931591
def __del__(self) -> None:
15941592
print("Simulator quit")
1595-
if self.connection:
1596-
self.connection.shutdown(socket.SHUT_RDWR)
1597-
self.connection.close()
1593+
self.client_socket.close()
15981594

15991595
simulator = Simulator()
16001596

src/rust/bitbox02-rust-c/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,7 @@ target-c-unit-tests = [
5959
# enable these features
6060
"app-bitcoin",
6161
"app-ethereum",
62+
"app-cardano",
6263
"firmware",
6364
"c-unit-testing",
6465
]

test/simulator/CMakeLists.txt

Lines changed: 185 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,185 @@
1+
# Copyright 2024 Shift Cryptosecurity AG
2+
#
3+
# Licensed under the Apache License, Version 2.0 (the "License");
4+
# you may not use this file except in compliance with the License.
5+
# You may obtain a copy of the License at
6+
#
7+
# http://www.apache.org/licenses/LICENSE-2.0
8+
#
9+
# Unless required by applicable law or agreed to in writing, software
10+
# distributed under the License is distributed on an "AS IS" BASIS,
11+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
# See the License for the specific language governing permissions and
13+
# limitations under the License.
14+
15+
16+
#-----------------------------------------------------------------------------
17+
# Build bitbox lib to use in tests
18+
19+
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wno-unused-parameter -Wno-missing-prototypes -Wno-missing-declarations -Wno-implicit-function-declaration -Wno-bad-function-cast")
20+
21+
set(DBB-FILTERED-SOURCES
22+
${DBB-FIRMWARE-SOURCES}
23+
${DBB-FIRMWARE-UI-SOURCES}
24+
${FIRMWARE-U2F-SOURCES}
25+
${DBB-FIRMWARE-USB-SOURCES}
26+
)
27+
28+
set(IGNORE_SOURCES
29+
"src/screen.c"
30+
"src/memory/nvmctrl.c"
31+
"src/memory/smarteeprom.c"
32+
"src/memory.mpu.c"
33+
)
34+
35+
# Exclude some files which depends on the hardware.
36+
foreach(SOURCEFILE ${IGNORE_SOURCES})
37+
list(FILTER DBB-FILTERED-SOURCES EXCLUDE REGEX ".*/${SOURCEFILE}$")
38+
endforeach()
39+
40+
message("FILTERED SOURCES: ${DBB-FILTERED-SOURCES}")
41+
42+
add_library(sd-mock-simulator
43+
STATIC
44+
framework/mock_diskio.c
45+
)
46+
target_include_directories(
47+
sd-mock-simulator
48+
PUBLIC
49+
$<TARGET_PROPERTY:fatfs,INTERFACE_INCLUDE_DIRECTORIES>
50+
)
51+
52+
53+
# We create a CMake "object library" to track all the compiled sources so that
54+
# they can be reused between a normal library and the manually crafted "merged"
55+
# library.
56+
# See https://cmake.org/cmake/help/v3.10/command/add_library.html#object-libraries
57+
add_library(bitbox_objects-simulator
58+
OBJECT
59+
${DBB-FILTERED-SOURCES}
60+
${CTAES-SOURCES}
61+
${ETHEREUM-SOURCES}
62+
framework/mock_cipher.c
63+
framework/mock_memory.c
64+
framework/mock_screen.c
65+
framework/mock_smarteeprom.c
66+
framework/mock_securechip.c
67+
)
68+
69+
add_library(bitbox-simulator
70+
STATIC
71+
$<TARGET_OBJECTS:bitbox_objects-simulator>
72+
)
73+
74+
# Here we create the "merged" library, which starts with the c-lib created by
75+
# cargo in the "bitbox02-rust-c" project. That project produces a c-lib without
76+
# mangled symbols so that it is easier to use from C. We then extend that
77+
# library with all the object files declared in "bitbox_objects-simulator", all the code
78+
# we want to be able to call from tests.
79+
# By linking to "bitbox_merged-simulator" in the rust unit tests we get access to all our
80+
# code. (That linkage is done by cargo using a "build.rs" script in the
81+
# bitbox02 rust project.)
82+
add_custom_command(
83+
OUTPUT ${CMAKE_ARCHIVE_OUTPUT_DIRECTORY}/libbitbox_merged-simulator.a
84+
DEPENDS c-unit-tests_rust_c bitbox_objects-simulator $<TARGET_OBJECTS:bitbox_objects-simulator>
85+
COMMAND ${CMAKE_COMMAND} -E copy $<TARGET_PROPERTY:c-unit-tests_rust_c,IMPORTED_LOCATION> ${CMAKE_ARCHIVE_OUTPUT_DIRECTORY}/libbitbox_merged-simulator.a
86+
COMMAND ar q ${CMAKE_ARCHIVE_OUTPUT_DIRECTORY}/libbitbox_merged-simulator.a $<TARGET_OBJECTS:bitbox_objects-simulator>
87+
VERBATIM
88+
COMMAND_EXPAND_LISTS
89+
)
90+
91+
add_custom_target(bitbox_merged-simulator DEPENDS ${CMAKE_ARCHIVE_OUTPUT_DIRECTORY}/libbitbox_merged-simulator.a)
92+
93+
target_include_directories(
94+
bitbox_objects-simulator
95+
SYSTEM PUBLIC
96+
${SYSTEMINCLUDES}
97+
${CMAKE_SOURCE_DIR}/external
98+
${CMAKE_SOURCE_DIR}/external/ctaes
99+
${CMAKE_SOURCE_DIR}/external/fatfs/source
100+
$<TARGET_PROPERTY:wallycore,INTERFACE_INCLUDE_DIRECTORIES>
101+
$<TARGET_PROPERTY:secp256k1,INTERFACE_INCLUDE_DIRECTORIES>
102+
$<TARGET_PROPERTY:fatfs,INTERFACE_INCLUDE_DIRECTORIES>
103+
)
104+
target_include_directories(
105+
bitbox_objects-simulator
106+
PUBLIC
107+
${INCLUDES}
108+
${CMAKE_CURRENT_SOURCE_DIR}/../unit-test/framework/includes
109+
${CMAKE_CURRENT_SOURCE_DIR}
110+
${CMAKE_BINARY_DIR}/src
111+
)
112+
113+
target_include_directories(
114+
bitbox-simulator
115+
SYSTEM PUBLIC
116+
${SYSTEMINCLUDES}
117+
${CMAKE_SOURCE_DIR}/external
118+
${CMAKE_SOURCE_DIR}/external/ctaes
119+
${CMAKE_SOURCE_DIR}/external/fatfs/source
120+
$<TARGET_PROPERTY:wallycore,INTERFACE_INCLUDE_DIRECTORIES>
121+
$<TARGET_PROPERTY:secp256k1,INTERFACE_INCLUDE_DIRECTORIES>
122+
$<TARGET_PROPERTY:fatfs,INTERFACE_INCLUDE_DIRECTORIES>
123+
)
124+
125+
target_include_directories(
126+
bitbox-simulator
127+
PUBLIC
128+
${INCLUDES}
129+
${CMAKE_CURRENT_SOURCE_DIR}/../unit-test/framework/includes
130+
${CMAKE_CURRENT_SOURCE_DIR}
131+
${CMAKE_BINARY_DIR}/src
132+
)
133+
134+
add_dependencies(bitbox_objects-simulator
135+
rust-cbindgen
136+
wallycore
137+
secp256k1
138+
ctaes
139+
fatfs
140+
sd-mock-simulator
141+
)
142+
target_link_libraries(bitbox-simulator PRIVATE ${LIBBITBOX02_RUST} "-lm")
143+
144+
target_compile_definitions(bitbox_objects-simulator PUBLIC "PRODUCT_BITBOX_MULTI=1" "APP_BTC=1" "APP_LTC=1" "APP_U2F=1" "APP_ETH=1")
145+
target_compile_definitions(bitbox_objects-simulator PUBLIC TESTING)
146+
147+
# Since wallycore is an external projects we need to specify the dependency
148+
add_dependencies(bitbox_objects-simulator libwally-core)
149+
150+
target_compile_definitions(bitbox-simulator PUBLIC "PRODUCT_BITBOX_MULTI=1" "APP_BTC=1" "APP_LTC=1" "APP_U2F=1" "APP_ETH=1")
151+
target_compile_definitions(bitbox-simulator PUBLIC TESTING)
152+
153+
target_link_libraries(bitbox-simulator
154+
PUBLIC
155+
secp256k1
156+
PRIVATE
157+
wallycore
158+
ctaes
159+
fatfs
160+
sd-mock-simulator
161+
)
162+
163+
if(SANITIZE_ADDRESS)
164+
target_compile_options(bitbox_objects-simulator PUBLIC "-fsanitize=address")
165+
target_compile_options(bitbox-simulator PUBLIC "-fsanitize=address")
166+
endif()
167+
if(SANTIZE_UNDEFINED)
168+
target_compile_options(bitbox_objects-simulator PUBLIC "-fsanitize=undefined")
169+
target_compile_options(bitbox-simulator PUBLIC "-fsanitize=undefined")
170+
endif()
171+
172+
#-----------------------------------------------------------------------------
173+
# Simulator
174+
175+
add_executable(simulator simulator.c framework/eh_personality.c)
176+
# asan must be first library in linking order
177+
target_link_libraries(simulator PRIVATE
178+
$<$<BOOL:${SANITIZE_ADDRESS}>:asan>
179+
$<$<BOOL:${SANITIZE_UNDEFINED}>:-fsanitize=undefined>
180+
-Wl,--start-group
181+
c-unit-tests_rust_c
182+
bitbox-simulator
183+
-Wl,--end-group
184+
""
185+
)
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
// Copyright 2022 Shift Crypto AG
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
// Needed to link the simulator executable in /test/simulator, which link to
16+
// bitbox_merged-simulator. `rust_eh_personality` is provided by Rust when building the firmware or
17+
// running Rust unit tests.
18+
void rust_eh_personality(void);
19+
void rust_eh_personality(void) {}
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
// Copyright 2023 Shift Crypto AG
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
#include <string.h>
16+
17+
#include <mock_cipher.h>
18+
19+
void cipher_mock_iv(uint8_t* iv_out)
20+
{
21+
memset(iv_out, 'a', 32);
22+
}
Lines changed: 82 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
// Copyright 2021 Shift Crypto AG
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
#include <stdint.h>
16+
#include <string.h>
17+
18+
// Must be included before diskio.h, see http://elm-chan.org/fsw/ff/bd/?show=3626
19+
#include <ff.h>
20+
21+
#include <diskio.h>
22+
23+
// This file is the disk middleware for use in tests, replacing sdmmc_diskio.c used in the firmware
24+
// to write to microSD cards.
25+
//
26+
// It writes and reads from RAM instead of to a card or disk so that unit tests can exercise all
27+
// sd-card related functionality.
28+
29+
// 100mb with 512 bytes per sector
30+
#define SECTOR_SIZE 512
31+
#define SECTOR_COUNT 204800
32+
static uint8_t _data[SECTOR_SIZE * SECTOR_COUNT] = {0};
33+
34+
DSTATUS disk_initialize(uint8_t drv)
35+
{
36+
(void)drv;
37+
return 0;
38+
}
39+
40+
DSTATUS disk_status(uint8_t drv)
41+
{
42+
(void)drv;
43+
return 0;
44+
}
45+
46+
DRESULT disk_read(BYTE pdrv, BYTE* buff, LBA_t sector, UINT count)
47+
{
48+
(void)pdrv;
49+
for (UINT i = 0; i < count; i++) {
50+
memcpy(&buff[SECTOR_SIZE * i], &_data[SECTOR_SIZE * sector + SECTOR_SIZE * i], SECTOR_SIZE);
51+
}
52+
return RES_OK;
53+
}
54+
55+
DRESULT disk_write(BYTE pdrv, const BYTE* buff, LBA_t sector, UINT count)
56+
{
57+
for (UINT i = 0; i < count; i++) {
58+
memcpy(&_data[SECTOR_SIZE * sector + SECTOR_SIZE * i], &buff[SECTOR_SIZE * i], SECTOR_SIZE);
59+
}
60+
return RES_OK;
61+
}
62+
63+
DRESULT disk_ioctl(BYTE pdrv, BYTE cmd, void* buff)
64+
{
65+
(void)pdrv;
66+
switch (cmd) {
67+
case CTRL_SYNC:
68+
// Already synced (RAM).
69+
return RES_OK;
70+
case GET_BLOCK_SIZE:
71+
*(DWORD*)buff = 1;
72+
return RES_OK;
73+
case GET_SECTOR_SIZE:
74+
*(LBA_t*)buff = SECTOR_SIZE;
75+
return RES_OK;
76+
case GET_SECTOR_COUNT:
77+
*(LBA_t*)buff = SECTOR_COUNT;
78+
return RES_OK;
79+
default:
80+
return RES_PARERR;
81+
}
82+
}

0 commit comments

Comments
 (0)