git-svn-id: file:///var/lib/svn/clamav-devel/trunk/clamav-devel@535 77e5149b-7576-45b1-b177-96237e5ba77b
Tomasz Kojm authored on 2004/05/02 09:51:01... | ... |
@@ -1,10 +1,14 @@ |
1 |
+Sun May 2 02:48:04 CEST 2004 (tk) |
|
2 |
+---------------------------------- |
|
3 |
+ * libclamav: support files compressed with compress.exe (test/test1.msc) |
|
4 |
+ |
|
1 | 5 |
Sat May 1 21:29:29 CEST 2004 (tk) |
2 | 6 |
---------------------------------- |
3 | 7 |
* clamd: stream scanner: |
4 | 8 |
+ scan exactly up to StreamMaxLength (patch by Joe Maimon |
5 | 9 |
<jmaimon*ttec.com>) |
6 | 10 |
+ fix description leak on ReadTimeout (patch by Maxim Dounin |
7 |
- <mdounin@rambler-co.ru>) |
|
11 |
+ <mdounin*rambler-co.ru>) |
|
8 | 12 |
* contrib/trashscan: v. 0.12 (Trashware <trashware*gmx.de>) |
9 | 13 |
* libclamav: in block-encrypted mode scan a raw encrypted archive before |
10 | 14 |
marking it as encrypted (requested by Andy Fiddaman |
... | ... |
@@ -32,7 +36,7 @@ Wed Apr 28 15:29:29 BST 2004 (njh) |
32 | 32 |
Send 554 after DATA received, not 550 |
33 | 33 |
Don't send rejection notices to rejection notices, we |
34 | 34 |
just end up playing ping-pong (patch by "Andrey |
35 |
- J.Melnikoff (TEMHOTA)" <temnota@kmv.ru> |
|
35 |
+ J.Melnikoff (TEMHOTA)" <temnota*kmv.ru> |
|
36 | 36 |
If CL_DEBUG is defined, don't redirect stdout/stderr |
37 | 37 |
Don't attempt to return an old signature if no |
38 | 38 |
filename has been given. There has never been |
... | ... |
@@ -179,7 +179,9 @@ libclamav_la_SOURCES = \ |
179 | 179 |
ole2_extract.h \ |
180 | 180 |
vba_extract.c \ |
181 | 181 |
vba_extract.h \ |
182 |
- cltypes.h |
|
182 |
+ cltypes.h \ |
|
183 |
+ msexpand.c \ |
|
184 |
+ msexpand.h |
|
183 | 185 |
|
184 | 186 |
|
185 | 187 |
lib_LTLIBRARIES = libclamav.la |
... | ... |
@@ -194,7 +196,7 @@ am_libclamav_la_OBJECTS = matcher.lo md5.lo others.lo readdb.lo cvd.lo \ |
194 | 194 |
dsig.lo str.lo scanners.lo unrarlib.lo zzip-dir.lo zzip-err.lo \ |
195 | 195 |
zzip-file.lo zzip-info.lo zzip-io.lo zzip-stat.lo zzip-zip.lo \ |
196 | 196 |
strc.lo blob.lo mbox.lo message.lo snprintf.lo strrcpy.lo \ |
197 |
- table.lo text.lo ole2_extract.lo vba_extract.lo |
|
197 |
+ table.lo text.lo ole2_extract.lo vba_extract.lo msexpand.lo |
|
198 | 198 |
libclamav_la_OBJECTS = $(am_libclamav_la_OBJECTS) |
199 | 199 |
|
200 | 200 |
DEFS = @DEFS@ |
... | ... |
@@ -207,7 +209,7 @@ am__depfiles_maybe = depfiles |
207 | 207 |
@AMDEP_TRUE@DEP_FILES = ./$(DEPDIR)/blob.Plo ./$(DEPDIR)/cvd.Plo \ |
208 | 208 |
@AMDEP_TRUE@ ./$(DEPDIR)/dsig.Plo ./$(DEPDIR)/matcher.Plo \ |
209 | 209 |
@AMDEP_TRUE@ ./$(DEPDIR)/mbox.Plo ./$(DEPDIR)/md5.Plo \ |
210 |
-@AMDEP_TRUE@ ./$(DEPDIR)/message.Plo \ |
|
210 |
+@AMDEP_TRUE@ ./$(DEPDIR)/message.Plo ./$(DEPDIR)/msexpand.Plo \ |
|
211 | 211 |
@AMDEP_TRUE@ ./$(DEPDIR)/ole2_extract.Plo ./$(DEPDIR)/others.Plo \ |
212 | 212 |
@AMDEP_TRUE@ ./$(DEPDIR)/readdb.Plo ./$(DEPDIR)/scanners.Plo \ |
213 | 213 |
@AMDEP_TRUE@ ./$(DEPDIR)/snprintf.Plo ./$(DEPDIR)/str.Plo \ |
... | ... |
@@ -288,6 +290,7 @@ distclean-compile: |
288 | 288 |
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/mbox.Plo@am__quote@ |
289 | 289 |
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/md5.Plo@am__quote@ |
290 | 290 |
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/message.Plo@am__quote@ |
291 |
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/msexpand.Plo@am__quote@ |
|
291 | 292 |
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/ole2_extract.Plo@am__quote@ |
292 | 293 |
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/others.Plo@am__quote@ |
293 | 294 |
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/readdb.Plo@am__quote@ |
... | ... |
@@ -47,6 +47,7 @@ extern "C" |
47 | 47 |
#define CL_EGZIP 103 /* gzip handler error */ |
48 | 48 |
#define CL_EBZIP 104 /* bzip2 handler error */ |
49 | 49 |
#define CL_EOLE2 105 /* OLE2 handler error */ |
50 |
+#define CL_EMSCOMP 106 /* compress.exe handler error */ |
|
50 | 51 |
#define CL_EACCES 200 /* access denied */ |
51 | 52 |
#define CL_ENULLARG 300 /* null argument error */ |
52 | 53 |
|
53 | 54 |
new file mode 100644 |
... | ... |
@@ -0,0 +1,158 @@ |
0 |
+/* |
|
1 |
+ * msexpand: Microsoft "compress.exe/expand.exe" compatible decompressor |
|
2 |
+ * |
|
3 |
+ * Copyright (c) 2000 Martin Hinner <mhi@penguin.cz> |
|
4 |
+ * Algorithm & data structures by M. Winterhoff <100326.2776@compuserve.com> |
|
5 |
+ * |
|
6 |
+ * Corrected and adapted to ClamAV by Tomasz Kojm <tkojm@clamav.net> |
|
7 |
+ * |
|
8 |
+ * This program is free software; you can redistribute it and/or modify |
|
9 |
+ * it under the terms of the GNU General Public License as published by |
|
10 |
+ * the Free Software Foundation; either version 2, or (at your option) |
|
11 |
+ * any later version. |
|
12 |
+ * |
|
13 |
+ * This program is distributed in the hope that it will be useful, |
|
14 |
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of |
|
15 |
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
|
16 |
+ * GNU General Public License for more details. |
|
17 |
+ * |
|
18 |
+ * You should have received a copy of the GNU General Public License |
|
19 |
+ * along with this program; if not, write to the Free Software |
|
20 |
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. |
|
21 |
+ */ |
|
22 |
+ |
|
23 |
+#include <stdio.h> |
|
24 |
+#include <stdlib.h> |
|
25 |
+#include <unistd.h> |
|
26 |
+#include <string.h> |
|
27 |
+ |
|
28 |
+#if HAVE_CONFIG_H |
|
29 |
+#include "clamav-config.h" |
|
30 |
+#endif |
|
31 |
+#include "cltypes.h" |
|
32 |
+#include "others.h" |
|
33 |
+ |
|
34 |
+int cli_msexpand(FILE *in, FILE *out) |
|
35 |
+{ |
|
36 |
+ int bits, ch, i, j, len, mask; |
|
37 |
+ unsigned char *buffer; |
|
38 |
+ uint32_t magic1, magic2, magic3, filesize; |
|
39 |
+ uint16_t reserved; |
|
40 |
+ |
|
41 |
+ |
|
42 |
+ if(fread(&magic1, sizeof(magic1), 1, in) != 1) { |
|
43 |
+ return -1; |
|
44 |
+ } |
|
45 |
+ |
|
46 |
+#if WORDS_BIGENDIAN == 1 |
|
47 |
+ if(magic1 == 0x535A4444L) |
|
48 |
+#else |
|
49 |
+ if(magic1 == 0x44445A53L) |
|
50 |
+#endif |
|
51 |
+ { |
|
52 |
+ if(fread(&magic2, sizeof(magic2), 1, in) != 1) { |
|
53 |
+ return -1; |
|
54 |
+ } |
|
55 |
+ |
|
56 |
+ if(fread(&reserved, sizeof(reserved), 1, in) != 1) { |
|
57 |
+ return -1; |
|
58 |
+ } |
|
59 |
+ |
|
60 |
+ if(fread(&filesize, sizeof(filesize), 1, in) != 1) { |
|
61 |
+ return -1; |
|
62 |
+ } |
|
63 |
+ |
|
64 |
+#if WORDS_BIGENDIAN == 1 |
|
65 |
+ if(magic2 != 0x88F02733L) |
|
66 |
+#else |
|
67 |
+ if(magic2 != 0x3327F088L) |
|
68 |
+#endif |
|
69 |
+ { |
|
70 |
+ cli_warnmsg("msexpand: Not a MS-compressed file\n"); |
|
71 |
+ return -1; |
|
72 |
+ } |
|
73 |
+ |
|
74 |
+ } else |
|
75 |
+#if WORDS_BIGENDIAN == 1 |
|
76 |
+ if(magic1 == 0x4B57414AL) |
|
77 |
+#else |
|
78 |
+ if(magic1 == 0x4A41574BL) |
|
79 |
+#endif |
|
80 |
+ { |
|
81 |
+ if(fread(&magic2, sizeof(magic2), 1, in) != 1) { |
|
82 |
+ return -1; |
|
83 |
+ } |
|
84 |
+ |
|
85 |
+ if(fread(&magic3, sizeof(magic3), 1, in) != 1) { |
|
86 |
+ return -1; |
|
87 |
+ } |
|
88 |
+ |
|
89 |
+ if(fread(&reserved, sizeof(reserved), 1, in) != 1) { |
|
90 |
+ return -1; |
|
91 |
+ } |
|
92 |
+ |
|
93 |
+#if WORDS_BIGENDIAN == 1 |
|
94 |
+ if(magic2 != 0x88F027D1L || magic3 != 0x03001200L) |
|
95 |
+#else |
|
96 |
+ if(magic2 != 0xD127F088L || magic3 != 0x00120003L) |
|
97 |
+#endif |
|
98 |
+ { |
|
99 |
+ cli_warnmsg("msexpand: Not a MS-compressed file\n"); |
|
100 |
+ return -1; |
|
101 |
+ } |
|
102 |
+ |
|
103 |
+ cli_warnmsg("msexpand: unsupported version 6.22\n"); |
|
104 |
+ return -1; |
|
105 |
+ |
|
106 |
+ } else { |
|
107 |
+ cli_warnmsg("msexpand: Not a MS-compressed file\n"); |
|
108 |
+ return -1; |
|
109 |
+ } |
|
110 |
+ |
|
111 |
+ if((buffer = (unsigned char *) cli_calloc(4096, sizeof(char))) == NULL) { |
|
112 |
+ cli_errmsg("msexpand: Can't allocate memory\n"); |
|
113 |
+ return -1; |
|
114 |
+ } |
|
115 |
+ |
|
116 |
+ i = 4096 - 16; |
|
117 |
+ |
|
118 |
+ while (1) { |
|
119 |
+ if((bits = fgetc(in)) == EOF) |
|
120 |
+ break; |
|
121 |
+ |
|
122 |
+ for(mask = 0x01; mask & 0xFF; mask <<= 1) { |
|
123 |
+ if(!(bits & mask)) { |
|
124 |
+ if((j = fgetc(in)) == EOF) |
|
125 |
+ break; |
|
126 |
+ len = fgetc(in); |
|
127 |
+ j += (len & 0xF0) << 4; |
|
128 |
+ len = (len & 15) + 3; |
|
129 |
+ while(len--) { |
|
130 |
+ buffer[i] = buffer[j]; |
|
131 |
+ if(fwrite(&buffer[i], sizeof(unsigned char), 1, out) != 1) { |
|
132 |
+ free(buffer); |
|
133 |
+ return -1; |
|
134 |
+ } |
|
135 |
+ j++; |
|
136 |
+ j %= 4096; |
|
137 |
+ i++; |
|
138 |
+ i %= 4096; |
|
139 |
+ } |
|
140 |
+ } else { |
|
141 |
+ if((ch = fgetc(in)) == EOF) |
|
142 |
+ break; |
|
143 |
+ |
|
144 |
+ buffer[i] = ch; |
|
145 |
+ if(fwrite(&buffer[i], sizeof(unsigned char), 1, out) != 1) { |
|
146 |
+ free(buffer); |
|
147 |
+ return -1; |
|
148 |
+ } |
|
149 |
+ i++; |
|
150 |
+ i %= 4096; |
|
151 |
+ } |
|
152 |
+ } |
|
153 |
+ } |
|
154 |
+ |
|
155 |
+ free(buffer); |
|
156 |
+ return 0; |
|
157 |
+} |
0 | 158 |
new file mode 100644 |
... | ... |
@@ -0,0 +1,26 @@ |
0 |
+/* |
|
1 |
+ * Copyright (C) 2004 Tomasz Kojm <tkojm@clamav.net> |
|
2 |
+ * |
|
3 |
+ * This program is free software; you can redistribute it and/or modify |
|
4 |
+ * it under the terms of the GNU General Public License as published by |
|
5 |
+ * the Free Software Foundation; either version 2 of the License, or |
|
6 |
+ * (at your option) any later version. |
|
7 |
+ * |
|
8 |
+ * This program is distributed in the hope that it will be useful, |
|
9 |
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of |
|
10 |
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
|
11 |
+ * GNU General Public License for more details. |
|
12 |
+ * |
|
13 |
+ * You should have received a copy of the GNU General Public License |
|
14 |
+ * along with this program; if not, write to the Free Software |
|
15 |
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. |
|
16 |
+ */ |
|
17 |
+ |
|
18 |
+#ifndef __MSEXPAND_H |
|
19 |
+#define __MSEXPAND_H |
|
20 |
+ |
|
21 |
+#include <stdio.h> |
|
22 |
+ |
|
23 |
+int cli_msexpand(FILE *in, FILE *out); |
|
24 |
+ |
|
25 |
+#endif |
... | ... |
@@ -120,6 +120,8 @@ const char *cl_strerror(int clerror) |
120 | 120 |
return "Malformed Zip detected."; |
121 | 121 |
case CL_EGZIP: |
122 | 122 |
return "GZip module failure."; |
123 |
+ case CL_EMSCOMP: |
|
124 |
+ return "MSExpand module failure."; |
|
123 | 125 |
case CL_EOLE2: |
124 | 126 |
return "OLE2 module failure."; |
125 | 127 |
case CL_ETMPFILE: |
... | ... |
@@ -42,6 +42,7 @@ int cli_scanrar_inuse = 0; |
42 | 42 |
#include "unrarlib.h" |
43 | 43 |
#include "ole2_extract.h" |
44 | 44 |
#include "vba_extract.h" |
45 |
+#include "msexpand.h" |
|
45 | 46 |
#include "scanners.h" |
46 | 47 |
|
47 | 48 |
#ifdef HAVE_ZLIB_H |
... | ... |
@@ -76,6 +77,7 @@ static const struct cli_magic_s cli_magic[] = { |
76 | 76 |
{0, "PK\003\004", 4, "ZIP", CL_ZIPFILE}, |
77 | 77 |
{0, "\037\213", 2, "GZip", CL_GZFILE}, |
78 | 78 |
{0, "BZh", 3, "BZip", CL_BZFILE}, |
79 |
+ {0, "SZDD", 4, "compress.exe'd", CL_MSCFILE}, |
|
79 | 80 |
|
80 | 81 |
/* Mail */ |
81 | 82 |
|
... | ... |
@@ -659,6 +661,48 @@ static int cli_scanbzip(int desc, const char **virname, long int *scanned, const |
659 | 659 |
} |
660 | 660 |
#endif |
661 | 661 |
|
662 |
+static int cli_scanmscomp(int desc, const char **virname, long int *scanned, const struct cl_node *root, const struct cl_limits *limits, int options, int *reclev) |
|
663 |
+{ |
|
664 |
+ int fd, ret = CL_CLEAN; |
|
665 |
+ FILE *tmp = NULL, *in; |
|
666 |
+ |
|
667 |
+ cli_dbgmsg("in cli_scanmscomp()\n"); |
|
668 |
+ |
|
669 |
+ if((in = fdopen(dup(desc), "rb")) == NULL) { |
|
670 |
+ cli_dbgmsg("Can't fdopen() descriptor %d.\n", desc); |
|
671 |
+ return CL_EMSCOMP; |
|
672 |
+ } |
|
673 |
+ |
|
674 |
+ if((tmp = tmpfile()) == NULL) { |
|
675 |
+ cli_dbgmsg("Can't generate tmpfile().\n"); |
|
676 |
+ fclose(in); |
|
677 |
+ return CL_ETMPFILE; |
|
678 |
+ } |
|
679 |
+ |
|
680 |
+ if(cli_msexpand(in, tmp) == -1) { |
|
681 |
+ cli_dbgmsg("msexpand failed.\n"); |
|
682 |
+ return CL_EMSCOMP; |
|
683 |
+ } |
|
684 |
+ |
|
685 |
+ fclose(in); |
|
686 |
+ if(fflush(tmp)) { |
|
687 |
+ cli_dbgmsg("fflush() failed\n"); |
|
688 |
+ fclose(tmp); |
|
689 |
+ return CL_EFSYNC; |
|
690 |
+ } |
|
691 |
+ |
|
692 |
+ fd = fileno(tmp); |
|
693 |
+ lseek(fd, 0, SEEK_SET); |
|
694 |
+ if((ret = cli_magic_scandesc(fd, virname, scanned, root, limits, options, reclev)) == CL_VIRUS) { |
|
695 |
+ cli_dbgmsg("MSCompress -> Found %s virus.\n", *virname); |
|
696 |
+ fclose(tmp); |
|
697 |
+ return CL_VIRUS; |
|
698 |
+ } |
|
699 |
+ |
|
700 |
+ fclose(tmp); |
|
701 |
+ return ret; |
|
702 |
+} |
|
703 |
+ |
|
662 | 704 |
static int cli_scandir(const char *dirname, const char **virname, long int *scanned, const struct cl_node *root, const struct cl_limits *limits, int options, int *reclev) |
663 | 705 |
{ |
664 | 706 |
DIR *dd; |
... | ... |
@@ -927,6 +971,11 @@ static int cli_magic_scandesc(int desc, const char **virname, long int *scanned, |
927 | 927 |
#endif |
928 | 928 |
break; |
929 | 929 |
|
930 |
+ case CL_MSCFILE: |
|
931 |
+ if(SCAN_ARCHIVE) |
|
932 |
+ ret = cli_scanmscomp(desc, virname, scanned, root, limits, options, reclev); |
|
933 |
+ break; |
|
934 |
+ |
|
930 | 935 |
case CL_MAILFILE: |
931 | 936 |
if(SCAN_MAIL) |
932 | 937 |
ret = cli_scanmail(desc, virname, scanned, root, limits, options, reclev); |