diff options
Diffstat (limited to 'openssl/agent/pkcs11/url.hxx')
-rw-r--r-- | openssl/agent/pkcs11/url.hxx | 246 |
1 files changed, 246 insertions, 0 deletions
diff --git a/openssl/agent/pkcs11/url.hxx b/openssl/agent/pkcs11/url.hxx new file mode 100644 index 0000000..b8ca056 --- /dev/null +++ b/openssl/agent/pkcs11/url.hxx @@ -0,0 +1,246 @@ +// file : openssl/agent/pkcs11/url.hxx -*- C++ -*- +// copyright : Copyright (c) 2014-2018 Code Synthesis Ltd +// license : MIT; see accompanying LICENSE file + +#ifndef OPENSSL_AGENT_PKCS11_URL_HXX +#define OPENSSL_AGENT_PKCS11_URL_HXX + +#include <libbutl/url.mxx> + +#include <openssl/types.hxx> +#include <openssl/utility.hxx> + +// glibc defines these macros in its <sys/types.h>. +// +#ifdef major +# undef major +#endif + +#ifdef minor +# undef minor +#endif + +namespace openssl +{ + namespace agent + { + namespace pkcs11 + { + // RFC7512 The PKCS #11 URI Scheme. + // + // Traits class for the PKCS#11 URL object. + // + // Notes: + // + // - The 'pkcs11:' URI scheme is rootless and doesn't use the fragment + // component. + // + // - The one-level path component is a sequence of semicolon-separated + // attribute name/value pairs that identify the referenced entity. It + // is stored in the URL-encoded representation as the id attribute + // contains binary data. + // + // - The query is a sequence of ampersand-separated access attribute + // name/value pairs that may or may not be used by the URL consumer. + // + // - All attribute values are textual, except for the id attribute which + // is binary. + // + // - There shouldn't be duplicate attributes in the path and query + // components. + // + // - Both path and query components can contain vendor-specific + // attributes. + // + // - An unrecognized attribute in the path component results in the + // parsing error. An unrecognized attribute in the query component is + // skipped. + // + // - The URL-referenced entity kind is context-specific. For example, + // the pkcs11:token=abc URL can refer the abc token or all objects + // stored in the abc token. + // + // - An attribute that is not present in the URL path component matches + // everything. Each additional attribute present in the path component + // further restricts the selection. Thus, in particular, the 'pkcs11:' + // URL is valid and matches everything. + // + struct url_traits + { + using string_type = string; + using path_type = string; + + using scheme_type = string; + using authority_type = butl::basic_url_authority<string_type>; + + static optional<scheme_type> + translate_scheme (const string_type&, + string_type&&, + optional<authority_type>&, + optional<path_type>&, + optional<string_type>&, + optional<string_type>&, + bool&); + + static string_type + translate_scheme (string_type&, + const scheme_type&, + const optional<authority_type>&, + const optional<path_type>&, + const optional<string_type>&, + const optional<string_type>&, + bool); + + static path_type + translate_path (string_type&&); + + static string_type + translate_path (const path_type&); + }; + + using url = butl::basic_url<string, url_traits>; + + // PKCS#11 entity (storage object, token, slot, or module) identity + // attributes. + // + struct library_version + { + unsigned char major; + unsigned char minor; + + // Create the version object from its string representation. Throw + // invalid_argument on the parsing error. + // + explicit + library_version (const string&); + + library_version (unsigned char mj, unsigned char mn) + : major (mj), minor (mn) {} + }; + + class identity + { + public: + // Module. + // + using library_version_type = pkcs11::library_version; + + optional<string> library_manufacturer; + optional<library_version_type> library_version; + optional<string> library_description; + + // Slot. + // + // Note that not all PKCS#11 libraries guarantee slot id to be stable + // across initializations. + // + optional<unsigned long> slot_id; + optional<string> slot_manufacturer; + optional<string> slot_description; + + // Token. + // + optional<string> serial; + optional<string> token; // Token label. + optional<string> model; + optional<string> manufacturer; + + // Storage object. + // + optional<vector<unsigned char>> id; + + optional<string> object; // Object label. + optional<string> type; // cert, data, private, public, or + // secret-key. + + // Parse the path component of pkcs11_url object. Throw + // invalid_argument if invalid attribute is encountered. + // + explicit + identity (const url&); + + // Create an identity that matches all PKCS#11 entities in the system. + // + identity () = default; + }; + + // PKCS#11 entity access attributes. + // + class access + { + public: + optional<string> pin_value; + optional<string> pin_source; + + // The library name with an extension and "lib" prefix stripped. + // + optional<path> module_name; + + // The library absolute path or the directory path where the PKCS#11 + // libraries are located. + // + optional<path> module_path; + + // Parse the query component of pkcs11_url object. Throw + // invalid_argument if invalid attribute is encountered. + // + explicit + access (const url&); + + // Create an object that provides no access attributes. + // + access () = default; + }; + + inline bool + operator== (const library_version& x, const library_version& y) + { + return x.major == y.major && x.minor == y.minor; + } + + inline bool + operator!= (const library_version& x, const library_version& y) + { + return !(x == y); + } + + inline bool + operator== (const identity& x, const identity& y) + { + return + // Module. + // + x.library_manufacturer == y.library_manufacturer && + x.library_version == y.library_version && + x.library_description == y.library_description && + + // Slot. + // + x.slot_id == y.slot_id && + x.slot_manufacturer == y.slot_manufacturer && + x.slot_description == y.slot_description && + + // Token. + // + x.serial == y.serial && + x.token == y.token && + x.model == y.model && + x.manufacturer == y.manufacturer && + + // Storage object. + // + x.id == y.id && + x.object == y.object && + x.type == y.type; + } + + inline bool + operator!= (const identity& x, const identity& y) + { + return !(x == y); + } + } + } +} + +#endif // OPENSSL_AGENT_PKCS11_URL_HXX |