Platinum Edition Using Visual Basic 5

Previous chapterNext chapterContents


- 45 -
Accessing the Windows Registry and INI Files

Learn about the contents of INI files and the Windows 95 Registry.
Use the Windows 95 API to access data that is stored in INI files.
Use native Visual Basic 5.0 commands to access the data stored in the Windows 95 Registry.
Use the Windows 95 API to access the data stored in the Windows 95 Registry.

The Windows 95 Registry and INI files are just two of the key elements within the Windows 95 operating system. Windows 95 as well as many other Windows based application make extensive use of INI files and the Registry. Since these two elements play such an important role in the system, your Visual Basic application will, from time to time need to either read the information stored in one of these sources of information or, need to update information stored in either of these locations.

There are various methods that can be used in order to access information stored in INI files, and the Windows 95 Registry. These access methods consist of native Visual Basic 5.0 funcation, as well as functions that are provided as part of the Windows 95 API.

In this chapter you look at both the structure of INI files, and the Registry, as well as the various methods that can be used in order to both read and update the information storedin these two within Windows 95.

Introducing INI Files and the Windows Registry

This section covers the following topics:

What INI Files Are

INI files, or Windows Initialization files, are holdovers from the days of 16-bit Windows. There are two types of INI files, system INI files, such as the WIN.INI file--primarily used by Windows 95--and private INI files, which are used by applications other than Windows 95.

An initialization file is a text-format file that is used to store an application's parameters or any additional information the application might need at run time. An example of this is the local date format.


NOTE: The discussion of INI files might seem inappropriate because this book covers Visual Basic 5.0, which is strictly a 32-bit application, and 32-bit applications primarily use the Registry.

You might find that it is easy to store application-based parameters in an INI file format while you are developing an application because they can quickly be changed using any text editor. Some applications make use of a mix of INI settings, as well as Registry settings. A good example of this is Windows 95 itself. Windows 95 stores the majority of its application-specific information in the Registry, but it still makes use of the SYSTEM.INI file, as well as assorted other INI files, to store additional information.

Under Windows NT, most of the contents of the WIN.INI file are mapped directly to the Registry. Therefore, if you update or query any of the sections of the WIN.INI file, you will be reading and writing directly to the Registry. You can modify the contents of INI files using any text editor or the Windows 95 API. Later in this chapter, in the section "INI Files and the Windows API," you learn how to access INI files with the Windows 95 API.

The Structure of INI Files

All INI files have the same standard structure, which is made up of the following elements:

Listing 45.1 illustrates the contents of a VB5.ini file.


NOTE: The contents of your VB5.ini file might be different from that in the listing, depending on the options that you have installed.

Listing 45.1 VB5.INI--The Contents of the VB5.ini File

[VBX Conversions32]
threed.vbx={0BA686C6-F7D3-101A-993E-0000C0EF6F5E}#2.0#0; C:\Sheridan\ActiveThreed\Threed20.ocx
[Add-Ins32]
RoseAddInMenues.Connector=1

As you can see from Listing 45.1, the VB5.ini contains two sections. The first section contains VBX conversion items (in this example, there is only one item that will be converted automatically). The second section contains information about 32-bit add-ins. There is additional add-in information stored in the VBADDIN.ini file.

See "Editing the VBADDIN.INI File," Chapter 43

What the Registry Is

The Registry has been a part of Windows since Windows version 3.1. Originally, the Registry was used to store information on how an application would open and print a file. With the advent of Windows 95 (with its multiple hardware and user profiles), a method of storing information was required. Due to limitation in the INI file architecture, Microsoft elected to use the Registry. The Registry is used to store hardware, user profile, and software configuration information.

The contents of the Registry are physically stored in two files: System.dat and User.dat. The System.dat file, which is located in the WINDOWS directory, contains the hardware and software configuration of the system. The User.dat file is located in the WINDOWS directory. There is one User.dat file for each user that has access to the system. The User.dat file contains user-specific information, pertaining to the user's preferences, as well as any user-specific security and application setup.

To accommodate the variety of information that needs to be stored in the Registry, provisions have been made to store various formats of data. Table 45.1 illustrates the various data formats stored in the Registry.

Table 45.1 Formats of Data Stored in the Registry

Data Type Description
REG_BINARY Binary Data
REG_DWORD Long Data Type
REG_DWORD_BIGENDIAN Long Data Type
REG_DWORD_LITTLE_ENDIAN Long Data Type
REG_EXPAND_SZ Compressed Environment String
REG_LINK Symbolic Link
REG_MULTI_SZ List of Strings separated by Null characters
REG_NONE Undefined Data type
REG_RESOURCE_LIST Device driver Resource list
REG_SC String bate type terminated by a null character

Detailed Description of Windows 95 API Registry Manipulation Functions

To access information that is stored in the Registry, you can use the Microsoft-supplied application Regedit. To access Regedit, choose Start, Run. Type regedit in the Open box and then press Enter.


NOTE: All of the items in the Data Type column are also available as Constants. See the sample in the section "Detailed Description of Windows 95 API Registry Manipulation Functions" for their definitions.

Figure 45.1 shows the top level view of the Registry as it is seen in the Regedit application.

Structure of the Registry

The Registry, much like INI files, is divided into many sections. In the Registry, these sections are referred to as keys. Each key contains related subkeys and values. The Registry contains two major keys and four minor keys containing data that is derived from the two major keys.

Major Registry Keys: HKEY_LOCAL_MACHINE

HKEY_USERS

Minor Registry Keys: HKEY_CLASSES_ROOT

HKEY_CURRENT_USER

HKEY_CURRENT_CONFIG

HKEY_DYN_DATA

FIG. 45.1
This top level view of the Registry shows all of the major Registry keys seen through the Regedit application.

The following portions of this chapter describe these Registry sections. You might also want to consult Que's Windows 95 Registry and Configuration Handbook, Second Edition, for even more coverage of the Windows 95 Registry.

Major Registry Keys

HKEY_LOCAL_MACHINE

The HKEY_LOCAL_MACHINE section of the Registry contains all of the Registry values that relate to the hardware and software configuration of the computer.

HKEY_USERS

The HKEY_USERS section of the Registry contains the default windows settings for all new users of the current systems. When a new user is initially created, the registry settings contained in the HKEY_USERS section will be used in order to determine the initial Windows 95 settings.

Minor Registry Keys

HKEY_CLASSES_ROOT

The HKEY_CLASSES_ROOT section of the Registry contains a duplicate of the information that is stored in the Software\Classes section of the HKEY_LOCAL_MACHINE section of the Registry.

Figure 45.2 illustrates the setting for the VBP type of files.

FIG. 45.2
This is the Visual Basic Association section of the Registry, as viewed through Regedit. The currently opened key displays the Open Visual Basic Project Registry Entry.

HKEY_CURRENT_USER

The HKEY_CURENT_USER section of the Registry contains all of the Windows and software settings for the user currently signed onto the system. Figure 45.3 illustrates various keys stored in the HKEY_CURRENT_USER section.

FIG. 45.3
These are the keys contained in the HKEY_CURRENT_USER section of the Registry.

HKEY_CURRENT_CONFIG

The HKEY_CURRENT_CONFIG section of the Registry contains all of the Registry information relating to the current configuration of Windows 95. The section is rebuilt every time Windows 95 is restarted.

HKEY_DYN_DATA

The HKEY_DYN_DATA section of the Registry contains information relating to currently running device drivers. This section is rebuilt every time Windows 95 is restarted.

INI Files and the Windows API

You can most easily and quickly access the data stored in INI files by using the Windows 95 API. The Windows 95 API provides functions with which you can read and update data from INI files. In this section, you learn about the various Windows 95 API functions that you can use to access INI files. You also learn to create a sample application to edit the contents of INI files.

Introduction to Windows 95 INI Manipulation Functions

In this section you learn how to use the various API functions contained in the Windows 95 API to edit and update INI files.

As mentioned previously, there are two different types of INI files--system INI (WIN.INI) files and private or application INI files. Therefore, there are two sets of similar Windows 95 API functions--one set for system files and another for private files.


NOTE: You can use the private INI functions to open system INI files.

Table 45.2 lists the various Windows 95 API functions that are available and gives a brief description of each function.

Table 45.2 Available Windows API Functions

API Function Description
GetProfileString Retrieves a string value from a named key in the WIN.INI file
GetProfileSection Retrieves all of the values stored in a named section of the WIN.INI file
GetProfileInt Retrieves an Integer value from a named key in the WIN.INI file
GetPrivateProfileString Retrieves a string value from a named key contained in a private INI file
GetPrivateProfileSection Retrieves all of the values stored in a named section of a private INI file
GetPrivateProfileInt Retrieves an Integer value of a named key contained in a private INI file
WriteProfileString Updates the value of a named key contained in the WIN.INI file (If the key did not previously exist, it is created.)
WriteProfileSection Updates a complete section contained in the WIN.INI file (If the section or any of the values did not previously exist, they are created.)
WritePrivateProfileString Updates the value of a named key contained in a private INI file (If the key did not previously exist, it is created.)
WritePrivateProfileSection Updates a complete section contained in a private INI file (If the section or any of the values did not previously exist, they are created.)

The description of both the Windows 95 API calls and the parameters needed for each function is discussed in the following section.

Detailed Description of Windows 95 API INI Manipulation Functions

In this section, you learn about the various Windows 95 API functions that you can use to manipulate INI files. In the final part of this section, you learn how to create a small application that can be used as a generic INI file editor.

The GetProfileString Function The declaration that must be included in your Visual Basic application for the GetProfileString function is:

Declare Function GetProfileString Lib "kernel32" Alias _
"GetProfileStringA" (ByVal lpAppName As_ String, _
ByVal lpKeyName As String, ByVal lpDefault As String, _
 ByVal lpReturnedString As String, _ bevel nSize As Long) _
As Long

The GetProfileString function requires the use of the following parameters:

Parameter Description
lpAppName The section in the INI file that contains the key that you want to obtain the value for
lpKeyName The name of the key whose value you want to retrieve
lpDefault The default value to be returned to your program if neither the section of the INI file nor the key is found
lpReturnedString The variable that is used to store the value retrieved by the API call (If this value is Null, the value defined in lpDefault is used.)
nSize The maximum number of characters to retrieve from the INI file

The GetProfileString function returns a Long value indicating the number of bytes that have been read.

The GetProfileSection Function The declaration that must be included in your Visual Basic application for the GetProfileSection function is:

Declare Function GetProfileSection Lib "kernel32" Alias _
"GetProfileSectionA" _(ByVal lpAppName As String, _
ByVal lpReturnedString As String, ByVal nSize As Long) _
 As Long

The GetProfileSection function requires the use of the following parameters:
Parameter Description
lpAppName The section in the INI file of which you want to obtain the contents.
lpReturnedString The variable that is used to store the value retrieved by the API call. Each key contained in this string is separated by a Null value, and the end of the string is marked by two Null values.
nSize The maximum number of characters to retrieve from the INI file.

The GetProfileSection function returns a Long value indicating the number of bytes that have been read.

GetProfileInt Function The declaration that must be included in your Visual Basic application for the GetProfileInt function is:

Declare Function GetProfileInt Lib "kernel32" Alias _
"GetProfileIntA" (ByVal lpAppName As String, _
ByVal lpKeyName As String, _
ByVal nDefault As Long) As Long

The GetProfileInt function requires the use of the following parameters:
Parameter Description
lpAppName The section in the INI file that contains the key you want to obtain the value for
lpKeyName The name of the key whose value you want to retrieve
nDefault The default value to be returned to your program if neither the section of the INI file nor the key is found

The GetProfileInt function returns a Long value containing the value that was retrieved by the API function.

The GetPrivateProfileString Function The declaration that must be included in your Visual Basic application for the GetPrivateProfileString function is:

Declare Function GetPrivateProfileString Lib "kernel32" Alias _
"GetPrivateProfileStringA" (ByVal lpApplicationName _
 As String, _ByVal lpKeyName As String, ByVal lpDefault As String, _
 ByVal lpReturnedString _As String, ByVal nSize As Long, _
 ByVal lpFileName As String) As Long

The GetPrivateProfileString function requires the use of the following parameters:

Parameter Description
lpApplicationName The section in the INI file that contains the key for which you want to obtain the value
lpKeyName The name of the key whose value you want to retrieve
lpDefault The default value to be returned to your program if neither the section of the INI file nor key is found
lpReturnedString The variable that is used to store the value retrieved by the API call (If this value is Null, the value defined in lpDefault is used.)
nSize The maximum number of characters to retrieve from the INI file
lpFilename The name and location of the INI file from which you want to retrieve information

The GetPrivateProfileString function returns a Long value that indicates the number of bytes that have been read.

The GetPrivateProfileSection Function The declaration that must be included in your Visual Basic application for the GetPrivateProfileSection function is:

Declare Function GetPrivateProfileSection Lib "kernel32" Alias _
"GetPrivateProfileSectionA" _(ByVal lpAppName As String, _
 ByVal lpReturnedString As String, ByVal nSize As Long, _
 ByVal lpFileName As String) As Long

The GetPrivateProfileSection function requires the use of the following parameters:

Parameter Description
lpAppName The section in the INI file that contains the key for which you want to obtain the value.
lpReturnedString The variable that is used to store the value retrieved by the API call. Each key contained in this string is separated by a Null value, and the end of the string is marked by two Null values.
nSize The maximum number of characters to retrieve from the INI file.
lpFilename The name and location of the INI file from which you want to retrieve information.

The GetPrivateProfileSection function returns a Long value that indicates the number of bytes that have been read.

The GetPrivateProfileInt Function The declaration that must be included in your Visual Basic application for the GetPrivateProfileInt function is:

Declare Function GetPrivateProfileInt Lib "kernel32" Alias _
"GetPrivateProfileIntA" (ByVal lpApplicationName As String, _
 ByVal lpKeyName As String, ByVal nDefault As Long, _
 ByVal lpFileName As String) As Long

The GetPrivateProfileInt function requires the use of the following parameters:

Parameter Description
lpApplicationName The section in the INI file that contains the key for which you want to obtain the value
lpKeyName The name of the key whose value you want to retrieve
nDefault The default value to be returned to your program if neither the section of the INI file nor the key is found
lpFilename The name and location of the INI file from which you want to retrieve information

The GetPrivateProfileInt function returns a Long value containing the value that was retrieved by the API function.


NOTE: In each INI API function, the size of the lpReturnedString variable must be predefined.

Accessing and Updating INI Files Using the Windows 95 API

In this section, you create a small application with which you can read, change, and update the contents of an INI file. After you complete this application, you will have an easy-to-use general purpose INI file editor.

To create the application, perform the following steps:

1. Start Visual Basic and select the option to Open a New Standard EXE project.

2. Choose Project, Components. Add the Microsoft Common Dialog Control to your project by selecting the box next to the name and clicking OK.

3. Choose Project, Add Module to add a standard module to the project.

4. Enter the code contained in Listing 45.2 into the Declarations section of the newly added standard module. This code contains all of the Windows 95 API calls that you will use in the example. Alternatively, you might want to copy the listing from file exam1.bas, which is included on the CD accompanying this book.

Listing 45.2 EXAM1A.BAS--INI File API Declarations that Need to be Placed in Module1

Declare Function GetProfileInt Lib "kernel32" Alias _
 "GetProfileIntA" (ByVal lpAppName As String, _
 ByVal lpKeyName As String, ByVal nDefault As Long) _
 As Long
Declare Function GetProfileSection Lib "kernel32" Alias _
 "GetProfileSectionA" (ByVal lpAppName As_ String, _
ByVal lpReturnedString As String, ByVal nSize As Long) _
 As Long
Declare Function GetProfileString Lib "kernel32" Alias _
 "GetProfileStringA" (ByVal lpAppName As_ String, _
 ByVal lpKeyName As String, ByVal lpDefault As String, _
 ByVal lpReturnedString As String, _ ByVal nSize As Long) _
 As Long
Declare Function GetPrivateProfileInt Lib "kernel32" Alias _
"GetPrivateProfileIntA" (ByVal_ lpApplicationName As String, _
 ByVal lpKeyName As String, ByVal nDefault As Long, _
 ByVal lpFileName_ As String) As Long
Declare Function GetPrivateProfileSection Lib "kernel32" _
 Alias _
 "GetPrivateProfileSectionA" (ByVal_ lpAppName As String, _
ByVal lpReturnedString As String, ByVal nSize As Long, _
ByVal lpFileName As_ String) As Long
Declare Function GetPrivateProfileString Lib "kernel32" _
Alias "GetPrivateProfileStringA" (ByVal_
 lpApplicationName_As String, _
 ByVal lpKeyName As String, ByVal lpDefault As String, _
ByVal_ lpReturnedString As String, ByVal nSize As Long, _
 ByVal lpFileName As String) As Long
Declare Function WritePrivateProfileSection Lib "kernel32" _
 Alias _"WritePrivateProfileSectionA" _ (ByVal lpAppName As String, _
 ByVal lpString As String, ByVal lpFileName As String) As Long
Declare Function WritePrivateProfileString Lib "kernel32" _
 Alias "WritePrivateProfileStringA" _
 (ByVal lpApplicationName As String, ByVal lpKeyName As String, _
 ByVal lpString As String, ByVal lpFileName_ As String) As Long
Declare Function WriteProfileSection Lib "kernel32" Alias _
"WriteProfileSectionA" (ByVal lpAppName_ As String, _
 ByVal lpString As String) As Long
Declare Function WriteProfileString Lib "kernel32" Alias _
 "WriteProfileStringA" (ByVal lpszSection As String, _
 ByVal lpszKeyName As String, ByVal lpszString As String) As Long
5. If no form is contained in the current project, choose Project, Add Form to add a form to the project.

6. Add the following controls to the form (don't worry about their properties because you set them in the next step):

Control

Description

Four Label controls

Two TextBox controls

Two ComboBox controls

Three CommandButton controls

One CommonDialog control

7. Set the following properties for the four Label controls:

Name =  lblValue
Caption  =   Value
Height  =   270
Left  =   270
Top  =  1440
Width  =   1245
Name = lblEntryName
Caption =  Entry Name
Height   =   270
Left  =   240
Top  =   1050
Width  =  1245
Name = lblSection
Caption  =   Section
Height   =   270
Left  =   240
Top  =   660
Width  =   1245
Name = lblIniFile
Caption  =  INI File
Height  =   270
Left  =   240
Top   =   240
Width  =   1245
8. Set the following properties for the two TextBox controls:
Name = txtFileName
Height  =   300
Left =   1560
TabIndex =   0
ToolTipText  =   Enter the Path/Name of the INI file or 
Depress the ""?"" button to Select an INI file
Top  =   240
Width  =   2505
Name = txtValue
Height  =   300
Left  =   1560
TabIndex  =   3
Top  =   1440
Width  =   2505
9. Set the following properties of the two ComboBox controls:
Name = comEntry
Height =   315
Left  =   1590
Style  =   2  `Dropdown List
TabIndex  =   2
ToolTipText =   Selection The Section You Wish to View
Top   =   1020
Width  =   2505
Name = comSection
Height =   315
Left  =   1560
Style =   2  `Dropdown List
TabIndex  =   1
ToolTipText =   Selection The Section You Wish to View
Top  =   630
Width =   2505
10. Set the following properties for the three CommandButton controls:
Name = cmdSave
Caption =   &Save
Height =   300
Left  =   3450
TabIndex =   4
ToolTipText =   Save The Changes
Top =   2910
Width =   700
Name =  cmdSelect
Caption  =   &?
Height  =   315
Left  =   4170
TabIndex =   7
ToolTipText =   Select INI File
Top  =   240
Width  =   345
Name = cmdExit
Caption  =   E&xit
Height =   300
Left  =   4260
TabIndex  =   5
ToolTipText =   Exit the Application
Top =   2910
Width  =   700
11. Set the following properties for the CommonDialog control:
Name = diaexam1
Left =   660
Top  =   2760
CancelError     =   -1  `True
DialogTitle =   Select File to Open
FileName   =   *.ini
Filter  =   Initialization file (*.ini)|*.ini
12. Set the following properties for the form that contains the newly added controls:
Name = exam1a
Caption  =   INI Files Sample 1
Height  =   3345
Width   =   5400
13. Enter the following code in the From_Unload event:
Set frmChp531a = Nothing
14. Enter the following code in the cmdExit_Click event:
Unload Me
15. Enter the following code in the cmdSave_Click event:
Dim nbytes As Long
nbytes = WritePrivateProfileString(comSection.Text, _
 comEntry.Text, txtValue.Text, txtFileName.Text)
16. Enter the following code in the cmdSelect_Click event. This code will be used to retrieve all of the section names contained in the selected INI file. Alternatively, you might want to copy the listing from file exam1a.frm, which is included on the CD accompanying this book.
Dim nBytes As Long
Dim csection As String
Dim cbuffer As String
Dim cstring As String
Dim nfirst As Integer
On Error Resume Next
If Len(txtFileName.Text) = 0 Then
    diaexam1.filename = ""
    diaexam1.ShowOpen
    If Err = cdlCancel Then
        ` the user depressed cancel
        Exit Sub
    End If
    txtFileName.Text = diachp531.filename
End If
comSection.Clear
If Len(txtFileName.Text) = 0 Then
` There has not been a file selected exit
    Exit Sub
End If
If Len(Dir$(txtFileName.Text)) = 0 Then
` invalid file name
    Exit Sub
End If
Open txtFileName.Text For Input As #1
Do While EOF(1) = False
    cstring = Input$(1, #1)
    If cstring = "[" Then
       first = True
        ` Drop the Bracket
        cstring = ""
    End If
    If cstring = "]" Then
        If nfirst = True Then
           If Len(csection) > 0 Then
                `Add it to the selction list
                comSection.AddItem csection
                ` Drop The trailing Bracket
                csection = ""
            End If
           first = False
        End If
      first = False
    End If
    If nfirst = True Then
        csection = csection & cstring
    End If

Loop
comSection.ListIndex = 0
Close #1
On Error GoTo 0
17. Enter the following code in the comEntry_Click event. This code will be used to retrieve the value of the selected INI Key:
Dim nBytes As String
Dim cvalue  As String
` Initialize returned string
`--------------------------
cvalue = Space$(4096)
nBytes = GetPrivateProfileString((comSection.Text), _
 (comEntry.Text), "", cvalue, 4096, txtFileName.Text)
txtValue.Text = cvalue
18. Enter the following code in the comSection_Click event. This code will be used to retrieve all of the entries contained in the selected section on the INI file:
Dim nBytes As Long
Dim cvalues As String * 32767
Dim cbuffer As String
Dim x As Integer
Dim y As Integer
Dim ctext As String
Dim nend As Integer
comEntry.Clear
nBytes = GetPrivateProfileSection((comSection.Text), _
 cvalues, 32767, txtFileName.Text)
` get all of the values
x = 1
y = 0
Do While Not nend = True
    x = InStr(y + 1, cvalues, Chr(0))
    ctext = Mid$(cvalues, y + 1, x - y - 1)
    If Len(ctext) = 0 Then
        Exit Do
    End If
    `
    `Strip off the "=" and value
    comEntry.AddItem Mid$(ctext, 1, InStr(ctext, "=") - 1)
    y = x
Loop
19. Enter the following Code into the txtSelection_LostFocus event. This code will be used to instigate a click of the Select button:
If Len(txtFileName.Text) > 0 Then
    cmdSelect_Click
End If
20. Choose Run, Start or press F5 to run the project.

21. After the project has started, enter the following in the INI File text box: c:\windows\system.ini. When you press Tab, the value in the combo box defaults to Boot. If you select Shell from the Entry Name combo box (providing you are using Explorer as the Shell for Windows 95), Explorer.exe appears in the Value box. If you want to change this (which I do not recommend), enter the new value in the text box and click Save to save the change.

Figure 45.4 illustrates the sample application.

FIG. 45.4
Access INI Files through the Windows API.

You have now seen various aspects of accessing INI files through the use of the Windows 95 API. In the next sections, you learn to access and alter the Windows Registry by using built-in Visual Basic functions.

Using Visual Basic to Access the Windows 95 Registry

In this section, you learn various ways to access and manipulate information that is stored in the Windows 95 Registry. First, you learn how to access the information using built-in Visual Basic commands. Second, you learn how to access information contained in the Windows 95 Registry by using Windows 95 API functions.

Accessing the Registry Through Visual Basic Commands

Visual Basic version 5.0 provides four commands that allow your application to access the Registry. The provided commands do not give you access to all of the data that is stored in the Registry. Instead, you are restricted to items that can be found under the following key:

HKEY_CURRENT_USER\Software\VB and VBA Program Settings

Figure 45.5 displays the contents of this key. While this protects the programmer from working havoc on the Registry, it is also very restrictive. If your application needs to access other information that is stored in the Registry, then you will have to use Windows 95 API calls as discussed later in the section "The Registry and the Windows 95 API."

Table 45.3 lists all of the Registry-related functions that are available in Visual Basic 5.0, as well as a brief description of each function.

Table 45.3 Registry Functions Available in Visual Basic 5.0

Visual Basic Function Description
DeleteSetting Allows you to delete a Registry setting as well as the Registry key
GetSetting Allows you to retrieve the value of a specified Registry key
GetAllSettings Allows you to retrieve all of the Registry keys and their settings for a specified application
SaveSetting Allows you to save a key and its value to the Registry (If the key did not previously exist, it is created.)

FIG. 45.5
This Registry section is available to Visual Basic functions.

A further description of the Visual Basic functions, as well as examples of their use, is discussed in the following section.

Detailed Description of Visual Basic Registry Manipulation Functions

In this section, you see the various parameters for the functions discussed in the preceding section, as well as their use in the Visual Basic Registry manipulation functions.

The DeleteSetting Function The DeleteSetting function uses the following syntax:

DeleteSetting capplication, csection,Key

The DeleteSetting function requires the use of the following parameters:

Parameter Description
capplication This string setting, which is contained in the upper key of the applications setting, is one that you would like to delete. (This value must be supplied.)
csection This string setting contains the section of the Registry that contains the key that you want to delete. (This value must be supplied.)
Key This optional parameter contains the name of the key that you want to delete. If this parameter is left empty, all of the keys in the named section are deleted.

If the named section or key does not exist, the DeleteSetting function takes no action, nor does it return an error.

The following example deletes the View option settings of the API Viewer application from the Windows 95 Registry (refer to Figure 45.5):

DeleteSetting "API Viewer, "Options","View"

GetSetting Function The GetSetting function uses the following syntax:

GetSetting capplication, csection, key, cDefault

The GetSetting function requires the use of the following parameters:

Parameter Description
capplication This string setting contains the upper key of the applications setting that you would like to retrieve. (This value must be supplied.)
csection This string setting contains the section of the Registry that contains the key you want to retrieve. (This value must be supplied.)
key This string setting contains the name of the key whose value you want to retrieve. (This value must be supplied.)
cDefault This parameter is used to supply your application with a default value if the key in the specified section does not exist. (This value is optional.)

The GetSetting function returns a Variant value containing the value of the key; if the key is not found, the cDefault value is returned.

The following example retrieves the values of the View Registry entry used by the API Viewer (refer to Figure 45.5). If the Value had been deleted, as illustrated in the previous example, the function would return a Null String.

vValue= GetSetting("API Viewer, "Options","View","")

The GetAllSettings Function The GetAllSettings function uses the following syntax:

GetAllSettings capplication, csection

The GetAllSettings function requires the use of the following parameters:
Parameter Description
capplication This string value contains the upper key of the applications setting that you would like to retrieve. This value must be supplied.
csection This string setting contains the name of the section of the Registry whose values you want to retrieve. This value must be supplied.

The GetAllSettings function returns a two-dimensional array of Variant values. This array contains the keys as well as the values from the named section of the Registry.

The following example retrieves all of the View options of the API Viewer Registry setting (refer to Figure 45.5). If the value is not found, the function returns a Null Variant value.

vValue= GetAllSettings("API Viewer, "Options")

Accessing and Updating the Registry Using Visual Basic Functions

In this section, you learn how to create a small application that reads, changes, and updates the contents of the Windows 95 Registry. This example accesses the information that pertains to add-ins available on your system. In addition, the application will save and restore its own setting regarding the size and position of the main form.


NOTE: The add-ins are hard-coded in the Form_Load event. The three most common entries have been selected , but your system might have different values. If you want to double check what your system's values are, use the Windows-supplied Regedit program to manually check the Registry entries on your system and update the Form_Load procedure appropriately.



NOTE: Prior to altering any of the data stored in the Windows 95 Registry, perform a backup of the information contained in the Registry. You can back up the Registry by choosing Registry, Export Registry when using the Regedit application.

To create the application, perform the following steps:

1. Start Visual Basic and select the option to Open a New Standard EXE project.

2. If no form is contained in the current project, choose Project, Add Form to add a form to the project.

3. Add the following controls to the form; don't change any of their properties as you will set them in the next step:

Control

Description

Three Label controls

One TextBox control

One ComboBox control

Three CommandButton controls

One ListBox control

4. Set the following properties for the three Label controls:

Name = lblKeyValue
Alignment =   1  `Right Justify
Caption =   Key Value
Height  =   195
Left  =   510
Top =   2130
Width =   1275
Name = lblKeys
Alignment =   1  `Right Justify
Caption =   Keys
Height  =   195
Left =   510
Top  =   810
Width =   1275
Name = lblAddin
Alignment =   1  `Right Justify
Caption  =   Add in
Height  =   195
Left =   510
TabIndex =   5
Top =   360
Width  =   1275
5. Set the following properties for the TextBox control:
Name = txtValue
Alignment =   1  `Right Justify
Height =   300
Left =   1920
TabIndex  =   2
ToolTipText  =   Alter the Value of the Key if it is Incorrect
Top   =   2100
Width =   2475
6. Set the following properties for the ComboBox control:
Name = comAddin
Height =   315
Left  =   1950
Style =   2  `Dropdown List
TabIndex =   0
ToolTipText =   Select The Addin You Would like 
Additional Information About
Top =   360
Width =   2445
7. Set the following properties for the three CommandButton controls:
Caption =   &Delete
Height =   345
Left =   1800
TabIndex  =   5
ToolTipText =   Delete the Key
Top =   2610
Width =   855
Name = cmdSave
Caption =   &Save
Height =   345
Left =   2700
TabIndex  =   4
ToolTipText =   Save The Changes
Top =   2610
Width =   855
Name =  cmdExit
Caption =   E&xit
Height Name =  cmdDelete
=   345
Left =   3600
TabIndex  =   3
ToolTipText =   Exit the Application
Top =   2610
Width =   855
8. Set the following properties for the ListBox control:
Name =  lstKeys
Height =   1230
Left =   1920
TabIndex =   1
ToolTipText =   Select the Key to Retrieve the Setting for
Top =   780
Width  =   2505
9. Set the following properties for the form containing the newly added controls:
Name = frmChp532
Caption  =   Chapter 53 Sample 2
Height  =   3465
Width   =   4500
10. Enter the following code in the Form_Load event. This code adds three items in the ComboBox and accesses the Registry to retrieve the application's form placement settings. (If the settings are not found, the design time values will be used):
` Set up the ComboBox with Known Data
comAddin.AddItem "VBAddinToolbar"
comAddin.AddItem "VisData"
comAddin.AddItem "VisualComponentManager"
comAddin.ListIndex = 0
If Len(GetSetting("exam2", "Position", "top")) <> 0 Then
     Me.Top = GetSetting("exam2", "Position", "top")
End If
If Len(GetSetting("exam2", "Position", "left")) <> 0 Then
     Me.Left = GetSetting("exam2", "Position", "left")
End If
If Len(GetSetting("exam2", "Position", "width")) <> 0 Then
     Me.Width = GetSetting("exam2", "Position", "width")
 End If
If Len(GetSetting("exam2", "Position", "Height")) <> 0 Then
     Me.Height = GetSetting("exam2", "Position", "Height")
End If
11. Enter the following code in the Form_Unload event:
Set exam2 = Nothing
12. Enter the following code in the cmdDelete_Click event. This code will delete the application's Registry values for the Key specified in the ComboBox:
DeleteSetting "Microsoft Visual Basic Addins", comAddin.Text, _
 lstkeys.Text
13. Enter the following code in the cmdExit_Click event. This code saves the form's current position and size in the Windows 95 Registry:
SaveSetting "exam2", "Position", "top", Me.Top
SaveSetting "exam2", "Position", "left", Me.Left
SaveSetting "exam2", "Position", "height", Me.Height
SaveSetting "exam2", "Position", "width", Me.Width
Unload Me
14. Enter the following code in the cmdSave_Click event. This code updates the value of the data stored for the Key (which has been selected in the Key ListBox) to the value the has been entered in the Key Value TextBox:
SaveSetting "Microsoft Visual Basic Addins", _
 comAddin.Text, _lstkeys.Text, txtValue.Text
15. Enter the following code in the comAddin_Click event. This code retrieves all of the Keys that are stored under the Add-in, which was selected in the ComboBox:
Dim vValues As Variant
Dim nCount As Integer
vValues = GetAllSettings("Microsoft_
 Visual Basic Addins", comAddin.Text)
For nCount = LBound(vValues, 1) To UBound(vValues, 1)
    lstkeys.AddItem vValues(nCount, 0)
Next nCount
16. Enter the following code in the lstKeys_Click event. This code will retrieve the value of the Key that has been selected in the Keys ListBox:
txtValue.Text = GetSetting("Microsoft Visual_
 Basic Addins", comAddin.Text, lstkeys.Text)
17. Choose Run, Start or press F5 to run the project.

After the Project is started, you should have a form on your display similar to that illustrated in Figure 45.6.

FIG. 45.6
Here is the Sample Registry Viewer Application.

If you select any of the items in the Keys list box, its Registry value is displayed in the Key Value text box. If you want to change the value in the text box, type in a new value and then click Save to update the value in the Registry. If you click the Delete button, the information is removed from the Registry.

After you have clicked the Exit button, start the Regedit program and open the following keys:

HKEY_CURRENT_USERS\Software\VB AND VBA Program Setting\exam2\Position

You should then see Registry settings similar to those illustrated in Figure 45.7. These settings represent the position and size of the form in the project when the Exit button is pressed. If you resize the form or move it prior to pressing Exit, the new settings are saved. The form will be restored to these settings the next time the project is run.

In this section, you have learned various aspects of accessing the Windows 95 Registry through the use of Visual Basic's built-in function. Although you only have limited access to the Registry, this is probably enough for most uses. The next section discusses accessing the Registry through the Windows 95 API, where there are very few, if any, limitations.

Windows 95 API Registry Functions

In this section, you create a small application that can be used to read, change, and update the contents of the Windows 95 Registry. This application will use the Windows 95 API function calls to access and update the information stored in the Windows 95 Registry. Once this application is complete, you can use it as a substitute for the Microsoft-supplied Regedit program.

FIG. 45.7
The Registry settings containing the sample forms position information.

Accessing the Registry Using the Windows 95 API

While Visual Basic provides four commands that allow your application to access the Registry, the Windows 95 API provides more than 20 functions. The Windows 95 API gives you full access to all of the keys and to the values of the data stored in the Registry. The commands that are provided allow you access to all of the data that is stored in the Registry.


NOTE: Unlike most Windows API functions, the Registry-related functions are not stored in one of the major Windows libraries (such as Kernel32). Instead, the Registry functions are contained in the advapi32.dll. This library, which is known as the Advanced API services library, contains all of the Registry as well as security Windows 95 API functions.

Table 45.4 lists all of the Windows API Registry-related functions, as well as brief descriptions of each.

Table 45.4 Windows API Registry-Related Functions

Function Description
RegCloseKey Closes a Registry key that has previously been opened by another API function. You must always close the Registry key when you are finished with it.
RegConnectRegistry Allows you to access a certain part of the Registry that is stored on a connected computer.
RegCreateKey/RegCreateKeyEx Allow you to create a new key in the Registry. If a key with the same attributes already exists, that key is opened. The RegCreateKeyEx function allows you to provide additional security information that can be placed on the Registry entry.
RegDeleteKey Deletes a specified Registry key and its associated value.
RegDeleteValue Deletes the value of the specified Registry key entry.
RegEnumKey/RegEnumKeyEx Allow you to step through the name of each subkey located under a specified key.
RegEnumValue Allows you to step through the values of each subkey located under a specified key.
RegFlushKey Forces an immediate write of information to the Registry.
RegLoadKey Loads the Registry information from a file that was previously created using the RegSaveKey.
RegNotifyChangeKeyValue Allows your application to monitor a Registry key and receive notification when that key has been changed.
RegOpenKey/RegOpenKeyEx Open a specified key. RegOpenKeyEx also opens a key but has additional security parameters.
RegQueryInfoKey Allows your application to obtain information about the key.
RegQueryValue/RegQueryValueEx Retrieve the default value for the key. The RegQueryValueEx also retrieves the security information of the key.
RegReplaceKey Replaces Registry information from a disk file. In addition, the RegReplaceKey creates a backup file of the information that has been replaced.
RegRestoreKey Restores Registry information from a file, which was created by the RegReplaceKey function.
RegSaveKey Saves a Registry key as well as all of its subkeys to a disk file. This file can later be used by the RegLoadKey function.
RegSetValue/RegSetValueEx Change the value of a specific key.
RegUnLoadKey Closes and removes from memory a key previously opened with the RegLoadKey function.

A detailed description of the Windows 95 API Registry functions will be provided later in this section. The next section details the various Constants that are used by the Windows 95 API Registry function.

Detailed Description of Windows 95 API Registry Manipulation Functions

This section discusses the usage of the various parameters of the Windows 95 API Registry manipulation functions.

When accessing the Registry through the Windows API, you must use certain predefined constants to represent the different branches of the Registry.

Table 45.5 lists the constants and their values.

Table 45.5 Registry Key Constants

Constant Value
HKEY_CLASSES_ROOT &H80000000
HKEY_CURRENT_CONFIG &H80000005
HKEY_CURRENT_USER &H80000001
HKEY_DYN_DATA &H80000006
HKEY_LOCAL_MACHINE &H80000002
HKEY_PERFORMANCE_DATA &H80000004
HKEY_USERS &H80000003

When creating keys in the Registry, specify the type of operations that will be allowed on the key. Table 45.6 lists all of the operations constants and their values.

Table 45.6 Key Creation Constants

Constant Value
KEY_CREATE_LINK &H20
KEY_CREATE_SUB_KEY &H4
KEY_EVENT &H1
KEY_NOTIFY &H10
KEY_QUERY_VALUE &H1
KEY_ALL_ACCESS &H3F
KEY_SET_VALUE &H2

The next section will take a closer look at the Windows 95 API Registry functions.

The RegCloseKey Function The declaration that must be included in your Visual Basic application for the RegCloseKey function is:

Declare Function RegCloseKey Lib "advapi32.dll" _
(ByVal hKey As Long) As Long

The RegCloseKey function requires the use of the following parameter:

hkey The Long integer that was returned by the RegOpenKey/RegOpenKeyEx function

The RegCloseKey function returns a Long value of 0 if the function was successful; any other values should be treated as error code.

The RegConnectRegistry Function The declaration that must be included in your Visual Basic application for the RegConnectRegistry function is:

Declare Function RegConnectRegistry Lib "advapi32.dll" _
 Alias "RegConnectRegistryA" (ByVal lpMachineName As String, _
 ByVal hKey As Long, phkResult As Long) As Long

The RegConnectRegistry function requires the use of the following parameters:

Parameter Description
lpMachineName The name of the computer whose Registry you want to access.
hkey The name of the key to open (can only be HKEY_LOCAL_MACHINE or HKEY_USERS).
phkResult If the function completes successfully, phkResult contains the handle to the specified key.

The RegConnectRegistry returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegCreateKey Function The declaration that must be included in your Visual Basic application for the RegCreateKey function is:

Declare Function RegCreateKey Lib "advapi32.dll" Alias _
 "RegCreateKeyA" (ByVal hKey As Long, ByVal lpSubKey As String, _
 phkResult As Long) As Long

The RegCreateKey function requires the use of the following parameters:

Parameter Description
hkey The root key under which to create the new key (refer to Table 45.5 for the valid constants).
lpSubKey The name of the new subkey to create.
phkResult If the function completes successfully, phkResult will contain the handle to the new key.

The RegCreateKey returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegCreateKeyEx Function The declaration that must be included in your Visual Basic application for the RegCreateKeyEx function is:

Declare Function RegCreateKeyEx Lib "advapi32.dll" _
Alias "RegCreateKeyExA" (ByVal hKey As Long, _
 ByVal lpSubKey As String, ByVal Reserved As Long, _
 ByVal lpClass As String, ByVal dwOptions As Long, _
 ByVal samDesired As Long, _
 lpSecurityAttributes As SECURITY_ATTRIBUTES, _
 phkResult As Long, lpdwDisposition As Long) As Long

The RegCreateKeyEx function requires the use of the following parameters:

Parameter Description
hKey The root key under which to create the new key (refer to Table 45.5 for the valid constants).
lpSubKey The name of the new subkey to create.
Reserved Not used. Set to 0.
lpClass The class of the new key (generally set to Null).
dwOptions The value of this parameter must be 0; any other value causes the key to be unavailable after the computer system is restarted.
samDesired A key access constant (refer to Table 45.6 for valid constants).
lpSecurityAttributes A structure defining the key security. Not applicable under Windows 95.
phkResult If the function completes successfully, phkResult will contain the handle to the new key.
lpdwDisposition The value of this parameter indicates whether a new key should be created or an existing key should be opened. Use one of the following two constants: REG_CREATED_NEW_KEY = &H1 REG_OPENED_EXISTING_KEY = &H2

The RegCreateKeyEx returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegDeleteKey Function The declaration that must be included in your Visual Basic application for the RegDeleteKey function is:

Declare Function RegDeleteKey Lib "advapi32.dll" Alias _
"RegDeleteKeyA" (ByVal hKey As Long, ByVal lpSubKey As String) _
 As Long

The RegDeleteKey function requires the use of the following parameters:

hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).
lpSubKey The name of the subkey to delete. All keys and their values located under this subkey are deleted.

The RegDeleteKey returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegDeleteValue Function The declaration that must be included in your Visual Basic application for the RegDeleteKey function is:

Declare Function RegDeleteValue Lib "advapi32.dll" Alias _
 "RegDeleteValueA" (ByVal hKey As Long, _
 ByVal lpValueName As String) As Long

The RegDeleteValue function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).
lpValueName The section of the key to delete (setting parameter to Null causes all values to be deleted).

The RegDeleteValue returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegEnumKey Function The declaration that must be included in your Visual Basic application for the RegEnum function is:

Declare Function RegEnumKey Lib "advapi32.dll" Alias _
 "RegEnumKeyA" (ByVal hKey As Long, ByVal dwIndex As Long, _
 ByVal lpName As String, ByVal cbName As Long) As Long

The RegEnumKey function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants)
dwIndex The index of the subkey that you want to retrieve
lpName The function retrieves the name of the key to this variable
cbName The size of the lpName variable

The RegEnumKey returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegEnumKeyEx Function The declaration that must be included in your Visual Basic application for the RegEnumKeyEx function is:

Declare Function RegEnumKeyEx Lib "advapi32.dll" Alias _
"RegEnumKeyExA" (ByVal hKey As Long, ByVal dwIndex As Long, _
 ByVal lpName As String, lpcbName As Long, lpReserved As Long, _
 ByVal lpClass As String, lpcbClass As Long, _
 lpftLastWriteTime As FILETIME) As Long

The RegEnumKeyEx function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).
dwindex The index of the subkey that you want to retrieve.
lpName The function retrieves the name of the key to this variable.
lpcbName The size of the lpName variable.
lpReserved Not used. Set to 0.
lpClass A string used to identify the class of the key (can be set to Null).
lpcbClass The size of the lpClass variable.
lpftLastWriteTime The time and date the Registry entry was last modified.

The RegEnumKeyEx returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegEnumValue Function The declaration that must be included in your Visual Basic application for the RegEnumValue function is:

Declare Function RegEnumValue Lib "advapi32.dll" Alias _
"RegEnumValueA" (ByVal hKey As Long, ByVal dwIndex As Long, _
 ByVal lpValueName As String, lpcbValueName As Long,
lpReserved As Long, lpType As Long, lpData As Byte, _
 lpcbData As Long) As Long

The RegEnumValue function requires the use of the following parameters:

hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).
dwindex The index of the subkey that you want to retrieve.
lpValueName The name of the Value located at the specified index.
lpcbValueName The size of the lpValueName variable.
lpReserved Not used. Set to 0.
lpType The type of data to retrieve. (see the RegQueryValueEx definition for a list of valid constants).
lpData The data to retrieve.
lpcbData The size of the lpData variable.

The RegEnumValue returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegFlushKey Function The declaration that must be included in your Visual Basic application for the RegFlushKey function is:

Declare Function RegFlushKey Lib "advapi32.dll" _
 (ByVal hKey As Long) As Long

The RegFlushKey function requires the use of the following parameter:

hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).

The RegFlushKey returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegLoadKey Function The declaration that must be included in your Visual Basic application for the RegLoadKey function is:

Declare Function RegLoadKey Lib "advapi32.dll" Alias _
 "RegLoadKeyA" (ByVal hKey As Long, ByVal lpSubKey _
 As String, ByVal lpFile As String) As Long

The RegLoadKey function requires the use of the following parameters:

Parameters Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants)
lpSubKey The name of the new key to create
lpFile The name of the file counting the Registry information that you want to load

The RegLoadKey returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegNotifyChangeKey Function The declaration that must be included in your Visual Basic application for the RegNotifyChangeKey function is:

Declare Function RegNotifyChangeKeyValue Lib "advapi32.dll" _
 (ByVal hKey As Long, ByVal bWatchSubtree As Long, _
 ByVal dwNotifyFilter As Long, ByVal hEvent As Long, _
 ByVal fAsynchronus As Long) As Long

The RegNotifyChangeKey function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for valid constants).
bWatchSubtree Set this value to True if you want to be informed about changes to the subkeys of the key handle contained in the hKey parameter.
dwNotifyFilter The type of key change that you want to detect. Must be one of the following constants:

REG_NOTIFY_CHANGE_ATTRIBUTES = &H2

REG_NOTIFY_CHANGE_LAST_SET = &H4

REG_NOTIFY_CHANGE_NAME = &H1

REG_NOTIFY_CHANGE_SECURITY = &H8
hEvent A handle to an event that caused the change.
fAysynchrous If this parameter is set to False, the function will not return a value until a change has been detected in the Registry. Otherwise, the function will return a value when the event specified in the hEvent parameter occurs.

The RegNotifyChangeKey returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegOpenKey Function The declaration that must be included in your Visual Basic application for the RegOpenKey function is:

Declare Function RegOpenKey Lib "advapi32.dll" Alias _
 "RegOpenKeyA" (ByVal hKey As Long, ByVal lpSubKey As String, _
 phkResult As Long) As Long

The RegOpenKey function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).
lpSubkey Name of the subkey to open.
phkResult If the function successfully completes, phkResult contains the handle to the key.

The RegOpenKey returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegOpenKeyEx Function The declaration that must be included in your Visual Basic application for the RegOpenKeyEx function is:

Declare Function RegOpenKeyEx Lib "advapi32.dll" Alias _
"RegOpenKeyExA" (ByVal hKey As Long, ByVal lpSubKey As String, _
 ByVal ulOptions As Long, ByVal samDesired As Long, _
 phkResult As Long) As Long

The RegOpenKeyEx function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).
lpSubkey Name of the subkey to open.
ulOptions Not used. Set to 0.
samDesired A key access constant (refer to Table 45.6 for valid constants).
phkResult If the function completes successfully, phkResult will contain the handle to the opened key.

The RegOpenKeyEx returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegQueryInfoKey Function The declaration that must be included in your Visual Basic application for the RegQueryInfoKey function is:

Declare Function RegQueryInfoKey Lib "advapi32.dll" Alias _
 "RegQueryInfoKeyA" (ByVal hKey As Long, ByVal lpClass As String, _
 lpcbClass As Long, lpReserved As Long, lpcSubKeys As Long, _
 lpcbMaxSubKeyLen As Long, lpcbMaxClassLen As Long, lpcValues As Long, _
lpcbMaxValueNameLen As Long, lpcbMaxValueLen As Long, _
 lpcbSecurityDescriptor As Long, _
 lpftLastWriteTime As FILETIME) _
 As Long

The RegQueryInfoKey function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or key access constant (refer to Table 45.5 for the valid constants).
lpClass The class of the key is returned in the parameter.
lpcbClass The size of the lpClass string.
lpReserved Not used. Set to 0.
lpcSubkeys The number of subkeys of the key specified in the hKey parameter.
lpcbMaxSubKeyLen The length of the longest subkey of the key specified in the hKey parameter.
lpcbMaxClassLen The length of the longest class name for the subkeys specified in the hKey parameter.
lpcValues The number of values for this key.
lpcbMaxValueNameLen The length of the longest name of a value for the subkeys specified in the hKey parameter.
lpcbMaxValueLen The buffer size needed to store the longest value for the subkeys specified in the hKey parameter
lpcbSecurityDescriptor The length of the key's security setting
lpftLastWriteTime The last modification date and time for the specified key

The RegQueryInfoKey returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegQueryValue Function The declaration that must be included in your Visual Basic application for the RegQueryValue function is:

Declare Function RegQueryValue Lib "advapi32.dll" Alias _
 "RegQueryValueA" (ByVal hKey As Long, _
 ByVal lpSubKey As String, ByVal lpValue As String, _
 lpcbValue As Long) As Long

The RegQueryValue function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).
lpSubkey Name of the subkey to query.
lpValue This parameter contains the retrieved value of the subkey.
lpcbValue The length of the lpValue parameter.

The RegQueryValue returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegQueryValueEx Function The following declaration that must be included in your Visual Basic application for the RegQueryValueEx function is:

Declare Function RegQueryValueEx Lib "advapi32.dll" Alias _
 "RegQueryValueExA" (ByVal hKey As Long, _
 ByVal lpValueName As String, ByVal lpReserved As Long, _
 lpType As Long, lpData As Any, lpcbData As Long) As Long

The RegQueryValueEx function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).
lpValueName The name of the value to retrieve.
lpReserved Not used. Set to 0.
lpType The type of data to retrieve. Must be one of the following constants:

REG_BINARY = 3
REG_DWORD = 4
REG_EXPAND_SZ = 2
REG_DWORD_BIG_ENDIAN = 5
REG_DWORD_LITTLE_ENDIAN = 4
REG_LINK = 6
REG_MULTI_SZ = 7
REG_NONE = 0
REG_RESOURCE_LIST = 8
REG_SZ = 1
lpData This parameter contains the value of the subkey
lpcbData The size of the lpData variable

The RegQueryValueEx returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegReplaceKey Function The following declaration that must be included in your Visual Basic application for the RegReplaceKey function is:

Declare Function RegReplaceKey Lib "advapi32.dll" Alias _
 "RegReplaceKeyA" (ByVal hKey As Long, _
 ByVal lpSubKey As String, ByVal lpNewFile As String, _
 ByVal lpOldFile As String) As Long

The RegReplaceKey function requires the use of the following parameters:

Parameters Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants)
lpSubkey Name of the subkey to replace
lpNewFile The name of the file containing the Registry information to import
lpOldFile The name of the file in which to back up the current Registry information

The RegReplaceKey returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegRestoreKey Function The declaration that must be included in your Visual Basic application for the RegRestoreKey function is:

Declare Function RegRestoreKey Lib "advapi32.dll" Alias _
 "RegRestoreKeyA" (ByVal hKey As Long, _
 ByVal lpFile As String, ByVal dwFlags As Long) As Long

The RegRestoreKey function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants)
lpFile The name of the file containing the Registry information to restore
dwFlags Set to 0 for a regular Registry restore

The RegRestoreKey returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegSaveKey Function The following declaration that must be included in your Visual Basic application for the RegSaveKey function is:

Declare Function RegSaveKey Lib "advapi32.dll" Alias _
 "RegSaveKeyA" (ByVal hKey As Long, _
 ByVal lpFile As String, _
 lpSecurityAttributes As SECURITY_ATTRIBUTES) As Long

The RegSaveKey function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).
lpFile The name of the file that will contain the saved Registry information.
lpSecurityAttributes Security information of the saved key.

The RegSaveKey returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegSetValue Function The following declaration that must be included in your Visual Basic application for the RegSetValue function is:

Declare Function RegSetValue Lib "advapi32.dll" Alias _
 "RegSetValueA" (ByVal hKey As Long, ByVal lpSubKey As String, _
 ByVal dwType As Long, ByVal lpData As String, _
 ByVal cbData As Long) As Long

The RegSetValue function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).
lpSubkey Name of the subkey whose value you want to set. If the subkey does not exist, it is created.
dwType Must be set to the constant REG_SZ. (see the RegQueryValueEx definition for value of the REG_SZ constant).
lpData The new value of the subkey.
cbData Length of the lpData parameter.

The RegSetValue returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegSetValueEx Function The following declaration that must be included in your Visual Basic application for the RegSetValueEx function is:

Declare Function RegSetValueEx Lib "advapi32.dll" Alias _
 "RegSetValueExA" (ByVal hKey As Long, _
 ByVal lpValueName As String, ByVal Reserved As Long, _
 ByVal dwType As Long, lpData As Any, ByVal cbData As Long) _
 As Long

The RegSetValueEx function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the valid constants).
lpValueName The name of the Value to set.
Reserved Not used. Set to 0.
dwType The type of data that is to be set (see the RegQueryValueEx definition for a list of valid constants).
lpData The value of the new key.
cbData Length of the lpData parameter.

The RegSetValueEx returns a Long value of 0 if the function was successful; any other values should be treated as error codes.

The RegUnLoadKey Function The following declaration that must be included in your Visual Basic application for the RegUnLoadKey function is:

Declare Function RegUnLoadKey Lib "advapi32.dll" Alias _
 "RegUnLoadKeyA" (ByVal hKey As Long, ByVal lpSubKey As String) _
 As Long

The RegUnLoadKey function requires the use of the following parameters:

Parameter Description
hKey The handle of the open key or a key access constant (refer to Table 45.5 for the Valid constants)
lpSubKey The name of the subkey to unload (this subkey must have been previously loaded using the RegLoadKey function)

Using the Windows 95 API to Access the Registry

In this section, you create a small application that reads the contents of the Windows 95 Registry. This example provides you with access to all sections of the Registry. In addition, you can view the values that are stored in all of the keys contained in the Registry.

To create the application, perform the following steps:

1. Start Visual Basic and choose Open a New Standard EXE project.

2. Choose Project, Components and add the Microsoft Common Controls 5.0 to your project by selecting the box next to the name and clicking OK.

3. Add a standard module to the project by choosing Project, Add Module.

4. Enter Listing 45.3 into the declarations section of the newly added standard module. Alternatively, you may want to copy the listing from file exam3a.bas, which is included on the CD accompanying this book.

Listing 45.3 exam3a.bas--Registry API Declarations that Need to be Placed in Module1

Option Explicit
Option Base 1
Declare Function RegCloseKey Lib "advapi32.dll" _
 (ByVal hKey As Long) As Long
Declare Function RegEnumKey Lib "advapi32.dll" Alias _
 "RegEnumKeyA" (ByVal hKey As Long, ByVal dwIndex As Long, _
 ByVal lpName As String, ByVal cbName As Long) As Long
Declare Function RegQueryValueEx Lib "advapi32.dll" Alias _
"RegQueryValueExA" (ByVal hKey As Long, _
 ByVal lpValueName As String, ByVal lpReserved As Long, _
 lpType As Long, lpData As Any, lpcbData As Long) As Long
Declare Function RegEnumValue Lib "advapi32.dll" Alias _
"RegEnumValueA" (ByVal hKey As Long, ByVal dwIndex As Long, _
 ByVal lpValueName As String, lpcbValueName As Long, _
 lpReserved As Long, lpType As Long, lpData As Byte, _
 lpcbData As Long) As Long
Declare Function RegLoadKey Lib "advapi32.dll" Alias _
 "RegLoadKeyA" (ByVal hKey As Long, ByVal lpSubKey As String, _
 ByVal lpFile As String) As Long
Declare Function RegOpenKey Lib "advapi32.dll" Alias _
 "RegOpenKeyA" (ByVal hKey As Long, ByVal lpSubKey As String, _
 phkResult As Long) As Long
Declare Function RegOpenKeyEx Lib "advapi32.dll" Alias _
 "RegOpenKeyExA" (ByVal hKey As Long, ByVal lpSubKey As String, _
 ByVal ulOptions As Long, ByVal samDesired As Long, _
 phkResult As Long) As Long
Public Const HKEY_CLASSES_ROOT = &H80000000
Public Const HKEY_CURRENT_CONFIG = &H80000005
Public Const HKEY_CURRENT_USER = &H80000001
Public Const HKEY_DYN_DATA = &H80000006
Public Const HKEY_LOCAL_MACHINE = &H80000002
Public Const HKEY_PERFORMANCE_DATA = &H80000004
Public Const HKEY_USERS = &H80000003
Public Const KEY_QUERY_VALUE = &H1
Public Const ERROR_NO_MORE_ITEMS = 259&
Public Const REG_BINARY = 3
Public Const REG_DWORD = 4
Public Const REG_DWORD_BIG_ENDIAN = 5
Public Const REG_DWORD_LITTLE_ENDIAN = 4
Public Const REG_EXPAND_SZ = 2
Public Const REG_LINK = 6
Public Const REG_MULTI_SZ = 7
Public Const REG_NONE = 0
Public Const REG_SZ = 1
Public Const REG_RESOURCE_LIST = 8
Public Const REG_FULL_RESOURCE_DESCRIPTOR = 9
5. If no form is contained in the current project, choose Project, Add Form to add a form to the project.

6. Add the following controls to the form; do not change any of their properties because you can set them in the next step:

Control

Description

One TreeView control

One CommandButton control

One ListBox control

One Label control

7. Set the following properties for the TreeView control:

Name = treReg
Height =   3735
Left  =   360
TabIndex =   0
Top  =   0
Width =   4755
LineStyle  =   1
Style =   7
Appearance =   1
8. Set the following properties for the CommandButton control:
Name =  cmdExit
Caption =   E&xit
Height  =   300
Left  =   8820
TabIndex   =   2
Top =   3540
Width =   915
9. Set the following properties for the ListBox control:
Name  = lstValues
Height =   1620
Left =   5160
TabIndex        =   2
Top  =   480
Width  =   4575
10. Set the following properties for the Label control:



Name =  lblValue
Caption  =   Values
Height  =   315
Left  =   5340
Top             =   60
Width           =   1995
11. Set the following properties for the Form containing the newly added controls:
Name = exam3
Caption  =   Registry Explorer  
Height =   3930
Left  =   2010
Top  =   1545
Width =   10065
12. Enter the following code into the Form_Load event. This code will retrieve all of the subkeys from the Registry and add them to the listview control:



Dim ntest As Long
Dim cname As String
Dim lname As Long
Dim x As Integer
Dim nodX As Node
Screen.MousePointer = vbHourglass
cname = Space$(4096)
lname = 4096
Set nodX = treReg.Nodes.Add(, , "HKEY_CLASSES_ROOT", "HKEY_CLASSES_ROOT")
Set nodX = treReg.Nodes.Add(, , "HKEY_CURRENT_USER", "HKEY_CURRENT_USER")
Set nodX = treReg.Nodes.Add(, , "HKEY_LOCAL_MACHINE", "HKEY_LOCAL_MACHINE")
Set nodX = treReg.Nodes.Add(, , "HKEY_USERS", "HKEY_USERS")
Set nodX = treReg.Nodes.Add(, , "HKEY_CURRENT_CONFIG", "HKEY_CURRENT_CONFIG")
Set nodX = treReg.Nodes.Add(, , "HKEY_DYN_DATA", "HKEY_DYN_DATA")
x = 0
Do While ntest = 0
    ` get all of the SubKeys for HKEY_CLASSES_ROOT
   test = RegEnumKey(HKEY_CLASSES_ROOT, x, cname, lname)
    If ntest = 0 Then
        Set nodX = treReg.Nodes.Add("HKEY_CLASSES_ROOT", tvwChild, _
 "A" & CStr(x), cname)
        x = x + 1
    End If
Loop
x = 0
ntest = 0
Do While ntest = 0
    ` get all of the SubKeys for HKEY_CURRENT_USER
   test = RegEnumKey(HKEY_CURRENT_USER, x, cname, lname)
    If ntest = 0 Then
        Set nodX = treReg.Nodes.Add("HKEY_CURRENT_USER", _
 tvwChild, "B" & CStr(x), cname)
        x = x + 1
    End If
Loop
x = 0
ntest = 0
Do While ntest = 0
    ` get all of the SubKeys for HKEY_LOCAL_MACHINE
   test = RegEnumKey(HKEY_LOCAL_MACHINE, x, cname, lname)
    If ntest = 0 Then
        Set nodX = treReg.Nodes.Add("HKEY_LOCAL_MACHINE", _
 tvwChild, "C" & CStr(x), cname)
        x = x + 1
    End If
Loop
x = 0
ntest = 0
Do While ntest = 0
    ` get all of the SubKeys for HKEY_USERS
   test = RegEnumKey(HKEY_USERS, x, cname, lname)
    If ntest = 0 Then
        Set nodX = treReg.Nodes.Add("HKEY_USERS", tvwChild, _
 "D" & CStr(x), cname)
        x = x + 1
    End If
Loop
x = 0
ntest = 0
Do While ntest = 0
    ` get all of the SubKeys for HKEY_CURRENT_CONFIG
   test = RegEnumKey(HKEY_CURRENT_CONFIG, x, cname, lname)
    If ntest = 0 Then
        Set nodX = treReg.Nodes.Add("HKEY_CURRENT_CONFIG", tvwChild, _
 "E" & CStr(x), cname)
        x = x + 1
    End If
Loop
x = 0
ntest = 0
Do While ntest = 0
    ` get all of the SubKeys for HKEY_DYN_DATA
   test = RegEnumKey(HKEY_DYN_DATA, x, cname, lname)
    If ntest = 0 Then
        Set nodX = treReg.Nodes.Add("HKEY_DYN_DATA", tvwChild, _
 "F" & CStr(x), cname)
        x = x + 1
    End If
Loop
Screen.MousePointer = vbDefault
13. Enter the following code into the Form_Unload event:
Set exam3 = Nothing
14. Enter the following code into the cmdExit_Click event:
Unload Me
15. Enter the following code in the treReg_NodeClick event. This code will expand the tree in the listview control and display all of the subkeys of the selected key. If the key selected is the final key in the chain of keys its values will be displayed in the list box:
Dim nodX As Node
Dim ntest As Integer
Dim lret As Long
Dim hKey As Long
Dim x As Integer
Dim cname As String
Dim cvname As String
Dim ctype As String
Dim lpcvalue As Long
Dim lname As Long
Dim lhandle As Long
Dim ntype As Long
Dim cdata As Byte
Dim ldata As Long
cname = Space$(4096)
cvname = Space$(25)
lname = 4096
`cdata = Space$(4096)
ldata = Len(cdata)
If Node.Children > 0 Then
    Exit Sub
Else
Select Case Mid$(Node.FullPath, 1, _
 InStr(1, Node.FullPath, "\") - 1)
Case "HKEY_CLASSES_ROOT"
    hKey = HKEY_CLASSES_ROOT
Case "HKEY_CURRENT_CONFIG"
    hKey = HKEY_CURRENT_CONFIG
Case "HKEY_CURRENT_USER"
    hKey = HKEY_CURRENT_USER
Case "HKEY_DYN_DATA"
    hKey = HKEY_DYN_DATA
Case "HKEY_LOCAL_MACHINE"
    hKey = HKEY_LOCAL_MACHINE
Case "HKEY_PERFORMANCE_DATA"
    hKey = HKEY_PERFORMANCE_DATA
Case "HKEY_USERS"
    hKey = HKEY_USERS
End Select
lret = RegOpenKeyEx(hKey, Mid$(Node.FullPath, _
 InStr(1, Node.FullPath, "\") + 1, Len(Node.FullPath) _
 - InStr(1, Node.FullPath, "\") + 1), 0, _
 KEY_QUERY_VALUE, lhandle)
If lret <> 0 Then
    Exit Sub
End If
ntest = 0
x = 0
Do While ntest <> ERROR_NO_MORE_ITEMS
   test = RegEnumKey(lhandle, x, cname, lname)
    If ntest = 0 Then
        Set nodX = treReg.Nodes.Add(Node.Index, tvwChild, _
 "A" & CStr(x) & CStr(Timer), cname)
        x = x + 1
    Else
       test = 0
        x = 0
        lstValues.Clear
        Do While ntest <> ERROR_NO_MORE_ITEMS

           test = RegEnumValue(lhandle, x, cvname, _
 Len(cvname), 0, ntype, cdata, ldata)
            If ntest = 0 Then
               lstValues.AddItem Trim$(cvname)
                x = x + 1
            End If
        Loop
    End If
Loop
End If
lret = RegCloseKey(lhandle)
If Node.Children <> 0 Then
   ode.Expanded = True
End If
16. Choose Run, Start, or press F5 to run the project.

After the Project is started, you should have a form on your display similar to that illustrated in Figure 45.8.

Using the Sample application, you can navigate your way through the Registry by using the TreeView control.

In this section, you have looked at various aspects of accessing the Windows 95 Registry through the use of Windows 95 API calls. You have seen that through the Windows 95 API you can access far more Registry information than is possible through the regular Visual Basic functions.

FIG. 45.8
Here is the Sample Registry Viewer Application.

From Here...

In this chapter, you have learned to access and manipulate information contained in INI files by using the Windows 95 API. In addition, you have learned how to manipulate Registry information through the use of the functions contained in Visual Basic and in the Windows 95 API.

See the following chapters for additional information on topics discussed in this chapter:



Macmillan Computer Publishing USA

© Copyright, Macmillan Computer Publishing. All rights reserved.