Multiple vulnerabilities were found in IIS 6.0 and 7.5 web servers. On the Full-Disclosure mailing list, Kingcope posted several IIS 6.0 and 7.5 bugs (also published as Exploit-DB 19033). Because I am a Windows Server and IIS admin, I took some time to test the various vulnerabilities...
An IIS PHP handler without resourceType="File" lets an attacker append /.php to an .aspx URL and get the source code back. Configure the PHP handler properly, or deny such URL sequences with URL Rewrite, Request Filtering or Helicon Ape.
I originally wrote this post in 2012, about IIS 6.0 (Windows Server 2003) and IIS 7.5 (Windows Server 2008 R2). Both are long out of support. A correctly configured PHP handler with resourceType="File" is still good practice on IIS 10, though.
The Windows bugs Kingcope posted are:
- Microsoft IIS 7.5 .NET source code disclosure and authentication bypass
- Microsoft IIS 7.5 Classic ASP Authentication Bypass
- Microsoft IIS 6.0 with PHP installed Authentication Bypass
I was successful in reproducing the Microsoft IIS 7.5 .NET source code disclosure and authentication bypass, but unfortunately couldn't reproduce the "Microsoft IIS 7.5 Classic ASP Authentication Bypass" and "Microsoft IIS 6.0 with PHP installed Authentication Bypass" vulnerabilities.
Microsoft IIS 7.5 .NET source code disclosure
In my limited time I could only verify the IIS 7.5 .NET source code disclosure vulnerability.
For the vulnerability to be effective, the Path Type of the PHP handler must remain unconfigured (Type="Unspecified"). For any request on a file using the .NET Framework, such as .aspx, that is not blocked through the request filtering rules (like misconfigured .CS and .VB files), IIS will return the full source code of the file.
And it executes it as PHP code! All you have to do is append /.php to the URI:
http://www.example.com/vuln.aspx/.php
It might also be possible to execute arbitrary PHP code under special circumstances.
Workarounds for Microsoft IIS 7.5 .NET source code disclosure
Fortunately, there are several workarounds available.
Configure the PHP handler properly in IIS
A properly configured IIS web server has its Request Restrictions (resourceType) set to File in the PHP handler. Without it, a request for a PHP file that doesn't exist gives you the nasty "No input file specified" error message.
If not configured, fix it with AppCmd.exe:
appcmd set config /section:system.webServer/handlers "-+[name='PHP',path='*.php',verb='*',modules='FastCgiModule',scriptProcessor='path\to\php-cgi.exe',resourceType='File']"
If you're unable to, you can deny certain URL sequences using IIS URL Rewrite or Helicon Ape.
Deny URL sequence using IIS URL Rewrite module
In your web.config file, add:
<rewrite>
<rules>
<rule name="DenyPHPafterASPX" stopProcessing="true">
<match url=".?" ignoreCase="true" />
<conditions logicalGrouping="MatchAll">
<add input="{URL}" pattern="^/(.*\.aspx)/(.*\.php)$" />
</conditions>
<action type="CustomResponse"
url="/"
statusCode="403"
statusReason="Forbidden"
statusDescription="Forbidden" />
</rule>
</rules>
</rewrite>
Deny URL sequence using IIS Request Filtering module
In your web.config file, add:
<configuration>
<system.webServer>
<security>
<requestFiltering>
<denyUrlSequences>
<add sequence=".aspx/.php" />
</denyUrlSequences>
</requestFiltering>
</security>
</system.webServer>
</configuration>
Or in Helicon Ape's .htaccess file:
RewriteEngine On
# DenyPHPafterASPX
RewriteCond %{REQUEST_URI} ^/(.*\.aspx)/(.*\.php)$ [NC]
RewriteRule .? / [F,L]
Important: the URL Rewrite and Helicon Ape rewrite rules must be made for any .NET Framework file extension, like .aspx, .vb, .cs, and so on.
On websites that don't use ASP.NET, you can block these file extensions altogether with Request Filtering. You can use AppCmd.exe to configure these, if not already. For example:
appcmd set config /section:system.webServer/security/requestFiltering /+"fileExtensions.[fileExtension='.aspx',allowed='False']"
appcmd set config /section:system.webServer/security/requestFiltering /+"fileExtensions.[fileExtension='.vb',allowed='False']"
appcmd set config /section:system.webServer/security/requestFiltering /+"fileExtensions.[fileExtension='.htaccess',allowed='False']"
Denying the .aspx extension makes IIS refuse every .aspx request, including /file.aspx/.php. That's exactly what you want on a PHP-only website, but it takes an ASP.NET website offline. For ASP.NET websites, use the URL Rewrite, denyUrlSequences or Helicon Ape rules above instead.
More hardening tips: important security measures for Windows Server IIS.
Microsoft IIS 6.0 with PHP installed Authentication Bypass
Kingcope replied that the IIS 6.0 PHP authentication bypass is only possible on Windows Server 2003 SP1. SP2 seems unaffected.
Microsoft IIS 7.5 Classic ASP Authentication Bypass
On two different server environments, I was unable to reproduce the Classic ASP authentication bypass. A web server with .NET Framework version 4.0.30319.237 returns an HttpException after adding ::$INDEX_ALLOCATION to the directory name:
[HttpException (0x80004005): A potentially dangerous Request.Path value
was detected from the client (:).]
System.Web.HttpRequest.ValidateInputIfRequiredByConfig() +9016361
System.Web.PipelineStepManager.ValidateHelper(HttpContext context) +59
A second web server with .NET Framework version 4.0.30319.269 returns a 401.2 - Unauthorized status. I tested with the following browsers: Google Chrome, Mozilla Firefox and Internet Explorer 9, as Kingcope thought that might make a difference.