I'm trying to use someone else's software, which has a realloc that fails in it. This is probably due to memory limitations, as it only happens when I use this software on huge datasets.
First question : how to diagnose if it's a soft or hard limitation? I mean, if it's due to my computer's memory limits, or to some limits the compiler / my C implementation imposes?
I'm running Mandriva Linux, 64 bit, with 4Gb RAM and 6GB swap, I don't think I'm reaching those limits.
The same failure happens on our computer cluster, which has about 60Gb of RAM ...
I used the makefile that came with the software, which adds these options to the gcc command :
CFLAGS = -O4 -funroll-loops -fomit-frame-pointer -finline-functions
More questions might follow depending on the answer, but the obvious question is : how to get around this limit ?
Well, you can check that the system isn't artificially imposing a limit on you by running `ulimit -m' which will tell you the maximum number of kB of memory the OS will allocate to you. If that reports anything other than "unlimited" you can increase the limit with `ulimit -m unlimited', but you need to be root to do this.
Other than that, you could always get realloc() to print the size of the memory it failed to move, to make sure you're not trying to move 2 GB of data or something ridiculous.
As an aside, whoever wrote the makefile was trying to be really aggressive with the optimizations. Perhaps they were using bad algorithms to start with, and thought to speed things up by cranking up the compiler optimizations. At any rate, these optimizing switches sometimes do, but sometimes don't, speed up execution time. Only a careful analysis (profiling) can provide the answer. At any rate, GCC offers up to -O3. -O4 is not an option, to my knowledge.
Is the binary you're running a 64- or 32-bit binary?
If it's 64-bit, the use of the "%d" field in that printf() statement leads me to believe the original developer had no clear understanding of the implications of using a 64-bit memory model. That printf() field should be "%ld" for a 64-bit size_t value.
The variable "k" is defined as a "size_t", isn't it?
Assuming the version of GCC is recent enough (And I assume that it is, as "Mandriva" only started shipping in late 2005, I believe), %zu (supported under C99) is also available.