This commit is contained in:
Marek Goc 2022-10-22 12:03:53 +02:00
parent d9a5f65e09
commit 3dab9a5c1f
21 changed files with 196 additions and 193 deletions

View File

@ -4,15 +4,15 @@ This is a partial implementation of S/MIME 4.0 in golang.
It consists of the following packages
- asn1<sup>[1]</sup> - ASN.1 marshalling and unmarshalling [![GoDoc](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/asn1?status.svg)](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/asn1)
- b64 - Pretty base64 encoding for S/MIME (basically just the PEM body) [![GoDoc](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/b64?status.svg)](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/b64)
- cms(cms/protocol)<sup>[2]</sup> - Cryptographic Message Syntax [rfc5652](https://tools.ietf.org/html/rfc5652)[![GoDoc](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/cms?status.svg)](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/cms) [![GoDoc](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/cms/protocol?status.svg)](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/cms/protocol)
- mime - Parsing for mime/multipart messages needed for S/MIME [![GoDoc](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/mime?status.svg)](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/mime)
- oid<sup>[3]</sup> - ASN.1 object identifiers and related crypto [![GoDoc](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/oid?status.svg)](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/oid)
- openssl - Shelled-out openssl for testing [![GoDoc](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/openssl?status.svg)](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/openssl)
- pki<sup>[4]</sup> - Creates x.509 pki for testing [![GoDoc](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/pki?status.svg)](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/pki)
- smime Secure/Multipurpose Internet Mail Extensions (S/MIME) Version 4.0 [rfc5751-bis-12](https://tools.ietf.org/html/draft-ietf-lamps-rfc5751-bis-12) [![GoDoc](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/smime?status.svg)](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/smime)
- timestamp<sup>[5]</sup> - Time-Stamp Protocol (TSP) [rfc3161](https://tools.ietf.org/html/rfc3161) [![GoDoc](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/timestamp?status.svg)](https://godoc.org/github.com/InfiniteLoopSpace/go_S-MIME/timestamp)
- asn1<sup>[1]</sup> - ASN.1 marshalling and unmarshalling
- b64 - Pretty base64 encoding for S/MIME (basically just the PEM body)
- cms(cms/protocol)<sup>[2]</sup> - Cryptographic Message Syntax [rfc5652](https://tools.ietf.org/html/rfc5652)
- mime - Parsing for mime/multipart messages needed for S/MIME
- oid<sup>[3]</sup> - ASN.1 object identifiers and related crypto
- openssl - Shelled-out openssl for testing
- pki<sup>[4]</sup> - Creates x.509 pki for testing
- smime Secure/Multipurpose Internet Mail Extensions (S/MIME) Version 4.0 [rfc5751-bis-12](https://tools.ietf.org/html/draft-ietf-lamps-rfc5751-bis-12)
- timestamp<sup>[5]</sup> - Time-Stamp Protocol (TSP) [rfc3161](https://tools.ietf.org/html/rfc3161)
It supports enveloped data with AES in CBC mode. Decryption also works with (3)DES. Authenticated-Enveloped-Data Content Type is also supported with AES-GCM and ChaCha20-Poly1305. Also RSAES-OAEP and RSASSA-PSS is supported.
@ -27,7 +27,7 @@ This is covered in
### Encryption and decryption
```go
import "github.com/InfiniteLoopSpace/go_S-MIME/smime"
import "git.ma-al.com/goc_marek/go_S-MIME/smime"
// Alice
mail := "From: Alice\nTo: Bob\n\nHello World!"
@ -41,7 +41,7 @@ plaintext, _ := SMIME.Decrypt(ciphertext)
### Signing and verfication
```go
import "github.com/InfiniteLoopSpace/go_S-MIME/smime"
import "git.ma-al.com/goc_marek/go_S-MIME/smime"
// Alice
AlicekeyPair, _ := tls.LoadX509KeyPair("AliceCert", "AliceKey")

View File

@ -9,9 +9,9 @@ import (
"log"
"time"
protocol "github.com/InfiniteLoopSpace/go_S-MIME/cms/protocol"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
timestamp "github.com/InfiniteLoopSpace/go_S-MIME/timestamp"
protocol "git.ma-al.com/goc_marek/go_S-MIME/cms/protocol"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
timestamp "git.ma-al.com/goc_marek/go_S-MIME/timestamp"
)
// CMS is an instance of cms to en-/decrypt and sign/verfiy CMS data

View File

@ -12,8 +12,8 @@ import (
"strings"
"testing"
openssl "github.com/InfiniteLoopSpace/go_S-MIME/openssl"
pki "github.com/InfiniteLoopSpace/go_S-MIME/pki"
openssl "git.ma-al.com/goc_marek/go_S-MIME/openssl"
pki "git.ma-al.com/goc_marek/go_S-MIME/pki"
)
var (

View File

@ -3,7 +3,7 @@ package protocol
import (
"encoding/asn1"
asn "github.com/InfiniteLoopSpace/go_S-MIME/asn1"
asn "git.ma-al.com/goc_marek/go_S-MIME/asn1"
)
// RawValue marshals val and returns the asn1.RawValue

View File

@ -5,19 +5,22 @@ import (
"encoding/asn1"
"log"
asn "github.com/InfiniteLoopSpace/go_S-MIME/asn1"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
asn "git.ma-al.com/goc_marek/go_S-MIME/asn1"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
)
//AuthEnvelopedData ::= SEQUENCE {
// AuthEnvelopedData ::= SEQUENCE {
// version CMSVersion,
// originatorInfo [0] IMPLICIT OriginatorInfo OPTIONAL,
// recipientInfos RecipientInfos,
// authEncryptedContentInfo EncryptedContentInfo,
/// authAttrs [1] IMPLICIT AuthAttributes OPTIONAL,
//
// / authAttrs [1] IMPLICIT AuthAttributes OPTIONAL,
//
// mac MessageAuthenticationCode,
// unauthAttrs [2] IMPLICIT UnauthAttributes OPTIONAL }
//https://tools.ietf.org/html/rfc5083##section-2.1
//
// https://tools.ietf.org/html/rfc5083##section-2.1
type AuthEnvelopedData struct {
Version int
OriginatorInfo asn1.RawValue `asn1:"optional,tag:0"`

View File

@ -7,8 +7,8 @@ import (
"encoding/asn1"
"fmt"
asn "github.com/InfiniteLoopSpace/go_S-MIME/asn1"
"github.com/InfiniteLoopSpace/go_S-MIME/b64"
asn "git.ma-al.com/goc_marek/go_S-MIME/asn1"
"git.ma-al.com/goc_marek/go_S-MIME/b64"
)
// ContentInfo ::= SEQUENCE {

View File

@ -13,7 +13,7 @@ import (
"errors"
"math/big"
"github.com/InfiniteLoopSpace/go_S-MIME/oid"
"git.ma-al.com/goc_marek/go_S-MIME/oid"
)
var errUnsupported = errors.New("Unsupported hash function")

View File

@ -4,10 +4,10 @@ import (
"crypto/x509/pkix"
"encoding/asn1"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
)
//EncryptedContentInfo ::= SEQUENCE {
// EncryptedContentInfo ::= SEQUENCE {
// contentType ContentType,
// contentEncryptionAlgorithm ContentEncryptionAlgorithmIdentifier,
// encryptedContent [0] IMPLICIT EncryptedContent OPTIONAL }

View File

@ -3,7 +3,7 @@ package protocol
import (
"encoding/asn1"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
)
// EncapsulatedContentInfo ::= SEQUENCE {

View File

@ -5,11 +5,11 @@ import (
"encoding/asn1"
"log"
asn "github.com/InfiniteLoopSpace/go_S-MIME/asn1"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
asn "git.ma-al.com/goc_marek/go_S-MIME/asn1"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
)
//EnvelopedData ::= SEQUENCE {
// EnvelopedData ::= SEQUENCE {
// version CMSVersion,
// originatorInfo [0] IMPLICIT OriginatorInfo OPTIONAL,
// recipientInfos RecipientInfos,

View File

@ -8,7 +8,7 @@ import (
"encoding/asn1"
"errors"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
)
type pssParameters struct {

View File

@ -13,10 +13,10 @@ import (
"log"
"time"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
)
//RecipientInfo ::= CHOICE {
// RecipientInfo ::= CHOICE {
// ktri KeyTransRecipientInfo,
// kari [1] KeyAgreeRecipientInfo,
// kekri [2] KEKRecipientInfo,
@ -42,7 +42,7 @@ func (recInfo *RecipientInfo) decryptKey(keyPair tls.Certificate) (key []byte, e
return
}
//KeyTransRecipientInfo ::= SEQUENCE {
// KeyTransRecipientInfo ::= SEQUENCE {
// version CMSVersion, -- always set to 0 or 2
// rid RecipientIdentifier,
// keyEncryptionAlgorithm KeyEncryptionAlgorithmIdentifier,
@ -112,7 +112,7 @@ func (ktri *KeyTransRecipientInfo) decryptKey(keyPair tls.Certificate) (key []by
return nil, nil
}
//RecipientIdentifier ::= CHOICE {
// RecipientIdentifier ::= CHOICE {
// issuerAndSerialNumber IssuerAndSerialNumber,
// subjectKeyIdentifier [0] SubjectKeyIdentifier }
type RecipientIdentifier struct {
@ -191,7 +191,7 @@ func encryptKeyRSA(key []byte, recipient *x509.Certificate) (ktri KeyTransRecipi
// ErrUnsupportedAlgorithm is returned if the algorithm is unsupported.
var ErrUnsupportedAlgorithm = errors.New("cms: cannot decrypt data: unsupported algorithm")
//KeyAgreeRecipientInfo ::= SEQUENCE {
// KeyAgreeRecipientInfo ::= SEQUENCE {
// version CMSVersion, -- always set to 3
// originator [0] EXPLICIT OriginatorIdentifierOrKey,
// ukm [1] EXPLICIT UserKeyingMaterial OPTIONAL,
@ -205,7 +205,7 @@ type KeyAgreeRecipientInfo struct {
RecipientEncryptedKeys []RecipientEncryptedKey `asn1:"sequence"` //RecipientEncryptedKeys ::= SEQUENCE OF RecipientEncryptedKey
}
//OriginatorIdentifierOrKey ::= CHOICE {
// OriginatorIdentifierOrKey ::= CHOICE {
// issuerAndSerialNumber IssuerAndSerialNumber,
// subjectKeyIdentifier [0] SubjectKeyIdentifier,
// originatorKey [1] OriginatorPublicKey }
@ -215,7 +215,7 @@ type OriginatorIdentifierOrKey struct {
OriginatorKey OriginatorPublicKey `asn1:"optional,tag:1"`
}
//OriginatorPublicKey ::= SEQUENCE {
// OriginatorPublicKey ::= SEQUENCE {
// algorithm AlgorithmIdentifier,
// publicKey BIT STRING
type OriginatorPublicKey struct {
@ -223,7 +223,7 @@ type OriginatorPublicKey struct {
PublicKey asn1.BitString
}
//RecipientEncryptedKey ::= SEQUENCE {
// RecipientEncryptedKey ::= SEQUENCE {
// rid KeyAgreeRecipientIdentifier,
// encryptedKey EncryptedKey }
type RecipientEncryptedKey struct {
@ -231,7 +231,7 @@ type RecipientEncryptedKey struct {
EncryptedKey []byte
}
//KeyAgreeRecipientIdentifier ::= CHOICE {
// KeyAgreeRecipientIdentifier ::= CHOICE {
// issuerAndSerialNumber IssuerAndSerialNumber,
// rKeyId [0] IMPLICIT RecipientKeyIdentifier }
type KeyAgreeRecipientIdentifier struct {
@ -239,7 +239,7 @@ type KeyAgreeRecipientIdentifier struct {
RKeyID RecipientKeyIdentifier `asn1:"optional,tag:0"`
}
//RecipientKeyIdentifier ::= SEQUENCE {
// RecipientKeyIdentifier ::= SEQUENCE {
// subjectKeyIdentifier SubjectKeyIdentifier,
// date GeneralizedTime OPTIONAL,
// other OtherKeyAttribute OPTIONAL }
@ -249,7 +249,7 @@ type RecipientKeyIdentifier struct {
Other OtherKeyAttribute `asn1:"optional"`
}
//OtherKeyAttribute ::= SEQUENCE {
// OtherKeyAttribute ::= SEQUENCE {
// keyAttrId OBJECT IDENTIFIER,
// keyAttr ANY DEFINED BY keyAttrId OPTIONAL }
type OtherKeyAttribute struct {

View File

@ -17,8 +17,8 @@ import (
"net/http"
"time"
asn "github.com/InfiniteLoopSpace/go_S-MIME/asn1"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
asn "git.ma-al.com/goc_marek/go_S-MIME/asn1"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
)
// SignedDataContent returns SignedData if ContentType is SignedData.

View File

@ -9,8 +9,8 @@ import (
"fmt"
"time"
asn "github.com/InfiniteLoopSpace/go_S-MIME/asn1"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
asn "git.ma-al.com/goc_marek/go_S-MIME/asn1"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
)
// SignerInfo ::= SEQUENCE {
@ -31,7 +31,7 @@ type SignerInfo struct {
UnsignedAttrs []Attribute `asn1:"set,optional,tag:1"` // UnsignedAttributes ::= SET SIZE (1..MAX) OF Attribute
}
//SignerIdentifier ::= CHOICE {
// SignerIdentifier ::= CHOICE {
// issuerAndSerialNumber IssuerAndSerialNumber,
// subjectKeyIdentifier [0] SubjectKeyIdentifier }
type SignerIdentifier struct {

View File

@ -13,12 +13,12 @@ import (
"log"
"strings"
"github.com/InfiniteLoopSpace/go_S-MIME/oid"
"git.ma-al.com/goc_marek/go_S-MIME/oid"
"github.com/InfiniteLoopSpace/go_S-MIME/b64"
"git.ma-al.com/goc_marek/go_S-MIME/b64"
cms "github.com/InfiniteLoopSpace/go_S-MIME/cms"
mime "github.com/InfiniteLoopSpace/go_S-MIME/mime"
cms "git.ma-al.com/goc_marek/go_S-MIME/cms"
mime "git.ma-al.com/goc_marek/go_S-MIME/mime"
)
// SMIME is an instance of cms to en-/decrypt and sign/verfiy SMIME messages

View File

@ -11,9 +11,9 @@ import (
"strings"
"testing"
"github.com/InfiniteLoopSpace/go_S-MIME/cms"
"github.com/InfiniteLoopSpace/go_S-MIME/openssl"
"github.com/InfiniteLoopSpace/go_S-MIME/pki"
"git.ma-al.com/goc_marek/go_S-MIME/cms"
"git.ma-al.com/goc_marek/go_S-MIME/openssl"
"git.ma-al.com/goc_marek/go_S-MIME/pki"
)
var (
@ -233,7 +233,7 @@ vCunrnVNqcBU+B1O8BiR4yPWnLMcRSyFRVJQA7HCp8JlDV6abXd8vPFfXuC9WN7rOvTKF8
Y0ZB9qANMAsGA1UdDzEEAwIAEA==
-----END PRIVATE KEY-----`
//https://github.com/fullsailor/pkcs7/issues/9
// https://github.com/fullsailor/pkcs7/issues/9
func TestSampleiTunesReceipt(t *testing.T) {
b, err := base64.StdEncoding.DecodeString(strings.TrimSpace(iTunesReceipt))
@ -359,7 +359,7 @@ VZXl0gKgxSOmDrcp1eQxdlymzrPv9U60wUJ0bkPfrU9qZj3mJrmrkQk61JTe3j6/
QfjfFBG9JG2mUmYQP1KQ3SypGHzDW8vngvsGu//tNU0NFfOqQu4bYU4VpQl0nPtD
4B85NkrgvQsWAQ==`
//https://github.com/fullsailor/pkcs7/issues/11
// https://github.com/fullsailor/pkcs7/issues/11
func TestSCEP(t *testing.T) {
b, err := base64.StdEncoding.DecodeString(SCEP)

View File

@ -6,9 +6,9 @@ import (
"math/big"
"time"
asn "github.com/InfiniteLoopSpace/go_S-MIME/asn1"
cms "github.com/InfiniteLoopSpace/go_S-MIME/cms/protocol"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
asn "git.ma-al.com/goc_marek/go_S-MIME/asn1"
cms "git.ma-al.com/goc_marek/go_S-MIME/cms/protocol"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
)
// TSTInfo ::= SEQUENCE {

View File

@ -5,7 +5,7 @@ import (
"fmt"
"strings"
cms "github.com/InfiniteLoopSpace/go_S-MIME/cms/protocol"
cms "git.ma-al.com/goc_marek/go_S-MIME/cms/protocol"
)
// PKIStatusInfo ::= SEQUENCE {

View File

@ -12,8 +12,8 @@ import (
"encoding/asn1"
"math/big"
cms "github.com/InfiniteLoopSpace/go_S-MIME/cms/protocol"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
cms "git.ma-al.com/goc_marek/go_S-MIME/cms/protocol"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
)
// TimeStampReq ::= SEQUENCE {
@ -93,7 +93,7 @@ func (req TimeStampReq) Do(url string) (TimeStampResp, error) {
return ParseResponse(buf.Bytes())
}
//MessageImprint ::= SEQUENCE {
// MessageImprint ::= SEQUENCE {
// hashAlgorithm AlgorithmIdentifier,
// hashedMessage OCTET STRING }
type MessageImprint struct {

View File

@ -1,11 +1,11 @@
package timestamp
import (
asn "github.com/InfiniteLoopSpace/go_S-MIME/asn1"
cms "github.com/InfiniteLoopSpace/go_S-MIME/cms/protocol"
asn "git.ma-al.com/goc_marek/go_S-MIME/asn1"
cms "git.ma-al.com/goc_marek/go_S-MIME/cms/protocol"
)
//TimeStampResp ::= SEQUENCE {
// TimeStampResp ::= SEQUENCE {
// status PKIStatusInfo,
// timeStampToken TimeStampToken OPTIONAL }
type TimeStampResp struct {

View File

@ -6,9 +6,9 @@ import (
"crypto/x509"
"time"
asn1 "github.com/InfiniteLoopSpace/go_S-MIME/asn1"
cms "github.com/InfiniteLoopSpace/go_S-MIME/cms/protocol"
oid "github.com/InfiniteLoopSpace/go_S-MIME/oid"
asn1 "git.ma-al.com/goc_marek/go_S-MIME/asn1"
cms "git.ma-al.com/goc_marek/go_S-MIME/cms/protocol"
oid "git.ma-al.com/goc_marek/go_S-MIME/oid"
)
const (