qemu/qga/service-win32.c
<<
>>
Prefs
   1/*
   2 * QEMU Guest Agent helpers for win32 service management
   3 *
   4 * Copyright IBM Corp. 2012
   5 *
   6 * Authors:
   7 *  Gal Hammer        <ghammer@redhat.com>
   8 *  Michael Roth      <mdroth@linux.vnet.ibm.com>
   9 *
  10 * This work is licensed under the terms of the GNU GPL, version 2 or later.
  11 * See the COPYING file in the top-level directory.
  12 */
  13#include <stdlib.h>
  14#include <stdio.h>
  15#include <glib.h>
  16#include <windows.h>
  17#include "qga/service-win32.h"
  18
  19static int printf_win_error(const char *text)
  20{
  21    DWORD err = GetLastError();
  22    char *message;
  23    int n;
  24
  25    FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER |
  26        FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
  27        NULL,
  28        err,
  29        MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
  30        (char *)&message, 0,
  31        NULL);
  32    n = printf("%s. (Error: %d) %s", text, (int)err, message);
  33    LocalFree(message);
  34
  35    return n;
  36}
  37
  38int ga_install_service(const char *path, const char *logfile)
  39{
  40    SC_HANDLE manager;
  41    SC_HANDLE service;
  42    TCHAR cmdline[MAX_PATH];
  43
  44    if (GetModuleFileName(NULL, cmdline, MAX_PATH) == 0) {
  45        printf_win_error("No full path to service's executable");
  46        return EXIT_FAILURE;
  47    }
  48
  49    _snprintf(cmdline, MAX_PATH - strlen(cmdline), "%s -d", cmdline);
  50
  51    if (path) {
  52        _snprintf(cmdline, MAX_PATH - strlen(cmdline), "%s -p %s", cmdline, path);
  53    }
  54    if (logfile) {
  55        _snprintf(cmdline, MAX_PATH - strlen(cmdline), "%s -l %s -v",
  56            cmdline, logfile);
  57    }
  58
  59    g_debug("service's cmdline: %s", cmdline);
  60
  61    manager = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
  62    if (manager == NULL) {
  63        printf_win_error("No handle to service control manager");
  64        return EXIT_FAILURE;
  65    }
  66
  67    service = CreateService(manager, QGA_SERVICE_NAME, QGA_SERVICE_DISPLAY_NAME,
  68        SERVICE_ALL_ACCESS, SERVICE_WIN32_OWN_PROCESS, SERVICE_AUTO_START,
  69        SERVICE_ERROR_NORMAL, cmdline, NULL, NULL, NULL, NULL, NULL);
  70
  71    if (service) {
  72        SERVICE_DESCRIPTION desc = { (char *)QGA_SERVICE_DESCRIPTION };
  73        ChangeServiceConfig2(service, SERVICE_CONFIG_DESCRIPTION, &desc);
  74
  75        printf("Service was installed successfully.\n");
  76    } else {
  77        printf_win_error("Failed to install service");
  78    }
  79
  80    CloseServiceHandle(service);
  81    CloseServiceHandle(manager);
  82
  83    return (service == NULL);
  84}
  85
  86int ga_uninstall_service(void)
  87{
  88    SC_HANDLE manager;
  89    SC_HANDLE service;
  90
  91    manager = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
  92    if (manager == NULL) {
  93        printf_win_error("No handle to service control manager");
  94        return EXIT_FAILURE;
  95    }
  96
  97    service = OpenService(manager, QGA_SERVICE_NAME, DELETE);
  98    if (service == NULL) {
  99        printf_win_error("No handle to service");
 100        CloseServiceHandle(manager);
 101        return EXIT_FAILURE;
 102    }
 103
 104    if (DeleteService(service) == FALSE) {
 105        printf_win_error("Failed to delete service");
 106    } else {
 107        printf("Service was deleted successfully.\n");
 108    }
 109
 110    CloseServiceHandle(service);
 111    CloseServiceHandle(manager);
 112
 113    return EXIT_SUCCESS;
 114}
 115