Example #1
0
/*
 * The Philosopher thread tries to take the 2 chopsticks closest to him 
 * (according to its number and the number of each chopstick) in order to eat.
 */
void
philosopher(int argc, char **argv)
{
    int left, right, first, second, mynum = 0;
    L4_Word_t me = L4_Myself().raw;
    L4_MsgTag_t tag = L4_Niltag;

    while (!libs_ready) ;
    if (argc) {
        mynum = atoi(argv[0]);
    } else {
        printf("(Philosopher 0x%lx) Error: Argument(s) missing!\n", me);
        L4_Set_MsgTag(L4_Niltag);
        L4_Send(dp_main);
        L4_Set_Label(&tag, 0xdead);
        L4_Set_MsgTag(tag);
        L4_Call(dp_main);
    }

    // Have to take chopsticks according to "my number"
    left = mynum;
    if (chopstick[mynum + 1]) {
        right = mynum + 1;
    } else {
        right = 0;
    }
    // This should allow to avoid deadlock when trying to grab the chopsticks.
    first = left < right ? left : right;
    second = first == left ? right : left;
    //printf("Philosopher %d: %lx, managed by %lx\n", mynum, me, dp_main.raw);
    //printf("Philosopher %d: chopsticks %d and %d\n", mynum, left, right);
    L4_Set_MsgTag(L4_Niltag);
    L4_Send(dp_main);
    while (meal_served == 0) ;
    okl4_libmutex_count_lock(chopstick[first]);
    //printf("Philosopher %d/%lx holds chopstick %d/%lx\n", mynum, me, first, chopstick[first]);
    okl4_libmutex_count_lock(chopstick[second]);
    //printf("Philosopher %d/%lx holds chopstick %d/%lx\n", mynum, me, second, chopstick[second]);
    //printf("Philosopher %d/%lx is eating\n", mynum, me);

    okl4_libmutex_count_unlock(chopstick[second]);
    okl4_libmutex_count_unlock(chopstick[first]);
    //printf("Philosopher %d: %lx/%lx finished eating\n", mynum, me, dp_main.raw);

    L4_Set_Label(&tag, 0xfed);
    L4_Set_MsgTag(tag);
    L4_Send(dp_main);
    L4_Send(L4_Myself());
}
Example #2
0
static void
ping_thread_simulated (void)
{
    volatile L4_Word_t x;
    /* Wait for pong thread to come up */
    L4_Msg_t msg;
    L4_MsgTag_t tag;
    for (int i=0; i < num_iterations; i++) {
        L4_Fpage_t ppage = L4_Fpage((L4_Word_t)&fault_area[i*1024], 4096);

        L4_Set_Rights(&ppage, L4_FullyAccessible);
        /* accept fpages */
        L4_Accept(L4_UntypedWordsAcceptor);

        /* send it to our pager */
        L4_MsgClear(&msg);
        L4_MsgAppendWord(&msg, (L4_Word_t) ppage.raw);
        L4_MsgAppendWord(&msg, (L4_Word_t) 0);
        L4_Set_Label(&msg.tag, L4_PAGEFAULT);
        L4_MsgLoad(&msg);

        /* make the call */
        tag = L4_Call(pager_tid);
        x = fault_area[i*1024];
    }

    /* Tell master that we're finished */
    L4_Set_MsgTag (L4_Niltag);
    L4_Send (master_tid);

    for (;;)
        L4_WaitForever();

    /* NOTREACHED */
}
Example #3
0
static void
waiting_notify_thread(void *arg)
{
    L4_Word_t notifybits;
    L4_MsgTag_t tag;
    L4_Word_t mask;

    tag = L4_Receive(main_tid);
    notifybits = L4_Label(tag);
    L4_Set_NotifyMask(notifybits);
    L4_Accept(L4_NotifyMsgAcceptor);
    L4_LoadMR(0, 0);
    L4_Send(main_tid);
    tag = L4_WaitNotify(&mask);
    if (L4_IpcFailed(tag)) {
        FAILED();
        return;
    }

    L4_Set_Label(&tag, notifybits);
    L4_Set_MsgTag(tag);
    L4_Call(main_tid);

    while (1) { }
}
Example #4
0
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;
}
Example #5
0
static void
ipc_test(struct bench_test *test, int args[])
{
    L4_ThreadId_t  tid;

    /* Send "begin" message to notify pager to startup both threads */
    L4_MsgTag_t tag = L4_Niltag;
    L4_Set_Label(&tag, START_LABEL);
    L4_Set_MsgTag(tag);
    L4_Send(pager_tid);
    L4_Wait(&tid);
}
Example #6
0
File: mutex.c Project: BruceYi/okl4
END_TEST

/*
\begin{test}{MUTEX0402}
  \TestDescription{Verify L4_TryLock on a locked mutex}
  \TestFunctionalityTested{\Func{L4\_TryLock}}
  \TestImplementationProcess{
    \begin{enumerate}
        \item Call \Func{L4\_CreateMutex} and check it returns successfully.
        \item Call \Func{L4\_Lock} and check it returns successfully.
        \item Create a thread.
        \item Thread calls L4\_TryLock on the held mutex.
        \item Check it returns an error.
    \end{enumerate}
  }
  \TestPassStatus{pass}
  \TestImplementationStatus{Implemented}
  \TestRegressionStatus{In regression test suite}
\end{test}
*/
START_TEST(MUTEX0402)
{
    L4_ThreadId_t try_lock_thread;
    L4_MsgTag_t tag;
    L4_Word_t res;

    res = okl4_kmutexid_allocany(mutexid_pool, &m);
    fail_unless(res == OKL4_OK, "Failed to allocate any mutex id.");
    res = L4_CreateMutex(m);
    fail_unless(res == 1, "L4_CreateMutex() failed");
    res = L4_Lock(m);
    fail_unless(res == 1, "L4_Lock() failed");
    try_lock_thread = createThread(lock_mutex_thread);
    L4_Set_Label(&tag, 0xb);
    L4_Set_MsgTag(tag);
    L4_Call(try_lock_thread);

    L4_Unlock(m);
    L4_DeleteMutex(m);
    okl4_kmutexid_free(mutexid_pool, m);
}
/*
 * Intermediate thread 1 has priority in between highest and medium thread.
 * Intermediate thread 2 has priority in between medium and lowest thread.
 * They set their flag each time they run during the PI test.
 */
void
mixed_pi_intermediate(int argc, char **argv)
{
    int num = 0;
    L4_ThreadId_t any_thread;
    L4_MsgTag_t tag = L4_Niltag;

    while (!libs_ready) ;
    if (argc) {
        num = atoi(argv[0]);
    } else {
        printf("(%s Intermediate Thread) Error: Argument(s) missing!\n", test_name);
        L4_Set_Label(&tag, 0xdead);
        L4_Set_MsgTag(tag);
        L4_Call(pi_main);
    }
    // Initialisation
    if (num == 1) {
        L4_Wait(&any_thread);
        L4_LoadMR(0, 0);
        L4_Send(pi_main);
    } else if (num == 2) {
        L4_Wait(&any_thread);
        while (L4_IsNilThread(medium2_prio_thread)) ;
        L4_LoadMR(0, 0);
        L4_Send(medium2_prio_thread);
    }
    L4_Yield();

    // Thread is now ready to set the flag the next time it is run.
    while(1) {
        if (num == 1) {
            flag1 = 1;
        } else if (num == 2) {
            flag3 = 1;
        }
        L4_LoadMR(0, 0);
        L4_Send(high_prio_thread);
    }
}
Example #8
0
File: mutex.c Project: BruceYi/okl4
END_TEST

/*
\begin{test}{MUTEX0301}
  \TestDescription{Verify unprivileged thread can not delete mutex}
  \TestFunctionalityTested{\Func{L4\_DeleteMutex}}
  \TestImplementationProcess{
    \begin{enumerate}
        \item Create a mutex.
        \item Create unprivileged thread.
        \item Unprivileged thread call \Func{L4\_DeleteMutex} with the created mutex.
        \item Checks \Func{L4\_DeleteMutex} returns an error.
    \end{enumerate}
  }
  \TestPassStatus{pass}
  \TestImplementationStatus{Implemented}
  \TestRegressionStatus{In regression test suite}
\end{test}
*/
START_TEST(MUTEX0301)
{
    L4_ThreadId_t unpriv_thread;
    L4_MsgTag_t tag;
    L4_Word_t res;

    res = okl4_kmutexid_allocany(mutexid_pool, &m);
    fail_unless(res == OKL4_OK, "Failed to allocate any mutex id.");
    res = L4_CreateMutex(m);
    fail_unless(res == 1, "L4_CreateMutex() failed");
    unpriv_thread = createThreadInSpace(L4_nilspace, create_delete_mutex_thread);
    L4_Set_Label(&tag, 0xd);
    L4_Set_MsgTag(tag);
    L4_Call(unpriv_thread);

    res = L4_DeleteMutex(m);
    fail_unless(res == 1, "L4_DeleteMutex() failed");
    okl4_kmutexid_free(mutexid_pool, m);
    deleteThread(unpriv_thread);
}
Example #9
0
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;
}