[#44310] プログラムに対して意図したとおりの文字列を渡す方法 — "Information Kanasansoft" <kanasansoft@...>

kanasanです。

9 messages 2007/12/05

[#44332] クラス:相互参照系の作成方法について質問です — "Saburoh Sakai" <sabroh@...>

はじめまして、さかいと申します。

12 messages 2007/12/11

[#44366] Rake改善プロジェクト — "Hajime Hoshi" <hajimehoshi@...>

東京大学修士 1 年の星一と申します。

14 messages 2007/12/19

[ruby-list:44321] Re: multipartで送信した時のRails/cgi.rbの動作について

From: "Makoto Kuwata" <kwa@...>
Date: 2007-12-06 16:13:21 UTC
List: ruby-list #44321
桑田です。

On Dec 6, 2007 5:36 PM, KOSEKI Kengo <kengo@tt.rim.or.jp> wrote:
> 最初はStringIOに入れておいて、そのフィールドの入力が
> 一定サイズを超えたらTempfileに移行するといいのではと
> 思ったんですが、、。

Ruby1.9のcgi.rbはそのような動作になっているみたいです。


> > 試しにパッチを作成してみました。Ruby1.8.6のcgi.rbをもとにしています。
>
>ありがとうございます!
>試してみます。

新しいパッチを作ったので、こちらを試していただけますか。
multipartでない場合でも、REQUEST_METHODが "POST" なら CONTENT_LENGTH の
長さを調べ、長過ぎるようならエラーにしています。
multipartの場合とそうでない場合とで、制限値を変えています。

Index: lib/cgi.rb
===================================================================
--- /user/local/lib/ruby/1.8/cgi.rb	2007-05-23 06:58:09.000000000 +0900
+++ lib/cgi.rb	2007-12-07 01:00:37.000000000 +0900
@@ -907,6 +907,17 @@
     params
   end

+
+  # Maximum content length of post data
+  MAX_CONTENT_LENGTH = 2 * 1024 * 1024
+
+  # Maximum content length of multipart data
+  MAX_MULTIPART_LENGTH = 128 * 1024 * 1024
+
+  # Maximum number of parameters when multipart
+  MAX_MULTIPART_COUNT = 128
+
+
   # Mixin module. It provides the follow functionality groups:
   #
   # 1. Access to CGI environment variables as methods.  See
@@ -984,9 +995,14 @@
         raise EOFError, "bad content body"
       end

+      max_count = MAX_MULTIPART_COUNT
+      n = 0
+
       loop do
+        raise StandardError.new("too many parameters.") if (n += 1) > max_count
+
         head = nil
-        if 10240 < content_length
+        if bufsize < content_length
           require "tempfile"
           body = Tempfile.new("CGI")
         else
@@ -1106,7 +1122,11 @@
          %r|\Amultipart/form-data.*boundary=\"?([^\";,]+)\"?|n.match(env_table['CONTENT_TYPE'])
         boundary = $1.dup
         @multipart = true
-        @params = read_multipart(boundary,
Integer(env_table['CONTENT_LENGTH']))
+        content_length = Integer(env_table['CONTENT_LENGTH'])
+        if content_length > MAX_MULTIPART_LENGTH
+          raise StandardError.new("too large multipart data.")
+        end
+        @params = read_multipart(boundary, content_length)
       else
         @multipart = false
         @params = CGI::parse(
@@ -1118,8 +1138,12 @@
                         env_table['QUERY_STRING'] or ""
                       end
                     when "POST"
+                      content_length = Integer(env_table['CONTENT_LENGTH'])
+                      if content_length > MAX_CONTENT_LENGTH
+                        raise StandardError.new("too large post data.")
+                      end
                       stdinput.binmode if defined? stdinput.binmode
-                      stdinput.read(Integer(env_table['CONTENT_LENGTH'])) or ''
+                      stdinput.read(content_length) or ''
                     else
                       read_from_cmdline
                     end
===================================================================

これに関連する話ですが、以前質問したときに cgi.rb のテストスクリプトは
存在しないといわれたので、今 cgi.rb のテストスクリプトを書いています。
そのうち公開すると思います。

--
makoto kuwata

In This Thread

Prev Next