... | ... |
@@ -1258,10 +1258,22 @@ int cli_ac_initdata(struct cli_ac_data *data, uint32_t partsigs, uint32_t lsigs, |
1258 | 1258 |
} |
1259 | 1259 |
for(i = 1; i < lsigs; i++) |
1260 | 1260 |
data->lsigcnt[i] = data->lsigcnt[0] + 64 * i; |
1261 |
+ data->yr_matches = (uint8_t *) cli_calloc(lsigs, sizeof(uint8_t)); |
|
1262 |
+ if (data->yr_matches == NULL) { |
|
1263 |
+ free(data->lsigcnt[0]); |
|
1264 |
+ free(data->lsigcnt); |
|
1265 |
+ if(partsigs) |
|
1266 |
+ free(data->offmatrix); |
|
1267 |
+ |
|
1268 |
+ if(reloffsigs) |
|
1269 |
+ free(data->offset); |
|
1270 |
+ return CL_EMEM; |
|
1271 |
+ } |
|
1261 | 1272 |
|
1262 | 1273 |
/* subsig offsets */ |
1263 |
- data->lsig_matches = (struct cli_lsig_matches **) cli_calloc(lsigs * sizeof(struct cli_lsig_matches *), sizeof(struct cli_lsig_matches *)); |
|
1274 |
+ data->lsig_matches = (struct cli_lsig_matches **) cli_calloc(lsigs, sizeof(struct cli_lsig_matches *)); |
|
1264 | 1275 |
if(!data->lsig_matches) { |
1276 |
+ free(data->yr_matches); |
|
1265 | 1277 |
free(data->lsigcnt[0]); |
1266 | 1278 |
free(data->lsigcnt); |
1267 | 1279 |
if(partsigs) |
... | ... |
@@ -1279,6 +1291,7 @@ int cli_ac_initdata(struct cli_ac_data *data, uint32_t partsigs, uint32_t lsigs, |
1279 | 1279 |
free(data->lsig_matches); |
1280 | 1280 |
free(data->lsigsuboff_last); |
1281 | 1281 |
free(data->lsigsuboff_first); |
1282 |
+ free(data->yr_matches); |
|
1282 | 1283 |
free(data->lsigcnt[0]); |
1283 | 1284 |
free(data->lsigcnt); |
1284 | 1285 |
if(partsigs) |
... | ... |
@@ -1298,6 +1311,7 @@ int cli_ac_initdata(struct cli_ac_data *data, uint32_t partsigs, uint32_t lsigs, |
1298 | 1298 |
free(data->lsigsuboff_first[0]); |
1299 | 1299 |
free(data->lsigsuboff_last); |
1300 | 1300 |
free(data->lsigsuboff_first); |
1301 |
+ free(data->yr_matches); |
|
1301 | 1302 |
free(data->lsigcnt[0]); |
1302 | 1303 |
free(data->lsigcnt); |
1303 | 1304 |
if(partsigs) |
... | ... |
@@ -1392,6 +1406,7 @@ void cli_ac_freedata(struct cli_ac_data *data) |
1392 | 1392 |
free(data->lsig_matches); |
1393 | 1393 |
data->lsig_matches = 0; |
1394 | 1394 |
} |
1395 |
+ free(data->yr_matches); |
|
1395 | 1396 |
free(data->lsigcnt[0]); |
1396 | 1397 |
free(data->lsigcnt); |
1397 | 1398 |
free(data->lsigsuboff_last[0]); |
... | ... |
@@ -61,6 +61,7 @@ struct cli_ac_data { |
61 | 61 |
uint32_t **lsigcnt; |
62 | 62 |
uint32_t **lsigsuboff_last, **lsigsuboff_first; |
63 | 63 |
struct cli_lsig_matches **lsig_matches; |
64 |
+ uint8_t *yr_matches; |
|
64 | 65 |
uint32_t *offset; |
65 | 66 |
uint32_t macro_lastmatch[32]; |
66 | 67 |
/** Hashset for versioninfo matching */ |
... | ... |
@@ -766,8 +766,7 @@ static int lsig_eval(cli_ctx *ctx, struct cli_matcher *root, struct cli_ac_data |
766 | 766 |
static int yara_eval(cli_ctx *ctx, struct cli_matcher *root, struct cli_ac_data *acdata, struct cli_target_info *target_info, const char *hash, uint32_t lsid) |
767 | 767 |
{ |
768 | 768 |
struct cli_ac_lsig *ac_lsig = root->ac_lsigtable[lsid]; |
769 |
- uint8_t * code_start = ac_lsig->u.code_start; |
|
770 |
- int rc = 0; |
|
769 |
+ int rc; |
|
771 | 770 |
YR_SCAN_CONTEXT context = {0}; |
772 | 771 |
|
773 | 772 |
if (target_info != NULL) { |
... | ... |
@@ -779,9 +778,13 @@ static int yara_eval(cli_ctx *ctx, struct cli_matcher *root, struct cli_ac_data |
779 | 779 |
|
780 | 780 |
rc = yr_execute_code(ac_lsig, acdata, &context, 0, 0); |
781 | 781 |
|
782 |
- if (rc == CL_VIRUS) |
|
783 |
- cli_append_virus(ctx, ac_lsig->virname); |
|
784 |
- |
|
782 |
+ if (rc == CL_VIRUS) { |
|
783 |
+ if (ac_lsig->flag & CLI_LSIG_FLAG_PRIVATE) { |
|
784 |
+ rc = CL_CLEAN; |
|
785 |
+ } else { |
|
786 |
+ cli_append_virus(ctx, ac_lsig->virname); |
|
787 |
+ } |
|
788 |
+ } |
|
785 | 789 |
return rc; |
786 | 790 |
} |
787 | 791 |
|
... | ... |
@@ -77,6 +77,8 @@ struct cli_lsig_tdb { |
77 | 77 |
#endif |
78 | 78 |
}; |
79 | 79 |
|
80 |
+#define CLI_LSIG_FLAG_PRIVATE 0x01 |
|
81 |
+ |
|
80 | 82 |
struct cli_bc; |
81 | 83 |
struct cli_ac_lsig { |
82 | 84 |
#define CLI_LSIG_NORMAL 0 |
... | ... |
@@ -85,6 +87,7 @@ struct cli_ac_lsig { |
85 | 85 |
uint32_t id; |
86 | 86 |
unsigned bc_idx; |
87 | 87 |
uint8_t type; |
88 |
+ uint8_t flag; |
|
88 | 89 |
union { |
89 | 90 |
char *logic; |
90 | 91 |
uint8_t *code_start; |
... | ... |
@@ -3764,6 +3764,8 @@ static int load_oneyara(YR_RULE *rule, int chkpua, struct cl_engine *engine, uns |
3764 | 3764 |
} else { |
3765 | 3765 |
if (NULL != (lsig->u.code_start = rule->code_start)) { |
3766 | 3766 |
lsig->type = (rule->cl_flags & RULE_OFFSETS) ? CLI_YARA_OFFSET : CLI_YARA_NORMAL; |
3767 |
+ if (RULE_IS_PRIVATE(rule)) |
|
3768 |
+ lsig->flag |= CLI_LSIG_FLAG_PRIVATE; |
|
3767 | 3769 |
} else { |
3768 | 3770 |
cli_errmsg("load_oneyara: code start is NULL\n"); |
3769 | 3771 |
FREE_TDB(tdb); |
... | ... |
@@ -3815,6 +3817,7 @@ static int load_oneyara(YR_RULE *rule, int chkpua, struct cl_engine *engine, uns |
3815 | 3815 |
memcpy(&lsig->tdb, &tdb, sizeof(tdb)); |
3816 | 3816 |
ytable_delete(&ytable); |
3817 | 3817 |
|
3818 |
+ rule->lsigid = root->ac_lsigs - 1; |
|
3818 | 3819 |
yara_loaded++; |
3819 | 3820 |
cli_yaramsg("load_oneyara: successfully loaded %s\n", rule->identifier); |
3820 | 3821 |
return CL_SUCCESS; |
... | ... |
@@ -157,6 +157,9 @@ int yr_execute_code( |
157 | 157 |
int cycle = 0; |
158 | 158 |
#if REAL_YARA |
159 | 159 |
int tidx = yr_get_tidx(); |
160 |
+#else |
|
161 |
+ |
|
162 |
+ cli_dbgmsg("yara_exec: beginning execution for lsig %i\n", aclsig->id); |
|
160 | 163 |
#endif |
161 | 164 |
|
162 | 165 |
#ifdef PROFILING_ENABLED |
... | ... |
@@ -422,8 +425,7 @@ int yr_execute_code( |
422 | 422 |
#if REAL_YARA |
423 | 423 |
push(rule->t_flags[tidx] & RULE_TFLAGS_MATCH ? 1 : 0); |
424 | 424 |
#else |
425 |
- //tbd clamav |
|
426 |
- push(rule->g_flags & RULE_TFLAGS_MATCH ? 1 : 0); |
|
425 |
+ push(acdata->yr_matches[rule->lsigid]); |
|
427 | 426 |
#endif |
428 | 427 |
break; |
429 | 428 |
|
... | ... |
@@ -436,7 +438,10 @@ int yr_execute_code( |
436 | 436 |
#if REAL_YARA |
437 | 437 |
rule->t_flags[tidx] |= RULE_TFLAGS_MATCH; |
438 | 438 |
#else |
439 |
- rule_matches++; |
|
439 |
+ { |
|
440 |
+ rule_matches++; |
|
441 |
+ acdata->yr_matches[aclsig->id] = 1; |
|
442 |
+ } |
|
440 | 443 |
#endif |
441 | 444 |
|
442 | 445 |
#ifdef PROFILING_ENABLED |