github.com/git-amp/amp-sdk-go@v0.7.5/stdlib/utils/certs.go (about) 1 package utils 2 3 import ( 4 "crypto/ecdsa" 5 "crypto/elliptic" 6 "crypto/rand" 7 "crypto/rsa" 8 "crypto/tls" 9 "crypto/x509" 10 "crypto/x509/pkix" 11 "encoding/hex" 12 "encoding/pem" 13 "fmt" 14 "math/big" 15 "net" 16 "os" 17 "time" 18 ) 19 20 func MakeSelfSignedX509Certificate() (*tls.Certificate, error) { 21 priv, err := ecdsa.GenerateKey(elliptic.P256(), rand.Reader) 22 if err != nil { 23 return nil, err 24 } 25 26 template := x509.Certificate{ 27 SerialNumber: big.NewInt(1), 28 Subject: pkix.Name{ 29 CommonName: "redwood", 30 }, 31 NotBefore: time.Now(), 32 NotAfter: time.Now().Add(time.Hour * 24 * 180), 33 34 KeyUsage: x509.KeyUsageKeyEncipherment | x509.KeyUsageDigitalSignature | x509.KeyUsageCertSign, 35 ExtKeyUsage: []x509.ExtKeyUsage{x509.ExtKeyUsageServerAuth}, 36 BasicConstraintsValid: true, 37 IsCA: true, 38 39 IPAddresses: []net.IP{net.ParseIP("127.0.0.1"), net.ParseIP("10.0.0.2")}, 40 } 41 42 derBytes, err := x509.CreateCertificate(rand.Reader, &template, &template, publicKey(priv), priv) 43 if err != nil { 44 return nil, err 45 } 46 47 var outCert tls.Certificate 48 outCert.Certificate = append(outCert.Certificate, derBytes) 49 outCert.PrivateKey = priv 50 return &outCert, nil 51 } 52 53 func publicKey(priv interface{}) interface{} { 54 switch k := priv.(type) { 55 case *rsa.PrivateKey: 56 return &k.PublicKey 57 case *ecdsa.PrivateKey: 58 return &k.PublicKey 59 default: 60 return nil 61 } 62 } 63 64 func DeviceIDFromX509Pubkey(pubkey interface{}) string { 65 switch k := pubkey.(type) { 66 case *ecdsa.PublicKey: 67 bs := elliptic.MarshalCompressed(k.Curve, k.X, k.Y) 68 return hex.EncodeToString(bs) 69 case *rsa.PublicKey: 70 return "" 71 default: 72 return "" 73 } 74 } 75 76 func pemBlockForKey(priv interface{}) *pem.Block { 77 switch k := priv.(type) { 78 case *rsa.PrivateKey: 79 return &pem.Block{Type: "RSA PRIVATE KEY", Bytes: x509.MarshalPKCS1PrivateKey(k)} 80 case *ecdsa.PrivateKey: 81 b, err := x509.MarshalECPrivateKey(k) 82 if err != nil { 83 fmt.Fprintf(os.Stderr, "Unable to marshal ECDSA private key: %v", err) 84 os.Exit(2) 85 } 86 return &pem.Block{Type: "EC PRIVATE KEY", Bytes: b} 87 default: 88 return nil 89 } 90 }