summaryrefslogtreecommitdiff
path: root/swift/common/middleware/tempurl.py
diff options
context:
space:
mode:
Diffstat (limited to 'swift/common/middleware/tempurl.py')
-rw-r--r--swift/common/middleware/tempurl.py31
1 files changed, 30 insertions, 1 deletions
diff --git a/swift/common/middleware/tempurl.py b/swift/common/middleware/tempurl.py
index c2381b318..1f94e8dd1 100644
--- a/swift/common/middleware/tempurl.py
+++ b/swift/common/middleware/tempurl.py
@@ -119,11 +119,13 @@ from urllib import urlencode
from urlparse import parse_qs
from swift.proxy.controllers.base import get_account_info
-from swift.common.swob import HeaderKeyDict, HTTPUnauthorized
+from swift.common.swob import HeaderKeyDict, HTTPUnauthorized, HTTPBadRequest
from swift.common.utils import split_path, get_valid_utf8_str, \
register_swift_info, get_hmac, streq_const_time, quote
+DISALLOWED_INCOMING_HEADERS = 'x-object-manifest'
+
#: Default headers to remove from incoming requests. Simply a whitespace
#: delimited list of header names and names can optionally end with '*' to
#: indicate a prefix match. DEFAULT_INCOMING_ALLOW_HEADERS is a list of
@@ -227,6 +229,10 @@ class TempURL(object):
#: The methods allowed with Temp URLs.
self.methods = methods
+ self.disallowed_headers = set(
+ 'HTTP_' + h.upper().replace('-', '_')
+ for h in DISALLOWED_INCOMING_HEADERS.split())
+
headers = DEFAULT_INCOMING_REMOVE_HEADERS
if 'incoming_remove_headers' in conf:
headers = conf['incoming_remove_headers']
@@ -320,6 +326,13 @@ class TempURL(object):
for hmac in hmac_vals)
if not is_valid_hmac:
return self._invalid(env, start_response)
+ # disallowed headers prevent accidently allowing upload of a pointer
+ # to data that the PUT tempurl would not otherwise allow access for.
+ # It should be safe to provide a GET tempurl for data that an
+ # untrusted client just uploaded with a PUT tempurl.
+ resp = self._clean_disallowed_headers(env, start_response)
+ if resp:
+ return resp
self._clean_incoming_headers(env)
env['swift.authorize'] = lambda req: None
env['swift.authorize_override'] = True
@@ -456,6 +469,22 @@ class TempURL(object):
body = '401 Unauthorized: Temp URL invalid\n'
return HTTPUnauthorized(body=body)(env, start_response)
+ def _clean_disallowed_headers(self, env, start_response):
+ """
+ Validate the absense of disallowed headers for "unsafe" operations.
+
+ :returns: None for safe operations or swob.HTTPBadResponse if the
+ request includes disallowed headers.
+ """
+ if env['REQUEST_METHOD'] in ('GET', 'HEAD', 'OPTIONS'):
+ return
+ for h in env:
+ if h in self.disallowed_headers:
+ return HTTPBadRequest(
+ body='The header %r is not allowed in this tempurl' %
+ h[len('HTTP_'):].title().replace('_', '-'))(
+ env, start_response)
+
def _clean_incoming_headers(self, env):
"""
Removes any headers from the WSGI environment as per the