From 3b5ddce2380efcb6d6896c48e6856025a60b7f5a Mon Sep 17 00:00:00 2001 From: Mamoru Tasaka Date: Tue, 12 Jan 2010 19:02:42 +0000 Subject: [PATCH] - CVE-2009-4492 ruby WEBrick log escape sequence (bug 554485) --- ruby-1.8.6.x-CVE-2009-4492.patch | 134 +++++++++++++++++++++++++++++++ ruby.spec | 8 +- 2 files changed, 141 insertions(+), 1 deletion(-) create mode 100644 ruby-1.8.6.x-CVE-2009-4492.patch diff --git a/ruby-1.8.6.x-CVE-2009-4492.patch b/ruby-1.8.6.x-CVE-2009-4492.patch new file mode 100644 index 0000000..00fa053 --- /dev/null +++ b/ruby-1.8.6.x-CVE-2009-4492.patch @@ -0,0 +1,134 @@ +Index: lib/webrick/httpstatus.rb +=================================================================== +--- lib/webrick/httpstatus.rb (revision 26273) ++++ lib/webrick/httpstatus.rb (revision 26274) +@@ -12,7 +12,17 @@ + + module HTTPStatus + +- class Status < StandardError; end ++ class Status < StandardError ++ def initialize(message=self.class, *rest) ++ super(AccessLog.escape(message), *rest) ++ end ++ class << self ++ attr_reader :code, :reason_phrase ++ end ++ def code() self::class::code end ++ def reason_phrase() self::class::reason_phrase end ++ alias to_i code ++ end + class Info < Status; end + class Success < Status; end + class Redirect < Status; end +@@ -68,6 +78,7 @@ + CodeToError = {} + + StatusMessage.each{|code, message| ++ message.freeze + var_name = message.gsub(/[ \-]/,'_').upcase + err_name = message.gsub(/[ \-]/,'') + +@@ -79,18 +90,12 @@ + when 500...600; parent = ServerError + end + +- eval %- +- RC_#{var_name} = #{code} +- class #{err_name} < #{parent} +- def self.code() RC_#{var_name} end +- def self.reason_phrase() StatusMessage[code] end +- def code() self::class::code end +- def reason_phrase() self::class::reason_phrase end +- alias to_i code +- end +- - +- +- CodeToError[code] = const_get(err_name) ++ const_set("RC_#{var_name}", code) ++ err_class = Class.new(parent) ++ err_class.instance_variable_set(:@code, code) ++ err_class.instance_variable_set(:@reason_phrase, message) ++ const_set(err_name, err_class) ++ CodeToError[code] = err_class + } + + def reason_phrase(code) +Index: lib/webrick/httprequest.rb +=================================================================== +--- lib/webrick/httprequest.rb (revision 26273) ++++ lib/webrick/httprequest.rb (revision 26274) +@@ -242,11 +242,7 @@ + @raw_header << line + end + end +- begin +- @header = HTTPUtils::parse_header(@raw_header) +- rescue => ex +- raise HTTPStatus::BadRequest, ex.message +- end ++ @header = HTTPUtils::parse_header(@raw_header.join) + end + + def parse_uri(str, scheme="http") +Index: lib/webrick/httpresponse.rb +=================================================================== +--- lib/webrick/httpresponse.rb (revision 26273) ++++ lib/webrick/httpresponse.rb (revision 26274) +@@ -132,7 +132,7 @@ + end + end + +- # Determin the message length (RFC2616 -- 4.4 Message Length) ++ # Determine the message length (RFC2616 -- 4.4 Message Length) + if @status == 304 || @status == 204 || HTTPStatus::info?(@status) + @header.delete('content-length') + @body = "" +Index: lib/webrick/httputils.rb +=================================================================== +--- lib/webrick/httputils.rb (revision 26273) ++++ lib/webrick/httputils.rb (revision 26274) +@@ -128,11 +128,11 @@ + when /^\s+(.*?)\s*\z/om + value = $1 + unless field +- raise "bad header '#{line.inspect}'." ++ raise HTTPStatus::BadRequest, "bad header '#{line}'." + end + header[field][-1] << " " << value + else +- raise "bad header '#{line.inspect}'." ++ raise HTTPStatus::BadRequest, "bad header '#{line}'." + end + } + header.each{|key, values| +Index: lib/webrick/accesslog.rb +=================================================================== +--- lib/webrick/accesslog.rb (revision 26273) ++++ lib/webrick/accesslog.rb (revision 26274) +@@ -53,15 +53,23 @@ + when ?e, ?i, ?n, ?o + raise AccessLogError, + "parameter is required for \"#{spec}\"" unless param +- params[spec][param] || "-" ++ param = params[spec][param] ? escape(param) : "-" + when ?t + params[spec].strftime(param || CLF_TIME_FORMAT) + when ?% + "%" + else +- params[spec] ++ escape(params[spec].to_s) + end + } + end ++ ++ def escape(data) ++ if data.tainted? ++ data.gsub(/[[:cntrl:]\\]+/) {$&.dump[1...-1]}.untaint ++ else ++ data ++ end ++ end + end + end diff --git a/ruby.spec b/ruby.spec index 1d53055..3c67fe7 100644 --- a/ruby.spec +++ b/ruby.spec @@ -16,7 +16,7 @@ Name: ruby Version: %{rubyver}%{?dotpatchlevel} -Release: 5%{?dist} +Release: 6%{?dist} License: Ruby or GPLv2 URL: http://www.ruby-lang.org/ BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n) @@ -56,6 +56,8 @@ Patch31: ruby-1.8.6-p369-ri-gem_multipath.patch # Patch32 from ruby_1_8 branch Patch32: ruby-1.8head-irb-save-history.patch Patch33: ruby-1.8.6-p383-mkmf-use-shared.patch +# Patch34 already applied in 1.8.6p388 +Patch34: ruby-1.8.6.x-CVE-2009-4492.patch Summary: An interpreter of object-oriented scripting language Group: Development/Languages @@ -197,6 +199,7 @@ pushd %{name}-%{arcver} %patch31 -p1 %patch32 -p0 %patch33 -p1 +%patch34 -p0 popd %build @@ -572,6 +575,9 @@ rm -rf $RPM_BUILD_ROOT %{_emacs_sitestartdir}/ruby-mode-init.el %changelog +* Wed Jan 13 2010 Mamoru Tasaka - 1.8.6.383-6 +- CVE-2009-4492 ruby WEBrick log escape sequence (bug 554485) + * Wed Dec 9 2009 Mamoru Tasaka - 1.8.6.383-5 - Change mkmf.rb to use LIBRUBYARG_SHARED so that have_library() works without libruby-static.a (bug 428384)