mirror of
git://projects.qi-hardware.com/iris.git
synced 2025-04-21 12:27:27 +03:00
make things work with terminals
This commit is contained in:
@@ -119,19 +119,19 @@ void kMemory_arch_init (kMemory *mem):
|
||||
mem->arch.shadow = NULL
|
||||
|
||||
static void tlb_reset (kMemory *mem, unsigned address, unsigned value):
|
||||
//dbg_log_line ()
|
||||
//kdebug_line ()
|
||||
unsigned asid = mem->arch.asid
|
||||
if asids[asid] != (unsigned)mem:
|
||||
//dbg_log ("not resetting tlb, because the asid is not in use.\n")
|
||||
//kdebug ("not resetting tlb, because the asid is not in use.\n")
|
||||
return
|
||||
//dbg_log ("resetting tlb for ")
|
||||
//dbg_log_num (address)
|
||||
//dbg_log ("\n")
|
||||
//kdebug ("resetting tlb for ")
|
||||
//kdebug_num (address)
|
||||
//kdebug ("\n")
|
||||
cp0_set (CP0_ENTRY_HI, address | asid)
|
||||
__asm__ volatile ("tlbp")
|
||||
unsigned idx
|
||||
cp0_get (CP0_INDEX, idx)
|
||||
if ~idx & 0x80000000:
|
||||
if !(idx & (1 << 31)):
|
||||
__asm__ volatile ("tlbr")
|
||||
if address & (1 << PAGE_BITS):
|
||||
cp0_set (CP0_ENTRY_LO1, value)
|
||||
@@ -139,23 +139,26 @@ static void tlb_reset (kMemory *mem, unsigned address, unsigned value):
|
||||
cp0_set (CP0_ENTRY_LO0, value)
|
||||
__asm__ volatile ("tlbwi")
|
||||
#if 0
|
||||
dbg_log ("tlb reset ")
|
||||
kdebug ("tlb reset ")
|
||||
unsigned hi, lo0, lo1
|
||||
cp0_get (CP0_ENTRY_LO0, lo0)
|
||||
cp0_get (CP0_ENTRY_LO1, lo1)
|
||||
cp0_get (CP0_ENTRY_HI, hi)
|
||||
dbg_log_num (lo0)
|
||||
dbg_log (":")
|
||||
dbg_log_num (lo1)
|
||||
dbg_log (" for ")
|
||||
dbg_log_num (hi)
|
||||
dbg_log ("\n")
|
||||
kdebug_num (idx, 2)
|
||||
kdebug ('|')
|
||||
kdebug_num (lo0)
|
||||
kdebug (":")
|
||||
kdebug_num (lo1)
|
||||
kdebug (" for ")
|
||||
kdebug_num (hi)
|
||||
kdebug ("\n")
|
||||
#endif
|
||||
cp0_set (CP0_ENTRY_HI, old_current->address_space->arch.asid)
|
||||
|
||||
static unsigned make_entry_lo (kPage *page):
|
||||
//dbg_log_line ()
|
||||
//kdebug_line ()
|
||||
if !page->frame:
|
||||
//dbg_log ("not mapping because there is no frame\n")
|
||||
//kdebug ("not mapping because there is no frame\n")
|
||||
return 0
|
||||
unsigned flags
|
||||
if page->flags & Kernel::Page::UNCACHED:
|
||||
@@ -168,7 +171,6 @@ static unsigned make_entry_lo (kPage *page):
|
||||
return ((page->frame & ~0x80000000) >> 6) | flags
|
||||
|
||||
bool kMemory_arch_map (kMemory *mem, kPage *page, unsigned address):
|
||||
//dbg_log_line ()
|
||||
if address >= 0x80000000:
|
||||
dpanic (address, "trying to map to kernel address")
|
||||
return false
|
||||
@@ -180,7 +182,7 @@ bool kMemory_arch_map (kMemory *mem, kPage *page, unsigned address):
|
||||
dpanic (address, "mapping not page-aligned")
|
||||
address &= PAGE_MASK
|
||||
if !mem->arch.directory:
|
||||
//dbg_log ("creating directory\n")
|
||||
//kdebug ("creating directory\n")
|
||||
mem->arch.directory = (Table **)mem->zalloc ()
|
||||
if !mem->arch.directory:
|
||||
dpanic (0, "unable to allocate directory")
|
||||
@@ -193,7 +195,7 @@ bool kMemory_arch_map (kMemory *mem, kPage *page, unsigned address):
|
||||
return false
|
||||
Table *table = mem->arch.directory[address >> 21]
|
||||
if !table:
|
||||
//dbg_log ("creating table\n")
|
||||
//kdebug ("creating table\n")
|
||||
table = (Table *)mem->zalloc ()
|
||||
if !table:
|
||||
dpanic (0, "unable to allocate table")
|
||||
@@ -206,21 +208,23 @@ bool kMemory_arch_map (kMemory *mem, kPage *page, unsigned address):
|
||||
mem->arch.directory[address >> 21] = table
|
||||
unsigned idx = (address >> 12) & ((1 << 9) - 1)
|
||||
if table->entrylo[idx]:
|
||||
dbg_log ("page already mapped: ")
|
||||
dbg_log_num (idx, 3)
|
||||
dbg_log (";")
|
||||
dbg_log_num (table->entrylo[idx])
|
||||
dbg_log ("/")
|
||||
dbg_log_num ((unsigned)table->page[idx])
|
||||
dbg_log (" table: ")
|
||||
dbg_log_num ((unsigned)table)
|
||||
dbg_log ("\n")
|
||||
kdebug ("page already mapped: ")
|
||||
kdebug_num (idx, 3)
|
||||
kdebug (";")
|
||||
kdebug_num (table->entrylo[idx])
|
||||
kdebug ("/")
|
||||
kdebug_num ((unsigned)table->page[idx])
|
||||
kdebug (" table: ")
|
||||
kdebug_num ((unsigned)table)
|
||||
kdebug ("\n")
|
||||
mem->unmap (table->page[idx])
|
||||
table->entrylo[idx] = make_entry_lo (page)
|
||||
table->page[idx] = page
|
||||
//dbg_log ("mapped at address ")
|
||||
//dbg_log_num (address)
|
||||
//dbg_log_char ('\n')
|
||||
//kdebug ("mapped ")
|
||||
//kdebug_num (page->frame)
|
||||
//kdebug (" at address ")
|
||||
//kdebug_num (address)
|
||||
//kdebug ('\n')
|
||||
page->mapping = address
|
||||
page->arch.next_mapped = mem->arch.shadow[address >> 21]
|
||||
if page->arch.next_mapped:
|
||||
@@ -230,7 +234,7 @@ bool kMemory_arch_map (kMemory *mem, kPage *page, unsigned address):
|
||||
return true
|
||||
|
||||
void kMemory_arch_unmap (kMemory *mem, kPage *page):
|
||||
//dbg_log_line ()
|
||||
//kdebug_line ()
|
||||
unsigned didx = page->mapping >> 21
|
||||
unsigned tidx = (page->mapping >> 12) & ((1 << 9) - 1)
|
||||
Table *table = mem->arch.directory[didx]
|
||||
@@ -248,7 +252,7 @@ void kMemory_arch_unmap (kMemory *mem, kPage *page):
|
||||
page->mapping = ~0
|
||||
|
||||
kPage *kMemory_arch_get_mapping (kMemory *mem, unsigned address):
|
||||
//dbg_log_line ()
|
||||
//kdebug_line ()
|
||||
if address >= 0x80000000 || !mem->arch.directory:
|
||||
return NULL
|
||||
Table *table = mem->arch.directory[address >> 21]
|
||||
@@ -257,7 +261,7 @@ kPage *kMemory_arch_get_mapping (kMemory *mem, unsigned address):
|
||||
return table->page[(address >> 12) & ((1 << 9) - 1)]
|
||||
|
||||
void kPage_arch_update_mapping (kPage *page):
|
||||
//dbg_log_line ()
|
||||
//kdebug_line ()
|
||||
if page->mapping == ~0:
|
||||
return
|
||||
unsigned target = make_entry_lo (page)
|
||||
|
||||
@@ -22,7 +22,7 @@
|
||||
#include "../kernel.hh"
|
||||
#include <elf.h>
|
||||
|
||||
#define NUM_SLOTS 4
|
||||
#define NUM_SLOTS 8
|
||||
#define NUM_CAPS 32
|
||||
|
||||
static void init_idle ():
|
||||
@@ -116,9 +116,9 @@ static void init_threads ():
|
||||
first_alarm = NULL
|
||||
kReceiver *init_receiver = NULL
|
||||
for unsigned i = 0; i < NUM_THREADS; ++i:
|
||||
dbg_log ("Starting thread ")
|
||||
dbg_log_num (i, 2)
|
||||
dbg_log ("\n")
|
||||
kdebug ("Starting thread ")
|
||||
kdebug_num (i, 2)
|
||||
kdebug ("\n")
|
||||
kMemory *mem = top_memory.alloc_memory ()
|
||||
assert (mem)
|
||||
kThread *thread = mem->alloc_thread (NUM_SLOTS)
|
||||
@@ -177,14 +177,14 @@ static void init_threads ():
|
||||
if !mem->map (page, p):
|
||||
panic (0x22446688, "unable to map initial page")
|
||||
return
|
||||
//dbg_log ("mapped page ")
|
||||
//kdebug ("mapped page ")
|
||||
//if readonly:
|
||||
// dbg_log ("as readonly ")
|
||||
//dbg_log ("at address ")
|
||||
//dbg_log_num (p)
|
||||
//dbg_log (" for ")
|
||||
//dbg_log_num (i, 1)
|
||||
//dbg_log_char ('\n')
|
||||
// kdebug ("as readonly ")
|
||||
//kdebug ("at address ")
|
||||
//kdebug_num (p)
|
||||
//kdebug (" for ")
|
||||
//kdebug_num (i, 1)
|
||||
//kdebug ('\n')
|
||||
else:
|
||||
if readonly:
|
||||
panic (0x33399993, "unwritable bss section")
|
||||
@@ -204,11 +204,11 @@ static void init_threads ():
|
||||
if !mem->map (page, p):
|
||||
panic (0x33557799, "unable to map initial bss page")
|
||||
return
|
||||
dbg_log ("mapped bss page at address ")
|
||||
dbg_log_num (p)
|
||||
dbg_log (" for ")
|
||||
dbg_log_num (i, 1)
|
||||
dbg_log_char ('\n')
|
||||
kdebug ("mapped bss page at address ")
|
||||
kdebug_num (p)
|
||||
kdebug (" for ")
|
||||
kdebug_num (i, 1)
|
||||
kdebug ('\n')
|
||||
else:
|
||||
if page->flags & Kernel::Page::MAPPED_READONLY:
|
||||
panic (0x20203030, "bss section starts on read-only page")
|
||||
@@ -224,7 +224,9 @@ static void init_threads ():
|
||||
if used[p]:
|
||||
mem->use ()
|
||||
continue
|
||||
//kdebug ("freeing unused page from initial file\n")
|
||||
top_memory.pfree (thread_start[i] + (p << PAGE_BITS))
|
||||
//kdebug ("freeing unused page list\n")
|
||||
mem->pfree ((unsigned)used)
|
||||
kPage *stackpage = mem->alloc_page ()
|
||||
stackpage->frame = mem->zalloc ()
|
||||
@@ -262,6 +264,9 @@ void init (unsigned mem):
|
||||
must_wait = false
|
||||
// Initialize kernel variables to empty.
|
||||
unsigned count = init_memory (mem)
|
||||
// Set up invoke system.
|
||||
reply_caps.init (1)
|
||||
replied_caps.init (1)
|
||||
// initialize system control coprocessor.
|
||||
init_cp0 ()
|
||||
// initialize everything about the idle task.
|
||||
|
||||
@@ -24,7 +24,8 @@ void arch_flush_cache ():
|
||||
for cacheline *line = (cacheline *)0x80000000; line < (cacheline *)0x80008000; ++line:
|
||||
__asm__ volatile ("lw $k0, %0; cache 0, 0($k0); cache 1, 0($k0)" :: "m"(line))
|
||||
|
||||
static void handle_exit ():
|
||||
static kThread *handle_exit ():
|
||||
dbg_check ()
|
||||
--dbg_code.h
|
||||
// Set must_wait to false, so random threads are not set to waiting when the kernel invokes something (such as a dbg_cap).
|
||||
must_wait = false
|
||||
@@ -32,11 +33,10 @@ static void handle_exit ():
|
||||
schedule ()
|
||||
if !current:
|
||||
current = &idle
|
||||
//if (current->flags & (Kernel::Thread::RUNNING | Kernel::Thread::WAITING)) != Kernel::Thread::RUNNING:
|
||||
//panic (current->flags, "non-scheduled thread running")
|
||||
if (current->flags & (Kernel::Thread::RUNNING | Kernel::Thread::WAITING)) != Kernel::Thread::RUNNING:
|
||||
panic (current->flags, "non-scheduled thread running")
|
||||
if old_current == current:
|
||||
return
|
||||
//dbg_send ((unsigned)current >> 12, 3)
|
||||
return current
|
||||
arch_flush_cache ()
|
||||
if current != &idle:
|
||||
if (kMemory *)asids[current->address_space->arch.asid] != current->address_space:
|
||||
@@ -58,6 +58,7 @@ static void handle_exit ():
|
||||
cp0_set (CP0_STATUS, 0x1000ff13)
|
||||
else:
|
||||
cp0_set (CP0_STATUS, 0x0000ff13)
|
||||
return current
|
||||
|
||||
/// A TLB miss has occurred. This is the slow version. It is only used
|
||||
/// when k0 or k1 is not 0, or when an error occurs.
|
||||
@@ -69,8 +70,7 @@ kThread *tlb_refill ():
|
||||
unsigned addr
|
||||
cp0_get (CP0_BAD_V_ADDR, addr)
|
||||
current->raise (Kernel::ERR_NO_PAGE_DIRECTORY, addr)
|
||||
handle_exit ()
|
||||
return current
|
||||
return handle_exit ()
|
||||
unsigned EntryHi
|
||||
cp0_get (CP0_ENTRY_HI, EntryHi)
|
||||
Table *t = directory[EntryHi >> 21]
|
||||
@@ -84,17 +84,20 @@ kThread *tlb_refill ():
|
||||
cp0_set (CP0_ENTRY_LO0, t->entrylo[idx])
|
||||
cp0_set (CP0_ENTRY_LO1, t->entrylo[idx + 1])
|
||||
__asm__ volatile ("tlbwr")
|
||||
#if 0
|
||||
dbg_log ("tlb refill ")
|
||||
dbg_log_num (t->entrylo[idx])
|
||||
dbg_log (":")
|
||||
dbg_log_num (t->entrylo[idx + 1])
|
||||
dbg_log (" for ")
|
||||
dbg_log_num (EntryHi)
|
||||
dbg_log ("\n")
|
||||
#endif
|
||||
handle_exit ()
|
||||
return current
|
||||
if dbg_code.l:
|
||||
kdebug ("tlb refill ")
|
||||
__asm__ volatile ("tlbp")
|
||||
unsigned index
|
||||
cp0_get (CP0_INDEX, index)
|
||||
kdebug_num (index, 2)
|
||||
kdebug ("|")
|
||||
kdebug_num (t->entrylo[idx])
|
||||
kdebug (":")
|
||||
kdebug_num (t->entrylo[idx + 1])
|
||||
kdebug (" for ")
|
||||
kdebug_num (EntryHi)
|
||||
kdebug ("\n")
|
||||
return handle_exit ()
|
||||
|
||||
/// An interrupt which is not an exception has occurred.
|
||||
kThread *interrupt ():
|
||||
@@ -126,8 +129,7 @@ kThread *interrupt ():
|
||||
#endif
|
||||
intc_ack_irq (TIMER_INTERRUPT)
|
||||
timer_interrupt ()
|
||||
handle_exit ()
|
||||
return current
|
||||
return handle_exit ()
|
||||
|
||||
void flush_tlb (unsigned asid):
|
||||
for unsigned tlb = 1; tlb < 32; ++tlb:
|
||||
@@ -147,9 +149,15 @@ static void arch_invoke ():
|
||||
if must_wait:
|
||||
old_current->recv_reply = old_current->arch.t[2]
|
||||
old_current->recv_arg = old_current->arch.t[3]
|
||||
//kdebug_num (old_current->recv_reply)
|
||||
//kdebug ("/")
|
||||
//kdebug_num (old_current->recv_arg)
|
||||
//kdebug ("\n")
|
||||
if !target.valid ():
|
||||
if must_wait:
|
||||
old_current->wait ()
|
||||
else:
|
||||
dpanic (target.index, "invalid target called")
|
||||
return
|
||||
msg.reply = old_current->find_capability (old_current->arch.t[0], &msg.copy[0])
|
||||
msg.arg = old_current->find_capability (old_current->arch.t[1], &msg.copy[1])
|
||||
@@ -236,9 +244,9 @@ kThread *exception ():
|
||||
if !dbg_cap.valid ():
|
||||
dpanic (0, "no log capability provided")
|
||||
break
|
||||
dbg_log ("log capability registered.\n")
|
||||
kdebug ("log capability registered.\n")
|
||||
break
|
||||
dbg_log_char (current->arch.a[1])
|
||||
kdebug (current->arch.a[1])
|
||||
#endif
|
||||
break
|
||||
case 10:
|
||||
@@ -294,13 +302,11 @@ kThread *exception ():
|
||||
default:
|
||||
panic (0xf6223344, "Impossible exception code")
|
||||
break
|
||||
handle_exit ()
|
||||
return current
|
||||
return handle_exit ()
|
||||
|
||||
/// There's a cache error. Big trouble. Probably not worth trying to recover.
|
||||
kThread *cache_error ():
|
||||
++dbg_code.h
|
||||
panic (0x33333333, "cache error")
|
||||
old_current = current
|
||||
handle_exit ()
|
||||
return current
|
||||
return handle_exit ()
|
||||
|
||||
@@ -29,7 +29,7 @@ arch_iris_sources = mips/interrupts.cc mips/arch.cc
|
||||
boot_sources = mips/init.cc mips/nanonote/board.cc
|
||||
arch_headers = mips/arch.hh mips/nanonote/jz4740.hh mips/nanonote/board.hh
|
||||
boot_threads = init udc
|
||||
programs = \#nanonote-gpio \#buzzer \#lcd metronome
|
||||
programs = \#nanonote-gpio \#buzzer \#lcd metronome ball
|
||||
|
||||
all: test
|
||||
|
||||
|
||||
@@ -72,7 +72,7 @@ void board_init ():
|
||||
UART0_DLLR = uart_div
|
||||
UART0_LCR = UARTLCR_WLEN_8 | UARTLCR_STOP1
|
||||
UART0_FCR = UARTFCR_UUE | UARTFCR_FE | UARTFCR_RFLS | UARTFCR_TFLS
|
||||
dbg_log ("\n\nSerial port initialized\n")
|
||||
kdebug ("\n\nSerial port initialized\n")
|
||||
#endif
|
||||
|
||||
void arch_reboot ():
|
||||
|
||||
@@ -137,13 +137,13 @@ void data::poll ():
|
||||
continue
|
||||
case Directory::LOCK_RO:
|
||||
std::cerr << "lock\n"
|
||||
if !lock++:
|
||||
std::cerr << "freezing file list\n"
|
||||
shevek::dir d (files)
|
||||
dir.clear ()
|
||||
for shevek::dir::const_iterator i = d.begin (); i != d.end (); ++i:
|
||||
if !i->name.empty () && i->name[0] != '.':
|
||||
dir.push_back (Name (i->name))
|
||||
lock++
|
||||
std::cerr << "freezing file list\n"
|
||||
shevek::dir d (files)
|
||||
dir.clear ()
|
||||
for shevek::dir::const_iterator i = d.begin (); i != d.end (); ++i:
|
||||
if !i->name.empty () && i->name[0] != '.':
|
||||
dir.push_back (Name (i->name))
|
||||
continue
|
||||
case Directory::UNLOCK_RO:
|
||||
std::cerr << "unlock\n"
|
||||
|
||||
Reference in New Issue
Block a user