Initial commit.
This commit is contained in:
commit
2fbd318615
|
@ -0,0 +1,3 @@
|
|||
[submodule "lib/printf"]
|
||||
path = lib/printf
|
||||
url = https://github.com/mpaland/printf.git
|
|
@ -0,0 +1,84 @@
|
|||
cmake_minimum_required(VERSION 3.10)
|
||||
|
||||
project(Flute_Hello)
|
||||
|
||||
enable_language(CXX)
|
||||
enable_language(ASM)
|
||||
|
||||
# Device specific settings, goes to CFLAGS and LDFLAGS
|
||||
set(CFLAGS_HARDWARE "-mabi=lp64 -march=rv64imac")
|
||||
|
||||
# Extra CFlags
|
||||
set(CFLAGS_EXTRA "-Og")
|
||||
set(LDFLAGS_EXTRA "-Wl,--print-memory-usage")
|
||||
|
||||
# Different linker scripts
|
||||
set(LDSCRIPT_BRAM "${CMAKE_SOURCE_DIR}/startup/flute_bram.ld")
|
||||
|
||||
# Copy them from Makefile
|
||||
set(C_SOURCES
|
||||
"src/main.c"
|
||||
"src/flute_system.c"
|
||||
"src/flute_it.c"
|
||||
"src/soc_peripherals.c"
|
||||
"src/syscalls.c"
|
||||
"src/system_init.c"
|
||||
"src/drivers/xilinx_gpio.c"
|
||||
"src/drivers/xilinx_timer.c"
|
||||
"src/drivers/xilinx_uartlite.c"
|
||||
"lib/printf/printf.c"
|
||||
)
|
||||
|
||||
# Copy them from Makefile
|
||||
set(ASM_SOURCES
|
||||
"startup/startup.S"
|
||||
)
|
||||
|
||||
# Copy them from Makefile
|
||||
add_definitions(
|
||||
)
|
||||
|
||||
# Copy them from Makefile
|
||||
include_directories(
|
||||
"include"
|
||||
"lib/printf"
|
||||
)
|
||||
|
||||
# Final compiler flags
|
||||
set(CMAKE_C_FLAGS "${CFLAGS_HARDWARE} ${CFLAGS_EXTRA} -Wall -fdata-sections -ffunction-sections")
|
||||
set(CMAKE_CXX_FLAGS "${CFLAGS_HARDWARE} ${CFLAGS_EXTRA} -Wall -fdata-sections -ffunction-sections")
|
||||
set(CMAKE_ASM_FLAGS "${CMAKE_C_FLAGS} -x assembler-with-cpp")
|
||||
set(CMAKE_EXE_LINKER_FLAGS "${CFLAGS_HARDWARE} -Wl,--gc-sections -specs=nano.specs -nostartfiles -lc -lm -lnosys ${LDFLAGS_EXTRA}")
|
||||
|
||||
# Main targets are added here
|
||||
|
||||
# **** Internal BRAM ****
|
||||
|
||||
# Create ELF
|
||||
add_executable("${CMAKE_PROJECT_NAME}_BRAM.elf" ${C_SOURCES} ${ASM_SOURCES})
|
||||
|
||||
target_link_options("${CMAKE_PROJECT_NAME}_BRAM.elf"
|
||||
PRIVATE "-T${LDSCRIPT_BRAM}"
|
||||
PRIVATE "-Wl,-Map=${CMAKE_CURRENT_BINARY_DIR}/${CMAKE_PROJECT_NAME}_BRAM.map,--cref"
|
||||
)
|
||||
|
||||
target_compile_options("${CMAKE_PROJECT_NAME}_BRAM.elf"
|
||||
PRIVATE "${FINAL_C_FLAGS}"
|
||||
)
|
||||
|
||||
add_custom_command(OUTPUT "${CMAKE_PROJECT_NAME}_BRAM.hex"
|
||||
COMMAND ${CMAKE_OBJCOPY} "-O" "ihex" "${CMAKE_PROJECT_NAME}_BRAM.elf" "${CMAKE_PROJECT_NAME}_BRAM.hex"
|
||||
DEPENDS "${CMAKE_PROJECT_NAME}_BRAM.elf"
|
||||
)
|
||||
add_custom_target("${CMAKE_PROJECT_NAME}_BRAM_HEX"
|
||||
DEPENDS "${CMAKE_PROJECT_NAME}_BRAM.hex"
|
||||
)
|
||||
|
||||
add_custom_command(OUTPUT "${CMAKE_PROJECT_NAME}_BRAM.bin"
|
||||
COMMAND ${CMAKE_OBJCOPY} "-O" "binary" "${CMAKE_PROJECT_NAME}_BRAM.elf" "${CMAKE_PROJECT_NAME}_BRAM.bin"
|
||||
DEPENDS "${CMAKE_PROJECT_NAME}_BRAM.elf"
|
||||
)
|
||||
|
||||
add_custom_target("${CMAKE_PROJECT_NAME}_BRAM_BIN"
|
||||
DEPENDS "${CMAKE_PROJECT_NAME}_BRAM.bin"
|
||||
)
|
|
@ -0,0 +1,13 @@
|
|||
#ifndef __IBEX_SYSTEM_H
|
||||
#define __IBEX_SYSTEM_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#define __csrr(csr, val) asm volatile("csrr %0, " csr "\n" : "=r"(val))
|
||||
#define __csrw(csr, val) asm volatile("csrw " csr ", %0\n" : : "r"(val))
|
||||
#define __csrs(csr, val) asm volatile("csrs " csr ", %0\n" : : "r"(val))
|
||||
#define __csrc(csr, val) asm volatile("csrc " csr ", %0\n" : : "r"(val))
|
||||
|
||||
void System_Delay(uint64_t ticks);
|
||||
|
||||
#endif
|
|
@ -0,0 +1,10 @@
|
|||
#ifndef __MAIN_H
|
||||
#define __MAIN_H
|
||||
|
||||
#include "flute_system.h"
|
||||
#include "soc_peripherals.h"
|
||||
|
||||
extern xilinx_uartlite_handle_t soc_uart;
|
||||
extern xilinx_gpio_handle_t soc_gpio;
|
||||
|
||||
#endif
|
|
@ -0,0 +1,39 @@
|
|||
#ifndef __SOC_PERIPHERALS_H
|
||||
#define __SOC_PERIPHERALS_H
|
||||
|
||||
#include "xilinx_uartlite.h"
|
||||
#include "xilinx_gpio.h"
|
||||
#include "xilinx_timer.h"
|
||||
|
||||
#include "flute_system.h"
|
||||
|
||||
// Peripheral defines
|
||||
#define UART0_BASE 0x40000000
|
||||
#define GPIO0_BASE 0x40010000
|
||||
#define TIMER0_BASE 0x40020000
|
||||
|
||||
#define CLINT_BASE 0x02000000
|
||||
|
||||
// SoC config
|
||||
#define SYS_CLK_FREQ 32000000
|
||||
#define SYS_TICK_RATE 1000
|
||||
|
||||
#define SYS_TICK_STEP (SYS_CLK_FREQ / SYS_TICK_RATE)
|
||||
|
||||
// Peripherals
|
||||
extern __IO xilinx_uartlite_t *UART0;
|
||||
extern __IO xilinx_gpio_t *GPIO0;
|
||||
extern __IO xilinx_timer_t *TIMER0;
|
||||
|
||||
// SysTick
|
||||
extern volatile uint64_t SysTick;
|
||||
|
||||
static inline uint32_t GetTick() {
|
||||
return SysTick;
|
||||
}
|
||||
|
||||
static inline uint32_t GetCoreClock() {
|
||||
return SYS_CLK_FREQ;
|
||||
}
|
||||
|
||||
#endif
|
|
@ -0,0 +1,13 @@
|
|||
#ifndef __XILINX_IP_DEFS_H
|
||||
#define __XILINX_IP_DEFS_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#define __IO volatile
|
||||
|
||||
#define RET_OK 0
|
||||
#define RET_ERR 1
|
||||
|
||||
typedef int sys_ret_t;
|
||||
|
||||
#endif
|
|
@ -0,0 +1,23 @@
|
|||
#ifndef __XILINX_GPIO_H
|
||||
#define __XILINX_GPIO_H
|
||||
|
||||
#include "system_defs.h"
|
||||
|
||||
typedef struct {
|
||||
__IO uint32_t DATA;
|
||||
__IO uint32_t TRI;
|
||||
__IO uint32_t DATA2;
|
||||
__IO uint32_t TRI2;
|
||||
} xilinx_gpio_t;
|
||||
|
||||
typedef struct {
|
||||
__IO xilinx_gpio_t *instance;
|
||||
} xilinx_gpio_handle_t;
|
||||
|
||||
sys_ret_t xilinx_gpio_init(xilinx_gpio_handle_t *handle);
|
||||
sys_ret_t xilinx_gpio_pinmode(xilinx_gpio_handle_t *handle, uint32_t pin, uint8_t output);
|
||||
sys_ret_t xilinx_gpio_write(xilinx_gpio_handle_t *handle, uint32_t pin, uint8_t value);
|
||||
uint8_t xilinx_gpio_read(xilinx_gpio_handle_t *handle, uint32_t pin);
|
||||
sys_ret_t xilinx_gpio_toggle(xilinx_gpio_handle_t *handle, uint32_t pin);
|
||||
|
||||
#endif
|
|
@ -0,0 +1,16 @@
|
|||
#ifndef __XILINX_TIMER_H
|
||||
#define __XILINX_TIMER_H
|
||||
|
||||
#include "system_defs.h"
|
||||
|
||||
typedef struct {
|
||||
__IO uint32_t TCSR0;
|
||||
__IO uint32_t TLR0;
|
||||
__IO uint32_t TCR0;
|
||||
__IO uint32_t RSVD;
|
||||
__IO uint32_t TCSR1;
|
||||
__IO uint32_t TLR1;
|
||||
__IO uint32_t TCR1;
|
||||
} xilinx_timer_t;
|
||||
|
||||
#endif
|
|
@ -0,0 +1,21 @@
|
|||
#ifndef __XILINX_UARTLITE_H
|
||||
#define __XILINX_UARTLITE_H
|
||||
|
||||
#include "system_defs.h"
|
||||
|
||||
typedef struct {
|
||||
__IO uint32_t RX_FIFO;
|
||||
__IO uint32_t TX_FIFO;
|
||||
__IO uint32_t STAT;
|
||||
__IO uint32_t CTRL;
|
||||
} xilinx_uartlite_t;
|
||||
|
||||
typedef struct {
|
||||
__IO xilinx_uartlite_t *instance;
|
||||
} xilinx_uartlite_handle_t;
|
||||
|
||||
sys_ret_t xilinx_uartlite_init(xilinx_uartlite_handle_t *handle);
|
||||
sys_ret_t xilinx_uartlite_send(xilinx_uartlite_handle_t *handle, uint8_t *data, uint32_t len);
|
||||
sys_ret_t xilinx_uartlite_receive(xilinx_uartlite_handle_t *handle, uint8_t *data, uint32_t len);
|
||||
|
||||
#endif
|
|
@ -0,0 +1 @@
|
|||
Subproject commit d3b984684bb8a8bdc48cc7a1abecb93ce59bbe3e
|
|
@ -0,0 +1,5 @@
|
|||
set(CMAKE_C_COMPILER $ENV{TOOLCHAIN_PATH}/riscv64-unknown-elf-gcc)
|
||||
set(CMAKE_CXX_COMPILER $ENV{TOOLCHAIN_PATH}/riscv64-unknown-elf-gcc)
|
||||
|
||||
# Make CMake happy about those compilers
|
||||
set(CMAKE_TRY_COMPILE_TARGET_TYPE "STATIC_LIBRARY")
|
|
@ -0,0 +1,35 @@
|
|||
#include "xilinx_gpio.h"
|
||||
|
||||
sys_ret_t xilinx_gpio_init(xilinx_gpio_handle_t *handle) {
|
||||
handle->instance->TRI = 0xFFFFFFFF;
|
||||
return RET_OK;
|
||||
}
|
||||
|
||||
sys_ret_t xilinx_gpio_pinmode(xilinx_gpio_handle_t *handle, uint32_t pin, uint8_t output) {
|
||||
if(output) {
|
||||
handle->instance->TRI &= ~(1U << pin);
|
||||
}
|
||||
else {
|
||||
handle->instance->TRI |= (1U << pin);
|
||||
}
|
||||
return RET_OK;
|
||||
}
|
||||
|
||||
sys_ret_t xilinx_gpio_write(xilinx_gpio_handle_t *handle, uint32_t pin, uint8_t value) {
|
||||
if(value) {
|
||||
handle->instance->DATA |= (1U << pin);
|
||||
}
|
||||
else {
|
||||
handle->instance->DATA &= ~(1U << pin);
|
||||
}
|
||||
return RET_OK;
|
||||
}
|
||||
|
||||
uint8_t xilinx_gpio_read(xilinx_gpio_handle_t *handle, uint32_t pin) {
|
||||
return (handle->instance->DATA & (1U << pin)) ? 1 : 0;
|
||||
}
|
||||
|
||||
sys_ret_t xilinx_gpio_toggle(xilinx_gpio_handle_t *handle, uint32_t pin) {
|
||||
handle->instance->DATA ^= (1U << pin);
|
||||
return RET_OK;
|
||||
}
|
|
@ -0,0 +1,2 @@
|
|||
#include "xilinx_timer.h"
|
||||
|
|
@ -0,0 +1,27 @@
|
|||
#include "xilinx_uartlite.h"
|
||||
|
||||
sys_ret_t xilinx_uartlite_init(xilinx_uartlite_handle_t *handle) {
|
||||
handle->instance->CTRL |= 0x03; // Reset FIFO
|
||||
|
||||
return RET_OK;
|
||||
}
|
||||
|
||||
sys_ret_t xilinx_uartlite_send(xilinx_uartlite_handle_t *handle, uint8_t *data, uint32_t len) {
|
||||
for(uint32_t i = 0; i < len; i++) {
|
||||
while(handle->instance->STAT & (1U << 0x03) || !(handle->instance->STAT & (1U << 0x02))) { // Check if TX FIFO is full
|
||||
// TODO: Unless we figure out where systick should be.
|
||||
}
|
||||
handle->instance->TX_FIFO = data[i];
|
||||
}
|
||||
return RET_OK;
|
||||
}
|
||||
|
||||
sys_ret_t xilinx_uartlite_receive(xilinx_uartlite_handle_t *handle, uint8_t *data, uint32_t len) {
|
||||
for(uint32_t i = 0; i < len; i++) {
|
||||
while((handle->instance->STAT & 0x01U) == 0) { // Check if RX FIFO is empty
|
||||
// TODO: Unless we figure out where our systick should be.
|
||||
}
|
||||
data[i] = handle->instance->RX_FIFO & 0xFF;
|
||||
}
|
||||
return RET_OK;
|
||||
}
|
|
@ -0,0 +1,22 @@
|
|||
#include "flute_system.h"
|
||||
#include "soc_peripherals.h"
|
||||
|
||||
void Timer_IRQHandler(void) {
|
||||
SysTick++;
|
||||
*(uint64_t *)(CLINT_BASE + 0x4000) = SYS_TICK_STEP;
|
||||
*(uint64_t *)(CLINT_BASE + 0xBFF8) = 0ULL;
|
||||
}
|
||||
|
||||
__attribute__((interrupt)) void Exception_Handler(void) {
|
||||
uint64_t mcause = 0;
|
||||
|
||||
__csrr("mcause", mcause);
|
||||
|
||||
switch(mcause) {
|
||||
case 0x8000000000000007: // MTIME
|
||||
Timer_IRQHandler();
|
||||
break;
|
||||
default:
|
||||
for(;;) {}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,23 @@
|
|||
#include "soc_peripherals.h"
|
||||
|
||||
void __enable_irqs(void){
|
||||
//
|
||||
}
|
||||
void __enable_mcount(void) {
|
||||
//
|
||||
}
|
||||
|
||||
void __read_mcycle(void) {
|
||||
//
|
||||
}
|
||||
|
||||
void __enable_irqn(int IRQn) {
|
||||
//
|
||||
}
|
||||
|
||||
void System_Delay(uint64_t ticks) {
|
||||
uint64_t tick_start = SysTick;
|
||||
while(SysTick < tick_start + ticks) {
|
||||
//
|
||||
}
|
||||
}
|
|
@ -0,0 +1,52 @@
|
|||
#include <stdint.h>
|
||||
|
||||
#include "printf.h"
|
||||
|
||||
#include "main.h"
|
||||
|
||||
xilinx_uartlite_handle_t soc_uart;
|
||||
xilinx_gpio_handle_t soc_gpio;
|
||||
|
||||
void _print_arch_string(uint64_t misa);
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
|
||||
printf("Running on a Bluespec flute core.\r\n");
|
||||
|
||||
uint64_t csr = 0;
|
||||
__csrr("misa", csr);
|
||||
|
||||
printf("MISA: 0x%016llx, this is a ", csr);
|
||||
_print_arch_string(csr);
|
||||
printf(" processor.\r\n");
|
||||
|
||||
printf("System clock frequency: %luHz\r\n", SYS_CLK_FREQ);
|
||||
|
||||
for(;;) {
|
||||
System_Delay(10000);
|
||||
__csrr("mcycle", csr);
|
||||
printf("mcycle: 0x%016llx\r\n", csr);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void _print_arch_string(uint64_t misa) {
|
||||
switch(misa >> 62) {
|
||||
case 1:
|
||||
printf("RV32");
|
||||
break;
|
||||
case 2:
|
||||
printf("RV64");
|
||||
break;
|
||||
case 3:
|
||||
printf("RV128");
|
||||
break;
|
||||
}
|
||||
|
||||
for(uint8_t i = 0; i < 26; i++) {
|
||||
if(misa >> i & 0x01ULL) {
|
||||
printf("%c", 'A' + i);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,5 @@
|
|||
#include "soc_peripherals.h"
|
||||
|
||||
__IO xilinx_uartlite_t *UART0 = (xilinx_uartlite_t *) UART0_BASE;
|
||||
__IO xilinx_gpio_t *GPIO0 = (xilinx_gpio_t *) GPIO0_BASE;
|
||||
__IO xilinx_timer_t *TIMER0 = (xilinx_timer_t *) TIMER0_BASE;
|
|
@ -0,0 +1,34 @@
|
|||
#include <stdint.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include "main.h"
|
||||
|
||||
extern int _heap_start;
|
||||
extern int _heap_end;
|
||||
static void *_old_heap = &_heap_start;
|
||||
|
||||
int _write(int handle, char *data, int size) {
|
||||
handle = handle;
|
||||
xilinx_uartlite_send(&soc_uart, (uint8_t *)data, size);
|
||||
return size;
|
||||
}
|
||||
|
||||
void *_sbrk(int nbytes) {
|
||||
char *_old = _old_heap;
|
||||
if(&_heap_start == &_heap_end) {
|
||||
errno = -ENOMEM;
|
||||
return (void *)-1;
|
||||
}
|
||||
if((_old + nbytes) < (char *)&_heap_end) {
|
||||
_old += nbytes;
|
||||
} else {
|
||||
errno = -ENOMEM;
|
||||
return (void *)-1;
|
||||
}
|
||||
|
||||
return _old_heap;
|
||||
}
|
||||
|
||||
void _putchar(char character) {
|
||||
xilinx_uartlite_send(&soc_uart, (uint8_t *)&character, 0x01);
|
||||
}
|
|
@ -0,0 +1,28 @@
|
|||
#include "main.h"
|
||||
|
||||
__IO uint64_t SysTick;
|
||||
|
||||
void System_Init(void) {
|
||||
soc_uart.instance = UART0;
|
||||
xilinx_uartlite_init(&soc_uart);
|
||||
|
||||
soc_gpio.instance = GPIO0;
|
||||
xilinx_gpio_init(&soc_gpio);
|
||||
|
||||
xilinx_gpio_pinmode(&soc_gpio, 0, 1);
|
||||
|
||||
// Setup interrupt system
|
||||
uint64_t csr = 0ULL;
|
||||
__csrw("mtvec", csr);
|
||||
|
||||
SysTick = 0ULL;
|
||||
|
||||
*(uint64_t *)(CLINT_BASE + 0x4000) = SYS_TICK_STEP;
|
||||
*(uint64_t *)(CLINT_BASE + 0xBFF8) = 0ULL;
|
||||
|
||||
csr = 1U << 7; // MTIE
|
||||
__csrw("mie", csr); // Enable timer interrupt
|
||||
|
||||
csr = 1U << 3; // MIE
|
||||
__csrw("mstatus", csr);
|
||||
}
|
|
@ -0,0 +1,91 @@
|
|||
_entry_point = 0x1000;
|
||||
|
||||
ENTRY(_entry_point)
|
||||
|
||||
_estack = 0x00020000;
|
||||
_minimum_stack_size = 0x1000;
|
||||
_minimum_heap_size = 0x1000;
|
||||
|
||||
MEMORY
|
||||
{
|
||||
RO_CODE (rx) : ORIGIN = 0x00000000, LENGTH = 64K
|
||||
RW_DATA (xrw) : ORIGIN = 0x00010000, LENGTH = 64K
|
||||
}
|
||||
|
||||
SECTIONS
|
||||
{
|
||||
.isr_vectors :
|
||||
{
|
||||
. = ALIGN(8);
|
||||
_vectors_start = .;
|
||||
KEEP(*(.isr_vectors))
|
||||
_vectors_end = .;
|
||||
. = ALIGN(8);
|
||||
} >RO_CODE
|
||||
|
||||
.text :
|
||||
{
|
||||
. = ALIGN(8);
|
||||
*(.text)
|
||||
*(.text*)
|
||||
KEEP (*(.init))
|
||||
KEEP (*(.fini))
|
||||
. = ALIGN(8);
|
||||
} >RO_CODE
|
||||
|
||||
.data :
|
||||
{
|
||||
. = ALIGN(8);
|
||||
_sdata = .;
|
||||
__global_pointer$ = . + 0x800;
|
||||
*(.data)
|
||||
*(.data*)
|
||||
*(.sdata)
|
||||
*(.sdata*)
|
||||
. = ALIGN(8);
|
||||
_edata = .;
|
||||
} >RW_DATA AT> RO_CODE
|
||||
|
||||
_sidata = LOADADDR(.data);
|
||||
|
||||
|
||||
.rodata :
|
||||
{
|
||||
. = ALIGN(8);
|
||||
*(.rodata)
|
||||
*(.rodata*)
|
||||
. = ALIGN(8);
|
||||
} >RO_CODE
|
||||
|
||||
.bss :
|
||||
{
|
||||
. = ALIGN(8);
|
||||
_sbss = .;
|
||||
_bss_start = _sbss;
|
||||
*(.bss)
|
||||
*(.bss*)
|
||||
*(.sbss)
|
||||
*(.sbss*)
|
||||
*(COMMON)
|
||||
. = ALIGN(8);
|
||||
_ebss = .;
|
||||
_bss_end = _ebss;
|
||||
} >RW_DATA
|
||||
|
||||
._heap_stack_space :
|
||||
{
|
||||
. = ALIGN(8);
|
||||
_heap_start = .;
|
||||
. = . + _minimum_heap_size;
|
||||
_heap_end = .;
|
||||
_end = .;
|
||||
. = ALIGN(8);
|
||||
. = . + _minimum_stack_size;
|
||||
. = ALIGN(8);
|
||||
} >RW_DATA
|
||||
|
||||
.riscv.attributes 0 :
|
||||
{
|
||||
*(.riscv.attributes)
|
||||
}
|
||||
}
|
|
@ -0,0 +1,90 @@
|
|||
.section .text
|
||||
|
||||
.global Reset_Handler
|
||||
|
||||
Reset_Handler:
|
||||
mv x1, x0
|
||||
mv x2, x1
|
||||
mv x3, x1
|
||||
mv x4, x1
|
||||
mv x5, x1
|
||||
mv x6, x1
|
||||
mv x7, x1
|
||||
mv x8, x1
|
||||
mv x9, x1
|
||||
mv x10, x1
|
||||
mv x11, x1
|
||||
mv x12, x1
|
||||
mv x13, x1
|
||||
mv x14, x1
|
||||
mv x15, x1
|
||||
mv x16, x1
|
||||
mv x17, x1
|
||||
mv x18, x1
|
||||
mv x19, x1
|
||||
mv x20, x1
|
||||
mv x21, x1
|
||||
mv x22, x1
|
||||
mv x23, x1
|
||||
mv x24, x1
|
||||
mv x25, x1
|
||||
mv x26, x1
|
||||
mv x27, x1
|
||||
mv x28, x1
|
||||
mv x29, x1
|
||||
mv x30, x1
|
||||
mv x31, x1
|
||||
|
||||
.option push
|
||||
.option norelax
|
||||
la gp, __global_pointer$
|
||||
.option pop
|
||||
|
||||
la sp, _estack
|
||||
|
||||
la x25, _sidata
|
||||
la x26, _sdata
|
||||
la x27, _edata
|
||||
|
||||
bge x26, x27, copy_data_end
|
||||
|
||||
copy_data:
|
||||
ld x24, 0(x25)
|
||||
sd x24, 0(x26)
|
||||
addi x25, x25, 8
|
||||
addi x26, x26, 8
|
||||
|
||||
blt x26, x27, copy_data
|
||||
|
||||
copy_data_end:
|
||||
|
||||
/* Zero .bss section */
|
||||
la x26, _sbss
|
||||
la x27, _ebss
|
||||
|
||||
bge x26, x27, zero_bss_end
|
||||
|
||||
zero_bss:
|
||||
sd x0, 0(x26)
|
||||
addi x26, x26, 8
|
||||
blt x26, x27, zero_bss
|
||||
|
||||
zero_bss_end:
|
||||
jal x1, System_Init
|
||||
|
||||
addi x10, x0, 0
|
||||
addi x11, x0, 0
|
||||
jal x1, main
|
||||
|
||||
inf_loop:
|
||||
jal x0, inf_loop
|
||||
|
||||
/* ISR vector table */
|
||||
.section .isr_vectors, "ax"
|
||||
.option norvc;
|
||||
|
||||
.org 0x00
|
||||
jal x0, Exception_Handler
|
||||
|
||||
.org 0x1000
|
||||
jal x0, Reset_Handler
|
Loading…
Reference in New Issue