From 7049becdfe5fa16820fc7dd3da0866cf08464efd Mon Sep 17 00:00:00 2001 From: Maximilian Hils Date: Sun, 15 Dec 2013 06:42:58 +0100 Subject: [PATCH 1/3] always return Content-Length: 0 if r is not set --- libpathod/language.py | 5 +++-- libpathod/pathoc.py | 12 ++++++------ libpathod/pathod.py | 4 ++-- test/test_pathoc.py | 12 ++++++------ 4 files changed, 17 insertions(+), 16 deletions(-) diff --git a/libpathod/language.py b/libpathod/language.py index 5cce6fdeb..ed5e5f600 100644 --- a/libpathod/language.py +++ b/libpathod/language.py @@ -765,11 +765,12 @@ class _Message(object): def resolve(self, settings, request_host): tokens = self.tokens[:] if not self.raw: - if self.body and not utils.get_header("Content-Length", self.headers): + if not utils.get_header("Content-Length", self.headers): + length = 0 if not self.body else len(self.body.value.get_generator(settings)) tokens.append( Header( ValueLiteral("Content-Length"), - ValueLiteral(str(len(self.body.value.get_generator(settings)))), + ValueLiteral(str(length)), ) ) if request_host: diff --git a/libpathod/pathoc.py b/libpathod/pathoc.py index 32707899e..34dec94f9 100644 --- a/libpathod/pathoc.py +++ b/libpathod/pathoc.py @@ -26,19 +26,19 @@ class Pathoc(tcp.TCPClient): self.ssl, self.sni = ssl, sni self.clientcert = clientcert - def http_connect(self, connect_to, wfile, rfile): - wfile.write( + def http_connect(self, connect_to): + self.wfile.write( 'CONNECT %s:%s HTTP/1.1\r\n'%tuple(connect_to) + '\r\n' ) - wfile.flush() - l = rfile.readline() + self.wfile.flush() + l = self.rfile.readline() if not l: raise PathocError("Proxy CONNECT failed") parsed = http.parse_response_line(l) if not parsed[1] == 200: raise PathocError("Proxy CONNECT failed: %s - %s"%(parsed[1], parsed[2])) - headers = http.read_headers(rfile) + headers = http.read_headers(self.rfile) def connect(self, connect_to=None): """ @@ -47,7 +47,7 @@ class Pathoc(tcp.TCPClient): """ tcp.TCPClient.connect(self) if connect_to: - self.http_connect(connect_to, self.wfile, self.rfile) + self.http_connect(connect_to) if self.ssl: try: self.convert_to_ssl(sni=self.sni, cert=self.clientcert) diff --git a/libpathod/pathod.py b/libpathod/pathod.py index 5fc1fd55b..d925de24b 100644 --- a/libpathod/pathod.py +++ b/libpathod/pathod.py @@ -123,8 +123,8 @@ class PathodHandler(tcp.BaseHandler): ) try: - content = http.read_http_body_request( - self.rfile, self.wfile, headers, httpversion, None + content = http.read_http_body( + self.rfile, headers, None, True ) except http.HttpError, s: s = str(s) diff --git a/test/test_pathoc.py b/test/test_pathoc.py index 31d73111c..7493b2e7f 100644 --- a/test/test_pathoc.py +++ b/test/test_pathoc.py @@ -136,16 +136,16 @@ class TestDaemon(_TestDaemon): def test_connect_fail(self): to = ("foobar", 80) c = pathoc.Pathoc("127.0.0.1", self.d.port) - r, w = cStringIO.StringIO(), cStringIO.StringIO() - tutils.raises("connect failed", c.http_connect, to, w, r) - r = cStringIO.StringIO( + c.rfile, c.wfile = cStringIO.StringIO(), cStringIO.StringIO() + tutils.raises("connect failed", c.http_connect, to) + c.rfile = cStringIO.StringIO( "HTTP/1.1 500 OK\r\n" ) - tutils.raises("connect failed", c.http_connect, to, w, r) - r = cStringIO.StringIO( + tutils.raises("connect failed", c.http_connect, to) + c.rfile = cStringIO.StringIO( "HTTP/1.1 200 OK\r\n" ) - c.http_connect(to, w, r) + c.http_connect(to) From 8229c3884f88b140240694f9d714c179d5561b17 Mon Sep 17 00:00:00 2001 From: Aldo Cortesi Date: Tue, 17 Dec 2013 14:32:41 +1300 Subject: [PATCH 2/3] Ability to specify SSL/TLS version --- libpathod/pathoc.py | 11 +++++++++-- pathoc | 15 +++++++++++++-- 2 files changed, 22 insertions(+), 4 deletions(-) diff --git a/libpathod/pathoc.py b/libpathod/pathoc.py index 32707899e..3e83db49a 100644 --- a/libpathod/pathoc.py +++ b/libpathod/pathoc.py @@ -15,9 +15,15 @@ class Response: def __repr__(self): return "Response(%s - %s)"%(self.status_code, self.msg) +SSLVERSIONS = { + 1: tcp.TLSv1_METHOD, + 2: tcp.SSLv2_METHOD, + 3: tcp.SSLv3_METHOD, + 4: tcp.SSLv23_METHOD, +} class Pathoc(tcp.TCPClient): - def __init__(self, host, port, ssl=None, sni=None, clientcert=None): + def __init__(self, host, port, ssl=None, sni=None, sslversion=1, clientcert=None): tcp.TCPClient.__init__(self, host, port) self.settings = dict( staticdir = os.getcwd(), @@ -25,6 +31,7 @@ class Pathoc(tcp.TCPClient): ) self.ssl, self.sni = ssl, sni self.clientcert = clientcert + self.sslversion = SSLVERSIONS[sslversion] def http_connect(self, connect_to, wfile, rfile): wfile.write( @@ -50,7 +57,7 @@ class Pathoc(tcp.TCPClient): self.http_connect(connect_to, self.wfile, self.rfile) if self.ssl: try: - self.convert_to_ssl(sni=self.sni, cert=self.clientcert) + self.convert_to_ssl(sni=self.sni, cert=self.clientcert, method=self.sslversion) except tcp.NetLibError, v: raise PathocError(str(v)) diff --git a/pathoc b/pathoc index 739f5659c..de8ae948b 100755 --- a/pathoc +++ b/pathoc @@ -60,7 +60,11 @@ if __name__ == "__main__": "-i", dest="sni", type=str, default=False, help="SSL Server Name Indication" ) - + group.add_argument( + "--sslversion", dest="sslversion", type=int, default=1, + choices=[1, 2, 3], + help="Use a specified protocol - TLSv1, SSLv2, SSLv3. Default to TLSv1." + ) group = parser.add_argument_group( 'Controlling Output', @@ -124,7 +128,14 @@ if __name__ == "__main__": try: for i in range(args.repeat): - p = pathoc.Pathoc(args.host, port, ssl=args.ssl, sni=args.sni, clientcert=args.clientcert) + p = pathoc.Pathoc( + args.host, + port, + ssl=args.ssl, + sni=args.sni, + sslversion=args.sslversion, + clientcert=args.clientcert + ) try: p.connect(connect_to) except (tcp.NetLibError, pathoc.PathocError), v: From 53e9b37675c3d4558405a4581ac96a8a43c4a82d Mon Sep 17 00:00:00 2001 From: Maximilian Hils Date: Thu, 9 Jan 2014 17:39:30 +0100 Subject: [PATCH 3/3] display build status from master branch --- README.mkd | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.mkd b/README.mkd index 01b92fcf7..972c7fe3e 100644 --- a/README.mkd +++ b/README.mkd @@ -1,4 +1,4 @@ -[![Build Status](https://travis-ci.org/mitmproxy/pathod.png)](https://travis-ci.org/mitmproxy/pathod) [![Coverage Status](https://coveralls.io/repos/mitmproxy/pathod/badge.png)](https://coveralls.io/r/mitmproxy/pathod) +[![Build Status](https://travis-ci.org/mitmproxy/pathod.png?branch=master)](https://travis-ci.org/mitmproxy/pathod) [![Coverage Status](https://coveralls.io/repos/mitmproxy/pathod/badge.png?branch=master)](https://coveralls.io/r/mitmproxy/pathod) __pathod__ is a collection of pathological tools for testing and torturing HTTP clients and servers. The project has three components: