Merge pull request #40 from hathach/develop

stm32f4 port (Cont)
This commit is contained in:
hathach 2019-03-19 02:58:09 -07:00 committed by GitHub
commit 1c89090d18
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
33 changed files with 15656 additions and 176 deletions

View File

@ -19,3 +19,5 @@ before_script:
script:
- make -j2 -C examples/device/cdc_msc_hid BOARD=metro_m0_express
- make -j2 -C examples/device/cdc_msc_hid BOARD=metro_m4_express
- make -j2 -C examples/device/cdc_msc_hid BOARD=stm32f407g_disc1

View File

@ -45,9 +45,10 @@ Currently the following OS are supported with tinyusb out of the box with a simp
The stack supports the following MCUs
- **NXP:** LPC11Uxx, LPC13xx, LPC175x_6x, LPC177x_8x, LPC40xx, LPC43xx
- **MicroChip:** SAMD21, SAMD51 (device only)
- **Nordic:** nRF52840
- **Nordic:** nRF52840
- **NXP:** LPC11Uxx, LPC13xx, LPC175x_6x, LPC177x_8x, LPC40xx, LPC43xx
- **MicroChip:** SAMD21, SAMD51 (device only)
- **ST:** STM32F4
[Here is the list of supported Boards](hw/bsp/readme.md)
@ -64,8 +65,8 @@ The stack is developed with GCC compiler, and should be compilable with others.
TinyUSB is currently used by these other projects:
* [Adafruit nRF52 Arduino](https://github.com/adafruit/Adafruit_nRF52_Arduino)
* [Adafruit nRF52 Bootloader](https://github.com/adafruit/Adafruit_nRF52_Bootloader)
* [CircuitPython](https://github.com/adafruit/circuitpython)
* [nRF52840 UF2 Bootloader](https://github.com/adafruit/Adafruit_nRF52_Bootloader)
## Porting

View File

@ -21,7 +21,6 @@ include $(TOP)/hw/bsp/$(BOARD)/board.mk
CC = $(CROSS_COMPILE)gcc
CXX = $(CROSS_COMPILE)g++
LD = $(CROSS_COMPILE)ld
OBJCOPY = $(CROSS_COMPILE)objcopy
SIZE = $(CROSS_COMPILE)size
MKDIR = mkdir
@ -63,9 +62,9 @@ else
endif
CFLAGS += $(INC) -Wall -Werror -std=gnu11 -nostdlib -DBOARD_$(shell echo $(BOARD) | tr a-z\- A-Z_)
LDFLAGS += $(CFLAGS) -nostartfiles -fshort-enums -Wl,-T,$(TOP)/$(LD_FILE) -Wl,-Map=$@.map -Wl,-cref -Wl,-gc-sections -specs=nosys.specs -specs=nano.specs
LIBS := -lgcc -lc -lm -lnosys
LIBS = -lgcc -lc -lm -lnosys
EXAMPLE_SOURCE += \
src/main.c \
@ -92,9 +91,11 @@ SRC_C += $(LIB_SOURCE)
# Assembly files can be name with upper case .S, convert it to .s
SRC_S := $(SRC_S:.S=.s)
OBJ += $(addprefix $(BUILD)/obj/, $(SRC_C:.c=.o))
OBJ += $(addprefix $(BUILD)/obj/, $(SRC_S:.s=.o))
OBJ += $(addprefix $(BUILD)/obj/, $(SRC_C:.c=.o))
# Set all as default goal
.DEFAULT_GOAL := all
all: $(BUILD)/$(BOARD)-firmware.bin size
OBJ_DIRS = $(sort $(dir $(OBJ)))
@ -104,11 +105,15 @@ $(OBJ_DIRS):
$(BUILD)/$(BOARD)-firmware.elf: $(OBJ)
@echo LINK $@
@$(CC) -o $@ $(LDFLAGS) $^ -Wl,--start-group $(LIBS) -Wl,--end-group
$(CC) -o $@ $(LDFLAGS) $^ -Wl,--start-group $(LIBS) -Wl,--end-group
$(BUILD)/$(BOARD)-firmware.bin: $(BUILD)/$(BOARD)-firmware.elf
@echo CREATE $@
$(OBJCOPY) -O binary -j .vectors -j .text -j .data $^ $@
@$(OBJCOPY) -O binary -j .vectors -j .text -j .data $^ $@
$(BUILD)/$(BOARD)-firmware.hex: $(BUILD)/$(BOARD)-firmware.elf
@echo CREATE $@
@$(OBJCOPY) -O ihex $^ $@
# We set vpath to point to the top of the tree so that the source files
# can be located. By following this scheme, it allows a single build rule
@ -129,7 +134,7 @@ $(BUILD)/obj/%.o: %.c
vpath %.s . $(TOP)
$(BUILD)/obj/%.o: %.s
@echo AS $(notdir $@)
$(AS) -o $@ $<
@$(CC) -x assembler-with-cpp $(ASFLAGS) -c -o $@ $<
# ASM sources upper case .S
vpath %.S . $(TOP)
@ -137,6 +142,27 @@ $(BUILD)/obj/%.o: %.S
@echo AS $(notdir $@)
@$(CC) -x assembler-with-cpp $(ASFLAGS) -c -o $@ $<
# Flash binary using Jlink
ifeq ($(OS),Windows_NT)
JLINKEXE = JLink.exe
else
JLINKEXE = JLinkExe
endif
# default jlink interface is swd
ifeq ($(JLINK_IF),)
JLINK_IF = swd
endif
# Flash using jlink
flash-jlink: $(BUILD)/$(BOARD)-firmware.hex
@echo halt > $(BUILD)/$(BOARD).jlink
@echo loadfile $^ >> $(BUILD)/$(BOARD).jlink
@echo r >> $(BUILD)/$(BOARD).jlink
@echo go >> $(BUILD)/$(BOARD).jlink
@echo exit >> $(BUILD)/$(BOARD).jlink
$(JLINKEXE) -device $(JLINK_DEVICE) -if $(JLINK_IF) -speed auto -CommandFile $(BUILD)/$(BOARD).jlink
size: $(BUILD)/$(BOARD)-firmware.elf
-@echo ''
@$(SIZE) $<

View File

@ -9,4 +9,5 @@
<import file_name="lpc11u6x/lpc11u6x.emProject" />
<import file_name="lpc18xx/lpc18xx.emProject" />
<import file_name="lpc40xx/lpc40xx.emProject" />
<import file_name="stm32f4/stm32f4.emProject" />
</solution>

View File

@ -0,0 +1,6 @@
<!DOCTYPE Board_Memory_Definition_File>
<root name="STM32F407VG">
<MemorySegment name="FLASH" start="0x08000000" size="0x00100000" access="ReadOnly" />
<MemorySegment name="RAM" start="0x10000000" size="0x00010000" access="Read/Write" />
<MemorySegment name="RAM2" start="0x20000000" size="0x00020000" access="Read/Write" />
</root>

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,817 @@
/*****************************************************************************
* SEGGER Microcontroller GmbH & Co. KG *
* Solutions for real time microcontroller applications *
*****************************************************************************
* *
* (c) 2017 SEGGER Microcontroller GmbH & Co. KG *
* *
* Internet: www.segger.com Support: support@segger.com *
* *
*****************************************************************************/
/*****************************************************************************
* Preprocessor Definitions *
* ------------------------ *
* VECTORS_IN_RAM *
* *
* If defined, an area of RAM will large enough to store the vector table *
* will be reserved. *
* *
*****************************************************************************/
.syntax unified
.code 16
.section .init, "ax"
.align 0
/*****************************************************************************
* Default Exception Handlers *
*****************************************************************************/
.thumb_func
.weak NMI_Handler
NMI_Handler:
b .
.thumb_func
.weak HardFault_Handler
HardFault_Handler:
b .
.thumb_func
.weak SVC_Handler
SVC_Handler:
b .
.thumb_func
.weak PendSV_Handler
PendSV_Handler:
b .
.thumb_func
.weak SysTick_Handler
SysTick_Handler:
b .
.thumb_func
Dummy_Handler:
b .
#if defined(__OPTIMIZATION_SMALL)
.weak WWDG_IRQHandler
.thumb_set WWDG_IRQHandler,Dummy_Handler
.weak PVD_IRQHandler
.thumb_set PVD_IRQHandler,Dummy_Handler
.weak TAMP_STAMP_IRQHandler
.thumb_set TAMP_STAMP_IRQHandler,Dummy_Handler
.weak RTC_WKUP_IRQHandler
.thumb_set RTC_WKUP_IRQHandler,Dummy_Handler
.weak RCC_IRQHandler
.thumb_set RCC_IRQHandler,Dummy_Handler
.weak EXTI0_IRQHandler
.thumb_set EXTI0_IRQHandler,Dummy_Handler
.weak EXTI1_IRQHandler
.thumb_set EXTI1_IRQHandler,Dummy_Handler
.weak EXTI2_IRQHandler
.thumb_set EXTI2_IRQHandler,Dummy_Handler
.weak EXTI3_IRQHandler
.thumb_set EXTI3_IRQHandler,Dummy_Handler
.weak EXTI4_IRQHandler
.thumb_set EXTI4_IRQHandler,Dummy_Handler
.weak DMA1_Stream0_IRQHandler
.thumb_set DMA1_Stream0_IRQHandler,Dummy_Handler
.weak DMA1_Stream1_IRQHandler
.thumb_set DMA1_Stream1_IRQHandler,Dummy_Handler
.weak DMA1_Stream2_IRQHandler
.thumb_set DMA1_Stream2_IRQHandler,Dummy_Handler
.weak DMA1_Stream3_IRQHandler
.thumb_set DMA1_Stream3_IRQHandler,Dummy_Handler
.weak DMA1_Stream4_IRQHandler
.thumb_set DMA1_Stream4_IRQHandler,Dummy_Handler
.weak DMA1_Stream5_IRQHandler
.thumb_set DMA1_Stream5_IRQHandler,Dummy_Handler
.weak DMA1_Stream6_IRQHandler
.thumb_set DMA1_Stream6_IRQHandler,Dummy_Handler
.weak ADC_IRQHandler
.thumb_set ADC_IRQHandler,Dummy_Handler
.weak CAN1_TX_IRQHandler
.thumb_set CAN1_TX_IRQHandler,Dummy_Handler
.weak CAN1_RX0_IRQHandler
.thumb_set CAN1_RX0_IRQHandler,Dummy_Handler
.weak CAN1_RX1_IRQHandler
.thumb_set CAN1_RX1_IRQHandler,Dummy_Handler
.weak CAN1_SCE_IRQHandler
.thumb_set CAN1_SCE_IRQHandler,Dummy_Handler
.weak EXTI9_5_IRQHandler
.thumb_set EXTI9_5_IRQHandler,Dummy_Handler
.weak TIM1_BRK_TIM9_IRQHandler
.thumb_set TIM1_BRK_TIM9_IRQHandler,Dummy_Handler
.weak TIM1_UP_TIM10_IRQHandler
.thumb_set TIM1_UP_TIM10_IRQHandler,Dummy_Handler
.weak TIM1_TRG_COM_TIM11_IRQHandler
.thumb_set TIM1_TRG_COM_TIM11_IRQHandler,Dummy_Handler
.weak TIM1_CC_IRQHandler
.thumb_set TIM1_CC_IRQHandler,Dummy_Handler
.weak TIM2_IRQHandler
.thumb_set TIM2_IRQHandler,Dummy_Handler
.weak TIM3_IRQHandler
.thumb_set TIM3_IRQHandler,Dummy_Handler
.weak TIM4_IRQHandler
.thumb_set TIM4_IRQHandler,Dummy_Handler
.weak I2C1_EV_IRQHandler
.thumb_set I2C1_EV_IRQHandler,Dummy_Handler
.weak I2C1_ER_IRQHandler
.thumb_set I2C1_ER_IRQHandler,Dummy_Handler
.weak I2C2_EV_IRQHandler
.thumb_set I2C2_EV_IRQHandler,Dummy_Handler
.weak I2C2_ER_IRQHandler
.thumb_set I2C2_ER_IRQHandler,Dummy_Handler
.weak SPI1_IRQHandler
.thumb_set SPI1_IRQHandler,Dummy_Handler
.weak SPI2_IRQHandler
.thumb_set SPI2_IRQHandler,Dummy_Handler
.weak USART1_IRQHandler
.thumb_set USART1_IRQHandler,Dummy_Handler
.weak USART2_IRQHandler
.thumb_set USART2_IRQHandler,Dummy_Handler
.weak USART3_IRQHandler
.thumb_set USART3_IRQHandler,Dummy_Handler
.weak EXTI15_10_IRQHandler
.thumb_set EXTI15_10_IRQHandler,Dummy_Handler
.weak RTC_Alarm_IRQHandler
.thumb_set RTC_Alarm_IRQHandler,Dummy_Handler
.weak OTG_FS_WKUP_IRQHandler
.thumb_set OTG_FS_WKUP_IRQHandler,Dummy_Handler
.weak TIM8_BRK_TIM12_IRQHandler
.thumb_set TIM8_BRK_TIM12_IRQHandler,Dummy_Handler
.weak TIM8_UP_TIM13_IRQHandler
.thumb_set TIM8_UP_TIM13_IRQHandler,Dummy_Handler
.weak TIM8_TRG_COM_TIM14_IRQHandler
.thumb_set TIM8_TRG_COM_TIM14_IRQHandler,Dummy_Handler
.weak TIM8_CC_IRQHandler
.thumb_set TIM8_CC_IRQHandler,Dummy_Handler
.weak DMA1_Stream7_IRQHandler
.thumb_set DMA1_Stream7_IRQHandler,Dummy_Handler
.weak FSMC_IRQHandler
.thumb_set FSMC_IRQHandler,Dummy_Handler
.weak SDIO_IRQHandler
.thumb_set SDIO_IRQHandler,Dummy_Handler
.weak TIM5_IRQHandler
.thumb_set TIM5_IRQHandler,Dummy_Handler
.weak SPI3_IRQHandler
.thumb_set SPI3_IRQHandler,Dummy_Handler
.weak UART4_IRQHandler
.thumb_set UART4_IRQHandler,Dummy_Handler
.weak UART5_IRQHandler
.thumb_set UART5_IRQHandler,Dummy_Handler
.weak TIM6_DAC_IRQHandler
.thumb_set TIM6_DAC_IRQHandler,Dummy_Handler
.weak TIM7_IRQHandler
.thumb_set TIM7_IRQHandler,Dummy_Handler
.weak DMA2_Stream0_IRQHandler
.thumb_set DMA2_Stream0_IRQHandler,Dummy_Handler
.weak DMA2_Stream1_IRQHandler
.thumb_set DMA2_Stream1_IRQHandler,Dummy_Handler
.weak DMA2_Stream2_IRQHandler
.thumb_set DMA2_Stream2_IRQHandler,Dummy_Handler
.weak DMA2_Stream3_IRQHandler
.thumb_set DMA2_Stream3_IRQHandler,Dummy_Handler
.weak DMA2_Stream4_IRQHandler
.thumb_set DMA2_Stream4_IRQHandler,Dummy_Handler
.weak ETH_IRQHandler
.thumb_set ETH_IRQHandler,Dummy_Handler
.weak ETH_WKUP_IRQHandler
.thumb_set ETH_WKUP_IRQHandler,Dummy_Handler
.weak CAN2_TX_IRQHandler
.thumb_set CAN2_TX_IRQHandler,Dummy_Handler
.weak CAN2_RX0_IRQHandler
.thumb_set CAN2_RX0_IRQHandler,Dummy_Handler
.weak CAN2_RX1_IRQHandler
.thumb_set CAN2_RX1_IRQHandler,Dummy_Handler
.weak CAN2_SCE_IRQHandler
.thumb_set CAN2_SCE_IRQHandler,Dummy_Handler
.weak OTG_FS_IRQHandler
.thumb_set OTG_FS_IRQHandler,Dummy_Handler
.weak DMA2_Stream5_IRQHandler
.thumb_set DMA2_Stream5_IRQHandler,Dummy_Handler
.weak DMA2_Stream6_IRQHandler
.thumb_set DMA2_Stream6_IRQHandler,Dummy_Handler
.weak DMA2_Stream7_IRQHandler
.thumb_set DMA2_Stream7_IRQHandler,Dummy_Handler
.weak USART6_IRQHandler
.thumb_set USART6_IRQHandler,Dummy_Handler
.weak I2C3_EV_IRQHandler
.thumb_set I2C3_EV_IRQHandler,Dummy_Handler
.weak I2C3_ER_IRQHandler
.thumb_set I2C3_ER_IRQHandler,Dummy_Handler
.weak OTG_HS_EP1_OUT_IRQHandler
.thumb_set OTG_HS_EP1_OUT_IRQHandler,Dummy_Handler
.weak OTG_HS_EP1_IN_IRQHandler
.thumb_set OTG_HS_EP1_IN_IRQHandler,Dummy_Handler
.weak OTG_HS_WKUP_IRQHandler
.thumb_set OTG_HS_WKUP_IRQHandler,Dummy_Handler
.weak OTG_HS_IRQHandler
.thumb_set OTG_HS_IRQHandler,Dummy_Handler
.weak DCMI_IRQHandler
.thumb_set DCMI_IRQHandler,Dummy_Handler
.weak FPU_IRQHandler
.thumb_set FPU_IRQHandler,Dummy_Handler
#else
.thumb_func
.weak WWDG_IRQHandler
WWDG_IRQHandler:
b .
.thumb_func
.weak PVD_IRQHandler
PVD_IRQHandler:
b .
.thumb_func
.weak TAMP_STAMP_IRQHandler
TAMP_STAMP_IRQHandler:
b .
.thumb_func
.weak RTC_WKUP_IRQHandler
RTC_WKUP_IRQHandler:
b .
.thumb_func
.weak RCC_IRQHandler
RCC_IRQHandler:
b .
.thumb_func
.weak EXTI0_IRQHandler
EXTI0_IRQHandler:
b .
.thumb_func
.weak EXTI1_IRQHandler
EXTI1_IRQHandler:
b .
.thumb_func
.weak EXTI2_IRQHandler
EXTI2_IRQHandler:
b .
.thumb_func
.weak EXTI3_IRQHandler
EXTI3_IRQHandler:
b .
.thumb_func
.weak EXTI4_IRQHandler
EXTI4_IRQHandler:
b .
.thumb_func
.weak DMA1_Stream0_IRQHandler
DMA1_Stream0_IRQHandler:
b .
.thumb_func
.weak DMA1_Stream1_IRQHandler
DMA1_Stream1_IRQHandler:
b .
.thumb_func
.weak DMA1_Stream2_IRQHandler
DMA1_Stream2_IRQHandler:
b .
.thumb_func
.weak DMA1_Stream3_IRQHandler
DMA1_Stream3_IRQHandler:
b .
.thumb_func
.weak DMA1_Stream4_IRQHandler
DMA1_Stream4_IRQHandler:
b .
.thumb_func
.weak DMA1_Stream5_IRQHandler
DMA1_Stream5_IRQHandler:
b .
.thumb_func
.weak DMA1_Stream6_IRQHandler
DMA1_Stream6_IRQHandler:
b .
.thumb_func
.weak ADC_IRQHandler
ADC_IRQHandler:
b .
.thumb_func
.weak CAN1_TX_IRQHandler
CAN1_TX_IRQHandler:
b .
.thumb_func
.weak CAN1_RX0_IRQHandler
CAN1_RX0_IRQHandler:
b .
.thumb_func
.weak CAN1_RX1_IRQHandler
CAN1_RX1_IRQHandler:
b .
.thumb_func
.weak CAN1_SCE_IRQHandler
CAN1_SCE_IRQHandler:
b .
.thumb_func
.weak EXTI9_5_IRQHandler
EXTI9_5_IRQHandler:
b .
.thumb_func
.weak TIM1_BRK_TIM9_IRQHandler
TIM1_BRK_TIM9_IRQHandler:
b .
.thumb_func
.weak TIM1_UP_TIM10_IRQHandler
TIM1_UP_TIM10_IRQHandler:
b .
.thumb_func
.weak TIM1_TRG_COM_TIM11_IRQHandler
TIM1_TRG_COM_TIM11_IRQHandler:
b .
.thumb_func
.weak TIM1_CC_IRQHandler
TIM1_CC_IRQHandler:
b .
.thumb_func
.weak TIM2_IRQHandler
TIM2_IRQHandler:
b .
.thumb_func
.weak TIM3_IRQHandler
TIM3_IRQHandler:
b .
.thumb_func
.weak TIM4_IRQHandler
TIM4_IRQHandler:
b .
.thumb_func
.weak I2C1_EV_IRQHandler
I2C1_EV_IRQHandler:
b .
.thumb_func
.weak I2C1_ER_IRQHandler
I2C1_ER_IRQHandler:
b .
.thumb_func
.weak I2C2_EV_IRQHandler
I2C2_EV_IRQHandler:
b .
.thumb_func
.weak I2C2_ER_IRQHandler
I2C2_ER_IRQHandler:
b .
.thumb_func
.weak SPI1_IRQHandler
SPI1_IRQHandler:
b .
.thumb_func
.weak SPI2_IRQHandler
SPI2_IRQHandler:
b .
.thumb_func
.weak USART1_IRQHandler
USART1_IRQHandler:
b .
.thumb_func
.weak USART2_IRQHandler
USART2_IRQHandler:
b .
.thumb_func
.weak USART3_IRQHandler
USART3_IRQHandler:
b .
.thumb_func
.weak EXTI15_10_IRQHandler
EXTI15_10_IRQHandler:
b .
.thumb_func
.weak RTC_Alarm_IRQHandler
RTC_Alarm_IRQHandler:
b .
.thumb_func
.weak OTG_FS_WKUP_IRQHandler
OTG_FS_WKUP_IRQHandler:
b .
.thumb_func
.weak TIM8_BRK_TIM12_IRQHandler
TIM8_BRK_TIM12_IRQHandler:
b .
.thumb_func
.weak TIM8_UP_TIM13_IRQHandler
TIM8_UP_TIM13_IRQHandler:
b .
.thumb_func
.weak TIM8_TRG_COM_TIM14_IRQHandler
TIM8_TRG_COM_TIM14_IRQHandler:
b .
.thumb_func
.weak TIM8_CC_IRQHandler
TIM8_CC_IRQHandler:
b .
.thumb_func
.weak DMA1_Stream7_IRQHandler
DMA1_Stream7_IRQHandler:
b .
.thumb_func
.weak FSMC_IRQHandler
FSMC_IRQHandler:
b .
.thumb_func
.weak SDIO_IRQHandler
SDIO_IRQHandler:
b .
.thumb_func
.weak TIM5_IRQHandler
TIM5_IRQHandler:
b .
.thumb_func
.weak SPI3_IRQHandler
SPI3_IRQHandler:
b .
.thumb_func
.weak UART4_IRQHandler
UART4_IRQHandler:
b .
.thumb_func
.weak UART5_IRQHandler
UART5_IRQHandler:
b .
.thumb_func
.weak TIM6_DAC_IRQHandler
TIM6_DAC_IRQHandler:
b .
.thumb_func
.weak TIM7_IRQHandler
TIM7_IRQHandler:
b .
.thumb_func
.weak DMA2_Stream0_IRQHandler
DMA2_Stream0_IRQHandler:
b .
.thumb_func
.weak DMA2_Stream1_IRQHandler
DMA2_Stream1_IRQHandler:
b .
.thumb_func
.weak DMA2_Stream2_IRQHandler
DMA2_Stream2_IRQHandler:
b .
.thumb_func
.weak DMA2_Stream3_IRQHandler
DMA2_Stream3_IRQHandler:
b .
.thumb_func
.weak DMA2_Stream4_IRQHandler
DMA2_Stream4_IRQHandler:
b .
.thumb_func
.weak ETH_IRQHandler
ETH_IRQHandler:
b .
.thumb_func
.weak ETH_WKUP_IRQHandler
ETH_WKUP_IRQHandler:
b .
.thumb_func
.weak CAN2_TX_IRQHandler
CAN2_TX_IRQHandler:
b .
.thumb_func
.weak CAN2_RX0_IRQHandler
CAN2_RX0_IRQHandler:
b .
.thumb_func
.weak CAN2_RX1_IRQHandler
CAN2_RX1_IRQHandler:
b .
.thumb_func
.weak CAN2_SCE_IRQHandler
CAN2_SCE_IRQHandler:
b .
.thumb_func
.weak OTG_FS_IRQHandler
OTG_FS_IRQHandler:
b .
.thumb_func
.weak DMA2_Stream5_IRQHandler
DMA2_Stream5_IRQHandler:
b .
.thumb_func
.weak DMA2_Stream6_IRQHandler
DMA2_Stream6_IRQHandler:
b .
.thumb_func
.weak DMA2_Stream7_IRQHandler
DMA2_Stream7_IRQHandler:
b .
.thumb_func
.weak USART6_IRQHandler
USART6_IRQHandler:
b .
.thumb_func
.weak I2C3_EV_IRQHandler
I2C3_EV_IRQHandler:
b .
.thumb_func
.weak I2C3_ER_IRQHandler
I2C3_ER_IRQHandler:
b .
.thumb_func
.weak OTG_HS_EP1_OUT_IRQHandler
OTG_HS_EP1_OUT_IRQHandler:
b .
.thumb_func
.weak OTG_HS_EP1_IN_IRQHandler
OTG_HS_EP1_IN_IRQHandler:
b .
.thumb_func
.weak OTG_HS_WKUP_IRQHandler
OTG_HS_WKUP_IRQHandler:
b .
.thumb_func
.weak OTG_HS_IRQHandler
OTG_HS_IRQHandler:
b .
.thumb_func
.weak DCMI_IRQHandler
DCMI_IRQHandler:
b .
.thumb_func
.weak FPU_IRQHandler
FPU_IRQHandler:
b .
#endif
/*****************************************************************************
* Vector Table *
*****************************************************************************/
.section .vectors, "ax"
.align 0
.global _vectors
.extern __stack_end__
.extern Reset_Handler
_vectors:
.word __stack_end__
.word Reset_Handler
.word NMI_Handler
.word HardFault_Handler
.word 0 /* Reserved */
.word 0 /* Reserved */
.word 0 /* Reserved */
.word 0 /* Reserved */
.word 0 /* Reserved */
.word 0 /* Reserved */
.word 0 /* Reserved */
.word SVC_Handler
.word 0 /* Reserved */
.word 0 /* Reserved */
.word PendSV_Handler
.word SysTick_Handler
.word WWDG_IRQHandler
.word PVD_IRQHandler
.word TAMP_STAMP_IRQHandler
.word RTC_WKUP_IRQHandler
.word Dummy_Handler /* Reserved */
.word RCC_IRQHandler
.word EXTI0_IRQHandler
.word EXTI1_IRQHandler
.word EXTI2_IRQHandler
.word EXTI3_IRQHandler
.word EXTI4_IRQHandler
.word DMA1_Stream0_IRQHandler
.word DMA1_Stream1_IRQHandler
.word DMA1_Stream2_IRQHandler
.word DMA1_Stream3_IRQHandler
.word DMA1_Stream4_IRQHandler
.word DMA1_Stream5_IRQHandler
.word DMA1_Stream6_IRQHandler
.word ADC_IRQHandler
.word CAN1_TX_IRQHandler
.word CAN1_RX0_IRQHandler
.word CAN1_RX1_IRQHandler
.word CAN1_SCE_IRQHandler
.word EXTI9_5_IRQHandler
.word TIM1_BRK_TIM9_IRQHandler
.word TIM1_UP_TIM10_IRQHandler
.word TIM1_TRG_COM_TIM11_IRQHandler
.word TIM1_CC_IRQHandler
.word TIM2_IRQHandler
.word TIM3_IRQHandler
.word TIM4_IRQHandler
.word I2C1_EV_IRQHandler
.word I2C1_ER_IRQHandler
.word I2C2_EV_IRQHandler
.word I2C2_ER_IRQHandler
.word SPI1_IRQHandler
.word SPI2_IRQHandler
.word USART1_IRQHandler
.word USART2_IRQHandler
.word USART3_IRQHandler
.word EXTI15_10_IRQHandler
.word RTC_Alarm_IRQHandler
.word OTG_FS_WKUP_IRQHandler
.word TIM8_BRK_TIM12_IRQHandler
.word TIM8_UP_TIM13_IRQHandler
.word TIM8_TRG_COM_TIM14_IRQHandler
.word TIM8_CC_IRQHandler
.word DMA1_Stream7_IRQHandler
.word FSMC_IRQHandler
.word SDIO_IRQHandler
.word TIM5_IRQHandler
.word SPI3_IRQHandler
.word UART4_IRQHandler
.word UART5_IRQHandler
.word TIM6_DAC_IRQHandler
.word TIM7_IRQHandler
.word DMA2_Stream0_IRQHandler
.word DMA2_Stream1_IRQHandler
.word DMA2_Stream2_IRQHandler
.word DMA2_Stream3_IRQHandler
.word DMA2_Stream4_IRQHandler
.word ETH_IRQHandler
.word ETH_WKUP_IRQHandler
.word CAN2_TX_IRQHandler
.word CAN2_RX0_IRQHandler
.word CAN2_RX1_IRQHandler
.word CAN2_SCE_IRQHandler
.word OTG_FS_IRQHandler
.word DMA2_Stream5_IRQHandler
.word DMA2_Stream6_IRQHandler
.word DMA2_Stream7_IRQHandler
.word USART6_IRQHandler
.word I2C3_EV_IRQHandler
.word I2C3_ER_IRQHandler
.word OTG_HS_EP1_OUT_IRQHandler
.word OTG_HS_EP1_IN_IRQHandler
.word OTG_HS_WKUP_IRQHandler
.word OTG_HS_IRQHandler
.word DCMI_IRQHandler
.word Dummy_Handler /* Reserved */
.word Dummy_Handler /* Reserved */
.word FPU_IRQHandler
_vectors_end:
#ifdef VECTORS_IN_RAM
.section .vectors_ram, "ax"
.align 0
.global _vectors_ram
_vectors_ram:
.space _vectors_end - _vectors, 0
#endif

View File

@ -0,0 +1,125 @@
/*****************************************************************************
* SEGGER Microcontroller GmbH & Co. KG *
* Solutions for real time microcontroller applications *
*****************************************************************************
* *
* (c) 2017 SEGGER Microcontroller GmbH & Co. KG *
* *
* Internet: www.segger.com Support: support@segger.com *
* *
*****************************************************************************/
/*****************************************************************************
* Preprocessor Definitions *
* ------------------------ *
* NO_FPU_ENABLE *
* *
* If defined, FPU will not be enabled. *
* *
* NO_STACK_INIT *
* *
* If defined, the stack pointer will not be initialised. *
* *
* NO_SYSTEM_INIT *
* *
* If defined, the SystemInit() function will not be called. By default *
* SystemInit() is called after reset to enable the clocks and memories to *
* be initialised prior to any C startup initialisation. *
* *
* NO_VTOR_CONFIG *
* *
* If defined, the vector table offset register will not be configured. *
* *
* MEMORY_INIT *
* *
* If defined, the MemoryInit() function will be called. By default *
* MemoryInit() is called after SystemInit() to enable an external memory *
* controller. *
* *
* STACK_INIT_VAL *
* *
* If defined, specifies the initial stack pointer value. If undefined, *
* the stack pointer will be initialised to point to the end of the *
* RAM segment. *
* *
* VECTORS_IN_RAM *
* *
* If defined, the exception vectors will be copied from Flash to RAM. *
* *
*****************************************************************************/
.syntax unified
.global Reset_Handler
.extern _vectors
.section .init, "ax"
.thumb_func
.equ VTOR_REG, 0xE000ED08
.equ FPU_CPACR_REG, 0xE000ED88
#ifndef STACK_INIT_VAL
#define STACK_INIT_VAL __RAM_segment_end__
#endif
Reset_Handler:
#ifndef NO_STACK_INIT
/* Initialise main stack */
ldr r0, =STACK_INIT_VAL
bic r0, #0x7
mov sp, r0
#endif
#ifndef NO_SYSTEM_INIT
/* Initialise system */
ldr r0, =SystemInit
blx r0
#endif
#ifdef MEMORY_INIT
ldr r0, =MemoryInit
blx r0
#endif
#ifdef VECTORS_IN_RAM
/* Copy exception vectors into RAM */
ldr r0, =__vectors_start__
ldr r1, =__vectors_end__
ldr r2, =__vectors_ram_start__
1:
cmp r0, r1
beq 2f
ldr r3, [r0]
str r3, [r2]
adds r0, r0, #4
adds r2, r2, #4
b 1b
2:
#endif
#ifndef NO_VTOR_CONFIG
/* Configure vector table offset register */
ldr r0, =VTOR_REG
#ifdef VECTORS_IN_RAM
ldr r1, =_vectors_ram
#else
ldr r1, =_vectors
#endif
str r1, [r0]
#endif
#if (defined(__ARM_ARCH_FPV4_SP_D16__) || defined(__ARM_ARCH_FPV5_D16__)) && !defined(NO_FPU_ENABLE)
/* Enable FPU */
ldr r0, =FPU_CPACR_REG
ldr r1, [r0]
orr r1, r1, #(0xF << 20)
str r1, [r0]
dsb
isb
#endif
/* Jump to program start */
b _start

View File

@ -0,0 +1,19 @@
/*****************************************************************************
* SEGGER Microcontroller GmbH & Co. KG *
* Solutions for real time microcontroller applications *
*****************************************************************************
* *
* (c) 2017 SEGGER Microcontroller GmbH & Co. KG *
* *
* Internet: www.segger.com Support: support@segger.com *
* *
*****************************************************************************/
function Reset() {
TargetInterface.resetAndStop();
}
function EnableTrace(traceInterfaceType) {
// TODO: Enable trace
}

View File

@ -0,0 +1,37 @@
<!DOCTYPE Linker_Placement_File>
<Root name="Flash Section Placement">
<MemorySegment name="$(FLASH_NAME:FLASH)">
<ProgramSection alignment="0x100" load="Yes" name=".vectors" start="$(FLASH_START:)" />
<ProgramSection alignment="4" load="Yes" name=".init" />
<ProgramSection alignment="4" load="Yes" name=".init_rodata" />
<ProgramSection alignment="4" load="Yes" name=".text" />
<ProgramSection alignment="4" load="Yes" name=".dtors" />
<ProgramSection alignment="4" load="Yes" name=".ctors" />
<ProgramSection alignment="4" load="Yes" name=".rodata" />
<ProgramSection alignment="4" load="Yes" name=".ARM.exidx" address_symbol="__exidx_start" end_symbol="__exidx_end" />
<ProgramSection alignment="4" load="Yes" runin=".fast_run" name=".fast" />
<ProgramSection alignment="4" load="Yes" runin=".data_run" name=".data" />
<ProgramSection alignment="4" load="Yes" runin=".tdata_run" name=".tdata" />
</MemorySegment>
<MemorySegment name="$(RAM_NAME:RAM);SRAM">
<ProgramSection alignment="0x100" load="No" name=".vectors_ram" start="$(RAM_START:$(SRAM_START:))" />
<ProgramSection alignment="4" load="No" name=".fast_run" />
<ProgramSection alignment="4" load="No" name=".data_run" />
<ProgramSection alignment="4" load="No" name=".bss" />
<ProgramSection alignment="4" load="No" name=".tbss" />
<ProgramSection alignment="4" load="No" name=".tdata_run" />
<ProgramSection alignment="4" load="No" name=".non_init" />
<ProgramSection alignment="4" size="__HEAPSIZE__" load="No" name=".heap" />
<ProgramSection alignment="8" size="__STACKSIZE__" load="No" place_from_segment_end="Yes" name=".stack" />
<ProgramSection alignment="8" size="__STACKSIZE_PROCESS__" load="No" name=".stack_process" />
</MemorySegment>
<MemorySegment name="$(FLASH2_NAME:FLASH2)">
<ProgramSection alignment="4" load="Yes" name=".text2" />
<ProgramSection alignment="4" load="Yes" name=".rodata2" />
<ProgramSection alignment="4" load="Yes" runin=".data2_run" name=".data2" />
</MemorySegment>
<MemorySegment name="$(RAM2_NAME:RAM2)">
<ProgramSection alignment="4" load="No" name=".data2_run" />
<ProgramSection alignment="4" load="No" name=".bss2" />
</MemorySegment>
</Root>

View File

@ -0,0 +1,85 @@
<!DOCTYPE CrossStudio_Project_File>
<solution Name="stm32f4" target="8" version="2">
<project Name="stm32f4">
<configuration
Name="Common"
Placement="Flash"
Target="STM32F407VG"
arm_architecture="v7EM"
arm_core_type="Cortex-M4"
arm_endian="Little"
arm_fp_abi="Hard"
arm_fpu_type="FPv4-SP-D16"
arm_interwork="No"
arm_linker_heap_size="256"
arm_linker_process_stack_size="0"
arm_linker_stack_size="256"
arm_simulator_memory_simulation_parameter="ROM;0x08000000;0x00100000;RAM;0x10000000;0x00010000;RAM;0x20000000;0x00020000"
arm_target_debug_interface_type="ADIv5"
arm_target_device_name="STM32F407VG"
arm_target_interface_type="SWD"
c_preprocessor_definitions="STM32F407xx;__STM32F4xx_FAMILY;__STM32F407_SUBFAMILY;ARM_MATH_CM4;FLASH_PLACEMENT=1;CFG_TUSB_MCU=OPT_MCU_STM32F4;HSE_VALUE=8000000;BOARD_STM32F407G_DISC1"
c_user_include_directories="../../src;$(rootDir)/src;$(rootDir)/hw;$(rootDir)/hw/mcu/st/cmsis;$(rootDir)/hw/mcu/st/stm32lib/CMSIS/STM32F4xx/Include"
debug_register_definition_file="$(ProjectDir)/STM32F40x_Registers.xml"
debug_target_connection="J-Link"
gcc_entry_point="Reset_Handler"
linker_memory_map_file="$(ProjectDir)/STM32F407VG_MemoryMap.xml"
linker_section_placement_file="$(ProjectDir)/flash_placement.xml"
macros="DeviceHeaderFile=$(PackagesDir)/STM32F4xx/CMSIS/Device/Include/stm32f4xx.h;DeviceLibraryIdentifier=M4lf;DeviceSystemFile=$(PackagesDir)/STM32F4xx/CMSIS/Device/Source/system_stm32f4xx.c;DeviceVectorsFile=$(PackagesDir)/STM32F4xx/Source/STM32F40x_Vectors.s;DeviceFamily=STM32F4xx;DeviceSubFamily=STM32F407;Target=STM32F407VG;Placement=Flash;rootDir=../../../../.."
package_dependencies="STM32F4xx"
project_directory=""
project_type="Executable"
target_reset_script="Reset();"
target_trace_initialize_script="EnableTrace(&quot;$(TraceInterfaceType)&quot;)" />
<folder Name="System Files">
<file file_name="thumb_crt0.s" />
<file file_name="STM32F4xx_Startup.s" />
<file file_name="STM32F40x_Vectors.s">
<configuration Name="Common" file_type="Assembly" />
</file>
<file file_name="STM32F4xx_Target.js">
<configuration Name="Common" file_type="Reset Script" />
</file>
</folder>
<folder
Name="tinyusb"
exclude=""
filter="*.c;*.h"
path="../../../../../src"
recurse="Yes" />
<folder
Name="src"
exclude=""
filter="*.c;*.h"
path="../../src"
recurse="Yes" />
<folder
Name="segger_rtt"
exclude=""
filter="*.c;*.h"
path="../../../../../lib/segger_rtt"
recurse="No" />
<folder Name="hw">
<folder Name="bsp">
<folder Name="stm32f407g_disc1">
<file file_name="../../../../../hw/bsp/stm32f407g_disc1/board_stm32f407g_disc1.c" />
<file file_name="../../../../../hw/bsp/stm32f407g_disc1/board_stm32f407g_disc1.h" />
</folder>
<file file_name="../../../../../hw/bsp/board.h" />
</folder>
<folder Name="mcu">
<folder Name="st">
<folder Name="system-init">
<file file_name="../../../../../hw/mcu/st/system-init/system_stm32f4xx.c" />
</folder>
<folder Name="stm32lib" />
</folder>
</folder>
</folder>
</project>
<configuration
Name="stm32f407g_disc1"
c_preprocessor_definitions="DEBUG"
gcc_debugging_level="Level 3"
gcc_optimization_level="None" />
</solution>

View File

@ -0,0 +1,415 @@
// **********************************************************************
// * SEGGER Microcontroller GmbH *
// * The Embedded Experts *
// **********************************************************************
// * *
// * (c) 2014 - 2018 SEGGER Microcontroller GmbH *
// * (c) 2001 - 2018 Rowley Associates Limited *
// * *
// * www.segger.com Support: support@segger.com *
// * *
// **********************************************************************
// * *
// * All rights reserved. *
// * *
// * Redistribution and use in source and binary forms, with or *
// * without modification, are permitted provided that the following *
// * conditions are met: *
// * *
// * - Redistributions of source code must retain the above copyright *
// * notice, this list of conditions and the following disclaimer. *
// * *
// * - Neither the name of SEGGER Microcontroller GmbH *
// * nor the names of its contributors may be used to endorse or *
// * promote products derived from this software without specific *
// * prior written permission. *
// * *
// * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND *
// * CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, *
// * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF *
// * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE *
// * DISCLAIMED. *
// * IN NO EVENT SHALL SEGGER Microcontroller GmbH BE LIABLE FOR *
// * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR *
// * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT *
// * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; *
// * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF *
// * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT *
// * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE *
// * USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH *
// * DAMAGE. *
// * *
// **********************************************************************
//
//
// Preprocessor Definitions
// ------------------------
// APP_ENTRY_POINT
//
// Defines the application entry point function, if undefined this setting
// defaults to "main".
//
// INITIALIZE_STACK
//
// If defined, the contents of the stack will be initialized to a the
// value 0xCC.
//
// INITIALIZE_SECONDARY_SECTIONS
//
// If defined, the .data2, .text2, .rodata2 and .bss2 sections will be initialized.
//
// INITIALIZE_TCM_SECTIONS
//
// If defined, the .data_tcm, .text_tcm, .rodata_tcm and .bss_tcm sections
// will be initialized.
//
// INITIALIZE_USER_SECTIONS
//
// If defined, the function InitializeUserMemorySections will be called prior
// to entering main in order to allow the user to initialize any user defined
// memory sections.
//
// FULL_LIBRARY
//
// If defined then
// - argc, argv are setup by the debug_getargs.
// - the exit symbol is defined and executes on return from main.
// - the exit symbol calls destructors, atexit functions and then debug_exit.
//
// If not defined then
// - argc and argv are zero.
// - the exit symbol is defined, executes on return from main and loops
//
#ifndef APP_ENTRY_POINT
#define APP_ENTRY_POINT main
#endif
#ifndef ARGSSPACE
#define ARGSSPACE 128
#endif
.syntax unified
.global _start
.extern APP_ENTRY_POINT
.global exit
.weak exit
#ifdef INITIALIZE_USER_SECTIONS
.extern InitializeUserMemorySections
#endif
.section .init, "ax"
.code 16
.balign 2
.thumb_func
_start:
/* Set up main stack if size > 0 */
ldr r1, =__stack_end__
ldr r0, =__stack_start__
subs r2, r1, r0
beq 1f
#ifdef __ARM_EABI__
movs r2, #0x7
bics r1, r2
#endif
mov sp, r1
#ifdef INITIALIZE_STACK
movs r2, #0xCC
ldr r0, =__stack_start__
bl memory_set
#endif
1:
/* Set up process stack if size > 0 */
ldr r1, =__stack_process_end__
ldr r0, =__stack_process_start__
subs r2, r1, r0
beq 1f
#ifdef __ARM_EABI__
movs r2, #0x7
bics r1, r2
#endif
msr psp, r1
movs r2, #2
msr control, r2
#ifdef INITIALIZE_STACK
movs r2, #0xCC
bl memory_set
#endif
1:
/* Copy initialized memory sections into RAM (if necessary). */
ldr r0, =__data_load_start__
ldr r1, =__data_start__
ldr r2, =__data_end__
bl memory_copy
ldr r0, =__text_load_start__
ldr r1, =__text_start__
ldr r2, =__text_end__
bl memory_copy
ldr r0, =__fast_load_start__
ldr r1, =__fast_start__
ldr r2, =__fast_end__
bl memory_copy
ldr r0, =__ctors_load_start__
ldr r1, =__ctors_start__
ldr r2, =__ctors_end__
bl memory_copy
ldr r0, =__dtors_load_start__
ldr r1, =__dtors_start__
ldr r2, =__dtors_end__
bl memory_copy
ldr r0, =__rodata_load_start__
ldr r1, =__rodata_start__
ldr r2, =__rodata_end__
bl memory_copy
ldr r0, =__tdata_load_start__
ldr r1, =__tdata_start__
ldr r2, =__tdata_end__
bl memory_copy
#ifdef INITIALIZE_SECONDARY_SECTIONS
ldr r0, =__data2_load_start__
ldr r1, =__data2_start__
ldr r2, =__data2_end__
bl memory_copy
ldr r0, =__text2_load_start__
ldr r1, =__text2_start__
ldr r2, =__text2_end__
bl memory_copy
ldr r0, =__rodata2_load_start__
ldr r1, =__rodata2_start__
ldr r2, =__rodata2_end__
bl memory_copy
#endif /* #ifdef INITIALIZE_SECONDARY_SECTIONS */
#ifdef INITIALIZE_TCM_SECTIONS
ldr r0, =__data_tcm_load_start__
ldr r1, =__data_tcm_start__
ldr r2, =__data_tcm_end__
bl memory_copy
ldr r0, =__text_tcm_load_start__
ldr r1, =__text_tcm_start__
ldr r2, =__text_tcm_end__
bl memory_copy
ldr r0, =__rodata_tcm_load_start__
ldr r1, =__rodata_tcm_start__
ldr r2, =__rodata_tcm_end__
bl memory_copy
#endif /* #ifdef INITIALIZE_TCM_SECTIONS */
/* Zero the bss. */
ldr r0, =__bss_start__
ldr r1, =__bss_end__
movs r2, #0
bl memory_set
ldr r0, =__tbss_start__
ldr r1, =__tbss_end__
movs r2, #0
bl memory_set
#ifdef INITIALIZE_SECONDARY_SECTIONS
ldr r0, =__bss2_start__
ldr r1, =__bss2_end__
mov r2, #0
bl memory_set
#endif /* #ifdef INITIALIZE_SECONDARY_SECTIONS */
#ifdef INITIALIZE_TCM_SECTIONS
ldr r0, =__bss_tcm_start__
ldr r1, =__bss_tcm_end__
mov r2, #0
bl memory_set
#endif /* #ifdef INITIALIZE_TCM_SECTIONS */
/* Initialize the heap */
ldr r0, = __heap_start__
ldr r1, = __heap_end__
subs r1, r1, r0
cmp r1, #8
blt 1f
movs r2, #0
str r2, [r0]
adds r0, r0, #4
str r1, [r0]
1:
#ifdef INITIALIZE_USER_SECTIONS
ldr r2, =InitializeUserMemorySections
blx r2
#endif
/* Call constructors */
ldr r0, =__ctors_start__
ldr r1, =__ctors_end__
ctor_loop:
cmp r0, r1
beq ctor_end
ldr r2, [r0]
adds r0, #4
push {r0-r1}
blx r2
pop {r0-r1}
b ctor_loop
ctor_end:
/* Setup initial call frame */
movs r0, #0
mov lr, r0
mov r12, sp
.type start, function
start:
/* Jump to application entry point */
#ifdef FULL_LIBRARY
movs r0, #ARGSSPACE
ldr r1, =args
ldr r2, =debug_getargs
blx r2
ldr r1, =args
#else
movs r0, #0
movs r1, #0
#endif
ldr r2, =APP_ENTRY_POINT
blx r2
.thumb_func
exit:
#ifdef FULL_LIBRARY
mov r5, r0 // save the exit parameter/return result
/* Call destructors */
ldr r0, =__dtors_start__
ldr r1, =__dtors_end__
dtor_loop:
cmp r0, r1
beq dtor_end
ldr r2, [r0]
add r0, #4
push {r0-r1}
blx r2
pop {r0-r1}
b dtor_loop
dtor_end:
/* Call atexit functions */
ldr r2, =_execute_at_exit_fns
blx r2
/* Call debug_exit with return result/exit parameter */
mov r0, r5
ldr r2, =debug_exit
blx r2
#endif
/* Returned from application entry point, loop forever. */
exit_loop:
b exit_loop
.thumb_func
memory_copy:
cmp r0, r1
beq 2f
subs r2, r2, r1
beq 2f
1:
ldrb r3, [r0]
adds r0, r0, #1
strb r3, [r1]
adds r1, r1, #1
subs r2, r2, #1
bne 1b
2:
bx lr
.thumb_func
memory_set:
cmp r0, r1
beq 1f
strb r2, [r0]
adds r0, r0, #1
b memory_set
1:
bx lr
// default C/C++ library helpers
.macro HELPER helper_name
.section .text.\helper_name, "ax", %progbits
.balign 2
.global \helper_name
.weak \helper_name
\helper_name:
.thumb_func
.endm
.macro JUMPTO name
#if defined(__thumb__) && !defined(__thumb2__)
mov r12, r0
ldr r0, =\name
push {r0}
mov r0, r12
pop {pc}
#else
b \name
#endif
.endm
HELPER __aeabi_read_tp
ldr r0, =__tbss_start__-8
bx lr
HELPER abort
b .
HELPER __assert
b .
HELPER __aeabi_assert
b .
HELPER __sync_synchronize
bx lr
HELPER __getchar
JUMPTO debug_getchar
HELPER __putchar
JUMPTO debug_putchar
HELPER __open
JUMPTO debug_fopen
HELPER __close
JUMPTO debug_fclose
HELPER __write
mov r3, r0
mov r0, r1
movs r1, #1
JUMPTO debug_fwrite
HELPER __read
mov r3, r0
mov r0, r1
movs r1, #1
JUMPTO debug_fread
HELPER __seek
push {r4, lr}
mov r4, r0
bl debug_fseek
cmp r0, #0
bne 1f
mov r0, r4
bl debug_ftell
pop {r4, pc}
1:
ldr r0, =-1
pop {r4, pc}
// char __user_locale_name_buffer[];
.section .bss.__user_locale_name_buffer, "aw", %nobits
.global __user_locale_name_buffer
.weak __user_locale_name_buffer
__user_locale_name_buffer:
.word 0x0
#ifdef FULL_LIBRARY
.bss
args:
.space ARGSSPACE
#endif
/* Setup attibutes of stack and heap sections so they don't take up room in the elf file */
.section .stack, "wa", %nobits
.section .stack_process, "wa", %nobits
.section .heap, "wa", %nobits

View File

@ -97,7 +97,7 @@
// #define CFG_TUD_DESC_PID 0x0001
// LPC 17xx and 40xx endpoint type (bulk/interrupt/iso) are fixed by its number
// Therefor we need to force endpoint number to correct type on lpc17xx
// Therefore we need to force endpoint number to correct type on lpc17xx
#if CFG_TUSB_MCU == OPT_MCU_LPC175X_6X || CFG_TUSB_MCU == OPT_MCU_LPC177X_8X || CFG_TUSB_MCU == OPT_MCU_LPC40XX
#define CFG_TUD_DESC_CDC_EPNUM_NOTIF 1
#define CFG_TUD_DESC_CDC_EPNUM 2

View File

@ -88,14 +88,14 @@ static const PINMUX_GRP_T pinclockmuxing[] =
// Invoked by startup code
void SystemInit(void)
{
/* Setup system level pin muxing */
Chip_SCU_SetPinMuxing(pinmuxing, sizeof(pinmuxing) / sizeof(PINMUX_GRP_T));
/* Setup system level pin muxing */
Chip_SCU_SetPinMuxing(pinmuxing, sizeof(pinmuxing) / sizeof(PINMUX_GRP_T));
/* Clock pins only, group field not used */
for (int i = 0; i < (sizeof(pinclockmuxing) / sizeof(pinclockmuxing[0])); i++)
{
Chip_SCU_ClockPinMuxSet(pinclockmuxing[i].pinnum, pinclockmuxing[i].modefunc);
}
/* Clock pins only, group field not used */
for (uint32_t i = 0; i < (sizeof(pinclockmuxing) / sizeof(pinclockmuxing[0])); i++)
{
Chip_SCU_ClockPinMuxSet(pinclockmuxing[i].pinnum, pinclockmuxing[i].modefunc);
}
Chip_SetupXtalClocking();
}
@ -115,7 +115,7 @@ void board_init(void)
const uint8_t ledports[] = {6, 6, 6, 6, 6, 4, 4, 4};
const uint8_t ledbits[] = {24, 25, 26, 27, 28, 12, 13, 14};
for (int i = 0; i < (sizeof(ledports) / sizeof(ledports[0])); i++)
for (uint32_t i = 0; i < (sizeof(ledports) / sizeof(ledports[0])); i++)
{
Chip_GPIO_SetPinDIROutput(LPC_GPIO_PORT, ledports[i], ledbits[i]);
Chip_GPIO_SetPinState(LPC_GPIO_PORT, LED_PORT, LED_PIN, false);
@ -197,10 +197,14 @@ void board_led_control(bool state)
}
//------------- Buttons -------------//
/*
static bool button_read(uint8_t id)
{
(void) id;
// return !TU_BIT_TEST( GPIO_ReadValue(buttons[id].gpio_port), buttons[id].gpio_pin ); // button is active low
return false;
}
*/
uint32_t board_buttons(void)
{
@ -216,9 +220,12 @@ uint32_t board_buttons(void)
uint8_t board_uart_getchar(void)
{
//return UART_ReceiveByte(BOARD_UART_PORT);
return 0;
}
void board_uart_putchar(uint8_t c)
{
(void) c;
//UART_Send(BOARD_UART_PORT, &c, 1, BLOCKING);
}

View File

@ -33,3 +33,8 @@ INC += \
VENDOR = microchip
CHIP_FAMILY = samd21
JLINK_DEVICE = ATSAMD21G18
# flash using jlink
flash: flash-jlink

View File

@ -32,3 +32,8 @@ INC += \
VENDOR = microchip
CHIP_FAMILY = samd51
JLINK_DEVICE = ATSAMD51J19
# flash using jlink
flash: flash-jlink

View File

@ -4,7 +4,11 @@
This code base already had supported for a handful of following boards
### NXP MCU ###
### Nordic nRF5x ###
- [nRF52840-DK (aka pca10056)](https://www.nordicsemi.com/Software-and-Tools/Development-Kits/nRF52840-DK)
### NXP LPC ###
- [LPCXpresso 11U68](https://www.nxp.com/support/developer-resources/evaluation-and-development-boards/lpcxpresso-boards/lpcxpresso-board-for-lpc11u68:OM13058)
- [LPCXpresso 1347](https://www.nxp.com/support/developer-resources/evaluation-and-development-boards/lpcxpresso-boards/lpcxpresso-board-for-lpc1347:OM13045)
@ -18,9 +22,9 @@ This code base already had supported for a handful of following boards
- [Adafruit Metro M0 Express](https://www.adafruit.com/product/3505)
- [Adafruit Metro M4 Express](https://www.adafruit.com/product/3382)
### Nordic nRF52840 ###
### ST STM32 ###
- [nRF52840-DK (aka pca10056)](https://www.nordicsemi.com/eng/Products/nRF52840-DK)
- [STM32F4 Discovery](https://www.st.com/en/evaluation-tools/stm32f4discovery.html)
## Add your own board ##

View File

@ -41,9 +41,9 @@ _Min_Stack_Size = 0x4000; /* required amount of stack */
/* Specify the memory areas */
MEMORY
{
RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 128K
CCMRAM (rw) : ORIGIN = 0x10000000, LENGTH = 64K
FLASH (rx) : ORIGIN = 0x8000000, LENGTH = 1024K
RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 128K
CCMRAM (rw) : ORIGIN = 0x10000000, LENGTH = 64K
FLASH (rx) : ORIGIN = 0x8000000, LENGTH = 1024K
}
/* Define output sections */

View File

@ -25,3 +25,24 @@ INC += \
VENDOR = st
CHIP_FAMILY = stm32f4
JLINK_DEVICE = stm32f407vg
# Path to STM32 Cube Programmer CLI
ifeq ($(OS),Windows_NT)
STM32Prog = C:/Program Files/STMicroelectronics/STM32Cube/STM32CubeProgrammer/bin/STM32_Programmer_CLI
else
UNAME_S := $(shell uname -s)
ifeq ($(UNAME_S),Linux)
STM32Prog = $(HOME)/STMicroelectronics/STM32Cube/STM32CubeProgrammer/bin/STM32_Programmer_CLI
endif
ifeq ($(UNAME_S),Darwin)
STM32Prog = STM32_Programmer_CLI
endif
endif
# flash target using on-board stlink
flash: $(BUILD)/$(BOARD)-firmware.elf
$(STM32Prog) --connect port=swd --write $< --go

View File

@ -45,8 +45,6 @@
//--------------------------------------------------------------------+
// MACRO TYPEDEF CONSTANT ENUM DECLARATION
//--------------------------------------------------------------------+
#define LED_STATE_ON 1
void board_init(void)
{
// Init the LED on PD14

View File

@ -171,14 +171,14 @@ static inline uint16_t tu_u16_le2be(uint16_t u16)
}
// Min
static inline uint8_t tu_min8(uint8_t x, uint8_t y) { return (x < y) ? x : y; }
static inline uint16_t tu_min16(uint16_t x, uint16_t y) { return (x < y) ? x : y; }
static inline uint32_t tu_min32(uint32_t x, uint32_t y) { return (x < y) ? x : y; }
static inline uint8_t tu_min8 (uint8_t x, uint8_t y ) { return (x < y) ? x : y; }
static inline uint16_t tu_min16 (uint16_t x, uint16_t y) { return (x < y) ? x : y; }
static inline uint32_t tu_min32 (uint32_t x, uint32_t y) { return (x < y) ? x : y; }
// Max
static inline uint8_t tu_max8(uint8_t x, uint8_t y) { return (x > y) ? x : y; }
static inline uint16_t tu_max16(uint16_t x, uint16_t y) { return (x > y) ? x : y; }
static inline uint32_t tu_max32(uint32_t x, uint32_t y) { return (x > y) ? x : y; }
static inline uint8_t tu_max8 (uint8_t x, uint8_t y ) { return (x > y) ? x : y; }
static inline uint16_t tu_max16 (uint16_t x, uint16_t y) { return (x > y) ? x : y; }
static inline uint32_t tu_max32 (uint32_t x, uint32_t y) { return (x > y) ? x : y; }
// Align
static inline uint32_t tu_align32 (uint32_t value) { return (value & 0xFFFFFFE0UL); }

View File

@ -94,10 +94,16 @@ TU_VERIFY_STATIC(sizeof(dcd_event_t) <= 12, "size is not correct");
*------------------------------------------------------------------*/
bool dcd_init (uint8_t rhport);
// Enable device interrupt
void dcd_int_enable (uint8_t rhport);
// Disable device interrupt
void dcd_int_disable(uint8_t rhport);
// Receive Set Address request, mcu port must also include status IN response
void dcd_set_address(uint8_t rhport, uint8_t dev_addr);
// Receive Set Config request
void dcd_set_config (uint8_t rhport, uint8_t config_num);
// Get current frame number
@ -118,15 +124,13 @@ void dcd_event_setup_received(uint8_t rhport, uint8_t const * setup, bool in_isr
// helper to send transfer complete event
void dcd_event_xfer_complete (uint8_t rhport, uint8_t ep_addr, uint32_t xferred_bytes, uint8_t result, bool in_isr);
/*------------------------------------------------------------------*/
/* Endpoint API
* - open : Configure endpoint's registers
* - xfer : Submit a transfer. When complete dcd_event_xfer_complete
* must be called to notify the stack
* - busy : Check if endpoint transferring is complete (TODO remove)
* - stall : stall ep. When control endpoint (addr = 0) is stalled,
* both direction (IN & OUT) of control ep must be stalled.
* - stall : stall endpoint
* - clear_stall : clear stall
* - stalled : check if stalled ( TODO remove )
*------------------------------------------------------------------*/

View File

@ -336,8 +336,8 @@ static bool process_control_request(uint8_t rhport, tusb_control_request_t const
switch ( p_request->bRequest )
{
case TUSB_REQ_SET_ADDRESS:
// response with status first before changing device address
usbd_control_status(rhport, p_request);
// DCD must include zero-length status response since depending on mcu,
// status could be sent either before or after changing device address
dcd_set_address(rhport, (uint8_t) p_request->wValue);
return true; // skip the rest
break;

View File

@ -74,7 +74,9 @@ void usbd_control_reset (uint8_t rhport)
void usbd_control_stall(uint8_t rhport)
{
dcd_edpt_stall(rhport, 0);
// when stalling control endpoint both IN and OUt will be stalled
dcd_edpt_stall(rhport, EDPT_CTRL_OUT);
dcd_edpt_stall(rhport, EDPT_CTRL_IN);
}
bool usbd_control_status(uint8_t rhport, tusb_control_request_t const * request)

View File

@ -61,7 +61,7 @@ bool usbd_control_xfer(uint8_t rhport, tusb_control_request_t const * request, v
// Send STATUS (zero length) packet
bool usbd_control_status(uint8_t rhport, tusb_control_request_t const * request);
// Stall control endpoint until new setup packet arrived
// Stall control endpoint (both IN and OUT) until new setup packet arrived
void usbd_control_stall(uint8_t rhport);
/*------------------------------------------------------------------*/

View File

@ -110,10 +110,12 @@ void dcd_int_disable(uint8_t rhport)
void dcd_set_address (uint8_t rhport, uint8_t dev_addr)
{
(void) rhport;
// Response with status first before changing device address
dcd_edpt_xfer(rhport, tu_edpt_addr(0, TUSB_DIR_IN), NULL, 0);
// Wait for EP0 to finish before switching the address.
while (USB->DEVICE.DeviceEndpoint[0].EPSTATUS.bit.BK1RDY == 1) {}
USB->DEVICE.DADD.reg = USB_DEVICE_DADD_DADD(dev_addr) | USB_DEVICE_DADD_ADDEN;
}
@ -230,11 +232,6 @@ void dcd_edpt_stall (uint8_t rhport, uint8_t ep_addr)
ep->EPSTATUSSET.reg = USB_DEVICE_EPSTATUSSET_STALLRQ1;
} else {
ep->EPSTATUSSET.reg = USB_DEVICE_EPSTATUSSET_STALLRQ0;
// for control, stall both IN & OUT
if (ep_addr == 0) {
ep->EPSTATUSSET.reg = USB_DEVICE_EPSTATUSSET_STALLRQ1;
}
}
}

View File

@ -115,10 +115,12 @@ void dcd_int_disable(uint8_t rhport)
void dcd_set_address (uint8_t rhport, uint8_t dev_addr)
{
(void) rhport;
// Response with status first before changing device address
dcd_edpt_xfer(rhport, tu_edpt_addr(0, TUSB_DIR_IN), NULL, 0);
// Wait for EP0 to finish before switching the address.
while (USB->DEVICE.DeviceEndpoint[0].EPSTATUS.bit.BK1RDY == 1) {}
USB->DEVICE.DADD.reg = USB_DEVICE_DADD_DADD(dev_addr) | USB_DEVICE_DADD_ADDEN;
}
@ -234,11 +236,6 @@ void dcd_edpt_stall (uint8_t rhport, uint8_t ep_addr)
ep->EPSTATUSSET.reg = USB_DEVICE_EPSTATUSSET_STALLRQ1;
} else {
ep->EPSTATUSSET.reg = USB_DEVICE_EPSTATUSSET_STALLRQ0;
// for control, stall both IN & OUT
if (ep_addr == 0) {
ep->EPSTATUSSET.reg = USB_DEVICE_EPSTATUSSET_STALLRQ1;
}
}
}

View File

@ -211,7 +211,7 @@ void dcd_set_address (uint8_t rhport, uint8_t dev_addr)
{
(void) rhport;
(void) dev_addr;
// Set Address is automatically update by hw controller
// Set Address is automatically update by hw controller, nothing to do
}
void dcd_set_config (uint8_t rhport, uint8_t config_num)

View File

@ -159,7 +159,8 @@ void dcd_set_config(uint8_t rhport, uint8_t config_num)
void dcd_set_address(uint8_t rhport, uint8_t dev_addr)
{
(void) rhport;
// Response with status first before changing device address
dcd_edpt_xfer(rhport, tu_edpt_addr(0, TUSB_DIR_IN), NULL, 0);
LPC_USB->DEVCMDSTAT &= ~CMDSTAT_DEVICE_ADDR_MASK;
LPC_USB->DEVCMDSTAT |= dev_addr;
@ -196,16 +197,9 @@ void dcd_edpt_stall(uint8_t rhport, uint8_t ep_addr)
{
(void) rhport;
if ( tu_edpt_number(ep_addr) == 0 )
{
// TODO cannot able to STALL Control OUT endpoint !!!!! FIXME try some walk-around
_dcd.ep[0][0].stall = _dcd.ep[1][0].stall = 1;
}
else
{
uint8_t const ep_id = ep_addr2id(ep_addr);
_dcd.ep[ep_id][0].stall = 1;
}
// TODO cannot able to STALL Control OUT endpoint !!!!! FIXME try some walk-around
uint8_t const ep_id = ep_addr2id(ep_addr);
_dcd.ep[ep_id][0].stall = 1;
}
bool dcd_edpt_stalled(uint8_t rhport, uint8_t ep_addr)

View File

@ -199,7 +199,7 @@ bool dcd_init(uint8_t rhport)
NVIC_ClearPendingIRQ(USB_IRQn);
NVIC_EnableIRQ(USB_IRQn);
return TUSB_ERROR_NONE;
return true;
}
void dcd_int_enable(uint8_t rhport)
@ -216,7 +216,9 @@ void dcd_int_disable(uint8_t rhport)
void dcd_set_address(uint8_t rhport, uint8_t dev_addr)
{
(void) rhport;
// Response with status first before changing device address
dcd_edpt_xfer(rhport, tu_edpt_addr(0, TUSB_DIR_IN), NULL, 0);
sie_write(SIE_CMDCODE_SET_ADDRESS, 1, 0x80 | dev_addr); // 7th bit is : device_enable
}

View File

@ -164,6 +164,9 @@ void dcd_int_disable(uint8_t rhport)
void dcd_set_address(uint8_t rhport, uint8_t dev_addr)
{
// Response with status first before changing device address
dcd_edpt_xfer(rhport, tu_edpt_addr(0, TUSB_DIR_IN), NULL, 0);
LPC_USB[rhport]->DEVICEADDR = (dev_addr << 25) | TU_BIT(24);
}
@ -214,14 +217,7 @@ void dcd_edpt_stall(uint8_t rhport, uint8_t ep_addr)
uint8_t const epnum = tu_edpt_number(ep_addr);
uint8_t const dir = tu_edpt_dir(ep_addr);
if ( epnum == 0)
{
// Stall both Control IN and OUT
LPC_USB[rhport]->ENDPTCTRL[epnum] |= ( (ENDPTCTRL_MASK_STALL << 16) || (ENDPTCTRL_MASK_STALL << 0) );
}else
{
LPC_USB[rhport]->ENDPTCTRL[epnum] |= ENDPTCTRL_MASK_STALL << (dir ? 16 : 0);
}
LPC_USB[rhport]->ENDPTCTRL[epnum] |= ENDPTCTRL_MASK_STALL << (dir ? 16 : 0);
}
bool dcd_edpt_stalled (uint8_t rhport, uint8_t ep_addr)

View File

@ -50,7 +50,7 @@
#define DEVICE_BASE (USB_OTG_DeviceTypeDef *) (USB_OTG_FS_PERIPH_BASE + USB_OTG_DEVICE_BASE)
#define OUT_EP_BASE (USB_OTG_OUTEndpointTypeDef *) (USB_OTG_FS_PERIPH_BASE + USB_OTG_OUT_ENDPOINT_BASE)
#define IN_EP_BASE (USB_OTG_INEndpointTypeDef *) (USB_OTG_FS_PERIPH_BASE + USB_OTG_IN_ENDPOINT_BASE)
#define FIFO_BASE(_x) (uint32_t *) (USB_OTG_FS_PERIPH_BASE + USB_OTG_FIFO_BASE + _x * USB_OTG_FIFO_SIZE)
#define FIFO_BASE(_x) (uint32_t *) (USB_OTG_FS_PERIPH_BASE + USB_OTG_FIFO_BASE + (_x) * USB_OTG_FIFO_SIZE)
static ATTR_ALIGNED(4) uint32_t _setup_packet[6];
static uint8_t _setup_offs; // We store up to 3 setup packets.
@ -80,20 +80,35 @@ static void bus_reset(void) {
dev->DOEPMSK |= USB_OTG_DOEPMSK_STUPM | USB_OTG_DOEPMSK_XFRCM;
dev->DIEPMSK |= USB_OTG_DIEPMSK_TOM | USB_OTG_DIEPMSK_XFRCM;
// Peripheral FIFO architecture (Rev18 RM 29.11)
//
// --------------- 320 ( 1280 bytes )
// | IN FIFO 3 |
// --------------- y + x + 16 + GRXFSIZ
// | IN FIFO 2 |
// --------------- x + 16 + GRXFSIZ
// | IN FIFO 1 |
// --------------- 16 + GRXFSIZ
// | IN FIFO 0 |
// --------------- GRXFSIZ
// | OUT FIFO |
// | ( Shared ) |
// --------------- 0
//
// FIFO sizes are set up by the following rules (each word 32-bits):
// OUT FIFO uses (based on page 1354 of Rev 17 of reference manual):
// All EP OUT shared a unique OUT FIFO which uses (based on page 1354 of Rev 17 of reference manual):
// * 10 locations in hardware for setup packets + setup control words
// (up to 3 setup packets).
// * 2 locations for OUT endpoint control words.
// * 64 bytes for maximum control packet size.
// * 16 for largest packet size of 64 bytes. ( TODO Highspeed is 512 bytes)
// * 1 location for global NAK (not required/used here).
// IN FIFO uses 64 bytes for maximum control packet size.
//
// However, for OUT FIFO, 10 + 2 + 16 = 28 doesn't seem to work (TODO: why?).
// Minimum that works in practice is 35, so allocate 40 32-bit locations
// as a buffer.
USB_OTG_FS->GRXFSIZ = 40;
USB_OTG_FS->DIEPTXF0_HNPTXFSIZ |= (16 << USB_OTG_TX0FD_Pos); // 16 32-bit words = 64 bytes
// It is recommended to allocate 2 times the largest packet size, therefore
// Recommended value = 10 + 1 + 2 x (16+2) = 47 --> Let's make it 50
USB_OTG_FS->GRXFSIZ = 50;
// Control IN uses FIFO 0 with 64 bytes ( 16 32-bit word )
USB_OTG_FS->DIEPTXF0_HNPTXFSIZ = (16 << USB_OTG_TX0FD_Pos) | (USB_OTG_FS->GRXFSIZ & 0x0000ffffUL);
out_ep[0].DOEPTSIZ |= (1 << USB_OTG_DOEPTSIZ_STUPCNT_Pos);
@ -182,6 +197,9 @@ void dcd_set_address (uint8_t rhport, uint8_t dev_addr)
USB_OTG_DeviceTypeDef * dev = DEVICE_BASE;
dev->DCFG |= (dev_addr << USB_OTG_DCFG_DAD_Pos) & USB_OTG_DCFG_DAD_Msk;
// Response with status after changing device address
dcd_edpt_xfer(rhport, tu_edpt_addr(0, TUSB_DIR_IN), NULL, 0);
}
void dcd_set_config (uint8_t rhport, uint8_t config_num)
@ -191,6 +209,15 @@ void dcd_set_config (uint8_t rhport, uint8_t config_num)
// Nothing to do
}
uint32_t dcd_get_frame_number(uint8_t rhport)
{
(void) rhport;
USB_OTG_DeviceTypeDef * dev = DEVICE_BASE;
return (dev->DSTS & USB_OTG_DSTS_FNSOF_Msk) >> USB_OTG_DSTS_FNSOF_Pos;
}
/*------------------------------------------------------------------*/
/* DCD Endpoint port
*------------------------------------------------------------------*/
@ -219,13 +246,34 @@ bool dcd_edpt_open (uint8_t rhport, tusb_desc_endpoint_t const * desc_edpt)
desc_edpt->wMaxPacketSize.size << USB_OTG_DOEPCTL_MPSIZ_Pos;
dev->DAINTMSK |= (1 << (USB_OTG_DAINTMSK_OEPM_Pos + epnum));
} else {
// Peripheral FIFO architecture (Rev18 RM 29.11)
//
// --------------- 320 ( 1280 bytes )
// | IN FIFO 3 |
// --------------- y + x + 16 + GRXFSIZ
// | IN FIFO 2 |
// --------------- x + 16 + GRXFSIZ
// | IN FIFO 1 |
// --------------- 16 + GRXFSIZ
// | IN FIFO 0 |
// --------------- GRXFSIZ
// | OUT FIFO |
// | ( Shared ) |
// --------------- 0
//
// Since OUT FIFO = 50, FIFO 0 = 16, average of FIFOx = (312-50-16) / 3 = 82 ~ 80
in_ep[epnum].DIEPCTL |= (1 << USB_OTG_DIEPCTL_USBAEP_Pos) | \
(epnum - 1) << USB_OTG_DIEPCTL_TXFNUM_Pos | \
desc_edpt->bmAttributes.xfer << USB_OTG_DIEPCTL_EPTYP_Pos | \
(desc_edpt->bmAttributes.xfer != TUSB_XFER_ISOCHRONOUS ? USB_OTG_DOEPCTL_SD0PID_SEVNFRM : 0) | \
desc_edpt->wMaxPacketSize.size << USB_OTG_DIEPCTL_MPSIZ_Pos;
dev->DAINTMSK |= (1 << (USB_OTG_DAINTMSK_IEPM_Pos + epnum));
USB_OTG_FS->DIEPTXF[epnum - 1] = (40 << USB_OTG_DIEPTXF_INEPTXFD_Pos) | (epnum * 0x100);
// Both TXFD and TXSA are in unit of 32-bit words
uint16_t const fifo_size = 80;
uint32_t const fifo_offset = (USB_OTG_FS->GRXFSIZ & 0x0000ffff) + 16 + fifo_size*(epnum-1);
USB_OTG_FS->DIEPTXF[epnum - 1] = (80 << USB_OTG_DIEPTXF_INEPTXFD_Pos) | fifo_offset;
}
return true;
@ -310,36 +358,46 @@ void dcd_edpt_stall (uint8_t rhport, uint8_t ep_addr)
uint8_t const dir = tu_edpt_dir(ep_addr);
if(dir == TUSB_DIR_IN) {
// Stop transmitting packets and NAK IN xfers.
in_ep[epnum].DIEPCTL |= USB_OTG_DIEPCTL_SNAK;
while((in_ep[epnum].DIEPINT & USB_OTG_DIEPINT_INEPNE) == 0);
// Only disable currently enabled non-control endpoint
if ( (epnum == 0) || !(in_ep[epnum].DIEPCTL & USB_OTG_DIEPCTL_EPENA) ){
in_ep[epnum].DIEPCTL |= (USB_OTG_DIEPCTL_SNAK | USB_OTG_DIEPCTL_STALL);
}else {
// Stop transmitting packets and NAK IN xfers.
in_ep[epnum].DIEPCTL |= USB_OTG_DIEPCTL_SNAK;
while((in_ep[epnum].DIEPINT & USB_OTG_DIEPINT_INEPNE) == 0);
// Disable the endpoint. Note that both SNAK and STALL are set here.
in_ep[epnum].DIEPCTL |= (USB_OTG_DIEPCTL_SNAK | USB_OTG_DIEPCTL_STALL | \
USB_OTG_DIEPCTL_EPDIS);
while((in_ep[epnum].DIEPINT & USB_OTG_DIEPINT_EPDISD_Msk) == 0);
in_ep[epnum].DIEPINT = USB_OTG_DIEPINT_EPDISD;
// Disable the endpoint. Note that both SNAK and STALL are set here.
in_ep[epnum].DIEPCTL |= (USB_OTG_DIEPCTL_SNAK | USB_OTG_DIEPCTL_STALL | \
USB_OTG_DIEPCTL_EPDIS);
while((in_ep[epnum].DIEPINT & USB_OTG_DIEPINT_EPDISD_Msk) == 0);
in_ep[epnum].DIEPINT = USB_OTG_DIEPINT_EPDISD;
}
// Flush the FIFO, and wait until we have confirmed it cleared.
USB_OTG_FS->GRSTCTL |= ((epnum - 1) << USB_OTG_GRSTCTL_TXFNUM_Pos);
USB_OTG_FS->GRSTCTL |= USB_OTG_GRSTCTL_TXFFLSH;
while((USB_OTG_FS->GRSTCTL & USB_OTG_GRSTCTL_TXFFLSH_Msk) != 0);
} else {
// Asserting GONAK is required to STALL an OUT endpoint.
// Simpler to use polling here, we don't use the "B"OUTNAKEFF interrupt
// anyway, and it can't be cleared by user code. If this while loop never
// finishes, we have bigger problems than just the stack.
dev->DCTL |= USB_OTG_DCTL_SGONAK;
while((USB_OTG_FS->GINTSTS & USB_OTG_GINTSTS_BOUTNAKEFF_Msk) == 0);
// Only disable currently enabled non-control endpoint
if ( (epnum == 0) || !(out_ep[epnum].DOEPCTL & USB_OTG_DOEPCTL_EPENA) ){
out_ep[epnum].DOEPCTL |= USB_OTG_DIEPCTL_STALL;
}else {
// Asserting GONAK is required to STALL an OUT endpoint.
// Simpler to use polling here, we don't use the "B"OUTNAKEFF interrupt
// anyway, and it can't be cleared by user code. If this while loop never
// finishes, we have bigger problems than just the stack.
dev->DCTL |= USB_OTG_DCTL_SGONAK;
while((USB_OTG_FS->GINTSTS & USB_OTG_GINTSTS_BOUTNAKEFF_Msk) == 0);
// Ditto here- disable the endpoint. Note that only STALL and not SNAK
// is set here.
out_ep[epnum].DOEPCTL |= (USB_OTG_DOEPCTL_STALL | USB_OTG_DOEPCTL_EPDIS);
while((out_ep[epnum].DOEPINT & USB_OTG_DOEPINT_EPDISD_Msk) == 0);
out_ep[epnum].DOEPINT = USB_OTG_DOEPINT_EPDISD;
// Ditto here- disable the endpoint. Note that only STALL and not SNAK
// is set here.
out_ep[epnum].DOEPCTL |= (USB_OTG_DOEPCTL_STALL | USB_OTG_DOEPCTL_EPDIS);
while((out_ep[epnum].DOEPINT & USB_OTG_DOEPINT_EPDISD_Msk) == 0);
out_ep[epnum].DOEPINT = USB_OTG_DOEPINT_EPDISD;
// Allow other OUT endpoints to keep receiving.
dev->DCTL |= USB_OTG_DCTL_CGONAK;
// Allow other OUT endpoints to keep receiving.
dev->DCTL |= USB_OTG_DCTL_CGONAK;
}
}
}
@ -574,7 +632,9 @@ static void handle_epout_ints(USB_OTG_DeviceTypeDef * dev, USB_OTG_OUTEndpointTy
// on a packet-basis. The core can internally handle multiple OUT
// packets; it would be more efficient to only trigger XFRC on a
// completed transfer for non-0 endpoints.
if(xfer->short_packet) {
// Transfer complete if short packet or total len is transferred
if(xfer->short_packet || (xfer->queued_len == xfer->total_len)) {
xfer->short_packet = false;
dcd_event_xfer_complete(0, n, xfer->queued_len, XFER_RESULT_SUCCESS, true);
} else {

View File

@ -1,69 +0,0 @@
/**************************************************************************/
/*!
@file hal_nrf5x.c
@author hathach
@section LICENSE
Software License Agreement (BSD License)
Copyright (c) 2018, hathach (tinyusb.org)
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:
1. Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright
notice, this list of conditions and the following disclaimer in the
documentation and/or other materials provided with the distribution.
3. Neither the name of the copyright holders nor the
names of its contributors may be used to endorse or promote products
derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ''AS IS'' AND ANY
EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
This file is part of the tinyusb stack.
*/
/**************************************************************************/
#include "tusb_option.h"
#if TUSB_OPT_DEVICE_ENABLED && CFG_TUSB_MCU == OPT_MCU_STM32F4
#include "stm32f4xx.h"
#include "tusb_hal.h"
/*------------------------------------------------------------------*/
/* TUSB HAL
*------------------------------------------------------------------*/
bool tusb_hal_init(void)
{
tusb_hal_int_enable(0);
return true;
}
void tusb_hal_int_enable(uint8_t rhport)
{
(void) rhport;
NVIC_EnableIRQ(OTG_FS_IRQn);
}
void tusb_hal_int_disable(uint8_t rhport)
{
(void) rhport;
NVIC_DisableIRQ(OTG_FS_IRQn);
}
#endif