Fixes to VM8086 handler to remove operand size errors.
authorJohn Hodge <[email protected]>
Fri, 23 Apr 2010 11:53:02 +0000 (19:53 +0800)
committerJohn Hodge <[email protected]>
Fri, 23 Apr 2010 11:53:02 +0000 (19:53 +0800)
18 files changed:
Kernel/Makefile.BuildNum
Kernel/arch/x86/Makefile
Kernel/arch/x86/desctab.asm
Kernel/arch/x86/kpanic.c
Kernel/arch/x86/mm_virt.c
Kernel/arch/x86/proc.c
Kernel/arch/x86/start.asm
Kernel/arch/x86/vm8086.c
Kernel/include/syscalls.h
Kernel/include/syscalls.inc.asm
Kernel/include/threads.h
Kernel/syscalls.c
Kernel/syscalls.lst
Kernel/threads.c
Modules/Display/VESA/main.c
Usermode/Libraries/libacess.so_src/core.asm
Usermode/Libraries/libc.so_src/stub.c
Usermode/include/sys/sys.h

index 620c1bb..ce0a54c 100644 (file)
@@ -1 +1 @@
-BUILD_NUM = 1982
+BUILD_NUM = 2027
index c52e369..0c44288 100644 (file)
@@ -31,5 +31,5 @@ endif
 
 A_OBJ  = start.ao main.o lib.o desctab.ao errors.o irq.o
 A_OBJ += mm_phys.o mm_virt.o
-A_OBJ += proc.o time.o vm8086.o
+A_OBJ += proc.o proc.ao time.o vm8086.o
 A_OBJ += kpanic.o
index 43bd8e4..27b7bb1 100644 (file)
@@ -190,6 +190,7 @@ DEF_SYSCALL 0xAC    ; Acess System Call
 ; IRQs
 ; - Timer
 [global Isr240]
+[extern SchedulerBase]
 Isr240:
        push 0
        jmp SchedulerBase
@@ -281,40 +282,3 @@ IRQCommon:
        popa
        add esp, 8      ; Error Code and ID
        iret
-
-; --------------
-; Task Scheduler
-; --------------
-[extern Proc_Scheduler]
-SchedulerBase:
-       pusha
-       push ds
-       push es
-       push fs
-       push gs
-       
-       mov ax, 0x10
-       mov ds, ax
-       mov es, ax
-       mov fs, ax
-       mov gs, ax
-       
-       mov eax, [esp+12*4]     ; CPU Number
-       push eax        ; Pus as argument
-       
-       call Proc_Scheduler
-       
-       add esp, 4      ; Remove Argument
-       
-       pop gs
-       pop fs
-       pop es
-       pop ds
-
-       mov dx, 0x20
-       mov al, 0x20
-       out dx, al              ; ACK IRQ
-       popa
-       add esp, 4      ; CPU ID
-       ; No Error code / int num
-       iret
index 1972fd3..798c513 100644 (file)
@@ -59,7 +59,9 @@ void KernelPanic_SetMode()
 {
         int    i;
        
-       // Some routines call this function twice, let's avoid that, shall we?
+       // This function is called by Panic(), but MM_PageFault and the
+       // CPU exception handers also call it, so let's not clear the screen
+       // twice
        if( giKP_Pos )  return ;
        
        // Restore VGA 0xB8000 text mode
index db89cc1..f2be750 100644 (file)
@@ -1013,7 +1013,7 @@ void MM_UnmapHWPages(tVAddr VAddr, Uint Number)
        
        for( j = 0; j < Number; j++ )
        {
-               MM_DerefPhys( gaPageTable[ (HW_MAP_ADDR >> 12) + i + j ] );
+               MM_DerefPhys( gaPageTable[ (HW_MAP_ADDR >> 12) + i + j ] & ~0xFFF );
                gaPageTable[ (HW_MAP_ADDR >> 12) + i + j ] = 0;
        }
        
index 6298067..e988416 100644 (file)
@@ -39,6 +39,7 @@ extern tThread        *Threads_GetNextToRun(int CPU);
 extern void    Threads_Dump();
 extern tThread *Threads_CloneTCB(Uint *Err, Uint Flags);
 extern void    Isr8(); // Double Fault
+extern void    Proc_AlterUserReturnAddr();
 
 // === PROTOTYPES ===
 void   ArchThreads_Init();
@@ -51,6 +52,7 @@ tThread       *Proc_GetCurThread();
 void   Proc_ChangeStack();
  int   Proc_Clone(Uint *Err, Uint Flags);
 void   Proc_StartProcess(Uint16 SS, Uint Stack, Uint Flags, Uint16 CS, Uint IP);
+void   Proc_CallFaultHandler(tThread *Thread);
 void   Proc_Scheduler();
 
 // === GLOBALS ===
@@ -693,6 +695,18 @@ int Proc_Demote(Uint *Err, int Dest, tRegs *Regs)
        return 0;
 }
 
+/**
+ * \brief Calls a signal handler in user mode
+ * \note Used for signals
+ */
+void Proc_CallFaultHandler(tThread *Thread)
+{
+       // Rewinds the stack and calls the user function
+       // Never returns
+       __asm__ __volatile__ ("mov %0, %%ebp;\n\tcall Proc_AlterUserReturnAddr" :: "r"(Thread->FaultHandler));
+       for(;;);
+}
+
 /**
  * \fn void Proc_Scheduler(int CPU)
  * \brief Swap current thread and clears dead threads
index d9a1e50..b98a016 100644 (file)
@@ -168,31 +168,6 @@ CallWithArgArray:
        pop ebp\r
        ret\r
 \r
-[extern Proc_Clone]\r
-[extern Threads_Exit]\r
-[global SpawnTask]\r
-SpawnTask:\r
-       ; Call Proc_Clone with Flags=0\r
-       xor eax, eax\r
-       push eax
-       push eax\r
-       call Proc_Clone\r
-       add esp, 8      ; Remove arguments from stack\r
-       \r
-       test eax, eax\r
-       jnz .parent\r
-       \r
-       ; In child, so now set up stack frame\r
-       mov ebx, [esp+4]        ; Child Function\r
-       mov edx, [esp+8]        ; Argument\r
-       ; Child\r
-       push edx        ; Argument\r
-       call ebx        ; Function\r
-       call Threads_Exit       ; Kill Thread\r
-       \r
-.parent:\r
-       ret\r
-\r
 [section .initpd]\r
 [global gaInitPageDir]\r
 [global gaInitPageTable]\r
index 8ef7453..1816eac 100644 (file)
 #define VM8086_STACK_OFS       0x0AFE
 enum eVM8086_Opcodes
 {
-       VM8086_OP_PUSHF = 0x9C,
-       VM8086_OP_POPF  = 0x9D,
-       VM8086_OP_INT_I = 0xCD,
-       VM8086_OP_IRET  = 0xCF,
-       VM8086_OP_IN_AD = 0xEC,
-       VM8086_OP_IN_ADX= 0xED
+       VM8086_OP_PUSHF   = 0x9C,
+       VM8086_OP_POPF    = 0x9D,
+       VM8086_OP_INT_I   = 0xCD,
+       VM8086_OP_IRET    = 0xCF,
+       VM8086_OP_IN_AD   = 0xEC,
+       VM8086_OP_IN_ADX  = 0xED,
+       VM8086_OP_OUT_AD  = 0xEE,
+       VM8086_OP_OUT_ADX = 0xEF
 };
 #define VM8086_PAGES_PER_INST  4
 
@@ -45,13 +47,16 @@ MODULE_DEFINE(0, 0x100, VM8086, VM8086_Install, NULL, NULL);
 tSpinlock      glVM8086_Process;
 tPID   gVM8086_WorkerPID;
 tTID   gVM8086_CallingThread;
-tVM8086        * volatile gpVM8086_State;
+tVM8086        * volatile gpVM8086_State = (void*)-1;  // Set to -1 to avoid race conditions
 
 // === FUNCTIONS ===
 int VM8086_Install(char **Arguments)
 {
        tPID    pid;    
        
+       // Lock to avoid race conditions
+       LOCK( &glVM8086_Process );
+       
        // Create BIOS Call process
        pid = Proc_Clone(NULL, CLONE_VM);
        if(pid == -1)
@@ -139,6 +144,11 @@ void VM8086_GPF(tRegs *Regs)
        if(Regs->eip == VM8086_MAGIC_IP && Regs->cs == VM8086_MAGIC_CS
        && Threads_GetPID() == gVM8086_WorkerPID)
        {
+               if( gpVM8086_State == (void*)-1 ) {
+                       Log_Log("VM8086", "Worker thread ready and waiting");
+                       RELEASE( &glVM8086_Process );   // Release lock obtained in VM8086_Install
+                       gpVM8086_State = NULL;
+               }
                if( gpVM8086_State ) {
                        gpVM8086_State->AX = Regs->eax; gpVM8086_State->CX = Regs->ecx;
                        gpVM8086_State->DX = Regs->edx; gpVM8086_State->BX = Regs->ebx;
@@ -176,7 +186,7 @@ void VM8086_GPF(tRegs *Regs)
                return ;
        }
        
-       opcode = *(Uint8*)( KERNEL_BASE + (Regs->cs*16) + (Regs->eip) );
+       opcode = *(Uint8*)( (Regs->cs*16) + (Regs->eip) );
        Regs->eip ++;
        switch(opcode)
        {
@@ -237,13 +247,13 @@ void VM8086_GPF(tRegs *Regs)
                #endif
                break;
                
-       case 0xEE:      //OUT DX, AL
+       case VM8086_OP_OUT_AD:  //OUT DX, AL
                outb(Regs->edx&0xFFFF, Regs->eax&0xFF);
                #if TRACE_EMU
                Log_Debug("VM8086", "Emulated OUT DX, AL (*0x%04x = 0x%02x)\n", Regs->edx&0xFFFF, Regs->eax&0xFF);
                #endif
                break;
-       case 0xEF:      //OUT DX, AX
+       case VM8086_OP_OUT_ADX: //OUT DX, AX
                outw(Regs->edx&0xFFFF, Regs->eax&0xFFFF);
                #if TRACE_EMU
                Log_Debug("VM8086", "Emulated OUT DX, AX (*0x%04x = 0x%04x)\n", Regs->edx&0xFFFF, Regs->eax&0xFFFF);
@@ -257,8 +267,31 @@ void VM8086_GPF(tRegs *Regs)
                break;
        
        case 0x66:
-               Log_Warning("VM8086", "Code at %04x:%04x attempted to use an operand override, ignored",
-                       Regs->cs, Regs->eip);
+               opcode = *(Uint8*)( (Regs->cs*16) + (Regs->eip&0xFFFF));
+               switch( opcode )
+               {
+               case VM8086_OP_IN_ADX:  //IN AX, DX
+                       Regs->eax = ind(Regs->edx&0xFFFF);
+                       #if TRACE_EMU
+                       Log_Debug("VM8086", "Emulated IN EAX, DX (Port 0x%x)\n", Regs->edx&0xFFFF);
+                       #endif
+                       break;
+               case VM8086_OP_OUT_ADX: //OUT DX, AX
+                       outd(Regs->edx&0xFFFF, Regs->eax);
+                       #if TRACE_EMU
+                       Log_Debug("VM8086", "Emulated OUT DX, EAX (*0x%04x = 0x%08x)\n", Regs->edx&0xFFFF, Regs->eax);
+                       #endif
+                       break;
+               default:
+                       Log_Error("VM8086", "Error - Unknown opcode 66 %02x caused a GPF at %04x:%04x",
+                               Regs->cs, Regs->eip,
+                               opcode
+                               );
+                       // Force an end to the call
+                       Regs->cs = VM8086_MAGIC_CS;
+                       Regs->eip = VM8086_MAGIC_IP;
+                       break;
+               }
                break;
        
        default:
index fb9a2ff..0007dc1 100644 (file)
@@ -9,7 +9,7 @@ enum eSyscalls {
        SYS_EXIT,       // 0 - Kill this thread
        SYS_CLONE,      // 1 - Create a new thread
        SYS_KILL,       // 2 - Send a signal
-       SYS_SIGNAL,     // 3 - Set signal Handler
+       SYS_SETFAULTHANDLER,    // 3 - Set signal Handler
        SYS_YIELD,      // 4 - Yield remainder of timestamp
        SYS_SLEEP,      // 5 - Sleep until messaged or signaled
        SYS_WAIT,       // 6 - Wait for a time or a message
@@ -63,7 +63,7 @@ enum eSyscalls {
 };
 
 static const char *cSYSCALL_NAMES[] = {
-       "SYS_EXIT","SYS_CLONE","SYS_KILL","SYS_SIGNAL","SYS_YIELD","SYS_SLEEP",
+       "SYS_EXIT","SYS_CLONE","SYS_KILL","SYS_SETFAULTHANDLER","SYS_YIELD","SYS_SLEEP",
        "SYS_WAIT","SYS_WAITTID","SYS_SETNAME","SYS_GETNAME","SYS_GETTID","SYS_GETPID",
        "SYS_SETPRI","SYS_SENDMSG","SYS_GETMSG","SYS_GETTIME","SYS_SPAWN","SYS_EXECVE",
        "SYS_LOADBIN","SYS_UNLOADBIN","SYS_LOADMOD","","","",
index a379deb..bd59af8 100644 (file)
@@ -5,7 +5,7 @@
 %define SYS_EXIT       0       ; Kill this thread
 %define SYS_CLONE      1       ; Create a new thread
 %define SYS_KILL       2       ; Send a signal
-%define SYS_SIGNAL     3       ; Set signal Handler
+%define SYS_SETFAULTHANDLER    3       ; Set signal Handler
 %define SYS_YIELD      4       ; Yield remainder of timestamp
 %define SYS_SLEEP      5       ; Sleep until messaged or signaled
 %define SYS_WAIT       6       ; Wait for a time or a message
index b55fe0e..28d669d 100644 (file)
@@ -17,11 +17,13 @@ typedef struct sMessage
 typedef struct sThread
 {
        // --- threads.c's
+       //  0
        struct sThread  *Next;  //!< Next thread in list
        tSpinlock       IsLocked;       //!< Thread's spinlock
        volatile int    Status;         //!< Thread Status
         int    RetStatus;      //!< Return Status
        
+       // 16
        Uint    TID;    //!< Thread ID
        Uint    TGID;   //!< Thread Group (Process)
        Uint    PTID;   //!< Parent Thread ID
@@ -29,19 +31,22 @@ typedef struct sThread
        char    *ThreadName;    //!< Name of thread
        
        // --- arch/proc.c's responsibility
+       // 40
        //! Kernel Stack Base
        tVAddr  KernelStack;
        
+       // 44 (x86)
        //! Memory Manager State
        tMemoryState    MemState;
        
+       // 48 (x86)
        //! State on task switch
        tTaskState      SavedState;
        
        // --- threads.c's
-        int    CurSignal;      //!< Signal currently being handled (0 for none)
-       tVAddr  SignalHandlers[NSIG];   //!< Signal Handler List
-       tTaskState      SignalState;    //!< Saved state for signal handler
+       // 60
+        int    CurFaultNum;    //!< Current fault number, 0: none
+       tVAddr  FaultHandler;   //!< Fault Handler
        
        tMsg * volatile Messages;       //!< Message Queue
        tMsg    *LastMessage;   //!< Last Message (speeds up insertion)
index 3456797..b49b4d6 100644 (file)
@@ -32,6 +32,7 @@ extern tUID   Threads_GetUID();
 extern int     Threads_SetUID(Uint *errno, tUID ID);
 extern tGID    Threads_GetGID();
 extern int     Threads_SetGID(Uint *errno, tGID ID);
+extern int     Threads_SetFaultHandler(Uint Handler);
 
 // === PROTOTYPES ===
  int   Syscall_ValidString(Uint Addr);
@@ -60,6 +61,11 @@ void SyscallHandler(tSyscallRegs *Regs)
        // -- Yield current timeslice
        case SYS_YIELD: Threads_Yield();        break;
        
+       // -- Set Error Handler
+       case SYS_SETFAULTHANDLER:
+               Threads_SetFaultHandler(Regs->Arg1);
+               break;
+       
        // -- Clone the current thread
        case SYS_CLONE:
                // Call clone system call
index c5978be..dde278c 100644 (file)
@@ -3,7 +3,7 @@
 SYS_EXIT       Kill this thread
 SYS_CLONE      Create a new thread
 SYS_KILL       Send a signal
-SYS_SIGNAL     Set signal Handler
+SYS_SETFAULTHANDLER    Set signal Handler
 SYS_YIELD      Yield remainder of timestamp
 SYS_SLEEP      Sleep until messaged or signaled
 SYS_WAIT       Wait for a time or a message
index 96a38da..f726f27 100644 (file)
@@ -22,6 +22,7 @@ extern void   ArchThreads_Init();
 extern void    Proc_Start();
 extern tThread *Proc_GetCurThread();
 extern int     Proc_Clone(Uint *Err, Uint Flags);
+extern void    Proc_CallFaultHandler(tThread *Thread);
 
 // === PROTOTYPES ===
 void   Threads_Init();
@@ -62,7 +63,7 @@ tThread       gThreadZero = {
        {0},    // Saved State
        {0},    // VM State
        
-       0, {0}, {0},    // Signal State
+       0, 0,   // Current Fault, Fault Handler
        
        NULL, NULL,     // Messages, Last Message
        DEFAULT_QUANTUM, DEFAULT_QUANTUM,       // Quantum, Remaining
@@ -201,12 +202,8 @@ tThread *Threads_CloneTCB(Uint *Err, Uint Flags)
        new->NumTickets = cur->NumTickets;
        
        // Set Signal Handlers
-       new->CurSignal = 0;
-       if(Flags & CLONE_VM)
-               memset(new->SignalHandlers, 0, sizeof(new->SignalHandlers));
-       else
-               memcpy(new->SignalHandlers, cur->SignalHandlers, sizeof(new->SignalHandlers));
-       memset(&new->SignalState, 0, sizeof(tTaskState));
+       new->CurFaultNum = 0;
+       new->FaultHandler = cur->FaultHandler;
        
        for( i = 0; i < NUM_CFG_ENTRIES; i ++ )
        {
@@ -566,57 +563,50 @@ void Threads_AddActive(tThread *Thread)
        RELEASE( &giThreadListLock );
 }
 
-#if 0
 /**
- * \fn void Threads_SetSignalHandler(int Num, void *Handler)
+ * \fn void Threads_SetSignalHandler(Uint Handler)
  * \brief Sets the signal handler for a signal
  */
-void Threads_SetSignalHandler(int Num, void *Handler)
-{
-       if(Num < 0 || Num >= NSIG)      return;
-       
-       gCurrentThread->SignalHandlers[Num] = Handler;
+void Threads_SetFaultHandler(Uint Handler)
+{      
+       Log_Log("Threads", "Threads_SetFaultHandler: Handler = %p", Handler);
+       Proc_GetCurThread()->FaultHandler = Handler;
 }
 
 /**
- * \fn void Threads_SendSignal(int TID, int Num)
- * \brief Send a signal to a thread
+ * \fn void Threads_Fault(int Num)
+ * \brief Calls a fault handler
  */
-void Threads_SendSignal(int TID, int Num)
+void Threads_Fault(int Num)
 {
-       tThread *thread = Proc_GetThread(TID);
-       void    *handler;
+       tThread *thread = Proc_GetCurThread();
+       
+       Log_Log("Threads", "Threads_Fault: thread = %p", thread);
        
        if(!thread)     return ;
        
-       handler = thread->SignalHandlers[Num];
+       Log_Log("Threads", "Threads_Fault: thread->FaultHandler = %p", thread->FaultHandler);
        
-       // Panic?
-       if(handler == SIG_ERR) {
-               Proc_Kill(TID);
+       switch(thread->FaultHandler)
+       {
+       case 0: // Panic?
+               Threads_Kill(thread, -1);
+               HALT();
                return ;
-       }
-       // Dump Core?
-       if(handler == -2) {
-               Proc_Kill(TID);
+       case 1: // Dump Core?
+               Threads_Kill(thread, -1);
+               HALT();
                return ;
        }
-       // Ignore?
-       if(handler == -2)       return;
-       
-       // Check the type and handle if the thread is already in a signal
-       if(thread->CurSignal != 0) {
-               if(Num < _SIGTYPE_FATAL)
-                       Proc_Kill(TID);
-               } else {
-                       while(thread->CurSignal != 0)
-                               Proc_Yield();
-               }
+       
+       // Double Fault? Oh, F**k
+       if(thread->CurFaultNum != 0) {
+               Threads_Kill(thread, -1);       // For now, just kill
+               HALT();
        }
        
-       //TODO: 
+       Proc_CallFaultHandler(thread);
 }
-#endif
 
 // --- Process Structure Access Functions ---
 tPID Threads_GetPID()
@@ -747,9 +737,9 @@ tThread *Threads_GetNextToRun(int CPU)
  */
 void Threads_SegFault(tVAddr Addr)
 {
-       //Threads_SendSignal( Proc_GetCurThread()->TID, SIGSEGV );
        Warning("Thread #%i committed a segfault at address %p", Proc_GetCurThread()->TID, Addr);
-       Threads_Exit( 0, -1 );
+       Threads_Fault( 1 );
+       //Threads_Exit( 0, -1 );
 }
 
 // === EXPORTS ===
index e625c57..c2217e4 100644 (file)
@@ -68,7 +68,7 @@ int Vesa_Install(char **Arguments)
        // Call Interrupt\r
        VM8086_Int(gpVesa_BiosState, 0x10);\r
        if(gpVesa_BiosState->AX != 0x004F) {\r
-               Log_Warning("VESA", "Vesa_Install - VESA/VBE Unsupported (AX = 0x%x)\n", gpVesa_BiosState->AX);\r
+               Log_Warning("VESA", "Vesa_Install - VESA/VBE Unsupported (AX = 0x%x)", gpVesa_BiosState->AX);\r
                return MODULE_ERR_NOTNEEDED;\r
        }\r
        \r
@@ -211,7 +211,8 @@ Uint64 Vesa_Write(tVFS_Node *Node, Uint64 Offset, Uint64 Length, void *Buffer)
                {\r
                tVT_Char        *chars = Buffer;\r
                 int    pitch = gVesa_Modes[giVesaCurrentMode].width;\r
-                int    widthInChars;\r
+                int    widthInChars = gVesa_Modes[giVesaCurrentMode].width/giVT_CharWidth;\r
+                int    heightInChars = gVesa_Modes[giVesaCurrentMode].height/giVT_CharHeight;\r
                 int    x, y;\r
                Uint32  *dest = (void*)gpVesa_Framebuffer;\r
                 int    i;\r
@@ -220,7 +221,6 @@ Uint64 Vesa_Write(tVFS_Node *Node, Uint64 Offset, Uint64 Length, void *Buffer)
                Offset /= sizeof(tVT_Char);\r
                \r
                LOG("gVesa_Modes[%i].width = %i", giVesaCurrentMode, gVesa_Modes[giVesaCurrentMode].width);\r
-               widthInChars = gVesa_Modes[giVesaCurrentMode].width/giVT_CharWidth;\r
                x = Offset % widthInChars;\r
                y = Offset / widthInChars;\r
                LOG("(x,y) = (%i,%i) = [%i,%i]", x, y, x * giVT_CharWidth, y * giVT_CharHeight * pitch);\r
@@ -232,11 +232,16 @@ Uint64 Vesa_Write(tVFS_Node *Node, Uint64 Offset, Uint64 Length, void *Buffer)
                        );\r
                \r
                // Sanity Check\r
-               if(y > gVesa_Modes[giVesaCurrentMode].height/giVT_CharHeight) {\r
+               if(y > heightInChars) {\r
                        LEAVE('i', 0);\r
                        return 0;\r
                }\r
                \r
+               if( Offset + Length > heightInChars*widthInChars ) {\r
+                       Length = heightInChars*widthInChars - Offset;\r
+                       Log_Notice("VESA", "Clipping write size to %i characters", (int)Length);\r
+               }\r
+               \r
                dest += y * giVT_CharHeight * pitch;\r
                dest += x * giVT_CharWidth;\r
                \r
@@ -251,7 +256,6 @@ Uint64 Vesa_Write(tVFS_Node *Node, Uint64 Offset, Uint64 Length, void *Buffer)
                                VT_Colour12to24(chars->FGCol)\r
                                );\r
                        \r
-                       \r
                        chars ++;\r
                        x ++;\r
                        if( x >= widthInChars ) {\r
@@ -301,6 +305,7 @@ Uint64 Vesa_Write(tVFS_Node *Node, Uint64 Offset, Uint64 Length, void *Buffer)
 int Vesa_Ioctl(tVFS_Node *Node, int ID, void *Data)\r
 {\r
         int    ret;\r
+       //Log_Debug("VESA", "Vesa_Ioctl: (Node=%p, ID=%i, Data=%p)", Node, ID, Data);\r
        switch(ID)\r
        {\r
        case DRV_IOCTL_TYPE:    return DRV_TYPE_VIDEO;\r
@@ -324,6 +329,9 @@ int Vesa_Ioctl(tVFS_Node *Node, int ID, void *Data)
                }\r
                return ret;\r
        \r
+       case VIDEO_IOCTL_SETCURSOR:     // Set cursor position\r
+               return 0;\r
+       \r
        case VIDEO_IOCTL_REQLFB:        // Request Linear Framebuffer\r
                return 0;\r
        }\r
index ef5b123..e097d8c 100644 (file)
@@ -18,7 +18,6 @@ SoMain:
 SYSCALL1       _exit, SYS_EXIT
 SYSCALL2       clone, SYS_CLONE
 SYSCALL2       kill, SYS_KILL
-SYSCALL2       signal, SYS_SIGNAL
 SYSCALL0       yield, SYS_YIELD
 SYSCALL0       sleep, SYS_SLEEP
 SYSCALL1       wait, SYS_WAIT
@@ -44,5 +43,6 @@ SYSCALL3      SysSpawn, SYS_SPAWN
 SYSCALL3       execve, SYS_EXECVE
 SYSCALL2       SysLoadBin, SYS_LOADBIN
 
+SYSCALL1       _SysSetFaultHandler, SYS_SETFAULTHANDLER
 
 SYSCALL6       _SysDebug, 0x100
index 9f629ba..55f4ca6 100644 (file)
@@ -3,6 +3,8 @@
  */\r
 #include "stdio_int.h"\r
 #include "lib.h"\r
+#include <stdio.h>\r
+#include <sys/sys.h>\r
 \r
 #define USE_CPUID      0\r
 \r
@@ -10,6 +12,7 @@
 #if USE_CPUID\r
 static void    cpuid(uint32_t Num, uint32_t *EAX, uint32_t *EBX, uint32_t *EDX, uint32_t *ECX);\r
 #endif\r
+void   ErrorHandler(int Fault);\r
 \r
 // === GLOBALS ===\r
 extern char **_envp;\r
@@ -53,9 +56,15 @@ int SoMain(unsigned int BaseAddress, int argc, char **argv, char **envp)
        }\r
        #endif\r
        \r
+       _SysSetFaultHandler(ErrorHandler);\r
+       \r
        return 1;\r
 }\r
 \r
+void ErrorHandler(int Fault)\r
+{\r
+       fprintf(stderr, "Fault = %i\n", Fault);\r
+}\r
 \r
 #if USE_CPUID\r
 /**\r
index 7ddf583..105d573 100644 (file)
@@ -36,3 +36,5 @@ extern int    getpid();       // Get Process ID
 extern int     sendmsg(int dest, unsigned int *Data);\r
 extern int     pollmsg(int *src, unsigned int *Data);\r
 extern int     getmsg(int *src, unsigned int *Data);\r
+\r
+extern int     _SysSetFaultHandler(void (*Handler)(int));\r

UCC git Repository :: git.ucc.asn.au