mirror of
https://github.com/reactos/reactos.git
synced 2024-06-28 17:01:28 +00:00
[regedit]
- Implement RegFindRecurse, RegFindWalk and helpers to find registry keys. Remove RegNextKey as its no longer used. Other misc fixes. Fixes searching in regedit. Patch by Katayama_Hirofumi. svn path=/trunk/; revision=47233
This commit is contained in:
parent
fa5c83b451
commit
5ab3830ab5
|
@ -25,13 +25,531 @@ static const TCHAR s_szFindFlagsR[] = _T("FindFlagsReactOS");
|
|||
static HWND s_hwndAbortDialog;
|
||||
static BOOL s_bAbort;
|
||||
|
||||
static DWORD s_dwFlags;
|
||||
static TCHAR s_szName[MAX_PATH];
|
||||
static DWORD s_cbName;
|
||||
static const TCHAR s_empty[] = {0};
|
||||
static const TCHAR s_backslash[] = {'\\', 0};
|
||||
|
||||
extern VOID SetValueName(HWND hwndLV, LPCTSTR pszValueName);
|
||||
|
||||
BOOL DoEvents(VOID)
|
||||
{
|
||||
MSG msg;
|
||||
if (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
|
||||
{
|
||||
if (msg.message == WM_QUIT)
|
||||
s_bAbort = TRUE;
|
||||
if (!IsDialogMessage(s_hwndAbortDialog, &msg))
|
||||
{
|
||||
TranslateMessage(&msg);
|
||||
DispatchMessage(&msg);
|
||||
}
|
||||
}
|
||||
return s_bAbort;
|
||||
}
|
||||
|
||||
static LPTSTR lstrstri(LPCTSTR psz1, LPCTSTR psz2)
|
||||
{
|
||||
INT i, cch1, cch2;
|
||||
|
||||
cch1 = lstrlen(psz1);
|
||||
cch2 = lstrlen(psz2);
|
||||
for(i = 0; i <= cch1 - cch2; i++)
|
||||
{
|
||||
if (CompareString(LOCALE_SYSTEM_DEFAULT, NORM_IGNORECASE,
|
||||
psz1 + i, cch2, psz2, cch2) == 2)
|
||||
return (LPTSTR) (psz1 + i);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static BOOL CompareName(LPCTSTR pszName1, LPCTSTR pszName2)
|
||||
{
|
||||
if (s_dwFlags & RSF_WHOLESTRING)
|
||||
{
|
||||
if (s_dwFlags & RSF_MATCHCASE)
|
||||
return lstrcmp(pszName1, pszName2) == 0;
|
||||
else
|
||||
return lstrcmpi(pszName1, pszName2) == 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (s_dwFlags & RSF_MATCHCASE)
|
||||
return _tcsstr(pszName1, pszName2) != NULL;
|
||||
else
|
||||
return lstrstri(pszName1, pszName2) != NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static BOOL
|
||||
CompareData(
|
||||
DWORD dwType,
|
||||
LPCTSTR psz1,
|
||||
LPCTSTR psz2)
|
||||
{
|
||||
INT i, cch1 = lstrlen(psz1), cch2 = lstrlen(psz2);
|
||||
if (dwType == REG_SZ || dwType == REG_EXPAND_SZ)
|
||||
{
|
||||
if (s_dwFlags & RSF_WHOLESTRING)
|
||||
{
|
||||
if (s_dwFlags & RSF_MATCHCASE)
|
||||
return 2 == CompareString(LOCALE_SYSTEM_DEFAULT, 0,
|
||||
psz1, cch1, psz2, cch2);
|
||||
else
|
||||
return 2 == CompareString(LOCALE_SYSTEM_DEFAULT,
|
||||
NORM_IGNORECASE, psz1, cch1, psz2, cch2);
|
||||
}
|
||||
|
||||
for(i = 0; i <= cch1 - cch2; i++)
|
||||
{
|
||||
if (s_dwFlags & RSF_MATCHCASE)
|
||||
{
|
||||
if (2 == CompareString(LOCALE_SYSTEM_DEFAULT, 0,
|
||||
psz1 + i, cch2, psz2, cch2))
|
||||
return TRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (2 == CompareString(LOCALE_SYSTEM_DEFAULT,
|
||||
NORM_IGNORECASE, psz1 + i, cch2, psz2, cch2))
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
int compare(const void *x, const void *y)
|
||||
{
|
||||
const LPCTSTR *a = (const LPCTSTR *)x;
|
||||
const LPCTSTR *b = (const LPCTSTR *)y;
|
||||
return lstrcmpi(*a, *b);
|
||||
}
|
||||
|
||||
BOOL RegFindRecurse(
|
||||
HKEY hKey,
|
||||
LPCTSTR pszSubKey,
|
||||
LPCTSTR pszValueName,
|
||||
LPTSTR *ppszFoundSubKey,
|
||||
LPTSTR *ppszFoundValueName)
|
||||
{
|
||||
HKEY hSubKey;
|
||||
LONG lResult;
|
||||
TCHAR szSubKey[MAX_PATH];
|
||||
DWORD i, c, cb, type;
|
||||
BOOL fPast = FALSE;
|
||||
LPTSTR *ppszNames = NULL;
|
||||
LPBYTE pb = NULL;
|
||||
|
||||
if (DoEvents())
|
||||
return FALSE;
|
||||
|
||||
lstrcpy(szSubKey, pszSubKey);
|
||||
hSubKey = NULL;
|
||||
|
||||
lResult = RegOpenKeyEx(hKey, szSubKey, 0, KEY_ALL_ACCESS, &hSubKey);
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
return FALSE;
|
||||
|
||||
if (pszValueName == NULL)
|
||||
pszValueName = s_empty;
|
||||
|
||||
lResult = RegQueryInfoKey(hSubKey, NULL, NULL, NULL, NULL, NULL, NULL,
|
||||
&c, NULL, NULL, NULL, NULL);
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
goto err;
|
||||
ppszNames = (LPTSTR *) malloc(c * sizeof(LPTSTR));
|
||||
if (ppszNames == NULL)
|
||||
goto err;
|
||||
ZeroMemory(ppszNames, c * sizeof(LPTSTR));
|
||||
|
||||
for(i = 0; i < c; i++)
|
||||
{
|
||||
if (DoEvents())
|
||||
goto err;
|
||||
|
||||
s_cbName = MAX_PATH * sizeof(TCHAR);
|
||||
lResult = RegEnumValue(hSubKey, i, s_szName, &s_cbName, NULL, NULL,
|
||||
NULL, &cb);
|
||||
if (lResult == ERROR_NO_MORE_ITEMS)
|
||||
{
|
||||
c = i;
|
||||
break;
|
||||
}
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
goto err;
|
||||
if (s_cbName >= MAX_PATH * sizeof(TCHAR))
|
||||
continue;
|
||||
|
||||
ppszNames[i] = _tcsdup(s_szName);
|
||||
}
|
||||
|
||||
qsort(ppszNames, c, sizeof(LPTSTR), compare);
|
||||
|
||||
for(i = 0; i < c; i++)
|
||||
{
|
||||
if (DoEvents())
|
||||
goto err;
|
||||
|
||||
if (!fPast && lstrcmpi(ppszNames[i], pszValueName) == 0)
|
||||
{
|
||||
fPast = TRUE;
|
||||
continue;
|
||||
}
|
||||
if (!fPast)
|
||||
continue;
|
||||
|
||||
if ((s_dwFlags & RSF_LOOKATVALUES) &&
|
||||
CompareName(ppszNames[i], s_szFindWhat))
|
||||
{
|
||||
*ppszFoundSubKey = _tcsdup(szSubKey);
|
||||
if (ppszNames[i][0] == 0)
|
||||
*ppszFoundValueName = NULL;
|
||||
else
|
||||
*ppszFoundValueName = _tcsdup(ppszNames[i]);
|
||||
goto success;
|
||||
}
|
||||
|
||||
lResult = RegQueryValueEx(hSubKey, ppszNames[i], NULL, &type,
|
||||
NULL, &cb);
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
goto err;
|
||||
pb = malloc(cb);
|
||||
if (pb == NULL)
|
||||
goto err;
|
||||
lResult = RegQueryValueEx(hSubKey, ppszNames[i], NULL, &type,
|
||||
pb, &cb);
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
goto err;
|
||||
|
||||
if ((s_dwFlags & RSF_LOOKATDATA) &&
|
||||
CompareData(type, (LPTSTR) pb, s_szFindWhat))
|
||||
{
|
||||
*ppszFoundSubKey = _tcsdup(szSubKey);
|
||||
if (ppszNames[i][0] == 0)
|
||||
*ppszFoundValueName = NULL;
|
||||
else
|
||||
*ppszFoundValueName = _tcsdup(ppszNames[i]);
|
||||
goto success;
|
||||
}
|
||||
free(pb);
|
||||
pb = NULL;
|
||||
}
|
||||
|
||||
if (ppszNames != NULL)
|
||||
{
|
||||
for(i = 0; i < c; i++)
|
||||
free(ppszNames[i]);
|
||||
free(ppszNames);
|
||||
}
|
||||
ppszNames = NULL;
|
||||
|
||||
lResult = RegQueryInfoKey(hSubKey, NULL, NULL, NULL, &c, NULL, NULL,
|
||||
NULL, NULL, NULL, NULL, NULL);
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
goto err;
|
||||
ppszNames = (LPTSTR *) malloc(c * sizeof(LPTSTR));
|
||||
if (ppszNames == NULL)
|
||||
goto err;
|
||||
ZeroMemory(ppszNames, c * sizeof(LPTSTR));
|
||||
|
||||
for(i = 0; i < c; i++)
|
||||
{
|
||||
if (DoEvents())
|
||||
goto err;
|
||||
|
||||
s_cbName = MAX_PATH * sizeof(TCHAR);
|
||||
lResult = RegEnumKeyEx(hSubKey, i, s_szName, &s_cbName, NULL, NULL,
|
||||
NULL, NULL);
|
||||
if (lResult == ERROR_NO_MORE_ITEMS)
|
||||
{
|
||||
c = i;
|
||||
break;
|
||||
}
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
goto err;
|
||||
if (s_cbName >= MAX_PATH * sizeof(TCHAR))
|
||||
continue;
|
||||
|
||||
ppszNames[i] = _tcsdup(s_szName);
|
||||
}
|
||||
|
||||
qsort(ppszNames, c, sizeof(LPTSTR), compare);
|
||||
|
||||
for(i = 0; i < c; i++)
|
||||
{
|
||||
if (DoEvents())
|
||||
goto err;
|
||||
|
||||
if ((s_dwFlags & RSF_LOOKATKEYS) &&
|
||||
CompareName(ppszNames[i], s_szFindWhat))
|
||||
{
|
||||
*ppszFoundSubKey = malloc(
|
||||
(lstrlen(szSubKey) + lstrlen(ppszNames[i]) + 2) *
|
||||
sizeof(TCHAR));
|
||||
if (*ppszFoundSubKey == NULL)
|
||||
goto err;
|
||||
if (szSubKey[0])
|
||||
{
|
||||
lstrcpy(*ppszFoundSubKey, szSubKey);
|
||||
lstrcatW(*ppszFoundSubKey, s_backslash);
|
||||
}
|
||||
else
|
||||
**ppszFoundSubKey = 0;
|
||||
lstrcatW(*ppszFoundSubKey, ppszNames[i]);
|
||||
*ppszFoundValueName = NULL;
|
||||
goto success;
|
||||
}
|
||||
|
||||
if (RegFindRecurse(hSubKey, ppszNames[i], NULL, ppszFoundSubKey,
|
||||
ppszFoundValueName))
|
||||
{
|
||||
LPTSTR psz = *ppszFoundSubKey;
|
||||
*ppszFoundSubKey = malloc(
|
||||
(lstrlen(szSubKey) + lstrlen(psz) + 2) * sizeof(TCHAR));
|
||||
if (*ppszFoundSubKey == NULL)
|
||||
goto err;
|
||||
if (szSubKey[0])
|
||||
{
|
||||
lstrcpy(*ppszFoundSubKey, szSubKey);
|
||||
lstrcatW(*ppszFoundSubKey, s_backslash);
|
||||
}
|
||||
else
|
||||
**ppszFoundSubKey = 0;
|
||||
lstrcatW(*ppszFoundSubKey, psz);
|
||||
free(psz);
|
||||
goto success;
|
||||
}
|
||||
}
|
||||
|
||||
err:
|
||||
if (ppszNames != NULL)
|
||||
{
|
||||
for(i = 0; i < c; i++)
|
||||
free(ppszNames[i]);
|
||||
free(ppszNames);
|
||||
}
|
||||
free(pb);
|
||||
RegCloseKey(hSubKey);
|
||||
return FALSE;
|
||||
|
||||
success:
|
||||
if (ppszNames != NULL)
|
||||
{
|
||||
for(i = 0; i < c; i++)
|
||||
free(ppszNames[i]);
|
||||
free(ppszNames);
|
||||
}
|
||||
RegCloseKey(hSubKey);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL RegFindWalk(
|
||||
HKEY * phKey,
|
||||
LPCTSTR pszSubKey,
|
||||
LPCTSTR pszValueName,
|
||||
LPTSTR *ppszFoundSubKey,
|
||||
LPTSTR *ppszFoundValueName)
|
||||
{
|
||||
LONG lResult;
|
||||
DWORD i, c;
|
||||
HKEY hBaseKey, hSubKey;
|
||||
TCHAR szKeyName[MAX_PATH];
|
||||
TCHAR szSubKey[MAX_PATH];
|
||||
LPTSTR pch;
|
||||
BOOL fPast;
|
||||
LPTSTR *ppszNames = NULL;
|
||||
|
||||
hBaseKey = *phKey;
|
||||
if (RegFindRecurse(hBaseKey, pszSubKey, pszValueName, ppszFoundSubKey,
|
||||
ppszFoundValueName))
|
||||
return TRUE;
|
||||
|
||||
if (lstrlen(pszSubKey) >= MAX_PATH)
|
||||
return FALSE;
|
||||
|
||||
lstrcpy(szSubKey, pszSubKey);
|
||||
while(szSubKey[0] != 0)
|
||||
{
|
||||
if (DoEvents())
|
||||
return FALSE;
|
||||
|
||||
pch = _tcsrchr(szSubKey, _T('\\'));
|
||||
if (pch == NULL)
|
||||
{
|
||||
lstrcpy(szKeyName, szSubKey);
|
||||
szSubKey[0] = 0;
|
||||
hSubKey = hBaseKey;
|
||||
}
|
||||
else
|
||||
{
|
||||
lstrcpyn(szKeyName, pch + 1, MAX_PATH);
|
||||
*pch = 0;
|
||||
lResult = RegOpenKeyEx(hBaseKey, szSubKey, 0, KEY_ALL_ACCESS,
|
||||
&hSubKey);
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
lResult = RegQueryInfoKey(hSubKey, NULL, NULL, NULL, &c, NULL, NULL,
|
||||
NULL, NULL, NULL, NULL, NULL);
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
goto err;
|
||||
|
||||
ppszNames = (LPTSTR *) malloc(c * sizeof(LPTSTR));
|
||||
if (ppszNames == NULL)
|
||||
goto err;
|
||||
ZeroMemory(ppszNames, c * sizeof(LPTSTR));
|
||||
|
||||
for(i = 0; i < c; i++)
|
||||
{
|
||||
if (DoEvents())
|
||||
goto err;
|
||||
|
||||
s_cbName = MAX_PATH * sizeof(TCHAR);
|
||||
lResult = RegEnumKeyExW(hSubKey, i, s_szName, &s_cbName,
|
||||
NULL, NULL, NULL, NULL);
|
||||
if (lResult == ERROR_NO_MORE_ITEMS)
|
||||
{
|
||||
c = i;
|
||||
break;
|
||||
}
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
break;
|
||||
ppszNames[i] = _tcsdup(s_szName);
|
||||
}
|
||||
|
||||
qsort(ppszNames, c, sizeof(LPTSTR), compare);
|
||||
|
||||
fPast = FALSE;
|
||||
for(i = 0; i < c; i++)
|
||||
{
|
||||
if (DoEvents())
|
||||
goto err;
|
||||
|
||||
if (!fPast && lstrcmpi(ppszNames[i], szKeyName) == 0)
|
||||
{
|
||||
fPast = TRUE;
|
||||
continue;
|
||||
}
|
||||
if (!fPast)
|
||||
continue;
|
||||
|
||||
if ((s_dwFlags & RSF_LOOKATKEYS) &&
|
||||
CompareName(ppszNames[i], s_szFindWhat))
|
||||
{
|
||||
*ppszFoundSubKey = malloc(
|
||||
(lstrlen(szSubKey) + lstrlen(ppszNames[i]) + 2) *
|
||||
sizeof(TCHAR));
|
||||
if (*ppszFoundSubKey == NULL)
|
||||
goto err;
|
||||
if (szSubKey[0])
|
||||
{
|
||||
lstrcpy(*ppszFoundSubKey, szSubKey);
|
||||
lstrcatW(*ppszFoundSubKey, s_backslash);
|
||||
}
|
||||
else
|
||||
**ppszFoundSubKey = 0;
|
||||
lstrcatW(*ppszFoundSubKey, ppszNames[i]);
|
||||
*ppszFoundValueName = NULL;
|
||||
goto success;
|
||||
}
|
||||
|
||||
if (RegFindRecurse(hSubKey, ppszNames[i], NULL,
|
||||
ppszFoundSubKey, ppszFoundValueName))
|
||||
{
|
||||
LPTSTR psz = *ppszFoundSubKey;
|
||||
*ppszFoundSubKey = malloc(
|
||||
(lstrlen(szSubKey) + lstrlen(psz) + 2) *
|
||||
sizeof(TCHAR));
|
||||
if (*ppszFoundSubKey == NULL)
|
||||
goto err;
|
||||
if (szSubKey[0])
|
||||
{
|
||||
lstrcpy(*ppszFoundSubKey, szSubKey);
|
||||
lstrcatW(*ppszFoundSubKey, s_backslash);
|
||||
}
|
||||
else
|
||||
**ppszFoundSubKey = 0;
|
||||
lstrcatW(*ppszFoundSubKey, psz);
|
||||
free(psz);
|
||||
goto success;
|
||||
}
|
||||
}
|
||||
if (ppszNames != NULL)
|
||||
{
|
||||
for(i = 0; i < c; i++)
|
||||
free(ppszNames[i]);
|
||||
free(ppszNames);
|
||||
}
|
||||
ppszNames = NULL;
|
||||
|
||||
if (hBaseKey != hSubKey)
|
||||
RegCloseKey(hSubKey);
|
||||
}
|
||||
|
||||
if (*phKey == HKEY_CLASSES_ROOT)
|
||||
{
|
||||
*phKey = HKEY_CURRENT_USER;
|
||||
if (RegFindRecurse(*phKey, s_empty, NULL, ppszFoundSubKey,
|
||||
ppszFoundValueName))
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
if (*phKey == HKEY_CURRENT_USER)
|
||||
{
|
||||
*phKey = HKEY_LOCAL_MACHINE;
|
||||
if (RegFindRecurse(*phKey, s_empty, NULL, ppszFoundSubKey,
|
||||
ppszFoundValueName))
|
||||
goto success;
|
||||
}
|
||||
|
||||
if (*phKey == HKEY_LOCAL_MACHINE)
|
||||
{
|
||||
*phKey = HKEY_USERS;
|
||||
if (RegFindRecurse(*phKey, s_empty, NULL, ppszFoundSubKey,
|
||||
ppszFoundValueName))
|
||||
goto success;
|
||||
}
|
||||
|
||||
if (*phKey == HKEY_USERS)
|
||||
{
|
||||
*phKey = HKEY_CURRENT_CONFIG;
|
||||
if (RegFindRecurse(*phKey, s_empty, NULL, ppszFoundSubKey,
|
||||
ppszFoundValueName))
|
||||
goto success;
|
||||
}
|
||||
|
||||
err:
|
||||
if (ppszNames != NULL)
|
||||
{
|
||||
for(i = 0; i < c; i++)
|
||||
free(ppszNames[i]);
|
||||
free(ppszNames);
|
||||
}
|
||||
if (hBaseKey != hSubKey)
|
||||
RegCloseKey(hSubKey);
|
||||
return FALSE;
|
||||
|
||||
success:
|
||||
if (ppszNames != NULL)
|
||||
{
|
||||
for(i = 0; i < c; i++)
|
||||
free(ppszNames[i]);
|
||||
free(ppszNames);
|
||||
}
|
||||
if (hBaseKey != hSubKey)
|
||||
RegCloseKey(hSubKey);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
static DWORD GetFindFlags(void)
|
||||
{
|
||||
HKEY hKey;
|
||||
DWORD dwFlags = RSF_LOOKATKEYS;
|
||||
DWORD dwType, dwValue, cbData;
|
||||
DWORD dwFlags = RSF_LOOKATKEYS | RSF_LOOKATVALUES | RSF_LOOKATDATA;
|
||||
|
||||
if (RegOpenKey(HKEY_CURRENT_USER, g_szGeneralRegKey, &hKey) == ERROR_SUCCESS)
|
||||
{
|
||||
|
@ -102,45 +620,48 @@ static INT_PTR CALLBACK AbortFindDialogProc(HWND hDlg, UINT uMsg, WPARAM wParam,
|
|||
return 0;
|
||||
}
|
||||
|
||||
static BOOL RegSearchProc(LPVOID lpParam)
|
||||
{
|
||||
MSG msg;
|
||||
UNREFERENCED_PARAMETER(lpParam);
|
||||
|
||||
if (s_hwndAbortDialog && PeekMessage(&msg, s_hwndAbortDialog, 0, 0, PM_REMOVE))
|
||||
{
|
||||
TranslateMessage(&msg);
|
||||
DispatchMessage(&msg);
|
||||
}
|
||||
return s_bAbort;
|
||||
}
|
||||
|
||||
BOOL FindNext(HWND hWnd)
|
||||
{
|
||||
HKEY hKeyRoot;
|
||||
LPCTSTR pszFindWhat;
|
||||
LPCTSTR pszKeyPath;
|
||||
DWORD dwFlags;
|
||||
LONG lResult;
|
||||
TCHAR szSubKey[512];
|
||||
TCHAR szError[512];
|
||||
TCHAR szTitle[64];
|
||||
BOOL fSuccess;
|
||||
TCHAR szFullKey[512];
|
||||
LPCTSTR pszValueName;
|
||||
LPTSTR pszFoundSubKey, pszFoundValueName;
|
||||
|
||||
pszFindWhat = s_szFindWhat;
|
||||
dwFlags = GetFindFlags() & ~(RSF_LOOKATVALUES | RSF_LOOKATDATA);
|
||||
s_dwFlags = GetFindFlags();
|
||||
|
||||
pszKeyPath = GetItemPath(g_pChildWnd->hTreeWnd, 0, &hKeyRoot);
|
||||
lstrcpyn(szSubKey, pszKeyPath, sizeof(szSubKey) / sizeof(szSubKey[0]));
|
||||
if (pszKeyPath == NULL)
|
||||
{
|
||||
hKeyRoot = HKEY_CLASSES_ROOT;
|
||||
pszKeyPath = s_empty;
|
||||
}
|
||||
|
||||
/* Create abort find dialog */
|
||||
s_hwndAbortDialog = CreateDialog(GetModuleHandle(NULL), MAKEINTRESOURCE(IDD_FINDING), hWnd, AbortFindDialogProc);
|
||||
s_hwndAbortDialog = CreateDialog(GetModuleHandle(NULL),
|
||||
MAKEINTRESOURCE(IDD_FINDING), hWnd, AbortFindDialogProc);
|
||||
if (s_hwndAbortDialog)
|
||||
{
|
||||
ShowWindow(s_hwndAbortDialog, SW_SHOW);
|
||||
UpdateWindow(s_hwndAbortDialog);
|
||||
}
|
||||
s_bAbort = FALSE;
|
||||
|
||||
lResult = RegSearch(hKeyRoot, szSubKey, sizeof(szSubKey) / sizeof(szSubKey[0]),
|
||||
pszFindWhat, 0, dwFlags, RegSearchProc, NULL);
|
||||
pszValueName = GetValueName(g_pChildWnd->hListWnd, -1);
|
||||
|
||||
EnableWindow(hFrameWnd, FALSE);
|
||||
EnableWindow(g_pChildWnd->hTreeWnd, FALSE);
|
||||
EnableWindow(g_pChildWnd->hListWnd, FALSE);
|
||||
EnableWindow(g_pChildWnd->hAddressBarWnd, FALSE);
|
||||
|
||||
fSuccess = RegFindWalk(&hKeyRoot, pszKeyPath, pszValueName,
|
||||
&pszFoundSubKey, &pszFoundValueName);
|
||||
|
||||
EnableWindow(hFrameWnd, TRUE);
|
||||
EnableWindow(g_pChildWnd->hTreeWnd, TRUE);
|
||||
EnableWindow(g_pChildWnd->hListWnd, TRUE);
|
||||
EnableWindow(g_pChildWnd->hAddressBarWnd, TRUE);
|
||||
|
||||
if (s_hwndAbortDialog)
|
||||
{
|
||||
|
@ -148,25 +669,15 @@ BOOL FindNext(HWND hWnd)
|
|||
s_hwndAbortDialog = NULL;
|
||||
}
|
||||
|
||||
/* Did the user click "Cancel"? If so, exit without displaying an error message */
|
||||
if (lResult == ERROR_OPERATION_ABORTED)
|
||||
return FALSE;
|
||||
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
if (fSuccess)
|
||||
{
|
||||
LoadString(NULL, IDS_APP_TITLE, szTitle, sizeof(szTitle) / sizeof(szTitle[0]));
|
||||
|
||||
if ((lResult != ERROR_NO_MORE_ITEMS) || !LoadString(NULL, IDS_FINISHEDFIND, szError, sizeof(szError) / sizeof(szError[0])))
|
||||
{
|
||||
FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM, NULL, lResult, 0,
|
||||
szError, sizeof(szError) / sizeof(szError[0]), NULL);
|
||||
}
|
||||
MessageBox(hWnd, szError, szTitle, MB_OK);
|
||||
return FALSE;
|
||||
RegKeyGetName(szFullKey, COUNT_OF(szFullKey), hKeyRoot, pszFoundSubKey);
|
||||
SelectNode(g_pChildWnd->hTreeWnd, szFullKey);
|
||||
SetValueName(g_pChildWnd->hListWnd, pszFoundValueName);
|
||||
free(pszFoundSubKey);
|
||||
free(pszFoundValueName);
|
||||
SetFocus(g_pChildWnd->hListWnd);
|
||||
}
|
||||
|
||||
RegKeyGetName(szFullKey, sizeof(szFullKey) / sizeof(szFullKey[0]), hKeyRoot, szSubKey);
|
||||
SelectNode(g_pChildWnd->hTreeWnd, szFullKey);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
@ -183,26 +694,17 @@ static INT_PTR CALLBACK FindDialogProc(HWND hDlg, UINT uMsg, WPARAM wParam, LPAR
|
|||
case WM_INITDIALOG:
|
||||
dwFlags = GetFindFlags();
|
||||
|
||||
/* Looking at values is not yet implemented */
|
||||
hControl = GetDlgItem(hDlg, IDC_LOOKAT_KEYS);
|
||||
if (hControl)
|
||||
SendMessage(hControl, BM_SETCHECK, (dwFlags & RSF_LOOKATKEYS) ? TRUE : FALSE, 0);
|
||||
|
||||
/* Looking at values is not yet implemented */
|
||||
hControl = GetDlgItem(hDlg, IDC_LOOKAT_VALUES);
|
||||
if (hControl)
|
||||
{
|
||||
lStyle = GetWindowLongPtr(hControl, GWL_STYLE);
|
||||
SetWindowLongPtr(hControl, GWL_STYLE, lStyle | WS_DISABLED);
|
||||
}
|
||||
SendMessage(hControl, BM_SETCHECK, (dwFlags & RSF_LOOKATVALUES) ? TRUE : FALSE, 0);
|
||||
|
||||
/* Looking at data is not yet implemented */
|
||||
hControl = GetDlgItem(hDlg, IDC_LOOKAT_DATA);
|
||||
if (hControl)
|
||||
{
|
||||
lStyle = GetWindowLongPtr(hControl, GWL_STYLE);
|
||||
SetWindowLongPtr(hControl, GWL_STYLE, lStyle | WS_DISABLED);
|
||||
}
|
||||
SendMessage(hControl, BM_SETCHECK, (dwFlags & RSF_LOOKATDATA) ? TRUE : FALSE, 0);
|
||||
|
||||
/* Match whole string */
|
||||
hControl = GetDlgItem(hDlg, IDC_MATCHSTRING);
|
||||
|
|
|
@ -27,6 +27,7 @@
|
|||
|
||||
int Image_String = 0;
|
||||
int Image_Bin = 0;
|
||||
INT iListViewSelect = -1;
|
||||
|
||||
typedef struct tagLINE_INFO
|
||||
{
|
||||
|
@ -76,6 +77,29 @@ LPCTSTR GetValueName(HWND hwndLV, int iStartAt)
|
|||
return lineinfo->name;
|
||||
}
|
||||
|
||||
VOID SetValueName(HWND hwndLV, LPCTSTR pszValueName)
|
||||
{
|
||||
INT i, c;
|
||||
LV_FINDINFO fi;
|
||||
|
||||
c = ListView_GetItemCount(hwndLV);
|
||||
for(i = 0; i < c; i++)
|
||||
{
|
||||
ListView_SetItemState(hwndLV, i, 0, LVIS_FOCUSED | LVIS_SELECTED);
|
||||
}
|
||||
if (pszValueName == NULL)
|
||||
i = 0;
|
||||
else
|
||||
{
|
||||
fi.flags = LVFI_STRING;
|
||||
fi.psz = pszValueName;
|
||||
i = ListView_FindItem(hwndLV, -1, &fi);
|
||||
}
|
||||
ListView_SetItemState(hwndLV, i, LVIS_FOCUSED | LVIS_SELECTED,
|
||||
LVIS_FOCUSED | LVIS_SELECTED);
|
||||
iListViewSelect = i;
|
||||
}
|
||||
|
||||
BOOL IsDefaultValue(HWND hwndLV, int i)
|
||||
{
|
||||
PLINE_INFO lineinfo;
|
||||
|
@ -497,6 +521,7 @@ BOOL RefreshListView(HWND hwndLV, HKEY hKey, LPCTSTR keyPath)
|
|||
DWORD val_count;
|
||||
HKEY hNewKey;
|
||||
LONG errCode;
|
||||
INT i, c;
|
||||
BOOL AddedDefault = FALSE;
|
||||
|
||||
if (!hwndLV) return FALSE;
|
||||
|
@ -552,7 +577,15 @@ BOOL RefreshListView(HWND hwndLV, HKEY hKey, LPCTSTR keyPath)
|
|||
{
|
||||
AddEntryToList(hwndLV, _T(""), REG_SZ, NULL, 0, 0, FALSE);
|
||||
}
|
||||
(void)ListView_SortItems(hwndLV, CompareFunc, (WPARAM)hwndLV);
|
||||
ListView_SortItems(hwndLV, CompareFunc, (WPARAM)hwndLV);
|
||||
c = ListView_GetItemCount(hwndLV);
|
||||
for(i = 0; i < c; i++)
|
||||
{
|
||||
ListView_SetItemState(hwndLV, i, 0, LVIS_FOCUSED | LVIS_SELECTED);
|
||||
}
|
||||
ListView_SetItemState(hwndLV, iListViewSelect,
|
||||
LVIS_FOCUSED | LVIS_SELECTED,
|
||||
LVIS_FOCUSED | LVIS_SELECTED);
|
||||
RegCloseKey(hNewKey);
|
||||
SendMessage(hwndLV, WM_SETREDRAW, TRUE, 0);
|
||||
|
||||
|
|
|
@ -1497,147 +1497,6 @@ done:
|
|||
return lResult;
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
* Searching
|
||||
*/
|
||||
|
||||
static LONG RegNextKey(HKEY hKey, LPTSTR lpSubKey, size_t iSubKeyLength)
|
||||
{
|
||||
LONG lResult;
|
||||
LPTSTR s;
|
||||
LPCTSTR pszOriginalKey;
|
||||
TCHAR szKeyName[256];
|
||||
HKEY hSubKey, hBaseKey;
|
||||
DWORD dwIndex = 0;
|
||||
DWORD cbName;
|
||||
FILETIME ft;
|
||||
BOOL bFoundKey = FALSE;
|
||||
|
||||
/* Try accessing a subkey */
|
||||
if (RegOpenKeyEx(hKey, lpSubKey, 0, KEY_ALL_ACCESS, &hSubKey) == ERROR_SUCCESS)
|
||||
{
|
||||
cbName = (DWORD) iSubKeyLength - _tcslen(lpSubKey) - 1;
|
||||
lResult = RegEnumKeyEx(hSubKey, 0, lpSubKey + _tcslen(lpSubKey) + 1,
|
||||
&cbName, NULL, NULL, NULL, &ft);
|
||||
RegCloseKey(hSubKey);
|
||||
|
||||
if (lResult == ERROR_SUCCESS)
|
||||
{
|
||||
lpSubKey[_tcslen(lpSubKey)] = '\\';
|
||||
bFoundKey = TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
if (!bFoundKey)
|
||||
{
|
||||
/* Go up and find the next sibling key */
|
||||
do
|
||||
{
|
||||
s = _tcsrchr(lpSubKey, TEXT('\\'));
|
||||
if (s)
|
||||
{
|
||||
*s = '\0';
|
||||
pszOriginalKey = s + 1;
|
||||
|
||||
hBaseKey = NULL;
|
||||
RegOpenKeyEx(hKey, lpSubKey, 0, KEY_ALL_ACCESS, &hBaseKey);
|
||||
}
|
||||
else
|
||||
{
|
||||
pszOriginalKey = lpSubKey;
|
||||
hBaseKey = hKey;
|
||||
}
|
||||
|
||||
if (hBaseKey)
|
||||
{
|
||||
dwIndex = 0;
|
||||
do
|
||||
{
|
||||
lResult = RegEnumKey(hBaseKey, dwIndex++, szKeyName, sizeof(szKeyName) / sizeof(szKeyName[0]));
|
||||
}
|
||||
while((lResult == ERROR_SUCCESS) && _tcscmp(szKeyName, pszOriginalKey));
|
||||
|
||||
if (lResult == ERROR_SUCCESS)
|
||||
{
|
||||
lResult = RegEnumKey(hBaseKey, dwIndex++, szKeyName, sizeof(szKeyName) / sizeof(szKeyName[0]));
|
||||
if (lResult == ERROR_SUCCESS)
|
||||
{
|
||||
bFoundKey = TRUE;
|
||||
_sntprintf(lpSubKey + _tcslen(lpSubKey), iSubKeyLength - _tcslen(lpSubKey), _T("\\%s"), szKeyName);
|
||||
}
|
||||
}
|
||||
RegCloseKey(hBaseKey);
|
||||
}
|
||||
}
|
||||
while(!bFoundKey);
|
||||
}
|
||||
return bFoundKey ? ERROR_SUCCESS : ERROR_NO_MORE_ITEMS;
|
||||
}
|
||||
|
||||
static BOOL RegSearchCompare(LPCTSTR s1, LPCTSTR s2, DWORD dwSearchFlags)
|
||||
{
|
||||
BOOL bResult;
|
||||
if (dwSearchFlags & RSF_WHOLESTRING)
|
||||
{
|
||||
if (dwSearchFlags & RSF_MATCHCASE)
|
||||
bResult = !_tcscmp(s1, s2);
|
||||
else
|
||||
bResult = !_tcsicmp(s1, s2);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (dwSearchFlags & RSF_MATCHCASE)
|
||||
bResult = (_tcsstr(s1, s2) != NULL);
|
||||
else
|
||||
{
|
||||
/* My kingdom for _tcsistr() */
|
||||
bResult = FALSE;
|
||||
while(*s1)
|
||||
{
|
||||
if (!_tcsnicmp(s1, s2, _tcslen(s2)))
|
||||
{
|
||||
bResult = TRUE;
|
||||
break;
|
||||
}
|
||||
s1++;
|
||||
}
|
||||
}
|
||||
}
|
||||
return bResult;
|
||||
}
|
||||
|
||||
LONG RegSearch(HKEY hKey, LPTSTR lpSubKey, size_t iSubKeyLength,
|
||||
LPCTSTR pszSearchString, DWORD dwValueIndex,
|
||||
DWORD dwSearchFlags, BOOL (*pfnCallback)(LPVOID), LPVOID lpParam)
|
||||
{
|
||||
LONG lResult;
|
||||
LPCTSTR s;
|
||||
|
||||
UNREFERENCED_PARAMETER(dwValueIndex);
|
||||
|
||||
if (dwSearchFlags & (RSF_LOOKATVALUES | RSF_LOOKATDATA))
|
||||
return ERROR_CALL_NOT_IMPLEMENTED; /* NYI */
|
||||
|
||||
do
|
||||
{
|
||||
if (pfnCallback)
|
||||
{
|
||||
if (pfnCallback(lpParam))
|
||||
return ERROR_OPERATION_ABORTED;
|
||||
}
|
||||
|
||||
lResult = RegNextKey(hKey, lpSubKey, iSubKeyLength);
|
||||
if (lResult != ERROR_SUCCESS)
|
||||
return lResult;
|
||||
|
||||
s = _tcsrchr(lpSubKey, TEXT('\\'));
|
||||
s = s ? s + 1 : lpSubKey;
|
||||
}
|
||||
while(!(dwSearchFlags & RSF_LOOKATKEYS) || !RegSearchCompare(s, pszSearchString, dwSearchFlags));
|
||||
|
||||
return ERROR_SUCCESS;
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
* Key naming and parsing
|
||||
*/
|
||||
|
|
|
@ -92,10 +92,6 @@ LONG RegQueryStringValue(HKEY hKey, LPCTSTR lpSubKey, LPCTSTR lpValueName, LPTST
|
|||
#define RSF_LOOKATDATA 0x00000008
|
||||
#define RSF_MATCHCASE 0x00010000
|
||||
|
||||
LONG RegSearch(HKEY hKey, LPTSTR lpSubKey, size_t iSubKeyLength,
|
||||
LPCTSTR pszSearchString, DWORD dwValueIndex,
|
||||
DWORD dwSearchFlags, BOOL (*pfnCallback)(LPVOID), LPVOID lpParam);
|
||||
|
||||
BOOL RegKeyGetName(LPTSTR pszDest, size_t iDestLength, HKEY hRootKey, LPCTSTR lpSubKey);
|
||||
|
||||
/* EOF */
|
||||
|
|
Loading…
Reference in a new issue