@.CHARSET CP1251

@ GNU AS
.syntax unified
.cpu cortex-m3
.thumb

.INCLUDE  "/src/inc/rcc.inc"
.INCLUDE  "/src/inc/gpio.inc"
.INCLUDE  "/src/inc/usart.inc"

.SECTION .asmcode

.global USART1_INIT
USART1_INIT:
                    @ Включим usart1 при помощи bitbanding
                    MOV             R1, 1
                    LDR             R0, = PERIPH_BASE + PERIPH_BB_BASE + ( RCC_BASE + RCC_APB2ENR ) * 32
                    STR             R1, [ R0, RCC_APB2ENR_USART1EN_N * 4 ]

                    @ включим GPIO_A (там находятся пины PA9 (tx)\PA10 (rx) нашего usart1)
@                    LDR             R0, = PERIPH_BASE + PERIPH_BB_BASE + ( RCC_BASE + RCC_APB2ENR ) * 32
                    STR             R1, [ R0, RCC_APB2ENR_IOPAEN_N * 4 ]

                    @ настроим PA9 \ PA10
                    LDR             R0, = GPIOA
                    LDR             R1, [ R0, GPIO_CRH ]
                    @ настройка PA9 на push\pull alternate function
                    LDR             R2, =GPIO_MODE_OUT50 + GPIO_CNF_OUT_AFPP << 2
                    BFI             R1, R2, GPIO_CRH_MODE9_N, 4
                    @ настройка PA10 на push\pull alternate function
                    LDR             R2, =GPIO_MODE_INPUT + GPIO_CNF_INP_PULLUP << 2
                    BFI             R1, R2, GPIO_CRH_MODE10_N, 4
                    STR             R1, [ R0, GPIO_CRH ]
                    @ включим подтяжку PA10
                    MOV             R1, 1 << 10
                    STR             R1, [ R0, GPIO_BSRR ]

                    @ настройка USART1
                    @ включим usart1
                    LDR             R0, = USART1
                    MOV             R1, USART_CR1_UE
                    STR             R1, [ R0, USART_CR1 ]
                    @ установим делитель частоты
                    LDR             R1, = 72000000 / 9600
                    STR             R1, [ R0, USART_BRR ]

                    @ включим и прием и передачу
                    LDR             R1, = USART_CR1_UE + USART_CR1_TE + USART_CR1_RE
                    STR             R1, [ R0, USART_CR1 ]

                    @ сбросим остальные регистры настройки, они после сброса итак нулевые, но если
                    @ раньше перифкрия использовалась - то подстраховываемся принудительным сбросом
                    MOV             R1, 0
                    STR             R1, [ R0, USART_CR2 ]
                    STR             R1, [ R0, USART_CR3 ]

                    BX              LR


.GLOBAL USART1_RX_WAIT
USART1_RX_WAIT:     @ ожидаем получения байта по usart1
                    PUSH            { R0, R1 }

                    LDR             R0, = USART1
usart_rxne:
                    LDR             R1, [ R0, USART_SR ]
                    TST             R1, USART_SR_RXNE
                    BEQ             usart_rxne
usart_exit:
                    POP             { R0, R1 }
                    BX              LR


.GLOBAL USART1_TX_WAIT
USART1_TX_WAIT:     @ ожидаем отправки байта по usart1
                    @ (ожидания передачи данных в аппаратный сдвиг-регистр)
                    PUSH            { R0, R1 }

usart_txe:          @ ожидаем отправки предыдущего байта по usart1
                    LDR             R1, [ R0, USART_SR ]
                    TST             R1, USART_SR_TXE
                    BEQ             usart_txe

                    B               usart_exit

