This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

EK-TM4C123GXL: My variables are not initialized in RAM?

Part Number: EK-TM4C123GXL
Other Parts Discussed in Thread: SW-TM4C,

Hello, I'm having trouble with something I'm writing in my TM4C123GX Launch Pad. I'm inexperienced with microcontrollers so I'm playing around with it using assembly. My problem is, I tried writing a program with a startup file provided in one of the TivaWare examples (startup_rvmdk.S), and it works fine except for that the variable I initialized (PM5_MASK) is blank. I tried asking this question somewhere else and was told it was the bootloader. Having little experience with microcontrollers, I'm very lost to where to even begin to figure out why my variable is 0 in RAM let alone understand how to use a bootloader. When I debug with the simulator and look at the value that should contain the value of the variable, it's always 0 unless I set it myself. What is the cause of this problem and how can I fix it? Here is my code below. I'm usaing Keil uVision. Thank you in advance!

main.s

	;Include constants I define to main
	INCLUDE my_Constants.s
	;Include variables I define to main
	IMPORT PB5_MASK

	AREA |.text|, CODE, READONLY
	THUMB
	EXPORT __main
	ENTRY
	
	;This  subroutine initializes GPIO
GPIO_Init	PROC
	...
	;write "high" to data register for port F pin 1 to turn on red LED. GPIODATA
	LDR r0, =AHB_PORTB
	LDR r1,[r0,#GPIODATAPB5]
	LDR r2, =PB5_MASK	;get RAM address of PB5 mask (pointer)
	LDR r3,[r2]	;get the value of PB5 mask
	ORR r3, r3, #0xF0
	STR r3,[r2]
	
	ORR r1, r1, r3	;Set PB5 to 'high'
	STR r1,[r0,#GPIODATAPB5]
	;LDR r1,[r0,#GPIODATAPB5]

	...
	BX LR
	
	ENDP
	
	
	;This subroutine initialies SysTick
SysTick_Init	PROC
	...
	ENDP
		
		
	
__main
	
	;call GPIO_Init subroutine and return
	BL GPIO_Init
	
	;call SysTick_Init subroutine and return
	BL SysTick_Init
	
stop 
	B stop	;While(1)
	
	END

my_Constants.s

	AREA My_Constants, CODE, READONLY
	THUMB
		
	;defining addresses here for practice

	;general base addresses
SYS_CONTROL	EQU 0x400FE000
...
	
	;offsets
GPIOHBCTL 	EQU 0x06C
...
	
	END

startup_rvmdk.s


;includes constants I define to startup file
		INCLUDE my_Constants.s
		;Include variables I define to startup file
		IMPORT PB5_MASK

        AREA    STACK, NOINIT, READWRITE, ALIGN=3
StackMem
        SPACE   Stack
__initial_sp

;******************************************************************************
;
; Allocate space for the heap.
;
;******************************************************************************
        AREA    HEAP, NOINIT, READWRITE, ALIGN=3
__heap_base
HeapMem
        SPACE   Heap
__heap_limit

;******************************************************************************
;
; Indicate that the code in this file preserves 8-byte alignment of the stack.
;
;******************************************************************************
        PRESERVE8

;******************************************************************************
;
; Place code into the reset code section.
;
;******************************************************************************
        AREA    RESET, CODE, READONLY
        THUMB

;******************************************************************************
;
; The vector table.
;
;******************************************************************************
        EXPORT  __Vectors
__Vectors
        DCD     StackMem + Stack            ; Top of Stack
        DCD     Reset_Handler               ; Reset Handler
        DCD     NmiSR                       ; NMI Handler
        DCD     FaultISR                    ; Hard Fault Handler
        ...                        ; Reserved
        DCD     IntDefaultHandler           ; The PendSV handler
        DCD     SysTick_Handler           	; The SysTick handler
        ...
;******************************************************************************
;
; This is the code that gets called when the processor first starts execution
; following a reset event.
;
;******************************************************************************
        EXPORT  Reset_Handler
Reset_Handler
        ;
        ; Enable the floating-point unit.  This must be done here to handle the
        ; case where main() uses floating-point and the function prologue saves
        ; floating-point registers (which will fault if floating-point is not
        ; enabled).  Any configuration of the floating-point unit using
        ; DriverLib APIs must be done here prior to the floating-point unit
        ; being enabled.
        ;
        ; Note that this does not use DriverLib since it might not be included
        ; in this project.
        ;
        MOVW    R0, #0xED88
        MOVT    R0, #0xE000
        LDR     R1, [R0]
        ORR     R1, #0x00F00000
        STR     R1, [R0]

        ;
        ; Call the C library enty point that handles startup.  This will copy
        ; the .data section initializers from flash to SRAM and zero fill the
        ; .bss section.
        ;
        IMPORT  __main
        B       __main

...
;I added the SysTick_Handler here. This toggle GPIODATA so the LED blinks
SysTick_Handler	PROC
	
	EXPORT SysTick_Handler
		
	;write "high" to data register for port F pin 1 to turn on red LED. GPIODATA
	LDR r0, =AHB_PORTB
	LDR r1, =PB5_MASK ;Get RAM address of PB5 mask value
	LDR r2,[r1] ;Grab value of PB5 mask
	EOR r2, r2, #0xF0	;Toggle mas to toggle PB5
	STR r2,[r1]	;Store the toggled mask to properly toggle next time
	STR r2,[r0,#GPIODATAPB5]
	;LDR r2,[r0,#GPIODATAPB5]

	;return to __main
	BX LR
	
	ENDP

...
        END

  • Hello Fuahua,

    It's not clear to me what you are trying to do with your application, but any case you should be using the software provided with our TivaWare package.

    TivaWare was written to provide a plethora of API's to allow you to setup TM4C devices and enable applications without needing to worry about all the minor details of how to initialize/configure peripherals. Because we invested so much time into making TivaWare usable for all applications customers face, we do not support assembly level code. Therefore to get support with TM4C devices, we ask that you use TivaWare as your starting point. If you are having challenges with that, we'll be happy to try and help you through them. Also TivaWare has many pre-made examples to get you going quickly which may be useful as well.

    You can download the latest TivaWare version from: www.ti.com/tool/SW-TM4C
  • Thank you for the reply! I understand there are API's available, but I want to learn the hardware and practice assembly. I wrote the program in assembly and it works fine; it toggles an external LED with SysTick. I don't understand why the variable that should be initiated is blank in RAM though. Someone told me it was because I didn't have a bootloader, and I have no knowledge of bootloaders, so I'm very lost. Sorry, I forgot to add in the code for the variable PB5_MASK in my post earlier.

    my_Variable.S:

    	AREA My_Variables, DATA, READWRITE
    	THUMB
    	
    		EXPORT PB5_MASK
    PB5_MASK DCD 240;0x000000F0
    	
    	END

  • Fuahua said:
    When I debug with the simulator and look at the value

    As you "have" the actual hardware (EK-TM4C123GXL) - it is hard to justify your use of (any) simulator.     From past experience - simulation may not prove as "convincing" as your use of - and monitoring - "Real MCU hardware!"     (again - which you have!)     Your scan/search of Keil's site should reveal (multiple, similar) "issues resulting from simulation."

    Now the kind vendor agent has taken "pains" to describe his firm's commitment to - and justification of - the (many) advantages resulting from use of the, "Tried, Tested/Proven and extensive API."     And you (appear) to dismiss that - and press on w/ASM.

    May we ask you to consider the, "Forum needs of "many" - rather than (just) your own?     What would occur if "many/most" here - similarly - demanded "ASM only" analysis & response?     Is it not clear that forum response time would drastically expand - and far fewer posters would be serviced?    That cannot be good - can it?

    You are of course "free" to employ ASM - when/where/as "you see fit."     But such focused & minority-usage support - when a vastly superior "alternative" sits, "At the ready" - borders upon the "unreasonable."

    Nothing prevents your "deep dive" into MCU Registers - and Memory Content - via use of the "working API."     It is noted that you  "want to learn the hardware" - yet your "ASM exclusive method" has not proven itself (especially) "learning effective" - has it?      In contrast - use of the API (vastly tested/proven & extensive) and the ready examples (none w/in ASM) provide a solid (and long) proven method to REALLY, "learn the hardware!"     (and - when and/or if required - to gain fast/effective/detailed support!)

  • Fuahua said:
    I don't understand why the variable that should be initiated is blank in RAM though.

    When booting programs from a flash based microcontroller start-up code running from flash is required to initialise variables in RAM. For programs written in C the run-time library startup code performs this initialisation, as per the comment from the following in your Reset_Handler function which is part of the startup_rvmdk.s file:

            ;
            ; Call the C library enty point that handles startup.  This will copy
            ; the .data section initializers from flash to SRAM and zero fill the
            ; .bss section.
            ;
            IMPORT  __main
            B       __main

    For programs written in assembler the initialisation of variables in RAM needs to be handled explicitly by the program.

  • Thank you for the reply. I'm very new to MCU's. I've taken a class, but we debugged using a simulator, so it didn't occur to me to use the actual hardware. I will do this in the future.

    I was not dismissing the agent. I appreciate his reply, but I want to practice in Assembly. This does not mean I won't use the API. I don't understand what you mean by "Forum needs of "many" ". I assume posters ask questions for themselves and not others. I just did the same. I will keep in mind if I program in assembly, I'm on my own.
  • Thank you for the reply! I see, I didn't understand that part very much to be honest. So I'll have to do the initialization myself. Thank you again.
  • Fuahua said:
    don't understand what you mean by "Forum needs of "many"

    Far & away - "C" proves the greatest resource employed by posters.    ASM & DRM are "down in the noise" - thus the "mass appeal" of such "tightly confined postings" is greatly reduced.     Note too - it requires far more EFFORT & TIME by Vendor Agents - or we outsiders - to painstakingly review each/every line of poster's ASM/DRM code.    Never easy, never fast, never fun!

    Now instead - when posters employ "normal/popular "C" - many can benefit - and the "Speed of Issue's resolution is (normally) so much faster - and greatly eased!    This results in, "MORE POSTER'S BEING ASSISTED - which SATISFIES the Forum needs of "many!"

    As to the post you've verified - employ caution - if you continue in the use of "simulator only" your issue may persist.    Again - as you "Have the Hardware" - best to exercise it...

    Note too that your review of the API will provide substantial insight into MCU Registers, and Control Bits - your learning may be as deep as you wish - ASM proves, "Not the only path to deep understanding..."