mirror of
https://github.com/drasko/codezero.git
synced 2026-01-11 18:33:16 +01:00
Undefined instruction handling/ipc revised, tests added, cleaned up.
This commit is contained in:
@@ -11,21 +11,17 @@
|
||||
|
||||
#include <l4/api/ipc.h>
|
||||
|
||||
/* SHMID used betweeen FS0 and BLKDEV0 servers */
|
||||
#define FS_BLKDEV_SHMID 0
|
||||
|
||||
/*** IPC Tags used between server tasks ***/
|
||||
|
||||
/*
|
||||
* Tag 0 for L4_IPC_TAG_PFAULT
|
||||
* Tag 1 for L4_IPC_TAG_UNDEF_FAULT
|
||||
*/
|
||||
|
||||
/* For ping ponging */
|
||||
#define L4_IPC_TAG_SYNC_EXTENDED 1
|
||||
#define L4_IPC_TAG_SYNC_FULL 2
|
||||
#define L4_IPC_TAG_SYNC 3
|
||||
|
||||
/* To obtain default shared page address */
|
||||
#define L4_IPC_TAG_SHPAGE 4
|
||||
|
||||
/* XXX: unused */
|
||||
#define L4_IPC_TAG_GRANT 5
|
||||
#define L4_IPC_TAG_SYNC_EXTENDED 3
|
||||
#define L4_IPC_TAG_SYNC_FULL 4
|
||||
#define L4_IPC_TAG_SYNC 5
|
||||
|
||||
/* Posix system call tags */
|
||||
#define L4_IPC_TAG_SHMGET 6
|
||||
|
||||
@@ -16,6 +16,8 @@
|
||||
#include <shpage.h>
|
||||
#include <libposix.h>
|
||||
|
||||
#if 0
|
||||
|
||||
/*
|
||||
* Shared page initialisation of posix-like tasks.
|
||||
*
|
||||
@@ -95,3 +97,4 @@ int shared_page_init(void)
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
@@ -79,6 +79,11 @@ void handle_requests(void)
|
||||
/* This has no receive phase */
|
||||
return;
|
||||
|
||||
case L4_IPC_TAG_UNDEF_FAULT:
|
||||
/* Undefined instruction fault. Ignore. */
|
||||
// printf("Undefined instruction fault caught.\n");
|
||||
ret = 0;
|
||||
break;
|
||||
case L4_IPC_TAG_PFAULT: {
|
||||
struct page *p;
|
||||
|
||||
|
||||
@@ -40,8 +40,7 @@ int main(int argc, char *argv[])
|
||||
wait_pager(pagerid);
|
||||
|
||||
printf("\n%s: Running POSIX API tests.\n", __TASKNAME__);
|
||||
|
||||
undeftest();
|
||||
|
||||
|
||||
small_io_test();
|
||||
|
||||
@@ -57,6 +56,8 @@ int main(int argc, char *argv[])
|
||||
|
||||
clonetest();
|
||||
|
||||
undeftest();
|
||||
|
||||
if (parent_of_all == getpid()) {
|
||||
ipc_full_test();
|
||||
ipc_extended_test();
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/*
|
||||
/*
|
||||
* undeftest.c:
|
||||
* Tests to see if kernel gracefully handles the undef exception
|
||||
*/
|
||||
@@ -13,17 +13,16 @@
|
||||
#include <errno.h>
|
||||
#include INC_GLUE(memory.h)
|
||||
|
||||
|
||||
int undeftest(void)
|
||||
{
|
||||
test_printf("UNDEF: Start\n");
|
||||
|
||||
|
||||
/* need a way to report FAIL case */
|
||||
__asm__ __volatile__(".word 0xf1f0feed\n\t"); /* Some pattern for easy recongition */
|
||||
|
||||
|
||||
/* If code reaches here its passed */
|
||||
printf("UNDEF TEST -- PASSED --\n");
|
||||
test_printf("UNDEF: Passed\n");
|
||||
if (getpid() == parent_of_all)
|
||||
printf("UNDEF TEST -- PASSED --\n");
|
||||
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
|
||||
/* Pagefault */
|
||||
#define L4_IPC_TAG_PFAULT 0
|
||||
#define L4_IPC_TAG_UNDEF_FAULT 1
|
||||
|
||||
#define L4_IPC_FLAGS_TYPE_MASK 0x0000000F
|
||||
#define L4_IPC_FLAGS_SHORT 0x00000000 /* Short IPC involves just primary message registers */
|
||||
|
||||
@@ -62,13 +62,13 @@ void ipc_restore_state(struct ipc_state *state)
|
||||
}
|
||||
|
||||
/* Send data fault ipc to the faulty task's pager */
|
||||
int fault_ipc_to_pager(u32 faulty_pc, u32 fsr, u32 far)
|
||||
int fault_ipc_to_pager(u32 faulty_pc, u32 fsr, u32 far, u32 ipc_tag)
|
||||
{
|
||||
int err;
|
||||
|
||||
/* mr[0] has the fault tag. The rest is the fault structure */
|
||||
u32 mr[MR_TOTAL] = {
|
||||
[MR_TAG] = L4_IPC_TAG_PFAULT,
|
||||
[MR_TAG] = ipc_tag,
|
||||
[MR_SENDER] = current->tid
|
||||
};
|
||||
|
||||
@@ -165,7 +165,8 @@ int pager_pagein_request(unsigned long addr, unsigned long size,
|
||||
/* For every page to be used by the kernel send a page-in request */
|
||||
for (int i = 0; i < npages; i++)
|
||||
if ((err = fault_ipc_to_pager(0, abort,
|
||||
addr + (i * PAGE_SIZE))) < 0)
|
||||
addr + (i * PAGE_SIZE),
|
||||
L4_IPC_TAG_PFAULT)) < 0)
|
||||
return err;
|
||||
|
||||
/* Restore ipc state */
|
||||
@@ -277,7 +278,7 @@ void data_abort_handler(u32 faulted_pc, u32 fsr, u32 far)
|
||||
goto error;
|
||||
|
||||
/* This notifies the pager */
|
||||
fault_ipc_to_pager(faulted_pc, fsr, far);
|
||||
fault_ipc_to_pager(faulted_pc, fsr, far, L4_IPC_TAG_PFAULT);
|
||||
|
||||
if (current->flags & TASK_SUSPENDING) {
|
||||
BUG_ON(current->nlocks);
|
||||
@@ -310,7 +311,7 @@ void prefetch_abort_handler(u32 faulted_pc, u32 fsr, u32 far, u32 lr)
|
||||
|
||||
if (KERN_ADDR(lr))
|
||||
goto error;
|
||||
fault_ipc_to_pager(faulted_pc, fsr, far);
|
||||
fault_ipc_to_pager(faulted_pc, fsr, far, L4_IPC_TAG_PFAULT);
|
||||
|
||||
if (current->flags & TASK_SUSPENDING) {
|
||||
BUG_ON(current->nlocks);
|
||||
@@ -336,17 +337,18 @@ error:
|
||||
|
||||
void undef_handler(u32 undef_addr, u32 spsr, u32 lr)
|
||||
{
|
||||
dprintk("Undefined instruction at address: ", undef_addr);
|
||||
printk("Undefined instruction: %d, PC: 0x%x, Mode: %s\n",
|
||||
current->tid, undef_addr,
|
||||
(spsr & ARM_MODE_MASK) == ARM_MODE_SVC ? "SVC" : "User");
|
||||
|
||||
dbg_abort("Undefined instruction @ PC: ", undef_addr);
|
||||
|
||||
//printk("Undefined instruction: tid: %d, PC: 0x%x, Mode: %s\n",
|
||||
// current->tid, undef_addr,
|
||||
// (spsr & ARM_MODE_MASK) == ARM_MODE_SVC ? "SVC" : "User");
|
||||
|
||||
if (KERN_ADDR(lr)) {
|
||||
printk("Panic: Undef in Kernel\n");
|
||||
goto error;
|
||||
}
|
||||
|
||||
fault_ipc_to_pager(undef_addr, 0, undef_addr);
|
||||
fault_ipc_to_pager(undef_addr, 0, undef_addr, L4_IPC_TAG_UNDEF_FAULT);
|
||||
|
||||
if (current->flags & TASK_SUSPENDING) {
|
||||
BUG_ON(current->nlocks);
|
||||
@@ -359,6 +361,10 @@ void undef_handler(u32 undef_addr, u32 spsr, u32 lr)
|
||||
return;
|
||||
|
||||
error:
|
||||
disable_irqs();
|
||||
dprintk("SPSR:", spsr);
|
||||
dprintk("LR:", lr);
|
||||
printascii("Kernel panic.\n");
|
||||
printascii("Halting system...\n");
|
||||
BUG();
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user