Closed Bug 609068 Opened 14 years ago Closed 14 years ago

Implement J-PAKE in FreeBL

Categories

(NSS :: Libraries, defect)

defect
Not set
blocker

Tracking

(blocking2.0 final+)

RESOLVED FIXED
3.12.9
Tracking Status
blocking2.0 --- final+

People

(Reporter: briansmith, Assigned: briansmith)

References

Details

(Whiteboard: [hardblocker])

Attachments

(4 files, 12 obsolete files)

31.76 KB, patch
rrelyea
: feedback-
Details | Diff | Splinter Review
36.29 KB, patch
Details | Diff | Splinter Review
36.44 KB, patch
Details | Diff | Splinter Review
1.02 KB, patch
rrelyea
: review+
Details | Diff | Splinter Review
Mozilla needs a J-PAKE implementation for Sync in Firefox 4. A J-PAKE implementation in NSS will eliminate the need for Firefox to depend on FreeBL's MPI library (and avoiding issues with platform-dependent MPI digit representations), and it should be easier to review--especially, in comparison with the OpenSSL implementation.
Blocks: 601645
blocking2.0: --- → ?
Assignee: nobody → bsmith
J-PAKE needs to be able to generate random nonces which are very much like DSA keys, except they are not limited to 160 bits. Here, I extended the DSA key generation code to work with subprimes larger than 160 bits. The code ensures that the pre-existing DSA functions continue to reject inputs that don't have a 160-bit subprimes.

The J-PAKE code will also use the new DSA_NewRandom function independently of DSA_NewKeyExtended in order to generate the random R value for Schnorr signatures. (See the next patch.)
Attachment #492858 - Flags: review?(rrelyea)
Comment on attachment 492858 [details] [diff] [review]
Extended DSA key generation logic used for J-PAKE

This is the hdf patch;( I'd give it an r+, but I already have;).

bob
Attachment #492858 - Flags: review?(rrelyea)
Sorry, Bob. Here's the correct patch.
Attachment #492858 - Attachment is obsolete: true
Attachment #492875 - Flags: review?(rrelyea)
Comment on attachment 492875 [details] [diff] [review]
Extended DSA key generation logic used for J-PAKE

r- but only for two small issues...

1) in dsa_GenerateGlobalRandomBytes, now that the length of 'dest' is no longer the passed in length, we should probably pass in it's length in *destLen and check it. I know the length has to be at least the length of qItem->len, but that's a little more obscure to the caller. We should check to make sure *destLen is at least the size to hold  our expected dest value (if (*destLen < qLen) fail).

This is not a bug in the current patch. the requested change will cause a change to line 445. kSeedLen needs to be set to sizeof (kSeed). (the other usage will already have seed->len set properly).

2) There is a leak at 268 in DSA_NewRandom if the generateBytes fails, we leak the seed.

Everything else looks good.

bob
Attachment #492875 - Flags: review?(rrelyea) → review-
In order to avoid conflicts in loader/ldvector, I combined the DSA changes with the new J-PAKE specific code.
Attachment #494054 - Flags: review?(rrelyea)
Attached file Changes to bltest for testing J-PAKE (obsolete) —
This patch for the J-PAKE tests needs some work and I would like some feedback about the general approach.
Attachment #494056 - Flags: review?(rrelyea)
Attached patch FreeBL J-PAKE tests in bltest (obsolete) — Splinter Review
With this patch, bltest -J will run the J-PAKE tests. 

The test vectors were created by instrumenting the latest OpenSSL J-PAKE implementation so that the intermediate results were output, and then capturing the output of sample runs.
Attachment #492875 - Attachment is obsolete: true
Attachment #494056 - Attachment is obsolete: true
Attachment #494059 - Flags: review?(rrelyea)
Attachment #494056 - Flags: review?(rrelyea)
(In reply to comment #4)
> Comment on attachment 492875 [details] [diff] [review]
> Extended DSA key generation logic used for J-PAKE
> 
> r- but only for two small issues...
> 
> 1) in dsa_GenerateGlobalRandomBytes, now that the length of 'dest' is no longer
> the passed in length, we should probably pass in it's length in *destLen and
> check it. I know the length has to be at least the length of qItem->len, but
> that's a little more obscure to the caller. We should check to make sure
> *destLen is at least the size to hold  our expected dest value (if (*destLen <
> qLen) fail).
> 
> This is not a bug in the current patch. the requested change will cause a
> change to line 445. kSeedLen needs to be set to sizeof (kSeed). (the other
> usage will already have seed->len set properly).

This is addressed in the new version of dsa.c. I used the (output buffer, output length, max length) pattern for the parameters that is common in the rest of NSS.

> 2) There is a leak at 268 in DSA_NewRandom if the generateBytes fails, we leak
> the seed.

This is also addressed in the new patch.
This is the same as the previous patch except that it includes the DSA_NewRandom stub in loader.c that I accidentally omitted previously.
Attachment #494054 - Attachment is obsolete: true
Attachment #494310 - Flags: review?(rrelyea)
Attachment #494054 - Flags: review?(rrelyea)
There should be a check that gx3 != gx4 and gx3 in round2 and also this check should be done in the OpenSSL implementation if it isn't already. I will add this check after I get Bob's review comments.
Comment on attachment 494310 [details] [diff] [review]
J-PAKE FreeBL Patch v2 - add DSA_NewRandom to loader.c

r-

The DSA Random stuff looks ok.

I have some questions that need to be answered before I r+, but the r- is primarily for a few bugs..

Bug: In JPAKE_Verify we check that R is < q, but we haven't set R to *r until later.

Without that R will be zero (which is less than q), so the test will always pass.
(NOTE, unlike GX, R of zero (and thus R=Nq) is not a problem (where GX= (n)*p-1 is a problem). Still the code should be correct.

Potential Bug: I can't see how you are using JPAKE_Round2, but I think you still need to raise your calculated base to the x2*s power at some point to get 'A' (I was just expecting it to be in JPAKE_Round2 rather than somewhere else).

General comment. I would have liked to see less 'name swapping' in the mp calls. Particularly confusing is the change of base from mpint to SECItem in two different, bug closely related functions, so that I originally thought we had a type mismatch. I also found the swapping of modulus and exponent a bit much. I would have rather just had p and q mp_int's (and x2s get's converted to mp_int twice, which sort of cries out for it's own mp_int).

Finally the question:

In JPAKE_sign, you take x and return gx. My question is is this how you are generating gx? I would have though you would use DSA_KeyGen to get both x and gx, then pass both to sign.

I don't see anything else that makes me sqirm;).

bob
Attachment #494310 - Flags: review?(rrelyea) → review-
(In reply to comment #11)
> Bug: In JPAKE_Verify we check that R is < q, but we haven't set R to *r until
> later.

> Without that R will be zero (which is less than q), so the test will always
> pass. (NOTE, unlike GX, R of zero (and thus R=Nq) is not a problem
> (where GX= (n)*p-1 is a problem). Still the code should be correct.

Yes, I added this check at the very end so that we only interoperate with implementations that follow the "spec" exactly to reduce the potential for any problems with R=Nq+x for N>0. I will move the initialization of R up.

> Potential Bug: I can't see how you are using JPAKE_Round2, but I think you
> still need to raise your calculated base to the x2*s power at some point to 
> get 'A' (I was just expecting it to be in JPAKE_Round2 rather than
> somewhere else).

JPAKE_Round2 is used two different ways:

1. It is used to generate A. In this case, the x2s parameter will be non-NULL and JPAKE_Round2 will return base and x2s. The caller then passes these to JPAKE_Sign to generate A=base^x2s, base^v, and R. (JPAKE_Sign isn't the best name because it doesn't account for the fact that it calculates base^exponent. Maybe JPAKE_RaiseAndSign would be a better name.)

2. It is used to calculate the base of B (where B=base^x4s) for the final round. In this case, x2s will be NULL and JPAKE-Round2 returns just the base.

> General comment. I would have liked to see less 'name swapping' in the mp
> calls. Particularly confusing is the change of base from mpint to SECItem in
> two different, bug closely related functions, so that I originally thought we
> had a type mismatch. I also found the swapping of modulus and exponent a bit
> much. I would have rather just had p and q mp_int's (and x2s get's converted > to mp_int twice, which sort of cries out for it's own mp_int).

I will make these clarifications.

> Finally the question:
> 
> In JPAKE_sign, you take x and return gx. My question is is this how you are
> generating gx? I would have though you would use DSA_KeyGen to get both x and
> gx, then pass both to sign.

In round 2, x isn't random; it is x2*s. I do the exponentiation g^x inside JPAKE_Sign to show and exploit the symmetry between the round 1 calculations and the round 2 calculations. In round1, we have (base=g, x=x1) and (base=g, x=x2); in round2, we have (base=g^(x1+x3+x4), x=x2*s) but otherwise the calculations are the same.

Thus, before Round1, I just call the new DSA_NewRandom directly to generate x1 and x2, since JPAKE_Sign does the exponentiation.
Attached patch Everything except jpake.c (obsolete) — Splinter Review
This patch addresses your review comments and adds a PLArenaPool parameter to DSA_NewRandom. By allowing the random value to be allocated in the arena, it will get zeroized in J-PAKE/softoken when the arena is freed.
Attachment #494310 - Attachment is obsolete: true
Attachment #495064 - Flags: review?(rrelyea)
Attached patch Patch to add jpake.c (obsolete) — Splinter Review
Patch to add jpake.c. Besides addressing the review comments, I also added checks for s < q and gx3 != gx4 and more general parameter validation.
Attachment #495065 - Flags: review?(rrelyea)
Comment on attachment 495064 [details] [diff] [review]
Everything except jpake.c

r+ rrelyea, but this patch needs jpake.c to land at the same time or before this patch.
Attachment #495064 - Flags: review?(rrelyea) → review+
> In round 2, x isn't random; it is x2*s. I do the exponentiation g^x inside
> JPAKE_Sign to show and exploit the symmetry between the round 1 calculations
> and the round 2 calculations. In round1, we have (base=g, x=x1) and (base=g,
> x=x2); in round2, we have (base=g^(x1+x3+x4), x=x2*s) but otherwise the
> calculations are the same.

OK, so the rounds are SNORR signed as well. I would prefer and optional parameter GX which could pass GX in and not have to calculate it. You may not need it for JPAKE_Sign, but I can use if for other SNORR-like operations.
Comment on attachment 495065 [details] [diff] [review]
Patch to add jpake.c

r+

I'm going to R+ this, but I would like an optional gxin (SECITEM *) parameter in JPAKE_SIGN.

if gxin == NULL, then you generate GX = g^x mod p, other wise GX = gxin.
You could optionally use the existing gx parameter. If gx->len == 0, then calculate it, otherwise, just use it.

bob
Attachment #495065 - Flags: review?(rrelyea) → review+
Bob, JPAKE_Sign is the only place that calculates g^x so gxin would always be NULL. This test program + the upcoming jpakesftk.c patch should make this clear.
Attachment #494059 - Attachment is obsolete: true
Attachment #495075 - Flags: review?(rrelyea)
Attachment #494059 - Flags: review?(rrelyea)
I think you missed my point.

I want a check so that someone else can use JPAKE_Sign by passing in gxin even if JPAKE doesn't do it. (I'm trying to save myself some future work here. If you add this, JPAKE_Sign can be used by other protocols for part of their work).

It's OK of you implement it as

gx->len = 0 rather than adding a new parameter.

bob
Attachment #495064 - Attachment is obsolete: true
Attachment #495065 - Attachment is obsolete: true
Attachment #495173 - Flags: review?(rrelyea)
Comment on attachment 495173 [details] [diff] [review]
J-PAKE FreeBL (v4) - now JPAKE_Sign has gxIn/gxOut parameters

r+ pending the equivalent change in pjake.c
Attachment #495173 - Flags: review?(rrelyea) → review+
jpake.c is already rolled into that patch. (I had only split the patch into two parts previously because I wasn't expecting the interface to change.)
Hmm, I see no pjake.c, did you cvs diff -Nup?

bob
jpake.c is a new file and cvs -Nup doesn't work. I guess I should use cvsdo.pl to create patches for new files, but AFAICT the site from which I am supposed to download cvsdo.pl is down. So, I did a normal diff -Nup /dev/null lib/freebl/jpake.c, appended it to the patch, and edited the filename in the patch.

I guess that isn't enough to satisfy the bugzilla patch UI but if you look at the raw patch it is at the bottom of the patch.
Attached patch cvs -N10p patch for jpake.c (obsolete) — Splinter Review
Here is the standalone version of the jpake.c patch if it helps.
Attachment #495192 - Flags: review?(rrelyea)
Comment on attachment 495192 [details] [diff] [review]
cvs -N10p patch for jpake.c

r+

I don't know what -10 was, but this patch seemed to not like the tools.
I reviewed the relevant changes, I presume that's all that changed.

bob
Attachment #495192 - Flags: review?(rrelyea) → review+
Tip/Trunk checkin

Checking in lib/freebl/blapi.h;
/cvsroot/mozilla/security/nss/lib/freebl/blapi.h,v  <--  blapi.h
new revision: 1.40; previous revision: 1.39
done
Checking in lib/freebl/dsa.c;
/cvsroot/mozilla/security/nss/lib/freebl/dsa.c,v  <--  dsa.c
new revision: 1.21; previous revision: 1.20
done
RCS file: /cvsroot/mozilla/security/nss/lib/freebl/jpake.c,v
done
Checking in lib/freebl/jpake.c;
/cvsroot/mozilla/security/nss/lib/freebl/jpake.c,v  <--  jpake.c
initial revision: 1.1
done
Checking in lib/freebl/ldvector.c;
/cvsroot/mozilla/security/nss/lib/freebl/ldvector.c,v  <--  ldvector.c
new revision: 1.27; previous revision: 1.26
done
Checking in lib/freebl/loader.c;
/cvsroot/mozilla/security/nss/lib/freebl/loader.c,v  <--  loader.c
new revision: 1.51; previous revision: 1.50
done
Checking in lib/freebl/loader.h;
/cvsroot/mozilla/security/nss/lib/freebl/loader.h,v  <--  loader.h
new revision: 1.32; previous revision: 1.31
done
Checking in lib/freebl/manifest.mn;
/cvsroot/mozilla/security/nss/lib/freebl/manifest.mn,v  <--  manifest.mn
new revision: 1.60; previous revision: 1.59
done
Checking in lib/freebl/stubs.c;
/cvsroot/mozilla/security/nss/lib/freebl/stubs.c,v  <--  stubs.c
new revision: 1.10; previous revision: 1.9
done
Checking in lib/freebl/stubs.h;
/cvsroot/mozilla/security/nss/lib/freebl/stubs.h,v  <--  stubs.h
new revision: 1.7; previous revision: 1.6
done
Branch checkin

hecking in lib/freebl/blapi.h;
/cvsroot/mozilla/security/nss/lib/freebl/blapi.h,v  <--  blapi.h
new revision: 1.33.22.2; previous revision: 1.33.22.1
done
Checking in lib/freebl/dsa.c;
/cvsroot/mozilla/security/nss/lib/freebl/dsa.c,v  <--  dsa.c
new revision: 1.20.22.1; previous revision: 1.20
done
Checking in lib/freebl/jpake.c;
/cvsroot/mozilla/security/nss/lib/freebl/jpake.c,v  <--  jpake.c
new revision: 1.1.2.2; previous revision: 1.1.2.1
done
Checking in lib/freebl/ldvector.c;
/cvsroot/mozilla/security/nss/lib/freebl/ldvector.c,v  <--  ldvector.c
new revision: 1.21.22.3; previous revision: 1.21.22.2
done
Checking in lib/freebl/loader.c;
/cvsroot/mozilla/security/nss/lib/freebl/loader.c,v  <--  loader.c
new revision: 1.44.22.2; previous revision: 1.44.22.1
done
Checking in lib/freebl/loader.h;
/cvsroot/mozilla/security/nss/lib/freebl/loader.h,v  <--  loader.h
new revision: 1.26.22.2; previous revision: 1.26.22.1
done
Checking in lib/freebl/manifest.mn;
/cvsroot/mozilla/security/nss/lib/freebl/manifest.mn,v  <--  manifest.mn
new revision: 1.58.2.1; previous revision: 1.58
done
Checking in lib/freebl/stubs.c;
/cvsroot/mozilla/security/nss/lib/freebl/stubs.c,v  <--  stubs.c
new revision: 1.8.2.1; previous revision: 1.8
done
Checking in lib/freebl/stubs.h;
/cvsroot/mozilla/security/nss/lib/freebl/stubs.h,v  <--  stubs.h
new revision: 1.5.2.1; previous revision: 1.5
done
Tweaks from Brian's patch before checkin:
   DOS ^M's were removed.
   stubs.c/h were updated to include NSS_SecureMemcmp
   stubs.h was added to jpake.c
Tweaks from Brian's patch before checkin:
   DOS ^M's were removed.
   stubs.c/h were updated to include NSS_SecureMemcmp
   stubs.h was added to jpake.c
No longer blocks: 601645
Mozilla will never call this with a zero s but it should still be guarded against.

I did not add checks for the range of x1 and x2 because they are generated by DSA_NewRandom in Softoken and DSA_NewRandom guarantees its output to be in the desired range.
Attachment #496110 - Flags: review?(rrelyea)
Target Milestone: --- → 3.12.9
blocking2.0: ? → final+
Comment on attachment 495213 [details] [diff] [review]
Patch for the stable branch that resolves the conflicts in ldvector.c, loader.h, loader.c

this patch is already in the branch.
Attachment #495213 - Flags: review?(rrelyea)
Comment on attachment 496110 [details] [diff] [review]
Patch on top of checked-in code to check shared key s != 0 [checked in]

r+ rrelyea
Attachment #496110 - Flags: review?(rrelyea) → review+
Comment on attachment 495175 [details] [diff] [review]
Tests for J-PAKE FreeBL in bltest (bltest -J) (v2)

This isn't a full review, but there are a few things that would be good to change:

1) It would be good politic to remove variable names like openssl_generated. (even better politic to actually generate them with NSS (there should be functions to generate pqg parameters for you.

2) bltest has a very nice facility to read base64 encoded data from files.It would be good to recast this test so you can read the input from files. (you could also expand the test cases in the future easily. (see mozilla/security/nss/cmd/bltest/tests).

Doing that would allow you to just add an entry into mozilla/security/nss/tests/cipher/cipher.txt to add the tests to all.sh.

bob
Attachment #495175 - Flags: feedback-
Attachment #495213 - Attachment is obsolete: true
Attachment #495173 - Attachment is obsolete: true
Attachment #495192 - Attachment is obsolete: true
Comment on attachment 496110 [details] [diff] [review]
Patch on top of checked-in code to check shared key s != 0 [checked in]

attachment 496110 [details] [diff] [review] was checked into the trunk and NSS_3_12_BRANCH with commit meessage "Bug 609068: Implement J-PAKE in FreeBL, additional check that s != 0, r=rrelyea"

All 4.0-blocking patches for this bug have been checked in. The bug is open because I need to rewrite the tests but that part isn't going to block 4.0. I recommend removing the blocking flag.
Attachment #496110 - Attachment description: Patch on top of checked-in code to check shared key s != 0 → Patch on top of checked-in code to check shared key s != 0 [checked in]
Alternatively, this bug can be left as it is and RESOLVED FIXED and we make a new bug that depends on this bug?
Whiteboard: [hardblocker]
Taking Philipp's advice. The bug for the tests is bug 625456.
Status: NEW → RESOLVED
Closed: 14 years ago
Resolution: --- → FIXED
See Also: → 625456
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Created:
Updated:
Size: