With RLIMIT_DATA > 2GB a 32-bit FreeBSD 7.3 allows ~120M memory to be allocated
via mmap before failing.
With RLIMIT_DATA set to 2GB it allows ~890M memory.
So check the RLIMIT_DATA and set it just below 2G.
You can also just do 'ulimit -d 2097151' to get the effects of this patch.
... | ... |
@@ -1,3 +1,7 @@ |
1 |
+Tue Aug 31 15:10:29 EEST 2010 (edwin) |
|
2 |
+------------------------------------- |
|
3 |
+ * clamd/clamd.c: limit RLIMIT_DATA to 2GB on 32-bit processes (bb #1941). |
|
4 |
+ |
|
1 | 5 |
Tue Aug 31 11:13:44 EEST 2010 (edwin) |
2 | 6 |
------------------------------------- |
3 | 7 |
* libclamav/regex/regexec.c: fix regex when sizeof(void*) != sizeof(long) (bb #2232). |
... | ... |
@@ -30,6 +30,7 @@ |
30 | 30 |
#endif |
31 | 31 |
#ifndef _WIN32 |
32 | 32 |
#include <sys/time.h> |
33 |
+#include <sys/resource.h> |
|
33 | 34 |
#endif |
34 | 35 |
#include <sys/types.h> |
35 | 36 |
#include <sys/stat.h> |
... | ... |
@@ -108,6 +109,7 @@ int main(int argc, char **argv) |
108 | 108 |
#ifndef _WIN32 |
109 | 109 |
struct passwd *user = NULL; |
110 | 110 |
struct sigaction sa; |
111 |
+ struct rlimit rlim; |
|
111 | 112 |
#endif |
112 | 113 |
time_t currtime; |
113 | 114 |
const char *dbdir, *cfgfile; |
... | ... |
@@ -295,6 +297,26 @@ int main(int argc, char **argv) |
295 | 295 |
logg("#Running as user %s (UID %u, GID %u)\n", user->pw_name, user->pw_uid, user->pw_gid); |
296 | 296 |
#endif |
297 | 297 |
|
298 |
+#ifdef RLIMIT_DATA |
|
299 |
+ if (getrlimit(RLIMIT_DATA, &rlim) == 0) { |
|
300 |
+ /* bb #1941. |
|
301 |
+ * On 32-bit FreeBSD if you set ulimit -d to >2GB then mmap() will fail |
|
302 |
+ * too soon (after ~120 MB). |
|
303 |
+ * Set limit lower than 2G if on 32-bit */ |
|
304 |
+ uint64_t lim = rlim.rlim_cur; |
|
305 |
+ lim = (int32_t) lim; |
|
306 |
+ if (sizeof(void*) == 4 && |
|
307 |
+ lim != rlim.rlim_cur) { |
|
308 |
+ rlim.rlim_cur = 2048*1024-1; |
|
309 |
+ if (setrlimit(RLIMIT_DATA, &rlim) < 0) |
|
310 |
+ logg("!setrlimit(RLIMIT_DATA) failed: %s\n", strerror(errno)); |
|
311 |
+ else |
|
312 |
+ logg("^Running on 32-bit system, and RLIMIT_DATA > 2GB, lowering to 2GB!\n"); |
|
313 |
+ } |
|
314 |
+ } |
|
315 |
+#endif |
|
316 |
+ |
|
317 |
+ |
|
298 | 318 |
if(logg_size) |
299 | 319 |
logg("#Log file size limited to %d bytes.\n", logg_size); |
300 | 320 |
else |