Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 2 additions & 4 deletions .github/workflows/add-remove-new-fulcio.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -197,15 +197,14 @@ jobs:

- name: Dump the trusted certs
run: |
curl ${CTLOG_URL}/sigstorescaffolding/ct/v1/get-roots | jq .certificates
curl ${CTLOG_URL}/ct/v1/get-roots | jq .certificates
env:
CTLOG_URL: ${{ env.CTLOG_URL }}

- name: Verify both Fulcio certs are there
run: |
go run ./cmd/ctlog/verifyfulcio/main.go \
--ctlog-url ${CTLOG_URL} \
--log-prefix sigstorescaffolding \
--fulcio ${FULCIO_URL} \
--fulcio ${NEW_FULCIO_URL}
env:
Expand All @@ -226,15 +225,14 @@ jobs:

- name: Dump the trusted certs
run: |
curl ${CTLOG_URL}/sigstorescaffolding/ct/v1/get-roots | jq .certificates
curl ${CTLOG_URL}/ct/v1/get-roots | jq .certificates
env:
CTLOG_URL: ${{ env.CTLOG_URL }}

- name: Verify that only new Fulcio cert is there
run: |
go run ./cmd/ctlog/verifyfulcio/main.go \
--ctlog-url ${CTLOG_URL} \
--log-prefix sigstorescaffolding \
--fulcio ${NEW_FULCIO_URL}
env:
CTLOG_URL: ${{ env.CTLOG_URL }}
Expand Down
134 changes: 29 additions & 105 deletions cmd/ctlog/createctconfig/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,10 +24,8 @@ import (
"errors"
"flag"
"fmt"
"log"
"net/url"
"os"
"strconv"

fulcioclient "github.com/sigstore/fulcio/pkg/api"
"github.com/sigstore/scaffolding/pkg/ctlog"
Expand All @@ -44,26 +42,18 @@ import (
)

const (
// Key in the configmap holding the value of the tree.
treeKey = "treeID"
configKey = "config"
privateKey = "private"
publicKey = "public"
bitSize = 4096
)

var (
cmname = flag.String("configmap", "ctlog-config", "Name of the configmap where the treeID lives")
privateKeySecret = flag.String("private-secret", "", "If there's an existing private key that should be used, read it from this secret, decrypt with the key-password and use it instead of creating a new one.")
secretName = flag.String("secret", "ctlog-secrets", "Name of the secret to create for the keyfiles")
pubKeySecretName = flag.String("pubkeysecret", "ctlog-public-key", "Name of the secret to create containing only the public key")
ctlogPrefix = flag.String("log-prefix", "sigstorescaffolding", "Prefix to append to the url. This is basically the name of the log.")
fulcioURL = flag.String("fulcio-url", "http://fulcio.fulcio-system.svc", "Where to fetch the fulcio Root CA from")
trillianServerAddr = flag.String("trillian-server", "log-server.trillian-system.svc:80", "Address of the gRPC Trillian Admin Server (host:port)")
// TODO: Support ed25519
keyType = flag.String("keytype", "ecdsa", "Which private key to generate [rsa,ecdsa]")
curveType = flag.String("curvetype", "p256", "Curve type to use [p256, p384,p521]")
keyPassword = flag.String("key-password", "test", "Password for encrypting the PEM key")
privateKeySecret = flag.String("private-secret", "", "If there's an existing private key that should be used, read it from this secret.")
secretName = flag.String("secret", "ctlog-secrets", "Name of the secret to create for the keyfiles")
pubKeySecretName = flag.String("pubkeysecret", "ctlog-public-key", "Name of the secret to create containing only the public key")
fulcioURL = flag.String("fulcio-url", "http://fulcio.fulcio-system.svc", "Where to fetch the fulcio Root CA from")
keyType = flag.String("keytype", "ecdsa", "Which private key to generate [rsa,ecdsa]")
curveType = flag.String("curvetype", "p256", "Curve type to use [p256, p384,p521]")

// Supported elliptic curve functions.
supportedCurves = map[string]elliptic.Curve{
Expand Down Expand Up @@ -100,25 +90,6 @@ func main() {
if err != nil {
logging.FromContext(ctx).Panicf("Failed to get clientset: %v", err)
}
cm, err := clientset.CoreV1().ConfigMaps(ns).Get(ctx, *cmname, metav1.GetOptions{})
if err != nil {
logging.FromContext(ctx).Panicf("Failed to get the configmap %s/%s: %v", ns, *cmname, err)
}

if cm.Data == nil {
cm.Data = make(map[string]string)
}
treeID, ok := cm.Data[treeKey]
if !ok {
logging.FromContext(ctx).Errorf("No treeid yet, bailing")
os.Exit(-1)
}

logging.FromContext(ctx).Infof("Found treeid: %s", treeID)
treeIDInt, err := strconv.ParseInt(treeID, 10, 64)
if err != nil {
logging.FromContext(ctx).Panicf("Invalid TreeID %s : %v", treeID, err)
}

// Fetch the fulcio Root CA
u, err := url.Parse(*fulcioURL)
Expand All @@ -131,97 +102,50 @@ func main() {
logging.FromContext(ctx).Panicf("Failed to fetch fulcio Root cert: %w", err)
}

// See if there's an existing configuration already in the ConfigMap
var existingCMConfig []byte
if cm.BinaryData != nil && cm.BinaryData[configKey] != nil {
logging.FromContext(ctx).Infof("Found existing ctlog config in ConfigMap")
existingCMConfig = cm.BinaryData[configKey]
}

// See if there's existing secret with the keys we want
nsSecret := clientset.CoreV1().Secrets(ns)
existingSecret, err := nsSecret.Get(ctx, *secretName, metav1.GetOptions{})
if err != nil && !apierrs.IsNotFound(err) {
logging.FromContext(ctx).Fatalf("Failed to get secret %s/%s: %v", ns, *secretName, err)
}

// If any of the private, public or config either from secret or configmap
// is not there, create a new configuration.
if existingSecret.Data[privateKey] == nil ||
existingSecret.Data[publicKey] == nil ||
(existingSecret.Data[configKey] == nil && existingCMConfig == nil) {
var ctlogConfig *ctlog.Config
var err error
if *privateKeySecret != "" {
// We have an existing private key, use it instead of creating
// a new one.
ctlogConfig, err = createConfigFromExistingSecret(ctx, nsSecret, *privateKeySecret)
} else {
// Create a fresh private key.
ctlogConfig, err = createConfigWithKeys(ctx, *keyType)
}
if err != nil {
logging.FromContext(ctx).Fatalf("Failed to generate keys: %v", err)
}
ctlogConfig.PrivKeyPassword = *keyPassword
ctlogConfig.LogID = treeIDInt
ctlogConfig.LogPrefix = *ctlogPrefix
ctlogConfig.TrillianServerAddr = *trillianServerAddr
if err = ctlogConfig.AddFulcioRoot(ctx, root.ChainPEM); err != nil {
logging.FromContext(ctx).Infof("Failed to add fulcio root: %v", err)
}
configMap, err := ctlogConfig.MarshalConfig(ctx)
if err != nil {
logging.FromContext(ctx).Fatalf("Failed to marshal ctlog config: %v", err)
}

if err := secret.ReconcileSecret(ctx, *secretName, ns, configMap, nsSecret); err != nil {
logging.FromContext(ctx).Fatalf("Failed to reconcile secret: %v", err)
}

pubData := map[string][]byte{publicKey: configMap[publicKey]}
if err := secret.ReconcileSecret(ctx, *pubKeySecretName, ns, pubData, nsSecret); err != nil {
logging.FromContext(ctx).Panicf("Failed to reconcile public key secret %s/%s: %v", ns, *secretName, err)
}

logging.FromContext(ctx).Infof("Created CTLog configuration")
// If either the private or public key from secret is not there, create a new configuration.
if existingSecret.Data[privateKey] != nil &&
existingSecret.Data[publicKey] != nil {
logging.FromContext(ctx).Infof("Public and private key already exist")
os.Exit(0)
}

// Prefer the secret config if it exists, but if it doesn't use
// configmap for backwards compatibility / migration.
if existingSecret.Data[configKey] != nil {
logging.FromContext(ctx).Infof("Found existing config in the secret, using that %s/%s", ns, *secretName)
var ctlogConfig *ctlog.Config
if *privateKeySecret != "" {
// We have an existing private key, use it instead of creating
// a new one.
ctlogConfig, err = createConfigFromExistingSecret(ctx, nsSecret, *privateKeySecret)
} else {
existingSecret.Data[configKey] = existingCMConfig
// Create a fresh private key.
ctlogConfig, err = createConfigWithKeys(ctx, *keyType)
}

existingConfig, err := ctlog.Unmarshal(ctx, existingSecret.Data)
if err != nil {
log.Fatalf("Failed to unmarshal existing configuration: %v", err)
logging.FromContext(ctx).Fatalf("Failed to generate keys: %v", err)
}

// Finally add Fulcio to it, marshal and write out.
if err = existingConfig.AddFulcioRoot(ctx, root.ChainPEM); err != nil {
log.Printf("Failed to add fulcio root: %v", err)
if err = ctlogConfig.AddFulcioRoot(ctx, root.ChainPEM); err != nil {
logging.FromContext(ctx).Infof("Failed to add fulcio root: %v", err)
}
marshaled, err := existingConfig.MarshalConfig(ctx)
marshaled, err := ctlogConfig.MarshalConfig()
if err != nil {
log.Fatalf("Failed to marshal new configuration: %v", err)
logging.FromContext(ctx).Fatalf("Failed to marshal ctlog config: %v", err)
}
// Take out the public / private key from the secret since we didn't mess
// with those. ReconcileSecret will not touch fields that are not here, so
// just remove them from the map.
delete(marshaled, privateKey)
delete(marshaled, publicKey)

if err := secret.ReconcileSecret(ctx, *secretName, ns, marshaled, nsSecret); err != nil {
logging.FromContext(ctx).Panicf("Failed to reconcile secret %s/%s: %v", ns, *secretName, err)
logging.FromContext(ctx).Fatalf("Failed to reconcile secret: %v", err)
}

pubData := map[string][]byte{publicKey: existingSecret.Data[publicKey]}
pubData := map[string][]byte{publicKey: marshaled[publicKey]}
if err := secret.ReconcileSecret(ctx, *pubKeySecretName, ns, pubData, nsSecret); err != nil {
logging.FromContext(ctx).Panicf("Failed to reconcile secret %s/%s: %v", ns, *secretName, err)
logging.FromContext(ctx).Panicf("Failed to reconcile public key secret %s/%s: %v", ns, *secretName, err)
}

logging.FromContext(ctx).Infof("Created CTLog configuration")
}

// createConfigWithKeys creates otherwise empty CTLogCOnfig but fills
Expand Down Expand Up @@ -263,7 +187,7 @@ func createConfigFromExistingSecret(ctx context.Context, nsSecret v1.SecretInter
if len(private) == 0 {
return nil, errors.New("secret missing private key entry")
}
priv, pub, err := ctlog.DecryptExistingPrivateKey(private, *keyPassword)
priv, pub, err := ctlog.ParseExistingPrivateKey(private)
if err != nil {
return nil, fmt.Errorf("decrypting existing private key secret: %w", err)
}
Expand Down
47 changes: 5 additions & 42 deletions cmd/ctlog/managectroots/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,11 +18,9 @@ import (
"flag"
"net/url"
"os"
"strings"

fulcioclient "github.com/sigstore/fulcio/pkg/api"
"github.com/sigstore/scaffolding/pkg/ctlog"
corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/client-go/kubernetes"
"k8s.io/client-go/rest"
Expand All @@ -31,19 +29,10 @@ import (
"sigs.k8s.io/release-utils/version"
)

const (
// Key in the configmap holding the value of the tree.
treeKey = "treeID"
configKey = "config"
bitSize = 4096
)

var (
cmname = flag.String("configmap", "ctlog-config", "Name of the configmap where the treeID lives. if configInSecret is false, ctlog config gets added here also.")
configInSecret = flag.Bool("config-in-secret", false, "If set to true, fetch / update the ctlog configuration proto into a secret specified in ctlog-secrets under key 'config'.")
secretName = flag.String("secret", "ctlog-secrets", "Name of the secret to fetch private key for CTLog.")
fulcioURL = flag.String("fulcio-url", "http://fulcio.fulcio-system.svc", "Where to fetch the fulcio Root CA from.")
operation = flag.String("operation", "", "Operation to perform for the specified fulcio [add,remove]")
secretName = flag.String("secret", "ctlog-secrets", "Name of the secret to fetch private key for CTLog.")
fulcioURL = flag.String("fulcio-url", "http://fulcio.fulcio-system.svc", "Where to fetch the fulcio Root CA from.")
operation = flag.String("operation", "", "Operation to perform for the specified fulcio [add,remove]")
)

type ctRootOp string
Expand Down Expand Up @@ -107,27 +96,7 @@ func main() {
current["private"] = secrets.Data["private"]
current["public"] = secrets.Data["public"]
current["rootca"] = secrets.Data["rootca"]
for k, v := range secrets.Data {
if strings.HasPrefix(k, "fulcio-") {
current[k] = v
}
}
// If the config is stored in the secret, we don't need to deal with the
// configmap.
var cm *corev1.ConfigMap
if !*configInSecret {
var err error
cm, err = clientset.CoreV1().ConfigMaps(ns).Get(ctx, *cmname, metav1.GetOptions{})
if err != nil {
logging.FromContext(ctx).Panicf("Failed to get the configmap %s/%s: %v", ns, *cmname, err)
}
if cm.BinaryData == nil || cm.BinaryData[configKey] == nil {
logging.FromContext(ctx).Fatalf("Configmap does not hold existing configmap %s/%s: %v", ns, *cmname, err)
}
current[configKey] = cm.BinaryData[configKey]
} else {
current[configKey] = secrets.Data[configKey]
}
current["fulcio"] = secrets.Data["fulcio"]

conf, err := ctlog.Unmarshal(ctx, current)
if err != nil {
Expand All @@ -144,16 +113,10 @@ func main() {
}

// Marshal it and update configuration
newConfig, err := conf.MarshalConfig(ctx)
newConfig, err := conf.MarshalConfig()
if err != nil {
logging.FromContext(ctx).Fatalf("Failed to marshal config: %v", err)
}
if !*configInSecret {
cm.BinaryData[configKey] = newConfig[configKey]
if _, err = clientset.CoreV1().ConfigMaps(ns).Update(ctx, cm, metav1.UpdateOptions{}); err != nil {
logging.FromContext(ctx).Fatalf("Failed to update configmap %s/%s: %v", ns, *cmname, err)
}
}

// Update the secret with the information
secrets.Data = newConfig
Expand Down
3 changes: 1 addition & 2 deletions cmd/ctlog/verifyfulcio/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,6 @@ type CertResponse struct {
func main() {
flag.Var(&fulcioList, "fulcio", "List of fulcios which must be in the list")
var ctlogURL = flag.String("ctlog-url", "ctlog.ctlog-system.svc", "CTLog to check Fulcios against.")
var ctlogPrefix = flag.String("log-prefix", "sigstorescaffolding", "Prefix to append to the gtlogURL url. This is basically the name of the log.")
flag.Parse()
var strictMatch = flag.Bool("strict", true, "If set to true ctlog must only contain the Fulcios in the list, no more, no less")
ctx := signals.NewContext()
Expand All @@ -66,7 +65,7 @@ func main() {
fmt.Printf("GOT: %s\n", fulcioList.String())

// First grab the certs that CTLog has.
ctlog := fmt.Sprintf("%s/%s/ct/v1/get-roots", *ctlogURL, *ctlogPrefix)
ctlog := fmt.Sprintf("%s/ct/v1/get-roots", *ctlogURL)
/* #nosec G107 */
ctlogResponse, err := http.Get(ctlog)
if err != nil {
Expand Down
1 change: 0 additions & 1 deletion config/ctlog/certs/300-createconfig.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,6 @@ spec:
- name: createctconfig
image: ko://github.com/sigstore/scaffolding/cmd/ctlog/createctconfig
args: [
"--configmap=ctlog-config",
"--secret=ctlog-secret"
]
env:
Expand Down
5 changes: 0 additions & 5 deletions config/ctlog/createtree/100-namespace.yaml

This file was deleted.

25 changes: 0 additions & 25 deletions config/ctlog/createtree/101-binding.yaml

This file was deleted.

13 changes: 0 additions & 13 deletions config/ctlog/createtree/101-configmap.yaml

This file was deleted.

6 changes: 0 additions & 6 deletions config/ctlog/createtree/101-service-account.yaml

This file was deleted.

Loading
Loading