16

Why should the OPTIONS method not be allowed on an HTTP server?

Lightness Races in Orbit
  • 2,173
  • 2
  • 14
  • 15
zzz
  • 277
  • 1
  • 2
  • 3
  • 10
    11 upvotes for a non-canonical question with no apparent research effort, context, or goals. Why? – oldmud0 Oct 04 '16 at 00:09
  • 1
    @oldmud0 - It must have appeared on hot network questions. It is very annoying that this encourages dumb questions while many smart questions get little attention. However, I've never seen any good idea to fix this. Personally, I think SE should stop attaching permissions to rep, and just treat it as an abstract number like Reddit karma. – paj28 Oct 04 '16 at 03:29
  • @paj28 This question is on the hot network questions as of now, at least. – user Oct 04 '16 at 08:37
  • If you don't leverage it, why should it be allowed on the server ? It only increases your attack surface. – niilzon Oct 03 '16 at 06:42

2 Answers2

34

An essential part of security is to reduce the attack surface by removing any functionality which is not needed. Usually this is also functionality which is less well tested and thus might be a vector for unexpected attacks. For example there might be restrictions/authorizations in the web application which are specific for GET, POST and which ignore any other methods. On the other hand part of the applications code might ignore the request method and thus access to protected resources might be possible using unprotected request methods. Thus removing OPTIONS, HEAD, TRACE etc makes sense in case these are not used.

But, OPTIONS might be needed in connection with CORS to allow cross origin requests. In this case removing it would impact functionality and thus it should not be removed.

In general it is a bad idea to just black list request methods which might be a problem. Instead white listing should be done, i.e. only allow request methods which are known to be handled properly by the application.

Steffen Ullrich
  • 184,332
  • 29
  • 363
  • 424
  • Also, it's worth noting that one can use JSONP or similar, to fetch a content without CORS. Also, browsers send the OPTIONS request before trying to use a POST/GET when using CORS, and there aren't many ways to avoid the OPTIONS request. – Ismael Miguel Oct 03 '16 at 13:41
  • 11
    @IsmaelMiguel: CORS was explicitly designed to get rid of these insecure workarounds like JSONP. It is not a good idea to use JSONP just to be able to block OPTIONS, because JSONP causes probably more trouble than knowingly allowing OPTIONS. – Steffen Ullrich Oct 03 '16 at 13:49
  • One can use a proxy to fetch the remote content. There are multiple CORS proxies out there. But if you want total safety, you can use a script on your server (in PHP, for example) that will comunicate with the remote service and then relay the contents to you. That should solve it, right? – Ismael Miguel Oct 03 '16 at 14:10
  • OPTION is also useful in RESTful design. Which operations are allowed on which resources needs to be communicated somehow. – JimmyJames Oct 03 '16 at 14:57
  • 1
    @IsmaelMiguel In order to do a credentialed cross-origin request, you'd need to pass your cookies to the proxy, which sounds suboptimal to me. Consider also services that are restricted to specific client IP ranges (e.g., so they're only usable by people in a certain country or university: see http://security.stackexchange.com/q/43639/13146); those services would not operate correctly for you if you had the right IP address to use them but then had to route through a proxy. – apsillers Oct 03 '16 at 14:58
  • 8
    @IsmaelMiguel: OPTIONS is not bad by itself and it makes no sense to create workarounds in order to be able to block OPTIONS. OPTIONS can be used securely. But it can be a problem if one is not aware that this method (and others like TRACE, HEAD...) exist and needs to be handled properly. Best is not to black list just OPTIONS but instead to white list any methods which the application is able to handle properly. – Steffen Ullrich Oct 03 '16 at 15:03
4

Others have pointed out that you want to limit your attack surface, and to be aware that some Ajax sites legitimately use OPTIONS. Anyway, I wanted to share a recent experience with you.

We had tested a site and discovered it was vulnerable to executable file upload. Roughly speaking, you could upload a JSP file as your profile picture, then execute the JSP file and take control of the server.

The client's first attempt at a fix blocked fetching the JSP with a GET request. However, we discovered it was still possible to execute the JSP using an OPTIONS request. You don't get the JSP output - but it's easy to code the JSP to connect back with an out-of-band mechanism.

In this case, allowing OPTIONS allowed a remote server compromise.


R commented that it's not OPTIONS at fault. That is true, it's poor coding at fault. However, if OPTIONS had been blanket disabled as a defence in depth measure, then this site would not have been exploitable.

paj28
  • 32,736
  • 8
  • 92
  • 130
  • 7
    While providing an example was nice, `OPTIONS` was clearly not at fault here. The fault was multiple flaws in how blocking the execution of the jsp was handled: (1) failure to restrict execution to a whitelist of non-writable locations, (2) presumably storing user-uploaded content in user-controlled filenames, (3) interpreting a file as jsp based on its filename and/or contents, (4) specifying an explicit method on the blocklist rather than blocking the path for all methods, etc. – R.. GitHub STOP HELPING ICE Oct 03 '16 at 17:01
  • No, I did not either upvote or downvote. – R.. GitHub STOP HELPING ICE Oct 03 '16 at 18:08
  • in your code i'm sure you can do a check on the filetypes that are supported for the profile picture right? – Arvind Sridharan Jul 17 '17 at 13:01
  • @ArvindSridharan - is who's code? – paj28 Jul 17 '17 at 13:56
  • @ArvindSridharan - This was a client app, so my role was limited to testing it. I never even saw the code. I recommended pretty much what you said, but I couldn't force them to follow it. As often happens, we ended up with a half-baked fix. – paj28 Jul 17 '17 at 16:34