2010-09-14 10 views
6

Dato un algoritmo hash come SHA1 o SHA256, come farei per ottenere la codifica ASN.1 DER come definito in RFC3447? (vedere a pagina 42 - link) Di seguito è riportato l'output desiderato.C# - Come calcolare la codifica ASN.1 DER di un particolare algoritmo di hash?

MD5  30 20 30 0c 06 08 2a 86 48 86 f7 0d 02 05 05 00 04 10 
SHA-1  30 21 30 09 06 05 2b 0e 03 02 1a 05 00 04 14 
SHA-256 30 31 30 0d 06 09 60 86 48 01 65 03 04 02 01 05 00 04 20 
SHA-384 30 41 30 0d 06 09 60 86 48 01 65 03 04 02 02 05 00 04 30 
SHA-512 30 51 30 0d 06 09 60 86 48 01 65 03 04 02 03 05 00 04 40 

Spero ci sia un modo intelligente per fare questo in C# che non mi richiede di scrivere un OID di routine di conversione ASN.1 DER (o hardcode). Qualche idea?

+0

Non è chiaro cosa intendi con "dato un algoritmo hash". Vuoi dire dato il nome dell'algoritmo hash come una stringa? È possibile convertire dalla notazione punteggiata della notazione Oid in byte, ma è comunque necessario disporre di una mappatura hardcoded dell'algoritmo di hash comune Oids. –

+0

L'input può essere un HashAlgorithm, una stringa o un Oid. Il risultato desiderato è un byte [] che corrisponde al formato codificato. –

risposta

13

questo modo si ottiene un pezzo di strada:

string oidString = CryptoConfig.MapNameToOID(hashName); // f.x. "MD5" 
byte[] encodedOid = CryptoConfig.EncodeOID(oidString); // Gives you f.x. 06 08 2a 86 48 86 f7 0d 02 05 

Poi basta inserire nella sequenza-intestazione (30<length>30<length2><oid>050004<hashlength>).

Ovviamente se si desidera creare una firma V1.5 RSA PKCS # 1, è meglio usare solo RSAPKCS1SignatureFormatter.


EDIT: Alcuni ulteriori dettagli:

L'ASN.1 volete codificare è questa:

DigestInfo ::= SEQUENCE { 
     digestAlgorithm AlgorithmIdentifier, 
     digest OCTET STRING 
} 

dove

AlgorithmIdentifier ::= SEQUENCE { 
     algorithm    OBJECT IDENTIFIER, 
     parameters    ANY DEFINED BY algorithm OPTIONAL 
} 

Quindi, per iniziare da all'interno: digest-AlgorithmIdentifier è costituito da un SEQUENCE -tag (30), una lunghezza (torneremo a quella), un OID e alcuni parametri. L'OID per f.x. SHA-1 è 1.3.14.3.2.26, che è codificato come 06 05 2b 0e 03 02 1a (tag OID 06, lunghezza 5 e codifica dell'OID). Tutte le solite funzioni hash hanno come parametri NULL, che è codificato come 05 00. Quindi AlgorithmIdentifier contiene 9 byte: questo è il precedente.

Possiamo ora continuare con il resto del DigestInfo: un OCTET STRING, che contiene il valore dell'hash. L'hash da 20 byte di SHA-1 sarà codificato come 04 20 <HASH>.

La lunghezza del contenuto di DigestInfo ora è 11 + 22 byte(). Abbiamo bisogno di avviare il DigestInfo con il SEQUENCE -tag, così finiamo con: 30 21 30 09 06 05 2b 0w 02 01 1a 05 00 04 20 <HASH>.

Se è necessario generarlo da soli, ora si dovrebbe essere in grado di vedere che length2 = encodedOid.Length + 2 e quella lunghezza = lunghezza2 + 2 + 2 + lunghezza hash.

Se hai bisogno di ulteriori informazioni sulla codifica ASN.1, posso consigliare Burt Kaliski's A Layman's Guide to a Subset of ASN.1, BER, and DER.

Problemi correlati