Skip to content

Proof of poly_challenge() including contracts #199

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 1 commit into
base: main
Choose a base branch
from

Conversation

rod-chapman
Copy link
Contributor

Fixes #113

Adds contracts and proof support files for poly_challenge()

and proof suppport files.

Signed-off-by: Rod Chapman <[email protected]>
@rod-chapman rod-chapman requested a review from mkannwischer May 2, 2025 12:37
@rod-chapman rod-chapman requested a review from a team as a code owner May 2, 2025 12:37

c->coeffs[i] = c->coeffs[j];

/* The least-significant bit of signs tells is if we want -1 or +1 */
Copy link
Contributor

Choose a reason for hiding this comment

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

Suggested change
/* The least-significant bit of signs tells is if we want -1 or +1 */
/* The least-significant bit of signs tells us if we want -1 or +1 */

{
if (pos >= SHAKE256_RATE)
{
shake256_squeezeblocks(buf, 1, &state);
pos = 0;
}
j = buf[pos++];
}
while (j > i) /* clang-format mangles layout owing to the contract above */
Copy link
Contributor

Choose a reason for hiding this comment

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

Suggested change
while (j > i) /* clang-format mangles layout owing to the contract above */
while (j > i); /* clang-format mangles layout owing to the contract above */

j = buf[pos++];
}
while (j > i) /* clang-format mangles layout owing to the contract above */
;
Copy link
Contributor

Choose a reason for hiding this comment

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

Suggested change
;

Copy link
Contributor

@mkannwischer mkannwischer May 3, 2025

Choose a reason for hiding this comment

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

You can stop clang-format from mangling your code here if you change .clang-format
from
- __loop__(x)={}
to
- __loop__(x)={} do

A little hacky, but it does not seem to have any bad side-effects in mldsa-native and mlkem-native.
While you touching .clang-format already maybe fix the typo in artific(i)ally

assigns(j, object_whole(buf), state, pos)
invariant(pos >= 1)
invariant(pos <= SHAKE256_RATE)
invariant(array_bound(c->coeffs, 0, MLDSA_N, -1, 2))
Copy link
Contributor

Choose a reason for hiding this comment

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

Can we remove this invariant since this loop does not change the value of c?

@@ -5,6 +5,7 @@
#ifndef MLD_POLY_H
#define MLD_POLY_H

#include <stdbool.h>
Copy link
Contributor

Choose a reason for hiding this comment

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

Do we need booleans here?

Copy link
Contributor

Choose a reason for hiding this comment

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

I don't think so


c->coeffs[i] = c->coeffs[j];

/* The least-significant bit of signs tells is if we want -1 or +1 */
Copy link
Contributor

Choose a reason for hiding this comment

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

Nit: "tells us"

Comment on lines +451 to +457
offset = 2 * (signs & 1);

b = buf[pos++];
} while (b > i);
/* offset has value 0 or 2 here, so (1 - (int32_t) offset) has
* value -1 or +1 */
c->coeffs[j] = 1 - (int32_t)offset;

c->coeffs[i] = c->coeffs[b];
c->coeffs[b] = 1 - 2 * (signs & 1);
/* Move to the next bit of signs for next time */
Copy link
Contributor

Choose a reason for hiding this comment

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

Curious about the deviation from the reference code here

Copy link
Contributor

Choose a reason for hiding this comment

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

Agree. We should strive to deviate only if we need to, and if so, leave a comment in the commit message and a /* Reference: ... */ comment.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

The original code mixed unsigned and signed arithmetic and relied on implicit conversions. As a result, CBMC was not able to reason about the range of the resulting expression, leading to a proof failure. As (re-written), it proves fine, it's probably clearer to a human reader what's going on.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

CBMC: Prove poly_challenge
5 participants