commit 9d58a367ce7528c094abb9548a18f495f6511c4e Author: imi415 Date: Mon Aug 8 01:16:52 2022 +0000 Initial commit diff --git a/.gitmodules b/.gitmodules new file mode 100644 index 0000000..4de5efe --- /dev/null +++ b/.gitmodules @@ -0,0 +1,3 @@ +[submodule "lib/printf"] + path = lib/printf + url = https://github.com/mpaland/printf.git diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 0000000..a95f8de --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,43 @@ +cmake_minimum_required(VERSION 3.10) + +enable_language(ASM) + +project(hello) + +set(TARGET_LDSCRIPT "${CMAKE_SOURCE_DIR}/stx7105.ld") + +set(TARGET_SOURCES + "lib/printf/printf.c" + "src/main.c" + "src/stx7105_exc.c" + "src/stx7105_utils.c" + "startup_stx7105.S" +) + +set(TARGET_INCLUDES + "include" + "lib/printf" +) + +set(TARGET_FLAGS_HARDWARE "-m4-300 -ml") + +set(CMAKE_C_FLAGS_DEBUG "-DDEBUG -g -O0") +set(CMAKE_CXX_FLAGS_DEBUG "-DDEBUG -g -O0") +set(CMAKE_EXE_LINKER_FLAGS_DEBUG "") + +set(CMAKE_C_FLAGS_RELEASE "-DNDEBUG -O2 -flto") +set(CMAKE_CXX_FLAGS_RELEASE "-DNDEBUG -O2 -flto") +set(CMAKE_EXE_LINKER_FLAGS_RELEASE "-flto") + +set(CMAKE_C_FLAGS "${TARGET_FLAGS_HARDWARE} -Wall -ffunction-sections -fdata-sections") +set(CMAKE_CXX_FLAGS "${TARGET_FLAGS_HARDWARE} -Wall -ffunction-sections -fdata-sections") +set(CMAKE_EXE_LINKER_FLAGS "${TARGET_FLAGS_HARDWARE} -Wall -lc -lm -nostartfiles -Wl,--print-memory-usage -Wl,--gc-sections") + +add_compile_definitions(${TARGET_DEFS}) +include_directories(${TARGET_INCLUDES}) + +add_executable(${CMAKE_PROJECT_NAME}.elf ${TARGET_SOURCES}) +target_link_options(${CMAKE_PROJECT_NAME}.elf + PRIVATE "-T${TARGET_LDSCRIPT}" + PRIVATE "-Wl,-Map=${CMAKE_PROJECT_NAME}.map" +) \ No newline at end of file diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..0d98490 --- /dev/null +++ b/LICENSE @@ -0,0 +1,7 @@ +Copyright 2022 imi415 + +Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. \ No newline at end of file diff --git a/LICENSE.STM b/LICENSE.STM new file mode 100644 index 0000000..79c0a2c --- /dev/null +++ b/LICENSE.STM @@ -0,0 +1,3 @@ +This project uses some initialization code from STLinux U-Boot, +the license header is kept in the corresponding files. +Check these files for license. diff --git a/include/stx7105.h b/include/stx7105.h new file mode 100644 index 0000000..99d349d --- /dev/null +++ b/include/stx7105.h @@ -0,0 +1,182 @@ +#ifndef STX7105_H +#define STX7105_H + +#include + +#define __PACKED __attribute__((packed, aligned(1))) +#define __IO volatile + +typedef struct { + __IO uint8_t POUT; /* Offset: 0x00, GPIO pin output register */ + uint8_t UNUSED0[3]; /* Offset: 0x01 */ + __IO uint8_t SET_POUT; /* Offset: 0x04, GPIO pin output set register */ + uint8_t UNUSED1[3]; /* Offset: 0x05 */ + __IO uint8_t CLR_POUT; /* Offset: 0x08, GPIO pin output clear register */ + uint8_t UNUSED2[7]; /* Offset: 0x09 */ + __IO uint8_t PIN; /* Offset: 0x10, GPIO pin input register */ + uint8_t UNUSED3[15]; /* Offset: 0x11 */ + __IO uint8_t PC0; /* Offset: 0x20, GPIO pin config register 0 */ + uint8_t UNUSED4[3]; /* Offset: 0x21 */ + __IO uint8_t SET_PC0; /* Offset: 0x24, GPIO pin config set register 0 */ + uint8_t UNUSED5[3]; /* Offset: 0x25 */ + __IO uint8_t CLR_PC0; /* Offset: 0x28, GPIO pin config clear register 0 */ + uint8_t UNUSED6[7]; /* Offset: 0x29 */ + __IO uint8_t PC1; /* Offset: 0x30, GPIO pin config register 1 */ + uint8_t UNUSED7[3]; /* Offset: 0x31 */ + __IO uint8_t SET_PC1; /* Offset: 0x34, GPIO pin config set register 1 */ + uint8_t UNUSED8[3]; /* Offset: 0x35 */ + __IO uint8_t CLR_PC1; /* Offset: 0x38, GPIO pin config clear register 1 */ + uint8_t UNUSED9[7]; /* Offset: 0x39 */ + __IO uint8_t PC2; /* Offset: 0x40, GPIO pin config register 2 */ + uint8_t UNUSED10[3]; /* Offset: 0x41 */ + __IO uint8_t SET_PC2; /* Offset: 0x44, GPIO pin config set register 2 */ + uint8_t UNUSED11[3]; /* Offset: 0x45 */ + __IO uint8_t CLR_PC2; /* Offset: 0x48, GPIO pin config clear register 2 */ + uint8_t UNUSED12[7]; /* Offset: 0x49 */ + __IO uint8_t PCOMP; /* Offset: 0x50, GPIO pin input comparison register */ + uint8_t UNUSED13[3]; /* Offset: 0x51 */ + __IO uint8_t SET_PCOMP; /* Offset: 0x54, GPIO pin input comparison set regiser */ + uint8_t UNUSED14[3]; /* Offset: 0x55 */ + __IO uint8_t CLR_PCOMP; /* Offset: 0x58, GPIO pin input comparison clear regiser */ + uint8_t UNUSED15[7]; /* Offset: 0x59 */ + __IO uint8_t PMASK; /* Offset: 0x60, GPIO pin input comparison mask register */ + uint8_t UNUSED16[3]; /* Offset: 0x61 */ + __IO uint8_t SET_PMASK; /* Offset: 0x64, GPIO pin input comparison mask set regiser */ + uint8_t UNUSED17[3]; /* Offset: 0x65 */ + __IO uint8_t CLR_PMASK; /* Offset: 0x68, GPIO pin input comparison mask clear regiser */ +} PIO_TypeDef; + +typedef struct { + __IO uint32_t BAUDRATE; /* Offset: 0x00, ASCn baud rate generator register */ + __IO uint32_t TX_BUF; /* Offset: 0x04, ASCn transmit buffer register */ + __IO uint32_t RX_BUF; /* Offset: 0x08, ASCn receive buffer register */ + __IO uint32_t CTRL; /* Offset: 0x0C, ASCn control register */ + __IO uint32_t INT_EN; /* Offset: 0x10, ASCn interrupt enable register */ + __IO uint32_t STA; /* Offset: 0x14, ASCn interrupt status register */ + __IO uint32_t GUARDTIME; /* Offset: 0x18, ASCn guard time register */ + __IO uint32_t TIMEOUT; /* Offset: 0x1C, ASCn time out register */ + __IO uint32_t TX_RST; /* Offset: 0x20, ASCn transmit FIFO reset register */ + __IO uint32_t RX_RST; /* Offset: 0x24, ASCn receive FIFO reset register */ + __IO uint32_t RETRIES; /* Offset: 0x28, ASCn number of retries on transmission register */ +} ASC_TypeDef; + +typedef struct { + __IO uint16_t ICR; /* Offset: 0x00, Interrupt control register */ + uint8_t UNUSED0[2]; /* Offset: 0x02 */ + __IO uint16_t IPRA; /* Offset: 0x04, Interrupt priority level A register */ + uint8_t UNUSED1[2]; /* Offset: 0x06 */ + __IO uint16_t IPRB; /* Offset: 0x08, Interrupt priority level B register */ + uint8_t UNUSED2[2]; /* Offset: 0x0A */ + __IO uint16_t IPRC; /* Offset: 0x0C, Interrupt priority level C register */ + uint8_t UNUSED3[2]; /* Offset: 0x0E */ + __IO uint16_t IPRD; /* Offset: 0x10, Interrupt priority level D register */ + uint8_t UNUSED4[2]; /* Offset: 0x12 */ +} INTC_TypeDef; + +typedef struct { + __IO uint8_t TOCR; /* Offset: 0x00, Timer output control register */ + uint8_t UNUSED0[3]; /* Offset: 0x01 */ + __IO uint8_t TSTR; /* Offset: 0x04, Timer start register */ + uint8_t UNUSED1[3]; /* Offset: 0x05 */ + __IO uint32_t TCOR0; /* Offset: 0x08, Timer constant register 0 */ + __IO uint32_t TCNT0; /* Offset: 0x0C, Timer counter 0 */ + __IO uint16_t TCR0; /* Offset: 0x10, Timer control register 0 */ + uint8_t UNUSED2[2]; /* Offset: 0x11 */ + __IO uint32_t TCOR1; /* Offset: 0x14, Timer constant register 1 */ + __IO uint32_t TCNT1; /* Offset: 0x18, Timer counter 1 */ + __IO uint16_t TCR1; /* Offset: 0x1C, Timer control register 1 */ + uint8_t UNUSED3[2]; /* Offset: 0x1E */ + __IO uint32_t TCOR2; /* Offset: 0x20, Timer constant register 2 */ + __IO uint32_t TCNT2; /* Offset: 0x24, Timer counter 2 */ + __IO uint16_t TCR2; /* Offset: 0x28, Timer control register 2 */ + __IO uint8_t UNUSED4[2]; /* Offset: 0x2A */ + uint32_t TCPR2; /* Offset: 0x2C */ +} TMU_TypeDef; + +typedef struct { + __IO uint32_t PTEH; /* Offset: 0x00000, Page table entry high register */ + __IO uint32_t PTEL; /* Offset: 0x00004, Page table entry low register */ + __IO uint32_t TTB; /* Offset: 0x00008, Translation table base register */ + __IO uint32_t TEA; /* Offset: 0x0000C, TLB exception address register */ + __IO uint32_t MMUCR; /* Offset: 0x00010, MMU control register */ + __IO uint8_t BASRA; /* Offset: 0x00014, Break ASID register A*/ + uint8_t UNUSED0[3]; /* Offset: 0x00015 */ + __IO uint8_t BASRB; /* Offset: 0x00018, Break ASID register B*/ + uint8_t UNUSED1[3]; /* Offset: 0x00019 */ + __IO uint32_t CCR; /* Offset: 0x0001C, Cache control register */ + __IO uint32_t TRA; /* Offset: 0x00020, TRAPA exception register */ + __IO uint32_t EXPEVT; /* Offset: 0x00024, Exception event register */ + __IO uint32_t INTEVT; /* Offset: 0x00028, Interrupt event register */ + uint32_t UNUSED2[3]; /* Offset: 0x0002C */ + __IO uint32_t QACR0; /* Offset: 0x00038, Queue address control register 0 */ + __IO uint32_t QACR1; /* Offset: 0x0003C, Queue address control register 1 */ + uint32_t UNUSED3[12]; /* Offset: 0x00040 */ + __IO uint32_t PASCR; /* Offset: 0x00070, Physical address space control register */ + __IO uint32_t RAMCR; /* Offset: 0x00074, On-chip memory control register */ + __IO uint32_t IRMCR; /* Offset: 0x00078, Instruction refetch inhibit control register */ + uint32_t UNUSED4[2097028]; /* Offset: 0x0007C, Am I serious? */ + __IO uint32_t BARA; /* Offset: 0x20000, Break address register A */ + __IO uint8_t BAMRA; /* Offset: 0x20004, Break address mask register A */ + uint8_t UNUSED5[3]; /* Offset: 0x20005 */ + __IO uint16_t BBRA; /* Offset: 0x20008, Break bus cycle register A */ + uint8_t UNUSED6[2]; /* Offset: 0x2000A */ + __IO uint32_t BARB; /* Offset: 0x2000B, Break address register B */ + __IO uint8_t BAMRB; /* Offset: 0x20010, Break address mask register B */ + uint8_t UNUSED7[3]; /* Offset: 0x20011 */ + __IO uint16_t BBRB; /* Offset: 0x20014, Break bus cycle register B */ + uint8_t UNUSED8[2]; /* Offset: 0x20016 */ + __IO uint32_t BDRB; /* Offset: 0x20018, Break data register B */ + __IO uint32_t BDMRB; /* Offset: 0x2001C, Break data mask register B */ + __IO uint16_t BRCR; /* Offset: 0x20020, Break control register */ + uint8_t UNUSED9[2]; /* Offset: 0x20022 */ +} CSR_TypeDef; + +#define PIO0_BASE (0xFD020000U) +#define PIO1_BASE (0xFD021000U) +#define PIO2_BASE (0xFD022000U) +#define PIO3_BASE (0xFD023000U) +#define PIO4_BASE (0xFD024000U) +#define PIO5_BASE (0xFD025000U) +#define PIO6_BASE (0xFD026000U) +#define ASC0_BASE (0xFD030000U) +#define ASC1_BASE (0xFD031000U) +#define ASC2_BASE (0xFD032000U) +#define ASC3_BASE (0xFD033000U) +#define CSR_BASE (0xFF000000U) +#define INTC_BASE (0xFFD00000U) +#define TMU_BASE (0xFFD80000U) + +#define PIO0 ((PIO_TypeDef *)PIO0_BASE) +#define PIO1 ((PIO_TypeDef *)PIO1_BASE) +#define PIO2 ((PIO_TypeDef *)PIO2_BASE) +#define PIO3 ((PIO_TypeDef *)PIO3_BASE) +#define PIO4 ((PIO_TypeDef *)PIO4_BASE) +#define PIO5 ((PIO_TypeDef *)PIO5_BASE) +#define PIO6 ((PIO_TypeDef *)PIO6_BASE) +#define ASC0 ((ASC_TypeDef *)ASC0_BASE) +#define ASC1 ((ASC_TypeDef *)ASC1_BASE) +#define ASC2 ((ASC_TypeDef *)ASC2_BASE) +#define ASC3 ((ASC_TypeDef *)ASC3_BASE) +#define CSR ((CSR_TypeDef *)CSR_BASE) +#define INTC ((INTC_TypeDef *)INTC_BASE) +#define TMU ((TMU_TypeDef *)TMU_BASE) + +#define TMU_TSTR_STR0_Pos 0 +#define TMU_TSTR_STR0_Msk (1U << TMU_TSTR_STR0_Pos) + +#define TMU_TSTR_STR1_Pos 1 +#define TMU_TSTR_STR1_Msk (1U << TMU_TSTR_STR1_Pos) + +#define TMU_TSTR_STR2_Pos 2 +#define TMU_TSTR_STR3_Msk (1U << TMU_TSTR_STR2_Pos) + +#define TMU_TCR_UNIE_Pos 5 +#define TMU_TCR_UNIE_Msk (1U << TMU_TCR_UNIE_Pos) + +#define TMU_TCR_UNF_Pos 8 +#define TMU_TCR_UNF_Msk (1U << TMU_TCR_UNF_Pos) + +#define INTC_IPRA_IPR_TMU0_Pos 12 +#define INTC_IPRA_IPR_TMU0_Msk (0x0FU << INTC_IPRA_IPR_TMU0_Pos) + +#endif \ No newline at end of file diff --git a/include/stx7105_utils.h b/include/stx7105_utils.h new file mode 100644 index 0000000..5cc2b2b --- /dev/null +++ b/include/stx7105_utils.h @@ -0,0 +1,11 @@ +#ifndef STX7105_UTILS_H +#define STX7105_UTILS_H + +#include + +void init_led(PIO_TypeDef *gpiox, uint8_t pin, uint8_t init_value); +void set_led(PIO_TypeDef *gpiox, uint8_t pin, uint8_t val); + +void delay_ms(uint32_t msec); + +#endif \ No newline at end of file diff --git a/sh-unknown-elf.cmake b/sh-unknown-elf.cmake new file mode 100644 index 0000000..9593af3 --- /dev/null +++ b/sh-unknown-elf.cmake @@ -0,0 +1,10 @@ +set(CMAKE_C_COMPILER sh-unknown-elf-gcc) +set(CMAKE_CXX_COMPILER sh-unknown-elf-g++) + +# Make CMake happy about those compilers +set(CMAKE_TRY_COMPILE_TARGET_TYPE "STATIC_LIBRARY") + +# Poor old Windows... +if(WIN32) + set(CMAKE_SYSTEM_NAME "Generic") +endif() \ No newline at end of file diff --git a/sh4helpers.gdb b/sh4helpers.gdb new file mode 100644 index 0000000..527ca2f --- /dev/null +++ b/sh4helpers.gdb @@ -0,0 +1,13 @@ +# The magic number below is the point where bootloader has completed initializing the LMI. + +define box_setup + sh4tp STMCLT2333_A:iptv7105:st40,no_pokes=1 + hbreak *0xA000008C + continue + delete breakpoint 1 + load + + hbreak _main +end + +box_setup diff --git a/src/main.c b/src/main.c new file mode 100644 index 0000000..58982f6 --- /dev/null +++ b/src/main.c @@ -0,0 +1,58 @@ +#include +#include + +#include "printf.h" +#include "stx7105.h" +#include "stx7105_utils.h" + +#define LED_RED_GPIO PIO0 +#define LED_RED_PIN 5U + +#define LED_BLUE_GPIO PIO0 +#define LED_BLUE_PIN 4U + +#define CONSOLE_ASC ASC2 +#define SYSTEM_DEVID (0xFE001000U) /* DEVID */ +#define SYSTEM_CONFIG34 (0xFE001188U) /* PIO4 */ +#define SYSTEM_CONFIG7 (0xFE00111CU) /* RXSEL */ + +void uart_init(void) { + PIO4->CLR_PC0 = 1U; /* PC = 110, AFOUT, PP */ + PIO4->SET_PC1 = 1U; + PIO4->SET_PC2 = 1U; + + *(uint32_t *)SYSTEM_CONFIG34 = 0x00000100UL; /* BIT[8,0] = 10, AF 3 */ + *(uint32_t *)SYSTEM_CONFIG7 &= ~(0x00000006UL); /* BIT[2:1], UART2 RX SEL */ + + CONSOLE_ASC->CTRL = 0x1509UL; /* 8N1, RX enable, FIFO enable, Baud mode 1 */ + CONSOLE_ASC->BAUDRATE = 0x04B8UL; /* 115200 in baud mode 1, assuming Fcomm=100MHz */ + CONSOLE_ASC->TX_RST = 0x01UL; /* Reset TX FIFO, any value OK */ + CONSOLE_ASC->RX_RST = 0x01UL; /* Reset RX FIFO, any value OK */ + CONSOLE_ASC->CTRL = 0x1589UL; /* 8N1, RX enable, FIFO enable, Baud mode 1 */ +} + +int main(void) { + init_led(LED_RED_GPIO, LED_RED_PIN, 0U); + init_led(LED_BLUE_GPIO, LED_BLUE_PIN, 0U); + + uart_init(); + + printf("Hello world\r\n"); + + for (;;) { + set_led(LED_BLUE_GPIO, LED_BLUE_PIN, 1U); + delay_ms(500); + printf("Hello ?\r\n"); + set_led(LED_BLUE_GPIO, LED_BLUE_PIN, 0U); + delay_ms(500); + } + + return 0; +} + +void _putchar(char ch) { + while(CONSOLE_ASC->STA & 1 << 9U) { + // wait for TX FIFO slot. + } + CONSOLE_ASC->TX_BUF = ch; +} \ No newline at end of file diff --git a/src/stx7105_exc.c b/src/stx7105_exc.c new file mode 100644 index 0000000..75dd1cc --- /dev/null +++ b/src/stx7105_exc.c @@ -0,0 +1,69 @@ +#include "stx7105.h" + +#define __WEAK __attribute__((weak)) +#define __IRQ __attribute__((interrupt_handler)) +#define __WEAK_IRQ __attribute__((weak, interrupt_handler)) + +typedef enum { + EXP_TYPE_TRAP = 0x160, +} expevt_type_t; + +typedef enum { + INT_TYPE_TMU_TNUI0 = 0x400, + INT_TYPE_TMU_TNUI1 = 0x420, + INT_TYPE_TMU_TNUI2 = 0x440, + INT_TYPE_TMU_TICPI2 = 0x460, +} intevt_type_t; + +typedef enum { + TRA_TYPE_SYSCALL = 34, +} tra_type_t; + + +__WEAK int tuni0_handler(void) { + /* Does nothing */ + return 0; +} + +__WEAK int syscall_handler(uint32_t p1, uint32_t p2, uint32_t p3, uint32_t p4) { + return 0; +} + +__WEAK int trap_handler(uint32_t p1, uint32_t p2, uint32_t p3, uint32_t p4) { + tra_type_t tra = CSR->TRA; + + switch (tra) { + case TRA_TYPE_SYSCALL: + return syscall_handler(p1, p2, p3, p4); + break; + default: + break; + } + + return 0; +} + +__WEAK_IRQ int general_exc_handler(uint32_t p1, uint32_t p2, uint32_t p3, uint32_t p4) { + expevt_type_t expevt = CSR->EXPEVT; + switch (expevt) { + case EXP_TYPE_TRAP: + return trap_handler(p1, p2, p3, p4); + break; + default: + break; + } + + return 0; +} + +__WEAK_IRQ int general_int_handler(void) { + intevt_type_t intevt = CSR->INTEVT; + switch (intevt) { + case INT_TYPE_TMU_TNUI0: + return tuni0_handler(); + break; + default: + break; + } + return 0; +} \ No newline at end of file diff --git a/src/stx7105_utils.c b/src/stx7105_utils.c new file mode 100644 index 0000000..6efa2eb --- /dev/null +++ b/src/stx7105_utils.c @@ -0,0 +1,56 @@ +#include "stx7105.h" + +/* Private */ +#include "stx7105_utils.h" + +volatile uint8_t s_tmu_flag = 0U; + +void init_led(PIO_TypeDef *gpiox, uint8_t pin, uint8_t init_value) { + gpiox->CLR_PC0 = 1 << pin; + gpiox->SET_PC1 = 1 << pin; + gpiox->CLR_PC2 = 1 << pin; + + set_led(gpiox, pin, init_value); +} + +void set_led(PIO_TypeDef *gpiox, uint8_t pin, uint8_t val) { + if (val) { + gpiox->SET_POUT = (1 << pin); + + } else { + gpiox->CLR_POUT = (1 << pin); + } +} + +void delay_ms(uint32_t msec) { + /* Initialize TMU and count to zero */ + /* TMU clock is from Peripheral clock, approx. 66MHz */ + /* Prescale to 66kHz for convenience (TMUs can only divide by max. 1024) */ + + uint32_t reload_value = msec * 66 - 1; + + TMU->TSTR &= ~TMU_TSTR_STR0_Msk; /* Stop counter */ + TMU->TCR0 = 0x04U | TMU_TCR_UNIE_Msk; /* 1024 prescale, enable interrupt */ + TMU->TCNT0 = reload_value; /* 66kHz */ + TMU->TCOR0 = reload_value; /* Reload register */ + TMU->TSTR |= TMU_TSTR_STR0_Msk; /* Start counter */ + + INTC->IPRA &= ~INTC_IPRA_IPR_TMU0_Msk; + INTC->IPRA |= (1U << INTC_IPRA_IPR_TMU0_Pos); /* Interrupt priority 1 */ + + /* Wait until underflow occurs */ + while(s_tmu_flag != 1) { + asm("sleep"); + } + + s_tmu_flag = 0U; + + TMU->TSTR &= ~TMU_TSTR_STR0_Msk; /* Stop counter */ +} + +int tuni0_handler(void) { + s_tmu_flag = 1U; + TMU->TCR0 &= ~(TMU_TCR_UNF_Msk); + + return 0; +} \ No newline at end of file diff --git a/startup_stx7105.S b/startup_stx7105.S new file mode 100644 index 0000000..686fec1 --- /dev/null +++ b/startup_stx7105.S @@ -0,0 +1,125 @@ +/* + * This section is read by bootloader, + * then the application will be copied according to the contents. + * !!DO NOT REMOVE!! + * See SPL project README for details. + */ + + .section .text.vtors, "ax" +_vtors: + .long _eidata + .long _start + +/* + * Startup code (CRT0) + */ + .section .text.init, "ax" + .global _start + +_start: + mov.l _stack_k, sp /* Setup R15(SP) */ + +_copy_data: + mov.l _sidata_k, r0 + mov.l _sdata_k, r1 + mov.l _edata_k, r2 + +_loop_copy_data: + mov.l @r0+, r3 /* Load a word to r3 from [sidata], with post-increment of 4 */ + mov.l r3, @r1 /* Store the word in r3 to [sdata] */ + add #4, r1 /* Increment sdata pointer */ + cmp/gt r1, r2 /* r2 greater or equal than r1? */ + bt _loop_copy_data + +_zero_bss: + mov.l _edata_k, r0 + mov.l _end_k, r1 + mov #0, r2 + +_loop_zero_bss: + mov.l r2, @r0 + add #4, r0 + cmp/gt r0, r1 + bt _loop_zero_bss + +_setup_fpu: + mov.l _set_fpscr_k, r1 + jsr @r1 + mov #0, r4 + lds r3, fpscr + +_setup_irq: + mov.l _exc_base_k, r0 + ldc r0, vbr + + stc sr, r0 /* Store SR into R0 */ + mov.l _exc_imask_k, r1 + and r1, r0 + ldc r0, sr + + .align 2 +_main_entry: + mov.l _main_k, r0 + jsr @r0 + or r0, r0 + + mov r0, r4 + mov.l _exit_k, r0 + jsr @r0 + or r0, r0 + + .balign 4 +/* libc FPU routine */ +_set_fpscr_k: + .long ___set_fpscr + +/* C library consts */ +_stack_k: + .long _stack +_sidata_k: + .long _sidata +_sdata_k: + .long _sdata +_edata_k: + .long _edata +_end_k: + .long _end + +/* Function pointers */ +_main_k: + .long _main /* Same address as main */ +_exit_k: + .long _exit +_exc_base_k: + .long _exc_base +_exc_imask_k: + .long 0xEFFFFF0F /* Clear IMASK (SR[7:4]) to 0 and BL bit, enable all exception levels */ + +/* + * Exception handlers + * These handlers are placed at VBR related addresses + */ + + .section .text.exc, "ax" + .align 4 +_exc_base: + .org 0x100, 0x00 +_exc_grnl_vector: + mov.l _exc_grnl_entry_k, r0 + jmp @r0 + nop + + .align 4 +_exc_grnl_entry_k: + .long _general_exc_handler + +_int_base: + .org 0x600, 0x00 +_int_grnl_vector: + mov.l _int_grnl_entry_k, r0 + jmp @r0 + nop + + .align 4 +_int_grnl_entry_k: + .long _general_int_handler \ No newline at end of file diff --git a/stx7105.ld b/stx7105.ld new file mode 100644 index 0000000..e9617f8 --- /dev/null +++ b/stx7105.ld @@ -0,0 +1,63 @@ + +HEAP_SIZE = 0x10000; +STACK_SIZE = 0x10000; + +ENTRY(_start) + +/* We don't use 29-bit mode since PMB and LMI initialization has to be done anyway. */ + +MEMORY { + EMI (rx) : ORIGIN = 0x80000000, LENGTH = 0x01000000 /* LMI virtual address: 0x8000_0000 */ + LMI (rwx) : ORIGIN = 0x81000000, LENGTH = 0x0F000000 /* LMI virtual address: 0x8100_0000 */ +} + +SECTIONS { + .text : { + . = ALIGN(4); + KEEP(*(.text.vtors)) + *(.text.init) + *(.text.exc) + *(.text) + *(.text*) + *(.rodata) + *(.rodata*) + . = ALIGN(4); + } >EMI + + _sidata = LOADADDR(.data); + + .data : { + . = ALIGN(4); + _sdata = .; + *(.data) + *(.data*) + . = ALIGN(4); + _edata = .; + } >LMI AT >EMI + + _eidata = (_sidata + _edata - _sdata); + + .bss : { + . = ALIGN(4); + __bss_start = .; + *(.bss) + *(.bss*) + *(COMMON) + . = ALIGN(8); + _end = .; + __end = _end; + } >LMI + + .heap : { + . = ALIGN(8); + . += HEAP_SIZE; + } + + .stack : { + . = ALIGN(8); + . += STACK_SIZE; + } + + _stack = ORIGIN(LMI) + LENGTH(LMI); + PROVIDE(__stack = _stack); +} \ No newline at end of file diff --git a/tools/flash_image.sh b/tools/flash_image.sh new file mode 100755 index 0000000..08b1af4 --- /dev/null +++ b/tools/flash_image.sh @@ -0,0 +1,14 @@ +#!/bin/sh + +IMAGE_NAME=$1 + +if [ -z "${IMAGE_NAME}" ] ; then + IMAGE_NAME=image.bin +fi + +if [ ! -f "${IMAGE_NAME}" ] ; then + echo "binary not exist." + exit -1 +fi + +flashrom --programmer ch341a_spi -w "${IMAGE_NAME}" \ No newline at end of file diff --git a/tools/pad_image.sh b/tools/pad_image.sh new file mode 100755 index 0000000..b5f0984 --- /dev/null +++ b/tools/pad_image.sh @@ -0,0 +1,33 @@ +#!/bin/sh + +FLASH_SIZE=1048576 + +INPUT_IMAGE="$1" +BINARY_NAME="$2" + +# ELF name not a valid name. +if [ ! -f "${INPUT_IMAGE}" ] ; then + echo "No such file." + exit -1 +fi + +# Output name not set.. +if [ -z "${BINARY_NAME}" ] ; then + echo "Binary name not set, using default" + BINARY_NAME="image.bin" +fi + +# Create binary file from ELF +sh-unknown-elf-objcopy -O binary ${INPUT_IMAGE} ${BINARY_NAME} +if [ "$?" -lt "0" ] ; then + exit -2 +fi + +# Calculate size and padding length +BINARY_SIZE=`stat --format "%s" ${BINARY_NAME}` +PAD_SIZE=$((${FLASH_SIZE} - ${BINARY_SIZE})) + +echo "Output binary size: ${BINARY_SIZE}, additional padding: ${PAD_SIZE}." + +# Pad output file using `dd` +tr '\0' '\377' < /dev/zero | dd bs=1 count=${PAD_SIZE} of=${BINARY_NAME} conv=notrunc seek=${BINARY_SIZE} \ No newline at end of file