zoukankan      html  css  js  c++  java
  • 如何在Windows服务程序中添加U盘插拔的消息

    研究了下这个问题,主要要在一般的windows服务程序中修改两个地方:

    一、调用RegisterServiceCtrlHandlerEx

    VOID WINAPI SvcMain( DWORD dwArgc, LPTSTR *lpszArgv )
    {
        // Register the handler function for the service.

        gSvcStatusHandle = RegisterServiceCtrlHandlerEx(
            SVCNAME,
            SvcCtrlHandler,
            NULL);

        if( !gSvcStatusHandle )
        {
            printf("Failed to register service control handler");
            return;
        }

        // These SERVICE_STATUS members remain as set here.

        gSvcStatus.dwServiceType = SERVICE_WIN32_OWN_PROCESS;
        gSvcStatus.dwServiceSpecificExitCode = 0;    

        // Report initial status to the SCM.

        ReportSvcStatus( SERVICE_START_PENDING, NO_ERROR, 3000 );

        // Perform service-specific initialization and work.

        HDEVNOTIFY hDevNotify;

        if(!DoRegisterDeviceInterface(GUID_DEVINTERFACE_VOLUME, &hDevNotify))
        {
            printf("DoRegisterDeviceInterface failed ");
            ReportSvcStatus( SERVICE_STOPPED, NO_ERROR, 0 );
            return;
        }

        SvcInit( dwArgc, lpszArgv );

        UnregisterDeviceNotification(hDevNotify);
    }

    二、注册设备响应接口

    /*
    Routine Description:
        Registers for notification of changes in the device interfaces for
        the specified interface class GUID.

    Parameters:
        InterfaceClassGuid - The interface class GUID for the device
            interfaces.

        hDevNotify - Receives the device notification handle. On failure,
            this value is NULL.

    Return Value:
        If the function succeeds, the return value is TRUE.
        If the function fails, the return value is FALSE.
    */

    BOOL DoRegisterDeviceInterface(
        GUID InterfaceClassGuid,
        HDEVNOTIFY *hDevNotify
    )

    {
        DEV_BROADCAST_DEVICEINTERFACE NotificationFilter;

        ZeroMemory( &NotificationFilter, sizeof(NotificationFilter) );
        NotificationFilter.dbcc_size =
            sizeof(DEV_BROADCAST_DEVICEINTERFACE);
        NotificationFilter.dbcc_devicetype = DBT_DEVTYP_DEVICEINTERFACE;
        NotificationFilter.dbcc_classguid = InterfaceClassGuid;

        *hDevNotify = RegisterDeviceNotification(
            gSvcStatusHandle,
            &NotificationFilter,
            DEVICE_NOTIFY_SERVICE_HANDLE
        );

        if(!*hDevNotify)
        {
            printf("RegisterDeviceNotification failed: %d ",
                    GetLastError());
            return FALSE;
        }

        return TRUE;
    }

    三、处理U盘插拔消息


    DWORD WINAPI SvcCtrlHandler(DWORD dwCtrl, DWORD dwEventType, LPVOID lpEventData, LPVOID lpContext)
    {
        // Handle the requested control code.
        switch(dwCtrl)
        {  
        case SERVICE_CONTROL_STOP:
            ReportSvcStatus(SERVICE_STOP_PENDING, NO_ERROR, 0);

            // Signal the service to stop.

            SetEvent(ghSvcStopEvent);
            
            return NO_ERROR;

        case SERVICE_CONTROL_DEVICEEVENT:
            if (DBT_DEVICEARRIVAL  == dwEventType)
            {
                FILE *fp;
                
                DEV_BROADCAST_HDR * pHdr = (DEV_BROADCAST_HDR *)lpEventData;
                PDEV_BROADCAST_DEVICEINTERFACE pDevInf;
                PDEV_BROADCAST_HANDLE pDevHnd;
                PDEV_BROADCAST_OEM pDevOem;
                PDEV_BROADCAST_PORT pDevPort;
                PDEV_BROADCAST_VOLUME pDevVolume;

                switch( pHdr->dbch_devicetype )
                {
                case DBT_DEVTYP_DEVICEINTERFACE:
                    pDevInf = (PDEV_BROADCAST_DEVICEINTERFACE)pHdr;

                    fp = fopen("C:\log.txt", "a+");
                    if (fp)
                    {
                        _ftprintf(fp, _T("%s "), pDevInf->dbcc_name);
                        fclose(fp);
                    }
                    break;
                case DBT_DEVTYP_HANDLE:
                    pDevHnd = (PDEV_BROADCAST_HANDLE)pHdr;
                    break;
                case DBT_DEVTYP_OEM:
                    pDevOem = (PDEV_BROADCAST_OEM)pHdr;
                    break;
                case DBT_DEVTYP_PORT:
                    pDevPort = (PDEV_BROADCAST_PORT)pHdr;
                    break;
                case DBT_DEVTYP_VOLUME:
                    pDevVolume = (PDEV_BROADCAST_VOLUME)pHdr;
                    break;
                }
            }
            break;

        case SERVICE_CONTROL_INTERROGATE:
            // Fall through to send current status.
            break;

        default:
            break;
        }

        ReportSvcStatus(gSvcStatus.dwCurrentState, NO_ERROR, 0);
        return NO_ERROR;
    }

  • 相关阅读:
    react-native 之ScrollView的使用
    gitHub 克隆项目慢
    react native 给View添加点击事件
    React Native View属性onLayout
    react native 样式与布局
    react native 对日期的处理
    react native 顶部菜单栏效果的实现
    iOS self.navigationController 推出界面怎么一次性回到指定第一个
    Java
    2021-5-13讲课内容hibernate主键id映射_XML方式
  • 原文地址:https://www.cnblogs.com/MaxWoods/p/3794934.html
Copyright © 2011-2022 走看看