Skip to content

Commit 0e860d2

Browse files
committed
rangeproof: add a bunch more testing
Add two new fixed rangeproof vectors; check that various extracted values are correct; add a test for creating and verifying single-value proofs.
1 parent 6da00ec commit 0e860d2

File tree

1 file changed

+261
-8
lines changed

1 file changed

+261
-8
lines changed

src/modules/rangeproof/tests_impl.h

+261-8
Original file line numberDiff line numberDiff line change
@@ -545,8 +545,95 @@ static void test_rangeproof(void) {
545545
}
546546
}
547547

548+
static void test_single_value_proof(uint64_t val) {
549+
unsigned char proof[5000];
550+
secp256k1_pedersen_commitment commit;
551+
unsigned char blind[32];
552+
unsigned char blind_out[32];
553+
unsigned char nonce[32];
554+
const unsigned char message[1] = " "; /* no message will fit into a single-value proof */
555+
unsigned char message_out[sizeof(proof)] = { 0 };
556+
size_t plen = sizeof(proof);
557+
size_t min_val_out = 0;
558+
size_t max_val_out = 0;
559+
size_t val_out = 0;
560+
size_t m_len_out = 0;
561+
562+
secp256k1_testrand256(blind);
563+
secp256k1_testrand256(nonce);
564+
CHECK(secp256k1_pedersen_commit(ctx, &commit, blind, val, secp256k1_generator_h));
565+
566+
CHECK(secp256k1_rangeproof_sign(
567+
ctx,
568+
proof, &plen,
569+
val, /* min_val */
570+
&commit, blind, nonce,
571+
-1, /* exp: -1 is magic value to indicate a single-value proof */
572+
0, /* min_bits */
573+
val, /* val */
574+
message, sizeof(message), /* Will cause this to fail */
575+
NULL, 0,
576+
secp256k1_generator_h
577+
) == 0);
578+
579+
plen = sizeof(proof);
580+
CHECK(secp256k1_rangeproof_sign(
581+
ctx,
582+
proof, &plen,
583+
val, /* min_val */
584+
&commit, blind, nonce,
585+
-1, /* exp: -1 is magic value to indicate a single-value proof */
586+
0, /* min_bits */
587+
val, /* val */
588+
NULL, 0,
589+
NULL, 0,
590+
secp256k1_generator_h
591+
) == 1);
592+
593+
/* Different proof sizes are unfortunate but is caused by `min_value` of
594+
* zero being special-cased and encoded more efficiently. */
595+
if (val == 0) {
596+
CHECK(plen == 65);
597+
} else {
598+
CHECK(plen == 73);
599+
}
600+
601+
CHECK(secp256k1_rangeproof_verify(
602+
ctx,
603+
&min_val_out, &max_val_out,
604+
&commit,
605+
proof, plen,
606+
NULL, 0,
607+
secp256k1_generator_h
608+
) == 1);
609+
CHECK(min_val_out == val);
610+
CHECK(max_val_out == val);
611+
612+
memset(message_out, 0, sizeof(message_out));
613+
m_len_out = sizeof(message_out);
614+
CHECK(secp256k1_rangeproof_rewind(
615+
ctx,
616+
blind_out, &val_out,
617+
message_out, &m_len_out,
618+
nonce,
619+
&min_val_out, &max_val_out,
620+
&commit,
621+
proof, plen,
622+
NULL, 0,
623+
secp256k1_generator_h
624+
));
625+
CHECK(val_out == val);
626+
CHECK(min_val_out == val);
627+
CHECK(max_val_out == val);
628+
CHECK(m_len_out == 0);
629+
CHECK(memcmp(blind, blind_out, 32) == 0);
630+
for (m_len_out = 0; m_len_out < sizeof(message_out); m_len_out++) {
631+
CHECK(message_out[m_len_out] == 0);
632+
}
633+
}
634+
548635
#define MAX_N_GENS 30
549-
void test_multiple_generators(void) {
636+
static void test_multiple_generators(void) {
550637
const size_t n_inputs = (secp256k1_testrand32() % (MAX_N_GENS / 2)) + 1;
551638
const size_t n_outputs = (secp256k1_testrand32() % (MAX_N_GENS / 2)) + 1;
552639
const size_t n_generators = n_inputs + n_outputs;
@@ -608,7 +695,18 @@ void test_multiple_generators(void) {
608695
}
609696

610697
void test_rangeproof_fixed_vectors(void) {
611-
const unsigned char vector_1[] = {
698+
size_t i;
699+
unsigned char blind[32];
700+
uint64_t value;
701+
uint64_t min_value;
702+
uint64_t max_value;
703+
secp256k1_pedersen_commitment pc;
704+
unsigned char message[4000] = {0};
705+
size_t m_len = sizeof(message);
706+
707+
/* Vector 1: no message */
708+
{
709+
static const unsigned char vector_1[] = {
612710
0x62, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x56, 0x02, 0x2a, 0x5c, 0x42, 0x0e, 0x1d,
613711
0x51, 0xe1, 0xb7, 0xf3, 0x69, 0x04, 0xb5, 0xbb, 0x9b, 0x41, 0x66, 0x14, 0xf3, 0x64, 0x42, 0x26,
614712
0xe3, 0xa7, 0x6a, 0x06, 0xbb, 0xa8, 0x5a, 0x49, 0x6f, 0x19, 0x76, 0xfb, 0xe5, 0x75, 0x77, 0x88,
@@ -651,25 +749,175 @@ void test_rangeproof_fixed_vectors(void) {
651749
0xa6, 0x45, 0xf6, 0xce, 0xcf, 0x48, 0xf6, 0x1e, 0x3d, 0xd2, 0xcf, 0xcb, 0x3a, 0xcd, 0xbb, 0x92,
652750
0x29, 0x24, 0x16, 0x7f, 0x8a, 0xa8, 0x5c, 0x0c, 0x45, 0x71, 0x33
653751
};
654-
const unsigned char commit_1[] = {
752+
static const unsigned char commit_1[] = {
655753
0x08,
656754
0xf5, 0x1e, 0x0d, 0xc5, 0x86, 0x78, 0x51, 0xa9, 0x00, 0x00, 0xef, 0x4d, 0xe2, 0x94, 0x60, 0x89,
657755
0x83, 0x04, 0xb4, 0x0e, 0x90, 0x10, 0x05, 0x1c, 0x7f, 0xd7, 0x33, 0x92, 0x1f, 0xe7, 0x74, 0x59
658756
};
659-
uint64_t min_value_1;
660-
uint64_t max_value_1;
661-
secp256k1_pedersen_commitment pc;
757+
static const unsigned char blind_1[] = {
758+
0x98, 0x44, 0xfc, 0x7a, 0x64, 0xa9, 0xca, 0xdf, 0xf3, 0x2f, 0x9f, 0x02, 0xba, 0x46, 0xc7, 0xd9,
759+
0x77, 0x47, 0xa4, 0xd3, 0x53, 0x17, 0xc6, 0x44, 0x30, 0x73, 0x84, 0xeb, 0x1f, 0xbe, 0xa1, 0xfb
760+
};
662761

663762
CHECK(secp256k1_pedersen_commitment_parse(ctx, &pc, commit_1));
664-
665763
CHECK(secp256k1_rangeproof_verify(
666764
ctx,
667-
&min_value_1, &max_value_1,
765+
&min_value, &max_value,
668766
&pc,
669767
vector_1, sizeof(vector_1),
670768
NULL, 0,
671769
secp256k1_generator_h
672770
));
771+
CHECK(min_value == 86);
772+
CHECK(max_value == 25586);
773+
774+
CHECK(secp256k1_rangeproof_rewind(
775+
ctx,
776+
blind, &value,
777+
message, &m_len,
778+
pc.data,
779+
&min_value, &max_value,
780+
&pc,
781+
vector_1, sizeof(vector_1),
782+
NULL, 0,
783+
secp256k1_generator_h
784+
));
785+
786+
CHECK(memcmp(blind, blind_1, 32) == 0);
787+
CHECK(value == 86);
788+
CHECK(min_value == 86);
789+
CHECK(max_value == 25586);
790+
CHECK(m_len == 448); /* length of the sidechannel in the proof */
791+
for (i = 0; i < m_len; i++) {
792+
/* No message encoded in this vector */
793+
CHECK(message[i] == 0);
794+
}
795+
}
796+
797+
/* Vector 2: embedded message */
798+
{
799+
static const unsigned char vector_2[] = {
800+
0x40, 0x03, 0x00, 0x90, 0x1a, 0x61, 0x64, 0xbb, 0x85, 0x1a, 0x78, 0x35, 0x1e, 0xe0, 0xd5, 0x96,
801+
0x71, 0x0f, 0x18, 0x8e, 0xf3, 0x33, 0xf0, 0x75, 0xfe, 0xd6, 0xc6, 0x11, 0x6b, 0x42, 0x89, 0xea,
802+
0xa2, 0x0c, 0x89, 0x25, 0x37, 0x81, 0x10, 0xf9, 0xf0, 0x9b, 0xda, 0x68, 0x2a, 0xd9, 0x2e, 0x0c,
803+
0x45, 0x17, 0x54, 0x6d, 0x02, 0xd2, 0x21, 0x5d, 0xbc, 0x10, 0xf8, 0x8f, 0xf1, 0x92, 0x40, 0xa9,
804+
0xc7, 0x24, 0x00, 0x1b, 0xc8, 0x75, 0x0f, 0xf6, 0x8f, 0x93, 0x8b, 0x78, 0x62, 0x73, 0x3c, 0x86,
805+
0x4b, 0x61, 0x7c, 0x0f, 0xc6, 0x41, 0xc9, 0xb3, 0xc1, 0x30, 0x7f, 0xd4, 0xee, 0x9f, 0x37, 0x08,
806+
0x9b, 0x64, 0x23, 0xd5, 0xe6, 0x1a, 0x03, 0x54, 0x74, 0x9b, 0x0b, 0xae, 0x6f, 0x2b, 0x1e, 0xf5,
807+
0x40, 0x44, 0xaa, 0x12, 0xe8, 0xbd, 0xe0, 0xa6, 0x85, 0x89, 0xf1, 0xa9, 0xd0, 0x3f, 0x2e, 0xc6,
808+
0x1f, 0x11, 0xf5, 0x44, 0x69, 0x99, 0x31, 0x10, 0x2e, 0x64, 0xc6, 0x44, 0xdb, 0x47, 0x06, 0x6d,
809+
0xd5, 0xf2, 0x8d, 0x19, 0x00, 0x39, 0xb8, 0xca, 0xda, 0x5c, 0x1d, 0x83, 0xbd, 0xa3, 0x6d, 0xbf,
810+
0x97, 0xdd, 0x83, 0x86, 0xc9, 0x56, 0xe2, 0xbb, 0x37, 0x4b, 0x2d, 0xb5, 0x9d, 0xf2, 0x7a, 0x6a,
811+
0x25, 0x47, 0xfa, 0x03, 0x05, 0xc5, 0xda, 0x73, 0xe1, 0x96, 0x15, 0x21, 0x23, 0xe5, 0xef, 0x55,
812+
0x36, 0xdd, 0xf1, 0xb1, 0x3f, 0x33, 0x1a, 0x91, 0x6c, 0x73, 0x64, 0xd3, 0x88, 0xe7, 0xc6, 0xc9,
813+
0x04, 0x29, 0xae, 0x55, 0x27, 0xa0, 0x80, 0x60, 0xaf, 0x0c, 0x09, 0x2f, 0xc8, 0x1b, 0xe6, 0x16,
814+
0x9e, 0xed, 0x29, 0xc7, 0x93, 0xce, 0xc7, 0x0d, 0xdf, 0x1f, 0x28, 0xba, 0xf3, 0x38, 0xc3, 0xaa,
815+
0x99, 0xd9, 0x21, 0x41, 0xb8, 0x10, 0xa5, 0x48, 0x37, 0xec, 0x60, 0xda, 0x64, 0x5a, 0x73, 0x55,
816+
0xd7, 0xff, 0x23, 0xfa, 0xf6, 0xc6, 0xf4, 0xe2, 0xca, 0x99, 0x2f, 0x30, 0x36, 0x48, 0x73, 0x8b,
817+
0x57, 0xa6, 0x62, 0x12, 0xa3, 0xe7, 0x5c, 0xa8, 0xd1, 0xe6, 0x85, 0x05, 0x59, 0xfe, 0x2b, 0x44,
818+
0xe4, 0x73, 0x1c, 0xc3, 0x56, 0x32, 0x07, 0x65, 0x4a, 0x58, 0xaf, 0x2b, 0x3f, 0x36, 0xca, 0xb4,
819+
0x1d, 0x5c, 0x2a, 0x46, 0x1f, 0xf7, 0x63, 0x59, 0x4f, 0x2b, 0xd0, 0xf6, 0xfc, 0xcf, 0x04, 0x09,
820+
0xb7, 0x65, 0x1b
821+
};
822+
static const unsigned char commit_2[] = {
823+
0x09,
824+
0x25, 0xa4, 0xbd, 0xc4, 0x57, 0x69, 0xeb, 0x4f, 0x34, 0x0f, 0xea, 0xb8, 0xe4, 0x72, 0x04, 0x54,
825+
0x06, 0xe5, 0xd6, 0x85, 0x15, 0x42, 0xea, 0x6e, 0x1d, 0x11, 0x11, 0x9c, 0x56, 0xf8, 0x10, 0x45
826+
};
827+
static const unsigned char blind_2[] = {
828+
0xdc, 0x79, 0x07, 0x89, 0x2d, 0xc4, 0xe3, 0x76, 0xf9, 0x13, 0x38, 0xd6, 0x4b, 0x46, 0xed, 0x9d,
829+
0x9b, 0xf6, 0x70, 0x3d, 0x04, 0xcf, 0x96, 0x8c, 0xfd, 0xb5, 0xff, 0x0a, 0x06, 0xc7, 0x08, 0x8b
830+
};
831+
static const unsigned char message_2[] = "When I see my own likeness in the depths of someone else's consciousness, I always experience a moment of panic.";
832+
833+
CHECK(secp256k1_pedersen_commitment_parse(ctx, &pc, commit_2));
834+
CHECK(secp256k1_rangeproof_verify(
835+
ctx,
836+
&min_value, &max_value,
837+
&pc,
838+
vector_2, sizeof(vector_2),
839+
NULL, 0,
840+
secp256k1_generator_h
841+
));
842+
CHECK(min_value == 0);
843+
CHECK(max_value == 15);
844+
845+
CHECK(secp256k1_rangeproof_rewind(
846+
ctx,
847+
blind, &value,
848+
message, &m_len,
849+
pc.data,
850+
&min_value, &max_value,
851+
&pc,
852+
vector_2, sizeof(vector_2),
853+
NULL, 0,
854+
secp256k1_generator_h
855+
));
856+
857+
CHECK(memcmp(blind, blind_2, 32) == 0);
858+
CHECK(value == 11);
859+
CHECK(min_value == 0);
860+
CHECK(max_value == 15);
861+
CHECK(m_len == 192); /* length of the sidechannel in the proof */
862+
CHECK(memcmp(message, message_2, sizeof(message_2)) == 0);
863+
for (i = sizeof(message_2); i < m_len; i++) {
864+
/* No message encoded in this vector */
865+
CHECK(message[i] == 0);
866+
}
867+
}
868+
869+
/* Vector 3: single-value proof of UINT64_MAX */
870+
{
871+
static const unsigned char vector_3[] = {
872+
0x20, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xdc, 0x7d, 0x0b, 0x79, 0x0e, 0xaf, 0x41,
873+
0xa5, 0x8e, 0x9b, 0x0c, 0x5b, 0xa3, 0xee, 0x7d, 0xfd, 0x3d, 0x6b, 0xf3, 0xac, 0x04, 0x8a, 0x43,
874+
0x75, 0xb0, 0xb7, 0x0e, 0x92, 0xd7, 0xdf, 0xf0, 0x76, 0xc4, 0xa5, 0xb6, 0x2f, 0xf1, 0xb5, 0xfb,
875+
0xb4, 0xb6, 0x29, 0xea, 0x34, 0x9b, 0x16, 0x30, 0x0d, 0x06, 0xf1, 0xb4, 0x3f, 0x0d, 0x73, 0x59,
876+
0x75, 0xbf, 0x5d, 0x19, 0x59, 0xef, 0x11, 0xf0, 0xbf
877+
};
878+
static const unsigned char commit_3[] = {
879+
0x08,
880+
0xc7, 0xea, 0x40, 0x7d, 0x26, 0x38, 0xa2, 0x99, 0xb9, 0x40, 0x22, 0x78, 0x17, 0x57, 0x65, 0xb3,
881+
0x36, 0x82, 0x18, 0x42, 0xc5, 0x57, 0x04, 0x5e, 0x58, 0x5e, 0xf6, 0x40, 0x8b, 0x24, 0x73, 0x10
882+
};
883+
static const unsigned char nonce_3[] = {
884+
0x84, 0x50, 0x94, 0x69, 0xa3, 0x4b, 0x6c, 0x62, 0x1a, 0xc7, 0xe2, 0x0e, 0x07, 0x9a, 0x6f, 0x85,
885+
0x5f, 0x26, 0x50, 0xcd, 0x88, 0x5a, 0x9f, 0xaa, 0x23, 0x5e, 0x0a, 0xe0, 0x7e, 0xc5, 0xe9, 0xf1
886+
};
887+
static const unsigned char blind_3[] = {
888+
0x68, 0x89, 0x47, 0x8c, 0x77, 0xec, 0xcc, 0x2b, 0x65, 0x01, 0x78, 0x6b, 0x06, 0x8b, 0x38, 0x94,
889+
0xc0, 0x6b, 0x9b, 0x4c, 0x02, 0xa6, 0xc8, 0xf6, 0xc0, 0x34, 0xea, 0x35, 0x57, 0xf4, 0xe1, 0x37
890+
};
891+
892+
CHECK(secp256k1_pedersen_commitment_parse(ctx, &pc, commit_3));
893+
CHECK(secp256k1_rangeproof_verify(
894+
ctx,
895+
&min_value, &max_value,
896+
&pc,
897+
vector_3, sizeof(vector_3),
898+
NULL, 0,
899+
secp256k1_generator_h
900+
));
901+
CHECK(min_value == UINT64_MAX);
902+
CHECK(max_value == UINT64_MAX);
903+
904+
CHECK(secp256k1_rangeproof_rewind(
905+
ctx,
906+
blind, &value,
907+
message, &m_len,
908+
nonce_3,
909+
&min_value, &max_value,
910+
&pc,
911+
vector_3, sizeof(vector_3),
912+
NULL, 0,
913+
secp256k1_generator_h
914+
));
915+
CHECK(memcmp(blind, blind_3, 32) == 0);
916+
CHECK(value == UINT64_MAX);
917+
CHECK(min_value == UINT64_MAX);
918+
CHECK(max_value == UINT64_MAX);
919+
CHECK(m_len == 0);
920+
}
673921
}
674922

675923
void test_pedersen_commitment_fixed_vector(void) {
@@ -694,6 +942,11 @@ void test_pedersen_commitment_fixed_vector(void) {
694942
void run_rangeproof_tests(void) {
695943
int i;
696944
test_api();
945+
946+
test_single_value_proof(0);
947+
test_single_value_proof(12345678);
948+
test_single_value_proof(UINT64_MAX);
949+
697950
test_rangeproof_fixed_vectors();
698951
test_pedersen_commitment_fixed_vector();
699952
for (i = 0; i < count / 2 + 1; i++) {

0 commit comments

Comments
 (0)