SunQuest
 
       Windows Scripting
  Home arrow Windows Scripting arrow Page 3 - Working with the Windows Registry in C++
ASP Free Forums 
.NET  
ASP  
ASP Code  
ASP.NET  
ASP.NET Code  
BrainDump  
C#  
Code Examples  
Database  
Database Code  
IIS  
Microsoft Access  
MS SQL Server  
Visual Basic.NET  
Windows Scripting  
Windows Security  
XML  
ASP Web Hosting  
ASP.NET Web Hosting 
Dedicated Servers 
Actuate Whitepapers 
Moblin 
Windows Web Hosting
 
IBM® developerWorks 
Sun Developer Network 
Weekly Newsletter
 
Developer Updates  
Free Website Content 
 RSS  Articles
 RSS  Forums
 RSS  All Feeds
Write For Us Get Paid 
Request Media Kit
Contact Us 
Site Map 
Privacy Policy 
Support 
 USERNAME
 
 PASSWORD
 
 
  >>> SIGN UP!  
  Lost Password? 
WINDOWS SCRIPTING

Working with the Windows Registry in C++
By: Barzan "Tony" Antal
  • Search For More Articles!
  • Disclaimer
  • Author Terms
  • Rating: 5 stars5 stars5 stars5 stars5 stars / 3
    2008-04-02

    Table of Contents:
  • Working with the Windows Registry in C++
  • Basic Registry Functions
  • More Registry Stuff
  • Final Words

  • Rate this Article: Poor Best 
      ADD THIS ARTICLE TO:
      Del.ici.ous Digg
      Blink Simpy
      Google Spurl
      Y! MyWeb Furl
    Email Me Similar Content When Posted
    Add Developer Shed Article Feed To Your Site
    Email Article To Friend
    Print Version Of Article
    PDF Version Of Article
     
     
    ADVERTISEMENT

    Be the architects of evolution and help create the mobile internet future. It’s your move---enter to win here!

    Working with the Windows Registry in C++ - More Registry Stuff


    (Page 3 of 4 )

    On the previous page I mentioned that here we’ll create a block of code that works recursively and enumerates the subkeys of the specified subkey. Since it’s recursive, the method calls itself and goes further (deeper) with each step until it reaches the bottom (end of the tree) and then continues along.

    Here’s how we call our RecurseEnumKeys() method. Don’t forget to declare its prototype at the top of your source file if you are coding using the top-down principle.

    RegOpenKeyEx(HKEY_LOCAL_MACHINE, TEXT("SoftwareDevShed Tutorial"), 0, KEY_ALL_ACCESS, &hKey);

    RecurseEnumKeys(hKey, 0);

    RegCloseKey(hKey);

    Now let’s see how the recursive method itself is written. We have two parameters. The first one is our hKey handle while the second is the level (how deep are we inside our subkey; you may need to use it later on even if we don’t use it right now in this snippet). We declare a few necessary variables at the beginning which will be used while calling the RegEnumKeyEx() function. dwIdx is the Index, szKeyName is the key name string, dwSize is the size for the keys, while fTime is a filetime variable.

    void RecurseEnumKeys(HKEY hKey, DWORD level)

    {

       DWORD dwIdx=0;

       TCHAR szKeyName[1024];

       DWORD dwSize=1024;

       FILETIME fTime;

       while(RegEnumKeyEx(hKey, dwIdx, szKeyName, &dwSize, NULL, NULL, NULL, &fTime) == ERROR_SUCCESS)

       {

           _tprintf(_T("\%s"),szKeyName);

           dwIdx++;

           HKEY hSubKey;

           if (RegOpenKeyEx(hKey, szKeyName, 0, KEY_READ, &hSubKey) == ERROR_SUCCESS)

           {

              RecurseEnumKeys(hSubKey, level+1);

              RegCloseKey(hSubKey);

           }

           printf("n");

       }

    }

    We simply move alongside the tree by calling its subkeys and moving deeper and deeper until we reach the bottom of the tree and then continue along, picking up the next subkey path (if there is one) and going on and on using the same methodology until we finish. Error handling is also included so that you can identify errors right away.

    Now let’s see how we are going to accomplish the dumping action. By dumping I mean exporting the contents of a particular subkey from the registry (or the entire registry per se – but that takes time and a little bit of disk space). The process per se isn’t hard at all but unfortunately it requires a certain “special privilege” to be enabled for the access token. It is disabled by default. Yes, even for Administrator profiles.

    I’m talking about the SE_BACKUP_NAME privilege. We are going to use the RegSaveKeyEx() function which does the job well; however, it requires the aforementioned privilege to be enabled (TRUE), otherwise it won’t work. This privilege allows the particular process for backup actions (such as using the RegSaveKeyEx for backing up).

    At first we will present our algorithm and then we’ll write a function that sets any explicitly specified privilege for any process token. This function will be called ModifyPrivilege(). We're going to call it for the SE_BACKUP_NAME privilege and ask for it to enable the privilege for us – “making it TRUE.”

    int hr = ModifyPrivilege(SE_BACKUP_NAME, TRUE);

    if (hr != S_OK)

       printf("nThe necessary SE_BACKUP_NAME privilege couldn't be enabled (no admin rights?).");

    if (RegOpenKeyEx(HKEY_CURRENT_USER, TEXT("Control PanelDesktop"), 0, KEY_ALL_ACCESS, &hKey)==ERROR_SUCCESS && RegSaveKeyEx(hKey, TEXT("C:dump.txt"), NULL, REG_LATEST_FORMAT)==ERROR_SUCCESS)

       printf("nSuccessfully dumped the contents of the specified hive.");

    RegCloseKey(hKey);

    Also, make sure that the output file does not exist already because our code doesn’t overwrite it. This is important; if you are playing around and have trouble figuring out why the file doesn’t update, this is why. You may implement a workaround but that’s not the point of our tutorial. Let’s stick with the topic.

    Below you can see our ModifyPrivilege() function. In the above code snippet we call this function for the SE_BACKUP_NAME and TRUE parameters. The function returns either an S_OK on success or ERROR_FUNCTION_FAILED in case of errors. But for the purpose of this tutorial I’ve added error handling after each step. Check it out!

    HRESULT ModifyPrivilege(LPCTSTR szPrivilege, BOOL bEnable)

    {

       HRESULT hr=S_OK;           // assuming success

       TOKEN_PRIVILEGES NewTokenPrivileges;

       LUID luid;

       HANDLE hToken=NULL;

       // we open the processtoken of the current process

       if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken))

       {

           printf("OpenProcessToken - Fail!n");

           return ERROR_FUNCTION_FAILED;

       }

       printf("OpenProcessToken - Success!n");

       // we lookup the local unique ID for the required privilege

       if (!LookupPrivilegeValue(NULL, szPrivilege, &luid))

       {

           CloseHandle(hToken);

           printf("LookupPrivilegeValue - Fail!n");

           return ERROR_FUNCTION_FAILED;

       }

       printf("LookupPrivilegeValue - Success!n");

       // we assign the values to the new token privileges struct

       NewTokenPrivileges.PrivilegeCount=1;

       NewTokenPrivileges.Privileges[0].Luid=luid;

       NewTokenPrivileges.Privileges[0].Attributes=(bEnable ? SE_PRIVILEGE_ENABLED : 0);

       // we overwrite the current token privileges with the new ones

       if (!AdjustTokenPrivileges(hToken, FALSE, &NewTokenPrivileges, 0, NULL, NULL))

       {

           CloseHandle(hToken);

           printf("AdjustTokenPrivileges - Fail!n");

           printf("nError: %un", GetLastError());

           return ERROR_FUNCTION_FAILED;

       }

       printf("AdjustTokenPrivileges - Success!n");

       CloseHandle(hToken);

       return hr;

    }

    This implementation is from Microsoft’s MSDN Library. The original source of the algorithm and code is here. I’ve slightly adjusted it to fit our purposes and managed its error handling and clarity so that it’s easier to understand the way it works. However, it's worth checking out the original MSDN article too.

    Now let’s explain how it works. We declare a few necessary variables and assume success (our hr variable gets S_OK). We proceed to open the process token of our current process using the OpenProcessToken() function. We have a handle which will point to our required token. With the help of GetCurrentProcess() we’ll find out its token. After we successfully open the token of our process we look up the ID (unique and local) for the specified privilege (which in our case is SE_BACKUP_NAME).

    Once we’ve done this too, we notify the user that we arrived at this point, and we start to build our NewState token_privileges struct. It’s going to contain only one privilege (thus Count = 1), Luid stands for its local unique ID, and the attribute for the privilege is of course the boolean fEnable parameter of our function. In our case we’ll call it for TRUE so we create our NewState struct specifying TRUE for our privilege.

    After this we have two more things left to do. One is to actually adjust the token privileges for our token using the AdjustTokenPrivileges() function. Don’t forget that we’ve already opened our token and we have a handle (hToken) that points to it. So we just call it for our NewState struct. Error handling is also included. Finally, we need to close our handle for the token of our process and then return the results.

    I truly hope that my above explanations and the comments in the block of code above helped you to understand and comprehend the algorithm and its implementation. But if you couldn’t follow along, have no fear because you can download the source code of the entire project that we created during this tutorial in archived format (ZIP).

    More Windows Scripting Articles
    More By Barzan "Tony" Antal


       · Thanks for reading this article tutorial. I hope you've found it...
     

    WINDOWS SCRIPTING ARTICLES

    - Understanding Procedures in VBScript
    - Printing Documents in WSH
    - Generating Outlook Signatures Based on Activ...
    - VBScript: Converting and Formatting with Fun...
    - VBScript: Conversion and Format Functions
    - VBScript: Array Functions
    - VBScript: Strings, You Can`t Function withou...
    - VBScript: More String Functions
    - VBScript: Functioning with Strings
    - Working with the Windows Registry in C++
    - Understanding Objects
    - HTML Applications: Giving WSH a User Interfa...
    - Modifying Computer Objects with Active Direc...
    - Logon Script to Send Email Notifications
    - Securing Computers and Active Directory





    © 2003-2008 by Developer Shed. All rights reserved. DS Cluster 5 hosted by Hostway