none
Device drivers: Facing Issue while developing windows service RRS feed

  • Question

  • Hello team,

              Currently we are developing kmdf driver for windowsIOT core device, In order to establish connection between Application and Genericusbfn.sys, we are following following windows service code, "Install, start, stop, delete of a windows service works fine", but we observed one thing , we didn't get any prints which are in ServiceMain() function which means control is not entering into ServiceMain() function and we are getting following error StartServiceCtrlDispatcher -> failed.here i include screen shots and code we follow, could anybody please guid us how to solve.

    NOTE: For developing windows service can i use console application template, if it is not relevant template could anybody tell us which template is used to develop windows service in c++.

         "Templates from visual studios 2017"

    Code we are using :

    #include <Windows.h> //Windows Service
    #include <iostream>
    #include <fstream>

    using namespace std;
    ofstream svc;

    //----Global Variable Declarations------//
    //ServiceName
    #define SERVICE_NAME TEXT("usbService") 
    // Service Status Structure
    SERVICE_STATUS ServiceStatus = { 0 };
    //Service Status Handle for Register the Service
    SERVICE_STATUS_HANDLE hServiceStatusHandle = NULL;
    // Event Handle for Service
    HANDLE hServiceEvent = NULL;
    //---- Windows Service Functions Declarations----//
    // Service Main Function
    void WINAPI ServiceMain(DWORD dwArgc, LPTSTR *lpArgv);
    // Service Control Handler
    void WINAPI ServiceControlHandler(DWORD dwControl);
    void ServiceReportStatus(
    DWORD dwCurrentState,
    DWORD dwWin32ExitCode,
    DWORD dwWaitHint); // Service Report Status
    // ServiceInit Fun
    void ServiceInit(DWORD dwArgc, LPTSTR *lpArgv);
    // Service install Fun
    void ServiceInstall(void);
    // Service delete Fun
    void ServiceDelete(void);
    // Service start Fun
    void ServiceStart(void);
    // Service Stop Fun
    void ServiceStop(void);
    //---------- Main Function------------//
    int main(int argc, CHAR *argv[])
    {
    svc.open("LOGS.txt");
    svc << "Inside main\n";

    cout << "In main fun Start" << endl;
    // Local Variable Definition
    BOOL bStServiceCtrlDispatcher = FALSE;
    // Functional Logic Starts Here
    if (lstrcmpiA(argv[1], "install") == 0)
    {
    //Call Service Install Fun.
    ServiceInstall();
    cout << "Installation Success" << endl;
    }// if
    else if (lstrcmpiA(argv[1], "start") == 0)
    {
    //Call Service Start Fun.
    ServiceStart();
    cout << "ServiceStart Success" << endl;
    }// else if
    else if (lstrcmpiA(argv[1], "stop") == 0)
    {
    //Call Service Stop Fun.
    ServiceStop();
    cout << "ServiceStop Success" << endl;
    }// else if
    else if (lstrcmpiA(argv[1], "delete") == 0)
    {
    //Call Service delete Fun.
    ServiceDelete();
    cout << "ServiceDelete" << endl;
    }
    else
    {
    //STEP-1 Fill the Service Table Entry (2D Array)
    SERVICE_TABLE_ENTRY DispatchTable[] =
    {
      { (LPWSTR) SERVICE_NAME,(LPSERVICE_MAIN_FUNCTION)ServiceMain},
      { NULL, NULL }
    };
    //STEP-2 -> Start Service Control Dispatcher
    bStServiceCtrlDispatcher = StartServiceCtrlDispatcher(
    DispatchTable);
    if (FALSE == bStServiceCtrlDispatcher)
    {
    cout << "StartServiceCtrlDispatcher Failed" << endl;
    cout << "Error Code - " << GetLastError() << endl;
    }
    else
    {
    cout << "StartServiceCtrlDispatcher Success" << endl;
    }// if
    }// else
    cout << "In main fun End" << endl;
    system("PAUSE");
    return 0;
    svc.close();
    }
    //--------------End of Main Function--------------//
    //--------- ServiceMain Function Definition--------//
    void WINAPI ServiceMain(DWORD dwArgc, LPTSTR *lpArgv)
    {
    svc << "inside ServiceMain\n";
    cout << "ServiceMain Start" << endl;
    // Local Variable definitions
    BOOL bServiceStatus = FALSE;
    /* STEP -1 ->Registering Service Control Handler
       Function to SCM */
    hServiceStatusHandle = RegisterServiceCtrlHandler(
    SERVICE_NAME,
    ServiceControlHandler);
    if (NULL == hServiceStatusHandle)
    {
    cout << " RegisterServiceCtrlHandler Failed " << endl;
    cout << "Error Code - " << GetLastError() << endl;
    }
    else
    {
    cout << "RegisterServiceCtrlHandler Success" << endl;
    }
    //STEP-2-> SERVICE_STATUS Initial Setup Here
    ServiceStatus.dwServiceType = SERVICE_WIN32_OWN_PROCESS;
    ServiceStatus.dwServiceSpecificExitCode = 0;
    /*STEP-3-> Call Service Report Status for Notifying
      Initial Setup */
    ServiceReportStatus(
    SERVICE_START_PENDING,
    NO_ERROR,
    3000);
    // STEP-4-> Check the Service Status
    bServiceStatus = SetServiceStatus(
    hServiceStatusHandle,
    &ServiceStatus);
    if (FALSE == bServiceStatus)
    {
    cout << "Service Status Initial Setup FAILED = " <<
    GetLastError() << endl;
    }
    else
    {
    cout << "Service Status initial Setup SUCCESS" << endl;
    }
    //STEP-5 -> Call ServiceInit Fun
    ServiceInit(dwArgc, lpArgv);
    cout << "ServiceMain End" << endl;
    }//------------End of ServiceMain-----------------//

    //----- Service Control Handler Definitions---------//
    void WINAPI ServiceControlHandler(DWORD dwControl)
    {
    svc << "inside ServiceControlHandler\n";
    cout << "ServiceControlHandler" << endl;
    switch (dwControl)
    {
    case SERVICE_CONTROL_S"white-space:pre;">{
    //Call ServiceReportStatus Function
    ServiceReportStatus(SERVICE_STOPPED, NO_ERROR, 0);
    cout << "Service stopped" << endl;
    break;
    }
    default:
    break;
    }//Switch
    cout << "ServiceControlHandler" << endl;
    } //-----End of Service Control Handler fun------//


    //--------------ServiceInit Definitions----------//
    void ServiceInit(DWORD dwArgc, LPTSTR *lpArgv)
    {
    svc << "inside ServiceInit\n";
    cout << "ServiceInit Start" << endl;
    //STEP-1 -> Create Event
    hServiceEvent = CreateEvent(
    NULL,//Security Attributes
    TRUE,//MANUAL Reset Event
    FALSE,//Non-Signaled
    NULL);//Name of Event
    if (NULL == hServiceEvent)
    {
    /* Call ServiceReportStatus Fun to Notify
    SCM for Current Status of Service*/
    ServiceReportStatus(SERVICE_STOPPED, NO_ERROR, 0);
    }
    else
    {
    /* Call ServiceReportStatus Fun to Notify
    SCM for Current Status of Service*/
    ServiceReportStatus(SERVICE_RUNNING, NO_ERROR, 0);
    }
    //STEP-2-> Check Whether to stop the Service
    while (1)
    {
    //WaitforSingleObject Which wait event to be Signaled.
    WaitForSingleObject(hServiceEvent, INFINITE);
    //Send Report status to SCM
    ServiceReportStatus(SERVICE_STOPPED, NO_ERROR, 0);
    }
    cout << "ServiceInit End" << endl;
    }//-------End of ServiceInit --------------------//

    //--------Service Report Status Fun Definitions-----//
    void ServiceReportStatus(
    DWORD dwCurrentState,
    DWORD dwWin32ExitCode,
    DWORD dwWaitHint)
    {
    svc << "inside ServiceReportStatus\n";
    cout << "ServiceReportStatus Start" << endl;
    // Local variable Definitions
    static DWORD dwCheckPoint = 1;
    BOOL bSetServiceStatus = FALSE;
    // STEP-1 Fill The SERVICE_STATUS Structure
    ServiceStatus.dwCurrentState = dwCurrentState;
    ServiceStatus.dwWin32ExitCode = dwWin32ExitCode;
    ServiceStatus.dwWaitHint = dwWaitHint;
    // STEP-2 -> Check the Current State of Service
    //Service is about to start
    if (dwCurrentState == SERVICE_START_PENDING)
    {
    ServiceStatus.dwControlsAccepted = 0;
    }
    else
    {
    ServiceStatus.dwControlsAccepted = SERVICE_ACCEPT_STOP;
    }
    //STEP-3 -> Progress for Service operation
    if ((dwCurrentState == SERVICE_RUNNING) ||
    (dwCurrentState == SERVICE_STOPPED))
    {
    ServiceStatus.dwCheckPoint = 0;
    }
    else
    {
    ServiceStatus.dwCheckPoint = dwCheckPoint++;
    }
    //STEP-4 -> Notify the current status of SCM
    bSetServiceStatus = SetServiceStatus(
    hServiceStatusHandle,
    &ServiceStatus);
    if (FALSE == bSetServiceStatus)
    {
    cout << "Service Status FAILED " << endl;
    cout << "Error No - " << GetLastError() << endl;
    }
    else
    {
    cout << "Service Status SUCCESS" << endl;
    }// if
    cout << "ServiceReportStatus End" << endl;
    }
    //---- End of ServiceReportStatus Fun Definition ------//

    void ServiceInstall(void)
    {
    svc << "inside ServiceInstall\n";
    cout << "ServiceInstall Start" << endl;
    // Local Variable Definitions
    SC_HANDLE hScOpenSCManager = NULL;
    SC_HANDLE hScCreateService = NULL;
    DWORD dwGetModuleFileName = 0;
    TCHAR szPath[MAX_PATH];
    /*STEP-1 -> GetModuleFileName Get the
    Executable file from SCM*/
    dwGetModuleFileName = GetModuleFileName(
    NULL,
    szPath,
    MAX_PATH);
    if (0 == dwGetModuleFileName)
    {
    cout << "Service Installation Failed " << endl;
    cout << "Error No = " << GetLastError() << endl;
    }
    else
    {
    cout << "Successfully install the File\n" << endl;
    }// if

       //STEP-2 -> Open the Service Control Manager
    hScOpenSCManager = OpenSCManager(
    NULL,//Local Machine
    NULL,//By default Database i.e. SERVICES_ACTIVE_DATABASE
    SC_MANAGER_ALL_ACCESS);//Access Right
    if (NULL == hScOpenSCManager)
    {
    cout << "OpenSCManager Failed " << endl;
    cout << "Error No - " << GetLastError() << endl;
    }
    else
    {
    cout << "OpenSCManager Success" << endl;
    }

    //STEP-3 -> Create the Service
    hScCreateService = CreateService(
    hScOpenSCManager,//SCM Handle
    SERVICE_NAME,//Service Name
    SERVICE_NAME,//Display Name
    SERVICE_ALL_ACCESS,//Access Right
    SERVICE_WIN32_OWN_PROCESS,//Service Type
    SERVICE_DEMAND_START,//Service Start Type
    SERVICE_ERROR_NORMAL,//Service Error Code
    szPath,//Service Path
    NULL,
    NULL,
    NULL,
    NULL,
    NULL);
    if (NULL == hScCreateService)
    {
    cout << "CreateService Failed " << endl;
    cout << "Error No - " << GetLastError() << endl;
    CloseServiceHandle(hScOpenSCManager);
    }
    else
    {
    cout << "CreateService Success" << endl;
    }
    /*STEP-4 -> Close the Handle for OpenSCManager
    and Create Service*/
    CloseServiceHandle(hScCreateService);
    CloseServiceHandle(hScOpenSCManager);

    cout << "ServiceInstall End" << endl;
    } //--End of ServiceInstall Definition--------//

    //------ServiceDelete Definition--------//
    void ServiceDelete(void)
    {
    svc << "inside ServiceDelete\n";
    cout << "ServiceDelete Start" << endl;
    // Local Variable Definitions
    SC_HANDLE hScOpenSCManager = NULL;
    SC_HANDLE hScOpenService = NULL;
    BOOL bDeleteService = FALSE;
    //STEP-1 -> Open the Service Control Manager
    hScOpenSCManager = OpenSCManager(
    NULL,
    NULL,
    SC_MANAGER_ALL_ACCESS);
    if (NULL == hScOpenSCManager)
    {
    cout << "OpenSCManager Failed " << endl;
    cout << "Error No - " << GetLastError() << endl;
    }
    else
    {
    cout << "OpenSCManager Success" << endl;
    }
    //STEP-2 -> Open the Service
    hScOpenService = OpenService(
    hScOpenSCManager,
    SERVICE_NAME,
    SERVICE_ALL_ACCESS);
    if (NULL == hScOpenService)
    {
    cout << "OpenService Failed " << endl;
    cout << "Error No- " << GetLastError() << endl;
    }
    else
    {
    cout << "OpenService Success " << endl;
    }
    //STEP-3 -> Delete Service
    bDeleteService = DeleteService(hScOpenService);
    if (FALSE == bDeleteService)
    {
    cout << "Delete Service Failed " << endl;
    cout << "Error No- " << GetLastError() << endl;
    }
    else
    {
    cout << "Delete Service Success" << endl;
    }

    /*STEP-4 -> Close the Handle for
    SCM and OpenService */
    CloseServiceHandle(hScOpenService);
    CloseServiceHandle(hScOpenSCManager);
    cout << "ServiceDelete End" << endl;
    }
    //---End of ServiceDelete Function-------------//

    //----ServiceStart Definitions-----//
    void ServiceStart(void)
    {
    svc << "inside ServiceStart\n";
    cout << "Inside ServiceStart function" << endl;
    // Local Variable Definitions
    BOOL bStartService = FALSE;
    SERVICE_STATUS_PROCESS SvcStatusProcess;
    SC_HANDLE hOpenSCManager = NULL;
    SC_HANDLE hOpenService = NULL;
    BOOL bQueryServiceStatus = FALSE;
    DWORD dwBytesNeeded;
    //STEP-1-> Open Service Control Manager
    hOpenSCManager = OpenSCManager(
    NULL,
    NULL,
    SC_MANAGER_ALL_ACCESS);
    if (NULL == hOpenSCManager)
    {
    cout << "hOpenSCManager Failed " << endl;
    cout << "Error No = " << GetLastError() << endl;
    }
    else
    {
    cout << "hOpenSCManager Success" << endl;
    }
    //STEP-2 OpenService
    hOpenService = OpenService(
    hOpenSCManager,
    SERVICE_NAME,
    SC_MANAGER_ALL_ACCESS);
    if (NULL == hOpenService)
    {
    cout << "OpenService Failed " << endl;
    cout << "Error No = " << GetLastError() << endl;
    CloseServiceHandle(hOpenSCManager);
    }
    else
    {
    cout << "OpenService Success" << endl;
    }
    //STEP-3->Query about current Service Status
    bQueryServiceStatus = QueryServiceStatusEx(
    hOpenService,
    SC_STATUS_PROCESS_INFO,
    (LPBYTE)&SvcStatusProcess,
    sizeof(SERVICE_STATUS_PROCESS),
    &dwBytesNeeded);

    if (FALSE == bQueryServiceStatus)
    {
    cout << "QueryService Failed " << endl;
    cout << "Error No = " << GetLastError() << endl;
    }
    else
    {
    cout << "QueryService Success" << endl;
    }
    //STEP-4 -> Checked Service is running or stopped
    if ((SvcStatusProcess.dwCurrentState != SERVICE_STOPPED) &&
    (SvcStatusProcess.dwCurrentState != SERVICE_STOP_PENDING))
    {
    cout << " service is already running" << endl;
    }
    else
    {
    cout << "Service is Already Stopped" << endl;
    }
    //STEP-5 -> If Service is stopped Then query the service
    while (SvcStatusProcess.dwCurrentState == SERVICE_STOP_PENDING)
    {

    bQueryServiceStatus = QueryServiceStatusEx(
    hOpenService,
    SC_STATUS_PROCESS_INFO,
    (LPBYTE)&SvcStatusProcess,
    sizeof(SERVICE_STATUS_PROCESS),
    &dwBytesNeeded);

    if (FALSE == bQueryServiceStatus)
    {
    cout << "QueryService Failed" << endl;
    cout << "Error No = " << GetLastError() << endl;
    CloseServiceHandle(hOpenService);
    CloseServiceHandle(hOpenSCManager);
    }
    else
    {
    cout << "QueryService Success" << endl;
    }

    }// while

    //STEP-6 -> Start The Service
    bStartService = StartService(
    hOpenService,
    NULL,
    NULL);
    if (FALSE == bStartService)
    {
    cout << "StartService Failed " << endl;
    cout << "Error No = " << GetLastError() << endl;
    CloseServiceHandle(hOpenService);
    CloseServiceHandle(hOpenSCManager);
    }
    else
    {
    cout << "StartService Success" << endl;
    }
    //STEP-7 -> Query the service again
    bQueryServiceStatus = QueryServiceStatusEx(
    hOpenService,
    SC_STATUS_PROCESS_INFO,
    (LPBYTE)&SvcStatusProcess,
    sizeof(SERVICE_STATUS_PROCESS),
    &dwBytesNeeded);

    if (FALSE == bQueryServiceStatus)
    {
    cout << "QueryService Failed " << endl;
    cout << "Error No = " << GetLastError() << endl;
    CloseServiceHandle(hOpenService);
    CloseServiceHandle(hOpenSCManager);
    }
    else
    {
    cout << "QueryService Success" << endl;
    }
    // STEP-8 -> Check Service is running or not

    if (SvcStatusProcess.dwCurrentState == SERVICE_RUNNING)
    {
    cout << "Service Started Running..." << endl;
    }
    else
    {
    cout << "Service Running Failed" << endl;
    cout << "Error No = " << GetLastError() << endl;
    CloseServiceHandle(hOpenService);
    CloseServiceHandle(hOpenSCManager);
    }
    /*STEP-9-> Close the Service Handle for
    OpenSCManager & OpenService*/
    CloseServiceHandle(hOpenService);
    CloseServiceHandle(hOpenSCManager);
    cout << "ServiceStart end" << endl;
    }//--End of ServiceStart fun definition-------//

    //-----ServiceStop Definitions----------//
    void ServiceStop(void)
    {
    svc << "inside ServiceStop\n";
    cout << "Inside Service Stop" << endl;
    //Local Variable Definitions
    SERVICE_STATUS_PROCESS SvcStatusProcess;
    SC_HANDLE hScOpenSCManager = NULL;
    SC_HANDLE hScOpenService = NULL;
    BOOL bQueryServiceStatus = TRUE;
    BOOL bControlService = TRUE;
    DWORD dwBytesNeeded;
    //STEP-1 -> Open Service Control Manager
    hScOpenSCManager = OpenSCManager(
    NULL,
    NULL,
    SC_MANAGER_ALL_ACCESS);
    if (NULL == hScOpenSCManager)
    {
    cout << "OpenSCManager Failed " << endl;
    cout << "Error No = " << GetLastError() << endl;
    }
    else
    {
    cout << "OpenSCManager Success" << endl;
    }// if
       //STEP-2 ->Open your Service
    hScOpenService = OpenService(
    hScOpenSCManager,
    SERVICE_NAME,
    SC_MANAGER_ALL_ACCESS);
    if (NULL == hScOpenService)
    {
    cout << "OpenService Failed " << endl;
    cout << "Error No = " << GetLastError() << endl;
    CloseServiceHandle(hScOpenSCManager);
    }
    else
    {
    cout << "OpenService Success" << endl;
    }// if

    //STEP-3 -> QueryServiceStatus

    bQueryServiceStatus = QueryServiceStatusEx(
    hScOpenService,
    SC_STATUS_PROCESS_INFO,
    (LPBYTE)&SvcStatusProcess,
    sizeof(SERVICE_STATUS_PROCESS),
    &dwBytesNeeded);
    if (FALSE == bQueryServiceStatus)
    {
    cout << "QueryService Failed " << endl;
    cout << "Error No = " << GetLastError() << endl;
    CloseServiceHandle(hScOpenService);
    CloseServiceHandle(hScOpenSCManager);
    }
    else
    {
    cout << "QueryService Success" << endl;
    }
    /*STEP-4 -> send a stop code to the
    Service Control Manager*/
    bControlService = ControlService(
    hScOpenService,
    SERVICE_CONTROL_STOP,
    (LPSERVICE_STATUS)&SvcStatusProcess);
    if (TRUE == bControlService)
    {
    cout << "Control Service Success" << endl;
    }
    else
    {
    cout << "Control Service Failed " << endl;
    cout << "Error No = " << GetLastError() << endl;
    CloseServiceHandle(hScOpenService);
    CloseServiceHandle(hScOpenSCManager);
    }// if

     //STEP-5 -> wait for Service to stop
    while (SvcStatusProcess.dwCurrentState != SERVICE_STOPPED)
    {
    //STEP-6 -> Inside While Loop Query the service
    bQueryServiceStatus = QueryServiceStatusEx(
    hScOpenService,
    SC_STATUS_PROCESS_INFO,
    (LPBYTE)&SvcStatusProcess,
    sizeof(SERVICE_STATUS_PROCESS),
    &dwBytesNeeded);

    if (TRUE == bQueryServiceStatus)
    {
    cout << "QueryService Failed" << endl;
    cout << "Error No = " << GetLastError() << endl;
    CloseServiceHandle(hScOpenService);
    CloseServiceHandle(hScOpenSCManager);
    }
    else
    {
    cout << "QueryService Success" << endl;
    }
    /*STEP-7 -> Inside While Loop, Check the
    current state of Service*/
    if (SvcStatusProcess.dwCurrentState == SERVICE_STOPPED)
    {
    cout << "Service Stopped Successfully" << endl;
    break;// Coming out from While loop
    }
    else
    {
    cout << "Service Stopped Failed" << endl;
    cout << "Error No = " << GetLastError() << endl;
    CloseServiceHandle(hScOpenService);
    CloseServiceHandle(hScOpenSCManager);
    }
    }// while
      //STEP-8 -> Close the handle for 

    CloseServiceHandle(hScOpenService);
    CloseServiceHandle(hScOpenSCManager);
    cout << "Service Stop" << endl;
    }//--End of ServiceStop Function Definition----//




    Saturday, April 4, 2020 3:39 PM

All replies

  • If I remember correctly Microsoft removed the template to create a service using unmanaged C++ a long, long time ago.

    You can find a sample Windows service in C++ (CppWindowsService) at https://github.com/microsoftarchive/msdn-code-gallery-microsoft/tree/master/OneCodeTeam

    • Edited by RLWA32 Saturday, April 4, 2020 4:11 PM
    Saturday, April 4, 2020 4:09 PM
  • It looks to me like everything is working just fine, buy you are unclear on how services work.  You will never see std::cout output from your service.  When you start your service, the operating system will launch a brand-new process to host the service. It is in that new process where you will call ServiceMain to start responding to messages.

    The reason you don't see any log messages is that every time you run the app, you are overwriting LOGS.txt from the last runs.  The service is going to start running in a separate process when you call "service start", at the very same time.

    I suggest you use a different log file for each function within your code.  Then you will see the messages.  Also note that you can use "net start usbService" and "net stop usbService"; you don't really have to run your own code to do that.


    Tim Roberts | Driver MVP Emeritus | Providenza &amp; Boekelheide, Inc.

    Monday, April 6, 2020 1:24 AM
  • Hello Tim Roberts , 

       As per your suggestion, i use diffrent logfiles for each function in my code, still i didn't get prints from "servicemain()", I think control not enters into this function, please let me know why this happens.

    Thanks and regards,

    Hemanth kumar velooru.



    Monday, April 6, 2020 4:48 AM