Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 5 additions & 3 deletions src/scalar_4x64_impl.h
Original file line number Diff line number Diff line change
Expand Up @@ -41,20 +41,22 @@ SECP256K1_INLINE static void secp256k1_scalar_set_int(secp256k1_scalar *r, unsig
SECP256K1_INLINE static uint32_t secp256k1_scalar_get_bits_limb32(const secp256k1_scalar *a, unsigned int offset, unsigned int count) {
SECP256K1_SCALAR_VERIFY(a);
VERIFY_CHECK(count > 0 && count <= 32);
VERIFY_CHECK((offset + count - 1) >> 6 == offset >> 6);
VERIFY_CHECK(offset <= 256 - count);
VERIFY_CHECK((offset + count - 1) >> 5 == offset >> 5);
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm convinced this will not break things and I like this more after fiddling with the bits.

But feels like the original check combined with line 43 was already sufficient for checking we are not able to cross limbs when trying to collect bits from the scalar.

One such case could be: offset = 31.

With the original check:
RHS: offset >> 6 = 0
LHS: (31 + count - 1) >> 6 => count < 34 so that RHS == LHS.

But line 43 already guarantee that count <= 32. Similar for the other limbs.


return (a->d[offset >> 6] >> (offset & 0x3F)) & (0xFFFFFFFF >> (32 - count));
}

SECP256K1_INLINE static uint32_t secp256k1_scalar_get_bits_var(const secp256k1_scalar *a, unsigned int offset, unsigned int count) {
SECP256K1_SCALAR_VERIFY(a);
VERIFY_CHECK(count > 0 && count <= 32);
VERIFY_CHECK(offset + count <= 256);
VERIFY_CHECK(offset <= 256 - count);
Comment on lines -52 to +53
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wonder if those aren't the same check.

I mean, offset + count could overflow while 256 - count can't because of the first check.
Is that the intended fix?


if ((offset + count - 1) >> 6 == offset >> 6) {
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here, we are checking if we are not crossing limbs when collecting bits. I think it's ok to inline the function in the following, but not so much if we are testing a different condition compared to the called function, which is what this PR proposes by changing line R45.

Why not

Suggested change
if ((offset + count - 1) >> 6 == offset >> 6) {
if ((offset + count - 1) >> 5 == offset >> 5) {

as well?

return secp256k1_scalar_get_bits_limb32(a, offset, count);
return (a->d[offset >> 6] >> (offset & 0x3F)) & (0xFFFFFFFF >> (32 - count));
} else {
VERIFY_CHECK((offset >> 6) + 1 < 4);
VERIFY_CHECK((offset & 0x3F) > 0);
return ((a->d[offset >> 6] >> (offset & 0x3F)) | (a->d[(offset >> 6) + 1] << (64 - (offset & 0x3F)))) & (0xFFFFFFFF >> (32 - count));
}
}
Expand Down
3 changes: 2 additions & 1 deletion src/scalar_8x32_impl.h
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ SECP256K1_INLINE static void secp256k1_scalar_set_int(secp256k1_scalar *r, unsig
SECP256K1_INLINE static uint32_t secp256k1_scalar_get_bits_limb32(const secp256k1_scalar *a, unsigned int offset, unsigned int count) {
SECP256K1_SCALAR_VERIFY(a);
VERIFY_CHECK(count > 0 && count <= 32);
VERIFY_CHECK(offset <= 256 - count);
VERIFY_CHECK((offset + count - 1) >> 5 == offset >> 5);

return (a->d[offset >> 5] >> (offset & 0x1F)) & (0xFFFFFFFF >> (32 - count));
Expand All @@ -62,7 +63,7 @@ SECP256K1_INLINE static uint32_t secp256k1_scalar_get_bits_limb32(const secp256k
SECP256K1_INLINE static uint32_t secp256k1_scalar_get_bits_var(const secp256k1_scalar *a, unsigned int offset, unsigned int count) {
SECP256K1_SCALAR_VERIFY(a);
VERIFY_CHECK(count > 0 && count <= 32);
VERIFY_CHECK(offset + count <= 256);
VERIFY_CHECK(offset <= 256 - count);

if ((offset + count - 1) >> 5 == offset >> 5) {
return secp256k1_scalar_get_bits_limb32(a, offset, count);
Expand Down
12 changes: 10 additions & 2 deletions src/scalar_low_impl.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,10 @@ SECP256K1_INLINE static void secp256k1_scalar_set_int(secp256k1_scalar *r, unsig

SECP256K1_INLINE static uint32_t secp256k1_scalar_get_bits_limb32(const secp256k1_scalar *a, unsigned int offset, unsigned int count) {
SECP256K1_SCALAR_VERIFY(a);

VERIFY_CHECK(count > 0 && count <= 32);
VERIFY_CHECK(offset <= 256 - count);
VERIFY_CHECK((offset + count - 1) >> 5 == offset >> 5);

if (offset < 32) {
return (*a >> offset) & (0xFFFFFFFF >> (32 - count));
} else {
Expand All @@ -38,8 +40,14 @@ SECP256K1_INLINE static uint32_t secp256k1_scalar_get_bits_limb32(const secp256k

SECP256K1_INLINE static uint32_t secp256k1_scalar_get_bits_var(const secp256k1_scalar *a, unsigned int offset, unsigned int count) {
SECP256K1_SCALAR_VERIFY(a);
VERIFY_CHECK(count > 0 && count <= 32);
VERIFY_CHECK(offset <= 256 - count);

return secp256k1_scalar_get_bits_limb32(a, offset, count);
if (offset < 32) {
return (*a >> offset) & (0xFFFFFFFF >> (32 - count));
} else {
return 0;
}
}

SECP256K1_INLINE static int secp256k1_scalar_check_overflow(const secp256k1_scalar *a) { return *a >= EXHAUSTIVE_TEST_ORDER; }
Expand Down
Loading