+# Copyright 2019 - Robin Krens
+# Cross compilers links
CC=arm-none-eabi-gcc
LD=arm-none-eabi-ld
AR=$(TOOLROOT)/arm-none-eabi-ar
AS=arm-none-eabi-as
MKIMG=arm-none-eabi-objcopy
-LDFLAGS+= -mthumb -mcpu=cortex-m0
+# Compiler flags
+# TODO:Cortex-m3 or Cortex-m0?
+LDFLAGS+= -mthumb -mcpu=cortex-m3
CFLAGS+= -mcpu=cortex-m3 -mthumb -g
+# Start up machine assembly
as:
$(AS) $(CFLAGS) -o start.o start.asm
+# Compile and link all
all:
$(AS) $(CFLAGS) -o start.o start.asm
$(CC) $(CFLAGS) -c -I./include -ffreestanding -o main.o main.c
$(LD) -nostartfiles -T link.ld -o start.out start.o main.o uart.o ivt.o systick.o sysinfo.o lib.o mm.o regf.o
$(MKIMG) -Obinary -R .data start.out kernel.bin
+# Run in Qemu; note this is a patched version for stm32-f103c8
run:
/usr/local/bin/qemu-system-arm -serial stdio -M stm32-f103c8 -kernel kernel.bin
-examine:
- arm-none-eabi-objdump -S start.out
+# Examine all sections
+examine-all:
+ arm-none-eabi-objdump -D start.out | less
+
+# Examine just headers
+examine-header:
+ arm-none-eabi-objdump -x start.out | less
+
+# Flash kernel to board
+flash:
+ stm32flash -w kernel.bin -v /dev/ttyUSB0
+
%.o: %.c
$(CC) -c $(CFLAGS) $< -o $@
/* Dummy interrupt */
-__attribute__ ((interrupt))
-void * dummy_isr(struct interrupt_frame * frame) {
+// __attribute__ ((interrupt))
+void * dummy_isr(/* struct interrupt_frame * frame */) {
uint8_t nr = *SCB_VTOR_ST & 0xFF;
char hexbuf[8];
+/* Still kind of a debug function */
void addrtohex(uint32_t addr) {
char tmpbuf[6] = {'A', 'B', 'C', 'D', 'E', 'F'};
memset(&hexbuf, 0, sizeof(uint32_t) * 8);
}
}
- uart_puts("ADDRESS: 0x");
+ //uart_puts("ADDRESS: 0x");
for (int i = 7; i >= 0; i--) {
uart_putc(hexbuf[i]);
}
//uart_puts(hexbuf);
- uart_putc('\n');
+ //uart_putc('\n');
}
ivt_init();
// clock_init();
uart_init();
- uart_puts("LOADING SYSTEM 0.1 ...\n");
+ //uart_puts("LOADING SYSTEM 0.1 ...\n");
systick_init();
- sysinfo();
mm_init();
+ sysinfo();
//int * p2 = mm_alloc(512);
//memset(p2, 'a', 512);
//addrtohex(p2);
//addrtohex(*p2);
-
- //uint32_t * p = (volatile unsigned) 0x21000000;
+
+ /* extern stub();
+ stub();
+ __asm__ __volatile__ ("udiv r1, r3 ,%0" :: "r"(0)); */
+
//regw_u32(p, 0x0CCCCCCCC, 4, 0x01);
//regw_u8(p, 0xFF, 0, 0x02);
* SIMPLE BITMAP IMPLEMENTATION
* */
+
#define CHUNKS 128
#define FREE 0x00
#define ALLOC 0x01
- .equ STACK_TOP, 0x20008000 /* placed at 32kB, TODO: could place at top of SRAM? */
+ .equ STACK_TOP, 0x20010000 /* placed at 32kB, TODO: could place at top of SRAM? */
.text
.global _start
.global reset, nmi, hardfault
b hardfault
.global stub
stub:
- mov r1, #'z'
- ldr r0, [r1]
- bx lr
- /* ldr R0,=10
+ ldr R0,=10
mov R1,#0
- udiv.w R2, R0, R1 */
+ udiv.w R2, R0, R1
.data
.word 'x'
#include <stm32.h>
#include <mmap.h>
+#define MEM_SIZE 0x00010000
+#define MEM_OFFSET 0x20000000
+
+uint32_t get_msp(void);
void sysinfo() {
uint32_t tmp = *MCU_ID;
-
- uart_puts("CHECKING SYS INFO\n");
+ uart_puts("# ROBSYS 0.1 LOADING...\n");
uart_puts("# DEVICE ID: ");
- if (tmp & 0x414) {
+ if (tmp & 0x414)
uart_puts("HIGH DENSITY\n");
- }
else {
uart_puts("UNKNOWN\n");
}
tmp = (tmp >> 16);
uart_puts("# REVISION: ");
-// addrtohex(tmp);
switch (tmp) {
case 0x1000:
uart_puts("REVISION A\n");
uart_puts("UNKNOWN\n");
}
+ extern char _endofbss;
+
+ uint32_t current_stack = get_msp();
+ uint32_t stack_usage = (MEM_OFFSET + MEM_SIZE) - current_stack;
+ uint32_t data_bss = &_endofbss - MEM_OFFSET;
+ uint32_t mem_free = MEM_SIZE - stack_usage - data_bss;
+
+ uart_puts("# TOTAL MEMORY: ");
+ addrtohex(MEM_SIZE);
+ uart_putc('\n');
+ uart_puts("# FREE MEMORY: ");
+ addrtohex(mem_free);
+ uart_putc('\n');
+ uart_puts("# STACK USAGE: ");
+ addrtohex(stack_usage);
+ uart_putc('\n');
+
}
+/* Get the master stack pointer's position
+ * Here we use a so-called naked function,
+ * that doesn't automatically push and pop */
+
+uint32_t get_msp(void) __attribute__( ( naked ) );
+uint32_t get_msp(void)
+{
+ uint32_t msp = 0;
+ __asm__ volatile ("mrs %0, msp\n\t"
+ "mov r0, %0 \n\t"
+ "bx lr \n\t" : "=r" (msp) );
+ return(msp);
+}
uint32_t psr; // N-4
};
-__attribute__ ((interrupt))
-void * systick_handler(struct interrupt_frame * frame) {
+//__attribute__ ((interrupt))
+void * systick_handler(/* struct interrupt_frame * frame */) {
- uint32_t volatile status;
+// uint32_t volatile status;
uart_puts("TICKING\n");
+// for(;;);
}