Search the Catalog
Windows System Policy Editor

Windows System Policy Editor

By Stacey Anderson-Redick
1st Edition June 2000
1-56592-649-8, Order Number: 6498
545 pages, $34.95

Chapter 8
Creating a Custom Template

Perhaps one of the most versatile functions of the SPE is the ability to create a custom template for just about any program that utilizes the Windows registry. This is particularly useful if an organization uses in-house software programs and needs to gain some measure of consistency across workstations. This consistency can be achieved using the SPE and a custom template.

This chapter will first examine the structure of a template, breaking it down into its smallest components while giving a full explanation and example of each. I will then go through the creation of a unique template, one that uses many popular Windows registry hacks. While creating this template, I will point out the information required and emulate the decision-making process for choosing the appropriate syntax and keywords.

The Four Zones

A template consists of four nested zones: class, category, policy and part. parts nest within policies; policies nest within categories; and categories nest within one single class. Figure 8-1 displays this basic structure.

Figure 8-1. Basic template structure

 

Two of the four zones are really organizational in nature. class separates computer and user policies, while category organizes policy options into logistical areas. It is policy and part that are the working parts of the template, and it is these two zones that contain the elements that allow the registry to be edited.

Information within each zone is displayed in a specific area of the computer or user properties page of the SPE, as shown in Figure 8-2. I will examine each zone in more detail in the following sections.

Figure 8-2. Template zones in the conf.adm template

 

In each of the four zones there are a number of available keywords. While most keywords are specific to their own areas, there are three that can be used anywhere within the four zones:

KEYNAME "value"
Indicates a full registry key path. Unless elsewhere specified, it will be inherited by all child areas of the template. The top-level key, HKLM or HKCU, does not need to be specified as it is assumed depending on which class type precedes the KEYNAME. Additional KEYNAME statements can be subkeys of a previously mentioned key. For example, the class statement could mention the key "Software\Microsoft\Windows\CurrentVersion" while a policy statement would only have to mention "Policies\Network." For example:

KEYNAME "Control Panel\Colors"

!!string
Indicates a string that will be replaced with a text label in the SPE properties window. This is used for labels on categories, policies, and parts, or for help text. Using this, a text label only has to be defined once. A section at the end of the template labeled [strings] contains the string definitions. For example:

!!Wallpaper1 !!Wallpaper2
[strings]
Wallpaper1="Black Thatch.bmp"

; comment
Comments can be entered anywhere in the template by preceding them with a semicolon. Any line beginning with a semicolon will not be processed by the SPE. For example:

;template version 2.1

The use of the !! keyword for text labels is not absolutely necessary. Text entered without the !! keyword will be used as is, but any text containing spaces would have to be enclosed within quotes.

Each of the four zones has a basic syntax and its own specific keywords, which I cover in the next sections.

Class

There are only two valid classes: Machine and User (see Table 8-1). They define one or the other of the two registry keys that can be edited by a template, either HKCU or HKLM. HKCU will appear as a user or group policy and is referred to as class USER. HKLM will appear as a computer policy and is referred to as class MACHINE.

Basic Syntax

CLASS class_type

Examples from conf.adm

CLASS MACHINE

CLASS USER

Category

On the SPE properties page, the text captions that appear beside the book icons are the categories (see Figure 8-2). They are included on either the computer or user/group properties page, depending on which class statement they follow. If they follow Class Machine, they will be on the computer properties page; if they follow Class User, they will be on the user or group properties page. Categories are used to give the template organizational structure and can be nested within each other to create main categories and subcategories.

Basic Syntax

CATEGORY !!string
KEYNAME "value"
[policy and part statements go here]
END CATEGORY

Example From conf.adm

CATEGORY !!NetMeeting2
KEYNAME "Software\Microsoft\Conferencing"
[policy and part statements]
END CATEGORY

KEYNAME is optional. If it is not specified here, it can be taken from the parent category, or it can be specified in the subsequent policy or part statements. If a KEYNAME is specified, it can be used by all child subcategories, policies and parts. This inheritance of keywords allows the template to be simplified by removing the necessity of repeating the oftentimes lengthy registry keywords.

Policy

The essence of the template is the policies that exist within a category. They are the familiar checkboxes that can be set to one of three positions: cleared, grayed or checked. While the class and category statements have no direct effect on the registry, changing a policy option will alter a registry key or value. The basic policy syntax is as follows:

POLICY !!string
KEYNAME "value"
   [optional keyword(s)]
   [optional PART statement(s)]
END POLICY

As with category, KEYNAME is optional and can be inherited from preceding policies or categories.

A policy can contain several optional keywords, listed here. They may be included within the part statements instead.

VALUENAME "value"
The VALUENAME of the registry key. It is optional only if the policy contains additional part statements. A VALUENAME containing spaces must be enclosed within quotes, although all valuenames may be enclosed in quotes for consistency. For example:

VALUENAME "Background"

VALUE value
The value of the registry entry specified by VALUENAME. If there is no VALUE statement, the default value when the policy box is checked is a DWORD of 1, and the default value when the policy box is cleared is to remove the value entirely.

If a value is specified, the default is for that value to be interpreted as a string (REG_SZ) value. Strings with spaces must be enclosed in quotes. To create specific DWORD values, the value must be preceded with the word NUMERIC. To totally remove a VALUENAME/VALUE registry pair, use a value of DELETE. For example:

VALUENAME "Background" VALUE "128 128 192"
VALUENAME "Platform_Type" VALUE NUMERIC 0
VALUENAME "StaticVxD" VALUE DELETE

DEFCHECKED
The policy box is initially checked.

VALUEON value
Overrides the checked position default of the VALUE keyword (DWORD value of 1) to another specified value. As with the VALUE keyword, values default to a string (REG_SZ) value unless preceded by the word NUMERIC. For example:

VALUEON "1"
VALUEON DELETE

VALUEOFF value
Overrides the default behavior to set a specified value when the box is in the cleared position. It follows the same rules as VALUEON.

ACTIONLISTON
Optional actions (other registry keys to be changed) if a policy box is set to the checked (on) position. For example, in the admin.adm template there is an option to choose a desktop color scheme by name (e.g., Rainy Day). The ACTIONLIST would then be used to change the color of each individual control panel item to achieve the Rainy Day color scheme.

ACTIONLISTOFF
Optional actions (other registry keys to be changed) if policy box is in the cleared (off ) position. The syntax for both ACTIONLISTON and ACTIONLISTOFF is as follows:

ACTIONLISTOFF (or ACTIONLISTON)
KEYWORD value
VALUENAME "value" VALUE value
END ACTIONLISTOFF (or END ACTIONLISTON)

Any number of policies can exist under any one category or subcategory.

TIP:

For Windows 9x there can be only two types of VALUE entries: string or DWORD. Binary values are not supported by the SPE templates. For Windows NT, only REG_DWORD, REG_SZ, and REG_EXPAND_SZ registry values are supported.

An example of a simple policy from the conf.adm template is as follows:

POLICY !!PreventAnswering
     PART !!PreventAnswering CHECKBOX
     VALUENAME "NoAnswering"
     END PART
END POLICY

You will notice in this example that the VALUENAME does not need to be specified immediately after the policy statement, as it is included within the PART statement instead. In addition, since a value is not specified, it will default to a DWORD value of 1.

Part

If there are policy options in addition to enabled and disabled (cleared and checked), then these can be identified in a part statement. Once the policy checkbox is set to the checked position, the part options become available in the lower gray portion of the user or computer property sheet. There are seven part types, and these types allow for the data to be presented in various forms such as text boxes, spin dials and so on (see each specific part type for more information).

The basic PART syntax is as follows:

PART !!string part_type
part_type optional_keyword
KEYNAME "value"
VALUENAME "value" VALUE value
END PART

The string is the label that appears beside the actual part type in the properties box. The available optional keywords will depend on the specific part type.

KEYNAME is again optional, as it can be inherited from the parent policy or category. Value is also optional, and if it is not specified, it will default to a DWORD value of 1. However, Valuename must be specified for most part types (see each part type for further information).

An example of a simple policy from the conf.adm template is as follows:

PART !!EnableNullModem CHECKBOX
    DEFCHECKED
    KEYNAME "Software\Microsoft\Conferencing\Transports\DIRCB"
    VALUENAME "Disabled"
END PART 

In this example the part type is a checkbox, and the part type optional keyword is DEFCHECKED (the checkbox will be in the checked position by default).

TIP:  

A simple policy (without any part statements) shares much in common with the part type CHECKBOX, as they both use the same syntax and optional keywords.

Putting It Together

Putting together the four zones (class, category, policy and part), the entire Machine portion of the conf.adm template displayed in Figure 8-2 appears like this:

CLASS MACHINE
 
CATEGORY !!NetMeeting2
KEYNAME "Software\Microsoft\Conferencing"
    POLICY !!NetMeeting2
        PART !!EnableTCPIP CHECKBOX
         KEYNAME "Software\Microsoft\Conferencing\Transports\TCPIP"
         VALUENAME "Disabled"
        END PART
 
        PART !!EnableNullModem CHECKBOX
         DEFCHECKED
         KEYNAME "Software\Microsoft\Conferencing\Transports\DIRCB"
         VALUENAME "Disabled"
        END PART
    END POLICY
END CATEGORY

If you examine this class example, you see that there is only one category, as well as a single policy within which are two part statements. Although this category specifies a keyname, it is not necessary as each of the two parts also specify keynames. In both parts, the valuename is specified although the Value is not, indicating that the default DWORD value of 1 will be used.

Part Types

The true flexibility of a custom template comes from the individual part types, of which there are seven:

Each part shares the same universal keywords shown in the four zones universal keyword list, in addition to their own unique keywords.

TEXT

The TEXT part type does not edit the registry, as it is merely descriptive text with no associated registry key or value. It allows you to put in explanatory text for your policy or parts as shown in Figure 8-3.

Figure 8-3. TEXT part option from nwnt.adm

 

The TEXT part that is displayed in Figure 8-3 is created by the following template statements:

PART !!BurstMode_TIP1 TEXT END PART
PART !!BurstMode_TIP2 TEXT END PART
PART !!BurstMode_TIP3 TEXT END PART
 
[strings]
BurstMode_TIP1="Burst Mode specifies whether Packet Burst is used.'Off'"
BurstMode_TIP2="disables Packet Burst. 'On' enables Packet Burst, which"
BurstMode_TIP3="reduces overall network traffic and improves performance."

The text is broken up into three lines so that it does not run off the edge of the properties window. Approximately 65 characters can be used before the text runs off the edge of the window.

EDITTEXT

EDITTEXT allows you to make a box for alphanumeric text input, as shown in Figure 8-4.

Figure 8-4. EDITTEXT part type from zakwinnt.adm

 

This part will have an associated registry keyname, which will either be specified or inherited from a parent policy or category. The EDITTEXT statement may also include one or more of the optional keywords shown in Table 8-1.

Table 8-1: EDITTEXT Keywords

Optional Keywords

Details

VALUENAME "value"

This keyword is not optional.

See policy optional keyword list for details.

VALUE value

See policy optional keyword list for details.

DEFAULT value

Specifies the initial text string. The default is a blank box. The value is set in the registry as a string (REG_SZ) type.

EXPANDABLETEXT

Allows use of environment variables by writing the value to the registry with the datatype REG_EXPAND_SZ.

MAXLEN value

Maximum length of the text, to a maximum of 255 characters.

REQUIRED

The policy cannot be set to the checked position until something is entered into the listbox. If nothing is entered, the user is prompted to do so by an error message.

OEMCONVERT

Sets the ES_OEMCONVERT style in the edit field so that typed text converts from the ANSI character set to the installed OEM character set.

The EDITTEXT part that is displayed in Figure 8-4 is created by the following template statements:

Part !!UserProfiles_FavoritesPath	EDITTEXT REQUIRED EXPANDABLETEXT
    Default !!UserProfiles_FavoritesPathDefault
    Valuename "Favorites"
End Part

You will notice that the edit box allows the use of environmental variables through the use of the keyword EXPANDABLETEXT. In addition, the use of the second keyword REQUIRED will not allow the user to leave the edit text box blank.

TIP:  

A custom template can be made that has an edit box of more than 255 characters; howeve,r only the first 255 characters will be passed onto the registry by the SPE.

CHECKBOX

A CHECKBOX can have two positions in a template, checked or unchecked (on or off). By default, if the box is checked, the value will be a REG_DWORD of 1. If the box is cleared, the value entry is set to zero.

Figure 8-5. CHECKBOX part option

 

This part will have an associated registry keyname, which will either be specified or inherited from a parent policy or category. The CHECKBOX part type uses the same optional keywords as the basic policy (see the policy optional keyword list for more information), as shown in Figure 8-5. These keywords are:

The CHECKBOX part that is displayed in Figure 8-5 is created by the following template statements:

PART !!DisableCache CHECKBOX
    VALUENAME "UserProfiles"
    VALUEON NUMERIC 0 
    VALUEOFF NUMERIC 1
ACTIONLISTON
    KEYNAME "Software\Microsoft\Windows\CurrentVersion\Internet Settings\5.0\ 
         Cache\Content"
    VALUENAME "PerUserItem" VALUE NUMERIC 0
END ACTIONLISTON
ACTIONLISTOFF
    KEYNAME "Software\Microsoft\Windows\CurrentVersion\Internet Settings\5.0\ 
         Cache\Content"
    VALUENAME "PerUserItem" VALUE NUMERIC 1
END ACTIONLISTOFF
END PART

You will notice that when the CHECKBOX is in the checked position, the ACTIONLISTON statement allows an additional registry edit to occur. Also, the ACTIONLISTOFF statement allows for an additional registry edit when the checkbox is in the cleared position. Typically ACTIONLISTON and ACTIONLISTOFF do not occur independently of each other, even if ACTIONLISTOFF does nothing else but delete the VALUENAME/VALUE registry pair created by the ACTIONLISTON.

NUMERIC

The NUMERIC part type allows you to type in a numeric value, or use a spin dial (the up and down arrows) to choose a value. The spin dial can have an optional specified range and increment value.

Figure 8-6. NUMERIC part option from winnt.adm

 

This part will have an associated registry keyname, which will either be specified or inherited from a parent policy or category. The NUMERIC statement may also include one or more of the optional keywords in Table 8-2.

Table 8-2: NUMERIC Optional Keywords

Optional Keywords

Details

VALUENAME "value"

This keyword is not optional. See the policy optional keyword list for details.

VALUE value

See the policy optional keyword list for details. This value will be read as a binary (REG_DWORD) value.

DEFAULT value

Specifies the initial numerical value; the default is a blank box.

MIN value

Minimum value, default is 0.

MAX value

Maximum value, default is 9999.

SPIN value

An increment for spin control; default is 1. Spin 0 removes the control arrows.

TXTCONVERT

Writes values as strings (REG_SZ) rather than DWORD values.

REQUIRED

The policy cannot be set to the checked position until something is entered into the list box. If nothing is entered, the user is prompted to do so by an error message.

The NUMERIC part that is displayed in Figure 8-6 is created by the following template statements:

PART !!ProfileSize     NUMERIC REQUIRED SPIN 100
     DEFAULT 30000
     MAX    30000
     MIN    300
     VALUENAME "MaxProfileSize"
END PART 

Notice that the spin dial will increase by increments of 100, from a minimum of 300 to a maximum of 30,000--which also happens to be the default value.

TIP:  

Due to a bug in Poledit, the maximum value that a user can type directly into a numeric box is 9999 (or 4 digits), although a spin dial can be used to increase the value beyond this number.

DROPDOWNLIST

A DROPDOWNLIST (see Figure 8-7) presents the user with a number of options from which to choose. The user is not free to type in any other choices.

Figure 8-7. DROPDOWNLIST part option from windows.adm

 

This part will have an associated registry keyname, which will be either specified or inherited from a parent policy or category. The DROPDOWNLIST statement may also include one or more of the optional keywords in Table 8-3.

Table 8-3: DROPDOWNLIST Optional Keywords

Optional Keywords

Details

VALUENAME "value"

This keyword is not optional, see the policy optional keyword list for details.

VALUE value

See the policy optional keyword list for details.

NOSORT

Will not sort data alphabetically. Default is to sort.

REQUIRED

The policy cannot be set to the checked position until something is entered into the list box. If nothing is entered, the user is prompted to do so with an error message.

ITEMLIST

The list of items to be included in the drop-down list.

The syntax is as follows (see the policy optional keyword list for VALUENAME and VALUE options):

ITEMLIST
    NAME !!string  VALUE value
ACTIONLIST
  KEYNAME "value"
    VALUENAME "value" VALUE value
END ACTIONLIST
END ITEMLIST

The ITEMLIST allows each choice, labeled by the !!string, and any associated additional registry edits, to be listed separately. In this situation, ACTIONLIST functions in much the same way as the CHECKBOX keyword ACTIONLISTON (policy optional keyword list).

The DROPDOWNLIST part that is displayed in Figure 8-7 is created by the following template statements:

PART !!AuthenticatorType DROPDOWNLIST
KEYNAME Security\Provider
VALUENAME "Platform_Type" REQUIRED
ITEMLIST
    NAME !!AT_NetWare      VALUE NUMERIC 3
ACTIONLIST
    KEYNAME System\CurrentControlSet\Services\VxD\NWSP
    VALUENAME "StaticVxD" VALUE nwsp.vxd
    VALUENAME "Start"         VALUE NUMERIC 0
    KEYNAME Security\Provider
    VALUENAME "Address_Book"  VALUE nwab32.dll
END ACTIONLIST
    NAME !!AT_NTAS          VALUE NUMERIC 2
ACTIONLIST
    KEYNAME System\CurrentControlSet\Services\VxD\MSSP
    VALUENAME "StaticVxD"     VALUE mssp.vxd
    VALUENAME "Start"         VALUE NUMERIC 0
    KEYNAME Security\Provider
    VALUENAME "Address_Book"  VALUE msab32.dll
END ACTIONLIST
    NAME !!AT_NT            VALUE NUMERIC 1
ACTIONLIST
    KEYNAME System\CurrentControlSet\Services\VxD\MSSP
    VALUENAME "StaticVxD" VALUE mssp.vxd
    VALUENAME "Start"         VALUE NUMERIC 0
    KEYNAME Security\Provider
    VALUENAME "Address_Book"  VALUE msab32.dll
END ACTIONLIST
END ITEMLIST
END PART

Notice that there are three NAMEs, indicating that there will be three options on this drop-down list. The value specified beside each name will be applied to the VALUENAME listed on line three (Platform_Type). Also notice that each name has an associated ACTIONLIST with additional registry edits.

COMBOBOX

The COMBOBOX (shown in Figure 8-8) is basically a combination of the part types EDITTEXT and DROPDOWNLIST. Like EDITTEXT you can type in alphanumeric text, or like DROPDOWNLIST you can choose from a list of suggestions.

Figure 8-8. COMBOBOX part option from admin.adm

 

This part will have an associated registry keyname, which will be either specified or inherited from a parent policy or category. The COMBOBOX statement may also include one or more of the optional keywords in Table 8-4.

Table 8-4: COMBOBOX Optional Keywords

Optional Keywords

Details

VALUENAME "value"

This keyword is not optional. See the policy optional keyword list for details.

VALUE value

See the policy optional keyword list for details.

DEFAULT value

Specifies the initial text string. Default is blank.

EXPANDABLETEXT

Allows use of environment variables by writing the value to the registry with the datatype REG_EXPAND_SZ.

MAXLEN value

Maximum length of the text.

REQUIRED

The policy cannot be set to the checked position until something is entered into the list box. If nothing is entered, the user is prompted to do so with an error message.

OEMCONVERT

Sets the ES_OEMCONVERT style in the edit field so that typed text is mapped from ANSI to OEM and back.

NOSORT

Do not sort data alphabetically. The default is to sort.

SUGGESTIONS

Lists suggestions to be included in the drop-down box. Each suggestion is separated from the next by a space. Suggestions with a space are enclosed by quotes:

SUGGESTIONS
!!string1 !!string2 !!string3
END SUGGESTIONS

The COMBOBOX part that is displayed in Figure 8-8 is created by the following template statements:

PART !!WallpaperName COMBOBOX REQUIRED
  SUGGESTIONS
      !!Wallpaper1 !!Wallpaper2 !!Wallpaper3 !!Wallpaper4 !!Wallpaper5
      !!Wallpaper6 !!Wallpaper7 !!Wallpaper8 !!Wallpaper9 !!Wallpaper10
  END SUGGESTIONS
  VALUENAME "Wallpaper"
END PART

You will notice that in this example VALUENAME appears after the suggestion list. It is not necessary for the valuename to follow the line containing the part type, although it is easier to debug your template if you use a specific keyword order.

LISTBOX

LISTBOX is the only part type which allows the addition and removal of multiple values under one registry key. One example of this type of registry key (Figure 8-9) is the key which lists all the programs that are run when Windows loads.

Figure 8-9. LISTBOX part option from admin.adm

 

This part will have an associated registry keyname, which will either be specified or inherited from a parent policy or category. However, unlike most of the other part types, VALUENAME and VALUE are not supported. There can be no single registry valuename or value possible for an option that allows multiple entries.

The LISTBOX statement may also include one or more of the optional keywords in Table 8-5.

Table 8-5: LISTBOX Optional Keywords

Optional Keywords

Details

VALUEPREFIX "value"

The prefix is added to an incremental number to create the VALUENAME. For example the prefix "Directory" will result in data named "Directory1" , "Directory2", and so on. Empty quotes "" will result in only the numerals. This keyword cannot be used with EXPLICITVALUE.

EXPLICITVALUE

Displays two columns in the Show Contents listbox, and provides the user with a place to enter both a valuename and value data. By default the valuename is identical to the value data. This keyword cannot be used with VALUEPREFIX.

ADDITIVE

Values entered will be appended to the existing registry entry. Default is that the values will overwrite what exists in the registry. NOTE: this keyword is not supported in ADM files for NT4; the values will still be overwritten.

The LISTBOX part that is displayed in Figure 8-9 is created by the following template statements:

PART !!RunListbox LISTBOX EXPLICITVALUE
END PART

Although LISTBOX has one of the most complex interfaces, its syntax is one of the simplest.

Part Type Keyword Summary

Table 8-6 can be used as a quick check to see if a part type supports a particular keyword. If a keyword is supported, this is indicated by an X in the table.

Table 8-6: Part Type Keyword Summary

Keyword

CHECK
BOX

COMBO
BOX

DROPDOWNLIST

LISTBOX

NUMERIC

EDITTEXT

TEXT

!!

X

X

X

X

X

X

X

KEYNAME

X

X

X

X

X

X

 

VALUENAME

X

X

X

 

X

X

 

VALUE

X

X

X

 

X

X

 

DEFCHECKED

X

 

 

 

 

 

 

VALUEON/ VALUEOFF

X

 

 

 

 

 

 

ACTIONLISTON/ ACTIONLISTOFF

X

 

 

 

 

 

 

DEFAULT

 

X

 

 

X

X

 

MIN

 

 

 

 

X

 

 

MAX

 

 

 

 

X

 

 

SPIN

 

 

 

 

X

 

 

Txtconvert

 

 

 

 

X

 

 

Required

 

X

X

 

X

X

 

Expandabletext

 

X

 

 

 

X

 

Maxlen

 

X

 

 

 

X

 

Oemconvert

 

X

 

 

 

X

 

Nosort

 

X

X

 

 

 

 

Suggestions

 

X

 

 

 

 

 

Itemlist

 

 

X

 

 

 

 

Actionlist

 

 

X

 

 

 

 

Valueprefix

 

 

 

X

 

 

 

Explicitvalue

 

 

 

X

 

 

 

Additive

 

 

 

X

 

 

 

#if version

To provide backward compatibility, you can perform logic testing for a specific version of poledit.exe. The original version of Poledit did not support the keywords NOSORT or EXPANDABLETEXT. If you would like your custom template to be available for wide distribution, you can prevent some error messages in older Poledit versions by performing version checking.

The Poledit shipped with Windows 95 is assumed to be Version 1. The versions shipped with Windows 98, NT4 Service Packs and Office 2000 are Version 2.

The syntax is very simple:

#if version operator poledit_version
part_keyword
#endif

There are five operators:

<
less than

>
greater than

<=
less than or equal to

>=
greater than or equal to

==
equal to

If the statement being tested is false, then processing will skip past the endif statement and continue.

An example of a policy that contains version checking from the off97NT4.adm template follows:

PART !!MyDocText EDITTEXT
    VALUENAME "Personal"
    #if VERSION > 1
       EXPANDABLETEXT
    #endif
    REQUIRED
END PART

This example will test to see if the version of Poledit is greater than Version 1, and if it is, will allow environment variables to be expanded.

Make a Template

I will cover the creation process of a Windows 9x template which incorporates a few popular registry hacks. Specifically these hacks are:

Creating the Policies and Parts

To begin creating the policies and parts you will need certain information about each of these registry changes, specifically:

The following tables itemize what is required for each proposed registry change. Once you have the required information, it is necessary to decide how you need to control the user's input. In other words, which part type would be best, or would a simple policy checkbox suffice?

Windows registration names

Under the General tab of the `My Computer' properties window is the name and organization of the registered owner. You may want to change this if workstations are moved from one department to another, or if you just want consistency across workstations. The information for this portion of the template is in Figure 8-7.

Table 8-7: Windows Registration Names

Class

Machine (HKLM)

Registry Key

Software\Microsoft\Windows\CurrentVersion

Valuename Owner

Organization

RegisteredOwner

RegisteredOrganization

Value

Entered by user

Value Type

String (REG_SZ)

The user will enter a varying text string, so obviously a simple policy checkbox will not suffice, and you will need to use a part. The part types that allow for text to be entered are EDITTEXT, COMBOBOX and LISTBOX. As there are no standard owner or organization names, there are no possible suggestions; therefore, COMBOBOX is not a good choice. LISTBOX (which does not support the use of VALUENAME) is not a good choice either as there are specific valuenames. This leaves me with EDITTEXT. Of our EDITTEXT options (Table 8-1), only REQUIRED is applicable since blank text would defeat the purpose of having this option.

It is always helpful to add some explanatory text, and in this case I could simply explain where the changes would be visible (My Computer properties). This section of the template could then appear like this:

KEYNAME "Software\Microsoft\Windows\CurrentVersion"
POLICY !!Changereg
   PART !!Changereg1 EDITTEXT REQUIRED
   VALUENAME "RegisteredOwner"
   END PART
   PART !!changereg2 EDITTEXT REQUIRED
   VALUENAME "RegisteredOrganization"
   END PART
   PART !!changeregtext1 TEXT END PART
   PART !!changeregtext2 TEXT END PART
END POLICY

These statements will create one policy with four parts. One part changes the owner's name, while a second changes the organization name. The remaining two parts add explanatory text. By splitting the text across two parts you prevent it from running off the end of the properties window.

Tips of the day

You can change the tips that display each time Windows 95 loads so that they are specific to your particular organization. These tips display with the Windows welcome screen, beneath the words "Did you know?". The welcome screen on a Windows 98 workstation is not compatible, and so this registry modification will only work with Windows 95. Despite this, it is still a good example to review. The information required for this portion of the template is summarized in Table 8-10.

Table 8-8: Tips of the Day

Class

Machine (HKLM)

Registry key

Software\Microsoft\Windows\CurrentVersion\Explorer\Tips

Valuename

Variable, tips are numbered sequentially

Value

Tip is entered by user

Value Type

String (REG_SZ)

The user will enter a varying text string. Again, a simple policy checkbox will not suffice. The part types that allow for text to be entered are EDITTEXT, COMBOBOX and LISTBOX. COMBOBOX is not a good choice as the tips will be at the discretion of the user, and there are no likely suggestions. EDITTEXT is not an option as there are no specific valuenames. The only part that allows for multiple valuenames is LISTBOX. For LISTBOX options (Table 8-5), I do not need to use VALUEPREFIX, since the tips are simply numbered. ADDITIVE could be used if the user wanted to append the tips to the pre-existing list. EXPLICITVALUE could be used if I wanted to allow the user to number the tips. In that case, the value would be the tip number, while the valuename would be the tip itself. This section of the template could then appear like this:

POLICY !!tips
	KEYNAME "Software\Microsoft\Windows\CurrentVersion\Explorer\Tips"
	PART !!tips LISTBOX
	END PART
	END POLICY

One thing to note is that the tips will not display if the option to show tips is turned off. Since this registry key has a hex value (REG_BINARY), it is not possible to change it using a policy template. However, a registry file could be used from the logon script (see Chapter 4, Building the Policy File) to append the change to the user's registry. This REG file would include the following lines:

[HKCU\Software\Microsoft\Windows\CurrentVersion\Explorer\Tips] 
"Show"=hex:01,00,00,00

A hex value of 00,00,00,00 turns the tips off. Alternately, you could use the admin.adm template to run the program welcome.exe at startup. Doing so will also change the appropriate registry keys.

Sound events

Sound files (WAV files) from the local drive or from the network drive can be used as the system start and exit sound events. The information required for this portion of the template is summarized in Table 8-9.

Table 8-9: Sound Events

Class

Machine (HKLM)

Registry Key

Start

Shutdown

 

AppEvents\Schemes\Apps\.Default\SystemStart\.Current

AppEvents\Schemes\Apps\.Default\SystemExit\.Current

Valuename

[Default]

Value

WAV filename is entered by user

Value Type

String (REG_SZ)

The user will enter a varying text string, so a simple policy checkbox will not suffice. The part options that allow for text to be entered are EDITTEXT, COMBOBOX and LISTBOX. LISTBOX is not an option as there are specific valuenames. There could be suggestions, as there are some standard Windows WAV files; therefore, COMBOBOX is a possible option. I also could choose EDITTEXT, if I did not want to include suggestions or were unsure of which sound files might be available on the local drive. Since it's easiest, I will go with EDITTEXT. Of our EDITTEXT options (Table 8-3), none are really required. Finally, I could choose to have the options displayed as two policies with one part each, or one policy with two parts. This is an individual choice; I chose to display it as two policies. This section of the template could then appear like this:

POLICY !!changestart
    KEYNAME "AppEvents\Schemes\Apps\.Default\SystemStart\.Current"
        PART !!wavfile EDITTEXT
        VALUENAME ""
        END PART
END POLICY
 
POLICY !!changeexit
    KEYNAME "AppEvents\Schemes\Apps\.Default\SystemExit\.Current"
        PART !!wavfile EDITTEXT
        VALUENAME ""
        END PART
END POLICY

Note that although the VAULENAME is displayed in the registry as [Default], you do not use this as the actual VALUENAME. If you did, the template would add a second [Default] VALUENAME rather than editing the true default value. To edit the [Default] VALUE you must use a VALUENAME consisting only of empty quotes.

Menu delay

On the Windows desktop, any associated submenus automatically open when the mouse cursor hovers over a menu. It is possible either to speed up this process or to slow it down so much that it seems to stop completely. In the latter case, a mouse click would be required to open the submenu. The information required for this portion of the template is summarized in Table 8-10.

Table 8-10: Cascading Menus Delay

Class

User (HKCU)

Registry key

Control Panel\Desktop

Valuename

MenuShowDelay

Value

0 to 10,000 milliseconds (Default 400)

Value Type

String (REG_SZ)

The value is a number with a range of 0 to 10,000. The part type that best displays numerical entries is NUMERIC. However, if you look at the value type you see that it is not DWORD, but string. It will be necessary to use the NUMERIC optional keyword (Table 8-2) TXTCONVERT to convert the value to a string. The Windows default delay is 400 milliseconds, so I should use the DEFAULT option and give it this value. Adding a spin dial will make it easier for the user to enter a value, and because increments of less then 500 milliseconds will make very little visible difference, I will set the dial for that incremental value. Finally, I can add a minimum value of 0 and a maximum value of 10,000.

Explanatory text could be added as not many people will be familiar with this setting. It is necessary to explain that lower numbers indicate faster cascading. This section of the template could then appear like this:

POLICY !!menudelay
    KEYNAME "Control Panel\Desktop"
        PART !!menudelay NUMERIC SPIN 500
          VALUENAME "MenuShowDelay"
          TXTCONVERT
          DEFAULT 400
          MIN 0
          MAX 10000
        END PART
        PART !!MENUTEXT TEXT END PART
END POLICY

Hiding drives

Specific drives can be hidden from Explorer and My Computer. A program that bypasses Explorer may still show the contents of these drives, so this policy should not be relied upon to keep out malicious users (see Chapter 6, Troubleshooting for more information). The information required for this portion of the template is summarized in Table 8-11.
Table 8-11: Hidden Drives

Class

User (HKCU)

Registry key

Software\Microsoft\CurrentVersion\Policies\Explorer

Valuename

NoDrives

Value

A: 1, B: 2, C: 4, D: 8, E: 16, F: 32, G: 64, H: 128, I: 256, J: 512, K: 1024, L: 2048, M: 4096, N: 8192, O: 16384,P: 32768, Q: 65536, R: 131072, S: 262144, T: 524288, U: 1048576, V: 2097152, W: 4194304, X: 8388608, Y: 16777216, Z: 33554432, ALL 67108863

To hide more than one drive, sum the value of each drive. For example, to hide A:, B:; and C:, add 1 + 2 + 4 =7

Value Type

Binary (REG_DWORD)

A simple policy checkbox could be used for each drive letter; however, to include all drives would necessitate having 26 policy checkboxes under one category. It would not appear as cluttered if you use one of the part types that allow the user to make a choice from a list of suggestions. part types fitting this description are COMBOBOX and DROPDOWNLIST. COMBOBOX is not a good choice as it allows user input and the user probably won't have any idea of which value to enter. This leaves me with DROPDOWNLIST. Of the DROPDOWNLIST options (Table 8-3), you may want to use NOSORT to display the drive optionS in a specific order. I will also use a Default value of 0 (no hidden drives), in case the option is checked inadvertently.

Only one drive, or a single combination of drives can be chosen. It would not be possible to display all 26 drive letters and allow the user to check off more than one drive to hide, as there is no template syntax to allow additive values. The last drive checked would be the hidden drive, while the others would simply be ignored. To allow the user to hide more than one drive, I must create specific options to do this in the drop-down list. In addition, explanatory text could mention that the drives would be hidden only in certain program areas. This section of the template could then appear like this:

POLICY !!HideDrives	
	KEYNAME Software\Microsoft\Windows\CurrentVersion\Policies\Explorer
		PART !!HIDEDRIVES DROPDOWNLIST REQUIRED
		#if version > 1
		NOSORT
		#endif
		VALUENAME "NoDrives"
			ITEMLIST
			NAME !!A VALUE NUMERIC 1
			NAME !!B VALUE NUMERIC 2
			NAME !!C VALUE NUMERIC 4
			NAME !!AB VALUE NUMERIC 3
			NAME !!ABC VALUE NUMERIC 7
			NAME !!CLEARALL VALUE NUMERIC 0 DEFAULT
			END ITEMLIST
		END PART	
		PART !!HIDEDRIVESTEXT1 TEXT END PART
		PART !!HIDEDRIVESTEXT2 TEXT END PART

In this example, I will allow the user the option to hide only drive A, only drive B, only drive C, both drive A and B, or all three drives A, B, and C.

Putting It Together

Once you have the policies and parts, you must group them into categories and then put those categories into their appropriate classes. I have already indicated in which class each policy belongs. Specifically, the policies in class MACHINE are those that change the Windows registration names and show daily tips. The other policies (sound events, menu cascade delay and hide drives) belong in USER.

Grouping the policies into categories is simply a process of deciding the most logical way to group them. In this example I will simply create one category for each of the Tables through Table 8-11.

Finally, a Strings section must be created for each value preceded by !!, with the text definition of that string. The complete policy template would appear like this:

; chapter8.adm
;;;;;;;;;;;;;;;;;;;;;
CLASS MACHINE  ;;;;;;
;;;;;;;;;;;;;;;;;;;;;
 
CATEGORY !!changereg
KEYNAME "Software\Microsoft\Windows\CurrentVersion"
	POLICY !!Changereg
		PART !!Changereg1 EDITTEXT REQUIRED
		VALUENAME "RegisteredOwner"
		END PART
		PART !!changereg2 EDITTEXT REQUIRED
		VALUENAME "RegisteredOrganization"
		END PART
		PART !!changeregtext1 TEXT END PART
		PART !!changeregtext2 TEXT END PART
	END POLICY
END CATEGORY
 
CATEGORY !!TIPS
	POLICY !!tips
	KEYNAME "Software\Microsoft\Windows\CurrentVersion\Explorer\Tips"
	PART !!tips LISTBOX EXPLICITVALUE
	END PART
	END POLICY
END CATEGORY
	
;;;;;;;;;;;;;;;;;;;;;
CLASS USER   ;;;;;;;;
;;;;;;;;;;;;;;;;;;;;;
 
CATEGORY !!changesounds
	POLICY !!changestart
	KEYNAME "AppEvents\Schemes\Apps\.Default\SystemStart\.Current"
		PART !!wavfile EDITTEXT
		VALUENAME ""
		END PART
	END POLICY
 
	POLICY !!changeexit
	KEYNAME "AppEvents\Schemes\Apps\.Default\SystemExit\.Current"
		PART !!wavfile EDITTEXT
		VALUENAME ""
		END PART
	END POLICY
END CATEGORY
 
CATEGORY !!menudelay
 
	POLICY !!menudelay
	KEYNAME "Control Panel\Desktop"
		PART !!menudelay NUMERIC SPIN 500
		VALUENAME "MenuShowDelay"
		TXTCONVERT
		DEFAULT 400
		MIN 0
		MAX 10000
	END PART
		PART !!MENUTEXT TEXT END PART
		END POLICY
END CATEGORY
 
CATEGORY !!HIDEDRIVES
	POLICY !!HideDrives	
	KEYNAME Software\Microsoft\Windows\CurrentVersion\Policies\Explorer
		PART !!HIDEDRIVES DROPDOWNLIST REQUIRED
		#if version > 1
		NOSORT
		#endif
		VALUENAME "NoDrives"
			ITEMLIST
			NAME !!A VALUE NUMERIC 1
			NAME !!B VALUE NUMERIC 2
			NAME !!C VALUE NUMERIC 4
			NAME !!AB VALUE NUMERIC 3
			NAME !!ABC VALUE NUMERIC 7
			NAME !!CLEARALL VALUE NUMERIC 0 DEFAULT
			END ITEMLIST
		END PART	
		PART !!HIDEDRIVESTEXT1 TEXT END PART
		PART !!HIDEDRIVESTEXT2 TEXT END PART
END POLICY
END CATEGORY
 
[STRINGS]
changereg="Change Registration"
changereg1="Registered Owner"
changereg2="Registered Organization"
changeregtext1="Change registration names under the "General" tab of"
changeregtext2=""My Computer" properties window"
tips="Write out your personalized "Tips of the Day""
changesounds="Change Windows Sound Events"
changestart="Change Windows Start Sound"
wavfile=".WAV file to use"
changeexit="Change Windows Exit Sound"
menudelay="Delay in milliseconds"
menutext="Change the delay before submenus automatically cascade open"
hidedrives="Hide Drives"
A="Restrict Drive A"
B="Restrict Drive B"
C="Restrict Drive C"
AB="Restrict Drive A and B"
ABC="Restrict Drive A, B, and C"
clearall="Do not restrict any drives" 
hidedrivestext1="Hide one or more drives from My Computer and Explorer"
hidedrivestext2="Note: Do not use with other "hide drives" policies"

Debugging the Template

Debugging the template, at least as far as proper syntax is concerned, is amazingly simple. Once you have completed the text file, save it with the ADM extension. Then load the template into the SPE. If an error is found, the SPE will display an error message telling you the line that caused the error, the unexpected keyword or text and a list of suitable keywords for the problem area.

However, the SPE will not check to see if the KEYNAME or values are reasonable. That can be done only by actually setting the policy options to see if you get the expected result in the registry or your program. One thing to note, if you make changes to the template while the SPE is still open, you must reload the template again for those changes to be visible in the SPE. To do this, select Options Template and then select the OK button. As an alternative, you can close the SPE, make the modifications to your template and then start the program up again. This will have the same effect since the template is reloaded automatically each time the SPE starts.

WARNING:

Always back up your registry before trying out your new template!

Summary

The template can be broken down into four main zones (class, category, policy and part). The class and category zones are mostly organizational in nature, while the policy and part zones contain the actual registry changes. The use of a template is made easier through the application of one or more of the seven part types (TEXT, EDITTEXT, CHECKBOX, NUMERIC, DROPDOWNLIST, COMBOBOX and LISTBOX). These part types allow the data to be collected in the most logical way based upon the value type and really account for the template's true versatility.

If you are like me, you will be eager to find all your favorite registry hacks to see if they can be incorporated into a custom policy template. If the hack is to a subkey of the HKCU or HKLM, and it has a value type of string (REG_SZ and REG_EXPAND_SZ) or DWORD (REG_DWORD) you probably can. Unfortunately, if the key is outside of the top-level keys HKCU and HKLM or if it has a Binary (REG_Binary) or other Windows NT registry value, those keys will still have to be edited by hand using the registry editor or a REG file. Despite these drawbacks, custom templates will extend the functionality of the SPE even into those organizations that use only in-house programs.

Back to: Windows System Policy Editor


O'Reilly Home | O'Reilly Bookstores | How to Order | O'Reilly Contacts
International | About O'Reilly | Affiliated Companies

© 2001, O'Reilly & Associates, Inc.
webmaster@oreilly.com