1
0
mirror of https://github.com/moparisthebest/curl synced 2024-12-22 08:08:50 -05:00

initial code added to support EPSV (IPv6-style PASV)

This commit is contained in:
Daniel Stenberg 2001-11-27 00:48:45 +00:00
parent 4382a80b9a
commit 6003f24f78

View File

@ -1258,6 +1258,23 @@ CURLcode ftp_use_pasv(struct connectdata *conn)
char *buf = data->state.buffer; /* this is our buffer */ char *buf = data->state.buffer; /* this is our buffer */
int ftpcode; /* receive FTP response codes in this */ int ftpcode; /* receive FTP response codes in this */
CURLcode result; CURLcode result;
Curl_addrinfo *addr=NULL;
Curl_ipconnect *conninfo;
/*
Here's the excecutive summary on what to do:
PASV is RFC959, expect:
227 Entering Passive Mode (a1,a2,a3,a4,p1,p2)
LPSV is RFC1639, expect:
228 Entering Long Passive Mode (4,4,a1,a2,a3,a4,2,p1,p2)
(Is this actually supported *anywhere*?)
EPSV is RFC2428, expect:
229 Entering Extended Passive Mode (|||port|)
*/
#if 0 #if 0
/* no support for IPv6 passive mode yet */ /* no support for IPv6 passive mode yet */
@ -1268,6 +1285,13 @@ CURLcode ftp_use_pasv(struct connectdata *conn)
int results[] = { 227, 0 }; int results[] = { 227, 0 };
#endif #endif
int modeoff; int modeoff;
unsigned short connectport; /* the local port connect() should use! */
unsigned short newport; /* remote port, not necessary the local one */
char *hostdataptr=NULL;
/* newhost must be able to hold a full IP-style address in ASCII, which
in the IPv6 case means 5*8-1 = 39 letters */
char newhost[48];
for (modeoff = 0; mode[modeoff]; modeoff++) { for (modeoff = 0; mode[modeoff]; modeoff++) {
FTPSENDF(conn, mode[modeoff], ""); FTPSENDF(conn, mode[modeoff], "");
@ -1283,16 +1307,9 @@ CURLcode ftp_use_pasv(struct connectdata *conn)
failf(data, "Odd return code after PASV"); failf(data, "Odd return code after PASV");
return CURLE_FTP_WEIRD_PASV_REPLY; return CURLE_FTP_WEIRD_PASV_REPLY;
} }
else if (strcmp(mode[modeoff], "PASV") == 0) { else if (227 == results[modeoff]) {
int ip[4]; int ip[4];
int port[2]; int port[2];
unsigned short newport; /* remote port, not necessary the local one */
unsigned short connectport; /* the local port connect() should use! */
char newhost[32];
Curl_addrinfo *addr;
char *hostdataptr=NULL;
Curl_ipconnect *conninfo;
char *str=buf; char *str=buf;
/* /*
@ -1321,6 +1338,42 @@ CURLcode ftp_use_pasv(struct connectdata *conn)
sprintf(newhost, "%d.%d.%d.%d", ip[0], ip[1], ip[2], ip[3]); sprintf(newhost, "%d.%d.%d.%d", ip[0], ip[1], ip[2], ip[3]);
newport = (port[0]<<8) + port[1]; newport = (port[0]<<8) + port[1];
/* we should compare to see if this is the same IP like the one
we're already connected to, as then we can skip the name function
call below, in similar style that we do for the EPSV reply */
}
#if 1
else if (strcmp(mode[modeoff], "EPSV") == 0) {
char *ptr = strchr(buf, '(');
if(ptr) {
unsigned int num;
char separator[4];
ptr++;
if(5 == sscanf(ptr, "%c%c%c%u%c",
&separator[0],
&separator[1],
&separator[2],
&num,
&separator[3])) {
/* the four separators should be identical */
newport = num;
/* we should use the same host we already are connected to */
addr = conn->hostaddr;
}
else
ptr=NULL;
}
if(!ptr) {
failf(data, "Weirdly formatted EPSV reply");
return CURLE_FTP_WEIRD_PASV_REPLY;
}
}
#endif
else
return CURLE_FTP_CANT_RECONNECT;
if(data->change.proxy) { if(data->change.proxy) {
/* /*
* This is a tunnel through a http proxy and we need to connect to the * This is a tunnel through a http proxy and we need to connect to the
@ -1331,7 +1384,7 @@ CURLcode ftp_use_pasv(struct connectdata *conn)
connectport = connectport =
(unsigned short)conn->port; /* we connect to the proxy's port */ (unsigned short)conn->port; /* we connect to the proxy's port */
} }
else { else if(!addr) {
/* normal, direct, ftp connection */ /* normal, direct, ftp connection */
addr = Curl_getaddrinfo(data, newhost, newport, &hostdataptr); addr = Curl_getaddrinfo(data, newhost, newport, &hostdataptr);
if(!addr) { if(!addr) {
@ -1365,9 +1418,6 @@ CURLcode ftp_use_pasv(struct connectdata *conn)
if(CURLE_OK != result) if(CURLE_OK != result)
return result; return result;
} }
}
else
return CURLE_FTP_CANT_RECONNECT;
return CURLE_OK; return CURLE_OK;
} }