Move fetching of revocation data, guess size of signature
This commit is contained in:
@@ -22,7 +22,7 @@ func (context *SignContext) updateByteRange() error {
|
|||||||
context.ByteRangeValues[1] = context.SignatureContentsStartByte - 1
|
context.ByteRangeValues[1] = context.SignatureContentsStartByte - 1
|
||||||
|
|
||||||
// Signature ByteRange part 2 start byte directly starts after the actual signature.
|
// Signature ByteRange part 2 start byte directly starts after the actual signature.
|
||||||
context.ByteRangeValues[2] = context.ByteRangeValues[1] + 1 + int64(signatureMaxLength) + 1
|
context.ByteRangeValues[2] = context.ByteRangeValues[1] + 1 + int64(context.SignatureMaxLength) + 1
|
||||||
|
|
||||||
// Signature ByteRange part 2 length is everything else of the file.
|
// Signature ByteRange part 2 length is everything else of the file.
|
||||||
context.ByteRangeValues[3] = output_file_size - context.ByteRangeValues[2]
|
context.ByteRangeValues[3] = output_file_size - context.ByteRangeValues[2]
|
||||||
|
@@ -29,7 +29,6 @@ type TSAResponse struct {
|
|||||||
TimeStampToken asn1.RawValue
|
TimeStampToken asn1.RawValue
|
||||||
}
|
}
|
||||||
|
|
||||||
var signatureMaxLength = uint32(1000000)
|
|
||||||
var signatureByteRangePlaceholder = "/ByteRange[0 ********** ********** **********]"
|
var signatureByteRangePlaceholder = "/ByteRange[0 ********** ********** **********]"
|
||||||
|
|
||||||
func (context *SignContext) createSignaturePlaceholder() (signature string, byte_range_start_byte int64, signature_contents_start_byte int64) {
|
func (context *SignContext) createSignaturePlaceholder() (signature string, byte_range_start_byte int64, signature_contents_start_byte int64) {
|
||||||
@@ -46,7 +45,7 @@ func (context *SignContext) createSignaturePlaceholder() (signature string, byte
|
|||||||
signature_contents_start_byte = int64(len(signature)) + 11
|
signature_contents_start_byte = int64(len(signature)) + 11
|
||||||
|
|
||||||
// Create a placeholder for the actual signature content, we wil replace it later.
|
// Create a placeholder for the actual signature content, we wil replace it later.
|
||||||
signature += " /Contents<" + strings.Repeat("0", int(signatureMaxLength)) + ">"
|
signature += " /Contents<" + strings.Repeat("0", int(context.SignatureMaxLength)) + ">"
|
||||||
|
|
||||||
if !context.SignData.Signature.Approval {
|
if !context.SignData.Signature.Approval {
|
||||||
signature += " /Reference [" // array of signature reference dictionaries
|
signature += " /Reference [" // array of signature reference dictionaries
|
||||||
@@ -88,6 +87,39 @@ func (context *SignContext) createSignaturePlaceholder() (signature string, byte
|
|||||||
return signature, byte_range_start_byte, signature_contents_start_byte
|
return signature, byte_range_start_byte, signature_contents_start_byte
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (context *SignContext) fetchRevocationData() error {
|
||||||
|
if context.SignData.RevocationFunction != nil {
|
||||||
|
if context.SignData.CertificateChains != nil && (len(context.SignData.CertificateChains) > 0) {
|
||||||
|
certificate_chain := context.SignData.CertificateChains[0]
|
||||||
|
if certificate_chain != nil && (len(certificate_chain) > 0) {
|
||||||
|
for i, certificate := range certificate_chain {
|
||||||
|
if i < len(certificate_chain)-1 {
|
||||||
|
err := context.SignData.RevocationFunction(certificate, certificate_chain[i+1], &context.SignData.RevocationData)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
err := context.SignData.RevocationFunction(certificate, nil, &context.SignData.RevocationData)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Calculate space needed for signature.
|
||||||
|
for _, crl := range context.SignData.RevocationData.CRL {
|
||||||
|
context.SignatureMaxLength += uint32(len(crl.FullBytes) * 2)
|
||||||
|
}
|
||||||
|
for _, ocsp := range context.SignData.RevocationData.OCSP {
|
||||||
|
context.SignatureMaxLength += uint32(len(ocsp.FullBytes) * 2)
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
func (context *SignContext) createSignature() ([]byte, error) {
|
func (context *SignContext) createSignature() ([]byte, error) {
|
||||||
|
|
||||||
// Sadly we can't efficiently sign a file, we need to read all the bytes we want to sign.
|
// Sadly we can't efficiently sign a file, we need to read all the bytes we want to sign.
|
||||||
@@ -107,54 +139,13 @@ func (context *SignContext) createSignature() ([]byte, error) {
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
signer_config := pkcs7.SignerInfoConfig{}
|
signer_config := pkcs7.SignerInfoConfig{
|
||||||
|
ExtraSignedAttributes: []pkcs7.Attribute{
|
||||||
TSATokenChain := make([][]*x509.Certificate, 0)
|
{
|
||||||
|
Type: asn1.ObjectIdentifier{1, 2, 840, 113583, 1, 1, 8},
|
||||||
if context.SignData.RevocationFunction != nil {
|
Value: context.SignData.RevocationData,
|
||||||
if context.SignData.CertificateChains != nil && (len(context.SignData.CertificateChains) > 0) {
|
},
|
||||||
certificate_chain := context.SignData.CertificateChains[0]
|
},
|
||||||
if certificate_chain != nil && (len(certificate_chain) > 0) {
|
|
||||||
for i, certificate := range certificate_chain {
|
|
||||||
if i < len(certificate_chain)-1 {
|
|
||||||
err = context.SignData.RevocationFunction(certificate, certificate_chain[i+1], &context.SignData.RevocationData)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
err = context.SignData.RevocationFunction(certificate, nil, &context.SignData.RevocationData)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if TSATokenChain != nil && (len(TSATokenChain) > 0) {
|
|
||||||
certificate_chain := TSATokenChain[0]
|
|
||||||
if certificate_chain != nil && (len(certificate_chain) > 0) {
|
|
||||||
for i, certificate := range certificate_chain {
|
|
||||||
if i < len(certificate_chain)-1 {
|
|
||||||
err = context.SignData.RevocationFunction(certificate, certificate_chain[i+1], &context.SignData.RevocationData)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
err = context.SignData.RevocationFunction(certificate, nil, &context.SignData.RevocationData)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
revocation_attribute := pkcs7.Attribute{
|
|
||||||
Type: asn1.ObjectIdentifier{1, 2, 840, 113583, 1, 1, 8},
|
|
||||||
Value: context.SignData.RevocationData,
|
|
||||||
}
|
|
||||||
signer_config.ExtraSignedAttributes = append(signer_config.ExtraSignedAttributes, revocation_attribute)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add the first certificate chain without our own certificate.
|
// Add the first certificate chain without our own certificate.
|
||||||
@@ -271,7 +262,7 @@ func (context *SignContext) replaceSignature() error {
|
|||||||
dst := make([]byte, hex.EncodedLen(len(signature)))
|
dst := make([]byte, hex.EncodedLen(len(signature)))
|
||||||
hex.Encode(dst, signature)
|
hex.Encode(dst, signature)
|
||||||
|
|
||||||
if uint32(len(dst)) > signatureMaxLength {
|
if uint32(len(dst)) > context.SignatureMaxLength {
|
||||||
return errors.New("Signature is too big to fit in reserved space.")
|
return errors.New("Signature is too big to fit in reserved space.")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
14
sign/sign.go
14
sign/sign.go
@@ -73,6 +73,7 @@ type SignContext struct {
|
|||||||
ByteRangeStartByte int64
|
ByteRangeStartByte int64
|
||||||
SignatureContentsStartByte int64
|
SignatureContentsStartByte int64
|
||||||
ByteRangeValues []int64
|
ByteRangeValues []int64
|
||||||
|
SignatureMaxLength uint32
|
||||||
}
|
}
|
||||||
|
|
||||||
func SignFile(input string, output string, sign_data SignData) error {
|
func SignFile(input string, output string, sign_data SignData) error {
|
||||||
@@ -143,6 +144,19 @@ func (context *SignContext) SignPDF() error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Base size for signature.
|
||||||
|
context.SignatureMaxLength = 100000
|
||||||
|
|
||||||
|
// Add estimated size for TSA.
|
||||||
|
// We can't kow actual size of TSA until after signing.
|
||||||
|
if context.SignData.TSA.URL != "" {
|
||||||
|
context.SignatureMaxLength += 10000
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fetch revocation data before adding signature placeholder.
|
||||||
|
// Revocation data can be quite large and we need to create enough space in the placeholder.
|
||||||
|
context.fetchRevocationData()
|
||||||
|
|
||||||
visual_signature, err := context.createVisualSignature()
|
visual_signature, err := context.createVisualSignature()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
|
Reference in New Issue
Block a user