Skip to content

Instantly share code, notes, and snippets.

@marcbarry
Last active August 13, 2021 17:05
Show Gist options
  • Star 10 You must be signed in to star a gist
  • Fork 5 You must be signed in to fork a gist
  • Save marcbarry/47644b4a43fbfb63ef54 to your computer and use it in GitHub Desktop.
Save marcbarry/47644b4a43fbfb63ef54 to your computer and use it in GitHub Desktop.
Security hardening pointers for web.config and machine.config
Prevent applications running if debug=true
<system.web>
  <deployment retail="true"/>
</system.web>

Security hardening web.config

For a complete template see this Gist

Disable tracing
<system.web>
  <trace enabled="false" />
</system.web>
Disable debug
<system.web>
  <compilation debug="false" />
</system.web>
Rename the cookie to something more obscure ASP.NET_SessionId
<system.web>
  <sessionState cookieName="s" />
</system.web>
Disable ASP.NET version HTTP header
<system.web>
  <httpRuntime enableVersionHeader="false" />
</system.web>
Secure cookies on HTTPS deployments

See httpCookies Element MSDN documentation for more information.

<system.web>
  <httpCookies httpOnlyCookies="false" requireSSL="false" />
</system.web>
Remove unwanted http headers
<system.webServer>
  <httpProtocol>
      <customHeaders>
        <remove name="Server" />
        <remove name="X-Powered-By" />
        <remove name="X-AspNet-Version" />
        <remove name="X-AspNetMvc-Version" />
      </customHeaders>
    </httpProtocol>
</system.webServer>
Configure custome error handlers for specific HTTP error codes
<system.webServer>
  <httpErrors errorMode="Custom">
    <remove statusCode="502" subStatusCode="-1" />
    <remove statusCode="501" subStatusCode="-1" />
    <remove statusCode="500" subStatusCode="-1" />
    <remove statusCode="412" subStatusCode="-1" />
    <remove statusCode="406" subStatusCode="-1" />
    <remove statusCode="405" subStatusCode="-1" />
    <remove statusCode="404" subStatusCode="-1" />
    <remove statusCode="403" subStatusCode="-1" />
    <remove statusCode="401" subStatusCode="-1" />
    <remove statusCode="400" subStatusCode="-1" />
	
    <error statusCode="400" subStatusCode="-1" path="/error-handler.aspx" prefixLanguageFilePath="" responseMode="ExecuteURL" />
    <error statusCode="401" subStatusCode="-1" path="/error-handler.aspx" prefixLanguageFilePath="" responseMode="ExecuteURL" />
    <error statusCode="402" subStatusCode="-1" path="/error-handler.aspx" prefixLanguageFilePath="" responseMode="ExecuteURL" />
    <error statusCode="403" subStatusCode="-1" path="/error-handler.aspx" prefixLanguageFilePath="" responseMode="ExecuteURL" />
    <error statusCode="404" subStatusCode="-1" path="/error-handler.aspx" prefixLanguageFilePath="" responseMode="ExecuteURL" />
    <error statusCode="405" subStatusCode="-1" path="/error-handler.aspx" prefixLanguageFilePath="" responseMode="ExecuteURL" />
    <error statusCode="406" subStatusCode="-1" path="/error-handler.aspx" prefixLanguageFilePath="" responseMode="ExecuteURL" />
    <error statusCode="412" subStatusCode="-1" path="/error-handler.aspx" prefixLanguageFilePath="" responseMode="ExecuteURL" />
    <error statusCode="500" subStatusCode="-1" path="/error-handler.aspx" prefixLanguageFilePath="" responseMode="ExecuteURL" />
    <error statusCode="501" subStatusCode="-1" path="/error-handler.aspx" prefixLanguageFilePath="" responseMode="ExecuteURL" />
    <error statusCode="502" subStatusCode="-1" path="/error-handler.aspx" prefixLanguageFilePath="" responseMode="ExecuteURL" />
  </httpErrors>
</system.webServer>
Remove unwanted modules to reduce your attack surface
<system.webServer>
  <handlers>
    <remove name="TraceHandler-Integrated-4.0" />
    <remove name="TraceHandler-Integrated" />
    <remove name="AssemblyResourceLoader-Integrated-4.0" />
    <remove name="AssemblyResourceLoader-Integrated" />
    <remove name="WebAdminHandler-Integrated-4.0" />
    <remove name="WebAdminHandler-Integrated" />
    <remove name="HttpRemotingHandlerFactory-soap-ISAPI-2.0-64" />
    <remove name="svc-ISAPI-4.0_32bit" />
    <remove name="ScriptHandlerFactoryAppServices-Integrated-4.0" />
    <remove name="ScriptResourceIntegrated-4.0" />
    <remove name="svc-ISAPI-4.0_64bit" />
    <remove name="svc-Integrated-4.0" />
    <remove name="vbhtm-ISAPI-4.0_32bit" />
    <remove name="vbhtm-ISAPI-4.0_64bit" />
    <remove name="vbhtm-Integrated-4.0" />
    <remove name="vbhtml-ISAPI-4.0_32bit" />
    <remove name="vbhtml-ISAPI-4.0_64bit" />
    <remove name="vbhtml-Integrated-4.0" />
    <remove name="xamlx-ISAPI-4.0_32bit" />
    <remove name="xamlx-ISAPI-4.0_64bit" />
    <remove name="xamlx-Integrated-4.0" />
    <remove name="xoml-ISAPI-4.0_32bit" />
    <remove name="xoml-ISAPI-4.0_64bit" />
    <remove name="xoml-Integrated-4.0" />
    <remove name="HttpRemotingHandlerFactory-rem-Integrated-4.0" />
    <remove name="HttpRemotingHandlerFactory-rem-ISAPI-2.0" />
    <remove name="rules-ISAPI-4.0_32bit" />
    <remove name="rules-Integrated-4.0" />
    <remove name="HttpRemotingHandlerFactory-soap-Integrated" />
    <remove name="HttpRemotingHandlerFactory-soap-ISAPI-2.0" />
    <remove name="HttpRemotingHandlerFactory-soap-ISAPI-4.0_64bit" />
    <remove name="HttpRemotingHandlerFactory-soap-Integrated-4.0" />
    <remove name="HttpRemotingHandlerFactory-soap-ISAPI-4.0_32bit" />
    <remove name="rules-ISAPI-4.0_64bit" />
    <remove name="HttpRemotingHandlerFactory-rem-ISAPI-2.0-64" />
    <remove name="HttpRemotingHandlerFactory-rem-Integrated" />
    <remove name="HttpRemotingHandlerFactory-rem-ISAPI-4.0_32bit" />
    <remove name="HttpRemotingHandlerFactory-rem-ISAPI-4.0_64bit" />
    <remove name="AXD-ISAPI-2.0-64" />
    <remove name="cshtml-ISAPI-4.0_64bit" />
    <remove name="cshtml-Integrated-4.0" />
    <remove name="cshtm-Integrated-4.0" />
    <remove name="cshtml-ISAPI-4.0_32bit" />
    <remove name="cshtm-ISAPI-4.0_64bit" />
    <remove name="cshtm-ISAPI-4.0_32bit" />
    <remove name="AXD-ISAPI-4.0_64bit" />
    <remove name="AXD-ISAPI-2.0" />
    <remove name="AXD-ISAPI-4.0_32bit" />
    <remove name="PageHandlerFactory-ISAPI-2.0-64" />
    <remove name="PageHandlerFactory-ISAPI-2.0" />
    <remove name="PageHandlerFactory-ISAPI-4.0_64bit" />
    <remove name="PageHandlerFactory-ISAPI-4.0_32bit" />
    <remove name="aspq-ISAPI-4.0_64bit" />
    <remove name="aspq-Integrated-4.0" />
    <remove name="WebServiceHandlerFactory-ISAPI-2.0" />
    <remove name="aspq-ISAPI-4.0_32bit" />
    <remove name="WebServiceHandlerFactory-Integrated-4.0" />
    <remove name="WebServiceHandlerFactory-Integrated" />
    <remove name="SimpleHandlerFactory-ISAPI-4.0_64bit" />
    <remove name="SimpleHandlerFactory-Integrated-4.0" />
    <remove name="SimpleHandlerFactory-Integrated" />
    <remove name="SimpleHandlerFactory-ISAPI-2.0" />
    <remove name="SimpleHandlerFactory-ISAPI-2.0-64" />
    <remove name="WebServiceHandlerFactory-ISAPI-4.0_32bit" />
    <remove name="WebServiceHandlerFactory-ISAPI-4.0_64bit" />
    <remove name="WebServiceHandlerFactory-ISAPI-2.0-64" />
    <remove name="SimpleHandlerFactory-ISAPI-4.0_32bit" />
    <remove name="ISAPI-dll" />
    <remove name="ExtensionlessUrlHandler-ISAPI-4.0_64bit" />
    <remove name="ExtensionlessUrlHandler-ISAPI-4.0_32bit" />
    <remove name="OPTIONSVerbHandler" />
    <remove name="TRACEVerbHandler" />
  </handlers>
</system.webServer>
Restrict which HTTP verbs your application will work with
<system.webServer>
  <security>
    <requestFiltering allowHighBitCharacters="false">
      <verbs allowUnlisted="false">
        <add verb="GET" allowed="true" />
        <add verb="POST" allowed="true" />
      </verbs>
    </requestFiltering>
  </security>
</system.webServer>
Install iis-remove-server-headers module

Consider installing iis-remove-server-headers to remove common headers which leak undesirable information.

  • Server
  • X-Powered-By
  • X-AspNet-Version
  • X-AspNetMvc-Version
@eL-Prova
Copy link

eL-Prova commented Sep 1, 2017

<httpCookies httpOnlyCookies="false" requireSSL="false" /> shouldn't be <httpCookies httpOnlyCookies="true" requireSSL="true" />

Further good practice:

<!-- Configure SSL URL Rewriting and IP filtering to block unwanted users -->
<system.webServer>
  <rewrite xdt:Transform="Insert">
    <rules>
      <rule name="HTTP to HTTPS redirect" stopProcessing="true">
        <match url="(.*)" />
        <conditions>
          <add input="{HTTPS}" pattern="off" ignoreCase="true" />
        </conditions>
        <action type="Redirect" redirectType="Found" url="https://{HTTP_HOST}/{R:1}" />
      </rule>
    </rules>
  </rewrite>
</system.webServer>

@hefese
Copy link

hefese commented Jun 17, 2019

The following configuration setting snippet should take place Machine.Config instead of Web.Config. If you use it in web.config, then at first, you don't feel there is an erroneous situation. But when you use IIS managed module iis-remove-server-headers (by Pingfu) in addition, as specified in this page, your server will prompt 500 Internal Error responses error to you, continuously.

<system.web>
  <deployment retail="true"/>
</system.web>

So this setting should be in Machine.Config. Thereby, everything will be ok. The others can take place in web.config.

Deployment retail value can only be set at the machine level, not at the application level. When retail is set to true, ASP.NET disables certain configuration settings such as trace output, custom errors, and debug capabilities. - https://www.devcurry.com/2010/11/using-deployment-retailtrue-attribute.html

@marcbarry
Copy link
Author

thanks @hefese and @eL-Prova. @hefese I've updated as per your suggestion.

@jscott-concord
Copy link

jscott-concord commented Aug 13, 2021

The above recommendation should be to set these values to true
httpOnlyCookies="false" requireSSL="false"

should look like the following
httpOnlyCookies="true" requireSSL="true"

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment