From: Daniel Danopia Date: 2009-10-22T06:45:09+09:00 Subject: Re: Certificate hashes using Base64, DER, ASN.1, PkiPath... I know how to hash, I said it's the hard part because I don't know how far off I am until I am right :P Here's the Base64 of my .cert file (I have a .key and .cert): MIIDqDCCAxGgAwIBAgIJAMIj9IivtNDGMA0GCSqGSIb3DQEBBQUAMIGVMQswCQYDVQQGEwJVUzETMBEGA1UECBMKTmV3IEplcnNleTEUMBIGA1UEBxMLTGFuZGlzdmlsbGUxEDAOBgNVBAoTB0Rhbm9waWExFDASBgNVBAsTC0dvb2dsZSBXYXZlMRQwEgYDVQQDEwtkYW5vcGlhLm5ldDEdMBsGCSqGSIb3DQEJARYObWVAZGFub3BpYS5uZXQwHhcNMDkxMDE3MjE0MjUxWhcNMTAxMDE3MjE0MjUxWjCBlTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFDASBgNVBAcTC0xhbmRpc3ZpbGxlMRAwDgYDVQQKEwdEYW5vcGlhMRQwEgYDVQQLEwtHb29nbGUgV2F2ZTEUMBIGA1UEAxMLZGFub3BpYS5uZXQxHTAbBgkqhkiG9w0BCQEWDm1lQGRhbm9waWEubmV0MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDHnWFfWfm6DNWrSarAfklo1EiJlDUEuik3U +F7b+Xuw66WwGLS9a55KwSc3QKLbf/HjNf9EDRRAqEjIRe3/KV+x19/bVvrc0EVYRocx1cN +4NoDor150IbffqBZEnjUGseGVe4B8yntex1P30y4MkCmWY5hKaWxHCdz861E1MDqQIDAQABo4H9MIH6MB0GA1UdDgQWBBTO0Ypdux4LGZAbemROJtfmKZZQrzCBygYDVR0jBIHCMIG/ gBTO0Ypdux4LGZAbemROJtfmKZZQr6GBm6SBmDCBlTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFDASBgNVBAcTC0xhbmRpc3ZpbGxlMRAwDgYDVQQKEwdEYW5vcGlhMRQwEgYDVQQLEwtHb29nbGUgV2F2ZTEUMBIGA1UEAxMLZGFub3BpYS5uZXQxHTAbBgkqhkiG9w0BCQEWDm1lQGRhbm9waWEubmV0ggkAwiP0iK +00MYwDAYDVR0TBAUwAwEB/ zANBgkqhkiG9w0BAQUFAAOBgQCA5My3QFJE8Svsw0eQN7MZ2/ OPvvDkVfqt3GX79y23pfy0b/y7DkyCAeQ7ilsFBlkiRaY8Y7g/pWg +w1jycN1bVbw8L2b04mYs +lALagtmKSZaui74QzN6wbaAm2YmbDGs7UdOpOODM4+jqdAUH4ZxAIx2YOYqJF1lJyPc3e7ZaA== (I sure hope Groups word-wraps.) And here is the Base64 of what it hashes. MIIDrDCCA6gwggMRoAMCAQICCQDCI/ SIr7TQxjANBgkqhkiG9w0BAQUFADCBlTELMAkGA1UEBhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFDASBgNVBAcTC0xhbmRpc3ZpbGxlMRAwDgYDVQQKEwdEYW5vcGlhMRQwEgYDVQQLEwtHb29nbGUgV2F2ZTEUMBIGA1UEAxMLZGFub3BpYS5uZXQxHTAbBgkqhkiG9w0BCQEWDm1lQGRhbm9waWEubmV0MB4XDTA5MTAxNzIxNDI1MVoXDTEwMTAxNzIxNDI1MVowgZUxCzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpOZXcgSmVyc2V5MRQwEgYDVQQHEwtMYW5kaXN2aWxsZTEQMA4GA1UEChMHRGFub3BpYTEUMBIGA1UECxMLR29vZ2xlIFdhdmUxFDASBgNVBAMTC2Rhbm9waWEubmV0MR0wGwYJKoZIhvcNAQkBFg5tZUBkYW5vcGlhLm5ldDCBnzNBgkqhkiG9w0BAQEFAAOBjQAwgYkCgYEAx51hX1n5ugzVq0mqwH5JaNRIiZQ1BLopN1Phe2/ l7sOulsBi0vWueSsEnN0Ci23/x4zX/RA0UQKhIyEXt/ ylfsdff21b63NBFWEaHMdXDfuDaA6K9edCG336gWRJ41BrHhlXuAfMp7XsdT99MuDJAplmOYSmlsRwnc/ OtRNTA6kCAwEAAaOB/TCB +jAdBgNVHQ4EFgQUztGKXbseCxmQG3pkTibX5imWUK8wgcoGA1UdIwSBwjCBv4AUztGKXbseCxmQG3pkTibX5imWUK +hgZukgZgwgZUxCzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpOZXcgSmVyc2V5MRQwEgYDVQQHEwtMYW5kaXN2aWxsZTEQMA4GA1UEChMHRGFub3BpYTEUMBIGA1UECxMLR29vZ2xlIFdhdmUxFDASBgNVBAMTC2Rhbm9waWEubmV0MR0wGwYJKoZIhvcNAQkBFg5tZUBkYW5vclhLm5ldIIJAMIj9IivtNDGMAwGA1UdEwQFMAMBAf8wDQYJKoZIhvcNAQEFBQADgYEAgOTMt0BSRPEr7MNHkDezGdvzj77w5FX6rdxl +/ctt6X8tG/ 8uw5MggHkO4pbBQZZIkWmPGO4P6VoPsNY8nDdW1W8PC9m9OJmLPpQC2oLZikmWrou +EMzesG2gJtmJmwxrO1HTqTjgzOPo6nQFB+GcQCMdmDmKiRdZScj3N3u2Wg= Here are my attempts at encoding my .cert into what it wants: irb(main):522:0> cert=Base64.decode64(cert) => ... irb(main):525:0> prehash.size => 942 irb(main):526:0> cert.size => 940 irb(main):527:0> cert2="0\202\003\254#{cert}" => ... irb(main):528:0> i=0;i+=1 while cert2[i]==prehash[i];i => 382 irb(main):531:0> c = OpenSSL::X509::Certificate.new(File.read ("danopia.net.cert")) => # irb(main):532:0> seq=OpenSSL::ASN1::Sequence.new([c]) => #]> irb(main):539:0> seq.to_der => "0\202\003\2540\202\003\2500\202\003\021\240\003\002\001\002\002\t \000\302#\364\210\257\264\320\3060\r\006\t*\206H\206\367\r \............................ irb(main):540:0> prehash => "0\202\003\2540\202\003\2500\202\003\021\240\003\002\001\002\002\t \000\302#\364\210\257\264\320\3060\r\006\t*\206H\206\367\r \............................. irb(main):541:0> i=0;i+=1 while seq.to_der[i]==prehash[i];i => 382 So it looks like the first part is right, but about a third of the way through, it suddenly changes. Here's the "good" version when it starts changing, followed by mine: (The first two chars are the same.) => "\201\2373A\202J\241\222!\275\303@@@A@\000\340c@\f b@\240`@1\347XW \326~n\2035j\322j\260\037\222Z5\022\"e\rA.\212M\324\370^\333\371 {\260\353\245\260\030\264\275k\236J\301'7@\242\333\177\361\3435\377D\r \024@\250H\310E\355\377)_\261\327\337\333V\372\334\320EXF\2071\325\303~ \340\332\003\242\275y\320\206\337~\240Y\022x\324\032\307\206U \356\001\363)\355{\035O\337L\2702@\246Y\216a)\245\261\034's\363\255D \324\300\352@\200\300@\000h\340\177L ~\214\aA\200\325GC \201\005\201\0053\264b\227n\307\202\306d \006\336\231\023\211\265\371\212e\224+\314 r\201\200\325GH\301 p\214 o \340\0053\264b\227n\307\202\306d\006\336\231\023\211\265\371\212e\224+ \350`f\351 f\f eLB\314\002A\200\325A\001\204\300\225T\314D\314\004A \200\325A\002\004\302\223\231]\310\022\231\\\234\331^LE\f \004\201\200\325A\001\304\302\323\030[\231\032\\\335\232[\e\031LD\f \003\201\200\325A\002\204\301\321\030[\233\334\032XLE\f \004\201\200\325A\002\304\302\321\333\333\331\333\031H\025\330]\231LE\f \004\201\200\325A\000\304\302\331\030[\233\334\032XK\233\231]\fGL \006\301\202J\241\222!\275\303@B@E\203\233YP\031\030 [\233\334\226\022\346\346WH \220\f\"?H\212\373M\fc\000\300`5Q\3210@S \0000\020\037\363\000\320`\222\250d\210op\320\020\020PP\0008\030\020\b \016L\313t\005$O\022\276\3144y\003{1\235\2778\373\357\016E_ \252\335\306_\277r\333z_\313F\377\313\260\344\310 \036C\270\245\260Pe \222$Zc\306;\203\372V\203\3545\217'\r\325\265[\303\302\366oN&b \317\245\000\266\240\266b\222e\253\242\357\20437\254\eh\t\266bf \303\032\316\324t\352N838\372:\235\001A\370g\020\b\307f\016b\242E \326Rr=\315\336\355\226" => "\201\2370\r\006\t*\206H\206\367\r \001\001\001\005\000\003\201\215\0000\201\211\002\201\201\000\307\235a_Y \371\272\f\325\253I\252\300~Ih\324H\211\2245\004\272)7S\341{o \345\356\303\256\226\300b\322\365\256y+\004\234\335\002\213m \377\307\214\327\375\0204Q\002\241#!\027\267\374\245~\307_\177m[\353sA \025a\032\034\307W\r\373\203h\016\212\365\347B\e}\372\201dI\343Pk \036\031W\270\a\314\247\265\354u?}2\340\311\002\231f9\204\246\226\304p \235\317\316\265\023S \003\251\002\003\001\000\001\243\201\3750\201\3720\035\006\003U \035\016\004\026\004\024\316\321\212]\273\036\v\031\220\ezdN& \327\346)\226P\2570\201\312\006\003U\035# \004\201\3020\201\277\200\024\316\321\212]\273\036\v\031\220\ezdN& \327\346)\226P\257\241\201\233\244\201\2300\201\2251\v0\t\006\003U \004\006\023\002US1\0230\021\006\003U\004\b\023\nNew Jersey1\0240\022\006\003U\004\a\023\vLandisville1\0200\016\006\003U \004\n\023\aDanopia1\0240\022\006\003U\004\v\023\vGoogle Wave1\0240\022\006\003U\004\003\023\vdanopia.net1\0350\e\006\t*\206H \206\367\r\001\t\001\026\016me@danopia.net\202\t\000\302# \364\210\257\264\320\3060\f\006\003U \035\023\004\0050\003\001\001\3770\r\006\t*\206H\206\367\r \001\001\005\005\000\003\201\201\000\200\344\314\267@RD\361+\354\303G \2207\263\031\333\363\217\276\360\344U\372\255\334e\373\367- \267\245\374\264o\374\273\016L\202\001\344;\212[\005\006Y\"E\246\303X\362p\335[U\274 wrote: > Daniel Danopia wrote: > > It seems like the hardest part is that it gives a hash. > > That's the easiest part to implement, although it does hide the > structure of what you're hashing :-) > > data = "hello" > require 'digest/sha1' > puts [Digest::SHA1.digest(data)].pack("m") > > > I think I'm > > going to add some debug code into the Java and print out a Base64 pre- > > hashing to see what is going on. > > That's a good idea. You can then see if it's really an ASN1 Sequence of > one or more certificates. > > Full specs of ASN1 and DER/BER are in these PDFs:http://www.itu.int/ITU-T/studygroups/com17/languages/X.680-0207.pdfhttp://www.itu.int/ITU-T/studygroups/com17/languages/X.690-0207.pdf > > HTH, > > Brian. > -- > Posted viahttp://www.ruby-forum.com/.