Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | File List | Namespace Members | Class Members | File Members

eprecomp.cpp

00001 // eprecomp.cpp - written and placed in the public domain by Wei Dai
00002 
00003 #include "pch.h"
00004 #include "eprecomp.h"
00005 #include "asn.h"
00006 
00007 NAMESPACE_BEGIN(CryptoPP)
00008 
00009 template <class T> void DL_FixedBasePrecomputationImpl<T>::SetBase(const DL_GroupPrecomputation<Element> &group, const Element &i_base)
00010 {
00011         m_base = group.NeedConversions() ? group.ConvertIn(i_base) : i_base;
00012 
00013         if (m_bases.empty() || !(m_base == m_bases[0]))
00014         {
00015                 m_bases.resize(1);
00016                 m_bases[0] = m_base;
00017         }
00018 
00019         if (group.NeedConversions())
00020                 m_base = i_base;
00021 }
00022 
00023 template <class T> void DL_FixedBasePrecomputationImpl<T>::Precompute(const DL_GroupPrecomputation<Element> &group, unsigned int maxExpBits, unsigned int storage)
00024 {
00025         assert(m_bases.size() > 0);
00026         assert(storage <= maxExpBits);
00027 
00028         if (storage > 1)
00029         {
00030                 m_windowSize = (maxExpBits+storage-1)/storage;
00031                 m_exponentBase = Integer::Power2(m_windowSize);
00032         }
00033 
00034         m_bases.resize(storage);
00035         for (unsigned i=1; i<storage; i++)
00036                 m_bases[i] = group.GetGroup().ScalarMultiply(m_bases[i-1], m_exponentBase);
00037 }
00038 
00039 template <class T> void DL_FixedBasePrecomputationImpl<T>::Load(const DL_GroupPrecomputation<Element> &group, BufferedTransformation &bt)
00040 {
00041         BERSequenceDecoder seq(bt);
00042         word32 version;
00043         BERDecodeUnsigned<word32>(seq, version, INTEGER, 1, 1);
00044         m_exponentBase.BERDecode(seq);
00045         m_windowSize = m_exponentBase.BitCount() - 1;
00046         m_bases.clear();
00047         while (!seq.EndReached())
00048                 m_bases.push_back(group.BERDecodeElement(seq));
00049         if (!m_bases.empty() && group.NeedConversions())
00050                 m_base = group.ConvertOut(m_bases[0]);
00051         seq.MessageEnd();
00052 }
00053 
00054 template <class T> void DL_FixedBasePrecomputationImpl<T>::Save(const DL_GroupPrecomputation<Element> &group, BufferedTransformation &bt) const
00055 {
00056         DERSequenceEncoder seq(bt);
00057         DEREncodeUnsigned<word32>(seq, 1);      // version
00058         m_exponentBase.DEREncode(seq);
00059         for (unsigned i=0; i<m_bases.size(); i++)
00060                 group.DEREncodeElement(seq, m_bases[i]);
00061         seq.MessageEnd();
00062 }
00063 
00064 template <class T> void DL_FixedBasePrecomputationImpl<T>::PrepareCascade(const DL_GroupPrecomputation<Element> &i_group, std::vector<BaseAndExponent<Element> > &eb, const Integer &exponent) const
00065 {
00066         const AbstractGroup<T> &group = i_group.GetGroup();
00067 
00068         Integer r, q, e = exponent;
00069         bool fastNegate = group.InversionIsFast() && m_windowSize > 1;
00070         unsigned int i;
00071 
00072         for (i=0; i+1<m_bases.size(); i++)
00073         {
00074                 Integer::DivideByPowerOf2(r, q, e, m_windowSize);
00075                 std::swap(q, e);
00076                 if (fastNegate && r.GetBit(m_windowSize-1))
00077                 {
00078                         ++e;
00079                         eb.push_back(BaseAndExponent<Element>(group.Inverse(m_bases[i]), m_exponentBase - r));
00080                 }
00081                 else
00082                         eb.push_back(BaseAndExponent<Element>(m_bases[i], r));
00083         }
00084         eb.push_back(BaseAndExponent<Element>(m_bases[i], e));
00085 }
00086 
00087 template <class T> T DL_FixedBasePrecomputationImpl<T>::Exponentiate(const DL_GroupPrecomputation<Element> &group, const Integer &exponent) const
00088 {
00089         std::vector<BaseAndExponent<Element> > eb;      // array of segments of the exponent and precalculated bases
00090         eb.reserve(m_bases.size());
00091         PrepareCascade(group, eb, exponent);
00092         return group.ConvertOut(GeneralCascadeMultiplication<Element>(group.GetGroup(), eb.begin(), eb.end()));
00093 }
00094 
00095 template <class T> T 
00096         DL_FixedBasePrecomputationImpl<T>::CascadeExponentiate(const DL_GroupPrecomputation<Element> &group, const Integer &exponent, 
00097                 const DL_FixedBasePrecomputation<T> &i_pc2, const Integer &exponent2) const
00098 {
00099         std::vector<BaseAndExponent<Element> > eb;      // array of segments of the exponent and precalculated bases
00100         const DL_FixedBasePrecomputationImpl<T> &pc2 = static_cast<const DL_FixedBasePrecomputationImpl<T> &>(i_pc2);
00101         eb.reserve(m_bases.size() + pc2.m_bases.size());
00102         PrepareCascade(group, eb, exponent);
00103         pc2.PrepareCascade(group, eb, exponent2);
00104         return group.ConvertOut(GeneralCascadeMultiplication<Element>(group.GetGroup(), eb.begin(), eb.end()));
00105 }
00106 
00107 NAMESPACE_END

Generated on Sun Mar 14 20:44:25 2004 for Crypto++ by doxygen 1.3.6-20040222