Rebase.
[official-gcc.git] / libgo / go / crypto / tls / generate_cert.go
blob5c6d8396d5208ea7a998718b2f154d3e688291b0
1 // Copyright 2009 The Go Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style
3 // license that can be found in the LICENSE file.
5 // +build ignore
7 // Generate a self-signed X.509 certificate for a TLS server. Outputs to
8 // 'cert.pem' and 'key.pem' and will overwrite existing files.
10 package main
12 import (
13 "crypto/rand"
14 "crypto/rsa"
15 "crypto/x509"
16 "crypto/x509/pkix"
17 "encoding/pem"
18 "flag"
19 "fmt"
20 "log"
21 "math/big"
22 "net"
23 "os"
24 "strings"
25 "time"
28 var (
29 host = flag.String("host", "", "Comma-separated hostnames and IPs to generate a certificate for")
30 validFrom = flag.String("start-date", "", "Creation date formatted as Jan 1 15:04:05 2011")
31 validFor = flag.Duration("duration", 365*24*time.Hour, "Duration that certificate is valid for")
32 isCA = flag.Bool("ca", false, "whether this cert should be its own Certificate Authority")
33 rsaBits = flag.Int("rsa-bits", 2048, "Size of RSA key to generate")
36 func main() {
37 flag.Parse()
39 if len(*host) == 0 {
40 log.Fatalf("Missing required --host parameter")
43 priv, err := rsa.GenerateKey(rand.Reader, *rsaBits)
44 if err != nil {
45 log.Fatalf("failed to generate private key: %s", err)
48 var notBefore time.Time
49 if len(*validFrom) == 0 {
50 notBefore = time.Now()
51 } else {
52 notBefore, err = time.Parse("Jan 2 15:04:05 2006", *validFrom)
53 if err != nil {
54 fmt.Fprintf(os.Stderr, "Failed to parse creation date: %s\n", err)
55 os.Exit(1)
59 notAfter := notBefore.Add(*validFor)
61 serialNumberLimit := new(big.Int).Lsh(big.NewInt(1), 128)
62 serialNumber, err := rand.Int(rand.Reader, serialNumberLimit)
63 if err != nil {
64 log.Fatalf("failed to generate serial number: %s", err)
67 template := x509.Certificate{
68 SerialNumber: serialNumber,
69 Subject: pkix.Name{
70 Organization: []string{"Acme Co"},
72 NotBefore: notBefore,
73 NotAfter: notAfter,
75 KeyUsage: x509.KeyUsageKeyEncipherment | x509.KeyUsageDigitalSignature,
76 ExtKeyUsage: []x509.ExtKeyUsage{x509.ExtKeyUsageServerAuth},
77 BasicConstraintsValid: true,
80 hosts := strings.Split(*host, ",")
81 for _, h := range hosts {
82 if ip := net.ParseIP(h); ip != nil {
83 template.IPAddresses = append(template.IPAddresses, ip)
84 } else {
85 template.DNSNames = append(template.DNSNames, h)
89 if *isCA {
90 template.IsCA = true
91 template.KeyUsage |= x509.KeyUsageCertSign
94 derBytes, err := x509.CreateCertificate(rand.Reader, &template, &template, &priv.PublicKey, priv)
95 if err != nil {
96 log.Fatalf("Failed to create certificate: %s", err)
99 certOut, err := os.Create("cert.pem")
100 if err != nil {
101 log.Fatalf("failed to open cert.pem for writing: %s", err)
103 pem.Encode(certOut, &pem.Block{Type: "CERTIFICATE", Bytes: derBytes})
104 certOut.Close()
105 log.Print("written cert.pem\n")
107 keyOut, err := os.OpenFile("key.pem", os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0600)
108 if err != nil {
109 log.Print("failed to open key.pem for writing:", err)
110 return
112 pem.Encode(keyOut, &pem.Block{Type: "RSA PRIVATE KEY", Bytes: x509.MarshalPKCS1PrivateKey(priv)})
113 keyOut.Close()
114 log.Print("written key.pem\n")