factory.h 7.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179
  1. // factory.h - originally written and placed in the public domain by Wei Dai
  2. /// \file factory.h
  3. /// \brief Classes and functions for registering and locating library objects
  4. #ifndef CRYPTOPP_OBJFACT_H
  5. #define CRYPTOPP_OBJFACT_H
  6. #include "cryptlib.h"
  7. #include "misc.h"
  8. #include "stdcpp.h"
  9. NAMESPACE_BEGIN(CryptoPP)
  10. /// \brief Object factory interface for registering objects
  11. /// \tparam AbstractClass Base class interface of the object
  12. template <class AbstractClass>
  13. class ObjectFactory
  14. {
  15. public:
  16. virtual ~ObjectFactory () {}
  17. virtual AbstractClass * CreateObject() const =0;
  18. };
  19. /// \brief Object factory for registering objects
  20. /// \tparam AbstractClass Base class interface of the object
  21. /// \tparam ConcreteClass Class object
  22. template <class AbstractClass, class ConcreteClass>
  23. class DefaultObjectFactory : public ObjectFactory<AbstractClass>
  24. {
  25. public:
  26. AbstractClass * CreateObject() const
  27. {
  28. return new ConcreteClass;
  29. }
  30. };
  31. /// \brief Object factory registry
  32. /// \tparam AbstractClass Base class interface of the object
  33. /// \tparam instance unique identifier
  34. template <class AbstractClass, int instance=0>
  35. class ObjectFactoryRegistry
  36. {
  37. public:
  38. class FactoryNotFound : public Exception
  39. {
  40. public:
  41. FactoryNotFound(const char *name) : Exception(OTHER_ERROR, std::string("ObjectFactoryRegistry: could not find factory for algorithm ") + name) {}
  42. };
  43. ~ObjectFactoryRegistry()
  44. {
  45. for (typename Map::iterator i = m_map.begin(); i != m_map.end(); ++i)
  46. {
  47. delete (ObjectFactory<AbstractClass> *)i->second;
  48. i->second = NULLPTR;
  49. }
  50. }
  51. void RegisterFactory(const std::string &name, ObjectFactory<AbstractClass> *factory)
  52. {
  53. m_map[name] = factory;
  54. }
  55. const ObjectFactory<AbstractClass> * GetFactory(const char *name) const
  56. {
  57. typename Map::const_iterator i = m_map.find(name);
  58. return i == m_map.end() ? NULLPTR : (ObjectFactory<AbstractClass> *)i->second;
  59. }
  60. AbstractClass *CreateObject(const char *name) const
  61. {
  62. const ObjectFactory<AbstractClass> *factory = GetFactory(name);
  63. if (!factory)
  64. throw FactoryNotFound(name);
  65. return factory->CreateObject();
  66. }
  67. // Return a vector containing the factory names. This is easier than returning an iterator.
  68. // from Andrew Pitonyak
  69. std::vector<std::string> GetFactoryNames() const
  70. {
  71. std::vector<std::string> names;
  72. typename Map::const_iterator iter;
  73. for (iter = m_map.begin(); iter != m_map.end(); ++iter)
  74. names.push_back(iter->first);
  75. return names;
  76. }
  77. CRYPTOPP_NOINLINE static ObjectFactoryRegistry<AbstractClass, instance> & Registry(CRYPTOPP_NOINLINE_DOTDOTDOT);
  78. private:
  79. // use void * instead of ObjectFactory<AbstractClass> * to save code size
  80. typedef std::map<std::string, void *> Map;
  81. Map m_map;
  82. };
  83. template <class AbstractClass, int instance>
  84. ObjectFactoryRegistry<AbstractClass, instance> & ObjectFactoryRegistry<AbstractClass, instance>::Registry(CRYPTOPP_NOINLINE_DOTDOTDOT)
  85. {
  86. static ObjectFactoryRegistry<AbstractClass, instance> s_registry;
  87. return s_registry;
  88. }
  89. /// \brief Object factory registry helper
  90. /// \tparam AbstractClass Base class interface of the object
  91. /// \tparam ConcreteClass Class object
  92. /// \tparam instance unique identifier
  93. template <class AbstractClass, class ConcreteClass, int instance = 0>
  94. struct RegisterDefaultFactoryFor
  95. {
  96. RegisterDefaultFactoryFor(const char *name=NULLPTR)
  97. {
  98. // BCB2006 workaround
  99. std::string n = name ? std::string(name) : std::string(ConcreteClass::StaticAlgorithmName());
  100. ObjectFactoryRegistry<AbstractClass, instance>::Registry().
  101. RegisterFactory(n, new DefaultObjectFactory<AbstractClass, ConcreteClass>);
  102. }
  103. };
  104. /// \fn RegisterAsymmetricCipherDefaultFactories
  105. /// \brief Register asymmetric ciphers
  106. /// \tparam SchemeClass interface of the object under a scheme
  107. /// \details Schemes include asymmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>),
  108. /// signature schemes (registers <tt>SchemeClass::Signer</tt> and <tt>SchemeClass::Verifier</tt>),
  109. /// symmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>),
  110. /// authenticated symmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>), etc.
  111. template <class SchemeClass>
  112. void RegisterAsymmetricCipherDefaultFactories(const char *name=NULLPTR)
  113. {
  114. RegisterDefaultFactoryFor<PK_Encryptor, typename SchemeClass::Encryptor>((const char *)name);
  115. RegisterDefaultFactoryFor<PK_Decryptor, typename SchemeClass::Decryptor>((const char *)name);
  116. }
  117. /// \fn RegisterSignatureSchemeDefaultFactories
  118. /// \brief Register signature schemes
  119. /// \tparam SchemeClass interface of the object under a scheme
  120. /// \details Schemes include asymmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>),
  121. /// signature schemes (registers <tt>SchemeClass::Signer</tt> and <tt>SchemeClass::Verifier</tt>),
  122. /// symmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>),
  123. /// authenticated symmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>), etc.
  124. template <class SchemeClass>
  125. void RegisterSignatureSchemeDefaultFactories(const char *name=NULLPTR)
  126. {
  127. RegisterDefaultFactoryFor<PK_Signer, typename SchemeClass::Signer>((const char *)name);
  128. RegisterDefaultFactoryFor<PK_Verifier, typename SchemeClass::Verifier>((const char *)name);
  129. }
  130. /// \fn RegisterSymmetricCipherDefaultFactories
  131. /// \brief Register symmetric ciphers
  132. /// \tparam SchemeClass interface of the object under a scheme
  133. /// \details Schemes include asymmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>),
  134. /// signature schemes (registers <tt>SchemeClass::Signer</tt> and <tt>SchemeClass::Verifier</tt>),
  135. /// symmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>),
  136. /// authenticated symmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>), etc.
  137. template <class SchemeClass>
  138. void RegisterSymmetricCipherDefaultFactories(const char *name=NULLPTR)
  139. {
  140. RegisterDefaultFactoryFor<SymmetricCipher, typename SchemeClass::Encryption, ENCRYPTION>((const char *)name);
  141. RegisterDefaultFactoryFor<SymmetricCipher, typename SchemeClass::Decryption, DECRYPTION>((const char *)name);
  142. }
  143. /// \fn RegisterAuthenticatedSymmetricCipherDefaultFactories
  144. /// \brief Register authenticated symmetric ciphers
  145. /// \tparam SchemeClass interface of the object under a scheme
  146. /// \details Schemes include asymmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>),
  147. /// signature schemes (registers <tt>SchemeClass::Signer</tt> and <tt>SchemeClass::Verifier</tt>),
  148. /// symmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>),
  149. /// authenticated symmetric ciphers (registers <tt>SchemeClass::Encryptor</tt> and <tt>SchemeClass::Decryptor</tt>), etc.
  150. template <class SchemeClass>
  151. void RegisterAuthenticatedSymmetricCipherDefaultFactories(const char *name=NULLPTR)
  152. {
  153. RegisterDefaultFactoryFor<AuthenticatedSymmetricCipher, typename SchemeClass::Encryption, ENCRYPTION>((const char *)name);
  154. RegisterDefaultFactoryFor<AuthenticatedSymmetricCipher, typename SchemeClass::Decryption, DECRYPTION>((const char *)name);
  155. }
  156. NAMESPACE_END
  157. #endif