The branch main has been updated by garga (ports committer):

URL: 
https://cgit.FreeBSD.org/src/commit/?id=345c30a94f6425954163f1e0b075a75f603d27cd

commit 345c30a94f6425954163f1e0b075a75f603d27cd
Author:     Renato Botelho <ga...@freebsd.org>
AuthorDate: 2021-04-01 21:02:57 +0000
Commit:     Renato Botelho <ga...@freebsd.org>
CommitDate: 2021-04-01 21:02:57 +0000

    libfetch: Retry with proxy auth when server returns 407
    
    PR:             220468
    Submitted by:   Egil Hasting <egil.hast...@higen.org> (based on)
    Reviewed by:    kevans, kp
    Approved by:    kp
    MFC after:      2 weeks
    Sponsored by:   Rubicon Communications, LLC ("Netgate")
    Differential Revision:  https://reviews.freebsd.org/D29533
---
 lib/libfetch/http.c | 55 +++++++++++++++++++++++++++++++++++++++++++++++------
 1 file changed, 49 insertions(+), 6 deletions(-)

diff --git a/lib/libfetch/http.c b/lib/libfetch/http.c
index 7f37b7d67197..e61e23b1425a 100644
--- a/lib/libfetch/http.c
+++ b/lib/libfetch/http.c
@@ -73,6 +73,7 @@ __FBSDID("$FreeBSD$");
 #include <locale.h>
 #include <netdb.h>
 #include <stdarg.h>
+#include <stdbool.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
@@ -1387,6 +1388,8 @@ http_connect(struct url *URL, struct url *purl, const 
char *flags)
        int verbose;
        int af, val;
        int serrno;
+       bool isproxyauth = false;
+       http_auth_challenges_t proxy_challenges;
 
 #ifdef INET6
        af = AF_UNSPEC;
@@ -1404,18 +1407,58 @@ http_connect(struct url *URL, struct url *purl, const 
char *flags)
 
        curl = (purl != NULL) ? purl : URL;
 
+retry:
        if ((conn = fetch_connect(curl->host, curl->port, af, verbose)) == NULL)
                /* fetch_connect() has already set an error code */
                return (NULL);
        init_http_headerbuf(&headerbuf);
        if (strcmp(URL->scheme, SCHEME_HTTPS) == 0 && purl) {
-               http_cmd(conn, "CONNECT %s:%d HTTP/1.1",
-                   URL->host, URL->port);
-               http_cmd(conn, "Host: %s:%d",
-                   URL->host, URL->port);
+               init_http_auth_challenges(&proxy_challenges);
+               http_cmd(conn, "CONNECT %s:%d HTTP/1.1", URL->host, URL->port);
+               http_cmd(conn, "Host: %s:%d", URL->host, URL->port);
+               if (isproxyauth) {
+                       http_auth_params_t aparams;
+                       init_http_auth_params(&aparams);
+                       if (*purl->user || *purl->pwd) {
+                               aparams.user = strdup(purl->user);
+                               aparams.password = strdup(purl->pwd);
+                       } else if ((p = getenv("HTTP_PROXY_AUTH")) != NULL &&
+                                   *p != '\0') {
+                               if (http_authfromenv(p, &aparams) < 0) {
+                                       http_seterr(HTTP_NEED_PROXY_AUTH);
+                                       fetch_syserr();
+                                       goto ouch;
+                               }
+                       } else if (fetch_netrc_auth(purl) == 0) {
+                               aparams.user = strdup(purl->user);
+                               aparams.password = strdup(purl->pwd);
+                       } else {
+                               /*
+                                * No auth information found in system - exiting
+                                * with warning.
+                                */
+                               warnx("Missing username and/or password set");
+                               fetch_syserr();
+                               goto ouch;
+                       }
+                       http_authorize(conn, "Proxy-Authorization",
+                           &proxy_challenges, &aparams, purl);
+                       clean_http_auth_params(&aparams);
+               }
                http_cmd(conn, "");
-               if (http_get_reply(conn) != HTTP_OK) {
-                       http_seterr(conn->err);
+               /* Get reply from CONNECT Tunnel attempt */
+               int httpreply = http_get_reply(conn);
+               if (httpreply != HTTP_OK) {
+                       http_seterr(httpreply);
+                       /* If the error is a 407/HTTP_NEED_PROXY_AUTH */
+                       if (httpreply == HTTP_NEED_PROXY_AUTH &&
+                           ! isproxyauth) {
+                               /* Try again with authentication. */
+                               clean_http_headerbuf(&headerbuf);
+                               fetch_close(conn);
+                               isproxyauth = true;
+                               goto retry;
+                       }
                        goto ouch;
                }
                /* Read and discard the rest of the proxy response */
_______________________________________________
dev-commits-src-all@freebsd.org mailing list
https://lists.freebsd.org/mailman/listinfo/dev-commits-src-all
To unsubscribe, send any mail to "dev-commits-src-all-unsubscr...@freebsd.org"

Reply via email to