I was just reading about how Google Go makes each thread with a reduced stack size by default, and then links to new stacks if an overflow would occur ( see page 16 in here ). I was wondering the best way to do that in C.
I have to say I am no C expert, so there might be a better way to detect a Stack Overflow on C, but giving my ignorance, here's how I thought I would implement it:
The first thing I thought is that every time we have a fresh new stack, we get a stack variable's address, and with that we have roughly the starting stack address. Then we would need to be able to retrieve how much stack space the thread has. This would be possible if the thread isn't the main thread, but I have no idea how we would get this info on C.
Then we would need to check (per function call, it could be) how much of the stack is already used, by retrieving current stack variable address. If we detect a possible stack overflow, we would need to have some way to create a new stack and link to the last one. The only way I thought it could be done in C would be to create a new thread to execute the function we want, and lock the current thread until the function returns its result.
So, would there be a cleaner/better way to implement this?
Stack overflow checking introduces a context switch overhead so its use is only recommended during the development or testing phases. It is likely that the stack will reach its greatest (deepest) value after the RTOS kernel has swapped the task out of the Running state because this is when the stack will contain the task context.
If the stack is full, then it is said to be an Overflow condition. Pop: Removes an item from the stack. The items are popped in the reversed order in which they are pushed. If the stack is empty, then it is said to be an Underflow condition.
In case you wish to attend live classes with experts, please refer DSA Live Classes for Working Professionals and Competitive Programming Live for Students. Push: Adds an item in the stack. If the stack is full, then it is said to be an Overflow condition.
The stack overflow hook function is called if the stack pointer contain a value that is outside of the valid stack range. This method is quick but not guaranteed to catch all stack overflows. Set configCHECK_FOR_STACK_OVERFLOW to 1 to use this method only.
See GCC's split-stack capability. I believe this was originally implemented to support Go. It pretty much works as you suggest.
EDIT: The commentary below discusses another system that does heap-allocation of activation records.
You can do this - I believe modern gcc may even have an option for it - but it greatly increases the cost of function calls and has very little practical benefit. Especially on modern systems with 64-bit addressing, there's plenty of address space for each thread to have its own stack plenty far from every other thread's stack. If you find yourself using more than logarithmic-scale call recursion, something is wrong with your algorithms anyway...
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With