We registered a COM object on our IIS 5.0 Web server. The object reads a configuration file to determine which drives the application should save data to. We mapped drives to remote shares and can't get the COM object to use the correct NTFS permissions. We gave the mapped drive permissions to the IUSR_hostname account, which should have let the object write to the remote location, but that didn't work. How do we assign a user account to a COM object?
I take a deep breath every time I see a question about COM security and user accounts. COM security is a complex subject, so a brief explanation can be dangerous. Don't use mapped drives. You don't need to do so on a server because Universal Naming Convention (UNC) paths typically work in scripting languages. In addition, mapped drives are part of the profile of the user who created the mappings. If anyone else logs on to the server from the console, the drive mappings can disappear or crash your application. In the past, mapped drives let you use 16-bit applications that didn't understand UNC paths in new OSs. They linger on as a convenience for client OSs but generally shouldn't be used on IIS servers. For more information about mapped drives, see the Microsoft article "Using Mapped Drives with IIS" (http://support.microsoft.com/default.aspx?scid=kb;en-us;q257174).
To eliminate mapped drives in your COM object, reference the remote location's UNC pathname. To provide the appropriate NTFS permissions on the remote content, you must know the object's security context (i.e., the user account that hosts the process that invokes the COM object). To discover the user account, code your object so that it can access a local file and audit successful read events. Then, run your application and see which user the Event Viewer Security log reports.
Typically in Windows 2000, COM objects run in the security context of the user who calls them. So if you allow anonymous authentication, the object will probably run as the IUSR account, just as you suspected. If you're loading the COM object from an Internet Server API (ISAPI) application, your ISAPI application might be calling the RevertToSelf function (http://msdn.microsoft.com/library/default.asp?url=/library/en-us/security/security/reverttoself.asp), which would cause the COM object to run in the System or IWAM_hostname account. The System account runs the Inetinfo process, and IWAM_hostname runs the DLLHOST process for out-of-process Web applications. The COM object typically "impersonates" the user, but calling RevertToSelf makes the application drop this impersonation and changes the COM object security context.
The IIS 5.0 Security Checklist offers some advice about this topic. Use the DumpBin tool to see whether the executable calls certain APIs. (DumpBin is included with many Win32 developer tools.)
For example, use the following syntax if you want to see whether a file named myisapi.dll calls RevertToSelf:
dumpbin /imports myisapi.dll | find "RevertToSelf"
If you don't see a result, myisapi.dll isn't calling RevertToSelf directly but might be calling the API through LoadLibrary, in which case you could use a similar command to search for the file.
If your object is running as System, you won't be able to access the remote content because the System account doesn't have network privileges. If your object is running as the IWAM user, it probably doesn't have credentials across the network. Run the COM object as a user, not as IUSR or IWAM. These accounts should have minimal NTFS permissions on the local server and certainly shouldn't have network privileges. (By default, the local IUSR account won't be able to access the network, either.)
To get back to your question about assigning a user account to the COM object, you can do so in the Microsoft Management Console (MMC) Component Services snap-in, which you can access from the Administrative Tools menu. Create your COM object as a package and select Expand Computers, My Computer. Then, right-click COM+ Applications, select New, and select Application from the context menu. This process launches the COM Application Install Wizard. Follow the prompts to import your package into Component Services.
Right-click the imported Package, select Properties, then select the Identity tab, which has two choices: Interactive userthe current logged on user and This user, with entries for User, Password, and Confirm password. Select This user and click Browse to select a user that both the remote and local systems can authenticate. Click OK, then restart IIS. You might need to use dcomcnfg.exe to assign launch permissions to this object's user.
Your COM object should now neatly reference the UNC location of your choice in a user context other than the anonymous user. You can also specify this information in the COM object code, if you prefer. Be sure to assign NTFS permissions on the remote content to allow access to the COM object's user.
Let me address another matter while I'm discussing this topic. IIS 5.0 and IIS 4.0 both have problems when file-change notifications that originate on the remote system are passed back to the IIS server. (IIS has a history of not receiving file-change notifications from content accessed on a remote server by using a UNC pathname.) Problems can arise when IIS delivers stale data.
In addition, when the system is under load, you might run up against built-in limits in internal resource management for files accessed with UNC pathnames. For more information about this problem, see the Microsoft article "IIS Runs Out of Work Items and Causes RPC Failures When Connecting to a Remote UNC Path" (http://support.microsoft.com/default.aspx?scid=kb;en-us;q221790).