Skip to content

Commit 7265f75

Browse files
authored
Address deprecated curl APIs (#4245)
This fixes the `linux-musl` and `osx-gcc` jobs which [started](https://github.com/git-for-windows/git/actions/runs/3985792568/jobs/6833602370) to [fail](https://github.com/git-for-windows/git/actions/runs/3985792568/jobs/6833601563).
2 parents 7360767 + de848e3 commit 7265f75

File tree

6 files changed

+81
-44
lines changed

6 files changed

+81
-44
lines changed

INSTALL

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -139,7 +139,7 @@ Issues of note:
139139
not need that functionality, use NO_CURL to build without
140140
it.
141141

142-
Git requires version "7.19.4" or later of "libcurl" to build
142+
Git requires version "7.19.5" or later of "libcurl" to build
143143
without NO_CURL. This version requirement may be bumped in
144144
the future.
145145

git-curl-compat.h

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -127,6 +127,14 @@
127127
#endif
128128

129129
/**
130+
* CURLOPT_PROTOCOLS_STR and CURLOPT_REDIR_PROTOCOLS_STR were added in 7.85.0,
131+
* released in August 2022.
132+
*/
133+
#if LIBCURL_VERSION_NUM >= 0x075500
134+
#define GIT_CURL_HAVE_CURLOPT_PROTOCOLS_STR 1
135+
#endif
136+
137+
/*
130138
* CURLSSLOPT_AUTO_CLIENT_CERT was added in 7.77.0, released in May
131139
* 2021.
132140
*/

http-push.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -198,13 +198,13 @@ static void curl_setup_http(CURL *curl, const char *url,
198198
const char *custom_req, struct buffer *buffer,
199199
curl_write_callback write_fn)
200200
{
201-
curl_easy_setopt(curl, CURLOPT_PUT, 1);
201+
curl_easy_setopt(curl, CURLOPT_UPLOAD, 1);
202202
curl_easy_setopt(curl, CURLOPT_URL, url);
203203
curl_easy_setopt(curl, CURLOPT_INFILE, buffer);
204204
curl_easy_setopt(curl, CURLOPT_INFILESIZE, buffer->buf.len);
205205
curl_easy_setopt(curl, CURLOPT_READFUNCTION, fread_buffer);
206-
curl_easy_setopt(curl, CURLOPT_IOCTLFUNCTION, ioctl_buffer);
207-
curl_easy_setopt(curl, CURLOPT_IOCTLDATA, buffer);
206+
curl_easy_setopt(curl, CURLOPT_SEEKFUNCTION, seek_buffer);
207+
curl_easy_setopt(curl, CURLOPT_SEEKDATA, buffer);
208208
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, write_fn);
209209
curl_easy_setopt(curl, CURLOPT_NOBODY, 0);
210210
curl_easy_setopt(curl, CURLOPT_CUSTOMREQUEST, custom_req);

http.c

Lines changed: 55 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -165,21 +165,19 @@ size_t fread_buffer(char *ptr, size_t eltsize, size_t nmemb, void *buffer_)
165165
return size / eltsize;
166166
}
167167

168-
curlioerr ioctl_buffer(CURL *handle, int cmd, void *clientp)
168+
int seek_buffer(void *clientp, curl_off_t offset, int origin)
169169
{
170170
struct buffer *buffer = clientp;
171171

172-
switch (cmd) {
173-
case CURLIOCMD_NOP:
174-
return CURLIOE_OK;
175-
176-
case CURLIOCMD_RESTARTREAD:
177-
buffer->posn = 0;
178-
return CURLIOE_OK;
179-
180-
default:
181-
return CURLIOE_UNKNOWNCMD;
172+
if (origin != SEEK_SET)
173+
BUG("seek_buffer only handles SEEK_SET");
174+
if (offset < 0 || offset >= buffer->buf.len) {
175+
error("curl seek would be outside of buffer");
176+
return CURL_SEEKFUNC_FAIL;
182177
}
178+
179+
buffer->posn = offset;
180+
return CURL_SEEKFUNC_OK;
183181
}
184182

185183
size_t fwrite_buffer(char *ptr, size_t eltsize, size_t nmemb, void *buffer_)
@@ -791,20 +789,37 @@ void setup_curl_trace(CURL *handle)
791789
curl_easy_setopt(handle, CURLOPT_DEBUGDATA, NULL);
792790
}
793791

794-
static long get_curl_allowed_protocols(int from_user)
792+
static void proto_list_append(struct strbuf *list, const char *proto)
795793
{
796-
long allowed_protocols = 0;
794+
if (!list)
795+
return;
796+
if (list->len)
797+
strbuf_addch(list, ',');
798+
strbuf_addstr(list, proto);
799+
}
797800

798-
if (is_transport_allowed("http", from_user))
799-
allowed_protocols |= CURLPROTO_HTTP;
800-
if (is_transport_allowed("https", from_user))
801-
allowed_protocols |= CURLPROTO_HTTPS;
802-
if (is_transport_allowed("ftp", from_user))
803-
allowed_protocols |= CURLPROTO_FTP;
804-
if (is_transport_allowed("ftps", from_user))
805-
allowed_protocols |= CURLPROTO_FTPS;
801+
static long get_curl_allowed_protocols(int from_user, struct strbuf *list)
802+
{
803+
long bits = 0;
806804

807-
return allowed_protocols;
805+
if (is_transport_allowed("http", from_user)) {
806+
bits |= CURLPROTO_HTTP;
807+
proto_list_append(list, "http");
808+
}
809+
if (is_transport_allowed("https", from_user)) {
810+
bits |= CURLPROTO_HTTPS;
811+
proto_list_append(list, "https");
812+
}
813+
if (is_transport_allowed("ftp", from_user)) {
814+
bits |= CURLPROTO_FTP;
815+
proto_list_append(list, "ftp");
816+
}
817+
if (is_transport_allowed("ftps", from_user)) {
818+
bits |= CURLPROTO_FTPS;
819+
proto_list_append(list, "ftps");
820+
}
821+
822+
return bits;
808823
}
809824

810825
#ifdef GIT_CURL_HAVE_CURL_HTTP_VERSION_2
@@ -959,10 +974,26 @@ static CURL *get_curl_handle(void)
959974

960975
curl_easy_setopt(result, CURLOPT_MAXREDIRS, 20);
961976
curl_easy_setopt(result, CURLOPT_POSTREDIR, CURL_REDIR_POST_ALL);
977+
978+
#ifdef GIT_CURL_HAVE_CURLOPT_PROTOCOLS_STR
979+
{
980+
struct strbuf buf = STRBUF_INIT;
981+
982+
get_curl_allowed_protocols(0, &buf);
983+
curl_easy_setopt(result, CURLOPT_REDIR_PROTOCOLS_STR, buf.buf);
984+
strbuf_reset(&buf);
985+
986+
get_curl_allowed_protocols(-1, &buf);
987+
curl_easy_setopt(result, CURLOPT_PROTOCOLS_STR, buf.buf);
988+
strbuf_release(&buf);
989+
}
990+
#else
962991
curl_easy_setopt(result, CURLOPT_REDIR_PROTOCOLS,
963-
get_curl_allowed_protocols(0));
992+
get_curl_allowed_protocols(0, NULL));
964993
curl_easy_setopt(result, CURLOPT_PROTOCOLS,
965-
get_curl_allowed_protocols(-1));
994+
get_curl_allowed_protocols(-1, NULL));
995+
#endif
996+
966997
if (getenv("GIT_CURL_VERBOSE"))
967998
http_trace_curl_no_data();
968999
setup_curl_trace(result);

http.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ struct buffer {
4040
size_t fread_buffer(char *ptr, size_t eltsize, size_t nmemb, void *strbuf);
4141
size_t fwrite_buffer(char *ptr, size_t eltsize, size_t nmemb, void *strbuf);
4242
size_t fwrite_null(char *ptr, size_t eltsize, size_t nmemb, void *strbuf);
43-
curlioerr ioctl_buffer(CURL *handle, int cmd, void *clientp);
43+
int seek_buffer(void *clientp, curl_off_t offset, int origin);
4444

4545
/* Slot lifecycle functions */
4646
struct active_request_slot *get_active_slot(void);

remote-curl.c

Lines changed: 13 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -717,25 +717,23 @@ static size_t rpc_out(void *ptr, size_t eltsize,
717717
return avail;
718718
}
719719

720-
static curlioerr rpc_ioctl(CURL *handle, int cmd, void *clientp)
720+
static int rpc_seek(void *clientp, curl_off_t offset, int origin)
721721
{
722722
struct rpc_state *rpc = clientp;
723723

724-
switch (cmd) {
725-
case CURLIOCMD_NOP:
726-
return CURLIOE_OK;
724+
if (origin != SEEK_SET)
725+
BUG("rpc_seek only handles SEEK_SET, not %d", origin);
727726

728-
case CURLIOCMD_RESTARTREAD:
729-
if (rpc->initial_buffer) {
730-
rpc->pos = 0;
731-
return CURLIOE_OK;
727+
if (rpc->initial_buffer) {
728+
if (offset < 0 || offset > rpc->len) {
729+
error("curl seek would be outside of rpc buffer");
730+
return CURL_SEEKFUNC_FAIL;
732731
}
733-
error(_("unable to rewind rpc post data - try increasing http.postBuffer"));
734-
return CURLIOE_FAILRESTART;
735-
736-
default:
737-
return CURLIOE_UNKNOWNCMD;
732+
rpc->pos = offset;
733+
return CURL_SEEKFUNC_OK;
738734
}
735+
error(_("unable to rewind rpc post data - try increasing http.postBuffer"));
736+
return CURL_SEEKFUNC_FAIL;
739737
}
740738

741739
struct check_pktline_state {
@@ -959,8 +957,8 @@ static int post_rpc(struct rpc_state *rpc, int stateless_connect, int flush_rece
959957
rpc->initial_buffer = 1;
960958
curl_easy_setopt(slot->curl, CURLOPT_READFUNCTION, rpc_out);
961959
curl_easy_setopt(slot->curl, CURLOPT_INFILE, rpc);
962-
curl_easy_setopt(slot->curl, CURLOPT_IOCTLFUNCTION, rpc_ioctl);
963-
curl_easy_setopt(slot->curl, CURLOPT_IOCTLDATA, rpc);
960+
curl_easy_setopt(slot->curl, CURLOPT_SEEKFUNCTION, rpc_seek);
961+
curl_easy_setopt(slot->curl, CURLOPT_SEEKDATA, rpc);
964962
if (options.verbosity > 1) {
965963
fprintf(stderr, "POST %s (chunked)\n", rpc->service_name);
966964
fflush(stderr);

0 commit comments

Comments
 (0)