]> granicus.if.org Git - curl/commitdiff
http2: more and better error checking
authorDaniel Stenberg <daniel@haxx.se>
Wed, 23 Jul 2014 07:23:56 +0000 (09:23 +0200)
committerDaniel Stenberg <daniel@haxx.se>
Wed, 23 Jul 2014 07:23:56 +0000 (09:23 +0200)
1 - fixes the warnings when built without http2 support

2 - adds CURLE_HTTP2, a new error code for errors detected by nghttp2
basically when they are about http2 specific things.

docs/libcurl/libcurl-errors.3
docs/libcurl/symbols-in-versions
include/curl/curl.h
lib/http.c
lib/http2.c
lib/http2.h
lib/strerror.c

index 9f295d47078a3a4a8f42de4cda88ca60a994344f..46aa3fef320a6423fa2fbf7e0d28b8af4df9756b 100644 (file)
@@ -83,6 +83,9 @@ FTP servers return a 227-line as a response to a PASV command. If libcurl
 fails to parse that line, this return code is passed back.
 .IP "CURLE_FTP_CANT_GET_HOST (15)"
 An internal failure to lookup the host used for the new connection.
+.IP "CURLE_HTTP2 (16)"
+A problem was detected in the HTTP2 framing layer. This is somewhat generic
+and can be one out of several problems, see the error buffer for details.
 .IP "CURLE_FTP_COULDNT_SET_TYPE (17)"
 Received an error when trying to set the transfer mode to binary or ASCII.
 .IP "CURLE_PARTIAL_FILE (18)"
index 0c9b2b0393b13c8cdf38e942bcd238a4c8bb40d4..6d7334867ea116546dfe7010cca1a9a3fb803a26 100644 (file)
@@ -79,6 +79,7 @@ CURLE_HTTP_PORT_FAILED          7.3           7.12.0
 CURLE_HTTP_POST_ERROR           7.1
 CURLE_HTTP_RANGE_ERROR          7.1           7.17.0
 CURLE_HTTP_RETURNED_ERROR       7.10.3
+CURLE_HTTP2                     7.38.0
 CURLE_INTERFACE_FAILED          7.12.0
 CURLE_LDAP_CANNOT_BIND          7.1
 CURLE_LDAP_INVALID_URL          7.10.8
index 526c7213e6e67efdfbec8117a29eb59f4e53473c..5528d87bf0b542830262b5dbf9354b877c6f8368 100644 (file)
@@ -423,7 +423,9 @@ typedef enum {
   CURLE_FTP_WEIRD_PASV_REPLY,    /* 13 */
   CURLE_FTP_WEIRD_227_FORMAT,    /* 14 */
   CURLE_FTP_CANT_GET_HOST,       /* 15 */
-  CURLE_OBSOLETE16,              /* 16 - NOT USED */
+  CURLE_HTTP2,                   /* 16 - A problem in the http2 framing layer.
+                                    [was obsoleted in August 2007 for 7.17.0,
+                                    reused in July 2014 for 7.38.0] */
   CURLE_FTP_COULDNT_SET_TYPE,    /* 17 */
   CURLE_PARTIAL_FILE,            /* 18 */
   CURLE_FTP_COULDNT_RETR_FILE,   /* 19 */
index 5e8499aa243eb00c062fe364b821e6224d9b96ca..f50ea5262f63be5b6d7c8cfcae7e33de7e399da7 100644 (file)
@@ -1760,8 +1760,9 @@ CURLcode Curl_http(struct connectdata *conn, bool *done)
       if(result)
         return result;
 
-      /* TODO: add error checking here */
-      Curl_http2_switched(conn);
+      result = Curl_http2_switched(conn);
+      if(result)
+        return result;
       break;
     case NPN_HTTP1_1:
       /* continue with HTTP/1.1 when explicitly requested */
@@ -1773,7 +1774,9 @@ CURLcode Curl_http(struct connectdata *conn, bool *done)
   }
   else {
     /* prepare for a http2 request */
-    Curl_http2_setup(conn);
+    result = Curl_http2_setup(conn);
+    if(result)
+      return result;
   }
 
   http = data->req.protop;
@@ -3007,8 +3010,9 @@ CURLcode Curl_http_readwrite_headers(struct SessionHandle *data,
             k->upgr101 = UPGR101_RECEIVED;
 
             /* switch to http2 now */
-            /* TODO: add error checking */
-            Curl_http2_switched(conn);
+            result = Curl_http2_switched(conn);
+            if(result)
+              return result;
           }
           break;
         default:
index c850fdb8f58b09a366486d8d6a767f7e371f45f1..fcc583dc973637f32d5f187110cc876bbfb7a2e7 100644 (file)
@@ -810,12 +810,12 @@ CURLcode Curl_http2_setup(struct connectdata *conn)
   return Curl_add_buffer(httpc->header_recvbuf, "HTTP/2.0 200\r\n", 14);
 }
 
-int Curl_http2_switched(struct connectdata *conn)
+CURLcode Curl_http2_switched(struct connectdata *conn)
 {
-  /* TODO: May get CURLE_AGAIN */
   CURLcode rc;
   struct http_conn *httpc = &conn->proto.httpc;
   int rv;
+  struct SessionHandle *data = conn->data;
 
   httpc->recv_underlying = (recving)conn->recv[FIRSTSOCKET];
   httpc->send_underlying = (sending)conn->send[FIRSTSOCKET];
@@ -827,7 +827,15 @@ int Curl_http2_switched(struct connectdata *conn)
      NGHTTP2_CLIENT_CONNECTION_PREFACE,
      NGHTTP2_CLIENT_CONNECTION_PREFACE_LEN,
      &rc);
-  assert(rv == 24);
+  if(rc)
+    /* TODO: This may get CURLE_AGAIN */
+    return rc;
+
+  if(rv != 24) {
+    failf(data, "Only sent partial HTTP2 packet");
+    return CURLE_SEND_ERROR;
+  }
+
   if(conn->data->req.upgr101 == UPGR101_RECEIVED) {
     /* stream 1 is opened implicitly on upgrade */
     httpc->stream_id = 1;
@@ -835,9 +843,9 @@ int Curl_http2_switched(struct connectdata *conn)
     rv = nghttp2_session_upgrade(httpc->h2, httpc->binsettings,
                                  httpc->binlen, NULL);
     if(rv != 0) {
-      failf(conn->data, "nghttp2_session_upgrade() failed: %s(%d)",
+      failf(data, "nghttp2_session_upgrade() failed: %s(%d)",
             nghttp2_strerror(rv), rv);
-      return -1;
+      return CURLE_HTTP2;
     }
   }
   else {
@@ -845,12 +853,12 @@ int Curl_http2_switched(struct connectdata *conn)
     httpc->stream_id = -1;
     rv = nghttp2_submit_settings(httpc->h2, NGHTTP2_FLAG_NONE, NULL, 0);
     if(rv != 0) {
-      failf(conn->data, "nghttp2_submit_settings() failed: %s(%d)",
+      failf(data, "nghttp2_submit_settings() failed: %s(%d)",
             nghttp2_strerror(rv), rv);
-      return -1;
+      return CURLE_HTTP2;
     }
   }
-  return 0;
+  return CURLE_OK;
 }
 
 #endif
index 5c0ce8e80cb0f77791ae0a16ae61ca434d8da608..66aa6fd5cedf0c0cf410f7f286d81c4e1e9de7e3 100644 (file)
@@ -37,13 +37,13 @@ CURLcode Curl_http2_send_request(struct connectdata *conn);
 CURLcode Curl_http2_request_upgrade(Curl_send_buffer *req,
                                     struct connectdata *conn);
 CURLcode Curl_http2_setup(struct connectdata *conn);
-int Curl_http2_switched(struct connectdata *conn);
+CURLcode Curl_http2_switched(struct connectdata *conn);
 #else /* USE_NGHTTP2 */
 #define Curl_http2_init(x) CURLE_UNSUPPORTED_PROTOCOL
 #define Curl_http2_send_request(x) CURLE_UNSUPPORTED_PROTOCOL
 #define Curl_http2_request_upgrade(x,y) CURLE_UNSUPPORTED_PROTOCOL
 #define Curl_http2_setup(x) CURLE_UNSUPPORTED_PROTOCOL
-#define Curl_http2_switched(x) (-1)
+#define Curl_http2_switched(x) CURLE_UNSUPPORTED_PROTOCOL
 #endif
 
 #endif /* HEADER_CURL_HTTP2_H */
index aec6d38f33663cfc64263a99c38d9c1a1322f476..66033f219817a05ab44f07b39787d5f01f40ebd4 100644 (file)
@@ -105,6 +105,9 @@ curl_easy_strerror(CURLcode error)
   case CURLE_FTP_CANT_GET_HOST:
     return "FTP: can't figure out the host in the PASV response";
 
+  case CURLE_HTTP2:
+    return "Error in the HTTP2 framing layer";
+
   case CURLE_FTP_COULDNT_SET_TYPE:
     return "FTP: couldn't set file type";
 
@@ -296,7 +299,6 @@ curl_easy_strerror(CURLcode error)
     return "The max connection limit is reached";
 
     /* error codes not used by current libcurl */
-  case CURLE_OBSOLETE16:
   case CURLE_OBSOLETE20:
   case CURLE_OBSOLETE24:
   case CURLE_OBSOLETE29: