jackiefzj
驱动牛犊
驱动牛犊
  • 注册日期2004-10-28
  • 最后登录2024-03-01
  • 粉丝0
  • 关注0
  • 积分495分
  • 威望135点
  • 贡献值0点
  • 好评度58点
  • 原创分0分
  • 专家分0分
  • 社区居民
阅读:1778回复:3

怎么在驱动里实现U盘的re-plug?

楼主#
更多 发布于:2008-05-29 11:51
希望对已经插入的U盘进行re-plug,或者相当于把U盘设备重启。使我的过滤驱动能不用重启就挂接上去。
DDK的src\storage\filters\addfilter中,用SetupApi可以实现这样的功能。但怎么在驱动内实现?
SetupAPI实现的原理怎么样?

以下为addfilter中的代码
/*
 * restarts the given device
 *
 * call CM_Query_And_Remove_Subtree (to unload the driver)
 * call CM_Reenumerate_DevNode on the _parent_ (to reload the driver)
 *
 * parameters:
 *   DeviceInfoSet  - The device information set which contains DeviceInfoData
 *   DeviceInfoData - Information needed to deal with the given device
 */
BOOLEAN
RestartDevice(
    IN HDEVINFO DeviceInfoSet,
    IN OUT PSP_DEVINFO_DATA DeviceInfoData
    )
{
    SP_PROPCHANGE_PARAMS params;
    SP_DEVINSTALL_PARAMS installParams;

    // for future compatibility; this will zero out the entire struct, rather
    // than just the fields which exist now
    memset(&params, 0, sizeof(SP_PROPCHANGE_PARAMS));

    // initialize the SP_CLASSINSTALL_HEADER struct at the beginning of the
    // SP_PROPCHANGE_PARAMS struct, so that SetupDiSetClassInstallParams will
    // work
    params.ClassInstallHeader.cbSize = sizeof(SP_CLASSINSTALL_HEADER);
    params.ClassInstallHeader.InstallFunction = DIF_PROPERTYCHANGE;

    // initialize SP_PROPCHANGE_PARAMS such that the device will be stopped.
    params.StateChange = DICS_STOP;
    params.Scope       = DICS_FLAG_CONFIGSPECIFIC;
    params.HwProfile   = 0; // current profile

    // prepare for the call to SetupDiCallClassInstaller (to stop the device)
    if( !SetupDiSetClassInstallParams( DeviceInfoSet,
                                       DeviceInfoData,
                                       (PSP_CLASSINSTALL_HEADER) &params,
                                       sizeof(SP_PROPCHANGE_PARAMS)
        ) )
    {
        printf("in RestartDevice(): couldn't set the install parameters!");
        printf(" error: %u\n", GetLastError());
        return (FALSE);
    }

    // stop the device
    if( !SetupDiCallClassInstaller( DIF_PROPERTYCHANGE,
                                    DeviceInfoSet,
                                    DeviceInfoData )
        )
    {
        printf("in RestartDevice(): call to class installer (STOP) failed!");
        printf(" error: %u\n", GetLastError() );
        return (FALSE);
    }

    // restarting the device
    params.StateChange = DICS_START;

    // prepare for the call to SetupDiCallClassInstaller (to stop the device)
    if( !SetupDiSetClassInstallParams( DeviceInfoSet,
                                       DeviceInfoData,
                                       (PSP_CLASSINSTALL_HEADER) &params,
                                       sizeof(SP_PROPCHANGE_PARAMS)
        ) )
    {
        printf("in RestartDevice(): couldn't set the install parameters!");
        printf(" error: %u\n", GetLastError());
        return (FALSE);
    }

    // restart the device
    if( !SetupDiCallClassInstaller( DIF_PROPERTYCHANGE,
                                    DeviceInfoSet,
                                    DeviceInfoData )
        )
    {
        printf("in RestartDevice(): call to class installer (START) failed!");
        printf(" error: %u\n", GetLastError());
        return (FALSE);
    }

    installParams.cbSize = sizeof(SP_DEVINSTALL_PARAMS);

    // same as above, the call will succeed, but we still need to check status
    if( !SetupDiGetDeviceInstallParams( DeviceInfoSet,
                                        DeviceInfoData,
                                        &installParams )
        )
    {
        printf("in RestartDevice(): couldn't get the device install params!");
        printf(" error: %u\n", GetLastError() );
        return (FALSE);
    }

    // to see if the machine needs to be rebooted
    if( installParams.Flags & DI_NEEDREBOOT )
    {
        return (FALSE);
    }

    // if we get this far, then the device has been stopped and restarted
    return (TRUE);
}
pandaforum
驱动小牛
驱动小牛
  • 注册日期2007-02-13
  • 最后登录2011-09-06
  • 粉丝0
  • 关注0
  • 积分728分
  • 威望282点
  • 贡献值1点
  • 好评度66点
  • 原创分0分
  • 专家分0分
沙发#
发布于:2008-07-01 09:26
SetupAPI的原理是用SetupDiCallClassInstaller切换设备的状态,相当于在设备管理器中,把设备禁用一下,然后再启用一下.
zjxj1988
驱动牛犊
驱动牛犊
  • 注册日期2007-03-06
  • 最后登录2009-03-20
  • 粉丝0
  • 关注0
  • 积分3分
  • 威望49点
  • 贡献值0点
  • 好评度17点
  • 原创分0分
  • 专家分0分
板凳#
发布于:2008-09-03 16:29
关注中~~
zhoujiamurong
驱动小牛
驱动小牛
  • 注册日期2006-03-20
  • 最后登录2009-05-06
  • 粉丝4
  • 关注0
  • 积分1081分
  • 威望360点
  • 贡献值0点
  • 好评度215点
  • 原创分0分
  • 专家分0分
地板#
发布于:2008-09-04 11:13
关注中...
游客

返回顶部