mirror of
https://github.com/EnderIce2/rpc-bridge.git
synced 2025-05-28 15:34:34 +00:00
Add script for Steam (#2)
This commit is contained in:
parent
7461479cbb
commit
7af098ab26
6
.vscode/settings.json
vendored
6
.vscode/settings.json
vendored
@ -2,7 +2,11 @@
|
|||||||
"C_Cpp.default.compilerPath": "/usr/bin/i686-w64-mingw32-gcc",
|
"C_Cpp.default.compilerPath": "/usr/bin/i686-w64-mingw32-gcc",
|
||||||
"files.associations": {
|
"files.associations": {
|
||||||
"*.su": "tsv",
|
"*.su": "tsv",
|
||||||
|
"thread": "cpp",
|
||||||
|
"bitset": "cpp",
|
||||||
|
"initializer_list": "cpp",
|
||||||
"windows.h": "c",
|
"windows.h": "c",
|
||||||
"namedpipeapi.h": "c"
|
"namedpipeapi.h": "c",
|
||||||
|
"*.rh": "c"
|
||||||
}
|
}
|
||||||
}
|
}
|
11
bridge.c
11
bridge.c
@ -440,17 +440,6 @@ void PipeBufferOutThread(LPVOID lpParam)
|
|||||||
|
|
||||||
void CreateBridge()
|
void CreateBridge()
|
||||||
{
|
{
|
||||||
static void(CDECL * wine_get_host_version)(const char **sysname, const char **release);
|
|
||||||
HMODULE hntdll = GetModuleHandle("ntdll.dll");
|
|
||||||
wine_get_host_version = (void *)GetProcAddress(hntdll, "wine_get_host_version");
|
|
||||||
|
|
||||||
assert(wine_get_host_version);
|
|
||||||
const char *__sysname;
|
|
||||||
const char *__release;
|
|
||||||
wine_get_host_version(&__sysname, &__release);
|
|
||||||
IsLinux = strcmp(__sysname, "Linux") == 0;
|
|
||||||
print("Running on %s\n", __sysname);
|
|
||||||
|
|
||||||
LPCTSTR lpszPipename = TEXT("\\\\.\\pipe\\discord-ipc-0");
|
LPCTSTR lpszPipename = TEXT("\\\\.\\pipe\\discord-ipc-0");
|
||||||
|
|
||||||
NewConnection:
|
NewConnection:
|
||||||
|
32
build/bridge.sh
Executable file
32
build/bridge.sh
Executable file
@ -0,0 +1,32 @@
|
|||||||
|
#! /bin/sh
|
||||||
|
|
||||||
|
# This script is used to run Steam Play with the bridge.
|
||||||
|
# Usage: /path/to/bridge.sh %command%
|
||||||
|
# Original script: https://github.com/0e4ef622/wine-discord-ipc-bridge/blob/master/winediscordipcbridge-steam.sh
|
||||||
|
# As requested by https://github.com/EnderIce2/rpc-bridge/issues/2
|
||||||
|
|
||||||
|
# Exporting BRIDGE_PATH to provide the bridge with its location.
|
||||||
|
export BRIDGE_PATH="$(dirname "$0")/bridge.exe"
|
||||||
|
|
||||||
|
# The "--steam" option prevents the game from
|
||||||
|
# hanging as "running" in Steam after it is closed.
|
||||||
|
# This is done by creating a dummy service with
|
||||||
|
# startup type SERVICE_DEMAND_START so this service
|
||||||
|
# is only started when we use this script.
|
||||||
|
BRIDGE_CMD="$BRIDGE_PATH --steam"
|
||||||
|
|
||||||
|
# Linux
|
||||||
|
TEMP_PATH="$XDG_RUNTIME_DIR"
|
||||||
|
# macOS but Steam Play is not supported on macOS https://github.com/ValveSoftware/Proton/issues/1344
|
||||||
|
TEMP_PATH=${TEMP_PATH:-"$TMPDIR"}
|
||||||
|
|
||||||
|
VESSEL_PATH="$BRIDGE_PATH"
|
||||||
|
IPC_PATHS="$TEMP_PATH /run/user/$UID $TEMP_PATH/snap.discord $TEMP_PATH/app/com.discordapp.Discord"
|
||||||
|
for discord_ipc in $IPC_PATHS; do
|
||||||
|
if [ -S "$discord_ipc"/discord-ipc-0 ]; then
|
||||||
|
VESSEL_PATH="$BRIDGE_PATH:$(echo "$discord_ipc"/discord-ipc-0)"
|
||||||
|
break
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
|
||||||
|
PROTON_REMOTE_DEBUG_CMD="$BRIDGE_CMD" PRESSURE_VESSEL_FILESYSTEMS_RW="$VESSEL_PATH:$PRESSURE_VESSEL_FILESYSTEMS_RW" "$@"
|
230
main.c
230
main.c
@ -9,8 +9,10 @@ BOOL RunningAsService = FALSE;
|
|||||||
void CreateBridge();
|
void CreateBridge();
|
||||||
void LaunchGame(int argc, char **argv);
|
void LaunchGame(int argc, char **argv);
|
||||||
void ServiceMain(int argc, char *argv[]);
|
void ServiceMain(int argc, char *argv[]);
|
||||||
void InstallService();
|
void InstallService(int ServiceStartType, LPCSTR Path);
|
||||||
|
char *native_getenv(const char *name);
|
||||||
void RemoveService();
|
void RemoveService();
|
||||||
|
extern BOOL IsLinux;
|
||||||
|
|
||||||
LPTSTR GetErrorMessage()
|
LPTSTR GetErrorMessage()
|
||||||
{
|
{
|
||||||
@ -45,7 +47,12 @@ void DetectWine()
|
|||||||
{
|
{
|
||||||
HMODULE hNTdll = GetModuleHandle("ntdll.dll");
|
HMODULE hNTdll = GetModuleHandle("ntdll.dll");
|
||||||
if (!hNTdll)
|
if (!hNTdll)
|
||||||
|
{
|
||||||
|
MessageBox(NULL, "Failed to load ntdll.dll",
|
||||||
|
GetErrorMessage(), MB_OK | MB_ICONERROR);
|
||||||
ExitProcess(1);
|
ExitProcess(1);
|
||||||
|
}
|
||||||
|
|
||||||
if (!GetProcAddress(hNTdll, "wine_get_version"))
|
if (!GetProcAddress(hNTdll, "wine_get_version"))
|
||||||
{
|
{
|
||||||
MessageBox(NULL, "This program is only intended to run under Wine.",
|
MessageBox(NULL, "This program is only intended to run under Wine.",
|
||||||
@ -69,6 +76,9 @@ void DetectWine()
|
|||||||
else if (result == IDNO)
|
else if (result == IDNO)
|
||||||
ExitProcess(1);
|
ExitProcess(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
IsLinux = strcmp(__sysname, "Linux") == 0;
|
||||||
|
printf("Running on %s\n", __sysname);
|
||||||
}
|
}
|
||||||
|
|
||||||
void print(char const *fmt, ...)
|
void print(char const *fmt, ...)
|
||||||
@ -82,6 +92,190 @@ void print(char const *fmt, ...)
|
|||||||
va_end(args);
|
va_end(args);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void HandleArguments(int argc, char *argv[])
|
||||||
|
{
|
||||||
|
if (strcmp(argv[1], "--service") == 0)
|
||||||
|
{
|
||||||
|
RunningAsService = TRUE;
|
||||||
|
print("Running as service\n");
|
||||||
|
|
||||||
|
SERVICE_TABLE_ENTRY ServiceTable[] =
|
||||||
|
{
|
||||||
|
{"rpc-bridge", (LPSERVICE_MAIN_FUNCTION)ServiceMain},
|
||||||
|
{NULL, NULL},
|
||||||
|
};
|
||||||
|
|
||||||
|
if (StartServiceCtrlDispatcher(ServiceTable) == FALSE)
|
||||||
|
{
|
||||||
|
print("Service failed to start\n");
|
||||||
|
ExitProcess(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (strcmp(argv[1], "--steam") == 0)
|
||||||
|
{
|
||||||
|
/* All this mess just so when you close the game,
|
||||||
|
it automatically closes the bridge and Steam
|
||||||
|
will not say that the game is still running. */
|
||||||
|
|
||||||
|
print("Running as Steam\n");
|
||||||
|
if (IsLinux == FALSE)
|
||||||
|
CreateBridge();
|
||||||
|
|
||||||
|
if (argc > 2)
|
||||||
|
{
|
||||||
|
if (strcmp(argv[2], "--no-service") == 0)
|
||||||
|
CreateBridge();
|
||||||
|
}
|
||||||
|
|
||||||
|
SC_HANDLE hSCManager = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
|
||||||
|
if (hSCManager == NULL)
|
||||||
|
{
|
||||||
|
print("(Steam) OpenSCManager: %s\n", GetErrorMessage());
|
||||||
|
ExitProcess(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
SC_HANDLE schService = OpenService(hSCManager, "rpc-bridge",
|
||||||
|
SERVICE_QUERY_CONFIG | SERVICE_CHANGE_CONFIG | SERVICE_START);
|
||||||
|
if (schService == NULL)
|
||||||
|
{
|
||||||
|
if (GetLastError() != ERROR_SERVICE_DOES_NOT_EXIST)
|
||||||
|
{
|
||||||
|
print("(Steam) OpenService: %s\n", GetErrorMessage());
|
||||||
|
ExitProcess(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
print("(Steam) Service does not exist, registering...\n");
|
||||||
|
|
||||||
|
WCHAR *(CDECL * wine_get_dos_file_name)(LPCSTR str) =
|
||||||
|
(void *)GetProcAddress(GetModuleHandleA("KERNEL32"),
|
||||||
|
"wine_get_dos_file_name");
|
||||||
|
|
||||||
|
char *unixPath = native_getenv("BRIDGE_PATH");
|
||||||
|
if (unixPath == NULL)
|
||||||
|
{
|
||||||
|
print("(Steam) BRIDGE_PATH not set\n");
|
||||||
|
ExitProcess(1);
|
||||||
|
}
|
||||||
|
WCHAR *dosPath = wine_get_dos_file_name(unixPath);
|
||||||
|
LPSTR asciiPath = (LPSTR)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, MAX_PATH);
|
||||||
|
WideCharToMultiByte(CP_ACP, 0, dosPath, -1, asciiPath, MAX_PATH, NULL, NULL);
|
||||||
|
|
||||||
|
strcat_s(asciiPath, MAX_PATH, " --service");
|
||||||
|
print("(Steam) Binary path: %s\n", asciiPath);
|
||||||
|
|
||||||
|
InstallService(SERVICE_DEMAND_START, asciiPath);
|
||||||
|
HeapFree(GetProcessHeap(), 0, asciiPath);
|
||||||
|
|
||||||
|
/* Create handle for StartService below */
|
||||||
|
print("(Steam) Service registered, opening handle...\n");
|
||||||
|
/* FIXME: For some reason here it freezes??? */
|
||||||
|
schService = OpenService(hSCManager, "rpc-bridge", SERVICE_START);
|
||||||
|
if (schService == NULL)
|
||||||
|
{
|
||||||
|
print("(Steam) Cannot open service after creation: %s\n", GetErrorMessage());
|
||||||
|
ExitProcess(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
DWORD dwBytesNeeded;
|
||||||
|
QueryServiceConfig(schService, NULL, 0, &dwBytesNeeded);
|
||||||
|
LPQUERY_SERVICE_CONFIG lpqsc = (LPQUERY_SERVICE_CONFIG)LocalAlloc(LPTR, dwBytesNeeded);
|
||||||
|
if (lpqsc == NULL)
|
||||||
|
{
|
||||||
|
print("(Steam) LocalAlloc: %s\n", GetErrorMessage());
|
||||||
|
ExitProcess(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!QueryServiceConfig(schService, lpqsc, dwBytesNeeded, &dwBytesNeeded))
|
||||||
|
{
|
||||||
|
print("(Steam) QueryServiceConfig: %s\n", GetErrorMessage());
|
||||||
|
ExitProcess(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
WCHAR *(CDECL * wine_get_dos_file_name)(LPCSTR str) =
|
||||||
|
(void *)GetProcAddress(GetModuleHandleA("KERNEL32"),
|
||||||
|
"wine_get_dos_file_name");
|
||||||
|
|
||||||
|
char *unixPath = native_getenv("BRIDGE_PATH");
|
||||||
|
if (unixPath == NULL)
|
||||||
|
{
|
||||||
|
print("(Steam) BRIDGE_PATH not set\n");
|
||||||
|
ExitProcess(1);
|
||||||
|
}
|
||||||
|
WCHAR *dosPath = wine_get_dos_file_name(unixPath);
|
||||||
|
LPSTR asciiPath = (LPSTR)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, MAX_PATH);
|
||||||
|
WideCharToMultiByte(CP_ACP, 0, dosPath, -1, asciiPath, MAX_PATH, NULL, NULL);
|
||||||
|
|
||||||
|
strcat_s(asciiPath, MAX_PATH, " --service");
|
||||||
|
print("(Steam) Binary path: %s\n", asciiPath);
|
||||||
|
|
||||||
|
if (strcmp(lpqsc->lpBinaryPathName, asciiPath) != 0)
|
||||||
|
{
|
||||||
|
print("(Steam) Service binary path is not correct, updating...\n");
|
||||||
|
ChangeServiceConfig(schService, SERVICE_NO_CHANGE, SERVICE_NO_CHANGE, SERVICE_NO_CHANGE,
|
||||||
|
asciiPath, NULL, NULL, NULL, NULL, NULL, NULL);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
print("(Steam) Service binary path is correct\n");
|
||||||
|
HeapFree(GetProcessHeap(), 0, asciiPath);
|
||||||
|
}
|
||||||
|
|
||||||
|
print("(Steam) Starting service...\n");
|
||||||
|
if (StartService(schService, 0, NULL) == FALSE)
|
||||||
|
{
|
||||||
|
if (GetLastError() == ERROR_SERVICE_ALREADY_RUNNING)
|
||||||
|
{
|
||||||
|
print("(Steam) Service is already running\n");
|
||||||
|
CloseServiceHandle(schService);
|
||||||
|
CloseServiceHandle(hSCManager);
|
||||||
|
ExitProcess(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
print("StartService: %s\n", GetErrorMessage());
|
||||||
|
MessageBox(NULL, GetErrorMessage(),
|
||||||
|
"StartService",
|
||||||
|
MB_OK | MB_ICONSTOP);
|
||||||
|
ExitProcess(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
print("(Steam) Service started successfully, exiting...\n");
|
||||||
|
CloseServiceHandle(schService);
|
||||||
|
CloseServiceHandle(hSCManager);
|
||||||
|
ExitProcess(0);
|
||||||
|
}
|
||||||
|
else if (strcmp(argv[1], "--install") == 0)
|
||||||
|
{
|
||||||
|
char filename[MAX_PATH];
|
||||||
|
GetModuleFileName(NULL, filename, MAX_PATH);
|
||||||
|
CopyFile(filename, "C:\\bridge.exe", FALSE);
|
||||||
|
|
||||||
|
InstallService(SERVICE_AUTO_START, "C:\\bridge.exe --service");
|
||||||
|
ExitProcess(0);
|
||||||
|
}
|
||||||
|
else if (strcmp(argv[1], "--uninstall") == 0)
|
||||||
|
{
|
||||||
|
RemoveService();
|
||||||
|
ExitProcess(0);
|
||||||
|
}
|
||||||
|
else if (strcmp(argv[1], "--help") == 0)
|
||||||
|
{
|
||||||
|
printf("Usage:\n");
|
||||||
|
printf(" %s [args]\n", argv[0]);
|
||||||
|
printf(" --help - Show this help\n");
|
||||||
|
printf(" --install - Install service\n");
|
||||||
|
printf(" This will copy the binary to C:\\bridge.exe and register it as a service\n");
|
||||||
|
printf(" --uninstall - Uninstall service\n");
|
||||||
|
printf(" This will remove the service and delete C:\\bridge.exe\n");
|
||||||
|
printf(" --steam - Reserved for Steam\n");
|
||||||
|
printf(" This will start the service and exit (used with bridge.sh)\n");
|
||||||
|
printf(" --no-service - Do not run as service\n");
|
||||||
|
printf(" (only for --steam)\n");
|
||||||
|
printf(" --service - Reserved for service\n");
|
||||||
|
ExitProcess(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int main(int argc, char *argv[])
|
int main(int argc, char *argv[])
|
||||||
{
|
{
|
||||||
DetectWine();
|
DetectWine();
|
||||||
@ -95,39 +289,7 @@ int main(int argc, char *argv[])
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (argc > 1)
|
if (argc > 1)
|
||||||
{
|
HandleArguments(argc, argv);
|
||||||
if (strcmp(argv[1], "--service") == 0)
|
|
||||||
{
|
|
||||||
RunningAsService = TRUE;
|
|
||||||
print("Running as service\n");
|
|
||||||
|
|
||||||
SERVICE_TABLE_ENTRY ServiceTable[] =
|
|
||||||
{
|
|
||||||
{"rpc-bridge", (LPSERVICE_MAIN_FUNCTION)ServiceMain},
|
|
||||||
{NULL, NULL},
|
|
||||||
};
|
|
||||||
|
|
||||||
if (StartServiceCtrlDispatcher(ServiceTable) == FALSE)
|
|
||||||
{
|
|
||||||
print("Service failed to start\n");
|
|
||||||
return GetLastError();
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
else if (strcmp(argv[1], "--install") == 0)
|
|
||||||
InstallService();
|
|
||||||
else if (strcmp(argv[1], "--uninstall") == 0)
|
|
||||||
RemoveService();
|
|
||||||
else if (strcmp(argv[1], "--help") == 0)
|
|
||||||
{
|
|
||||||
printf("Usage:\n");
|
|
||||||
printf(" %s [args]\n", argv[0]);
|
|
||||||
printf(" --install - Install service\n");
|
|
||||||
printf(" --uninstall - Uninstall service\n");
|
|
||||||
printf(" --help - Show this help\n");
|
|
||||||
ExitProcess(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)CreateBridge,
|
CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)CreateBridge,
|
||||||
NULL, 0, NULL);
|
NULL, 0, NULL);
|
||||||
|
45
service.c
45
service.c
@ -8,6 +8,7 @@ SERVICE_STATUS_HANDLE g_StatusHandle = NULL;
|
|||||||
void print(char const *fmt, ...);
|
void print(char const *fmt, ...);
|
||||||
void CreateBridge();
|
void CreateBridge();
|
||||||
LPTSTR GetErrorMessage();
|
LPTSTR GetErrorMessage();
|
||||||
|
extern BOOL IsLinux;
|
||||||
|
|
||||||
void WINAPI ServiceCtrlHandler(DWORD CtrlCode)
|
void WINAPI ServiceCtrlHandler(DWORD CtrlCode)
|
||||||
{
|
{
|
||||||
@ -83,68 +84,47 @@ void ServiceMain(DWORD argc, LPTSTR *argv)
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
void DetectDarwin()
|
void InstallService(int ServiceStartType, LPCSTR Path)
|
||||||
{
|
{
|
||||||
static void(CDECL * wine_get_host_version)(const char **sysname, const char **release);
|
print("Registering service\n");
|
||||||
wine_get_host_version = (void *)GetProcAddress(GetModuleHandle("ntdll.dll"),
|
|
||||||
"wine_get_host_version");
|
if (IsLinux == FALSE)
|
||||||
const char *__sysname;
|
|
||||||
const char *__release;
|
|
||||||
wine_get_host_version(&__sysname, &__release);
|
|
||||||
if (strcmp(__sysname, "Darwin") == 0)
|
|
||||||
{
|
{
|
||||||
/* FIXME: I don't know how to get the TMPDIR without getenv */
|
/* FIXME: I don't know how to get the TMPDIR without getenv */
|
||||||
MessageBox(NULL, "Registering as a service is not supported on macOS at the moment.",
|
MessageBox(NULL, "Registering as a service is not supported on macOS at the moment.",
|
||||||
"Unsupported", MB_OK | MB_ICONINFORMATION);
|
"Unsupported", MB_OK | MB_ICONINFORMATION);
|
||||||
ExitProcess(1);
|
ExitProcess(1);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
void InstallService()
|
SC_HANDLE schSCManager = OpenSCManager(NULL, NULL, SC_MANAGER_CREATE_SERVICE);
|
||||||
{
|
|
||||||
print("Registering to run on startup\n");
|
|
||||||
|
|
||||||
DetectDarwin();
|
|
||||||
|
|
||||||
SC_HANDLE schSCManager, schService;
|
|
||||||
DWORD dwTagId;
|
|
||||||
|
|
||||||
schSCManager = OpenSCManager(NULL, NULL, SC_MANAGER_CREATE_SERVICE);
|
|
||||||
if (schSCManager == NULL)
|
if (schSCManager == NULL)
|
||||||
{
|
{
|
||||||
|
print("Failed to open service manager\n");
|
||||||
MessageBox(NULL, GetErrorMessage(),
|
MessageBox(NULL, GetErrorMessage(),
|
||||||
"OpenSCManager",
|
"OpenSCManager",
|
||||||
MB_OK | MB_ICONSTOP);
|
MB_OK | MB_ICONSTOP);
|
||||||
ExitProcess(1);
|
ExitProcess(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
schService =
|
DWORD dwTagId;
|
||||||
CreateService(schSCManager,
|
SC_HANDLE schService = CreateService(schSCManager,
|
||||||
"rpc-bridge", "Wine RPC Bridge",
|
"rpc-bridge", "Wine RPC Bridge",
|
||||||
SERVICE_ALL_ACCESS, SERVICE_WIN32_OWN_PROCESS,
|
SERVICE_ALL_ACCESS, SERVICE_WIN32_OWN_PROCESS,
|
||||||
SERVICE_AUTO_START, SERVICE_ERROR_NORMAL,
|
ServiceStartType, SERVICE_ERROR_NORMAL,
|
||||||
"C:\\bridge.exe --service",
|
Path, NULL, &dwTagId, NULL, NULL, NULL);
|
||||||
NULL, &dwTagId, NULL, NULL, NULL);
|
|
||||||
|
|
||||||
if (schService == NULL)
|
if (schService == NULL)
|
||||||
{
|
{
|
||||||
|
print("Failed to create service\n");
|
||||||
MessageBox(NULL, GetErrorMessage(),
|
MessageBox(NULL, GetErrorMessage(),
|
||||||
"CreateService",
|
"CreateService",
|
||||||
MB_OK | MB_ICONSTOP);
|
MB_OK | MB_ICONSTOP);
|
||||||
ExitProcess(1);
|
ExitProcess(1);
|
||||||
}
|
}
|
||||||
else
|
|
||||||
{
|
|
||||||
char filename[MAX_PATH];
|
|
||||||
GetModuleFileName(NULL, filename, MAX_PATH);
|
|
||||||
CopyFile(filename, "C:\\bridge.exe", FALSE);
|
|
||||||
|
|
||||||
print("Service installed successfully\n");
|
print("Service installed successfully\n");
|
||||||
CloseServiceHandle(schService);
|
CloseServiceHandle(schService);
|
||||||
}
|
|
||||||
|
|
||||||
CloseServiceHandle(schSCManager);
|
CloseServiceHandle(schSCManager);
|
||||||
ExitProcess(0);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void RemoveService()
|
void RemoveService()
|
||||||
@ -208,5 +188,4 @@ void RemoveService()
|
|||||||
print("Service removed successfully\n");
|
print("Service removed successfully\n");
|
||||||
CloseServiceHandle(schService);
|
CloseServiceHandle(schService);
|
||||||
CloseServiceHandle(schSCManager);
|
CloseServiceHandle(schSCManager);
|
||||||
ExitProcess(0);
|
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user