From 176af7eff2e33b331c92febbeda98123da1151f3 Mon Sep 17 00:00:00 2001 From: Ernie Miller Date: Fri, 8 Jun 2012 16:42:01 -0400 Subject: [PATCH] Additional fix for CVE-2012-2661 While the patched PredicateBuilder in 3.0.13 prevents a user from specifying a table name using the `table.column` format, it doesn't protect against the nesting of hashes changing the table context in the next call to build_from_hash. This fix covers this case as well. --- .../active_record/relation/predicate_builder.rb | 6 +++--- activerecord/test/cases/relation/where_test.rb | 6 ++++++ 2 files changed, 9 insertions(+), 3 deletions(-) diff --git a/activerecord/lib/active_record/relation/predicate_builder.rb b/activerecord/lib/active_record/relation/predicate_builder.rb index 84e88cf..e74ba73 100644 --- a/activerecord/lib/active_record/relation/predicate_builder.rb +++ b/activerecord/lib/active_record/relation/predicate_builder.rb @@ -5,17 +5,17 @@ module ActiveRecord @engine = engine end - def build_from_hash(attributes, default_table, check_column = true) + def build_from_hash(attributes, default_table, allow_table_name = true) predicates = attributes.map do |column, value| table = default_table - if value.is_a?(Hash) + if allow_table_name && value.is_a?(Hash) table = Arel::Table.new(column, :engine => @engine) build_from_hash(value, table, false) else column = column.to_s - if check_column && column.include?('.') + if allow_table_name && column.include?('.') table_name, column = column.split('.', 2) table = Arel::Table.new(table_name, :engine => @engine) end diff --git a/activerecord/test/cases/relation/where_test.rb b/activerecord/test/cases/relation/where_test.rb index 90c690e..b9eef1d 100644 --- a/activerecord/test/cases/relation/where_test.rb +++ b/activerecord/test/cases/relation/where_test.rb @@ -11,6 +11,12 @@ module ActiveRecord end end + def test_where_error_with_hash + assert_raises(ActiveRecord::StatementInvalid) do + Post.where(:id => { :posts => {:author_id => 10} }).first + end + end + def test_where_with_table_name post = Post.first assert_equal post, Post.where(:posts => { 'id' => post.id }).first -- 1.7.5.4