nssdb

package
v0.61.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Apr 15, 2025 License: Apache-2.0 Imports: 29 Imported by: 0

README

This package is for inserting a certificate and key into an NSS database.

NSS Database Internals

Certificates, public keys, and private keys are stored as PKCS #11 objects. Each object is a collection of attributes stored in binary format. Some attributes are ASN.1 encoded. Refer to the PKCS #11 spec for documentation on how an attribute is encoded.

Schema

An NSS DB directory will include a file certs9.db that holds the certificate database and a file key4.db that holds the keys database. Both are sqlite databases. The certificates database comprises a single table nssPublic. The keys database comprises a table named metaData and a table named nssPrivate. The nssPublic and nssPrivate tables have the same schema. As of NSS 3.107 there are 119 columns in these tables. Each column holds the value of an attribute on the PKCS #11 object.

Encryption and signing

The CKA_VALUE of private key objects in the key4 database is encrypted and encoded. The encoded structure includes parameters necessary to decrypt the value. This package uses the same defaults as NSS 3.107:

  • Generate keys with PBKDF2 with a unique salt and target length 32
  • PBKDF2 uses 1 iteration with an empty password and 10000 when the password is set
  • Encrypt with AES256-CBC with a unique initialization vector
  • Sign with HMAC-SHA256

A signature of the private key is stored in the metaData table since AES256-CBC encryption is not authenticated. The signature is over the 32-byte raw private key along with object ID and attribute type.

Generating Column Names

The generate directory holds a utility for generating a map from attribute names in the nss source code to column names in the sqlite databases. The sqlite column name is always the letter a followed by a number in hexadecimal format. For example, the CKA_ISSUER attribute has the column name a81 in the nssPublic and nssPrivate tables of the sqlite database. This is parsed from the following line in lib/util/pkcs11t.h.

#define CKA_ISSUER 0x00000081UL

To update the column map, clone the nss repo into the generate directory and then run make columns.

Status

This package only supports importing certificates with an EC P-256 keypair.

Documentation

Overview

generated by nssdb/generate/main.go

Index

Constants

View Source
const (
	CKO_DATA              = iota //nolint:stylecheck,revive // name matches source
	CKO_CERTIFICATE              //nolint:stylecheck,revive // name matches source
	CKO_PUBLIC_KEY               //nolint:stylecheck,revive // name matches source
	CKO_PRIVATE_KEY              //nolint:stylecheck,revive // name matches source
	CKO_SECRET_KEY               //nolint:stylecheck,revive // name matches source
	CKO_HW_FEATURE               //nolint:stylecheck,revive // name matches source
	CKO_DOMAIN_PARAMETERS        //nolint:stylecheck,revive // name matches source
	CKO_MECHANISM                //nolint:stylecheck,revive // name matches source
	CKO_PROFILE                  //nolint:stylecheck,revive // name matches source
)

CKA_CLASS values https://github.com/nss-dev/nss/blob/NSS_3_107_RTM/lib/util/pkcs11t.h#L320-L334

View Source
const (
	CKK_RSA = iota //nolint:stylecheck,revive // name matches source
	CKK_DSA        //nolint:stylecheck,revive // name matches source
	CKK_DH         //nolint:stylecheck,revive // name matches source
	CKK_EC         //nolint:stylecheck,revive // name matches source
)

CKA_KEY_TYPE values https://github.com/nss-dev/nss/blob/NSS_3_107_RTM/lib/util/pkcs11t.h#L366

View Source
const (
	CKC_X_509           = iota //nolint:stylecheck,revive // name matches source
	CKC_X_509_ATTR_CERT        //nolint:stylecheck,revive // name matches source
	CKC_WTLS                   //nolint:stylecheck,revive // name matches source
)

CKA_CERTIFICATE_TYPE values https://github.com/nss-dev/nss/blob/NSS_3_107_RTM/lib/util/pkcs11t.h#L453-L458

Variables

This section is empty.

Functions

This section is empty.

Types

type Metadata

type Metadata struct {
	ID    string
	Item1 []byte
	Item2 []byte
}

type NSSDB

type NSSDB struct {
	Key  *sql.DB
	Cert *sql.DB
	// contains filtered or unexported fields
}

func New

func New(dir string, pw []byte) (*NSSDB, error)

New opens connections to the cert9 and key4 sqlite databases in the provided directory. It defaults to the current directory if not set. The password argument is not required if the NSS database was created with the --empty-password flag.

func (*NSSDB) AddCertificate

func (db *NSSDB) AddCertificate(ctx context.Context, cert *x509.Certificate, name string) (uint32, uint32, error)

AddCertificate returns the id of the certificate and public key objects. Any certificates or public keys with the same subject key id will be replaced. The only supported key type is ECDSA with curve P-256.

func (*NSSDB) AddPrivateKey

func (db *NSSDB) AddPrivateKey(ctx context.Context, privKey *ecdsa.PrivateKey, name string, ckaID []byte, certCNs ...string) (uint32, error)

AddPrivateKey adds a private key to the nssPrivate database and returns its id. The ckaID argument should come from the SubjectKeyID of the associated certificate. Keys with the same ckaID will be replaced. Only ecdsa keys with curve P-256 are supported.

func (*NSSDB) AddPublicKey

func (db *NSSDB) AddPublicKey(ctx context.Context, pubKey *ecdsa.PublicKey, ckaID []byte) (uint32, error)

AddPublicKey adds a public key to the nssPublic database and returns its id. The ckaID argument should come from the SubjectKeyID of the associated certificate. Keys with the same ckaID will be replaced. Only ecdsa keys with curve P-256 are supported.

func (*NSSDB) Close

func (db *NSSDB) Close() error

func (*NSSDB) DeleteCertificate

func (db *NSSDB) DeleteCertificate(ctx context.Context, id uint32) error

DeleteCertificate deletes a certificate and its keys.

func (*NSSDB) DeleteCertificatesByName

func (db *NSSDB) DeleteCertificatesByName(ctx context.Context, name string) error

DeleteCertificatesByName deletes all certificates with the given nickname, along with their keys.

func (*NSSDB) DeleteObject

func (db *NSSDB) DeleteObject(ctx context.Context, id uint32) error

Delete deletes an object.

func (*NSSDB) DeleteObjectPrivate

func (db *NSSDB) DeleteObjectPrivate(ctx context.Context, id uint32) error

DeletePrivate deletes an object from the nssPrivate database in the key db.

func (*NSSDB) DeleteObjectPublic

func (db *NSSDB) DeleteObjectPublic(ctx context.Context, id uint32) error

DeletePublic deletes an object from the nssPublic database in the cert db.

func (*NSSDB) GetMetadata

func (db *NSSDB) GetMetadata(ctx context.Context, id string) (*Metadata, error)

The schema of the metaData table is (id string, item1, item2)

func (*NSSDB) GetObject

func (db *NSSDB) GetObject(ctx context.Context, id uint32) (*Object, error)

GetObject fetches a single object by id from either the nssPublic table in the cert db or the nssPrivate table in the key db if not found in nssPublic.

func (*NSSDB) GetObjectPrivate

func (db *NSSDB) GetObjectPrivate(ctx context.Context, id uint32) (*Object, error)

GetObjectPrivate fetches a single object by id from the nssPrivate table in the key db.

func (*NSSDB) GetObjectPublic

func (db *NSSDB) GetObjectPublic(ctx context.Context, id uint32) (*Object, error)

GetObjectPublic fetches a single object by id from the nssPublic table in the cert db.

func (*NSSDB) GetPassword

func (db *NSSDB) GetPassword(ctx context.Context) (*Password, error)

func (*NSSDB) Import

func (db *NSSDB) Import(ctx context.Context, name string, cert *x509.Certificate, privKey crypto.PrivateKey) (uint32, uint32, uint32, error)

Import returns (cert id, public key id, private key id) on success. The certificates subject key id will be added as CKA_ID to all three objects to bind them together. All certificate and key objects with the same CKA_ID will be replaced. Certificates with the same name and different subject key id will not be replaced. Use DeleteCertificateByName for that. The only supported key type is ECDSA with curve P-256.

func (*NSSDB) InsertPrivate

func (db *NSSDB) InsertPrivate(ctx context.Context, obj *Object) (uint32, error)

InsertPrivate adds an object to the nssPrivate table of the key db.

func (*NSSDB) InsertPublic

func (db *NSSDB) InsertPublic(ctx context.Context, obj *Object) (uint32, error)

InsertPublic adds an object to the nssPublic table of the cert db.

func (*NSSDB) ListCertificateObjects

func (db *NSSDB) ListCertificateObjects(ctx context.Context) ([]*Object, error)

ListCertificateObjects returns all x509 certificate objects from the nssPublic table in the cert db.

func (*NSSDB) ListObjects

func (db *NSSDB) ListObjects(ctx context.Context) ([]*Object, error)

ListObjects fetches all objects in the nssPublic and nssPrivate tables.

func (*NSSDB) ListObjectsPrivate

func (db *NSSDB) ListObjectsPrivate(ctx context.Context) ([]*Object, error)

ListObjectPrivate fetches all rows in the nssPrivate table in the key db.

func (*NSSDB) ListObjectsPublic

func (db *NSSDB) ListObjectsPublic(ctx context.Context) ([]*Object, error)

ListObjectsPublic fetches all objects in the nssPublic table in the cert db.

func (*NSSDB) Reset

func (db *NSSDB) Reset(ctx context.Context) error

Reset deletes all objects and their metadata from the certificate and key databases. It does not delete the password from the metaData table.

type Object

type Object struct {
	ID                  uint32
	Attributes          map[string][]byte
	ULongAttributes     map[string]uint32
	EncryptedAttributes map[string][]byte
	Metadata            []*Metadata
}

Object is an entry in nssPublic or nssPrivate plus any related entries in the metaData table. The encoding for and meaning of most attributes can be found in the PKCS #11 spec.

func (*Object) Print

func (obj *Object) Print()

func (Object) ToECPublicKey

func (obj Object) ToECPublicKey() (*ecdsa.PublicKey, error)

func (Object) ToX509Certificate

func (obj Object) ToX509Certificate() (*x509.Certificate, error)

ToX509Certificate converts an Object to an x509 Certificate.

func (Object) Validate

func (obj Object) Validate(name string, want []byte) error

func (Object) ValidateULong

func (obj Object) ValidateULong(name string, want uint32) error

type Password

type Password struct {
	Salt              []byte
	EncryptedPassword []byte
}

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL