90
common/exception.hpp
Normal file
90
common/exception.hpp
Normal file
@@ -0,0 +1,90 @@
|
||||
#pragma once
|
||||
#include <exception>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <utility>
|
||||
|
||||
namespace nkg {
|
||||
|
||||
class exception : public std::exception {
|
||||
private:
|
||||
int m_source_line;
|
||||
std::string m_source_file;
|
||||
std::string m_custom_message;
|
||||
std::vector<std::string> m_hints;
|
||||
|
||||
public:
|
||||
[[noreturn]]
|
||||
static void trap_then_terminate() {
|
||||
#if _MSC_VER
|
||||
__debugbreak();
|
||||
#elif defined(__GNUC__) || defined(__GNUG__) || defined(__clang__)
|
||||
__builtin_trap();
|
||||
|
||||
#else
|
||||
#error "exception.hpp: unknown compiler is detected."
|
||||
#endif
|
||||
std::terminate();
|
||||
}
|
||||
|
||||
exception(std::string_view file, int line, std::string_view message) noexcept :
|
||||
std::exception(), m_source_line(line), m_source_file(file), m_custom_message(message) {}
|
||||
|
||||
exception(const exception&) noexcept = default;
|
||||
exception(exception&&) noexcept = default;
|
||||
|
||||
exception& operator=(const exception&) noexcept = default;
|
||||
exception& operator=(exception&&) noexcept = default;
|
||||
|
||||
[[nodiscard]]
|
||||
int source_line() const noexcept {
|
||||
return m_source_line;
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
const std::string& source_file() const noexcept {
|
||||
return m_source_file;
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
const std::string& custom_message() const noexcept {
|
||||
return m_custom_message;
|
||||
}
|
||||
|
||||
exception&& push_hint(std::string_view hint) noexcept {
|
||||
m_hints.emplace_back(hint);
|
||||
return std::move(*this);
|
||||
}
|
||||
|
||||
exception&& pop_hint() noexcept {
|
||||
m_hints.pop_back();
|
||||
return std::move(*this);
|
||||
}
|
||||
|
||||
const std::vector<std::string>& hints() const noexcept {
|
||||
return m_hints;
|
||||
}
|
||||
|
||||
virtual const char* what() const noexcept override {
|
||||
return m_custom_message.c_str();
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
virtual bool error_code_exists() const noexcept {
|
||||
return false;
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
virtual intptr_t error_code() const noexcept {
|
||||
trap_then_terminate();
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
virtual const std::string& error_string() const noexcept {
|
||||
trap_then_terminate();
|
||||
}
|
||||
|
||||
virtual ~exception() override = default;
|
||||
};
|
||||
|
||||
}
|
||||
12
common/exceptions/index_exception.hpp
Normal file
12
common/exceptions/index_exception.hpp
Normal file
@@ -0,0 +1,12 @@
|
||||
#pragma once
|
||||
#include "../exception.hpp"
|
||||
|
||||
namespace nkg::exceptions {
|
||||
|
||||
class index_exception : public ::nkg::exception {
|
||||
public:
|
||||
index_exception(std::string_view file, int line, std::string_view message) noexcept :
|
||||
::nkg::exception(file, line, message) {}
|
||||
};
|
||||
|
||||
}
|
||||
12
common/exceptions/key_exception.hpp
Normal file
12
common/exceptions/key_exception.hpp
Normal file
@@ -0,0 +1,12 @@
|
||||
#pragma once
|
||||
#include "../exception.hpp"
|
||||
|
||||
namespace nkg::exceptions {
|
||||
|
||||
class key_exception : public ::nkg::exception {
|
||||
public:
|
||||
key_exception(std::string_view file, int line, std::string_view message) noexcept :
|
||||
::nkg::exception(file, line, message) {}
|
||||
};
|
||||
|
||||
}
|
||||
12
common/exceptions/operation_canceled_exception.hpp
Normal file
12
common/exceptions/operation_canceled_exception.hpp
Normal file
@@ -0,0 +1,12 @@
|
||||
#pragma once
|
||||
#include "../exception.hpp"
|
||||
|
||||
namespace nkg::exceptions {
|
||||
|
||||
class operation_canceled_exception : public ::nkg::exception {
|
||||
public:
|
||||
operation_canceled_exception(std::string_view file, int line, std::string_view message) noexcept :
|
||||
::nkg::exception(file, line, message) {}
|
||||
};
|
||||
|
||||
}
|
||||
36
common/exceptions/unix_exception.hpp
Normal file
36
common/exceptions/unix_exception.hpp
Normal file
@@ -0,0 +1,36 @@
|
||||
#pragma once
|
||||
#include <errno.h>
|
||||
#include <string.h>
|
||||
#include "../exception.hpp"
|
||||
|
||||
namespace nkg::exceptions {
|
||||
|
||||
class unix_exception : public ::nkg::exception {
|
||||
public:
|
||||
using error_code_t = decltype(errno);
|
||||
|
||||
private:
|
||||
error_code_t m_error_code;
|
||||
std::string m_error_string;
|
||||
|
||||
public:
|
||||
unix_exception(std::string_view file, int line, error_code_t unix_errno, std::string_view message) noexcept :
|
||||
::nkg::exception(file, line, message), m_error_code(unix_errno), m_error_string(strerror(unix_errno)) {}
|
||||
|
||||
[[nodiscard]]
|
||||
virtual bool error_code_exists() const noexcept override {
|
||||
return true;
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
virtual intptr_t error_code() const noexcept override {
|
||||
return m_error_code;
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
virtual const std::string& error_string() const noexcept override {
|
||||
return m_error_string;
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
21
common/resource_traits/cxx_dynamic_array_traits.hpp
Normal file
21
common/resource_traits/cxx_dynamic_array_traits.hpp
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
|
||||
namespace nkg::resource_traits {
|
||||
|
||||
template<typename element_t>
|
||||
struct cxx_dynamic_array_traits {
|
||||
using handle_t = element_t*;
|
||||
|
||||
static constexpr handle_t invalid_value = nullptr;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
|
||||
static void release(const handle_t& handle) {
|
||||
delete[] handle;
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
21
common/resource_traits/cxx_object_traits.hpp
Normal file
21
common/resource_traits/cxx_object_traits.hpp
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
|
||||
namespace nkg::resource_traits {
|
||||
|
||||
template<typename object_t>
|
||||
struct cxx_object_traits {
|
||||
using handle_t = object_t*;
|
||||
|
||||
static constexpr handle_t invalid_value = nullptr;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
|
||||
static void release(const handle_t& handle) {
|
||||
delete handle;
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
20
common/resource_traits/keystone/keystone_alloc.hpp
Normal file
20
common/resource_traits/keystone/keystone_alloc.hpp
Normal file
@@ -0,0 +1,20 @@
|
||||
#pragma once
|
||||
#include <keystone/keystone.h>
|
||||
|
||||
namespace nkg::resource_traits::keystone {
|
||||
|
||||
struct keystone_alloc {
|
||||
using handle_t = unsigned char*;
|
||||
|
||||
static constexpr handle_t invalid_value = nullptr;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
|
||||
static void release(const handle_t& handle) noexcept {
|
||||
ks_free(handle);
|
||||
}
|
||||
};
|
||||
}
|
||||
21
common/resource_traits/keystone/keystone_handle.hpp
Normal file
21
common/resource_traits/keystone/keystone_handle.hpp
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
#include <keystone/keystone.h>
|
||||
|
||||
namespace nkg::resource_traits::keystone {
|
||||
|
||||
struct keystone_handle {
|
||||
using handle_t = ks_engine*;
|
||||
|
||||
static constexpr handle_t invalid_value = nullptr;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
|
||||
static void release(const handle_t& handle) {
|
||||
ks_close(handle);
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
21
common/resource_traits/openssl/bignum.hpp
Normal file
21
common/resource_traits/openssl/bignum.hpp
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
#include <openssl/bn.h>
|
||||
|
||||
namespace nkg::resource_traits::openssl {
|
||||
|
||||
struct bignum {
|
||||
using handle_t = BIGNUM*;
|
||||
|
||||
static constexpr handle_t invalid_value = nullptr;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
|
||||
static void release(const handle_t& handle) noexcept {
|
||||
BN_free(handle);
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
21
common/resource_traits/openssl/bio.hpp
Normal file
21
common/resource_traits/openssl/bio.hpp
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
#include <openssl/bio.h>
|
||||
|
||||
namespace nkg::resource_traits::openssl {
|
||||
|
||||
struct bio {
|
||||
using handle_t = BIO*;
|
||||
|
||||
static constexpr handle_t invalid_value = nullptr;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
|
||||
static void release(const handle_t& handle) noexcept {
|
||||
BIO_free(handle);
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
21
common/resource_traits/openssl/bio_chain.hpp
Normal file
21
common/resource_traits/openssl/bio_chain.hpp
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
#include <openssl/bio.h>
|
||||
|
||||
namespace nkg::resource_traits::openssl {
|
||||
|
||||
struct bio_chain {
|
||||
using handle_t = BIO*;
|
||||
|
||||
static constexpr handle_t invalid_value = nullptr;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
|
||||
static void release(const handle_t& handle) noexcept {
|
||||
BIO_free_all(handle);
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
21
common/resource_traits/openssl/rsa.hpp
Normal file
21
common/resource_traits/openssl/rsa.hpp
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
#include <openssl/rsa.h>
|
||||
|
||||
namespace nkg::resource_traits::openssl {
|
||||
|
||||
struct rsa {
|
||||
using handle_t = RSA*;
|
||||
|
||||
static constexpr handle_t invalid_value = nullptr;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
|
||||
static void release(const handle_t& handle) noexcept {
|
||||
RSA_free(handle);
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
21
common/resource_traits/unicorn/unicorn_alloc.hpp
Normal file
21
common/resource_traits/unicorn/unicorn_alloc.hpp
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
#include <unicorn/unicorn.h>
|
||||
|
||||
namespace nkg::resource_traits::unicorn {
|
||||
|
||||
struct unicorn_alloc {
|
||||
using handle_t = void*;
|
||||
|
||||
static constexpr handle_t invalid_value = nullptr;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
|
||||
static void release(const handle_t& handle) {
|
||||
uc_free(handle);
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
21
common/resource_traits/unicorn/unicorn_handle.hpp
Normal file
21
common/resource_traits/unicorn/unicorn_handle.hpp
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
#include <unicorn/unicorn.h>
|
||||
|
||||
namespace nkg::resource_traits::unicorn {
|
||||
|
||||
struct unicorn_handle {
|
||||
using handle_t = uc_engine*;
|
||||
|
||||
static constexpr handle_t invalid_value = nullptr;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
|
||||
static void release(const handle_t& handle) {
|
||||
uc_close(handle);
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
21
common/resource_traits/unix_os/file_descriptor.hpp
Normal file
21
common/resource_traits/unix_os/file_descriptor.hpp
Normal file
@@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
#include <unistd.h>
|
||||
|
||||
namespace nkg::resource_traits::unix_os {
|
||||
|
||||
struct file_descriptor {
|
||||
using handle_t = int;
|
||||
|
||||
static constexpr handle_t invalid_value = -1;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
|
||||
static void release(const handle_t& handle) {
|
||||
close(handle);
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
19
common/resource_traits/unix_os/map_view.hpp
Normal file
19
common/resource_traits/unix_os/map_view.hpp
Normal file
@@ -0,0 +1,19 @@
|
||||
#pragma once
|
||||
#include <errno.h>
|
||||
#include <unistd.h>
|
||||
#include <sys/mman.h>
|
||||
|
||||
namespace nkg::resource_traits::unix_os {
|
||||
|
||||
struct map_view {
|
||||
using handle_t = void*;
|
||||
|
||||
static inline const handle_t invalid_value = MAP_FAILED;
|
||||
|
||||
[[nodiscard]]
|
||||
static bool is_valid(const handle_t& handle) noexcept {
|
||||
return handle != invalid_value;
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
238
common/resource_wrapper.hpp
Normal file
238
common/resource_wrapper.hpp
Normal file
@@ -0,0 +1,238 @@
|
||||
#pragma once
|
||||
#include <type_traits>
|
||||
#include <utility>
|
||||
|
||||
namespace nkg {
|
||||
|
||||
template<typename resource_traits_t, typename releaser_t = void>
|
||||
class resource_wrapper {
|
||||
public:
|
||||
using handle_t = typename resource_traits_t::handle_t;
|
||||
static_assert(std::is_trivial_v<handle_t> && std::is_standard_layout_v<handle_t>, "`resource_wrapper` requires a handle with POD type.");
|
||||
|
||||
private:
|
||||
handle_t m_handle;
|
||||
releaser_t m_releaser;
|
||||
|
||||
public:
|
||||
template<typename releaser_arg_t>
|
||||
resource_wrapper(releaser_arg_t&& releaser) noexcept :
|
||||
m_handle(resource_traits_t::invalid_value),
|
||||
m_releaser(std::forward<releaser_arg_t>(releaser)) {}
|
||||
|
||||
template<typename releaser_arg_t>
|
||||
resource_wrapper(const handle_t& handle, releaser_arg_t&& releaser) noexcept :
|
||||
m_handle(handle),
|
||||
m_releaser(std::forward<releaser_arg_t>(releaser)) {}
|
||||
|
||||
template<typename releaser_arg_t>
|
||||
resource_wrapper(resource_traits_t, releaser_arg_t&& releaser) noexcept :
|
||||
m_handle(resource_traits_t::invalid_value),
|
||||
m_releaser(std::forward<releaser_arg_t>(releaser)) {}
|
||||
|
||||
template<typename releaser_arg_t>
|
||||
resource_wrapper(resource_traits_t, const handle_t& handle, releaser_arg_t&& releaser) noexcept :
|
||||
m_handle(handle),
|
||||
m_releaser(std::forward<releaser_t>(releaser)) {}
|
||||
|
||||
//
|
||||
// `resource_wrapper` does not allow copy-construct
|
||||
//
|
||||
resource_wrapper(const resource_wrapper& other) = delete;
|
||||
|
||||
//
|
||||
// `resource_wrapper` allows move-construct.
|
||||
//
|
||||
resource_wrapper(resource_wrapper&& other) noexcept :
|
||||
m_handle(other.m_handle),
|
||||
m_releaser(std::move(other.m_releaser))
|
||||
{
|
||||
other.m_handle = resource_traits_t::invalid_value;
|
||||
}
|
||||
|
||||
//
|
||||
// `resource_wrapper` does not allow to copy.
|
||||
//
|
||||
resource_wrapper& operator=(const resource_wrapper& other) = delete;
|
||||
|
||||
//
|
||||
// `resource_wrapper` allows to move.
|
||||
//
|
||||
resource_wrapper& operator=(resource_wrapper&& other) noexcept {
|
||||
if (this != std::addressof(other)) {
|
||||
m_handle = other.m_handle;
|
||||
m_releaser = std::move(other.m_releaser);
|
||||
other.m_handle = resource_traits_t::invalid_value;
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
template<typename ptr_t = handle_t, std::enable_if_t<std::is_pointer_v<handle_t>, ptr_t> = nullptr>
|
||||
[[nodiscard]]
|
||||
ptr_t operator->() const noexcept {
|
||||
return m_handle;
|
||||
}
|
||||
|
||||
template<typename as_t>
|
||||
[[nodiscard]]
|
||||
as_t as() const noexcept {
|
||||
return reinterpret_cast<as_t>(m_handle);
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
bool is_valid() const noexcept {
|
||||
return resource_traits_t::is_valid(m_handle);
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
const handle_t& get() const noexcept {
|
||||
return m_handle;
|
||||
}
|
||||
|
||||
template<typename as_t = handle_t>
|
||||
[[nodiscard]]
|
||||
as_t* unsafe_addressof() noexcept {
|
||||
return reinterpret_cast<as_t*>(std::addressof(m_handle));
|
||||
}
|
||||
|
||||
void set(const handle_t& handle) {
|
||||
if (is_valid()) {
|
||||
m_releaser(m_handle);
|
||||
}
|
||||
m_handle = handle;
|
||||
}
|
||||
|
||||
void discard() noexcept {
|
||||
m_handle = resource_traits_t::invalid_value;
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
handle_t transfer() noexcept {
|
||||
handle_t t = m_handle;
|
||||
m_handle = resource_traits_t::invalid_value;
|
||||
return t;
|
||||
}
|
||||
|
||||
void release() {
|
||||
if (is_valid()) {
|
||||
m_releaser(m_handle);
|
||||
m_handle = resource_traits_t::invalid_value;
|
||||
}
|
||||
}
|
||||
|
||||
~resource_wrapper() {
|
||||
release();
|
||||
}
|
||||
};
|
||||
|
||||
template<typename resource_traits_t>
|
||||
class resource_wrapper<resource_traits_t, void> {
|
||||
public:
|
||||
using handle_t = typename resource_traits_t::handle_t;
|
||||
static_assert(std::is_trivial_v<handle_t>&& std::is_standard_layout_v<handle_t>, "`resource_wrapper` requires a handle with POD type.");
|
||||
|
||||
private:
|
||||
handle_t m_handle;
|
||||
|
||||
public:
|
||||
resource_wrapper() noexcept :
|
||||
m_handle(resource_traits_t::invalid_value) {}
|
||||
|
||||
resource_wrapper(const handle_t& handle) noexcept :
|
||||
m_handle(handle) {}
|
||||
|
||||
resource_wrapper(resource_traits_t) noexcept :
|
||||
m_handle(resource_traits_t::invalid_value) {}
|
||||
|
||||
resource_wrapper(resource_traits_t, const handle_t& handle) noexcept :
|
||||
m_handle(handle) {}
|
||||
|
||||
resource_wrapper(const resource_wrapper& other) = delete;
|
||||
|
||||
resource_wrapper(resource_wrapper&& other) noexcept :
|
||||
m_handle(other.m_handle)
|
||||
{
|
||||
other.m_handle = resource_traits_t::invalid_value;
|
||||
}
|
||||
|
||||
resource_wrapper& operator=(const resource_wrapper& other) = delete;
|
||||
|
||||
resource_wrapper& operator=(resource_wrapper&& other) noexcept {
|
||||
if (this != std::addressof(other)) {
|
||||
m_handle = other.m_handle;
|
||||
other.m_handle = resource_traits_t::invalid_value;
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
template<typename ptr_t = handle_t, std::enable_if_t<std::is_pointer_v<handle_t>, ptr_t> = nullptr>
|
||||
[[nodiscard]]
|
||||
ptr_t operator->() const noexcept {
|
||||
return m_handle;
|
||||
}
|
||||
|
||||
template<typename as_t>
|
||||
[[nodiscard]]
|
||||
as_t as() const noexcept {
|
||||
return reinterpret_cast<as_t>(m_handle);
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
bool is_valid() const noexcept {
|
||||
return resource_traits_t::is_valid(m_handle);
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
const handle_t& get() const noexcept {
|
||||
return m_handle;
|
||||
}
|
||||
|
||||
template<typename as_t = handle_t>
|
||||
[[nodiscard]]
|
||||
as_t* unsafe_addressof() noexcept {
|
||||
return reinterpret_cast<as_t*>(std::addressof(m_handle));
|
||||
}
|
||||
|
||||
void set(const handle_t& handle) {
|
||||
if (is_valid()) {
|
||||
resource_traits_t::release(m_handle);
|
||||
}
|
||||
m_handle = handle;
|
||||
}
|
||||
|
||||
void discard() noexcept {
|
||||
m_handle = resource_traits_t::invalid_value;
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
handle_t transfer() noexcept {
|
||||
handle_t t = m_handle;
|
||||
m_handle = resource_traits_t::invalid_value;
|
||||
return t;
|
||||
}
|
||||
|
||||
void release() {
|
||||
if (is_valid()) {
|
||||
resource_traits_t::release(m_handle);
|
||||
m_handle = resource_traits_t::invalid_value;
|
||||
}
|
||||
}
|
||||
|
||||
~resource_wrapper() {
|
||||
release();
|
||||
}
|
||||
};
|
||||
|
||||
template<typename resource_traits_t>
|
||||
resource_wrapper(resource_traits_t) ->
|
||||
resource_wrapper<resource_traits_t, void>;
|
||||
|
||||
template<typename resource_traits_t, typename arg_t>
|
||||
resource_wrapper(resource_traits_t, arg_t&&) ->
|
||||
resource_wrapper<resource_traits_t, std::conditional_t<!std::is_same_v<std::remove_cv_t<std::remove_reference_t<arg_t>>, typename resource_traits_t::handle_t>, std::remove_reference_t<arg_t>, void>>;
|
||||
|
||||
template<typename resource_traits_t, typename releaser_t, typename handle_t = typename resource_traits_t::handle_t>
|
||||
resource_wrapper(resource_traits_t, const handle_t&, releaser_t&&) ->
|
||||
resource_wrapper<resource_traits_t, std::remove_reference_t<releaser_t>>;
|
||||
|
||||
}
|
||||
327
common/rsa_cipher.cpp
Normal file
327
common/rsa_cipher.cpp
Normal file
@@ -0,0 +1,327 @@
|
||||
#include "rsa_cipher.hpp"
|
||||
#include <openssl/pem.h>
|
||||
#include <openssl/bio.h>
|
||||
|
||||
#include "resource_traits/openssl/bio.hpp"
|
||||
#include "resource_traits/openssl/bignum.hpp"
|
||||
|
||||
#define NKG_CURRENT_SOURCE_FILE() u8".\\common\\rsa_cipher.cpp"
|
||||
#define NKG_CURRENT_SOURCE_LINE() __LINE__
|
||||
|
||||
namespace nkg {
|
||||
|
||||
RSA* rsa_cipher::_read_private_key_from_bio(BIO* p_bio) {
|
||||
resource_wrapper new_rsa
|
||||
{ resource_traits::openssl::rsa{}, PEM_read_bio_RSAPrivateKey(p_bio, nullptr, nullptr, nullptr) };
|
||||
|
||||
if (new_rsa.is_valid()) {
|
||||
return new_rsa.transfer();
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"PEM_read_bio_RSAPrivateKey failed.")
|
||||
.push_hint(u8"Are you sure that you DO provide a valid RSA private key file?");
|
||||
}
|
||||
}
|
||||
|
||||
RSA* rsa_cipher::_read_public_key_pem_from_bio(BIO* p_bio) {
|
||||
resource_wrapper new_rsa
|
||||
{ resource_traits::openssl::rsa{}, PEM_read_bio_RSA_PUBKEY(p_bio, nullptr, nullptr, nullptr) };
|
||||
|
||||
if (new_rsa.is_valid()) {
|
||||
return new_rsa.transfer();
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"PEM_read_bio_RSA_PUBKEY failed.")
|
||||
.push_hint(u8"Are you sure that you DO provide a valid RSA public key file with PEM format?");
|
||||
}
|
||||
}
|
||||
|
||||
RSA* rsa_cipher::_read_public_key_pkcs1_from_bio(BIO* p_bio) {
|
||||
resource_wrapper new_rsa
|
||||
{ resource_traits::openssl::rsa{}, PEM_read_bio_RSAPublicKey(p_bio, nullptr, nullptr, nullptr) };
|
||||
|
||||
if (new_rsa.is_valid()) {
|
||||
return new_rsa.transfer();
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"PEM_read_bio_RSAPublicKey failed.")
|
||||
.push_hint(u8"Are you sure that you DO provide a valid RSA public key file with PKCS1 format?");
|
||||
}
|
||||
}
|
||||
|
||||
void rsa_cipher::_write_private_key_to_bio(RSA* p_rsa, BIO* p_bio) {
|
||||
auto r = PEM_write_bio_RSAPrivateKey(p_bio, p_rsa, nullptr, nullptr, 0, nullptr, nullptr);
|
||||
if (r == 0) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"PEM_write_bio_RSAPrivateKey failed.");
|
||||
};
|
||||
}
|
||||
|
||||
void rsa_cipher::_write_public_key_pem_to_bio(RSA* p_rsa, BIO* p_bio) {
|
||||
auto r = PEM_write_bio_RSA_PUBKEY(p_bio, p_rsa);
|
||||
if (r == 0) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"PEM_write_bio_RSA_PUBKEY failed.");
|
||||
}
|
||||
}
|
||||
|
||||
void rsa_cipher::_write_public_key_pkcs1_to_bio(RSA* p_rsa, BIO* p_bio) {
|
||||
auto r = PEM_write_bio_RSAPublicKey(p_bio, p_rsa);
|
||||
if (r == 0) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"PEM_write_bio_RSAPublicKey failed.");
|
||||
}
|
||||
}
|
||||
|
||||
rsa_cipher::rsa_cipher() : m_rsa(RSA_new()) {
|
||||
if (!m_rsa.is_valid()) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), ERR_get_error(), u8"RSA_new failed.");
|
||||
}
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
size_t rsa_cipher::bits() const {
|
||||
#if (OPENSSL_VERSION_NUMBER & 0xffff0000) == 0x10000000 // openssl 1.0.x
|
||||
if (m_rsa->n) {
|
||||
return BN_num_bits(m_rsa->n);
|
||||
} else {
|
||||
throw no_key_assigned_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"RSA modulus has not been set.");
|
||||
}
|
||||
#elif (OPENSSL_VERSION_NUMBER & 0xffff0000) == 0x10100000 // openssl 1.1.x
|
||||
return RSA_bits(m_rsa.get());
|
||||
#else
|
||||
#error "rsa_cipher.cpp: uexpected OpenSSL version"
|
||||
#endif
|
||||
}
|
||||
|
||||
void rsa_cipher::generate_key(int bits, unsigned int e) {
|
||||
resource_wrapper bn_e{ resource_traits::openssl::bignum{}, BN_new() };
|
||||
|
||||
if (!bn_e.is_valid()) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), ERR_get_error(), u8"BN_new failed.");
|
||||
}
|
||||
|
||||
if (BN_set_word(bn_e.get(), e) == 0) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BN_set_word failed.");
|
||||
}
|
||||
|
||||
if (RSA_generate_key_ex(m_rsa.get(), bits, bn_e.get(), nullptr) == 0) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), ERR_get_error(), u8"RSA_generate_key_ex failed.");
|
||||
}
|
||||
}
|
||||
|
||||
void rsa_cipher::export_private_key_file(std::string_view file_path) const {
|
||||
resource_wrapper bio_file
|
||||
{ resource_traits::openssl::bio{}, BIO_new_file(file_path.data(), "w")};
|
||||
|
||||
if (bio_file.is_valid()) {
|
||||
_write_private_key_to_bio(m_rsa.get(), bio_file.get());
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new_file failed.");
|
||||
}
|
||||
}
|
||||
|
||||
void rsa_cipher::export_public_key_file_pem(std::string_view file_path) const {
|
||||
resource_wrapper bio_file
|
||||
{ resource_traits::openssl::bio{}, BIO_new_file(file_path.data(), "w")};
|
||||
|
||||
if (bio_file.is_valid()) {
|
||||
_write_public_key_pem_to_bio(m_rsa.get(), bio_file.get());
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new_file failed.");
|
||||
}
|
||||
}
|
||||
|
||||
void rsa_cipher::export_public_key_file_pkcs1(std::string_view file_path) const {
|
||||
resource_wrapper bio_file
|
||||
{ resource_traits::openssl::bio{}, BIO_new_file(file_path.data(), "w")};
|
||||
|
||||
if (bio_file.is_valid()) {
|
||||
_write_public_key_pkcs1_to_bio(m_rsa.get(), bio_file.get());
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new_file failed.");
|
||||
}
|
||||
}
|
||||
|
||||
void rsa_cipher::import_private_key_file(std::string_view file_path) {
|
||||
resource_wrapper bio_file
|
||||
{ resource_traits::openssl::bio{}, BIO_new_file(file_path.data(), "r") };
|
||||
|
||||
if (bio_file.is_valid()) {
|
||||
m_rsa.set(_read_private_key_from_bio(bio_file.get()));
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new_file failed.");
|
||||
}
|
||||
}
|
||||
|
||||
void rsa_cipher::import_public_key_file_pem(std::string_view file_path) {
|
||||
resource_wrapper bio_file
|
||||
{ resource_traits::openssl::bio{}, BIO_new_file(file_path.data(), "r") };
|
||||
|
||||
if (bio_file.is_valid()) {
|
||||
m_rsa.set(_read_public_key_pem_from_bio(bio_file.get()));
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new_file failed.");
|
||||
}
|
||||
}
|
||||
|
||||
void rsa_cipher::import_public_key_file_pkcs1(std::string_view file_path) {
|
||||
resource_wrapper bio_file
|
||||
{ resource_traits::openssl::bio{}, BIO_new_file(file_path.data(), "r") };
|
||||
|
||||
if (bio_file.is_valid()) {
|
||||
m_rsa.set(_read_public_key_pkcs1_from_bio(bio_file.get()));
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new_file failed.");
|
||||
}
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
std::string rsa_cipher::export_private_key_string() const {
|
||||
resource_wrapper bio_memory{ resource_traits::openssl::bio{}, BIO_new(BIO_s_mem()) };
|
||||
|
||||
if (bio_memory.is_valid()) {
|
||||
_write_private_key_to_bio(m_rsa.get(), bio_memory.get());
|
||||
|
||||
const char* pch = nullptr;
|
||||
long lch = BIO_get_mem_data(bio_memory.get(), &pch);
|
||||
|
||||
return std::string(pch, lch);
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new failed.");
|
||||
}
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
std::string rsa_cipher::export_public_key_string_pem() const {
|
||||
resource_wrapper bio_memory{ resource_traits::openssl::bio{}, BIO_new(BIO_s_mem()) };
|
||||
|
||||
if (bio_memory.is_valid()) {
|
||||
_write_public_key_pem_to_bio(m_rsa.get(), bio_memory.get());
|
||||
|
||||
const char* pch = nullptr;
|
||||
long lch = BIO_get_mem_data(bio_memory.get(), &pch);
|
||||
|
||||
return std::string(pch, lch);
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new failed.");
|
||||
}
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
std::string rsa_cipher::export_public_key_string_pkcs1() const {
|
||||
resource_wrapper bio_memory{ resource_traits::openssl::bio{}, BIO_new(BIO_s_mem()) };
|
||||
|
||||
if (bio_memory.is_valid()) {
|
||||
_write_public_key_pkcs1_to_bio(m_rsa.get(), bio_memory.get());
|
||||
|
||||
const char* pch = nullptr;
|
||||
long lch = BIO_get_mem_data(bio_memory.get(), &pch);
|
||||
|
||||
return std::string(pch, lch);
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new failed.");
|
||||
}
|
||||
}
|
||||
|
||||
void rsa_cipher::import_private_key_string(std::string_view key_string) {
|
||||
resource_wrapper bio_memory{ resource_traits::openssl::bio{}, BIO_new(BIO_s_mem()) };
|
||||
|
||||
if (!bio_memory.is_valid()) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new failed.");
|
||||
}
|
||||
|
||||
if (BIO_puts(bio_memory.get(), key_string.data()) <= 0) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_puts failed.");
|
||||
}
|
||||
|
||||
m_rsa.set(_read_private_key_from_bio(bio_memory.get()));
|
||||
}
|
||||
|
||||
void rsa_cipher::import_public_key_string_pem(std::string_view key_string) {
|
||||
resource_wrapper bio_memory{ resource_traits::openssl::bio{}, BIO_new(BIO_s_mem()) };
|
||||
|
||||
if (!bio_memory.is_valid()) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new failed.");
|
||||
}
|
||||
|
||||
if (BIO_puts(bio_memory.get(), key_string.data()) <= 0) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_puts failed.");
|
||||
}
|
||||
|
||||
m_rsa.set(_read_public_key_pem_from_bio(bio_memory.get()));
|
||||
}
|
||||
|
||||
void rsa_cipher::import_public_key_string_pkcs1(std::string_view key_string) {
|
||||
resource_wrapper bio_memory{ resource_traits::openssl::bio{}, BIO_new(BIO_s_mem()) };
|
||||
|
||||
if (!bio_memory.is_valid()) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_new failed.");
|
||||
}
|
||||
|
||||
if (BIO_puts(bio_memory.get(), key_string.data()) <= 0) {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"BIO_puts failed.");
|
||||
}
|
||||
|
||||
m_rsa.set(_read_public_key_pkcs1_from_bio(bio_memory.get()));
|
||||
}
|
||||
|
||||
size_t rsa_cipher::public_encrypt(const void* plaintext, size_t plaintext_size, void* ciphertext, int padding) const {
|
||||
if (plaintext_size <= INT_MAX) {
|
||||
int bytes_written =
|
||||
RSA_public_encrypt(static_cast<int>(plaintext_size), reinterpret_cast<const unsigned char*>(plaintext), reinterpret_cast<unsigned char*>(ciphertext), m_rsa.get(), padding);
|
||||
|
||||
if (bytes_written != -1) {
|
||||
return bytes_written;
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), ERR_get_error(), u8"RSA_public_encrypt failed.");
|
||||
}
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"plaintext_size > INT_MAX");
|
||||
}
|
||||
}
|
||||
|
||||
size_t rsa_cipher::private_encrypt(const void* plaintext, size_t plaintext_size, void* ciphertext, int padding) const {
|
||||
if (plaintext_size <= INT_MAX) {
|
||||
int bytes_written =
|
||||
RSA_private_encrypt(static_cast<int>(plaintext_size), reinterpret_cast<const unsigned char*>(plaintext), reinterpret_cast<unsigned char*>(ciphertext), m_rsa.get(), padding);
|
||||
|
||||
if (bytes_written != -1) {
|
||||
return bytes_written;
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), ERR_get_error(), u8"RSA_public_encrypt failed.");
|
||||
}
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"plaintext_size > INT_MAX");
|
||||
}
|
||||
}
|
||||
|
||||
size_t rsa_cipher::public_decrypt(const void* ciphertext, size_t ciphertext_size, void* plaintext, int padding) const {
|
||||
if (ciphertext_size <= INT_MAX) {
|
||||
int bytes_written =
|
||||
RSA_public_decrypt(static_cast<int>(ciphertext_size), reinterpret_cast<const unsigned char*>(ciphertext), reinterpret_cast<unsigned char*>(plaintext), m_rsa.get(), padding);
|
||||
|
||||
if (bytes_written != -1) {
|
||||
return bytes_written;
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), ERR_get_error(), u8"RSA_public_decrypt failed.")
|
||||
.push_hint(u8"Are your sure you DO provide a correct public key?");
|
||||
}
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"ciphertext_size > INT_MAX");
|
||||
}
|
||||
}
|
||||
|
||||
size_t rsa_cipher::private_decrypt(const void* ciphertext, size_t ciphertext_size, void* plaintext, int padding) const {
|
||||
if (ciphertext_size <= INT_MAX) {
|
||||
int bytes_written =
|
||||
RSA_private_decrypt(static_cast<int>(ciphertext_size), reinterpret_cast<const unsigned char*>(ciphertext), reinterpret_cast<unsigned char*>(plaintext), m_rsa.get(), padding);
|
||||
|
||||
if (bytes_written != -1) {
|
||||
return bytes_written;
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), ERR_get_error(), u8"RSA_public_decrypt failed.")
|
||||
.push_hint(u8"Are your sure you DO provide a correct private key?");
|
||||
}
|
||||
} else {
|
||||
throw backend_error(NKG_CURRENT_SOURCE_FILE(), NKG_CURRENT_SOURCE_LINE(), u8"ciphertext_size > INT_MAX");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#undef NKG_CURRENT_SOURCE_FILE
|
||||
#undef NKG_CURRENT_SOURCE_LINE
|
||||
123
common/rsa_cipher.hpp
Normal file
123
common/rsa_cipher.hpp
Normal file
@@ -0,0 +1,123 @@
|
||||
#pragma once
|
||||
#include <string>
|
||||
#include <optional>
|
||||
|
||||
#include <openssl/err.h>
|
||||
#include <openssl/rsa.h>
|
||||
|
||||
#include "resource_wrapper.hpp"
|
||||
#include "resource_traits/openssl/rsa.hpp"
|
||||
|
||||
#include "exception.hpp"
|
||||
|
||||
#define NKG_CURRENT_SOURCE_FILE() u8".\\common\\rsa_cipher.hpp"
|
||||
#define NKG_CURRENT_SOURCE_LINE() __LINE__
|
||||
|
||||
namespace nkg {
|
||||
|
||||
class rsa_cipher {
|
||||
public:
|
||||
class no_key_assigned_error : public ::nkg::exception {
|
||||
public:
|
||||
no_key_assigned_error(std::string_view file, int line, std::string_view message) noexcept :
|
||||
::nkg::exception(file, line, message) {}
|
||||
};
|
||||
|
||||
class backend_error : public ::nkg::exception {
|
||||
public:
|
||||
using error_code_t = decltype(ERR_get_error());
|
||||
|
||||
private:
|
||||
std::optional<error_code_t> m_error_code;
|
||||
std::string m_error_string;
|
||||
|
||||
public:
|
||||
backend_error(std::string_view file, int line, std::string_view message) noexcept :
|
||||
::nkg::exception(file, line, message) {}
|
||||
|
||||
backend_error(std::string_view file, int line, error_code_t openssl_errno, std::string_view message) noexcept :
|
||||
::nkg::exception(file, line, message), m_error_code(openssl_errno) {}
|
||||
|
||||
[[nodiscard]]
|
||||
virtual bool error_code_exists() const noexcept override {
|
||||
return m_error_code.has_value();
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
virtual intptr_t error_code() const noexcept override {
|
||||
if (error_code_exists()) { return m_error_code.value(); } else { trap_then_terminate(); }
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
virtual const std::string& error_string() const noexcept override {
|
||||
if (error_code_exists()) { return m_error_string; } else { trap_then_terminate(); }
|
||||
}
|
||||
};
|
||||
|
||||
private:
|
||||
resource_wrapper<resource_traits::openssl::rsa> m_rsa;
|
||||
|
||||
[[nodiscard]]
|
||||
static RSA* _read_private_key_from_bio(BIO* p_bio);
|
||||
|
||||
[[nodiscard]]
|
||||
static RSA* _read_public_key_pem_from_bio(BIO* p_bio);
|
||||
|
||||
[[nodiscard]]
|
||||
static RSA* _read_public_key_pkcs1_from_bio(BIO* p_bio);
|
||||
|
||||
static void _write_private_key_to_bio(RSA* p_rsa, BIO* p_bio);
|
||||
|
||||
static void _write_public_key_pem_to_bio(RSA* p_rsa, BIO* p_bio);
|
||||
|
||||
static void _write_public_key_pkcs1_to_bio(RSA* p_rsa, BIO* p_bio);
|
||||
|
||||
public:
|
||||
|
||||
rsa_cipher();
|
||||
|
||||
[[nodiscard]]
|
||||
size_t bits() const;
|
||||
|
||||
void generate_key(int bits, unsigned int e = RSA_F4);
|
||||
|
||||
void export_private_key_file(std::string_view file_path) const;
|
||||
|
||||
void export_public_key_file_pem(std::string_view file_path) const;
|
||||
|
||||
void export_public_key_file_pkcs1(std::string_view file_path) const;
|
||||
|
||||
void import_private_key_file(std::string_view file_path);
|
||||
|
||||
void import_public_key_file_pem(std::string_view file_path);
|
||||
|
||||
void import_public_key_file_pkcs1(std::string_view file_path);
|
||||
|
||||
[[nodiscard]]
|
||||
std::string export_private_key_string() const;
|
||||
|
||||
[[nodiscard]]
|
||||
std::string export_public_key_string_pem() const;
|
||||
|
||||
[[nodiscard]]
|
||||
std::string export_public_key_string_pkcs1() const;
|
||||
|
||||
void import_private_key_string(std::string_view key_string);
|
||||
|
||||
void import_public_key_string_pem(std::string_view key_string);
|
||||
|
||||
void import_public_key_string_pkcs1(std::string_view key_string);
|
||||
|
||||
size_t public_encrypt(const void* plaintext, size_t plaintext_size, void* ciphertext, int padding) const;
|
||||
|
||||
size_t private_encrypt(const void* plaintext, size_t plaintext_size, void* ciphertext, int padding) const;
|
||||
|
||||
size_t public_decrypt(const void* ciphertext, size_t ciphertext_size, void* plaintext, int padding) const;
|
||||
|
||||
size_t private_decrypt(const void* ciphertext, size_t ciphertext_size, void* plaintext, int padding) const;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#undef NKG_CURRENT_SOURCE_FILE
|
||||
#undef NKG_CURRENT_SOURCE_LINE
|
||||
Reference in New Issue
Block a user