]> git.ipfire.org Git - thirdparty/squid.git/commitdiff
Make HttpParser parse method directly into HttpRequestMethod object
authorAmos Jeffries <squid3@treenet.co.nz>
Sat, 28 Dec 2013 01:03:29 +0000 (17:03 -0800)
committerAmos Jeffries <squid3@treenet.co.nz>
Sat, 28 Dec 2013 01:03:29 +0000 (17:03 -0800)
There appears to be no need for the HTTP method object to be outside
the parser. We can simplify the processing code by parsing directly into
the object from the I/O buffer.

TODO:
* fix parsing of whitespace prefix in accordance with HTTPbis specs.
* make parser incremental to end of method

src/client_side.cc
src/http/Http1Parser.cc
src/http/Http1Parser.h
src/http/RequestMethod.h
src/tests/testHttp1Parser.cc

index c82f1fb9b5334f1fa5997b595c4542f7bec470a4..a0052656a3907fb59de5a79c5f61794c35d7cfb1 100644 (file)
@@ -206,7 +206,7 @@ static IOACB httpsAccept;
 #endif
 static CTCB clientLifetimeTimeout;
 static ClientSocketContext *parseHttpRequestAbort(ConnStateData * conn, const char *uri);
-static ClientSocketContext *parseHttpRequest(ConnStateData *, const Http::Http1ParserPointer &, HttpRequestMethod *);
+static ClientSocketContext *parseHttpRequest(ConnStateData *, const Http::Http1ParserPointer &);
 #if USE_IDENT
 static IDCB clientIdentDone;
 #endif
@@ -2212,7 +2212,7 @@ prepareTransparentURL(ConnStateData * conn, ClientHttpRequest *http, char *url,
  *          a ClientSocketContext structure on success or failure.
  */
 static ClientSocketContext *
-parseHttpRequest(ConnStateData *csd, const Http::Http1ParserPointer &hp, HttpRequestMethod * method_p)
+parseHttpRequest(ConnStateData *csd, const Http::Http1ParserPointer &hp)
 {
     char *req_hdr = NULL;
     char *end;
@@ -2221,9 +2221,6 @@ parseHttpRequest(ConnStateData *csd, const Http::Http1ParserPointer &hp, HttpReq
     ClientSocketContext *result;
     StoreIOBuffer tempBuffer;
 
-    /* pre-set these values to make aborting simpler */
-    *method_p = Http::METHOD_NONE;
-
     /* NP: don't be tempted to move this down or remove again.
      * It's the only DDoS protection old-String has against long URL */
     if ( hp->bufsiz <= 0) {
@@ -2280,11 +2277,8 @@ parseHttpRequest(ConnStateData *csd, const Http::Http1ParserPointer &hp, HttpReq
         return parseHttpRequestAbort(csd, "error:request-too-large");
     }
 
-    /* Set method_p */
-    *method_p = HttpRequestMethod(&hp->buf[hp->req.m_start], &hp->buf[hp->req.m_end]+1);
-
     /* deny CONNECT via accelerated ports */
-    if (*method_p == Http::METHOD_CONNECT && csd->port && csd->port->flags.accelSurrogate) {
+    if (*(hp->method()) == Http::METHOD_CONNECT && csd->port && csd->port->flags.accelSurrogate) {
         debugs(33, DBG_IMPORTANT, "WARNING: CONNECT method received on " << csd->port->transport.protocol << " Accelerator port " << csd->port->s.port());
         /* XXX need a way to say "this many character length string" */
         debugs(33, DBG_IMPORTANT, "WARNING: for request: " << hp->buf);
@@ -2292,7 +2286,7 @@ parseHttpRequest(ConnStateData *csd, const Http::Http1ParserPointer &hp, HttpReq
         return parseHttpRequestAbort(csd, "error:method-not-allowed");
     }
 
-    if (*method_p == Http::METHOD_NONE) {
+    if (*(hp->method()) == Http::METHOD_NONE) {
         /* XXX need a way to say "this many character length string" */
         debugs(33, DBG_IMPORTANT, "clientParseRequestMethod: Unsupported method in request '" << hp->buf << "'");
         hp->request_parse_status = Http::scMethodNotAllowed;
@@ -2638,7 +2632,7 @@ bool ConnStateData::serveDelayedError(ClientSocketContext *context)
 #endif // USE_SSL
 
 static void
-clientProcessRequest(ConnStateData *conn, const Http::Http1ParserPointer &hp, ClientSocketContext *context, const HttpRequestMethod& method)
+clientProcessRequest(ConnStateData *conn, const Http::Http1ParserPointer &hp, ClientSocketContext *context)
 {
     ClientHttpRequest *http = context->http;
     HttpRequest::Pointer request;
@@ -2648,6 +2642,7 @@ clientProcessRequest(ConnStateData *conn, const Http::Http1ParserPointer &hp, Cl
     bool unsupportedTe = false;
     bool expectBody = false;
     const AnyP::ProtocolVersion &http_ver = hp->messageProtocol();
+    const HttpRequestMethodPointer method = hp->method();
 
     /* We have an initial client stream in place should it be needed */
     /* setup our private context */
@@ -2663,14 +2658,14 @@ clientProcessRequest(ConnStateData *conn, const Http::Http1ParserPointer &hp, Cl
         assert (repContext);
         switch (hp->request_parse_status) {
         case Http::scHeaderTooLarge:
-            repContext->setReplyToError(ERR_TOO_BIG, Http::scBadRequest, method, http->uri, conn->clientConnection->remote, NULL, conn->in.buf, NULL);
+            repContext->setReplyToError(ERR_TOO_BIG, Http::scBadRequest, *method, http->uri, conn->clientConnection->remote, NULL, conn->in.buf, NULL);
             break;
         case Http::scMethodNotAllowed:
-            repContext->setReplyToError(ERR_UNSUP_REQ, Http::scMethodNotAllowed, method, http->uri,
+            repContext->setReplyToError(ERR_UNSUP_REQ, Http::scMethodNotAllowed, *method, http->uri,
                                         conn->clientConnection->remote, NULL, conn->in.buf, NULL);
             break;
         default:
-            repContext->setReplyToError(ERR_INVALID_REQ, hp->request_parse_status, method, http->uri,
+            repContext->setReplyToError(ERR_INVALID_REQ, hp->request_parse_status, *method, http->uri,
                                         conn->clientConnection->remote, NULL, conn->in.buf, NULL);
         }
         assert(context->http->out.offset == 0);
@@ -2678,7 +2673,7 @@ clientProcessRequest(ConnStateData *conn, const Http::Http1ParserPointer &hp, Cl
         goto finish;
     }
 
-    if ((request = HttpRequest::CreateFromUrlAndMethod(http->uri, method)) == NULL) {
+    if ((request = HttpRequest::CreateFromUrlAndMethod(http->uri, *method)) == NULL) {
         clientStreamNode *node = context->getClientReplyContext();
         debugs(33, 5, "Invalid URL: " << http->uri);
         conn->quitAfterError(request.getRaw());
@@ -2686,7 +2681,7 @@ clientProcessRequest(ConnStateData *conn, const Http::Http1ParserPointer &hp, Cl
         setLogUri(http, http->uri,  true);
         clientReplyContext *repContext = dynamic_cast<clientReplyContext *>(node->data.getRaw());
         assert (repContext);
-        repContext->setReplyToError(ERR_INVALID_URL, Http::scBadRequest, method, http->uri, conn->clientConnection->remote, NULL, NULL, NULL);
+        repContext->setReplyToError(ERR_INVALID_URL, Http::scBadRequest, *method, http->uri, conn->clientConnection->remote, NULL, NULL, NULL);
         assert(context->http->out.offset == 0);
         context->pullData();
         goto finish;
@@ -2704,7 +2699,7 @@ clientProcessRequest(ConnStateData *conn, const Http::Http1ParserPointer &hp, Cl
         setLogUri(http, http->uri,  true);
         clientReplyContext *repContext = dynamic_cast<clientReplyContext *>(node->data.getRaw());
         assert (repContext);
-        repContext->setReplyToError(ERR_UNSUP_HTTPVERSION, Http::scHttpVersionNotSupported, method, http->uri,
+        repContext->setReplyToError(ERR_UNSUP_HTTPVERSION, Http::scHttpVersionNotSupported, *method, http->uri,
                                     conn->clientConnection->remote, NULL, hp->rawHeaderBuf(), NULL);
         assert(context->http->out.offset == 0);
         context->pullData();
@@ -2722,7 +2717,7 @@ clientProcessRequest(ConnStateData *conn, const Http::Http1ParserPointer &hp, Cl
         setLogUri(http, http->uri,  true);
         clientReplyContext *repContext = dynamic_cast<clientReplyContext *>(node->data.getRaw());
         assert (repContext);
-        repContext->setReplyToError(ERR_INVALID_REQ, Http::scBadRequest, method, http->uri, conn->clientConnection->remote, NULL, NULL, NULL);
+        repContext->setReplyToError(ERR_INVALID_REQ, Http::scBadRequest, *method, http->uri, conn->clientConnection->remote, NULL, NULL, NULL);
         assert(context->http->out.offset == 0);
         context->pullData();
         goto finish;
@@ -2805,7 +2800,7 @@ clientProcessRequest(ConnStateData *conn, const Http::Http1ParserPointer &hp, Cl
         unsupportedTe = te.size() && te != "identity";
     } // else implied identity coding
 
-    mustReplyToOptions = (method == Http::METHOD_OPTIONS) &&
+    mustReplyToOptions = (*method == Http::METHOD_OPTIONS) &&
                          (request->header.getInt64(HDR_MAX_FORWARDS) == 0);
     if (!urlCheckRequest(request.getRaw()) || mustReplyToOptions || unsupportedTe) {
         clientStreamNode *node = context->getClientReplyContext();
@@ -2963,7 +2958,6 @@ ConnStateData::concurrentRequestQueueFilled() const
 bool
 ConnStateData::clientParseRequests()
 {
-    HttpRequestMethod method;
     bool parsed_req = false;
 
     debugs(33, 5, HERE << clientConnection << ": attempting to parse");
@@ -2997,7 +2991,7 @@ ConnStateData::clientParseRequests()
             parser_->bufsiz = in.notYetUsed;
 
         /* Process request */
-        ClientSocketContext *context = parseHttpRequest(this, parser_, &method);
+        ClientSocketContext *context = parseHttpRequest(this, parser_);
         PROF_stop(parseHttpRequest);
 
         /* partial or incomplete request */
@@ -3015,7 +3009,7 @@ ConnStateData::clientParseRequests()
                                              CommTimeoutCbPtrFun(clientLifetimeTimeout, context->http));
             commSetConnTimeout(clientConnection, Config.Timeout.lifetime, timeoutCall);
 
-            clientProcessRequest(this, parser_, context, method);
+            clientProcessRequest(this, parser_, context);
 
             parsed_req = true; // XXX: do we really need to parse everything right NOW ?
 
index f153413172a1a0cd5a5839a187eab2c72757dbdf..8b535c0212008d72f7e8d05349af2927848b4d9a 100644 (file)
@@ -1,6 +1,7 @@
 #include "squid.h"
 #include "Debug.h"
 #include "http/Http1Parser.h"
+#include "http/RequestMethod.h"
 #include "profiler/Profiler.h"
 #include "SquidConfig.h"
 
@@ -18,6 +19,7 @@ Http::Http1Parser::clear()
     req.u_start = req.u_end = -1;
     req.v_start = req.v_end = -1;
     msgProtocol_ = AnyP::ProtocolVersion();
+    method_ = NULL;
 }
 
 void
@@ -137,6 +139,9 @@ Http::Http1Parser::parseRequestFirstLine()
         return -1;
     }
 
+    /* Set method_ */
+    method_ = new HttpRequestMethod(&buf[req.m_start], &buf[req.m_end]+1);
+
     // First non-whitespace after first SP = beginning of URL+Version
     if (second_word > line_end || second_word < req.start) {
         request_parse_status = Http::scBadRequest; // missing URI
index 45dc22233b89408d7d5d2d669512752d7b39b539..0be9b09b33f5906314ca005ee1e235672b3c3cdb 100644 (file)
@@ -2,6 +2,7 @@
 #define _SQUID_SRC_HTTP_HTTP1PARSER_H
 
 #include "base/RefCount.h"
+#include "http/forward.h"
 #include "http/ProtocolVersion.h"
 #include "http/StatusCode.h"
 
@@ -104,6 +105,9 @@ public:
     /// the protocol label for this message
     const AnyP::ProtocolVersion & messageProtocol() const {return msgProtocol_;}
 
+    /// the HTTP method if this is a request method
+    const HttpRequestMethodPointer & method() const {return method_;}
+
     // Offsets for pieces of the MiME Header segment
     int hdr_start, hdr_end;
 
@@ -123,6 +127,9 @@ private:
 
     /// what protocol label has been found in the first line
     AnyP::ProtocolVersion msgProtocol_;
+
+    /// what request method has been found on the first line
+    HttpRequestMethodPointer method_;
 };
 
 } // namespace Http
index 1bb5f000424391f90d3ed4660c755992084d3e15..40bb82433cddce54b978be3231c17e31545c8957 100644 (file)
@@ -13,7 +13,7 @@
  * It has a runtime extension facility to allow it to
  * efficiently support new methods
  */
-class HttpRequestMethod
+class HttpRequestMethod : public RefCountable
 {
 public:
     HttpRequestMethod() : theMethod(Http::METHOD_NONE), theImage() {}
index 8079e21fdcc51e1aef63c17ae1cfbb8ef2df31e5..50281f4caebcb122c022d69a9c462385f655e3b1 100644 (file)
@@ -8,6 +8,7 @@
 
 #include "testHttp1Parser.h"
 #include "http/Http1Parser.h"
+#include "http/RequestMethod.h"
 #include "Mem.h"
 #include "MemBuf.h"
 #include "SquidConfig.h"
@@ -52,6 +53,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start], (output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start], (output.req.u_end-output.req.u_start+1)));
@@ -71,16 +73,17 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(Http::scOkay, output.request_parse_status);
         CPPUNIT_ASSERT_EQUAL(0, output.req.start);
         CPPUNIT_ASSERT_EQUAL((int)input.contentSize()-1, output.req.end);
-        CPPUNIT_ASSERT_EQUAL(0,memcmp("GET /\r\n", &output.buf[output.req.start],(output.req.end-output.req.start+1)));
+        CPPUNIT_ASSERT_EQUAL(0,memcmp("POST /\r\n", &output.buf[output.req.start],(output.req.end-output.req.start+1)));
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
-        CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
-        CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start], (output.req.m_end-output.req.m_start+1)));
-        CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
-        CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
+        CPPUNIT_ASSERT_EQUAL(3, output.req.m_end);
+        CPPUNIT_ASSERT_EQUAL(0, memcmp("POST", &output.buf[output.req.m_start], (output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_POST), *output.method_);
+        CPPUNIT_ASSERT_EQUAL(5, output.req.u_start);
+        CPPUNIT_ASSERT_EQUAL(5, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start], (output.req.u_end-output.req.u_start+1)));
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_end);
-        CPPUNIT_ASSERT_EQUAL(AnyP::ProtocolVersion(AnyP::PROTO_HTTP,0,9), output.msgProtocol_);
+        CPPUNIT_ASSERT_EQUAL(AnyP::ProtocolVersion(), output.msgProtocol_);
         input.reset();
     }
 #endif
@@ -98,6 +101,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -121,6 +125,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -144,6 +149,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -169,6 +175,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -206,6 +213,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(6, output.req.v_start);
         CPPUNIT_ASSERT_EQUAL(12, output.req.v_end);
@@ -227,6 +235,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -251,6 +260,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -275,6 +285,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -299,6 +310,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -323,6 +335,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -347,6 +360,7 @@ testHttp1Parser::testParseRequestLineProtocols()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -382,6 +396,7 @@ testHttp1Parser::testParseRequestLineStrange()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(5, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(5, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -406,6 +421,7 @@ testHttp1Parser::testParseRequestLineStrange()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(9, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/fo o/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -430,6 +446,7 @@ testHttp1Parser::testParseRequestLineStrange()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end); // strangeness generated by following RFC
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -465,6 +482,7 @@ testHttp1Parser::testParseRequestLineTerminators()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -489,6 +507,7 @@ testHttp1Parser::testParseRequestLineTerminators()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -515,6 +534,7 @@ testHttp1Parser::testParseRequestLineTerminators()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -563,6 +583,7 @@ testHttp1Parser::testParseRequestLineTerminators()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(13, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/ HTTP/1.1", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -584,6 +605,7 @@ testHttp1Parser::testParseRequestLineTerminators()
         CPPUNIT_ASSERT_EQUAL(-1, output.req.end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_end);
+        CPPUNIT_ASSERT(!output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
@@ -601,6 +623,7 @@ testHttp1Parser::testParseRequestLineTerminators()
         CPPUNIT_ASSERT_EQUAL(-1, output.req.end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_end);
+        CPPUNIT_ASSERT(!output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
@@ -618,6 +641,7 @@ testHttp1Parser::testParseRequestLineTerminators()
         CPPUNIT_ASSERT_EQUAL(-1, output.req.end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_end);
+        CPPUNIT_ASSERT(!output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
@@ -635,6 +659,7 @@ testHttp1Parser::testParseRequestLineTerminators()
         CPPUNIT_ASSERT_EQUAL(-1, output.req.end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_end);
+        CPPUNIT_ASSERT(!output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
@@ -668,6 +693,7 @@ testHttp1Parser::testParseRequestLineMethods()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp(".", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(".", NULL), *output.method_);
         CPPUNIT_ASSERT_EQUAL(2, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -692,6 +718,7 @@ testHttp1Parser::testParseRequestLineMethods()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(6, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("OPTIONS", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_OPTIONS), *output.method_);
         CPPUNIT_ASSERT_EQUAL(8, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(8, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("*", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -716,6 +743,7 @@ testHttp1Parser::testParseRequestLineMethods()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(9, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("HELLOWORLD", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod("HELLOWORLD",NULL), *output.method_);
         CPPUNIT_ASSERT_EQUAL(11, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(11, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -739,6 +767,7 @@ testHttp1Parser::testParseRequestLineMethods()
         CPPUNIT_ASSERT_EQUAL(0, memcmp("A\n", &output.buf[output.req.start],(output.req.end-output.req.start+1)));
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_end);
+        CPPUNIT_ASSERT(!output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
@@ -759,6 +788,7 @@ testHttp1Parser::testParseRequestLineMethods()
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET\n", &output.buf[output.req.start],(output.req.end-output.req.start+1)));
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_end);
+        CPPUNIT_ASSERT(!output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
@@ -782,6 +812,7 @@ testHttp1Parser::testParseRequestLineMethods()
         CPPUNIT_ASSERT_EQUAL(1, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(3, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(5, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(5, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -806,12 +837,14 @@ testHttp1Parser::testParseRequestLineMethods()
         CPPUNIT_ASSERT_EQUAL(0, memcmp(" GET / HTTP/1.1\n", &output.buf[output.req.start],(output.req.end-output.req.start+1)));
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_end);
+        CPPUNIT_ASSERT(!output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_end);
         CPPUNIT_ASSERT_EQUAL(AnyP::ProtocolVersion(AnyP::PROTO_NONE,0,0), output.msgProtocol_);
         input.reset();
+        Config.onoff.relaxed_header_parser = 1;
     }
 
     // tab padded method (NP: tab is not SP so treated as any other binary)
@@ -828,6 +861,7 @@ testHttp1Parser::testParseRequestLineMethods()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(3, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("\tGET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(&output.buf[output.req.m_start],&output.buf[output.req.m_end+1]), *output.method_);
         CPPUNIT_ASSERT_EQUAL(5, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(5, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -864,6 +898,7 @@ testHttp1Parser::testParseRequestLineInvalid()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod("/",NULL), *output.method_);
         CPPUNIT_ASSERT_EQUAL(2, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(9, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("HTTP/1.0", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -889,6 +924,7 @@ testHttp1Parser::testParseRequestLineInvalid()
         CPPUNIT_ASSERT_EQUAL(1, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(1, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod("/",NULL), *output.method_);
         CPPUNIT_ASSERT_EQUAL(3, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(10, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("HTTP/1.0", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -913,6 +949,7 @@ testHttp1Parser::testParseRequestLineInvalid()
         CPPUNIT_ASSERT_EQUAL(0, memcmp(" / HTTP/1.0\n", &output.buf[output.req.start],(output.req.end-output.req.start+1)));
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_end);
+        CPPUNIT_ASSERT(!output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
@@ -935,6 +972,7 @@ testHttp1Parser::testParseRequestLineInvalid()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(3, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET\x0B", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+//        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod("GET\0x0B",NULL), *output.method_);
         CPPUNIT_ASSERT_EQUAL(5, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(5, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -958,6 +996,7 @@ testHttp1Parser::testParseRequestLineInvalid()
         CPPUNIT_ASSERT_EQUAL(-1, output.req.end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_end);
+        CPPUNIT_ASSERT(!output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
@@ -980,6 +1019,7 @@ testHttp1Parser::testParseRequestLineInvalid()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(3, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET\0", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+//        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod("GET\0",NULL), *output.method_);
         CPPUNIT_ASSERT_EQUAL(5, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(5, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("/", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -1004,6 +1044,7 @@ testHttp1Parser::testParseRequestLineInvalid()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(5, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(12, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
@@ -1027,6 +1068,7 @@ testHttp1Parser::testParseRequestLineInvalid()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(2, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("GET", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(Http::METHOD_GET), *output.method_);
         CPPUNIT_ASSERT_EQUAL(4, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(11, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("HTTP/1.1", &output.buf[output.req.u_start],(output.req.u_end-output.req.u_start+1)));
@@ -1049,6 +1091,7 @@ testHttp1Parser::testParseRequestLineInvalid()
         CPPUNIT_ASSERT_EQUAL(0, memcmp("\xB\xC\xE\xF\n", &output.buf[output.req.start],(output.req.end-output.req.start+1)));
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_end);
+        CPPUNIT_ASSERT(!output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
@@ -1073,6 +1116,7 @@ testHttp1Parser::testParseRequestLineInvalid()
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(0, output.req.m_end);
         CPPUNIT_ASSERT_EQUAL(0, memcmp("\t", &output.buf[output.req.m_start],(output.req.m_end-output.req.m_start+1)));
+        CPPUNIT_ASSERT_EQUAL(HttpRequestMethod(&output.buf[output.req.m_start],&output.buf[output.req.m_end+1]), *output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);
@@ -1095,6 +1139,7 @@ testHttp1Parser::testParseRequestLineInvalid()
         CPPUNIT_ASSERT_EQUAL(-1, output.req.end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.m_end);
+        CPPUNIT_ASSERT(!output.method_);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_start);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.u_end);
         CPPUNIT_ASSERT_EQUAL(-1, output.req.v_start);