From mboxrd@z Thu Jan 1 00:00:00 1970 Delivered-To: chneukirchen@gmail.com Received: by 10.49.85.105 with SMTP id g9csp291316qez; Tue, 22 Jan 2013 16:20:50 -0800 (PST) Return-Path: Received-SPF: pass (google.com: domain of rack-devel+bncBDKJRJVBSMLBBYOZ7SDQKGQEJ5ZKHHQ@googlegroups.com designates 10.50.108.200 as permitted sender) client-ip=10.50.108.200 Authentication-Results: mr.google.com; spf=pass (google.com: domain of rack-devel+bncBDKJRJVBSMLBBYOZ7SDQKGQEJ5ZKHHQ@googlegroups.com designates 10.50.108.200 as permitted sender) smtp.mail=rack-devel+bncBDKJRJVBSMLBBYOZ7SDQKGQEJ5ZKHHQ@googlegroups.com; dkim=pass header.i=@googlegroups.com X-Received: from mr.google.com ([10.50.108.200]) by 10.50.108.200 with SMTP id hm8mr16780910igb.10.1358900449997 (num_hops = 1); Tue, 22 Jan 2013 16:20:49 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=googlegroups.com; s=20120806; h=x-received:x-beenthere:x-received:x-received:received-spf:date:from :to:subject:message-id:mime-version:user-agent:x-original-sender :x-original-authentication-results:reply-to:precedence:mailing-list :list-id:x-google-group-id:list-post:list-help:list-archive:sender :list-subscribe:list-unsubscribe:content-type:content-disposition; bh=NHDsOW20k4PTVZV8nWSV83mUSwCGu3VJSc5xZXCYlrI=; b=iAPN9JSxMwajYGr/N8jkqcN2GwKK+1aTFp2XBwLF3ZvqQnY/lDHjs7OdlQaS/2LkXp MJd9sRrgJ4u+Niq80Aw+ESCj5WTbnpzDvSC/ZsU1HAFRrwsq8l2pADn8tEzj5nyzZojv H1Py986Nj0KSTLgsmVDxMdWGyKmAq1xr4TrI+jeIDLdyBlKnMddnwH9bq+ReATP/kN/p uIsg7JGuVuGtFQp7dX2+UG694IrxU4o/SZGJM6CxwEAD7RmgaV+zFjk4Vopdo1i1SkVz 1nDoEakqas78h/FM3rsecYZ2dPWVLyFfHda72PM22OwxTP0s7sKn8RtElW5SI0MIviqt XWtQ== X-Received: by 10.50.108.200 with SMTP id hm8mr4765188igb.10.1358900449709; Tue, 22 Jan 2013 16:20:49 -0800 (PST) X-BeenThere: rack-devel@googlegroups.com Received: by 10.50.155.193 with SMTP id vy1ls3745221igb.19.gmail; Tue, 22 Jan 2013 16:20:49 -0800 (PST) X-Received: by 10.66.85.168 with SMTP id i8mr3148831paz.21.1358900449067; Tue, 22 Jan 2013 16:20:49 -0800 (PST) X-Received: by 10.66.85.168 with SMTP id i8mr3148830paz.21.1358900449054; Tue, 22 Jan 2013 16:20:49 -0800 (PST) Received: from dcvr.yhbt.net (dcvr.yhbt.net. [64.71.152.64]) by gmr-mx.google.com with ESMTP id vg4si3426699pbc.2.2013.01.22.16.20.48; Tue, 22 Jan 2013 16:20:48 -0800 (PST) Received-SPF: pass (google.com: best guess record for domain of normalperson@yhbt.net designates 64.71.152.64 as permitted sender) client-ip=64.71.152.64; Received: from localhost (dcvr.yhbt.net [127.0.0.1]) by dcvr.yhbt.net (Postfix) with ESMTP id 80D6E1F6E1; Wed, 23 Jan 2013 00:20:48 +0000 (UTC) Date: Wed, 23 Jan 2013 00:20:48 +0000 From: Eric Wong To: rack-devel Subject: [RFC/PATCH] lint: additional response checking/skipping for hijack Message-ID: <20130123002048.GA362@dcvr.yhbt.net> MIME-Version: 1.0 User-Agent: Mutt/1.5.21 (2010-09-15) X-Original-Sender: normalperson@yhbt.net X-Original-Authentication-Results: gmr-mx.google.com; spf=pass (google.com: best guess record for domain of normalperson@yhbt.net designates 64.71.152.64 as permitted sender) smtp.mail=normalperson@yhbt.net Reply-To: rack-devel@googlegroups.com Precedence: list Mailing-list: list rack-devel@googlegroups.com; contact rack-devel+owners@googlegroups.com List-ID: X-Google-Group-Id: 486215384060 List-Post: , List-Help: , List-Archive: Sender: rack-devel@googlegroups.com List-Subscribe: , List-Unsubscribe: , Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Not a serious patch for now, at least not all of it. I suspect middlewares will break badly if the body.each/body.close checks are enforced. --- lib/rack/lint.rb | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/lib/rack/lint.rb b/lib/rack/lint.rb index 1bc2127..f895772 100644 --- a/lib/rack/lint.rb +++ b/lib/rack/lint.rb @@ -9,6 +9,7 @@ class Lint def initialize(app) @app = app @content_length = nil + @response_hijacked = false end # :stopdoc: @@ -47,6 +48,15 @@ def _call(env) ## and returns an Array of exactly three values: status, headers, @body = @app.call(env) + + # hijacked requests may not give a valid response, do not check them + if env.include?("rack.hijack_io") + # request hijacking implies response hijacking, this will ensure + # the response body raises if body.each or body.close gets called + @response_hijacked = true + return [ status, headers, self ] + end + ## The *status*, check_status status ## the *headers*, @@ -530,6 +540,7 @@ def check_hijack_response(headers, env) headers['rack.hijack'] = proc do |io| original_hijack.call HijackWrapper.new(io) end + @response_hijacked = true else ## ## The special response header rack.hijack must only be set @@ -636,6 +647,9 @@ def verify_content_length(bytes) ## === The Body def each + assert("server is not attempting to iterate hijacked response body") { + @response_hijacked == false + } @closed = false bytes = 0 @@ -683,6 +697,9 @@ def each end def close + assert("server is not attempting to close hijacked response") { + @response_hijacked == false + } @closed = true @body.close if @body.respond_to?(:close) end -- Eric Wong