~zooko/cryptopp/trunk

« back to all changes in this revision

Viewing changes to rw.cpp

  • Committer: weidai
  • Date: 2009-03-02 02:39:17 UTC
  • Revision ID: svn-v4:57ff6487-cd31-0410-9ec3-f628ee90f5f0:trunk/c5:433
changes for 5.6: 
    - added AuthenticatedSymmetricCipher interface class and Filter wrappers
    - added CCM, GCM (with SSE2 assembly), CMAC, and SEED
    - improved AES speed on x86 and x64
    - removed WORD64_AVAILABLE; compiler 64-bit int support is now required

Show diffs side-by-side

added added

removed removed

Lines of Context:
93
93
        if (modulusSize < 16)
94
94
                throw InvalidArgument("InvertibleRWFunction: specified modulus length is too small");
95
95
 
96
 
        const NameValuePairs &primeParam = MakeParametersForTwoPrimesOfEqualSize(modulusSize);
 
96
        AlgorithmParameters primeParam = MakeParametersForTwoPrimesOfEqualSize(modulusSize);
97
97
        m_p.GenerateRandom(rng, CombinedNameValuePairs(primeParam, MakeParameters("EquivalentTo", 3)("Mod", 8)));
98
98
        m_q.GenerateRandom(rng, CombinedNameValuePairs(primeParam, MakeParameters("EquivalentTo", 7)("Mod", 8)));
99
99
 
121
121
        seq.MessageEnd();
122
122
}
123
123
 
124
 
Integer InvertibleRWFunction::CalculateInverse(RandomNumberGenerator &rng, const Integer &in) const
 
124
Integer InvertibleRWFunction::CalculateInverse(RandomNumberGenerator &rng, const Integer &x) const
125
125
{
126
 
        // no need to do blinding because RW is only used for signatures
127
 
 
128
126
        DoQuickSanityCheck();
129
 
 
130
 
        Integer cp=in%m_p, cq=in%m_q;
131
 
 
 
127
        ModularArithmetic modn(m_n);
 
128
        Integer r, rInv;
 
129
        do {    // do this in a loop for people using small numbers for testing
 
130
                r.Randomize(rng, Integer::One(), m_n - Integer::One());
 
131
                rInv = modn.MultiplicativeInverse(r);
 
132
        } while (rInv.IsZero());
 
133
        Integer re = modn.Square(r);
 
134
        re = modn.Multiply(re, x);                      // blind
 
135
 
 
136
        Integer cp=re%m_p, cq=re%m_q;
132
137
        if (Jacobi(cp, m_p) * Jacobi(cq, m_q) != 1)
133
138
        {
134
 
                cp = cp%2 ? (cp+m_p) >> 1 : cp >> 1;
135
 
                cq = cq%2 ? (cq+m_q) >> 1 : cq >> 1;
 
139
                cp = cp.IsOdd() ? (cp+m_p) >> 1 : cp >> 1;
 
140
                cq = cq.IsOdd() ? (cq+m_q) >> 1 : cq >> 1;
136
141
        }
137
142
 
138
 
        cp = ModularSquareRoot(cp, m_p);
139
 
        cq = ModularSquareRoot(cq, m_q);
140
 
 
141
 
        Integer out = CRT(cq, m_q, cp, m_p, m_u);
142
 
 
143
 
        return STDMIN(out, m_n-out);
 
143
        #pragma omp parallel
 
144
                #pragma omp sections
 
145
                {
 
146
                        #pragma omp section
 
147
                                cp = ModularSquareRoot(cp, m_p);
 
148
                        #pragma omp section
 
149
                                cq = ModularSquareRoot(cq, m_q);
 
150
                }
 
151
 
 
152
        Integer y = CRT(cq, m_q, cp, m_p, m_u);
 
153
        y = modn.Multiply(y, rInv);                             // unblind
 
154
        y = STDMIN(y, m_n-y);
 
155
        if (ApplyFunction(y) != x)                              // check
 
156
                throw Exception(Exception::OTHER_ERROR, "InvertibleRWFunction: computational error during private key operation");
 
157
        return y;
144
158
}
145
159
 
146
160
bool InvertibleRWFunction::Validate(RandomNumberGenerator &rng, unsigned int level) const