aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Crute <mike@crute.us>2021-11-10 22:27:57 -0800
committerMike Crute <mike@crute.us>2021-11-10 22:27:57 -0800
commit4a1bc8a259a83ff83c6f9d82a387d96569b2d346 (patch)
tree9ef6ac43e8232c4faed4622896134c5628a825e9
parent8c5b1d33cc3d4af0b7c0e0fc37a90ef80ba25fe5 (diff)
downloadgolib-4a1bc8a259a83ff83c6f9d82a387d96569b2d346.tar.bz2
golib-4a1bc8a259a83ff83c6f9d82a387d96569b2d346.tar.xz
golib-4a1bc8a259a83ff83c6f9d82a387d96569b2d346.zip
Import crypto utilsv0.2.0
-rw-r--r--crypto/ecdsa/ecdsa.go11
-rw-r--r--crypto/x509/csr.go28
-rw-r--r--encoding/pem/read.go61
-rw-r--r--encoding/pem/write.go62
4 files changed, 162 insertions, 0 deletions
diff --git a/crypto/ecdsa/ecdsa.go b/crypto/ecdsa/ecdsa.go
new file mode 100644
index 0000000..3793663
--- /dev/null
+++ b/crypto/ecdsa/ecdsa.go
@@ -0,0 +1,11 @@
1package ecdsa
2
3import (
4 "crypto/ecdsa"
5 "crypto/elliptic"
6 "crypto/rand"
7)
8
9func GenerateECPrivateKey() (*ecdsa.PrivateKey, error) {
10 return ecdsa.GenerateKey(elliptic.P256(), rand.Reader)
11}
diff --git a/crypto/x509/csr.go b/crypto/x509/csr.go
new file mode 100644
index 0000000..76ea809
--- /dev/null
+++ b/crypto/x509/csr.go
@@ -0,0 +1,28 @@
1package x509
2
3import (
4 "crypto/rand"
5 "crypto/rsa"
6 "crypto/x509"
7 "crypto/x509/pkix"
8)
9
10const defaultRSAKeyStrength = 4096
11
12func GenerateRSAKeyCSR(domains ...string) ([]byte, *rsa.PrivateKey, error) {
13 ckey, err := rsa.GenerateKey(rand.Reader, defaultRSAKeyStrength)
14 if err != nil {
15 return nil, nil, err
16 }
17
18 csr, err := x509.CreateCertificateRequest(rand.Reader, &x509.CertificateRequest{
19 Subject: pkix.Name{CommonName: domains[0]},
20 DNSNames: domains,
21 ExtraExtensions: []pkix.Extension{},
22 }, ckey)
23 if err != nil {
24 return nil, nil, err
25 }
26
27 return csr, ckey, nil
28}
diff --git a/encoding/pem/read.go b/encoding/pem/read.go
new file mode 100644
index 0000000..dbf2f73
--- /dev/null
+++ b/encoding/pem/read.go
@@ -0,0 +1,61 @@
1package pem
2
3import (
4 "crypto/ecdsa"
5 "crypto/x509"
6 "encoding/pem"
7 "fmt"
8 "os"
9)
10
11func LoadECPrivateKey(filename string) (*ecdsa.PrivateKey, error) {
12 pb, err := os.ReadFile(filename)
13 if err != nil {
14 return nil, err
15 }
16
17 block, _ := pem.Decode(pb)
18 if block == nil {
19 return nil, fmt.Errorf("failed to decode pem bytes")
20 }
21
22 key, err := x509.ParseECPrivateKey(block.Bytes)
23 if err != nil {
24 return nil, err
25 }
26
27 return key, nil
28}
29
30func CertificateFromPemData(data []byte) (*x509.Certificate, error) {
31 block, _ := pem.Decode(data)
32 if block == nil {
33 return nil, fmt.Errorf("Unable to decode PEM")
34 }
35
36 crt, err := x509.ParseCertificate(block.Bytes)
37 if err != nil {
38 return nil, err
39 }
40
41 return crt, nil
42}
43
44func CertificateRequestFromPemDataRaw(data []byte) (*x509.CertificateRequest, []byte, error) {
45 block, _ := pem.Decode(data)
46 if block == nil {
47 return nil, nil, fmt.Errorf("Unable to decode PEM")
48 }
49
50 csr, err := x509.ParseCertificateRequest(block.Bytes)
51 if err != nil {
52 return nil, nil, err
53 }
54
55 return csr, block.Bytes, nil
56}
57
58func CertificateRequestFromPemData(data []byte) (*x509.CertificateRequest, error) {
59 csr, _, err := CertificateRequestFromPemDataRaw(data)
60 return csr, err
61}
diff --git a/encoding/pem/write.go b/encoding/pem/write.go
new file mode 100644
index 0000000..c239f8e
--- /dev/null
+++ b/encoding/pem/write.go
@@ -0,0 +1,62 @@
1package pem
2
3import (
4 "bytes"
5 "crypto/ecdsa"
6 "crypto/rsa"
7 "crypto/x509"
8 "encoding/pem"
9 "io"
10 "os"
11)
12
13func pemWrite(filename, header string, data [][]byte) error {
14 out, err := os.OpenFile(filename, os.O_RDWR|os.O_CREATE, 0600)
15 if err != nil {
16 return err
17 }
18 defer out.Close()
19
20 for _, d := range data {
21 err = pem.Encode(out, &pem.Block{
22 Type: header,
23 Bytes: d,
24 })
25 if err != nil {
26 return err
27 }
28 }
29
30 return nil
31}
32
33func WriteRSAPrivateKey(filename string, key *rsa.PrivateKey) error {
34 return pemWrite(filename, "RSA PRIVATE KEY", [][]byte{x509.MarshalPKCS1PrivateKey(key)})
35}
36
37func WriteCertificateChain(filename string, der [][]byte) error {
38 return pemWrite(filename, "CERTIFICATE", der)
39}
40
41func WriteECPrivateKey(filename string, key *ecdsa.PrivateKey) error {
42 m, err := x509.MarshalECPrivateKey(key)
43 if err != nil {
44 return err
45 }
46
47 return pemWrite(filename, "EC PRIVATE KEY", [][]byte{m})
48}
49
50func CSRToPEMReader(der []byte) (io.ReadCloser, error) {
51 out := &bytes.Buffer{}
52
53 err := pem.Encode(out, &pem.Block{
54 Type: "CERTIFICATE REQUEST",
55 Bytes: der,
56 })
57 if err != nil {
58 return nil, err
59 }
60
61 return io.NopCloser(out), nil
62}