X-Git-Url: http://git.iain.cx/?a=blobdiff_plain;f=gui.cpp;h=ca21ace0bb2fd759aad564fec6f372b9f37c9ab7;hb=470de9224d9473853d24006d7ae13eba818ecf0f;hp=013f2f0a9566e10f8a506ec46311a4775e2592b6;hpb=b3a4446ab363b5895aa2e04c645ed5d5dfa00442;p=nssm.git diff --git a/gui.cpp b/gui.cpp index 013f2f0..ca21ace 100644 --- a/gui.cpp +++ b/gui.cpp @@ -1,18 +1,9 @@ #include "nssm.h" -static enum { NSSM_TAB_APPLICATION, NSSM_TAB_SHUTDOWN, NSSM_TAB_EXIT, NSSM_TAB_IO, NSSM_NUM_TABS }; +static enum { NSSM_TAB_APPLICATION, NSSM_TAB_SHUTDOWN, NSSM_TAB_EXIT, NSSM_TAB_IO, NSSM_TAB_ENVIRONMENT, NSSM_NUM_TABS }; static HWND tablist[NSSM_NUM_TABS]; static int selected_tab; -static void strip_basename(char *buffer) { - size_t len = strlen(buffer); - size_t i; - for (i = len; i && buffer[i] != '\\' && buffer[i] != '/'; i--); - /* X:\ is OK. */ - if (i && buffer[i-1] == ':') i++; - buffer[i] = '\0'; -} - int nssm_gui(int resource, char *name) { /* Create window */ HWND dlg = CreateDialog(0, MAKEINTRESOURCE(resource), 0, install_dlg); @@ -96,6 +87,8 @@ int install(HWND window) { nssm_service_t *service = alloc_nssm_service(); if (service) { + set_nssm_service_defaults(service); + /* Get service name. */ if (! GetDlgItemText(window, IDC_NAME, service->name, sizeof(service->name))) { popup_message(MB_OK | MB_ICONEXCLAMATION, NSSM_GUI_MISSING_SERVICE_NAME); @@ -120,11 +113,10 @@ int install(HWND window) { if (! GetDlgItemText(window, IDC_FLAGS, service->flags, sizeof(service->flags))) { popup_message(MB_OK | MB_ICONEXCLAMATION, NSSM_GUI_INVALID_OPTIONS); return 4; - } + } } /* Get stop method stuff. */ - service->stop_method = ~0; check_stop_method(service, NSSM_STOP_METHOD_CONSOLE, IDC_METHOD_CONSOLE); check_stop_method(service, NSSM_STOP_METHOD_WINDOW, IDC_METHOD_WINDOW); check_stop_method(service, NSSM_STOP_METHOD_THREADS, IDC_METHOD_THREADS); @@ -143,6 +135,85 @@ int install(HWND window) { check_io("stdin", service->stdin_path, sizeof(service->stdin_path), IDC_STDIN); check_io("stdout", service->stdout_path, sizeof(service->stdout_path), IDC_STDOUT); check_io("stderr", service->stderr_path, sizeof(service->stderr_path), IDC_STDERR); + /* Override stdout and/or stderr. */ + if (SendDlgItemMessage(tablist[NSSM_TAB_IO], IDC_TRUNCATE, BM_GETCHECK, 0, 0) & BST_CHECKED) { + if (service->stdout_path[0]) service->stdout_disposition = CREATE_ALWAYS; + if (service->stderr_path[0]) service->stderr_disposition = CREATE_ALWAYS; + } + + /* Get environment. */ + unsigned long envlen = (unsigned long) SendMessage(GetDlgItem(tablist[NSSM_TAB_ENVIRONMENT], IDC_ENVIRONMENT), WM_GETTEXTLENGTH, 0, 0); + if (envlen) { + char *env = (char *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, envlen + 2); + if (! env) { + popup_message(MB_OK | MB_ICONEXCLAMATION, NSSM_EVENT_OUT_OF_MEMORY, "environment", "install()"); + cleanup_nssm_service(service); + return 5; + } + + if (! GetDlgItemText(tablist[NSSM_TAB_ENVIRONMENT], IDC_ENVIRONMENT, env, envlen + 1)) { + popup_message(MB_OK | MB_ICONEXCLAMATION, NSSM_GUI_INVALID_ENVIRONMENT); + HeapFree(GetProcessHeap(), 0, env); + cleanup_nssm_service(service); + return 5; + } + + /* Strip CR and replace LF with NULL. */ + unsigned long newlen = 0; + unsigned long i, j; + for (i = 0; i < envlen; i++) if (env[i] != '\r') newlen++; + /* Must end with two NULLs. */ + newlen += 2; + + char *newenv = (char *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, newlen); + if (! newenv) { + HeapFree(GetProcessHeap(), 0, env); + popup_message(MB_OK | MB_ICONEXCLAMATION, NSSM_EVENT_OUT_OF_MEMORY, "environment", "install()"); + cleanup_nssm_service(service); + return 5; + } + + for (i = 0, j = 0; i < envlen; i++) { + if (env[i] == '\r') continue; + if (env[i] == '\n') newenv[j] = '\0'; + else newenv[j] = env[i]; + j++; + } + + HeapFree(GetProcessHeap(), 0, env); + env = newenv; + envlen = newlen; + + /* Test the environment is valid. */ + char path[MAX_PATH]; + GetModuleFileName(0, path, sizeof(path)); + STARTUPINFO si; + ZeroMemory(&si, sizeof(si)); + si.cb = sizeof(si); + PROCESS_INFORMATION pi; + ZeroMemory(&pi, sizeof(pi)); + + if (! CreateProcess(0, path, 0, 0, 0, CREATE_SUSPENDED, env, 0, &si, &pi)) { + unsigned long error = GetLastError(); + if (error == ERROR_INVALID_PARAMETER) { + popup_message(MB_OK | MB_ICONEXCLAMATION, NSSM_GUI_INVALID_ENVIRONMENT); + HeapFree(GetProcessHeap(), 0, env); + envlen = 0; + } + cleanup_nssm_service(service); + return 5; + } + TerminateProcess(pi.hProcess, 0); + + if (SendDlgItemMessage(tablist[NSSM_TAB_ENVIRONMENT], IDC_ENVIRONMENT_REPLACE, BM_GETCHECK, 0, 0) & BST_CHECKED) { + service->env = env; + service->envlen = envlen; + } + else { + service->env_extra = env; + service->env_extralen = envlen; + } + } } /* See if it works. */ @@ -370,6 +441,8 @@ INT_PTR CALLBACK install_dlg(HWND window, UINT message, WPARAM w, LPARAM l) { switch (message) { /* Creating the dialogue */ case WM_INITDIALOG: + SetFocus(GetDlgItem(window, IDC_NAME)); + HWND tabs; HWND combo; tabs = GetDlgItem(window, IDC_TAB1); @@ -426,6 +499,13 @@ INT_PTR CALLBACK install_dlg(HWND window, UINT message, WPARAM w, LPARAM l) { tablist[NSSM_TAB_IO] = CreateDialog(0, MAKEINTRESOURCE(IDD_IO), window, tab_dlg); ShowWindow(tablist[NSSM_TAB_IO], SW_HIDE); + /* Environment tab. */ + tab.pszText = message_string(NSSM_GUI_TAB_ENVIRONMENT); + tab.cchTextMax = (int) strlen(tab.pszText) + 1; + SendMessage(tabs, TCM_INSERTITEM, NSSM_TAB_ENVIRONMENT, (LPARAM) &tab); + tablist[NSSM_TAB_ENVIRONMENT] = CreateDialog(0, MAKEINTRESOURCE(IDD_ENVIRONMENT), window, tab_dlg); + ShowWindow(tablist[NSSM_TAB_ENVIRONMENT], SW_HIDE); + selected_tab = 0; return 1;