... | ... |
@@ -496,6 +496,19 @@ int asn1_get_x509(fmap_t *map, void **asn1data, unsigned int *size, cli_crt *x50 |
496 | 496 |
|
497 | 497 |
if(asn1_expect_objtype(map, tbs.next, &crt.size, &obj, 0x03)) /* signature */ |
498 | 498 |
return 1; |
499 |
+ if(obj.size > 513) { |
|
500 |
+ cli_dbgmsg("asn1_get_x509: signature too long\n"); |
|
501 |
+ return 1; |
|
502 |
+ } |
|
503 |
+ if(!fmap_need_ptr_once(map, obj.content, obj.size)) { |
|
504 |
+ cli_dbgmsg("asn1_get_x509: cannot read signature\n"); |
|
505 |
+ return 1; |
|
506 |
+ } |
|
507 |
+ if(mp_read_signed_bin(&x509->sig, obj.content, obj.size)) { |
|
508 |
+ cli_dbgmsg("asn1_get_x509: cannot convert signature to big number\n"); |
|
509 |
+ return 1; |
|
510 |
+ } |
|
511 |
+ |
|
499 | 512 |
if(crt.size) { |
500 | 513 |
cli_dbgmsg("asn1_get_x509: found unexpected extra data in signature\n"); |
501 | 514 |
return 1; |
... | ... |
@@ -512,7 +525,7 @@ int asn1_get_x509(fmap_t *map, void **asn1data, unsigned int *size, cli_crt *x50 |
512 | 512 |
|
513 | 513 |
|
514 | 514 |
|
515 |
-int asn1_parse_mscat(FILE *f) { |
|
515 |
+int asn1_parse_mscat(FILE *f, crtmgr *cmgr) { |
|
516 | 516 |
struct cli_asn1 asn1, deep, deeper; |
517 | 517 |
unsigned int size, dsize; |
518 | 518 |
fmap_t *map; |
... | ... |
@@ -682,6 +695,7 @@ int asn1_parse_mscat(FILE *f) { |
682 | 682 |
dsize = 1; |
683 | 683 |
break; |
684 | 684 |
} |
685 |
+ crtmgr_add(cmgr, &x509); |
|
685 | 686 |
cli_crt_clear(&x509); |
686 | 687 |
} |
687 | 688 |
if(dsize) |
... | ... |
@@ -23,6 +23,6 @@ int ms_asn1_get_sha1(fmap_t *map, void *asn1data, unsigned int avail, unsigned i |
23 | 23 |
int asn1_get_time(fmap_t *map, void **asn1data, unsigned int *size, time_t *time); |
24 | 24 |
int asn1_get_rsa_pubkey(fmap_t *map, void **asn1data, unsigned int *size, cli_crt *x509); |
25 | 25 |
int asn1_get_x509(fmap_t *map, void **asn1data, unsigned int *size, cli_crt *x509); |
26 |
-int asn1_parse_mscat(FILE *f); |
|
26 |
+int asn1_parse_mscat(FILE *f, crtmgr *c); |
|
27 | 27 |
|
28 | 28 |
#endif |
... | ... |
@@ -1,9 +1,15 @@ |
1 |
+#if HAVE_CONFIG_H |
|
2 |
+#include "clamav-config.h" |
|
3 |
+#endif |
|
4 |
+ |
|
1 | 5 |
#include "crtmgr.h" |
6 |
+#include "others.h" |
|
2 | 7 |
|
3 | 8 |
int cli_crt_init(cli_crt *x509) { |
4 | 9 |
if(mp_init_multi(&x509->n, &x509->e, &x509->sig, NULL)) |
5 | 10 |
return 1; |
6 | 11 |
x509->not_before = x509->not_after = 0; |
12 |
+ x509->prev = x509->next = NULL; |
|
7 | 13 |
return 0; |
8 | 14 |
} |
9 | 15 |
|
... | ... |
@@ -11,6 +17,43 @@ void cli_crt_clear(cli_crt *x509) { |
11 | 11 |
mp_clear_multi(&x509->n, &x509->e, &x509->sig, NULL); |
12 | 12 |
} |
13 | 13 |
|
14 |
+int crtmgr_add(crtmgr *m, cli_crt *x509) { |
|
15 |
+ cli_crt *i = m->crts; |
|
16 |
+ while(i) { |
|
17 |
+ if(x509->not_before == i->not_before && x509->not_after == i->not_after && !memcmp(x509->subject, i->subject, sizeof(i->subject))) { |
|
18 |
+ if(mp_cmp(&x509->n, &i->n) || mp_cmp(&x509->e, &i->e)) |
|
19 |
+ cli_dbgmsg("crtmgr_add: conflicting pk for the same cert\n"); |
|
20 |
+ return 0; |
|
21 |
+ } |
|
22 |
+ i = i->next; |
|
23 |
+ } |
|
24 |
+ i = cli_malloc(sizeof(*i)); |
|
25 |
+ if(!i) |
|
26 |
+ return 1; |
|
27 |
+ |
|
28 |
+ if(mp_init_multi(&i->n, &i->e, &i->sig, NULL)) { |
|
29 |
+ free(i); |
|
30 |
+ return 1; |
|
31 |
+ } |
|
32 |
+ if(mp_copy(&x509->n, &i->n) || mp_copy(&x509->e, &i->e) || mp_copy(&x509->sig, &i->sig)) { |
|
33 |
+ cli_crt_clear(i); |
|
34 |
+ free(i); |
|
35 |
+ return 1; |
|
36 |
+ } |
|
37 |
+ memcpy(i->subject, x509->subject, sizeof(i->subject)); |
|
38 |
+ memcpy(i->issuer, x509->issuer, sizeof(i->issuer)); |
|
39 |
+ i->not_before = x509->not_before; |
|
40 |
+ i->not_after = x509->not_after; |
|
41 |
+ i->hashtype = x509->hashtype; |
|
42 |
+ i->next = m->crts; |
|
43 |
+ i->prev = NULL; |
|
44 |
+ if(m->crts) |
|
45 |
+ m->crts->prev = i; |
|
46 |
+ m->crts = i; |
|
47 |
+ cli_dbgmsg("crtmgr_add: added cert\n"); |
|
48 |
+ return 0; |
|
49 |
+} |
|
50 |
+ |
|
14 | 51 |
/* typedef struct { */ |
15 | 52 |
/* cli_crt *certs; */ |
16 | 53 |
/* unsigned int ncerts; */ |
... | ... |
@@ -9,7 +9,7 @@ |
9 | 9 |
typedef enum { CLI_SHA1RSA, CLI_MD5RSA } cli_crt_hashtype; |
10 | 10 |
|
11 | 11 |
|
12 |
-typedef struct { |
|
12 |
+typedef struct cli_crt_t { |
|
13 | 13 |
uint8_t subject[SHA1_HASH_SIZE]; |
14 | 14 |
uint8_t issuer[SHA1_HASH_SIZE]; |
15 | 15 |
mp_int n; |
... | ... |
@@ -18,9 +18,18 @@ typedef struct { |
18 | 18 |
time_t not_before; |
19 | 19 |
time_t not_after; |
20 | 20 |
cli_crt_hashtype hashtype; |
21 |
+ struct cli_crt_t *prev; |
|
22 |
+ struct cli_crt_t *next; |
|
21 | 23 |
} cli_crt; |
22 | 24 |
|
25 |
+typedef struct { |
|
26 |
+ cli_crt *crts; |
|
27 |
+} crtmgr; |
|
28 |
+ |
|
29 |
+ |
|
23 | 30 |
int cli_crt_init(cli_crt *x509); |
24 | 31 |
void cli_crt_clear(cli_crt *x509); |
25 | 32 |
|
33 |
+int crtmgr_add(crtmgr *m, cli_crt *x509); |
|
34 |
+ |
|
26 | 35 |
#endif |
... | ... |
@@ -44,6 +44,7 @@ |
44 | 44 |
#include "bytecode.h" |
45 | 45 |
#include "bytecode_api.h" |
46 | 46 |
#include "events.h" |
47 |
+#include "crtmgr.h" |
|
47 | 48 |
|
48 | 49 |
/* |
49 | 50 |
* CL_FLEVEL is the signature f-level specific to the current code and |
... | ... |
@@ -251,6 +252,9 @@ struct cl_engine { |
251 | 251 |
/* Used for memory pools */ |
252 | 252 |
mpool_t *mempool; |
253 | 253 |
|
254 |
+ /* crtmgr stuff */ |
|
255 |
+ crtmgr cmgr; |
|
256 |
+ |
|
254 | 257 |
/* Callback(s) */ |
255 | 258 |
clcb_pre_cache cb_pre_cache; |
256 | 259 |
clcb_pre_scan cb_pre_scan; |
... | ... |
@@ -2353,7 +2353,7 @@ static int cli_loadcdb(FILE *fs, struct cl_engine *engine, unsigned int *signo, |
2353 | 2353 |
} |
2354 | 2354 |
|
2355 | 2355 |
static int cli_loadmscat(FILE *fs, struct cl_engine *engine, unsigned int options, struct cli_dbio *dbio) { |
2356 |
- asn1_parse_mscat(fs); |
|
2356 |
+ asn1_parse_mscat(fs, &engine->cmgr); |
|
2357 | 2357 |
return 0; |
2358 | 2358 |
} |
2359 | 2359 |
|