On Wed, Aug 04, 2021 at 10:53:39AM +0200, Claudio Jeker wrote:
> This adds a few more HTTP Status codes to the mix of the accepted ones.
> Mainly 100, 103 and 203 are now also accepted. All other codes in the 1xx
> and 2xx are still considered an error since they are not expected from the
> GET request made by the http client. This is a minimal HTTP client and it
> should remain minimal. If a server is sending back something unexpected
> just fail and fall back to rsync.
Update with additional comments for the various status codes.
--
:wq Claudio
Index: http.c
===================================================================
RCS file: /cvs/src/usr.sbin/rpki-client/http.c,v
retrieving revision 1.34
diff -u -p -r1.34 http.c
--- http.c 23 Jul 2021 16:03:47 -0000 1.34
+++ http.c 4 Aug 2021 15:22:22 -0000
@@ -865,7 +865,9 @@ http_request(struct http_connection *con
/*
* Parse the HTTP status line.
- * Return 0 for status codes 200, 301-304, 307-308.
+ * Return 0 for status codes 100, 103, 200, 203, 301-304, 307-308.
+ * The other 1xx and 2xx status codes are explicitly not handled and are
+ * considered an error.
* Failure codes and other errors return -1.
* The redirect loop limit is enforced here.
*/
@@ -885,7 +887,7 @@ http_parse_status(struct http_connection
cp++;
strlcpy(ststr, cp, sizeof(ststr));
- status = strtonum(ststr, 200, 599, &errstr);
+ status = strtonum(ststr, 100, 599, &errstr);
if (errstr != NULL) {
strnvis(gerror, cp, sizeof gerror, VIS_SAFE);
warnx("Error retrieving %s: %s", http_info(conn->host),
@@ -894,19 +896,23 @@ http_parse_status(struct http_connection
}
switch (status) {
- case 301:
- case 302:
- case 303:
- case 307:
- case 308:
+ case 301: /* Redirect: moved permanently */
+ case 302: /* Redirect: found / moved temporarily */
+ case 303: /* Redirect: see other */
+ case 307: /* Redirect: temporary redirect */
+ case 308: /* Redirect: permanent redirect */
if (conn->req->redirect_loop++ > 10) {
warnx("%s: Too many redirections requested",
http_info(conn->host));
return -1;
}
/* FALLTHROUGH */
- case 200:
- case 304:
+ case 100: /* Informational: continue (ignored) */
+ case 103: /* Informational: early hints (ignored) */
+ /* FALLTHROUGH */
+ case 200: /* Success: OK */
+ case 203: /* Success: non-authoritative information (proxy) */
+ case 304: /* Redirect: not modified */
conn->status = status;
break;
default:
@@ -931,6 +937,14 @@ http_isredirect(struct http_connection *
return 0;
}
+static inline int
+http_isok(struct http_connection *conn)
+{
+ if (conn->status >= 200 && conn->status < 300)
+ return 1;
+ return 0;
+}
+
static void
http_redirect(struct http_connection *conn)
{
@@ -1165,7 +1179,7 @@ again:
}
/* Check status header and decide what to do next */
- if (conn->status == 200 || http_isredirect(conn)) {
+ if (http_isok(conn) || http_isredirect(conn)) {
if (http_isredirect(conn))
http_redirect(conn);
@@ -1174,6 +1188,8 @@ again:
else
conn->state = STATE_RESPONSE_DATA;
goto again;
+ } else if (conn->status == 100 || conn->status == 103) {
+ conn->state = STATE_RESPONSE_STATUS;
} else if (conn->status == 304) {
return http_done(conn, HTTP_NOT_MOD);
}