comment ^ ;##/***************************************************************************************************************************** ;* * ;* INTERRUPT HANDLERS * ;* * ;##\***************************************************************************************************************************** ;******************************************************************************************************************************** ;* * ;* > EXCEPTION HANDLERS * ;* * ;##\***************************************************************************************************************************** IntDivError proc mov eax,[esp][4] TestOutputVar "Divide Error at ",eax jmp $ ; mov edi,pLocalAPIC ; xor eax,eax ; mov [edi].EndOfIntReg,eax ; iretd IntDivError endp IntInvalidOpcode proc mov eax,[esp][4] TestOutputVar "Invalid Opcode Ex at ",eax jmp $ ; mov edi,pLocalAPIC ; xor eax,eax ; mov [edi].EndOfIntReg,eax ; iretd IntInvalidOpcode endp IntDeviceNotAvailable proc ;occurs on 1st FPU/MMX/SSE instruction after a task switch (could be used for saving previous state and/or loading state for this program) push eax push edi IF TESTING_MODE mov eax,[esp][4] TestOutputVar "Device Not Available Ex at ",eax ENDIF clts ;clear TS flag in CR0, so it doesn't happen again for this switch mov edi,pLocalAPIC ASSUME EDI:PTR LOCALAPICMEM xor eax,eax mov [edi].EndOfIntReg,eax pop edi pop eax iretd ASSUME EDI:NOTHING IntDeviceNotAvailable endp IntDoubleFault proc mov eax,[esp][4] TestOutputVar "Double-Fault Exception at ",eax jmp $ ; mov edi,pLocalAPIC ; xor eax,eax ; mov [edi].EndOfIntReg,eax ; iretd IntDoubleFault endp IntInvalidTSS proc mov eax,[esp][4] TestOutputVar "Invalid TSS Ex at ",eax jmp $ ; mov edi,pLocalAPIC ; xor eax,eax ; mov [edi].EndOfIntReg,eax ; iretd IntInvalidTSS endp IntSegmentNotPresent proc mov eax,[esp][4] TestOutputVar "Seg Not Present Ex at ",eax jmp $ ; mov edi,pLocalAPIC ; xor eax,eax ; mov [edi].EndOfIntReg,eax ; iretd IntSegmentNotPresent endp IntStackFault proc mov eax,[esp][4] TestOutputVar "Stack Fault at ",eax jmp $ ; mov edi,pLocalAPIC ; xor eax,eax ; mov [edi].EndOfIntReg,eax ; iretd IntStackFault endp IntProtectionFault proc mov eax,[esp][4] TestOutputVar "Protection Fault at ",eax mov eax,[esp][0] TestOutputVar " error code: ",eax jmp $ ; mov edi,pLocalAPIC ; xor eax,eax ; mov [edi].EndOfIntReg,eax ; iretd IntProtectionFault endp IntPageFault proc mov eax,[esp][4] TestOutputVar "Page Fault at ",eax mov eax,CR2 TestOutputVar " access address: ",eax jmp $ ; mov edi,pLocalAPIC ;this part will be needed in valid page fault handler for after boot ; xor eax,eax ; ; mov [edi].EndOfIntReg,eax ; ; iretd ; IntPageFault endp IntMachineCheckEx proc mov eax,[esp][4] TestOutputVar "Machine Check Ex at ",eax jmp $ ; mov edi,pLocalAPIC ; xor eax,eax ; mov [edi].EndOfIntReg,eax ; iretd IntMachineCheckEx endp IntSIMDException proc mov eax,[esp][4] TestOutputVar "SIMD Fl-Pt Ex at ",eax jmp $ ; mov edi,pLocalAPIC ; xor eax,eax ; mov [edi].EndOfIntReg,eax ; iretd IntSIMDException endp IntOtherError proc mov eax,[esp][4] TestOutputVar "Unknown Exception at ",eax jmp $ ; mov edi,pLocalAPIC ; xor eax,eax ; mov [edi].EndOfIntReg,eax ; iretd IntOtherError endp ;##/ ;##/ ^ comment ^ ;*&; 0016A0D0 <00 WaitIOStart(eax=DeviceNum) ;*&; 0016CBE0 >05 Should work for MP WaitIOStart proc push eax push ecx push edx mov edx,eax GetThreadInfoOffset ASSUME ECX:PTR THREADHANDLEINFO GetSystemAccess lock bts DeviceUseFlags,edx jc DeviceBusy shl edx,16 add edx,INST_STAT_IOUSE CommonReturn: mov eax,CurMillisecCount and [ecx][LOFFSET_HANDLE_INFO].Status,INST_STAT_CRITSEC_BIT or [ecx][LOFFSET_HANDLE_INFO].Status,edx mov [ecx][LOFFSET_HANDLE_INFO].StatusTime,eax ReleaseSystemAccess sti pop edx pop ecx pop eax ret DeviceBusy: shl edx,16 add edx,INST_STAT_IOWAIT mov eax,CurMillisecCount and [ecx][LOFFSET_HANDLE_INFO].Status,INST_STAT_CRITSEC_BIT or [ecx][LOFFSET_HANDLE_INFO].Status,edx mov [ecx][LOFFSET_HANDLE_INFO].StatusTime,eax mov eax,pSystemTSS ASSUME EAX:PTR NEILDOWSTSS mov [eax].MainTSS.rEIP,offset MainProcessRouter call far ptr SYSTEM_TASK_SELECTOR:00000000h ;will return via the saved EIP value add edx,INST_STAT_IOUSE-INST_STAT_IOWAIT jmp CommonReturn ;and only once allowed the requested device ASSUME EAX:NOTHING ASSUME ECX:NOTHING WaitIOStart endp ;*&; 0016EDF0 <00 WaitIOEnd ;*&; 0016EEF0 >05 Doesn't change status after system task, 'cause IOInts must (or IOProcessRouter) ;*&; 0016EFD0 05 IOProcessRouter must clear device busy bit when all tasks done ;*&; 0016FEF8 05 Should work for MP WaitIOEnd proc push eax push ecx GetThreadInfoOffset ASSUME ECX:PTR THREADHANDLEINFO GetSystemAccess cmp word ptr [ecx][LOFFSET_HANDLE_INFO].Status,INST_STAT_IOUSE jne DoneIOWait mov eax,pSystemTSS ASSUME EAX:PTR NEILDOWSTSS mov [eax].MainTSS.rEIP,offset MainProcessRouter call far ptr SYSTEM_TASK_SELECTOR:00000000h ;will return via the saved EIP value DoneIOWait: ReleaseSystemAccess sti pop ecx pop eax ret WaitIOEnd endp ^