/
signer.go
123 lines (113 loc) · 3.43 KB
/
signer.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
package PrcIdSigner
import (
"bytes"
"code.google.com/p/go.crypto/openpgp"
"code.google.com/p/go.crypto/openpgp/armor"
"code.google.com/p/go.crypto/openpgp/packet"
"crypto"
"errors"
)
//SignPubKeyPKS takes asciiarmored private key which will sign the public key
//Public key is also ascii armored,pripwd is password of private key in string
//This function will return ascii armored signed public key i.e. (pubkey+sign by prikey)
//If lifeTime==0 then signature doesnt expire
func SignPubKeyPKS(asciiPub string, asciiPri string, pripwd string, lifeTime uint32) (asciiSignedKey string, err error) {
//get Private key from armor
_, priEnt, errPri := GetPri(asciiPri, pripwd) //pripwd is the password todecrypt the private key
_, pubEnt, errPub := GetPub(asciiPub) //This will generate signature and add it to pubEnt
if errPri != nil {
err = errPri
return
}
if errPub != nil {
err = errPub
return
}
usrIdstring := ""
for _, uIds := range pubEnt.Identities {
usrIdstring = uIds.Name
}
var prcPubEnt, prcPriEnt PrcEntity
prcPubEnt.Entity = &pubEnt
prcPriEnt.Entity = &priEnt
//prcPubEnt
//fmt.Println(usrIdstring)
myConf := &packet.Config{DefaultHash: crypto.SHA1}
errSign := prcPubEnt.PRCSignIdentityLifeTime(usrIdstring, prcPriEnt, myConf, lifeTime)
if errSign != nil {
err = errSign
return
}
idnts := pubEnt.Identities
for _, sss := range idnts {
for _ = range sss.Signatures {
asciiSignedKey, err = PubEntToAsciiArmor(pubEnt)
}
}
return
}
//GetPub gets packet.PublicKey and openpgp.Entity of Public Key from ascii armor
func GetPub(asciiPub string) (pubKey packet.PublicKey, retEntity openpgp.Entity, err error) {
read1 := bytes.NewReader([]byte(asciiPub))
entityList, errReadArm := openpgp.ReadArmoredKeyRing(read1)
if errReadArm != nil {
err = errReadArm
return
}
for _, pubKeyEntity := range entityList {
if pubKeyEntity.PrimaryKey != nil {
pubKey = *pubKeyEntity.PrimaryKey
retEntity = *pubKeyEntity
}
}
return
}
//GetPri gets packet.PrivateKEy and openpgp.Entity of Decrypted Private Key from ascii armor
func GetPri(asciiPri string, pripwd string) (priKey packet.PrivateKey, priEnt openpgp.Entity, err error) {
read1 := bytes.NewReader([]byte(asciiPri))
entityList, errReadArm := openpgp.ReadArmoredKeyRing(read1)
if errReadArm != nil {
// fmt.Println("Reading PriKey ", errReadArm.Error())
err = errReadArm
return
}
for _, can_pri := range entityList {
smPr := can_pri.PrivateKey
retEntity := can_pri
if smPr == nil {
// fmt.Println("No Private Key")
err = errors.New("No private key found in armor")
return
}
priKey = *smPr
errDecr := priKey.Decrypt([]byte(pripwd))
if errDecr != nil {
// fmt.Println("Decrypting ", errDecr.Error())
err = errDecr
return
}
retEntity.PrivateKey = &priKey
priEnt = *retEntity
}
return
}
//PubEntToAsciiArmor creates ASscii Armor from pubEnt of type openpgp.Entity
func PubEntToAsciiArmor(pubEnt openpgp.Entity) (asciiEntity string, err error) {
gotWriter := bytes.NewBuffer(nil)
wr, errEncode := armor.Encode(gotWriter, openpgp.PublicKeyType, nil)
if errEncode != nil {
// fmt.Println("Encoding Armor ", errEncode.Error())
err = errEncode
return
}
errSerial := pubEnt.Serialize(wr)
if errSerial != nil {
// fmt.Println("Serializing PubKey ", errSerial.Error())
}
errClosing := wr.Close()
if errClosing != nil {
// fmt.Println("Closing writer ", errClosing.Error())
}
asciiEntity = gotWriter.String()
return
}