Windows Registry

Reading And Writing Windows Registry Using WinAPI

If you are the windows application or driver developer, then might be you need to access the windows registry. In this article, I will describe the way to how to create and access the key in windows registry. Here, I am assuming you are familiar with windows internals and API. If you are not familiar with windows internal and API, see this popular course: Windows Internals

Below find the list of some WinAPI that I am using to create and access the windows registry key:
  • RegOpenKeyEx
  • RegCreateKeyEx
  • RegSetValueEx
  • RegQueryValueEx
  • RegCloseKey

You can find here a complete list of registry functions – MSDN.

Note: To access the windows registry you should have the admin rights.

Before creating the key we need to understand the windows registry hives. The hives are the group of registry keys, subkey, and the registry values.

You can see the registry hives in registry editor left-hand side of the screen. You can open the registry editor to running the command regedit in the search box or Run window.

Here is a list of some common registry hives in Windows:
  • HKEY_CLASSES_ROOT
  • HKEY_CURRENT_USER
  • HKEY_LOCAL_MACHINE
  • HKEY_USERS
  • HKEY_CURRENT_CONFIG

I think now time to see the example code. In this example code, I will create a key and read/write the value.

How to create a key under the hives:

In this code, you just need to pass the registry hives and key name which you want to create. If everything is fine then this function creates the key under the given hives.

BOOL CreateRegistryKey(HKEY hKeyParent,PWCHAR subkey)
{
    DWORD dwDisposition; //It verify new key is created or open existing key
    HKEY  hKey;
    DWORD Ret;


    Ret =
        RegCreateKeyEx(
            hKeyParent,
            subkey,
            0,
            NULL,
            REG_OPTION_NON_VOLATILE,
            KEY_ALL_ACCESS,
            NULL,
            &hKey,
            &dwDisposition);

    if (Ret != ERROR_SUCCESS)
    {
        printf("Error opening or creating new key\n");
        return FALSE;
    }

    RegCloseKey(hKey); //close the key
    return TRUE;
}

 

 

Write a DWORD value into the created key:

In this function, you need to pass the hives name, key name, value name and DWORD value which you want to store in the key. In this function, I am opening the key and just write the value. If everything fines then the value will store in the registry.

BOOL WriteInRegistry(HKEY hKeyParent, PWCHAR subkey, PWCHAR valueName,DWORD data)
{
    DWORD Ret; //use to check status
    HKEY hKey; //key


    //Open the key
    Ret = RegOpenKeyEx(
              hKeyParent,
              subkey,
              0,
              KEY_WRITE,
              &hKey
          );

    if (Ret == ERROR_SUCCESS)
    {

        //Set the value in key
        if (ERROR_SUCCESS !=
                RegSetValueEx(
                    hKey,
                    valueName,
                    0,
                    REG_DWORD,
                    reinterpret_cast<BYTE *>(&data),
                    sizeof(data)))
        {
            RegCloseKey(hKey);
            return FALSE;
        }

        //close the key
        RegCloseKey(hKey);

        return TRUE;
    }

    return FALSE;
}

 

If you love online courses, then here is a good c language course for you from the Pluralsight, 10 days trial is Free.

C tutorial

Write a string into the created key:

In this function, you need to pass the hives name, key name, value name, and string which you want to store in the key. Here one thing is to need to remember the size of wide char is 16 bits, so you need to be careful before writing the string into the windows registry.

BOOL writeStringInRegistry(HKEY hKeyParent, PWCHAR subkey, PWCHAR valueName, PWCHAR strData)
{
    DWORD Ret;
    HKEY hKey;

    //Check if the registry exists
    Ret = RegOpenKeyEx(
              hKeyParent,
              subkey,
              0,
              KEY_WRITE,
              &hKey
          );

    if (Ret == ERROR_SUCCESS)
    {
        if (ERROR_SUCCESS !=
                RegSetValueEx(
                    hKey,
                    valueName,
                    0,
                    REG_SZ,
                    (LPBYTE)(strData),
                    ((((DWORD)lstrlen(strData) + 1)) * 2)))
        {
            RegCloseKey(hKey);
            return FALSE;
        }

        RegCloseKey(hKey);
        return TRUE;
    }

    return FALSE;
}

 

 

Read a DWORD value from the created key:

Before reading the value from a key, you should open it first. You require hives name, key name and value name to read the DWORD.

BOOL readDwordValueRegistry(HKEY hKeyParent, PWCHAR subkey, PWCHAR valueName, DWORD *readData)
{

    HKEY hKey;
    DWORD Ret;

    //Check if the registry exists
    Ret = RegOpenKeyEx(
              hKeyParent,
              subkey,
              0,
              KEY_READ,
              &hKey
          );

    if (Ret == ERROR_SUCCESS)
    {

        DWORD data;
        DWORD len = sizeof(DWORD);//size of data

        Ret = RegQueryValueEx(
                  hKey,
                  valueName,
                  NULL,
                  NULL,
                  (LPBYTE)(&data),
                  &len
              );

        if (Ret == ERROR_SUCCESS)
        {
            RegCloseKey(hKey);
            (*readData) = data;
            return TRUE;
        }

        RegCloseKey(hKey);
        return TRUE;
    }
    else
    {
        return FALSE;
    }
}

 

 

Read a string from the created key:

Similar to the above method. You require hives name, key name and value name to read the string from the key. Before reading the string you need to give the proper length of the string either you will get an error.

BOOL readStringFromRegistry(HKEY hKeyParent, PWCHAR subkey, PWCHAR valueName, PWCHAR *readData)
{
    HKEY hKey;
    DWORD len = TOTAL_BYTES_READ;

    DWORD readDataLen = len;

    PWCHAR readBuffer = (PWCHAR )malloc(sizeof(PWCHAR)* len);
    if (readBuffer == NULL)
        return FALSE;

    //Check if the registry exists
    DWORD Ret = RegOpenKeyEx(
                    hKeyParent,
                    subkey,
                    0,
                    KEY_READ,
                    &hKey
                );

    if (Ret == ERROR_SUCCESS)
    {

        Ret = RegQueryValueEx(
                  hKey,
                  valueName,
                  NULL,
                  NULL,
                  (BYTE*)readBuffer,
                  &readDataLen
              );

        while (Ret == ERROR_MORE_DATA)
        {
            // Get a buffer that is big enough.

            len += OFFSET_BYTES;
            readBuffer = (PWCHAR)realloc(readBuffer, len);
            readDataLen = len;

            Ret = RegQueryValueEx(
                      hKey,
                      valueName,
                      NULL,
                      NULL,
                      (BYTE*)readBuffer,
                      &readDataLen
                  );
        }

        if (Ret != ERROR_SUCCESS)
        {
            RegCloseKey(hKey);
            return false;;
        }

        *readData = readBuffer;

        RegCloseKey(hKey);
        return true;
    }
    else
    {
        return false;
    }
}

 

 

To understand the above methods let see an example code, In the below example, I have created a key “Aticleworld” and two value “date” and “Message”. I will store and read the stored value from the key using the above-described methods.

windows registry key

#include "stdafx.h"
#include <windows.h>
#include <stdio.h>

#define TOTAL_BYTES_READ    1024
#define OFFSET_BYTES 1024


//Create key in registry
BOOL CreateRegistryKey(HKEY hKeyParent,PWCHAR subkey)
{
    DWORD dwDisposition; //It verify new key is created or open existing key
    HKEY  hKey;
    DWORD Ret;


    Ret =
        RegCreateKeyEx(
            hKeyParent,
            subkey,
            0,
            NULL,
            REG_OPTION_NON_VOLATILE,
            KEY_ALL_ACCESS,
            NULL,
            &hKey,
            &dwDisposition);

    if (Ret != ERROR_SUCCESS)
    {
        printf("Error opening or creating key.\n");
        return FALSE;
    }

    RegCloseKey(hKey);
    return TRUE;
}


//Write data in registry
BOOL WriteDwordInRegistry(HKEY hKeyParent, PWCHAR subkey, PWCHAR valueName,DWORD data)
{
    DWORD Ret;
    HKEY hKey;


    //Open the key
    Ret = RegOpenKeyEx(
              hKeyParent,
              subkey,
              0,
              KEY_WRITE,
              &hKey
          );

    if (Ret == ERROR_SUCCESS)
    {

        //Set the value in key
        if (ERROR_SUCCESS !=
                RegSetValueEx(
                    hKey,
                    valueName,
                    0,
                    REG_DWORD,
                    reinterpret_cast<BYTE *>(&data),
                    sizeof(data)))
        {
            RegCloseKey(hKey);
            return FALSE;
        }

        //close the key
        RegCloseKey(hKey);

        return TRUE;
    }

    return FALSE;
}


//Read data from registry
BOOL readDwordValueRegistry(HKEY hKeyParent, PWCHAR subkey, PWCHAR valueName, DWORD *readData)
{

    HKEY hKey;
    DWORD Ret;

    //Check if the registry exists
    Ret = RegOpenKeyEx(
              hKeyParent,
              subkey,
              0,
              KEY_READ,
              &hKey
          );

    if (Ret == ERROR_SUCCESS)
    {

        DWORD data;
        DWORD len = sizeof(DWORD);//size of data

        Ret = RegQueryValueEx(
                  hKey,
                  valueName,
                  NULL,
                  NULL,
                  (LPBYTE)(&data),
                  &len
              );

        if (Ret == ERROR_SUCCESS)
        {
            RegCloseKey(hKey);
            (*readData) = data;
            return TRUE;
        }

        RegCloseKey(hKey);
        return TRUE;
    }
    else
    {
        return FALSE;
    }
}



//Write range and type into the registry
BOOL writeStringInRegistry(HKEY hKeyParent, PWCHAR subkey, PWCHAR valueName, PWCHAR strData)
{
    DWORD Ret;
    HKEY hKey;

    //Check if the registry exists
    Ret = RegOpenKeyEx(
              hKeyParent,
              subkey,
              0,
              KEY_WRITE,
              &hKey
          );

    if (Ret == ERROR_SUCCESS)
    {
        if (ERROR_SUCCESS !=
                RegSetValueEx(
                    hKey,
                    valueName,
                    0,
                    REG_SZ,
                    (LPBYTE)(strData),
                    ((((DWORD)lstrlen(strData) + 1)) * 2)))
        {
            RegCloseKey(hKey);
            return FALSE;
        }

        RegCloseKey(hKey);
        return TRUE;
    }

    return FALSE;
}

//read customer infromation from the registry
BOOL readUserInfoFromRegistry(HKEY hKeyParent, PWCHAR subkey, PWCHAR valueName, PWCHAR *readData)
{
    HKEY hKey;
    DWORD len = TOTAL_BYTES_READ;

    DWORD readDataLen = len;

    PWCHAR readBuffer = (PWCHAR )malloc(sizeof(PWCHAR)* len);
    if (readBuffer == NULL)
        return FALSE;

    //Check if the registry exists
    DWORD Ret = RegOpenKeyEx(
                    hKeyParent,
                    subkey,
                    0,
                    KEY_READ,
                    &hKey
                );

    if (Ret == ERROR_SUCCESS)
    {

        Ret = RegQueryValueEx(
                  hKey,
                  valueName,
                  NULL,
                  NULL,
                  (BYTE*)readBuffer,
                  &readDataLen
              );

        while (Ret == ERROR_MORE_DATA)
        {
            // Get a buffer that is big enough.

            len += OFFSET_BYTES;
            readBuffer = (PWCHAR)realloc(readBuffer, len);
            readDataLen = len;

            Ret = RegQueryValueEx(
                      hKey,
                      valueName,
                      NULL,
                      NULL,
                      (BYTE*)readBuffer,
                      &readDataLen
                  );
        }

        if (Ret != ERROR_SUCCESS)
        {
            RegCloseKey(hKey);
            return false;;
        }

        *readData = readBuffer;

        RegCloseKey(hKey);
        return true;
    }
    else
    {
        return false;
    }
}

//main function
int _tmain(int argc, _TCHAR* argv[])
{
    BOOL status;
    DWORD readData;
    PWCHAR readMessage = nullptr;

    status = CreateRegistryKey(HKEY_CURRENT_USER, L"Aticleworld"); //create key
    if (status != TRUE)
        return FALSE;

    status = WriteDwordInRegistry(HKEY_CURRENT_USER, L"Aticleworld",L"date",12082016); //write dword
    if (status != TRUE)
        return FALSE;

    status = readDwordValueRegistry(HKEY_CURRENT_USER, L"Aticleworld", L"date", &readData); //read dword
    if (status != TRUE)
        return FALSE;

    printf("%ld", readData);

    status = writeStringInRegistry(HKEY_CURRENT_USER, L"Aticleworld", L"Message", L"Happy"); //write string
    if (status != TRUE)
        return FALSE;

    status = readUserInfoFromRegistry(HKEY_CURRENT_USER, L"Aticleworld", L"Message", &readMessage); //read string
    if (status != TRUE)
        return FALSE;

    if (readMessage != nullptr)
    {
        printf(" Message = %S\n", readMessage);
        free(readMessage);
        readMessage = nullptr;
    }

    return 0;
}