Compare commits

...

2 Commits

Author SHA1 Message Date
Jan Dittberner 65c5bac2d9 Implement delta CRL support
This commit provides real CRL support with persistent storage of CRLs as well
as support for delta CRLs using github.com/balacode/go-delta
2 years ago
Jan Dittberner 1031ee3118 Implement configuration support for CA profiles 2 years ago

@ -85,7 +85,7 @@ func main() {
healthHandler := health.New(version, access)
revokingRepositories, err := configureRepositories(caConfig)
revokingRepositories, err := configureRepositories(caConfig, logger)
if err != nil {
logger.WithError(err).Fatal("could not setup revoking repositories")
}
@ -117,20 +117,21 @@ func main() {
func configureRepositories(
caConfig *config.SignerConfig,
logger *logrus.Logger,
) (map[string]*revoking.X509Revoking, error) {
var err error
result := make(map[string]*revoking.X509Revoking)
for _, name := range caConfig.RootCAs() {
result[fmt.Sprintf("root-%s", name)], err = buildX509Revoking(caConfig, name)
result[fmt.Sprintf("root-%s", name)], err = buildX509Revoking(caConfig, name, logger)
if err != nil {
return nil, err
}
}
for _, name := range caConfig.SubordinateCAs() {
result[fmt.Sprintf("sub-%s", name)], err = buildX509Revoking(caConfig, name)
result[fmt.Sprintf("sub-%s", name)], err = buildX509Revoking(caConfig, name, logger)
if err != nil {
return nil, err
}
@ -139,7 +140,11 @@ func configureRepositories(
return result, nil
}
func buildX509Revoking(caConfig *config.SignerConfig, name string) (*revoking.X509Revoking, error) {
func buildX509Revoking(
caConfig *config.SignerConfig,
name string,
logger *logrus.Logger,
) (*revoking.X509Revoking, error) {
caDef, err := caConfig.GetCADefinition(name)
if err != nil {
return nil, fmt.Errorf("could not get CA definition for %s: %w", name, err)
@ -155,6 +160,7 @@ func buildX509Revoking(caConfig *config.SignerConfig, name string) (*revoking.X5
caDef.KeyInfo.CRLSignatureAlgorithm,
caDef.Certificate,
caDef.KeyPair,
logger,
), nil
}

@ -16,6 +16,8 @@ require (
)
require (
github.com/balacode/go-delta v0.1.0 // indirect
github.com/balacode/zr v1.0.0 // indirect
github.com/davecgh/go-spew v1.1.1 // indirect
github.com/miekg/pkcs11 v1.1.1 // indirect
github.com/pkg/errors v0.9.1 // indirect

@ -1,5 +1,9 @@
github.com/ThalesIgnite/crypto11 v1.2.5 h1:1IiIIEqYmBvUYFeMnHqRft4bwf/O36jryEUpY+9ef8E=
github.com/ThalesIgnite/crypto11 v1.2.5/go.mod h1:ILDKtnCKiQ7zRoNxcp36Y1ZR8LBPmR2E23+wTQe/MlE=
github.com/balacode/go-delta v0.1.0 h1:pwz4CMn06P2bIaIfAx3GSabMPwJp/Ww4if+7SgPYa3I=
github.com/balacode/go-delta v0.1.0/go.mod h1:wLNrwTI3lHbPBvnLzqbHmA7HVVlm1u22XLvhbeA6t3o=
github.com/balacode/zr v1.0.0 h1:MCupkEoXvrnCljc4KddiDOhR04ZLUAACgtKuo3o+9vc=
github.com/balacode/zr v1.0.0/go.mod h1:pLeSAL3DhZ9L0JuiRkUtIX3mLOCtzBLnDhfmykbSmkE=
github.com/dave/jennifer v1.4.1 h1:XyqG6cn5RQsTj3qlWQTKlRGAyrTcsk1kUmWdZBzRjDw=
github.com/dave/jennifer v1.4.1/go.mod h1:7jEdnm+qBcxl8PC0zyp7vxcpSRnzXSt9r39tpTVGlwA=
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=

@ -31,6 +31,8 @@ import (
"gopkg.in/yaml.v3"
"git.cacert.org/cacert-gosigner/pkg/messages"
"git.cacert.org/cacert-gosigner/internal/x509/openssl"
"git.cacert.org/cacert-gosigner/internal/x509/revoking"
"git.cacert.org/cacert-gosigner/internal/x509/signing"
@ -540,6 +542,7 @@ type CaCertificateEntry struct {
KeyPair crypto.Signer
Parent string
Storage string
Profiles []messages.CAProfile
}
func (c *CaCertificateEntry) UnmarshalYAML(value *yaml.Node) error {
@ -551,6 +554,10 @@ func (c *CaCertificateEntry) UnmarshalYAML(value *yaml.Node) error {
ExtKeyUsage []string `yaml:"ext-key-usages,omitempty"`
Parent string `yaml:"parent"`
Storage string `yaml:"storage"`
Profiles []struct {
Name string `yaml:"name"`
UseFor string `yaml:"use-for"`
} `yaml:"profiles"`
}
err := value.Decode(&m)
@ -590,6 +597,22 @@ func (c *CaCertificateEntry) UnmarshalYAML(value *yaml.Node) error {
c.Storage = "default"
}
if m.Profiles != nil {
c.Profiles = make([]messages.CAProfile, len(m.Profiles))
for i, prof := range m.Profiles {
usage, err := messages.ParseUsage(prof.UseFor)
if err != nil {
return fmt.Errorf("config error: %w", err)
}
c.Profiles[i] = messages.CAProfile{
Name: prof.Name,
UseFor: usage,
}
}
}
return nil
}

@ -20,6 +20,7 @@ package handler
import (
"errors"
"fmt"
"math/big"
"sync"
"time"
@ -242,16 +243,31 @@ func (m *MsgPackHandler) handleHealthCommand() (*messages.HealthResponse, error)
}
func (m *MsgPackHandler) handleFetchCRLCommand(command *messages.FetchCRLCommand) (*messages.FetchCRLResponse, error) {
res, err := m.fetchCRLHandler.FetchCRL(command.IssuerID)
var crlNumber *big.Int
if command.LastKnownID != nil {
crlNumber = new(big.Int).SetBytes(command.LastKnownID)
}
res, err := m.fetchCRLHandler.FetchCRL(command.IssuerID, crlNumber)
if err != nil {
return nil, fmt.Errorf("could not fetch CRL: %w", err)
}
return &messages.FetchCRLResponse{
IsDelta: false,
CRLNumber: res.Number,
CRLData: res.CRLData,
}, nil
unchanged := crlNumber != nil && crlNumber.Cmp(res.Number) == 0
response := &messages.FetchCRLResponse{
IssuerID: command.IssuerID,
IsDelta: res.IsDelta,
UnChanged: unchanged,
CRLNumber: res.Number.Bytes(),
}
if !unchanged {
response.CRLData = res.CRLData
}
return response, nil
}
func New(logger *logrus.Logger, handlers ...RegisterHandler) (protocol.ServerHandler, error) {

@ -37,6 +37,8 @@ import (
"github.com/ThalesIgnite/crypto11"
"github.com/sirupsen/logrus"
"git.cacert.org/cacert-gosigner/pkg/messages"
"git.cacert.org/cacert-gosigner/internal/config"
"git.cacert.org/cacert-gosigner/internal/health"
)
@ -68,7 +70,7 @@ func (a *Access) Healthy() (*health.Info, error) {
moreInfo := make(map[string]string)
const checkFailed = "failed"
var checkFailed = messages.CertificateInfo{Status: "failed", Signing: false}.String()
for _, ca := range a.signerConfig.RootCAs() {
infoKey := fmt.Sprintf("root-%s", ca)
@ -82,7 +84,12 @@ func (a *Access) Healthy() (*health.Info, error) {
continue
}
moreInfo[infoKey] = fmt.Sprintf("ok, valid until %s", cert.NotAfter.UTC().Format(time.RFC3339))
moreInfo[infoKey] = messages.CertificateInfo{
Status: "ok",
Signing: false,
Profiles: []messages.CAProfile{},
ValidUntil: cert.NotAfter.UTC(),
}.String()
}
for _, ca := range a.signerConfig.SubordinateCAs() {
@ -115,7 +122,12 @@ func (a *Access) Healthy() (*health.Info, error) {
continue
}
moreInfo[infoKey] = fmt.Sprintf("ok, valid until %s", cert.NotAfter.UTC().Format(time.RFC3339))
moreInfo[infoKey] = messages.CertificateInfo{
Status: "ok",
Signing: true,
Profiles: def.Profiles,
ValidUntil: cert.NotAfter.UTC(),
}.String()
}
return &health.Info{

@ -27,6 +27,7 @@ import (
"math/big"
"os"
"path"
"path/filepath"
"strings"
"sync"
"time"
@ -96,6 +97,70 @@ type Repository struct {
crlNumberFileName string
lock sync.Locker
entries []indexEntry
crlDirectory string
}
func (r *Repository) CleanUp() {
panic("implement me")
}
func (r *Repository) buildCRLFilename(b *big.Int) string {
number := fmt.Sprintf("%020x", b)
return path.Join(r.crlDirectory, number[:2], number[2:4], fmt.Sprintf("%s.crl", number[4:]))
}
func (r *Repository) currentCRLLink() string {
return path.Join(r.crlDirectory, "current.crl")
}
func (r *Repository) LoadCRL(b *big.Int) ([]byte, error) {
var crlFileName string
if b == nil {
crlFileName = r.currentCRLLink()
} else {
crlFileName = r.buildCRLFilename(b)
}
crlData, err := os.ReadFile(crlFileName)
if err != nil {
return nil, fmt.Errorf("could not read CRL from %s: %w", crlFileName, err)
}
return crlData, nil
}
func (r *Repository) StoreCRL(b *big.Int, bytes []byte) error {
if b == nil {
return errors.New("crl number must not be nil")
}
crlFilename := r.buildCRLFilename(b)
err := os.MkdirAll(path.Dir(crlFilename), 0o700)
if err != nil {
return fmt.Errorf("could not create directory hierarchy for %s: %w", crlFilename, err)
}
err = os.WriteFile(crlFilename, bytes, 0o600)
if err != nil {
return fmt.Errorf("could not write CRL to %s: %w", crlFilename, err)
}
crlLink := r.currentCRLLink()
if err = os.Remove(crlLink); err != nil {
if !os.IsNotExist(err) {
return fmt.Errorf("could not remove CRL symlink %s: %w", crlLink, err)
}
}
if err = os.Symlink(crlFilename, crlLink); err != nil {
return fmt.Errorf("could not create CRL symlink from %s to %s: %w", crlFilename, crlLink, err)
}
return nil
}
func (r *Repository) NextCRLNumber() (*big.Int, error) {
@ -420,15 +485,21 @@ func NewFileRepository(baseDirectory string) (*Repository, error) {
return nil, fmt.Errorf("could not change to base directory %s: %w", baseDirectory, err)
}
err = os.MkdirAll(baseDirectory, 0750) //nolint:gomnd
err = os.MkdirAll(baseDirectory, 0o750) //nolint:gomnd
if err != nil {
return nil, fmt.Errorf("could not create base directory %s: %w", baseDirectory, err)
}
}
baseDirectory, err = filepath.Abs(baseDirectory)
if err != nil {
return nil, fmt.Errorf("could not get absolute name for %s: %w", baseDirectory, err)
}
return &Repository{
indexFileName: path.Join(baseDirectory, "index.txt"),
crlNumberFileName: path.Join(baseDirectory, "crlnumber"),
crlDirectory: path.Join(baseDirectory, "crls"),
lock: &sync.Mutex{},
}, nil
}

@ -26,6 +26,9 @@ import (
type Repository interface {
// StoreRevocation stores information about a revoked certificate.
StoreRevocation(*pkix.RevokedCertificate) error
LoadCRL(*big.Int) ([]byte, error)
StoreCRL(*big.Int, []byte) error
RevokedCertificates() ([]pkix.RevokedCertificate, error)
NextCRLNumber() (*big.Int, error)
CleanUp()
}

@ -28,6 +28,9 @@ import (
"math/big"
"strings"
"time"
"github.com/balacode/go-delta"
"github.com/sirupsen/logrus"
)
var OidCRLReason = asn1.ObjectIdentifier{2, 5, 29, 21}
@ -93,6 +96,7 @@ type X509Revoking struct {
crlAlgorithm x509.SignatureAlgorithm
crlIssuer *x509.Certificate
signer crypto.Signer
logger *logrus.Logger
}
type RevokeCertificate struct {
@ -108,8 +112,9 @@ func NewRevokeCertificate(serialNumber *big.Int, reason CRLReason) *RevokeCertif
}
type CRLInformation struct {
CRL []byte // DER encoded CRL
Number *big.Int
CRL []byte // DER encoded CRL
Number *big.Int
NextUpdate time.Time
}
func (r *X509Revoking) Revoke(revokeCertificate *RevokeCertificate) (*pkix.RevokedCertificate, error) {
@ -126,7 +131,7 @@ func (r *X509Revoking) Revoke(revokeCertificate *RevokeCertificate) (*pkix.Revok
return revoked, nil
}
func (r *X509Revoking) CreateCRL() (*CRLInformation, error) {
func (r *X509Revoking) createCRL() (*CRLInformation, error) {
revoked, err := r.repository.RevokedCertificates()
if err != nil {
return nil, fmt.Errorf("could not get revocation information: %w", err)
@ -137,17 +142,63 @@ func (r *X509Revoking) CreateCRL() (*CRLInformation, error) {
return nil, fmt.Errorf("could not get next CRL number: %w", err)
}
nextUpdate := time.Now().UTC().Add(defaultCRLValidity)
list, err := x509.CreateRevocationList(rand.Reader, &x509.RevocationList{
SignatureAlgorithm: r.crlAlgorithm,
RevokedCertificates: revoked,
Number: nextNumber,
NextUpdate: time.Now().UTC().Add(defaultCRLValidity),
ThisUpdate: time.Now().UTC(),
NextUpdate: nextUpdate,
}, r.crlIssuer, r.signer)
if err != nil {
return nil, fmt.Errorf("could not sign revocation list: %w", err)
}
return &CRLInformation{CRL: list, Number: nextNumber}, nil
err = r.repository.StoreCRL(nextNumber, list)
if err != nil {
return nil, fmt.Errorf("could not store new CRL: %w", err)
}
return &CRLInformation{CRL: list, Number: nextNumber, NextUpdate: nextUpdate}, nil
}
func (r *X509Revoking) GetCurrentCRL() (*CRLInformation, error) {
return r.GetCRL(nil)
}
const maximumCRLLifetime = 6 * time.Hour
func (r *X509Revoking) GetCRL(number *big.Int) (*CRLInformation, error) {
var (
crl []byte
err error
list *x509.RevocationList
)
crl, err = r.repository.LoadCRL(number)
if err != nil {
r.logger.WithError(err).Warn("could not load CRL")
if number != nil {
return nil, fmt.Errorf("could not load crl number 0x%0x", number)
}
}
if crl != nil {
list, err = x509.ParseRevocationList(crl)
if err != nil {
r.logger.WithError(err).Warn("could not parse CRL")
}
stillValid := list.ThisUpdate.Add(maximumCRLLifetime).After(time.Now().UTC())
if number != nil || stillValid {
return &CRLInformation{CRL: crl, Number: list.Number, NextUpdate: list.NextUpdate}, nil
}
}
return r.createCRL()
}
func NewX509Revoking(
@ -155,12 +206,20 @@ func NewX509Revoking(
crlAlgorithm x509.SignatureAlgorithm,
issuer *x509.Certificate,
signer crypto.Signer,
logger *logrus.Logger,
) *X509Revoking {
return &X509Revoking{repository: repo, crlAlgorithm: crlAlgorithm, crlIssuer: issuer, signer: signer}
return &X509Revoking{
repository: repo,
crlAlgorithm: crlAlgorithm,
crlIssuer: issuer,
signer: signer,
logger: logger,
}
}
type Result struct {
CRLData []byte
IsDelta bool
Number *big.Int
}
@ -172,16 +231,45 @@ func NewFetchCRLHandler(repositories map[string]*X509Revoking) *FetchCRLHandler
return &FetchCRLHandler{repositories: repositories}
}
func (h *FetchCRLHandler) FetchCRL(issuerID string) (*Result, error) {
func (h *FetchCRLHandler) FetchCRL(issuerID string, crlNumber *big.Int) (*Result, error) {
var (
currentCRL, oldCRL *CRLInformation
err error
)
repo, ok := h.repositories[issuerID]
if !ok {
return nil, fmt.Errorf("unknown issuer ID %s", issuerID)
}
currentCRL, err := repo.CreateCRL()
if repo.signer == nil {
return nil, fmt.Errorf("key for issuer ID %s is not available", issuerID)
}
currentCRL, err = repo.GetCurrentCRL()
if err != nil {
return nil, fmt.Errorf("could not get CRL for issuer ID %s: %w", issuerID, err)
}
if crlNumber == nil {
return &Result{CRLData: currentCRL.CRL, Number: currentCRL.Number, IsDelta: false}, nil
}
if crlNumber.Cmp(currentCRL.Number) == 0 {
return &Result{CRLData: nil, Number: currentCRL.Number, IsDelta: false}, nil
}
oldCRL, err = repo.GetCRL(crlNumber)
if err != nil {
return nil, fmt.Errorf("could not create CRL for issuer ID %s: %w", issuerID, err)
return &Result{CRLData: currentCRL.CRL, Number: currentCRL.Number, IsDelta: false}, nil
}
diff := delta.Make(oldCRL.CRL, currentCRL.CRL)
patchBytes := diff.Bytes()
if len(patchBytes) > len(currentCRL.CRL) {
return &Result{CRLData: currentCRL.CRL, Number: currentCRL.Number, IsDelta: false}, nil
}
return &Result{CRLData: currentCRL.CRL, Number: currentCRL.Number}, nil
return &Result{CRLData: patchBytes, Number: currentCRL.Number, IsDelta: true}, nil
}

@ -18,6 +18,7 @@ limitations under the License.
package revoking_test
import (
"bytes"
"crypto/rand"
"crypto/rsa"
"crypto/x509"
@ -28,6 +29,7 @@ import (
"math/big"
"testing"
"github.com/sirupsen/logrus"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
@ -49,9 +51,36 @@ func randomSerial(t *testing.T) *big.Int {
type testRepo struct {
crlNumber *big.Int
crls map[string][]byte
current string
revoked []pkix.RevokedCertificate
}
func (t *testRepo) LoadCRL(b *big.Int) ([]byte, error) {
var key string
if b == nil {
key = t.current
} else {
key = b.String()
}
crl, ok := t.crls[key]
if !ok {
return nil, errors.New("no CRL for you")
}
return crl, nil
}
func (t *testRepo) StoreCRL(b *big.Int, crl []byte) error {
t.crls[b.String()] = crl
return nil
}
func (t *testRepo) CleanUp() {}
func (t *testRepo) NextCRLNumber() (*big.Int, error) {
newNumber := new(big.Int).Add(t.crlNumber, big.NewInt(1))
@ -74,7 +103,9 @@ func (t *testRepo) StoreRevocation(revoked *pkix.RevokedCertificate) error {
return nil
}
type brokenRepo struct{}
type brokenRepo struct {
noStoreRepo
}
func (r *brokenRepo) NextCRLNumber() (*big.Int, error) {
return nil, errors.New("don't know")
@ -88,14 +119,28 @@ func (*brokenRepo) StoreRevocation(_ *pkix.RevokedCertificate) error {
return errors.New("cannot store")
}
type noStoreRepo struct{}
func (r noStoreRepo) StoreRevocation(_ *pkix.RevokedCertificate) error {
// do nothing
return nil
}
type brokenRepoNoCrlNumber struct {
noStoreRepo
}
func (r noStoreRepo) LoadCRL(_ *big.Int) ([]byte, error) {
return nil, errors.New("no CRL")
}
func (b brokenRepoNoCrlNumber) StoreRevocation(_ *pkix.RevokedCertificate) error {
func (r noStoreRepo) StoreCRL(_ *big.Int, _ []byte) error {
// do nothing
return nil
}
func (r noStoreRepo) CleanUp() {}
func (b brokenRepoNoCrlNumber) RevokedCertificates() ([]pkix.RevokedCertificate, error) {
return make([]pkix.RevokedCertificate, 0), nil
}
@ -105,11 +150,7 @@ func (b brokenRepoNoCrlNumber) NextCRLNumber() (*big.Int, error) {
}
type brokenRepoNoRevocations struct {
}
func (b brokenRepoNoRevocations) StoreRevocation(_ *pkix.RevokedCertificate) error {
// do nothing
return nil
noStoreRepo
}
func (b brokenRepoNoRevocations) RevokedCertificates() ([]pkix.RevokedCertificate, error) {
@ -121,11 +162,18 @@ func (b brokenRepoNoRevocations) NextCRLNumber() (*big.Int, error) {
}
func TestX509Revoking_Revoke(t *testing.T) {
testRepository := testRepo{revoked: make([]pkix.RevokedCertificate, 0), crlNumber: big.NewInt(0)}
testRepository := testRepo{
revoked: make([]pkix.RevokedCertificate, 0),
crlNumber: big.NewInt(0),
crls: map[string][]byte{},
}
caKey, caCertificate := prepareTestCA(t)
r := revoking.NewX509Revoking(&testRepository, x509.ECDSAWithSHA256, caCertificate, caKey)
logger := logrus.New()
logger.SetOutput(&bytes.Buffer{})
r := revoking.NewX509Revoking(&testRepository, x509.ECDSAWithSHA256, caCertificate, caKey, logger)
serial := randomSerial(t)
@ -149,7 +197,10 @@ func TestX509Revoking_Revoke(t *testing.T) {
func TestX509Revoking_Revoke_BrokenRepo(t *testing.T) {
caKey, caCertificate := prepareTestCA(t)
r := revoking.NewX509Revoking(&brokenRepo{}, x509.SHA256WithRSA, caCertificate, caKey)
logger := logrus.New()
logger.SetOutput(&bytes.Buffer{})
r := revoking.NewX509Revoking(&brokenRepo{}, x509.SHA256WithRSA, caCertificate, caKey, logger)
serial := randomSerial(t)
@ -163,11 +214,12 @@ func TestX509Revoking_Revoke_BrokenRepo(t *testing.T) {
func TestX509Revoking_CreateCRL(t *testing.T) {
key, certificate := prepareTestCA(t)
logger := logrus.New()
logger.SetOutput(&bytes.Buffer{})
r := revoking.NewX509Revoking(
&testRepo{revoked: make([]pkix.RevokedCertificate, 0), crlNumber: big.NewInt(0)},
x509.SHA256WithRSA,
certificate,
key,
&testRepo{revoked: make([]pkix.RevokedCertificate, 0), crlNumber: big.NewInt(0), crls: map[string][]byte{}},
x509.SHA256WithRSA, certificate, key, logger,
)
serial := randomSerial(t)
@ -175,7 +227,7 @@ func TestX509Revoking_CreateCRL(t *testing.T) {
_, err := r.Revoke(revoking.NewRevokeCertificate(serial, revoking.CRLReasonKeyCompromise))
require.NoError(t, err)
crl, err := r.CreateCRL()
crl, err := r.GetCRL(nil)
assert.NoError(t, err)
assert.NotNil(t, crl)
@ -200,48 +252,55 @@ func TestX509Revoking_CreateCRL(t *testing.T) {
assert.True(t, found)
}
func TestX509Revoking_CreateCRL_BrokenRepoNoRevocations(t *testing.T) {
func TestX509Revoking_GetCRL_BrokenRepoNoRevocations(t *testing.T) {
caKey, caCertificate := prepareTestCA(t)
r := revoking.NewX509Revoking(&brokenRepoNoRevocations{}, x509.SHA256WithRSA, caCertificate, caKey)
logger := logrus.New()
logger.SetOutput(&bytes.Buffer{})
r := revoking.NewX509Revoking(&brokenRepoNoRevocations{}, x509.SHA256WithRSA, caCertificate, caKey, logger)
serial := randomSerial(t)
_, err := r.Revoke(revoking.NewRevokeCertificate(serial, revoking.CRLReasonKeyCompromise))
require.NoError(t, err)
crl, err := r.CreateCRL()
crl, err := r.GetCRL(nil)
assert.Error(t, err)
assert.ErrorContains(t, err, "could not get revocation information")
assert.Nil(t, crl)
}
func TestX509Revoking_CreateCRL_BrokenRepoNoCRLNumber(t *testing.T) {
func TestX509Revoking_GetCRL_BrokenRepoNoCRLNumber(t *testing.T) {
caKey, caCertificate := prepareTestCA(t)
r := revoking.NewX509Revoking(&brokenRepoNoCrlNumber{}, x509.SHA256WithRSA, caCertificate, caKey)
logger := logrus.New()
logger.SetOutput(&bytes.Buffer{})
r := revoking.NewX509Revoking(&brokenRepoNoCrlNumber{}, x509.SHA256WithRSA, caCertificate, caKey, logger)
serial := randomSerial(t)
_, err := r.Revoke(revoking.NewRevokeCertificate(serial, revoking.CRLReasonKeyCompromise))
require.NoError(t, err)
crl, err := r.CreateCRL()
crl, err := r.GetCRL(nil)
assert.Error(t, err)
assert.ErrorContains(t, err, "could not get next CRL number")
assert.Nil(t, crl)
}
func TestX509Revoking_CreateCRL_WrongAlgorithm(t *testing.T) {
func TestX509Revoking_GetCRL_WrongAlgorithm(t *testing.T) {
key, certificate := prepareTestCA(t)
logger := logrus.New()
logger.SetOutput(&bytes.Buffer{})
r := revoking.NewX509Revoking(
&testRepo{revoked: make([]pkix.RevokedCertificate, 0), crlNumber: big.NewInt(0)},
x509.ECDSAWithSHA256,
certificate,
key,
&testRepo{revoked: make([]pkix.RevokedCertificate, 0), crlNumber: big.NewInt(0), crls: map[string][]byte{}},
x509.ECDSAWithSHA256, certificate, key, logger,
)
serial := randomSerial(t)
@ -249,7 +308,7 @@ func TestX509Revoking_CreateCRL_WrongAlgorithm(t *testing.T) {
_, err := r.Revoke(revoking.NewRevokeCertificate(serial, revoking.CRLReasonKeyCompromise))
require.NoError(t, err)
crl, err := r.CreateCRL()
crl, err := r.GetCRL(nil)
assert.Error(t, err)
assert.ErrorContains(t, err, "could not sign revocation list")

@ -22,6 +22,7 @@ package messages
import (
"crypto/x509"
"encoding/json"
"encoding/pem"
"fmt"
"math/big"
@ -101,8 +102,8 @@ func (r *ResponseAnnounce) String() string {
}
type FetchCRLCommand struct {
IssuerID string `msgpack:"issuer_id"`
LastKnownID *big.Int `msgpack:"last_known_id"`
IssuerID string `msgpack:"issuer_id"`
LastKnownID []byte `msgpack:"last_known_id"`
}
func (f *FetchCRLCommand) String() string {
@ -111,7 +112,7 @@ func (f *FetchCRLCommand) String() string {
_, _ = fmt.Fprintf(builder, "issuerId='%s'", f.IssuerID)
if f.LastKnownID != nil {
_, _ = fmt.Fprintf(builder, ", lastKnownId=%s", f.LastKnownID.Text(16))
_, _ = fmt.Fprintf(builder, ", lastKnownId=0x%s", new(big.Int).SetBytes(f.LastKnownID).Text(16))
}
return builder.String()
@ -144,6 +145,66 @@ func (i *HealthInfo) String() string {
return builder.String()
}
type ProfileUsage string
const (
UsageOcsp ProfileUsage = "ocsp"
UsagePerson ProfileUsage = "person"
UsageClient ProfileUsage = "client"
UsageCode ProfileUsage = "code"
UsageServer ProfileUsage = "server"
)
var validProfileUsages = map[string]ProfileUsage{
"ocsp": UsageOcsp,
"person": UsagePerson,
"client": UsageClient,
"code": UsageCode,
"server": UsageServer,
}
func ParseUsage(u string) (ProfileUsage, error) {
usage, ok := validProfileUsages[u]
if !ok {
return "", fmt.Errorf("unsupported profile usage: %s", u)
}
return usage, nil
}
type CAProfile struct {
Name string `json:"name"`
UseFor ProfileUsage `json:"use-for"`
}
func (p CAProfile) String() string {
return fmt.Sprintf("profile['%s': '%s']", p.Name, p.UseFor)
}
type CertificateInfo struct {
Status string `json:"status"`
Signing bool `json:"signing"`
Profiles []CAProfile `json:"profiles"`
ValidUntil time.Time `json:"valid-until"`
}
func (i CertificateInfo) String() string {
marshal, _ := json.Marshal(i)
return string(marshal)
}
func (i *HealthInfo) ParseCertificateInfo(info string) (*CertificateInfo, error) {
certInfo := CertificateInfo{}
err := json.Unmarshal([]byte(info), &certInfo)
if err != nil {
return nil, fmt.Errorf("could not parse certificate information: %w", err)
}
return &certInfo, nil
}
type HealthResponse struct {
Version string `msgpack:"version"`
Healthy bool `msgpack:"healthy"`
@ -165,38 +226,54 @@ func (h *HealthResponse) String() string {
type FetchCRLResponse struct {
IssuerID string `msgpack:"issuer_id"`
IsDelta bool `msgpack:"is_delta"`
UnChanged bool `msgpack:"unchanged"`
CRLData []byte `msgpack:"crl_data"`
CRLNumber *big.Int
CRLNumber []byte `msgpack:"crl_number"`
}
func (r *FetchCRLResponse) String() string {
builder := &strings.Builder{}
_, _ = fmt.Fprintf(builder, "issuer id=%s, delta CRL data=%v", r.IssuerID, r.IsDelta)
_, _ = fmt.Fprintf(
builder,
"issuer id=%s, delta CRL data=%t, unchanged=%t, CRL number=0x%s",
r.IssuerID,
r.IsDelta,
r.UnChanged,
new(big.Int).SetBytes(r.CRLNumber).Text(16),
)
if r.UnChanged {
return builder.String()
}
if r.IsDelta {
_, _ = fmt.Fprint(builder, ", delta CRL data not shown")
} else {
revocationList, err := x509.ParseRevocationList(r.CRLData)
if err != nil {
_, _ = fmt.Fprintf(builder, ", could not parse CRL: %s", err.Error())
} else {
_, _ = fmt.Fprintf(
builder,
", CRL info: issuer=%s, number=%s, next update=%s, revoked certificates=%d",
revocationList.Issuer,
revocationList.Number,
revocationList.NextUpdate,
len(revocationList.RevokedCertificates),
)
_, _ = builder.WriteString(", CRL data:\n")
_ = pem.Encode(builder, &pem.Block{
Type: "CERTIFICATE REVOCATION LIST",
Bytes: r.CRLData,
})
}
return builder.String()
}
revocationList, err := x509.ParseRevocationList(r.CRLData)
if err != nil {
_, _ = fmt.Fprintf(builder, ", could not parse CRL: %s", err.Error())
return builder.String()
}
_, _ = fmt.Fprintf(
builder,
", CRL info: issuer=%s, number=0x%s, next update=%s, revoked certificates=%d",
revocationList.Issuer,
revocationList.Number.Text(16),
revocationList.NextUpdate,
len(revocationList.RevokedCertificates),
)
_, _ = builder.WriteString(", CRL data:\n")
_ = pem.Encode(builder, &pem.Block{
Type: "CERTIFICATE REVOCATION LIST",
Bytes: r.CRLData,
})
return builder.String()
}

@ -26,6 +26,36 @@ func ___encode(i interface{}) ([]byte, error) {
// encodeAsArray
func ___encodeAsArray(i interface{}) ([]byte, error) {
switch v := i.(type) {
case FetchCRLCommand:
encoder := enc.NewEncoder()
size, err := ___calcArraySizeFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder)
if err != nil {
return nil, err
}
encoder.MakeBytes(size)
b, offset, err := ___encodeArrayFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder, 0)
if err != nil {
return nil, err
}
if size != offset {
return nil, fmt.Errorf("%s size / offset different %d : %d", "FetchCRLCommand", size, offset)
}
return b, err
case *FetchCRLCommand:
encoder := enc.NewEncoder()
size, err := ___calcArraySizeFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, encoder)
if err != nil {
return nil, err
}
encoder.MakeBytes(size)
b, offset, err := ___encodeArrayFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, encoder, 0)
if err != nil {
return nil, err
}
if size != offset {
return nil, fmt.Errorf("%s size / offset different %d : %d", "FetchCRLCommand", size, offset)
}
return b, err
case HealthCommand:
encoder := enc.NewEncoder()
size, err := ___calcArraySizeHealthCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder)
@ -116,6 +146,36 @@ func ___encodeAsArray(i interface{}) ([]byte, error) {
return nil, fmt.Errorf("%s size / offset different %d : %d", "HealthResponse", size, offset)
}
return b, err
case FetchCRLResponse:
encoder := enc.NewEncoder()
size, err := ___calcArraySizeFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder)
if err != nil {
return nil, err
}
encoder.MakeBytes(size)
b, offset, err := ___encodeArrayFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder, 0)
if err != nil {
return nil, err
}
if size != offset {
return nil, fmt.Errorf("%s size / offset different %d : %d", "FetchCRLResponse", size, offset)
}
return b, err
case *FetchCRLResponse:
encoder := enc.NewEncoder()
size, err := ___calcArraySizeFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, encoder)
if err != nil {
return nil, err
}
encoder.MakeBytes(size)
b, offset, err := ___encodeArrayFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, encoder, 0)
if err != nil {
return nil, err
}
if size != offset {
return nil, fmt.Errorf("%s size / offset different %d : %d", "FetchCRLResponse", size, offset)
}
return b, err
case ErrorResponse:
encoder := enc.NewEncoder()
size, err := ___calcArraySizeErrorResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder)
@ -153,6 +213,36 @@ func ___encodeAsArray(i interface{}) ([]byte, error) {
// encodeAsMap
func ___encodeAsMap(i interface{}) ([]byte, error) {
switch v := i.(type) {
case FetchCRLCommand:
encoder := enc.NewEncoder()
size, err := ___calcMapSizeFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder)
if err != nil {
return nil, err
}
encoder.MakeBytes(size)
b, offset, err := ___encodeMapFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder, 0)
if err != nil {
return nil, err
}
if size != offset {
return nil, fmt.Errorf("%s size / offset different %d : %d", "FetchCRLCommand", size, offset)
}
return b, err
case *FetchCRLCommand:
encoder := enc.NewEncoder()
size, err := ___calcMapSizeFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, encoder)
if err != nil {
return nil, err
}
encoder.MakeBytes(size)
b, offset, err := ___encodeMapFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, encoder, 0)
if err != nil {
return nil, err
}
if size != offset {
return nil, fmt.Errorf("%s size / offset different %d : %d", "FetchCRLCommand", size, offset)
}
return b, err
case HealthCommand:
encoder := enc.NewEncoder()
size, err := ___calcMapSizeHealthCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder)
@ -243,6 +333,36 @@ func ___encodeAsMap(i interface{}) ([]byte, error) {
return nil, fmt.Errorf("%s size / offset different %d : %d", "HealthResponse", size, offset)
}
return b, err
case FetchCRLResponse:
encoder := enc.NewEncoder()
size, err := ___calcMapSizeFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder)
if err != nil {
return nil, err
}
encoder.MakeBytes(size)
b, offset, err := ___encodeMapFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder, 0)
if err != nil {
return nil, err
}
if size != offset {
return nil, fmt.Errorf("%s size / offset different %d : %d", "FetchCRLResponse", size, offset)
}
return b, err
case *FetchCRLResponse:
encoder := enc.NewEncoder()
size, err := ___calcMapSizeFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, encoder)
if err != nil {
return nil, err
}
encoder.MakeBytes(size)
b, offset, err := ___encodeMapFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, encoder, 0)
if err != nil {
return nil, err
}
if size != offset {
return nil, fmt.Errorf("%s size / offset different %d : %d", "FetchCRLResponse", size, offset)
}
return b, err
case ErrorResponse:
encoder := enc.NewEncoder()
size, err := ___calcMapSizeErrorResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, encoder)
@ -289,6 +409,20 @@ func ___decode(data []byte, i interface{}) (bool, error) {
// decodeAsArray
func ___decodeAsArray(data []byte, i interface{}) (bool, error) {
switch v := i.(type) {
case *FetchCRLCommand:
decoder := dec.NewDecoder(data)
offset, err := ___decodeArrayFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, decoder, 0)
if err == nil && offset != decoder.Len() {
return true, fmt.Errorf("read length is different [%d] [%d] ", offset, decoder.Len())
}
return true, err
case **FetchCRLCommand:
decoder := dec.NewDecoder(data)
offset, err := ___decodeArrayFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, decoder, 0)
if err == nil && offset != decoder.Len() {
return true, fmt.Errorf("read length is different [%d] [%d] ", offset, decoder.Len())
}
return true, err
case *HealthCommand:
decoder := dec.NewDecoder(data)
offset, err := ___decodeArrayHealthCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, decoder, 0)
@ -331,6 +465,20 @@ func ___decodeAsArray(data []byte, i interface{}) (bool, error) {
return true, fmt.Errorf("read length is different [%d] [%d] ", offset, decoder.Len())
}
return true, err
case *FetchCRLResponse:
decoder := dec.NewDecoder(data)
offset, err := ___decodeArrayFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, decoder, 0)
if err == nil && offset != decoder.Len() {
return true, fmt.Errorf("read length is different [%d] [%d] ", offset, decoder.Len())
}
return true, err
case **FetchCRLResponse:
decoder := dec.NewDecoder(data)
offset, err := ___decodeArrayFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, decoder, 0)
if err == nil && offset != decoder.Len() {
return true, fmt.Errorf("read length is different [%d] [%d] ", offset, decoder.Len())
}
return true, err
case *ErrorResponse:
decoder := dec.NewDecoder(data)
offset, err := ___decodeArrayErrorResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, decoder, 0)
@ -352,6 +500,20 @@ func ___decodeAsArray(data []byte, i interface{}) (bool, error) {
// decodeAsMap
func ___decodeAsMap(data []byte, i interface{}) (bool, error) {
switch v := i.(type) {
case *FetchCRLCommand:
decoder := dec.NewDecoder(data)
offset, err := ___decodeMapFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, decoder, 0)
if err == nil && offset != decoder.Len() {
return true, fmt.Errorf("read length is different [%d] [%d] ", offset, decoder.Len())
}
return true, err
case **FetchCRLCommand:
decoder := dec.NewDecoder(data)
offset, err := ___decodeMapFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, decoder, 0)
if err == nil && offset != decoder.Len() {
return true, fmt.Errorf("read length is different [%d] [%d] ", offset, decoder.Len())
}
return true, err
case *HealthCommand:
decoder := dec.NewDecoder(data)
offset, err := ___decodeMapHealthCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, decoder, 0)
@ -394,6 +556,20 @@ func ___decodeAsMap(data []byte, i interface{}) (bool, error) {
return true, fmt.Errorf("read length is different [%d] [%d] ", offset, decoder.Len())
}
return true, err
case *FetchCRLResponse:
decoder := dec.NewDecoder(data)
offset, err := ___decodeMapFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, decoder, 0)
if err == nil && offset != decoder.Len() {
return true, fmt.Errorf("read length is different [%d] [%d] ", offset, decoder.Len())
}
return true, err
case **FetchCRLResponse:
decoder := dec.NewDecoder(data)
offset, err := ___decodeMapFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(*v, decoder, 0)
if err == nil && offset != decoder.Len() {
return true, fmt.Errorf("read length is different [%d] [%d] ", offset, decoder.Len())
}
return true, err
case *ErrorResponse:
decoder := dec.NewDecoder(data)
offset, err := ___decodeMapErrorResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v, decoder, 0)
@ -412,6 +588,192 @@ func ___decodeAsMap(data []byte, i interface{}) (bool, error) {
return false, nil
}
// calculate size from git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLCommand
func ___calcArraySizeFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v FetchCRLCommand, encoder *enc.Encoder) (int, error) {
size := 0
size += encoder.CalcStructHeaderFix(2)
size += encoder.CalcString(v.IssuerID)
if v.LastKnownID != nil {
s, err := encoder.CalcSliceLength(len(v.LastKnownID), true)
if err != nil {
return 0, err
}
size += s
for _, vv := range v.LastKnownID {
size += encoder.CalcByte(vv)
}
} else {
size += encoder.CalcNil()
}
return size, nil
}
// calculate size from git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLCommand
func ___calcMapSizeFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v FetchCRLCommand, encoder *enc.Encoder) (int, error) {
size := 0
size += encoder.CalcStructHeaderFix(2)
size += encoder.CalcStringFix(9)
size += encoder.CalcString(v.IssuerID)
size += encoder.CalcStringFix(13)
if v.LastKnownID != nil {
s, err := encoder.CalcSliceLength(len(v.LastKnownID), true)
if err != nil {
return 0, err
}
size += s
for _, vv := range v.LastKnownID {
size += encoder.CalcByte(vv)
}
} else {
size += encoder.CalcNil()
}
return size, nil
}
// encode from git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLCommand
func ___encodeArrayFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v FetchCRLCommand, encoder *enc.Encoder, offset int) ([]byte, int, error) {
var err error
offset = encoder.WriteStructHeaderFixAsArray(2, offset)
offset = encoder.WriteString(v.IssuerID, offset)
if v.LastKnownID != nil {
offset = encoder.WriteSliceLength(len(v.LastKnownID), offset, true)
for _, vv := range v.LastKnownID {
offset = encoder.WriteByte(vv, offset)
}
} else {
offset = encoder.WriteNil(offset)
}
return encoder.EncodedBytes(), offset, err
}
// encode from git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLCommand
func ___encodeMapFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v FetchCRLCommand, encoder *enc.Encoder, offset int) ([]byte, int, error) {
var err error
offset = encoder.WriteStructHeaderFixAsMap(2, offset)
offset = encoder.WriteStringFix("issuer_id", 9, offset)
offset = encoder.WriteString(v.IssuerID, offset)
offset = encoder.WriteStringFix("last_known_id", 13, offset)
if v.LastKnownID != nil {
offset = encoder.WriteSliceLength(len(v.LastKnownID), offset, true)
for _, vv := range v.LastKnownID {
offset = encoder.WriteByte(vv, offset)
}
} else {
offset = encoder.WriteNil(offset)
}
return encoder.EncodedBytes(), offset, err
}
// decode to git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLCommand
func ___decodeArrayFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v *FetchCRLCommand, decoder *dec.Decoder, offset int) (int, error) {
offset, err := decoder.CheckStructHeader(2, offset)
if err != nil {
return 0, err
}
{
var vv string
vv, offset, err = decoder.AsString(offset)
if err != nil {
return 0, err
}
v.IssuerID = vv
}
if !decoder.IsCodeNil(offset) {
var vv []byte
var vvl int
vvl, offset, err = decoder.SliceLength(offset)
if err != nil {
return 0, err
}
vv = make([]byte, vvl)
for vvi := range vv {
var vvv byte
vvv, offset, err = decoder.AsByte(offset)
if err != nil {
return 0, err
}
vv[vvi] = vvv
}
v.LastKnownID = vv
} else {
offset++
}
return offset, err
}
// decode to git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLCommand
func ___decodeMapFetchCRLCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v *FetchCRLCommand, decoder *dec.Decoder, offset int) (int, error) {
keys := [][]byte{
{uint8(0x69), uint8(0x73), uint8(0x73), uint8(0x75), uint8(0x65), uint8(0x72), uint8(0x5f), uint8(0x69), uint8(0x64)}, // issuer_id
{uint8(0x6c), uint8(0x61), uint8(0x73), uint8(0x74), uint8(0x5f), uint8(0x6b), uint8(0x6e), uint8(0x6f), uint8(0x77), uint8(0x6e), uint8(0x5f), uint8(0x69), uint8(0x64)}, // last_known_id
}
offset, err := decoder.CheckStructHeader(2, offset)
if err != nil {
return 0, err
}
count := 0
for count < 2 {
var dataKey []byte
dataKey, offset, err = decoder.AsStringBytes(offset)
if err != nil {
return 0, err
}
fieldIndex := -1
for i, key := range keys {
if len(dataKey) != len(key) {
continue
}
fieldIndex = i
for dataKeyIndex := range dataKey {
if dataKey[dataKeyIndex] != key[dataKeyIndex] {
fieldIndex = -1
break
}
}
if fieldIndex >= 0 {
break
}
}
switch fieldIndex {
case 0:
{
var vv string
vv, offset, err = decoder.AsString(offset)
if err != nil {
return 0, err
}
v.IssuerID = vv
}
count++
case 1:
if !decoder.IsCodeNil(offset) {
var vv []byte
var vvl int
vvl, offset, err = decoder.SliceLength(offset)
if err != nil {
return 0, err
}
vv = make([]byte, vvl)
for vvi := range vv {
var vvv byte
vvv, offset, err = decoder.AsByte(offset)
if err != nil {
return 0, err
}
vv[vvi] = vvv
}
v.LastKnownID = vv
} else {
offset++
}
count++
default:
return 0, fmt.Errorf("unknown key[%s] found", string(dataKey))
}
}
return offset, err
}
// calculate size from git.cacert.org/cacert-gosigner/pkg/messages.HealthCommand
func ___calcArraySizeHealthCommand_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v HealthCommand, encoder *enc.Encoder) (int, error) {
size := 0
@ -969,6 +1331,327 @@ func ___decodeMapHealthResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f
return offset, err
}
// calculate size from git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLResponse
func ___calcArraySizeFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v FetchCRLResponse, encoder *enc.Encoder) (int, error) {
size := 0
size += encoder.CalcStructHeaderFix(5)
size += encoder.CalcString(v.IssuerID)
size += encoder.CalcBool(v.IsDelta)
size += encoder.CalcBool(v.UnChanged)
if v.CRLData != nil {
s, err := encoder.CalcSliceLength(len(v.CRLData), true)
if err != nil {
return 0, err
}
size += s
for _, vv := range v.CRLData {
size += encoder.CalcByte(vv)
}
} else {
size += encoder.CalcNil()
}
if v.CRLNumber != nil {
s, err := encoder.CalcSliceLength(len(v.CRLNumber), true)
if err != nil {
return 0, err
}
size += s
for _, vv := range v.CRLNumber {
size += encoder.CalcByte(vv)
}
} else {
size += encoder.CalcNil()
}
return size, nil
}
// calculate size from git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLResponse
func ___calcMapSizeFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v FetchCRLResponse, encoder *enc.Encoder) (int, error) {
size := 0
size += encoder.CalcStructHeaderFix(5)
size += encoder.CalcStringFix(9)
size += encoder.CalcString(v.IssuerID)
size += encoder.CalcStringFix(8)
size += encoder.CalcBool(v.IsDelta)
size += encoder.CalcStringFix(9)
size += encoder.CalcBool(v.UnChanged)
size += encoder.CalcStringFix(8)
if v.CRLData != nil {
s, err := encoder.CalcSliceLength(len(v.CRLData), true)
if err != nil {
return 0, err
}
size += s
for _, vv := range v.CRLData {
size += encoder.CalcByte(vv)
}
} else {
size += encoder.CalcNil()
}
size += encoder.CalcStringFix(10)
if v.CRLNumber != nil {
s, err := encoder.CalcSliceLength(len(v.CRLNumber), true)
if err != nil {
return 0, err
}
size += s
for _, vv := range v.CRLNumber {
size += encoder.CalcByte(vv)
}
} else {
size += encoder.CalcNil()
}
return size, nil
}
// encode from git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLResponse
func ___encodeArrayFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v FetchCRLResponse, encoder *enc.Encoder, offset int) ([]byte, int, error) {
var err error
offset = encoder.WriteStructHeaderFixAsArray(5, offset)
offset = encoder.WriteString(v.IssuerID, offset)
offset = encoder.WriteBool(v.IsDelta, offset)
offset = encoder.WriteBool(v.UnChanged, offset)
if v.CRLData != nil {
offset = encoder.WriteSliceLength(len(v.CRLData), offset, true)
for _, vv := range v.CRLData {
offset = encoder.WriteByte(vv, offset)
}
} else {
offset = encoder.WriteNil(offset)
}
if v.CRLNumber != nil {
offset = encoder.WriteSliceLength(len(v.CRLNumber), offset, true)
for _, vv := range v.CRLNumber {
offset = encoder.WriteByte(vv, offset)
}
} else {
offset = encoder.WriteNil(offset)
}
return encoder.EncodedBytes(), offset, err
}
// encode from git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLResponse
func ___encodeMapFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v FetchCRLResponse, encoder *enc.Encoder, offset int) ([]byte, int, error) {
var err error
offset = encoder.WriteStructHeaderFixAsMap(5, offset)
offset = encoder.WriteStringFix("issuer_id", 9, offset)
offset = encoder.WriteString(v.IssuerID, offset)
offset = encoder.WriteStringFix("is_delta", 8, offset)
offset = encoder.WriteBool(v.IsDelta, offset)
offset = encoder.WriteStringFix("unchanged", 9, offset)
offset = encoder.WriteBool(v.UnChanged, offset)
offset = encoder.WriteStringFix("crl_data", 8, offset)
if v.CRLData != nil {
offset = encoder.WriteSliceLength(len(v.CRLData), offset, true)
for _, vv := range v.CRLData {
offset = encoder.WriteByte(vv, offset)
}
} else {
offset = encoder.WriteNil(offset)
}
offset = encoder.WriteStringFix("crl_number", 10, offset)
if v.CRLNumber != nil {
offset = encoder.WriteSliceLength(len(v.CRLNumber), offset, true)
for _, vv := range v.CRLNumber {
offset = encoder.WriteByte(vv, offset)
}
} else {
offset = encoder.WriteNil(offset)
}
return encoder.EncodedBytes(), offset, err
}
// decode to git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLResponse
func ___decodeArrayFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v *FetchCRLResponse, decoder *dec.Decoder, offset int) (int, error) {
offset, err := decoder.CheckStructHeader(5, offset)
if err != nil {
return 0, err
}
{
var vv string
vv, offset, err = decoder.AsString(offset)
if err != nil {
return 0, err
}
v.IssuerID = vv
}
{
var vv bool
vv, offset, err = decoder.AsBool(offset)
if err != nil {
return 0, err
}
v.IsDelta = vv
}
{
var vv bool
vv, offset, err = decoder.AsBool(offset)
if err != nil {
return 0, err
}
v.UnChanged = vv
}
if !decoder.IsCodeNil(offset) {
var vv []byte
var vvl int
vvl, offset, err = decoder.SliceLength(offset)
if err != nil {
return 0, err
}
vv = make([]byte, vvl)
for vvi := range vv {
var vvv byte
vvv, offset, err = decoder.AsByte(offset)
if err != nil {
return 0, err
}
vv[vvi] = vvv
}
v.CRLData = vv
} else {
offset++
}
if !decoder.IsCodeNil(offset) {
var vv []byte
var vvl int
vvl, offset, err = decoder.SliceLength(offset)
if err != nil {
return 0, err
}
vv = make([]byte, vvl)
for vvi := range vv {
var vvv byte
vvv, offset, err = decoder.AsByte(offset)
if err != nil {
return 0, err
}
vv[vvi] = vvv
}
v.CRLNumber = vv
} else {
offset++
}
return offset, err
}
// decode to git.cacert.org/cacert-gosigner/pkg/messages.FetchCRLResponse
func ___decodeMapFetchCRLResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v *FetchCRLResponse, decoder *dec.Decoder, offset int) (int, error) {
keys := [][]byte{
{uint8(0x69), uint8(0x73), uint8(0x73), uint8(0x75), uint8(0x65), uint8(0x72), uint8(0x5f), uint8(0x69), uint8(0x64)}, // issuer_id
{uint8(0x69), uint8(0x73), uint8(0x5f), uint8(0x64), uint8(0x65), uint8(0x6c), uint8(0x74), uint8(0x61)}, // is_delta
{uint8(0x75), uint8(0x6e), uint8(0x63), uint8(0x68), uint8(0x61), uint8(0x6e), uint8(0x67), uint8(0x65), uint8(0x64)}, // unchanged
{uint8(0x63), uint8(0x72), uint8(0x6c), uint8(0x5f), uint8(0x64), uint8(0x61), uint8(0x74), uint8(0x61)}, // crl_data
{uint8(0x63), uint8(0x72), uint8(0x6c), uint8(0x5f), uint8(0x6e), uint8(0x75), uint8(0x6d), uint8(0x62), uint8(0x65), uint8(0x72)}, // crl_number
}
offset, err := decoder.CheckStructHeader(5, offset)
if err != nil {
return 0, err
}
count := 0
for count < 5 {
var dataKey []byte
dataKey, offset, err = decoder.AsStringBytes(offset)
if err != nil {
return 0, err
}
fieldIndex := -1
for i, key := range keys {
if len(dataKey) != len(key) {
continue
}
fieldIndex = i
for dataKeyIndex := range dataKey {
if dataKey[dataKeyIndex] != key[dataKeyIndex] {
fieldIndex = -1
break
}
}
if fieldIndex >= 0 {
break
}
}
switch fieldIndex {
case 0:
{
var vv string
vv, offset, err = decoder.AsString(offset)
if err != nil {
return 0, err
}
v.IssuerID = vv
}
count++
case 1:
{
var vv bool
vv, offset, err = decoder.AsBool(offset)
if err != nil {
return 0, err
}
v.IsDelta = vv
}
count++
case 2:
{
var vv bool
vv, offset, err = decoder.AsBool(offset)
if err != nil {
return 0, err
}
v.UnChanged = vv
}
count++
case 3:
if !decoder.IsCodeNil(offset) {
var vv []byte
var vvl int
vvl, offset, err = decoder.SliceLength(offset)
if err != nil {
return 0, err
}
vv = make([]byte, vvl)
for vvi := range vv {
var vvv byte
vvv, offset, err = decoder.AsByte(offset)
if err != nil {
return 0, err
}
vv[vvi] = vvv
}
v.CRLData = vv
} else {
offset++
}
count++
case 4:
if !decoder.IsCodeNil(offset) {
var vv []byte
var vvl int
vvl, offset, err = decoder.SliceLength(offset)
if err != nil {
return 0, err
}
vv = make([]byte, vvl)
for vvi := range vv {
var vvv byte
vvv, offset, err = decoder.AsByte(offset)
if err != nil {
return 0, err
}
vv[vvi] = vvv
}
v.CRLNumber = vv
} else {
offset++
}
count++
default:
return 0, fmt.Errorf("unknown key[%s] found", string(dataKey))
}
}
return offset, err
}
// calculate size from git.cacert.org/cacert-gosigner/pkg/messages.ErrorResponse
func ___calcArraySizeErrorResponse_e587a81c7cb163b35488bdef0f58c292f99f4bd65a81377f81e5b18c3d86855d(v ErrorResponse, encoder *enc.Encoder) (int, error) {
size := 0

Loading…
Cancel
Save