Thursday, 26 March 2015

Starting WebClient Service Programmatically

I've been asked how you can start the WebClient service on Windows 7+ programmatically, specifically in relation to this issue. If you try and start it manually (say using the sc tool) as a normal user you'll find you get access denied. However the service is actually registered with a service trigger, so it'll be started automatically in response to a specific system event.

We can dump the trigger information for the service using the command sc qtriggerinfo WebClient which gives us:
START SERVICE
   CUSTOM       : 22b6d684-fa63-4578-87c9-effcbe6643c7 [ETW PROVIDER UUID]
This indicates that the service trigger is a custom ETW event trigger with the specified provider UUID. So all we need to do is write an event using that trigger as a normal user and we'll get the WebClient service to start. So something like:
bool StartWebClientService()
{
    const GUID _MS_Windows_WebClntLookupServiceTrigger_Provider =
        { 0x22B6D684, 0xFA63, 0x4578, 
        { 0x87, 0xC9, 0xEF, 0xFC, 0xBE, 0x66, 0x43, 0xC7 } };
    REGHANDLE Handle;
    bool success = false;

    if (EventRegister(&_MS_Windows_WebClntLookupServiceTrigger_Provider,
        nullptr, nullptr, &Handle) == ERROR_SUCCESS)
    {
        EVENT_DESCRIPTOR desc;

        EventDescCreate(&desc, 1, 0, 0, 4, 0, 0, 0);

        success = EventWrite(Handle, &desc, 0, nullptr) == ERROR_SUCCESS;

        EventUnregister(Handle);
    }

    return success;
}
I haven't tested this from all locations but you can almost certainly cause this trigger to run even from a heavily restrictive sandbox such as Chrome or EPM.