Browse code

libclamav: versioninfo hashset was not properly cached (bb#2065)

Tomasz Kojm authored on 2010/09/07 23:57:51
Showing 6 changed files
... ...
@@ -1,3 +1,7 @@
1
+Tue Sep  7 16:55:43 CEST 2010 (tk)
2
+----------------------------------
3
+ * libclamav: versioninfo hashset was not properly cached (bb#2065)
4
+
1 5
 Thu Sep  2 21:21:58 EEST 2010 (edwin)
2 6
 -------------------------------------
3 7
  * libclamav/c++/bytecode2llvm.cpp: fix hung clamd on FreeBSD (bb #2235)
... ...
@@ -55,7 +55,7 @@ struct cli_exe_info {
55 55
     /** Number of sections*/
56 56
     uint16_t nsections;
57 57
     /** Hashset for versioninfo matching */
58
-    struct cli_hashset *vinfo;
58
+    struct cli_hashset vinfo;
59 59
     /** Resrources RVA - PE ONLY */
60 60
     uint32_t res_addr;
61 61
     /** Address size - PE ONLY */
... ...
@@ -888,8 +888,6 @@ int cli_ac_initdata(struct cli_ac_data *data, uint32_t partsigs, uint32_t lsigs,
888 888
 	return CL_ENULLARG;
889 889
     }
890 890
 
891
-    cli_hashset_init_noalloc(&data->vinfo);
892
-
893 891
     data->reloffsigs = reloffsigs;
894 892
     if(reloffsigs) {
895 893
 	data->offset = (uint32_t *) cli_malloc(reloffsigs * 2 * sizeof(uint32_t));
... ...
@@ -980,7 +978,8 @@ int cli_ac_caloff(const struct cli_matcher *root, struct cli_ac_data *data, cons
980 980
 	unsigned int i;
981 981
 	struct cli_ac_patt *patt;
982 982
 
983
-    /* info.exeinfo.vinfo = &data->vinfo; */
983
+    if(info)
984
+	data->vinfo = &info->exeinfo.vinfo;
984 985
 
985 986
     for(i = 0; i < root->ac_reloff_num; i++) {
986 987
 	patt = root->ac_reloff[i];
... ...
@@ -1001,8 +1000,6 @@ void cli_ac_freedata(struct cli_ac_data *data)
1001 1001
 {
1002 1002
 	uint32_t i;
1003 1003
 
1004
-    cli_hashset_destroy(&data->vinfo);
1005
-
1006 1004
     if(data && data->partsigs) {
1007 1005
 	for(i = 0; i < data->partsigs; i++) {
1008 1006
 	    if(data->offmatrix[i]) {
... ...
@@ -1176,7 +1173,7 @@ int cli_ac_scanbuff(const unsigned char *buffer, uint32_t length, const char **v
1176 1176
 			}
1177 1177
 			realoff = offset + bp - pt->prefix_length;
1178 1178
 			if(pt->offdata[0] == CLI_OFF_VERSION) {
1179
-			    if(!cli_hashset_contains_maybe_noalloc(&mdata->vinfo, realoff)) {
1179
+			    if(!cli_hashset_contains_maybe_noalloc(mdata->vinfo, realoff)) {
1180 1180
 				pt = pt->next_same;
1181 1181
 				continue;
1182 1182
 			    }
... ...
@@ -41,7 +41,7 @@ struct cli_ac_data {
41 41
     uint32_t *offset;
42 42
     uint32_t macro_lastmatch[32];
43 43
     /** Hashset for versioninfo matching */
44
-    struct cli_hashset vinfo;
44
+    struct cli_hashset *vinfo;
45 45
 };
46 46
 
47 47
 struct cli_ac_special {
... ...
@@ -361,6 +361,7 @@ static void targetinfo(struct cli_target_info *info, unsigned int target, fmap_t
361 361
 
362 362
     memset(info, 0, sizeof(struct cli_target_info));
363 363
     info->fsize = map->len;
364
+    cli_hashset_init_noalloc(&info->exeinfo.vinfo);
364 365
 
365 366
     if(target == 1)
366 367
 	einfo = cli_peheader;
... ...
@@ -612,6 +613,7 @@ int cli_fmap_scandesc(cli_ctx *ctx, cli_file_t ftype, uint8_t ftonly, struct cli
612 612
 	if((ret = cli_ac_initdata(&gdata, groot->ac_partsigs, groot->ac_lsigs, groot->ac_reloff_num, CLI_DEFAULT_AC_TRACKLEN)) || (ret = cli_ac_caloff(groot, &gdata, &info))) {
613 613
 	    if(info.exeinfo.section)
614 614
 		free(info.exeinfo.section);
615
+	    cli_hashset_destroy(&info.exeinfo.vinfo);
615 616
 	    return ret;
616 617
 	}
617 618
 
... ...
@@ -621,6 +623,7 @@ int cli_fmap_scandesc(cli_ctx *ctx, cli_file_t ftype, uint8_t ftonly, struct cli
621 621
 		cli_ac_freedata(&gdata);
622 622
 	    if(info.exeinfo.section)
623 623
 		free(info.exeinfo.section);
624
+	    cli_hashset_destroy(&info.exeinfo.vinfo);
624 625
 	    return ret;
625 626
 	}
626 627
 	if(troot->bm_offmode) {
... ...
@@ -631,6 +634,7 @@ int cli_fmap_scandesc(cli_ctx *ctx, cli_file_t ftype, uint8_t ftonly, struct cli
631 631
 		    cli_ac_freedata(&tdata);
632 632
 		    if(info.exeinfo.section)
633 633
 			free(info.exeinfo.section);
634
+		    cli_hashset_destroy(&info.exeinfo.vinfo);
634 635
 		    return ret;
635 636
 		}
636 637
 		bm_offmode = 1;
... ...
@@ -659,6 +663,7 @@ int cli_fmap_scandesc(cli_ctx *ctx, cli_file_t ftype, uint8_t ftonly, struct cli
659 659
 		    cli_bm_freeoff(&toff);
660 660
 		if(info.exeinfo.section)
661 661
 		    free(info.exeinfo.section);
662
+		cli_hashset_destroy(&info.exeinfo.vinfo);
662 663
 		return ret;
663 664
 	    }
664 665
 	}
... ...
@@ -675,6 +680,7 @@ int cli_fmap_scandesc(cli_ctx *ctx, cli_file_t ftype, uint8_t ftonly, struct cli
675 675
 		}
676 676
 		if(info.exeinfo.section)
677 677
 		    free(info.exeinfo.section);
678
+		cli_hashset_destroy(&info.exeinfo.vinfo);
678 679
 		return ret;
679 680
 	    } else if((acmode & AC_SCAN_FT) && ret >= CL_TYPENO) {
680 681
 		if(ret > type)
... ...
@@ -704,6 +710,7 @@ int cli_fmap_scandesc(cli_ctx *ctx, cli_file_t ftype, uint8_t ftonly, struct cli
704 704
 
705 705
     if(info.exeinfo.section)
706 706
 	free(info.exeinfo.section);
707
+    cli_hashset_destroy(&info.exeinfo.vinfo);
707 708
 
708 709
     if(ret == CL_VIRUS)
709 710
 	return CL_VIRUS;
... ...
@@ -2461,7 +2461,7 @@ int cli_peheader(fmap_t *map, struct cli_exe_info *peinfo)
2461 2461
     else
2462 2462
 	peinfo->res_addr = EC32(dirs[2].VirtualAddress);
2463 2463
 
2464
-    while(dirs[2].Size && peinfo->vinfo) {
2464
+    while(dirs[2].Size) {
2465 2465
 	struct vinfo_list vlist;
2466 2466
 	uint8_t *vptr, *baseptr;
2467 2467
     	uint32_t rva, res_sz;
... ...
@@ -2470,7 +2470,7 @@ int cli_peheader(fmap_t *map, struct cli_exe_info *peinfo)
2470 2470
 	memset(&vlist, 0, sizeof(vlist));
2471 2471
     	findres(0x10, 0xffffffff, EC32(dirs[2].VirtualAddress), map, peinfo->section, peinfo->nsections, hdr_size, versioninfo_cb, &vlist);
2472 2472
 	if(!vlist.count) break; /* No version_information */
2473
-	if(cli_hashset_init(peinfo->vinfo, 32, 80)) {
2473
+	if(cli_hashset_init(&peinfo->vinfo, 32, 80)) {
2474 2474
 	    cli_errmsg("cli_peheader: Unable to init vinfo hashset\n");
2475 2475
 	    free(section_hdr);
2476 2476
 	    free(peinfo->section);
... ...
@@ -2595,9 +2595,9 @@ int cli_peheader(fmap_t *map, struct cli_exe_info *peinfo)
2595 2595
 				continue;
2596 2596
 			    }
2597 2597
 
2598
-			    if(cli_hashset_addkey(peinfo->vinfo, (uint32_t)(vptr - baseptr + 6))) {
2598
+			    if(cli_hashset_addkey(&peinfo->vinfo, (uint32_t)(vptr - baseptr + 6))) {
2599 2599
 				cli_errmsg("cli_peheader: Unable to add rva to vinfo hashset\n");
2600
-				cli_hashset_destroy(peinfo->vinfo);
2600
+				cli_hashset_destroy(&peinfo->vinfo);
2601 2601
 				free(section_hdr);
2602 2602
 				free(peinfo->section);
2603 2603
 				peinfo->section = NULL;