started memory allocator, allocated final stack, added move_init_stack
authorJohn Tsiombikas <nuclear@member.fsf.org>
Mon, 1 Feb 2021 23:15:47 +0000 (01:15 +0200)
committerJohn Tsiombikas <nuclear@member.fsf.org>
Mon, 1 Feb 2021 23:15:47 +0000 (01:15 +0200)
function

Makefile.amiga
amiga.ld
fs-uae.conf
src/amiga/amigalib.c
src/amiga/hwregs.inc [new file with mode: 0644]
src/amiga/intr.s
src/amiga/mem.c
src/amiga/startup.s
src/debug.h

index 3d9b352..3d7a910 100644 (file)
@@ -22,7 +22,7 @@ OBJCOPY = $(tool_prefix)objcopy
 
 inc = -Isrc -Isrc/amiga -Isrc/amiga/libc
 
-ASFLAGS = -m68000
+ASFLAGS = -m68000 $(inc)
 CFLAGS = -m68000 -ffreestanding -nostdinc -fno-builtin -pedantic -Wall -Os $(inc)
 LDFLAGS = -m68000 -T amiga.ld -Wl,-print-gc-sections -Wl,-Map,link.map -ffreestanding \
                  -nostdlib -lgcc
index 4e77fb1..7e9c58f 100644 (file)
--- a/amiga.ld
+++ b/amiga.ld
@@ -1,7 +1,5 @@
 OUTPUT_ARCH(m68k)
 
-PROVIDE (_stacktop = 0x80000);
-
 SECTIONS {
        /* bootblock will load us at 64k */
        . = 0x10000;
index 06f3627..b8dee97 100644 (file)
@@ -15,7 +15,7 @@ console_debugger = 1
 warp_mode = 1
 chip_memory = 512
 fast_memory = 0
-slow_memory = 0
+slow_memory = 512
 initial_grab_input = 0
 serial_port = /tmp/uaetty
 
index 0ef32c7..eed7149 100644 (file)
@@ -4,9 +4,7 @@
 int alib_init(void)
 {
        execbase = *(void**)4;
-
        printf("execbase: %lx\n", (unsigned int)execbase);
-       printf("memlist: %lx\n", (unsigned int)&execbase->memlist);
 
        return 0;
 }
diff --git a/src/amiga/hwregs.inc b/src/amiga/hwregs.inc
new file mode 100644 (file)
index 0000000..781def4
--- /dev/null
@@ -0,0 +1,6 @@
+| vi:filetype=gas68k:
+
+       .equ DMACON,    0x002
+       .equ VPOSR,     0x004
+       .equ VHPOSR,    0x006
+       .equ COLOR0,    0x180
index 946b2d8..61259f9 100644 (file)
@@ -1,10 +1,7 @@
 | vi:filetype=gas68k:
-       .section .text
+       .include "hwregs.inc"
 
-       .equ DMACON, 0x002
-       .equ VPOSR, 0x004
-       .equ VHPOSR, 0x006
-       .equ COLOR0, 0x180
+       .section .text
 
        .global exc_init
 exc_init:
index d118d5a..6610841 100644 (file)
 #include "amigalib.h"
 #include "debug.h"
 
+#define MAGIC  0xa55a
+#define STACK_SIZE     4096
+
+enum {
+       MEM_FAST,
+       MEM_SLOW,
+       MEM_CHIP,
+       MEM_USED        = 0x8000
+};
+
+struct memrange {
+       uint16_t magic;
+       uint16_t attr;
+       uint32_t size;
+       struct memrange *next;
+       unsigned char start[];
+};
+
+#define NUM_POOLS      3
+static struct memrange *pool[NUM_POOLS];
+static uint32_t stack_base, stack_top;
+
+extern int _mem_start;
+
+void move_init_stack(uint32_t newtop); /* in startup.s */
+
 int init_mem(void)
 {
+       int i;
+       struct memrange *mr;
        struct alib_memnode *mem;
+       uint32_t mem_start = (uint32_t)&_mem_start;
 
-       printf("chip memory top: %lx\n", (unsigned long)execbase->chipmem_top);
-       printf("ext memory top: %lx\n", (unsigned long)execbase->extmem_top);
+       printf("mem_start: %lu\n", mem_start);
 
        printf("Memory ranges:\n");
        mem = execbase->memlist.head;
        while(mem->n_next) {
+               unsigned long start, end, size;
                char *stype;
+               int type;
+
+               /* assume we're dealing with at least 64k blocks */
+               start = (unsigned long)mem->start & 0xff0000;
+               end = ((unsigned long)mem->end + 0xffff) & 0xff0000;
+               size = end - start;
+
                if(mem->attrib & ALIB_MEMF_CHIP) {
                        stype = "chip";
+                       type = MEM_CHIP;
                } else if(mem->attrib & ALIB_MEMF_FAST) {
-                       stype = "fast";
+                       if(start >= 0xc00000 && end <= 0xd80000) {
+                               stype = "slow";
+                               type = MEM_SLOW;
+                       } else {
+                               stype = "fast";
+                               type = MEM_FAST;
+                       }
                } else {
-                       stype = "unknown";
+                       printf("ignoring memory range %06lx - %06lx of unknown type: %u\n",
+                                       start, end, mem->attrib);
+                       mem = mem->n_next;
+                       continue;
                }
-               printf(" %06lx - %06lx: %s\n", (unsigned long)mem->start,
-                               (unsigned long)mem->end, stype);
+
+               printf(" %06lx - %06lx: %s (%ldk)\n", start, end, stype, size >> 10);
                mem = mem->n_next;
+
+               if(mem_start >= start && mem_start < end) {
+                       size -= mem_start - start;
+                       start = mem_start;
+               }
+
+               mr = (struct memrange*)start;
+               mr->magic = MAGIC;
+               mr->attr = type;
+               mr->size = size - sizeof *mr;
+               mr->next = pool[type];
+               pool[type] = mr;
        }
 
+       /* allocate stack space at the top of a memory range, order of preference:
+        * fast, slow, chip
+        */
+       for(i=0; i<NUM_POOLS; i++) {
+               mr = pool[i];
+               if(mr && mr->size >= STACK_SIZE) {
+                       stack_top = (uint32_t)mr->start + mr->size;
+                       stack_base = stack_top - STACK_SIZE;
+                       mr->size -= STACK_SIZE;
+                       break;
+               }
+       }
+
+       if(!stack_base) {
+               panic("Failed to allocate stack, no suitable memory ranges found!\n");
+       }
+
+       printf("Allocated %dk stack space: %06lx - %06lx\n", STACK_SIZE >> 10, stack_base, stack_top);
+       move_init_stack(stack_top);
+
        return 0;
 }
index e008e47..bd61774 100644 (file)
@@ -1,5 +1,9 @@
 | vi:filetype=gas68k:
+       .include "hwregs.inc"
+
+       .global move_init_stack
        .global halt_cpu
+       .global panic
        .extern main
 
        .section .startup,"a"
@@ -8,7 +12,7 @@
        move.l #super, 0x80
        trap #0
 super:
-       ori.w #0x0300, %sr      | disable interrupts
+       or.w #0x0700, %sr       | disable interrupts
 
        | zero the .bss section
        move.l #_bss_start, %a0
@@ -19,9 +23,9 @@ super:
        cmp.l %a0, %a1
        bne.s 0b
 1:
-       | setup the stack at the top of (traditional) chipmem for now
-       move.l #0x80000, %sp
-       andi.w #0xf8ff, %sr     | enable interrupts
+       | setup a temporary stack
+       move.l #0x40000, %sp
+       and.w #0xf8ff, %sr      | enable interrupts
 
        | initialize early exception handlers
        jsr exc_init
@@ -29,5 +33,30 @@ super:
        jsr main
 0:     bra.b 0b
 
+move_init_stack:
+       move.l #0x40000, %a1    | a1 <- old stack
+       move.l 4(%sp), %a0      | a0 <- new stack
+0:     move.l -(%a1), %d0
+       move.l %d0, -(%a0)
+       cmp.l %sp, %a1
+       bhi.s 0b
+       move.l %a0, %sp
+       rts
+
 halt_cpu:
        stop #0x2700
+
+panic:
+       or.w #0x0700, %sr
+       move.l #0xdff000, %a0
+       move.w #0x7fff, DMACON(%a0)     | clear all DMACON bits
+       move.w #0xf00, COLOR0(%a0)
+
+       pea str_panic
+       jsr printf
+       add.l #8, %sp   | also get rid of the reutrn address
+
+       jsr printf
+       bra halt_cpu
+
+str_panic: .asciz "Kernel panic!\n~~~~~~~~~~~~~\n"
index 51386cd..6911b68 100644 (file)
@@ -3,4 +3,6 @@
 
 void memdump(void *ptr, int len);
 
+void panic(const char *fmt, ...);      /* defined in amiga/startup.s */
+
 #endif /* DEBUG_H_ */