git-svn-id: file:///var/lib/svn/clamav-devel/trunk/clamav-devel@1362 77e5149b-7576-45b1-b177-96237e5ba77b
Tomasz Kojm authored on 2005/03/01 10:19:48... | ... |
@@ -1,3 +1,8 @@ |
1 |
+Tue Mar 1 02:16:15 CET 2005 (tk) |
|
2 |
+--------------------------------- |
|
3 |
+ * clamscan: respect --exclude/include when entering directories (requested |
|
4 |
+ by Dean Plant <dean.plant*roke.co.uk>) |
|
5 |
+ |
|
1 | 6 |
Tue Mar 1 01:51:53 CET 2005 (tk) |
2 | 7 |
--------------------------------- |
3 | 8 |
* clamscan: add "Engine version" to summary (requested by Robert |
... | ... |
@@ -39,10 +39,6 @@ |
39 | 39 |
#include <clamav.h> |
40 | 40 |
#include <errno.h> |
41 | 41 |
|
42 |
-#ifdef HAVE_REGEX_H |
|
43 |
-#include <regex.h> |
|
44 |
-#endif |
|
45 |
- |
|
46 | 42 |
#include "defaults.h" |
47 | 43 |
#include "others.h" |
48 | 44 |
#include "options.h" |
... | ... |
@@ -76,7 +72,7 @@ int scanmanager(const struct optstruct *opt) |
76 | 76 |
#if !defined(C_CYGWIN) && !defined(C_OS2) && !defined(C_BEOS) |
77 | 77 |
if(!geteuid()) { |
78 | 78 |
if((user = getpwnam(UNPUSER)) == NULL) { |
79 |
- mprintf("@Can't get information about user "UNPUSER".\n"); |
|
79 |
+ mprintf("@Can't get information about user "UNPUSER"\n"); |
|
80 | 80 |
exit(60); /* this is critical problem, so we just exit here */ |
81 | 81 |
} |
82 | 82 |
} |
... | ... |
@@ -122,7 +118,7 @@ int scanmanager(const struct optstruct *opt) |
122 | 122 |
} |
123 | 123 |
|
124 | 124 |
if(!trie) { |
125 |
- mprintf("@Can't initialize the virus database.\n"); |
|
125 |
+ mprintf("@Can't initialize the virus database\n"); |
|
126 | 126 |
return 50; |
127 | 127 |
} |
128 | 128 |
|
... | ... |
@@ -214,7 +210,7 @@ int scanmanager(const struct optstruct *opt) |
214 | 214 |
|
215 | 215 |
/* we need full path for some reasons (eg. archive handling) */ |
216 | 216 |
if(!getcwd(cwd, sizeof(cwd))) { |
217 |
- mprintf("@Can't get absolute pathname of current working directory.\n"); |
|
217 |
+ mprintf("@Can't get absolute pathname of current working directory\n"); |
|
218 | 218 |
ret = 57; |
219 | 219 |
} else |
220 | 220 |
ret = scandirs(cwd, trie, user, opt, limits, options); |
... | ... |
@@ -243,7 +239,7 @@ int scanmanager(const struct optstruct *opt) |
243 | 243 |
if(compression && (thefilename[0] != '/' && thefilename[0] != '\\' && thefilename[1] != ':')) { |
244 | 244 |
/* we need to complete the path */ |
245 | 245 |
if(!getcwd(cwd, sizeof(cwd))) { |
246 |
- mprintf("@Can't get absolute pathname of current working directory.\n"); |
|
246 |
+ mprintf("@Can't get absolute pathname of current working directory\n"); |
|
247 | 247 |
free(limits); |
248 | 248 |
return 57; |
249 | 249 |
} else { |
... | ... |
@@ -295,29 +291,6 @@ int scanmanager(const struct optstruct *opt) |
295 | 295 |
return ret; |
296 | 296 |
} |
297 | 297 |
|
298 |
-int match_regex(const char *filename, const char *pattern) |
|
299 |
-{ |
|
300 |
-#ifdef HAVE_REGEX_H |
|
301 |
- regex_t reg; |
|
302 |
- int match, flags; |
|
303 |
-#if !defined(C_CYGWIN) && !defined(C_OS2) |
|
304 |
- flags = 0; |
|
305 |
-#else |
|
306 |
- flags = REG_ICASE; /* case insensitive on Windows */ |
|
307 |
-#endif |
|
308 |
- if(regcomp(®, pattern, flags) != 0) { |
|
309 |
- mprintf("!%s: Could not parse regular expression %s.\n", filename, pattern); |
|
310 |
- logg("!%s: Could not parse regular expression %s.\n", filename, pattern); |
|
311 |
- return 2; |
|
312 |
- } |
|
313 |
- match = (regexec(®, filename, 0, NULL, 0) == REG_NOMATCH) ? 0 : 1; |
|
314 |
- regfree(®); |
|
315 |
- return match; |
|
316 |
-#else /* HAVE_REGEX_H */ |
|
317 |
- return strstr(filename, pattern) ? 1 : 0; |
|
318 |
-#endif |
|
319 |
-} |
|
320 |
- |
|
321 | 298 |
int scanfile(const char *filename, struct cl_node *root, const struct passwd *user, const struct optstruct *opt, const struct cl_limits *limits, int options) |
322 | 299 |
{ |
323 | 300 |
int ret, included; |
... | ... |
@@ -331,50 +304,51 @@ int scanfile(const char *filename, struct cl_node *root, const struct passwd *us |
331 | 331 |
if(stat(filename, &sb) != -1) |
332 | 332 |
if(sb.st_dev == procdev) { |
333 | 333 |
if(!printinfected) |
334 |
- mprintf("%s: Excluded (/proc).\n", filename); |
|
334 |
+ mprintf("%s: Excluded (/proc)\n", filename); |
|
335 | 335 |
return 0; |
336 | 336 |
} |
337 | 337 |
#endif |
338 |
- |
|
338 |
+ |
|
339 | 339 |
if(optl(opt, "exclude")) { |
340 | 340 |
argument = getfirstargl(opt, "exclude", &optnode); |
341 |
- while (argument) { |
|
341 |
+ while(argument) { |
|
342 | 342 |
if(match_regex(filename, argument) == 1) { |
343 | 343 |
if(!printinfected) |
344 |
- mprintf("%s: Excluded.\n", filename); |
|
344 |
+ mprintf("%s: Excluded\n", filename); |
|
345 | 345 |
return 0; |
346 | 346 |
} |
347 | 347 |
argument = getnextargl(&optnode, "exclude"); |
348 | 348 |
} |
349 | 349 |
} |
350 |
- |
|
350 |
+ |
|
351 | 351 |
if(optl(opt, "include")) { |
352 | 352 |
included = 0; |
353 |
- argument = getfirstargl(opt, "include",&optnode); |
|
354 |
- while (argument && !included) { |
|
355 |
- if(match_regex(filename, argument) == 1) |
|
353 |
+ argument = getfirstargl(opt, "include", &optnode); |
|
354 |
+ while(argument && !included) { |
|
355 |
+ if(match_regex(filename, argument) == 1) { |
|
356 | 356 |
included = 1; |
357 |
+ break; |
|
358 |
+ } |
|
357 | 359 |
argument = getnextargl(&optnode, "include"); |
358 | 360 |
} |
359 | 361 |
|
360 |
- if (!included) { |
|
362 |
+ if(!included) { |
|
361 | 363 |
if(!printinfected) |
362 |
- mprintf("%s: Excluded.\n", filename); |
|
364 |
+ mprintf("%s: Excluded\n", filename); |
|
363 | 365 |
return 0; |
364 | 366 |
} |
365 |
- |
|
366 | 367 |
} |
367 | 368 |
|
368 | 369 |
if(fileinfo(filename, 1) == 0) { |
369 | 370 |
if(!printinfected) |
370 |
- mprintf("%s: Empty file.\n", filename); |
|
371 |
+ mprintf("%s: Empty file\n", filename); |
|
371 | 372 |
return 0; |
372 | 373 |
} |
373 | 374 |
|
374 | 375 |
if(geteuid()) |
375 | 376 |
if(checkaccess(filename, NULL, R_OK) != 1) { |
376 | 377 |
if(!printinfected) |
377 |
- mprintf("%s: Access denied.\n", filename); |
|
378 |
+ mprintf("%s: Access denied\n", filename); |
|
378 | 379 |
return 0; |
379 | 380 |
} |
380 | 381 |
|
... | ... |
@@ -392,12 +366,12 @@ int scanfile(const char *filename, struct cl_node *root, const struct passwd *us |
392 | 392 |
if((ret = checkfile(filename, root, limits, options)) == CL_VIRUS) { |
393 | 393 |
if(optl(opt, "remove")) { |
394 | 394 |
if(unlink(filename)) { |
395 |
- mprintf("%s: Can't remove.\n", filename); |
|
396 |
- logg("%s: Can't remove.\n", filename); |
|
395 |
+ mprintf("%s: Can't remove\n", filename); |
|
396 |
+ logg("%s: Can't remove\n", filename); |
|
397 | 397 |
claminfo.notremoved++; |
398 | 398 |
} else { |
399 |
- mprintf("%s: Removed.\n", filename); |
|
400 |
- logg("%s: Removed.\n", filename); |
|
399 |
+ mprintf("%s: Removed\n", filename); |
|
400 |
+ logg("%s: Removed\n", filename); |
|
401 | 401 |
} |
402 | 402 |
} else if (optl(opt, "move")) |
403 | 403 |
move_infected(filename, opt); |
... | ... |
@@ -428,21 +402,21 @@ int scanfile(const char *filename, struct cl_node *root, const struct passwd *us |
428 | 428 |
/* check permissions */ |
429 | 429 |
switch(checkaccess(filename, UNPUSER, R_OK)) { |
430 | 430 |
case -1: |
431 |
- mprintf("@Can't get information about user "UNPUSER".\n"); |
|
431 |
+ mprintf("@Can't get information about user "UNPUSER"\n"); |
|
432 | 432 |
exit(60); /* this is a critical problem so we just exit here */ |
433 | 433 |
case -2: |
434 |
- mprintf("@Can't fork.\n"); |
|
434 |
+ mprintf("@Can't fork\n"); |
|
435 | 435 |
exit(61); |
436 | 436 |
case 0: /* read access denied */ |
437 | 437 |
if(geteuid()) { |
438 | 438 |
if(!printinfected) |
439 |
- mprintf("%s: Access denied to archive.\n", filename); |
|
439 |
+ mprintf("%s: Access denied to archive\n", filename); |
|
440 | 440 |
} else { |
441 | 441 |
|
442 | 442 |
if(limits && limits->maxfilesize) |
443 | 443 |
if(fileinfo(filename, 1) / 1024 > limits->maxfilesize) { |
444 | 444 |
if(!printinfected) |
445 |
- mprintf("%s: Archive too big.\n", filename); |
|
445 |
+ mprintf("%s: Archive too big\n", filename); |
|
446 | 446 |
return 0; |
447 | 447 |
} |
448 | 448 |
|
... | ... |
@@ -458,12 +432,12 @@ int scanfile(const char *filename, struct cl_node *root, const struct passwd *us |
458 | 458 |
if((ret = checkfile(filename, root, limits, options)) == CL_VIRUS) { |
459 | 459 |
if(optl(opt, "remove")) { |
460 | 460 |
if(unlink(filename)) { |
461 |
- mprintf("%s: Can't remove.\n", filename); |
|
462 |
- logg("%s: Can't remove.\n", filename); |
|
461 |
+ mprintf("%s: Can't remove\n", filename); |
|
462 |
+ logg("%s: Can't remove\n", filename); |
|
463 | 463 |
claminfo.notremoved++; |
464 | 464 |
} else { |
465 |
- mprintf("%s: Removed.\n", filename); |
|
466 |
- logg("%s: Removed.\n", filename); |
|
465 |
+ mprintf("%s: Removed\n", filename); |
|
466 |
+ logg("%s: Removed\n", filename); |
|
467 | 467 |
} |
468 | 468 |
} else if (optl(opt, "move")) |
469 | 469 |
move_infected(filename, opt); |
... | ... |
@@ -481,7 +455,7 @@ int scancompressed(const char *filename, struct cl_node *root, const struct pass |
481 | 481 |
stat(filename, &statbuf); |
482 | 482 |
|
483 | 483 |
if(!S_ISREG(statbuf.st_mode)) { |
484 |
- mprintf("^Suspected archive %s is not a regular file.\n", filename); |
|
484 |
+ mprintf("^Suspected archive %s is not a regular file\n", filename); |
|
485 | 485 |
return 0; /* hmm ? */ |
486 | 486 |
} |
487 | 487 |
|
... | ... |
@@ -497,7 +471,7 @@ int scancompressed(const char *filename, struct cl_node *root, const struct pass |
497 | 497 |
#endif |
498 | 498 |
|
499 | 499 |
if(checkaccess(tmpdir, UNPUSER, W_OK) != 1) { |
500 |
- mprintf("@Can't write to the temporary directory.\n"); |
|
500 |
+ mprintf("@Can't write to the temporary directory\n"); |
|
501 | 501 |
exit(64); |
502 | 502 |
} |
503 | 503 |
|
... | ... |
@@ -606,10 +580,10 @@ int scancompressed(const char *filename, struct cl_node *root, const struct pass |
606 | 606 |
|
607 | 607 |
switch(ret) { |
608 | 608 |
case -1: |
609 |
- mprintf("@Can't fork().\n"); |
|
609 |
+ mprintf("@Can't fork()\n"); |
|
610 | 610 |
exit(61); /* this is critical problem, so we just exit here */ |
611 | 611 |
case -2: |
612 |
- mprintf("@Can't execute some unpacker. Check paths and permissions on the temporary directory.\n"); |
|
612 |
+ mprintf("@Can't execute some unpacker. Check paths and permissions on the temporary directory\n"); |
|
613 | 613 |
/* This is no longer a critical error (since 0.24). We scan |
614 | 614 |
* raw archive. |
615 | 615 |
*/ |
... | ... |
@@ -619,12 +593,12 @@ int scancompressed(const char *filename, struct cl_node *root, const struct pass |
619 | 619 |
if((ret = checkfile(filename, root, limits, 0)) == CL_VIRUS) { |
620 | 620 |
if(optl(opt, "remove")) { |
621 | 621 |
if(unlink(filename)) { |
622 |
- mprintf("%s: Can't remove.\n", filename); |
|
623 |
- logg("%s: Can't remove.\n", filename); |
|
622 |
+ mprintf("%s: Can't remove\n", filename); |
|
623 |
+ logg("%s: Can't remove\n", filename); |
|
624 | 624 |
claminfo.notremoved++; |
625 | 625 |
} else { |
626 |
- mprintf("%s: Removed.\n", filename); |
|
627 |
- logg("%s: Removed.\n", filename); |
|
626 |
+ mprintf("%s: Removed\n", filename); |
|
627 |
+ logg("%s: Removed\n", filename); |
|
628 | 628 |
} |
629 | 629 |
} else if (optl(opt, "move")) |
630 | 630 |
move_infected(filename, opt); |
... | ... |
@@ -642,12 +616,12 @@ int scancompressed(const char *filename, struct cl_node *root, const struct pass |
642 | 642 |
if((ret = checkfile(filename, root, limits, 0)) == CL_VIRUS) { |
643 | 643 |
if(optl(opt, "remove")) { |
644 | 644 |
if(unlink(filename)) { |
645 |
- mprintf("%s: Can't remove.\n", filename); |
|
646 |
- logg("%s: Can't remove.\n", filename); |
|
645 |
+ mprintf("%s: Can't remove\n", filename); |
|
646 |
+ logg("%s: Can't remove\n", filename); |
|
647 | 647 |
claminfo.notremoved++; |
648 | 648 |
} else { |
649 |
- mprintf("%s: Removed.\n", filename); |
|
650 |
- logg("%s: Removed.\n", filename); |
|
649 |
+ mprintf("%s: Removed\n", filename); |
|
650 |
+ logg("%s: Removed\n", filename); |
|
651 | 651 |
} |
652 | 652 |
} else if (optl(opt, "move")) |
653 | 653 |
move_infected(filename, opt); |
... | ... |
@@ -662,12 +636,12 @@ int scancompressed(const char *filename, struct cl_node *root, const struct pass |
662 | 662 |
|
663 | 663 |
if(optl(opt, "remove")) { |
664 | 664 |
if(unlink(filename)) { |
665 |
- mprintf("%s: Can't remove.\n", filename); |
|
666 |
- logg("%s: Can't remove.\n", filename); |
|
665 |
+ mprintf("%s: Can't remove\n", filename); |
|
666 |
+ logg("%s: Can't remove\n", filename); |
|
667 | 667 |
claminfo.notremoved++; |
668 | 668 |
} else { |
669 |
- mprintf("%s: Removed.\n", filename); |
|
670 |
- logg("%s: Removed.\n", filename); |
|
669 |
+ mprintf("%s: Removed\n", filename); |
|
670 |
+ logg("%s: Removed\n", filename); |
|
671 | 671 |
} |
672 | 672 |
} else if (optl(opt, "move")) |
673 | 673 |
move_infected(filename, opt); |
... | ... |
@@ -687,7 +661,7 @@ int scandenied(const char *filename, struct cl_node *root, const struct passwd * |
687 | 687 |
|
688 | 688 |
stat(filename, &statbuf); |
689 | 689 |
if(!S_ISREG(statbuf.st_mode)) { |
690 |
- mprintf("^Suspected archive %s is not a regular file.\n", filename); |
|
690 |
+ mprintf("^Suspected archive %s is not a regular file\n", filename); |
|
691 | 691 |
return 0; |
692 | 692 |
} |
693 | 693 |
|
... | ... |
@@ -704,7 +678,7 @@ int scandenied(const char *filename, struct cl_node *root, const struct passwd * |
704 | 704 |
|
705 | 705 |
|
706 | 706 |
if(checkaccess(tmpdir, UNPUSER, W_OK) != 1) { |
707 |
- mprintf("@Can't write to the temporary directory %s.\n", tmpdir); |
|
707 |
+ mprintf("@Can't write to the temporary directory %s\n", tmpdir); |
|
708 | 708 |
exit(64); |
709 | 709 |
} |
710 | 710 |
|
... | ... |
@@ -725,7 +699,7 @@ int scandenied(const char *filename, struct cl_node *root, const struct passwd * |
725 | 725 |
sprintf(tmpfile, "%s/%s", gendir, pt); |
726 | 726 |
|
727 | 727 |
if(filecopy(filename, tmpfile) == -1) { |
728 |
- mprintf("!I/O error.\n"); |
|
728 |
+ mprintf("!I/O error\n"); |
|
729 | 729 |
perror("copyfile()"); |
730 | 730 |
exit(58); |
731 | 731 |
} |
... | ... |
@@ -745,12 +719,12 @@ int scandenied(const char *filename, struct cl_node *root, const struct passwd * |
745 | 745 |
|
746 | 746 |
if(optl(opt, "remove")) { |
747 | 747 |
if(unlink(filename)) { |
748 |
- mprintf("%s: Can't remove.\n", filename); |
|
749 |
- logg("%s: Can't remove.\n", filename); |
|
748 |
+ mprintf("%s: Can't remove\n", filename); |
|
749 |
+ logg("%s: Can't remove\n", filename); |
|
750 | 750 |
claminfo.notremoved++; |
751 | 751 |
} else { |
752 |
- mprintf("%s: Removed.\n", filename); |
|
753 |
- logg("%s: Removed.\n", filename); |
|
752 |
+ mprintf("%s: Removed\n", filename); |
|
753 |
+ logg("%s: Removed\n", filename); |
|
754 | 754 |
} |
755 | 755 |
} else if (optl(opt, "move")) |
756 | 756 |
move_infected(filename, opt); |
... | ... |
@@ -821,7 +795,7 @@ int checkstdin(const struct cl_node *root, const struct cl_limits *limits, int o |
821 | 821 |
#endif |
822 | 822 |
|
823 | 823 |
if(checkaccess(tmpdir, UNPUSER, W_OK) != 1) { |
824 |
- mprintf("@Can't write to temporary directory.\n"); |
|
824 |
+ mprintf("@Can't write to temporary directory\n"); |
|
825 | 825 |
return 64; |
826 | 826 |
} |
827 | 827 |
|
... | ... |
@@ -901,18 +875,18 @@ int clamav_unpack(const char *prog, char **args, const char *tmpdir, const struc |
901 | 901 |
|
902 | 902 |
#ifdef HAVE_SETGROUPS |
903 | 903 |
if(setgroups(1, &user->pw_gid)) { |
904 |
- fprintf(stderr, "ERROR: setgroups() failed.\n"); |
|
904 |
+ fprintf(stderr, "ERROR: setgroups() failed\n"); |
|
905 | 905 |
exit(1); |
906 | 906 |
} |
907 | 907 |
#endif |
908 | 908 |
|
909 | 909 |
if(setgid(user->pw_gid)) { |
910 |
- fprintf(stderr, "ERROR: setgid(%d) failed.\n", (int) user->pw_gid); |
|
910 |
+ fprintf(stderr, "ERROR: setgid(%d) failed\n", (int) user->pw_gid); |
|
911 | 911 |
exit(1); |
912 | 912 |
} |
913 | 913 |
|
914 | 914 |
if(setuid(user->pw_uid)) { |
915 |
- fprintf(stderr, "ERROR: setuid(%d) failed.\n", (int) user->pw_uid); |
|
915 |
+ fprintf(stderr, "ERROR: setuid(%d) failed\n", (int) user->pw_uid); |
|
916 | 916 |
exit(1); |
917 | 917 |
} |
918 | 918 |
} |
... | ... |
@@ -957,7 +931,7 @@ int clamav_unpack(const char *prog, char **args, const char *tmpdir, const struc |
957 | 957 |
switch(WTERMSIG(status)) { |
958 | 958 |
|
959 | 959 |
case 9: |
960 |
- mprintf("\nUnpacker process %d stopped due to exceeded limits.\n", pid); |
|
960 |
+ mprintf("\nUnpacker process %d stopped due to exceeded limits\n", pid); |
|
961 | 961 |
return 0; |
962 | 962 |
case 6: /* abort */ |
963 | 963 |
mprintf("@Can't run %s\n", prog); |
... | ... |
@@ -40,6 +40,10 @@ |
40 | 40 |
#include <signal.h> |
41 | 41 |
#include <target.h> |
42 | 42 |
|
43 |
+#ifdef HAVE_REGEX_H |
|
44 |
+#include <regex.h> |
|
45 |
+#endif |
|
46 |
+ |
|
43 | 47 |
#include "output.h" |
44 | 48 |
#include "others.h" |
45 | 49 |
|
... | ... |
@@ -123,3 +127,26 @@ int isnumb(const char *str) |
123 | 123 |
|
124 | 124 |
return 1; |
125 | 125 |
} |
126 |
+ |
|
127 |
+int match_regex(const char *filename, const char *pattern) |
|
128 |
+{ |
|
129 |
+#ifdef HAVE_REGEX_H |
|
130 |
+ regex_t reg; |
|
131 |
+ int match, flags; |
|
132 |
+#if !defined(C_CYGWIN) && !defined(C_OS2) |
|
133 |
+ flags = 0; |
|
134 |
+#else |
|
135 |
+ flags = REG_ICASE; /* case insensitive on Windows */ |
|
136 |
+#endif |
|
137 |
+ if(regcomp(®, pattern, flags) != 0) { |
|
138 |
+ mprintf("!%s: Could not parse regular expression %s.\n", filename, pattern); |
|
139 |
+ logg("!%s: Could not parse regular expression %s.\n", filename, pattern); |
|
140 |
+ return 2; |
|
141 |
+ } |
|
142 |
+ match = (regexec(®, filename, 0, NULL, 0) == REG_NOMATCH) ? 0 : 1; |
|
143 |
+ regfree(®); |
|
144 |
+ return match; |
|
145 |
+#else /* HAVE_REGEX_H */ |
|
146 |
+ return strstr(filename, pattern) ? 1 : 0; |
|
147 |
+#endif |
|
148 |
+} |
... | ... |
@@ -51,7 +51,40 @@ int treewalk(const char *dirname, struct cl_node *root, const struct passwd *use |
51 | 51 |
struct dirent *dent; |
52 | 52 |
struct stat statbuf; |
53 | 53 |
char *fname; |
54 |
- int scanret = 0; |
|
54 |
+ int scanret = 0, included; |
|
55 |
+ struct optnode *optnode; |
|
56 |
+ char *argument; |
|
57 |
+ |
|
58 |
+ |
|
59 |
+ if(optl(opt, "exclude")) { |
|
60 |
+ argument = getfirstargl(opt, "exclude", &optnode); |
|
61 |
+ while(argument) { |
|
62 |
+ if(match_regex(dirname, argument) == 1) { |
|
63 |
+ if(!printinfected) |
|
64 |
+ mprintf("%s: Excluded\n", dirname); |
|
65 |
+ return 0; |
|
66 |
+ } |
|
67 |
+ argument = getnextargl(&optnode, "exclude"); |
|
68 |
+ } |
|
69 |
+ } |
|
70 |
+ |
|
71 |
+ if(optl(opt, "include")) { |
|
72 |
+ included = 0; |
|
73 |
+ argument = getfirstargl(opt, "include", &optnode); |
|
74 |
+ while(argument && !included) { |
|
75 |
+ if(match_regex(dirname, argument) == 1) { |
|
76 |
+ included = 1; |
|
77 |
+ break; |
|
78 |
+ } |
|
79 |
+ argument = getnextargl(&optnode, "include"); |
|
80 |
+ } |
|
81 |
+ |
|
82 |
+ if(!included) { |
|
83 |
+ if(!printinfected) |
|
84 |
+ mprintf("%s: Excluded\n", dirname); |
|
85 |
+ return 0; |
|
86 |
+ } |
|
87 |
+ } |
|
55 | 88 |
|
56 | 89 |
claminfo.dirs++; |
57 | 90 |
|