For people interested in Ruby internals:

Investigating how Ruby allocates memory, I found that it calls malloc() to
allocate very small segments of memory, does it very often, and often
free's the memory just to reallocate it later (with same size).

I have written replacement malloc/realloc/free functions that allocates
blocks of memory (1.5Kb) and uses it as a memory segment pool for equally
sized segments.

This scheme has proven itself to be quite efficient on at least the Intel
CPU. With Linux/Glibc and Solaris/Sun-libc, I can save up to 15% memory
with block allocation. The allocation is a sligtly faster than plain
malloc. I have a 3% speedup with a CPU intensive script and 10% speedup
with a memory intensive application that allocates a lot of small memory
memory segments (E.g., creating a hash with hundreds of thousands of
keys).

However, on a Sparc CPU less memory saved because the CPU requires
alignment to 8 bytes. On Intel, no alignment is required.

The patch for the current ruby CVS (2001/08/21) is here:

http://www.cs.auc.dk/~larsch/ruby/ruby-20010821-bmalloc-0.1-patch

This version is tested on i386-cygwin, i386-linux, i386-solaris2.8, and
sparc-solaris2.8 but the allocation is still faster that plain malloc().

Comments, questions, and suggestions for improvements are welcome!

I should also mention the disadvantages of this scheme. For small scripts,
more memory than with current ruby will be allocated because the allocator
always reserves 1.5Kb for each memory segment size. However, the overhead
is not more that 100Kb in most cases and there is literally no CPU time
overhead.

Also, the memory allocation scheme is non-compacting and does NOT return
memory to the operating system using free(). This may be problem if script
make the interpreter allocate many objects of one size, then frees those
objects and start allocating objects of another size. I should be possible
to write a routine that frees unused blocks, but this is not in the
current implementation, and it's efficiency in freeing memory may be low.
Of course, segments larger than 256 bytes which are not stored in blocks
are freed normally, for example, long strings are freed normally when the
GC reclaims the memory allocated for them.

-- 
Lars Christensen, larsch / cs.auc.dk