5

The question says it all. Attempting to increase the stack size in the linker options generates the error :

Maximum Stack Size must be an integer between 65536 and 16777216.

Is this 16MB limit a fundamental limitation of the Delphi compiler or is this an arbitrary limit imposed by the IDE? Is there another way to increase this value?

Note (in anticipation of the comments...) :

  • The need for a larger stack is due to enormous static array types used as local variables
  • I understand that the need to do this is symptomatic of terrible design
  • This is a large legacy application whose design and maintenance I am not responsible for.
  • Refactoring to dynamic arrays works, but incurs a 50% performance penalty.
  • Other refactorings are possible - probably weeks of work. This will likely end up as a side-project.
  • In the meantime, functionality is needed now and a larger stack would be an easy fix.
  • Yes, I really, really know this a bad, bad thing to do.
J...
  • 30,968
  • 6
  • 66
  • 143
  • 1
    Have you tried PXXXArray/GetMem approaсh? Is it possible to move largest local arrays (from non-recursive procedures) to global variables (heap) as temporary solution? – MBo Jul 21 '14 at 12:43
  • @MBo Possibly, but there are hundreds of functions involved. To be clear, I'm pretty sure I have a (few) good ideas of how to refactor this to a more sensible design. It's just a question of time and effort. – J... Jul 21 '14 at 12:48

2 Answers2

4

You can increase it as high as 2147483647, using the {$MAXSTACKSIZE} (or {$M minstacksize maxstacksize} compiler directive. Note this is a different use for {$M} than the {$M+/-} used to indicate generation of RTTI for classes.

From the XE6 docwiki (it applied to prior versions as well):

The $M directive specifies an application's stack allocation parameters. minstacksize must be an integer number between 1024 and 2147483647 that specifies the minimum size of an application's stack, and maxstacksize must be an integer number between minstacksize and 2147483647 that specifies the maximum size of an application's stack.

If there is not enough memory available to satisfy an application's minimum stack requirement, Windows will report an error upon attempting to start the application.

Community
  • 1
  • 1
Ken White
  • 123,280
  • 14
  • 225
  • 444
  • Strange - the project linker settings were actually set to the 1MB default and I had this complier directive in a .cfg file that was setting it to 16777216. Increasing it seemed to have no effect which is why I went to the linker config dialog instead. When I scrapped it from the .cfg file and added it to the main .pas file it all worked out. Should have mentioned it in my question. This seems to have worked. Thanks! – J... Jul 21 '14 at 13:36
  • is there a way to know how much of this value is used? – peiman F. Jun 18 '19 at 09:50
  • @peimanF. See : [This answer](https://stackoverflow.com/a/21219845/327083) for a quick and easy check on the committed stack size. – J... Jul 31 '19 at 18:17
2

This is a Delphi IDE limitation. You can specify a larger limit using the $MINSTACKSIZE and $MAXSTACKSIZE directives. It seems strange that the IDE designers decided to stop you doing something from the IDE that you could do from the compiler.

Note that changing the default stack size is risky. This will affect all stacks in your process, even for threads not created by your code. So you might find it more effective to restrict the change just to a specific thread. This can be achieved by passing a stack size as a parameter to CreateThread.

Finally, I am sure that there will be a performant solution that does not involve increasing the stack size.

David Heffernan
  • 601,492
  • 42
  • 1,072
  • 1,490
  • 1
    To edit the PE file after linking, EDITBIN can be used, found an article on this here: http://joeduffyblog.com/2006/07/03/modifying-stack-reserve-and-commit-sizes-on-existing-binaries/ – Lasse V. Karlsen Jul 21 '14 at 12:49
  • 1
    Unfortunately, for legacy reasons, the main thread is often heavily involved in computation in this application so it is affected as well as worker threads. I am also sure that there is a performant solution. The last time I performed such a refactoring on this application, however, it consumed three months of dev time and another three months of debugging. Seventeen years of inexperienced development can make a very, very large mess. – J... Jul 21 '14 at 12:57