The MASM Forum Archive 2004 to 2012

General Forums => The Laboratory => Topic started by: zooba on November 19, 2006, 03:48:12 AM

Title: Low Fragmentation Heap is slow
Post by: zooba on November 19, 2006, 03:48:12 AM
I've posted previously (http://www.masm32.com/board/index.php?topic=5710.0) about an apparent memory leak in the LFH, and I've done some benchmarking today that show some interesting numbers:

_              |   1    |   2    |   4    |   8    |   16   |   32   |   64   |
Normal Heap    |    281 |    281 |    281 |    281 |    281 |    290 |    281 |
Low Frag Heap  |   2055 |   2054 |   2054 |   2056 |   1799 |   1569 |   2013 |

_              |  128   |  256   |  512   |  1024  |  2048  |  4096  |  8192  |
Normal Heap    |    281 |    286 |    285 |    540 |    540 |    542 |    542 |
Low Frag Heap  |   1640 |   1445 |   1668 |   1482 |   1696 |   1542 |   1795 |


The first and most obvious thing to notice is that the normal heap is much much quicker than the LFH. For allocations of less than 1024 bytes the normal heap is between 280-290 clocks, while the LFH ranges between 1445-2056. Above 1024 bytes, the normal heap approximately doubles in time sitting around 540 clocks, while the LFH has dropped to the mid 1000's. This is surprising since the LFH is supposed to be optimised for small allocations.

The other interesting point which I haven't included in the test program (though the modifications to test it are minimal) is that with serialisation disabled, the normal heap sits consistently around 370-390 clocks (the LFH won't work without serialisation).

Maybe someone else will find this interesting, not sure. However, I am definitely removing the LFH code from ASM Runtime. Should make for some decent speed improvements I think...

Cheers,

Zooba :U

(Note: LFH timings are only meaningful on Windows XP or later, since previous versions didn't have it. Win2K and earlier will display normal heap timings for both heaps)

[attachment deleted by admin]
Title: Re: Low Fragmentation Heap is slow
Post by: hutch-- on November 19, 2006, 01:34:14 PM
These are interesting numbers. From my own point of view, I would prefer OLE string for very large counts of variable length strings as they are properly designed for it. I know that a number of the conventional memory allocation techniques are faster but OLE manages massive counts of strings with no noticable problems of fragmentation.
Title: Re: Low Fragmentation Heap is slow
Post by: zooba on November 20, 2006, 06:10:58 AM
I've used the OLE string functions before when interfacing with VB and haven't had any problems except that many are exclusively designed for Unicode strings (ie. no directly equivalent ANSI version).

Do you have any suggestions on how I can test for fragmentation issues?

Cheers,

Zooba :U
Title: Re: Low Fragmentation Heap is slow
Post by: hutch-- on November 20, 2006, 11:25:01 AM
Here the two APIs fr byte sized OLE string.

        invoke SysAllocStringByteLen,0,ln
        invoke SysFreeString,strhandle


I have not has the slightest of problems with OLE string and this is after shoving millions of strings into OLE string. I don't know a way of testing fragmentation but you would get some idea by allocationg massive quantities of strings and track the entire system memory.
Title: Re: Low Fragmentation Heap is slow
Post by: zooba on November 20, 2006, 12:25:21 PM
Quote from: hutch-- on November 20, 2006, 11:25:01 AM
Here the two APIs fr byte sized OLE string.

        invoke SysAllocStringByteLen,0,ln
        invoke SysFreeString,strhandle


Yes, I suppose that's enough for simple allocation/deallocation. When I was using it for VB interfacing I often needed to copy a regular string into a BSTR. The SysAllocString function will copy a full string up to the first null terminator while the closest equivalent SysAllocStringByteLen for ANSI strings requires the length to be calculated first.

Quote from: hutch-- on November 20, 2006, 11:25:01 AM
I don't know a way of testing fragmentation but you would get some idea by allocationg massive quantities of strings and track the entire system memory.

A heap (I think) grows in increments of 4KB (or whatever the page size is) and doesn't reduce until you call HeapCompact. A non-growable heap just fails when it can't find space. So presumably allocating heaps of strings will simply take up heaps of memory. Is fragmentation really a big issue (ie. big enough for Microsoft to justify a LFH)? I don't think I've ever noticed the effects before, and I've done quite a lot of stuff using strings on a heap.

Cheers,

Zooba :U
Title: Re: Low Fragmentation Heap is slow
Post by: zooba on December 16, 2006, 02:35:22 AM
Added a new bit to my test program which returns the number of bytes overhead for each allocation:

Quote               |   1    |   2    |   4    |   8    |   16   |   32   |   64   |
Normal Heap    |    273 |    556 |    556 |    556 |    552 |    552 |    551 |
    Overhead   |     15 |     14 |     12 |      8 |      8 |      8 |      8 |
Low Frag Heap  |   2040 |   2042 |   2040 |   2040 |   1756 |   1573 |   1986 |
    Overhead   |     15 |     14 |     12 |      8 |      8 |      8 |      8 |

               |  128   |  256   |  512   |  1024  |  2048  |  4096  |  8192  |
Normal Heap    |    552 |    551 |    547 |    532 |    532 |    521 |    538 |
    Overhead   |      8 |      8 |      8 |      8 |      8 |      8 |      8 |
Low Frag Heap  |   1654 |   1446 |   1683 |   1483 |   1711 |   1546 |   1820 |
    Overhead   |      8 |      8 |      8 |      8 |      8 |      8 |      8 |

It appears the minimum allocation size is 16 bytes with 8 bytes of required overhead. There is no difference between standard heap and LFH, though the HeapWalk function predates the LFH, so it may not compute it properly.

Cheers,

Zooba :U

[attachment deleted by admin]