How to make sure that the service is already running

This is the forum for miscellaneous technical/programming questions.

Moderator: 2ffat

How to make sure that the service is already running

Postby Lena » Thu Feb 08, 2018 3:23 am

Hello.
Tell me please how to make sure that the service is already running? This is the postgres database, which can be seen in the task manager.
Sometimes there is a situation that immediately after the start of the computer, the user quickly launches my application and gets an error because my application try access to postgres database. If the user waited for extra seconds 10-30, there would be no error.
I would like to handle this situation and give the user a message that Windows has not yet uploaded the postgres service.
How can I make sure that the service is already running and really works?
Thanks.
Lena
BCBJ Master
BCBJ Master
 
Posts: 544
Joined: Sun Feb 06, 2011 1:28 pm

Re: How to make sure that the service is already running

Postby HsiaLin » Sun Feb 11, 2018 11:39 pm

I dont know anything about postgres databases but would it be
possible to try to get the db version inside a loop of some type
then break out of the loop once the version was sent. You would
know its loaded up at that point.
HsiaLin
BCBJ Master
BCBJ Master
 
Posts: 289
Joined: Sun Jul 08, 2007 6:29 pm

Re: How to make sure that the service is already running

Postby Lena » Mon Feb 12, 2018 5:02 am

Thank you for your advice.

P.S.
To control the service, I also found this code;
Code: Select all
void __fastcall TForm1::Button3Click(TObject *Sender)
{
 
 String aServiceName = "Dhcp";
 SC_HANDLE h_manager,h_svc;
 SERVICE_STATUS svc_status;
 LPSERVICE_STATUS svc_status2 = &svc_status;   
h_manager = OpenSCManager(NULL,NULL,SC_MANAGER_CONNECT);
   if(h_manager > 0)
     {
      h_svc = OpenService(h_manager,aServiceName.c_str(),SERVICE_QUERY_STATUS);
       if(h_svc > 0)
         {
           if(QueryServiceStatus(h_svc,svc_status2))
           {
             if (svc_status2->dwCurrentState==SERVICE_STOPPED)
             {
              ShowMessage("STOPPED");
             }
             else ShowMessage("STARTED");
           }
         }
     }
CloseServiceHandle(h_svc);
CloseServiceHandle(h_manager);
Lena
BCBJ Master
BCBJ Master
 
Posts: 544
Joined: Sun Feb 06, 2011 1:28 pm

Re: How to make sure that the service is already running

Postby rlebeau » Mon Feb 12, 2018 3:36 pm

Lena wrote:To control the service, I also found this code;


Yes, if you want to know if the service is running, you need to query it manually.

Lena wrote:
Code: Select all
SERVICE_STATUS svc_status;
LPSERVICE_STATUS svc_status2 = &svc_status;   



You don't need that svc_status2 variable. Just pass &svc_status directly to QueryServiceStatus().

Lena wrote:
Code: Select all
h_manager = OpenSCManager(NULL,NULL,SC_MANAGER_CONNECT);
if(h_manager > 0)



You need to check for !NULL (!0), not for >0.

Lena wrote:
Code: Select all
h_svc = OpenService(h_manager,aServiceName.c_str(),SERVICE_QUERY_STATUS);
if(h_svc > 0)



Same here.

Lena wrote:
Code: Select all
if (svc_status2->dwCurrentState==SERVICE_STOPPED)
{
    ShowMessage("STOPPED");
}
else ShowMessage("STARTED");



There are other statuses you should be paying attention to, like SERVICE_STOP_PENDING and SERVICE_START_PENDING.

You are also not reporting any errors if they occur.

Try something more like this:

Code: Select all
#include <System.Diagnostics.hpp>
#include <memory>

inline bool IsPendingState(DWORD state) {
    return (
        (state == SERVICE_CONTINUE_PENDING) ||
        (state == SERVICE_PAUSE_PENDING) ||
        (state == SERVICE_START_PENDING) ||
        (state == SERVICE_STOP_PENDING)
    );
}

struct ServiceHandleDeleter
{
    typedef SC_HANDLE pointer;
    void operator()(SC_HANDLE hsc) const noexcept
    {
        CloseServiceHandle(hsc);
    }
};

using SC_HANDLE_PTR = std::unique_ptr<SC_HANDLE, ServiceHandleDeleter>;

void __fastcall TForm1::Button3Click(TObject *Sender)
{
    SC_HANDLE_PTR h_manager(OpenSCManager(NULL, NULL, SC_MANAGER_CONNECT));
    if (h_manager == nullptr)
        RaiseLastOSError();

    SC_HANDLE_PTR h_svc(OpenService(h_manager.get(), TEXT("Dhcp"), SERVICE_QUERY_STATUS));
    if (h_svc == nullptr)
        RaiseLastOSError();

    SERVICE_STATUS svc_status;
    if (!QueryServiceStatus(h_svc.get(), &svc_status))
        RaiseLastOSError();

    while (IsPendingState(svc_status.dwCurrentState))
    {
        DWORD state = svc_status.dwCurrentState;
        DWORD checkpoint = svc_status.dwCheckPoint;
        DWORD wait = svc_status.dwWaitHint;

        TStopwatch sw =  TStopwatch::StartNew();
        do
        {
            if (MsgWaitForMultipleObjects(0, NULL, FALSE, wait, QS_ALLINPUT) == WAIT_OBJECT_0)
                Application->ProcessMessages();

            __int64 elapsed = sw.ElapsedMilliseconds;
            if (elapsed >= __int64(wait))
            {
                sw.Stop();

                if (!QueryServiceStatus(h_svc.get(), &svc_status))
                    RaiseLastOSError();

                if (svc_status.dwCurrentState != state)
                    break;

                if (svc_status.dwCheckPoint == checkpoint)
                    throw Exception(_D("Service is not updating its status correctly"));

                wait = svc_status.dwWaitHint;
                sw.Start();
            }
            else
                wait -= DWORD(elapsed);
        }
        while (true);
    }

    switch (svc_status.dwCurrentState)
    {
        case SERVICE_PAUSED:
            ShowMessage("PAUSED");
            break;

        case SERVICE_STOPPED:
            ShowMessage("STOPPED");
            break;

        case SERVICE_RUNNING:
            ShowMessage("STARTED");
            break;
    }
}
Remy Lebeau (TeamB)
Lebeau Software
User avatar
rlebeau
BCBJ Author
BCBJ Author
 
Posts: 1484
Joined: Wed Jun 01, 2005 3:21 am
Location: California, USA

Re: How to make sure that the service is already running

Postby Lena » Tue Feb 13, 2018 4:16 am

Thank You very much!
Lena
BCBJ Master
BCBJ Master
 
Posts: 544
Joined: Sun Feb 06, 2011 1:28 pm


Return to Technical

Who is online

Users browsing this forum: No registered users and 17 guests