Merge branch 'spec-update' into policy
Conflicts: ca/certificate-authority_test.go
This commit is contained in:
commit
df7614ff9b
|
|
@ -7,14 +7,19 @@ package ca
|
|||
|
||||
import (
|
||||
"crypto/x509"
|
||||
"encoding/asn1"
|
||||
"encoding/hex"
|
||||
"encoding/pem"
|
||||
"net/http"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
apisign "github.com/cloudflare/cfssl/api/sign"
|
||||
"github.com/cloudflare/cfssl/auth"
|
||||
"github.com/cloudflare/cfssl/config"
|
||||
"github.com/cloudflare/cfssl/signer/local"
|
||||
_ "github.com/mattn/go-sqlite3"
|
||||
|
||||
"github.com/letsencrypt/boulder/policy"
|
||||
"github.com/letsencrypt/boulder/sa"
|
||||
"github.com/letsencrypt/boulder/test"
|
||||
)
|
||||
|
|
@ -105,38 +110,113 @@ var CA_CERT_PEM = "-----BEGIN CERTIFICATE-----\n" +
|
|||
"8jcQV9i1MJFGXV7k3En0lQv2z5AD9aFtkc6UjHpAzB8xEWMO0ZAtBg==\n" +
|
||||
"-----END CERTIFICATE-----"
|
||||
|
||||
// CSR generated by Go:
|
||||
// * Random public key
|
||||
// * CN = example.com
|
||||
// * DNSNames = example.com, www.example.com
|
||||
var CN_AND_SAN_CSR_HEX = "308202a130820189020100301a311830160603550403130f6e6f742d6578" +
|
||||
"616d706c652e636f6d30820122300d06092a864886f70d01010105000382" +
|
||||
"010f003082010a0282010100e56ccbe37003c150202e6f543f9eb1d0e590" +
|
||||
"76ac7f1f62654fa82fe131a23c66bd53a2f62ff7852015c84a394e36836d" +
|
||||
"2018eba278e0740c85c4c6102787400c2ef069b4a72e6eb8ad8d1da5d76b" +
|
||||
"f3e70dafc126578ed28cf40030e7fe5b5307ef630254726c639561b5445d" +
|
||||
"372847bdb02576aa3622a688158c6af09d3938dbeba4d670cec4325be73a" +
|
||||
"fa52a0a04dcba2f335f1e85020704db94ca125dce70b3209294c6c46ed4b" +
|
||||
"48b95d8d51ae2d2fd227116023a48ca7381e35fd302ad2999df625a4b5ee" +
|
||||
"82a0d0fefa88ac6a62b01674de75637ef83328202cda9930947d932000b0" +
|
||||
"e53b82e099ab60fec9c8b6d4eccdee508b6ebca7e6ca3f752046c8350203" +
|
||||
"010001a042304006092a864886f70d01090e31333031302f0603551d1104" +
|
||||
"283026820f6e6f742d6578616d706c652e636f6d82137777772e6e6f742d" +
|
||||
"6578616d706c652e636f6d300d06092a864886f70d01010b050003820101" +
|
||||
"008c4bf2ab4dfd28d768697eecc5be889a6275287c7dd24f9232ffad5675" +
|
||||
"de708c9cc911545d0e84f61b6584c5e237915bbf231d6518e7e228be2e65" +
|
||||
"b4d50bd9729ce9e6aee00482e014de4edd4b9a4f9a7777b8943ef3512dbf" +
|
||||
"940ac561c25b34ded9db1074136b978a65943ab1259608fb8109e008eac6" +
|
||||
"23d7b29b2f1fad3a8e358aa070ead688016d9efed6da43412b136903de07" +
|
||||
"137462d3f9203a344d84d7eb336999004e7e9972d5176001e2792f206e6c" +
|
||||
"7c70b86d312459f21751d29ea53b41f9d02a229f9d7615b2a7ac83e849d0" +
|
||||
"d0d9f8a08f8d7ba23295e77c95bc060c9227bfec0afb8c898e33c89903d7" +
|
||||
"bbde4cf059dcc3e6c4ae4eef207c499d62"
|
||||
|
||||
// CSR generated by Go:
|
||||
// * Random public key
|
||||
// * CN = not-example.com
|
||||
// * DNSNames = [none]
|
||||
var NO_SAN_CSR_HEX = "3082025f30820147020100301a311830160603550403130f6e6f742d6578" +
|
||||
"616d706c652e636f6d30820122300d06092a864886f70d01010105000382" +
|
||||
"010f003082010a0282010100aa6e56ff24906f93b855e7871dc8411a3cf7" +
|
||||
"678d9563627e8ca37ab17dfe814ef7f828d6aa92b717f0da9df56990b953" +
|
||||
"989d5afc3f2dddacd2b504b89782b49e55a04a64a4370d8ab1b2688f2596" +
|
||||
"98132e5ce536f812ef5eb13824a922bbb89e30d6f2cace77462b9e65264a" +
|
||||
"32320a7b348f9903b16640bc8c1c5f1208c6b456fd85bfa96ee9b7642c68" +
|
||||
"3ab05b142d249525a730b230b39f2ba8d6f253263b5c3948b1a3d8a3467f" +
|
||||
"7cfcdd1fdd6bff7828fda12784fd277be8c680fcdf2cc4676acff5df759f" +
|
||||
"f4bc712ee1a560157233cbf6bb4bcb91dd1c5d2824b42f4913e4715c1ba4" +
|
||||
"001fde0d90c274bfa81a79e4a0d00a7ddcbfdd8de4183b497487a20d0203" +
|
||||
"010001a000300d06092a864886f70d01010b050003820101000ead204cfd" +
|
||||
"45d307dd49de6937d7e2d8abf17490a49a8cee5250ef7799ef53229f8cfc" +
|
||||
"735b9f65d789f898945f3d5536a09932e241050bd5473c47a4ac2493707f" +
|
||||
"1142bf9a06d047384ad463463acb3744d435b4cff8c8b0f9673e8700e13b" +
|
||||
"6bc99a486823fa85f7707e1bb8430e62541715ab6cb3fae3efb8356042a5" +
|
||||
"c9f493dd08eff690570cce65cffc4fe354aa40957dc16a37a833aa968f62" +
|
||||
"693d5059d53f6a96a159195d3fb7b558d462de63d945d4e3680d2b1f2c98" +
|
||||
"33c3bfd92a9235de3d345a431ee5a675e0e18308bd2729413acd84432da4" +
|
||||
"2410e1b87ae70227dd9a98e49ee6aeea9eaff67f968691918201e94697f2" +
|
||||
"da010d6f939cea40c26038"
|
||||
|
||||
// CSR generated by Go:
|
||||
// * Random public key
|
||||
// * C = US
|
||||
// * CN = [none]
|
||||
// * DNSNames = not-example.com
|
||||
var CSR_HEX = "3082028c30820174020100301a311830160603550403130f" +
|
||||
"6e6f742d6578616d706c652e636f6d30820122300d06092a" +
|
||||
"864886f70d01010105000382010f003082010a0282010100" +
|
||||
"aac67dd1e11fae980048b0ac91be005f21d9df8bb38461cc" +
|
||||
"a7dfad601a00e91ae488c240a03ec53a5752a33d837d2d9c" +
|
||||
"357c6a99ea7e55fe75482524480bb367aa85f75541bd0284" +
|
||||
"ede1ab9b54925a5c9f88d08f9dc857ee707a59d3503b31ea" +
|
||||
"64e42099acd70d2204c872ef49983e44cc2bc24389159fc5" +
|
||||
"f6ca41b80540fb7a2fbf8aa43af7f539782f20f185d416cc" +
|
||||
"66a88e5f8913a292b4a217e5b12e8244a9686af3b49ac88b" +
|
||||
"215c6eb097c4befa3e66257a1358791e2bc471c18ba2ca6e" +
|
||||
"161d2dcb53ebcb06e6b4b2e6cd42ff970581bc4971009cbd" +
|
||||
"7ccc3f89648db720e2908a1be613a9c3afb46b477261c1bc" +
|
||||
"c057bc749a102e6bd9dc45d87b2d97c50203010001a02d30" +
|
||||
"2b06092a864886f70d01090e311e301c301a0603551d1104" +
|
||||
"133011820f6e6f742d6578616d706c652e636f6d300d0609" +
|
||||
"2a864886f70d01010b05000382010100a37025c2cb88b4fa" +
|
||||
"f3c8417820a78a069b92cef45a3d2f3fbd18f41a07128258" +
|
||||
"38bc55e6c1c416e5f34c365924391294741c23657ffa77e4" +
|
||||
"aa3d589b560cbb9156aae175637cbb5061d69eefa7f432ca" +
|
||||
"c9e4d03feaa367954cf6986a72ca76307c01852db72b43ae" +
|
||||
"5ab7f673b81b58e06d8af1f681cd7c88d2fbc8c80d592a3f" +
|
||||
"7c3ea20035b73c8e6afc8daea4d168fe469f7da9e4bac660" +
|
||||
"fc207d1d93dce118dc7381e69fa4af37bb4d4d6d5342fa55" +
|
||||
"7798a363aa04cf350ad1748e96eabee04fa379dd98524ea1" +
|
||||
"53f07e1654e6077f4aaaf5c5b27edaf0385b48e0fc281424" +
|
||||
"6363a01370c89e666169276eb133731cff2379d46d2fff9d" +
|
||||
"f277b6d23fa24f9b"
|
||||
var NO_CN_CSR_HEX = "3082027f30820167020100300d310b300906035504061302555330820122" +
|
||||
"300d06092a864886f70d01010105000382010f003082010a0282010100d8" +
|
||||
"b3c11610ce17614f6d78de3f079db430e479c38978da8cd625b7c70dd445" +
|
||||
"57fd99b9831693e6b9b09fb7c74a82058a1f1a4e1e087f04f93aa73bc35a" +
|
||||
"688440205a6f5fd56ff478c5554b14c3b2a1a0b5eed1aef7189ad848e117" +
|
||||
"04b1eb6c29b47ada40a5719a38ce2f2869896bf5405c2bafd4c7dfb99c0e" +
|
||||
"9f26f80145e16b73bbacf67aedcd3b7ce57bb5b67cf692aec7956d23c236" +
|
||||
"2336c2408b65469630dccca3ca006f28e36ca8c95dda84b6586f29c8de63" +
|
||||
"661c09b58253e386a74707394cbba4de165f2745a65b717b9fd4b8b84c09" +
|
||||
"85583b5c17d3e88bbf71c88eeeccb5d552d61cde7835ec83d6ec9b41114a" +
|
||||
"0583f8eeae8a536cb3ca5786c22ab30203010001a02d302b06092a864886" +
|
||||
"f70d01090e311e301c301a0603551d1104133011820f6e6f742d6578616d" +
|
||||
"706c652e636f6d300d06092a864886f70d01010b05000382010100430239" +
|
||||
"8db6b64b94d93399db32335232967ca6a748048483db8cb2b387871f758c" +
|
||||
"6f7bf1593624b142127847cd2a511897bbadd8ad038468fb309fa2161031" +
|
||||
"949b9ba24931b0d363ad2f8dae56a4c908ba748d41c664aa129dcb1a6f88" +
|
||||
"0b90502cd244d9abd8dd5e78f763730660655a350f1c25af95cf1f89dda9" +
|
||||
"076f4e6b84b6da9a98ed87f538624e4338fa0ff1a404e763dd6800694a21" +
|
||||
"d28595927606308aefa1ac7e8f5600b05e33c0a7b25d3a9f5032c7c25264" +
|
||||
"026c039733b179315254af4f25e90a1d00facd69313b36fdc66a5818fb49" +
|
||||
"a0d90e0745d66a82d337289c9968b3ec4a4826c530c758cacecc18e06366" +
|
||||
"dd8962c451c3ce22c2aed33726"
|
||||
|
||||
// CSR generated by Go:
|
||||
// * Random public key
|
||||
// * C = US
|
||||
// * CN = [none]
|
||||
// * DNSNames = [none]
|
||||
var NO_NAME_CSR_HEX = "308202523082013a020100300d310b300906035504061302555330820122" +
|
||||
"300d06092a864886f70d01010105000382010f003082010a0282010100bc" +
|
||||
"fae49f68f02c42500b2faf251628ee19e8ef048a35fef311c9c419c80606" +
|
||||
"ab37340ad6e25cf4cc63c0283994b4ba705d86950ad5298094e0b9684647" +
|
||||
"8d67abc695741317b4ff8da9fd33120342559cfdaf9109ac403f0d0bf9ff" +
|
||||
"54dd79fa2256b218a9bdb17c608167c7fcad4cf839733c7eab9589fe6137" +
|
||||
"e99bb24c24b7eb74e19f51ffee4ea62c4ab756f099ff5197c5032f60edff" +
|
||||
"36022b8a99d35aeb706854fa9a31ea8a362a2251f08b93023b32e1df771a" +
|
||||
"970f08a30ced656950b8ef71600d65d6995a0b92903b179c05a76f702a08" +
|
||||
"0b41402c308d8ab57f14b5516b89fe317e38e13d7adad7f7025743610881" +
|
||||
"9fb60268f0773b08b62ac8c8c84f2d0203010001a000300d06092a864886" +
|
||||
"f70d01010b050003820101001eda9ce8253e8b933348851acd38ab63cd64" +
|
||||
"f833d7ffc711f1b6e6a37a7deb7ad44b5589d90533ed61dfd48cab2775e2" +
|
||||
"a19c41f5cb69faa9dde856606822a3bf798381836214154c17bc037f23ad" +
|
||||
"67c84d876855c0aea871dc55bd14b2cd267e49b734bc7a38c29c334611bf" +
|
||||
"ec7efdc56a1512e25fd12ca99a5809b1b6a808caf6a8baefff7fb2bda454" +
|
||||
"5c226849674900ce7a1f90287ab31be80a4e2b6d64765b9d973628e60299" +
|
||||
"6423edd74e7a58005bd520d4173f0c30d935de530477480d7725d9758f9a" +
|
||||
"58c004d9e1e55af59ea517dfbd2bccca58216d8130b9f77c90328b2aa54b" +
|
||||
"1778a629b584f2bc059489a236131de9b444adca90218c31a499a485"
|
||||
|
||||
func TestIssueCertificate(t *testing.T) {
|
||||
// Decode pre-generated values
|
||||
|
|
@ -146,29 +226,70 @@ func TestIssueCertificate(t *testing.T) {
|
|||
caCertPEM, _ := pem.Decode([]byte(CA_CERT_PEM))
|
||||
caCert, _ := x509.ParseCertificate(caCertPEM.Bytes)
|
||||
|
||||
csrDER, _ := hex.DecodeString(CSR_HEX)
|
||||
csr, _ := x509.ParseCertificateRequest(csrDER)
|
||||
// Uncomment to create a CFSSL local signer
|
||||
|
||||
// Create a CFSSL local signer
|
||||
signer, _ := local.NewSigner(caKey, caCert, x509.SHA256WithRSA, nil)
|
||||
// CFSSL config
|
||||
hostPort := "localhost:9000"
|
||||
authKey := "79999d86250c367a2b517a1ae7d409c1"
|
||||
profileName := "ee"
|
||||
|
||||
// Create an SA
|
||||
sa, err := sa.NewSQLStorageAuthority("sqlite3", ":memory:")
|
||||
test.AssertNotError(t, err, "Failed to create SA")
|
||||
sa.InitTables()
|
||||
|
||||
// Create an online CFSSL instance
|
||||
// This is designed to mimic what LE plans to do
|
||||
authHandler, err := auth.New(authKey, nil)
|
||||
test.AssertNotError(t, err, "Failed to create authentication handler")
|
||||
policy := &config.Signing{
|
||||
Profiles: map[string]*config.SigningProfile{
|
||||
profileName: &config.SigningProfile{
|
||||
Usage: []string{"server auth"},
|
||||
CA: false,
|
||||
IssuerURL: []string{"http://not-example.com/issuer-url"},
|
||||
OCSP: "http://not-example.com/ocsp",
|
||||
CRL: "http://not-example.com/crl",
|
||||
|
||||
Policies: []asn1.ObjectIdentifier{
|
||||
asn1.ObjectIdentifier{2, 23, 140, 1, 2, 1},
|
||||
},
|
||||
Expiry: 8760 * time.Hour,
|
||||
Backdate: time.Hour,
|
||||
Provider: authHandler,
|
||||
},
|
||||
},
|
||||
Default: &config.SigningProfile{
|
||||
Expiry: time.Hour,
|
||||
},
|
||||
}
|
||||
signer, err := local.NewSigner(caKey, caCert, x509.SHA256WithRSA, policy)
|
||||
test.AssertNotError(t, err, "Failed to create signer")
|
||||
signHandler, err := apisign.NewAuthHandlerFromSigner(signer)
|
||||
test.AssertNotError(t, err, "Failed to create signing API endpoint")
|
||||
http.Handle("/api/v1/cfssl/authsign", signHandler)
|
||||
// This goroutine should get killed when main() return
|
||||
go (func() { http.ListenAndServe(hostPort, nil) })()
|
||||
|
||||
// Create a CA
|
||||
/*
|
||||
// Uncomment to test with a remote signer
|
||||
ca, err := NewCertificateAuthorityImpl("localhost:9000", "79999d86250c367a2b517a1ae7d409c1", "ee")
|
||||
ca, err := NewCertificateAuthorityImpl(hostPort, authKey, profileName)
|
||||
test.AssertNotError(t, err, "Failed to create CA")
|
||||
ca.SA = sa
|
||||
*/
|
||||
|
||||
/*
|
||||
// Uncomment to test with a local signer
|
||||
signer, _ := local.NewSigner(caKey, caCert, x509.SHA256WithRSA, nil)
|
||||
ca := CertificateAuthorityImpl{
|
||||
Signer: signer,
|
||||
SA: sa,
|
||||
PA: policy.NewPolicyAuthorityImpl(),
|
||||
}
|
||||
*/
|
||||
|
||||
csrs := []string{CN_AND_SAN_CSR_HEX, NO_SAN_CSR_HEX, NO_CN_CSR_HEX}
|
||||
for _, csrHEX := range csrs {
|
||||
csrDER, _ := hex.DecodeString(csrHEX)
|
||||
csr, _ := x509.ParseCertificateRequest(csrDER)
|
||||
|
||||
// Sign CSR
|
||||
certObj, err := ca.IssueCertificate(*csr)
|
||||
|
|
@ -180,11 +301,25 @@ func TestIssueCertificate(t *testing.T) {
|
|||
|
||||
test.AssertEquals(t, cert.Subject.CommonName, "not-example.com")
|
||||
|
||||
if len(cert.DNSNames) != 1 || cert.DNSNames[0] != "not-example.com" {
|
||||
if len(cert.DNSNames) == 0 || cert.DNSNames[0] != "not-example.com" {
|
||||
// NB: This does not check for www.not-example.com in the 'both' case
|
||||
t.Errorf("Improper list of domain names %v", cert.DNSNames)
|
||||
}
|
||||
|
||||
if len(cert.Subject.Country) > 0 {
|
||||
t.Errorf("Subject contained unauthorized values")
|
||||
}
|
||||
|
||||
// Verify that the cert got stored in the DB
|
||||
_, err = sa.GetCertificate(certObj.ID)
|
||||
test.AssertNotError(t, err, "Certificate not found in database")
|
||||
}
|
||||
|
||||
// Test that the CA rejects CSRs with no names
|
||||
csrDER, _ := hex.DecodeString(NO_NAME_CSR_HEX)
|
||||
csr, _ := x509.ParseCertificateRequest(csrDER)
|
||||
_, err = ca.IssueCertificate(*csr)
|
||||
if err == nil {
|
||||
t.Errorf("CA improperly agreed to create a certificate with no name")
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,3 +1,8 @@
|
|||
// Copyright 2014 ISRG. All rights reserved
|
||||
// This Source Code Form is subject to the terms of the Mozilla Public
|
||||
// License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
|
||||
module.exports = {
|
||||
|
||||
fromStandardB64: function(x) {
|
||||
|
|
|
|||
|
|
@ -1,3 +1,8 @@
|
|||
// Copyright 2014 ISRG. All rights reserved
|
||||
// This Source Code Form is subject to the terms of the Mozilla Public
|
||||
// License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
|
||||
var crypto = require("crypto");
|
||||
var forge = require("node-forge");
|
||||
var util = require("./acme-util.js");
|
||||
|
|
|
|||
Loading…
Reference in New Issue