20 #include <gtest/gtest.h>
29 #include "../bn/internal.h"
30 #include "../../internal.h"
31 #include "../../test/abi_test.h"
32 #include "../../test/file_test.h"
33 #include "../../test/test_util.h"
39 #if !defined(OPENSSL_NO_ASM) && defined(OPENSSL_X86_64) && \
40 !defined(OPENSSL_SMALL) && !defined(BORINGSSL_SHARED_LIBRARY)
42 TEST(P256_X86_64Test, SelectW5) {
44 alignas(64) P256_POINT
table[16];
45 for (
size_t i = 0;
i < 16;
i++) {
51 for (
int i = 0;
i <= 16;
i++) {
62 EXPECT_EQ(
Bytes(
reinterpret_cast<const char *
>(&expected),
sizeof(expected)),
63 Bytes(
reinterpret_cast<const char *
>(&val),
sizeof(val)));
72 TEST(P256_X86_64Test, SelectW7) {
74 alignas(64) P256_POINT_AFFINE
table[64];
75 for (
size_t i = 0;
i < 64;
i++) {
80 for (
int i = 0;
i <= 64;
i++) {
81 P256_POINT_AFFINE val;
84 P256_POINT_AFFINE expected;
91 EXPECT_EQ(
Bytes(
reinterpret_cast<const char *
>(&expected),
sizeof(expected)),
92 Bytes(
reinterpret_cast<const char *
>(&val),
sizeof(val)));
97 P256_POINT_AFFINE val;
101 TEST(P256_X86_64Test, BEEU) {
107 bssl::UniquePtr<EC_GROUP>
group(
111 BN_ULONG order_words[P256_LIMBS];
115 BN_ULONG
in[P256_LIMBS],
out[P256_LIMBS];
126 static const BN_ULONG kOneMont[P256_LIMBS] = {
127 TOBN(0xc46353d, 0x039cdaaf),
128 TOBN(0x43190552, 0x58e8617b),
133 for (BN_ULONG
i = 1;
i < 2000;
i++) {
142 in[1] =
in[2] =
in[3] = 0;
168 static bool GetFieldElement(
FileTest *t, BN_ULONG
out[P256_LIMBS],
170 std::vector<uint8_t>
bytes;
175 if (
bytes.size() != BN_BYTES * P256_LIMBS) {
183 for (
size_t i = 0;
i <
bytes.size();
i++) {
184 out[P256_LIMBS - 1 - (
i / BN_BYTES)] <<= 8;
185 out[P256_LIMBS - 1 - (
i / BN_BYTES)] |=
bytes[
i];
191 static std::string FieldElementToString(
const BN_ULONG
a[P256_LIMBS]) {
193 for (
size_t i = P256_LIMBS-1;
i < P256_LIMBS;
i--) {
194 char buf[2 * BN_BYTES + 1];
202 const char *expected_expr,
const char *actual_expr,
203 const BN_ULONG expected[P256_LIMBS],
const BN_ULONG actual[P256_LIMBS]) {
204 if (
OPENSSL_memcmp(expected, actual,
sizeof(BN_ULONG) * P256_LIMBS) == 0) {
209 <<
"Expected: " << FieldElementToString(expected) <<
" ("
210 << expected_expr <<
")\n"
211 <<
"Actual: " << FieldElementToString(actual) <<
" (" << actual_expr
215 #define EXPECT_FIELD_ELEMENTS_EQUAL(a, b) \
216 EXPECT_PRED_FORMAT2(ExpectFieldElementsEqual, a, b)
218 static bool PointToAffine(P256_POINT_AFFINE *
out,
const P256_POINT *
in) {
220 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
221 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff,
222 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
226 bssl::UniquePtr<BIGNUM>
p(
BN_bin2bn(kP,
sizeof(kP),
nullptr));
227 if (!
x || !
y || !
z || !
p ||
235 if (
BN_cmp(
x.get(),
p.get()) >= 0 ||
248 bssl::UniquePtr<BN_MONT_CTX> mont(
274 const char *expected_expr,
const char *actual_expr,
275 const P256_POINT_AFFINE *expected,
const P256_POINT *actual) {
278 P256_POINT_AFFINE affine;
279 if (!PointToAffine(&affine, actual)) {
281 <<
"Could not convert " << actual_expr <<
" to affine: ("
282 << FieldElementToString(actual->X) <<
", "
283 << FieldElementToString(actual->Y) <<
", "
284 << FieldElementToString(actual->Z) <<
")";
287 if (
OPENSSL_memcmp(expected, &affine,
sizeof(P256_POINT_AFFINE)) != 0) {
289 <<
"Expected: (" << FieldElementToString(expected->X) <<
", "
290 << FieldElementToString(expected->Y) <<
") (" << expected_expr
292 <<
"Actual: (" << FieldElementToString(affine.X) <<
", "
293 << FieldElementToString(affine.Y) <<
") (" << actual_expr <<
")";
299 #define EXPECT_POINTS_EQUAL(a, b) EXPECT_PRED_FORMAT2(ExpectPointsEqual, a, b)
301 static void TestNegate(
FileTest *t) {
302 BN_ULONG
a[P256_LIMBS],
b[P256_LIMBS];
307 BN_ULONG
ret[P256_LIMBS];
309 EXPECT_FIELD_ELEMENTS_EQUAL(
b,
ret);
313 EXPECT_FIELD_ELEMENTS_EQUAL(
b,
ret);
317 EXPECT_FIELD_ELEMENTS_EQUAL(
a,
ret);
321 EXPECT_FIELD_ELEMENTS_EQUAL(
a,
ret);
324 static void TestMulMont(
FileTest *t) {
325 BN_ULONG
a[P256_LIMBS],
b[P256_LIMBS],
result[P256_LIMBS];
330 BN_ULONG
ret[P256_LIMBS];
332 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
335 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
339 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
343 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
347 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
351 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
355 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
359 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
363 static void TestFromMont(
FileTest *t) {
364 BN_ULONG
a[P256_LIMBS],
result[P256_LIMBS];
368 BN_ULONG
ret[P256_LIMBS];
369 ecp_nistz256_from_mont(
ret,
a);
370 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
373 ecp_nistz256_from_mont(
ret,
ret );
374 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
377 static void TestPointAdd(
FileTest *t) {
412 P256_POINT_AFFINE a_affine, b_affine, infinity;
419 if (
OPENSSL_memcmp(&a_affine, &b_affine,
sizeof(a_affine)) != 0 ||
446 static void TestOrdMulMont(
FileTest *t) {
449 BN_ULONG
a[P256_LIMBS],
b[P256_LIMBS],
result[P256_LIMBS];
454 BN_ULONG
ret[P256_LIMBS];
456 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
459 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
463 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
467 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
471 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
475 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
479 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
483 EXPECT_FIELD_ELEMENTS_EQUAL(
result,
ret);
487 TEST(P256_X86_64Test, TestVectors) {
488 return FileTestGTest(
"crypto/fipsmodule/ec/p256-x86_64_tests.txt",
490 if (
t->GetParameter() ==
"Negate") {
492 }
else if (
t->GetParameter() ==
"MulMont") {
494 }
else if (
t->GetParameter() ==
"FromMont") {
496 }
else if (
t->GetParameter() ==
"PointAdd") {
498 }
else if (
t->GetParameter() ==
"OrdMulMont") {
501 FAIL() <<
"Unknown test type:" << t->GetParameter();
507 TEST(P256_X86_64Test, ABI) {
508 BN_ULONG
a[P256_LIMBS],
b[P256_LIMBS],
c[P256_LIMBS];
524 static const P256_POINT kA = {
525 {TOBN(0x60559ac7, 0xc8d0d89d), TOBN(0x6cda3400, 0x545f7e2c),
526 TOBN(0x9b5159e0, 0x323e6048), TOBN(0xcb8dea33, 0x27057fe6)},
527 {TOBN(0x81a2d3bc, 0xc93a2d53), TOBN(0x81f40762, 0xa4f33ccf),
528 TOBN(0xc3c3300a, 0xa8ad50ea), TOBN(0x553de89b, 0x31719830)},
529 {TOBN(0x3fd9470f, 0xb277d181), TOBN(0xc191b8d5, 0x6376f206),
530 TOBN(0xb2572c1f, 0x45eda26f), TOBN(0x4589e40d, 0xf2efc546)},
532 static const P256_POINT kB = {
533 {TOBN(0x3cf0b0aa, 0x92054341), TOBN(0xb949bb80, 0xdab57807),
534 TOBN(0x99de6814, 0xefd21b3e), TOBN(0x32ad5649, 0x7c6c6e83)},
535 {TOBN(0x06afaa02, 0x688399e0), TOBN(0x75f2d096, 0x2a3ce65c),
536 TOBN(0xf6a31eb7, 0xca0244b3), TOBN(0x57b33b7a, 0xcfeee75e)},
537 {TOBN(0x7617d2e0, 0xb4f1d35f), TOBN(0xa922cb10, 0x7f592b65),
538 TOBN(0x12fd6c7a, 0x51a2f474), TOBN(0x337d5e1e, 0xc2fc711b)},
542 {TOBN(0, 0), TOBN(0, 0), TOBN(0, 0), TOBN(0, 0)},
543 {TOBN(0, 0), TOBN(0, 0), TOBN(0, 0), TOBN(0, 0)},
544 {TOBN(0, 0), TOBN(0, 0), TOBN(0, 0), TOBN(0, 0)},
559 static const P256_POINT_AFFINE kC = {
560 {TOBN(0x7e3ad339, 0xfb3fa5f0), TOBN(0x559d669d, 0xe3a047b2),
561 TOBN(0x8883b298, 0x7042e595), TOBN(0xfabada65, 0x7e477f08)},
562 {TOBN(0xd9cfceb8, 0xda1c3e85), TOBN(0x80863761, 0x0ce6d6bc),
563 TOBN(0xa8409d84, 0x66034f02), TOBN(0x05519925, 0x31a68d55)},
566 static const P256_POINT_AFFINE kInfinityAffine = {
567 {TOBN(0, 0), TOBN(0, 0), TOBN(0, 0), TOBN(0, 0)},
568 {TOBN(0, 0), TOBN(0, 0), TOBN(0, 0), TOBN(0, 0)},