aboutsummaryrefslogtreecommitdiffstats
path: root/actionpack
diff options
context:
space:
mode:
authorJordan Owens <jkowens@gmail.com>2016-01-12 14:05:54 -0500
committerJordan Owens <jkowens@gmail.com>2016-01-12 14:05:54 -0500
commit918f0eea970c9f0d39b8d470a316ad5109935dae (patch)
treece831158a47a0c8cf3e0cc82c1536ac4eb5c4b63 /actionpack
parent15299f3a5c0e068b4945bdb8199755100dc91e13 (diff)
downloadrails-918f0eea970c9f0d39b8d470a316ad5109935dae.tar.gz
rails-918f0eea970c9f0d39b8d470a316ad5109935dae.tar.bz2
rails-918f0eea970c9f0d39b8d470a316ad5109935dae.zip
Prevent attempt to serve a request with a null byte
File paths cannot contain null byte characters and methods that do path operations such as Rack::Utils#clean_path_info will raise unwanted errors.
Diffstat (limited to 'actionpack')
-rw-r--r--actionpack/lib/action_dispatch/middleware/static.rb6
-rw-r--r--actionpack/test/dispatch/static_test.rb4
2 files changed, 9 insertions, 1 deletions
diff --git a/actionpack/lib/action_dispatch/middleware/static.rb b/actionpack/lib/action_dispatch/middleware/static.rb
index ea9ab3821d..41c220236a 100644
--- a/actionpack/lib/action_dispatch/middleware/static.rb
+++ b/actionpack/lib/action_dispatch/middleware/static.rb
@@ -27,7 +27,7 @@ module ActionDispatch
# in the server's `public/` directory (see Static#call).
def match?(path)
path = ::Rack::Utils.unescape_path path
- return false unless path.valid_encoding?
+ return false unless valid_path?(path)
path = Rack::Utils.clean_path_info path
paths = [path, "#{path}#{ext}", "#{path}/#{@index}#{ext}"]
@@ -94,6 +94,10 @@ module ActionDispatch
false
end
end
+
+ def valid_path?(path)
+ path.valid_encoding? && !path.include?("\0")
+ end
end
# This middleware will attempt to return the contents of a file's body from
diff --git a/actionpack/test/dispatch/static_test.rb b/actionpack/test/dispatch/static_test.rb
index 1da57ab50b..ea8b5e904e 100644
--- a/actionpack/test/dispatch/static_test.rb
+++ b/actionpack/test/dispatch/static_test.rb
@@ -40,6 +40,10 @@ module StaticTests
assert_equal "Hello, World!", get("/doorkeeper%E3E4".force_encoding('ASCII-8BIT')).body
end
+ def test_handles_urls_with_null_byte
+ assert_equal "Hello, World!", get("/doorkeeper%00").body
+ end
+
def test_sets_cache_control
app = assert_deprecated do
ActionDispatch::Static.new(DummyApp, @root, "public, max-age=60")