home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Club Amiga de Montreal - CAM
/
CAM_CD_1.iso
/
files
/
160.lha
/
Fragit
/
POSTER
< prev
next >
Wrap
Text File
|
1988-04-27
|
4KB
|
72 lines
Well, all this talk about memory fragmentation got me motivated to write
a little program to deliberately fragment memory. I named it Fragit 8-)
Fragit seems to have uncovered a subtle "window of vunerability" in
Exec's memory management. First, let me describe what Fragit does
exactly.
Fragit allocates random sized blocks of memory, using RangeRand() to
generate psuedo-random size values that range from 24 bytes to 10000 bytes.
Thus, both odd and even fragment sizes are generated, but all sizes are
"legal" from a Kernal viewpoint -- it just rounds them up to the next
8 byte size boundary.
These random sized fragments are linked together into a dynamically
allocated linked-list of Exec style MinNodes. AddHead() is used to insert
a new node (called a FragNode) at the head of the list.
Fragit checks AvailMem(MEMF_PUBLIC) before it allocates a new random
fragment; if the available memory has dropped below the threshold set
(which defaults to 100K), Fragit _randomly_ deallocates one of the nodes
in the MinList of FragNodes. This is done by generating a random number
N such that 0 <= N < 100, then skipping through the FragNode list to the
Nth node in the list. If Fragit hits the end of the list, it merely
wraps around to the head of the list again. The node is then Remove()'ed
from the list and deallocated. Of course, Fragit checks to see if the list
is empty before trying to remove or deallocate a node!
Thus, if AvailMem(MEMF_PUBLIC) is less than the low memory threshold,
Fragit starts deallocating random fragments in the list until there is
enough memory to attempt allocating another fragment. When AvailMem()
shows that there is more system memory than the low memory threshold,
it attempts to allocate and add another fragment to the head of the
list.
The result is a dynamic allocation nightmare: thousands of memory
fragments are being created and destroyed every minute. In a matter
of moments, you can fragment free memory so badly that you can't even
resize a window! The idea was to put stress on the AllocMem()/FreeMem()
parts of an application undergoing debugging by simulating a very busy,
highly fragmented memory environment.
Unfortunately, Fragit seems to have demonstrated even if you have plenty
of RAM and a good sized MEMF_LARGEST, that merely calling AllocMem() can crash
the system with a GURU 3 or 4! This only seems to happen when you
set a fairly high value for the low memory threshold (1meg seems to do it)
combined with a large random allocation size (asking AllocMem() for blocks
that are between 20K and 50K in size.)
I don't think Fragit is at fault -- if I change the code so that
fragmentation never occurs (i.e., always AddHead()/RemHead()), then the
program never fails. Fragit always returns every byte allocated, uses no
special tricks, and is using Exec calls for the list management. Also,
it runs for hours using the default values supplied: 100K low memory threshold,
24 byte lower limit and a 10000 byte upper limit on fragment sizes.
(NOTE: if I run NoFastMem, it WILL crash occasionally with these defaults)
I've reproduced this problem on both my 1-Meg 500 and my 9-Meg 2000 - it
_might_ be the expansion ram, but I sort of doubt it. With the verbose
flag set, I can tell that the program is either croaking on AllocMem() or
soon after that -- no telling where since it is just about impossible
to trace it with a debugger.
I've posted the source code (MANX 3.6a) and the executable in
amiga.dev/listings as "fragit.arc". Please download and try this program
out on other hardware configurations with various parameter settings and
see if you can reproduce this problem! Either my code, Exec, or the hardware
is at fault, and I can't sleep soundly until I know which one is the
culprit. Needless to say, if the problem is in Exec, I'm going to blame
all GURU 3's and 4's generated by my commercial code on Carl. 8-(
Justin V. McCormick