void sys$sigma0_map_fpage(L4_Fpage_t virt_page, L4_Fpage_t phys_page, unsigned int priv) { L4_ThreadId_t tid; L4_MsgTag_t tag; L4_Msg_t msg; L4_MapItem_t map; // Find Pager's ID tid = L4_Pager(); L4_Set_Rights(&phys_page, priv); L4_Accept(L4_MapGrantItems(virt_page)); L4_MsgClear(&msg); L4_MsgAppendWord(&msg, (L4_Word_t) phys_page.raw); L4_MsgAppendWord(&msg, (L4_Word_t) 0); L4_Set_Label(&msg.tag, SIGMA0_REQUEST_LABEL); L4_MsgLoad(&msg); tag = L4_Call(tid); PANIC(L4_IpcFailed(tag), notice(IPC_F_FAILED "IPC failed (error %ld: %s)\n", L4_ErrorCode(), L4_ErrorCode_String(L4_ErrorCode()))); L4_MsgStore(tag, &msg); L4_MsgGetMapItem(&msg, 0, &map); if (dbg$virtual_memory == 1) { if (map.X.snd_fpage.raw == L4_Nilpage.raw) { notice(MEM_I_REJMAP "rejecting mapping\n"); notice(MEM_I_REJMAP "virtual $%016lX - $%016lX\n", L4_Address(virt_page), L4_Address(virt_page) + (L4_Size(virt_page) - 1)); notice(MEM_I_REJMAP "physical $%016lX - $%016lX\n", L4_Address(phys_page), L4_Address(phys_page) + (L4_Size(phys_page) - 1)); } else { notice(MEM_I_ACCMAP "accepting mapping\n"); notice(MEM_I_ACCMAP "virtual $%016lX - $%016lX\n", L4_Address(virt_page), L4_Address(virt_page) + (L4_Size(virt_page) - 1)); notice(MEM_I_ACCMAP "physical $%016lX - $%016lX\n", L4_Address(phys_page), L4_Address(phys_page) + (L4_Size(phys_page) - 1)); } } return; }
static void sos_debug_flush(void) { L4_Msg_t msg; L4_MsgTag_t tag; L4_MsgClear(&msg); L4_Set_MsgLabel(&msg, TAG_SETSYSCALL(SOS_UNMAP_ALL)); L4_MsgLoad(&msg); tag = L4_Send(L4_Pager()); if (L4_IpcFailed(tag)) { L4_Word_t err = L4_ErrorCode(); printf("sos_debug_flush failed (error: %lx)\n", err); } }
static L4_ThreadId_t create_local_thread(char *desc, L4_KernelInterfacePage_t *kip, int idx, threadfunc_t func, L4_Word_t stack_size) { L4_Word_t utcb_size = L4_UtcbSize(kip); L4_Word_t my_utcb = L4_MyLocalId().raw; my_utcb = (my_utcb & ~(utcb_size - 1)); L4_ThreadId_t tid = L4_GlobalId(L4_ThreadNo(L4_Myself()) + idx, 1); L4_Word_t utcb_location = my_utcb + idx * utcb_size; if (FALSE == L4_ThreadControl(tid, L4_Myself(), L4_Myself(), L4_Pager(), (void *) utcb_location)) { printf("panic: can't execute %s: error code %d\n", desc, (int) L4_ErrorCode()); return L4_nilthread; } void *stack = kmalloc(stack_size); L4_Start_SpIp(tid, (L4_Word_t) stack + stack_size - 32, (L4_Word_t) func); return tid; }
/* poke/peek thread. obeys POKE, PEEK, and QUIT. */ static void poke_peek_fn(void *param_ptr) { #if 0 diag("%s: started as %lu:%lu. pager is %#lx", __func__, L4_ThreadNo(L4_MyGlobalId()), L4_Version(L4_MyGlobalId()), L4_Pager()); #endif for(;;) { L4_ThreadId_t from; L4_MsgTag_t tag = L4_Wait(&from); for(;;) { if(L4_IpcFailed(tag)) break; if(tag.X.label == QUIT_LABEL) { // diag("%s: quitting", __func__); return; } else if(tag.X.label == PEEK_LABEL) { L4_Word_t addr; L4_StoreMR(1, &addr); L4_LoadMR(0, (L4_MsgTag_t){ .X.u = 1 }.raw); L4_LoadMR(1, *(uint8_t *)addr); } else if(tag.X.label == POKE_LABEL) {
/** * Starts the clock driver. This will map the memory region where the * registers are in uncached mode, start the time stamp timer register * and enable the interrupts for our time stamp timer and the general * purpose timer 0. * * @return CLOCK_R_OK if the timer is started successfully * CLOCK_R_FAIL if the memory region could not be mapped */ int start_timer(void) { assert(!driver_initialized); // initialize variables timestamp_irq_tid = L4_GlobalId(NSLU2_TIMESTAMP_IRQ, 1); timer0_irq_tid = L4_GlobalId(NSLU2_TIMER0_IRQ, 1); registers_fpage = L4_FpageLog2(NSLU2_OSTS_PHYS_BASE, 12); // Set up uncached memory mapping for registers L4_Set_Rights(®isters_fpage, L4_FullyAccessible); L4_PhysDesc_t phys = L4_PhysDesc(NSLU2_OSTS_PHYS_BASE, L4_UncachedMemory); if(L4_MapFpage(L4_Pager(), registers_fpage, phys)) { // enable timer0 interrupts TIMER0_ONE_SHOT(0); TIMER0_STOP(); (*(L4_Word_t*)OST_STATUS) |= (0x1 << 0); int res = L4_AssociateInterrupt(timer0_irq_tid, root_thread_g); assert(res); // start timestamp timer *((L4_Word_t*)OST_TS) = 0x00000000; // reset counter // enable timestamp interrupts (*(L4_Word_t*)OST_STATUS) |= (0x1 << 2); res = L4_AssociateInterrupt(timestamp_irq_tid, root_thread_g); assert(res); driver_initialized = TRUE; return CLOCK_R_OK; } else { return CLOCK_R_FAIL; } }
int l4e_sigma0_map_fpage(L4_Fpage_t virt_page, L4_Fpage_t phys_page) { /* * XXX: These two special cases are workarounds for broken superpage * support in pistachio. On ARM, 1M superpages are disabled by * pistachio to reduce the size of the mapping database, however due to * bugs in the mapping code, any mappings >= 1M get converted into 4K * mappings (rather than 64K). For MIPS, the tlb refill code assumes * only 4K mappings are used, even the the pagetable building code will * use superpages where possible. -- alexw */ #if defined(ARCH_ARM) uintptr_t virt_base = L4_Address(virt_page); uintptr_t phys_base = L4_Address(phys_page); uintptr_t offset = 0; uintptr_t step = L4_Size(virt_page) > 0x10000 ? 0x10000 : L4_Size(virt_page); uintptr_t limit = L4_Size(virt_page) - 1; for (virt_page = L4_Fpage(virt_base + offset, step), phys_page = L4_Fpage(phys_base + offset, step); offset < limit; offset += step, virt_page = L4_Fpage(virt_base + offset, step), phys_page = L4_Fpage(phys_base + offset, step)) #elif defined(ARCH_MIPS64) uintptr_t virt_base = L4_Address(virt_page); uintptr_t phys_base = L4_Address(phys_page); uintptr_t offset = 0; uintptr_t step = 0x1000; uintptr_t limit = L4_Size(virt_page) - 1; for (virt_page = L4_Fpage(virt_base + offset, step), phys_page = L4_Fpage(phys_base + offset, step); offset < limit; offset += step, virt_page = L4_Fpage(virt_base + offset, step), phys_page = L4_Fpage(phys_base + offset, step)) #endif { L4_ThreadId_t tid; L4_MsgTag_t tag; L4_Msg_t msg; L4_MapItem_t map; /* * find our pager's ID */ tid = L4_Pager(); L4_Set_Rights(&phys_page, L4_FullyAccessible); /* accept fpages */ L4_Accept(L4_MapGrantItems(virt_page)); /* send it to our pager */ L4_MsgClear(&msg); L4_MsgAppendWord(&msg, (L4_Word_t) phys_page.raw); L4_MsgAppendWord(&msg, (L4_Word_t) 0); L4_Set_Label(&msg.tag, SIGMA0_REQUEST_LABEL); L4_MsgLoad(&msg); /* make the call */ tag = L4_Call(tid); /* check for an error */ if (L4_IpcFailed(tag)) { return 2; } L4_MsgStore(tag, &msg); L4_MsgGetMapItem(&msg, 0, &map); /* * rejected mapping? */ if (map.X.snd_fpage.raw == L4_Nilpage.raw) { return 1; } } return 0; }
{ #if 0 diag("flushing %#lx:%#lx (dpos %d)", L4_Address(drop), L4_Size(drop), dpos); #endif L4_Set_Rights(&drop, L4_FullyAccessible); L4_FlushFpage(drop); } /* pass it on. */ L4_LoadBR(0, L4_CompleteAddressSpace.raw); L4_LoadMR(0, (L4_MsgTag_t){ .X.label = 0xffe0 | rwx, .X.u = 2 }.raw); L4_LoadMR(1, faddr); L4_LoadMR(2, fip); tag = L4_Call(L4_Pager()); if(L4_IpcFailed(tag)) { diag("drop-to-pager IPC failed, ec %lu", L4_ErrorCode()); muidl_raise_no_reply(); } else if(tag.X.t != 2 || tag.X.u != 0) { diag("drop-to-pager IPC returned weird tag %#lx", tag.raw); map->raw[0] = 0; map->raw[1] = 0; } else { /* AOK! */ L4_StoreMRs(1, 2, map->raw); } }
void ttyout_init(void) { /* Perform any initialisation you require here */ sSystemId = L4_Pager(); }