Atšķirība starp pakalpojumu un lietojumprogrammu. Kuri Windows pakalpojumi ir nepieciešami un kurus var atspējot. Uz trigeriem balstītu pakalpojumu parādīšanās

No programmatūras saderības viedokļa. Tāpēc ir tikai dabiski, ka mēs atgriežamies pie pakalpojumu apspriešanas operētājsistēmas Windows 7 kontekstā. Taču šoreiz mēs runāsim par dažām operētājsistēmā Windows 7 pieejamo pakalpojumu optimizēšanas priekšrocībām. Šis raksts ir par jaunu līdzekli sistēmā Windows 7. Iedarbināt sākuma pakalpojumus. Bet pirms mēs aplūkojam API, apskatīsim pakalpojumu kopējo ainu.

Kas ir pakalpojumi?

Pakalpojums ir iekšējs mehānisms, kas iebūvēts Windows operētājsistēmā. Pakalpojumus var uzskatīt par īpašām lietojumprogrammām, kas darbojas neatkarīgi no pašreizējā lietotāja konteksta. Pakalpojumi atšķiras no parastajām lietojumprogrammām ar to, ka tos var konfigurēt, lai tie darbotos no sistēmas ieslēgšanas (sāknēšanas) līdz izslēgšanai, neprasot lietotāja klātbūtni. Tas nozīmē, ka pakalpojumi var darboties pat tad, ja lietotājs nav pieteicies.

Mēs labprātāk uztveram pakalpojumus kā tādus uzdevumus, kas darbojas fonā un neietekmē lietotāja darbības. Pakalpojumi operētājsistēmā Windows ir atbildīgi par visa veida fona darbībām, sākot ar attālo procedūru izsaukumu (RPC), printera spolētāju un līdz pat tīkla atrašanās vietas noteikšanai.

Gadu gaitā Windows ir pieaudzis, un līdz ar to arī pakalpojumu skaits. Būsim godīgi, fona pakalpojumi operētājsistēmā Windows ir nedaudz sāpīgi — operētājsistēmā ir iekļauti daudzi pakalpojumi. Turklāt neatkarīgi programmatūras izstrādātāji (ISV) un to lietojumprogrammas pievieno vēl vairāk pakalpojumu. Piemēram, programmatūras atjaunināšanas pakalpojumi. Tomēr daži pakalpojumi ir kritiski un ir nepieciešami sāknēšanas procesa laikā, savukārt citi ir nepieciešami vēlāk, kad konkrēts lietotājs piesakās, un citi nav jāsāk vispār, līdz tie tiek izsaukti. Neskatoties uz to, aplūkojot pašlaik darbojošos pakalpojumu sarakstu, jūs redzat daudzus objektus, kuriem nav jādarbojas 24x7.

Kas vainas pakalpojumiem, kas darbojas 24 stundas diennaktī, 7 dienas nedēļā?

Ir vairākas problēmas, kas saistītas ar diennakts pakalpojumiem. Pirmkārt, kāpēc kaut kam vajadzētu darboties (pat fonā), ja tas nav vajadzīgs? Jebkurš darbības process (ieskaitot pakalpojumus) patērē vērtīgus atmiņas un CPU resursus, ko varētu izmantot citām lietojumprogrammām un pakalpojumiem. Ja saskaitāt visus pakalpojumus, kas darbojas noteiktā brīdī, tie kopā veido ievērojamu atmiņas, rokturu, pavedienu un CPU lietojuma apjomu. Visi šie "iztērētie" resursi samazina datora kopējo veiktspēju, samazina tā reaģētspēju un liek datoram izskatīties gausam un lēnam. Turklāt, tā kā daudzi pakalpojumi ir konfigurēti, lai palaistu automātiski (sāk darboties, kad sistēma tiek startēta), tie ietekmē datora sāknēšanas laiku.

Otrkārt, šie izniekotie resursi tieši ietekmē enerģijas patēriņu. Jo lielāka ir CPU slodze, jo vairāk enerģijas patērē dators. Tas var būt ļoti svarīgi klēpjdatoriem un var samazināt akumulatora darbības laiku par vairākām stundām.

Treškārt, nepārtraukta neproduktīvas programmatūras darbināšana var izraisīt atmiņas noplūdes un vispārēju sistēmas nestabilitāti. Tas noved pie lietojumprogrammu un, visbeidzot, datora kļūmes.

Visbeidzot, ja pakalpojums darbojas 24 x 7 un ja tas ir labi zināms pakalpojums (kas varētu būt katrai populārai lietojumprogrammai, piemēram, PDF lasītājs), tas rada lielu uzbrukuma virsmu. Uzbrucējs var izmantot informāciju, ka noteikta populāra lietojumprogramma instalē diennakts pakalpojumu, un mēģināt to uzlauzt, lai piekļūtu datoram.

Ņemot vērā visu iepriekš minēto, jums var rasties jautājums, kāpēc tik daudzi izstrādātāji iestata savus pakalpojumus nepārtrauktai darbībai, ja viņiem ir cita iespēja. Pat pirms Windows 7 pakalpojumu palaišanai bija pieejamas vairākas iespējas:

  • Atspējots pilnībā atspējo pakalpojumu un neļauj tam un atkarīgiem pakalpojumiem startēt — tas nozīmē, ka lietotājam pakalpojums ir jāiespējo manuāli no vadības paneļa vai komandu uzvednes
  • Rokasgrāmata sāk pakalpojumu pēc vajadzības (citu pakalpojumu atkarību dēļ) vai kad pakalpojums tiek izsaukts no lietojumprogrammas, izmantojot atbilstošos API, kā tas tiks parādīts zemāk
  • Automātiski pēc pieteikšanās sāk pakalpojumu
  • Automātiska aizkavēšanās– operētājsistēmā Windows Vista ieviests jaunāks startēšanas veids, ar kuru pakalpojums sākas pēc sāknēšanas un sākotnējo darbību pabeigšanas, kas paātrina sistēmas palaišanu.

Diemžēl daudzi ISV (ieskaitot pašu Microsoft) turpina iestatīt savus pakalpojumus uz Automated vai Automatic Delayed, jo tas šķiet vienkāršākais risinājums ikvienam. Pakalpojums vienkārši darbojas 24x7 un vienmēr ir pieejams, novēršot nepieciešamību pārbaudīt atkarības vai pakalpojuma darbību.

Ir daudz esošo pakalpojumu piemēru, kas var izmantot daudz mazāk resursu un kļūt drošāki, nestrādājot visu diennakti. Piemēram, padomājiet par atjaunināšanas pakalpojumu, kas pārbauda jaunus lietojumprogrammas atjauninājumus. Ja dators nav savienots ar tīklu un tam nav IP adreses, kāpēc tam vajadzētu darboties? Tas neko nevar darīt, kāpēc gan atstāt programmu, kas nedara neko? Padomājiet par politikas pārvaldības pakalpojumu, kas tiek izmantots, mainot grupas politikas vai kad dators pievienojas domēnam vai atstāj to, bet tagad, kad dators ir savienots ar manu mājas tīklu, pakalpojums atkal darbojas tukšā režīmā.

Uz trigeriem balstītu pakalpojumu parādīšanās

Iepriekš minēto problēmu risinājums ir pārvietot pakalpojumu no “vienmēr ieslēgta stāvokļa” uz cita veida fona darbībām, piemēram, ieplānotiem uzdevumiem vai aktivizētiem pakalpojumiem. Šis raksts ir par Windows 7 Trigger Start Services. Par operētājsistēmas Windows 7 ieplānotajiem uzdevumiem var teikt daudz interesantu lietu, kas tiks darīts nākamajos rakstos.

Pēdējo reizi atjaunināts: 31.10.2015

Viens no svarīgākajiem Windows OS komponentiem ir pakalpojumi. Faktiski tās ir atsevišķas lietojumprogrammas, kurām nav grafiskā interfeisa un kuras fonā veic dažādus uzdevumus. Pakalpojumus var palaist operētājsistēmas startēšanas brīdī vai jebkurā citā laikā, kad lietotājs strādā. Izplatīts pakalpojumu piemērs ir dažādi tīmekļa serveri, kas fonā klausās konkrētu portu savienojumu izveidei, un, ja ir savienojumi, tie mijiedarbojas ar tiem. Tie var būt arī dažādi citu instalēto programmu atjaunināšanas palīgpakalpojumi, kas sazinās ar serveri, lai noskaidrotu, vai ir pieejama jauna lietojumprogrammas versija. Kopumā mēs varam atvērt pakalpojumu paneli un paši redzēt visus instalētos un darbotos pakalpojumus:

Apskatīsim, kā izveidot savus pakalpojumus C#. Kā īstenojamo uzdevumu mēs izvēlēsimies uzraudzīt izmaiņas noteiktā failu sistēmas mapē. Tagad izveidosim pakalpojumu, lai to izpildītu.

Vispirms izveidosim jaunu projektu, kura tips būs Windows Service. Sauksim projektu FileWatcherService:

Pēc tam Visual Studio ģenerē projektu, kurā ir viss nepieciešamais. Lai gan mums nav obligāti jāizvēlas šāda veida projekts, mēs varētu izveidot klases bibliotēkas projektu un pēc tam definēt tajā visas nepieciešamās klases.

Tātad jaunais projekts izskatās šādi:

Ir arī fails Program.cs un faktiskais pakalpojuma mezgls Service1.cs.

Pakalpojums ir parasta lietojumprogramma, taču tā netiek startēta pati par sevi. Visi zvani un piekļuve tam notiek caur pakalpojumu kontroles pārvaldnieku (Service Control Manager vai SCM). Kad pakalpojums sākas automātiski sistēmas startēšanas laikā vai manuāli, SCM izsauc galveno metodi programmā Programmas klasē:

Statiskā klase programma ( static void Main() ( ServiceBase ServicesToRun; ServicesToRun = new ServiceBase ( new Service1() ); ServiceBase.Run(ServicesToRun); ) )

Galvenā metode pēc noklusējuma ir definēta, lai vienlaikus palaistu vairākus pakalpojumus, kas ir definēti masīvā ServicesToRun. Tomēr pēc noklusējuma projektā ir tikai viens pakalpojums Service1. Pati palaišana tiek veikta, izmantojot Palaist metodi: ServiceBase.Run(ServicesToRun) .

Pakalpojumu, kas tiek palaists, attēlo Service1.cs mezgls. Tomēr patiesībā tas nav vienkāršs koda fails. Atverot šo mezglu, mēs redzēsim pakalpojumu noformētāja failu Service1.Designer.cs un Service1 klasi.

Service1 klase faktiski apzīmē pakalpojumu. Pēc noklusējuma tam ir šāds kods:

Sistēmas izmantošana; izmantojot System.Collections.Generic; izmantojot System.ComponentModel; izmantojot System.Data; izmantojot System.Diagnostics; izmantojot System.Linq; izmantojot System.ServiceProcess; izmantojot System.Text; izmantojot System.Threading.Tasks; nosaukumvieta FileWatcherService ( publiska daļēja klase Service1: ServiceBase ( publiskais pakalpojums1() ( InitializeComponent(); ) protected override void OnStart(string args) ( ) protected override void OnStop() ( ) ) )

Pakalpojuma klasei ir jābūt mantotai no ServiceBase bāzes klases. Šī klase definē vairākas metodes, no kurām svarīgākās ir OnStart() metode, kas sāk servisa veiktās darbības, un OnStop() metode, kas aptur servisu.

Pēc tam, kad SCM izsauc galveno metodi un reģistrē pakalpojumu, tas tiek tieši izsaukts, palaižot OnStart metodi.

Kad pakalpojumu konsolē vai komandrindā nosūtām komandu pārtraukt pakalpojumu, SCM izsauc OnStop metodi, lai to apturētu.

Papildus šīm divām pakalpojumu klases metodēm varat ignorēt vēl vairākas ServiceBase bāzes klases metodes:

    OnPause: tiek izsaukts, kad pakalpojums ir apturēts

    OnContinue: tiek izsaukts, kad pakalpojums tiek atsākts pēc tā apturēšanas

    OnShutdown: tiek izsaukts, kad sistēma Windows tiek izslēgta

    OnPowerEvent: tiek izsaukts, kad mainās barošanas režīms

    OnCustomCommand: tiek izsaukts, kad pakalpojums saņem pielāgotu komandu no pakalpojumu vadības pārvaldnieka (SCM).

Service1 klases konstruktorā tiek izsaukta metode InitializeComponent(), kas ir definēta dizainera failā Service1.Designer.cs:

Nosaukumtelpa FileWatcherService ( daļēja klase Service1 ( privātā System.ComponentModel.IContainer komponenti = null; aizsargāta ignorēšana void Dispose(bool disposing) ( if (disposing && (components != null)) ( komponenti.Dispose(); ) base.Dispose(disposing ); ) private void InitializeComponent() ( komponenti = new System.ComponentModel.Container(); this.ServiceName = "Service1"; ) ) )

Vienīgais, kas tajā ir jāatzīmē, ir pakalpojuma nosaukuma iestatīšana (ServiceName rekvizīts):

This.ServiceName = "Pakalpojums1";

Šis ir nosaukums, kas tiks parādīts pakalpojumu konsolē pēc šī pakalpojuma instalēšanas. Mēs varam to mainīt vai atstāt tādu, kāds tas ir.

Tagad mainīsim pakalpojuma kodu šādi:

Sistēmas izmantošana; izmantojot System.ServiceProcess; izmantojot System.IO; izmantojot System.Threading; nosaukumvieta FileWatcherService ( publiska daļēja klase Service1: ServiceBase ( Logger logger; public Service1() ( InitializeComponent(); this.CanStop = true; this.CanPauseAndContinue = true; this.AutoLog = true; ) aizsargāta ignorēšana void OnStart(virknes args) ( logger = new Logger(); Thread.Sleep(1000); ) ) klases reģistrētājs ( FileSystemWatcher vērotājs; objekts obj = jauns objekts(); bool iespējots = patiess; publiskais reģistrētājs() ( watcher = new FileSystemWatcher("D:\\Temp"); watcher.Deleted += Watcher_Deleted; watcher.Created + = Watcher_Created; Watcher.Changed += Watcher.Renamed += Watcher_Renamed = false = false ) // failu pārdēvēšana private void Watcher_Renamed(objekta sūtītājs, RenamedEventArgs e) ( string fileEvent = "pārdēvēts uz " + e.FullPath; virkne filePath = e.OldFullPath; RecordEntry(faila notikums, faila ceļš); ) // failu mainīšana privātā void Watcher_Changed(objekta sūtītājs, FileSystemEventArgs e) ( string fileEvent = "mainīts"; virkne filePath = e.FullPath; RecordEntry(fileEvent, filePath); ) // failu izveidošana privāts void Watcher_Created(objectEvent, FileSys e) ( virkne fileEvent = "izveidots"; virkne filePath = e.FullPath; RecordEntry(fileEvent, filePath); ) // failu dzēšana private void Watcher_Deleted(objekta sūtītājs, FileSystemEventArgs e) ( virkne fileEvent = "dzēsts"; virknes filePath = e.FullPath; RecordEntry(fileEvent, filePath privāts void RecordEntry(string fileEvent, string filePath) ( lock (obj) ( izmantojot (StreamWriter rakstītājs = new StreamWriter("D:\\templog.txt", true)) ( rakstītājs); .WriteLine(String.Format("(0) fails (1) bija (2)", DateTime.Now.ToString("dd/MM/gggg hh:mm:ss"), filePath, fileEvent)); ; ) ) )

Galvenā klase, kas ietver visu funkcionalitāti, ir Logger klase. Izmantojot FileSystemWatcher objektu, tas pārraudzīs izmaiņas mapē D://Temp. Sākt() metode norāda, ka mēs skatīsim izmaiņas, izmantojot FileSystemWatcher objektu. Un viss darbs turpināsies tik ilgi, kamēr iespējotais Būla mainīgais ir patiess. Un Stop() metode ļaus klasei beigties.

FileSystemWatcher notikumi ļauj pārraudzīt visas izmaiņas skatītajā mapē. Tas ierakstīs izmaiņas failā templog.txt. Lai izvairītos no resursu sacensībām failam templog.txt, kurā tiek ierakstītas izmaiņas, ierakstīšanas procedūru bloķē lock(obj) stubs.

Rezultātā pēc izveidošanas, mainīšanas, pārdēvēšanas un dzēšanas žurnālfailā būs kaut kas līdzīgs:

30.07.2015 12:15:40 fails D:\Temp\Jauns teksta dokuments.txt tika izveidots 07/30/2015 12:15:46 fails D:\Temp\New text document.txt tika pārdēvēts par D:\ Temp\sveiki /2015 12:16:01 fails D: \Temp\hello.txt ir izdzēsts

Pakalpojuma klasē Service1 konstruktorā ir iestatītas vairākas opcijas:

This.CanStop = taisnība; // šo pakalpojumu var apturēt.CanPauseAndContinue = true; // pakalpojumu var apturēt un pēc tam turpināt šo.AutoLog = true; // pakalpojums var rakstīt žurnālā

OnStart() metodē tiek izsaukts jauns pavediens, lai palaistu Logger objektu:

Aizsargāta ignorēšana void OnStart(string args) ( logger = new Logger(); Thread loggerThread = new Thread(new ThreadStart(logger.Start)); loggerThread.Start(); )

Jaunais pavediens ir nepieciešams, jo pašreizējais pavediens apstrādā tikai SCM komandas un pēc iespējas ātrāk jāatgriežas no OnStart metodes.

Kad no SCM tiek saņemta komanda apturēt pakalpojumu, tiek aktivizēta OnStop metode, kas izsauc logger.Stop() metodi. Papildu aizkave ļaus apturēt reģistrētāja pavedienu:

Aizsargāta ignorēšana void OnStop() ( logger.Stop(); Thread.Sleep(1000); )

Taču ar pašu servisa klasi nepietiek. Mums ir arī jāizveido servisa instalētājs.

Vai arī lietotāju (gan lokālo, gan attālo) darbvirsma, tomēr dažiem pakalpojumiem ir iespējams izņēmums - mijiedarbība ar konsoli (sesijas numurs 0, kurā lietotājs ir reģistrēts lokāli vai uzsākot pakalpojumu mstsc ar /console slēdzi).

Ir vairāki pakalpojumu režīmi:

  • aizliegts palaist;
  • manuāla palaišana (pēc pieprasījuma);
  • automātiska palaišana, kad dators sāk darboties;
  • automātiska (aizkavēta) palaišana (ieviesta operētājsistēmās Windows Vista un Windows Server 2008);
  • obligātais serviss/vadītājs (automātiska palaišana un nespēja (lietotājam) apturēt servisu).

Fona režīms

Sāciet, apturiet un mainiet Windows pakalpojumus

Pakalpojumus un to atribūtus var mainīt MMC:

Dažādām operētājsistēmu versijām var būt daži pakalpojumi, bet citi nav. Dažas programmas un programmas, kas tiek instalētas atsevišķi, var arī izveidot savus pakalpojumus.

Microsoft Windows operētājsistēmas pakalpojumu saraksts

Parādāmais vārds Pakalpojuma nosaukums Funkcijas Apraksts
DHCP klients Dhcp Reģistrē un atjaunina šī datora IP adreses un DNS ierakstus. Ja šis pakalpojums tiks apturēts, šis dators nevarēs iegūt dinamiskas IP adreses un veikt DNS atjauninājumus.
DNS klients Dnscache DNS klienta pakalpojums (dnscache) kešatmiņā saglabā domēna nosaukumu sistēmas (DNS) nosaukumus un reģistrē konkrētā datora pilnībā kvalificētu nosaukumu. Ja pakalpojums tiek apturēts, DNS nosaukuma noteikšana turpināsies. Tomēr DNS nosaukumu rindu rezultāti netiks saglabāti kešatmiņā un datora nosaukums netiks reģistrēts.
KtmRm izplatītajam darījumu koordinatoram KtmRm Koordinē darījumus starp MSDTC un Kernel Transaction Manager (KTM).
ReadyBoost EMDMgmt ReadyBoost Atbalsts sistēmas veiktspējas uzlabošanai, izmantojot tehnoloģiju ReadyBoost.
Superfetch SysMain Superfetch Uztur un uzlabo sistēmas veiktspēju.
Windows audio Audiosrv Audio rīku pārvaldība Windows programmām. Ja šis pakalpojums tiek apturēts, audio ierīces un efekti nedarbosies pareizi.
Windows CardSpace idsvc Nodrošina drošu iespēju izveidot, pārvaldīt un atklāt digitālās identitātes.
Automātiska atjaunināšana WUAUSERV Ietver Windows atjauninājumu lejupielādi un instalēšanu. Ja pakalpojums ir atspējots, šis dators nevarēs izmantot automātisko atjaunināšanu vai Windows atjaunināšanas vietni.
Attālās procedūras izsaukums (RPC) RpcSs Nodrošina kartēšanu starp galapunktiem un citiem RPC pakalpojumiem.

Microsoft lietojumprogrammu un programmu izveidoto pakalpojumu saraksts

Trešo pušu lietojumprogrammu un programmu izveidoto pakalpojumu piemēri

Parādāmais vārds Pakalpojuma nosaukums Funkcijas Apraksts
ESET HTTP serveris EhttpSrv pretvīrusu aizsardzība ESET HTTP servera komponents

Kā palaist lietojumprogrammu kā Windows pakalpojumu

Vai ir iespējams palaist klienta lietojumprogrammu kā pakalpojumu? Vienā no tiem es aprakstīju veidus, kā izveidot Windows pakalpojumu, izmantojot standarta OS rīkus. Tomēr ne katra konsoles lietojumprogramma var darboties kā pakalpojums, un programmas ar grafisko interfeisu principā nevar darboties šādā veidā. Bet joprojām ir iespējams palaist lietojumprogrammu kā pakalpojumu, un programma ar oriģinālo nosaukumu mums palīdzēs Nepiesūcošu pakalpojumu vadītājs.

NSSM ir bezmaksas atvērtā pirmkoda programmatūra, un tā atbalsta visas Microsoft operētājsistēmas no Windows 2000 līdz Windows 8. NSSM nav nepieciešama instalēšana, vienkārši lejupielādējiet un izpakojiet to. Izplatīšanā ir iekļautas versijas 32 un 64 bitu operētājsistēmām. Programmu var dabūt no mājas lapas nssm.cc, šobrīd jaunākā stabilā versija ir 2.21.1, kuru izmantošu.

Lai demonstrētu NSSM iespējas, mēģināsim palaist Windows Notepad kā pakalpojumu operētājsistēmā Windows 8.1.

Pakalpojuma izveide

Lai izveidotu pakalpojumu ar nosaukumu piezīmju grāmatiņa palaidiet komandu konsoli, dodieties uz mapi ar neizpakoto NSSM (64 bitu Windows) un ievadiet komandu nssm install notepad, kas atver NSSM grafiskās instalēšanas logu. Lai izveidotu pakalpojumu, laukā Path norādiet izpildāmā faila ceļu un noklikšķiniet uz pogas "Instalēt pakalpojumu". Turklāt laukā Opcijas varat norādīt atslēgas, kas nepieciešamas pakalpojuma palaišanai.

Veidojot jaunu pakalpojumu, varat norādīt arī dažus papildu parametrus.

Cilnē Shutdown ir norādītas izslēgšanas metodes un taimauta, kas tiek izmantota, kad lietojumprogramma parasti izslēdzas vai avarē. Kad NSSM saņem apturēšanas komandu (piemēram, kad lietojumprogramma tiek izslēgta), tas mēģina apturēt kontrolēto lietojumprogrammu parastā veidā. Ja lietojumprogramma nereaģē, NSSM var piespiedu kārtā pārtraukt visus šīs lietojumprogrammas procesus un apakšprocesus.

Lietojumprogrammas izslēgšanai ir pavisam četri posmi, un pēc noklusējuma tie tiks izmantoti šādā secībā:

Pirmajā posmā NSSM mēģina ģenerēt un nosūtīt notikumu Ctrl+C.Šī metode labi darbojas konsoles lietojumprogrammām vai skriptiem, bet nav piemērojama grafiskām lietojumprogrammām;
Pēc tam NSSM nosaka visus lietojumprogrammas izveidotos logus un nosūta tiem WM_CLOSE ziņojumu, izraisot lietojumprogrammas aizvēršanu;
Trešais solis ir tāds, ka NSSM aprēķina visus lietojumprogrammas izveidotos pavedienus un nosūta tiem WM_QUIT ziņojumu, kas tiks saņemts, ja lietojumprogrammā ir pavedienu ziņojumu rinda;
Kā pēdējo līdzekli NSSM var izsaukt TerminateProcess() metodi, liekot lietojumprogrammai pārtraukt darbību.

Ir iespējams atspējot dažas vai pat visas metodes, taču dažādām lietojumprogrammām darbojas dažādas metodes, un ir ieteicams atstāt visu, kā ir, lai nodrošinātu lietojumprogrammas pareizu izslēgšanu.

Pēc noklusējuma, kad pakalpojums avarē, NSSM mēģina to restartēt. Cilnē “Izejas darbības” varat mainīt automātisko darbību, kad lietojumprogramma tiek pārtraukta neparasti, kā arī iestatīt aizkavi pirms lietojumprogrammas automātiskās restartēšanas.

Cilnē “Ievade/Izvade (I/O)” varat iestatīt lietojumprogrammas ievades/izejas novirzīšanu uz noteiktu failu.

Cilnē “Vide” pakalpojumam varat iestatīt jaunus vides mainīgos vai ignorēt esošos.

Varat arī neizmantot grafisko apvalku un nekavējoties izveidot pakalpojumu konsolē ar šādu komandu:

nssm instalējiet notepad ″C:\Windows\system32\notepad.exe″

Pakalpojumu vadība

Pēc pakalpojuma izveides, izmantojot NSSM, dodieties uz pakalpojumu papildinājumu un atrodiet piezīmju grāmatiņas pakalpojumu. Kā redzat, pēc izskata tas neatšķiras no citiem pakalpojumiem, mēs to varam arī palaist, apturēt vai mainīt palaišanas režīmu. Tomēr ņemiet vērā, ka nssm.exe ir norādīts kā izpildāmais fails.

Un, ja mēs pārejam uz uzdevumu pārvaldnieku, mēs redzēsim šādu attēlu: NSSM darbojas kā galvenais (vecāks) process, notepad pakalpojums darbojas kā tā atvasinātais process, un Notepad lietojumprogramma jau darbojas šajā pakārtotajā procesā.

Pakalpojuma noņemšana

Lai noņemtu pakalpojumu, ievadiet komandu nssm remove notepad un apstipriniet tās noņemšanu. Un, ievadot komandu nssm remove notepad apstiprināt , jūs varat iztikt bez apstiprinājuma.

Sāciet pakalpojumu interaktīvi

Galvenā atšķirība starp lietotāja lietojumprogrammu un pakalpojumu ir tāda, ka pēc palaišanas lietojumprogrammai var būt nepieciešamas papildu lietotāja darbības, lai turpinātu darbību, piemēram, pogas nospiešanu vai komandas ievadīšanu. Lai to izdarītu, jums ir jāpiekļūst tam, kas, kā izrādās, nav tik vienkārši izdarāms.

Lai sāktu pakalpojumu interaktīvā režīmā, tā rekvizīti ir jāatver pakalpojumu papildprogrammā un cilnē “Pieteikšanās” atzīmējiet izvēles rūtiņu “Atļaut mijiedarbību ar darbvirsmu”.

Un tad sākas brīnumi :) Interaktīvā režīmā palaists serviss atveras izolētā sesijā (0.sesija). Šai sesijai var piekļūt, tikai izmantojot interaktīvo pakalpojumu noteikšanas pakalpojumu (ui0detect), kas uzrauga interaktīvo pakalpojumu palaišanu datorā un izdod brīdinājumu. Operētājsistēmā Windows 7\Server 2008 šis pakalpojums ir aktīvs pēc noklusējuma, bet operētājsistēmā Windows 8\Server 2012 tas ir atspējots un neparādās pakalpojumu grafiskajā papildprogrammā (vismaz es to tur neatradu). Turklāt, ja atrodat šo noslēpumaino pakalpojumu un mēģināsit to palaist, jūs saņemsit kļūdas ziņojumu.

Taču fakts ir tāds, ka, lai to palaistu, datorā ir jāļauj darboties interaktīvajiem pakalpojumiem. Tāpēc atveriet reģistra redaktoru, atrodiet sadaļā HKLM\System\CurrentControlSet\Control\Windows DWORD tipa parametru ar nosaukumu NoInteractiveServices un iestatiet tā vērtību uz 0 .

Pēc tam atveriet PowerShell konsoli un sāciet atklāšanas pakalpojumu ar komandu:

Start-Service -Name ui0detect

Pārliecinoties, ka noteikšanas pakalpojums darbojas, mēs restartējam piezīmju grāmatiņas pakalpojumu, un tiek parādīts šis logs. Izvēlieties "Skatīt ziņojumu"

un mēs atrodamies nulles sesijā, kurā darbojas mūsu lietojumprogramma. Tad mēs ar to veicam nepieciešamās darbības un atgriežamies atpakaļ.

Šis ir interesants risinājums lietojumprogrammu palaišanai kā Windows pakalpojumiem. Nav pati skaistākā, bet gluži atbilst nosaukumam :)


Windows NT pakalpojums ir īpašs process, kam ir vienots interfeiss mijiedarbībai ar Windows NT operētājsistēmu. Pakalpojumi ir sadalīti divos veidos - Win32 pakalpojumos, kas mijiedarbojas ar operētājsistēmu, izmantojot pakalpojumu vadības pārvaldnieku (SCM), un draiveros, kas darbojas, izmantojot Windows NT ierīces draivera protokolu. Šajā rakstā mēs apspriedīsim tikai Win32 pakalpojumus.

Pakalpojumu pielietošana

Viena no svarīgākajām pakalpojuma īpašībām ir neinteraktivitāte. Tipisks pakalpojums darbojas fonā, vidusmēra lietotājs to nepamana. Šī iemesla dēļ pakalpojumi ir vispiemērotākie šāda veida lietojumprogrammu ieviešanai:

  • Serveri klienta-servera arhitektūrā (piemēram, MS SQL, MS Exchange Server)
  • Tīkla pakalpojumi Windows NT (serveris, darbstacija);
  • Servera (funkcionalitātes ziņā) izplatīto lietojumprogrammu komponenti (piemēram, visu veidu uzraudzības programmas).

Pakalpojumu pamatīpašības

Pakalpojums atšķiras no parastās Win32 lietojumprogrammas ar 3 galvenajām īpašībām. Apskatīsim katru no tiem.

Pirmkārt, ir iespējams pareizi apturēt (apturēt) pakalpojumu. Lietotājam vai citai lietojumprogrammai, kas izmanto standarta mehānismus, ir iespēja mainīt pakalpojuma stāvokli - pārvietot to no darba stāvokļa uz apturētu stāvokli vai pat apturēt tā darbību. Šajā gadījumā pakalpojums pirms stāvokļa maiņas saņem īpašu paziņojumu, pateicoties kuram tas var veikt darbības, kas nepieciešamas pārejai uz jaunu stāvokli, piemēram, atbrīvot aizņemtos resursus.

Otrkārt, iespēja palaist servisu pirms lietotāja reģistrēšanas un līdz ar to iespēja strādāt bez reģistrēta lietotāja vispār. Jebkuru pakalpojumu var palaist automātiski, kad operētājsistēma tiek startēta, un sākt darboties pat pirms lietotāja pieteikšanās sistēmā.

Un visbeidzot – spēja strādāt patvaļīgā drošības kontekstā. Windows NT drošības konteksts definē piekļuves tiesību kopu procesam dažādiem sistēmas objektiem un datiem. Atšķirībā no tipiskas Win32 lietojumprogrammas, kas vienmēr darbojas tā lietotāja drošības kontekstā, kurš pašlaik ir pieteicies sistēmā, pakalpojumam tā izpildes drošības kontekstu var noteikt iepriekš. Tas nozīmē, ka pakalpojumam var būt iepriekš noteikts piekļuves tiesību kopums sistēmas objektiem un tādējādi ierobežot tā darbību apjomu. Pakalpojumiem ir īpašs noklusējuma drošības konteksta veids, ko sauc par vietējo sistēmu. Pakalpojumam, kas darbojas šajā kontekstā, ir tiesības tikai uz resursiem vietējā datorā. Nekādas tīkla darbības nevar veikt ar vietējās sistēmas tiesībām, jo ​​šim kontekstam ir nozīme tikai lokālajā datorā un citi tīkla datori to neatpazīst.

Pakalpojuma mijiedarbība ar citām lietojumprogrammām

Jebkura lietojumprogramma, kurai ir atbilstošas ​​tiesības, var mijiedarboties ar pakalpojumu. Mijiedarbība, pirmkārt, ietver pakalpojuma stāvokļa maiņu, tas ir, tā pārsūtīšanu uz vienu no trim stāvokļiem - darbojas (Start), apturēta (Pauze), apturēšana un tiek veikta, iesniedzot SCM pieprasījumus. Pieprasījumi ir trīs veidu - ziņojumi no pakalpojumiem (nosaka to stāvokļus), pieprasījumi, kas saistīti ar pakalpojuma konfigurācijas maiņu vai informācijas iegūšanu par to, un lietojumprogrammu pieprasījumi mainīt pakalpojuma stāvokli.

Lai pārvaldītu pakalpojumu, vispirms ir jāiegūst tā rokturis, izmantojot OpenService Win32 API funkciju. Funkcija StartService sāk pakalpojumu. Ja nepieciešams, pakalpojuma stāvoklis tiek mainīts, izsaucot funkciju ControlService.

Pakalpojumu datu bāze

Informācija par katru pakalpojumu tiek glabāta reģistrā - atslēgā HKLM\SYSTEM\CurrentControlSet\Services\ServiceName. Tajā ir šāda informācija:

  • Pakalpojuma veids. Norāda, vai šī lietojumprogramma ievieš tikai vienu pakalpojumu (ekskluzīvu) vai arī lietojumprogrammā ir vairāki no tiem. Ekskluzīvs pakalpojums var darboties jebkurā drošības kontekstā. Vairāki pakalpojumi vienā lietojumprogrammā var darboties tikai vietējās sistēmas kontekstā.
  • Palaišanas veids. Automātiski — pakalpojums sākas sistēmas startēšanas brīdī. Pēc pieprasījuma - pakalpojumu manuāli sāk lietotājs. Deaktivizēts — pakalpojumu nevar palaist.
  • Izpildāmā moduļa nosaukums (EXE fails).
  • Startēšanas pasūtījums saistībā ar citiem pakalpojumiem. Dažos gadījumos, lai pakalpojums darbotos pareizi, ir jādarbojas vienam vai vairākiem citiem pakalpojumiem. Šajā gadījumā reģistrā ir informācija par pakalpojumiem, kas sākti pirms šī.
  • Pakalpojuma izpildes drošības konteksts (tīkla nosaukums un parole). Pēc noklusējuma drošības konteksts ir LocalSystem.

Lietojumprogrammām, kas vēlas izgūt informāciju par pakalpojumu vai mainīt pakalpojuma iestatījumu, būtībā jāmaina informācija pakalpojuma datubāzē reģistrā. To var izdarīt, izmantojot atbilstošās Win32 API funkcijas:

  • OpenSCManager, CreateService, OpenService, CloseServiceHandle - lai izveidotu (atvērtu) pakalpojumu;
  • QueryServiceConfig, QueryServiceObjectSecurity, EnumDependentServices, EnumServicesStatus - lai iegūtu informāciju par pakalpojumu;
  • ChangeServiceConfig, SetServiceObjectSecurity, LockServiceDatabase, UnlockServiceDatabase, QueryServiceLockStatus — lai mainītu pakalpojuma konfigurācijas informāciju.

Pakalpojuma iekšējā struktūra.

Lai tas notiktu, aplikācijai ir jābūt attiecīgi strukturētai, proti, jāiekļauj noteikts funkciju kopums (C++ izteiksmē) ar noteiktu funkcionalitāti. Īsi apskatīsim katru no tiem.

galvenā funkcija

Kā jūs zināt, galvenā funkcija ir jebkuras Win32 konsoles lietojumprogrammas ieejas punkts. Kad pakalpojums sākas, vispirms tiek izpildīts šīs funkcijas kods. 30 sekunžu laikā no sākuma galvenajai funkcijai ir jāizsauc StartServiceCtrlDispatcher, lai izveidotu savienojumu starp lietojumprogrammu un SCM. Visi sakari starp jebkuru pakalpojumu noteiktā lietojumprogrammā un SCM tiek veikti funkcijā StartServiceCtrlDispatcher, kas tiek pārtraukta tikai pēc tam, kad visi lietojumprogrammas pakalpojumi ir apturēti.

ServiceMain funkcija

Papildus procesa mēroga ievades punktam katram lietojumprogrammā ieviestajam pakalpojumam ir arī atsevišķs ieejas punkts. To funkciju nosaukumi, kas ir pakalpojuma ievades punkti (vienkāršības labad sauksim tās visas vienādi - ServiceMain), tiek nodoti SCM vienā no parametriem, izsaucot StartServiceCtrlDispatcher. Kad katrs pakalpojums sākas, tiek izveidots atsevišķs pavediens, lai izpildītu ServiceMain.

Pēc kontroles saņemšanas pakalpojumam ServiceMain vispirms ir jāreģistrē pakalpojuma pieprasījumu apstrādātājs, funkcija Apdarinātājs, katram pakalpojumam lietojumprogrammā. Tam parasti ServiceMain seko dažas darbības, lai inicializētu pakalpojumu - atmiņas piešķiršana, datu nolasīšana utt. Šīm darbībām ir jāpievieno SCM paziņojumi, ka pakalpojums joprojām tiek palaists un nav radušās nekādas kļūmes. Paziņojumi tiek nosūtīti, izmantojot SetServiceStatus funkcijas izsaukumus. Visiem zvaniem, izņemot pašu pēdējo, ir jābūt ar parametru SERVICE_START_PENDING, bet pēdējam – ar parametru SERVICE_RUNNING. Zvanu biežumu nosaka pakalpojuma izstrādātājs, pamatojoties uz šādu nosacījumu: laika intervāla ilgums starp diviem blakus esošajiem SetServiceStatus izsaukumiem nedrīkst pārsniegt parametra dwWaitHint vērtību, kas tika nodots SCM pirmajā no diviem zvaniem. Pretējā gadījumā SCM, savlaicīgi nesaņemot nākamo paziņojumu, piespiedu kārtā apturēs pakalpojumu. Šī metode ļauj izvairīties no pakalpojuma sākuma situācijas, kas rodas noteiktu kļūmju rašanās rezultātā (atcerieties, ka pakalpojumi parasti nav interaktīvi un tos var palaist lietotāja prombūtnes laikā). Parastā prakse ir tāda, ka SCM tiek paziņots pēc nākamās inicializācijas darbības pabeigšanas.

Apdarinātāja funkcija

Kā minēts iepriekš, apdarinātājs ir atzvanīšanas funkcijas prototips, pakalpojuma pieprasījumu apstrādātājs, kas ir unikāls katram pakalpojumam lietojumprogrammā. Apdarinātājs tiek izsaukts, kad pakalpojums saņem pieprasījumu (sākt, pauze, atsākt, apturēt, pašreizējā stāvokļa ziņojumu) un veic nepieciešamās darbības saskaņā ar pieprasījumu, pēc tam ziņo par jauno stāvokli SCM.

Īpaši jāatzīmē viens pieprasījums - pieprasījums, kas saņemts, izslēdzot sistēmu (Shutdown). Šis pieprasījums norāda uz nepieciešamību deinitializēt un iziet. Microsoft saka, ka katram pakalpojumam tiek dotas 20 sekundes, lai tas tiktu izslēgts, pirms tas ir spiests pārtraukt. Tomēr testi ir parādījuši, ka šis nosacījums ne vienmēr tiek izpildīts un pakalpojums ir spiests pārtraukt pirms šī laika perioda beigām.

Servisa drošības sistēma

Jebkurai darbībai ar pakalpojumiem ir nepieciešamas atbilstošas ​​lietojumprogrammas tiesības. Visām lietojumprogrammām ir tiesības izveidot savienojumu ar SCM, uzskaitīt pakalpojumus un pārbaudīt, vai pakalpojumu datu bāze nav bloķēta. Tikai lietojumprogrammas ar administratīvām tiesībām var reģistrēt jaunu pakalpojumu sistēmā vai bloķēt pakalpojumu datu bāzi.

Katram pakalpojumam ir drošības deskriptors, kas apraksta, kuriem lietotājiem ir tiesības uz kādu darbību. Noklusējums:

  • Visiem lietotājiem ir SERVICE_QUERY_CONFIG, SERVICE_QUERY_STATUS, SERVICE_ENUMERATE_DEPENDENTS, SERVICE_INTERROGATE un SERVICE_USER_DEFINED_CONTROL tiesības;
  • Lietotājiem, kas pieder pie Power Users grupas un LocalSystem konta, papildus ir tiesības SERVICE_START, SERVICE_PAUSE_CONTINUE un SERVICE_STOP;
  • Lietotājiem, kas pieder administratoru un sistēmas operatoru grupām, ir tiesības SERVICE_ALL_ACCESS.

Pakalpojumi un interaktivitāte

Pēc noklusējuma interaktīvie pakalpojumi var darboties tikai LocalSystem drošības kontekstā. Tas ir saistīts ar rādīšanas īpatnībām monitora ekrānā operētājsistēmā Windows NT, kur, piemēram, ir tāds objekts kā “Desktop”, lai strādātu ar kuru jums ir jābūt atbilstošām piekļuves tiesībām, kas ir patvaļīgs konts, kas nav LocalSystem. var nebūt. Neskatoties uz to, ka vairumā gadījumu šis ierobežojums nav būtisks, dažreiz ir nepieciešams izveidot pakalpojumu, kas parādītu informāciju monitora ekrānā un vienlaikus tiktu izpildīts drošības kontekstā, kas nav LocalSystem, lai Piemēram, lietojumprogrammu servera komponents lietojumprogrammu palaišanai attālā datorā.

Koda fragments no . ilustrē šo iespēju.

Šajā fragmentā, atbildot uz pieprasījumu, ko lietojumprogrammas klienta puse nosūtījusi kā RPC sekas, pakalpojums monitora ekrānā parāda īsziņu.

Pakalpojuma piemērs (atslēgas fragmenti)

Apskatīsim C++ lietojumprogrammas galveno fragmentu piemēru, kas ievieš Windows NT pakalpojumu. Skaidrības labad ir izlaistas nebūtiskas koda daļas.

galvenā funkcija

Galvenais funkcijas kods ir parādīts B.

ServiceMain funkcija

Pakalpojumā ServiceMain ietvertā koda iezīme ir tāda, ka bieži vien nav iespējams iepriekš paredzēt konkrētas darbības izpildes laiku, īpaši ņemot vērā, ka tā izpilde notiek operētājsistēmā ar preventīvu vairākuzdevumu izpildi. Ja darbība ilgst ilgāk par SetServiceStatus izsaukuma parametrā norādīto laika intervālu, pakalpojums nevarēs savlaicīgi nosūtīt nākamo paziņojumu, kā rezultātā SCM pārtrauks darbību. Potenciālo darbību piemēri ir tīkla funkciju izsaukumi ar lieliem taimautiem vai liela informācijas apjoma vienlaicīga lasīšana no lēnas informācijas nesēja. Turklāt šī pieeja ir pilnīgi nepiemērota pakalpojuma atkļūdošanai, jo programmas izpilde atkļūdotā pavada garas pauzes, kas ir nepieciešamas izstrādātājam.

Lai novērstu šo problēmu, visas darbības, kas mijiedarbojas ar SCM, ir jāveic atsevišķā pavedienā neatkarīgi no darbībām, kas notiek inicializācijas fāzē.

B parāda algoritmu pareizai pakalpojuma palaišanai, izmantojot papildu pavedienu.

Apdarinātāja funkcija

B parāda Handler funkcijas kodu un papildu pavedienus. Pieprasījumiem "Apturēt" un "Izslēgt" tiek izmantots algoritms pareizai pakalpojuma apturēšanai, līdzīgs tam, ko izmanto, uzsākot pakalpojumu, ar vienīgo atšķirību, ka parametra SERVICE_START_PENDING vietā parametrs SERVICE_STOP_PENDING tiek nodots SetserviceStatus. no SERVICE_RUNNING — SERVICE_STOPPED.

Ideālā gadījumā šī pieeja būtu jāizmanto arī pieprasījumos "Pauze" un "Turpināt". Ziņkārīgs lasītājs to var viegli īstenot, pamatojoties uz šiem piemēriem.

Secinājums

Nobeigumā vēlamies atzīmēt, ka, pārejot uz Windows NT 2000, pakalpojumu attīstība nemainījās. Pakalpojumi joprojām ir svarīga programmatūras daļa Windows platformā, sniedzot izstrādātājiem plašas iespējas.


// Funkcija, kas līdzīga MessageBox Win32 API int ServerMessageBox(RPC_BINDING_HANDLE h, LPSTR lpszText, LPSTR lpszTitle, UINT fuStyle) ( DWORD dwThreadId; HWINSTA hwinstaSave; HDESK hdeskSave int HWINtKESTA; HWINtUSKrezultāts; HWINtUSK s " Logs stacija " un "Desktop". GetDesktopWindow(); hwinstaSave = GetProcessWindowStation(); dwThreadId = GetCurrentThreadId(); hdeskSave = GetThreadDesktop(dwThreadId); // Mainiet drošības kontekstu uz to RPC un //, kuru izsauc klients iegūt piekļuvi lietotājam // objektiem "Window station" un "Desktop" SetProcessWindowStation( hwinstaUser); ) SetThreadDesktop(hdeskUser); // Parāda parastu teksta logu. rezultāts = MessageBox(NULL, lpszText, lpszTitle, fuStyle); // Atjaunot saglabātos objektus // "Window station" un "Desktop". SetThreadDesktop(hdeskSave); SetProcessWindowStation(hwinstaSave); CloseDesktop(hdeskUser); CloseWindowStation(hwinstaUser); atgriešanās rezultāts; ) void main() ( SERVICE_TABLE_ENTRY steTable = ((SERVICENAME, ServiceMain), (NULL, NULL) ); // Izveidojiet savienojumu ar SCM. Šīs funkcijas ietvaros // tiek saņemti un nosūtīti pieprasījumi. StartServiceCtrlDispatcher(steTable); ) void WINAPI ServiceMain (DWORD dwArgc, LPSTR *psArgv) ( // Nekavējoties reģistrējiet pieprasījumu apstrādātāju. hSS = RegisterServiceCtrlHandler(SERVICENAME, ServiceHandler); sStatus.dwCheckPoint = 0; sStatus.dwControlsAccepted = SERVICE_ACCEPT_ACTINUS.d wServiceType = SERVICE_WIN32_OWN_PROCESS ; sStatus.dwWaitHint = 0; katru // sekundi, ka pakalpojums ir inicializācijas procesā // Tiek izveidots notikums pavediena sinhronizēšanai. // Pēc tam tiek palaists darbinieka pavediens, // kuram tiek izveidots notikums. hSendStartPending = CreateEvent(NULL, TRUE, FALSE, NULL); HANDLE hSendStartThread; DWORD dwThreadId; hSendStartThread = CreateThread(NULL, 0, SendStartPending, NULL, 0, &dwThreadId); //Šeit tiek veikta visa pakalpojuma inicializācija. InitService(); SetEvent(hSendStartPending); if(WaitForSingleObject(hSendStartThread, 2000) != WAIT_OBJECT_0) ( TerminateThread(hSendStartThread, 0); ) CloseHandle(hSendStartPending); CloseHandle(hSendStartThread); hWork = CreateEvent(NULL, TRUE, FALSE, NULL); hServiceThread = CreateThread(NULL, 0, ServiceFunc, 0, 0, &dwThreadId); sStatus.dwCurrentState = PAKALPOJUMU_DARBĪBA; SetServiceStatus(hSS, &sStatus); ) // Pavedienu funkcija, kas nosūta paziņojumus uz SCM // katru sekundi, kad notiek inicializācijas process. Funkcija // beidzas, kad ir iestatīts notikums hSendStartPending //. DWORD WINAPI SendStartPending(LPVOID) ( sStatus.dwCheckPoint = 0; sStatus.dwCurrentState = SERVICE_START_PENDING; sStatus.dwWaitHint = 2000; // "Sleep" 1 sekundi. Ja pēc hS beigu signāls nav ievadīts // pēc 1 sekundes stāvokli (pakalpojuma inicializācija nav // beigusies), nosūtiet nākamo paziņojumu, // iestatiet maksimālo laika intervālu // līdz 2 sekundēm, lai līdz // nākamajam paziņojumam būtu laika rezerve, kamēr (patiess) ( SetServiceStatus(hSS, &sStatus) if(WaitForSingleObject, 1000)! Datu lasīšana, // atmiņas piešķiršana utt. void InitService() ( ... ) // Funkcija, kas satur pakalpojuma kodu. DWORD WINAPI ServiceFunc(LPVOID) ( while (true) ( if (!bPause) ( // Tas satur kodu, kas parasti // veic noteikta veida cikliskas darbības... ) if (WaitForSingleObject(hWork, 1000)!=WAIT_TIMEOUT ) break ) return 0; TRUE, FALSE, NULL); hSendStopThread = CreateThread(NULL, 0, SendStopPending, NULL, 0, & dwThreadId); if (WaitForSingleObject(hServiceThread, 1000) != WAITader (JECT_0)hre SetEvent(hSendStopPending) ; CloseHandle(hServiceThread); if(WaitForSingleObject(hSendStopThread, 2000) != WAIT_OBJECT_0) ( TerminateThread(hSendStopThread, 0); ) CloseHandle(hSstusstopS); pārtraukums; case SERVICE_CONTROL_PAUSE: bPause = true; sStatus.dwCurrentState = SERVICE_PAUSED; SetServiceStatus(hSS, &sStatus); pārtraukums; case SERVICE_CONTROL_CONTINUE: bPause = true; sStatus.dwCurrentState = PAKALPOJUMU_DARBĪBA; SetServiceStatus(hSS, &sStatus); pārtraukums; gadījums SERVICE_CONTROL_INTERROGATE: SetServiceStatus(hSS, &sStatus); pārtraukums; noklusējuma: SetServiceStatus(hSS, &sStatus); pārtraukums; ) ) // Pavediena funkcija, kas līdzīga SendStartPending //, lai apturētu pakalpojumu. DWORD WINAPI SendStopPending(LPVOID) ( sStatus.dwCheckPoint = 0; sStatus.dwCurrentState = SERVICE_STOP_PENDING; sStatus.dwWaitHint = 2000; while (true) (>SetServiceStatus(SckPoint aitForSingleObject) (hSendStopPending, 1000 )! =WAIT_TIMEOUT) pārtraukums. sStatus.