fREGISTRY


Quick Data

Header file:registry.h
Object name:fREGISTRY
Object index:1 of 1 Object

General Description

Nowadays, every program needs to be able to look at, read and write to the registry. So that's what this component does - look at, read, and write to the registry. I think you'll find it very useful.

Firstly, though, I will go over some definitions with you. The registry is a complex beast, and the descriptions are confusing, but all you can do is try your best to understand it.

Before you read these definitions, I trust you at least have an idea of what the registry is. If you don't, please go and find out first. If you want to see the registry, then click Start, then Run, and then type 'regedit' into the box. Click Ok, and the registry editor will load. Have a browse around - but don't change much unless you know what you are doing! I have deleted large keys before, only to cripple Windows to the point where I had to format my hard drive and start again. Just use some common sense, and you should be fine. Anyway, onto the descriptions:

The rule of thumb when writing to a registry, according to Microsoft, is to keep strings and binary data under two kilobytes. Any more than that, and the system "apparently" slows down and becomes less efficient. I can't see anybody saving more than that much in the registry anyway, but please just keep this in mind - after all, Microsoft designed the standard, and they should know how it works best.


Methods

These methods are split up a little bit to make navigating them a little easier.

Connecting to a registry, opening a key, or creating a key.


Prototype Description

bool ConnectRemoteRegistry(char* ComputerName, HKEY MainKey); This function connects to a remote computers registry, if they have the remote registry service installed and functioning. You probably will never have a use for this, but it's here anyway. I attempted to set up a remote registry service on my home network (a Win98SE to Win98FE) but found that I could not get it to work - as the sharing needs to be 'User Level', which involves NT servers and other such stuff, which becomes rather messy. Why couldn't it be simple? Oh, sorry, that's Microsoft we are talking about... <Ah-hem> Where was I? Oh, yes, if you want to know the values for MainKey, please see the next function. This function returns TRUE if it was successful, or FALSE otherwise.
bool OpenKey(HKEY MainKey, char* SubKey); This function opens the specified 'Key' - or, following my filesystem analogy, opens the specified folder. MainKey is one of the following values: (taken from the Win32 SDK Reference Manual)
  • HKEY_CLASSES_ROOT
  • HKEY_CURRENT_USER
  • HKEY_LOCAL_MACHINE
  • HKEY_USERS
Plus another few undocumented ones:
  • HKEY_PERFORMANCE_DATA
  • HKEY_CURRENT_CONFIG
  • HKEY_DYN_DATA (Careful with this one - it never worked for me.)
And SubKey defines what 'Folder' to open. This function returns TRUE if successful, or FALSE otherwise.
bool CreateKey(HKEY MainKey, char* SubKey); This function is exactly like the OpenKey() function except that it creates the specified 'Key' (or folder). If that key already exists, it is simply opened. MainKey and SubKey are the same as they would be for the OpenKey() function. This function returns TRUE if it was successful (regardless of whether or not it created a key), or FALSE otherwise.
void CloseKey(void); This function closes the current key that you opened with CreateKey() or OpenKey().
void FlushKeys(void); This function forces Windows to flush any changes you made to the contents of a key. Normally Windows will cache these changes until it feels it is ready to write them to disk, but calling this function will override that and force a write-to-disk.
bool DeleteKey(char* Key); This function deletes the specified key. This function will delete the key and it's subkeys, and also all the values under that key. This function returns TRUE if sucessful, or FALSE otherwise.
bool DeleteValue(char* Value); This function deletes a value under the currently opened key. All you need to do is specify the name of that value. This function returns TRUE if successful, or FALSE otherwise.

Writing values to the registry

To save stating the obvious over and over, all of these functions do similar things. They add a value to the registry. The new value has the name of ValueName, and the data specified by the second variable passed. If the value already exists, it is updated, and if the value does not exist, it is added. Simple as that. Also, each function returns TRUE if successful, or FALSE otherwise. Finally, any values added or updated are done so under the currently open key.

And past finally... you may have noticed in RegEdit that there is a "(Default)" value under every key. This value is simply a value without a name - and you are permitted to add and read these as well. Just specify "" for ValueName.

Prototype Description

bool SetStringValue(char* ValueName, char* String); This function writes a string value into the registry.
bool SetDWORDValueINT(char* ValueName, int Number); This function sets a DWORD value in the registry, from an int number. There seems to be some incompatibility between DWORDS and int's - thus this function. A DWORD is actually a long unsigned int.
bool SetDWORDValue(char* ValueName, DWORD Number); This function sets a DWORD value in the registry from a DWORD variable. Could be handy, considering that this seems to 'be' the number format when using the registry. Many programs use this like a bool - in that if a value is 1 (one), then it is true, and if it is 0 (Zero) it is false.
bool SetBinaryValue(char* ValueName, char* Data, int Size); This function sets a binary value in the registry. This could be useful for storing things like floats, or just general binary data. Data specifies a pointer to the data, and Size indicates how many bytes to enter into the registry.

Getting key names from the registry

It can be quite useful to get what keys exist in the registry... a necessity if you are writing your own Regedit.


Prototype Description

int GetNumberSubKeys(void); This function returns the number of keys under the currently open key.
char* GetKeyName(int Index); This function returns one of the keys under the current key. I'd recommend using the above function to determine the number of keys, and then loop through them to get all the keys.

Getting the values (or a value) from the registry

Now here is something that is really lucrative... getting values from the registry. These functions do manage to do that task, although getting them working was a long and tiring experience.


Prototype Description

int GetNumberValues(void); This function returns the number of values under the currently open key. You can use this function in conjunction with the next function to work out the number of values to enumerate.
bool LoadValue(int Index); This function loads the data from a value specified by Index. You can loop through all the values and read them - but you need to load the data first. After you have loaded the data, you can use the following functions (after the GetValue() function) to read this data. This function will return TRUE if it worked ok, or FALSE otherwise. If it returned FALSE, it will probably mean that you have extended past the range of values.
bool GetValue(char* ValueName); This function is like the above function, except that it makes finding a value a whole lot easier. Instead of specifying an index, this function takes a name of a value. It will search through the current key until a value with the specified name is found, and then it will load that data into memory, ready for you to read with the following functions. If the value can not be found, FALSE is returned. If a value is found, TRUE is returned.
char* GetValueName(void); This function returns the name of the value that you previously found with the LoadValue() or GetValue() functions.
char* GetData(void); This function returns the data which was associated with the value that you previously found with the LoadValue() or GetValue() functions. Please note that this data returned is binary data, and is compatible with binary and string values. If you want to return a number, then please use the following functions.
int GetNumber(void); This function returns a int number based on what the value was.
DWORD GetNumberDWORD(void); This function returns the DWORD value from the value that you loaded before.
int GetType(void); This function returns the type of the previously loaded value. The return value can be any one of the following: (taken from the Win32 SDK Reference Manual)
  • REG_BINARY - Binary data in any form.
  • REG_DWORD - A 32-bit number.
  • REG_DWORD_LITTLE_ENDIAN - A 32-bit number in little-endian format (same as REG_DWORD). In little-endian format, the most significant byte of a word is the high-order byte. This is the most common format for computers running Windows NT and Windows 95.
  • REG_DWORD_BIG_ENDIAN - A 32-bit number in big-endian format. In big-endian format, the most significant byte of a word is the low-order byte.
  • REG_EXPAND_SZ - A null-terminated string that contains unexpanded references to environment variables (for example, “%PATH%”). It will be a Unicode or ANSI string depending on whether you use the Unicode or ANSI functions.
  • REG_LINK - A Unicode symbolic link.
  • REG_MULTI_SZ - An array of null-terminated strings, terminated by two null characters.
  • REG_NONE - No defined value type.
  • REG_RESOURCE_LIST - A device-driver resource list.
  • REG_SZ - A null-terminated string. It will be a Unicode or ANSI string, depending on whether you use the Unicode or ANSI functions.
I'd be guessing that you'd rarely use half of these things - but here they are, in the event that you'd want to use them.
bool IsTypeString(void); This function returns TRUE if the previously loaded value was a string - any type of string.
bool IsTypeDWORD(void); This function returns TRUE if the previously loaded value was a DWORD (or a number).
bool IsTypeBinary(void); This function returns TRUE if the previously loaded value was binary data.
bool HasNoType(void); This function returns TRUE if the previously loaded value is registered as having no type.
int GetDataSize(void); This function returns the size of the data that made up the previously loaded value. This could be very useful when returning the size of some binary data that you loaded.
void CleanUp(void); This function cleans up and releases the memory previously allocated to hold the data that remains in memory whilst you worked on it. This data will be released when the class is destroyed, but you may wish to clear it as soon as you are finished.

Sample Code

The following snippet gives a basic idea of how to use this component.


//Now this is just a simple example... just to show some
//basic things.

//Firstly, we will recover the type of your primary CPU,
//which just so happens to be stored in the registry...
fREGISTRY Registry;

Registry.OpenKey(HKEY_LOCAL_MACHINE, 
                 "Hardware\\Description\\System\\CentralProcessor\\0");

//Note that I haven't shown any error checking. You should
//error check.

//Also note the double slashes (\\). That's the escape code for
//a single slash (\). You'll only need it if you hard-code a location,
//but when the user enters a location, say into an edit control,
//you will not need to have the double slash. You probably already
//know this, but just to make sure...

//Now find a certain value, and show it.
Registry.GetValue("Identifier");
if (Registry.IsTypeString())
   {
   MessageBox(NULL, Registry.GetData(),
              "And your primary processor is...", 0);
   }

//When you are done, or you wish to change keys, close the current
//key...
Registry.CloseKey();

//Now enumerate all the sub-keys under HKEY_LOCAL_MACHINE\Software
//(should be many keys).
Registry.OpenKey(HKEY_LOCAL_MACHINE, "Software");
for (int Temp = 0; Temp < Registry.GetNumberSubKeys(); Temp++)
    {
    ... = Registry.GetKeyName();
    }

//And that's it!
Registry.CloseKey();

Back to indexThe FreeFoote Foundation Classes Documentation