Since its introduction as Windows NT Server 4.0, Terminal Server Edition (WTS), Terminal Services has been a popular Windows feature, and its ease of use has increased dramatically with each new version of the Windows server family. In Windows .NET Server, Terminal Services is so useful that the functionality alone might be reason enough for your business to migrate to a .NET infrastructure. To best evaluate what’s new in Terminal Services for .NET Server, you need to examine the server features, then see how the client integrates into the server. You also need to consider how Terminal Services for .NET Server handles remote server administration and application hosting.
Remote Administration by Default
When Microsoft first introduced WTS, the product was separate from the rest of the NT Server 4.0 family. You couldn’t install WTS on an existing server; Microsoft required that you purchase the OS software and perform a clean installation. In Windows 2000 Server, Terminal Services became a feature under Windows Components that you could enable through the Control Panel Add/Remove Programs applet. During Win2K Terminal Services setup, you specify whether you want to use Terminal Services in Remote Administration mode or in Application Server mode (for hosting applications). This choice determines several Terminal Services settings, such as maximum number of connected users and whether the system puts a priority on its Terminal Services users.
In .NET Server, Terminal Services further separates remote administration from application hosting. (The vast majority of Terminal Services installations on servers are intended for remote administration rather than for application hosting.) The feature retains its maximum of two connected users—unlike Windows XP’s Remote Desktop maximum of one connected user (i.e., your direct connection to the client’s console). XP’s Remote Desktop isn’t intended as an administration tool; rather, its purpose is to permit users to connect remotely to their PCs. To differentiate between XP’s and .NET Server’s implementations of the technology, Microsoft calls the .NET Server feature Remote Desktop for Administration. In .NET Server, Microsoft has simplified the Terminal Services application server–mode terminology to simply Terminal Server. (You enable Terminal Server in the Add/Remove Programs applet.) The underlying technology that powers both Remote Desktop for Administration and Terminal Server is Terminal Services.
Enabling remote administration through .NET Server’s Remote Desktop for Administration is a straightforward two-step process. The first step is to permit remote access to the computer that you want to administer. On the Control Panel System applet’s Remote tab, select the Allow users to connect remotely to this computer check box, as Figure 1 shows. The second step highlights enhancements in the Terminal Services security model.
In Win2K, the Terminal Services security model works differently from other server-management tools. To configure which users can access the server, you must launch the Microsoft Management Console (MMC) Terminal Services Configuration snap-in, select the RDP-Tcp connection, click Properties, and select the Permissions property sheet to access the familiar ACL dialog box.
Terminal Services in .NET Server has more familiar foundations. Every .NET Server machine has a built-in Remote Desktop Users group, which lets you manage remote permissions. This group is a local group on member servers and a domain local group on domain controllers (DCs). You can create a practical security model based on this group. The first step is to rename the Remote Desktop Users domain local group to a more appropriate name (e.g., Remote DC Users) because the group controls access only to DCs. Next, per good security practice, populate this group only with groups—not individuals—that require local access to DCs. (The Remote Desktop Users group isn’t populated when you enable Remote Desktop for Administration on the server.) One annoyance is that you can’t add another built-in local group (e.g., Administrators) to the built-in Remote Desktop Users group. However, you can add a global group (e.g., Domain Admins). To be fair, this limitation isn’t Terminal Services’ fault—it’s inherent in the base security model.
You can create a Remote Client Users group in the domain and populate it with groups (e.g., Help Desk). Placing the Remote Client Users group into each client’s Remote Desktop Users local group completes the security model. At first glance, you might think that you could use Group Policy’s Restricted Groups to control the membership of the client’s Remote Desktop Users group. However, Restricted Groups doesn’t currently support a merge function that combines users and groups at the domain or organizational unit (OU) level into the local group’s existing membership, so Restricted Groups would override the client’s local Remote Desktop Users membership. Because the client’s own user object resides in the local Remote Desktop Users group, it would be overridden and the client wouldn’t be able to remotely access his or her machine. However, you can use Restricted Groups to easily control the membership of the domain’s Remote Client Users group.
Connecting to the Console Session
The big news for Terminal Services remote administration in the enterprise server–management arena is a tiny option not available in Win2K. On a Win2K server, you can remotely manage just about anything, but you can’t connect to the server’s console session—aka session ID 0—which is the session you see when you log on to the physical server console. Some applications (e.g., antivirus software) display their UI only to session ID 0. Also, many system messages pop up only on session ID 0. Because Win2K doesn’t offer this important functionality, Win2K Terminal Services doesn’t negate the need for third-party remote-console applications at many companies.
The ability in .NET Server to access this console session is by itself an important business reason to deploy .NET Server. You get true remote management at no extra cost, and you can replace any third-party console software that you have. To connect directly to the server’s console session, you can either select the Connect to console check box in the MMC Remote Desktops snap-in (this check box is selected by default) or use the Remote Desktop Connection (mstsc.exe) program’s /console switch.
You won’t immediately know that you’re connected to the console. To determine whether you’re connected to session ID 0, you can launch the MMC Terminal Services Manager snap-in from Administrative Tools and select the server in question. You can also use the environment-variable Query Session command from a command prompt. Also, if you attempt to log on to the physical console while someone is connected remotely, you’ll receive a message that warns you about the other logged-on user, preventing you from accidentally logging off another administrator who’s doing console work.
New Group Policies
Microsoft has added 36 new Group Policies to Terminal Services. These Group Policies—which reside in Computer Configuration (or User Configuration), Administrative Templates, Windows Components, Terminal Services—control seven functions: client/server data redirection, encryption and security, licensing, temporary folders, Session Directory, sessions, and general settings.
Client/server data redirection. The Group Policies concerning client/server data redirection (which works with Terminal Services to send server-side session data to the client, as well as handy client information to the server) let you control some of the slickest new Terminal Services features. In Win2K, you can redirect only the client’s local printer—a capability that lets you print effectively from the server—but in .NET Server you can redirect audio, the clipboard, COM ports, LPT ports, smart cards, and even time zones. Time-zone redirection, for example, is essential for companies that have offices in several time zones. Terminal Server sessions will show the users’ local time regardless of whether the terminal server resides in their time zone. However, the most impressive new redirection feature involves the client computer’s drives. By default, Terminal Server automatically maps client drives upon connection. Mapped drives appear in the session folder tree in Windows Explorer or My Computer in the format \TSCLIENT\drive letter. This useful feature simplifies the transfer of data between the client and host computers. The client/server data-redirection policies let you enable or disable each redirection type independently. You might want to disable this capability if you have sensitive data on the terminal server that you don’t want to end up on a client’s notebook or if a local edit on the client would sidestep document management on the server.
Encryption and security. The Group Policies concerning encryption and security have two functions. The first function lets you enable or disable users’ ability to automatically log on to a terminal server by supplying a password from the Remote Desktop client. The second function lets you determine whether the client can set the encryption level and whether to require high encryption for all connections.
Licensing. The Group Policy concerning licensing controls whether a .NET Server license server can provide licenses to a Win2K server. Enabling this policy prevents .NET Server Terminal Services from allocating Client Access Licenses (CALs) to clients connecting to Win2K terminal servers.
Temporary folders. The Group Policies concerning temporary folders determine whether each user gets a \temp directory or the system throws temporary files for all users into one directory. Another policy determines whether the system clears the client’s \temp directory at logoff.
Session Directory. The Group Policies concerning Session Directory control several aspects of Session Directory configuration for a terminal server farm. I cover this in more depth in the Application Hosting section.
Sessions. The Group Policies concerning sessions control the length of time that active, idle, and disconnected Terminal Services sessions remain on the server before the system disconnects or deletes them. These policies are probably your first line of defense for terminal servers that are approaching their capacity.
General settings. Thirteen general Terminal Services policies concern bandwidth control (e.g., Enforce removal of desktop wallpaper, Limit maximum color depth), management (e.g., Restrict Terminal Services users to a single remote session, Remove Disconnect item from Shut Down dialog), and roaming profiles and user home directories. One useful policy for the Terminal Services administrator is Allow users to connect remotely using Terminal Services. This policy is particularly handy if you need to shut down a busy terminal server farm for maintenance. You can use the Change logon /disable command from a command prompt on each terminal server, but such individual configuration is impractical in a large terminal server farm. Just when you think you’ve kicked everyone off, someone else logs on. The Allow users to connect remotely using Terminal Services policy lets you lock out new connection attempts and effectively drain all of an OU’s terminal servers before shutting them down.
.NET Server Terminal Services’ Remote Assistance feature is a boon to companies that have servers and administrators distributed across a wide geographic area. I’ve witnessed many situations in which an enterprise’s remote server management center or second-level support center would benefit from the ability of a third-level support entity to "look over their shoulder" to observe errors encountered on a server—for example while deploying a service pack or hotfix. Simple remote-console tools don’t offer such capability, but Remote Assistance lets you either monitor a session or take control of it so that the server operator can follow your actions. (A target machine configured only for remote administration won’t permit this type of connection.)
To enable Remote Assistance, you use the same Remote tab (which Figure 1 shows) on which you enable remote administration. The client requesting assistance is called the Novice, and the user heeding the request is the Expert. For basic information about Remote Assistance, see Sean Daily, "XP’s Help and Support Features," May 2002.
Users can request remote assistance in three ways, but only one of these options is truly suitable for enterprise server management. The first two methods—email and Windows Messenger—are acceptable for remote assistance in XP (e.g., if your brother-in-law needs help straightening out his email settings but you don’t want to drive to his house). However, good security practice dictates that email and Windows Messenger shouldn’t be installed on active servers that you aren’t using for terminal-server application hosting.
The third method for requesting remote assistance is to create and save an invitation. On the main Remote Assistance screen—accessible from Start, Help and Support, Remote Assistance—the Novice selects Invite someone to help you, then clicks Save at the bottom of the next page. The Novice can then choose how he or she wants to send the saved invitation file to an Expert—for example, by storing it on a disk or a shared network location, or by sending it over another email service or an FTP connection.
I recommend using a standardized hidden share (e.g., RA$), with permissions locked down so that only support personnel can read or write to the file. In this scenario, the Novice creates the invitation, which has a password and default 1-hour expiration time, and saves it to the share. I recommend using the target server’s NetBIOS name as the invitation’s filename so that you can easily scrub the share of old invitations. (The extension will be .msrcincident.) As the Expert, you access the share, open the invitation, and accept it. The Novice accepts your request to join, and you connect to the remote session. If the novice grants you permission, you can also take control of the session by clicking the Request Control button on the toolbar at the top of the main Remote Assistance screen.
Win2K’s Terminal Services implementation provides a neat solution for users who need to access a standard set of applications without installing them locally. For example, imagine a thin-client scenario at a manufacturing company. Client machines are primarily used for factory applications, but the machines have the Remote Desktop Connection program installed. A centrally located terminal server containing popular Microsoft Office applications lets the factory users open standardized human resources documents in, for example, Microsoft Word—without installing Office locally. However, Win2K’s solution doesn’t transparently scale outward to multiple servers. As the terminal server user population increases, each group of users must be assigned to a specific server, but moving Win2K users from one terminal server to another to balance the terminal servers’ loads is problematic.
.NET Server introduces terminal server connection management, which works with a load-balancing service (e.g., Network Load Balancing—NLB) to scale Terminal Services for application hosting beyond Win2K’s native functionality. Terminal server connection management groups terminal servers into farms, and each farm appears to clients as one machine with one IP address. This scenario is essentially the classic definition of a cluster—and indeed it is a cluster. However, it’s an NLB cluster rather than a server cluster. NLB clusters provide scalability and high availability for TCP- and UDP-based services and applications by combining as many as 32 servers running .NET Enterprise Server into one cluster. By using NLB to group several cloned (or identical) clustered computers into one logical resource, you can enhance the availability of applications.
A terminal server load-balancing cluster lets users connect to the cluster and log on, log off, disconnect, or reconnect to their terminal server session just as they would on a typical server. Figure 2 shows what happens behind the scenes when a user connects to a terminal server farm. First, the user connects to the Session Directory. Second, the Session Directory informs the client which terminal server he or she can connect to or where the client has an existing session. Third, the client connects directly to the specified terminal server. If you want to engineer such a solution, you first need to overcome several potential problems. Working through these problems can provide an overview of how a terminal server cluster works.
How are new clients directed to an available terminal server, and why don’t they need to know the individual server’s name or IP address? The NLB service handles new clients, which don’t have an existing session on a terminal server in the farm or cluster. The service also maps the client to the appropriate server within the farm; the client needs only to know the cluster’s name or address. After you determine which servers you want to add to your Terminal Services farm, set up NLB between them. .NET Server’s Help offers extensive documentation about how to plan and implement an NLB cluster.
How does the cluster keep track of which user is connected to which session on which server? Terminal Services’ new Session Directory service is a database that keeps track of sessions on terminal servers in a cluster. The service also provides the necessary information at connection time to connect users to existing sessions. Session Directory runs on one server, and that server doesn’t need to have Terminal Services installed or Remote Desktop enabled. To create a Session Directory server, you change the Terminal Services Session Directory service from manual (or disabled) to automatic, then start the service. By default, this service is installed in manual startup mode on all .NET Server machines. According to Microsoft, the service isn’t particularly resource-intensive, so it needn’t reside on a dedicated server.
How do you inform the Session Directory server about the location of its authorized terminal servers? When you first start the Terminal Services Session Directory service, the system creates a local group called Session Directory Computers. The Session Directory service won’t accept any connections from servers whose domain computer accounts aren’t included in this group. By default, the Session Directory Computers group contains all domain computers; you can use the group to lock down your Session Directory. The default setting is the easiest but most insecure setting.
How do you inform the terminal servers about the location of their Session Directory server? Group Policy is the best method for directing terminal servers to their Session Directory server. Place all your terminal servers in one OU (e.g., TS Cluster), then create a Group Policy Object (GPO) for the OU. Edit the new policy and drill down to Computer Configuration, Administrative Templates, Windows Components, Terminal Services, Session Directory. On the resulting screen, you can name the cluster, tell it where its Session Directory server resides, and notify all the cluster’s terminal servers that the Session Directory server is active. Figure 3 shows the Session Directory policies. Notice the helpful policy description in the Session Directory pane (new for .NET Server Administrative Templates). The Supported on text on the Properties dialog box’s Setting tab helps you determine on which OS version the policy will be effective.
Consider installing a second NIC on each server in your terminal server farm—one for Terminal Services client network traffic and the other for server-to-server network traffic. Separating these two types of traffic can provide a performance boost. Also, placing all clustered terminal servers under one GPO has benefits beyond easily configuring the Session Directory service—it also lets you configure other policies in the GPO identically across the grouped terminal servers.
.NET Server’s Terminal Services has built upon an already powerful Win2K feature set. On the remote-management side of the equation, the ability to use Remote Assistance and control the server console are strong arguments in favor of upgrading your DC infrastructure from Win2K to .NET Server. On the application-hosting side, Terminal Services load-balancing clusters let you greatly increase the number of clients that can use remote application hosting—and still keep things simple for your users.
Sean Deuby is a contributing editor for Windows & .NET Magazine and a senior Windows 2000 and Windows NT systems engineer with Intel, where he specializes in enterprise Win2K and Windows .NET Server design. He is the author of Windows 2000 Server: Planning and Migration (Macmillan). You can reach him at firstname.lastname@example.org.