+ {
+ // A code constraint on the root, applying to one of two intermediates in the graph, should
+ // result in only one valid chain.
+ name: "code constrained root, two paths, one valid",
+ graph: trustGraphDescription{
+ Roots: []rootDescription{{Subject: "root", Constraint: func(chain []*Certificate) error {
+ for _, c := range chain {
+ if c.Subject.CommonName == "inter a" {
+ return errors.New("bad")
+ }
+ }
+ return nil
+ }}},
+ Leaf: "leaf",
+ Graph: []trustGraphEdge{
+ {
+ Issuer: "root",
+ Subject: "inter a",
+ Type: intermediateCertificate,
+ },
+ {
+ Issuer: "root",
+ Subject: "inter b",
+ Type: intermediateCertificate,
+ },
+ {
+ Issuer: "inter a",
+ Subject: "inter c",
+ Type: intermediateCertificate,
+ },
+ {
+ Issuer: "inter b",
+ Subject: "inter c",
+ Type: intermediateCertificate,
+ },
+ {
+ Issuer: "inter c",
+ Subject: "leaf",
+ Type: leafCertificate,
+ },
+ },
+ },
+ expectedChains: []string{"CN=leaf -> CN=inter c -> CN=inter b -> CN=root"},
+ },
+ {
+ // A code constraint on the root, applying to the only path, should result in an error.
+ name: "code constrained root, one invalid path",
+ graph: trustGraphDescription{
+ Roots: []rootDescription{{Subject: "root", Constraint: func(chain []*Certificate) error {
+ for _, c := range chain {
+ if c.Subject.CommonName == "leaf" {
+ return errors.New("bad")
+ }
+ }
+ return nil
+ }}},
+ Leaf: "leaf",
+ Graph: []trustGraphEdge{
+ {
+ Issuer: "root",
+ Subject: "inter",
+ Type: intermediateCertificate,
+ },
+ {
+ Issuer: "inter",
+ Subject: "leaf",
+ Type: leafCertificate,
+ },
+ },
+ },
+ expectedErr: "x509: certificate signed by unknown authority (possibly because of \"bad\" while trying to verify candidate authority certificate \"root\")",
+ },