windows service程序的入门范例(一)

windows service程序的入门范例(一)

 

Windows Service 程序编写方法


1.最简单的创建一个windows service程序
(1)新建一个win32控制台程序
(2)开始->运行->cmd,必须右键—>以管理员身份运行,此时进入dos命令提示符界面。
(3)输入 sc create test binPath= “D:\Code_Test\VS2012_test\test_console\test_console\Release\test_console.exe”

 

图1



【注意】等号“=”后面,必须空一格,否则可能报错。


2.查看已经创建的服务
(1)开始->附件->运行->输入:services.msc

(2)进入系统的服务界面,可看到新创建的test服务。如下图2所示。

 

图2 查看服务

3.删除一个服务程序
进入命令提示符,输入指令:sc delete test

 

图3 删除一个服务



4.程序实例
4.1 概述

(1)由于service程序,不需要界面,我们在建工程的时候,建立一个控制台程序即可。


(2)main函数的使用方法
由于windows服务不需要界面,所以大部分程序为win32控制台应用程序,所以程序主函数为main 而不是WinMain()。在主函数要做的主要工作就是两件事:
① 初始化一个SERVICE_TABLE_ENTRY 分派表结构体。
② 然后调用StartServiceCtrlDispatcher();这将把调用进程的主线程转换为控制分派器。该分派器启动一个新线程,该线程运行分派表中对应于你的服务的ServiceMain()函数。ServiceMain()函数将在下面提到。


4.2 ServiceMain()函数用法
ServiceMain函数为void WINAPI ServiceMain(int argc, char** argv)格式的函数,函数名字可以任意定义。它的作用就是:将你需要执行的任务放到该函数中循环执行即可。
ServiceMain()就是服务程序的工作函数。
在ServiceMain执行你的任务前,需要给SERVICE_TABLE_ENTRY 分派表结构体进行赋值,注意由于此时服务还没有开始执行你的任务所以我们将服务的状态设置为SERVICE_START_PENDING,即正在初始化。


4.3 程序代码
以下代码,为全部的代码,可以直接运行,已经验证通过。
(1) 新建一个控制台程序
(2) 在main()所在的文件里面,使用以下代码

(3) 这个代码的功能,是每隔5s,打印一条日志到日志文件C:\\log.txt里面。

// test_console.cpp : 定义控制台应用程序的入口点。
//
#include <stdio.h>
#include <iostream>
#include <windows.h>
#include <tchar.h>

using namespace std;

#define SLEEP_TIME 5000 //间隔时间

#define FILE_PATH "C://log.txt" //信息输出文件

bool brun = false;

SERVICE_STATUS servicestatus;

SERVICE_STATUS_HANDLE hstatus;

int WriteToLog(char* str);

void WINAPI ServiceMain(int argc, char** argv);

void WINAPI CtrlHandler(DWORD request);

int InitService();

int WriteToLog(char* str)
{

	FILE* pfile;
	fopen_s(&pfile, FILE_PATH, "a+");
	if (pfile == NULL)
	{
		return -1;
	}
	fprintf_s(pfile, "%s\n", str);
	fclose(pfile);
	return 0;
}

void WINAPI ServiceMain(int argc, char** argv)
{
	servicestatus.dwServiceType = SERVICE_WIN32;
	servicestatus.dwCurrentState = SERVICE_START_PENDING;
	servicestatus.dwControlsAccepted = SERVICE_ACCEPT_SHUTDOWN | SERVICE_ACCEPT_STOP;//在本例中只接受系统关机和停止服务两种控制命令
	servicestatus.dwWin32ExitCode = 0;
	servicestatus.dwServiceSpecificExitCode = 0;
	servicestatus.dwCheckPoint = 0;
	servicestatus.dwWaitHint = 0;

	hstatus = ::RegisterServiceCtrlHandler(L"testservice", CtrlHandler);

	if (hstatus == 0)

	{

		WriteToLog("RegisterServiceCtrlHandler failed");
		return;

	}

	WriteToLog("RegisterServiceCtrlHandler success");

	//向SCM 报告运行状态

	servicestatus.dwCurrentState = SERVICE_RUNNING;

	SetServiceStatus(hstatus, &servicestatus);

	//下面就开始任务循环了,你可以添加你自己希望服务做的工作

	brun = true;

	MEMORYSTATUS memstatus;

	char str[100];

	memset(str, '\0', 100);

	while (brun)
	{
		GlobalMemoryStatus(&memstatus);
		int availmb = memstatus.dwAvailPhys / 1024 / 1024;
		sprintf_s(str, 100, "available memory is %dMB", availmb);
		WriteToLog(str);
		Sleep(SLEEP_TIME);
	}
	WriteToLog("service stopped");
}

void WINAPI CtrlHandler(DWORD request)
{
	switch (request)
	{
	case SERVICE_CONTROL_STOP:
		brun = false;
		servicestatus.dwCurrentState = SERVICE_STOPPED;
		break;

	case SERVICE_CONTROL_SHUTDOWN:
		brun = false;
		servicestatus.dwCurrentState = SERVICE_STOPPED;
		break;

	default:
		break;
	}

	SetServiceStatus(hstatus, &servicestatus);
}


int _tmain(int argc, _TCHAR* argv[])
{
	SERVICE_TABLE_ENTRY entrytable[1];

	entrytable[0].lpServiceName = L"testservice";

	entrytable[0].lpServiceProc = (LPSERVICE_MAIN_FUNCTION)ServiceMain;

	StartServiceCtrlDispatcher(entrytable);

	return 0;
}

大家运行程序,会生成一个exe文件。

(4)以管理员身份,运行命令提示符 cmd.exe
 
① 首先,注册服务(注意, 代码里面的服务名称是testservice,此处要一致)
sc create testservice binPath= D:\Code_Test\VS2012_test\test_console\test_console\Debug\test_console.exe

备注 在本博主的实际试验中以上命令不需要双引号


②    然后,启动服务(注意,服务名称要写对)
sc start testservice
服务的运行结果如下图5所示:

 

图5 后台服务写日志成功



③ 关闭服务和删除服务
             sc stop testservice

             sc delete testservice

图6 关闭与删除

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值