Merge branch 'master' of https://github.com/RT-Thread/rt-thread
This commit is contained in:
commit
c5927f51b3
|
@ -12,14 +12,14 @@ TextBase = '0x30000000'
|
|||
CROSS_TOOL = 'gcc'
|
||||
|
||||
if os.getenv('RTT_CC'):
|
||||
CROSS_TOOL = os.getenv('RTT_CC')
|
||||
CROSS_TOOL = os.getenv('RTT_CC')
|
||||
|
||||
if CROSS_TOOL == 'gcc':
|
||||
PLATFORM = 'gcc'
|
||||
EXEC_PATH = 'C:/Program Files/CodeSourcery/Sourcery G++ Lite/bin'
|
||||
PLATFORM = 'gcc'
|
||||
EXEC_PATH = 'C:/Program Files/CodeSourcery/Sourcery G++ Lite/bin'
|
||||
elif CROSS_TOOL == 'keil':
|
||||
PLATFORM = 'armcc'
|
||||
EXEC_PATH = 'C:/Keil'
|
||||
PLATFORM = 'armcc'
|
||||
EXEC_PATH = 'C:/Keil'
|
||||
elif CROSS_TOOL == 'iar':
|
||||
print '================ERROR============================'
|
||||
print 'Not support iar yet!'
|
||||
|
|
|
@ -17,9 +17,6 @@
|
|||
#include "system.h"
|
||||
#include "het.h"
|
||||
|
||||
int ulRegTest1Counter;
|
||||
int ulRegTest2Counter;
|
||||
|
||||
static rt_uint8_t user_thread_stack[512];
|
||||
static struct rt_thread user_thread;
|
||||
static void user_thread_entry(void *p)
|
||||
|
@ -35,28 +32,11 @@ static void user_thread_entry(void *p)
|
|||
}
|
||||
}
|
||||
|
||||
static rt_uint8_t test_thread_stack[512];
|
||||
static struct rt_thread test_thread;
|
||||
void vRegTestTask1(void*);
|
||||
|
||||
static rt_uint8_t test_thread_stack2[512];
|
||||
static struct rt_thread test_thread2;
|
||||
void vRegTestTask2(void*);
|
||||
|
||||
int rt_application_init()
|
||||
{
|
||||
rt_thread_init(&user_thread, "user1", user_thread_entry, RT_NULL,
|
||||
user_thread_stack, sizeof(user_thread_stack), 21, 20);
|
||||
rt_thread_startup(&user_thread);
|
||||
|
||||
rt_thread_init(&test_thread, "test1", vRegTestTask1, RT_NULL,
|
||||
test_thread_stack, sizeof(test_thread_stack), 21, 20);
|
||||
rt_thread_startup(&test_thread);
|
||||
|
||||
rt_thread_init(&test_thread2, "test2", vRegTestTask2, RT_NULL,
|
||||
test_thread_stack2, sizeof(test_thread_stack2), 22, 20);
|
||||
rt_thread_startup(&test_thread2);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -1,472 +0,0 @@
|
|||
;/*
|
||||
; FreeRTOS V7.4.2 - Copyright (C) 2013 Real Time Engineers Ltd.
|
||||
;
|
||||
;
|
||||
; ***************************************************************************
|
||||
; * *
|
||||
; * FreeRTOS tutorial books are available in pdf and paperback. *
|
||||
; * Complete, revised, and edited pdf reference manuals are also *
|
||||
; * available. *
|
||||
; * *
|
||||
; * Purchasing FreeRTOS documentation will not only help you, by *
|
||||
; * ensuring you get running as quickly as possible and with an *
|
||||
; * in-depth knowledge of how to use FreeRTOS, it will also help *
|
||||
; * the FreeRTOS project to continue with its mission of providing *
|
||||
; * professional grade, cross platform, de facto standard solutions *
|
||||
; * for microcontrollers - completely free of charge! *
|
||||
; * *
|
||||
; * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *
|
||||
; * *
|
||||
; * Thank you for using FreeRTOS, and thank you for your support! *
|
||||
; * *
|
||||
; ***************************************************************************
|
||||
;
|
||||
;
|
||||
; This file is part of the FreeRTOS distribution.
|
||||
;
|
||||
; FreeRTOS is free software; you can redistribute it and/or modify it under
|
||||
; the terms of the GNU General Public License (version 2) as published by the
|
||||
; Free Software Foundation AND MODIFIED BY the FreeRTOS exception.
|
||||
; >>>NOTE<<< The modification to the GPL is included to allow you to
|
||||
; distribute a combined work that includes FreeRTOS without being obliged to
|
||||
; provide the source code for proprietary components outside of the FreeRTOS
|
||||
; kernel. FreeRTOS is distributed in the hope that it will be useful, but
|
||||
; WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
|
||||
; or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
||||
; more details. You should have received a copy of the GNU General Public
|
||||
; License and the FreeRTOS license exception along with FreeRTOS; if not it
|
||||
; can be viewed here: http://www.freertos.org/a00114.html and also obtained
|
||||
; by writing to Richard Barry, contact details for whom are available on the
|
||||
; FreeRTOS WEB site.
|
||||
;
|
||||
; 1 tab == 4 spaces!
|
||||
;
|
||||
; ***************************************************************************
|
||||
; * *
|
||||
; * Having a problem? Start by reading the FAQ "My application does *
|
||||
; * not run, what could be wrong? *
|
||||
; * *
|
||||
; * http://www.FreeRTOS.org/FAQHelp.html *
|
||||
; * *
|
||||
; ***************************************************************************
|
||||
;
|
||||
;
|
||||
; http://www.FreeRTOS.org - Documentation, training, latest information,
|
||||
; license and contact details.
|
||||
;
|
||||
; http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,
|
||||
; including FreeRTOS+Trace - an indispensable productivity tool.
|
||||
;
|
||||
; Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell
|
||||
; the code with commercial support, indemnification, and middleware, under
|
||||
; the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also
|
||||
; provide a safety engineered and independently SIL3 certified version under
|
||||
; the SafeRTOS brand: http://www.SafeRTOS.com.
|
||||
;*/
|
||||
|
||||
;-------------------------------------------------
|
||||
; port to RT-Thread by Grissiom
|
||||
;
|
||||
.def vRegTestTask1
|
||||
.ref ulRegTest1Counter
|
||||
.ref rt_thread_delay
|
||||
|
||||
.text
|
||||
.arm
|
||||
|
||||
vRegTestTask1:
|
||||
; Fill each general purpose register with a known value.
|
||||
mov r0, #0xFF
|
||||
mov r1, #0x11
|
||||
mov r2, #0x22
|
||||
mov r3, #0x33
|
||||
mov r4, #0x44
|
||||
mov r5, #0x55
|
||||
mov r6, #0x66
|
||||
mov r7, #0x77
|
||||
mov r8, #0x88
|
||||
mov r9, #0x99
|
||||
mov r10, #0xAA
|
||||
mov r11, #0xBB
|
||||
mov r12, #0xCC
|
||||
mov r14, #0xEE
|
||||
|
||||
.if (__TI_VFP_SUPPORT__)
|
||||
; Fill each FPU register with a known value.
|
||||
vmov d0, r0, r1
|
||||
vmov d1, r2, r3
|
||||
vmov d2, r4, r5
|
||||
vmov d3, r6, r7
|
||||
vmov d4, r8, r9
|
||||
vmov d5, r10, r11
|
||||
vmov d6, r0, r1
|
||||
vmov d7, r2, r3
|
||||
vmov d8, r4, r5
|
||||
vmov d9, r6, r7
|
||||
vmov d10, r8, r9
|
||||
vmov d11, r10, r11
|
||||
vmov d12, r0, r1
|
||||
vmov d13, r2, r3
|
||||
vmov d14, r4, r5
|
||||
vmov d15, r6, r7
|
||||
.endif
|
||||
|
||||
|
||||
vRegTestLoop1:
|
||||
|
||||
STMFD sp!, {r0-r3, r12}
|
||||
; Force yeild
|
||||
MOV r0, #5
|
||||
BL rt_thread_delay
|
||||
LDMFD sp!, {r0-r3, r12}
|
||||
|
||||
.if (__TI_VFP_SUPPORT__)
|
||||
; Check all the VFP registers still contain the values set above.
|
||||
; First save registers that are clobbered by the test.
|
||||
STMFD sp!, { r0-r1 }
|
||||
|
||||
vmov r0, r1, d0
|
||||
cmp r0, #0xFF
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x11
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d1
|
||||
cmp r0, #0x22
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x33
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d2
|
||||
cmp r0, #0x44
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x55
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d3
|
||||
cmp r0, #0x66
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x77
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d4
|
||||
cmp r0, #0x88
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x99
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d5
|
||||
cmp r0, #0xAA
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0xBB
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d6
|
||||
cmp r0, #0xFF
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x11
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d7
|
||||
cmp r0, #0x22
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x33
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d8
|
||||
cmp r0, #0x44
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x55
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d9
|
||||
cmp r0, #0x66
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x77
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d10
|
||||
cmp r0, #0x88
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x99
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d11
|
||||
cmp r0, #0xAA
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0xBB
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d12
|
||||
cmp r0, #0xFF
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x11
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d13
|
||||
cmp r0, #0x22
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x33
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d14
|
||||
cmp r0, #0x44
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x55
|
||||
bne reg1_error_loopf
|
||||
vmov r0, r1, d15
|
||||
cmp r0, #0x66
|
||||
bne reg1_error_loopf
|
||||
cmp r1, #0x77
|
||||
bne reg1_error_loopf
|
||||
|
||||
; Restore the registers that were clobbered by the test.
|
||||
LDMFD sp!, {r0-r1}
|
||||
|
||||
; VFP register test passed. Jump to the core register test.
|
||||
b reg1_loopf_pass
|
||||
|
||||
reg1_error_loopf:
|
||||
; If this line is hit then a VFP register value was found to be
|
||||
; incorrect.
|
||||
b reg1_error_loopf
|
||||
|
||||
reg1_loopf_pass:
|
||||
|
||||
.endif ;__TI_VFP_SUPPORT__
|
||||
|
||||
; Test each general purpose register to check that it still contains the
|
||||
; expected known value, jumping to vRegTestError1 if any register contains
|
||||
; an unexpected value.
|
||||
cmp r0, #0xFF
|
||||
bne vRegTestError1
|
||||
cmp r1, #0x11
|
||||
bne vRegTestError1
|
||||
cmp r2, #0x22
|
||||
bne vRegTestError1
|
||||
cmp r3, #0x33
|
||||
bne vRegTestError1
|
||||
cmp r4, #0x44
|
||||
bne vRegTestError1
|
||||
cmp r5, #0x55
|
||||
bne vRegTestError1
|
||||
cmp r6, #0x66
|
||||
bne vRegTestError1
|
||||
cmp r7, #0x77
|
||||
bne vRegTestError1
|
||||
cmp r8, #0x88
|
||||
bne vRegTestError1
|
||||
cmp r9, #0x99
|
||||
bne vRegTestError1
|
||||
cmp r10, #0xAA
|
||||
bne vRegTestError1
|
||||
cmp r11, #0xBB
|
||||
bne vRegTestError1
|
||||
cmp r12, #0xCC
|
||||
bne vRegTestError1
|
||||
|
||||
; This task is still running without jumping to vRegTestError1, so increment
|
||||
; the loop counter so the check task knows the task is running error free.
|
||||
stmfd sp!, { r0-r1 }
|
||||
ldr r0, Count1Const
|
||||
ldr r1, [r0]
|
||||
add r1, r1, #1
|
||||
str r1, [r0]
|
||||
ldmfd sp!, { r0-r1 }
|
||||
|
||||
; Loop again, performing the same tests.
|
||||
b vRegTestLoop1
|
||||
|
||||
Count1Const .word ulRegTest1Counter
|
||||
|
||||
vRegTestError1:
|
||||
b vRegTestError1
|
||||
|
||||
|
||||
;-------------------------------------------------
|
||||
;
|
||||
.def vRegTestTask2
|
||||
.ref ulRegTest2Counter
|
||||
.text
|
||||
.arm
|
||||
;
|
||||
vRegTestTask2:
|
||||
; Fill each general purpose register with a known value.
|
||||
mov r0, #0xFF000000
|
||||
mov r1, #0x11000000
|
||||
mov r2, #0x22000000
|
||||
mov r3, #0x33000000
|
||||
mov r4, #0x44000000
|
||||
mov r5, #0x55000000
|
||||
mov r6, #0x66000000
|
||||
mov r7, #0x77000000
|
||||
mov r8, #0x88000000
|
||||
mov r9, #0x99000000
|
||||
mov r10, #0xAA000000
|
||||
mov r11, #0xBB000000
|
||||
mov r12, #0xCC000000
|
||||
mov r14, #0xEE000000
|
||||
|
||||
.if (__TI_VFP_SUPPORT__)
|
||||
|
||||
; Fill each FPU register with a known value.
|
||||
vmov d0, r0, r1
|
||||
vmov d1, r2, r3
|
||||
vmov d2, r4, r5
|
||||
vmov d3, r6, r7
|
||||
vmov d4, r8, r9
|
||||
vmov d5, r10, r11
|
||||
vmov d6, r0, r1
|
||||
vmov d7, r2, r3
|
||||
vmov d8, r4, r5
|
||||
vmov d9, r6, r7
|
||||
vmov d10, r8, r9
|
||||
vmov d11, r10, r11
|
||||
vmov d12, r0, r1
|
||||
vmov d13, r2, r3
|
||||
vmov d14, r4, r5
|
||||
vmov d15, r6, r7
|
||||
.endif
|
||||
|
||||
vRegTestLoop2:
|
||||
|
||||
.if (__TI_VFP_SUPPORT__)
|
||||
; Check all the VFP registers still contain the values set above.
|
||||
; First save registers that are clobbered by the test.
|
||||
STMFD sp!, { r0-r1 }
|
||||
|
||||
vmov r0, r1, d0
|
||||
cmp r0, #0xFF000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x11000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d1
|
||||
cmp r0, #0x22000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x33000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d2
|
||||
cmp r0, #0x44000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x55000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d3
|
||||
cmp r0, #0x66000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x77000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d4
|
||||
cmp r0, #0x88000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x99000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d5
|
||||
cmp r0, #0xAA000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0xBB000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d6
|
||||
cmp r0, #0xFF000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x11000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d7
|
||||
cmp r0, #0x22000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x33000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d8
|
||||
cmp r0, #0x44000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x55000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d9
|
||||
cmp r0, #0x66000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x77000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d10
|
||||
cmp r0, #0x88000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x99000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d11
|
||||
cmp r0, #0xAA000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0xBB000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d12
|
||||
cmp r0, #0xFF000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x11000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d13
|
||||
cmp r0, #0x22000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x33000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d14
|
||||
cmp r0, #0x44000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x55000000
|
||||
bne reg2_error_loopf
|
||||
vmov r0, r1, d15
|
||||
cmp r0, #0x66000000
|
||||
bne reg2_error_loopf
|
||||
cmp r1, #0x77000000
|
||||
bne reg2_error_loopf
|
||||
|
||||
; Restore the registers that were clobbered by the test.
|
||||
LDMFD sp!, {r0-r1}
|
||||
|
||||
; VFP register test passed. Jump to the core register test.
|
||||
b reg2_loopf_pass
|
||||
|
||||
reg2_error_loopf:
|
||||
; If this line is hit then a VFP register value was found to be
|
||||
; incorrect.
|
||||
b reg2_error_loopf
|
||||
|
||||
reg2_loopf_pass:
|
||||
|
||||
.endif ;__TI_VFP_SUPPORT__
|
||||
|
||||
; Test each general purpose register to check that it still contains the
|
||||
; expected known value, jumping to vRegTestError2 if any register contains
|
||||
; an unexpected value.
|
||||
cmp r0, #0xFF000000
|
||||
bne vRegTestError2
|
||||
cmp r1, #0x11000000
|
||||
bne vRegTestError2
|
||||
cmp r2, #0x22000000
|
||||
bne vRegTestError2
|
||||
cmp r3, #0x33000000
|
||||
bne vRegTestError2
|
||||
cmp r4, #0x44000000
|
||||
bne vRegTestError2
|
||||
cmp r5, #0x55000000
|
||||
bne vRegTestError2
|
||||
cmp r6, #0x66000000
|
||||
bne vRegTestError2
|
||||
cmp r7, #0x77000000
|
||||
bne vRegTestError2
|
||||
cmp r8, #0x88000000
|
||||
bne vRegTestError2
|
||||
cmp r9, #0x99000000
|
||||
bne vRegTestError2
|
||||
cmp r10, #0xAA000000
|
||||
bne vRegTestError2
|
||||
cmp r11, #0xBB000000
|
||||
bne vRegTestError2
|
||||
cmp r12, #0xCC000000
|
||||
bne vRegTestError2
|
||||
cmp r14, #0xEE000000
|
||||
bne vRegTestError2
|
||||
|
||||
; This task is still running without jumping to vRegTestError2, so increment
|
||||
; the loop counter so the check task knows the task is running error free.
|
||||
stmfd sp!, { r0-r1 }
|
||||
ldr r0, Count2Const
|
||||
ldr r1, [r0]
|
||||
add r1, r1, #1
|
||||
str r1, [r0]
|
||||
ldmfd sp!, { r0-r1 }
|
||||
|
||||
; Loop again, performing the same tests.
|
||||
b vRegTestLoop2
|
||||
|
||||
Count2Const .word ulRegTest2Counter
|
||||
|
||||
vRegTestError2:
|
||||
b vRegTestError2
|
||||
|
||||
;-------------------------------------------------
|
||||
|
||||
|
||||
|
|
@ -48,6 +48,11 @@ extern unsigned char * const system_data_end;
|
|||
*/
|
||||
void rtthread_startup(void)
|
||||
{
|
||||
/*// RM48 does not have cache implemented
|
||||
*rt_hw_cpu_icache_enable();
|
||||
*rt_hw_cpu_dcache_enable();
|
||||
*/
|
||||
|
||||
/* init hardware interrupt */
|
||||
rt_hw_interrupt_init();
|
||||
|
||||
|
|
|
@ -212,6 +212,7 @@
|
|||
// </section>
|
||||
|
||||
#define RT_VFP_LAZY_STACKING
|
||||
#define RT_USING_CPU_FFS
|
||||
// </RDTConfigurator>
|
||||
|
||||
#endif
|
||||
|
|
|
@ -33,9 +33,6 @@ objs = PrepareBuilding(env, RTT_ROOT)
|
|||
# STM32 firemare library building script
|
||||
objs = objs + SConscript( GetCurrentDir() + '/Libraries/SConscript', variant_dir='build/bsp/Libraries', duplicate=0)
|
||||
|
||||
if GetDepend('RT_USING_RTGUI'):
|
||||
objs = objs + SConscript(RTT_ROOT + '/examples/gui/SConscript', variant_dir='build/examples/gui', duplicate=0)
|
||||
|
||||
# build program
|
||||
env.Program(TARGET, objs)
|
||||
|
||||
|
|
|
@ -368,6 +368,7 @@ typedef struct ureqest* ureq_t;
|
|||
#define SCSI_INQUIRY_CMD 0x12
|
||||
#define SCSI_ALLOW_MEDIUM_REMOVAL 0x1e
|
||||
#define SCSI_MODE_SENSE_6 0x1a
|
||||
#define SCSI_START_STOP 0x1b
|
||||
#define SCSI_READ_CAPACITIES 0x23
|
||||
#define SCSI_READ_CAPACITY 0x25
|
||||
#define SCSI_READ_10 0x28
|
||||
|
|
|
@ -146,6 +146,11 @@ enum udev_msg_type
|
|||
USB_MSG_DATA_NOTIFY,
|
||||
USB_MSG_SOF,
|
||||
USB_MSG_RESET,
|
||||
/* we don't need to add a "PLUG_IN" event because after the cable is
|
||||
* plugged in(before any SETUP) the classed have nothing to do. If the host
|
||||
* is ready, it will send RESET and we will have USB_MSG_RESET. So, a RESET
|
||||
* should reset and run the class while plug_in is not. */
|
||||
USB_MSG_PLUG_OUT,
|
||||
};
|
||||
typedef enum udev_msg_type udev_msg_type;
|
||||
|
||||
|
|
|
@ -33,6 +33,7 @@ static rt_device_t disk;
|
|||
static rt_uint32_t _block;
|
||||
static rt_uint32_t _count, _size;
|
||||
static struct rt_device_blk_geometry geometry;
|
||||
static rt_uint32_t _removed = 0;
|
||||
|
||||
static struct udevice_descriptor dev_desc =
|
||||
{
|
||||
|
@ -126,13 +127,13 @@ static rt_err_t _request_sense(udevice_t device, uep_t ep_in)
|
|||
|
||||
data.ErrorCode = 0x70;
|
||||
data.Valid = 0;
|
||||
data.SenseKey = 5;
|
||||
data.SenseKey = 2; //TODO
|
||||
data.Information[0] = 0;
|
||||
data.Information[1] = 0;
|
||||
data.Information[2] = 0;
|
||||
data.Information[3] = 0;
|
||||
data.AdditionalSenseLength = 0x0b;
|
||||
data.AdditionalSenseCode = 0x20;
|
||||
data.AdditionalSenseLength = 0x0a;
|
||||
data.AdditionalSenseCode = 0x3a; //TODO
|
||||
data.AdditionalSenseCodeQualifier =0;
|
||||
|
||||
dcd_ep_write(device->dcd, ep_in, (rt_uint8_t*)&data, sizeof(struct request_sense_data));
|
||||
|
@ -299,6 +300,19 @@ static rt_err_t _verify_10(udevice_t device)
|
|||
return RT_EOK;
|
||||
}
|
||||
|
||||
static void _send_status(udevice_t device, mass_eps_t eps, ustorage_csw_t csw)
|
||||
{
|
||||
dcd_ep_write(device->dcd, eps->ep_in, (rt_uint8_t*)csw, SIZEOF_CSW);
|
||||
dcd_ep_read(device->dcd, eps->ep_out, eps->ep_out->buffer, SIZEOF_CBW);
|
||||
status = STATUS_CBW;
|
||||
}
|
||||
|
||||
static void _start_stop(ustorage_cbw_t cbw)
|
||||
{
|
||||
//TODO
|
||||
_removed = 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* This function will handle mass storage bulk in endpoint request.
|
||||
*
|
||||
|
@ -313,13 +327,11 @@ static rt_err_t _ep_in_handler(udevice_t device, uclass_t cls, rt_size_t size)
|
|||
RT_ASSERT(device != RT_NULL);
|
||||
|
||||
eps = cls->eps;
|
||||
if(status == STATUS_CSW)
|
||||
if (status == STATUS_CSW)
|
||||
{
|
||||
dcd_ep_write(device->dcd, eps->ep_in, (rt_uint8_t*)&csw, SIZEOF_CSW);
|
||||
status = STATUS_CBW;
|
||||
dcd_ep_read(device->dcd, eps->ep_out, eps->ep_out->buffer, SIZEOF_CBW);
|
||||
_send_status(device, eps, &csw);
|
||||
}
|
||||
if(status == STATUS_SEND)
|
||||
else if (status == STATUS_SEND)
|
||||
{
|
||||
rt_device_read(disk, _block, eps->ep_in->buffer, 1);
|
||||
dcd_ep_write(device->dcd, eps->ep_in, eps->ep_in->buffer,
|
||||
|
@ -388,8 +400,8 @@ static rt_err_t _ep_out_handler(udevice_t device, uclass_t cls, rt_size_t size)
|
|||
switch(cbw->cb[0])
|
||||
{
|
||||
case SCSI_TEST_UNIT_READY:
|
||||
dcd_ep_write(device->dcd, eps->ep_in, (rt_uint8_t*)&csw, SIZEOF_CSW);
|
||||
dcd_ep_read(device->dcd, eps->ep_out, eps->ep_out->buffer, SIZEOF_CBW);
|
||||
csw.status = _removed;
|
||||
_send_status(device, eps, &csw);
|
||||
break;
|
||||
case SCSI_REQUEST_SENSE:
|
||||
_request_sense(device, eps->ep_in);
|
||||
|
@ -404,8 +416,7 @@ static rt_err_t _ep_out_handler(udevice_t device, uclass_t cls, rt_size_t size)
|
|||
status = STATUS_CSW;
|
||||
break;
|
||||
case SCSI_ALLOW_MEDIUM_REMOVAL:
|
||||
dcd_ep_write(device->dcd, eps->ep_in, (rt_uint8_t*)&csw, SIZEOF_CSW);
|
||||
dcd_ep_read(device->dcd, eps->ep_out, eps->ep_out->buffer, SIZEOF_CBW);
|
||||
_send_status(device, eps, &csw);
|
||||
break;
|
||||
case SCSI_READ_CAPACITIES:
|
||||
_read_capacities(device, eps->ep_in);
|
||||
|
@ -425,6 +436,10 @@ static rt_err_t _ep_out_handler(udevice_t device, uclass_t cls, rt_size_t size)
|
|||
case SCSI_VERIFY_10:
|
||||
_verify_10(device);
|
||||
break;
|
||||
case SCSI_START_STOP:
|
||||
_start_stop(cbw);
|
||||
_send_status(device, eps, &csw);
|
||||
break;
|
||||
}
|
||||
}
|
||||
else if(status == STATUS_RECEIVE)
|
||||
|
@ -439,9 +454,7 @@ static rt_err_t _ep_out_handler(udevice_t device, uclass_t cls, rt_size_t size)
|
|||
_block ++;
|
||||
if(_size == 0)
|
||||
{
|
||||
dcd_ep_write(device->dcd, eps->ep_in, (rt_uint8_t*)&csw, SIZEOF_CSW);
|
||||
dcd_ep_read(device->dcd, eps->ep_out, eps->ep_out->buffer, SIZEOF_CBW);
|
||||
status = STATUS_CBW;
|
||||
_send_status(device, eps, &csw);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
|
@ -666,6 +666,60 @@ rt_err_t _sof_notify(udevice_t device)
|
|||
return RT_EOK;
|
||||
}
|
||||
|
||||
/**
|
||||
* This function will stop all class.
|
||||
*
|
||||
* @param device the usb device object.
|
||||
*
|
||||
* @return RT_EOK.
|
||||
*/
|
||||
rt_err_t _stop_notify(udevice_t device)
|
||||
{
|
||||
struct rt_list_node *i;
|
||||
uclass_t cls;
|
||||
|
||||
RT_ASSERT(device != RT_NULL);
|
||||
|
||||
/* to notity every class that sof event comes */
|
||||
for (i = device->curr_cfg->cls_list.next;
|
||||
i != &device->curr_cfg->cls_list;
|
||||
i = i->next)
|
||||
{
|
||||
cls = (uclass_t)rt_list_entry(i, struct uclass, list);
|
||||
if(cls->ops->stop != RT_NULL)
|
||||
cls->ops->stop(device, cls);
|
||||
}
|
||||
|
||||
return RT_EOK;
|
||||
}
|
||||
|
||||
/**
|
||||
* This function will run all class.
|
||||
*
|
||||
* @param device the usb device object.
|
||||
*
|
||||
* @return RT_EOK.
|
||||
*/
|
||||
rt_err_t _run_notify(udevice_t device)
|
||||
{
|
||||
struct rt_list_node *i;
|
||||
uclass_t cls;
|
||||
|
||||
RT_ASSERT(device != RT_NULL);
|
||||
|
||||
/* to notity every class that sof event comes */
|
||||
for (i = device->curr_cfg->cls_list.next;
|
||||
i != &device->curr_cfg->cls_list;
|
||||
i = i->next)
|
||||
{
|
||||
cls = (uclass_t)rt_list_entry(i, struct uclass, list);
|
||||
if(cls->ops->run != RT_NULL)
|
||||
cls->ops->run(device, cls);
|
||||
}
|
||||
|
||||
return RT_EOK;
|
||||
}
|
||||
|
||||
/**
|
||||
* This function will reset all class.
|
||||
*
|
||||
|
@ -680,17 +734,8 @@ rt_err_t _reset_notify(udevice_t device)
|
|||
|
||||
RT_ASSERT(device != RT_NULL);
|
||||
|
||||
/* to notity every class that sof event comes */
|
||||
for (i=device->curr_cfg->cls_list.next;
|
||||
i!=&device->curr_cfg->cls_list; i=i->next)
|
||||
{
|
||||
cls = (uclass_t)rt_list_entry(i, struct uclass, list);
|
||||
if(cls->ops->stop != RT_NULL)
|
||||
cls->ops->stop(device, cls);
|
||||
|
||||
if(cls->ops->run != RT_NULL)
|
||||
cls->ops->run(device, cls);
|
||||
}
|
||||
_stop_notify(device);
|
||||
_run_notify(device);
|
||||
|
||||
return RT_EOK;
|
||||
}
|
||||
|
@ -1402,6 +1447,10 @@ static void rt_usbd_thread_entry(void* parameter)
|
|||
_sof_notify(device);
|
||||
break;
|
||||
case USB_MSG_DATA_NOTIFY:
|
||||
/* some buggy drivers will have USB_MSG_DATA_NOTIFY before the core
|
||||
* got configured. */
|
||||
if (device->state != USB_STATE_CONFIGURED)
|
||||
break;
|
||||
ep = rt_usbd_find_endpoint(device, &cls, msg.content.ep_msg.ep_addr);
|
||||
if(ep != RT_NULL)
|
||||
ep->handler(device, cls, msg.content.ep_msg.size);
|
||||
|
@ -1415,6 +1464,9 @@ static void rt_usbd_thread_entry(void* parameter)
|
|||
if (device->state == USB_STATE_ADDRESS)
|
||||
_reset_notify(device);
|
||||
break;
|
||||
case USB_MSG_PLUG_OUT:
|
||||
_stop_notify(device);
|
||||
break;
|
||||
default:
|
||||
rt_kprintf("unknown msg type\n");
|
||||
break;
|
||||
|
|
|
@ -147,6 +147,17 @@ typedef rt_base_t rt_off_t; /**< Type for offset */
|
|||
#define ALIGN(n) __declspec(align(n))
|
||||
#define rt_inline static __inline
|
||||
#define RTT_API
|
||||
#elif defined (__TI_COMPILER_VERSION__)
|
||||
/* The way that TI compiler set section is different from other(at least
|
||||
* GCC and MDK) compilers. See ARM Optimizing C/C++ Compiler 5.9.3 for more
|
||||
* details. */
|
||||
#define SECTION(x)
|
||||
#define UNUSED
|
||||
#define ALIGN(n)
|
||||
#define rt_inline static inline
|
||||
#define RTT_API
|
||||
#else
|
||||
#error not supported tool chain
|
||||
#endif
|
||||
|
||||
/* initialization export */
|
||||
|
|
|
@ -13,6 +13,7 @@
|
|||
* 2012-06-01 aozima set pendsv priority to 0xFF.
|
||||
* 2012-08-17 aozima fixed bug: store r8 - r11.
|
||||
* 2013-02-20 aozima port to gcc.
|
||||
* 2013-06-18 aozima add restore MSP feature.
|
||||
*/
|
||||
|
||||
.cpu cortex-m3
|
||||
|
@ -21,6 +22,7 @@
|
|||
.thumb
|
||||
.text
|
||||
|
||||
.equ SCB_VTOR, 0xE000ED04 /* Vector Table Offset Register */
|
||||
.equ ICSR, 0xE000ED04 /* interrupt control state register */
|
||||
.equ PENDSVSET_BIT, 0x10000000 /* value to trigger PendSV exception */
|
||||
|
||||
|
@ -152,6 +154,13 @@ rt_hw_context_switch_to:
|
|||
LDR R1, =PENDSVSET_BIT
|
||||
STR R1, [R0]
|
||||
|
||||
/* restore MSP */
|
||||
LDR r0, =SCB_VTOR
|
||||
LDR r0, [r0]
|
||||
LDR r0, [r0]
|
||||
NOP
|
||||
MSR msp, r0
|
||||
|
||||
CPSIE I /* enable interrupts at processor level */
|
||||
|
||||
/* never reach here! */
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
; * 2010-01-25 Bernard first version
|
||||
; * 2012-06-01 aozima set pendsv priority to 0xFF.
|
||||
; * 2012-08-17 aozima fixed bug: store r8 - r11.
|
||||
; * 2013-06-18 aozima add restore MSP feature.
|
||||
; */
|
||||
|
||||
;/**
|
||||
|
@ -19,6 +20,7 @@
|
|||
; */
|
||||
;/*@{*/
|
||||
|
||||
SCB_VTOR EQU 0xE000ED08 ; Vector Table Offset Register
|
||||
NVIC_INT_CTRL EQU 0xE000ED04 ; interrupt control state register
|
||||
NVIC_SHPR3 EQU 0xE000ED20 ; system priority register (2)
|
||||
NVIC_PENDSV_PRI EQU 0x00FF0000 ; PendSV priority value (lowest)
|
||||
|
@ -178,6 +180,13 @@ rt_hw_context_switch_to:
|
|||
STR r1, [r0]
|
||||
NOP
|
||||
|
||||
; restore MSP
|
||||
LDR r0, =SCB_VTOR
|
||||
LDR r0, [r0]
|
||||
LDR r0, [r0]
|
||||
NOP
|
||||
MSR msp, r0
|
||||
|
||||
; enable interrupts at processor level
|
||||
CPSIE I
|
||||
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
; * 2010-01-25 Bernard first version
|
||||
; * 2012-06-01 aozima set pendsv priority to 0xFF.
|
||||
; * 2012-08-17 aozima fixed bug: store r8 - r11.
|
||||
; * 2013-06-18 aozima add restore MSP feature.
|
||||
; */
|
||||
|
||||
;/**
|
||||
|
@ -19,6 +20,7 @@
|
|||
; */
|
||||
;/*@{*/
|
||||
|
||||
SCB_VTOR EQU 0xE000ED08 ; Vector Table Offset Register
|
||||
NVIC_INT_CTRL EQU 0xE000ED04 ; interrupt control state register
|
||||
NVIC_SHPR3 EQU 0xE000ED20 ; system priority register (2)
|
||||
NVIC_PENDSV_PRI EQU 0x00FF0000 ; PendSV priority value (lowest)
|
||||
|
@ -183,6 +185,13 @@ rt_hw_context_switch_to PROC
|
|||
STR r1, [r0]
|
||||
NOP
|
||||
|
||||
; restore MSP
|
||||
LDR r0, =SCB_VTOR
|
||||
LDR r0, [r0]
|
||||
LDR r0, [r0]
|
||||
NOP
|
||||
MSR msp, r0
|
||||
|
||||
; enable interrupts at processor level
|
||||
CPSIE I
|
||||
|
||||
|
|
|
@ -10,161 +10,170 @@
|
|||
* Change Logs:
|
||||
* Date Author Notes
|
||||
* 2009-10-11 Bernard First version
|
||||
* 2010-12-29 onelife Modify for EFM32
|
||||
* 2011-06-17 onelife Merge all of the assembly source code into context_gcc.S
|
||||
* 2011-07-12 onelife Add interrupt context check function
|
||||
* 2010-12-29 onelife Modify for EFM32
|
||||
* 2011-06-17 onelife Merge all of the assembly source code into context_gcc.S
|
||||
* 2011-07-12 onelife Add interrupt context check function
|
||||
* 2013-06-18 aozima add restore MSP feature.
|
||||
*/
|
||||
|
||||
.cpu cortex-m3
|
||||
.fpu softvfp
|
||||
.syntax unified
|
||||
.thumb
|
||||
.text
|
||||
.cpu cortex-m3
|
||||
.fpu softvfp
|
||||
.syntax unified
|
||||
.thumb
|
||||
.text
|
||||
|
||||
.equ ICSR, 0xE000ED04 /* interrupt control state register */
|
||||
.equ PENDSVSET_BIT, 0x10000000 /* value to trigger PendSV exception */
|
||||
|
||||
.equ SHPR3, 0xE000ED20 /* system priority register (3) */
|
||||
.equ PENDSV_PRI_LOWEST, 0x00FF0000 /* PendSV priority value (lowest) */
|
||||
.equ SCB_VTOR, 0xE000ED04 /* Vector Table Offset Register */
|
||||
.equ ICSR, 0xE000ED04 /* interrupt control state register */
|
||||
.equ PENDSVSET_BIT, 0x10000000 /* value to trigger PendSV exception */
|
||||
|
||||
.equ SHPR3, 0xE000ED20 /* system priority register (3) */
|
||||
.equ PENDSV_PRI_LOWEST, 0x00FF0000 /* PendSV priority value (lowest) */
|
||||
|
||||
/*
|
||||
* rt_base_t rt_hw_interrupt_disable();
|
||||
*/
|
||||
.global rt_hw_interrupt_disable
|
||||
.type rt_hw_interrupt_disable, %function
|
||||
.global rt_hw_interrupt_disable
|
||||
.type rt_hw_interrupt_disable, %function
|
||||
rt_hw_interrupt_disable:
|
||||
MRS R0, PRIMASK
|
||||
CPSID I
|
||||
BX LR
|
||||
MRS R0, PRIMASK
|
||||
CPSID I
|
||||
BX LR
|
||||
|
||||
/*
|
||||
* void rt_hw_interrupt_enable(rt_base_t level);
|
||||
*/
|
||||
.global rt_hw_interrupt_enable
|
||||
.type rt_hw_interrupt_enable, %function
|
||||
.global rt_hw_interrupt_enable
|
||||
.type rt_hw_interrupt_enable, %function
|
||||
rt_hw_interrupt_enable:
|
||||
MSR PRIMASK, R0
|
||||
BX LR
|
||||
MSR PRIMASK, R0
|
||||
BX LR
|
||||
|
||||
/*
|
||||
* void rt_hw_context_switch(rt_uint32 from, rt_uint32 to);
|
||||
* R0 --> from
|
||||
* R1 --> to
|
||||
*/
|
||||
.global rt_hw_context_switch_interrupt
|
||||
.type rt_hw_context_switch_interrupt, %function
|
||||
.global rt_hw_context_switch
|
||||
.type rt_hw_context_switch, %function
|
||||
.global rt_hw_context_switch_interrupt
|
||||
.type rt_hw_context_switch_interrupt, %function
|
||||
.global rt_hw_context_switch
|
||||
.type rt_hw_context_switch, %function
|
||||
rt_hw_context_switch_interrupt:
|
||||
rt_hw_context_switch:
|
||||
/* set rt_thread_switch_interrupt_flag to 1 */
|
||||
LDR R2, =rt_thread_switch_interrupt_flag
|
||||
LDR R3, [R2]
|
||||
CMP R3, #1
|
||||
BEQ _reswitch
|
||||
MOV R3, #1
|
||||
STR R3, [R2]
|
||||
/* set rt_thread_switch_interrupt_flag to 1 */
|
||||
LDR R2, =rt_thread_switch_interrupt_flag
|
||||
LDR R3, [R2]
|
||||
CMP R3, #1
|
||||
BEQ _reswitch
|
||||
MOV R3, #1
|
||||
STR R3, [R2]
|
||||
|
||||
LDR R2, =rt_interrupt_from_thread /* set rt_interrupt_from_thread */
|
||||
STR R0, [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]
|
||||
LDR R2, =rt_interrupt_to_thread /* set rt_interrupt_to_thread */
|
||||
STR R1, [R2]
|
||||
|
||||
LDR R0, =ICSR /* trigger the PendSV exception (causes context switch) */
|
||||
LDR R1, =PENDSVSET_BIT
|
||||
STR R1, [R0]
|
||||
BX LR
|
||||
LDR R0, =ICSR /* trigger the PendSV exception (causes context switch) */
|
||||
LDR R1, =PENDSVSET_BIT
|
||||
STR R1, [R0]
|
||||
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
|
||||
*/
|
||||
.global PendSV_Handler
|
||||
.type PendSV_Handler, %function
|
||||
.global PendSV_Handler
|
||||
.type PendSV_Handler, %function
|
||||
PendSV_Handler:
|
||||
/* disable interrupt to protect context switch */
|
||||
MRS R2, PRIMASK
|
||||
CPSID I
|
||||
/* disable interrupt to protect context switch */
|
||||
MRS R2, PRIMASK
|
||||
CPSID I
|
||||
|
||||
/* get rt_thread_switch_interrupt_flag */
|
||||
LDR R0, =rt_thread_switch_interrupt_flag
|
||||
LDR R1, [R0]
|
||||
CBZ R1, pendsv_exit /* pendsv aLReady handled */
|
||||
/* get rt_thread_switch_interrupt_flag */
|
||||
LDR R0, =rt_thread_switch_interrupt_flag
|
||||
LDR R1, [R0]
|
||||
CBZ R1, pendsv_exit /* pendsv aLReady handled */
|
||||
|
||||
/* clear rt_thread_switch_interrupt_flag to 0 */
|
||||
MOV R1, #0
|
||||
STR R1, [R0]
|
||||
/* clear rt_thread_switch_interrupt_flag to 0 */
|
||||
MOV R1, #0
|
||||
STR R1, [R0]
|
||||
|
||||
LDR R0, =rt_interrupt_from_thread
|
||||
LDR R1, [R0]
|
||||
CBZ R1, swtich_to_thread /* skip register save at the first time */
|
||||
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 */
|
||||
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 */
|
||||
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 */
|
||||
LDMFD R1!, {R4 - R11} /* pop R4 - R11 register */
|
||||
MSR PSP, R1 /* update stack pointer */
|
||||
|
||||
pendsv_exit:
|
||||
/* restore interrupt */
|
||||
MSR PRIMASK, R2
|
||||
/* restore interrupt */
|
||||
MSR PRIMASK, R2
|
||||
|
||||
ORR LR, LR, #0x04
|
||||
BX LR
|
||||
ORR LR, LR, #0x04
|
||||
BX LR
|
||||
|
||||
/*
|
||||
* void rt_hw_context_switch_to(rt_uint32 to);
|
||||
* R0 --> to
|
||||
*/
|
||||
.global rt_hw_context_switch_to
|
||||
.type rt_hw_context_switch_to, %function
|
||||
.global rt_hw_context_switch_to
|
||||
.type rt_hw_context_switch_to, %function
|
||||
rt_hw_context_switch_to:
|
||||
LDR R1, =rt_interrupt_to_thread
|
||||
STR R0, [R1]
|
||||
LDR R1, =rt_interrupt_to_thread
|
||||
STR R0, [R1]
|
||||
|
||||
/* set from thread to 0 */
|
||||
LDR R1, =rt_interrupt_from_thread
|
||||
MOV R0, #0
|
||||
STR R0, [R1]
|
||||
/* set from thread to 0 */
|
||||
LDR R1, =rt_interrupt_from_thread
|
||||
MOV R0, #0
|
||||
STR R0, [R1]
|
||||
|
||||
/* set interrupt flag to 1 */
|
||||
LDR R1, =rt_thread_switch_interrupt_flag
|
||||
MOV R0, #1
|
||||
STR R0, [R1]
|
||||
/* set interrupt flag to 1 */
|
||||
LDR R1, =rt_thread_switch_interrupt_flag
|
||||
MOV R0, #1
|
||||
STR R0, [R1]
|
||||
|
||||
/* set the PendSV exception priority */
|
||||
LDR R0, =SHPR3
|
||||
LDR R1, =PENDSV_PRI_LOWEST
|
||||
LDR.W R2, [R0,#0] /* read */
|
||||
ORR R1, R1, R2 /* modify */
|
||||
STR R1, [R0] /* write-back */
|
||||
/* set the PendSV exception priority */
|
||||
LDR R0, =SHPR3
|
||||
LDR R1, =PENDSV_PRI_LOWEST
|
||||
LDR.W R2, [R0,#0] /* read */
|
||||
ORR R1, R1, R2 /* modify */
|
||||
STR R1, [R0] /* write-back */
|
||||
|
||||
LDR R0, =ICSR /* trigger the PendSV exception (causes context switch) */
|
||||
LDR R1, =PENDSVSET_BIT
|
||||
STR R1, [R0]
|
||||
LDR R0, =ICSR /* trigger the PendSV exception (causes context switch) */
|
||||
LDR R1, =PENDSVSET_BIT
|
||||
STR R1, [R0]
|
||||
|
||||
CPSIE I /* enable interrupts at processor level */
|
||||
/* restore MSP */
|
||||
LDR r0, =SCB_VTOR
|
||||
LDR r0, [r0]
|
||||
LDR r0, [r0]
|
||||
NOP
|
||||
MSR msp, r0
|
||||
|
||||
/* never reach here! */
|
||||
CPSIE I /* enable interrupts at processor level */
|
||||
|
||||
/* never reach here! */
|
||||
|
||||
/* compatible with old version */
|
||||
.global rt_hw_interrupt_thread_switch
|
||||
.type rt_hw_interrupt_thread_switch, %function
|
||||
.global rt_hw_interrupt_thread_switch
|
||||
.type rt_hw_interrupt_thread_switch, %function
|
||||
rt_hw_interrupt_thread_switch:
|
||||
BX LR
|
||||
NOP
|
||||
BX LR
|
||||
NOP
|
||||
|
||||
.global HardFault_Handler
|
||||
.type HardFault_Handler, %function
|
||||
.global HardFault_Handler
|
||||
.type HardFault_Handler, %function
|
||||
HardFault_Handler:
|
||||
/* get current context */
|
||||
MRS R0, PSP /* get fault thread stack pointer */
|
||||
|
@ -179,8 +188,8 @@ HardFault_Handler:
|
|||
* rt_uint32_t rt_hw_interrupt_check(void);
|
||||
* R0 --> state
|
||||
*/
|
||||
.global rt_hw_interrupt_check
|
||||
.type rt_hw_interrupt_check, %function
|
||||
.global rt_hw_interrupt_check
|
||||
.type rt_hw_interrupt_check, %function
|
||||
rt_hw_interrupt_check:
|
||||
MRS R0, IPSR
|
||||
BX LR
|
||||
MRS R0, IPSR
|
||||
BX LR
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
; * Date Author Notes
|
||||
; * 2009-01-17 Bernard first version
|
||||
; * 2009-09-27 Bernard add protect when contex switch occurs
|
||||
; * 2013-06-18 aozima add restore MSP feature.
|
||||
; */
|
||||
|
||||
;/**
|
||||
|
@ -18,6 +19,7 @@
|
|||
; */
|
||||
;/*@{*/
|
||||
|
||||
SCB_VTOR EQU 0xE000ED08 ; Vector Table Offset Register
|
||||
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)
|
||||
|
@ -151,6 +153,13 @@ rt_hw_context_switch_to:
|
|||
LDR r1, =NVIC_PENDSVSET
|
||||
STR r1, [r0]
|
||||
|
||||
; restore MSP
|
||||
LDR r0, =SCB_VTOR
|
||||
LDR r0, [r0]
|
||||
LDR r0, [r0]
|
||||
NOP
|
||||
MSR msp, r0
|
||||
|
||||
CPSIE I ; enable interrupts at processor level
|
||||
|
||||
; never reach here!
|
||||
|
|
|
@ -10,6 +10,7 @@
|
|||
; * Change Logs:
|
||||
; * Date Author Notes
|
||||
; * 2009-01-17 Bernard first version
|
||||
; * 2013-06-18 aozima add restore MSP feature.
|
||||
; */
|
||||
|
||||
;/**
|
||||
|
@ -17,6 +18,7 @@
|
|||
; */
|
||||
;/*@{*/
|
||||
|
||||
SCB_VTOR EQU 0xE000ED08 ; Vector Table Offset Register
|
||||
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)
|
||||
|
@ -158,6 +160,13 @@ rt_hw_context_switch_to PROC
|
|||
LDR r1, =NVIC_PENDSVSET
|
||||
STR r1, [r0]
|
||||
|
||||
; restore MSP
|
||||
LDR r0, =SCB_VTOR
|
||||
LDR r0, [r0]
|
||||
LDR r0, [r0]
|
||||
NOP
|
||||
MSR msp, r0
|
||||
|
||||
; enable interrupts at processor level
|
||||
CPSIE I
|
||||
|
||||
|
|
|
@ -102,7 +102,7 @@ rt_uint8_t *rt_hw_stack_init(void *tentry,
|
|||
*/
|
||||
void rt_hw_exception_install(rt_err_t (*exception_handle)(void* context))
|
||||
{
|
||||
rt_exception_hook = exception_handle;
|
||||
rt_exception_hook = exception_handle;
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -110,15 +110,16 @@ void rt_hw_exception_install(rt_err_t (*exception_handle)(void* context))
|
|||
*/
|
||||
void rt_hw_hard_fault_exception(struct exception_stack_frame* context)
|
||||
{
|
||||
extern long list_thread(void);
|
||||
extern long list_thread(void);
|
||||
|
||||
if (rt_exception_hook != RT_NULL)
|
||||
{
|
||||
rt_err_t result;
|
||||
if (rt_exception_hook != RT_NULL)
|
||||
{
|
||||
rt_err_t result;
|
||||
|
||||
result = rt_exception_hook(context);
|
||||
if (result == RT_EOK) return;
|
||||
}
|
||||
result = rt_exception_hook(context);
|
||||
if (result == RT_EOK)
|
||||
return;
|
||||
}
|
||||
|
||||
rt_kprintf("psr: 0x%08x\n", context->psr);
|
||||
rt_kprintf(" pc: 0x%08x\n", context->pc);
|
||||
|
@ -135,7 +136,8 @@ void rt_hw_hard_fault_exception(struct exception_stack_frame* context)
|
|||
list_thread();
|
||||
#endif
|
||||
|
||||
while (1);
|
||||
while (1)
|
||||
;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
* Date Author Notes
|
||||
* 2009-10-11 Bernard first version
|
||||
* 2012-01-01 aozima support context switch load/store FPU register.
|
||||
* 2013-06-18 aozima add restore MSP feature.
|
||||
*/
|
||||
|
||||
/**
|
||||
|
@ -23,10 +24,11 @@
|
|||
.thumb
|
||||
.text
|
||||
|
||||
.equ NVIC_INT_CTRL, 0xE000ED04 /* interrupt control state register */
|
||||
.equ NVIC_SYSPRI2, 0xE000ED20 /* system priority register (2) */
|
||||
.equ NVIC_PENDSV_PRI, 0x00FF0000 /* PendSV priority value (lowest) */
|
||||
.equ NVIC_PENDSVSET, 0x10000000 /* value to trigger PendSV exception */
|
||||
.equ SCB_VTOR, 0xE000ED04 /* Vector Table Offset Register */
|
||||
.equ NVIC_INT_CTRL, 0xE000ED04 /* interrupt control state register */
|
||||
.equ NVIC_SYSPRI2, 0xE000ED20 /* system priority register (2) */
|
||||
.equ NVIC_PENDSV_PRI, 0x00FF0000 /* PendSV priority value (lowest) */
|
||||
.equ NVIC_PENDSVSET, 0x10000000 /* value to trigger PendSV exception */
|
||||
|
||||
/*
|
||||
* rt_base_t rt_hw_interrupt_disable();
|
||||
|
@ -106,9 +108,9 @@ PendSV_Handler:
|
|||
MRS r1, psp /* get from thread stack pointer */
|
||||
|
||||
#if defined (__VFP_FP__) && !defined(__SOFTFP__)
|
||||
VSTMDB r1!, {d8 - d15} /* push FPU register s16~s31 */
|
||||
VSTMDB r1!, {d8 - d15} /* push FPU register s16~s31 */
|
||||
#endif
|
||||
|
||||
|
||||
STMFD r1!, {r4 - r11} /* push r4 - r11 register */
|
||||
LDR r0, [r0]
|
||||
STR r1, [r0] /* update from thread stack pointer */
|
||||
|
@ -164,6 +166,13 @@ rt_hw_context_switch_to:
|
|||
LDR r1, =NVIC_PENDSVSET
|
||||
STR r1, [r0]
|
||||
|
||||
/* restore MSP */
|
||||
LDR r0, =SCB_VTOR
|
||||
LDR r0, [r0]
|
||||
LDR r0, [r0]
|
||||
NOP
|
||||
MSR msp, r0
|
||||
|
||||
CPSIE I /* enable interrupts at processor level */
|
||||
|
||||
/* never reach here! */
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
; * 2009-01-17 Bernard first version
|
||||
; * 2009-09-27 Bernard add protect when contex switch occurs
|
||||
; * 2012-01-01 aozima support context switch load/store FPU register.
|
||||
; * 2013-06-18 aozima add restore MSP feature.
|
||||
; */
|
||||
|
||||
;/**
|
||||
|
@ -19,6 +20,7 @@
|
|||
; */
|
||||
;/*@{*/
|
||||
|
||||
SCB_VTOR EQU 0xE000ED08 ; Vector Table Offset Register
|
||||
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)
|
||||
|
@ -162,6 +164,13 @@ rt_hw_context_switch_to:
|
|||
LDR r1, =NVIC_PENDSVSET
|
||||
STR r1, [r0]
|
||||
|
||||
; restore MSP
|
||||
LDR r0, =SCB_VTOR
|
||||
LDR r0, [r0]
|
||||
LDR r0, [r0]
|
||||
NOP
|
||||
MSR msp, r0
|
||||
|
||||
CPSIE I ; enable interrupts at processor level
|
||||
|
||||
; never reach here!
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
; * Date Author Notes
|
||||
; * 2009-01-17 Bernard first version.
|
||||
; * 2012-01-01 aozima support context switch load/store FPU register.
|
||||
; * 2013-06-18 aozima add restore MSP feature.
|
||||
; */
|
||||
|
||||
;/**
|
||||
|
@ -18,6 +19,7 @@
|
|||
; */
|
||||
;/*@{*/
|
||||
|
||||
SCB_VTOR EQU 0xE000ED08 ; Vector Table Offset Register
|
||||
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)
|
||||
|
@ -108,10 +110,10 @@ PendSV_Handler PROC
|
|||
MRS r1, psp ; get from thread stack pointer
|
||||
|
||||
IF {FPU} != "SoftVFP"
|
||||
VSTMFD r1!, {d8 - d15} ; push FPU register s16~s31
|
||||
VSTMFD r1!, {d8 - d15} ; push FPU register s16~s31
|
||||
ENDIF
|
||||
|
||||
STMFD r1!, {r4 - r11} ; push r4 - r11 register
|
||||
STMFD r1!, {r4 - r11} ; push r4 - r11 register
|
||||
LDR r0, [r0]
|
||||
STR r1, [r0] ; update from thread stack pointer
|
||||
|
||||
|
@ -169,6 +171,13 @@ rt_hw_context_switch_to PROC
|
|||
LDR r1, =NVIC_PENDSVSET
|
||||
STR r1, [r0]
|
||||
|
||||
; restore MSP
|
||||
LDR r0, =SCB_VTOR
|
||||
LDR r0, [r0]
|
||||
LDR r0, [r0]
|
||||
NOP
|
||||
MSR msp, r0
|
||||
|
||||
; enable interrupts at processor level
|
||||
CPSIE I
|
||||
|
||||
|
|
|
@ -28,18 +28,22 @@
|
|||
; * rt_base_t rt_hw_interrupt_disable();
|
||||
; */
|
||||
.def rt_hw_interrupt_disable
|
||||
.asmfunc
|
||||
rt_hw_interrupt_disable
|
||||
MRS r0, cpsr
|
||||
CPSID IF
|
||||
BX lr
|
||||
.endasmfunc
|
||||
|
||||
;/*
|
||||
; * void rt_hw_interrupt_enable(rt_base_t level);
|
||||
; */
|
||||
.def rt_hw_interrupt_enable
|
||||
.asmfunc
|
||||
rt_hw_interrupt_enable
|
||||
MSR cpsr_c, r0
|
||||
BX lr
|
||||
.endasmfunc
|
||||
|
||||
;/*
|
||||
; * void rt_hw_context_switch(rt_uint32 from, rt_uint32 to);
|
||||
|
@ -47,6 +51,7 @@ rt_hw_interrupt_enable
|
|||
; * r1 --> to
|
||||
; */
|
||||
.def rt_hw_context_switch
|
||||
.asmfunc
|
||||
rt_hw_context_switch
|
||||
STMDB sp!, {lr} ; push pc (lr should be pushed in place of PC)
|
||||
STMDB sp!, {r0-r12, lr} ; push lr & register file
|
||||
|
@ -88,12 +93,14 @@ __no_vfp_frame2
|
|||
MSR spsr_cxsf, r4
|
||||
|
||||
LDMIA sp!, {r0-r12, lr, pc}^ ; pop new task r0-r12, lr & pc, copy spsr to cpsr
|
||||
.endasmfunc
|
||||
|
||||
;/*
|
||||
; * void rt_hw_context_switch_to(rt_uint32 to);
|
||||
; * r0 --> to
|
||||
; */
|
||||
.def rt_hw_context_switch_to
|
||||
.asmfunc
|
||||
rt_hw_context_switch_to
|
||||
LDR sp, [r0] ; get new task stack pointer
|
||||
|
||||
|
@ -112,12 +119,14 @@ __no_vfp_frame_to
|
|||
MSR spsr_cxsf, r4
|
||||
|
||||
LDMIA sp!, {r0-r12, lr, pc}^ ; pop new task r0-r12, lr & pc, copy spsr to cpsr
|
||||
.endasmfunc
|
||||
|
||||
;/*
|
||||
; * void rt_hw_context_switch_interrupt(rt_uint32 from, rt_uint32 to);
|
||||
; */
|
||||
|
||||
.def rt_hw_context_switch_interrupt
|
||||
.asmfunc
|
||||
rt_hw_context_switch_interrupt
|
||||
LDR r2, pintflag
|
||||
LDR r3, [r2]
|
||||
|
@ -131,6 +140,7 @@ _reswitch
|
|||
LDR r2, ptothread ; set rt_interrupt_to_thread
|
||||
STR r1, [r2]
|
||||
BX lr
|
||||
.endasmfunc
|
||||
|
||||
.def IRQ_Handler
|
||||
IRQ_Handler
|
||||
|
|
|
@ -39,4 +39,56 @@ void rt_hw_cpu_shutdown()
|
|||
while (1);
|
||||
}
|
||||
|
||||
#ifdef RT_USING_CPU_FFS
|
||||
int __rt_ffs(int value)
|
||||
{
|
||||
if (value == 0)
|
||||
return value;
|
||||
|
||||
__asm(" rsb r1, r0, #0");
|
||||
__asm(" and r1, r1, r0");
|
||||
__asm(" clz r1, r1");
|
||||
__asm(" rsb r0, r1, #32");
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef __TI_COMPILER_VERSION__
|
||||
void rt_hw_cpu_icache_enable()
|
||||
{
|
||||
__asm(" MRC p15, #0, r1, c1, c0, #0 ; Read SCTLR configuration data");
|
||||
__asm(" ORR r1, r1, #0x1 <<12 ; instruction cache enable");
|
||||
__asm(" MCR p15, #0, r0, c7, c5, #0 ; Invalidate entire instruction cache, r0 is ignored");
|
||||
__asm(" MCR p15, #0, r1, c1, c0, #0 ; enabled instruction cache");
|
||||
__asm(" ISB");
|
||||
}
|
||||
|
||||
void rt_hw_cpu_icache_disable()
|
||||
{
|
||||
__asm(" MRC p15, #0, r1, c1, c0, #0 ; Read SCTLR configuration data");
|
||||
__asm(" BIC r1, r1, #0x1 <<12 ; instruction cache enable");
|
||||
__asm(" MCR p15, #0, r1, c1, c0, #0 ; disabled instruction cache");
|
||||
__asm(" ISB");
|
||||
}
|
||||
|
||||
void rt_hw_cpu_dcache_enable()
|
||||
{
|
||||
__asm(" MRC p15, #0, R1, c1, c0, #0 ; Read SCTLR configuration data");
|
||||
__asm(" ORR R1, R1, #0x1 <<2");
|
||||
__asm(" DSB");
|
||||
__asm(" MCR p15, #0, r0, c15, c5, #0 ; Invalidate entire data cache");
|
||||
__asm(" MCR p15, #0, R1, c1, c0, #0 ; enabled data cache");
|
||||
}
|
||||
|
||||
void rt_hw_cpu_dcache_disable()
|
||||
{
|
||||
/* FIXME: Clean entire data cache. This routine depends on the data cache
|
||||
* size. It can be omitted if it is known that the data cache has no dirty
|
||||
* data. */
|
||||
__asm(" MRC p15, #0, r1, c1, c0, #0 ; Read SCTLR configuration data");
|
||||
__asm(" BIC r1, r1, #0x1 <<2");
|
||||
__asm(" DSB");
|
||||
__asm(" MCR p15, #0, r1, c1, c0, #0 ; disabled data cache");
|
||||
}
|
||||
|
||||
#endif
|
||||
/*@}*/
|
||||
|
|
|
@ -22,7 +22,7 @@
|
|||
/* exception and interrupt handler table */
|
||||
struct rt_irq_desc irq_desc[MAX_HANDLERS];
|
||||
|
||||
extern rt_uint32_t rt_interrupt_nest;
|
||||
extern volatile rt_uint8_t rt_interrupt_nest;
|
||||
|
||||
/* exception and interrupt handler table */
|
||||
rt_uint32_t rt_interrupt_from_thread, rt_interrupt_to_thread;
|
||||
|
|
|
@ -52,8 +52,8 @@ rt_hw_context_switch:
|
|||
mrs r4, spsr
|
||||
stmfd sp!, {r4} @ push spsr
|
||||
|
||||
str sp, [r0] @ store sp in preempted tasks TCB
|
||||
ldr sp, [r1] @ get new task stack pointer
|
||||
str sp, [r0] @ store sp in preempted tasks TCB
|
||||
ldr sp, [r1] @ get new task stack pointer
|
||||
|
||||
ldmfd sp!, {r4} @ pop new task spsr
|
||||
msr spsr_cxsf, r4
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
* Change Logs:
|
||||
* Date Author Notes
|
||||
* 2006-03-13 Bernard first version
|
||||
* 2009-04-20 yi.qiu modified according bernard's stm32 version
|
||||
* 2009-04-20 yi.qiu modified according bernard's stm32 version
|
||||
*/
|
||||
|
||||
#include <rtthread.h>
|
||||
|
@ -26,208 +26,220 @@
|
|||
/**
|
||||
* This function initializes serial
|
||||
*/
|
||||
static rt_err_t rt_serial_init (rt_device_t dev)
|
||||
static rt_err_t rt_serial_init(rt_device_t dev)
|
||||
{
|
||||
struct serial_device* uart = (struct serial_device*) dev->user_data;
|
||||
struct serial_device* uart = (struct serial_device*) dev->user_data;
|
||||
|
||||
if (!(dev->flag & RT_DEVICE_FLAG_ACTIVATED))
|
||||
{
|
||||
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 = uart->int_rx->save_index = 0;
|
||||
}
|
||||
|
||||
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_INT_RX)
|
||||
{
|
||||
rt_memset(uart->int_rx->rx_buffer, 0,
|
||||
sizeof(uart->int_rx->rx_buffer));
|
||||
uart->int_rx->read_index = uart->int_rx->save_index = 0;
|
||||
}
|
||||
|
||||
dev->flag |= RT_DEVICE_FLAG_ACTIVATED;
|
||||
}
|
||||
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;
|
||||
}
|
||||
|
||||
return RT_EOK;
|
||||
dev->flag |= RT_DEVICE_FLAG_ACTIVATED;
|
||||
}
|
||||
|
||||
return RT_EOK;
|
||||
}
|
||||
|
||||
/* save a char to serial buffer */
|
||||
static void rt_serial_savechar(struct serial_device* uart, char ch)
|
||||
{
|
||||
rt_base_t level;
|
||||
|
||||
/* disable interrupt */
|
||||
level = rt_hw_interrupt_disable();
|
||||
rt_base_t level;
|
||||
|
||||
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;
|
||||
}
|
||||
/* disable interrupt */
|
||||
level = rt_hw_interrupt_disable();
|
||||
|
||||
/* enable interrupt */
|
||||
rt_hw_interrupt_enable(level);
|
||||
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);
|
||||
}
|
||||
|
||||
static rt_err_t rt_serial_open(rt_device_t dev, rt_uint16_t oflag)
|
||||
{
|
||||
RT_ASSERT(dev != RT_NULL);
|
||||
|
||||
return RT_EOK;
|
||||
{
|
||||
RT_ASSERT(dev != RT_NULL);
|
||||
|
||||
return RT_EOK;
|
||||
}
|
||||
|
||||
static rt_err_t rt_serial_close(rt_device_t dev)
|
||||
{
|
||||
RT_ASSERT(dev != RT_NULL);
|
||||
{
|
||||
RT_ASSERT(dev != RT_NULL);
|
||||
|
||||
return RT_EOK;
|
||||
return RT_EOK;
|
||||
}
|
||||
|
||||
static rt_size_t rt_serial_read (rt_device_t dev, rt_off_t pos, void* buffer, rt_size_t size)
|
||||
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 serial_device* uart;
|
||||
|
||||
ptr = buffer;
|
||||
err_code = RT_EOK;
|
||||
uart = (struct serial_device*)dev->user_data;
|
||||
rt_uint8_t* ptr;
|
||||
rt_err_t err_code;
|
||||
struct serial_device* uart;
|
||||
|
||||
if (dev->flag & RT_DEVICE_FLAG_INT_RX)
|
||||
{
|
||||
rt_base_t level;
|
||||
ptr = buffer;
|
||||
err_code = RT_EOK;
|
||||
uart = (struct serial_device*)dev->user_data;
|
||||
|
||||
/* interrupt mode Rx */
|
||||
while (size)
|
||||
{
|
||||
if (uart->int_rx->read_index != uart->int_rx->save_index)
|
||||
{
|
||||
*ptr++ = uart->int_rx->rx_buffer[uart->int_rx->read_index];
|
||||
size --;
|
||||
if (ptr == RT_NULL)
|
||||
{
|
||||
err_code = -RT_ENOMEM;
|
||||
rt_set_errno(err_code);
|
||||
return -RT_ENOMEM;
|
||||
}
|
||||
if (dev->flag & RT_DEVICE_FLAG_INT_RX)
|
||||
{
|
||||
rt_base_t level;
|
||||
|
||||
/* disable interrupt */
|
||||
level = rt_hw_interrupt_disable();
|
||||
/* interrupt mode Rx */
|
||||
while (size)
|
||||
{
|
||||
if (uart->int_rx->read_index != uart->int_rx->save_index)
|
||||
{
|
||||
*ptr++ = uart->int_rx->rx_buffer[uart->int_rx->read_index];
|
||||
size --;
|
||||
|
||||
uart->int_rx->read_index ++;
|
||||
if (uart->int_rx->read_index >= UART_RX_BUFFER_SIZE)
|
||||
uart->int_rx->read_index = 0;
|
||||
/* disable interrupt */
|
||||
level = rt_hw_interrupt_disable();
|
||||
|
||||
/* enable interrupt */
|
||||
rt_hw_interrupt_enable(level);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* 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->ustat & USTAT_RCV_READY)
|
||||
{
|
||||
*ptr = uart->uart_device->urxh & 0xff;
|
||||
ptr ++;
|
||||
}
|
||||
}
|
||||
}
|
||||
uart->int_rx->read_index ++;
|
||||
if (uart->int_rx->read_index >= UART_RX_BUFFER_SIZE)
|
||||
uart->int_rx->read_index = 0;
|
||||
|
||||
/* set error code */
|
||||
rt_set_errno(err_code);
|
||||
return (rt_uint32_t)ptr - (rt_uint32_t)buffer;
|
||||
/* enable interrupt */
|
||||
rt_hw_interrupt_enable(level);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* 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->ustat & USTAT_RCV_READY)
|
||||
{
|
||||
*ptr = uart->uart_device->urxh & 0xff;
|
||||
ptr ++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* set error code */
|
||||
rt_set_errno(err_code);
|
||||
return (rt_uint32_t)ptr - (rt_uint32_t)buffer;
|
||||
}
|
||||
|
||||
static rt_size_t rt_serial_write (rt_device_t dev, rt_off_t pos, const void* buffer, rt_size_t size)
|
||||
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 serial_device* uart;
|
||||
|
||||
err_code = RT_EOK;
|
||||
ptr = (rt_uint8_t*)buffer;
|
||||
uart = (struct serial_device*)dev->user_data;
|
||||
rt_uint8_t* ptr;
|
||||
rt_err_t err_code;
|
||||
struct serial_device* uart;
|
||||
|
||||
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;
|
||||
err_code = RT_EOK;
|
||||
ptr = (rt_uint8_t*)buffer;
|
||||
uart = (struct serial_device*)dev->user_data;
|
||||
|
||||
/* 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
|
||||
{
|
||||
/* polling mode */
|
||||
while (size)
|
||||
{
|
||||
/*
|
||||
* to be polite with serial console add a line feed
|
||||
* to the carriage return character
|
||||
*/
|
||||
if (*ptr == '\n' && (dev->flag & RT_DEVICE_FLAG_STREAM))
|
||||
{
|
||||
while (!(uart->uart_device->ustat & USTAT_TXB_EMPTY));
|
||||
uart->uart_device->utxh = '\r';
|
||||
}
|
||||
if (ptr == RT_NULL)
|
||||
{
|
||||
err_code = -RT_ENOMEM;
|
||||
rt_set_errno(err_code);
|
||||
return -RT_ENOMEM;
|
||||
}
|
||||
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++;
|
||||
|
||||
while (!(uart->uart_device->ustat & USTAT_TXB_EMPTY));
|
||||
uart->uart_device->utxh = (*ptr & 0xFF);
|
||||
-- size;
|
||||
|
||||
++ptr; --size;
|
||||
}
|
||||
}
|
||||
/* move to next position */
|
||||
uart->int_tx->save_index ++;
|
||||
|
||||
/* set error code */
|
||||
rt_set_errno(err_code);
|
||||
|
||||
return (rt_uint32_t)ptr - (rt_uint32_t)buffer;
|
||||
/* 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
|
||||
{
|
||||
/* polling mode */
|
||||
while (size)
|
||||
{
|
||||
/*
|
||||
* to be polite with serial console add a line feed
|
||||
* to the carriage return character
|
||||
*/
|
||||
if (*ptr == '\n' && (dev->flag & RT_DEVICE_FLAG_STREAM))
|
||||
{
|
||||
while (!(uart->uart_device->ustat & USTAT_TXB_EMPTY));
|
||||
uart->uart_device->utxh = '\r';
|
||||
}
|
||||
|
||||
while (!(uart->uart_device->ustat & USTAT_TXB_EMPTY));
|
||||
uart->uart_device->utxh = (*ptr & 0xFF);
|
||||
|
||||
++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)
|
||||
static rt_err_t rt_serial_control(rt_device_t dev, rt_uint8_t cmd, void *args)
|
||||
{
|
||||
RT_ASSERT(dev != RT_NULL);
|
||||
RT_ASSERT(dev != RT_NULL);
|
||||
|
||||
switch (cmd)
|
||||
{
|
||||
case RT_DEVICE_CTRL_SUSPEND:
|
||||
/* suspend device */
|
||||
dev->flag |= RT_DEVICE_FLAG_SUSPENDED;
|
||||
break;
|
||||
|
||||
case RT_DEVICE_CTRL_RESUME:
|
||||
/* resume device */
|
||||
dev->flag &= ~RT_DEVICE_FLAG_SUSPENDED;
|
||||
break;
|
||||
}
|
||||
|
||||
return RT_EOK;
|
||||
switch (cmd)
|
||||
{
|
||||
case RT_DEVICE_CTRL_SUSPEND:
|
||||
/* suspend device */
|
||||
dev->flag |= RT_DEVICE_FLAG_SUSPENDED;
|
||||
break;
|
||||
|
||||
case RT_DEVICE_CTRL_RESUME:
|
||||
/* resume device */
|
||||
dev->flag &= ~RT_DEVICE_FLAG_SUSPENDED;
|
||||
break;
|
||||
}
|
||||
|
||||
return RT_EOK;
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -235,49 +247,49 @@ static rt_err_t rt_serial_control (rt_device_t dev, rt_uint8_t cmd, void *args)
|
|||
*/
|
||||
rt_err_t rt_hw_serial_register(rt_device_t device, const char* name, rt_uint32_t flag, struct serial_device *serial)
|
||||
{
|
||||
RT_ASSERT(device != RT_NULL);
|
||||
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->user_data = serial;
|
||||
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->user_data = serial;
|
||||
|
||||
/* register a character device */
|
||||
return rt_device_register(device, name, RT_DEVICE_FLAG_RDWR | flag);
|
||||
/* 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 serial_device* uart = (struct serial_device*) device->user_data;
|
||||
|
||||
/* interrupt mode receive */
|
||||
RT_ASSERT(device->flag & RT_DEVICE_FLAG_INT_RX);
|
||||
struct serial_device* uart = (struct serial_device*) device->user_data;
|
||||
|
||||
/* save on rx buffer */
|
||||
while (uart->uart_device->ustat & USTAT_RCV_READY)
|
||||
{
|
||||
rt_serial_savechar(uart, uart->uart_device->urxh & 0xff);
|
||||
}
|
||||
/* interrupt mode receive */
|
||||
RT_ASSERT(device->flag & RT_DEVICE_FLAG_INT_RX);
|
||||
|
||||
/* 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;
|
||||
/* save on rx buffer */
|
||||
while (uart->uart_device->ustat & USTAT_RCV_READY)
|
||||
{
|
||||
rt_serial_savechar(uart, uart->uart_device->urxh & 0xff);
|
||||
}
|
||||
|
||||
device->rx_indicate(device, rx_length);
|
||||
}
|
||||
/* 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);
|
||||
}
|
||||
}
|
||||
|
||||
/*@}*/
|
||||
|
|
|
@ -10,8 +10,8 @@
|
|||
* Change Logs:
|
||||
* Date Author Notes
|
||||
* 2006-03-13 Bernard first version
|
||||
* 2006-10-05 Alsor.Z for s3c2440 initialize
|
||||
* 2008-01-29 Yi.Qiu for QEMU emulator
|
||||
* 2006-10-05 Alsor.Z for s3c2440 initialize
|
||||
* 2008-01-29 Yi.Qiu for QEMU emulator
|
||||
*/
|
||||
|
||||
#define CONFIG_STACKSIZE 512
|
||||
|
@ -23,7 +23,7 @@
|
|||
#define S_LR 56
|
||||
#define S_SP 52
|
||||
|
||||
#define S_IP 48
|
||||
#define S_IP 48
|
||||
#define S_FP 44
|
||||
#define S_R10 40
|
||||
#define S_R9 36
|
||||
|
|
|
@ -83,6 +83,11 @@ def PrepareBuilding(env, root_directory, has_libcpu=False, remove_components = [
|
|||
action='store_true',
|
||||
default=False,
|
||||
help='copy header of rt-thread directory to local.')
|
||||
AddOption('--cscope',
|
||||
dest='cscope',
|
||||
action='store_true',
|
||||
default=False,
|
||||
help='Build Cscope cross reference database. Requires cscope installed.')
|
||||
|
||||
# add build library option
|
||||
AddOption('--buildlib',
|
||||
|
@ -341,6 +346,10 @@ def EndBuilding(target, program = None):
|
|||
if GetOption('copy-header') and program != None:
|
||||
MakeCopyHeader(program)
|
||||
|
||||
if GetOption('cscope'):
|
||||
from cscope import CscopeDatabase
|
||||
CscopeDatabase(Projects)
|
||||
|
||||
def SrcRemove(src, remove):
|
||||
if type(src[0]) == type('str'):
|
||||
for item in src:
|
||||
|
|
|
@ -38,8 +38,12 @@ def CB_AddCFiles(ProjectFiles, parent, gname, files, project_path):
|
|||
|
||||
def CBProject(target, script, program):
|
||||
project_path = os.path.dirname(os.path.abspath(target))
|
||||
|
||||
if os.path.isfile('template.cbp'):
|
||||
tree = etree.parse('template.cbp')
|
||||
else:
|
||||
tree = etree.parse(os.path.join(os.path.dirname(__file__), 'template.cbp'))
|
||||
|
||||
tree = etree.parse('template.cbp')
|
||||
root = tree.getroot()
|
||||
|
||||
out = file(target, 'wb')
|
||||
|
@ -75,7 +79,7 @@ def CBProject(target, script, program):
|
|||
Add = SubElement(elem, 'Add')
|
||||
Add.set('directory', path)
|
||||
|
||||
for macro in building.Env['CPPDEFINES']:
|
||||
for macro in building.Env.get('CPPDEFINES', []):
|
||||
Add = SubElement(elem, 'Add')
|
||||
Add.set('option', "-D"+macro)
|
||||
|
||||
|
|
|
@ -0,0 +1,37 @@
|
|||
import os
|
||||
|
||||
def _get_src(project):
|
||||
li = []
|
||||
for group in project:
|
||||
for f in group['src']:
|
||||
li.append(os.path.normpath(f.rfile().abspath))
|
||||
return li
|
||||
|
||||
def _get_header_dir(dirp):
|
||||
li = []
|
||||
for root, dirs, files in os.walk(dirp):
|
||||
for d in dirs:
|
||||
fpath = os.path.join(root, d)
|
||||
li.extend(_get_header_dir(fpath))
|
||||
|
||||
for f in files:
|
||||
if f[-2:] == '.h':
|
||||
fpath = os.path.join(root, f)
|
||||
li.append(os.path.normpath(fpath))
|
||||
return li
|
||||
|
||||
def _get_header(project):
|
||||
li = []
|
||||
for g in project:
|
||||
for d in g.get('CPPPATH', []):
|
||||
li.extend(_get_header_dir(d))
|
||||
return li
|
||||
|
||||
def CscopeDatabase(project):
|
||||
files = set(_get_src(project) + _get_header(project))
|
||||
with open('cscope.files', 'w') as db:
|
||||
db.write('-k\n-q\n')
|
||||
db.write('\n'.join(files))
|
||||
db.flush() # let cscope see the full content
|
||||
os.system('cscope -b')
|
||||
|
11
tools/iar.py
11
tools/iar.py
|
@ -37,7 +37,10 @@ def IARAddGroup(parent, name, files, project_path):
|
|||
|
||||
file = SubElement(group, 'file')
|
||||
file_name = SubElement(file, 'name')
|
||||
file_name.text = ('$PROJ_DIR$\\' + path).decode(fs_encoding)
|
||||
if os.path.isabs(path):
|
||||
file_name.text = path.decode(fs_encoding)
|
||||
else:
|
||||
file_name.text = ('$PROJ_DIR$\\' + path).decode(fs_encoding)
|
||||
|
||||
def IARWorkspace(target):
|
||||
# make an workspace
|
||||
|
@ -91,7 +94,11 @@ def IARProject(target, script):
|
|||
if name.text == 'CCIncludePath2' or name.text == 'newCCIncludePaths':
|
||||
for path in paths:
|
||||
state = SubElement(option, 'state')
|
||||
state.text = '$PROJ_DIR$\\' + path
|
||||
if os.path.isabs(path):
|
||||
state.text = path
|
||||
else:
|
||||
state.text = '$PROJ_DIR$\\' + path
|
||||
|
||||
if name.text == 'CCDefines':
|
||||
for define in CPPDEFINES:
|
||||
state = SubElement(option, 'state')
|
||||
|
|
|
@ -0,0 +1,41 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="yes" ?>
|
||||
<CodeBlocks_project_file>
|
||||
<FileVersion major="1" minor="6" />
|
||||
<Project>
|
||||
<Option title="project" />
|
||||
<Option pch_mode="2" />
|
||||
<Option compiler="gcc" />
|
||||
<Build>
|
||||
<Target title="Debug">
|
||||
<Option output="build/bin/Debug/project" prefix_auto="1" extension_auto="1" />
|
||||
<Option object_output="build/obj/Debug/" />
|
||||
<Option type="1" />
|
||||
<Option compiler="gcc" />
|
||||
<Compiler>
|
||||
<Add option="-g" />
|
||||
</Compiler>
|
||||
</Target>
|
||||
<Target title="Release">
|
||||
<Option output="build/bin/Release/project" prefix_auto="1" extension_auto="1" />
|
||||
<Option object_output="build/obj/Release/" />
|
||||
<Option type="1" />
|
||||
<Option compiler="gcc" />
|
||||
<Compiler>
|
||||
<Add option="-O2" />
|
||||
</Compiler>
|
||||
<Linker>
|
||||
<Add option="-s" />
|
||||
</Linker>
|
||||
</Target>
|
||||
</Build>
|
||||
<Compiler>
|
||||
<Add option="-Wall" />
|
||||
</Compiler>
|
||||
<Extensions>
|
||||
<code_completion />
|
||||
<envvars />
|
||||
<debugger />
|
||||
<lib_finder disable_auto="1" />
|
||||
</Extensions>
|
||||
</Project>
|
||||
</CodeBlocks_project_file>
|
Loading…
Reference in New Issue