Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add PKCS1v15 as a RSA signature and verification option on the Transit secret engine #4018

Merged
merged 7 commits into from
Mar 15, 2018
Next Next commit
Option to specify the RSA signature type, in specific add support for…
… PKCS1v15
broamski committed Mar 7, 2018
commit e27dfb0b67ee3ada67832065a70a1cca86096ead
16 changes: 14 additions & 2 deletions builtin/logical/transit/path_sign_verify.go
Original file line number Diff line number Diff line change
@@ -63,6 +63,11 @@ to the min_encryption_version configured on the key.`,
Type: framework.TypeBool,
Description: `Set to 'true' when the input is already hashed. If the key type is 'rsa-2048' or 'rsa-4096', then the algorithm used to hash the input should be indicated by the 'algorithm' parameter.`,
},
"rsa_sig_type": &framework.FieldSchema{
Type: framework.TypeString,
Default: "pss",
Description: `The RSA signature type to use for signing. Options are 'pss' or 'pkcs1v15'. Defaults to 'pss'`,
},
},

Callbacks: map[logical.Operation]framework.OperationFunc{
@@ -126,6 +131,11 @@ Defaults to "sha2-256". Not valid for all key types.`,
Type: framework.TypeBool,
Description: `Set to 'true' when the input is already hashed. If the key type is 'rsa-2048' or 'rsa-4096', then the algorithm used to hash the input should be indicated by the 'algorithm' parameter.`,
},
"rsa_sig_type": &framework.FieldSchema{
Type: framework.TypeString,
Default: "pss",
Description: `The RSA signature type to use for signature verification. Options are 'pss' or 'pkcs1v15'. Defaults to 'pss'`,
},
},

Callbacks: map[logical.Operation]framework.OperationFunc{
@@ -146,6 +156,7 @@ func (b *backend) pathSignWrite(ctx context.Context, req *logical.Request, d *fr
algorithm = d.Get("algorithm").(string)
}
prehashed := d.Get("prehashed").(bool)
rsasigtype := d.Get("rsa_sig_type").(string)

input, err := base64.StdEncoding.DecodeString(inputB64)
if err != nil {
@@ -195,7 +206,7 @@ func (b *backend) pathSignWrite(ctx context.Context, req *logical.Request, d *fr
input = hf.Sum(nil)
}

sig, err := p.Sign(ver, context, input, algorithm)
sig, err := p.Sign(ver, context, input, algorithm, rsasigtype)
if err != nil {
return nil, err
}
@@ -239,6 +250,7 @@ func (b *backend) pathVerifyWrite(ctx context.Context, req *logical.Request, d *
algorithm = d.Get("algorithm").(string)
}
prehashed := d.Get("prehashed").(bool)
rsasigtype := d.Get("rsa_sig_type").(string)

input, err := base64.StdEncoding.DecodeString(inputB64)
if err != nil {
@@ -288,7 +300,7 @@ func (b *backend) pathVerifyWrite(ctx context.Context, req *logical.Request, d *
input = hf.Sum(nil)
}

valid, err := p.VerifySignature(context, input, sig, algorithm)
valid, err := p.VerifySignature(context, input, sig, algorithm, rsasigtype)
if err != nil {
switch err.(type) {
case errutil.UserError:
29 changes: 23 additions & 6 deletions helper/keysutil/policy.go
Original file line number Diff line number Diff line change
@@ -836,7 +836,7 @@ func (p *Policy) HMACKey(version int) ([]byte, error) {
return p.Keys[strconv.Itoa(version)].HMACKey, nil
}

func (p *Policy) Sign(ver int, context, input []byte, algorithm string) (*SigningResult, error) {
func (p *Policy) Sign(ver int, context, input []byte, algorithm string, rsasigtype string) (*SigningResult, error) {
if !p.Type.SigningSupported() {
return nil, fmt.Errorf("message signing not supported for key type %v", p.Type)
}
@@ -918,9 +918,19 @@ func (p *Policy) Sign(ver int, context, input []byte, algorithm string) (*Signin
return nil, errutil.InternalError{Err: fmt.Sprintf("unsupported algorithm %s", algorithm)}
}

sig, err = rsa.SignPSS(rand.Reader, key, algo, input, nil)
if err != nil {
return nil, err
switch rsasigtype {
case "pss":
sig, err = rsa.SignPSS(rand.Reader, key, algo, input, nil)
if err != nil {
return nil, err
}
case "pkcs1v15":
sig, err = rsa.SignPKCS1v15(rand.Reader, key, algo, input)
if err != nil {
return nil, err
}
default:
return nil, errutil.InternalError{Err: fmt.Sprintf("unsupported rsa signature type %s", rsasigtype)}
}

default:
@@ -938,7 +948,7 @@ func (p *Policy) Sign(ver int, context, input []byte, algorithm string) (*Signin
return res, nil
}

func (p *Policy) VerifySignature(context, input []byte, sig, algorithm string) (bool, error) {
func (p *Policy) VerifySignature(context, input []byte, sig, algorithm string, rsasigtype string) (bool, error) {
if !p.Type.SigningSupported() {
return false, errutil.UserError{Err: fmt.Sprintf("message verification not supported for key type %v", p.Type)}
}
@@ -1024,7 +1034,14 @@ func (p *Policy) VerifySignature(context, input []byte, sig, algorithm string) (
return false, errutil.InternalError{Err: fmt.Sprintf("unsupported algorithm %s", algorithm)}
}

err = rsa.VerifyPSS(&key.PublicKey, algo, input, sigBytes, nil)
switch rsasigtype {
case "pss":
err = rsa.VerifyPSS(&key.PublicKey, algo, input, sigBytes, nil)
case "pkcs1v15":
err = rsa.VerifyPKCS1v15(&key.PublicKey, algo, input, sigBytes)
default:
return false, errutil.InternalError{Err: fmt.Sprintf("unsupported rsa signature type %s", rsasigtype)}
}

return err == nil, nil