2 Samba Unix/Linux SMB client library
3 Distributed SMB/CIFS Server Management Utility
4 Copyright (C) Gerald (Jerry) Carter 2005
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
21 #include "utils/net.h"
24 /********************************************************************
25 ********************************************************************/
27 static WERROR
query_service_state(struct rpc_pipe_client
*pipe_hnd
,
34 SERVICE_STATUS service_status
;
35 WERROR result
= WERR_GENERAL_FAILURE
;
37 /* now cycle until the status is actually 'watch_state' */
39 result
= rpccli_svcctl_open_service(pipe_hnd
, mem_ctx
, hSCM
, &hService
,
40 service
, SC_RIGHT_SVC_QUERY_STATUS
);
42 if ( !W_ERROR_IS_OK(result
) ) {
43 d_fprintf(stderr
, "Failed to open service. [%s]\n", dos_errstr(result
));
47 result
= rpccli_svcctl_query_status(pipe_hnd
, mem_ctx
, &hService
, &service_status
);
48 if ( W_ERROR_IS_OK(result
) ) {
49 *state
= service_status
.state
;
52 rpccli_svcctl_close_service(pipe_hnd
, mem_ctx
, &hService
);
57 /********************************************************************
58 ********************************************************************/
60 static WERROR
watch_service_state(struct rpc_pipe_client
*pipe_hnd
,
69 WERROR result
= WERR_GENERAL_FAILURE
;
73 while ( (state
!= watch_state
) && i
<30 ) {
76 result
= query_service_state(pipe_hnd
, mem_ctx
, hSCM
, service
, &state
);
77 if ( !W_ERROR_IS_OK(result
) ) {
92 /********************************************************************
93 ********************************************************************/
95 static WERROR
control_service(struct rpc_pipe_client
*pipe_hnd
,
103 WERROR result
= WERR_GENERAL_FAILURE
;
104 SERVICE_STATUS service_status
;
107 /* Open the Service */
109 result
= rpccli_svcctl_open_service(pipe_hnd
, mem_ctx
, hSCM
, &hService
,
110 service
, (SC_RIGHT_SVC_STOP
|SC_RIGHT_SVC_PAUSE_CONTINUE
) );
112 if ( !W_ERROR_IS_OK(result
) ) {
113 d_fprintf(stderr
, "Failed to open service. [%s]\n", dos_errstr(result
));
119 result
= rpccli_svcctl_control_service(pipe_hnd
, mem_ctx
, &hService
,
120 control
, &service_status
);
122 if ( !W_ERROR_IS_OK(result
) ) {
123 d_fprintf(stderr
, "Control service request failed. [%s]\n", dos_errstr(result
));
127 /* loop -- checking the state until we are where we want to be */
129 result
= watch_service_state(pipe_hnd
, mem_ctx
, hSCM
, service
, watch_state
, &state
);
131 d_printf("%s service is %s.\n", service
, svc_status_string(state
));
134 rpccli_svcctl_close_service(pipe_hnd
, mem_ctx
, &hService
);
139 /********************************************************************
140 ********************************************************************/
142 static NTSTATUS
rpc_service_list_internal(const DOM_SID
*domain_sid
,
143 const char *domain_name
,
144 struct cli_state
*cli
,
145 struct rpc_pipe_client
*pipe_hnd
,
151 ENUM_SERVICES_STATUS
*services
;
152 WERROR result
= WERR_GENERAL_FAILURE
;
155 uint32 num_services
= 0;
159 d_printf("Usage: net rpc service list\n");
163 result
= rpccli_svcctl_open_scm(pipe_hnd
, mem_ctx
, &hSCM
, SC_RIGHT_MGR_ENUMERATE_SERVICE
);
164 if ( !W_ERROR_IS_OK(result
) ) {
165 d_fprintf(stderr
, "Failed to open Service Control Manager. [%s]\n", dos_errstr(result
));
166 return werror_to_ntstatus(result
);
169 result
= rpccli_svcctl_enumerate_services(pipe_hnd
, mem_ctx
, &hSCM
, SVCCTL_TYPE_WIN32
,
170 SVCCTL_STATE_ALL
, &num_services
, &services
);
172 if ( !W_ERROR_IS_OK(result
) ) {
173 d_fprintf(stderr
, "Failed to enumerate services. [%s]\n", dos_errstr(result
));
177 if ( num_services
== 0 )
178 d_printf("No services returned\n");
180 for ( i
=0; i
<num_services
; i
++ ) {
181 rpcstr_pull( servicename
, services
[i
].servicename
.buffer
, sizeof(servicename
), -1, STR_TERMINATE
);
182 rpcstr_pull( displayname
, services
[i
].displayname
.buffer
, sizeof(displayname
), -1, STR_TERMINATE
);
184 d_printf("%-20s \"%s\"\n", servicename
, displayname
);
188 rpccli_svcctl_close_service(pipe_hnd
, mem_ctx
, &hSCM
);
190 return werror_to_ntstatus(result
);
193 /********************************************************************
194 ********************************************************************/
196 static NTSTATUS
rpc_service_status_internal(const DOM_SID
*domain_sid
,
197 const char *domain_name
,
198 struct cli_state
*cli
,
199 struct rpc_pipe_client
*pipe_hnd
,
204 POLICY_HND hSCM
, hService
;
205 WERROR result
= WERR_GENERAL_FAILURE
;
207 SERVICE_STATUS service_status
;
208 SERVICE_CONFIG config
;
209 fstring ascii_string
;
212 d_printf("Usage: net rpc service status <service>\n");
216 fstrcpy( servicename
, argv
[0] );
218 /* Open the Service Control Manager */
220 result
= rpccli_svcctl_open_scm(pipe_hnd
, mem_ctx
, &hSCM
, SC_RIGHT_MGR_ENUMERATE_SERVICE
);
221 if ( !W_ERROR_IS_OK(result
) ) {
222 d_fprintf(stderr
, "Failed to open Service Control Manager. [%s]\n", dos_errstr(result
));
223 return werror_to_ntstatus(result
);
226 /* Open the Service */
228 result
= rpccli_svcctl_open_service(pipe_hnd
, mem_ctx
, &hSCM
, &hService
, servicename
,
229 (SC_RIGHT_SVC_QUERY_STATUS
|SC_RIGHT_SVC_QUERY_CONFIG
) );
231 if ( !W_ERROR_IS_OK(result
) ) {
232 d_fprintf(stderr
, "Failed to open service. [%s]\n", dos_errstr(result
));
238 result
= rpccli_svcctl_query_status(pipe_hnd
, mem_ctx
, &hService
, &service_status
);
239 if ( !W_ERROR_IS_OK(result
) ) {
240 d_fprintf(stderr
, "Query status request failed. [%s]\n", dos_errstr(result
));
244 d_printf("%s service is %s.\n", servicename
, svc_status_string(service_status
.state
));
248 result
= rpccli_svcctl_query_config(pipe_hnd
, mem_ctx
, &hService
, &config
);
249 if ( !W_ERROR_IS_OK(result
) ) {
250 d_fprintf(stderr
, "Query config request failed. [%s]\n", dos_errstr(result
));
254 /* print out the configuration information for the service */
256 d_printf("Configuration details:\n");
257 d_printf("\tControls Accepted = 0x%x\n", service_status
.controls_accepted
);
258 d_printf("\tService Type = 0x%x\n", config
.service_type
);
259 d_printf("\tStart Type = 0x%x\n", config
.start_type
);
260 d_printf("\tError Control = 0x%x\n", config
.error_control
);
261 d_printf("\tTag ID = 0x%x\n", config
.tag_id
);
263 if ( config
.executablepath
) {
264 rpcstr_pull( ascii_string
, config
.executablepath
->buffer
, sizeof(ascii_string
), -1, STR_TERMINATE
);
265 d_printf("\tExecutable Path = %s\n", ascii_string
);
268 if ( config
.loadordergroup
) {
269 rpcstr_pull( ascii_string
, config
.loadordergroup
->buffer
, sizeof(ascii_string
), -1, STR_TERMINATE
);
270 d_printf("\tLoad Order Group = %s\n", ascii_string
);
273 if ( config
.dependencies
) {
274 rpcstr_pull( ascii_string
, config
.dependencies
->buffer
, sizeof(ascii_string
), -1, STR_TERMINATE
);
275 d_printf("\tDependencies = %s\n", ascii_string
);
278 if ( config
.startname
) {
279 rpcstr_pull( ascii_string
, config
.startname
->buffer
, sizeof(ascii_string
), -1, STR_TERMINATE
);
280 d_printf("\tStart Name = %s\n", ascii_string
);
283 if ( config
.displayname
) {
284 rpcstr_pull( ascii_string
, config
.displayname
->buffer
, sizeof(ascii_string
), -1, STR_TERMINATE
);
285 d_printf("\tDisplay Name = %s\n", ascii_string
);
289 rpccli_svcctl_close_service(pipe_hnd
, mem_ctx
, &hService
);
290 rpccli_svcctl_close_service(pipe_hnd
, mem_ctx
, &hSCM
);
292 return werror_to_ntstatus(result
);
295 /********************************************************************
296 ********************************************************************/
298 static NTSTATUS
rpc_service_stop_internal(const DOM_SID
*domain_sid
,
299 const char *domain_name
,
300 struct cli_state
*cli
,
301 struct rpc_pipe_client
*pipe_hnd
,
307 WERROR result
= WERR_GENERAL_FAILURE
;
311 d_printf("Usage: net rpc service status <service>\n");
315 fstrcpy( servicename
, argv
[0] );
317 /* Open the Service Control Manager */
319 result
= rpccli_svcctl_open_scm(pipe_hnd
, mem_ctx
, &hSCM
, SC_RIGHT_MGR_ENUMERATE_SERVICE
);
320 if ( !W_ERROR_IS_OK(result
) ) {
321 d_fprintf(stderr
, "Failed to open Service Control Manager. [%s]\n", dos_errstr(result
));
322 return werror_to_ntstatus(result
);
325 result
= control_service(pipe_hnd
, mem_ctx
, &hSCM
, servicename
,
326 SVCCTL_CONTROL_STOP
, SVCCTL_STOPPED
);
328 rpccli_svcctl_close_service(pipe_hnd
, mem_ctx
, &hSCM
);
330 return werror_to_ntstatus(result
);
333 /********************************************************************
334 ********************************************************************/
336 static NTSTATUS
rpc_service_pause_internal(const DOM_SID
*domain_sid
,
337 const char *domain_name
,
338 struct cli_state
*cli
,
339 struct rpc_pipe_client
*pipe_hnd
,
345 WERROR result
= WERR_GENERAL_FAILURE
;
349 d_printf("Usage: net rpc service status <service>\n");
353 fstrcpy( servicename
, argv
[0] );
355 /* Open the Service Control Manager */
357 result
= rpccli_svcctl_open_scm(pipe_hnd
, mem_ctx
, &hSCM
, SC_RIGHT_MGR_ENUMERATE_SERVICE
);
358 if ( !W_ERROR_IS_OK(result
) ) {
359 d_fprintf(stderr
, "Failed to open Service Control Manager. [%s]\n", dos_errstr(result
));
360 return werror_to_ntstatus(result
);
363 result
= control_service(pipe_hnd
, mem_ctx
, &hSCM
, servicename
,
364 SVCCTL_CONTROL_PAUSE
, SVCCTL_PAUSED
);
366 rpccli_svcctl_close_service(pipe_hnd
, mem_ctx
, &hSCM
);
368 return werror_to_ntstatus(result
);
371 /********************************************************************
372 ********************************************************************/
374 static NTSTATUS
rpc_service_resume_internal(const DOM_SID
*domain_sid
,
375 const char *domain_name
,
376 struct cli_state
*cli
,
377 struct rpc_pipe_client
*pipe_hnd
,
383 WERROR result
= WERR_GENERAL_FAILURE
;
387 d_printf("Usage: net rpc service status <service>\n");
391 fstrcpy( servicename
, argv
[0] );
393 /* Open the Service Control Manager */
395 result
= rpccli_svcctl_open_scm(pipe_hnd
, mem_ctx
, &hSCM
, SC_RIGHT_MGR_ENUMERATE_SERVICE
);
396 if ( !W_ERROR_IS_OK(result
) ) {
397 d_fprintf(stderr
, "Failed to open Service Control Manager. [%s]\n", dos_errstr(result
));
398 return werror_to_ntstatus(result
);
401 result
= control_service(pipe_hnd
, mem_ctx
, &hSCM
, servicename
,
402 SVCCTL_CONTROL_CONTINUE
, SVCCTL_RUNNING
);
404 rpccli_svcctl_close_service(pipe_hnd
, mem_ctx
, &hSCM
);
406 return werror_to_ntstatus(result
);
409 /********************************************************************
410 ********************************************************************/
412 static NTSTATUS
rpc_service_start_internal(const DOM_SID
*domain_sid
,
413 const char *domain_name
,
414 struct cli_state
*cli
,
415 struct rpc_pipe_client
*pipe_hnd
,
420 POLICY_HND hSCM
, hService
;
421 WERROR result
= WERR_GENERAL_FAILURE
;
426 d_printf("Usage: net rpc service status <service>\n");
430 fstrcpy( servicename
, argv
[0] );
432 /* Open the Service Control Manager */
434 result
= rpccli_svcctl_open_scm( pipe_hnd
, mem_ctx
, &hSCM
, SC_RIGHT_MGR_ENUMERATE_SERVICE
);
435 if ( !W_ERROR_IS_OK(result
) ) {
436 d_fprintf(stderr
, "Failed to open Service Control Manager. [%s]\n", dos_errstr(result
));
437 return werror_to_ntstatus(result
);
440 /* Open the Service */
442 result
= rpccli_svcctl_open_service(pipe_hnd
, mem_ctx
, &hSCM
, &hService
,
443 servicename
, SC_RIGHT_SVC_START
);
445 if ( !W_ERROR_IS_OK(result
) ) {
446 d_fprintf(stderr
, "Failed to open service. [%s]\n", dos_errstr(result
));
452 result
= rpccli_svcctl_start_service(pipe_hnd
, mem_ctx
, &hService
, NULL
, 0 );
453 if ( !W_ERROR_IS_OK(result
) ) {
454 d_fprintf(stderr
, "Query status request failed. [%s]\n", dos_errstr(result
));
458 result
= watch_service_state(pipe_hnd
, mem_ctx
, &hSCM
, servicename
, SVCCTL_RUNNING
, &state
);
460 if ( W_ERROR_IS_OK(result
) && (state
== SVCCTL_RUNNING
) )
461 d_printf("Successfully started service: %s\n", servicename
);
463 d_fprintf(stderr
, "Failed to start service: %s [%s]\n", servicename
, dos_errstr(result
) );
466 rpccli_svcctl_close_service(pipe_hnd
, mem_ctx
, &hService
);
467 rpccli_svcctl_close_service(pipe_hnd
, mem_ctx
, &hSCM
);
469 return werror_to_ntstatus(result
);
472 /********************************************************************
473 ********************************************************************/
475 static int rpc_service_list( int argc
, const char **argv
)
477 return run_rpc_command( NULL
, PI_SVCCTL
, 0,
478 rpc_service_list_internal
, argc
, argv
);
481 /********************************************************************
482 ********************************************************************/
484 static int rpc_service_start( int argc
, const char **argv
)
486 return run_rpc_command( NULL
, PI_SVCCTL
, 0,
487 rpc_service_start_internal
, argc
, argv
);
490 /********************************************************************
491 ********************************************************************/
493 static int rpc_service_stop( int argc
, const char **argv
)
495 return run_rpc_command( NULL
, PI_SVCCTL
, 0,
496 rpc_service_stop_internal
, argc
, argv
);
499 /********************************************************************
500 ********************************************************************/
502 static int rpc_service_resume( int argc
, const char **argv
)
504 return run_rpc_command( NULL
, PI_SVCCTL
, 0,
505 rpc_service_resume_internal
, argc
, argv
);
508 /********************************************************************
509 ********************************************************************/
511 static int rpc_service_pause( int argc
, const char **argv
)
513 return run_rpc_command( NULL
, PI_SVCCTL
, 0,
514 rpc_service_pause_internal
, argc
, argv
);
517 /********************************************************************
518 ********************************************************************/
520 static int rpc_service_status( int argc
, const char **argv
)
522 return run_rpc_command( NULL
, PI_SVCCTL
, 0,
523 rpc_service_status_internal
, argc
, argv
);
526 /********************************************************************
527 ********************************************************************/
529 static int net_help_service( int argc
, const char **argv
)
531 d_printf("net rpc service list View configured Win32 services\n");
532 d_printf("net rpc service start <service> Start a service\n");
533 d_printf("net rpc service stop <service> Stop a service\n");
534 d_printf("net rpc service pause <service> Pause a service\n");
535 d_printf("net rpc service resume <service> Resume a paused service\n");
536 d_printf("net rpc service status <service> View the current status of a service\n");
541 /********************************************************************
542 ********************************************************************/
544 int net_rpc_service(int argc
, const char **argv
)
546 struct functable func
[] = {
547 {"list", rpc_service_list
},
548 {"start", rpc_service_start
},
549 {"stop", rpc_service_stop
},
550 {"pause", rpc_service_pause
},
551 {"resume", rpc_service_resume
},
552 {"status", rpc_service_status
},
557 return net_run_function( argc
, argv
, func
, net_help_service
);
559 return net_help_service( argc
, argv
);