mirror of
git://projects.qi-hardware.com/iris.git
synced 2025-04-21 12:27:27 +03:00
lcd working
This commit is contained in:
@@ -27,7 +27,7 @@ OBJCOPYFLAGS = $(addprefix --remove-section=.,$(junk))
|
||||
arch_kernel_sources = mips/interrupts.cc mips/test.cc mips/arch.cc
|
||||
boot_sources = mips/init.cc
|
||||
BUILT_SOURCES = $(kernel_sources) $(boot_sources)
|
||||
arch_headers = mips/arch.hh
|
||||
arch_headers = mips/arch.hh mips/jz4730.hh
|
||||
boot_threads = keyboard lcd
|
||||
|
||||
uimage:
|
||||
@@ -35,11 +35,11 @@ uimage:
|
||||
mips/entry.o: $(boot_threads)
|
||||
mips/init.o: TARGET_FLAGS = -I/usr/include
|
||||
$(boot_threads): TARGET_FLAGS = -I.
|
||||
$(boot_threads): mips/jz4730.hh boot-programs/devices.hh
|
||||
$(boot_threads): boot-programs/devices.hh
|
||||
|
||||
# Transform ':' into ';' so vim doesn't think there are errors.
|
||||
uimage: kernel.raw.gz Makefile mips/Makefile.arch
|
||||
mkimage -A MIPS -O Linux -C gzip -a $(load) -e 0x$(shell /bin/sh -c '$(OBJDUMP) -t kernel | grep __start$$ | cut -b-8') -n "Shevek's kernel" -d $< $@ | sed -e 's/:/;/g'
|
||||
mkimage -A MIPS -O Linux -C gzip -a $(load) -e 0xa$(shell /bin/sh -c '$(OBJDUMP) -t kernel | grep __start$$ | cut -b2-8') -n "Iris" -d $< $@ | sed -e 's/:/;/g'
|
||||
|
||||
%.o:%.S Makefile mips/Makefile.arch mips/arch.hh
|
||||
$(CC) $(CPPFLAGS) $(TARGET_FLAGS) -DKERNEL_STACK_SIZE=0x2000 -c $< -o $@
|
||||
@@ -49,7 +49,7 @@ kernel: mips/entry.o $(subst .cc,.o,$(kernel_sources)) mips/boot.o $(subst .cc,.
|
||||
$(LD) --omagic -Ttext $(load) $^ -o $@
|
||||
|
||||
%.raw: %
|
||||
$(OBJCOPY) -S $(addprefix --remove-section=.,$(junk)) -Obinary $< $@
|
||||
$(OBJCOPY) -S $(OBJCOPYFLAGS) -Obinary $< $@
|
||||
|
||||
%.gz: %
|
||||
gzip < $< > $@
|
||||
|
||||
@@ -318,3 +318,4 @@ void arch_register_interrupt (unsigned num, Receiver *r):
|
||||
intc_unmask_irq (num)
|
||||
else:
|
||||
intc_mask_irq (num)
|
||||
dbg_code = 0
|
||||
|
||||
@@ -25,13 +25,15 @@
|
||||
#define Status 12
|
||||
#define Config 16
|
||||
|
||||
// Note that this code starts at 0xa0000000, even though it is linked for
|
||||
// 0x80000000. This means that until the jump below, it must be PIC.
|
||||
__start:
|
||||
bal 1f
|
||||
nop
|
||||
.word _gp
|
||||
// For some reason the disassembler considers everything
|
||||
// after __start non-code until the next label. So I add a label.
|
||||
start_hack_for_disassembler:
|
||||
nop
|
||||
.word _gp
|
||||
1: lw $gp, 0($ra)
|
||||
|
||||
la $sp, kernel_stack + KERNEL_STACK_SIZE
|
||||
|
||||
@@ -110,10 +110,11 @@ static unsigned mkcap (Memory *mem, unsigned type, void *obj):
|
||||
static void init_threads ():
|
||||
Thread *previous = NULL
|
||||
first_scheduled = NULL
|
||||
first_sleeper = NULL
|
||||
first_alarm = NULL
|
||||
Receiver *init_receiver = NULL
|
||||
for unsigned i = 0; i < NUM_THREADS; ++i:
|
||||
Memory *mem = top_memory.alloc_memory ()
|
||||
assert (mem)
|
||||
Thread *thread = mem->alloc_thread ()
|
||||
Page **pages = (Page **)mem->zalloc ()
|
||||
Elf32_Ehdr *header = (Elf32_Ehdr *)thread_start[i]
|
||||
@@ -134,36 +135,42 @@ static void init_threads ():
|
||||
thread->sp = 0x80000000
|
||||
for unsigned section = 0; section < header->e_shnum; ++section:
|
||||
Elf32_Shdr *shdr = (Elf32_Shdr *)(thread_start[i] + header->e_shoff + section * header->e_shentsize)
|
||||
if !(shdr->sh_flags & SHF_ALLOC):
|
||||
if ~shdr->sh_flags & SHF_ALLOC:
|
||||
continue
|
||||
bool writable = shdr->sh_flags & SHF_WRITE
|
||||
//bool executable = shdr->sh_flags & SHF_EXEC_INSTR
|
||||
if shdr->sh_type != SHT_NOBITS:
|
||||
for unsigned p = (shdr->sh_addr & PAGE_MASK); p <= ((shdr->sh_addr + shdr->sh_size - 1) & PAGE_MASK); p += PAGE_SIZE:
|
||||
unsigned idx = (p - (shdr->sh_addr & PAGE_MASK)) >> PAGE_BITS
|
||||
unsigned file_offset = shdr->sh_offset >> PAGE_BITS
|
||||
for unsigned p = (shdr->sh_addr & PAGE_MASK); p < shdr->sh_addr + shdr->sh_size; p += PAGE_SIZE:
|
||||
unsigned section_offset = (p - (shdr->sh_addr & PAGE_MASK)) >> PAGE_BITS
|
||||
unsigned idx = file_offset + section_offset
|
||||
if !pages[idx]:
|
||||
pages[idx] = mem->alloc_page ()
|
||||
pages[idx]->data.frame = thread_start[i] + (idx << PAGE_BITS)
|
||||
pages[idx]->data.flags = (writable ? PAGE_FLAG_WRITABLE : 0) | PAGE_FLAG_PAYING | PAGE_FLAG_FRAME
|
||||
pages[idx]->data.flags = PAGE_FLAG_WRITABLE | PAGE_FLAG_PAYING | PAGE_FLAG_FRAME
|
||||
++top_memory.limit
|
||||
mem->use ()
|
||||
if !mem->map (pages[idx], p, writable):
|
||||
panic (0x22446688, "unable to map initial page")
|
||||
else:
|
||||
for unsigned p = (shdr->sh_addr & PAGE_MASK); p <= ((shdr->sh_addr + shdr->sh_size - 1) & PAGE_MASK); p += PAGE_SIZE:
|
||||
bool write = false
|
||||
Page *page = mem->get_mapping (p, &write)
|
||||
if !writable:
|
||||
panic (0x33399993, "unwritable bss section")
|
||||
for unsigned p = (shdr->sh_addr & PAGE_MASK); p < shdr->sh_addr + shdr->sh_size; p += PAGE_SIZE:
|
||||
Page *page = mem->get_mapping (p, &writable)
|
||||
if !page:
|
||||
page = mem->alloc_page ()
|
||||
if !page:
|
||||
panic (0x00220022, "out of memory")
|
||||
page->data.frame = mem->zalloc ()
|
||||
page->data.flags = (writable ? PAGE_FLAG_WRITABLE : 0) | PAGE_FLAG_PAYING | PAGE_FLAG_FRAME
|
||||
if !page->data.frame || !mem->map (page, p, true):
|
||||
if !page->data.frame:
|
||||
panic (0x02220022, "out of memory");
|
||||
page->data.flags = PAGE_FLAG_WRITABLE | PAGE_FLAG_PAYING | PAGE_FLAG_FRAME
|
||||
if !mem->map (page, p, true):
|
||||
panic (0x33557799, "unable to map initial bss page")
|
||||
else:
|
||||
if !write:
|
||||
if !writable:
|
||||
panic (0x20203030, "bss section starts on read-only page")
|
||||
for unsigned a = p; a < p + PAGE_SIZE; a += 4:
|
||||
for unsigned a = p; a < ((p + PAGE_SIZE) & PAGE_MASK); a += 4:
|
||||
if a >= shdr->sh_addr + shdr->sh_size:
|
||||
break
|
||||
if a < shdr->sh_addr:
|
||||
@@ -201,11 +208,10 @@ static void init_threads ():
|
||||
|
||||
// Initialize the kernel, finish by falling into the idle task.
|
||||
void init (unsigned mem):
|
||||
dbg_code = 0
|
||||
// Disable interrupts and set interrupt vectors to normal.
|
||||
cp0_set0 (CP0_STATUS)
|
||||
// Initialize kernel variables to empty.
|
||||
sleepers = NULL
|
||||
runners = NULL
|
||||
unsigned count = init_memory (mem)
|
||||
// initialize system control coprocessor.
|
||||
init_cp0 ()
|
||||
|
||||
@@ -20,7 +20,7 @@
|
||||
#include "../kernel.hh"
|
||||
|
||||
static void handle_exit (Thread *old_current):
|
||||
if !current:
|
||||
if !current || (current == &idle):
|
||||
schedule ()
|
||||
if !current:
|
||||
current = &idle
|
||||
@@ -77,7 +77,6 @@ Thread *tlb_refill ():
|
||||
Thread *interrupt ():
|
||||
//panic (0x88877722, "Interrupt")
|
||||
Thread *old_current = current
|
||||
//dbg_send (INTC_IPR)
|
||||
unsigned ipr = INTC_IPR
|
||||
for unsigned i = 0; i < 32; ++i:
|
||||
if ipr & (1 << i):
|
||||
@@ -94,6 +93,7 @@ Thread *interrupt ():
|
||||
c.data[j] = 0
|
||||
c.cap[j] = NULL
|
||||
c.copy[j] = false
|
||||
dbg_code = (unsigned)arch_interrupt_receiver[i]->owner
|
||||
arch_interrupt_receiver[i]->send_message (i, &c)
|
||||
if ipr & (1 << IRQ_OST0):
|
||||
ost_clear_uf (0)
|
||||
@@ -118,15 +118,12 @@ static void arch_invoke ():
|
||||
bool wait
|
||||
Thread *caller = current
|
||||
target = caller->address_space->find_capability (caller->arch.v0, &wait)
|
||||
do_schedule = false
|
||||
if wait:
|
||||
caller->wait ()
|
||||
if !target:
|
||||
// There must be no action here.
|
||||
//dbg_send (3, 2)
|
||||
//dbg_send (caller->arch.v0)
|
||||
// Calling an invalid capability always fails.
|
||||
caller->arch.v0 = 0
|
||||
else:
|
||||
if wait:
|
||||
caller->wait ()
|
||||
Capability::Context c
|
||||
c.cap[0] = caller->address_space->find_capability (caller->arch.a0, &c.copy[0])
|
||||
c.cap[1] = caller->address_space->find_capability (caller->arch.a1, &c.copy[1])
|
||||
@@ -136,8 +133,9 @@ static void arch_invoke ():
|
||||
c.data[1] = caller->arch.t1
|
||||
c.data[2] = caller->arch.t2
|
||||
c.data[3] = caller->arch.t3
|
||||
caller->arch.v0 = target->invoke (&c) ? 1 : 0
|
||||
if caller != current && caller != &idle && (caller->flags & (THREAD_FLAG_RUNNING | THREAD_FLAG_WAITING)) == THREAD_FLAG_RUNNING:
|
||||
target->invoke (&c)
|
||||
// If the caller received a reply from the kernel, it is no longer set as current. Don't let it lose its timeslice.
|
||||
if caller != current && (caller->flags & (THREAD_FLAG_RUNNING | THREAD_FLAG_WAITING)) == THREAD_FLAG_RUNNING && !do_schedule:
|
||||
current = caller
|
||||
|
||||
/// A general exception has occurred.
|
||||
@@ -160,15 +158,21 @@ Thread *exception ():
|
||||
panic (0x31223344, "TLB load or instruction fetch.")
|
||||
case 3:
|
||||
// TLB store.
|
||||
unsigned a
|
||||
cp0_get (CP0_EPC, a)
|
||||
dbg_send (a)
|
||||
panic (0x41223344, "TLB store.")
|
||||
case 4:
|
||||
// Address error load or instruction fetch.
|
||||
unsigned a
|
||||
cp0_get (CP0_EPC, a)
|
||||
dbg_send (a)
|
||||
panic (0x51223344, "Address error load or instruction fetch.")
|
||||
case 5:
|
||||
// Address error store.
|
||||
unsigned a
|
||||
cp0_get (CP0_EPC, a)
|
||||
dbg_send (a, 16)
|
||||
cp0_get (CP0_BAD_V_ADDR, a)
|
||||
dbg_send (a, 32)
|
||||
panic (0x61223344, "Address error store.")
|
||||
case 6:
|
||||
// Bus error instruction fetch.
|
||||
@@ -183,7 +187,10 @@ Thread *exception ():
|
||||
break
|
||||
case 9:
|
||||
// Breakpoint.
|
||||
panic (0x91223344, "Breakpoint.")
|
||||
//panic (0x91223344, "Breakpoint.")
|
||||
dbg_send (current->arch.a0, current->arch.a1)
|
||||
current->pc += 4
|
||||
break
|
||||
case 10:
|
||||
// Reserved instruction.
|
||||
panic (0xa1223344, "Reserved instruction.")
|
||||
|
||||
@@ -23,7 +23,6 @@
|
||||
|
||||
// Main clock, for cpu, serial port, and with divisors for most other hardware
|
||||
#define JZ_EXTAL 3686400
|
||||
//#define JZ_EXTAL 3072000
|
||||
// RTC clock
|
||||
#define RTC_CLOCK 32768
|
||||
|
||||
@@ -36,7 +35,7 @@
|
||||
#define LCD_PHYSICAL 0x13050000
|
||||
#define CIM_PHYSICAL 0x13060000
|
||||
#define ETH_PHYSICAL 0x13100000
|
||||
#define NBM_PHYSICAL 0x13F00000
|
||||
#define NBM_PHYSICAL 0x13f00000
|
||||
#define CPM_PHYSICAL 0x10000000
|
||||
#define INTC_PHYSICAL 0x10001000
|
||||
#define OST_PHYSICAL 0x10002000
|
||||
@@ -98,49 +97,53 @@
|
||||
|
||||
#else
|
||||
// In user space, they just need a mapping.
|
||||
#define HARB_BASE 0x00000000
|
||||
#define EMC_BASE 0x00001000
|
||||
#define DMAC_BASE 0x00002000
|
||||
#define UHC_BASE 0x00003000
|
||||
#define UDC_BASE 0x00004000
|
||||
#define LCD_BASE 0x00005000
|
||||
#define CIM_BASE 0x00006000
|
||||
#define ETH_BASE 0x00007000
|
||||
#define NBM_BASE 0x00008000
|
||||
#define CPM_BASE 0x00009000
|
||||
#define INTC_BASE 0x0000a000
|
||||
#define OST_BASE 0x0000b000
|
||||
#define RTC_BASE 0x0000c000
|
||||
#define WDT_BASE 0x0000d000
|
||||
#define GPIO_BASE 0x0000e000
|
||||
#define AIC_BASE 0x0000f000
|
||||
#define MSC_BASE 0x00010000
|
||||
#define UART0_BASE 0x00011000
|
||||
#define UART1_BASE 0x00012000
|
||||
#define UART2_BASE 0x00013000
|
||||
#define UART3_BASE 0x00014000
|
||||
#define FIR_BASE 0x00015000
|
||||
#define SCC_BASE 0x00016000
|
||||
#define SCC0_BASE 0x00017000
|
||||
#define I2C_BASE 0x00018000
|
||||
#define SSI_BASE 0x00019000
|
||||
#define SCC1_BASE 0x0001a000
|
||||
#define PWM0_BASE 0x0001b000
|
||||
#define PWM1_BASE 0x0001c000
|
||||
#define DES_BASE 0x0001d000
|
||||
#define UPRT_BASE 0x0001e000
|
||||
#define KBC_BASE 0x0001f000
|
||||
#define UNMAPPED_BASE 0x00000000
|
||||
|
||||
#define HARB_BASE 0x00001000
|
||||
#define EMC_BASE 0x00002000
|
||||
#define DMAC_BASE 0x00003000
|
||||
#define UHC_BASE 0x00004000
|
||||
#define UDC_BASE 0x00005000
|
||||
#define LCD_BASE 0x00006000
|
||||
#define CIM_BASE 0x00007000
|
||||
#define ETH_BASE 0x00008000
|
||||
#define NBM_BASE 0x00009000
|
||||
#define CPM_BASE 0x0000a000
|
||||
#define INTC_BASE 0x0000b000
|
||||
#define OST_BASE 0x0000c000
|
||||
#define RTC_BASE 0x0000d000
|
||||
#define WDT_BASE 0x0000e000
|
||||
#define GPIO_BASE 0x0000f000
|
||||
#define AIC_BASE 0x00010000
|
||||
#define MSC_BASE 0x00011000
|
||||
#define UART0_BASE 0x00012000
|
||||
#define UART1_BASE 0x00013000
|
||||
#define UART2_BASE 0x00014000
|
||||
#define UART3_BASE 0x00015000
|
||||
#define FIR_BASE 0x00016000
|
||||
#define SCC_BASE 0x00017000
|
||||
#define SCC0_BASE 0x00018000
|
||||
#define I2C_BASE 0x00019000
|
||||
#define SSI_BASE 0x0001a000
|
||||
#define SCC1_BASE 0x0001b000
|
||||
#define PWM0_BASE 0x0001c000
|
||||
#define PWM1_BASE 0x0001d000
|
||||
#define DES_BASE 0x0001e000
|
||||
#define UPRT_BASE 0x0001f000
|
||||
#define KBC_BASE 0x00020000
|
||||
|
||||
// Default lcd framebuffer mapping space.
|
||||
#define LCD_FRAMEBUFFER_BASE ((unsigned short *)0x00021000)
|
||||
|
||||
// Map IO memory (requires a priviledged __my_thread capability).
|
||||
#include <iris.h>
|
||||
static void __map_io (unsigned physical, unsigned mapping):
|
||||
Capability page = memory_create_page (__my_memory)
|
||||
// 0 means not cachable.
|
||||
alloc_physical (page, physical, 0)
|
||||
// 0 means not cachable; 0 means don't free when done.
|
||||
alloc_physical (page, physical, 0, 0)
|
||||
// 1 means writable.
|
||||
memory_map (__my_memory, page, mapping, 1)
|
||||
//drop (page)
|
||||
#endif
|
||||
drop (page)
|
||||
|
||||
#define map_harb() do { __map_io (HARB_PHYSICAL, HARB_BASE); } while (0)
|
||||
#define map_emc() do { __map_io (EMC_PHYSICAL, EMC_BASE); } while (0)
|
||||
@@ -175,6 +178,8 @@ static void __map_io (unsigned physical, unsigned mapping):
|
||||
#define map_uprt() do { __map_io (UPRT_PHYSICAL, UPRT_BASE); } while (0)
|
||||
#define map_kbc() do { __map_io (KBC_PHYSICAL, KBC_BASE); } while (0)
|
||||
|
||||
#endif
|
||||
|
||||
#define REG8(x) (*(volatile unsigned char *)(x))
|
||||
#define REG16(x) (*(volatile unsigned short *)(x))
|
||||
#define REG32(x) (*(volatile unsigned *)(x))
|
||||
|
||||
@@ -97,6 +97,8 @@ void dbg_sleep (unsigned ms):
|
||||
__gpio_as_output (CAPSLOCKLED_IO)
|
||||
|
||||
void dbg_send (unsigned code, unsigned bits):
|
||||
if bits > 32:
|
||||
bits = 32
|
||||
for int i = bits - 1; i >= 0; --i:
|
||||
bool on = code & (1 << i)
|
||||
dbg_led (false, false, false)
|
||||
|
||||
Reference in New Issue
Block a user