sign_pss (p1, p2, p3 = {})
public
Signs data using the Probabilistic Signature Scheme (RSA-PSS) and
returns the calculated signature.
RSAError will be raised if an
error occurs.
See #verify_pss for the
verification operation.
digest
A String containing the message digest algorithm
name.
data
A String . The data to be signed.
salt_length
The length in octets of the salt. Two special values are reserved:
:digest means the digest length, and :max means the
maximum possible length for the combination of the private key and the
selected message digest algorithm.
mgf1_hash
The hash algorithm used in MGF1 (the currently supported mask generation
function (MGF)).
Example
data = " Sign me! "
pkey = OpenSSL :: PKey :: RSA . new ( 2048 )
signature = pkey . sign_pss (" SHA256 ", data , salt_length : :max , mgf1_hash : " SHA256 ")
pub_key = pkey . public_key
puts pub_key . verify_pss (" SHA256 ", signature , data ,
salt_length : :auto , mgf1_hash : " SHA256 ")
Show source static VALUE
ossl_rsa_sign_pss(int argc, VALUE *argv, VALUE self)
{
VALUE digest, data, options, kwargs[2], signature;
static ID kwargs_ids[2];
EVP_PKEY *pkey;
EVP_PKEY_CTX *pkey_ctx;
const EVP_MD *md, *mgf1md;
EVP_MD_CTX *md_ctx;
size_t buf_len;
int salt_len;
if (!kwargs_ids[0]) {
kwargs_ids[0] = rb_intern_const("salt_length");
kwargs_ids[1] = rb_intern_const("mgf1_hash");
}
rb_scan_args(argc, argv, "2:", &digest, &data, &options);
rb_get_kwargs(options, kwargs_ids, 2, 0, kwargs);
if (kwargs[0] == ID2SYM(rb_intern("max")))
salt_len = -2; /* RSA_PSS_SALTLEN_MAX_SIGN */
else if (kwargs[0] == ID2SYM(rb_intern("digest")))
salt_len = -1; /* RSA_PSS_SALTLEN_DIGEST */
else
salt_len = NUM2INT(kwargs[0]);
mgf1md = ossl_evp_get_digestbyname(kwargs[1]);
pkey = GetPrivPKeyPtr(self);
buf_len = EVP_PKEY_size(pkey);
md = ossl_evp_get_digestbyname(digest);
StringValue(data);
signature = rb_str_new(NULL, (long)buf_len);
md_ctx = EVP_MD_CTX_new();
if (!md_ctx)
goto err;
if (EVP_DigestSignInit(md_ctx, &pkey_ctx, md, NULL, pkey) != 1)
goto err;
if (EVP_PKEY_CTX_set_rsa_padding(pkey_ctx, RSA_PKCS1_PSS_PADDING) != 1)
goto err;
if (EVP_PKEY_CTX_set_rsa_pss_saltlen(pkey_ctx, salt_len) != 1)
goto err;
if (EVP_PKEY_CTX_set_rsa_mgf1_md(pkey_ctx, mgf1md) != 1)
goto err;
if (EVP_DigestSignUpdate(md_ctx, RSTRING_PTR(data), RSTRING_LEN(data)) != 1)
goto err;
if (EVP_DigestSignFinal(md_ctx, (unsigned char *)RSTRING_PTR(signature), &buf_len) != 1)
goto err;
rb_str_set_len(signature, (long)buf_len);
EVP_MD_CTX_free(md_ctx);
return signature;
err:
EVP_MD_CTX_free(md_ctx);
ossl_raise(eRSAError, NULL);
}