我的机器是winXP,用USB口虚拟了一个串口,连接了一个modem
正常情况下要在控制面板->电话和调制解调器 中添加一个标准33600bps调制解调器才能正常通信
现在我想自己写程序完成这个安装过程(不调用电话和调制解调器窗口)
inf文件用的是C:\WINDOWS\inf\mdmgen.inf (XP安装时用的就是这个文件)
HardwareId 是mdmgen336
虚拟串口号是COM3
主要代码是用DDK中的示例代码稍加改动完成的,网上也很容易搜到,(为了问题方便回答,再贴一遍)
请大家结合代码帮我分析一下吧
我的问题是:
1)mdmgen.inf中有所有的标准调制解调器的信息,我该如何选用我要的安装呢?是通过设备描述还是HardwareId,应该在哪儿传递这个参数呢?
2)怎样把驱动装在COM3上呢?这个参数又是在那儿传递的?
3)当程序执行到SetupDiCallClassInstaller函数(红色标注处)时正确返回了,但是查看注册表信息时只在调制解调器类{4D36E96D-E325-11CE-BFC1-08002BE10318}下添加了0000项,但是没有任何键和键值.
执行到UpdateDriverForPlugAndPlayDevices函数时,就返回了0xE000020B错误,上网查了一下,好像是不能在未注册的设备上安装驱动,也就是说上一步并未真正成功.
我在哪出错了?看了很多资料,MSDN和DDK的都看了,网上也搜了很多文章,但还是没搞懂,请高手指教一下吧.
回帖时请详细解释一下,不要再告诉我看什么了,头已经大了.除非那上有明确的解答.谢谢
篇幅所限,代码在下面
{
return DisplayError(TEXT("GetINFC
int InstallDriver(_TCHAR *InfName, _TCHAR *HardwareID)
{
WIN32_FIND_DATA FindFileData;
BOOL RebootRequired = 0; // Must be cleared.
_TCHAR *FName, *HWID;
FName = InfName;
HWID = HardwareID;
if (FindFirstFile(FName,&FindFileData)==INVALID_HANDLE_VALUE)
{
//_tprintf(TEXT(" File not found.\n"));
//_tprintf(TEXT("usage: install \n"));
return 2; // Install Failure
}
//
// Look to see if this device allready exists.
//
if (FindExistingDevice(HWID))
{
//
// No Need to Create a Device Node, just call our API.
//
if (!UpdateDriverForPlugAndPlayDevices(0, // No Window Handle
HWID, // Hardware ID
FName, // FileName
INSTALLFLAG_FORCE,
&RebootRequired))
{
DisplayError(TEXT("UpdateDriverForPlugAndPlayDevices"));
return 2; // Install Failure
}
}
else
{
if (GetLastError()!= ERROR_NO_MORE_ITEMS)
{
//
// An unknown failure from FindExistingDevice()
//
//_tprintf(TEXT("(IERROR_NO_MORE_ITEMS)\n"));
//_tprintf(TEXT("(Install Failure! Code = 2)\n"));
return 2; // Install Failure
}
//
// Driver Does not exist, Create and call the API.
// HardwareID must be a multi-sz string, which argv[2] is.
//
if (!InstallRootEnumeratedDriver(HWID, // HardwareID
FName, // FileName
&RebootRequired))
{
//_tprintf(TEXT("(InstallRootEnumeratedDriver Failure! Code = 2)\n"));
return 2; // Install Failure
}
}
//_tprintf(TEXT("Driver Installed successfully.\n"));
if (RebootRequired)
{
//_tprintf(TEXT("(Reboot Required)\n"));
return 1; // Install Success, reboot required.
}
return 0; // Install Success, no reboot required.
}
int RemoveDriver(_TCHAR *HardwareID)
{
HDEVINFO DeviceInfoSet;
SP_DEVINFO_DATA DeviceInfoData;
DWORD i,err;
DeviceInfoSet = SetupDiGetClassDevs(NULL, // All Classes
0,
0,
DIGCF_ALLCLASSES | DIGCF_PRESENT ); // All devices present on system
if (DeviceInfoSet == INVALID_HANDLE_VALUE)
{
DisplayError(TEXT("GetClassDevs(All Present Devices)"));
return 1;
}
//
// Enumerate through all Devices.
//
DeviceInfoData.cbSize = sizeof(SP_DEVINFO_DATA);
for (i=0;SetupDiEnumDeviceInfo(DeviceInfoSet,i,&DeviceInfoData);i++)
{
DWORD DataT;
LPTSTR p,buffer = NULL;
DWORD buffersize = 0;
//
// We won't know the size of the HardwareID buffer until we call
// this function. So call it with a null to begin with, and then
// use the required buffer size to Alloc the nessicary space.
// Keep calling we have success or an unknown failure.
//
while (!SetupDiGetDeviceRegistryProperty(
DeviceInfoSet,
&DeviceInfoData,
SPDRP_HARDWAREID,
&DataT,
(PBYTE)buffer,
buffersize,
&buffersize))
{
if (GetLastError() == ERROR_INVALID_DATA)
{
//
// May be a Legacy Device with no HardwareID. Continue.
//
break;
}
else if (GetLastError() == ERROR_INSUFFICIENT_BUFFER)
{
//
// We need to change the buffer size.
//
if (buffer)
LocalFree(buffer);
buffer = (char *)LocalAlloc(LPTR,buffersize);
}
else
{
//
// Unknown Failure.
//
DisplayError(TEXT("GetDeviceRegistryProperty"));
goto cleanup_DeviceInfo;
}
}
if (GetLastError() == ERROR_INVALID_DATA)
continue;
//
// Compare each entry in the buffer multi-sz list with our HardwareID.
//
for (p=buffer;*p&&(p<&buffer[buffersize]);p+=lstrlen(p)+sizeof(TCHAR))
{
//_tprintf(TEXT("Compare device ID: [%s]\n"),p);
if (!_tcscmp(HardwareID,p))
{
//_tprintf(TEXT("Found! [%s]\n"),p);
//
// Worker function to remove device.
//
if (!SetupDiCallClassInstaller(DIF_REMOVE,
DeviceInfoSet,
&DeviceInfoData))
{
DisplayError(TEXT("CallClassInstaller(REMOVE)"));
}
break;
}
}
if (buffer) LocalFree(buffer);
}
if ((GetLastError()!=NO_ERROR)&&(GetLastError()!=ERROR_NO_MORE_ITEMS))
{
DisplayError(TEXT("EnumDeviceInfo"));
}
//
// Cleanup.
//
cleanup_DeviceInfo:
err = GetLastError();
SetupDiDestroyDeviceInfoList(DeviceInfoSet);
return err;
}
{4D36E96D-E325-11CE-BFC1-08002BE10318}
请大家回答3楼的问题就好了
感觉应该离成功不远了,请高手们点拨一下
赶快完成了,五一好放假回家啊
谢谢了!
我就是想用上面的代码完成一个驱动程序的安装过程
虽然安装的是XP提供的一个标准的虚拟调制解调器
但是安装过程应该和安装一个真实的设备一样
先要把设备连到系统上,即注册到系统中,系统得到这个设备的硬件ID
然后选择相应的inf文件进行安装
我现在应该就是卡在没有成功注册设备,就相当于设备根本没有成功连到系统中
我的代码还缺什么步骤或者什么参数不对呢?迷惑啊
请大家快来帮忙看看吧
不知道楼主解决了没有?我想在也想做这方面的东西,请教一下安装的时候,你的Infname是指WINDOWS的mdmgen.inf?HARDWAREID就是输入gen336还是其他??
谢谢
楼主帮下忙啊,我也遇到和你一样的问题,能教下小弟不,
邮箱guoleimail2003@163.com
好不容易找到本帖子,不知道最近这个问题,大家有什么新的进展。我也想做这种程序。
我也有同样的问题
不过我不太理解硬件ID是怎么确定的,我想自动安装ramdisk驱动,但他的硬件ID是什么呢?
我调用SetupDiCallClassInstaller一直返回失败,
注册表中HardwareID的值是字符串,而不是二进制数
请问有无用VISTA或server 2K8的朋友,能否将[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Class\{4D36E96D-E325-11CE-BFC1-08002BE10318}] 信息导出后mail to : banny18@163.com 不胜感谢!
这个问题我也在做,也是搞不清楚。希望有高人指点一下。或者加我的QQ308692420一起探讨这个问题。