In article
Post by JerryThanks for the helpful comments.
First,
ulimit -s unlimited
-bash: ulimit: stack size: cannot modify limit: Operation not
permitted but I understand that it works on Linux. And possibly the
reason is the difference in the way that Linux and OS X treat stack
and heap memory. (Don't be confused and think I know what I'm talking
about but I read that somewhere.)
ulimit allows querying the hard limit of stack space
ulimit -Hs
which on OS X reports 65532 = 2^16 -4 kilobytes, about 67 MB. The user
ulimit -s 65532
The default soft limit on OS X is 8192 kB, found by
ulimit -s
So here's me being naive: I would have thought that Ada (or GNAT
specifically) would be smart enough to allocate memory for large
objects such as my long array in a transparent way so that I don't
have to worry about it, thus (in the Ada spirit) making it harder to
screw up. (Like not having to worry about whether arguments to
subprograms are passed by value or by reference--it just happens.)
But it seems that I will have to allocate memory for large objects
using pointers (and thus take the memory from the heap). Is that
right?
I think so. When I ran into this some years ago, I was pleasantly
surprised at how easy it was to change over to heap allocation for my
largest data structure. Under Mac OS 9, such allocations fragmented the
heap, but Mac OS X behaves more reasonably.
The menace listed below allocates megabyte-sized blocks right up to the
limit of wired memory, as shown by top:
-----
with Ada.Text_IO;
procedure Heap_Test is
Megabyte : constant Positive := 1024 * 1024;
type Block is array (0 .. Megabyte - 1) of Character;
type Block_Ptr is access all Block;
BPtr : Block_Ptr;
N : Natural := 1;
begin
Ada.Text_IO.Put_Line("*** Heap test...");
while True loop
BPtr := new Block;
Ada.Text_IO.Put (N'Img);
N := N + 1;
end loop;
Ada.Text_IO.New_Line;
end Heap_Test;
-----
This horror raises STORAGE_ERROR at the `ulimit -s` you showed, but only
when compiled with -fstack-check:
-----
with Ada.Text_IO;
procedure Stack_Test is
Megabyte : constant Positive := 1024 * 1024;
type Block is array (0 .. Megabyte - 1) of Character;
procedure Allocate_Stack (N : Positive) is
Local : Block := (others => Character'Val(0));
begin
Ada.Text_IO.Put (N'Img);
Allocate_Stack(N + 1);
end;
begin
Ada.Text_IO.Put_Line("*** Stack test...");
Allocate_Stack(1);
Ada.Text_IO.New_Line;
end Stack_Test;
-----
For reference, ulimit is a bash built-in, so `man bash` for details:
<http://linux.die.net/man/1/bash>
--
John B. Matthews
trashgod at gmail dot com
<http://sites.google.com/site/drjohnbmatthews>