Skip to content

Commit f81621d

Browse files
committed
Add Nuvoton NuMicro M2354 crypto callback port
1 parent 768f646 commit f81621d

19 files changed

Lines changed: 5140 additions & 11 deletions
Lines changed: 135 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,135 @@
1+
name: "Nuvoton M2354 port"
2+
3+
# Keeps the Nuvoton NuMicro M2354 crypto callback port compiling against the
4+
# real vendor BSP. The port has no autotools option and is not built by any
5+
# other job: an application compiles wolfcrypt/src/port/nuvoton/*.c into its own
6+
# project, the same way wolfcrypt/src/port/st/stm32.c is carried. Without this
7+
# guard a header rename in the BSP, or a refactor in aes.c, ecc.c or cryptocb.h,
8+
# would break the port silently until someone next built for the board.
9+
#
10+
# Nothing is faked. arm-none-eabi-gcc is a plain apt package and the BSP is a
11+
# public GitHub repository, so both legs compile against the genuine Nuvoton
12+
# StdDriver headers at a pinned commit.
13+
#
14+
# secure WOLFSSL_NUVOTON_SECURE, the whole port including nuvoton_hw.c
15+
# nonsecure WOLFSSL_NUVOTON_NSC, where nuvoton_hw.c compiles to nothing
16+
# and the cmse_nonsecure_entry veneers supply the symbols
17+
#
18+
# The runnable example, including those veneers, lives in wolfssl-examples
19+
# under embedded/nuvoton_m2354. Functional correctness is validated on a
20+
# NuMaker-M2354, not here; see wolfcrypt/src/port/nuvoton/README.md.
21+
22+
# START OF COMMON SECTION
23+
on:
24+
push:
25+
branches: [ 'master', 'main', 'release/**' ]
26+
paths:
27+
- 'wolfcrypt/src/port/nuvoton/**'
28+
- 'wolfssl/wolfcrypt/port/nuvoton/**'
29+
- '.github/workflows/nuvoton-m2354-compile.yml'
30+
pull_request:
31+
types: [opened, synchronize, reopened, ready_for_review]
32+
branches: [ '**' ]
33+
paths:
34+
- 'wolfcrypt/src/**'
35+
- 'wolfssl/wolfcrypt/**'
36+
- '.github/workflows/nuvoton-m2354-compile.yml'
37+
workflow_dispatch:
38+
39+
concurrency:
40+
group: ${{ github.workflow }}-${{ github.ref }}
41+
cancel-in-progress: true
42+
43+
permissions:
44+
contents: read
45+
# END OF COMMON SECTION
46+
47+
env:
48+
# Pinned so a BSP change cannot break a PR that did not touch the port. Bump
49+
# it deliberately.
50+
BSP_REF: 3d423be763edabe1d8b3f27dea363b69e787f8f9
51+
52+
jobs:
53+
compile:
54+
name: ${{ matrix.leg }} (Cortex-M23)
55+
if: ${{ github.event_name != 'pull_request' || github.event.pull_request.draft == false }}
56+
runs-on: ubuntu-24.04
57+
timeout-minutes: 20
58+
strategy:
59+
fail-fast: false
60+
matrix:
61+
include:
62+
- leg: secure
63+
world: WOLFSSL_NUVOTON_SECURE
64+
- leg: nonsecure
65+
world: WOLFSSL_NUVOTON_NSC
66+
steps:
67+
- uses: actions/checkout@v4
68+
name: Checkout wolfSSL
69+
70+
- name: Install the toolchain
71+
run: |
72+
sudo apt-get update
73+
sudo apt-get install -y gcc-arm-none-eabi
74+
75+
- name: Checkout the Nuvoton M2354 BSP
76+
run: |
77+
set -e
78+
# The full repository is around 256 MB and almost none of it is
79+
# needed, so take one commit and only the driver tree.
80+
git clone --filter=blob:none --no-checkout --sparse \
81+
https://github.com/OpenNuvoton/M2354BSP "$GITHUB_WORKSPACE/M2354BSP"
82+
cd "$GITHUB_WORKSPACE/M2354BSP"
83+
git sparse-checkout set \
84+
Library/StdDriver/inc Library/Device Library/CMSIS
85+
git fetch --depth 1 origin "$BSP_REF"
86+
git checkout "$BSP_REF"
87+
88+
- name: Compile the port
89+
run: |
90+
set -e
91+
BSP="$GITHUB_WORKSPACE/M2354BSP"
92+
mkdir -p "$GITHUB_WORKSPACE/cfg"
93+
94+
# Minimal configuration: enough to reach every engine in the port.
95+
# The example in wolfssl-examples carries a realistic one.
96+
cat > "$GITHUB_WORKSPACE/cfg/user_settings.h" <<'EOF'
97+
#ifndef CI_USER_SETTINGS_H
98+
#define CI_USER_SETTINGS_H
99+
#define WOLFSSL_NUVOTON_M2354
100+
#define SINGLE_THREADED
101+
#define NO_FILESYSTEM
102+
#define WOLFSSL_SMALL_STACK
103+
#define WOLFSSL_SHA224
104+
#define WOLFSSL_SHA384
105+
#define WOLFSSL_SHA512
106+
#define HAVE_HASHDRBG
107+
#define HAVE_AES_CBC
108+
#define HAVE_AES_ECB
109+
#define WOLFSSL_AES_DIRECT
110+
#define WOLFSSL_AES_COUNTER
111+
#define HAVE_AESGCM
112+
#define HAVE_ECC
113+
#define HAVE_ECC_DHE
114+
#define HAVE_ECC_SIGN
115+
#define HAVE_ECC_VERIFY
116+
#define HAVE_ECC384
117+
#define WOLFSSL_KEY_GEN
118+
#define TFM_TIMING_RESISTANT
119+
#define ECC_TIMING_RESISTANT
120+
#define WC_RSA_BLINDING
121+
#endif
122+
EOF
123+
124+
CFLAGS="-mcpu=cortex-m23 -mthumb -Os -Wall -Wextra -Werror -c"
125+
CFLAGS="$CFLAGS -I. -I$GITHUB_WORKSPACE/cfg -DWOLFSSL_USER_SETTINGS"
126+
CFLAGS="$CFLAGS -D${{ matrix.world }}"
127+
CFLAGS="$CFLAGS -I$BSP/Library/StdDriver/inc"
128+
CFLAGS="$CFLAGS -I$BSP/Library/Device/Nuvoton/M2354/Include"
129+
CFLAGS="$CFLAGS -I$BSP/Library/CMSIS/Include"
130+
131+
for f in wolfcrypt/src/port/nuvoton/*.c wolfcrypt/src/random.c; do
132+
echo " $f"
133+
# shellcheck disable=SC2086
134+
arm-none-eabi-gcc $CFLAGS -o /dev/null "$f"
135+
done

wolfcrypt/src/asn.c

Lines changed: 19 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -33869,17 +33869,22 @@ int DecodeECC_DSA_Sig_Ex(const byte* sig, word32 sigLen, mp_int* r, mp_int* s,
3386933869
#endif
3387033870

3387133871

33872-
#ifdef WOLFSSL_ASN_TEMPLATE
33873-
#if defined(HAVE_ECC) && defined(WOLFSSL_CUSTOM_CURVES)
33872+
#ifdef WOLFSSL_ASN_HEX_STRING
3387433873
/* Convert data to hex string.
3387533874
*
3387633875
* Big-endian byte array is converted to big-endian hexadecimal string.
3387733876
*
33877+
* Written for the custom ECC curve parameters, which SEC 1 carries as byte
33878+
* arrays and ecc_set_type holds as strings. Hardware ports whose driver takes
33879+
* key material the same way reuse it rather than growing their own copy; see
33880+
* WOLFSSL_ASN_HEX_STRING in asn.h. Base16_Decode() goes the other way and
33881+
* accepts either case, so the two pair up.
33882+
*
3387833883
* @param [in] input Buffer containing data.
3387933884
* @param [in] inSz Size of data in buffer.
33880-
* @param [out] out Buffer to hold hex string.
33885+
* @param [out] out Buffer to hold hex string. Needs inSz * 2 + 1 bytes.
3388133886
*/
33882-
static void DataToHexString(const byte* input, word32 inSz, char* out)
33887+
void wc_DataToHexString(const byte* input, word32 inSz, char* out)
3388333888
{
3388433889
static const char hexChar[] = { '0', '1', '2', '3', '4', '5', '6', '7',
3388533890
'8', '9', 'a', 'b', 'c', 'd', 'e', 'f' };
@@ -33893,7 +33898,10 @@ static void DataToHexString(const byte* input, word32 inSz, char* out)
3389333898
/* NUL terminate string. */
3389433899
out[i * 2] = '\0';
3389533900
}
33901+
#endif /* WOLFSSL_ASN_HEX_STRING */
3389633902

33903+
#ifdef WOLFSSL_ASN_TEMPLATE
33904+
#if defined(HAVE_ECC) && defined(WOLFSSL_CUSTOM_CURVES)
3389733905
#ifndef WOLFSSL_ECC_CURVE_STATIC
3389833906
/* Convert data to hex string and place in allocated buffer.
3389933907
*
@@ -33920,7 +33928,7 @@ static int DataToHexStringAlloc(const byte* input, word32 inSz, char** out,
3392033928
}
3392133929
else {
3392233930
/* Convert to hex string. */
33923-
DataToHexString(input, inSz, str);
33931+
wc_DataToHexString(input, inSz, str);
3392433932
*out = str;
3392533933
}
3392633934

@@ -34123,23 +34131,23 @@ static int EccSpecifiedECDomainDecode(const byte* input, word32 inSz,
3412334131
#else
3412434132
if (ret == 0) {
3412534133
/* Base X-ordinate */
34126-
DataToHexString(base + 1, (word32)curve->size, (char *)curve->Gx);
34134+
wc_DataToHexString(base + 1, (word32)curve->size, (char *)curve->Gx);
3412734135
/* Base Y-ordinate */
34128-
DataToHexString(base + 1 + curve->size, (word32)curve->size, (char *)curve->Gy);
34136+
wc_DataToHexString(base + 1 + curve->size, (word32)curve->size, (char *)curve->Gy);
3412934137
/* Prime */
34130-
DataToHexString(dataASN[ECCSPECIFIEDASN_IDX_PRIME_P].data.ref.data,
34138+
wc_DataToHexString(dataASN[ECCSPECIFIEDASN_IDX_PRIME_P].data.ref.data,
3413134139
dataASN[ECCSPECIFIEDASN_IDX_PRIME_P].data.ref.length,
3413234140
(char *)curve->prime);
3413334141
/* Parameter A */
34134-
DataToHexString(dataASN[ECCSPECIFIEDASN_IDX_PARAM_A].data.ref.data,
34142+
wc_DataToHexString(dataASN[ECCSPECIFIEDASN_IDX_PARAM_A].data.ref.data,
3413534143
dataASN[ECCSPECIFIEDASN_IDX_PARAM_A].data.ref.length,
3413634144
(char *)curve->Af);
3413734145
/* Parameter B */
34138-
DataToHexString(dataASN[ECCSPECIFIEDASN_IDX_PARAM_B].data.ref.data,
34146+
wc_DataToHexString(dataASN[ECCSPECIFIEDASN_IDX_PARAM_B].data.ref.data,
3413934147
dataASN[ECCSPECIFIEDASN_IDX_PARAM_B].data.ref.length,
3414034148
(char *)curve->Bf);
3414134149
/* Order of curve */
34142-
DataToHexString(dataASN[ECCSPECIFIEDASN_IDX_ORDER].data.ref.data,
34150+
wc_DataToHexString(dataASN[ECCSPECIFIEDASN_IDX_ORDER].data.ref.data,
3414334151
dataASN[ECCSPECIFIEDASN_IDX_ORDER].data.ref.length,
3414434152
(char *)curve->order);
3414534153
}

wolfcrypt/src/include.am

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -131,6 +131,15 @@ EXTRA_DIST += wolfcrypt/src/port/ti/ti-aes.c \
131131
wolfcrypt/src/port/silabs/silabs_hash.c \
132132
wolfcrypt/src/port/silabs/silabs_random.c \
133133
wolfcrypt/src/port/silabs/README.md \
134+
wolfcrypt/src/port/nuvoton/nuvoton_hw.h \
135+
wolfcrypt/src/port/nuvoton/nuvoton_hw.c \
136+
wolfcrypt/src/port/nuvoton/nuvoton_cryptocb.c \
137+
wolfcrypt/src/port/nuvoton/nuvoton_cb_rng.c \
138+
wolfcrypt/src/port/nuvoton/nuvoton_cb_hash.c \
139+
wolfcrypt/src/port/nuvoton/nuvoton_cb_cipher.c \
140+
wolfcrypt/src/port/nuvoton/nuvoton_cb_pk.c \
141+
wolfcrypt/src/port/nuvoton/nuvoton_key.c \
142+
wolfcrypt/src/port/nuvoton/README.md \
134143
wolfcrypt/src/port/st/stm32.c \
135144
wolfcrypt/src/port/st/README.md \
136145
wolfcrypt/src/port/st/STM32MP13.md \

0 commit comments

Comments
 (0)