Author: rhuijben
Date: Wed Nov 25 01:29:14 2015
New Revision: 1716290

URL: http://svn.apache.org/viewvc?rev=1716290&view=rev
Log:
* buckets/fcgi_buckets.c
  (serf__bucket_fcgi_unframe_read_info): Retry reading when possible.
    Handle more status values on record completely read.

* buckets/http2_frame_buckets.c
  (serf__bucket_http2_unframe_read_info): Stop folding several status
    values to APR_SUCCESS.

* protocols/http2_buckets.h
  (serf__bucket_hpack_decode_create): Update documentation.

Modified:
    serf/trunk/buckets/fcgi_buckets.c
    serf/trunk/buckets/http2_frame_buckets.c
    serf/trunk/protocols/http2_buckets.h

Modified: serf/trunk/buckets/fcgi_buckets.c
URL: 
http://svn.apache.org/viewvc/serf/trunk/buckets/fcgi_buckets.c?rev=1716290&r1=1716289&r2=1716290&view=diff
==============================================================================
--- serf/trunk/buckets/fcgi_buckets.c (original)
+++ serf/trunk/buckets/fcgi_buckets.c Wed Nov 25 01:29:14 2015
@@ -74,8 +74,7 @@ apr_status_t serf__bucket_fcgi_unframe_r
                                                  apr_uint16_t *frame_type)
 {
     fcgi_unframe_ctx_t *ctx = bucket->data;
-    const char *data;
-    apr_size_t len;
+    const unsigned char *header;
     apr_status_t status;
 
     if (ctx->record_remaining == 0)
@@ -88,71 +87,74 @@ apr_status_t serf__bucket_fcgi_unframe_r
         return APR_SUCCESS;
     }
 
-    status = serf_bucket_read(ctx->stream, ctx->record_remaining, &data, &len);
-    if (!SERF_BUCKET_READ_ERROR(status))
+    do
     {
-        const unsigned char *header;
+        const char *data;
+        apr_size_t len;
 
-        if (len < FCGI_RECORD_SIZE)
-        {
+        status = serf_bucket_read(ctx->stream, ctx->record_remaining, &data, 
&len);
+
+        if (SERF_BUCKET_READ_ERROR(status))
+            return status;
+
+        if (len < FCGI_RECORD_SIZE) {
             memcpy(ctx->buffer + FCGI_RECORD_SIZE - ctx->record_remaining,
                    data, len);
 
             ctx->record_remaining -= len;
             header = ctx->buffer;
         }
-        else
-        {
+        else {
             header = (const void *)data;
             ctx->record_remaining = 0;
         }
+    } while (!status && ctx->record_remaining > 0);
 
-        if (ctx->record_remaining == 0)
-        {
-            /* We combine version and frametype in a single value */
-            ctx->frame_type = (header[0] << 8) | header[1];
-            ctx->streamid = (header[2] << 8) | header[3];
-            ctx->payload_remaining = (header[4] << 8) | header[5];
-            /* header[6] is reserved */
-            ctx->pad_remaining = header[7];
-
-            /* Fill output arguments if necessary */
-            if (stream_id)
-                *stream_id = ctx->streamid;
-            if (frame_type)
-                *frame_type = ctx->frame_type;
-
-            status = (ctx->payload_remaining == 0) ? APR_EOF
-                : APR_SUCCESS;
-
-            /* If we hava a zero-length frame we have to call the eof callback
-            now, as the read operations will just shortcut to APR_EOF */
-            if (ctx->payload_remaining == 0 && ctx->end_of_frame)
-            {
-                apr_status_t cb_status;
-
-                cb_status = (*ctx->end_of_frame)(ctx->end_of_frame_baton,
-                                                 bucket);
-
-                ctx->end_of_frame = NULL;
-
-                if (SERF_BUCKET_READ_ERROR(cb_status))
-                    status = cb_status;
-            }
-        }
+    if (ctx->record_remaining == 0)
+    {
+        /* We combine version and frametype in a single value */
+        ctx->frame_type = (header[0] << 8) | header[1];
+        ctx->streamid = (header[2] << 8) | header[3];
+        ctx->payload_remaining = (header[4] << 8) | header[5];
+        /* header[6] is reserved */
+        ctx->pad_remaining = header[7];
+
+        /* Fill output arguments if necessary */
+        if (stream_id)
+            *stream_id = ctx->streamid;
+        if (frame_type)
+            *frame_type = ctx->frame_type;
+
+        if (ctx->payload_remaining == 0)
+            status = APR_EOF;
         else if (APR_STATUS_IS_EOF(status))
+            status = SERF_ERROR_TRUNCATED_STREAM;
+
+        /* If we hava a zero-length frame we have to call the eof callback
+           now, as the read operations will just shortcut to APR_EOF */
+        if (ctx->payload_remaining == 0 && ctx->end_of_frame)
         {
-            /* Reading frame failed because we couldn't read the header. Report
-               a read failure instead of semi-success */
-            if (ctx->record_remaining == FCGI_RECORD_SIZE)
-                status = SERF_ERROR_EMPTY_STREAM;
-            else
-                status = SERF_ERROR_TRUNCATED_STREAM;
-        }
-        else if (!status)
-            status = APR_EAGAIN;
+            apr_status_t cb_status;
+
+            cb_status = (*ctx->end_of_frame)(ctx->end_of_frame_baton,
+                                                bucket);
 
+            ctx->end_of_frame = NULL;
+
+            if (SERF_BUCKET_READ_ERROR(cb_status))
+                status = cb_status;
+        }
+    }
+    else if (APR_STATUS_IS_EOF(status))
+    {
+        /* Reading frame failed because we couldn't read the header. Report
+            a read failure instead of semi-success */
+        if (ctx->record_remaining == FCGI_RECORD_SIZE)
+            status = SERF_ERROR_EMPTY_STREAM;
+        else
+            status = SERF_ERROR_TRUNCATED_STREAM;
     }
+
     return status;
 }
 

Modified: serf/trunk/buckets/http2_frame_buckets.c
URL: 
http://svn.apache.org/viewvc/serf/trunk/buckets/http2_frame_buckets.c?rev=1716290&r1=1716289&r2=1716290&view=diff
==============================================================================
--- serf/trunk/buckets/http2_frame_buckets.c (original)
+++ serf/trunk/buckets/http2_frame_buckets.c Wed Nov 25 01:29:14 2015
@@ -166,8 +166,10 @@ serf__bucket_http2_unframe_read_info(ser
             return SERF_ERROR_HTTP2_FRAME_SIZE_ERROR;
         }
 
-        status = (ctx->payload_remaining == 0) ? APR_EOF
-            : APR_SUCCESS;
+        if (ctx->payload_remaining == 0)
+            status = APR_EOF;
+        else if (APR_STATUS_IS_EOF(status))
+            status = SERF_ERROR_TRUNCATED_STREAM;
 
         /* If we hava a zero-length frame we have to call the eof callback
             now, as the read operations will just shortcut to APR_EOF */

Modified: serf/trunk/protocols/http2_buckets.h
URL: 
http://svn.apache.org/viewvc/serf/trunk/protocols/http2_buckets.h?rev=1716290&r1=1716289&r2=1716290&view=diff
==============================================================================
--- serf/trunk/protocols/http2_buckets.h (original)
+++ serf/trunk/protocols/http2_buckets.h Wed Nov 25 01:29:14 2015
@@ -178,7 +178,7 @@ extern const serf_bucket_type_t serf_buc
 #define SERF_BUCKET_IS_HPACK_DECODE(b) SERF_BUCKET_CHECK((b), hpack_decode)
 
 /* If ITEM_CALLBACK is not null calls it for every item while reading, and
-   the bucket will just return no data and APR_EAGAIN until done.
+   the bucket will just return no data until EOF.
 
    If ITEM_CALLBACK is NULL, the bucket will read as a HTTP/1 like header 
block,
    starting with a status line and ending with "\r\n\r\n", which allows using


Reply via email to