Criptografia e
Assinatura Digital
Patricia Rabelo
[email protected]
1
Multipurpose Internet Mail Extensions
(MIME)




Norma da internet para o formato das
mensagens de correio eletrônico. A grande
maioria das mensagens de correio eletrônico
são trocadas usando o protocolo SMTP e
usam o formato MIME.
Dividido em cabeçalho e conteúdo
Cabeçalho - identifica o tipo do conteúdo,
conjunto de caracteres e codificação
Conteúdo – dado a ser transmitido
2
Multipurpose Internet Mail Extensions
(MIME) - EXEMPLO
Content-type: multipart/mixed; boundary="frontier"
MIME-version: 1.0
--frontier
Content-type: text/plain
Este é o corpo da mensagem.
--frontier
Content-type: application/octet-stream
Content-transfer-encoding: base64
gajwO4+n2Fy4FV3V7zD9awd7uG8/TITP/vIocxXnnf/5mjgQjcipBUL1b3
uyLwAVtBLOP4nV
LdIAhSzlZnyLAF8na0n7g6OSeej7aqIl3NIXCfxDsPsY6NQjSvV77j4hWE
jlF/aglS6ghfju
FgRr+OX8QZMI1OmR4rUJUS7xgoknalqj3HJvaOpeb3CFlNI9VGZYz6
H6zuQBOWZzNB8glwpC
--frontier--
3
Secure Multipurpose Internet Mail
extension (S/MIME)


S/MIME oferece uma forma segura e consistente de enviar e
receber dados no formato MIME
Oferece os seguintes serviços: autenticação, integridade da
mensagem e não-rejeição da mensagem original e
confidencialidade.
S/MIME pode ser utilizado por qualquer protocolo que suporte
MIME, como HTTP
Utilizado nos softwares S/MIME de ConnectSoft, Frontier, FTP
Software, Qualcomm, Microsoft, Lotus, Wollongong, Banyan,
NCD, SecureWare, VeriSign, Netscape, and Novell.
Uma das partes do MIME consiste no blob no formato PKCS#7

Ver RFC 3851: http://www.ietf.org/rfc



4
Secure Multipurpose Internet Mail
extension (S/MIME)

Tipos de S/MIME:





Enveloped-data
Signed-data
Certs-only
Compressed-data
(p7m)
(p7s)
(p7c)
(p7z)
Headers:



MIME type: application/pkcs7-mime parameters: any file
suffix: any
MIME type: multipart/signed parameters:
protocol="application/pkcs7-signature" file suffix: any
MIME type: application/octet-stream parameters: any file
suffix: p7m, p7s, p7c, p7z
5
S/Mime – Enveloped data
 Mensagem
criptografada
 Tipo: “enveloped- data”
 extensão:".p7m".
Content-Type: application/pkcs7-mime; smime-type=enveloped-data;
name=smime.p7m
Content-Transfer-Encoding: base64
Content-Disposition: attachment; filename=smime.p7m
rfvbnj756tbBghyHhHUujhJhjH77n8HHGT9HG4VQpfyF467GhIGfHfYT6
7n8HHGghyHhHUujhJh4VQpfyF467GhIGfHfYGTrfvbnjT6jH7756tbB9H
f8HHGTrfvhJhjH776tbB9HG4VQbnj7567GhIGfHfYT6ghyHhHUujpfyF4
0GhIGfHfQbnj756YT64V
6
S/Mime – Signed data




Mensagem assinada
Tipo: signed-data
Conteúdo inserido no pkcs#7
Extensão: “.p7m”
Content-Type: application/pkcs7-mime; smime-type=signed-data;
name=smime.p7m
Content-Transfer-Encoding: base64
Content-Disposition: attachment; filename=smime.p7m
567GhIGfHfYT6ghyHhHUujpfyF4f8HHGTrfvhJhjH776tbB9HG4VQbnj7
77n8HHGT9HG4VQpfyF467GhIGfHfYT6rfvbnj756tbBghyHhHUujhJhjH
HUujhJh4VQpfyF467GhIGfHfYGTrfvbnjT6jH7756tbB9H7n8HHGghyHh
6YT64V0GhIGfHfQbnj75
7
S/Mime – Certs Only data



Mensagem para transmitir certificados
Tipo: “certs-only”
Extensão: “.p7c”
8
S/Mime – Compressed data



Mensagem compactada
Tipo: “compressed-data”
Extensão: “.p7z”
Content-Type: application/pkcs7-mime; smime-type=compresseddata; name=smime.p7z
Content-Transfer-Encoding: base64
Content-Disposition: attachment; filename=smime.p7z
rfvbnj756tbBghyHhHUujhJhjH77n8HHGT9HG4VQpfyF467GhIGf
HfYT6
7n8HHGghyHhHUujhJh4VQpfyF467GhIGfHfYGTrfvbnjT6jH7756
tbB9H
f8HHGTrfvhJhjH776tbB9HG4VQbnj7567GhIGfHfYT6ghyHhHUuj
pfyF4 0GhIGfHfQbnj756YT64V
9
Segurança via WEB

Desenvolver práticas de segurança que
permita o acesso da chave privada para o
usuário (assinante/assinatura ou
destinatário/criptografia), porém que a proteja
do acesso pelo servidor web.
10
PKCS
Public Key Cryptography Standards
PKCS #1 – 2.1RSA Cryptography StandardSee RFC 3447. Defines the mathematical
properties and format of RSA public and private keys (ASN.1-encoded in clear-text), and
the basic algorithms and encoding/padding schemes for performing RSA encryption,
decryption, and producing and verifying signatures.
PKCS #2 – WithdrawnNo longer active. Covered RSA encryption of message digests, but was
merged into PKCS #1
PKCS #3 – 1.4Diffie-Hellman Key Agreement StandardA cryptographic protocol that allows two
parties that have no prior knowledge of each other to jointly establish a shared secret key
over an insecure communications channel.
PKCS #4 – WithdrawnNo longer active. Covered RSA key syntax, but was merged into PKCS
#1.
PKCS #5 – 2.0Password-based Encryption StandardSee RFC 2898 and PBKDF2.
PKCS #6 – 1.5Extended-Certificate Syntax StandardDefines extensions to the old v1 X.509
certificate specification. Obsoleted by v3 of the same.
PKCS #7 – 1.5Cryptographic Message Syntax StandardSee RFC 2315. Used to sign and/or
encrypt messages under a PKI. Used also for certificate dissemination (for instance as a
response to a PKCS#10 message). Formed the basis for S/MIME, which is now based on
RFC 3852, an updated Cryptographic Message Syntax Standard (CMS). Often used for
single sign-on.
11
PKCS
Public Key Cryptography Standards
PKCS #8 – 1.2Private-Key Information Syntax Standard.Used to carry private certificate
keypairs (encrypted or unencrypted).
PKCS #9 - 2.0Selected Attribute TypesDefines selected attribute types for use in PKCS #6
extended certificates, PKCS #7 digitally signed messages, PKCS #8 private-key
information, and PKCS #10 certificate-signing requests.
PKCS #10 - 1.7Certification Request StandardSee RFC 2986. Format of messages sent to a
certification authority to request certification of a public key. See certificate signing request.
PKCS #11 - 2.20Cryptographic Token Interface (Cryptoki)An API defining a generic interface to
cryptographic tokens (see also Hardware Security Module). Often used for single sign-on
and smartcard [1].
PKCS #12 - 1.0Personal Information Exchange Syntax StandardDefines a file format
commonly used to store private keys with accompanying public key certificates, protected
with a password-based symmetric key. PFX is a predecessor to PKCS#12. This is a
container format that can contain multiple embedded objects, e.g. multiple certificates.
Usually protected/encrypted with a password. Can be used as a format for the Java key
store. Can be used by Tomcat, but NOT by Apache.
PKCS #13 – Elliptic Curve Cryptography Standard(Under development)
PKCS #14 – Pseudo-random Number Generation(Under development.)
PKCS #15 – 1.1Cryptographic Token Information Format StandardDefines a standard allowing
users of cryptographic tokens to identify themselves to applications, independent of the
application's Cryptoki implementation (PKCS #11) or other API. RSA has relinquished ICcard-related parts of this standard to ISO/IEC 7816-15 [2].
12
Cryptographic Message Syntax (CMS)
RFC3851

O CMS descreve uma sintaxe para proteção de dados, tanto
para assinatura digital quanto criptografia.
 Essa sintaxe permite encapsulamento, dados encapsulados
podem estar presentes de forma aninhada.
 Derivado do formato PKCS#7 versão 1.5
 Formato expresso em ASN.1 [X.208-88], com a codificação
BER (Basic Encoded Rules) [X.209-88]


ASN.1 – linguagem que define as palavras reservados do formato
BER – codificação binária que identifica o tamanho de cada parte da informação 
decodificação em um único passo.
13
Cryptographic Message Syntax (CMS)
RFC3851
id-ct-contentInfo OBJECT IDENTIFIER ::= { iso(1) memberbody(2) us(840) rsadsi(113549) pkcs(1) pkcs9(9)
smime(16) ct(1) 6 }
ContentInfo ::= SEQUENCE
{
contentType ContentType,
content [0] EXPLICIT ANY DEFINED BY contentType
}
ContentType ::= OBJECT IDENTIFIER
14
Cryptographic Message Syntax (CMS)

Content Type pode identificar o tipo do conteúdo com os seguintes
valores:

Dados (id-data):


Assinatura (id-signedData):


OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1)
pkcs7(7) 5 }
Dado criptografado (id-encryptedData):


OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1)
pkcs7(7) 3 }
Hash de dados (Digested-data):


OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1)
pkcs7(7) 2 }
Criptografia (id-envelopedData):


OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1)
pkcs7(7) 1 }
OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1)
pkcs7(7) 6 }
Dado Autenticado (id-ct-authData):

OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) rsadsi(113549) pkcs(1)
pkcs-9(9) smime(16) ct(1) 2 }
15
Processo - assinatura
1.
2.
3.
4.
O digest da mensagem a ser transmitida é
calculado utilizando o algoritmo de assinatura
especificado por cada assinante.
Para cada assinante, o digest calculado é
criptografado pela chave privada do assinante.
O valor do digest criptografado e demais
informações específicas de cada assinante são
inseridas no SignerInfo value: certificados, CRLs,
etc.
Os SignerInfo de todos os assinante são coletados
no SignedData.
16
Processo – Validação de assinatura
1.

2.
3.
O receptor decifra o digest da mensagem de cada assinante
utilizando a chave pública do respectivo assinante.
A chave pública pode ser obtida a partir de certificados que
pode estar eventualmente no SignerInfo do assinante ou a
partir de uma fonte confiável do receptor dado que o receptor
tenha o “issuer distinguished name” e “issuer-specific serial
number” do certificado do assinante.
O digest do mensagem é calculado de forma independente
pelo receptor utilizando o algoritmo de cada assinante.
Em seguida, o valor do digest calculado é comparado com o
valor do digest decifrado. Se a comparação for bem sucedida,
a assinatura é válida.
17
CMS – Signed Data
RFC 3852
SignedData ::= SEQUENCE {
version CMSVersion,
digestAlgorithms DigestAlgorithmIdentifiers,
encapContentInfo EncapsulatedContentInfo,
certificates [0] IMPLICIT CertificatesSet OPTIONAL,
crls [1] IMPLICIT CertificateRevocationLists OPTIONAL,
signerInfos SignerInfos
}
DigestAlgorithmIdentifiers ::= SET OF DigestAlgorithmIdentifier
DigestAlgorithmIdentifier ::= AlgorithmIdentifier
EncapsulatedContentInfo ::= SEQUENCE {
eContentType ContentType,
eContent [0] EXPLICIT OCTET STRING OPTIONAL
}
ContentType ::= OBJECT IDENTIFIER
CertificatesSet ::= SET OF ExtendedCertificateOrCertificate
ExtendedCertificateOrCertificate ::= CHOICE {
certificate Certificate,
-- X.509 extendedCertificate [0] IMPLICIT ExtendedCertificate
}
CertificateRevocationLists ::= SET OF CertificateRevocationList
SignerInfos ::= SET OF SignerInfo
18
CMS – Signed Data
SignerInfo ::= SEQUENCE {
version CMSVersion,
sid SignerIdentifier,
digestAlgorithm DigestAlgorithmIdentifier,
signedAttrs [0] IMPLICIT SignedAttributes OPTIONAL,
signatureAlgorithm SignatureAlgorithmIdentifier,
signature SignatureValue,
unsignedAttrs [1] IMPLICIT UnsignedAttributes OPTIONAL }
RFC 3852
SignerIdentifier ::= CHOICE {
issuerAndSerialNumber IssuerAndSerialNumber,
subjectKeyIdentifier [0] SubjectKeyIdentifier }
SignedAttributes ::= SET SIZE (1..MAX) OF Attribute
UnsignedAttributes ::= SET SIZE (1..MAX) OF Attribute
Attribute ::= SEQUENCE {
attrType OBJECT IDENTIFIER,
attrValues SET OF AttributeValue }
AttributeValue ::= ANY
SignatureValue ::= OCTET STRING
19
CMS – Signed Data
RFC 3852

Version – varia de acordo com o que foi incluído na mensagem:










Formatos dos certificados que estão presentes
Formatos das CRLS que estão presentes
Tipo do conteúdo
Versão do formato do certificado
Versão do formato do SignerInfo
Content – opcional, quando ausente temos uma assinatura externa
AlgorithmIdentifier – pode ser MD2, MD5
Certificates – conjunto de certificados no formato PKCS #6 e certificados X.509.
Este conjunto deve ser suficiente para validar toda a cadeia de certificados de cada
assinante.
CRLs - certificate revocation list (CRL) consiste na lista de números seriais de
certificados que foram revogados ou que não estão válidos e, consequentemente,
não devem ser confiáveis. Há 2 status de revogação (ver RFC 3280): revoked
(permanente) ou hold (temporário).
SignedAttributes - Atributos que são assinados junto com a mensagem, exemplos:





data e hora da assinatura.
SMIME capabilities – preferências para comunicação com o receptor
SMIME encription key preference
Id message digest
Id content type
20
Processo – Criptografia
Uma chave para criptografar o conteúdo é gerada aleatoriamente
(content-encryption key).
2. Para cada destinatário, a chave aleatória pode ser criptografada:
1.
•
•
•
•
pela chave pública do destinatário e armazenada no seu respectivo
KeyTransRecipientInfo;
por uma chave simétrica obtida por um acordo entre
remetente/destinatário e armazenada no seu respectivo
KEyAgreeRecipientInfo
por uma chave simétrica previamente obtida(chave de sessão) e
armazenada no seu respectivo KEKRecipientInfo;
por uma chave derivada de uma senha e armazenada em
PasswordRecipientInfo.
Para cada destinatário, a chave aleatória criptografa e outras
informações específicas do destinatário são armazenadas no
RecipientInfo value
4. O conteúdo é criptografado com a chave aleatória gerada.
5. Os registros do RecipientInfo dos destinatários e o conteúdo
criptografa são armazenados no EnvelopedData.
3.
21
Processo – Validação de Criptografia
1.
2.
3.
O destinatário recebe o EnvelopedData,
identifica seu respectivo RecipientInfo e o
decifra utilizando sua chave privada
O destinatário obtém a chave aleatória
gerada (content-encription key).
O destinatário decifra o conteúdo utilizando
a chave aleatória (content-encription key).
22
CMS – Enveloped Data
RFC 3852
EnvelopedData ::= SEQUENCE {
version CMSVersion,
originatorInfo [0] IMPLICIT OriginatorInfo OPTIONAL,
recipientInfos RecipientInfos,
encryptedContentInfo EncryptedContentInfo,
unprotectedAttrs [1] IMPLICIT UnprotectedAttributes OPTIONAL
}
OriginatorInfo ::= SEQUENCE {
certs [0] IMPLICIT CertificateSet OPTIONAL,
crls [1] IMPLICIT RevocationInfoChoices OPTIONAL
}
RecipientInfos ::= SET OF RecipientInfo
23
CMS – Enveloped Data
RFC 3852
EncryptedContentInfo ::= SEQUENCE
{
contentType ContentType,
contentEncryptionAlgorithm ContentEncryptionAlgorithmIdentifier,
encryptedContent [0] IMPLICIT EncryptedContent OPTIONAL
}
EncryptedContent ::= OCTET STRING
RecipientInfo ::= SEQUENCE
{
ktri KeyTransRecipientInfo,
kari [1] KeyAgreeRecipientInfo,
kekri [2] KEKRecipientInfo,
pwri [3] PasswordRecipientinfo,
ori [4] OtherRecipientInfo
}
EncryptedKey ::= OCTET STRING
UnprotectedAttributes ::= SET SIZE (1..MAX) OF Attribute
24
Exemplo utilizando
CRIPTO API - C
http://msdn.microsoft.com/en-us/library/cc527452.aspx
25
//------------------------------------------------------------------// Copyright (c) Microsoft Corporation. All rights reserved.
...
//------------------------------------------------------------------// Define the name of a certificate subject. The definition of SIGNER_NAME must be changed to the name of
// the subject of a certificate that has access to a private key. That certificate must have either the
// CERT_KEY_PROV_INFO_PROP_ID or CERT_KEY_CONTEXT_PROP_ID property set for the context to
// provide access to the private signature key.
#define SIGNER_NAME L"Insert_signer_name_here"
// Define the name of the store where the needed certificate//
#define CERT_STORE_NAME L"MY"
can be found.
//------------------------------------------------------------------int _tmain(int argc, _TCHAR* argv[])
{
CRYPT_DATA_BLOB SignedMessage;
if(SignMessage(&SignedMessage))
{
CRYPT_DATA_BLOB DecodedMessage;
if(VerifySignedMessage(&SignedMessage, &DecodedMessage))
free(DecodedMessage.pbData);
free(SignedMessage.pbData);
}
_tprintf(TEXT("Press any key to exit."));
}
26
//------------------------------------------------------------------// SignMessage
bool SignMessage(CRYPT_DATA_BLOB *pSignedMessageBlob)
{
//inicialization
...
// Initialize the output pointer.
pSignedMessageBlob->cbData = 0;
pSignedMessageBlob->pbData = NULL;
// The message to be signed. Usually, the message exists somewhere and a pointer is passed to the application.
pbMessage = (BYTE*)TEXT("CryptoAPI is a good way to handle security");
// Calculate the size of message. To include the terminating null character,
cbMessage = (lstrlen((TCHAR*) pbMessage) + 1) * sizeof(TCHAR);
// Create the MessageArray and the MessageSizeArray.
const BYTE* MessageArray[] = {pbMessage};
DWORD_PTR MessageSizeArray[1];
MessageSizeArray[0] = cbMessage;
// Open the certificate store.
if ( ( hCertStore = CertOpenStore( CERT_STORE_PROV_SYSTEM,
0,
NULL,
CERT_SYSTEM_STORE_CURRENT_USER, CERT_STORE_NAME))){
// Get a pointer to the signer's certificate. This certificate must have access to the signer's private key.
if(pSignerCert = CertFindCertificateInStore( hCertStore,
MY_ENCODING_TYPE,
0,
CERT_FIND_SUBJECT_STR,
SIGNER_NAME,
NULL)) {
...
27
// Initialize the signature structure.
SigParams.cbSize = sizeof(CRYPT_SIGN_MESSAGE_PARA);
SigParams.dwMsgEncodingType = MY_ENCODING_TYPE;
SigParams.pSigningCert = pSignerCert;
SigParams.HashAlgorithm.pszObjId = szOID_RSA_SHA1RSA;
SigParams.HashAlgorithm.Parameters.cbData = NULL;
SigParams.cMsgCert = 1;
SigParams.rgpMsgCert = &pSignerCert; //incluindo certificado do assinante
SigParams.cAuthAttr = 0;
SigParams.dwInnerContentType = 0;
SigParams.cMsgCrl = 0;
SigParams.cUnauthAttr = 0;
SigParams.dwFlags = 0;
SigParams.pvHashAuxInfo = NULL;
SigParams.rgAuthAttr = NULL;
// First, get the size of the signed BLOB.
if( CryptSignMessage(&SigParams,
FALSE,
&cbSignedMessageBlob))
1,
MessageArray,
MessageSizeArray,
NULL,
// Allocate memory for the signed BLOB.
if((pbSignedMessageBlob = (BYTE*)malloc(cbSignedMessageBlob)))
// Get the signed message BLOB.
if(CryptSignMessage( &SigParams,
FALSE,
1,
pbSignedMessageBlob,
&cbSignedMessageBlob))
MessageArray,
MessageSizeArray,
// pbSignedMessageBlob now contains the signed BLOB.
fReturn = true;
// Clean up and free memory as needed.
if(pSignerCert)
CertFreeCertificateContext(pSignerCert);
if(hCertStore)
CertCloseStore(hCertStore, CERT_CLOSE_STORE_CHECK_FLAG);
return fReturn;
28
//// Verify the message signature. Usually, this would be done in a separate program.
bool VerifySignedMessage( CRYPT_DATA_BLOB *pSignedMessageBlob, CRYPT_DATA_BLOB *pDecodedMessageBlob)
{
bool fReturn = false; DWORD cbDecodedMessageBlob; BYTE *pbDecodedMessageBlob = NULL;
CRYPT_VERIFY_MESSAGE_PARA VerifyParams;
....
// Initialize the VerifyParams data structure.
VerifyParams.cbSize = sizeof(CRYPT_VERIFY_MESSAGE_PARA);
VerifyParams.dwMsgAndCertEncodingType = MY_ENCODING_TYPE;
VerifyParams.hCryptProv = 0;
VerifyParams.pfnGetSignerCertificate = NULL;
VerifyParams.pvGetArg = NULL;
// First, call CryptVerifyMessageSignature to get the length of thebuffer needed to hold the decoded message.
if( CryptVerifyMessageSignature( &VerifyParams,
0,
pSignedMessageBlob->pbData,
pSignedMessageBlob->cbData,
&cbDecodedMessageBlob,
NULL))
NULL,
// Allocate memory for the decoded message.
if((pbDecodedMessageBlob = (BYTE*)malloc(cbDecodedMessageBlob)))
// Call CryptVerifyMessageSignature again to verify the signature and, if successful, copy the decoded message into the buffer.
// This will validate the signature against the certificate in the local store.
if(CryptVerifyMessageSignature( &VerifyParams,
0,
pSignedMessageBlob->pbData,
pSignedMessageBlob->cbData,
pbDecodedMessageBlob,
&cbDecodedMessageBlob,
NULL))
{
// emite mensagem "The verified message is \"%s\".\n"), pbDecodedMessageBlob);
fReturn = true;
} else
{
// emite mensagem "Verification message failed. \n"));
}
...
// If the decoded message buffer is still around, it means the function was successful. Copy the pointer and size into the output parameter.
if(pbDecodedMessageBlob) {
pDecodedMessageBlob->cbData = cbDecodedMessageBlob;
pDecodedMessageBlob->pbData = pbDecodedMessageBlob;
}
return fReturn;
}
29
Download

Segurança Digital