Author Topic: Stack_Mem  (Read 7216 times)

Offline hervé

  • Jr. Member
  • **
  • Posts: 98
    • View Profile
Stack_Mem
« on: October 04, 2010, 03:59:05 PM »
Hello Mark,

I need help with your variables names  :-\.
On LPC23XX.c :
Code: [Select]
        _extern_ unsigned char Stack_Mem;
        #define HEAP_START_ADDRESS  &Stack_Mem                           // Keil - start of stack
.....
        fnInitialiseHeap(ctOurHeap, HEAP_START_ADDRESS);                     // initialise heap
That means that you initialized OUR_HEAP_SIZE locations from Stack_Mem for the µTaskerHeap.


but on LPC23xx_keil.s:
Code: [Select]
        EXPORT  Stack_Mem
        AREA    STACK, NOINIT, READWRITE, ALIGN=3
Stack_Mem       SPACE   USR_Stack_Size
What is the use of this line, which reserved USR_Stack_Size locations from Stack_Mem again.


Offline mark

  • Global Moderator
  • Hero Member
  • *****
  • Posts: 3236
    • View Profile
    • uTasker
Re: Stack_Mem
« Reply #1 on: October 04, 2010, 04:49:37 PM »
Hi Hervé

The original Keil configuration requires the user to define the size of the processor's stack space. The user would set
USR_Stack_Size  EQU     0x00000004
to a value adequate for the purpose.
The linker would then locate this area of RAM from the address following the system variables.

I didn't like this since it means that you need to know how much memory is being used by the system and then set a stack size so that it more or less makes use of the available memory (or just waste memory if inaccurate, or result in an immediate crash if too large...). Therefore I modified the start-up so that the processor simply sets its stack to the top of the available memory. By setting USR_Stack_Size  EQU     0x00000004 the Keil system still creates 4 bytes on memory just after the system variables (I don't think that it accepts 1, but the size is also not really of any significance).

This location's address is Stack_Mem (this can also be found in the map file).

The uTasker heap management simply uses this address to know where the end of the system variables is. It then inserts heap from there up the the size defined by the user (OUR_HEAP_SIZE) and the rest is available for the processor's stack (without having to explicitly define how much).

The Keil initialisation (I don't think that there is source code for this and so one more or less has to accept it so that it all works with the Keil environment) calls a routine __user_initial_stackheap (in the original assembler) which is used to return such address values for the initialisation sequence's internal workings:

__user_initial_stackheap                                                 ; this is called by the Keil initialisation routine

                LDR     R0, =  Heap_Mem                                  ; inform where the heap memory is located
               ;LDR     R1, =(Stack_Mem + USR_Stack_Size)                ; this is used by Keil to set the SP
                LDR     R1, = __stack_und_end__                          ; we don't use a specified stack size but rather leave the SP at its original location
                SUB     R1, R1, #Stack_Sizes                             ; SP below the IRQ stacks
                LDR     R2, = (Heap_Mem + Heap_Size)                     ; we don't generally use library heap but the heap size can be increase if required
                LDR     R3, = Stack_Mem                                  ; this is the location of the last system variable (initialised, followed by bss)
                BX      LR

                END


You can see that I slightly modified this so that it returns a fixed stack pointer value.

Does that explain your question or is there a specific detail that you are interested in?

Regards

Mark

Offline hervé

  • Jr. Member
  • **
  • Posts: 98
    • View Profile
Re: Stack_Mem
« Reply #2 on: October 06, 2010, 07:00:52 AM »
Thanks Mark, you help a lot.