tony2001 Sun Oct 23 14:31:40 2005 EDT
Modified files:
/php-src/ext/standard dns.c
Log:
fix #34938 (dns_get_record() doesn't resolve long hostnames and leaks)
http://cvs.php.net/diff.php/php-src/ext/standard/dns.c?r1=1.73&r2=1.74&ty=u
Index: php-src/ext/standard/dns.c
diff -u php-src/ext/standard/dns.c:1.73 php-src/ext/standard/dns.c:1.74
--- php-src/ext/standard/dns.c:1.73 Sun Oct 23 11:29:38 2005
+++ php-src/ext/standard/dns.c Sun Oct 23 14:31:36 2005
@@ -18,7 +18,7 @@
+----------------------------------------------------------------------+
*/
-/* $Id: dns.c,v 1.73 2005/10/23 15:29:38 iliaa Exp $ */
+/* $Id: dns.c,v 1.74 2005/10/23 18:31:36 tony2001 Exp $ */
/* {{{ includes */
#include "php.h"
@@ -357,9 +357,8 @@
#define QFIXEDSZ 4 /* fixed data in query <arpa/nameser.h> */
#endif /* QFIXEDSZ */
-#ifndef MAXHOSTNAMELEN
+#undef MAXHOSTNAMELEN
#define MAXHOSTNAMELEN 1024
-#endif /* MAXHOSTNAMELEN */
#ifndef MAXRESOURCERECORDS
#define MAXRESOURCERECORDS 64
@@ -370,10 +369,25 @@
u_char qb2[65536];
} querybuf;
+/* just a hack to free resources allocated by glibc in __res_nsend()
+ * See also:
+ * res_thread_freeres() in glibc/resolv/res_init.c
+ * __libc_res_nsend() in resolv/res_send.c
+ * */
+static void _php_dns_free_res(struct __res_state res) { /* {{{ */
+ int ns;
+ for (ns = 0; ns < MAXNS; ns++) {
+ if (res._u._ext.nsaddrs[ns] != NULL) {
+ free (res._u._ext.nsaddrs[ns]);
+ res._u._ext.nsaddrs[ns] = NULL;
+ }
+ }
+} /* }}} */
+
/* {{{ php_parserr */
static u_char *php_parserr(u_char *cp, querybuf *answer, int type_to_fetch,
int store, zval **subarray)
{
- u_short type, class, dlen;
+ u_short type, dlen;
u_long ttl;
long n, i;
u_short s;
@@ -383,14 +397,13 @@
*subarray = NULL;
- n = dn_expand(answer->qb2, answer->qb2+65536, cp, name, (sizeof(name))
- 2);
+ n = dn_expand(answer->qb2, answer->qb2+65536, cp, name, sizeof(name) -
2);
if (n < 0) {
return NULL;
}
cp += n;
GETSHORT(type, cp);
- GETSHORT(class, cp);
GETLONG(ttl, cp);
GETSHORT(dlen, cp);
if (type_to_fetch != T_ANY && type != type_to_fetch) {
@@ -650,7 +663,7 @@
HEADER *hp;
querybuf buf, answer;
u_char *cp = NULL, *end = NULL;
- long n, qd, an, ns = 0, ar = 0;
+ int n, qd, an, ns = 0, ar = 0;
int type, first_query = 1, store_results = 1;
switch (ZEND_NUM_ARGS()) {
@@ -747,6 +760,7 @@
break;
}
if (type_to_fetch) {
+ memset(&res, 0, sizeof(res));
res_ninit(&res);
res.retrans = 5;
res.options &= ~RES_DEFNAMES;
@@ -756,6 +770,7 @@
php_error_docref(NULL TSRMLS_CC, E_WARNING,
"res_nmkquery() failed");
zval_dtor(return_value);
res_nclose(&res);
+ _php_dns_free_res(res);
RETURN_FALSE;
}
n = res_nsend(&res, buf.qb2, n, answer.qb2, sizeof
answer);
@@ -763,6 +778,7 @@
php_error_docref(NULL TSRMLS_CC, E_WARNING,
"res_nsend() failed");
zval_dtor(return_value);
res_nclose(&res);
+ _php_dns_free_res(res);
RETURN_FALSE;
}
@@ -781,6 +797,7 @@
php_error_docref(NULL TSRMLS_CC,
E_WARNING, "Unable to parse DNS data received");
zval_dtor(return_value);
res_nclose(&res);
+ _php_dns_free_res(res);
RETURN_FALSE;
}
cp += n + QFIXEDSZ;
@@ -796,6 +813,7 @@
}
}
res_nclose(&res);
+ _php_dns_free_res(res);
}
}
--
PHP CVS Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php