|
|
/////////////////////////////////////////////////////////////////////////////
//
// Copyright (c) 1998 Microsoft Corporation
//
// Module Name:
// RegUtils.cpp
//
// Abstract:
// Registry utilities
//
// Author:
// Galen Barbee (galenb) November 16, 1998
//
// Revision History:
// 16-Nov-1998 GalenB Stolen from nt\private\gina\samples\gptdemo
//
// Notes:
//
/////////////////////////////////////////////////////////////////////////////
#include "ClusRtlP.h"
#include <tchar.h>
//*************************************************************
//
// CheckSlash()
//
// Purpose: Checks for an ending slash and adds one if
// it is missing.
//
// Parameters: lpDir - directory
//
// Return: Pointer to the end of the string
//
// Comments:
//
// History: Date Author Comment
// 6/19/95 ericflo Created
//
//*************************************************************
LPTSTR CheckSlash( LPTSTR lpDir ) { DWORD dwStrLen; LPTSTR lpEnd;
lpEnd = lpDir + lstrlen( lpDir ); if ( *( lpEnd - 1 ) != TEXT( '\\' ) ) { *lpEnd = TEXT( '\\' ); lpEnd++; *lpEnd = TEXT( '\0' ); }
return lpEnd;
}
//*************************************************************
//
// RegDelnodeRecurse()
//
// Purpose: Deletes a registry key and all it's subkeys / values.
// Called by RegDelnode
//
// Parameters: hKeyRoot - Root key
// lpSubKey - SubKey to delete
//
// Return: TRUE if successful
// FALSE if an error occurs
//
// Comments:
//
// History: Date Author Comment
// 10/3/95 ericflo Created
//
//*************************************************************
BOOL RegDelnodeRecurse( HKEY hKeyRoot, LPTSTR lpSubKey ) { LPTSTR lpEnd; LONG lResult; DWORD dwSize; TCHAR szName[MAX_PATH]; HKEY hKey; FILETIME ftWrite;
//
// First, see if we can delete the key without having
// to recurse.
//
lResult = RegDeleteKey( hKeyRoot, lpSubKey ); if (lResult == ERROR_SUCCESS) { return TRUE; }
lResult = RegOpenKeyEx( hKeyRoot, lpSubKey, 0, KEY_READ, &hKey ); if ( lResult != ERROR_SUCCESS ) { return FALSE; }
lpEnd = CheckSlash( lpSubKey );
//
// Enumerate the keys
//
dwSize = MAX_PATH; lResult = RegEnumKeyEx( hKey, 0, szName, &dwSize, NULL, NULL, NULL, &ftWrite ); if ( lResult == ERROR_SUCCESS ) { do {
lstrcpy( lpEnd, szName );
if ( !RegDelnodeRecurse( hKeyRoot, lpSubKey ) ) { break; }
//
// Enumerate again
//
dwSize = MAX_PATH;
lResult = RegEnumKeyEx( hKey, 0, szName, &dwSize, NULL, NULL, NULL, &ftWrite );
} while ( lResult == ERROR_SUCCESS ); }
lpEnd--; *lpEnd = TEXT( '\0' );
RegCloseKey( hKey );
//
// Try again to delete the key
//
lResult = RegDeleteKey( hKeyRoot, lpSubKey ); if ( lResult == ERROR_SUCCESS ) { return TRUE; }
return FALSE; }
//*************************************************************
//
// RegDelnode()
//
// Purpose: Deletes a registry key and all it's subkeys / values
//
// Parameters: hKeyRoot - Root key
// lpSubKey - SubKey to delete
//
// Return: TRUE if successful
// FALSE if an error occurs
//
// Comments:
//
// History: Date Author Comment
// 10/3/95 ericflo Created
//
//*************************************************************
BOOL RegDelnode( HKEY hKeyRoot, const LPTSTR lpSubKey ) { TCHAR szDelKey[2 * MAX_PATH];
lstrcpy ( szDelKey, lpSubKey );
return RegDelnodeRecurse( hKeyRoot, szDelKey );
}
//*************************************************************
//
// RegCleanUpValue()
//
// Purpose: Removes the target value and if no more values / keys
// are present, removes the key. This function then
// works up the parent tree removing keys if they are
// also empty. If any parent key has a value / subkey,
// it won't be removed.
//
// Parameters: hKeyRoot - Root key
// lpSubKey - SubKey
// lpValueName - Value to remove
//
//
// Return: TRUE if successful
// FALSE if an error occurs
//
//*************************************************************
BOOL RegCleanUpValue( HKEY hKeyRoot, LPTSTR lpSubKey, LPTSTR lpValueName ) { LPTSTR lpEnd; DWORD dwKeys; DWORD dwValues; LONG lResult; HKEY hKey; TCHAR szDelKey[2 * MAX_PATH];
//
// Make a copy of the subkey so we can write to it.
//
lstrcpy( szDelKey, lpSubKey );
//
// First delete the value
//
lResult = RegOpenKeyEx( hKeyRoot, szDelKey, 0, KEY_WRITE, &hKey ); if ( lResult == ERROR_SUCCESS ) { lResult = RegDeleteValue( hKey, lpValueName );
RegCloseKey( hKey );
if ( lResult != ERROR_SUCCESS ) { if ( lResult != ERROR_FILE_NOT_FOUND ) { //DebugMsg((DM_WARNING, TEXT("RegCleanUpKey: Failed to delete value <%s> with %d."), lpValueName, lResult));
return FALSE; } } }
//
// Now loop through each of the parents. If the parent is empty
// eg: no values and no other subkeys, then remove the parent and
// keep working up.
//
lpEnd = szDelKey + lstrlen( szDelKey ) - 1;
while ( lpEnd >= szDelKey ) {
//
// Find the parent key
//
while ( ( lpEnd > szDelKey ) && ( *lpEnd != TEXT( '\\' ) ) ) { lpEnd--; }
//
// Open the key
//
lResult = RegOpenKeyEx( hKeyRoot, szDelKey, 0, KEY_READ, &hKey ); if ( lResult != ERROR_SUCCESS ) { if ( lResult == ERROR_FILE_NOT_FOUND ) { goto LoopAgain; } else { //DebugMsg((DM_WARNING, TEXT("RegCleanUpKey: Failed to open key <%s> with %d."), szDelKey, lResult));
return FALSE; } }
//
// See if there any any values / keys
//
lResult = RegQueryInfoKey( hKey, NULL, NULL, NULL, &dwKeys, NULL, NULL, &dwValues, NULL, NULL, NULL, NULL );
RegCloseKey( hKey );
if ( lResult != ERROR_SUCCESS ) { //DebugMsg((DM_WARNING, TEXT("RegCleanUpKey: Failed to query key <%s> with %d."), szDelKey, lResult));
return FALSE; }
//
// Exit now if this key has values or keys
//
if ( ( dwKeys != 0 ) || ( dwValues != 0 ) ) { return TRUE; }
RegDeleteKey( hKeyRoot, szDelKey );
LoopAgain: //
// If we are at the beginning of the subkey, we can leave now.
//
if ( lpEnd == szDelKey ) { return TRUE; }
//
// There is a parent key. Remove the slash and loop again.
//
if ( *lpEnd == TEXT( '\\' ) ) { *lpEnd = TEXT( '\0' ); } }
return TRUE;
}
|