[otbn] Add standalone tests for ECC P-256 operations
Adds some initial tests for the OTBN P-256 lib:
- curve point test
- scalar multiplication test
- ECDSA sign test
- ECDSA verify test
Signed-off-by: Felix Miller <felix.miller@gi-de.com>
diff --git a/sw/otbn/code-snippets/meson.build b/sw/otbn/code-snippets/meson.build
index 091aca3..91179ff 100644
--- a/sw/otbn/code-snippets/meson.build
+++ b/sw/otbn/code-snippets/meson.build
@@ -9,6 +9,9 @@
'modexp': files(
'modexp.s'
),
+ 'p256': files(
+ 'p256.s'
+ ),
'loop': files(
'loop.s',
),
@@ -32,4 +35,20 @@
'err_test': files(
'err_test.s',
),
+ 'p256_curve_point_test': files(
+ 'p256_curve_point_test.s',
+ 'p256.s',
+ ),
+ 'p256_scalar_mult_test': files(
+ 'p256_scalar_mult_test.s',
+ 'p256.s',
+ ),
+ 'p256_ecdsa_sign_test': files(
+ 'p256_ecdsa_sign_test.s',
+ 'p256.s',
+ ),
+ 'p256_ecdsa_verify_test': files(
+ 'p256_ecdsa_verify_test.s',
+ 'p256.s',
+ ),
}
diff --git a/sw/otbn/code-snippets/p256.s b/sw/otbn/code-snippets/p256.s
index 04b67d4..6af0cfd 100644
--- a/sw/otbn/code-snippets/p256.s
+++ b/sw/otbn/code-snippets/p256.s
@@ -7,6 +7,12 @@
* https://chromium.googlesource.com/chromiumos/platform/ec/+/refs/heads/cr50_stab/chip/g/dcrypto/dcrypto_p256.c
*/
+.globl p256init
+.globl p256isoncurve
+.globl p256scalarmult
+.globl p256sign
+.globl p256verify
+
.text
SetupP256PandMuLow:
diff --git a/sw/otbn/code-snippets/p256_curve_point_test.s b/sw/otbn/code-snippets/p256_curve_point_test.s
new file mode 100644
index 0000000..14594ec
--- /dev/null
+++ b/sw/otbn/code-snippets/p256_curve_point_test.s
@@ -0,0 +1,87 @@
+/* Copyright lowRISC contributors. */
+/* Licensed under the Apache License, Version 2.0, see LICENSE for details. */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+/**
+ * Standalone elliptic curve P-256 curve point test
+ *
+ * Uses OTBN ECC P-256 lib to check if a curve point is on the P-256 curve. The
+ * point is on the curve if the R and S return values are identical. The test
+ * uses an example point which is on the curve. The point's coordinates are
+ * contained in the .data section below.
+ *
+ * R and S are copied to the wide registers. See comment at the end of the file
+ * for expected values for the example point.
+ */
+
+.text
+
+curve_point_test:
+ jal x1, p256init
+ jal x1, p256isoncurve
+
+ /* pointer to R */
+ lw x21, 12(x0)
+ /* pointer to S */
+ lw x22, 16(x0)
+
+ /* copy result to wide reg file */
+ li x8, 0
+ bn.lid x8, 0(x21)
+ li x9, 1
+ bn.lid x9, 0(x22)
+
+ ecall
+
+
+.data
+
+/* pointer to k (dptr_k) */
+.word 0x00000020
+
+/* pointer to rnd (dptr_rnd) */
+.word 0x00000040
+
+/* pointer to msg (dptr_msg) */
+.word 0x00000060
+
+/* pointer to R (dptr_r) */
+.word 0x00000080
+
+/* pointer to S (dptr_s) */
+.word 0x000000a0
+
+/* pointer to X (dptr_x) */
+.word 0x000000c0
+
+/* pointer to Y (dptr_y) */
+.word 0x000000e0
+
+/* pointer to D (dptr_d) */
+.word 0x00000100
+
+/* example curve point x-coordinate */
+.skip 160
+.word 0xbfa8c334
+.word 0x9773b7b3
+.word 0xf36b0689
+.word 0x6ec0c0b2
+.word 0xdb6c8bf3
+.word 0x1628ce58
+.word 0xfacdc546
+.word 0xb5511a6a
+
+/* example curve point y-coordinate */
+.word 0x9e008c2e
+.word 0xa8707058
+.word 0xab9c6924
+.word 0x7f7a11d0
+.word 0xb53a17fa
+.word 0x43dd09ea
+.word 0x1f31c143
+.word 0x42a1c697
+
+/* Expected values wide register file (w0=R, w1=S):
+w0 = 0xb103b614b389c6b8e1a08330a6ce0b9c4b3726ec0bf61f6bdd66af03a4af5660
+w1 = 0xb103b614b389c6b8e1a08330a6ce0b9c4b3726ec0bf61f6bdd66af03a4af5660
+*/
diff --git a/sw/otbn/code-snippets/p256_ecdsa_sign_test.s b/sw/otbn/code-snippets/p256_ecdsa_sign_test.s
new file mode 100644
index 0000000..16c1514
--- /dev/null
+++ b/sw/otbn/code-snippets/p256_ecdsa_sign_test.s
@@ -0,0 +1,99 @@
+/* Copyright lowRISC contributors. */
+/* Licensed under the Apache License, Version 2.0, see LICENSE for details. */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+/**
+ * Standalone elliptic curve P-256 ECDSA sign test
+ *
+ * Uses OTBN ECC P-256 lib to perform an ECDSA signing operation.
+ * An example message digest, the private signing key and a random value k are
+ * provided in the .data section below. Note that this test does not yet use
+ * OTBN's entropy interface as a source for the random value in the ECDSA
+ * operation.
+ *
+ * Resulting R and S of the signature are copied to the wide registers. See
+ * comment at the end of the file for expected values.
+ */
+
+.text
+
+ecdsa_sign_test:
+ jal x1, p256init
+ jal x1, p256sign
+
+ /* pointer to R */
+ lw x21, 12(x0)
+ /* pointer to S */
+ lw x22, 16(x0)
+
+ /* copy result to wide reg file */
+ li x8, 0
+ bn.lid x8, 0(x21)
+ li x9, 1
+ bn.lid x9, 0(x22)
+
+ ecall
+
+
+.data
+
+/* pointer to k (dptr_k) */
+.word 0x00000020
+
+/* pointer to rnd (dptr_rnd) */
+.word 0x00000040
+
+/* pointer to msg (dptr_msg) */
+.word 0x00000060
+
+/* pointer to R (dptr_r) */
+.word 0x00000080
+
+/* pointer to S (dptr_s) */
+.word 0x000000a0
+
+/* pointer to X (dptr_x) */
+.word 0x000000c0
+
+/* pointer to Y (dptr_y) */
+.word 0x000000e0
+
+/* pointer to D (dptr_d) */
+.word 0x00000100
+
+/* example random scalar k */
+.word 0xfe6d1071
+.word 0x21d0a016
+.word 0xb0b2c781
+.word 0x9590ef5d
+.word 0x3fdfa379
+.word 0x1b76ebe8
+.word 0x74210263
+.word 0x1420fc41
+
+/* message digest */
+.skip 32
+.word 0x4456fd21
+.word 0x400bdd7d
+.word 0xb54d7452
+.word 0x17d015f1
+.word 0x90d4d90b
+.word 0xb028ad8a
+.word 0x6ce90fef
+.word 0x06d71207
+
+/* private key d */
+.skip 128
+.word 0xc7df1a56
+.word 0xfbd94efe
+.word 0xaa847f52
+.word 0x2d869bf4
+.word 0x543b963b
+.word 0xe5f2cbee
+.word 0x9144233d
+.word 0xc0fbe256
+
+/* Expected values wide register file (w0=R, w1=S):
+w0 = 0x815215ad7dd27f336b35843cbe064de299504edd0c7d87dd1147ea5680a9674a
+w1 = 0xa3991e01c444042086e30cd999e589ad4dad9404e90a6d17d0b1051ec93fd605
+*/
diff --git a/sw/otbn/code-snippets/p256_ecdsa_verify_test.s b/sw/otbn/code-snippets/p256_ecdsa_verify_test.s
new file mode 100644
index 0000000..edcefbf
--- /dev/null
+++ b/sw/otbn/code-snippets/p256_ecdsa_verify_test.s
@@ -0,0 +1,117 @@
+/* Copyright lowRISC contributors. */
+/* Licensed under the Apache License, Version 2.0, see LICENSE for details. */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+/**
+ * Standalone elliptic curve P-256 ECDSA signature verification test
+ *
+ * Uses OTBN ECC P-256 lib to perform an ECDSA signature verification.
+ * Coordinates of the public key, the message digest and R and S of the
+ * signature are provided in the .data section below.
+ *
+ * Signature verification was successful, if the return values in the rnd and R
+ * location are identical. The return values are copied to wide registers. See
+ * comment at the end of the file for expected values for this example.
+ */
+
+.text
+
+ecdsa_verify_test:
+ jal x1, p256init
+ jal x1, p256verify
+
+ /* pointer to rnd */
+ lw x21, 4(x0)
+ /* pointer to R */
+ lw x22, 12(x0)
+
+ /* copy result to wide reg file */
+ li x8, 0
+ bn.lid x8, 0(x21)
+ li x9, 1
+ bn.lid x9, 0(x22)
+
+ ecall
+
+
+.data
+
+/* pointer to k (dptr_k) */
+.word 0x00000020
+
+/* pointer to rnd (dptr_rnd) */
+.word 0x00000040
+
+/* pointer to msg (dptr_msg) */
+.word 0x00000060
+
+/* pointer to R (dptr_r) */
+.word 0x00000080
+
+/* pointer to S (dptr_s) */
+.word 0x000000a0
+
+/* pointer to X (dptr_x) */
+.word 0x000000c0
+
+/* pointer to Y (dptr_y) */
+.word 0x000000e0
+
+/* pointer to D (dptr_d) */
+.word 0x00000100
+
+/* message digest */
+.skip 64
+.word 0x4456fd21
+.word 0x400bdd7d
+.word 0xb54d7452
+.word 0x17d015f1
+.word 0x90d4d90b
+.word 0xb028ad8a
+.word 0x6ce90fef
+.word 0x06d71207
+
+/* signature R */
+.word 0x80a9674a
+.word 0x1147ea56
+.word 0x0c7d87dd
+.word 0x99504edd
+.word 0xbe064de2
+.word 0x6b35843c
+.word 0x7dd27f33
+.word 0x815215ad
+
+/* signature S */
+.word 0xc93fd605
+.word 0xd0b1051e
+.word 0xe90a6d17
+.word 0x4dad9404
+.word 0x99e589ad
+.word 0x86e30cd9
+.word 0xc4440420
+.word 0xa3991e01
+
+/* public key x-coordinate */
+.word 0xbfa8c334
+.word 0x9773b7b3
+.word 0xf36b0689
+.word 0x6ec0c0b2
+.word 0xdb6c8bf3
+.word 0x1628ce58
+.word 0xfacdc546
+.word 0xb5511a6a
+
+/* public key y-coordinate */
+.word 0x9e008c2e
+.word 0xa8707058
+.word 0xab9c6924
+.word 0x7f7a11d0
+.word 0xb53a17fa
+.word 0x43dd09ea
+.word 0x1f31c143
+.word 0x42a1c697
+
+/* Expected values wide register file (w0=rnd, w1=R):
+w0 = 0x815215ad7dd27f336b35843cbe064de299504edd0c7d87dd1147ea5680a9674a
+w1 = 0x815215ad7dd27f336b35843cbe064de299504edd0c7d87dd1147ea5680a9674a
+*/
diff --git a/sw/otbn/code-snippets/p256_scalar_mult_test.s b/sw/otbn/code-snippets/p256_scalar_mult_test.s
new file mode 100644
index 0000000..91bc987
--- /dev/null
+++ b/sw/otbn/code-snippets/p256_scalar_mult_test.s
@@ -0,0 +1,96 @@
+/* Copyright lowRISC contributors. */
+/* Licensed under the Apache License, Version 2.0, see LICENSE for details. */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+/**
+ * Standalone elliptic curve P-256 scalar multiplication test
+ *
+ * Uses OTBN ECC P-256 lib to perform a scalar multiplication with a valid
+ * example curve point and an example scalar. Both scalar and coordinates of
+ * the curve point are contained in the .data section below.
+ *
+ * x and y cordinates of the resulting curve points are copied to wide
+ * registers. See comment at the end of the file for expected values.
+ */
+
+.text
+
+scalar_mult_test:
+ jal x1, p256init
+ jal x1, p256scalarmult
+
+ /* pointer to x-coordinate */
+ lw x21, 20(x0)
+ /* pointer to y-coordinate */
+ lw x22, 24(x0)
+
+ /* copy result to wide reg file */
+ li x8, 0
+ bn.lid x8, 0(x21)
+ li x9, 1
+ bn.lid x9, 0(x22)
+
+ ecall
+
+
+.data
+
+/* pointer to k (dptr_k) */
+.word 0x00000020
+
+/* pointer to rnd (dptr_rnd) */
+.word 0x00000040
+
+/* pointer to msg (dptr_msg) */
+.word 0x00000060
+
+/* pointer to R (dptr_r) */
+.word 0x00000080
+
+/* pointer to S (dptr_s) */
+.word 0x000000a0
+
+/* pointer to X (dptr_x) */
+.word 0x000000c0
+
+/* pointer to Y (dptr_y) */
+.word 0x000000e0
+
+/* pointer to D (dptr_d) */
+.word 0x00000100
+
+/* example scalar */
+.word 0xfe6d1071
+.word 0x21d0a016
+.word 0xb0b2c781
+.word 0x9590ef5d
+.word 0x3fdfa379
+.word 0x1b76ebe8
+.word 0x74210263
+.word 0x1420fc41
+
+/* example curve point x-coordinate */
+.skip 128
+.word 0xbfa8c334
+.word 0x9773b7b3
+.word 0xf36b0689
+.word 0x6ec0c0b2
+.word 0xdb6c8bf3
+.word 0x1628ce58
+.word 0xfacdc546
+.word 0xb5511a6a
+
+/* example curve point y-coordinate */
+.word 0x9e008c2e
+.word 0xa8707058
+.word 0xab9c6924
+.word 0x7f7a11d0
+.word 0xb53a17fa
+.word 0x43dd09ea
+.word 0x1f31c143
+.word 0x42a1c697
+
+/* Expected values wide register file (w0=X, w1=Y):
+w0 = 0x5f33d746a326640a739a9490ec15c10372869f3de675b2e85742271d18c9eb82
+w1 = 0xb5ebbd1e4ac99c9e3d70a862e41fe23ace6ab34f7ac9f99a4c403defb76c462d
+*/
diff --git a/sw/otbn/code-snippets/rules.mk b/sw/otbn/code-snippets/rules.mk
index 40d5d9a..b7533e6 100644
--- a/sw/otbn/code-snippets/rules.mk
+++ b/sw/otbn/code-snippets/rules.mk
@@ -94,3 +94,27 @@
$(otbn-code-snippets-obj-dir)/modexp.o
$(otbn-code-snippets-bin-dir)/rsa_1024_enc_test.elf: \
otbn-libs += $(otbn-code-snippets-obj-dir)/modexp.o
+
+# p256 curve point test depends on p256init, p256isoncurve, defined in p256.s
+$(otbn-code-snippets-bin-dir)/p256_curve_point_test.elf: \
+ $(otbn-code-snippets-obj-dir)/p256.o
+$(otbn-code-snippets-bin-dir)/p256_curve_point_test.elf: \
+ otbn-libs += $(otbn-code-snippets-obj-dir)/p256.o
+
+# p256 scalar mult test depends on p256init, p256scalarmult, defined in p256.s
+$(otbn-code-snippets-bin-dir)/p256_scalar_mult_test.elf: \
+ $(otbn-code-snippets-obj-dir)/p256.o
+$(otbn-code-snippets-bin-dir)/p256_scalar_mult_test.elf: \
+ otbn-libs += $(otbn-code-snippets-obj-dir)/p256.o
+
+# p256 ECDSA sign test depends on p256init, p256sign, defined in p256.s
+$(otbn-code-snippets-bin-dir)/p256_ecdsa_sign_test.elf: \
+ $(otbn-code-snippets-obj-dir)/p256.o
+$(otbn-code-snippets-bin-dir)/p256_ecdsa_sign_test.elf: \
+ otbn-libs += $(otbn-code-snippets-obj-dir)/p256.o
+
+# p256 ECDSA verify test depends on p256init, p256verify, defined in p256.s
+$(otbn-code-snippets-bin-dir)/p256_ecdsa_verify_test.elf: \
+ $(otbn-code-snippets-obj-dir)/p256.o
+$(otbn-code-snippets-bin-dir)/p256_ecdsa_verify_test.elf: \
+ otbn-libs += $(otbn-code-snippets-obj-dir)/p256.o