• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>

            yehao's Blog

            后臺服務(wù)程序開發(fā)模式(一)

            轉(zhuǎn)自http://www.7880.com/Info/Article-5a8eada0.html

            一直感覺
            VC++太復(fù)雜了,但昨天看了汪蒲陽編著的因特網(wǎng)應(yīng)用編程,其中寫到后臺服務(wù)程序的編寫,論述的非常詳細(xì),而且邏輯清晰,看了之后感覺明白不少,故拿來與需要之人共享,并更正了原程序的一些錯誤,補充了一些材料。另外還有一種用C++編寫后臺服務(wù)程序的思路(不算.NET上服務(wù)程序開發(fā)模型),以后整理好了再發(fā)上來。

             

            2000/XP等基于NT 的操作系統(tǒng)中,有一個服務(wù)管理器,它管理的后臺進(jìn)程被稱為 service。

            服務(wù)是一種應(yīng)用程序類型,它在后臺運行,與 UNIX 后臺應(yīng)用程序類似。服務(wù)應(yīng)用程序通常可以

            在本地和通過網(wǎng)絡(luò)為用戶提供一些功能,例如客戶端/服務(wù)器應(yīng)用程序、Web 服務(wù)器、數(shù)據(jù)庫服

            務(wù)器以及其他基于服務(wù)器的應(yīng)用程序。

                后臺服務(wù) 程序是在后臺悄悄運行的。我們通過將自己的程序登記為服務(wù),可以使自己的程序不出現(xiàn)

            在任務(wù)管理器中,并且隨系統(tǒng)啟動而最先運行,隨系統(tǒng)關(guān)閉而最后停止。

                

                 服務(wù)控制管理器是一個RPC 服務(wù)器,它顯露了一組應(yīng)用編程接口,程序員可以方便的編寫程序來配置

            服務(wù)和控制遠(yuǎn)程服務(wù)器中服務(wù)程序。

                 服務(wù)程序通常編寫成控制臺類型的應(yīng)用程序,總的來說,一個遵守服務(wù)控制管理程序接口要求的程序

            包含下面三個函數(shù):

            1。服務(wù)程序主函數(shù)(main):調(diào)用系統(tǒng)函數(shù) StartServiceCtrlDispatcher 連接程序主線程到服務(wù)控制管理程序。

            2。服務(wù)入口點函數(shù)(ServiceMain):執(zhí)行服務(wù)初始化任務(wù),同時執(zhí)行多個服務(wù)的服務(wù)進(jìn)程有多個服務(wù)入口函數(shù)。

            3。控制服務(wù)處理程序函數(shù)(Handler):在服務(wù)程序收到控制請求時由控制分發(fā)線程引用。(此處是Service_Ctrl)。

             另外在系統(tǒng)運行此服務(wù)之前需要安裝登記服務(wù)程序:installService 函數(shù)。刪除服務(wù)程序則需要先刪除服務(wù)安裝登記:removeService 函數(shù)。

             

            服務(wù)類型:

            類型

            說明

            SERVICE_FILE_SYSTEM_DRIVER=2

            文件系統(tǒng)驅(qū)動服務(wù)。

            SERVICE_KERNEL_DRIVER=1

            驅(qū)動服務(wù)。

            SERVICE_WIN32_OWN_PROCESS=16

            獨占一個進(jìn)程的服務(wù)。

            SERVICE_WIN32_SHARE_PROCESS=32

            與其他服務(wù)共享一個進(jìn)程的服務(wù)。

            新建WIN32控制臺程序, 其源文件名為service.cpp 。我用的開發(fā)工具是VC++.NET。

             

            1.服務(wù)程序主函數(shù)

                服務(wù)控制管理程序啟動服務(wù)程序后,等待服務(wù)程序主函數(shù)調(diào)用系統(tǒng)函StartServiceCtrlDispatcher。一個SERVICE_WIN32_OWN_PROCESS 類型的服務(wù)應(yīng)該立即調(diào)用 StartServiceCtrlDispatcher 函數(shù),可以在服務(wù)啟動后讓服務(wù)入口點函數(shù)完成初始化工作。對于 SERVICE_WIN32_OWN_PROCESS 類型的服務(wù)和程序中所有服務(wù)共同的初始化工作可以在主函數(shù)中完成,但不要超過30秒。否則必須建立另外的線程完成這些共同的初始化工作,從而保證服務(wù)程序主函數(shù)能及時地調(diào)用 StartServiceCtrlDispatcher 函數(shù)。

             

             

            主函數(shù)處理了三中命令行參數(shù):- install,- remove,- debug,分別用于安裝,刪除和調(diào)試服務(wù)程序。如果不帶參數(shù)運行,則認(rèn)為是服務(wù)控制管理出現(xiàn)啟動該服務(wù)程序。參數(shù)不正確則給出提示信息。

             

            StartServiceCtrlDispatcher 函數(shù)負(fù)責(zé)把程序主線程連接到服務(wù)控制管理程序。具體描述如下:

            BOOL StartServiceCtrlDispatcher(

              const LPSERVICE_TABLE_ENTRY lpServiceTable);

            lpServiceStartTable 指向 SERVICE_TABLE_ENTRY 結(jié)構(gòu)類型的數(shù)組,他包含了調(diào)用進(jìn)程所提供的每個服務(wù)的入口函數(shù)和字符串名。表中的最后一個元素必須為 NULL,指明入口表結(jié)束。SERVICE_TABLE_ENTRY 結(jié)構(gòu)具體描述如下:

             

            typedef struct _SERVICE_TABLE_ENTRY {  LPTSTR lpServiceName;  LPSERVICE_MAIN_FUNCTION lpServiceProc;

            } SERVICE_TABLE_ENTRY, *LPSERVICE_TABLE_ENTRY;

             

            lpServiceName 是一個以 NULL 結(jié)尾的字符串,標(biāo)識服務(wù)名。如果是 SERVICE_WIN32_OWN_PROCESS 類型的服務(wù),這個字符串會被忽略。

            lpServiceProc 指向服務(wù)入口點函數(shù)。

             

             

            //服務(wù)程序主函數(shù)。

            #include "stdafx.h"

            #include "Windows.h"

            #define SZAPPNAME      "serverSample"     //服務(wù)程序名

            #define SZSERVICENAME  "serviceSample"    //標(biāo)識服務(wù)的內(nèi)部名

             

            //內(nèi)部變量

            bool                   bDebugServer=false;

            SERVICE_STATUS              ssStatus;

            SERVICE_STATUS_HANDLE  sshStatusHandle;

            DWORD                       dwErr=0;

            TCHAR                       szErr[256];

             

            //下面的函數(shù)由程序?qū)崿F(xiàn)

            void  WINAPI  Service_Main(DWORD dwArgc, LPTSTR *lpszArgv);

            void  WINAPI  Service_Ctrl(DWORD dwCtrlCode);

            void installService();

            void removeService();

            void debugService(int argc,char** argv);

            bool ReportStatusToSCMgr(DWORD dwCurrentState,DWORD dwWin32ExitCode,DWORD dwWaitHint);

            void AddToMessageLog(LPTSTR lpszMsg);

             

            int _tmain(int argc, _TCHAR* argv[])

            {   

                 SERVICE_TABLE_ENTRY dispatchTable[]=

                 {

                     {TEXT(SZSERVICENAME),(LPSERVICE_MAIN_FUNCTION)Service_Main},

                     { NULL,NULL}

                 };

                 if((argc>1)&&((*argv[1]=='-')||(argv[1]=="/")))

                 {

                     if(_stricmp("install",argv[1]+1)==0)

                     {

                          installService();

                     }

                     else if(_stricmp("remove",argv[1]+1)==0)

                     {

                          removeService();

                     }

                     else if(_stricmp("debug",argv[1]+1)==0)

                     {

                          bDebugServer=true;

                          debugService(argc,argv);

                     }

                     else

                     {        //如果未能和上面的如何參數(shù)匹配,則可能是服務(wù)控制管理程序來啟動該程序。立即調(diào)用

                               //StartServiceCtrlDispatcher 函數(shù)。

                          printf("%s - install to install the service \n",SZAPPNAME);

                          printf("%s - remove to remove the service \n",SZAPPNAME);

                          printf("%s - debug to debug the service \n",SZAPPNAME);

                          printf("\n StartServiceCtrlDispatcher being called.\n");

                          printf("This may take several seconds.Please wait.\n");

                          if(!StartServiceCtrlDispatcher(dispatchTable))

                               AddToMessageLog(TEXT("StartServiceCtrlDispatcher failed."));

                          else

                               AddToMessageLog(TEXT("StartServiceCtrlDispatcher OK."));

                     }

                     exit(0);

                 }

                 return 0;

            }

            posted on 2011-06-17 14:36 厚積薄發(fā) 閱讀(315) 評論(0)  編輯 收藏 引用 所屬分類: Windows編程

            導(dǎo)航

            <2025年8月>
            272829303112
            3456789
            10111213141516
            17181920212223
            24252627282930
            31123456

            統(tǒng)計

            常用鏈接

            留言簿

            隨筆分類

            文章分類

            文章檔案

            搜索

            最新評論

            国产V亚洲V天堂无码久久久| 久久只有这精品99| 精品久久香蕉国产线看观看亚洲| 欧美777精品久久久久网| 久久精品中文无码资源站| 久久久久久免费一区二区三区| 999久久久国产精品| 久久国产精品成人片免费| 久久一本综合| 精品人妻伦九区久久AAA片69| 国产亚洲欧美精品久久久| 欧美成a人片免费看久久| 久久精品国产亚洲AV嫖农村妇女| 久久久久无码国产精品不卡| 伊人久久免费视频| 久久天天躁狠狠躁夜夜网站| 久久综合给合久久国产免费| 久久天天躁狠狠躁夜夜2020| 久久99国产精品99久久| 国产成年无码久久久免费| 少妇久久久久久久久久| 色婷婷久久综合中文久久蜜桃av| 久久久久免费视频| 成人精品一区二区久久| 欧美一级久久久久久久大| 久久受www免费人成_看片中文| 亚洲乱亚洲乱淫久久| 国产人久久人人人人爽| 久久久久久毛片免费播放| 人妻少妇久久中文字幕| 国内精品久久久久影院薰衣草| 人妻无码精品久久亚瑟影视 | 精品久久久久久国产潘金莲 | 久久久久久青草大香综合精品| 久久中文字幕人妻丝袜| 久久国产视屏| 色综合久久88色综合天天 | 国产成人AV综合久久| 国产精品伊人久久伊人电影 | 久久精品亚洲日本波多野结衣 | 好久久免费视频高清|