I installed Windows 2000 Service Pack 2 (SP2) 128-bit encryption on a new server, and I'm trying to set the option to change passwords through Microsoft Internet Information Services (IIS) 5.0. The Win2K server is a member of a Windows NT 4.0 domain. The installation also consists of migrated content from another server running Internet Information Server (IIS) 4.0. I used Robocopy to copy the content to the new server, and I used Addusers to replicate the user accounts. I added the virtual directory for Iisadmpwd in the Default Web Site. I've enabled Basic and Integrated Windows authentication and required 128-bit Secure Sockets Layer (SSL) connections. When a user accesses the site, the site asks for the user's username and password, accepts them, and seems to work. The account, however, is marked must change password at next login, so the server brings up the page for an expired password and prompts the user to change his or her password. When the user submits the change, the server immediately prompts the user again to change the password. Why doesn't the password change?

Migrating from IIS 4.0 to IIS 5.0 is quite a task, and you've used a methodology that I often recommend. Your migration and 128-bit encryption shouldn't be causing problems. However, before I talk about a solution, let me say that I don't recommend that you let users change passwords to Win2K or NT 4.0 accounts over the Internet unless you're using a VPN. Changing passwords over the Internet isn't a good idea for two reasons. First, having that kind of doorway open to anyone who can find it is a security risk. Second, the only way you can use a browser to effectively authenticate over the Internet is to set Basic authentication, which requires SSL to be secure. Therefore, authentication over the Internet requires constant diligence to maintain security. In addition, when you've authenticated with Basic authentication, you can't turn off SSL because the server sends credentials with each request for a file. As you discovered, when you perform a clean installation of IIS 5.0, the Iisadmpwd virtual directory, which contains the files that let users change passwords, isn't present as it was in IIS 4.0.

Nevertheless, the required files are loaded onto the IIS 5.0 server, and you can manually create the Iisadmpwd virtual directory and map it to \%systemroot%\winnt\system32\iisadmpwd. In that virtual directory, you'll discover the infamous .htr files that let users change passwords for their user accounts over the Internet. (I say infamous because the .htr files have been the subject of more than one Microsoft security bulletin. My bias is that when a particular feature has been nailed a few times as a security problem, that feature is more likely than other parts of the server to turn up further problems.)

If you don't manually create the Iisadmpwd virtual directory, the .htr files are still present on your server and make a potential target to malicious users. I suggest removing the .htr files and the Application Mapping feature in IIS 5.0, which maps the .htr files to C:\winnt\system32\inetsrv\ism.dll.

In addition to manually creating the Iisadmpwd virtual directory (or otherwise providing access to it), you must make a change to the metabase. Set the value in the metabase for w3svc/<n>/passwordchangeflags, where <n> is the instance number for the Web site:

  • 0—Password changes require an SSL connection.
  • 1—Password changes don't require an SSL channel.
  • 2—Password change notification is disabled.
  • 4—Advanced notification of password change is disabled.

You can use MetaEdit or scripting with Microsoft Active Directory Service Interfaces (ADSI) to set this value.

Aside from security problems with changing passwords over the Internet, at least one operational difficulty, which you seem to have encountered, exists with IIS 5.0. Because IIS 5.0 manages the password-change process differently than IIS 4.0 does, if you don't allow Anonymous access to the Iisadmpwd virtual directory, you wind up in an infinite loop. (Clearly, Anonymous access to the password-change files isn't a great idea.) Fortunately, a hotfix is available for this bug. Contact Microsoft Product Support Services (PSS) at for the hotfix.

How can I determine the password for the IUSR_computername and IWAM_computername accounts that Microsoft IIS installation creates?

These accounts' passwords reside in the user account database (i.e., the SAM) on Windows 2000 (without Active Directory—AD) and Windows NT 4.0 or in AD on Win2K domain controllers (DCs). As a result, obtaining passwords from those data stores is a severe breach of security. Although you can obtain those passwords by using a few tools, you don't have to work that hard because the passwords also reside in the metabase. Enter the script that Listing 1 shows in a text editor such as Notepad, then save the script as getpass.vbs (any name will do as long as it ends in .vbs). When you execute the script, you'll see the username and password of the default IUSR_computername and IWAM_computername accounts.

My site depends heavily on Secure Sockets Layer (SSL). I am trying to determine resource requirements and am wondering how long an SSL session is maintained once created. If I navigate away from a secure page and then back right away, the session resumes. How long does this session stay valid when not in use?

Although SSL is very useful, it's an expensive operation from the viewpoint of server resources. I recommend using SSL only when necessary, which varies from not at all for casual Web sites to always for stockbroker Web sites. So, planning for how much load SSL places on your server is important in high-volume sites.

The amount of time an SSL session stays open is important. You want to release server resources as soon as you can, but if you release them too quickly, you'll need to rebuild the SSL session, which increases the burden on the server. Microsoft changed the default timeout for the SSL session cache from 2 minutes in Windows NT 4.0 to 5 minutes in Windows 2000. If you expect extended SSL sessions, I recommend increasing the SSL session timeout, which the ServerCacheTime registry entry controls. (If you enable HTTP 1.1 KeepAlives, the server ignores the timeout parameter and doesn't terminate a session until the browser explicitly closes the connection or the TCP/IP session times out. KeepAlives are enabled by default.)

This registry entry isn't present by default. To add the registry entry, you need to create the ServerCacheTime REG_DWORD value in the HKEY_LOCAL_MACHINE \SYSTEM\CurrentControlSet\Control\SecurityProviders\SCHANNEL registry subkey. (Always back up your metabase before making changes to it.) After you've created the value, set the data field to the number of milliseconds (ms) you want for the timeout. (The default value of 5 minutes in Internet Information Services—IIS—5.0 is 300,000ms.) You can find details about this and other useful IIS 5.0 tuning tips and tricks at

I run an application on Internet Information Server (IIS) 4.0 that uses the Session_onEnd event to trigger cleanup for the application. I've discovered that the event doesn't always fire when a session ends. Some articles and newsgroups state that this problem is a known bug. I can't find any such reference, but clearly Session_onEnd isn't working as expected in IIS 4.0. My tests with Internet Information Services (IIS) 5.0 show that Microsoft has apparently fixed the problem. Can you shed some light on this bug in IIS 4.0?

The problem isn't a bug. Rather, it boils down to a COM threading problem. The answer to your question requires an understanding of how COM components work with various threading models. Details about this important subject are beyond the scope of this answer, but IIS administrators should have a keen interest in this topic for several reasons. The chief concern is that COM objects that your system uses (including Microsoft-provided COM objects) can dramatically affect performance and scalability.

When you create a COM object, it's assigned a threading model. Three threading models exist:

  • Apartment threading—Only one thread from an object can communicate with the server. You can, however, have multiple instances of the object, each with its own thread. This threading model is the only one that the Microsoft Access database engine supports, which is the primary reason Microsoft recommends Microsoft SQL Server as the database of choice with IIS.
  • Free threading—An object can use (spawn) multiple threads.
  • Both threading—An object can be accessed as an Apartment-threaded object or Free-threaded object.

You asked why Session_onEnd doesn't appear to fire in IIS 4.0 but seems to work in IIS 5.0. By default, ADO is marked as Apartment threaded in the registry, which means that one thread is at work for a database access request. In this mode, the thread that creates the ADO object is the same thread that must destroy the ADO object. Let's say that a user makes a query to a database and that database isn't available for 15 minutes. Tired of waiting, the user leaves the page and goes back to downloading .mp3 files or whatever he or she was up to. The user session is over, but the thread that must destroy the session isn't available because it's still waiting on the database. Session_onEnd actually fires, but a thread can't destroy the ADO object because the only thread that can do the job is busy. This delay gives the appearance that Session_OnEnd never fired.

This same sequence of events can occur if you try to use Active Server Pages (ASP)­intrinsic objects in Session_onEnd. You can't, for example, use the Response object to send information to the browser because the session is closed. This fact might seem obvious to some, but it eludes more programmers than you might think.

So, how did Microsoft improve this functionality in IIS 5.0? IIS 4.0 trusts the registry setting that says ADO is Apartment threaded, but IIS 5.0 doesn't. Instead, IIS 5.0 queries the component to get its threading model. ADO is really Both threaded, so IIS 5.0 can create the ADO object on one thread, then use another thread to destroy the ADO object. This ability makes the Session_onEnd event appear fixed in IIS 5.0.

You can reconfigure ADO so that it's marked as Both threaded on Windows NT 4.0 by modifying the registry. (Always use extreme caution when editing the registry.) Microsoft provides a file to assist with this reconfiguration. To reconfigure ADO, follow these steps:

  1. Locate the file adofre15.reg. (If you accepted the defaults for program file location when you installed IIS, adofre15.reg will be in C:\program files\common files\system\ado.)
  2. Make the directory containing the file your current directory, and issue the regedit adofre15.reg command. Reboot the server.
  3. If you make the above change and decide to return to the Apartment-threaded model, repeat the above process with the adoapt15.reg command.