?? system.cpp
字號(hào):
//***********************************************************************/
// Author : Garry
// Original Date : Nov,06 2004
// Module Name : system.cpp
// Module Funciton :
// This module countains system mechanism releated objects's
// implementation..
// Including the following aspect:
// 1. Interrupt object and interrupt management code;
// 2. Timer object and timer management code;
// 3. System level parameters management coee,such as
// physical memory,system time,etc;
// 4. Other system mechanism releated objects.
//
// ************
// This file is one of the most important file of Hello China.
// ************
// Last modified Author :
// Last modified Date :
// Last modified Content :
// 1.
// 2.
// Lines number :
//***********************************************************************/
#ifndef __STDAFX_H__
#include "..\INCLUDE\StdAfx.h"
#endif
__PERF_RECORDER TimerIntPr = {
U64_ZERO,
U64_ZERO,
U64_ZERO,
U64_ZERO}; //Performance recorder object used to mesure
//the performance of timer interrupt.
//
//TimerInterruptHandler routine.
//The following routine is the most CRITICAL routine of kernel of Hello China.
//The routine does the following:
// 1. Schedule timer object;
// 2. Update the system level variables,such as dwClockTickCounter;
// 3. Schedule kernel thread(s).
//
static BOOL TimerInterruptHandler(LPVOID lpEsp,LPVOID)
{
DWORD dwPriority = 0L;
__TIMER_OBJECT* lpTimerObject = 0L;
__KERNEL_THREAD_MESSAGE Msg ;
__PRIORITY_QUEUE* lpTimerQueue = NULL;
__PRIORITY_QUEUE* lpSleepingQueue = NULL;
__KERNEL_THREAD_OBJECT* lpKernelThread = NULL;
DWORD dwFlags = 0L;
if(NULL == lpEsp) //Parameter check.
return TRUE;
if(System.dwClockTickCounter == System.dwNextTimerTick) //Should schedule timer.
{
lpTimerQueue = System.lpTimerQueue;
lpTimerObject = (__TIMER_OBJECT*)lpTimerQueue->GetHeaderElement(
(__COMMON_OBJECT*)lpTimerQueue,
&dwPriority);
if(NULL == lpTimerObject)
goto __CONTINUE_1;
dwPriority = MAX_DWORD_VALUE - dwPriority;
while(dwPriority <= System.dwNextTimerTick) //Strictly speaking,the dwPriority
//variable must EQUAL System.dw-
//NextTimerTick,but in the implement-
//ing of the current version,there
//may be some error exists,so we assume
//dwPriority equal or less than dwNext-
//TimerTic.
{
if(NULL == lpTimerObject->DirectTimerHandler) //Send a message to the kernel thread.
{
Msg.wCommand = KERNEL_MESSAGE_TIMER;
Msg.dwParam = lpTimerObject->dwTimerID;
KernelThreadManager.SendMessage(
(__COMMON_OBJECT*)lpTimerObject->lpKernelThread,
&Msg);
//PrintLine("Send a timer message to kernel thread.");
}
else
{
lpTimerObject->DirectTimerHandler(
lpTimerObject->lpHandlerParam); //Call the associated handler.
}
switch(lpTimerObject->dwTimerFlags)
{
case TIMER_FLAGS_ONCE: //Delete the timer object processed just now.
ObjectManager.DestroyObject(&ObjectManager,
(__COMMON_OBJECT*)lpTimerObject);
break;
case TIMER_FLAGS_ALWAYS: //Re-insert the timer object into timer queue.
dwPriority = lpTimerObject->dwTimeSpan;
dwPriority /= SYSTEM_TIME_SLICE;
dwPriority += System.dwClockTickCounter;
dwPriority = MAX_DWORD_VALUE - dwPriority;
lpTimerQueue->InsertIntoQueue((__COMMON_OBJECT*)lpTimerQueue,
(__COMMON_OBJECT*)lpTimerObject,
dwPriority);
break;
default:
break;
}
lpTimerObject = (__TIMER_OBJECT*)lpTimerQueue->GetHeaderElement(
(__COMMON_OBJECT*)lpTimerQueue,
&dwPriority); //Check another timer object.
if(NULL == lpTimerObject)
break;
dwPriority = MAX_DWORD_VALUE - dwPriority;
}
if(NULL == lpTimerObject) //There is no timer object in queue.
{
__ENTER_CRITICAL_SECTION(NULL,dwFlags);
System.dwNextTimerTick = 0L;
__LEAVE_CRITICAL_SECTION(NULL,dwFlags);
}
else
{
__ENTER_CRITICAL_SECTION(NULL,dwFlags);
System.dwNextTimerTick = dwPriority; //Update the next timer tick counter.
__LEAVE_CRITICAL_SECTION(NULL,dwFlags);
dwPriority = MAX_DWORD_VALUE - dwPriority;
lpTimerQueue->InsertIntoQueue((__COMMON_OBJECT*)lpTimerQueue,
(__COMMON_OBJECT*)lpTimerObject,
dwPriority);
}
}
__CONTINUE_1:
//
//The following code wakes up all kernel thread(s) whose status is SLEEPING and
//the time it(then) set is out.
//
if(System.dwClockTickCounter == KernelThreadManager.dwNextWakeupTick) //There must existes
//kernel thread(s) to
//be wake up.
{
lpSleepingQueue = KernelThreadManager.lpSleepingQueue;
lpKernelThread = (__KERNEL_THREAD_OBJECT*)lpSleepingQueue->GetHeaderElement(
(__COMMON_OBJECT*)lpSleepingQueue,
&dwPriority);
while(lpKernelThread)
{
dwPriority = MAX_DWORD_VALUE - dwPriority; //Now,dwPriority countains the tick
//counter value.
if(dwPriority > System.dwClockTickCounter)
break; //This kernel thread should not be wake up.
lpKernelThread->dwThreadStatus = KERNEL_THREAD_STATUS_READY;
KernelThreadManager.AddReadyKernelThread(
(__COMMON_OBJECT*)&KernelThreadManager,
lpKernelThread); //Insert the waked up kernel thread into ready queue.
lpKernelThread = (__KERNEL_THREAD_OBJECT*)lpSleepingQueue->GetHeaderElement(
(__COMMON_OBJECT*)lpSleepingQueue,
&dwPriority); //Check next kernel thread in sleeping queue.
}
if(NULL == lpKernelThread)
{
__ENTER_CRITICAL_SECTION(NULL,dwFlags);
KernelThreadManager.dwNextWakeupTick = 0L;
__LEAVE_CRITICAL_SECTION(NULL,dwFlags);
}
else
{
__ENTER_CRITICAL_SECTION(NULL,dwFlags);
KernelThreadManager.dwNextWakeupTick = dwPriority;
__LEAVE_CRITICAL_SECTION(NULL,dwFlags);
dwPriority = MAX_DWORD_VALUE - dwPriority;
lpSleepingQueue->InsertIntoQueue((__COMMON_OBJECT*)lpSleepingQueue,
(__COMMON_OBJECT*)lpKernelThread,
dwPriority);
}
}
goto __TERMINAL;
__TERMINAL:
__ENTER_CRITICAL_SECTION(NULL,dwFlags);
System.dwClockTickCounter ++; //Update the system clock interrupt counter.
__LEAVE_CRITICAL_SECTION(NULL,dwFlags);
//KernelThreadManager.ScheduleFromInt((__COMMON_OBJECT*)&KernelThreadManager,
// lpEsp);
return TRUE;
}
//
//The implementation of ConnectInterrupt routine of Interrupt Object.
//The routine do the following:
// 1. Insert the current object into interrupt object array(maintenanced by system object);
// 2. Set the object's data members correctly.
//
__COMMON_OBJECT* BOOL ConnectInterrupt(__COMMON_OBJECT* lpThis,
__INTERRUPT_HANDLER lpInterruptHandler,
LPVOID lpHandlerParam,
UCHAR ucVector,
UCHAR ucReserved1,
UCHAR ucReserved2,
UCHAR ucInterruptMode,
BOOL bIfShared,
DWORD dwCPUMask)
{
__INTERRUPT_OBJECT* lpInterrupt = NULL;
__INTERRUPT_OBJECT* lpObjectRoot = NULL;
__SYSTEM* lpSystem = NULL;
DWORD dwFlags = 0L;
if((NULL == lpThis) || (NULL == lpInterruptHandler)) //Parameters valid check.
return NULL;
if(ucVector >= MAX_INTERRUPT_VECTOR) //Impossible!!!
return NULL;
lpInterrupt = (__INTERRUPT_OBJECT*)
ObjectManager.CreateObject(&ObjectManager,NULL,OBJECT_TYPE_INTERRUPT);
if(NULL == lpInterrupt) //Failed to create interrupt object.
return FALSE;
if(!lpInterrupt->Initialize((__COMMON_OBJECT*)lpInterrupt)) //Failed to initialize.
return FALSE;
lpInterrupt->lpPrevInterruptObject = NULL;
lpInterrupt->lpNextInterruptObject = NULL;
lpInterrupt->InterruptHandler = lpInterruptHandler;
lpInterrupt->lpHandlerParam = lpHandlerParam;
lpInterrupt->ucVector = ucVector;
__ENTER_CRITICAL_SECTION(NULL,dwFlags);
lpObjectRoot = lpSystem->lpInterruptVector[ucVector];
if(NULL == lpObjectRoot) //If this is the first interrupt object of the vector.
{
System.lpInterruptVector[ucVector] = lpInterrupt;
}
else
{
lpInterrupt->lpNextInterruptObject = lpObjectRoot;
lpObjectRoot->lpPrevInterruptObject = lpInterrupt;
System.lpInterruptVector[ucVector] = lpInterrupt;
}
//LEAVE_CRITICAL_SECTION();
__LEAVE_CRITICAL_SECTION(NULL,dwFlags);
return (__COMMON_OBJECT*)lpInterrupt;
}
//
//The implementation of DisconnectInterrupt.
//
static VOID DisconnectInterrupt(__COMMON_OBJECT* lpThis,
__COMMON_OBJECT* lpInterrupt)
{
__INTERRUPT_OBJECT* lpIntObject = NULL;
__SYSTEM* lpSystem = NULL;
UCHAR ucVector = NULL;
DWORD dwFlags = 0L;
if((NULL == lpThis) || (NULL == lpInterrupt)) //Parameters check.
return;
lpSystem = (__SYSTEM*)lpThis;
lpIntObject = (__INTERRUPT_OBJECT*)lpInterrupt;
ucVector = lpIntObject->ucVector;
//ENTER_CRITICAL_SECTION();
__ENTER_CRITICAL_SECTION(NULL,dwFlags);
if(NULL == lpIntObject->lpPrevInterruptObject) //This is the first interrupt object.
{
lpSystem->lpInterruptVector[ucVector] = lpIntObject->lpNextInterruptObject;
if(NULL != lpIntObject->lpNextInterruptObject) //Is not the last object.
{
lpIntObject->lpNextInterruptObject->lpPrevInterruptObject = NULL;
}
}
else //This is not the first object.
{
lpIntObject->lpPrevInterruptObject->lpNextInterruptObject = lpIntObject->lpNextInterruptObject;
if(NULL != lpIntObject->lpNextInterruptObject)
{
lpIntObject->lpNextInterruptObject->lpPrevInterruptObject = lpIntObject->lpPrevInterruptObject;
}
}
//LEAVE_CRITICAL_SECTION();
__LEAVE_CRITICAL_SECTION(NULL,dwFlags);
return;
}
//
//The implementation of Initialize routine of interrupt object.
//
BOOL InterruptInitialize(__COMMON_OBJECT* lpThis)
{
__INTERRUPT_OBJECT* lpInterrupt = NULL;
if(NULL == lpThis)
return FALSE;
lpInterrupt = (__INTERRUPT_OBJECT*)lpThis;
lpInterrupt->lpPrevInterruptObject = NULL;
lpInterrupt->lpNextInterruptObject = NULL;
lpInterrupt->InterruptHandler = NULL;
lpInterrupt->lpHandlerParam = NULL;
lpInterrupt->ucVector = 0L;
return TRUE;
}
//
//The implementation of Uninitialize of interrupt object.
//This routine does nothing.
//
VOID InterruptUninitialize(__COMMON_OBJECT* lpThis)
{
return;
}
//
//The implementation of timer object.
//
BOOL TimerInitialize(__COMMON_OBJECT* lpThis) //Initializing routine of timer object.
{
__TIMER_OBJECT* lpTimer = NULL;
if(NULL == lpThis)
return FALSE;
lpTimer = (__TIMER_OBJECT*)lpThis;
lpTimer->dwTimerID = 0L;
lpTimer->dwTimeSpan = 0L;
lpTimer->lpKernelThread = NULL;
lpTimer->lpHandlerParam = NULL;
lpTimer->DirectTimerHandler = NULL;
return TRUE;
}
//
//Uninitializing routine of timer object.
//
VOID TimerUninitialize(__COMMON_OBJECT* lpThis)
{
return;
}
//-----------------------------------------------------------------------------------
//
// The implementation of system object.
//
//------------------------------------------------------------------------------------
//
//Initializing routine of system object.
//The routine do the following:
// 1. Create a priority queue,to be used as lpTimerQueue,countains the timer object;
// 2. Create an interrupt object,as TIMER interrupt object;
// 3. Initialize system level variables,such as dwPhysicalMemorySize,etc.
//
static BOOL SystemInitialize(__COMMON_OBJECT* lpThis)
{
__SYSTEM* lpSystem = NULL;
__PRIORITY_QUEUE* lpPriorityQueue = NULL;
__INTERRUPT_OBJECT* lpIntObject = NULL;
BOOL bResult = FALSE;
DWORD dwFlags = 0L;
if(NULL == lpThis)
return FALSE;
lpSystem = (__SYSTEM*)lpThis;
lpPriorityQueue = (__PRIORITY_QUEUE*)ObjectManager.CreateObject(&ObjectManager,
NULL,
OBJECT_TYPE_PRIORITY_QUEUE);
if(NULL == lpPriorityQueue) //Failed to create priority queue.
return FALSE;
if(!lpPriorityQueue->Initialize((__COMMON_OBJECT*)lpPriorityQueue)) //Failed to initialize
//priority queue.
goto __TERMINAL;
lpSystem->lpTimerQueue = lpPriorityQueue;
lpIntObject = (__INTERRUPT_OBJECT*)ObjectManager.CreateObject(
&ObjectManager,
NULL,
OBJECT_TYPE_INTERRUPT);
if(NULL == lpIntObject)
goto __TERMINAL;
bResult = lpIntObject->Initialize((__COMMON_OBJECT*)lpIntObject);
if(!bResult)
goto __TERMINAL;
lpIntObject->ucVector = INTERRUPT_VECTOR_TIMER;
lpIntObject->lpHandlerParam = NULL;
lpIntObject->InterruptHandler = TimerInterruptHandler;
?? 快捷鍵說明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號(hào)
Ctrl + =
減小字號(hào)
Ctrl + -