#include "idl_types.h"

/*
  svcctl interface definitions
*/

[ uuid("367abb81-9844-35f1-ad32-98f038001003"),
  version(2.0),
  pointer_default(unique),
  endpoint("ncacn_np:[\\pipe\\svcctl]", "ncalrpc:"),
  helpstring("Service Control")
] interface svcctl
{
	typedef struct {
		uint32 is_locked;
		[string,charset(UTF16)] uint16 *lock_owner;
		uint32 lock_duration;
	} SERVICE_LOCK_STATUS;

	typedef struct {
		uint32 type;
		uint32 state;
		uint32 controls_accepted;
		WERROR win32_exit_code;
		uint32 service_exit_code;
		uint32 check_point;
		uint32 wait_hint;
	} SERVICE_STATUS;

	typedef struct {
		[relative] astring *service_name;
		[relative] astring *display_name;
		SERVICE_STATUS status;
	} ENUM_SERVICE_STATUS;

	const int SERVICE_TYPE_KERNEL_DRIVER       = 0x01;
	const int SERVICE_TYPE_FS_DRIVER           = 0x02;
	const int SERVICE_TYPE_ADAPTER             = 0x04;
	const int SERVICE_TYPE_RECOGNIZER_DRIVER   = 0x08;
	const int SERVICE_TYPE_DRIVER=SERVICE_TYPE_KERNEL_DRIVER|SERVICE_TYPE_FS_DRIVER|SERVICE_TYPE_RECOGNIZER_DRIVER;
	const int SERVICE_TYPE_WIN32_OWN_PROCESS   = 0x10;
	const int SERVICE_TYPE_WIN32_SHARE_PROCESS = 0x20;
	const int SERVICE_TYPE_WIN32=SERVICE_TYPE_WIN32_OWN_PROCESS|SERVICE_TYPE_WIN32_SHARE_PROCESS;

	const int SERVICE_STATE_ACTIVE   = 0x01;
	const int SERVICE_STATE_INACTIVE = 0x02;
	const int SERVICE_STATE_ALL      = 0x03;

	typedef [public,bitmap32bit] bitmap {
		SV_TYPE_WORKSTATION       = 0x00000001,
		SV_TYPE_SERVER            = 0x00000002,
		SV_TYPE_SQLSERVER         = 0x00000004,
		SV_TYPE_DOMAIN_CTRL       = 0x00000008,
		SV_TYPE_DOMAIN_BAKCTRL    = 0x00000010,
		SV_TYPE_TIME_SOURCE       = 0x00000020,
		SV_TYPE_AFP               = 0x00000040,
		SV_TYPE_NOVELL            = 0x00000080,

		SV_TYPE_DOMAIN_MEMBER     = 0x00000100,
		SV_TYPE_PRINTQ_SERVER     = 0x00000200,
		SV_TYPE_DIALIN_SERVER     = 0x00000400,
		SV_TYPE_SERVER_UNIX       = 0x00000800,
		SV_TYPE_NT                = 0x00001000,
		SV_TYPE_WFW               = 0x00002000,
		SV_TYPE_SERVER_MFPN       = 0x00004000,
		SV_TYPE_SERVER_NT         = 0x00008000,
		SV_TYPE_POTENTIAL_BROWSER = 0x00010000,
		SV_TYPE_BACKUP_BROWSER    = 0x00020000,
		SV_TYPE_MASTER_BROWSER    = 0x00040000,
		SV_TYPE_DOMAIN_MASTER     = 0x00080000,
		SV_TYPE_SERVER_OSF        = 0x00100000,
		SV_TYPE_SERVER_VMS        = 0x00200000,
		SV_TYPE_WIN95_PLUS        = 0x00400000,
		SV_TYPE_DFS_SERVER        = 0x00800000,
		SV_TYPE_ALTERNATE_XPORT   = 0x20000000,
		SV_TYPE_LOCAL_LIST_ONLY   = 0x40000000,
		SV_TYPE_DOMAIN_ENUM       = 0x80000000
	} svcctl_ServerType;

	const uint32 SV_TYPE_ALL	= 0xFFFFFFFF;

	/*****************/
	/* Function 0x00 */
	WERROR svcctl_CloseServiceHandle(
		[in,out,ref] policy_handle *handle
	);

	/*****************/
	/* Function 0x01 */

	typedef enum {
		FIXME=1
	} SERVICE_CONTROL;
	
	WERROR svcctl_ControlService(
		[in,ref] policy_handle *handle,
		[in] uint32 control,
		[out,ref] SERVICE_STATUS *service_status
	);

	/*****************/
	/* Function 0x02 */
	WERROR svcctl_DeleteService(
		[in,ref] policy_handle *handle
	);

	/*****************/
	/* Function 0x03 */

	WERROR svcctl_LockServiceDatabase(
		[in,ref] policy_handle *handle,
		[out,ref] policy_handle *lock
	);

	/*****************/
	/* Function 0x04 */
	WERROR svcctl_QueryServiceObjectSecurity(
		[in] policy_handle *handle,
		[in] uint32 security_flags,
		[out,ref,size_is(buffer_size)] uint8 *buffer,
		[in,range(0,0x40000)] uint32 buffer_size,
		[out,ref,range(0,0x40000)] uint32 *needed
	);

	/*****************/
	/* Function 0x05 */
	WERROR svcctl_SetServiceObjectSecurity(
		[in] policy_handle *handle,
		[in] uint32 security_flags,
		[in,ref,size_is(buffer_size)] uint8 *buffer,
		[in] uint32 buffer_size
	);

	/*****************/
	/* Function 0x06 */
	WERROR svcctl_QueryServiceStatus(
		[in,ref] policy_handle *handle,
		[out,ref] SERVICE_STATUS *service_status
	);

	/*****************/
	/* Function 0x07 */
	WERROR svcctl_SetServiceStatus(
	);

	/*****************/
	/* Function 0x08 */
	WERROR svcctl_UnlockServiceDatabase(
		[in,out,ref] policy_handle *lock
	);

	/*****************/
	/* Function 0x09 */
	WERROR svcctl_NotifyBootConfigStatus(
	);

	/*****************/
	/* Function 0x0a */
	WERROR svcctl_SCSetServiceBitsW(
		[in,ref] policy_handle *handle,
		[in] uint32 bits,
		[in] boolean32 bitson,
		[in] boolean32 immediate
	);

	/*****************/
	/* Function 0x0b */
	WERROR svcctl_ChangeServiceConfigW(
		[in,ref] policy_handle *handle,
		[in] uint32 type,
		[in] uint32 start,
		[in] uint32 error,
		[in,unique] [string,charset(UTF16)] uint16 *binary_path,
		[in,unique] [string,charset(UTF16)] uint16 *load_order_group,
		[out,ref] uint32 *tag_id,
		[in,unique] [string,charset(UTF16)] uint16 *dependencies,
		[in,unique] [string,charset(UTF16)] uint16 *service_start_name,
		[in,unique] [string,charset(UTF16)] uint16 *password,
		[in,unique] [string,charset(UTF16)] uint16 *display_name
	);

	/*****************/
	/* Function 0x0c */
	WERROR svcctl_CreateServiceW(
		[in,ref] policy_handle *scmanager_handle,
		[in] [string,charset(UTF16)] uint16 ServiceName[],
		[in,unique] [string,charset(UTF16)] uint16 *DisplayName,
		[in] uint32 desired_access,
		[in] uint32 type,
		[in] uint32 start_type,
		[in] uint32 error_control,
		[in] [string,charset(UTF16)] uint16 binary_path[],
		[in,unique] [string,charset(UTF16)] uint16 *LoadOrderGroupKey,
		[in,out,unique] uint32 *TagId,
		[in,unique,size_is(dependencies_size)] uint8 *dependencies,
		[in] uint32 dependencies_size,
		[in,unique] [string,charset(UTF16)] uint16 *service_start_name,
		[in,unique,size_is(password_size)] uint8 *password,
		[in] uint32 password_size,
		[out,ref] policy_handle *handle
	);

	/*****************/
	/* Function 0x0d */
	WERROR svcctl_EnumDependentServicesW(
		[in,ref] policy_handle *service,
		[in] uint32 state,
		[out,unique] ENUM_SERVICE_STATUS *service_status,
		[in] uint32 buf_size,
		[out,ref] uint32 *bytes_needed,
		[out,ref] uint32 *services_returned
	);

	/*****************/
	/* Function 0x0e */
	WERROR svcctl_EnumServicesStatusW(
		[in,ref] policy_handle *handle,
		[in] uint32 type,
		[in] uint32 state,
		[in] uint32 buf_size,
		[out,size_is(buf_size)] uint8 service[*],
		[out,ref] uint32 *bytes_needed,
		[out,ref] uint32 *services_returned,
		[in,out,unique] uint32 *resume_handle
	);

	/*****************/
	/* Function 0x0f */
	WERROR svcctl_OpenSCManagerW(
		[in,unique] [string,charset(UTF16)] uint16 *MachineName,
		[in,unique] [string,charset(UTF16)] uint16 *DatabaseName,
		[in] uint32 access_mask,
		[out,ref] policy_handle *handle
	);

	/*****************/
	/* Function 0x10 */
	WERROR svcctl_OpenServiceW(
		[in,ref] policy_handle *scmanager_handle,
		[in] [string,charset(UTF16)] uint16 ServiceName[],
		[in] uint32 access_mask,
		[out,ref] policy_handle *handle
	);

	/*****************/
	/* Function 0x11 */
	WERROR svcctl_QueryServiceConfigW(
		[in,ref] policy_handle *handle,
		[out] uint8 query[buf_size], /*QUERY_SERVICE_CONFIG */
		[in] uint32 buf_size,
		[out,ref] uint32 *bytes_needed
	);

	/*****************/
	/* Function 0x12 */
	WERROR svcctl_QueryServiceLockStatusW(
		[in,ref] policy_handle *handle,
		[in] uint32 buf_size,
		[out,ref] SERVICE_LOCK_STATUS *lock_status,
		[out,ref] uint32 *required_buf_size
	);

	/*****************/
	/* Function 0x13 */
	WERROR svcctl_StartServiceW(
		[in,ref] policy_handle *handle,
		[in] uint32 NumArgs,
		[in,unique/*FIXME:,length_is(NumArgs)*/] [string,charset(UTF16)] uint16 *Arguments
	);

	/*****************/
	/* Function 0x14 */
	WERROR svcctl_GetServiceDisplayNameW(
		[in,ref] policy_handle *handle,
		[in,unique] [string,charset(UTF16)] uint16 *service_name,
		[out,ref] [string,charset(UTF16)] uint16 **display_name,
		[in,out,unique] uint32 *display_name_length
	); 

	/*****************/
	/* Function 0x15 */
	WERROR svcctl_GetServiceKeyNameW(
		[in,ref] policy_handle *handle,
		[in,unique] [string,charset(UTF16)] uint16 *service_name,
		[out,ref] [string,charset(UTF16)] uint16 **key_name,
		[in,out,unique] uint32 *display_name_length
	);

	/*****************/
	/* Function 0x16 */
	WERROR svcctl_SCSetServiceBitsA(
		[in,ref] policy_handle *handle,
		[in] uint32 bits,
		[in] boolean32 bitson,
		[in] boolean32 immediate
	);

	/*****************/
	/* Function 0x17 */
	WERROR svcctl_ChangeServiceConfigA(
		[in,ref] policy_handle *handle,
		[in] uint32 type,
		[in] uint32 start,
		[in] uint32 error,
		[in,unique] [string,charset(UTF16)] uint16 *binary_path,
		[in,unique] [string,charset(UTF16)] uint16 *load_order_group,
		[out,ref] uint32 *tag_id,
		[in,unique] [string,charset(UTF16)] uint16 *dependencies,
		[in,unique] [string,charset(UTF16)] uint16 *service_start_name,
		[in,unique] [string,charset(UTF16)] uint16 *password,
		[in,unique] [string,charset(UTF16)] uint16 *display_name
	);

	/*****************/
	/* Function 0x18 */
	WERROR svcctl_CreateServiceA(
		[in,ref] policy_handle *handle,
		[in,unique] [string,charset(UTF16)] uint16 *ServiceName,
		[in,unique] [string,charset(UTF16)] uint16 *DisplayName,
		[in] uint32 desired_access,
		[in] uint32 type,
		[in] uint32 start_type,
		[in] uint32 error_control,
		[in,unique] [string,charset(UTF16)] uint16 *binary_path,
		[in,unique] [string,charset(UTF16)] uint16 *LoadOrderGroupKey,
		[out,unique] uint32 *TagId,
		[in,unique] [string,charset(UTF16)] uint16 *dependencies,
		[in,unique] [string,charset(UTF16)] uint16 *service_start_name,
		[in,unique] [string,charset(UTF16)] uint16 *password
	);

	/*****************/
	/* Function 0x19 */
	WERROR svcctl_EnumDependentServicesA(
		[in,ref] policy_handle *service,
		[in] uint32 state,
		[out,unique] ENUM_SERVICE_STATUS *service_status,
		[in] uint32 buf_size,
		[out,ref] uint32 *bytes_needed,
		[out,ref] uint32 *services_returned
	);

	/*****************/
	/* Function 0x1a */
	WERROR svcctl_EnumServicesStatusA(
		[in,ref] policy_handle *handle,
		[in] uint32 type,
		[in] uint32 state,
		[in] uint32 buf_size,
		[out,size_is(buf_size)] uint8 service[*],
		[out,ref] uint32 *bytes_needed,
		[out,ref] uint32 *services_returned,
		[in,out,unique] uint32 *resume_handle
	);
	
	/*****************/
	/* Function 0x1b */
	WERROR svcctl_OpenSCManagerA(
		[in,unique] [string,charset(UTF16)] uint16 *MachineName,
		[in,unique] [string,charset(UTF16)] uint16 *DatabaseName,
		[in] uint32 access_mask,
		[out,ref] policy_handle *handle
	);

	/*****************/
	/* Function 0x1c */
	WERROR svcctl_OpenServiceA(
		[in,ref] policy_handle *scmanager_handle,
		[in,unique] [string,charset(UTF16)] uint16 *ServiceName,
		[in] uint32 access_mask
	);

	/*****************/
	/* Function 0x1d */
	WERROR svcctl_QueryServiceConfigA(
		[in,ref] policy_handle *handle,
		[out] uint8 query[buf_size], /*QUERYU_SERVICE_CONFIG */
		[in] uint32 buf_size,
		[out,ref] uint32 *bytes_needed
	);

	/*****************/
	/* Function 0x1e */
	WERROR svcctl_QueryServiceLockStatusA(
		[in,ref] policy_handle *handle,
		[in] uint32 buf_size,
		[out,ref] SERVICE_LOCK_STATUS *lock_status,
		[out,ref] uint32 *required_buf_size
	);

	/*****************/
	/* Function 0x1f */
	WERROR svcctl_StartServiceA(
		[in,ref] policy_handle *handle,
		[in] uint32 NumArgs,
		[in,unique/*FIXME:,length_is(NumArgs)*/] [string,charset(UTF16)] uint16 *Arguments
	);

	/*****************/
	/* Function 0x20 */
	WERROR svcctl_GetServiceDisplayNameA(
		[in,ref] policy_handle *handle,
		[in,unique] [string,charset(UTF16)] uint16 *service_name,
		[out,ref] [string,charset(UTF16)] uint16 **display_name,
		[in,out,unique] uint32 *display_name_length
	); 

	/*****************/
	/* Function 0x21 */
	WERROR svcctl_GetServiceKeyNameA(
		[in,ref] policy_handle *handle,
		[in,unique] [string,charset(UTF16)] uint16 *service_name,
		[out,ref] [string,charset(UTF16)] uint16 **key_name,
		[in,out,unique] uint32 *display_name_length
	);

	/*****************/
	/* Function 0x22 */
	WERROR svcctl_GetCurrentGroupeStateW(
	);

	/*****************/
	/* Function 0x23 */
	WERROR svcctl_EnumServiceGroupW(
	);

	/*****************/
	/* Function 0x24 */
	WERROR svcctl_ChangeServiceConfig2A(
		[in,ref] policy_handle *handle,
		[in] uint32 info_level,
		[in,unique] uint8 *info
	);

	/*****************/
	/* Function 0x25 */
	WERROR svcctl_ChangeServiceConfig2W(
		[in,ref] policy_handle *handle,
		[in] uint32 info_level,
		[in,unique] uint8 *info
	);

	/*****************/
	/* Function 0x26 */
	WERROR svcctl_QueryServiceConfig2A(
		[in,ref] policy_handle *handle,
		[in] uint32 info_level,
		[out] uint8 buffer[buf_size],
		[in] uint32 buf_size,
		[out,ref] uint32 *bytes_needed
	);

	/*****************/
	/* Function 0x27 */
	WERROR svcctl_QueryServiceConfig2W(
		[in,ref] policy_handle *handle,
		[in] uint32 info_level,
		[out] uint8 buffer[buf_size],
		[in] uint32 buf_size,
		[out,ref] uint32 *bytes_needed
	);

	/*****************/
	/* Function 0x28 */
	WERROR svcctl_QueryServiceStatusEx(
		[in,ref] policy_handle *handle,
		[in] uint32 info_level,
		[out] uint8 buffer[buf_size],
		[in] uint32 buf_size,
		[out,ref] uint32 *bytes_needed
	);

	/*****************/
	/* Function 0x29 */
	WERROR EnumServicesStatusExA(
		[in,ref] policy_handle *scmanager,
		[in] uint32 info_level,
		[in] uint32 type,
		[in] uint32 state,
		[out] uint8 services[buf_size],
		[in] uint32 buf_size,
		[out,ref] uint32 *bytes_needed,
		[out,ref] uint32 *service_returned,
		[in,out,unique] uint32 *resume_handle,
		[out,ref] [string,charset(UTF16)] uint16 **group_name
	);

	/*****************/
	/* Function 0x2a */
	WERROR EnumServicesStatusExW(
		[in,ref] policy_handle *scmanager,
		[in] uint32 info_level,
		[in] uint32 type,
		[in] uint32 state,
		[out] uint8 services[buf_size],
		[in] uint32 buf_size,
		[out,ref] uint32 *bytes_needed,
		[out,ref] uint32 *service_returned,
		[in,out,unique] uint32 *resume_handle,
		[out,ref] [string,charset(UTF16)] uint16 **group_name
	);

	/*****************/
	/* Function 0x2b */
	WERROR svcctl_SCSendTSMessage(
	);
}
