diff --git a/src/security/transform/private-key.cpp b/src/security/transform/private-key.cpp
new file mode 100644
index 0000000..0c61817
--- /dev/null
+++ b/src/security/transform/private-key.cpp
@@ -0,0 +1,440 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/**
+ * Copyright (c) 2013-2016 Regents of the University of California.
+ *
+ * This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
+ *
+ * ndn-cxx library is free software: you can redistribute it and/or modify it under the
+ * terms of the GNU Lesser General Public License as published by the Free Software
+ * Foundation, either version 3 of the License, or (at your option) any later version.
+ *
+ * ndn-cxx library is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE.  See the GNU Lesser General Public License for more details.
+ *
+ * You should have received copies of the GNU General Public License and GNU Lesser
+ * General Public License along with ndn-cxx, e.g., in COPYING.md file.  If not, see
+ * <http://www.gnu.org/licenses/>.
+ *
+ * See AUTHORS.md for complete list of ndn-cxx authors and contributors.
+ */
+
+#include "private-key.hpp"
+#include "buffer-source.hpp"
+#include "stream-source.hpp"
+#include "base64-encode.hpp"
+#include "base64-decode.hpp"
+#include "stream-sink.hpp"
+#include "../../encoding/buffer-stream.hpp"
+#include "../detail/openssl-helper.hpp"
+#include "../key-params.hpp"
+
+#include <string.h>
+
+#define ENSURE_PRIVATE_KEY_LOADED(key) \
+  do { \
+    if (key == nullptr) \
+      BOOST_THROW_EXCEPTION(Error("Private key has not been loaded yet")); \
+  } while (false)
+
+namespace ndn {
+namespace security {
+namespace transform {
+
+class PrivateKey::Impl
+{
+public:
+  Impl()
+    : key(nullptr)
+  {
+  }
+
+  ~Impl()
+  {
+    EVP_PKEY_free(key);
+  }
+
+public:
+  EVP_PKEY* key;
+};
+
+PrivateKey::PrivateKey()
+  : m_impl(new Impl)
+{
+}
+
+PrivateKey::~PrivateKey() = default;
+
+void
+PrivateKey::loadPkcs1(const uint8_t* buf, size_t size)
+{
+  detail::Bio mem(BIO_s_mem());
+  BIO_write(mem.get(), buf, size);
+
+  d2i_PrivateKey_bio(mem.get(), &m_impl->key);
+
+  ENSURE_PRIVATE_KEY_LOADED(m_impl->key);
+}
+
+void
+PrivateKey::loadPkcs1(std::istream& is)
+{
+  OBufferStream os;
+  streamSource(is) >> streamSink(os);
+  this->loadPkcs1(os.buf()->buf(), os.buf()->size());
+}
+
+void
+PrivateKey::loadPkcs1Base64(const uint8_t* buf, size_t size)
+{
+  OBufferStream os;
+  bufferSource(buf, size) >> base64Decode() >> streamSink(os);
+  this->loadPkcs1(os.buf()->buf(), os.buf()->size());
+}
+
+void
+PrivateKey::loadPkcs1Base64(std::istream& is)
+{
+  OBufferStream os;
+  streamSource(is) >> base64Decode() >> streamSink(os);
+  this->loadPkcs1(os.buf()->buf(), os.buf()->size());
+}
+
+void
+PrivateKey::loadPkcs8(const uint8_t* buf, size_t size, const char* pw, size_t pwLen)
+{
+  BOOST_ASSERT(std::strlen(pw) == pwLen);
+
+  detail::Bio mem(BIO_s_mem());
+  BIO_write(mem.get(), buf, size);
+
+  m_impl->key = d2i_PKCS8PrivateKey_bio(mem.get(), &m_impl->key, nullptr, const_cast<char*>(pw));
+
+  ENSURE_PRIVATE_KEY_LOADED(m_impl->key);
+}
+
+static inline int
+passwordCallback(char* buf, int size, int rwflag, void* u)
+{
+  auto cb = reinterpret_cast<PrivateKey::PasswordCallback*>(u);
+  return (*cb)(buf, size, rwflag);
+}
+
+void
+PrivateKey::loadPkcs8(const uint8_t* buf, size_t size, PasswordCallback pwCallback)
+{
+  OpenSSL_add_all_algorithms();
+  detail::Bio mem(BIO_s_mem());
+  BIO_write(mem.get(), buf, size);
+
+  if (pwCallback)
+    m_impl->key = d2i_PKCS8PrivateKey_bio(mem.get(), &m_impl->key, passwordCallback, &pwCallback);
+  else
+    m_impl->key = d2i_PKCS8PrivateKey_bio(mem.get(), &m_impl->key, nullptr, nullptr);
+
+  ENSURE_PRIVATE_KEY_LOADED(m_impl->key);
+}
+
+void
+PrivateKey::loadPkcs8(std::istream& is, const char* pw, size_t pwLen)
+{
+  OBufferStream os;
+  streamSource(is) >> streamSink(os);
+  this->loadPkcs8(os.buf()->buf(), os.buf()->size(), pw, pwLen);
+}
+
+void
+PrivateKey::loadPkcs8(std::istream& is, PasswordCallback pwCallback)
+{
+  OBufferStream os;
+  streamSource(is) >> streamSink(os);
+  this->loadPkcs8(os.buf()->buf(), os.buf()->size(), pwCallback);
+}
+
+void
+PrivateKey::loadPkcs8Base64(const uint8_t* buf, size_t size, const char* pw, size_t pwLen)
+{
+  OBufferStream os;
+  bufferSource(buf, size) >> base64Decode() >> streamSink(os);
+  this->loadPkcs8(os.buf()->buf(), os.buf()->size(), pw, pwLen);
+}
+
+void
+PrivateKey::loadPkcs8Base64(const uint8_t* buf, size_t size, PasswordCallback pwCallback)
+{
+  OBufferStream os;
+  bufferSource(buf, size) >> base64Decode() >> streamSink(os);
+  this->loadPkcs8(os.buf()->buf(), os.buf()->size(), pwCallback);
+}
+
+void
+PrivateKey::loadPkcs8Base64(std::istream& is, const char* pw, size_t pwLen)
+{
+  OBufferStream os;
+  streamSource(is) >> base64Decode() >> streamSink(os);
+  this->loadPkcs8(os.buf()->buf(), os.buf()->size(), pw, pwLen);
+}
+
+void
+PrivateKey::loadPkcs8Base64(std::istream& is, PasswordCallback pwCallback)
+{
+  OBufferStream os;
+  streamSource(is) >> base64Decode() >> streamSink(os);
+  this->loadPkcs8(os.buf()->buf(), os.buf()->size(), pwCallback);
+}
+
+void
+PrivateKey::savePkcs1(std::ostream& os) const
+{
+  bufferSource(*this->toPkcs1()) >> streamSink(os);
+}
+
+void
+PrivateKey::savePkcs1Base64(std::ostream& os) const
+{
+  bufferSource(*this->toPkcs1()) >> base64Encode() >> streamSink(os);
+}
+
+void
+PrivateKey::savePkcs8(std::ostream& os, const char* pw, size_t pwLen) const
+{
+  bufferSource(*this->toPkcs8(pw, pwLen)) >> streamSink(os);
+}
+
+void
+PrivateKey::savePkcs8(std::ostream& os, PasswordCallback pwCallback) const
+{
+  bufferSource(*this->toPkcs8(pwCallback)) >> streamSink(os);
+}
+
+void
+PrivateKey::savePkcs8Base64(std::ostream& os, const char* pw, size_t pwLen) const
+{
+  bufferSource(*this->toPkcs8(pw, pwLen)) >> base64Encode() >> streamSink(os);
+}
+
+void
+PrivateKey::savePkcs8Base64(std::ostream& os, PasswordCallback pwCallback) const
+{
+  bufferSource(*this->toPkcs8(pwCallback)) >> base64Encode() >> streamSink(os);
+}
+
+ConstBufferPtr
+PrivateKey::derivePublicKey() const
+{
+  ENSURE_PRIVATE_KEY_LOADED(m_impl->key);
+
+  uint8_t* pkcs8 = nullptr;
+  int len = i2d_PUBKEY(m_impl->key, &pkcs8);
+
+  if (len <= 0)
+    BOOST_THROW_EXCEPTION(Error("Failed to derive public key"));
+
+  auto result = make_shared<Buffer>(pkcs8, len);
+  OPENSSL_free(pkcs8);
+
+  return result;
+}
+
+ConstBufferPtr
+PrivateKey::decrypt(const uint8_t* cipherText, size_t cipherLen) const
+{
+  ENSURE_PRIVATE_KEY_LOADED(m_impl->key);
+
+  switch (EVP_PKEY_type(m_impl->key->type)) {
+  case EVP_PKEY_RSA:
+    return rsaDecrypt(cipherText, cipherLen);
+  default:
+    BOOST_THROW_EXCEPTION(Error("Decryption is not supported for this key type"));
+  }
+}
+
+void*
+PrivateKey::getEvpPkey() const
+{
+  return m_impl->key;
+}
+
+ConstBufferPtr
+PrivateKey::toPkcs1() const
+{
+  ENSURE_PRIVATE_KEY_LOADED(m_impl->key);
+
+  OpenSSL_add_all_algorithms();
+  detail::Bio mem(BIO_s_mem());
+  int ret = i2d_PrivateKey_bio(mem.get(), m_impl->key);
+  if (ret != 1)
+    BOOST_THROW_EXCEPTION(Error("Cannot convert key into PKCS1 format"));
+
+  int len8 = BIO_pending(mem.get());
+  auto buffer = make_shared<Buffer>(len8);
+  BIO_read(mem.get(), buffer->buf(), len8);
+
+  return buffer;
+}
+
+ConstBufferPtr
+PrivateKey::toPkcs8(const char* pw, size_t pwLen) const
+{
+  ENSURE_PRIVATE_KEY_LOADED(m_impl->key);
+
+  BOOST_ASSERT(std::strlen(pw) == pwLen);
+
+  OpenSSL_add_all_algorithms();
+  detail::Bio mem(BIO_s_mem());
+  int ret = i2d_PKCS8PrivateKey_bio(mem.get(), m_impl->key, EVP_des_cbc(),
+                                    const_cast<char*>(pw), pwLen, nullptr, nullptr);
+  if (ret != 1)
+    BOOST_THROW_EXCEPTION(Error("Cannot convert key into PKCS8 format"));
+
+  int len8 = BIO_pending(mem.get());
+  auto buffer = make_shared<Buffer>(len8);
+  BIO_read(mem.get(), buffer->buf(), len8);
+
+  return buffer;
+}
+
+ConstBufferPtr
+PrivateKey::toPkcs8(PasswordCallback pwCallback) const
+{
+  ENSURE_PRIVATE_KEY_LOADED(m_impl->key);
+
+  OpenSSL_add_all_algorithms();
+  detail::Bio mem(BIO_s_mem());
+  int ret = i2d_PKCS8PrivateKey_bio(mem.get(), m_impl->key, EVP_des_cbc(),
+                                    nullptr, 0,
+                                    passwordCallback, &pwCallback);
+  if (ret != 1)
+    BOOST_THROW_EXCEPTION(Error("Cannot convert key into PKCS8 format"));
+
+  int len8 = BIO_pending(mem.get());
+  auto buffer = make_shared<Buffer>(len8);
+  BIO_read(mem.get(), buffer->buf(), len8);
+
+  return buffer;
+}
+
+ConstBufferPtr
+PrivateKey::rsaDecrypt(const uint8_t* cipherText, size_t cipherLen) const
+{
+  detail::EvpPkeyCtx ctx(m_impl->key);
+
+  if (EVP_PKEY_decrypt_init(ctx.get()) <= 0)
+    BOOST_THROW_EXCEPTION(Error("Failed to initialize decryption context"));
+
+  if (EVP_PKEY_CTX_set_rsa_padding(ctx.get(), RSA_PKCS1_OAEP_PADDING) <= 0)
+    BOOST_THROW_EXCEPTION(Error("Failed to set padding"));
+
+  size_t outlen = 0;
+  // Determine buffer length
+  if (EVP_PKEY_decrypt(ctx.get(), nullptr, &outlen, cipherText, cipherLen) <= 0)
+    BOOST_THROW_EXCEPTION(Error("Failed to estimate output length"));
+
+  auto out = make_shared<Buffer>(outlen);
+
+  if (EVP_PKEY_decrypt(ctx.get(), out->buf(), &outlen, cipherText, cipherLen) <= 0)
+    BOOST_THROW_EXCEPTION(Error("Failed to decrypt cipher text"));
+
+  out->resize(outlen);
+  return out;
+}
+
+static unique_ptr<PrivateKey>
+generateRsaKey(uint32_t keySize)
+{
+  detail::EvpPkeyCtx kctx(EVP_PKEY_RSA);
+
+  int ret = EVP_PKEY_keygen_init(kctx.get());
+  if (ret != 1)
+    BOOST_THROW_EXCEPTION(PrivateKey::Error("Fail to generate RSA key"));
+
+  ret = EVP_PKEY_CTX_set_rsa_keygen_bits(kctx.get(), keySize);
+  if (ret != 1)
+    BOOST_THROW_EXCEPTION(PrivateKey::Error("Fail to generate RSA key"));
+
+  detail::EvpPkey key;
+  ret = EVP_PKEY_keygen(kctx.get(), &key);
+  if (ret != 1)
+    BOOST_THROW_EXCEPTION(PrivateKey::Error("Fail to generate RSA key"));
+
+  detail::Bio mem(BIO_s_mem());
+  i2d_PrivateKey_bio(mem.get(), key.get());
+  int len = BIO_pending(mem.get());
+  Buffer buffer(len);
+  BIO_read(mem.get(), buffer.buf(), len);
+
+  auto privateKey = make_unique<PrivateKey>();
+  privateKey->loadPkcs1(buffer.buf(), buffer.size());
+
+  return privateKey;
+}
+
+static unique_ptr<PrivateKey>
+generateEcKey(uint32_t keySize)
+{
+  detail::EvpPkeyCtx ctx(EVP_PKEY_EC);
+
+  int ret = EVP_PKEY_paramgen_init(ctx.get());
+  if (ret != 1)
+    BOOST_THROW_EXCEPTION(PrivateKey::Error("Fail to generate EC key"));
+
+  switch (keySize) {
+    case 256:
+      ret = EVP_PKEY_CTX_set_ec_paramgen_curve_nid(ctx.get(), NID_X9_62_prime256v1);
+      break;
+    case 384:
+      ret = EVP_PKEY_CTX_set_ec_paramgen_curve_nid(ctx.get(), NID_secp384r1);
+      break;
+    default:
+      BOOST_THROW_EXCEPTION(PrivateKey::Error("Fail to generate EC key"));
+  }
+  if (ret != 1)
+    BOOST_THROW_EXCEPTION(PrivateKey::Error("Fail to generate EC key"));
+
+  detail::EvpPkey params;
+  ret = EVP_PKEY_paramgen(ctx.get(), &params);
+  if (ret != 1)
+    BOOST_THROW_EXCEPTION(PrivateKey::Error("Fail to generate EC key"));
+
+  detail::EvpPkeyCtx kctx(params.get());
+  ret = EVP_PKEY_keygen_init(kctx.get());
+  if (ret != 1)
+    BOOST_THROW_EXCEPTION(PrivateKey::Error("Fail to generate EC key"));
+
+  detail::EvpPkey key;
+  ret = EVP_PKEY_keygen(kctx.get(), &key);
+  if (ret != 1)
+    BOOST_THROW_EXCEPTION(PrivateKey::Error("Fail to generate EC key"));
+
+  detail::Bio mem(BIO_s_mem());
+  i2d_PrivateKey_bio(mem.get(), key.get());
+  int len = BIO_pending(mem.get());
+  Buffer buffer(len);
+  BIO_read(mem.get(), buffer.buf(), len);
+
+  auto privateKey = make_unique<PrivateKey>();
+  privateKey->loadPkcs1(buffer.buf(), buffer.size());
+
+  return privateKey;
+}
+
+unique_ptr<PrivateKey>
+generatePrivateKey(const KeyParams& keyParams)
+{
+  switch (keyParams.getKeyType()) {
+    case KeyType::RSA: {
+      const RsaKeyParams& rsaParams = static_cast<const RsaKeyParams&>(keyParams);
+      return generateRsaKey(rsaParams.getKeySize());
+    }
+    case KeyType::EC: {
+      const EcdsaKeyParams& ecdsaParams = static_cast<const EcdsaKeyParams&>(keyParams);
+      return generateEcKey(ecdsaParams.getKeySize());
+    }
+    default:
+      BOOST_THROW_EXCEPTION(std::invalid_argument("Unsupported asymmetric key type"));
+  }
+}
+
+} // namespace transform
+} // namespace security
+} // namespace ndn
diff --git a/src/security/transform/private-key.hpp b/src/security/transform/private-key.hpp
new file mode 100644
index 0000000..eae0787
--- /dev/null
+++ b/src/security/transform/private-key.hpp
@@ -0,0 +1,264 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/**
+ * Copyright (c) 2013-2016 Regents of the University of California.
+ *
+ * This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
+ *
+ * ndn-cxx library is free software: you can redistribute it and/or modify it under the
+ * terms of the GNU Lesser General Public License as published by the Free Software
+ * Foundation, either version 3 of the License, or (at your option) any later version.
+ *
+ * ndn-cxx library is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE.  See the GNU Lesser General Public License for more details.
+ *
+ * You should have received copies of the GNU General Public License and GNU Lesser
+ * General Public License along with ndn-cxx, e.g., in COPYING.md file.  If not, see
+ * <http://www.gnu.org/licenses/>.
+ *
+ * See AUTHORS.md for complete list of ndn-cxx authors and contributors.
+ */
+
+#ifndef NDN_CXX_SECURITY_TRANSFORM_PRIVATE_KEY_HPP
+#define NDN_CXX_SECURITY_TRANSFORM_PRIVATE_KEY_HPP
+
+#include "public-key.hpp"
+#include "../../encoding/buffer.hpp"
+
+namespace ndn {
+
+class KeyParams;
+
+namespace security {
+namespace transform {
+
+/**
+ * @brief Abstraction of private key in crypto transformation
+ */
+class PrivateKey : noncopyable
+{
+public:
+  class Error : public std::runtime_error
+  {
+  public:
+    explicit
+    Error(const std::string& what)
+      : std::runtime_error(what)
+    {
+    }
+  };
+
+  friend class SignerFilter;
+
+  /**
+   * @brief Callback for application to handle password input
+   *
+   * Password should be stored in @p buf and should not be longer than @p size.  It is
+   * recommended to ask the user to verify the passphrase if @p shouldConfirm is true, e.g., by
+   * prompting for the password twice.
+   */
+  typedef function<int(char* buf, size_t bufSize, bool shouldConfirm)> PasswordCallback;
+
+public:
+  /**
+   * @brief Create a private key instance
+   *
+   * One must call loadXXXX(...) to load private key.
+   */
+  PrivateKey();
+
+  ~PrivateKey();
+
+  /**
+   * @brief Load the private key in PKCS#1 format from a buffer @p buf
+   */
+  void
+  loadPkcs1(const uint8_t* buf, size_t size);
+
+  /**
+   * @brief Load the private key in PKCS#1 format from a stream @p is
+   */
+  void
+  loadPkcs1(std::istream& is);
+
+  /**
+   * @brief Load the private key in base64-encoded PKCS#1 format from a buffer @p buf
+   */
+  void
+  loadPkcs1Base64(const uint8_t* buf, size_t size);
+
+  /**
+   * @brief Load the private key in base64-encoded PKCS#1 format from a stream @p is
+   */
+  void
+  loadPkcs1Base64(std::istream& is);
+
+  /**
+   * @brief Load the private key in encrypted PKCS#8 format from a buffer @p buf with passphrase @p pw
+   *
+   * @pre strlen(pw) == pwLen
+   */
+  void
+  loadPkcs8(const uint8_t* buf, size_t size, const char* pw, size_t pwLen);
+
+  /**
+   * @brief Load the private key in encrypted PKCS#8 format from a buffer @p buf with
+   *        passphrase obtained from @p pwCallback
+   *
+   * The default password callback is provided by OpenSSL
+   */
+  void
+  loadPkcs8(const uint8_t* buf, size_t size, PasswordCallback pwCallback = nullptr);
+
+  /**
+   * @brief Load the private key in encrypted PKCS#8 format from a stream @p is with passphrase @p pw
+   *
+   * @pre strlen(pw) == pwLen
+   */
+  void
+  loadPkcs8(std::istream& is, const char* pw, size_t pwLen);
+
+  /**
+   * @brief Load the private key in encrypted PKCS#8 format from a stream @p is with passphrase
+   *        obtained from @p pwCallback
+   *
+   * The default password callback is provided by OpenSSL
+   */
+  void
+  loadPkcs8(std::istream& is, PasswordCallback pwCallback = nullptr);
+
+  /**
+   * @brief Load the private key in base64-encoded encrypted PKCS#8 format from a buffer @p buf
+   *        with passphrase @p pw
+   *
+   * @pre strlen(pw) == pwLen
+   */
+  void
+  loadPkcs8Base64(const uint8_t* buf, size_t size, const char* pw, size_t pwLen);
+
+  /**
+   * @brief Load the private key in encrypted PKCS#8 format from a buffer @p buf with
+   *        passphrase obtained from @p pwCallback
+   *
+   * The default password callback is provided by OpenSSL
+   */
+  void
+  loadPkcs8Base64(const uint8_t* buf, size_t size, PasswordCallback pwCallback = nullptr);
+
+  /**
+   * @brief Load the private key in base64-encoded encrypted PKCS#8 format from a stream @p is
+   *        with passphrase @p pw
+   *
+   * @pre strlen(pw) == pwLen
+   */
+  void
+  loadPkcs8Base64(std::istream& is, const char* pw, size_t pwLen);
+
+  /**
+   * @brief Load the private key in base64-encoded encrypted PKCS#8 format from a stream @p is
+   *        with passphrase obtained from @p pwCallback
+   *
+   * The default password callback is provided by OpenSSL
+   */
+  void
+  loadPkcs8Base64(std::istream& is, PasswordCallback pwCallback = nullptr);
+
+  /**
+   * @brief Save the private key in PKCS#1 format into a stream @p os
+   */
+  void
+  savePkcs1(std::ostream& os) const;
+
+  /**
+   * @brief Save the private key in base64-encoded PKCS#1 format into a stream @p os
+   */
+  void
+  savePkcs1Base64(std::ostream& os) const;
+
+  /**
+   * @brief Save the private key in encrypted PKCS#8 format into a stream @p os
+   */
+  void
+  savePkcs8(std::ostream& os, const char* pw, size_t pwLen) const;
+
+  /**
+   * @brief Save the private key in encrypted PKCS#8 format into a stream @p os with passphrase
+   *        obtained from @p pwCallback
+   *
+   * The default password callback is provided by OpenSSL
+   */
+  void
+  savePkcs8(std::ostream& os, PasswordCallback pwCallback = nullptr) const;
+
+  /**
+   * @brief Save the private key in base64-encoded encrypted PKCS#8 format into a stream @p os
+   */
+  void
+  savePkcs8Base64(std::ostream& os, const char* pw, size_t pwLen) const;
+
+  /**
+   * @brief Save the private key in base64-encoded encrypted PKCS#8 format into a stream @p os
+   *        with passphrase obtained from @p pwCallback
+   *
+   * The default password callback is provided by OpenSSL
+   */
+  void
+  savePkcs8Base64(std::ostream& os, PasswordCallback pwCallback = nullptr) const;
+
+  /**
+   * @return Public key bits in PKCS#8 format
+   */
+  ConstBufferPtr
+  derivePublicKey() const;
+
+  /**
+   * @return Plain text of @p cipherText decrypted using the private key.
+   *
+   * Only RSA encryption is supported for now.
+   */
+  ConstBufferPtr
+  decrypt(const uint8_t* cipherText, size_t cipherLen) const;
+
+private:
+  /**
+   * @return A pointer to an EVP_PKEY instance.
+   *
+   * One need to explicitly cast the return value to EVP_PKEY*.
+   */
+  void*
+  getEvpPkey() const;
+
+private:
+  ConstBufferPtr
+  toPkcs1() const;
+
+  ConstBufferPtr
+  toPkcs8(const char* pw, size_t pwLen) const;
+
+  ConstBufferPtr
+  toPkcs8(PasswordCallback pwCallback = nullptr) const;
+
+  ConstBufferPtr
+  rsaDecrypt(const uint8_t* cipherText, size_t cipherLen) const;
+
+private:
+  class Impl;
+  unique_ptr<Impl> m_impl;
+};
+
+/**
+ * @brief generate a private key according to @p keyParams.
+ *
+ * @note the public key can be derived from the private key
+ *
+ * @throw std::argument_error if the key type is not supported
+ * @throw std::runtime_error when failing to generate the key
+ */
+unique_ptr<PrivateKey>
+generatePrivateKey(const KeyParams& keyParams);
+
+} // namespace transform
+} // namespace security
+} // namespace ndn
+
+#endif // NDN_CXX_SECURITY_TRANSFORM_PRIVATE_KEY_HPP
diff --git a/src/security/transform/public-key.cpp b/src/security/transform/public-key.cpp
new file mode 100644
index 0000000..a0116e9
--- /dev/null
+++ b/src/security/transform/public-key.cpp
@@ -0,0 +1,198 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/**
+ * Copyright (c) 2013-2016 Regents of the University of California.
+ *
+ * This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
+ *
+ * ndn-cxx library is free software: you can redistribute it and/or modify it under the
+ * terms of the GNU Lesser General Public License as published by the Free Software
+ * Foundation, either version 3 of the License, or (at your option) any later version.
+ *
+ * ndn-cxx library is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE.  See the GNU Lesser General Public License for more details.
+ *
+ * You should have received copies of the GNU General Public License and GNU Lesser
+ * General Public License along with ndn-cxx, e.g., in COPYING.md file.  If not, see
+ * <http://www.gnu.org/licenses/>.
+ *
+ * See AUTHORS.md for complete list of ndn-cxx authors and contributors.
+ */
+
+#include "public-key.hpp"
+#include "buffer-source.hpp"
+#include "stream-source.hpp"
+#include "base64-encode.hpp"
+#include "base64-decode.hpp"
+#include "stream-sink.hpp"
+#include "../../encoding/buffer-stream.hpp"
+#include "../detail/openssl-helper.hpp"
+
+#define ENSURE_PUBLIC_KEY_LOADED(key) \
+  do { \
+    if (key == nullptr) \
+      BOOST_THROW_EXCEPTION(Error("Public key has not been loaded yet")); \
+  } while (false)
+
+namespace ndn {
+namespace security {
+namespace transform {
+
+class PublicKey::Impl
+{
+public:
+  Impl()
+    : key(nullptr)
+  {
+  }
+
+  ~Impl()
+  {
+    EVP_PKEY_free(key);
+  }
+
+public:
+  EVP_PKEY* key;
+};
+
+PublicKey::PublicKey()
+  : m_impl(new Impl)
+{
+}
+
+PublicKey::~PublicKey() = default;
+
+KeyType
+PublicKey::getKeyType() const
+{
+  ENSURE_PUBLIC_KEY_LOADED(m_impl->key);
+
+  switch (EVP_PKEY_type(m_impl->key->type)) {
+  case EVP_PKEY_RSA:
+    return KeyType::RSA;
+  case EVP_PKEY_EC:
+    return KeyType::EC;
+  default:
+    BOOST_THROW_EXCEPTION(Error("Public key type is not recognized"));
+  }
+}
+
+void
+PublicKey::loadPkcs8(const uint8_t* buf, size_t size)
+{
+  m_impl->key = d2i_PUBKEY(nullptr, &buf, size);
+
+  ENSURE_PUBLIC_KEY_LOADED(m_impl->key);
+}
+
+void
+PublicKey::loadPkcs8(std::istream& is)
+{
+  OBufferStream os;
+  {
+    using namespace transform;
+    streamSource(is) >> streamSink(os);
+  }
+  this->loadPkcs8(os.buf()->buf(), os.buf()->size());
+}
+
+void
+PublicKey::loadPkcs8Base64(const uint8_t* buf, size_t size)
+{
+  OBufferStream os;
+  {
+    using namespace transform;
+    bufferSource(buf, size) >> base64Decode() >> streamSink(os);
+  }
+  this->loadPkcs8(os.buf()->buf(), os.buf()->size());
+}
+
+void
+PublicKey::loadPkcs8Base64(std::istream& is)
+{
+  OBufferStream os;
+  {
+    using namespace transform;
+    streamSource(is) >> base64Decode() >> streamSink(os);
+  }
+  this->loadPkcs8(os.buf()->buf(), os.buf()->size());
+}
+
+void
+PublicKey::savePkcs8(std::ostream& os) const
+{
+  using namespace transform;
+  bufferSource(*this->toPkcs8()) >> streamSink(os);
+}
+
+void
+PublicKey::savePkcs8Base64(std::ostream& os) const
+{
+  using namespace transform;
+  bufferSource(*this->toPkcs8()) >> base64Encode() >> streamSink(os);
+}
+
+ConstBufferPtr
+PublicKey::encrypt(const uint8_t* plainText, size_t plainLen) const
+{
+  ENSURE_PUBLIC_KEY_LOADED(m_impl->key);
+
+  switch (EVP_PKEY_type(m_impl->key->type)) {
+  case EVP_PKEY_RSA:
+    return rsaEncrypt(plainText, plainLen);
+  default:
+    BOOST_THROW_EXCEPTION(Error("Encryption is not supported for this key type"));
+  }
+}
+
+void*
+PublicKey::getEvpPkey() const
+{
+  return m_impl->key;
+}
+
+ConstBufferPtr
+PublicKey::toPkcs8() const
+{
+  ENSURE_PUBLIC_KEY_LOADED(m_impl->key);
+
+  uint8_t* pkcs8 = nullptr;
+  int len = i2d_PUBKEY(m_impl->key, &pkcs8);
+
+  if (pkcs8 == nullptr)
+    BOOST_THROW_EXCEPTION(Error("Failed to convert to pkcs8 format"));
+
+  auto buffer = make_shared<Buffer>(pkcs8, len);
+  OPENSSL_free(pkcs8);
+
+  return buffer;
+}
+
+ConstBufferPtr
+PublicKey::rsaEncrypt(const uint8_t* plainText, size_t plainLen) const
+{
+  detail::EvpPkeyCtx ctx(m_impl->key);
+
+  if (EVP_PKEY_encrypt_init(ctx.get()) <= 0)
+    BOOST_THROW_EXCEPTION(Error("Failed to initialize encryption context"));
+
+  if (EVP_PKEY_CTX_set_rsa_padding(ctx.get(), RSA_PKCS1_OAEP_PADDING) <= 0)
+    BOOST_THROW_EXCEPTION(Error("Failed to set padding"));
+
+  size_t outlen = 0;
+  // Determine buffer length
+  if (EVP_PKEY_encrypt(ctx.get(), nullptr, &outlen, plainText, plainLen) <= 0)
+    BOOST_THROW_EXCEPTION(Error("Failed to estimate output length"));
+
+  auto out = make_shared<Buffer>(outlen);
+
+  if (EVP_PKEY_encrypt(ctx.get(), out->buf(), &outlen, plainText, plainLen) <= 0)
+    BOOST_THROW_EXCEPTION(Error("Failed to decrypt cipher text"));
+
+  out->resize(outlen);
+  return out;
+}
+
+} // namespace transform
+} // namespace security
+} // namespace ndn
diff --git a/src/security/transform/public-key.hpp b/src/security/transform/public-key.hpp
new file mode 100644
index 0000000..169b9e0
--- /dev/null
+++ b/src/security/transform/public-key.hpp
@@ -0,0 +1,137 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/**
+ * Copyright (c) 2013-2016 Regents of the University of California.
+ *
+ * This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
+ *
+ * ndn-cxx library is free software: you can redistribute it and/or modify it under the
+ * terms of the GNU Lesser General Public License as published by the Free Software
+ * Foundation, either version 3 of the License, or (at your option) any later version.
+ *
+ * ndn-cxx library is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE.  See the GNU Lesser General Public License for more details.
+ *
+ * You should have received copies of the GNU General Public License and GNU Lesser
+ * General Public License along with ndn-cxx, e.g., in COPYING.md file.  If not, see
+ * <http://www.gnu.org/licenses/>.
+ *
+ * See AUTHORS.md for complete list of ndn-cxx authors and contributors.
+ */
+
+#ifndef NDN_CXX_SECURITY_TRANSFORM_PUBLIC_KEY_HPP
+#define NDN_CXX_SECURITY_TRANSFORM_PUBLIC_KEY_HPP
+
+#include "../security-common.hpp"
+#include "../../encoding/buffer.hpp"
+
+namespace ndn {
+namespace security {
+namespace transform {
+
+class VerifierFilter;
+
+/**
+ * @brief Abstraction of public key in crypto transformation
+ */
+class PublicKey : noncopyable
+{
+public:
+  class Error : public std::runtime_error
+  {
+  public:
+    explicit
+    Error(const std::string& what)
+      : std::runtime_error(what)
+    {
+    }
+  };
+
+  friend class VerifierFilter;
+
+public:
+  /**
+   * @brief Create a public key instance
+   *
+   * One must call loadXXXX(...) to load public key.
+   */
+  PublicKey();
+
+  ~PublicKey();
+
+  /**
+   * @brief Get the type of the public key
+   */
+  KeyType
+  getKeyType() const;
+
+  /**
+   * @brief Load the public key in PKCS#8 format from a buffer @p buf
+   */
+  void
+  loadPkcs8(const uint8_t* buf, size_t size);
+
+  /**
+   * @brief Load the public key in PKCS#8 format from a stream @p is
+   */
+  void
+  loadPkcs8(std::istream& is);
+
+  /**
+   * @brief Load the public key in base64-encoded PKCS#8 format from a buffer @p buf
+   */
+  void
+  loadPkcs8Base64(const uint8_t* buf, size_t size);
+
+  /**
+   * @brief Load the public key in base64-encoded PKCS#8 format from a stream @p is
+   */
+  void
+  loadPkcs8Base64(std::istream& is);
+
+  /**
+   * @brief Save the public key in PKCS#8 format into a stream @p os
+   */
+  void
+  savePkcs8(std::ostream& os) const;
+
+  /**
+   * @brief Save the public key in base64-encoded PKCS#8 format into a stream @p os
+   */
+  void
+  savePkcs8Base64(std::ostream& os) const;
+
+  /**
+   * @return Cipher text of @p plainText encrypted using the public key.
+   *
+   * Only RSA encryption is supported for now.
+   */
+  ConstBufferPtr
+  encrypt(const uint8_t* plainText, size_t plainLen) const;
+
+private:
+  /**
+   * @return A pointer to an EVP_PKEY instance.
+   *
+   * One need to explicitly cast the return value to EVP_PKEY*.
+   */
+  void*
+  getEvpPkey() const;
+
+private:
+  ConstBufferPtr
+  toPkcs8() const;
+
+  ConstBufferPtr
+  rsaEncrypt(const uint8_t* plainText, size_t plainLen) const;
+
+private:
+  class Impl;
+  unique_ptr<Impl> m_impl;
+};
+
+} // namespace transform
+} // namespace security
+} // namespace ndn
+
+#endif // NDN_CXX_SECURITY_TRANSFORM_PUBLIC_KEY_HPP
