EVP_SKEY(3ossl)

πŸ’– EVP_SKEY β€” the opaque symmetric key glow-up πŸ’–

okay bestie, so this is the OpenSSL manual page for EVP_SKEY (section 3ossl), and it's literally the whole lore of opaque symmetric key allocation and handling. sit down, hydrate, we're doing keys today 🫢


✨ NAME ✨

EVP_SKEY, EVP_SKEY_generate, EVP_SKEY_import, EVP_SKEY_import_raw_key, EVP_SKEY_up_ref, EVP_SKEY_export, EVP_SKEY_get0_raw_key, EVP_SKEY_get0_key_id, EVP_SKEY_get0_skeymgmt_name, EVP_SKEY_get0_provider_name, EVP_SKEY_free, EVP_SKEY_is_a, EVP_SKEY_to_provider β€” opaque symmetric key allocation and handling functions πŸ‘‘


🌸 SYNOPSIS 🌸

#include <openssl/evp.h>

typedef evp_skey_st EVP_SKEY;

EVP_SKEY *EVP_SKEY_generate(OSSL_LIB_CTX *libctx, const char *skeymgmtname,
                            const char *propquery, const OSSL_PARAM *params);
EVP_SKEY *EVP_SKEY_import(OSSL_LIB_CTX *libctx, const char *skeymgmtname,
                          const char *propquery,
                          int selection, const OSSL_PARAM *params);
EVP_SKEY *EVP_SKEY_import_raw_key(OSSL_LIB_CTX *libctx, const char *skeymgmtname,
                                  unsigned char *key, size_t len,
                                  const char *propquery);
int EVP_SKEY_export(const EVP_SKEY *skey, int selection,
                    OSSL_CALLBACK *export_cb, void *export_cbarg);
int EVP_SKEY_get0_raw_key(const EVP_SKEY *skey, const unsigned char **key,
                         size_t *len);
const char *EVP_SKEY_get0_key_id(const EVP_SKEY *skey);

const char *EVP_SKEY_get0_skeymgmt_name(const EVP_SKEY *skey);
const char *EVP_SKEY_get0_provider_name(const EVP_SKEY *skey);

int EVP_SKEY_up_ref(EVP_SKEY *key);
void EVP_SKEY_free(EVP_SKEY *key);
int EVP_SKEY_is_a(const EVP_SKEY *skey, const char *name);
EVP_SKEY *EVP_SKEY_to_provider(EVP_SKEY *skey, OSSL_LIB_CTX *libctx,
                               OSSL_PROVIDER *prov, const char *propquery);

like look at that signature list. it's giving ✨*organized*✨


πŸ’… DESCRIPTION πŸ’…

EVP_SKEY is a generic structure that holds symmetric keys as opaque objects. the keys themselves are often called the "internal key", and they get handled by providers using EVP_SKEYMGMT(3). iykyk.

so conceptually? an EVP_SKEY internal key may hold a symmetric key, and along with that, key parameters if the key type is the kind of diva that requires them. πŸ’…

  • EVP_SKEY_generate() β€” creates a brand new EVP_SKEY object and initializes it according to the params argument. new key, who dis πŸ”₯
  • EVP_SKEY_import() β€” allocates an empty EVP_SKEY structure (this is the one OpenSSL uses to store symmetric keys), assigns the EVP_SKEYMGMT object associated with the key, and initializes the object from the params argument. it's giving "move in, decorate later" πŸŽ€
  • EVP_SKEY_import_raw_key() β€” a lil helper bestie 🫢 it creates an EVP_SKEY object containing the raw byte representation of the symmetric keys from the buffer key having length len. the skeymgmtname defines the name of the target EVP_SKEYMGMT for the newly created key.
  • EVP_SKEY_export() β€” extracts values from a key skey using the selection. selection is described below (spoiler: it's the Selections bit, scroll down babe). it uses a callback export_cb that gets passed the value of export_cbarg. check openssl-core.h(7) for more info about the callback. ⚠️ heads up: the OSSL_PARAM(3) array that's passed to the callback is not persistent after the callback returns. so don't be out here holding onto it like it's gonna text back πŸ’€
  • EVP_SKEY_get0_raw_key() β€” returns a pointer to the raw key bytes to the passed address and sets the key len. the returned address is managed by the internal key management and shouldn't be freed explicitly. also? this operation can fail when the underlying key management doesn't support export of the secret key. no key for you πŸ™ˆ
  • EVP_SKEY_get0_key_id() β€” returns a NUL-terminated string providing some human-readable identifier of the key, if provided by the underlying key management. the pointer becomes invalid after freeing the EVP_SKEY object. use it, love it, then let it go 😭
  • EVP_SKEY_get0_skeymgmt_name() and EVP_SKEY_get0_provider_name() β€” return the names of the associated EVP_SKEYMGMT object and its provider, correspondingly. name drop, but make it architecture ✨
  • EVP_SKEY_up_ref() β€” increments the reference count of key. more refs, more love πŸ’œ
  • EVP_SKEY_free() β€” decrements the reference count of key and, if the reference count is zero, frees it. if key is NULL, nothing is done. respectful. iconic. no notes. πŸ‘‘
  • EVP_SKEY_is_a() β€” checks if the key type of skey is name. vibe check fr fr.
  • EVP_SKEY_to_provider() β€” simplifies the task of importing a skey into a different provider identified by prov. if prov is NULL, the default provider for the key type identified via skey is used. glowed up and moved providers, we love a relocation arc πŸ¦‹

πŸŽ€ Selections πŸŽ€

these are the constants you can use for selection:

  • OSSL_SKEYMGMT_SELECT_SECRET_KEY β€” only the raw key representation will be selected. just the secret, nothing else, mysterious πŸ’…
  • OSSL_SKEYMGMT_SELECT_PARAMETERS β€” only the key parameters will be selected. this includes optional key parameters. the accessories, the whole fit πŸŽ€
  • OSSL_SKEYMGMT_SELECT_ALL β€” all parameters will be selected. everything. the full lewk. πŸ”₯

🫢 NOTES 🫢

the EVP_SKEY structure is used by various OpenSSL functions which require a general symmetric key without reference to any particular algorithm. it's the versatile bestie of the key world.

⚠️ real talk: the EVP_SKEY_to_provider() function will fail and return NULL if the origin key skey cannot be exported from its provider. no export, no glow-up, periodt.

πŸ’€ RETURN VALUES πŸ’€

  • EVP_SKEY_generate(), EVP_SKEY_import() and EVP_SKEY_import_raw_key() return either the newly allocated EVP_SKEY structure or NULL if an error occurred.
  • EVP_SKEY_get0_key_id() returns either a valid pointer or NULL.
  • EVP_SKEY_up_ref() returns 1 for success and 0 on failure.
  • EVP_SKEY_export() and EVP_SKEY_get0_raw_key() return 1 for success and 0 on failure.
  • EVP_SKEY_get0_skeymgmt_name() and EVP_SKEY_get0_provider_name() return the names of the associated EVP_SKEYMGMT object and its provider correspondingly.
  • EVP_SKEY_is_a() returns 1 if skey has the key type name, otherwise 0.
  • EVP_SKEY_to_provider() returns a new EVP_SKEY suitable for operations with the prov provider or NULL in case of failure.

like 1 = slay, 0 = not slay. simple as. ✨


🌈 SEE ALSO 🌈

EVP_SKEYMGMT(3), provider(7), OSSL_PARAM(3)


⭐ HISTORY ⭐

the EVP_SKEY API and functions EVP_SKEY_export(), EVP_SKEY_free(), EVP_SKEY_get0_raw_key(), EVP_SKEY_import(), EVP_SKEY_import_raw_key(), EVP_SKEY_up_ref(), EVP_SKEY_generate(), EVP_SKEY_get0_key_id(), EVP_SKEY_get0_provider_name(), EVP_SKEY_get0_skeymgmt_name(), EVP_SKEY_is_a(), EVP_SKEY_to_provider() were introduced in OpenSSL 3.5. they're new new. fresh off the press. πŸ“


Copyright 2025-2026 The OpenSSL Project Authors. All Rights Reserved.

Licensed under the Apache License 2.0 (the "License"). You may not use this file except in compliance with the License. You can obtain a copy in the file LICENSE in the source distribution or at <https://www.openssl.org/source/license.html>.


okay that's the whole page bestie, you're officially keypilled πŸ”‘βœ¨ this was EVP_SKEY(3ossl) from OpenSSL 3.5.9, dated 2026-09-29 β€” go forth and handle those opaque symmetric keys responsibly, mwah πŸ’–πŸ¦‹

πŸ“¦ where this page comes from