xref: /reactos/base/applications/sc/sc.c (revision d5b576b2)
1 /*
2  * PROJECT:     ReactOS Services
3  * LICENSE:     GPL - See COPYING in the top level directory
4  * FILE:        base/applications/sc/sc.c
5  * PURPOSE:     parse command line
6  * COPYRIGHT:   Copyright 2005 - 2006 Ged Murphy <gedmurphy@gmail.com>
7  *
8  */
9 
10 #include "sc.h"
11 
12 SC_HANDLE hSCManager;
13 
14 VOID
15 ReportLastError(VOID)
16 {
17     LPVOID lpMsgBuf;
18     DWORD RetVal;
19 
20     DWORD ErrorCode = GetLastError();
21     if (ErrorCode != ERROR_SUCCESS)
22     {
23         RetVal = FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER |
24                                FORMAT_MESSAGE_FROM_SYSTEM |
25                                FORMAT_MESSAGE_IGNORE_INSERTS,
26                                NULL,
27                                ErrorCode,
28                                MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), /* Default language */
29                                (LPTSTR) &lpMsgBuf,
30                                0,
31                                NULL );
32 
33         if (RetVal != 0)
34         {
35             _tprintf(_T("%s"), (LPTSTR)lpMsgBuf);
36             LocalFree(lpMsgBuf);
37         }
38     }
39 }
40 
41 
42 static INT
43 ScControl(LPCTSTR Server,       // remote machine name
44           LPCTSTR Command,      // sc command
45           LPCTSTR *ServiceArgs, // any options
46           DWORD ArgCount)       // argument counter
47 {
48     LPCTSTR ServiceName = NULL;
49 
50     if (Server)
51     {
52         _tprintf(_T("Remote service control is not yet implemented\n"));
53         return 2;
54     }
55 
56     if (!lstrcmpi(Command, _T("query")))
57     {
58         Query(ServiceArgs,
59               ArgCount,
60               FALSE);
61     }
62     else if (!lstrcmpi(Command, _T("queryex")))
63     {
64         Query(ServiceArgs,
65               ArgCount,
66               TRUE);
67     }
68     else if (!lstrcmpi(Command, _T("start")))
69     {
70         if (ArgCount > 0)
71         {
72             ServiceName = *ServiceArgs++;
73             ArgCount--;
74 
75             Start(ServiceName,
76                   ServiceArgs,
77                   ArgCount);
78         }
79         else
80             StartUsage();
81     }
82     else if (!lstrcmpi(Command, _T("pause")))
83     {
84         if (ArgCount > 0)
85         {
86             ServiceName = *ServiceArgs++;
87             ArgCount--;
88 
89             Control(SERVICE_CONTROL_PAUSE,
90                     ServiceName,
91                     ServiceArgs,
92                     ArgCount);
93         }
94         else
95             PauseUsage();
96     }
97     else if (!lstrcmpi(Command, _T("interrogate")))
98     {
99         if (ArgCount > 0)
100         {
101             ServiceName = *ServiceArgs++;
102             ArgCount--;
103 
104             Control(SERVICE_CONTROL_INTERROGATE,
105                     ServiceName,
106                     ServiceArgs,
107                     ArgCount);
108         }
109         else
110             InterrogateUsage();
111     }
112     else if (!lstrcmpi(Command, _T("stop")))
113     {
114         if (ArgCount > 0)
115         {
116             ServiceName = *ServiceArgs++;
117             ArgCount--;
118 
119             Control(SERVICE_CONTROL_STOP,
120                     ServiceName,
121                     ServiceArgs,
122                     ArgCount);
123         }
124         else
125             StopUsage();
126     }
127     else if (!lstrcmpi(Command, _T("continue")))
128     {
129         if (ArgCount > 0)
130         {
131             ServiceName = *ServiceArgs++;
132             ArgCount--;
133 
134             Control(SERVICE_CONTROL_CONTINUE,
135                     ServiceName,
136                     ServiceArgs,
137                     ArgCount);
138         }
139         else
140             ContinueUsage();
141     }
142     else if (!lstrcmpi(Command, _T("delete")))
143     {
144         if (ArgCount > 0)
145         {
146             ServiceName = *ServiceArgs++;
147             ArgCount--;
148 
149             Delete(ServiceName);
150         }
151         else
152             DeleteUsage();
153     }
154     else if (!lstrcmpi(Command, _T("create")))
155     {
156         Create(ServiceArgs, ArgCount);
157     }
158     else if (!lstrcmpi(Command, _T("control")))
159     {
160         INT ControlCode = 0;
161 
162         if (ArgCount > 1)
163         {
164             ServiceName = *ServiceArgs++;
165             ArgCount--;
166 
167             if (!lstrcmpi(ServiceArgs[0], _T("paramchange")))
168                 ControlCode = SERVICE_CONTROL_PARAMCHANGE;
169             else if (!lstrcmpi(ServiceArgs[0], _T("netbindadd")))
170                 ControlCode = SERVICE_CONTROL_NETBINDADD;
171             else if (!lstrcmpi(ServiceArgs[0], _T("netbindremove")))
172                 ControlCode = SERVICE_CONTROL_NETBINDREMOVE;
173             else if (!lstrcmpi(ServiceArgs[0], _T("netbindenable")))
174                 ControlCode = SERVICE_CONTROL_NETBINDENABLE;
175             else if (!lstrcmpi(ServiceArgs[0], _T("netbinddisable")))
176                 ControlCode = SERVICE_CONTROL_NETBINDDISABLE;
177             else
178             {
179                 ControlCode = _ttoi(ServiceArgs[0]);
180                 if ((ControlCode < 128) || (ControlCode > 255))
181                     ControlCode = 0;
182             }
183 
184             ServiceArgs++;
185             ArgCount--;
186 
187             if (ControlCode != 0)
188                 Control(ControlCode,
189                         ServiceName,
190                         ServiceArgs,
191                         ArgCount);
192             else
193                 ControlUsage();
194         }
195         else
196             ControlUsage();
197     }
198     else if (!lstrcmpi(Command, _T("sdshow")))
199     {
200         if (ArgCount > 0)
201         {
202             ServiceName = *ServiceArgs++;
203             ArgCount--;
204 
205             SdShow(ServiceName);
206         }
207         else
208             SdShowUsage();
209     }
210     else if (!lstrcmpi(Command, _T("sdset")))
211     {
212         LPCTSTR SecurityDescriptor;
213 
214         if (ArgCount > 1)
215         {
216             ServiceName = *ServiceArgs++;
217             ArgCount--;
218 
219             SecurityDescriptor = *ServiceArgs++;
220             ArgCount--;
221 
222             SdSet(ServiceName, SecurityDescriptor);
223         }
224         else
225             SdSetUsage();
226     }
227     else if (!lstrcmpi(Command, _T("qc")))
228     {
229         if (ArgCount > 0)
230         {
231             ServiceName = *ServiceArgs++;
232             ArgCount--;
233 
234             QueryConfig(ServiceName);
235         }
236         else
237             QueryConfigUsage();
238     }
239     else if (!lstrcmpi(Command, _T("qdescription")))
240     {
241         if (ArgCount > 0)
242         {
243             ServiceName = *ServiceArgs++;
244             ArgCount--;
245 
246             QueryDescription(ServiceName);
247         }
248         else
249             QueryDescriptionUsage();
250     }
251     else if (!lstrcmpi(Command, _T("qfailure")))
252     {
253         if (ArgCount > 0)
254         {
255             ServiceName = *ServiceArgs++;
256             ArgCount--;
257 
258             QueryFailure(ServiceName);
259         }
260         else
261             QueryFailureUsage();
262     }
263     else if (!lstrcmpi(Command, _T("description")))
264     {
265         LPCTSTR Description = NULL;
266 
267         if (ArgCount > 0)
268         {
269             ServiceName = *ServiceArgs++;
270             ArgCount--;
271 
272             if (ArgCount > 0)
273             {
274                 Description = *ServiceArgs++;
275                 ArgCount--;
276             }
277 
278             SetDescription(ServiceName, Description);
279         }
280         else
281             SetDescriptionUsage();
282     }
283     else if (!lstrcmpi(Command, _T("config")))
284     {
285         SetConfig(ServiceArgs, ArgCount);
286     }
287     else if (!lstrcmpi(Command, _T("failure")))
288     {
289         SetFailure(ServiceArgs, ArgCount);
290     }
291     else if (!lstrcmpi(Command, _T("GetDisplayName")))
292     {
293         if (ArgCount > 0)
294         {
295             ServiceName = *ServiceArgs++;
296             ArgCount--;
297 
298             GetDisplayName(ServiceName);
299         }
300         else
301             GetDisplayNameUsage();
302     }
303     else if (!lstrcmpi(Command, _T("GetKeyName")))
304     {
305         if (ArgCount > 0)
306         {
307             ServiceName = *ServiceArgs++;
308             ArgCount--;
309 
310             GetKeyName(ServiceName);
311         }
312         else
313             GetKeyNameUsage();
314     }
315     else if (!lstrcmpi(Command, _T("EnumDepend")))
316     {
317         if (ArgCount > 0)
318         {
319             ServiceName = *ServiceArgs++;
320             ArgCount--;
321 
322             EnumDepend(ServiceName);
323         }
324         else
325             EnumDependUsage();
326     }
327     else
328     {
329         MainUsage();
330     }
331 
332     return 0;
333 }
334 
335 int _tmain(int argc, LPCTSTR argv[])
336 {
337     LPCTSTR Server = NULL;   // remote machine
338     LPCTSTR Command = NULL;  // sc command
339     LPCTSTR *Args = NULL;    // Any remaining args
340 
341     if (argc < 2)
342     {
343         MainUsage();
344         return -1;
345     }
346 
347     /* get server name */
348     if ((argv[1][0] == '\\') && (argv[1][1] == '\\'))
349     {
350         if (argc < 3)
351         {
352             MainUsage();
353             return -1;
354         }
355 
356         Server = argv[1];
357         Command = argv[2];
358         if (argc > 3)
359             Args = &argv[3];
360 
361         return ScControl(Server,
362                          Command,
363                          Args,
364                          argc-3);
365     }
366     else
367     {
368         Command = argv[1];
369         if (argc > 2)
370             Args = &argv[2];
371 
372         return ScControl(Server,
373                          Command,
374                          Args,
375                          argc-2);
376     }
377 }
378