mirror of
https://github.com/ValdikSS/GoodbyeDPI.git
synced 2024-12-22 06:15:27 +00:00
Windows Service support.
Program can now be started as a Windows Service. No additional arguments needed. Refer to `service_install` and `service_remove` scripts in released zip file.
This commit is contained in:
parent
95765f3ed9
commit
23babdc8fa
22
README.md
22
README.md
@ -79,26 +79,8 @@ And for x86_64:
|
|||||||
|
|
||||||
# How to install as Windows Service
|
# How to install as Windows Service
|
||||||
|
|
||||||
One way is using an [srvstart](http://www.rozanski.org.uk/software) program.
|
Use `service_install_russia_blacklist.cmd`, `service_install_russia_blacklist_dnsredir.cmd` and `service_remove.cmd` scripts.
|
||||||
Unpack it to `goodbyedpi` directory and create 3 files:
|
Modify them according to your own needs.
|
||||||
|
|
||||||
*goodbyedpi.ini*
|
|
||||||
```INI
|
|
||||||
[GoodByeDPI]
|
|
||||||
startup=goodbyedpi.exe
|
|
||||||
shutdown_method=winmessage
|
|
||||||
auto_restart=n
|
|
||||||
```
|
|
||||||
*srvinstall.bat*
|
|
||||||
```Batchfile
|
|
||||||
srvstart install GoodByeDPI -c %CD%\goodbyedpi.ini
|
|
||||||
```
|
|
||||||
*srvremove.bat*
|
|
||||||
```Batchfile
|
|
||||||
srvstart remove GoodByeDPI
|
|
||||||
```
|
|
||||||
Run these batch files as Administrator to install/remove service.
|
|
||||||
Open Windows Services panel to run service or make it start automaticaly.
|
|
||||||
|
|
||||||
# Similar projects
|
# Similar projects
|
||||||
|
|
||||||
|
13
goodbyedpi.c
13
goodbyedpi.c
@ -11,6 +11,7 @@
|
|||||||
#include <getopt.h>
|
#include <getopt.h>
|
||||||
#include "windivert.h"
|
#include "windivert.h"
|
||||||
#include "goodbyedpi.h"
|
#include "goodbyedpi.h"
|
||||||
|
#include "service.h"
|
||||||
#include "dnsredir.h"
|
#include "dnsredir.h"
|
||||||
#include "blackwhitelist.h"
|
#include "blackwhitelist.h"
|
||||||
|
|
||||||
@ -52,6 +53,7 @@
|
|||||||
} \
|
} \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
|
static int running_from_service = 0;
|
||||||
static HANDLE filters[MAX_FILTERS];
|
static HANDLE filters[MAX_FILTERS];
|
||||||
static int filter_num = 0;
|
static int filter_num = 0;
|
||||||
static const char *http10_redirect_302 = "HTTP/1.0 302 ";
|
static const char *http10_redirect_302 = "HTTP/1.0 302 ";
|
||||||
@ -144,7 +146,7 @@ static int deinit(HANDLE handle) {
|
|||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void deinit_all() {
|
void deinit_all() {
|
||||||
for (int i = 0; i < filter_num; i++) {
|
for (int i = 0; i < filter_num; i++) {
|
||||||
deinit(filters[i]);
|
deinit(filters[i]);
|
||||||
}
|
}
|
||||||
@ -277,6 +279,15 @@ int main(int argc, char *argv[]) {
|
|||||||
char *hdr_name_addr = NULL, *hdr_value_addr = NULL;
|
char *hdr_name_addr = NULL, *hdr_value_addr = NULL;
|
||||||
int hdr_value_len;
|
int hdr_value_len;
|
||||||
|
|
||||||
|
if (!running_from_service && service_register(argc, argv)) {
|
||||||
|
/* We've been called as a service. Register service
|
||||||
|
* and exit this thread. main() would be called from
|
||||||
|
* service.c next time.
|
||||||
|
*/
|
||||||
|
running_from_service = 1;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (filter_string == NULL) {
|
if (filter_string == NULL) {
|
||||||
filter_string = malloc(strlen(filter_string_template) + 1);
|
filter_string = malloc(strlen(filter_string_template) + 1);
|
||||||
strcpy(filter_string, filter_string_template);
|
strcpy(filter_string, filter_string_template);
|
||||||
|
@ -5,3 +5,6 @@
|
|||||||
#else
|
#else
|
||||||
#define debug(...) printf(__VA_ARGS__)
|
#define debug(...) printf(__VA_ARGS__)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
int main(int argc, char *argv[]);
|
||||||
|
void deinit_all();
|
||||||
|
83
service.c
Normal file
83
service.c
Normal file
@ -0,0 +1,83 @@
|
|||||||
|
#include <windows.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include "goodbyedpi.h"
|
||||||
|
#include "service.h"
|
||||||
|
|
||||||
|
#define SERVICE_NAME "GoodbyeDPI"
|
||||||
|
|
||||||
|
static SERVICE_STATUS ServiceStatus;
|
||||||
|
static SERVICE_STATUS_HANDLE hStatus;
|
||||||
|
static int service_argc;
|
||||||
|
static char **service_argv;
|
||||||
|
|
||||||
|
int service_register(int argc, char *argv[])
|
||||||
|
{
|
||||||
|
SERVICE_TABLE_ENTRY ServiceTable[] = {
|
||||||
|
{SERVICE_NAME, (LPSERVICE_MAIN_FUNCTION)service_main},
|
||||||
|
{NULL, NULL}
|
||||||
|
};
|
||||||
|
/*
|
||||||
|
* Save argc & argv as service_main is called with different
|
||||||
|
* arguments, which are passed from "start" command, not
|
||||||
|
* from the program command line.
|
||||||
|
* We don't need this behaviour.
|
||||||
|
*/
|
||||||
|
service_argc = argc;
|
||||||
|
service_argv = malloc(sizeof(void*) * argc);
|
||||||
|
for (int i = 0; i < argc; i++) {
|
||||||
|
service_argv[i] = strdup(argv[i]);
|
||||||
|
}
|
||||||
|
return StartServiceCtrlDispatcher(ServiceTable);
|
||||||
|
}
|
||||||
|
|
||||||
|
void service_main(int argc __attribute__((unused)),
|
||||||
|
char *argv[] __attribute__((unused)))
|
||||||
|
{
|
||||||
|
ServiceStatus.dwServiceType = SERVICE_WIN32_OWN_PROCESS;
|
||||||
|
ServiceStatus.dwCurrentState = SERVICE_RUNNING;
|
||||||
|
ServiceStatus.dwControlsAccepted = SERVICE_ACCEPT_STOP | SERVICE_ACCEPT_SHUTDOWN;
|
||||||
|
ServiceStatus.dwWin32ExitCode = 0;
|
||||||
|
ServiceStatus.dwServiceSpecificExitCode = 0;
|
||||||
|
ServiceStatus.dwCheckPoint = 1;
|
||||||
|
ServiceStatus.dwWaitHint = 0;
|
||||||
|
|
||||||
|
hStatus = RegisterServiceCtrlHandler(
|
||||||
|
SERVICE_NAME,
|
||||||
|
(LPHANDLER_FUNCTION)service_controlhandler);
|
||||||
|
if (hStatus == (SERVICE_STATUS_HANDLE)0)
|
||||||
|
{
|
||||||
|
// Registering Control Handler failed
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
SetServiceStatus(hStatus, &ServiceStatus);
|
||||||
|
|
||||||
|
// Calling main with saved argc & argv
|
||||||
|
main(service_argc, service_argv);
|
||||||
|
|
||||||
|
if (ServiceStatus.dwCurrentState != SERVICE_STOPPED) {
|
||||||
|
// If terminated with error
|
||||||
|
ServiceStatus.dwWin32ExitCode = 1;
|
||||||
|
ServiceStatus.dwCurrentState = SERVICE_STOPPED;
|
||||||
|
SetServiceStatus (hStatus, &ServiceStatus);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Control handler function
|
||||||
|
void service_controlhandler(DWORD request)
|
||||||
|
{
|
||||||
|
switch(request)
|
||||||
|
{
|
||||||
|
case SERVICE_CONTROL_STOP:
|
||||||
|
case SERVICE_CONTROL_SHUTDOWN:
|
||||||
|
deinit_all();
|
||||||
|
ServiceStatus.dwWin32ExitCode = 0;
|
||||||
|
ServiceStatus.dwCurrentState = SERVICE_STOPPED;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
// Report current status
|
||||||
|
SetServiceStatus (hStatus, &ServiceStatus);
|
||||||
|
return;
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user