wbemprox: Implement Win32_Service.PauseService.
This commit is contained in:
parent
64a7f2ea7f
commit
8fe25b2b89
|
@ -7,6 +7,7 @@ C_SRCS = \
|
|||
main.c \
|
||||
query.c \
|
||||
reg.c \
|
||||
service.c \
|
||||
services.c \
|
||||
table.c \
|
||||
wbemlocator.c
|
||||
|
|
|
@ -65,8 +65,6 @@ static const WCHAR class_processW[] =
|
|||
{'W','i','n','3','2','_','P','r','o','c','e','s','s',0};
|
||||
static const WCHAR class_processorW[] =
|
||||
{'W','i','n','3','2','_','P','r','o','c','e','s','s','o','r',0};
|
||||
static const WCHAR class_serviceW[] =
|
||||
{'W','i','n','3','2','_','S','e','r','v','i','c','e',0};
|
||||
static const WCHAR class_sounddeviceW[] =
|
||||
{'W','i','n','3','2','_','S','o','u','n','d','D','e','v','i','c','e',0};
|
||||
static const WCHAR class_videocontrollerW[] =
|
||||
|
@ -132,8 +130,6 @@ static const WCHAR prop_methodW[] =
|
|||
{'M','e','t','h','o','d',0};
|
||||
static const WCHAR prop_modelW[] =
|
||||
{'M','o','d','e','l',0};
|
||||
static const WCHAR prop_nameW[] =
|
||||
{'N','a','m','e',0};
|
||||
static const WCHAR prop_netconnectionstatusW[] =
|
||||
{'N','e','t','C','o','n','n','e','c','t','i','o','n','S','t','a','t','u','s',0};
|
||||
static const WCHAR prop_numlogicalprocessorsW[] =
|
||||
|
@ -295,7 +291,9 @@ static const struct column col_service[] =
|
|||
{ prop_servicetypeW, CIM_STRING },
|
||||
{ prop_startmodeW, CIM_STRING },
|
||||
{ prop_stateW, CIM_STRING },
|
||||
{ prop_systemnameW, CIM_STRING|COL_FLAG_DYNAMIC }
|
||||
{ prop_systemnameW, CIM_STRING|COL_FLAG_DYNAMIC },
|
||||
/* methods */
|
||||
{ method_pauseserviceW, CIM_FLAG_ARRAY|COL_FLAG_METHOD }
|
||||
};
|
||||
static const struct column col_sounddevice[] =
|
||||
{
|
||||
|
@ -473,6 +471,8 @@ struct record_service
|
|||
const WCHAR *startmode;
|
||||
const WCHAR *state;
|
||||
const WCHAR *systemname;
|
||||
/* methods */
|
||||
class_method *pause_service;
|
||||
};
|
||||
struct record_sounddevice
|
||||
{
|
||||
|
@ -514,6 +514,7 @@ static const struct record_diskdrive data_diskdrive[] =
|
|||
};
|
||||
static const struct record_params data_params[] =
|
||||
{
|
||||
{ class_serviceW, method_pauseserviceW, -1, param_returnvalueW, CIM_UINT32, VT_I4 },
|
||||
{ class_stdregprovW, method_enumkeyW, 1, param_defkeyW, CIM_SINT32, 0, 0x80000002 },
|
||||
{ class_stdregprovW, method_enumkeyW, 1, param_subkeynameW, CIM_STRING },
|
||||
{ class_stdregprovW, method_enumkeyW, -1, param_returnvalueW, CIM_UINT32, VT_I4 },
|
||||
|
@ -1103,15 +1104,16 @@ static void fill_service( struct table *table )
|
|||
|
||||
status = &services[i].ServiceStatusProcess;
|
||||
rec = (struct record_service *)(table->data + offset);
|
||||
rec->accept_pause = (status->dwControlsAccepted & SERVICE_ACCEPT_PAUSE_CONTINUE) ? -1 : 0;
|
||||
rec->accept_stop = (status->dwControlsAccepted & SERVICE_ACCEPT_STOP) ? -1 : 0;
|
||||
rec->displayname = heap_strdupW( services[i].lpDisplayName );
|
||||
rec->name = heap_strdupW( services[i].lpServiceName );
|
||||
rec->process_id = status->dwProcessId;
|
||||
rec->servicetype = get_service_type( status->dwServiceType );
|
||||
rec->startmode = get_service_startmode( config->dwStartType );
|
||||
rec->state = get_service_state( status->dwCurrentState );
|
||||
rec->systemname = heap_strdupW( sysnameW );
|
||||
rec->accept_pause = (status->dwControlsAccepted & SERVICE_ACCEPT_PAUSE_CONTINUE) ? -1 : 0;
|
||||
rec->accept_stop = (status->dwControlsAccepted & SERVICE_ACCEPT_STOP) ? -1 : 0;
|
||||
rec->displayname = heap_strdupW( services[i].lpDisplayName );
|
||||
rec->name = heap_strdupW( services[i].lpServiceName );
|
||||
rec->process_id = status->dwProcessId;
|
||||
rec->servicetype = get_service_type( status->dwServiceType );
|
||||
rec->startmode = get_service_startmode( config->dwStartType );
|
||||
rec->state = get_service_state( status->dwCurrentState );
|
||||
rec->systemname = heap_strdupW( sysnameW );
|
||||
rec->pause_service = service_pause_service;
|
||||
heap_free( config );
|
||||
offset += sizeof(*rec);
|
||||
num_rows++;
|
||||
|
|
|
@ -0,0 +1,113 @@
|
|||
/*
|
||||
* Win32_Service methods implementation
|
||||
*
|
||||
* Copyright 2012 Hans Leidekker for CodeWeavers
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2.1 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
|
||||
*/
|
||||
|
||||
#define COBJMACROS
|
||||
|
||||
#include "config.h"
|
||||
#include <stdarg.h>
|
||||
|
||||
#include "windef.h"
|
||||
#include "winbase.h"
|
||||
#include "wbemcli.h"
|
||||
#include "winsvc.h"
|
||||
|
||||
#include "wine/debug.h"
|
||||
#include "wbemprox_private.h"
|
||||
|
||||
WINE_DEFAULT_DEBUG_CHANNEL(wbemprox);
|
||||
|
||||
static UINT map_error( DWORD error )
|
||||
{
|
||||
switch (error)
|
||||
{
|
||||
case ERROR_SUCCESS: return 0;
|
||||
case ERROR_ACCESS_DENIED: return 2;
|
||||
case ERROR_DEPENDENT_SERVICES_RUNNING: return 3;
|
||||
case ERROR_INVALID_SERVICE_CONTROL: return 4;
|
||||
case ERROR_SERVICE_CANNOT_ACCEPT_CTRL: return 5;
|
||||
case ERROR_SERVICE_NOT_ACTIVE: return 6;
|
||||
case ERROR_SERVICE_REQUEST_TIMEOUT: return 7;
|
||||
case ERROR_SERVICE_ALREADY_RUNNING: return 10;
|
||||
default:
|
||||
WARN("unknown error %u\n", error);
|
||||
break;
|
||||
}
|
||||
return 8;
|
||||
}
|
||||
|
||||
static HRESULT control_service( const WCHAR *name, DWORD control, VARIANT *retval )
|
||||
{
|
||||
SC_HANDLE manager, service = NULL;
|
||||
SERVICE_STATUS status;
|
||||
UINT error = 0;
|
||||
|
||||
if (!(manager = OpenSCManagerW( NULL, NULL, SC_MANAGER_ENUMERATE_SERVICE )))
|
||||
{
|
||||
error = map_error( GetLastError() );
|
||||
goto done;
|
||||
}
|
||||
if (!(service = OpenServiceW( manager, name, SERVICE_STOP|SERVICE_START|SERVICE_PAUSE_CONTINUE )))
|
||||
{
|
||||
error = map_error( GetLastError() );
|
||||
goto done;
|
||||
}
|
||||
if (!ControlService( service, control, &status )) error = map_error( GetLastError() );
|
||||
|
||||
done:
|
||||
set_variant( VT_UI4, error, NULL, retval );
|
||||
CloseServiceHandle( service );
|
||||
CloseServiceHandle( manager );
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
HRESULT service_pause_service( IWbemClassObject *obj, IWbemClassObject *in, IWbemClassObject **out )
|
||||
{
|
||||
VARIANT name, retval;
|
||||
IWbemClassObject *sig;
|
||||
HRESULT hr;
|
||||
|
||||
TRACE("%p, %p, %p\n", obj, in, out);
|
||||
|
||||
hr = IWbemClassObject_Get( obj, prop_nameW, 0, &name, NULL, NULL );
|
||||
if (hr != S_OK) return hr;
|
||||
|
||||
hr = create_signature( class_serviceW, method_pauseserviceW, PARAM_OUT, &sig );
|
||||
if (hr != S_OK)
|
||||
{
|
||||
VariantClear( &name );
|
||||
return hr;
|
||||
}
|
||||
hr = IWbemClassObject_SpawnInstance( sig, 0, out );
|
||||
if (hr != S_OK)
|
||||
{
|
||||
VariantClear( &name );
|
||||
IWbemClassObject_Release( sig );
|
||||
return hr;
|
||||
}
|
||||
hr = control_service( V_BSTR(&name), SERVICE_CONTROL_PAUSE, &retval );
|
||||
if (hr != S_OK) goto done;
|
||||
hr = IWbemClassObject_Put( *out, param_returnvalueW, 0, &retval, CIM_UINT32 );
|
||||
|
||||
done:
|
||||
VariantClear( &name );
|
||||
IWbemClassObject_Release( sig );
|
||||
if (hr != S_OK) IWbemClassObject_Release( *out );
|
||||
return hr;
|
||||
}
|
|
@ -201,6 +201,7 @@ HRESULT EnumWbemClassObject_create(IUnknown *, struct query *, LPVOID *) DECLSPE
|
|||
HRESULT reg_enum_key(IWbemClassObject *, IWbemClassObject *, IWbemClassObject **) DECLSPEC_HIDDEN;
|
||||
HRESULT reg_enum_values(IWbemClassObject *, IWbemClassObject *, IWbemClassObject **) DECLSPEC_HIDDEN;
|
||||
HRESULT reg_get_stringvalue(IWbemClassObject *, IWbemClassObject *, IWbemClassObject **) DECLSPEC_HIDDEN;
|
||||
HRESULT service_pause_service(IWbemClassObject *, IWbemClassObject *, IWbemClassObject **) DECLSPEC_HIDDEN;
|
||||
|
||||
static void *heap_alloc( size_t len ) __WINE_ALLOC_SIZE(1);
|
||||
static inline void *heap_alloc( size_t len )
|
||||
|
@ -233,11 +234,15 @@ static inline WCHAR *heap_strdupW( const WCHAR *src )
|
|||
return dst;
|
||||
}
|
||||
|
||||
static const WCHAR class_serviceW[] = {'W','i','n','3','2','_','S','e','r','v','i','c','e',0};
|
||||
static const WCHAR class_stdregprovW[] = {'S','t','d','R','e','g','P','r','o','v',0};
|
||||
|
||||
static const WCHAR prop_nameW[] = {'N','a','m','e',0};
|
||||
|
||||
static const WCHAR method_enumkeyW[] = {'E','n','u','m','K','e','y',0};
|
||||
static const WCHAR method_enumvaluesW[] = {'E','n','u','m','V','a','l','u','e','s',0};
|
||||
static const WCHAR method_getstringvalueW[] = {'G','e','t','S','t','r','i','n','g','V','a','l','u','e',0};
|
||||
static const WCHAR method_pauseserviceW[] = {'P','a','u','s','e','S','e','r','v','i','c','e',0};
|
||||
|
||||
static const WCHAR param_defkeyW[] = {'h','D','e','f','K','e','y',0};
|
||||
static const WCHAR param_namesW[] = {'s','N','a','m','e','s',0};
|
||||
|
|
Loading…
Reference in New Issue