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.

Stellaris launchpad LM4F120 - initialize UART in assembly

Hi there,

 

I'm pretty new to the world of ARM microprocessors ,having recently started with the Stellaris launchpad LM4F120. I wish to send data from the microcontroller over a serial interface to be read with a terminal program such as Putty.

The trouble is, I have not been able to find any resources on the internet that would help me initialize and use UART in the assembly language.

I'm using Keil on Windows7.

Any help in the form of links to simple tutorials or example code snippets would be greatly appreciated.

 

Thanks.

  • What is the reason you desire assembly language?

    You are correct that there are not examples in assembly language.  All of the examples utilize C code for the source input description format used by the code generation tools to generate the desired application firmware.

  • Thank you for the swift response.

    I need to read the uninitialized start-up values of the memory and send it to the computer via the UART interface.

    At this stage, the code has to be in the start-up file, in assembly.

    I was hoping to find at least some technical documentation on the subject.

    -Ali

  • Hi,

    You can use the file bl_startup_rvmdk.S from boot_loader folder - it is a very nice example written in asm; use it with care since has some other purpose. For UART initialization, you can use a separate file in C and link with this startup - call that function from there. It must work.

    Petrei

  • ###############################################################################
    #                                                                             #
    #     IAR Assembler V6.40.1.53790/W32 for ARM 09/Feb/2013  08:26:36           #
    #     Copyright 1999-2012 IAR Systems AB.                                     #
    #                                                                             #
    #           Source file   =  C:\MyWork\Uart_Echo.s                            #
    #           List file     =  C:\MyWork\Debug\List\Uart_Echo.lst               #
    #           Object file   =  C:\MyWork\Debug\Obj\Uart_Echo.o                  #
    #           Command line  =  C:\MyWork\Uart_Echo.s -OC:\MyWork\Debug\Obj\     #
    #                            -s+ -M<> -w+ -r -LC:\MyWork\Debug\List\ -t8      #
    #                            --cpu Cortex-M4F --fpu VFPv4_sp                  #
    #                                                                             #
    ###############################################################################

        1                                   PUBLIC  __iar_program_start
        2                                   SECTION .intvec : CODE
        3                                   DATA
        4    00000000 00800020              DC32    0x20008000
        5    00000004 ........              DC32    __iar_program_start
        6                                   CODE
        7                           __iar_program_start:
        8    00000008 1448                  LDR     R0, uart0
        9    0000000A 154C                  LDR     R4, rom
       10    0000000C 256B                  LDR     R5, [R4, #0x30]
       11    0000000E AE69                  LDR     R6, [R5, #0x18]
       12    00000010 B047                  BLX     R6              ;Enable
                                                                     uart0
       13    00000012 1448                  LDR     R0, gpioA
       14    00000014 B047                  BLX     R6              ;Enable
                                                                     gpioA
       15    00000016 4FF04020              MOV.W   R0, #0x40004000 ;baseA
       16    0000001A 0321                  MOVS    R1, #0x03       ;bit1
                                                                     +bit0
       17    0000001C E668                  LDR     R6, [R4, #0x0C]
       18    0000001E 766D                  LDR     R6, [R6, #0x54]
       19    00000020 B047                  BLX     R6              ;pin type
       20    00000022 2E6E                  LDR     R6, [R5, #0x60]
       21    00000024 B047                  BLX     R6              ;get clock
                                                                     frequency
       22    00000026 0146                  MOV     R1, R0
       23    00000028 1048                  LDR     R0, uart0D
       24    0000002A 4FF4E132              MOV     R2, #115200
       25    0000002E 4FF06003              MOV     R3, #0x60
       26    00000032 2568                  LDR     R5, [R4]
       27    00000034 0446                  MOV     R4, R0
       28    00000036 6E69                  LDR     R6, [R5, #0x14]
       29    00000038 B047                  BLX     R6              ;115200,
                                                                     8N1
       30    0000003A AE6B                  LDR     R6, [R5, #0x38]
       31    0000003C 2D68                  LDR     R5, [R5]
       32    0000003E B047          main:   BLX     R6              ;wait for
                                                                     RXD
       33    00000040 0D28                  CMP     R0, #0x0D       ;<CR>?
       34    00000042 03D0                  BEQ     gotCR
       35    00000044 C1B2                  UXTB    R1, R0
       36    00000046 2046                  MOV     R0, R4
       37    00000048 A847                  BLX     R5              ;send to
                                                                     TXD
       38    0000004A F8E7                  B       main
       39    0000004C 7027          gotCR:  MOVS    R7, #0x70       ;the snake
       40    0000004E 3978          next:   LDRB    R1, [R7]
       41    00000050 0137                  ADDS    R7, #1
       42    00000052 0029                  CMP     R1, #0
       43    00000054 F3D0                  BEQ     main
       44    00000056 2046                  MOV     R0, R4
       45    00000058 A847                  BLX     R5
       46    0000005A F8E7                  B       next
       47                                   DATA
       48    0000005C 01000010      uart0:  DC32    0x10000001
       49    00000060 14000001      rom:    DC32    0x01000014
       50    00000064 01000020      gpioA:  DC32    0x20000001
       51    00000068 2C450040      pctlA:  DC32    0x4000452C
       52    0000006C 00C00040      uart0D: DC32    0x4000C000
       53    00000070 0D0A4D7920736 snake:  DC8     "\r\nMy snake is mightier than
                                                     yours. Mine has legs!\r\n"
                      E616B65206973
                      206D696768746
                      9657220746861
                      6E20796F75727
                      32E204D696E65
                      20686173206C6
                      56773210D0A00
       54                                   END
    ##############################
    #           CRC:0            #
    #        Errors:   0         #
    #        Warnings: 0         #
    #         Bytes: 164         #
    ##############################

  • Thank you for your trouble.

    I need to enter the code in the startup file, so can you tell me which sections I can omit and which specific location I should insert it?

    Many thanks!

    This is the startup file:

    ; <<< Use Configuration Wizard in Context Menu >>>
    ;******************************************************************************
    ;
    ; startup_rvmdk.S - Startup code for use with Keil's uVision.
    ;
    ; Copyright (c) 2012 Texas Instruments Incorporated.  All rights reserved.
    ; Software License Agreement
    ;
    ; Texas Instruments (TI) is supplying this software for use solely and
    ; exclusively on TI's microcontroller products. The software is owned by
    ; TI and/or its suppliers, and is protected under applicable copyright
    ; laws. You may not combine this software with "viral" open-source
    ; software in order to form a larger program.
    ;
    ; THIS SOFTWARE IS PROVIDED "AS IS" AND WITH ALL FAULTS.
    ; NO WARRANTIES, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING, BUT
    ; NOT LIMITED TO, IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
    ; A PARTICULAR PURPOSE APPLY TO THIS SOFTWARE. TI SHALL NOT, UNDER ANY
    ; CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL, OR CONSEQUENTIAL
    ; DAMAGES, FOR ANY REASON WHATSOEVER.
    ;
    ; This is part of revision 9453 of the EK-LM4F120XL Firmware Package.
    ;
    ;******************************************************************************

    ;******************************************************************************
    ;
    ; <o> Stack Size (in Bytes) <0x0-0xFFFFFFFF:8>
    ;
    ;******************************************************************************
    Stack   EQU     0x00000100

    ;******************************************************************************
    ;
    ; <o> Heap Size (in Bytes) <0x0-0xFFFFFFFF:8>
    ;
    ;******************************************************************************
    Heap    EQU     0x00000000

    ;******************************************************************************
    ;
    ; Allocate space for the stack.
    ;
    ;******************************************************************************
            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
            DCD     IntDefaultHandler           ; The MPU fault handler
            DCD     IntDefaultHandler           ; The bus fault handler
            DCD     IntDefaultHandler           ; The usage fault handler
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     IntDefaultHandler           ; SVCall handler
            DCD     IntDefaultHandler           ; Debug monitor handler
            DCD     0                           ; Reserved
            DCD     IntDefaultHandler           ; The PendSV handler
            DCD     IntDefaultHandler           ; The SysTick handler
            DCD     IntDefaultHandler           ; GPIO Port A
            DCD     IntDefaultHandler           ; GPIO Port B
            DCD     IntDefaultHandler           ; GPIO Port C
            DCD     IntDefaultHandler           ; GPIO Port D
            DCD     IntDefaultHandler           ; GPIO Port E
            DCD     IntDefaultHandler           ; UART0 Rx and Tx
            DCD     IntDefaultHandler           ; UART1 Rx and Tx
            DCD     IntDefaultHandler           ; SSI0 Rx and Tx
            DCD     IntDefaultHandler           ; I2C0 Master and Slave
            DCD     IntDefaultHandler           ; PWM Fault
            DCD     IntDefaultHandler           ; PWM Generator 0
            DCD     IntDefaultHandler           ; PWM Generator 1
            DCD     IntDefaultHandler           ; PWM Generator 2
            DCD     IntDefaultHandler           ; Quadrature Encoder 0
            DCD     IntDefaultHandler           ; ADC Sequence 0
            DCD     IntDefaultHandler           ; ADC Sequence 1
            DCD     IntDefaultHandler           ; ADC Sequence 2
            DCD     IntDefaultHandler           ; ADC Sequence 3
            DCD     IntDefaultHandler           ; Watchdog timer
            DCD     IntDefaultHandler           ; Timer 0 subtimer A
            DCD     IntDefaultHandler           ; Timer 0 subtimer B
            DCD     IntDefaultHandler           ; Timer 1 subtimer A
            DCD     IntDefaultHandler           ; Timer 1 subtimer B
            DCD     IntDefaultHandler           ; Timer 2 subtimer A
            DCD     IntDefaultHandler           ; Timer 2 subtimer B
            DCD     IntDefaultHandler           ; Analog Comparator 0
            DCD     IntDefaultHandler           ; Analog Comparator 1
            DCD     IntDefaultHandler           ; Analog Comparator 2
            DCD     IntDefaultHandler           ; System Control (PLL, OSC, BO)
            DCD     IntDefaultHandler           ; FLASH Control
            DCD     IntDefaultHandler           ; GPIO Port F
            DCD     IntDefaultHandler           ; GPIO Port G
            DCD     IntDefaultHandler           ; GPIO Port H
            DCD     IntDefaultHandler           ; UART2 Rx and Tx
            DCD     IntDefaultHandler           ; SSI1 Rx and Tx
            DCD     IntDefaultHandler           ; Timer 3 subtimer A
            DCD     IntDefaultHandler           ; Timer 3 subtimer B
            DCD     IntDefaultHandler           ; I2C1 Master and Slave
            DCD     IntDefaultHandler           ; Quadrature Encoder 1
            DCD     IntDefaultHandler           ; CAN0
            DCD     IntDefaultHandler           ; CAN1
            DCD     IntDefaultHandler           ; CAN2
            DCD     IntDefaultHandler           ; Ethernet
            DCD     IntDefaultHandler           ; Hibernate
            DCD     IntDefaultHandler           ; USB0
            DCD     IntDefaultHandler           ; PWM Generator 3
            DCD     IntDefaultHandler           ; uDMA Software Transfer
            DCD     IntDefaultHandler           ; uDMA Error
            DCD     IntDefaultHandler           ; ADC1 Sequence 0
            DCD     IntDefaultHandler           ; ADC1 Sequence 1
            DCD     IntDefaultHandler           ; ADC1 Sequence 2
            DCD     IntDefaultHandler           ; ADC1 Sequence 3
            DCD     IntDefaultHandler           ; I2S0
            DCD     IntDefaultHandler           ; External Bus Interface 0
            DCD     IntDefaultHandler           ; GPIO Port J
            DCD     IntDefaultHandler           ; GPIO Port K
            DCD     IntDefaultHandler           ; GPIO Port L
            DCD     IntDefaultHandler           ; SSI2 Rx and Tx
            DCD     IntDefaultHandler           ; SSI3 Rx and Tx
            DCD     IntDefaultHandler           ; UART3 Rx and Tx
            DCD     IntDefaultHandler           ; UART4 Rx and Tx
            DCD     IntDefaultHandler           ; UART5 Rx and Tx
            DCD     IntDefaultHandler           ; UART6 Rx and Tx
            DCD     IntDefaultHandler           ; UART7 Rx and Tx
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     IntDefaultHandler           ; I2C2 Master and Slave
            DCD     IntDefaultHandler           ; I2C3 Master and Slave
            DCD     IntDefaultHandler           ; Timer 4 subtimer A
            DCD     IntDefaultHandler           ; Timer 4 subtimer B
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     0                           ; Reserved
            DCD     IntDefaultHandler           ; Timer 5 subtimer A
            DCD     IntDefaultHandler           ; Timer 5 subtimer B
            DCD     IntDefaultHandler           ; Wide Timer 0 subtimer A
            DCD     IntDefaultHandler           ; Wide Timer 0 subtimer B
            DCD     IntDefaultHandler           ; Wide Timer 1 subtimer A
            DCD     IntDefaultHandler           ; Wide Timer 1 subtimer B
            DCD     IntDefaultHandler           ; Wide Timer 2 subtimer A
            DCD     IntDefaultHandler           ; Wide Timer 2 subtimer B
            DCD     IntDefaultHandler           ; Wide Timer 3 subtimer A
            DCD     IntDefaultHandler           ; Wide Timer 3 subtimer B
            DCD     IntDefaultHandler           ; Wide Timer 4 subtimer A
            DCD     IntDefaultHandler           ; Wide Timer 4 subtimer B
            DCD     IntDefaultHandler           ; Wide Timer 5 subtimer A
            DCD     IntDefaultHandler           ; Wide Timer 5 subtimer B
            DCD     IntDefaultHandler           ; FPU
            DCD     IntDefaultHandler           ; PECI 0
            DCD     IntDefaultHandler           ; LPC 0
            DCD     IntDefaultHandler           ; I2C4 Master and Slave
            DCD     IntDefaultHandler           ; I2C5 Master and Slave
            DCD     IntDefaultHandler           ; GPIO Port M
            DCD     IntDefaultHandler           ; GPIO Port N
            DCD     IntDefaultHandler           ; Quadrature Encoder 2
            DCD     IntDefaultHandler           ; Fan 0
            DCD     0                           ; Reserved
            DCD     IntDefaultHandler           ; GPIO Port P (Summary or P0)
            DCD     IntDefaultHandler           ; GPIO Port P1
            DCD     IntDefaultHandler           ; GPIO Port P2
            DCD     IntDefaultHandler           ; GPIO Port P3
            DCD     IntDefaultHandler           ; GPIO Port P4
            DCD     IntDefaultHandler           ; GPIO Port P5
            DCD     IntDefaultHandler           ; GPIO Port P6
            DCD     IntDefaultHandler           ; GPIO Port P7
            DCD     IntDefaultHandler           ; GPIO Port Q (Summary or Q0)
            DCD     IntDefaultHandler           ; GPIO Port Q1
            DCD     IntDefaultHandler           ; GPIO Port Q2
            DCD     IntDefaultHandler           ; GPIO Port Q3
            DCD     IntDefaultHandler           ; GPIO Port Q4
            DCD     IntDefaultHandler           ; GPIO Port Q5
            DCD     IntDefaultHandler           ; GPIO Port Q6
            DCD     IntDefaultHandler           ; GPIO Port Q7
            DCD     IntDefaultHandler           ; GPIO Port R
            DCD     IntDefaultHandler           ; GPIO Port S
            DCD     IntDefaultHandler           ; PWM 1 Generator 0
            DCD     IntDefaultHandler           ; PWM 1 Generator 1
            DCD     IntDefaultHandler           ; PWM 1 Generator 2
            DCD     IntDefaultHandler           ; PWM 1 Generator 3
            DCD     IntDefaultHandler           ; PWM 1 Fault

    ;******************************************************************************
    ;
    ; 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

    ;******************************************************************************
    ;
    ; This is the code that gets called when the processor receives a NMI.  This
    ; simply enters an infinite loop, preserving the system state for examination
    ; by a debugger.
    ;
    ;******************************************************************************
    NmiSR
            B       NmiSR

    ;******************************************************************************
    ;
    ; This is the code that gets called when the processor receives a fault
    ; interrupt.  This simply enters an infinite loop, preserving the system state
    ; for examination by a debugger.
    ;
    ;******************************************************************************
    FaultISR
            B       FaultISR

    ;******************************************************************************
    ;
    ; This is the code that gets called when the processor receives an unexpected
    ; interrupt.  This simply enters an infinite loop, preserving the system state
    ; for examination by a debugger.
    ;
    ;******************************************************************************
    IntDefaultHandler
            B       IntDefaultHandler

    ;******************************************************************************
    ;
    ; Make sure the end of this section is aligned.
    ;
    ;******************************************************************************
            ALIGN

    ;******************************************************************************
    ;
    ; Some code in the normal code section for initializing the heap and stack.
    ;
    ;******************************************************************************
            AREA    |.text|, CODE, READONLY

    ;******************************************************************************
    ;
    ; The function expected of the C library startup code for defining the stack
    ; and heap memory locations.  For the C library version of the startup code,
    ; provide this function so that the C library initialization code can find out
    ; the location of the stack and heap.
    ;
    ;******************************************************************************
        IF :DEF: __MICROLIB
            EXPORT  __initial_sp
            EXPORT  __heap_base
            EXPORT  __heap_limit
        ELSE
            IMPORT  __use_two_region_memory
            EXPORT  __user_initial_stackheap
    __user_initial_stackheap
            LDR     R0, =HeapMem
            LDR     R1, =(StackMem + Stack)
            LDR     R2, =(HeapMem + Heap)
            LDR     R3, =StackMem
            BX      LR
        ENDIF

    ;******************************************************************************
    ;
    ; Make sure the end of this section is aligned.
    ;
    ;******************************************************************************
            ALIGN

    ;******************************************************************************
    ;
    ; Tell the assembler that we're done.
    ;
    ;******************************************************************************
            END

  • Sorry, I do not know anything about Keil. And I do not know much about IAR either. I read about the chip and understood that:

    For this chip, (a) there are 256 KB of Flash at 0x00000000-0x0003FFFF, (b) there are 32 KB of RAM at 0x20000000-0x20007FFF, (c) there are 32 KB of ROM at 0x01000000-0x01007FFF, and (d) peripheries are mapped into other address ranges.

    I also understood that after power up or reset, (a) the contents stored in memory locations 0x00000000-0x00000003 will be loaded into the Stack Pointer, (b) the contents stored in memory locations 0x00000004-0x00000007 will be loaded into the Program Counter, and (c) CPU will start to execute the machine code pointed by the Program Counter.

    Hence, with my limited knowledge of IAR, I tried to make it to do the following:
    (a) Load the top of RAM address (i.e., 0x20008000) to Flash location 0x00000000 so that my code could use all the RAM as stack.
    (b) Load the address where my code starts (i.e., 0x00000008 with the symbolic name iar_program_start) to Flash location 0x00000004 so that the CPU will start to execute that code.
    (c) Load the machine code of what I wanted the CPU to execute starting at Flash location 0x00000008.

    It seems that I managed to do that with IAR. The resulting Assembly Listing is shown in my last posting. Where the first column is the line number of my source code (not very meaningful). The second column is the address in hex presentation that the Assembler assigned to. The third column is the contents in hex presentation. The forth column and beyond are my original source code.

    It sets up the UART0 for 115200, N, 8, 1 for full duplex operation. It then waits for RXD and echoes that back to TXD. Furthermore, if the incoming RXD is a <CR>, it sends a null terminated string about snakes (a Chinese allegory). The entire thing takes only 164 bytes.

    Using Keil, I think you should be able to do something similar. But what you have shown seems to be the start-up code for c-program. It is totally irrelevant in my opinion.

  • Hi old_cow_yellow,

    I really appreciate you were sharing your ASM code. I am rather new to ARM MCUs and especially ASM, so please excuse any foolish questions.

    I was able to port it to CCS 5.1. However, I wondered whether I could change your code to use UART1 + GPIOB. I see that you are working with ROM functions most of the time. Thus, I was reading the Stellaris ROM User's Guide. However, while exploring the code several questions came up:

    1. uart0:  DC32    0x10000001   I dont know to what this is pointing to. I thought the ROM_UARTTABLE, but this would be 0x01000011, wouldnt it?

    2: rom:    DC32    0x01000014  This is the pointer to the ROM_GPIOTABLE, right?

    3: gpioA:  DC32    0x20000001 I couldnt find the semantics for this value as well. However, I know I have to configure GPIOB for using UART1, so should this value be changed to 0x20000002?

    4: LDR R5, [R4, #0x30]

        LDR R6, [R5, #0x18]   I am not sure about these lines. I was checking the ROM table and the first one could correspond to ROM_USBIntDisableControl. If so, when using UART1, this should be changed to ROM_UARTIntDisable?

    5. MOV.W   R0, #0x40004000  This corresponds to GPIO_PORTA_DATA_BITS_R, so I was changing the value to 0x40005000. However, the ASM compiler complains. Thats why I defined a constant:

    GPIOB_D EQU 0x40005000 and replaced the line above with: LDR R0, =GPIOB_D

    I more or less understand the semantics of the rest of the code. To use UART1 I also changed the following constants:

    PCTLA    EQU 0x4000552C             ; GPIO_PORTB_PCTL_R
    UART1D EQU  0x4000D000            ; UART1_DR_R

    However, while debugging the code, always the HardFault handler gets called after line 14 (see below for my modified code; only UART init is shown).

    It would be awesome to get some tips on how to proceed, so I get a better understanding on how to interact with the board using ASM.

            LDR     R0, =UART0
            LDR     R4, =ROM
            LDR     R5, [R4, #0x30]		;ROM_USBIntDisableControl?
            LDR     R6, [R5, #0x18]
            BLX     R6              	;Enable uart0
            LDR     R0, =GPIOA
            BLX     R6              	;Enable gpioA
            ;MOV.W   R0, #0x40004000 	;baseB				; GPIO_PORTB_DATA_BITS_R
            LDR		R0, =GPIO_PORTB_DATA_BITS_R
    		MOVS    R1, #0x03       	;bit1 +bit0
            LDR     R6, [R4, #0x0C]
            LDR     R6, [R6, #0x54]
            BLX     R6              	;pin type
            LDR     R6, [R5, #0x60]
            BLX     R6              	;get clock frequency
            MOV     R1, R0
            LDR     R0, =UART1D
            MOV     R2, #115200
            MOV     R3, #0x60
            LDR     R5, [R4]
            MOV     R4, R0
            LDR     R6, [R5, #0x14]
            BLX     R6              	;115200, 8N1
            LDR     R6, [R5, #0x38]
            LDR     R5, [R5]