|
|
/*************************************************************************
* * reguc.c * * Registry APIs for user configuration data and TerminalServer AppServer detection * * Copyright (c) 1998 Microsoft Corporation * * *************************************************************************/
/*
* Includes */ #include <nt.h>
#include <ntrtl.h>
#include <nturtl.h>
#include <ntsam.h>
#include <windows.h>
#include <ntddkbd.h>
#include <ntddmou.h>
#include <winstaw.h>
#include <regapi.h>
#include <regsam.h>
/*
* External Procedures defined here */ LONG WINAPI RegUserConfigSet( WCHAR *, WCHAR *, PUSERCONFIGW, ULONG ); LONG WINAPI RegUserConfigQuery( WCHAR *, WCHAR *, PUSERCONFIGW, ULONG, PULONG ); LONG WINAPI RegUserConfigDelete( WCHAR *, WCHAR * ); LONG WINAPI RegUserConfigRename( WCHAR *, WCHAR *, WCHAR * ); LONG WINAPI RegDefaultUserConfigQueryW( WCHAR *, PUSERCONFIGW, ULONG, PULONG ); LONG WINAPI RegDefaultUserConfigQueryA( CHAR *, PUSERCONFIGA, ULONG, PULONG ); BOOLEAN WINAPI RegIsTServer( WCHAR * );
/*
* other internal Procedures used (not defined here) */ VOID CreateUserConfig( HKEY, PUSERCONFIG, PWINSTATIONNAMEW ); VOID QueryUserConfig( HKEY, PUSERCONFIG, PWINSTATIONNAMEW ); VOID UserConfigU2A( PUSERCONFIGA, PUSERCONFIGW ); VOID AnsiToUnicode( WCHAR *, ULONG, CHAR * ); VOID CreateNWLogonAdmin( HKEY, PNWLOGONADMIN ); VOID QueryNWLogonAdmin( HKEY, PNWLOGONADMIN );
/*******************************************************************************
* * RegUserConfigSet (UNICODE) * * Creates or updates the specified user's User Configuration structure in * the SAM of the user's Domain controller. * * ENTRY: * pServerName (input) * Points to string of server to access (NULL for current machine). * pUserName (input) * Points to name of user to set configuration data for. * pUserConfig (input) * Pointer to a USERCONFIG structure containing specified user's * configuration information. * UserConfigLength (input) * Specifies the length in bytes of the pUserConfig buffer. * * EXIT: * ERROR_SUCCESS - no error * ERROR_INSUFFICIENT_BUFFER - pUserConfig buffer too small * otherwise: the error code * ******************************************************************************/
LONG WINAPI RegUserConfigSet( WCHAR * pServerName, WCHAR * pUserName, PUSERCONFIGW pUserConfig, ULONG UserConfigLength ) { LONG Error;
/*
* Validate length of buffer */ if ( UserConfigLength < sizeof(USERCONFIGW) ) return( ERROR_INSUFFICIENT_BUFFER );
Error = RegSAMUserConfig( FALSE, pUserName, pServerName, pUserConfig );
return( Error ); }
/*******************************************************************************
* * RegUserConfigQuery (UNICODE) * * Query the specified user's configuration from the indicated server. * * ENTRY: * pServerName (input) * Points to string of server to access (NULL for current machine). * pUserName (input) * Points to name of user to query configuration data for. * pUserConfig (input) * Pointer to a USERCONFIGW structure that will receive the user's * configuration data. * UserConfigLength (input) * Specifies the length in bytes of the pUserConfig buffer. * pReturnLength (output) * Receives the number of bytes placed in the pUserConfig buffer. * * EXIT: * ERROR_SUCCESS - no error * otherwise: the error code * ******************************************************************************/
LONG WINAPI RegUserConfigQuery( WCHAR * pServerName, WCHAR * pUserName, PUSERCONFIGW pUserConfig, ULONG UserConfigLength, PULONG pReturnLength ) { LONG Error; // WCHAR KeyString[256+USERNAME_LENGTH];
// HKEY ServerHandle, UserHandle;
/*
* Validate length and zero-initialize the destination * USERCONFIGW buffer. */ if ( UserConfigLength < sizeof(USERCONFIGW) ) return( ERROR_INSUFFICIENT_BUFFER );
if ( ( pUserName == NULL ) ) // || ((wcslen(USERCONFIG_REG_NAME) + wcslen(pUserName)) >= (256+USERNAME_LENGTH))) {
{ return ERROR_INVALID_PARAMETER; }
memset(pUserConfig, 0, UserConfigLength);
Error = RegSAMUserConfig( TRUE , pUserName , pServerName , pUserConfig );
// all valid sam errors are returned:299987
#if 0 // this has to go!!!!
if( Error == ERROR_FILE_NOT_FOUND ) { /*
* Connect to registry of specified server. */
if( (Error = RegConnectRegistry( pServerName, HKEY_LOCAL_MACHINE, &ServerHandle )) != ERROR_SUCCESS ) { KdPrint( ( "REGAPI - RegUserConfigQuery@RegConnectRegistry returned 0x%x\n", Error ) );
return( Error );
/*
* Open the key for specified user. */ wcscpy( KeyString, USERCONFIG_REG_NAME ); wcscat( KeyString, pUserName );
if ( (Error = RegOpenKeyEx( ServerHandle, KeyString, 0, KEY_READ, &UserHandle )) != ERROR_SUCCESS ) {
KdPrint( ( "REGAPI - RegUserConfigQuery@RegOpenKeyEx returned 0x%x\n", Error ) ); RegCloseKey( ServerHandle ); return( Error ); }
/*
* Query USERCONFIG Structure */ QueryUserConfig( UserHandle, pUserConfig, NULL );
/*
* Close registry handles. */
RegCloseKey( UserHandle ); RegCloseKey( ServerHandle ); } #endif // legacy crap
*pReturnLength = sizeof(USERCONFIGW);
return( Error ); }
/*******************************************************************************
* * -- FOR COMPATIBILITY ONLY-- * Deletion of the user configuration will occur when the user is * removed, since the UserConfiguration is part of the SAM. The old * Registry-based user configuration is left intact and must be * managed with registry-based 1.6 versions. * * RegUserConfigDelete (UNICODE) * * Delete the specified user's configuration from the indicated server. * * ENTRY: * pServerName (input) * Points to string of server to access (NULL for current machine). * pUserName (input) * Points to name of user to delete configuration data for. * * EXIT: * ERROR_SUCCESS - no error * otherwise: the error code * ******************************************************************************/
LONG WINAPI RegUserConfigDelete( WCHAR * pServerName, WCHAR * pUserName ) { return( NO_ERROR ); }
/*******************************************************************************
* * -- FOR COMPATIBILITY ONLY-- * Renaming of the user configuration will occur when the user is * rename, since the UserConfiguration is part of the SAM. The old * Registry-based user configuration is left intact and must be * managed with registry-based 1.6 versions. * * RegUserConfigRename (UNICODE) * * Rename the specified user's configuration on the indicated server. * * ENTRY: * pServerName (input) * Points to string of server to access. * pUserOldName (input) * Points to old name of user. * pUserNewName (input) * Points to new name of user. * * EXIT: * ERROR_SUCCESS - no error * otherwise: the error code * ******************************************************************************/
LONG WINAPI RegUserConfigRename( WCHAR * pServerName, WCHAR * pUserOldName, WCHAR * pUserNewName ) { return( NO_ERROR ); }
/*******************************************************************************
* * RegDefaultUserConfigQueryA (ANSI stub) * * Query the Default User Configuration from the indicated server's registry. * * ENTRY: * see RegDefaultUserConfigQueryW * * EXIT: * see RegDefaultUserConfigQueryW * ******************************************************************************/
LONG WINAPI RegDefaultUserConfigQueryA( CHAR * pServerName, PUSERCONFIGA pUserConfig, ULONG UserConfigLength, PULONG pReturnLength ) { USERCONFIGW UserConfigW; WCHAR ServerNameW[ DOMAIN_LENGTH + 1 ]; ULONG ReturnLengthW;
/*
* Validate length and zero-initialize the destination * USERCONFIGA structure. */ if ( UserConfigLength < sizeof(USERCONFIGA) ) return( ERROR_INSUFFICIENT_BUFFER ); memset(pUserConfig, 0, UserConfigLength);
/*
* Convert server name to UINCODE (if present). */ if ( pServerName ) AnsiToUnicode( ServerNameW, sizeof(ServerNameW), pServerName );
/*
* Query Default User Configuration (will always return success). */ RegDefaultUserConfigQueryW( pServerName ? ServerNameW : (WCHAR *)NULL, &UserConfigW, sizeof(USERCONFIGW), &ReturnLengthW );
/*
* Copy USERCONFIGW elements to USERCONFIGA elements. */ UserConfigU2A( pUserConfig, &UserConfigW );
*pReturnLength = sizeof(USERCONFIGA);
return( ERROR_SUCCESS ); }
/*******************************************************************************
* * RegDefaultUserConfigQueryW (UNICODE) * * Query the Default User Configuration from the indicated server's registry. * * ENTRY: * pServerName (input) * Points to string of server to access (NULL for current machine). * pUserConfig (input) * Pointer to a USERCONFIGW structure that will receive the default * user configuration information. * UserConfigLength (input) * Specifies the length in bytes of the pUserConfig buffer. * pReturnLength (output) * Receives the number of bytes placed in the pUserConfig buffer. * * EXIT: * Always will return ERROR_SUCCESS, unless UserConfigLength is incorrect. * ******************************************************************************/
LONG WINAPI RegDefaultUserConfigQueryW( WCHAR * pServerName, PUSERCONFIGW pUserConfig, ULONG UserConfigLength, PULONG pReturnLength ) { HKEY ServerHandle, ConfigHandle; DWORD Disp;
/*
* Validate length and zero-initialize the destination * USERCONFIGW buffer. */ if ( UserConfigLength < sizeof(USERCONFIGW) ) return( ERROR_INSUFFICIENT_BUFFER );
/*
* Initialize to an initial default in case of failure down the road. */ memset(pUserConfig, 0, UserConfigLength); // pUserConfig->fInheritInitialProgram = TRUE;
// pUserConfig->Shadow = Shadow_EnableInputNotify;
//
// butchd 10/10/97: Make the default based on the regapi's
// built-in preferences (use HKEY_LOCAL_MACHINE for
// a valid registry handle that will not have actual
// DefaultUserConfig key/values present)
//
QueryUserConfig( HKEY_LOCAL_MACHINE, pUserConfig, NULL );
*pReturnLength = sizeof(USERCONFIGW);
/*
* Connect to registry of specified server. If a failure is seen at * this point, return ERROR_SUCCESS immediately (no point in trying * to write the default user configuration key and values). */ if ( RegConnectRegistry( pServerName, HKEY_LOCAL_MACHINE, &ServerHandle ) != ERROR_SUCCESS ) return( ERROR_SUCCESS );
/*
* Open default user configuration registry key. If this fails, we will * attempt to create the key and write the initial default information * there, returning ERROR_SUCCESS whether that succeeds or not. */ if ( RegOpenKeyEx( ServerHandle, DEFCONFIG_REG_NAME, 0, KEY_READ, &ConfigHandle ) != ERROR_SUCCESS ) {
if ( RegCreateKeyEx( ServerHandle, DEFCONFIG_REG_NAME, 0, NULL, REG_OPTION_NON_VOLATILE, KEY_ALL_ACCESS, NULL, &ConfigHandle, &Disp ) == ERROR_SUCCESS ) {
CreateUserConfig( ConfigHandle, pUserConfig, NULL ); RegCloseKey( ConfigHandle ); } RegCloseKey( ServerHandle ); return( ERROR_SUCCESS ); }
/*
* Query USERCONFIG Structure */ QueryUserConfig( ConfigHandle, pUserConfig, NULL );
/*
* Close registry handles. */ RegCloseKey( ConfigHandle ); RegCloseKey( ServerHandle );
return( ERROR_SUCCESS ); }
/*******************************************************************************
* * RegIsTServer (UNICODE) * * Determine if the specified server is a Terminal Server by checking for * a TServer-specific registry key. * * ENTRY: * pServerName (input) * Points to string of server to check. * * EXIT: * TRUE if Terminal Server; FALSE otherwise * ******************************************************************************/
BOOLEAN WINAPI RegIsTServer( WCHAR * pServerName ) { LONG Error; HKEY ServerHandle, UserHandle;
/*
* Connect to registry of specified server. */ if ( (Error = RegConnectRegistry( pServerName, HKEY_LOCAL_MACHINE, &ServerHandle )) != ERROR_SUCCESS ) return( FALSE );
/*
* Open the Winstations key on the server to see if it is * a Terminal Server. */ if ( (Error = RegOpenKeyEx( ServerHandle, WINSTATION_REG_NAME, 0, KEY_READ, &UserHandle )) != ERROR_SUCCESS ) {
RegCloseKey( ServerHandle ); return( FALSE ); }
/*
* Close registry handles. */ RegCloseKey( UserHandle ); RegCloseKey( ServerHandle );
return( TRUE ); }
|