⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ntdrivercode.txt

📁 一个内核驱动的源代码,做内核开发的不错的参考程序
💻 TXT
📖 第 1 页 / 共 4 页
字号:
	// 初始化打kerenl事件
    {
        KeResetEvent( pDevEx->StopEvent ) ;
    }
	Status = STATUS_SUCCESS ;

    return Status ;
}

NTSTATUS HZStartEngine(PDEVICE_EXTENSION pDevEx)
{
    UINT32    dwOneLineBytes = 0 ;
    NTSTATUS  Status ;

	pDevEx->dwKernelError = NORMAL;
	pDevEx->dwSramNumCounter = 0;
	pDevEx->bIsCheckLineTooLong = FALSE;
	pDevEx->bIsScannerStart = FALSE;
	pDevEx->ISRTestSpeed.LowPart = 0;
	pDevEx->ISRTestSpeed.HighPart = 0;
	pDevEx->DataTestSpeed.LowPart = 0;
	pDevEx->DataTestSpeed.HighPart = 0;

    // 清事件
    KeClearEvent(pDevEx->SramEvent) ;

    // 设置扫描一线单元数
    dwOneLineBytes = (pDevEx->dwOneLineOutputIn32Bits) << 2 ;
    SetOneLineBytes(pDevEx,(USHORT)dwOneLineBytes) ;
    
    // 启动前端的状态机
    ActiveFrontendEngine(pDevEx) ;
    
    // 检测到IDLE信号,发USE信号启动.
#ifdef TEST_SPEED
	StartEngine(pDevEx) ;
	Status = STATUS_SUCCESS ;
#else
    if ( ReadIDLE(pDevEx) )
    {
        StartEngine(pDevEx) ;
		if(IsScannerStart(pDevEx))
			pDevEx->bIsScannerStart = TRUE;//置启动标志

		Status = STATUS_SUCCESS ;
    }
    else
        Status = STATUS_UNSUCCESSFUL ;
#endif

    return Status ;
}

NTSTATUS HZStopEngine(IN PIRP pIrp,IN PDEVICE_EXTENSION pDevEx)
{
    PULONG  pIOBuffer = (PULONG) pIrp->AssociatedIrp.SystemBuffer ;
    NTSTATUS Status ;
    int     dwWaitIACKAtScan = (pDevEx->dwWaitIACKPerMiliSecond) << 16 ;
    int     i = 0 ;
    PBUFFER_NODE lpTmp = NULL ;
    
    Status = STATUS_UNSUCCESSFUL ;

    if ( *pIOBuffer == 0 )  // 正常结束,等最末块Sram空信号
    {
        for ( i = 0 ; i < dwWaitIACKAtScan ; i ++)
        {
            if ( IsAllBufferEmpty(pDevEx))// ||
//				pDevEx->bIsScannerStart == TRUE)
            {
				pDevEx->bIsScannerStart = FALSE;//清启动标志
                if ( !IsDataLate(pDevEx) )
                {
//                  BacktoDirectMode(pDevEx);
					Status = STATUS_SUCCESS ;
//					if(!IsNormalQuit(pDevEx))
//					{//异常退出
//						pIrp->IoStatus.Information = sizeof(ULONG) ;
//						*(PULONG)pIOBuffer = 2 ;
						
//						return STATUS_UNSUCCESSFUL ;
//					}
                }
                break ;
            }
        }
    }
    else                    // 打印非正常结束,重置设备
    {                       
        ResetOP(pDevEx) ;
        Status = STATUS_SUCCESS ;
    }

    pIrp->IoStatus.Information = sizeof(ULONG) ;
    *(PULONG)pIOBuffer = 0 ;
	//内存链是否为空
    lpTmp = (PBUFFER_NODE) pDevEx->lpHeadNode ;
    do {
        if ( lpTmp->NodeFlag != NODE_EMPTY )
        {
            *(PULONG)pIOBuffer = 1 ;
            break ;
        }
        lpTmp = lpTmp->lpNextNode ;
    } while ( lpTmp != (PBUFFER_NODE)pDevEx->lpHeadNode ) ;

    return Status ;
}

BOOLEAN HZDoIo(IN OUT PVOID Context)
{
    PDEVICE_EXTENSION pDevEx = Context ;
    volatile ULONG * const lpAddress = (volatile ULONG * const)pDevEx->HZMemoryBase ;
    NTSTATUS Status = STATUS_SUCCESS ;
    PVOID    pWriteData  = NULL ;
    ULONG    WriteLength = 0 ;

#ifdef TEST_SPEED
	LARGE_INTEGER  Times1,Times2;
    KeQuerySystemTime(&Times1);
#endif
    pWriteData = pDevEx->DataAddress ;
    WriteLength= pDevEx->DataLength ;

    if ( pWriteData == NULL || WriteLength == 0 )
        Status = STATUS_UNSUCCESSFUL ;

    if( NT_SUCCESS(pDevEx->Status) && NT_SUCCESS(Status) )
    {   // 如果没有预送一块sram,那么先预送一块数据到sram
        if ( !(pDevEx->bIsPreSend) )
        {
            pDevEx->bIsPreSend = TRUE ;
            while ( WriteLength > 0 )
            {
                if ( WriteLength > 0x4000 )  // 16K 
                {
                    RtlCopyMemory((PVOID)lpAddress,pWriteData,0x4000) ;
                    KeFlushWriteBuffer() ;
                    WriteLength -= 0x4000 ;
                    (char *)pWriteData += 0x4000 ;
                }
                else
                {
                    RtlCopyMemory((PVOID)lpAddress,pWriteData,WriteLength) ;
                    KeFlushWriteBuffer() ;
                    WriteLength -= 0x4000 ;
                }

            }
            pDevEx->dwTotalSramNum -- ;
        }
        // 已经预送了一块sram,把数据送到当前的核心态 buffer
        else
        {
            RtlCopyMemory( ((PBUFFER_NODE)pDevEx->lpWriteNode)->lpBuffer,
                           pWriteData,WriteLength ) ;   // WriteLength = 512K.
            ((PBUFFER_NODE)pDevEx->lpWriteNode)->NodeFlag = NODE_FULL ;
            (PBUFFER_NODE)pDevEx->lpWriteNode = ((PBUFFER_NODE)pDevEx->lpWriteNode)->lpNextNode ;
            if ( ((PBUFFER_NODE)pDevEx->lpWriteNode)->NodeFlag == NODE_EMPTY )
                KeSetEvent(pDevEx->SramEvent,0,FALSE) ;
        }
        Status = STATUS_SUCCESS ;
    }

    if ( NT_SUCCESS(pDevEx->Status) )
        pDevEx->Status = Status ;

#ifdef TEST_SPEED
    KeQuerySystemTime(&Times2);
	pDevEx->DataTestSpeed.LowPart = pDevEx->DataTestSpeed.LowPart +
		Times2.LowPart - Times1.LowPart;
	pDevEx->DataTestSpeed.HighPart = pDevEx->DataTestSpeed.HighPart +
		Times2.HighPart - Times1.HighPart;
#endif
    return TRUE ;
}

VOID HZStartIo(IN PDEVICE_OBJECT DeviceObject,IN PIRP pIrp)
{
    PDEVICE_EXTENSION pDevEx = DeviceObject->DeviceExtension ;
    PIO_STACK_LOCATION  pIrpStack ;

    pIrpStack = IoGetCurrentIrpStackLocation(pIrp);      // Get IrpLocation

    pDevEx->DataAddress = MmGetSystemAddressForMdl( pIrp->MdlAddress ) ;
    pDevEx->DataLength  = pIrpStack->Parameters.Write.Length ;

    // Synchronize with ISR
    KeSynchronizeExecution( pDevEx->InterruptObject, HZDoIo, pDevEx ) ;

    pIrp->IoStatus.Information = 0;
	pIrp->IoStatus.Status = pDevEx->Status;
	IoStartNextPacket(DeviceObject, FALSE);
	IoCompleteRequest(pIrp, IO_NO_INCREMENT);
}


VOID HZDpcRoutine(IN PKDPC Dpc,
					IN PVOID DeferredContext,
					IN PVOID SystemArgument1,
					IN PVOID SystemArgument2)
{
    PDEVICE_OBJECT DeviceObject ;
    PDEVICE_EXTENSION pDevEx ;

    DeviceObject = DeferredContext;
    pDevEx = DeviceObject->DeviceExtension;

    KeSetEvent(pDevEx->SramEvent,0,FALSE) ;

    if ( pDevEx->dwTotalSramNum == 0 )
        KeSetEvent(pDevEx->StopEvent,0,FALSE) ;

    return ;
}


NTSTATUS CheckInterrupt(PDEVICE_EXTENSION pDevEx)
{
    NTSTATUS Status ;
    ULONG    dwPortStatus = 0 ;

    Status = STATUS_UNSUCCESSFUL ;

    if ( pDevEx->PortWasMapped )
        dwPortStatus = READ_REGISTER_ULONG((PULONG)pDevEx->AmccPortBase+AMCC_INTCSR_INDEX) ;
    else
        dwPortStatus = READ_PORT_ULONG((PULONG)pDevEx->AmccPortBase+AMCC_INTCSR_INDEX) ;

    if ( (dwPortStatus & INTERRUPT_ASSERTED) == INTERRUPT_ASSERTED )
        Status = STATUS_SUCCESS ;

    if ( NT_SUCCESS(Status) )
    {
        Status = STATUS_UNSUCCESSFUL ;
        if ( pDevEx->PortWasMapped )
            dwPortStatus = READ_REGISTER_ULONG((PULONG)pDevEx->AmccPortBase+AMCC_MBEF_INDEX) ;
        else
            dwPortStatus = READ_PORT_ULONG((PULONG)pDevEx->AmccPortBase+AMCC_MBEF_INDEX) ;
        
        if ( (dwPortStatus & AMCC_IMB4_FULL) == AMCC_IMB4_FULL )
            Status = STATUS_SUCCESS ;
    }

    return Status ;
}

void ClearInterrupt(PDEVICE_EXTENSION pDevEx)
{
    ULONG    dwPortStatus = 0 ;

    if ( pDevEx->PortWasMapped )
        dwPortStatus = READ_REGISTER_ULONG((PULONG)pDevEx->AmccPortBase+AMCC_IMB4_INDEX) ;
    else
        dwPortStatus = READ_PORT_ULONG((PULONG)pDevEx->AmccPortBase+AMCC_IMB4_INDEX) ;
    
    if ( pDevEx->PortWasMapped )
        WRITE_REGISTER_ULONG( ((PULONG)pDevEx->AmccPortBase+AMCC_INTCSR_INDEX), SELECT_INTERRUPT_SOURCE ) ;
    else
        WRITE_PORT_ULONG( ((PULONG)pDevEx->AmccPortBase+AMCC_INTCSR_INDEX), SELECT_INTERRUPT_SOURCE ) ;
}

BOOLEAN HZInterruptServiceRoutine(IN PKINTERRUPT Interrupt,
									 IN OUT PVOID Context)
{
    PDEVICE_OBJECT DeviceObject = Context ;
    PDEVICE_EXTENSION pDevEx = DeviceObject->DeviceExtension ;
    volatile ULONG * const lpAddress = (volatile ULONG * const)pDevEx->HZMemoryBase ;
    NTSTATUS  Status = STATUS_SUCCESS ;
    ULONG     Counter = 0 ;
    PVOID     pWriteData = NULL ;
    BOOLEAN   bIsSendData = FALSE ;
	
#ifdef TEST_SPEED
	LARGE_INTEGER  Times1,Times2;
    KeQuerySystemTime(&Times1);
#endif
	// 判断中断是否有效
    Status = CheckInterrupt(pDevEx) ;

    // 判断当中断发生时,sram是否为空.如果空,送核心态缓冲区数据到sram.
    if ( NT_SUCCESS(Status) )
    {
        // 检查是否线长设短
/*      if(pDevEx->dwSramNumCounter>=2)
		{
			if ( IsLineWidthTooLong(pDevEx) )
			{
				Status = STATUS_UNSUCCESSFUL ;
				pDevEx->Status = STATUS_UNSUCCESSFUL ;
				pDevEx->dwKernelError = WIDTHLONG;
			}
        }*/
		// 检查卡上SRAM缓冲区是否为空
        if ( NT_SUCCESS(Status) )
        {
			if ( !IsBufferEmpty(pDevEx) )
			{
				Status = STATUS_UNSUCCESSFUL ;
				pDevEx->Status = STATUS_UNSUCCESSFUL ;
				pDevEx->dwKernelError = SRAMEMPTY;
			}
		}
        // 检查核心态的内存链是否为空
        if ( NT_SUCCESS(Status) )
        {
            if ( ((PBUFFER_NODE)pDevEx->lpReadNode)->NodeFlag == NODE_EMPTY )
            {
                Status = STATUS_UNSUCCESSFUL ;
                pDevEx->Status = STATUS_UNSUCCESSFUL ;
				pDevEx->dwKernelError = KERNELMEMEMPTY;
            }
        }
        // 检查是否点阵迟到
        if ( NT_SUCCESS(Status) )
        {
            if ( IsDataLate(pDevEx) )
            {
                Status = STATUS_UNSUCCESSFUL ;
                pDevEx->Status = STATUS_UNSUCCESSFUL ;
				pDevEx->dwKernelError = DATALATE;
            }
        }

        // SRAM空,核心态缓冲区非空并且点阵不迟到
        if ( NT_SUCCESS(Status) )
        {
			// 512K,每次送16K,送32次
            bIsSendData = TRUE ;
            pWriteData = ((PBUFFER_NODE)pDevEx->lpReadNode)->lpBuffer ;
            for ( Counter = 0; Counter < 32; Counter++ )
            {
                RtlCopyMemory((PVOID)lpAddress,pWriteData,0x4000) ;
                KeFlushWriteBuffer() ;
                (char *)pWriteData += 0x4000 ;
            }
            // 置满标志或者最末块标志
            {
                if ( pDevEx->dwTotalSramNum == 1 )
                {
                    SetLastBlockSRAMBufferOffset(pDevEx) ;
                    SetLastBlockFullFlag(pDevEx) ;
                }
                
                pDevEx->dwTotalSramNum -- ;
				pDevEx->dwSramNumCounter ++ ;
            }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -