前几天学习了wince流驱动的一些知识,总结如下。本人菜鸟,如有错误还望大家不吝赐教
内容主要分三部分:
一、用vs2005生成流驱动所需的动态链接库(.dll文件),生成注册表文件(.reg文件)
二、用vs2005建立用于动态加载&卸载驱动的程序
三、用vs2005生成驱动调试程序
接下来是详细流程
一、用vs2005生成流驱动所需的动态链接库(.dll文件),生成注册表文件(.reg文件)
我用的板子是mini2440,按照开发板提供的说明书安装了wince6.0。我要做的流驱动很简单,就是在调试时能产生一些调试信息。
首先用vs2005新建一个Win32智能设备项目(如下图),输入项目名称。
点确定,出现下面界面,再点下一步
选择平台(如下)我选Mini2440,下一步
注意:应用程序类型选DLL,如有需要可以勾上空项目。到此,项目成功建立。
接下来删除String.cpp中全部代码,添加如下代码:
#include "stdafx.h"
#include "tchar.h"
HANDLE g_hInstance;
#define BUFSIZE 256
WCHAR achBuffer[BUFSIZE];
static AFX_EXTENSION_MODULE StringDLL = { NULL, NULL };
BOOL WINAPI DllEntryPoint(HANDLE hinstDLL, DWORD dwReason, LPVOID lpReserved)
{
switch(dwReason)
{
case DLL_PROCESS_ATTACH:
g_hInstance = hinstDLL;
RETAILMSG(1,(TEXT("STRINGS: DLL_PROCESS_ATTACH\n")));
return TRUE;
case DLL_THREAD_ATTACH:
RETAILMSG(1,(TEXT("STRINGS: DLL_THREAD_ATTACH\n")));
break;
case DLL_THREAD_DETACH:
RETAILMSG(1,(TEXT("STRINGS: DLL_THREAD_DETACH\n")));
break;
case DLL_PROCESS_DETACH:
RETAILMSG(1,(TEXT("STRINGS: DLL_PROCESS_DETACH\n")));
break;
#ifdef UNDER_CE
case DLL_PROCESS_EXITING:
RETAILMSG(1,(TEXT("STRINGS: DLL_PROCESS_EXITING\n")));
break;
case DLL_SYSTEM_STARTED:
RETAILMSG(1,(TEXT("STRINGS: DLL_SYSTEM_STARTED\n")));
break;
#endif
}
return TRUE;
}
BOOL STR_Close(DWORD hOpenContext)
{
BOOL bRet = TRUE;
RETAILMSG(1,(TEXT("STRINGS: STR_Close\n")));
return bRet;
}
BOOL STR_Deinit(DWORD hDeviceContext)
{
BOOL bRet = TRUE;
RETAILMSG(1,(TEXT("STRINGS: STR_Deinit\n")));
return bRet;
}
DWORD STR_Init(DWORD dwContext)
{
DWORD dwRet = 0;
RETAILMSG(1,(TEXT("STRINGS: STR_Init\n")));
// Initialize buffer to zero.
memset (achBuffer, 0, BUFSIZE * sizeof(WCHAR));
// Set return value to non-zero.
dwRet = 1;
return dwRet;
}
BOOL STR_IOControl(DWORD hOpenContext,
DWORD dwCode,
PBYTE pBufIn,
DWORD dwLenIn,
PBYTE pBufOut,
DWORD dwLenOut,
PDWORD pdwActualOut)
{
BOOL bRet = TRUE;
RETAILMSG(1,(TEXT("STRINGS: STR_IOControl\n")));
return bRet;
}
DWORD STR_Open(DWORD hDeviceContext, DWORD AccessCode, DWORD ShareMode)
{
DWORD dwRet = 0;
RETAILMSG(1,(TEXT("STRINGS: STR_Open\n")));
dwRet = 1; // Have to make non-zero for this call to succeed.
return dwRet;
}
void STR_PowerDown(DWORD hDeviceContext)
{
RETAILMSG(1,(TEXT("STRINGS: STR_PowerDown\n")));
}
void STR_PowerUp(DWORD hDeviceContext)
{
RETAILMSG(1,(TEXT("STRINGS: STR_PowerUp\n")));
}
DWORD STR_Read(DWORD hOpenContext, LPVOID pBuffer, DWORD Count)
{
DWORD dwRet = 0;
RETAILMSG(1,(TEXT("STRINGS: STR_Read\n")));
// Copy the smaller of buffer size or string size.
DWORD cbBuffer = wcslen(achBuffer);
dwRet = min(cbBuffer, Count);
wcsncpy((LPWSTR)pBuffer, achBuffer, dwRet);
// Return number of bytes read.
return dwRet;
}
DWORD STR_Seek(DWORD hOpenContext, long Amount, DWORD Type)
{
DWORD dwRet = 0;
RETAILMSG(1,(TEXT("STRINGS: STR_Seek\n")));
return dwRet;
}
DWORD STR_Write(DWORD hOpenContext, LPCVOID pSourceBytes, DWORD NumberOfBytes)
{
DWORD dwRet = 0;
RETAILMSG(1,(TEXT("STRINGS: STR_Write\n")));
// Copy the smaller of buffer size or number of bytes they send us.
dwRet = min(BUFSIZE, NumberOfBytes);
wcsncpy(achBuffer, (LPWSTR)pSourceBytes, dwRet);
// Return number of bytes written.
return dwRet;
}
接下来新建String.def文件,并将其加入解决方案。具体方法请参考下图
然后,将String.def里的内容修改如下修改为如下
LIBRARY "String"
EXPORTS
STR_Init
STR_Deinit
STR_Open
STR_Close
STR_Read
STR_Write
STR_Seek
STR_IOControl
STR_PowerDown
STR_PowerUp
这样就可以编译了,不过之前别忘了在/项目/String属性的linker/input里加入模块定义文件“.\String.def”(如下图所示)
编译完后,生成String.dll文件
接下来建立注册表文件String.reg:
[HKEY_LOCAL_MACHINE\Drivers\BuiltIn\String]
"Index"=dword:1
"Prefix"="STR"
"Dll"="String.dll"
"Order"=dword:0
至此,在上位机所做的工作完成。
将String.dll与String.reg拷贝到wince系统的ARM里,将注册表导入ARM系统,重启ARM,流驱动就能自动加载了