Windows ATL Service 服务的创建(VS2010)

1 使用VS2010床加一个ATL服务项目
第一步
这里写图片描述
第二步
这里写图片描述
第三步
这里写图片描述

创建好之后,
重写父类的以下方法

        HRESULT RegisterAppId(bool bService = false) throw ();
        void ServiceMain(DWORD dwArgc, LPTSTR* lpszArgv);
        HRESULT PostMessageLoop();
        void Handler(DWORD dwOpcode);
        void OnStop();
        void OnPause();
        void  OnContinue();
        void  OnInterrogate();
        void  OnShutdown();
        HRESULT PreMessageLoop(int nShowCmd);
全部代码如下
// MyService.cpp : WinMain 的实现


#include "stdafx.h"
#include "resource.h"
#include "MyService_i.h"


#include <stdio.h>

class CMyServiceModule : public ATL::CAtlServiceModuleT< CMyServiceModule, IDS_SERVICENAME >
    {
public :
    DECLARE_LIBID(LIBID_MyServiceLib)
    DECLARE_REGISTRY_APPID_RESOURCEID(IDR_MYSERVICE, "{38D52E46-9042-4AC9-9D57-4A13E350B4EF}")
        HRESULT InitializeSecurity() throw()
    {
        // TODO : 调用 CoInitializeSecurity 并为服务提供适当的安全设置
        // 建议 - PKT 级别的身份验证、
        // RPC_C_IMP_LEVEL_IDENTIFY 的模拟级别
        // 以及适当的非 null 安全说明符。

        return S_OK;
    }

        HRESULT RegisterAppId(bool bService = false) throw ();
        void ServiceMain(DWORD dwArgc, LPTSTR* lpszArgv);
        HRESULT PostMessageLoop();
        void Handler(DWORD dwOpcode);
        void OnStop();
        void OnPause();
        void  OnContinue();
        void  OnInterrogate();
        void  OnShutdown();
        HRESULT PreMessageLoop(int nShowCmd);


    };

CMyServiceModule _AtlModule;



//
extern "C" int WINAPI _tWinMain(HINSTANCE /*hInstance*/, HINSTANCE /*hPrevInstance*/, 
                                LPTSTR /*lpCmdLine*/, int nShowCmd)
{
    return _AtlModule.WinMain(nShowCmd);
}


HRESULT CMyServiceModule::RegisterAppId(bool bService ) throw ()
{
    HRESULT hr = S_OK;
    BOOL res = __super ::RegisterAppId(bService);
    if (bService)
    {
        if (IsInstalled())
        {
            SC_HANDLE hSCM = ::OpenSCManagerW(NULL, NULL, SERVICE_CHANGE_CONFIG);
            SC_HANDLE hService = NULL;
            if (hSCM == NULL)
            {
                hr = ATL::AtlHresultFromLastError();
            }
            else
            {
                hService = ::OpenService(hSCM, m_szServiceName, SERVICE_CHANGE_CONFIG);
                if (hService != NULL)
                {
                    ::ChangeServiceConfig(hService, SERVICE_NO_CHANGE,
                        SERVICE_AUTO_START,// 修改服务为自动启动
                        NULL, NULL, NULL, NULL, NULL, NULL, NULL,
                        m_szServiceName); // 通过修改资源IDS_SERVICENAME 修改服务的显示名字

                    SERVICE_DESCRIPTION Description;
                    TCHAR szDescription[1024];
                    ZeroMemory(szDescription, 1024);
                    ZeroMemory(&Description, sizeof (SERVICE_DESCRIPTION));
                    lstrcpy(szDescription, _T("测试服务描述信息" ));
                    Description.lpDescription = szDescription;
                    ::ChangeServiceConfig2(hService, SERVICE_CONFIG_DESCRIPTION, &Description);
                    ::CloseServiceHandle(hService);
                }
                else
                {
                    hr = ATL::AtlHresultFromLastError();
                }
                ::CloseServiceHandle(hSCM);
            }
        }
    }
    return hr;
}

void CMyServiceModule::ServiceMain(DWORD dwArgc, LPTSTR* lpszArgv)
{
    // TODO: 在此添加专用代码和/或调用基类

    //log(_T("invoke methode ServcieMain\n"));
    __super::ServiceMain(dwArgc,lpszArgv);
    //CAtlServiceModuleT::ServiceMain(dwArgc, lpszArgv);
}


HRESULT CMyServiceModule::PostMessageLoop()
{
    // TODO: 在此添加专用代码和/或调用基类
    //log(_T("invoke methode POstMessageLoop\n"));
    return CAtlServiceModuleT::PostMessageLoop();
}


void CMyServiceModule::Handler(DWORD dwOpcode)
{
    // TODO: 在此添加专用代码和/或调用基类
    //log(_T("invoke methode Handler with parameter\n"));
    __super::Handler(dwOpcode);
}


void CMyServiceModule::OnStop() throw()
{
    //log(_T("invoke OnStop\n"));
//  m_serverListener.stopServer();
    //log("停止服务监听");
    __super::OnStop();
}

void CMyServiceModule::OnPause() throw()
{
    //log(_T("invoke OnPause\n"));
    __super::OnPause();
}

void CMyServiceModule::OnContinue() throw()
{
    //log(_T("invoke OnContinue\n"));
    __super::OnContinue();
}

void CMyServiceModule::OnInterrogate() throw()
{
    //log(_T("invoke OnInterrogate\n"));
    __super::OnInterrogate();

}

void CMyServiceModule::OnShutdown() throw()
{
    //log(_T("invoke OnShutdown\n"));
    __super::OnShutdown();
}


HRESULT CMyServiceModule::PreMessageLoop(int nShowCmd)
{
    // TODO: 在此添加专用代码和/或调用基类
    HRESULT res= CAtlServiceModuleT::PreMessageLoop(nShowCmd);
    //log(_T("invoke method PreMessageLoop\n"));
    if(SUCCEEDED(res)){

        //SetServiceStatus(SERVICE_RUNNING);
        //m_serverListener.startServer();
        //log("启动服务监听");
    }

    return res;
}

使用cmd切换到项目输出目录,使用程序名.exe /Service
这里写图片描述

然后打开服务管理页面,就可以看到我们刚才安装的服务了
这里写图片描述

启动服务会出现
这里写图片描述

这个错误已经有人解决了,我们安装这个方法修改后,重新编程程序,再次使用 程序名.exe /Service 命令安装服务,然后在服务管理器中启动服务,运行了比较久出现如下错误
这里写图片描述
这个问题有人解决了,参考修改后,重新编译下代码,就可以了
这里写图片描述

我花了半天时间才写出来。1053那个错误,值得注意

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
如果你想在 Windows 平台上开发 C++ 应用程序,并且需要使用 ATL(Active Template Library)技术来简化 COM 组件开发,可以按照以下步骤操作: 1. 安装 Visual Studio:ATL 是 Visual C++ 的一个组件,因此需要安装 Visual Studio(包括 Visual C++ 组件)才能使用 ATL。你可以从 Microsoft 官网下载最新版本的 Visual Studio,也可以使用早期版本的 Visual Studio。 2. 创建 ATL 项目:在 Visual Studio 中,选择“File”->“New”->“Project”->“ATL”->“ATL Project”,然后按照向导创建一个 ATL 项目。 3. 编写 COM 组件代码:在 ATL 项目中,你可以使用 ATL 宏和模板来快速开发 COM 组件。具体来说,你可以使用 `ATL::CComObjectRootEx` 类来定义 COM 对象的基本行为,使用 `ATL::CComCoClass` 宏来定义 COM 对象的类工厂,使用 `ATL::CComPtr` 类来管理 COM 对象之间的引用计数等。 4. 注册 COM 组件:在 ATL 项目中,你可以使用 `ATL::CComModule` 类来管理 COM 组件的注册表信息。具体来说,你需要在 `DllMain` 函数中调用 `ATL::CComModule::Init` 函数来初始化 COM 模块,然后在 `DllMain` 函数中调用 `ATL::CComModule::Term` 函数来清理 COM 模块。如果你想手动注册 COM 组件,可以使用 `ATL::AtlRegisterClassCategoriesHelper` 函数和 `ATL::AtlRegisterClassObject` 函数来实现。 5. 使用 COM 组件:在其他应用程序中,你可以使用 COM 组件的类 ID 和接口 ID 来创建 COM 对象,并调用 COM 对象的方法来实现特定功能。具体来说,你可以使用 `CoCreateInstance` 函数来创建 COM 对象,使用 `QueryInterface` 函数来获取 COM 对象的接口指针,然后使用接口指针来调用 COM 对象的方法。 总之,使用 ATL 技术可以帮助你更快速、更方便地开发高质量的 COM 组件,并在 Windows 平台上实现各种应用程序之间的互操作。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值