- don't read the description directly from the registry

- give each property dialog it's own service data instead of relying on the the global current. This will eventually allow us to have multiple property dialogs open.

svn path=/trunk/; revision=28618
This commit is contained in:
Ged Murphy 2007-08-28 14:49:47 +00:00
parent 66747af942
commit fd255663f3
5 changed files with 198 additions and 158 deletions

View file

@ -161,7 +161,7 @@ ChangeListViewText(PMAIN_WND_INFO Info,
{ {
LPTSTR lpDescription; LPTSTR lpDescription;
lpDescription = GetDescription(Info->pCurrentService->lpServiceName); lpDescription = GetServiceDescription(Info->pCurrentService->lpServiceName);
item.pszText = lpDescription; item.pszText = lpDescription;
SendMessage(Info->hListView, SendMessage(Info->hListView,

View file

@ -71,13 +71,14 @@ VOID CompleteProgressBar(HWND hProgDlg);
/* query.c */ /* query.c */
ENUM_SERVICE_STATUS_PROCESS* GetSelectedService(PMAIN_WND_INFO Info); ENUM_SERVICE_STATUS_PROCESS* GetSelectedService(PMAIN_WND_INFO Info);
LPTSTR GetExecutablePath(PMAIN_WND_INFO Info); LPQUERY_SERVICE_CONFIG GetServiceConfig(LPTSTR lpServiceName);
LPTSTR GetServiceDescription(LPTSTR lpServiceName);
LPTSTR GetExecutablePath(LPTSTR lpServiceName);
BOOL RefreshServiceList(PMAIN_WND_INFO Info); BOOL RefreshServiceList(PMAIN_WND_INFO Info);
BOOL UpdateServiceStatus(ENUM_SERVICE_STATUS_PROCESS* pService); BOOL UpdateServiceStatus(ENUM_SERVICE_STATUS_PROCESS* pService);
/* reg */ /* reg */
BOOL SetDescription(LPTSTR, LPTSTR); BOOL SetDescription(LPTSTR, LPTSTR);
LPTSTR GetDescription(LPTSTR);
/* propsheet.c */ /* propsheet.c */
LONG APIENTRY OpenPropSheet(PMAIN_WND_INFO Info); LONG APIENTRY OpenPropSheet(PMAIN_WND_INFO Info);

View file

@ -9,15 +9,22 @@
#include "precomp.h" #include "precomp.h"
typedef struct _SERVICEPROPSHEET
{
PMAIN_WND_INFO Info;
ENUM_SERVICE_STATUS_PROCESS *pService;
} SERVICEPROPSHEET, *PSERVICEPROPSHEET;
static VOID static VOID
SetButtonStates(PMAIN_WND_INFO Info, SetButtonStates(PSERVICEPROPSHEET dlgInfo,
HWND hwndDlg) HWND hwndDlg)
{ {
HWND hButton; HWND hButton;
DWORD Flags, State; DWORD Flags, State;
Flags = Info->pCurrentService->ServiceStatusProcess.dwControlsAccepted; Flags = dlgInfo->pService->ServiceStatusProcess.dwControlsAccepted;
State = Info->pCurrentService->ServiceStatusProcess.dwCurrentState; State = dlgInfo->pService->ServiceStatusProcess.dwCurrentState;
if (State == SERVICE_STOPPED) if (State == SERVICE_STOPPED)
{ {
@ -49,56 +56,53 @@ SetButtonStates(PMAIN_WND_INFO Info,
* values and sets it to value of the selected item * values and sets it to value of the selected item
*/ */
static VOID static VOID
SetStartupType(PMAIN_WND_INFO Info, SetStartupType(LPTSTR lpServiceName,
HWND hwndDlg) HWND hwndDlg)
{ {
HWND hList; HWND hList;
HKEY hKey; LPQUERY_SERVICE_CONFIG pServiceConfig;
TCHAR buf[25]; LPTSTR lpBuf;
DWORD dwValueSize = 0;
DWORD StartUp = 0; DWORD StartUp = 0;
LPCTSTR Path = _T("System\\CurrentControlSet\\Services\\%s"); UINT i;
TCHAR KeyBuf[300];
/* open the registry key for the service */
_sntprintf(KeyBuf,
sizeof(KeyBuf) / sizeof(TCHAR),
Path,
Info->pCurrentService->lpServiceName);
RegOpenKeyEx(HKEY_LOCAL_MACHINE,
KeyBuf,
0,
KEY_READ,
&hKey);
hList = GetDlgItem(hwndDlg, IDC_START_TYPE); hList = GetDlgItem(hwndDlg, IDC_START_TYPE);
LoadString(hInstance, IDS_SERVICES_AUTO, buf, sizeof(buf) / sizeof(TCHAR)); for (i = IDS_SERVICES_AUTO; i <= IDS_SERVICES_DIS; i++)
SendMessage(hList, CB_ADDSTRING, 0, (LPARAM)buf);
LoadString(hInstance, IDS_SERVICES_MAN, buf, sizeof(buf) / sizeof(TCHAR));
SendMessage(hList, CB_ADDSTRING, 0, (LPARAM)buf);
LoadString(hInstance, IDS_SERVICES_DIS, buf, sizeof(buf) / sizeof(TCHAR));
SendMessage(hList, CB_ADDSTRING, 0, (LPARAM)buf);
dwValueSize = sizeof(DWORD);
if (RegQueryValueEx(hKey,
_T("Start"),
NULL,
NULL,
(LPBYTE)&StartUp,
&dwValueSize))
{ {
RegCloseKey(hKey); if (AllocAndLoadString(&lpBuf,
return; hInstance,
i))
{
SendMessage(hList,
CB_ADDSTRING,
0,
(LPARAM)lpBuf);
HeapFree(ProcessHeap,
0,
lpBuf);
}
} }
if (StartUp == 0x02) pServiceConfig = GetServiceConfig(lpServiceName);
SendMessage(hList, CB_SETCURSEL, 0, 0);
else if (StartUp == 0x03) if (pServiceConfig)
SendMessage(hList, CB_SETCURSEL, 1, 0); {
else if (StartUp == 0x04) switch (pServiceConfig->dwStartType)
SendMessage(hList, CB_SETCURSEL, 2, 0); {
case SERVICE_AUTO_START: StartUp = 0; break;
case SERVICE_DEMAND_START: StartUp = 1; break;
case SERVICE_DISABLED: StartUp = 2; break;
}
SendMessage(hList,
CB_SETCURSEL,
StartUp,
0);
HeapFree(ProcessHeap,
0,
pServiceConfig);
}
} }
@ -107,28 +111,28 @@ SetStartupType(PMAIN_WND_INFO Info,
* the relevant service information * the relevant service information
*/ */
static VOID static VOID
GetDlgInfo(PMAIN_WND_INFO Info, GetDlgInfo(PSERVICEPROPSHEET dlgInfo,
HWND hwndDlg) HWND hwndDlg)
{ {
LPQUERY_SERVICE_CONFIG pServiceConfig;
LPTSTR lpDescription; LPTSTR lpDescription;
LPTSTR lpPathToExe;
/* set the service name */ /* set the service name */
SendDlgItemMessage(hwndDlg, SendDlgItemMessage(hwndDlg,
IDC_SERV_NAME, IDC_SERV_NAME,
WM_SETTEXT, WM_SETTEXT,
0, 0,
(LPARAM)Info->pCurrentService->lpServiceName); (LPARAM)dlgInfo->pService->lpServiceName);
/* set the display name */ /* set the display name */
SendDlgItemMessage(hwndDlg, SendDlgItemMessage(hwndDlg,
IDC_DISP_NAME, IDC_DISP_NAME,
WM_SETTEXT, WM_SETTEXT,
0, 0,
(LPARAM)Info->pCurrentService->lpDisplayName); (LPARAM)dlgInfo->pService->lpDisplayName);
/* set the description */ /* set the description */
if ((lpDescription = GetDescription(Info->pCurrentService->lpServiceName))) if ((lpDescription = GetServiceDescription(dlgInfo->pService->lpServiceName)))
{ {
SendDlgItemMessage(hwndDlg, SendDlgItemMessage(hwndDlg,
IDC_DESCRIPTION, IDC_DESCRIPTION,
@ -139,29 +143,24 @@ GetDlgInfo(PMAIN_WND_INFO Info,
HeapFree(ProcessHeap, HeapFree(ProcessHeap,
0, 0,
lpDescription); lpDescription);
} }
/* set the executable path */ pServiceConfig = GetServiceConfig(dlgInfo->pService->lpServiceName);
if ((lpPathToExe = GetExecutablePath(Info))) if (pServiceConfig)
{ {
SendDlgItemMessage(hwndDlg, SendDlgItemMessage(hwndDlg,
IDC_EXEPATH, IDC_EXEPATH,
WM_SETTEXT, WM_SETTEXT,
0, 0,
(LPARAM)lpPathToExe); (LPARAM)pServiceConfig->lpBinaryPathName);
HeapFree(ProcessHeap,
0,
lpPathToExe);
} }
/* set startup type */ /* set startup type */
SetStartupType(Info, hwndDlg); SetStartupType(dlgInfo->pService->lpServiceName, hwndDlg);
/* set service status */ /* set service status */
if (Info->pCurrentService->ServiceStatusProcess.dwCurrentState == SERVICE_RUNNING) if (dlgInfo->pService->ServiceStatusProcess.dwCurrentState == SERVICE_RUNNING)
{ {
TCHAR szServiceStatus[32]; TCHAR szServiceStatus[32];
@ -194,7 +193,6 @@ GetDlgInfo(PMAIN_WND_INFO Info,
} }
/* /*
* General Property dialog callback. * General Property dialog callback.
* Controls messages to the General dialog * Controls messages to the General dialog
@ -205,13 +203,12 @@ GeneralPageProc(HWND hwndDlg,
WPARAM wParam, WPARAM wParam,
LPARAM lParam) LPARAM lParam)
{ {
PMAIN_WND_INFO Info; PSERVICEPROPSHEET dlgInfo;
/* Get the window context */ /* Get the window context */
Info = (PMAIN_WND_INFO)GetWindowLongPtr(hwndDlg, dlgInfo = (PSERVICEPROPSHEET)GetWindowLongPtr(hwndDlg,
GWLP_USERDATA); GWLP_USERDATA);
if (dlgInfo == NULL && uMsg != WM_INITDIALOG)
if (Info == NULL && uMsg != WM_INITDIALOG)
{ {
return FALSE; return FALSE;
} }
@ -220,14 +217,14 @@ GeneralPageProc(HWND hwndDlg,
{ {
case WM_INITDIALOG: case WM_INITDIALOG:
{ {
Info = (PMAIN_WND_INFO)(((LPPROPSHEETPAGE)lParam)->lParam); dlgInfo = (PSERVICEPROPSHEET)(((LPPROPSHEETPAGE)lParam)->lParam);
if (Info != NULL) if (dlgInfo != NULL)
{ {
SetWindowLongPtr(hwndDlg, SetWindowLongPtr(hwndDlg,
GWLP_USERDATA, GWLP_USERDATA,
(LONG_PTR)Info); (LONG_PTR)dlgInfo);
GetDlgInfo(Info, hwndDlg); GetDlgInfo(dlgInfo, hwndDlg);
SetButtonStates(Info, hwndDlg); SetButtonStates(dlgInfo, hwndDlg);
} }
} }
break; break;
@ -236,31 +233,34 @@ GeneralPageProc(HWND hwndDlg,
switch(LOWORD(wParam)) switch(LOWORD(wParam))
{ {
case IDC_START_TYPE: case IDC_START_TYPE:
/* Enable the 'Apply' button */ if (HIWORD(wParam) == CBN_SELCHANGE)
//PropSheet_Changed(GetParent(hwndDlg), hwndDlg); PropSheet_Changed(GetParent(hwndDlg), hwndDlg);
break; break;
case IDC_START: case IDC_START:
SendMessage(Info->hMainWnd, WM_COMMAND, ID_START, 0); if (DoStart(dlgInfo->Info))
{
//UpdateServiceStatus(dlgInfo->pService);
//ChangeListViewText(dlgInfo, LVSTATUS);
//SetMenuAndButtonStates(Info);
}
break; break;
case IDC_STOP: case IDC_STOP:
SendMessage(Info->hMainWnd, WM_COMMAND, ID_STOP, 0); //SendMessage(Info->hMainWnd, WM_COMMAND, ID_STOP, 0);
break; break;
case IDC_PAUSE: case IDC_PAUSE:
SendMessage(Info->hMainWnd, WM_COMMAND, ID_PAUSE, 0); //SendMessage(Info->hMainWnd, WM_COMMAND, ID_PAUSE, 0);
break; break;
case IDC_RESUME: case IDC_RESUME:
SendMessage(Info->hMainWnd, WM_COMMAND, ID_RESUME, 0); //SendMessage(Info->hMainWnd, WM_COMMAND, ID_RESUME, 0);
break; break;
case IDC_START_PARAM: case IDC_START_PARAM:
/* Enable the 'Apply' button */ PropSheet_Changed(GetParent(hwndDlg), hwndDlg);
//PropSheet_Changed(GetParent(hwndDlg), hwndDlg);
break; break;
} }
break; break;
@ -273,9 +273,8 @@ GeneralPageProc(HWND hwndDlg,
switch (lpnm->code) switch (lpnm->code)
{ {
case MCN_SELECT: case PSN_APPLY:
/* Enable the 'Apply' button */ MessageBox(NULL, _T("apply"), NULL, 0);
PropSheet_Changed(GetParent(hwndDlg), hwndDlg);
break; break;
} }
} }
@ -381,7 +380,7 @@ AddEditButton(HWND hwnd, UINT message, LPARAM lParam)
static VOID static VOID
InitPropSheetPage(PROPSHEETPAGE *psp, InitPropSheetPage(PROPSHEETPAGE *psp,
PMAIN_WND_INFO Info, PSERVICEPROPSHEET dlgInfo,
WORD idDlg, WORD idDlg,
DLGPROC DlgProc) DLGPROC DlgProc)
{ {
@ -391,7 +390,7 @@ InitPropSheetPage(PROPSHEETPAGE *psp,
psp->hInstance = hInstance; psp->hInstance = hInstance;
psp->pszTemplate = MAKEINTRESOURCE(idDlg); psp->pszTemplate = MAKEINTRESOURCE(idDlg);
psp->pfnDlgProc = DlgProc; psp->pfnDlgProc = DlgProc;
psp->lParam = (LPARAM)Info; psp->lParam = (LPARAM)dlgInfo;
} }
@ -400,6 +399,8 @@ OpenPropSheet(PMAIN_WND_INFO Info)
{ {
PROPSHEETHEADER psh; PROPSHEETHEADER psh;
PROPSHEETPAGE psp[2]; PROPSHEETPAGE psp[2];
PSERVICEPROPSHEET pServicePropSheet;
LONG Ret = 0;
ZeroMemory(&psh, sizeof(PROPSHEETHEADER)); ZeroMemory(&psh, sizeof(PROPSHEETHEADER));
psh.dwSize = sizeof(PROPSHEETHEADER); psh.dwSize = sizeof(PROPSHEETHEADER);
@ -414,11 +415,27 @@ OpenPropSheet(PMAIN_WND_INFO Info)
psh.ppsp = psp; psh.ppsp = psp;
InitPropSheetPage(&psp[0], Info, IDD_DLG_GENERAL, GeneralPageProc); pServicePropSheet = HeapAlloc(ProcessHeap,
//InitPropSheetPage(&psp[1], Info, IDD_DLG_GENERAL, LogonPageProc); 0,
//InitPropSheetPage(&psp[2], Info, IDD_DLG_GENERAL, RecoveryPageProc); sizeof(*pServicePropSheet));
InitPropSheetPage(&psp[1], Info, IDD_DLG_DEPEND, DependanciesPageProc); if (pServicePropSheet)
{
/* save current service, as it could change while the dialog is open */
pServicePropSheet->pService = Info->pCurrentService;
pServicePropSheet->Info = Info;
return (LONG)(PropertySheet(&psh) != -1); InitPropSheetPage(&psp[0], pServicePropSheet, IDD_DLG_GENERAL, GeneralPageProc);
//InitPropSheetPage(&psp[1], Info, IDD_DLG_GENERAL, LogonPageProc);
//InitPropSheetPage(&psp[2], Info, IDD_DLG_GENERAL, RecoveryPageProc);
InitPropSheetPage(&psp[1], pServicePropSheet, IDD_DLG_DEPEND, DependanciesPageProc);
Ret = (LONG)(PropertySheet(&psh) != -1);
HeapFree(ProcessHeap,
0,
pServicePropSheet);
}
return Ret;
} }

View file

@ -27,29 +27,25 @@ GetSelectedService(PMAIN_WND_INFO Info)
} }
/* get vendor of service binary */ LPQUERY_SERVICE_CONFIG
LPTSTR GetServiceConfig(LPTSTR lpServiceName)
GetExecutablePath(PMAIN_WND_INFO Info)
{ {
SC_HANDLE hSCManager = NULL; SC_HANDLE hSCManager = NULL;
SC_HANDLE hSc = NULL; SC_HANDLE hSc = NULL;
LPQUERY_SERVICE_CONFIG pServiceConfig = NULL; LPQUERY_SERVICE_CONFIG pServiceConfig = NULL;
DWORD BytesNeeded = 0; DWORD BytesNeeded = 0;
LPTSTR lpExePath = NULL;
/* open handle to the SCM */
hSCManager = OpenSCManager(NULL, hSCManager = OpenSCManager(NULL,
NULL, NULL,
SC_MANAGER_ENUMERATE_SERVICE); SC_MANAGER_ENUMERATE_SERVICE);
if (hSCManager == NULL) if (hSCManager == NULL)
{ {
GetError(); GetError();
return FALSE; return NULL;
} }
/* get a handle to the service requested for starting */
hSc = OpenService(hSCManager, hSc = OpenService(hSCManager,
Info->pCurrentService->lpServiceName, lpServiceName,
SERVICE_QUERY_CONFIG); SERVICE_QUERY_CONFIG);
if (hSc == NULL) if (hSc == NULL)
{ {
@ -70,34 +66,103 @@ GetExecutablePath(PMAIN_WND_INFO Info)
if (pServiceConfig == NULL) if (pServiceConfig == NULL)
goto cleanup; goto cleanup;
if (QueryServiceConfig(hSc, if (!QueryServiceConfig(hSc,
pServiceConfig, pServiceConfig,
BytesNeeded, BytesNeeded,
&BytesNeeded)) &BytesNeeded))
{ {
lpExePath = HeapAlloc(ProcessHeap, HeapFree(ProcessHeap,
0, 0,
(_tcslen(pServiceConfig->lpBinaryPathName) +1 ) * sizeof(TCHAR)); pServiceConfig);
_tcscpy(lpExePath, pServiceConfig->lpBinaryPathName); pServiceConfig = NULL;
} }
} }
} }
cleanup: cleanup:
if (pServiceConfig)
HeapFree(ProcessHeap,
0,
pServiceConfig);
if (hSCManager != NULL) if (hSCManager != NULL)
CloseServiceHandle(hSCManager); CloseServiceHandle(hSCManager);
if (hSc != NULL) if (hSc != NULL)
CloseServiceHandle(hSc); CloseServiceHandle(hSc);
return lpExePath; return pServiceConfig;
} }
LPTSTR
GetServiceDescription(LPTSTR lpServiceName)
{
SC_HANDLE hSCManager = NULL;
SC_HANDLE hSc = NULL;
SERVICE_DESCRIPTION *pServiceDescription = NULL;
LPTSTR lpDescription = NULL;
DWORD BytesNeeded = 0;
hSCManager = OpenSCManager(NULL,
NULL,
SC_MANAGER_ENUMERATE_SERVICE);
if (hSCManager == NULL)
{
GetError();
return NULL;
}
hSc = OpenService(hSCManager,
lpServiceName,
SERVICE_QUERY_CONFIG);
if (hSc)
{
if (!QueryServiceConfig2(hSc,
SERVICE_CONFIG_DESCRIPTION,
NULL,
0,
&BytesNeeded))
{
if (GetLastError() == ERROR_INSUFFICIENT_BUFFER)
{
pServiceDescription = (SERVICE_DESCRIPTION *) HeapAlloc(ProcessHeap,
0,
BytesNeeded);
if (pServiceDescription == NULL)
goto cleanup;
if (QueryServiceConfig2(hSc,
SERVICE_CONFIG_DESCRIPTION,
(LPBYTE)pServiceDescription,
BytesNeeded,
&BytesNeeded))
{
if (pServiceDescription->lpDescription)
{
lpDescription = HeapAlloc(ProcessHeap,
0,
(_tcslen(pServiceDescription->lpDescription) + 1) * sizeof(TCHAR));
if (lpDescription)
_tcscpy(lpDescription,
pServiceDescription->lpDescription);
}
}
}
}
}
cleanup:
if (pServiceDescription)
HeapFree(ProcessHeap,
0,
pServiceDescription);
if (hSCManager != NULL)
CloseServiceHandle(hSCManager);
if (hSc != NULL)
CloseServiceHandle(hSc);
return lpDescription;
}
static BOOL static BOOL
GetServiceList(PMAIN_WND_INFO Info, GetServiceList(PMAIN_WND_INFO Info,
DWORD *NumServices) DWORD *NumServices)
@ -206,6 +271,7 @@ BOOL
RefreshServiceList(PMAIN_WND_INFO Info) RefreshServiceList(PMAIN_WND_INFO Info)
{ {
ENUM_SERVICE_STATUS_PROCESS *pService; ENUM_SERVICE_STATUS_PROCESS *pService;
LPTSTR lpDescription;
LVITEM lvItem; LVITEM lvItem;
TCHAR szNumServices[32]; TCHAR szNumServices[32];
TCHAR szStatus[64]; TCHAR szStatus[64];
@ -223,7 +289,6 @@ RefreshServiceList(PMAIN_WND_INFO Info)
for (Index = 0; Index < NumServices; Index++) for (Index = 0; Index < NumServices; Index++)
{ {
HKEY hKey = NULL; HKEY hKey = NULL;
LPTSTR lpDescription = NULL;
LPTSTR lpLogOnAs = NULL; LPTSTR lpLogOnAs = NULL;
DWORD StartUp = 0; DWORD StartUp = 0;
DWORD dwValueSize; DWORD dwValueSize;
@ -260,7 +325,7 @@ RefreshServiceList(PMAIN_WND_INFO Info)
lvItem.iItem = ListView_InsertItem(Info->hListView, &lvItem); lvItem.iItem = ListView_InsertItem(Info->hListView, &lvItem);
/* set the description */ /* set the description */
if ((lpDescription = GetDescription(pService->lpServiceName))) if ((lpDescription = GetServiceDescription(pService->lpServiceName)))
{ {
lvItem.pszText = lpDescription; lvItem.pszText = lpDescription;
lvItem.iSubItem = 1; lvItem.iSubItem = 1;

View file

@ -57,46 +57,3 @@ SetDescription(LPTSTR lpServiceName,
return bRet; return bRet;
} }
LPTSTR
GetDescription(LPTSTR lpServiceName)
{
HKEY hKey;
LPTSTR lpDescription = NULL;
DWORD dwValueSize = 0;
hKey = OpenServiceKey(lpServiceName);
if (hKey)
{
if (RegQueryValueEx(hKey,
_T("Description"),
NULL,
NULL,
NULL,
&dwValueSize) == ERROR_SUCCESS)
{
lpDescription = HeapAlloc(ProcessHeap,
0,
dwValueSize);
if (lpDescription)
{
if(RegQueryValueEx(hKey,
_T("Description"),
NULL,
NULL,
(LPBYTE)lpDescription,
&dwValueSize) != ERROR_SUCCESS)
{
HeapFree(ProcessHeap,
0,
lpDescription);
}
}
}
RegCloseKey(hKey);
}
return lpDescription;
}