diff options
| author | bernard.xiong <[email protected]> | 2009-07-02 22:48:23 +0000 |
|---|---|---|
| committer | bernard.xiong <[email protected]> | 2009-07-02 22:48:23 +0000 |
| commit | bda4730a9482c23083006abea939ee8d95d6ecff (patch) | |
| tree | 83005121824bd50ac74e63688c0d5eac148665f8 /libcpu/arm | |
| parent | 80c72e66de0b00b1a6de3e3508366a4c3eee458d (diff) | |
import RT-Thread RTOS 0.3.x to Google SVN
git-svn-id: https://rt-thread.googlecode.com/svn/trunk@2 bbd45198-f89e-11dd-88c7-29a3b14d5316
Diffstat (limited to 'libcpu/arm')
| -rw-r--r-- | libcpu/arm/stm32/context_iar.S | 170 | ||||
| -rw-r--r-- | libcpu/arm/stm32/context_rvds.S | 189 | ||||
| -rw-r--r-- | libcpu/arm/stm32/cpu.c | 42 | ||||
| -rw-r--r-- | libcpu/arm/stm32/fault.c | 34 | ||||
| -rw-r--r-- | libcpu/arm/stm32/fault_rvds.S | 31 | ||||
| -rw-r--r-- | libcpu/arm/stm32/interrupt.c | 25 | ||||
| -rw-r--r-- | libcpu/arm/stm32/serial.c | 586 | ||||
| -rw-r--r-- | libcpu/arm/stm32/serial.h | 69 | ||||
| -rw-r--r-- | libcpu/arm/stm32/stack.c | 59 | ||||
| -rw-r--r-- | libcpu/arm/stm32/start_iar.c | 176 | ||||
| -rw-r--r-- | libcpu/arm/stm32/start_rvds.s | 250 |
11 files changed, 1631 insertions, 0 deletions
diff --git a/libcpu/arm/stm32/context_iar.S b/libcpu/arm/stm32/context_iar.S new file mode 100644 index 0000000000..d20cdf9dd4 --- /dev/null +++ b/libcpu/arm/stm32/context_iar.S @@ -0,0 +1,170 @@ +;/* +; * File : context.S +; * This file is part of RT-Thread RTOS +; * COPYRIGHT (C) 2006, RT-Thread Development Team +; * +; * The license and distribution terms for this file may be +; * found in the file LICENSE in this distribution or at +; * http://www.rt-thread.org/license/LICENSE +; * +; * Change Logs: +; * Date Author Notes +; * 2009-01-17 Bernard first version +; */ + +;/** +; * @addtogroup STM32 +; */ +;/*@{*/ + +NVIC_INT_CTRL EQU 0xE000ED04 ; interrupt control state register +NVIC_SYSPRI2 EQU 0xE000ED20 ; system priority register (2) +NVIC_PENDSV_PRI EQU 0x00FF0000 ; PendSV priority value (lowest) +NVIC_PENDSVSET EQU 0x10000000 ; value to trigger PendSV exception + + SECTION .text:CODE(2) + THUMB + REQUIRE8 + PRESERVE8 + + IMPORT rt_thread_switch_interrput_flag + IMPORT rt_interrupt_from_thread + IMPORT rt_interrupt_to_thread + +;/* +; * rt_base_t rt_hw_interrupt_disable(); +; */ + EXPORT rt_hw_interrupt_disable +rt_hw_interrupt_disable: + MRS r0, PRIMASK + CPSID I + BX LR + +;/* +; * void rt_hw_interrupt_enable(rt_base_t level); +; */ + EXPORT rt_hw_interrupt_enable +rt_hw_interrupt_enable: + MSR PRIMASK, r0 + BX LR + +;/* +; * void rt_hw_context_switch(rt_uint32 from, rt_uint32 to); +; * r0 --> from +; * r1 --> to +; */ + EXPORT rt_hw_context_switch +rt_hw_context_switch: + LDR r2, =rt_interrupt_from_thread + STR r0, [r2] + + LDR r2, =rt_interrupt_to_thread + STR r1, [r2] + + LDR r0, =NVIC_INT_CTRL ; trigger the PendSV exception (causes context switch) + LDR r1, =NVIC_PENDSVSET + STR r1, [r0] + CPSIE I ; enable interrupts at processor level + BX LR + +; r0 --> swith from thread stack +; r1 --> swith to thread stack +; psr, pc, lr, r12, r3, r2, r1, r0 are pushed into [from] stack + EXPORT rt_hw_pend_sv +rt_hw_pend_sv: + LDR r0, =rt_interrupt_from_thread + LDR r1, [r0] + CBZ r1, swtich_to_thread ; skip register save at the first time + + MRS r1, psp ; get from thread stack pointer + STMFD r1!, {r4 - r11} ; push r4 - r11 register + LDR r0, [r0] + STR r1, [r0] ; update from thread stack pointer + +swtich_to_thread + LDR r1, =rt_interrupt_to_thread + LDR r1, [r1] + LDR r1, [r1] ; load thread stack pointer + + LDMFD r1!, {r4 - r11} ; pop r4 - r11 register + MSR psp, r1 ; update stack pointer + + ORR lr, lr, #0x04 + BX lr + +;/* +; * void rt_hw_context_switch_to(rt_uint32 to); +; * r0 --> to +; */ + EXPORT rt_hw_context_switch_to +rt_hw_context_switch_to: + LDR r1, =rt_interrupt_to_thread + STR r0, [r1] + + ; set from thread to 0 + LDR r1, =rt_interrupt_from_thread + MOV r0, #0x0 + STR r0, [r1] + + ; set the PendSV exception priority + LDR r0, =NVIC_SYSPRI2 + LDR r1, =NVIC_PENDSV_PRI + STR r1, [r0] + + LDR r0, =NVIC_INT_CTRL ; trigger the PendSV exception (causes context switch) + LDR r1, =NVIC_PENDSVSET + STR r1, [r0] + + CPSIE I ; enable interrupts at processor level + + ; never reach here! + +;/* +; * void rt_hw_context_switch_interrupt(rt_uint32 from, rt_uint32 to) +; * { +; * if (rt_thread_switch_interrput_flag == 1) +; * { +; * rt_interrupt_to_thread = to; +; * } +; * else +; * { +; * rt_thread_switch_interrput_flag = 1; +; * rt_interrupt_from_thread = from; +; * rt_interrupt_to_thread = to; +; * } +; * } +; */ + EXPORT rt_hw_context_switch_interrupt +rt_hw_context_switch_interrupt: + LDR r2, =rt_thread_switch_interrput_flag + LDR r3, [r2] + CMP r3, #1 + BEQ _reswitch + MOV r3, #1 ; set rt_thread_switch_interrput_flag to 1 + STR r3, [r2] + LDR r2, =rt_interrupt_from_thread ; set rt_interrupt_from_thread + STR r0, [r2] +_reswitch: + LDR r2, =rt_interrupt_to_thread ; set rt_interrupt_to_thread + STR r1, [r2] + BX lr + + EXPORT rt_hw_interrupt_thread_switch +rt_hw_interrupt_thread_switch: + LDR r0, =rt_thread_switch_interrput_flag + LDR r1, [r0] + CBZ r1, _no_switch + + ; clear rt_thread_switch_interrput_flag to 0 + MOV r1, #0x00 + STR r1, [r0] + + ; trigger context switch + LDR r0, =NVIC_INT_CTRL ; trigger the PendSV exception (causes context switch) + LDR r1, =NVIC_PENDSVSET + STR r1, [r0] + +_no_switch: + BX lr + + END
\ No newline at end of file diff --git a/libcpu/arm/stm32/context_rvds.S b/libcpu/arm/stm32/context_rvds.S new file mode 100644 index 0000000000..7aeefb2257 --- /dev/null +++ b/libcpu/arm/stm32/context_rvds.S @@ -0,0 +1,189 @@ +;/*
+; * File : context.S
+; * This file is part of RT-Thread RTOS
+; * COPYRIGHT (C) 2006, RT-Thread Development Team
+; *
+; * The license and distribution terms for this file may be
+; * found in the file LICENSE in this distribution or at
+; * http://www.rt-thread.org/license/LICENSE
+; *
+; * Change Logs:
+; * Date Author Notes
+; * 2009-01-17 Bernard first version
+; */
+
+;/**
+; * @addtogroup STM32
+; */
+;/*@{*/
+
+NVIC_INT_CTRL EQU 0xE000ED04 ; interrupt control state register
+NVIC_SYSPRI2 EQU 0xE000ED20 ; system priority register (2)
+NVIC_PENDSV_PRI EQU 0x00FF0000 ; PendSV priority value (lowest)
+NVIC_PENDSVSET EQU 0x10000000 ; value to trigger PendSV exception
+
+ AREA |.text|, CODE, READONLY, ALIGN=2
+ THUMB
+ REQUIRE8
+ PRESERVE8
+
+ IMPORT rt_thread_switch_interrput_flag
+ IMPORT rt_interrupt_from_thread
+ IMPORT rt_interrupt_to_thread
+
+;/*
+; * rt_base_t rt_hw_interrupt_disable();
+; */
+rt_hw_interrupt_disable PROC
+ EXPORT rt_hw_interrupt_disable
+ MRS r0, PRIMASK
+ CPSID I
+ BX LR
+ ENDP
+
+;/*
+; * void rt_hw_interrupt_enable(rt_base_t level);
+; */
+rt_hw_interrupt_enable PROC
+ EXPORT rt_hw_interrupt_enable
+ MSR PRIMASK, r0
+ BX LR
+ ENDP
+
+;/*
+; * void rt_hw_context_switch(rt_uint32 from, rt_uint32 to);
+; * r0 --> from
+; * r1 --> to
+; */
+rt_hw_context_switch PROC
+ EXPORT rt_hw_context_switch
+
+ ; set rt_thread_switch_interrput_flag to 1
+ LDR r2, =rt_thread_switch_interrput_flag
+ LDR r3, [r2]
+ MOV r3, #1
+ STR r3, [r2]
+
+ LDR r2, =rt_interrupt_from_thread ; set rt_interrupt_from_thread
+ STR r0, [r2]
+ LDR r2, =rt_interrupt_to_thread ; set rt_interrupt_to_thread
+ STR r1, [r2]
+
+ LDR r0, =NVIC_INT_CTRL ; trigger the PendSV exception (causes context switch)
+ LDR r1, =NVIC_PENDSVSET
+ STR r1, [r0]
+ ; CPSIE I ; enable interrupts at processor level
+ BX LR
+ ENDP
+
+; r0 --> swith from thread stack
+; r1 --> swith to thread stack
+; psr, pc, lr, r12, r3, r2, r1, r0 are pushed into [from] stack
+rt_hw_pend_sv PROC
+ EXPORT rt_hw_pend_sv
+ ; clear rt_thread_switch_interrput_flag to 0
+ LDR r0, =rt_thread_switch_interrput_flag
+ MOV r1, #0x00
+ STR r1, [r0]
+
+ LDR r0, =rt_interrupt_from_thread
+ LDR r1, [r0]
+ CBZ r1, swtich_to_thread ; skip register save at the first time
+
+ MRS r1, psp ; get from thread stack pointer
+ STMFD r1!, {r4 - r11} ; push r4 - r11 register
+ LDR r0, [r0]
+ STR r1, [r0] ; update from thread stack pointer
+
+swtich_to_thread
+ LDR r1, =rt_interrupt_to_thread
+ LDR r1, [r1]
+ LDR r1, [r1] ; load thread stack pointer
+
+ LDMFD r1!, {r4 - r11} ; pop r4 - r11 register
+ MSR psp, r1 ; update stack pointer
+
+ ORR lr, lr, #0x04
+ BX lr
+ ENDP
+
+;/*
+; * void rt_hw_context_switch_to(rt_uint32 to);
+; * r0 --> to
+; */
+rt_hw_context_switch_to PROC
+ EXPORT rt_hw_context_switch_to
+ LDR r1, =rt_interrupt_to_thread
+ STR r0, [r1]
+
+ ; set from thread to 0
+ LDR r1, =rt_interrupt_from_thread
+ MOV r0, #0x0
+ STR r0, [r1]
+
+ ; set the PendSV exception priority
+ LDR r0, =NVIC_SYSPRI2
+ LDR r1, =NVIC_PENDSV_PRI
+ STR r1, [r0]
+
+ LDR r0, =NVIC_INT_CTRL ; trigger the PendSV exception (causes context switch)
+ LDR r1, =NVIC_PENDSVSET
+ STR r1, [r0]
+
+ CPSIE I ; enable interrupts at processor level
+
+ ; never reach here!
+ ENDP
+
+;/*
+; * void rt_hw_context_switch_interrupt(rt_uint32 from, rt_uint32 to)
+; * {
+; * if (rt_thread_switch_interrput_flag == 1)
+; * {
+; * rt_interrupt_to_thread = to;
+; * }
+; * else
+; * {
+; * rt_thread_switch_interrput_flag = 1;
+; * rt_interrupt_from_thread = from;
+; * rt_interrupt_to_thread = to;
+; * }
+; * }
+; */
+rt_hw_context_switch_interrupt PROC
+ EXPORT rt_hw_context_switch_interrupt
+ LDR r2, =rt_thread_switch_interrput_flag
+ LDR r3, [r2]
+ CMP r3, #1
+ BEQ _reswitch
+ MOV r3, #1 ; set rt_thread_switch_interrput_flag to 1
+ STR r3, [r2]
+ LDR r2, =rt_interrupt_from_thread ; set rt_interrupt_from_thread
+ STR r0, [r2]
+_reswitch
+ LDR r2, =rt_interrupt_to_thread ; set rt_interrupt_to_thread
+ STR r1, [r2]
+ BX lr
+ ENDP
+
+rt_hw_interrupt_thread_switch PROC
+ EXPORT rt_hw_interrupt_thread_switch
+ LDR r0, =rt_thread_switch_interrput_flag
+ LDR r1, [r0]
+ CBZ r1, _no_switch
+
+ ; clear rt_thread_switch_interrput_flag to 0
+ ; MOV r1, #0x00
+ ; STR r1, [r0]
+
+ ; trigger context switch
+ LDR r0, =NVIC_INT_CTRL ; trigger the PendSV exception (causes context switch)
+ LDR r1, =NVIC_PENDSVSET
+ STR r1, [r0]
+
+_no_switch
+ BX lr
+
+ ENDP
+
+ END
\ No newline at end of file diff --git a/libcpu/arm/stm32/cpu.c b/libcpu/arm/stm32/cpu.c new file mode 100644 index 0000000000..080634c2b9 --- /dev/null +++ b/libcpu/arm/stm32/cpu.c @@ -0,0 +1,42 @@ +/*
+ * File : cpu.c
+ * This file is part of RT-Thread RTOS
+ * COPYRIGHT (C) 2006, RT-Thread Develop Team
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://openlab.rt-thread.com/license/LICENSE
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2006-03-13 Bernard first version
+ */
+
+#include <rtthread.h>
+
+/**
+ * @addtogroup S3C2410
+ */
+/*@{*/
+
+/**
+ * reset cpu by dog's time-out
+ *
+ */
+void rt_hw_cpu_reset()
+{
+ /*NOTREACHED*/
+}
+
+/**
+ * shutdown CPU
+ *
+ */
+void rt_hw_cpu_shutdown()
+{
+ rt_kprintf("shutdown...\n");
+
+ RT_ASSERT(0);
+}
+
+/*@}*/
diff --git a/libcpu/arm/stm32/fault.c b/libcpu/arm/stm32/fault.c new file mode 100644 index 0000000000..c3cf747018 --- /dev/null +++ b/libcpu/arm/stm32/fault.c @@ -0,0 +1,34 @@ +#include <rtthread.h>
+
+struct stack_contex
+{
+ rt_uint32_t r0;
+ rt_uint32_t r1;
+ rt_uint32_t r2;
+ rt_uint32_t r3;
+ rt_uint32_t r12;
+ rt_uint32_t lr;
+ rt_uint32_t pc;
+ rt_uint32_t psr;
+};
+
+extern void rt_hw_interrupt_thread_switch(void);
+extern void list_thread(void);
+extern rt_thread_t rt_current_thread;
+void rt_hw_hard_fault_exception(struct stack_contex* contex)
+{
+ rt_kprintf("hard fault on thread: %s\n", rt_current_thread->name);
+ rt_kprintf("psr: 0x%08x\n", contex->psr);
+ rt_kprintf(" pc: 0x%08x\n", contex->pc);
+ rt_kprintf(" lr: 0x%08x\n", contex->lr);
+ rt_kprintf("r12: 0x%08x\n", contex->r12);
+ rt_kprintf("r03: 0x%08x\n", contex->r3);
+ rt_kprintf("r02: 0x%08x\n", contex->r2);
+ rt_kprintf("r01: 0x%08x\n", contex->r1);
+ rt_kprintf("r00: 0x%08x\n", contex->r0);
+
+#ifdef RT_USING_FINSH
+ list_thread();
+#endif
+ while (1);
+}
diff --git a/libcpu/arm/stm32/fault_rvds.S b/libcpu/arm/stm32/fault_rvds.S new file mode 100644 index 0000000000..e4f0aaa964 --- /dev/null +++ b/libcpu/arm/stm32/fault_rvds.S @@ -0,0 +1,31 @@ +;/*
+; * File : context.S
+; * This file is part of RT-Thread RTOS
+; * COPYRIGHT (C) 2006, RT-Thread Development Team
+; *
+; * The license and distribution terms for this file may be
+; * found in the file LICENSE in this distribution or at
+; * http://www.rt-thread.org/license/LICENSE
+; *
+; * Change Logs:
+; * Date Author Notes
+; * 2009-01-17 Bernard first version
+; */
+
+ AREA |.text|, CODE, READONLY, ALIGN=2
+ THUMB
+ REQUIRE8
+ PRESERVE8
+
+ IMPORT rt_hw_hard_fault_exception
+
+rt_hw_hard_fault PROC
+ EXPORT rt_hw_hard_fault
+
+ ; get current context
+ MRS r0, psp ; get fault thread stack pointer
+ BL rt_hw_hard_fault_exception
+
+ ORR lr, lr, #0x04
+ BX lr
+
\ No newline at end of file diff --git a/libcpu/arm/stm32/interrupt.c b/libcpu/arm/stm32/interrupt.c new file mode 100644 index 0000000000..a57656c7fb --- /dev/null +++ b/libcpu/arm/stm32/interrupt.c @@ -0,0 +1,25 @@ +/* + * File : trap.c + * This file is part of RT-Thread RTOS + * COPYRIGHT (C) 2006, RT-Thread Development Team + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://openlab.rt-thread.com/license/LICENSE + * + * Change Logs: + * Date Author Notes + * 2006-03-13 Bernard first version + */ + +#include <rtthread.h> + +#define MAX_HANDLERS 32 + +extern rt_uint32_t rt_interrupt_nest; + +/* exception and interrupt handler table */ +rt_uint32_t rt_interrupt_from_thread, rt_interrupt_to_thread; +rt_uint32_t rt_thread_switch_interrput_flag; + +/*@}*/ diff --git a/libcpu/arm/stm32/serial.c b/libcpu/arm/stm32/serial.c new file mode 100644 index 0000000000..c5dbb0b24e --- /dev/null +++ b/libcpu/arm/stm32/serial.c @@ -0,0 +1,586 @@ +/*
+ * File : serial.c
+ * This file is part of RT-Thread RTOS
+ * COPYRIGHT (C) 2006, RT-Thread Development Team
+ *
+ * The license and distribution terms for this file may be
+ * found in the file LICENSE in this distribution or at
+ * http://openlab.rt-thread.com/license/LICENSE
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2009-02-05 Bernard first version
+ */
+
+#include "serial.h"
+
+static void rt_serial_enable_dma(DMA_Channel_TypeDef* dma_channel,
+ rt_uint32_t address, rt_uint32_t size);
+
+/**
+ * @addtogroup STM32
+ */
+/*@{*/
+
+/**
+ * This function read a character from serial without interrupt enable mode
+ *
+ * @return the read char
+ */
+char rt_serial_getc(struct stm32_serial_device* uart)
+{
+ rt_base_t level;
+ char ch = 0;
+
+ /* disable interrupt */
+ level = rt_hw_interrupt_disable();
+
+ if (uart->int_rx->read_index != uart->int_rx->save_index)
+ {
+ ch = uart->int_rx->rx_buffer[uart->int_rx->read_index];
+
+ uart->int_rx->read_index ++;
+ if (uart->int_rx->read_index >= UART_RX_BUFFER_SIZE)
+ uart->int_rx->read_index = 0;
+ }
+
+ /* enable interrupt */
+ rt_hw_interrupt_enable(level);
+
+ return ch;
+}
+
+/* save a char to serial buffer */
+void rt_serial_savechar(struct stm32_serial_device* uart, char ch)
+{
+ rt_base_t level;
+
+ /* disable interrupt */
+ level = rt_hw_interrupt_disable();
+
+ uart->int_rx->rx_buffer[uart->int_rx->save_index] = ch;
+ uart->int_rx->save_index ++;
+ if (uart->int_rx->save_index >= UART_RX_BUFFER_SIZE)
+ uart->int_rx->save_index = 0;
+
+ /* if the next position is read index, discard this 'read char' */
+ if (uart->int_rx->save_index == uart->int_rx->read_index)
+ {
+ uart->int_rx->read_index ++;
+ if (uart->int_rx->read_index >= UART_RX_BUFFER_SIZE)
+ uart->int_rx->read_index = 0;
+ }
+
+ /* enable interrupt */
+ rt_hw_interrupt_enable(level);
+}
+
+/**
+ * This function will write a character to serial without interrupt enable mode
+ *
+ * @param c the char to write
+ */
+void rt_serial_putc(rt_device_t device, const char c)
+{
+ struct stm32_serial_device* uart = (struct stm32_serial_device*) device->private;
+
+ /*
+ * to be polite with serial console add a line feed
+ * to the carriage return character
+ */
+ if (c=='\n' && (device->flag & RT_DEVICE_FLAG_STREAM))
+ rt_serial_putc(device, '\r');
+
+ while (!(uart->uart_device->SR & USART_FLAG_TXE));
+ uart->uart_device->DR = (c & 0x1FF);
+}
+
+/* RT-Thread Device Interface */
+static rt_err_t rt_serial_init (rt_device_t dev)
+{
+ struct stm32_serial_device* uart = (struct stm32_serial_device*) dev->private;
+
+ if (!(dev->flag & RT_DEVICE_FLAG_ACTIVATED))
+ {
+ if (dev->flag & RT_DEVICE_FLAG_INT_RX)
+ {
+ rt_memset(uart->int_rx->rx_buffer, 0,
+ sizeof(uart->int_rx->rx_buffer));
+ uart->int_rx->read_index = 0;
+ uart->int_rx->read_index = 0;
+ }
+
+ if (dev->flag & RT_DEVICE_FLAG_DMA_RX)
+ {
+ RT_ASSERT(uart->dma_rx->dma_channel != RT_NULL);
+ uart->dma_rx->read_index = uart->dma_rx->read_descriptor = 0;
+ uart->dma_rx->is_full = RT_FALSE;
+ }
+
+ if (dev->flag & RT_DEVICE_FLAG_INT_TX)
+ {
+ rt_memset(uart->int_tx->tx_buffer, 0,
+ sizeof(uart->int_tx->tx_buffer));
+ uart->int_tx->write_index = uart->int_tx->save_index = 0;
+ }
+
+ if (dev->flag & RT_DEVICE_FLAG_DMA_TX)
+ {
+ RT_ASSERT(uart->dma_rx->dma_channel != RT_NULL);
+ uart->dma_tx->list_head = uart->dma_tx->list_tail = RT_NULL;
+ }
+
+ /* Enable USART */
+ USART_Cmd(uart->uart_device, ENABLE);
+
+ dev->flag |= RT_DEVICE_FLAG_ACTIVATED;
+ }
+
+ return RT_EOK;
+}
+
+static rt_err_t rt_serial_open(rt_device_t dev, rt_uint16_t oflag)
+{
+ struct stm32_serial_device* uart;
+
+ RT_ASSERT(dev != RT_NULL);
+
+ uart = (struct stm32_serial_device*)dev->private;
+
+ if (dev->flag & RT_DEVICE_FLAG_DMA_RX)
+ {
+ /* enable Rx DMA */
+ rt_serial_enable_dma(uart->dma_rx->dma_channel,
+ (rt_uint32_t)&(uart->dma_rx->rx_buffer[uart->dma_rx->save_descriptor][0]),
+ UART_DMA_RX_BUFFER_SIZE);
+ }
+
+ return RT_EOK;
+}
+
+static rt_err_t rt_serial_close(rt_device_t dev)
+{
+ struct stm32_serial_device* uart;
+
+ RT_ASSERT(dev != RT_NULL);
+
+ uart = (struct stm32_serial_device*)dev->private;
+
+ if (dev->flag & RT_DEVICE_FLAG_DMA_RX)
+ {
+ /* disable DMA */
+ DMA_Cmd(uart->dma_rx->dma_channel, DISABLE);
+ }
+ return RT_EOK;
+}
+
+static rt_size_t rt_serial_read (rt_device_t dev, rt_off_t pos, void* buffer, rt_size_t size)
+{
+ rt_uint8_t* ptr;
+ rt_err_t err_code;
+ struct stm32_serial_device* uart;
+
+ ptr = buffer;
+ err_code = RT_EOK;
+ uart = (struct stm32_serial_device*)dev->private;
+
+ if (dev->flag & RT_DEVICE_FLAG_INT_RX)
+ {
+ rt_int32_t ch;
+
+ /* interrupt mode Rx */
+ while (size)
+ {
+ /* get a character */
+ ch = rt_serial_getc(uart);
+ if (ch < 0)
+ {
+ /* set error code */
+ err_code = -RT_EEMPTY;
+ }
+ else
+ {
+ *ptr++ = ch;
+ size --;
+ }
+ }
+ }
+ else if (dev->flag & RT_DEVICE_FLAG_DMA_RX)
+ {
+ /* check queue empty */
+ if ((uart->dma_rx->read_descriptor == uart->dma_rx->save_descriptor))
+ {
+ /* set error code */
+ err_code = -RT_EEMPTY;
+ }
+ else
+ {
+ /* read data */
+ while ((rt_uint32_t)ptr - (rt_uint32_t)buffer < size)
+ {
+ /* read buffer */
+ *ptr ++ = uart->dma_rx->
+ rx_buffer[uart->dma_rx->read_descriptor][uart->dma_rx->read_index];
+
+ /* move to next position */
+ uart->dma_rx->read_index ++;
+
+ /* wrap read index */
+ if (uart->dma_rx->read_index >= UART_DMA_RX_BUFFER_SIZE)
+ {
+ /* wrap read index */
+ uart->dma_rx->read_index = 0;
+
+ /* move to next read descriptor */
+ uart->dma_rx->read_descriptor ++;
+ /* wrap read descriptor */
+ if (uart->dma_rx->read_descriptor >= UART_DMA_RX_DESCRIPTOR)
+ uart->dma_rx->read_descriptor = 0;
+
+ if (uart->dma_rx->is_full == RT_TRUE)
+ {
+ rt_uint32_t level;
+
+ level = rt_hw_interrupt_disable();
+ uart->dma_rx->save_descriptor ++;
+ if (uart->dma_rx->save_descriptor >= UART_DMA_RX_DESCRIPTOR)
+ uart->dma_rx->save_descriptor = 0;
+ rt_hw_interrupt_enable(level);
+
+ /* re-enable DMA to receive */
+ rt_serial_enable_dma(uart->dma_rx->dma_channel,
+ (rt_uint32_t)&(uart->dma_rx->rx_buffer[uart->dma_rx->save_descriptor][0]),
+ UART_DMA_RX_BUFFER_SIZE);
+ }
+
+ /* check queue empty */
+ if ((uart->dma_rx->read_descriptor == uart->dma_rx->save_descriptor))
+ {
+ /* set error code */
+ err_code = -RT_EEMPTY;
+ break;
+ }
+ }
+ }
+ }
+ }
+ else
+ {
+ /* polling mode */
+ while ((rt_uint32_t)ptr - (rt_uint32_t)buffer < size)
+ {
+ while (uart->uart_device->SR & USART_FLAG_RXNE)
+ {
+ *ptr = uart->uart_device->DR & 0xff;
+ ptr ++;
+ }
+ }
+ }
+
+ /* set error code */
+ rt_set_errno(err_code);
+ return (rt_uint32_t)ptr - (rt_uint32_t)buffer;
+}
+
+static void rt_serial_enable_dma(DMA_Channel_TypeDef* dma_channel,
+ rt_uint32_t address, rt_uint32_t size)
+{
+ RT_ASSERT(dma_channel != RT_NULL);
+
+ /* disable DMA */
+ DMA_Cmd(dma_channel, DISABLE);
+
+ /* set buffer address */
+ dma_channel->CMAR = address;
+ /* set size */
+ dma_channel->CNDTR = size;
+
+ /* enable DMA */
+ DMA_Cmd(dma_channel, ENABLE);
+}
+
+static rt_size_t rt_serial_write (rt_device_t dev, rt_off_t pos, const void* buffer, rt_size_t size)
+{
+ rt_uint8_t* ptr;
+ rt_err_t err_code;
+ struct stm32_serial_device* uart;
+
+ err_code = RT_EOK;
+ ptr = (rt_uint8_t*)buffer;
+ uart = (struct stm32_serial_device*)dev->private;
+
+ if (dev->flag & RT_DEVICE_FLAG_INT_TX)
+ {
+ /* interrupt mode Tx */
+ while (uart->int_tx->save_index != uart->int_tx->write_index)
+ {
+ /* save on tx buffer */
+ uart->int_tx->tx_buffer[uart->int_tx->save_index] = *ptr++;
+
+ -- size;
+
+ /* move to next position */
+ uart->int_tx->save_index ++;
+
+ /* wrap save index */
+ if (uart->int_tx->save_index >= UART_TX_BUFFER_SIZE)
+ uart->int_tx->save_index = 0;
+ }
+
+ /* set error code */
+ if (size > 0)
+ err_code = -RT_EFULL;
+ }
+ else if (dev->flag & RT_DEVICE_FLAG_DMA_TX)
+ {
+ /* DMA mode Tx */
+
+ /* allocate a data node */
+ struct stm32_serial_data_node* data_node =
+ (struct stm32_serial_data_node*) rt_malloc (sizeof(struct stm32_serial_data_node));
+ if (data_node == RT_NULL)
+ {
+ /* set error code */
+ err_code = -RT_ENOMEM;
+ }
+ else
+ {
+ rt_uint32_t level;
+
+ /* fill data node */
+ data_node->data_ptr = ptr;
+ data_node->data_size = size;
+
+ /* insert to data link */
+ data_node->next = RT_NULL;
+
+ /* disable interrupt */
+ level = rt_hw_interrupt_disable();
+
+ data_node->prev = uart->dma_tx->list_tail;
+ if (uart->dma_tx->list_tail != RT_NULL)
+ uart->dma_tx->list_tail->next = data_node;
+ uart->dma_tx->list_tail = data_node;
+
+ if (uart->dma_tx->list_head == RT_NULL)
+ {
+ /* start DMA to transmit data */
+ uart->dma_tx->list_head = data_node;
+
+ /* Enable DMA Channel */
+ rt_serial_enable_dma(uart->dma_tx->dma_channel,
+ (rt_uint32_t)uart->dma_tx->list_head->data_ptr,
+ uart->dma_tx->list_head->data_size);
+ }
+
+ /* enable interrupt */
+ rt_hw_interrupt_enable(level);
+ }
+ }
+ else
+ {
+ /* polling mode */
+ while (size)
+ {
+ rt_serial_putc(dev, *ptr);
+ ++ptr; --size;
+ }
+ }
+
+ /* set error code */
+ rt_set_errno(err_code);
+
+ return (rt_uint32_t)ptr - (rt_uint32_t)buffer;
+}
+
+static rt_err_t rt_serial_control (rt_device_t dev, rt_uint8_t cmd, void *args)
+{
+ struct stm32_serial_device* uart;
+
+ RT_ASSERT(dev != RT_NULL);
+
+ uart = (struct stm32_serial_device*)dev->private;
+ switch (cmd)
+ {
+ case RT_DEVICE_CTRL_SUSPEND:
+ /* suspend device */
+ dev->flag |= RT_DEVICE_FLAG_SUSPENDED;
+ USART_Cmd(uart->uart_device, DISABLE);
+ break;
+
+ case RT_DEVICE_CTRL_RESUME:
+ /* resume device */
+ dev->flag &= ~RT_DEVICE_FLAG_SUSPENDED;
+ USART_Cmd(uart->uart_device, ENABLE);
+ break;
+ }
+
+ return RT_EOK;
+}
+
+/*
+ * serial register for STM32
+ * support STM32F103VB and STM32F103ZE
+ */
+rt_err_t rt_hw_serial_register(rt_device_t device, const char* name, rt_uint32_t flag, struct stm32_serial_device *serial)
+{
+ RT_ASSERT(device != RT_NULL);
+
+ device->type = RT_Device_Class_Char;
+ device->rx_indicate = RT_NULL;
+ device->tx_complete = RT_NULL;
+ device->init = rt_serial_init;
+ device->open = rt_serial_open;
+ device->close = rt_serial_close;
+ device->read = rt_serial_read;
+ device->write = rt_serial_write;
+ device->control = rt_serial_control;
+ device->private = serial;
+
+ /* register a character device */
+ return rt_device_register(device, name, RT_DEVICE_FLAG_RDWR | flag);
+}
+
+/* ISR for serial interrupt */
+void rt_hw_serial_isr(rt_device_t device)
+{
+ struct stm32_serial_device* uart = (struct stm32_serial_device*) device->private;
+
+ if(USART_GetITStatus(uart->uart_device, USART_IT_RXNE) != RESET)
+ {
+ /* interrupt mode receive */
+ RT_ASSERT(device->flag & RT_DEVICE_FLAG_INT_RX);
+
+ /* save on rx buffer */
+ while (uart->uart_device->SR & USART_FLAG_RXNE)
+ {
+ rt_serial_savechar(uart, uart->uart_device->DR & 0xff);
+ }
+
+ /* clear interrupt */
+ USART_ClearITPendingBit(uart->uart_device, USART_IT_RXNE);
+
+ /* invoke callback */
+ if (device->rx_indicate != RT_NULL)
+ {
+ rt_size_t rx_length;
+
+ /* get rx length */
+ rx_length = uart->int_rx->read_index > uart->int_rx->save_index ?
+ UART_RX_BUFFER_SIZE - uart->int_rx->read_index + uart->int_rx->save_index :
+ uart->int_rx->save_index - uart->int_rx->read_index;
+
+ device->rx_indicate(device, rx_length);
+ }
+ }
+
+ if (USART_GetITStatus(uart->uart_device, USART_IT_TC) != RESET)
+ {
+ /* interrupt mode transmission */
+ RT_ASSERT(device->flag & RT_DEVICE_FLAG_INT_TX);
+
+ /* transmission completed */
+ uart->int_tx->write_index ++;
+ if (uart->int_tx->write_index >= UART_TX_BUFFER_SIZE)
+ uart->int_tx->write_index = 0;
+
+ /* clear interrupt */
+ USART_ClearITPendingBit(uart->uart_device, USART_IT_RXNE);
+
+ /* start next transmission */
+ if (uart->int_tx->write_index <
+ uart->int_tx->save_index)
+ {
+ uart->uart_device->DR = uart->int_tx
+ ->tx_buffer[uart->int_tx->write_index];
+ }
+ }
+}
+
+/*
+ * ISR for DMA mode Rx
+ */
+void rt_hw_serial_dma_rx_isr(rt_device_t device)
+{
+ rt_uint32_t next_descriptor;
+ struct stm32_serial_device* uart = (struct stm32_serial_device*) device->private;
+
+ /* DMA mode receive */
+ RT_ASSERT(device->flag & RT_DEVICE_FLAG_DMA_RX);
+
+ /* invoke callback */
+ if (device->rx_indicate != RT_NULL)
+ device->rx_indicate(device, UART_DMA_RX_BUFFER_SIZE);
+
+ next_descriptor = uart->dma_rx->save_descriptor;
+
+ /* move to next descriptor */
+ next_descriptor ++;
+ if (next_descriptor >= UART_DMA_RX_DESCRIPTOR)
+ next_descriptor = 0;
+
+ if (next_descriptor != uart->dma_rx->read_descriptor)
+ {
+ uart->dma_rx->save_descriptor = next_descriptor;
+ /* enable next DMA */
+ rt_serial_enable_dma(uart->dma_rx->dma_channel,
+ (rt_uint32_t)&(uart->dma_rx->rx_buffer[uart->dma_rx->save_descriptor][0]),
+ UART_DMA_RX_BUFFER_SIZE);
+ }
+ else
+ {
+ /* no descriptor yet, disable DMA */
+ DMA_Cmd(uart->dma_rx->dma_channel, DISABLE);
+ uart->dma_rx->is_full = RT_TRUE;
+ }
+}
+
+/*
+ * ISR for DMA mode Tx
+ */
+void rt_hw_serial_dma_tx_isr(rt_device_t device)
+{
+ rt_uint32_t level;
+ struct stm32_serial_data_node* data_node;
+ struct stm32_serial_device* uart = (struct stm32_serial_device*) device->private;
+
+ /* DMA mode receive */
+ RT_ASSERT(device->flag & RT_DEVICE_FLAG_DMA_TX);
+
+ /* get the first data node */
+ data_node = uart->dma_tx->list_head;
+ RT_ASSERT(data_node != RT_NULL);
+
+ /* invoke call to notify tx complete */
+ if (device->tx_complete != RT_NULL)
+ device->tx_complete(device, data_node->data_ptr);
+
+ /* disable interrupt */
+ level = rt_hw_interrupt_disable();
+
+ /* remove list tail */
+ uart->dma_tx->list_tail = data_node->prev;
+ if (uart->dma_tx->list_tail == RT_NULL)
+ uart->dma_tx->list_head = RT_NULL;
+
+ /* enable interrupt */
+ rt_hw_interrupt_enable(level);
+
+ /* free data node memory */
+ rt_free(data_node);
+
+ if (uart->dma_tx->list_tail != RT_NULL)
+ {
+ /* transmit next data node */
+ rt_serial_enable_dma(uart->dma_tx->dma_channel,
+ (rt_uint32_t)uart->dma_tx->list_tail->data_ptr,
+ uart->dma_tx->list_tail->data_size);
+ }
+ else
+ {
+ /* no data to be transmitted, disable DMA */
+ DMA_Cmd(uart->dma_tx->dma_channel, DISABLE);
+ }
+}
+
+/*@}*/
diff --git a/libcpu/arm/stm32/serial.h b/libcpu/arm/stm32/serial.h new file mode 100644 index 0000000000..a36cad79a2 --- /dev/null +++ b/libcpu/arm/stm32/serial.h @@ -0,0 +1,69 @@ +#ifndef __RT_HW_SERIAL_H__
+#define __RT_HW_SERIAL_H__
+
+#include <rthw.h>
+#include <rtthread.h>
+
+/* STM32F10x library definitions */
+#include <stm32f10x_lib.h>
+
+#define UART_DMA_RX_DESCRIPTOR 2
+#define UART_DMA_RX_BUFFER_SIZE 16
+
+#define UART_RX_BUFFER_SIZE 64
+#define UART_TX_BUFFER_SIZE 64
+
+struct stm32_serial_dma_rx
+{
+ DMA_Channel_TypeDef* dma_channel;
+ rt_uint8_t rx_buffer[UART_DMA_RX_DESCRIPTOR][UART_RX_BUFFER_SIZE];
+ rt_uint32_t save_descriptor;
+ rt_uint32_t read_index, read_descriptor;
+ rt_bool_t is_full;
+};
+
+/* data node for Tx Mode */
+struct stm32_serial_data_node
+{
+ rt_uint8_t *data_ptr;
+ rt_size_t data_size;
+ struct stm32_serial_data_node *next, *prev;
+};
+struct stm32_serial_dma_tx
+{
+ DMA_Channel_TypeDef* dma_channel;
+ struct stm32_serial_data_node *list_head, *list_tail;
+};
+
+struct stm32_serial_int_rx
+{
+ rt_uint8_t rx_buffer[UART_RX_BUFFER_SIZE];
+ rt_uint32_t read_index, save_index;
+};
+
+struct stm32_serial_int_tx
+{
+ rt_uint8_t tx_buffer[UART_TX_BUFFER_SIZE];
+ rt_uint32_t write_index, save_index;
+};
+
+struct stm32_serial_device
+{
+ USART_TypeDef* uart_device;
+
+ /* rx structure */
+ struct stm32_serial_int_rx* int_rx;
+ struct stm32_serial_dma_rx* dma_rx;
+
+ /* tx structure */
+ struct stm32_serial_int_tx* int_tx;
+ struct stm32_serial_dma_tx* dma_tx;
+};
+
+rt_err_t rt_hw_serial_register(rt_device_t device, const char* name, rt_uint32_t flag, struct stm32_serial_device *serial);
+
+void rt_hw_serial_isr(rt_device_t device);
+void rt_hw_serial_dma_rx_isr(rt_device_t device);
+void rt_hw_serial_dma_tx_isr(rt_device_t device);
+
+#endif
diff --git a/libcpu/arm/stm32/stack.c b/libcpu/arm/stm32/stack.c new file mode 100644 index 0000000000..c7f8c71ab4 --- /dev/null +++ b/libcpu/arm/stm32/stack.c @@ -0,0 +1,59 @@ +/* + * File : stack.c + * This file is part of RT-Thread RTOS + * COPYRIGHT (C) 2006, RT-Thread Development Team + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://openlab.rt-thread.com/license/LICENSE + * + * Change Logs: + * Date Author Notes + * 2006-08-23 Bernard the first version + */ +#include <rtthread.h> + +/** + * @addtogroup STM32 + */ +/*@{*/ + +/** + * This function will initialize thread stack + * + * @param tentry the entry of thread + * @param parameter the parameter of entry + * @param stack_addr the beginning stack address + * @param texit the function will be called when thread exit + * + * @return stack address + */ +rt_uint8_t *rt_hw_stack_init(void *tentry, void *parameter, + rt_uint8_t *stack_addr, void *texit) +{ + unsigned long *stk; + + stk = (unsigned long *)stack_addr; + *(stk) = 0x01000000L; /* PSR */ + *(--stk) = (unsigned long)tentry; /* entry point, pc */ + *(--stk) = (unsigned long)texit; /* lr */ + *(--stk) = 0; /* r12 */ + *(--stk) = 0; /* r3 */ + *(--stk) = 0; /* r2 */ + *(--stk) = 0; /* r1 */ + *(--stk) = (unsigned long)parameter; /* r0 : argument */ + + *(--stk) = 0; /* r11 */ + *(--stk) = 0; /* r10 */ + *(--stk) = 0; /* r9 */ + *(--stk) = 0; /* r8 */ + *(--stk) = 0; /* r7 */ + *(--stk) = 0; /* r6 */ + *(--stk) = 0; /* r5 */ + *(--stk) = 0; /* r4 */ + + /* return task's current stack address */ + return (rt_uint8_t *)stk; +} + +/*@}*/ diff --git a/libcpu/arm/stm32/start_iar.c b/libcpu/arm/stm32/start_iar.c new file mode 100644 index 0000000000..3cc01ed9e8 --- /dev/null +++ b/libcpu/arm/stm32/start_iar.c @@ -0,0 +1,176 @@ +/******************** (C) COPYRIGHT 2008 STMicroelectronics ******************** +* File Name : stm32f10x_vector.c +* Author : MCD Application Team +* Version : V2.0.3 +* Date : 09/22/2008 +* Description : STM32F10x vector table for EWARM5.x toolchain. +* This module performs: +* - Set the initial SP +* - Set the initial PC == __iar_program_start, +* - Set the vector table entries with the exceptions ISR address, +* - Configure external SRAM mounted on STM3210E-EVAL board +* to be used as data memory (optional, to be enabled by user) +* After Reset the Cortex-M3 processor is in Thread mode, +* priority is Privileged, and the Stack is set to Main. +******************************************************************************** +* THE PRESENT FIRMWARE WHICH IS FOR GUIDANCE ONLY AIMS AT PROVIDING CUSTOMERS +* WITH CODING INFORMATION REGARDING THEIR PRODUCTS IN ORDER FOR THEM TO SAVE TIME. +* AS A RESULT, STMICROELECTRONICS SHALL NOT BE HELD LIABLE FOR ANY DIRECT, +* INDIRECT OR CONSEQUENTIAL DAMAGES WITH RESPECT TO ANY CLAIMS ARISING FROM THE +* CONTENT OF SUCH FIRMWARE AND/OR THE USE MADE BY CUSTOMERS OF THE CODING +* INFORMATION CONTAINED HEREIN IN CONNECTION WITH THEIR PRODUCTS. +*******************************************************************************/ + +/* Includes ------------------------------------------------------------------*/ +#include "stm32f10x_lib.h" +#include "stm32f10x_it.h" + +/* Private typedef -----------------------------------------------------------*/ +typedef void( *intfunc )( void ); +typedef union { intfunc __fun; void * __ptr; } intvec_elem; + +/* Private define ------------------------------------------------------------*/ +/* Uncomment the following line if you need to use external SRAM mounted on + STM3210E-EVAL board as data memory */ +/* #define DATA_IN_ExtSRAM */ + +/* Private macro -------------------------------------------------------------*/ +/* Private variables ---------------------------------------------------------*/ +/* Private function prototypes -----------------------------------------------*/ +/* Private functions ---------------------------------------------------------*/ + + +#pragma language=extended +#pragma segment="CSTACK" + +void __iar_program_start( void ); + +#pragma location = ".intvec" +/* STM32F10x Vector Table entries */ +const intvec_elem __vector_table[] = +{ + { .__ptr = __sfe( "CSTACK" ) }, + __iar_program_start, + NMIException, + HardFaultException, + MemManageException, + BusFaultException, + UsageFaultException, + 0, 0, 0, 0, /* Reserved */ + SVCHandler, + DebugMonitor, + 0, /* Reserved */ + rt_hw_pend_sv, + SysTickHandler, + WWDG_IRQHandler, + PVD_IRQHandler, + TAMPER_IRQHandler, + RTC_IRQHandler, + FLASH_IRQHandler, + RCC_IRQHandler, + EXTI0_IRQHandler, + EXTI1_IRQHandler, + EXTI2_IRQHandler, + EXTI3_IRQHandler, + EXTI4_IRQHandler, + DMA1_Channel1_IRQHandler, + DMA1_Channel2_IRQHandler, + DMA1_Channel3_IRQHandler, + DMA1_Channel4_IRQHandler, + DMA1_Channel5_IRQHandler, + DMA1_Channel6_IRQHandler, + DMA1_Channel7_IRQHandler, + ADC1_2_IRQHandler, + USB_HP_CAN_TX_IRQHandler, + USB_LP_CAN_RX0_IRQHandler, + CAN_RX1_IRQHandler, + CAN_SCE_IRQHandler, + EXTI9_5_IRQHandler, + TIM1_BRK_IRQHandler, + TIM1_UP_IRQHandler, + TIM1_TRG_COM_IRQHandler, + TIM1_CC_IRQHandler, + TIM2_IRQHandler, + TIM3_IRQHandler, + TIM4_IRQHandler, + I2C1_EV_IRQHandler, + I2C1_ER_IRQHandler, + I2C2_EV_IRQHandler, + I2C2_ER_IRQHandler, + SPI1_IRQHandler, + SPI2_IRQHandler, + USART1_IRQHandler, + USART2_IRQHandler, + USART3_IRQHandler, + EXTI15_10_IRQHandler, + RTCAlarm_IRQHandler, + USBWakeUp_IRQHandler, + TIM8_BRK_IRQHandler, + TIM8_UP_IRQHandler, + TIM8_TRG_COM_IRQHandler, + TIM8_CC_IRQHandler, + ADC3_IRQHandler, + FSMC_IRQHandler, + SDIO_IRQHandler, + TIM5_IRQHandler, + SPI3_IRQHandler, + UART4_IRQHandler, + UART5_IRQHandler, + TIM6_IRQHandler, + TIM7_IRQHandler, + DMA2_Channel1_IRQHandler, + DMA2_Channel2_IRQHandler, + DMA2_Channel3_IRQHandler, + DMA2_Channel4_5_IRQHandler, +}; + +#ifdef DATA_IN_ExtSRAM +#pragma language=extended + +__interwork int __low_level_init(void); + +#pragma location="ICODE" +__interwork int __low_level_init(void) +{ + +/* FSMC Bank1 NOR/SRAM3 is used for the STM3210E-EVAL, if another Bank is + required, then adjust the Register Addresses*/ + + /* Enable FSMC clock */ + *(vu32 *)0x40021014 = 0x00000114; + + /* Enable GPIOD, GPIOE, GPIOF and GPIOG clocks */ + *(vu32 *)0x40021018 = 0x000001E0; + +/* --------------- SRAM Data lines, NOE and NWE configuration ---------------*/ +/*---------------- SRAM Address lines configuration -------------------------*/ +/*---------------- NOE and NWE configuration --------------------------------*/ +/*---------------- NE3 configuration ----------------------------------------*/ +/*---------------- NBL0, NBL1 configuration ---------------------------------*/ + + *(vu32 *)0x40011400 = 0x44BB44BB; + *(vu32 *)0x40011404 = 0xBBBBBBBB; + + *(vu32 *)0x40011800 = 0xB44444BB; + *(vu32 *)0x40011804 = 0xBBBBBBBB; + + *(vu32 *)0x40011C00 = 0x44BBBBBB; + *(vu32 *)0x40011C04 = 0xBBBB4444; + + *(vu32 *)0x40012000 = 0x44BBBBBB; + *(vu32 *)0x40012004 = 0x44444B44; + +/*---------------- FSMC Configuration ---------------------------------------*/ +/*---------------- Enable FSMC Bank1_SRAM Bank ------------------------------*/ + + *(vu32 *)0xA0000010 = 0x00001011; + *(vu32 *)0xA0000014 = 0x00000200; + + + return (1); +} +#endif /*DATA_IN_ExtSRAM*/ + +/******************* (C) COPYRIGHT 2008 STMicroelectronics *****END OF FILE****/ + + diff --git a/libcpu/arm/stm32/start_rvds.s b/libcpu/arm/stm32/start_rvds.s new file mode 100644 index 0000000000..ec9419fe07 --- /dev/null +++ b/libcpu/arm/stm32/start_rvds.s @@ -0,0 +1,250 @@ +;******************** (C) COPYRIGHT 2008 STMicroelectronics ********************
+;* File Name : stm32f10x_vector.s
+;* Author : MCD Application Team
+;* Version : V1.1.2
+;* Date : 09/22/2008
+;* Description : STM32F10x vector table for RVMDK toolchain.
+;* This module performs:
+;* - Set the initial SP
+;* - Set the initial PC == Reset_Handler
+;* - Set the vector table entries with the exceptions ISR address
+;* - Configure external SRAM mounted on STM3210E-EVAL board
+;* to be used as data memory (optional, to be enabled by user)
+;* - Branches to __main in the C library (which eventually
+;* calls main()).
+;* After Reset the CortexM3 processor is in Thread mode,
+;* priority is Privileged, and the Stack is set to Main.
+;* <<< Use Configuration Wizard in Context Menu >>>
+;*******************************************************************************
+; THE PRESENT FIRMWARE WHICH IS FOR GUIDANCE ONLY AIMS AT PROVIDING CUSTOMERS
+; WITH CODING INFORMATION REGARDING THEIR PRODUCTS IN ORDER FOR THEM TO SAVE TIME.
+; AS A RESULT, STMICROELECTRONICS SHALL NOT BE HELD LIABLE FOR ANY DIRECT,
+; INDIRECT OR CONSEQUENTIAL DAMAGES WITH RESPECT TO ANY CLAIMS ARISING FROM THE
+; CONTENT OF SUCH FIRMWARE AND/OR THE USE MADE BY CUSTOMERS OF THE CODING
+; INFORMATION CONTAINED HEREIN IN CONNECTION WITH THEIR PRODUCTS.
+;*******************************************************************************
+
+; Amount of memory (in bytes) allocated for Stack
+; Tailor this value to your application needs
+;// <h> Stack Configuration
+;// <o> Stack Size (in Bytes) <0x0-0xFFFFFFFF:8>
+;// </h>
+Stack_Size EQU 0x00000200
+
+ AREA STACK, NOINIT, READWRITE, ALIGN=3
+Stack_Mem SPACE Stack_Size
+
+__initial_sp
+; If you need to use external SRAM mounted on STM3210E-EVAL board as data memory
+; and internal SRAM for Stack, uncomment the following line and comment the line above
+;__initial_sp EQU 0x20000000 + Stack_Size ; "Use MicroLIB" must be checked in
+ ; the Project->Options->Target window
+
+; Amount of memory (in bytes) allocated for Heap
+; Tailor this value to your application needs
+;// <h> Heap Configuration
+;// <o> Heap Size (in Bytes) <0x0-0xFFFFFFFF:8>
+;// </h>
+
+Heap_Size EQU 0x00000000
+
+ AREA HEAP, NOINIT, READWRITE, ALIGN=3
+__heap_base
+Heap_Mem SPACE Heap_Size
+__heap_limit
+
+ THUMB
+ PRESERVE8
+
+ ; Import exceptions handlers
+ IMPORT NMIException
+ IMPORT rt_hw_hard_fault
+ IMPORT MemManageException
+ IMPORT BusFaultException
+ IMPORT UsageFaultException
+ IMPORT SVCHandler
+ IMPORT DebugMonitor
+ IMPORT rt_hw_pend_sv
+ IMPORT SysTickHandler
+ IMPORT WWDG_IRQHandler
+ IMPORT PVD_IRQHandler
+ IMPORT TAMPER_IRQHandler
+ IMPORT RTC_IRQHandler
+ IMPORT FLASH_IRQHandler
+ IMPORT RCC_IRQHandler
+ IMPORT EXTI0_IRQHandler
+ IMPORT EXTI1_IRQHandler
+ IMPORT EXTI2_IRQHandler
+ IMPORT EXTI3_IRQHandler
+ IMPORT EXTI4_IRQHandler
+ IMPORT DMA1_Channel1_IRQHandler
+ IMPORT DMA1_Channel2_IRQHandler
+ IMPORT DMA1_Channel3_IRQHandler
+ IMPORT DMA1_Channel4_IRQHandler
+ IMPORT DMA1_Channel5_IRQHandler
+ IMPORT DMA1_Channel6_IRQHandler
+ IMPORT DMA1_Channel7_IRQHandler
+ IMPORT ADC1_2_IRQHandler
+ IMPORT USB_HP_CAN_TX_IRQHandler
+ IMPORT USB_LP_CAN_RX0_IRQHandler
+ IMPORT CAN_RX1_IRQHandler
+ IMPORT CAN_SCE_IRQHandler
+ IMPORT EXTI9_5_IRQHandler
+ IMPORT TIM1_BRK_IRQHandler
+ IMPORT TIM1_UP_IRQHandler
+ IMPORT TIM1_TRG_COM_IRQHandler
+ IMPORT TIM1_CC_IRQHandler
+ IMPORT TIM2_IRQHandler
+ IMPORT TIM3_IRQHandler
+ IMPORT TIM4_IRQHandler
+ IMPORT I2C1_EV_IRQHandler
+ IMPORT I2C1_ER_IRQHandler
+ IMPORT I2C2_EV_IRQHandler
+ IMPORT I2C2_ER_IRQHandler
+ IMPORT SPI1_IRQHandler
+ IMPORT SPI2_IRQHandler
+ IMPORT USART1_IRQHandler
+ IMPORT USART2_IRQHandler
+ IMPORT USART3_IRQHandler
+ IMPORT EXTI15_10_IRQHandler
+ IMPORT RTCAlarm_IRQHandler
+ IMPORT USBWakeUp_IRQHandler
+ IMPORT TIM8_BRK_IRQHandler
+ IMPORT TIM8_UP_IRQHandler
+ IMPORT TIM8_TRG_COM_IRQHandler
+ IMPORT TIM8_CC_IRQHandler
+ IMPORT ADC3_IRQHandler
+ IMPORT FSMC_IRQHandler
+ IMPORT SDIO_IRQHandler
+ IMPORT TIM5_IRQHandler
+ IMPORT SPI3_IRQHandler
+ IMPORT UART4_IRQHandler
+ IMPORT UART5_IRQHandler
+ IMPORT TIM6_IRQHandler
+ IMPORT TIM7_IRQHandler
+ IMPORT DMA2_Channel1_IRQHandler
+ IMPORT DMA2_Channel2_IRQHandler
+ IMPORT DMA2_Channel3_IRQHandler
+ IMPORT DMA2_Channel4_5_IRQHandler
+
+;*******************************************************************************
+; Fill-up the Vector Table entries with the exceptions ISR address
+;*******************************************************************************
+ AREA RESET, DATA, READONLY
+ EXPORT __Vectors
+
+__Vectors DCD __initial_sp ; Top of Stack
+ DCD Reset_Handler
+ DCD NMIException
+ DCD rt_hw_hard_fault
+ DCD MemManageException
+ DCD BusFaultException
+ DCD UsageFaultException
+ DCD 0 ; Reserved
+ DCD 0 ; Reserved
+ DCD 0 ; Reserved
+ DCD 0 ; Reserved
+ DCD SVCHandler
+ DCD DebugMonitor
+ DCD 0 ; Reserved
+ DCD rt_hw_pend_sv
+ DCD SysTickHandler
+ DCD WWDG_IRQHandler
+ DCD PVD_IRQHandler
+ DCD TAMPER_IRQHandler
+ DCD RTC_IRQHandler
+ DCD FLASH_IRQHandler
+ DCD RCC_IRQHandler
+ DCD EXTI0_IRQHandler
+ DCD EXTI1_IRQHandler
+ DCD EXTI2_IRQHandler
+ DCD EXTI3_IRQHandler
+ DCD EXTI4_IRQHandler
+ DCD DMA1_Channel1_IRQHandler
+ DCD DMA1_Channel2_IRQHandler
+ DCD DMA1_Channel3_IRQHandler
+ DCD DMA1_Channel4_IRQHandler
+ DCD DMA1_Channel5_IRQHandler
+ DCD DMA1_Channel6_IRQHandler
+ DCD DMA1_Channel7_IRQHandler
+ DCD ADC1_2_IRQHandler
+ DCD USB_HP_CAN_TX_IRQHandler
+ DCD USB_LP_CAN_RX0_IRQHandler
+ DCD CAN_RX1_IRQHandler
+ DCD CAN_SCE_IRQHandler
+ DCD EXTI9_5_IRQHandler
+ DCD TIM1_BRK_IRQHandler
+ DCD TIM1_UP_IRQHandler
+ DCD TIM1_TRG_COM_IRQHandler
+ DCD TIM1_CC_IRQHandler
+ DCD TIM2_IRQHandler
+ DCD TIM3_IRQHandler
+ DCD TIM4_IRQHandler
+ DCD I2C1_EV_IRQHandler
+ DCD I2C1_ER_IRQHandler
+ DCD I2C2_EV_IRQHandler
+ DCD I2C2_ER_IRQHandler
+ DCD SPI1_IRQHandler
+ DCD SPI2_IRQHandler
+ DCD USART1_IRQHandler
+ DCD USART2_IRQHandler
+ DCD USART3_IRQHandler
+ DCD EXTI15_10_IRQHandler
+ DCD RTCAlarm_IRQHandler
+ DCD USBWakeUp_IRQHandler
+ DCD TIM8_BRK_IRQHandler
+ DCD TIM8_UP_IRQHandler
+ DCD TIM8_TRG_COM_IRQHandler
+ DCD TIM8_CC_IRQHandler
+ DCD ADC3_IRQHandler
+ DCD FSMC_IRQHandler
+ DCD SDIO_IRQHandler
+ DCD TIM5_IRQHandler
+ DCD SPI3_IRQHandler
+ DCD UART4_IRQHandler
+ DCD UART5_IRQHandler
+ DCD TIM6_IRQHandler
+ DCD TIM7_IRQHandler
+ DCD DMA2_Channel1_IRQHandler
+ DCD DMA2_Channel2_IRQHandler
+ DCD DMA2_Channel3_IRQHandler
+ DCD DMA2_Channel4_5_IRQHandler
+
+ AREA |.text|, CODE, READONLY
+
+; Reset handler routine
+Reset_Handler PROC
+ EXPORT Reset_Handler
+
+ IMPORT __main
+ LDR R0, =__main
+ BX R0
+ ENDP
+
+ ALIGN
+
+;*******************************************************************************
+; User Stack and Heap initialization
+;*******************************************************************************
+ 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, = Heap_Mem
+ LDR R1, = (Stack_Mem + Stack_Size)
+ LDR R2, = (Heap_Mem + Heap_Size)
+ LDR R3, = Stack_Mem
+ BX LR
+
+ ALIGN
+
+ ENDIF
+
+ END
+
+;******************* (C) COPYRIGHT 2008 STMicroelectronics *****END OF FILE*****
|
