windows-nt/Source/XPSP1/NT/admin/snapin/wsecmgr/regvalue.cpp
2020-09-26 16:20:57 +08:00

566 lines
16 KiB
C++

// This is a part of the Microsoft Management Console.
// Copyright (C) 1995-2001 Microsoft Corporation
// All rights reserved.
//
// This source code is only intended as a supplement to the
// Microsoft Management Console and related
// electronic documentation provided with the interfaces.
#include "stdafx.h"
#include "snapmgr.h"
#include "util.h"
#include "regvldlg.h"
//#include <shlwapi.h>
//#include <shlwapip.h>
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
//
// create registry value list under configuration node
//
void CSnapin::CreateProfileRegValueList(MMC_COOKIE cookie,
PEDITTEMPLATE pSceInfo,
LPDATAOBJECT pDataObj)
{
if ( !pSceInfo || !(pSceInfo->pTemplate) ) {
return;
}
DWORD nCount = pSceInfo->pTemplate->RegValueCount;
PSCE_REGISTRY_VALUE_INFO regArray = pSceInfo->pTemplate->aRegValues;
CString strDisplayName;
LPTSTR pDisplayName=NULL;
DWORD displayType = 0;
LPTSTR szUnits=NULL;
PREGCHOICE pChoices=NULL;
PREGFLAGS pFlags=NULL;
CResult *pResult;
for ( DWORD i=0; i<nCount; i++) {
if ( !LookupRegValueProperty(regArray[i].FullValueName,
&pDisplayName,
&displayType,
&szUnits,
&pChoices,
&pFlags) ) {
continue;
}
if ( !pDisplayName ) {
strDisplayName = regArray[i].FullValueName;
} else {
strDisplayName = pDisplayName;
LocalFree(pDisplayName);
}
//
// add this item
//
pResult = AddResultItem(strDisplayName,
NULL,
(LONG_PTR)&(regArray[i]),
ITEM_PROF_REGVALUE,
-1,
cookie,
false,
szUnits,
displayType,
pSceInfo,
pDataObj);
if (pResult && pChoices) {
pResult->SetRegChoices(pChoices);
}
if (pResult && pFlags) {
pResult->SetRegFlags(pFlags);
}
if ( szUnits ) {
LocalFree(szUnits);
}
szUnits = NULL;
}
return;
}
void
CSnapin::CreateAnalysisRegValueList(MMC_COOKIE cookie,
PEDITTEMPLATE pAnalTemp,
PEDITTEMPLATE pEditTemp,
LPDATAOBJECT pDataObj,
RESULT_TYPES type)
{
if ( !pAnalTemp || !(pAnalTemp->pTemplate) ||
!pEditTemp || !(pEditTemp->pTemplate) ) {
return;
}
DWORD nEditCount = pEditTemp->pTemplate->RegValueCount; // should be everything
PSCE_REGISTRY_VALUE_INFO paEdit = pEditTemp->pTemplate->aRegValues;
PSCE_REGISTRY_VALUE_INFO paAnal = pAnalTemp->pTemplate->aRegValues;
CString strDisplayName;
LPTSTR pDisplayName=NULL;
DWORD displayType = 0;
LPTSTR szUnits = NULL;
PREGCHOICE pChoices = NULL;
PREGFLAGS pFlags = NULL;
CResult *pResult=NULL;
for ( DWORD i=0; i<nEditCount; i++) {
if ( !LookupRegValueProperty(paEdit[i].FullValueName,
&pDisplayName,
&displayType,
&szUnits,
&pChoices,
&pFlags) ) {
continue;
}
if ( !pDisplayName ) {
strDisplayName = paEdit[i].FullValueName;
} else {
strDisplayName = pDisplayName;
LocalFree(pDisplayName);
}
//
// find the match in the analysis array
// should always find a match because all existing reg values are
// added to the array when getinfo is called
//
for ( DWORD j=0; j< pAnalTemp->pTemplate->RegValueCount; j++ ) {
if ( pAnalTemp->pTemplate->aRegValues &&
pAnalTemp->pTemplate->aRegValues[j].FullValueName &&
_wcsicmp(pAnalTemp->pTemplate->aRegValues[j].FullValueName, paEdit[i].FullValueName) == 0 ) {
if( reinterpret_cast<CFolder *>(cookie)->GetModeBits() & MB_LOCAL_POLICY ){
break;
}
//
// find a analysis result - this item may be a mismatch (when Value is not NULL)
// SceEnumAllRegValues will set the status field to good if this item was not
// added because it did not exist when it was originally loaded from the SAP table.
// This tells us that this item is a MATCH and we should copy the value.
//
if ( !(paAnal[j].Value) && paEdit[i].Value &&
paAnal[j].Status != SCE_STATUS_ERROR_NOT_AVAILABLE &&
paAnal[j].Status != SCE_STATUS_NOT_ANALYZED ) {
//
// this is a good item, copy the config info as the analysis info
//
paAnal[j].Value = (PWSTR)LocalAlloc(0,
(wcslen(paEdit[i].Value)+1)*sizeof(WCHAR));
if ( paAnal[j].Value ) {
wcscpy(paAnal[j].Value, paEdit[i].Value);
} else {
// else out of memory
if ( szUnits ) {
LocalFree(szUnits);
}
szUnits = NULL;
return;
}
}
break;
}
}
DWORD status = SCE_STATUS_GOOD;
if ( j < pAnalTemp->pTemplate->RegValueCount ) {
status = CEditTemplate::ComputeStatus( &paEdit[i], &pAnalTemp->pTemplate->aRegValues[j] );
} else {
//
// did not find the analysis array, shouldn't happen
//
status = SCE_STATUS_NOT_CONFIGURED;
}
//
// add this item
//
if ( j < pAnalTemp->pTemplate->RegValueCount) {
pResult = AddResultItem(strDisplayName,
(LONG_PTR)&(pAnalTemp->pTemplate->aRegValues[j]),
(LONG_PTR)&(paEdit[i]),
type,
status,
cookie,
false,
szUnits,
displayType,
pEditTemp,
pDataObj);
if (pResult && pChoices) {
pResult->SetRegChoices(pChoices);
}
if (pResult && pFlags) {
pResult->SetRegFlags(pFlags);
}
} else {
//
// a good/not configured item
//
pResult = AddResultItem(strDisplayName,
NULL,
(LONG_PTR)&(paEdit[i]),
type,
status,
cookie,
false,
szUnits,
displayType,
pEditTemp,
pDataObj);
if (pResult && pChoices) {
pResult->SetRegChoices(pChoices);
}
}
if ( szUnits ) {
LocalFree(szUnits);
}
szUnits = NULL;
}
return;
}
BOOL
LookupRegValueProperty(
IN LPTSTR RegValueFullName,
OUT LPTSTR *pDisplayName,
OUT PDWORD displayType,
OUT LPTSTR *pUnits OPTIONAL,
OUT PREGCHOICE *pChoices OPTIONAL,
OUT PREGFLAGS *pFlags OPTIONAL
)
{
if ( !RegValueFullName || !pDisplayName || !displayType ) {
return FALSE;
}
CString strTmp = RegValueFullName;
//
// replace the \\ with / before search reg
//
int npos = strTmp.Find(L'\\');
while (npos > 0) {
*(strTmp.GetBuffer(1)+npos) = L'/';
npos = strTmp.Find(L'\\');
}
//
// query the values from registry
//
*pDisplayName = NULL;
HKEY hKey=NULL;
HKEY hKey2=NULL;
DWORD rc = RegOpenKeyEx(
HKEY_LOCAL_MACHINE,
SCE_ROOT_REGVALUE_PATH,
0,
KEY_READ,
&hKey
);
if (rc == ERROR_SUCCESS) {
rc = RegOpenKeyEx(
hKey,
(PWSTR)(LPCTSTR)strTmp,
0,
KEY_READ,
&hKey2
);
}
BOOL bRet;
if ( ERROR_SUCCESS == rc) {
DWORD RegType = 0;
PWSTR Value=NULL;
HRESULT hr = S_OK;
Value = (PWSTR) LocalAlloc(LPTR,MAX_PATH*sizeof(WCHAR));
if (Value) {
//
// 126714 - shouldn't hard code display strings in the registry
// store them indirectly so they can support MUI
//
hr = SHLoadRegUIString(hKey2,
SCE_REG_DISPLAY_NAME,
Value,
MAX_PATH);
if (FAILED(hr)) {
rc = MyRegQueryValue(
hKey,
(PWSTR)(LPCTSTR)strTmp,
SCE_REG_DISPLAY_NAME,
(PVOID *)&Value,
&RegType
);
} else {
rc = ERROR_SUCCESS;
}
}
if ( rc == ERROR_SUCCESS ) {
if ( Value ) {
*pDisplayName = Value;
Value = NULL;
} else {
//
// did not find correct display name, use the reg name (outsize)
//
*pDisplayName = NULL;
}
}
rc = MyRegQueryValue(
hKey,
(PWSTR)(LPCTSTR)strTmp,
SCE_REG_DISPLAY_TYPE,
(PVOID *)&displayType,
&RegType
);
if ( Value ) {
LocalFree(Value);
Value = NULL;
}
if ( pUnits ) {
//
// query the units
//
rc = MyRegQueryValue(
hKey,
(PWSTR)(LPCTSTR)strTmp,
SCE_REG_DISPLAY_UNIT,
(PVOID *)&Value,
&RegType
);
if ( rc == ERROR_SUCCESS ) {
if ( RegType == REG_SZ && Value ) {
*pUnits = Value;
Value = NULL;
} else {
//
// did not find units
//
*pUnits = NULL;
}
}
if ( Value ) {
LocalFree(Value);
Value = NULL;
}
}
//
// find the registry key but may not find the display name
//
bRet = TRUE;
if ( pChoices ) {
//
// query the choices
//
*pChoices = NULL;
rc = MyRegQueryValue(hKey,
(PWSTR)(LPCTSTR)strTmp,
SCE_REG_DISPLAY_CHOICES,
(PVOID *)&Value,
&RegType
);
if (ERROR_SUCCESS == rc) {
if ((REG_MULTI_SZ == RegType) && Value) {
LPTSTR szChoice = NULL;
LPTSTR szLabel = NULL; // max field size for szChoice + dwVal
DWORD dwVal = -1;
PREGCHOICE pRegChoice = NULL;
PREGCHOICE pLast = NULL;
szChoice = Value;
do {
//
// Divide szChoice into dwValue and szLabel sections
//
szLabel = _tcschr(szChoice,L'|');
*szLabel = L'\0';
szLabel++;
dwVal = _ttoi(szChoice);
pRegChoice = (PREGCHOICE) LocalAlloc(LPTR,sizeof(REGCHOICE));
if (pRegChoice) {
//
// Fill in fields of new reg choice
//
pRegChoice->dwValue = dwVal;
pRegChoice->szName = (LPTSTR) LocalAlloc(LPTR,(lstrlen(szLabel)+1)*sizeof(TCHAR));
if (NULL == pRegChoice->szName) {
//
// Out of memory. Bummer.
//
LocalFree(pRegChoice);
pRegChoice = NULL;
break;
}
lstrcpy(pRegChoice->szName,szLabel);
//
// Attach new item to end of list
//
if (NULL == *pChoices) {
*pChoices = pRegChoice;
} else {
pLast->pNext = pRegChoice;
}
pLast = pRegChoice;
}
szChoice = _tcschr(szLabel,L'\0');
szChoice++;
} while (*szChoice);
} else {
//
// Did not find choices
//
bRet = FALSE;
}
}
if ( Value ) {
LocalFree(Value);
Value = NULL;
}
}
if ( pFlags ) {
//
// query the Flags
//
*pFlags = NULL;
rc = MyRegQueryValue(hKey,
(PWSTR)(LPCTSTR)strTmp,
SCE_REG_DISPLAY_FLAGLIST,
(PVOID *)&Value,
&RegType
);
if (ERROR_SUCCESS == rc) {
if ((REG_MULTI_SZ == RegType) && Value) {
LPTSTR szFlag = NULL;
LPTSTR szLabel = NULL; // max field size for szFlag + dwVal
DWORD dwVal = -1;
PREGFLAGS pRegFlag = NULL;
PREGFLAGS pLast = NULL;
szFlag = Value;
do {
//
// Divide szFlag into dwValue and szLabel sections
//
szLabel = _tcschr(szFlag,L'|');
*szLabel = L'\0';
szLabel++;
dwVal = _ttoi(szFlag);
pRegFlag = (PREGFLAGS) LocalAlloc(LPTR,sizeof(REGFLAGS));
if (pRegFlag) {
//
// Fill in fields of new reg Flag
//
pRegFlag->dwValue = dwVal;
pRegFlag->szName = (LPTSTR) LocalAlloc(LPTR,(lstrlen(szLabel)+1)*sizeof(TCHAR));
if (NULL == pRegFlag->szName) {
//
// Out of memory. Bummer.
//
LocalFree(pRegFlag);
pRegFlag = NULL;
break;
}
lstrcpy(pRegFlag->szName,szLabel);
//
// Attach new item to end of list
//
if (NULL == *pFlags) {
*pFlags = pRegFlag;
} else {
pLast->pNext = pRegFlag;
}
pLast = pRegFlag;
}
szFlag = wcschr(szLabel,L'\0');
szFlag++;
} while (*szFlag);
} else {
//
// Did not find Flags
//
bRet = FALSE;
}
}
if ( Value ) {
LocalFree(Value);
Value = NULL;
}
}
} else {
//
// did not find the registry key
//
bRet = FALSE;
}
if ( hKey ) {
RegCloseKey(hKey);
}
if ( hKey2 ) {
RegCloseKey(hKey2);
}
return bRet;
}