Browse code

libclamav: report correct offset via cli_ac_result (bb#2076)

If sigs A*B, A{n-}B, etc. generate multiple matches, the reported offset
will be always for the first occurrence of A.

Tomasz Kojm authored on 2010/06/22 03:08:26
Showing 2 changed files
... ...
@@ -1,3 +1,7 @@
1
+Mon Jun 21 20:07:09 CEST 2010 (tk)
2
+----------------------------------
3
+ * libclamav: report correct offset via cli_ac_result (bb#2076)
4
+
1 5
 Fri Jun 18 15:41:08 CEST 2010 (tk)
2 6
 ----------------------------------
3 7
  * libclamav: minimize header parsing (bb#2065)
... ...
@@ -1121,7 +1121,7 @@ int cli_ac_scanbuff(const unsigned char *buffer, uint32_t length, const char **v
1121 1121
 	struct cli_ac_patt *patt, *pt;
1122 1122
         uint32_t i, bp, realoff, matchend;
1123 1123
 	uint16_t j;
1124
-	int32_t **offmatrix;
1124
+	int32_t **offmatrix, swap;
1125 1125
 	uint8_t found;
1126 1126
 	int type = CL_CLEAN;
1127 1127
 	struct cli_ac_result *newres;
... ...
@@ -1231,7 +1231,7 @@ int cli_ac_scanbuff(const unsigned char *buffer, uint32_t length, const char **v
1231 1231
 			    if(pt->partno != 1) {
1232 1232
 				found = 0;
1233 1233
 				for(j = 1; j <= CLI_DEFAULT_AC_TRACKLEN && offmatrix[pt->partno - 2][j] != -1; j++) {
1234
-				    found = 1;
1234
+				    found = j;
1235 1235
 				    if(pt->maxdist)
1236 1236
 					if(realoff - offmatrix[pt->partno - 2][j] > pt->maxdist)
1237 1237
 					    found = 0;
... ...
@@ -1245,6 +1245,16 @@ int cli_ac_scanbuff(const unsigned char *buffer, uint32_t length, const char **v
1245 1245
 				}
1246 1246
 			    }
1247 1247
 
1248
+			    if(pt->partno == 2 && found > 1) {
1249
+				swap = offmatrix[pt->parts - 1][1];
1250
+				offmatrix[pt->parts - 1][1] = offmatrix[pt->parts - 1][found];
1251
+				offmatrix[pt->parts - 1][found] = swap;
1252
+
1253
+				swap = offmatrix[0][1];
1254
+				offmatrix[0][1] = offmatrix[0][found];
1255
+				offmatrix[0][found] = swap;
1256
+			    }
1257
+
1248 1258
 			    if(pt->partno == 1 || (found && (pt->partno != pt->parts))) {
1249 1259
 				offmatrix[pt->partno - 1][0] %= CLI_DEFAULT_AC_TRACKLEN;
1250 1260
 				offmatrix[pt->partno - 1][0]++;
... ...
@@ -1262,7 +1272,9 @@ int cli_ac_scanbuff(const unsigned char *buffer, uint32_t length, const char **v
1262 1262
 					cli_dbgmsg("Matched signature for file type %s\n", pt->virname);
1263 1263
 					type = pt->type;
1264 1264
 					if(ftoffset && (!*ftoffset || (*ftoffset)->cnt < MAX_EMBEDDED_OBJ || type == CL_TYPE_ZIPSFX) && (type >= CL_TYPE_SFX || ((ftype == CL_TYPE_MSEXE || ftype == CL_TYPE_ZIP || ftype == CL_TYPE_MSOLE2) && type == CL_TYPE_MSEXE)))  {
1265
-					    /* FIXME: we don't know which offset of the first part is the correct one */
1265
+					    /* FIXME: the first offset in the array is most likely the correct one but
1266
+					     * it may happen it is not
1267
+					     */
1266 1268
 					    for(j = 1; j <= CLI_DEFAULT_AC_TRACKLEN && offmatrix[0][j] != -1; j++)
1267 1269
 						if(ac_addtype(ftoffset, type, offmatrix[pt->parts - 1][j], ctx))
1268 1270
 						    return CL_EMEM;
... ...
@@ -1287,7 +1299,7 @@ int cli_ac_scanbuff(const unsigned char *buffer, uint32_t length, const char **v
1287 1287
 					newres->virname = pt->virname;
1288 1288
 					newres->customdata = pt->customdata;
1289 1289
 					newres->next = *res;
1290
-					newres->offset = realoff;
1290
+					newres->offset = offmatrix[pt->parts - 1][1];
1291 1291
 					*res = newres;
1292 1292
 
1293 1293
 					pt = pt->next_same;