225
/* Given an ASN.1 chunk of a structure like:
227
24 NDEF: OCTET STRING -- This is not passed to us
228
04 1: OCTET STRING -- INPUT point s to here
235
: } -- This denotes a Null tag and are the last
236
-- two bytes in INPUT.
238
Create a new buffer with the content of that octet string. INPUT
239
is the orginal buffer with a length as stored at LENGTH. Returns
240
NULL on error or a new malloced buffer with the length of this new
241
buffer stored at LENGTH and the number of bytes parsed from input
242
are added to the value stored at INPUT_CONSUMED. INPUT_CONSUMED is
243
allowed to be passed as NULL if the caller is not interested in
245
static unsigned char *
246
cram_octet_string (const unsigned char *input, size_t *length,
247
size_t *input_consumed)
249
const unsigned char *s = input;
251
unsigned char *output, *d;
254
/* Allocate output buf. We know that it won't be longer than the
256
d = output = gcry_malloc (n);
262
if (parse_tag (&s, &n, &ti))
264
if (ti.class == UNIVERSAL && ti.tag == TAG_OCTET_STRING
265
&& !ti.ndef && !ti.is_constructed)
267
memcpy (d, s, ti.length);
272
else if (ti.class == UNIVERSAL && !ti.tag && !ti.is_constructed)
279
*length = d - output;
281
*input_consumed += s - input;
286
*input_consumed += s - input;
225
string_to_key (int id, char *salt, int iter, const char *pw,
294
string_to_key (int id, char *salt, size_t saltlen, int iter, const char *pw,
226
295
int req_keylen, unsigned char *keybuf)
317
set_key_iv (gcry_cipher_hd_t chd, char *salt, int iter, const char *pw,
392
set_key_iv (gcry_cipher_hd_t chd, char *salt, size_t saltlen, int iter,
393
const char *pw, int keybytes)
320
395
unsigned char keybuf[24];
323
398
assert (keybytes == 5 || keybytes == 24);
324
if (string_to_key (1, salt, iter, pw, keybytes, keybuf))
399
if (string_to_key (1, salt, saltlen, iter, pw, keybytes, keybuf))
326
401
rc = gcry_cipher_setkey (chd, keybuf, keybytes);
346
crypt_block (unsigned char *buffer, size_t length, char *salt, int iter,
347
const char *pw, int cipher_algo, int encrypt)
421
crypt_block (unsigned char *buffer, size_t length, char *salt, size_t saltlen,
422
int iter, const char *pw, int cipher_algo, int encrypt)
349
424
gcry_cipher_hd_t chd;
356
431
wipememory (buffer, length);
359
if (set_key_iv (chd, salt, iter, pw,
434
if (set_key_iv (chd, salt, saltlen, iter, pw,
360
435
cipher_algo == GCRY_CIPHER_RFC2268_40? 5:24))
362
437
wipememory (buffer, length);
383
458
parse_bag_encrypted_data (const unsigned char *buffer, size_t length,
384
int startoffset, const char *pw,
459
int startoffset, size_t *r_consumed, const char *pw,
385
460
void (*certcb)(void*, const unsigned char*, size_t),
388
463
struct tag_info ti;
389
464
const unsigned char *p = buffer;
465
const unsigned char *p_start = buffer;
390
466
size_t n = length;
391
467
const char *where;
393
470
unsigned int iter;
394
471
unsigned char *plain = NULL;
395
472
int bad_pass = 0;
473
unsigned char *cram_buffer = NULL;
474
size_t consumed = 0; /* Number of bytes consumed from the orginal buffer. */
398
477
if (parse_tag (&p, &n, &ti))
450
529
if (parse_tag (&p, &n, &ti))
452
if (ti.class || ti.tag != TAG_OCTET_STRING || ti.length != 8 )
531
if (ti.class || ti.tag != TAG_OCTET_STRING
532
|| ti.length < 8 || ti.length > 16 )
535
memcpy (salt, p, saltlen);
457
538
if (parse_tag (&p, &n, &ti))
459
540
if (ti.class || ti.tag != TAG_INTEGER || !ti.length )
468
549
where = "rc2-ciphertext";
469
550
if (parse_tag (&p, &n, &ti))
471
if (ti.class != CONTEXT || ti.tag != 0 || !ti.length )
553
consumed = p - p_start;
554
if (ti.class == CONTEXT && ti.tag == 0 && ti.is_constructed && ti.ndef)
556
/* Mozilla exported certs now come with single byte chunks of
557
octect strings. (Mozilla Firefox 1.0.4). Arghh. */
558
where = "cram-rc2-ciphertext";
559
cram_buffer = cram_octet_string ( p, &n, &consumed);
562
p = p_start = cram_buffer;
564
*r_consumed = consumed;
565
r_consumed = NULL; /* Ugly hack to not update that value any further. */
568
else if (ti.class == CONTEXT && ti.tag == 0 && ti.length )
474
573
log_info ("%lu bytes of RC2 encrypted text\n", ti.length);
482
581
memcpy (plain, p, ti.length);
483
crypt_block (plain, ti.length, salt, iter, pw, GCRY_CIPHER_RFC2268_40, 0);
582
crypt_block (plain, ti.length, salt, saltlen,
583
iter, pw, GCRY_CIPHER_RFC2268_40, 0);
489
589
/* # warning debug code is enabled */
635
741
static gcry_mpi_t *
636
742
parse_bag_data (const unsigned char *buffer, size_t length, int startoffset,
743
size_t *r_consumed, const char *pw)
640
746
struct tag_info ti;
641
747
const unsigned char *p = buffer;
748
const unsigned char *p_start = buffer;
642
749
size_t n = length;
643
750
const char *where;
645
753
unsigned int iter;
647
755
unsigned char *plain = NULL;
648
756
gcry_mpi_t *result = NULL;
649
757
int result_count, i;
758
unsigned char *cram_buffer = NULL;
759
size_t consumed = 0; /* Number of bytes consumed from the orginal buffer. */
652
762
if (parse_tag (&p, &n, &ti))
658
768
if (ti.class || ti.tag != TAG_OCTET_STRING)
771
consumed = p - p_start;
772
if (ti.is_constructed && ti.ndef)
774
/* Mozilla exported certs now come with single byte chunks of
775
octect strings. (Mozilla Firefox 1.0.4). Arghh. */
776
where = "cram-data.outersegs";
777
cram_buffer = cram_octet_string ( p, &n, &consumed);
780
p = p_start = cram_buffer;
782
*r_consumed = consumed;
783
r_consumed = NULL; /* Ugly hack to not update that value any further. */
661
787
where = "data.outerseqs";
662
788
if (parse_tag (&p, &n, &ti))
710
836
if (parse_tag (&p, &n, &ti))
712
if (ti.class || ti.tag != TAG_OCTET_STRING || ti.length != 8 )
838
if (ti.class || ti.tag != TAG_OCTET_STRING
839
|| ti.length < 8 || ti.length > 16)
842
memcpy (salt, p, saltlen);
717
845
if (parse_tag (&p, &n, &ti))
719
847
if (ti.class || ti.tag != TAG_INTEGER || !ti.length )
742
870
memcpy (plain, p, ti.length);
743
crypt_block (plain, ti.length, salt, iter, pw, GCRY_CIPHER_3DES, 0);
871
consumed += p - p_start + ti.length;
872
crypt_block (plain, ti.length, salt, saltlen, iter, pw, GCRY_CIPHER_3DES, 0);
878
/* # warning debug code is enabled */
879
/* FILE *fp = fopen ("tmp-rc2-plain-key.der", "wb"); */
880
/* if (!fp || fwrite (p, n, 1, fp) != 1) */
748
886
where = "decrypted-text";
749
887
if (parse_tag (&p, &n, &ti) || ti.class || ti.tag != TAG_SEQUENCE)
887
1035
if (ti.class != UNIVERSAL || ti.tag != TAG_OCTET_STRING)
1038
if (ti.is_constructed && ti.ndef)
1040
/* Mozilla exported certs now come with single byte chunks of
1041
octect strings. (Mozilla Firefox 1.0.4). Arghh. */
1042
where = "cram-bags";
1043
cram_buffer = cram_octet_string ( p, &n, NULL);
1046
p = p_start = cram_buffer;
891
1050
if (parse_tag (&p, &n, &ti))
893
1052
if (ti.class != UNIVERSAL || ti.tag != TAG_SEQUENCE)
1054
bagseqndef = ti.ndef;
895
1055
bagseqlength = ti.length;
1056
while (bagseqlength || bagseqndef)
898
/*log_debug ( "at offset %u\n", (p - buffer));*/
1058
log_debug ( "at offset %u\n", (p - p_start));
899
1059
where = "bag-sequence";
900
1060
if (parse_tag (&p, &n, &ti))
1062
if (bagseqndef && ti.class == UNIVERSAL && !ti.tag && !ti.is_constructed)
902
1064
if (ti.class != UNIVERSAL || ti.tag != TAG_SEQUENCE)
905
if (bagseqlength < ti.nhdr)
907
bagseqlength -= ti.nhdr;
908
if (bagseqlength < ti.length)
910
bagseqlength -= ti.length;
1069
if (bagseqlength < ti.nhdr)
1071
bagseqlength -= ti.nhdr;
1072
if (bagseqlength < ti.length)
1074
bagseqlength -= ti.length;
911
1077
len = ti.length;
913
1079
if (parse_tag (&p, &n, &ti))
916
1086
if (ti.tag == TAG_OBJECT_ID && ti.length == DIM(oid_encryptedData)
917
1087
&& !memcmp (p, oid_encryptedData, DIM(oid_encryptedData)))
1089
size_t consumed = 0;
919
1091
p += DIM(oid_encryptedData);
920
1092
n -= DIM(oid_encryptedData);
921
len -= DIM(oid_encryptedData);
1094
len -= DIM(oid_encryptedData);
922
1095
where = "bag.encryptedData";
923
if (parse_bag_encrypted_data (p, n, (p - buffer), pw,
1096
if (parse_bag_encrypted_data (p, n, (p - p_start), &consumed, pw,
924
1097
certcb, certcbarg))
927
1102
else if (ti.tag == TAG_OBJECT_ID && ti.length == DIM(oid_data)
928
&& !memcmp (p, oid_data, DIM(oid_data)))
1103
&& !memcmp (p, oid_data, DIM(oid_data)))
932
len -= DIM(oid_data);
933
return parse_bag_data (p, n, (p-buffer), pw);
1107
log_info ("already got an data object, skipping next one\n");
1113
size_t consumed = 0;
1118
len -= DIM(oid_data);
1119
result = parse_bag_data (p, n, (p - p_start), &consumed, pw);
936
log_info ( "unknown bag type - skipped\n");
1128
log_info ("unknown bag type - skipped\n");
938
1133
if (len < 0 || len > n)
1139
/* Need to skip the Null Tag. */
1140
if (parse_tag (&p, &n, &ti))
1142
if (!(ti.class == UNIVERSAL && !ti.tag && !ti.is_constructed))
1147
gcry_free (cram_buffer);
946
log_error ("error at \"%s\", offset %u\n", where, (p - buffer));
1150
log_error ("error at \"%s\", offset %u\n", where, (p - p_start));
1151
/* fixme: need to release RESULT. */
1152
gcry_free (cram_buffer);
1568
1775
/* Encrypt it. */
1569
1776
gcry_randomize (salt, 8, GCRY_STRONG_RANDOM);
1570
crypt_block (buffer, buflen, salt, 2048, pw, GCRY_CIPHER_RFC2268_40, 1);
1777
crypt_block (buffer, buflen, salt, 8, 2048, pw,
1778
GCRY_CIPHER_RFC2268_40, 1);
1572
1780
/* Encode the encrypted stuff into a bag. */
1573
1781
seqlist[seqlistidx].buffer = build_cert_bag (buffer, buflen, salt, &n);
1589
1797
/* Encrypt it. */
1590
1798
gcry_randomize (salt, 8, GCRY_STRONG_RANDOM);
1591
crypt_block (buffer, buflen, salt, 2048, pw, GCRY_CIPHER_3DES, 1);
1799
crypt_block (buffer, buflen, salt, 8, 2048, pw, GCRY_CIPHER_3DES, 1);
1593
1801
/* Encode the encrypted stuff into a bag. */
1594
1802
seqlist[seqlistidx].buffer = build_key_bag (buffer, buflen, salt, &n);