summaryrefslogtreecommitdiff
path: root/www/w3m/patches/patch-ae
blob: 343fdb98693f66e57fc062bd408cb123ce089cda (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
$NetBSD: patch-ae,v 1.3 2000/08/16 00:31:34 itojun Exp $
Index: ftp.c
===================================================================
RCS file: /cvsroot/apps/w3m/ftp.c,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -1 -r1.1 -r1.2
--- ftp.c	2000/08/15 23:53:35	1.1
+++ ftp.c	2000/08/16 00:28:03	1.2
@@ -15,4 +15,5 @@
 
-#ifdef FTPPASS_HOSTNAMEGEN
 #include <sys/socket.h>
+
+#ifdef FTPPASS_HOSTNAMEGEN
 #include <netinet/in.h>
@@ -22,3 +23,8 @@
 
+#ifdef INET6
+#include <netdb.h>
+#endif
+
 typedef struct _FTP {
+    int family;
     FILE *rcontrol;
@@ -105,2 +111,8 @@
     Str tmp;
+#ifdef INET6
+    struct sockaddr_storage ss;
+#else
+    struct sockaddr ss;
+#endif
+    int sslen;
     FTP ftp = New(struct _FTP);
@@ -116,3 +128,7 @@
 	if (n > 0 && pass[n - 1] == '@') {
+#ifdef INET6
+	    struct sockaddr_storage sockname;
+#else
 	    struct sockaddr_in sockname;
+#endif
 	    int socknamelen = sizeof(sockname);
@@ -120,5 +136,19 @@
 	    if (!getsockname(fd, (struct sockaddr *) &sockname, &socknamelen)) {
+#ifdef INET6
+		char hbuf[NI_MAXHOST];
+#else
 		struct hostent *sockent;
+#endif
 		Str tmp2 = Strnew_charp(pass);
 
+#ifdef INET6
+		if (getnameinfo((struct sockaddr *)&sockname, socknamelen,
+		    hbuf, sizeof(hbuf), NULL, 0, NI_NAMEREQD) == 0) {
+		    Strcat_charp(tmp2, hbuf);
+		} else if (getnameinfo((struct sockaddr *)&sockname, socknamelen,
+			 hbuf, sizeof(hbuf), NULL, 0, 0) == 0) {
+		    Strcat_m_charp(tmp2, "[", hbuf, "]", NULL);
+		} else
+		    Strcat_charp(tmp2, "invalid");
+#else
 		if (sockent = gethostbyaddr((char *) &sockname.sin_addr,
@@ -129,2 +159,3 @@
 		    Strcat_m_charp(tmp2, "[", inet_ntoa(sockname.sin_addr), "]", NULL);
+#endif
 
@@ -135,2 +166,8 @@
 #endif
+    sslen = sizeof(ss);
+    if (getsockname(fd, (struct sockaddr *)&ss, &sslen) < 0) {
+	close(fd);
+	return -1;
+    }
+    ftp->family = ((struct sockaddr *)&ss)->sa_family;
     ftp->rcontrol = fdopen(fd, "rb");
@@ -176,3 +213,46 @@
 
+#ifdef INET6
 int
+ftp_epsv(FTP ftp)
+{
+    int port;
+    int data_s;
+    char *p;
+    Str tmp;
+    char hbuf[NI_MAXHOST];
+    struct sockaddr_storage ss;
+    int sslen;
+
+    sslen = sizeof(ss);
+    if (getpeername(fileno(ftp->wcontrol), (struct sockaddr *)&ss, &sslen) < 0)
+	return -1;
+    if (getnameinfo((struct sockaddr *)&ss, ((struct sockaddr *)&ss)->sa_len,
+	hbuf, sizeof(hbuf), NULL, 0, NI_NUMERICHOST) != 0) {
+	return -1;
+    }
+
+    fwrite("EPSV\r\n", 6, sizeof(char), ftp->wcontrol);
+    fflush(ftp->wcontrol);
+    tmp = read_response(ftp);
+    if (atoi(tmp->ptr) != 229)
+	return -1;
+    for (p = tmp->ptr + 4; *p && *p != '('; p++);	/*)*/
+    if (*p == '\0')
+	return -1;
+    p++;
+    /* find "|||port|" */
+    if (p[0] && p[0] == p[1] && p[0] == p[2])
+	p += 3;
+    else
+	return -1;
+    sscanf(p, "%d", &port);
+    data_s = openSocket(hbuf, "", port);
+    if (data_s < 0)
+	return -1;
+    ftp->data = fdopen(data_s, "rb");
+    return 0;
+}
+#endif
+
+int
 ftp_pasv(FTP ftp)
@@ -183,2 +263,9 @@
     Str tmp;
+
+#ifdef INET6
+    if (ftp->family == AF_INET6 || ftp->family == AF_INET) {
+	if (ftp_epsv(ftp) == 0)
+	    return 0;
+    }
+#endif