@@ -2,20 +2,28 @@ package main
2
2
3
3
import (
4
4
"bytes"
5
+ "crypto/dsa"
6
+ "crypto/ecdsa"
7
+ "crypto/rsa"
8
+ "crypto/sha256"
5
9
"crypto/x509"
6
10
"database/sql"
11
+ "database/sql/driver"
7
12
"encoding/json"
8
13
"errors"
9
14
"fmt"
15
+ _ "github.com/lib/pq"
10
16
"io/ioutil"
11
17
"log"
18
+ "math/big"
12
19
"strings"
13
20
"time"
14
21
15
22
"github.com/gomodule/redigo/redis"
16
- _ "github.com/lib/pq"
17
23
)
18
24
25
+ type BigNumber big.Int
26
+
19
27
type certMapElm struct {
20
28
CertHash string
21
29
chain chain
@@ -42,6 +50,7 @@ type chain struct {
42
50
}
43
51
44
52
var db * sql.DB
53
+ //var db *sqlx.DB
45
54
var cr redis.Conn
46
55
47
56
var connectRedis = false
@@ -92,17 +101,53 @@ func main() {
92
101
if err != nil {
93
102
log .Fatal (fmt .Sprintf ("Insert Certificate into DB failed: %q" , err ))
94
103
}
95
- // Launch go routine to create the relationship between certificates and sessions
96
- err = linkSessionCert (ids , idc )
104
+ // Create the relationship between certificates and sessions
105
+ err = linkSessionCerts (ids , idc )
106
+ if err != nil {
107
+ log .Fatal (fmt .Sprintf ("Could not link Certs and Session into DB: %q" , err ))
108
+ }
109
+ }
110
+ }
111
+
112
+ // insertPublicKeys insert each public key of each certificate of a session
113
+ func insertPublicKey (c x509.Certificate ) (string , error ) {
114
+ pub , err := x509 .ParsePKIXPublicKey (c .RawSubjectPublicKeyInfo )
115
+ hash := fmt .Sprintf ("%x" , sha256 .Sum256 (c .RawSubjectPublicKeyInfo ))
116
+ if err != nil {
117
+ return hash , nil
118
+ }
119
+
120
+ switch pub := pub .(type ) {
121
+ case * rsa.PublicKey :
122
+ q := `INSERT INTO "public_key" (hash, type, modulus, exponent, modulus_size) VALUES ($1, $2, $3, $4, $5)`
123
+ _ , err := db .Query (q , hash , "RSA" , (* BigNumber )(pub .N ), pub .E , pub .Size ())
124
+ if err != nil {
125
+ return hash , nil
126
+ }
127
+ case * dsa.PublicKey :
128
+ q := `INSERT INTO "public_key" (hash, type, "G", "P", "Q", "Y") VALUES ($1, $2, $3, $4, $5, $6)`
129
+ _ , err := db .Query (q , hash , "DSA" , (* BigNumber )(pub .Parameters .G ), (* BigNumber )(pub .Parameters .P ), (* BigNumber )(pub .Parameters .Q ), (* BigNumber )(pub .Y ))
130
+ if err != nil {
131
+ return hash , nil
132
+ }
133
+ case * ecdsa.PublicKey :
134
+ q := `INSERT INTO "public_key" (hash, type, "Y", "X", "P", "N", "B", "bitsize", "Gx", "Gy") VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10)`
135
+ _ , err := db .Query (q , hash , "ECDSA" , pub .Y , pub .X , pub .Curve .Params ().P , pub .Curve .Params ().N , pub .Curve .Params ().B , pub .Curve .Params ().BitSize , pub .Curve .Params ().Gx , pub .Curve .Params ().Gy )
97
136
if err != nil {
98
- log . Fatal ( fmt . Sprintf ( "Could not link Certs and Session into DB failed: %q" , err ))
137
+ return hash , nil
99
138
}
100
- // Launch go routine to create public keys
139
+ default :
140
+ return hash , fmt .Errorf ("PKIx: could not determine the type of key %g" , pub )
101
141
}
142
+ return hash , nil
143
+ }
144
+
145
+ func (bn * BigNumber ) Value () (driver.Value , error ) {
146
+ return driver .Value ((* big .Int )(bn ).Text (10 )), nil
102
147
}
103
148
104
- // linkSessionCert creates the link between a session and its certificates
105
- func linkSessionCert (ids int64 , idc []string ) error {
149
+ // linkSessionCerts creates the link between a session and its certificates
150
+ func linkSessionCerts (ids int64 , idc []string ) error {
106
151
for _ , i := range idc {
107
152
q := `INSERT INTO "many_sessionRecord_has_many_certificate" ("id_sessionRecord", "hash_certificate") VALUES ($1, $2)`
108
153
_ , err := db .Query (q , ids , i )
@@ -117,7 +162,7 @@ func linkSessionCert(ids int64, idc []string) error {
117
162
// contains a slice of certificate). If the chain of trust is build successfully
118
163
// it marked as valid, If not root is found or if the chain is broken, it
119
164
// does not touch the original slice and mark the chain as invalid.
120
- func buildChain (s * sessionRecord ) ( * sessionRecord ) {
165
+ func buildChain (s * sessionRecord ) * sessionRecord {
121
166
certChain := make ([]certMapElm , 0 )
122
167
123
168
// First we find the leaf
@@ -157,25 +202,35 @@ func insertCertificate(c certMapElm) (string, error) {
157
202
var hash string
158
203
err := db .QueryRow (q , c .CertHash , c .Certificate .IsCA , c .Certificate .Issuer .String (), c .Certificate .Subject .String (), c .chain .s , c .chain .isValid , getFullPath (c .CertHash )).Scan (& hash )
159
204
if err != nil {
160
- return "" , err
205
+ return hash , err
206
+ }
207
+ key , err := insertPublicKey (* c .Certificate )
208
+ if err != nil {
209
+ return hash , err
210
+ }
211
+
212
+ q = `INSERT INTO "many_certificate_has_many_public_key" ("hash_certificate", "hash_public_key") VALUES ($1, $2)`
213
+ _ , err = db .Query (q , hash , key )
214
+ if err != nil {
215
+ return hash , err
161
216
}
162
217
return hash , nil
163
218
}
164
219
165
220
// getFullPath takes a certificate's hash and return the full path to
166
221
// its location on disk
167
- func getFullPath (h string ) ( string ) {
222
+ func getFullPath (h string ) string {
168
223
return "TODO PATH"
169
224
}
170
225
171
226
func insertCertificates (s * sessionRecord ) ([]string , error ) {
172
227
var inserted []string
173
228
for _ , certificate := range s .Certificates {
174
- idc , err := insertCertificate (certificate )
229
+ tmp , err := insertCertificate (certificate )
230
+ inserted = append (inserted , tmp )
175
231
if err != nil {
176
232
return inserted , err
177
233
}
178
- inserted = append (inserted , idc )
179
234
}
180
235
return inserted , nil
181
236
}
@@ -203,7 +258,7 @@ func initDB() {
203
258
err := errors .New ("" )
204
259
db , err = sql .Open ("postgres" , connStr )
205
260
if err != nil {
206
- panic (err )
261
+ log . Fatalln (err )
207
262
}
208
263
}
209
264
0 commit comments