Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 19 Nov 2015 13:36:53 +0000 (UTC)
From:      Marcelo Araujo <araujo@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r291073 - head/lib/libc/yp
Message-ID:  <201511191336.tAJDarqb056295@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: araujo
Date: Thu Nov 19 13:36:53 2015
New Revision: 291073
URL: https://svnweb.freebsd.org/changeset/base/291073

Log:
  If a NIS server has long entries on its database that is bigger than
  1024 specified on YPMAXRECORD the ypmatch can get in an infinite retry
  loop when is requesting the information from the NIS server.
  
  The ypmatch(1) will return an error until the command receives an
  kill(1).
  
  To avoid this problem, we check the MAX_RETRIES that is by default set
  to 20 and avoid get in infinet loop at the client side.
  
  NOTE: FreeBSD nis(8) server doesn't present this issue.
  
  Submitted by:	Ravi Pokala <rpokala@panasas.com>,
  		Lakshmi N. Sundararajan <lakshmi.n@msystechnologies.com>,
  		Lewis, Fred <flewis@panasas.com>,
  		Pushkar Kothavade <pushkar.kothavade@msystechnologies.com>
  Approved by:	bapt (mentor)
  MFC after:	1 month
  Differential Revision:	D4095

Modified:
  head/lib/libc/yp/yplib.c

Modified: head/lib/libc/yp/yplib.c
==============================================================================
--- head/lib/libc/yp/yplib.c	Thu Nov 19 12:55:43 2015	(r291072)
+++ head/lib/libc/yp/yplib.c	Thu Nov 19 13:36:53 2015	(r291073)
@@ -655,7 +655,7 @@ yp_match(char *indomain, char *inmap, co
 	struct timeval tv;
 	struct ypreq_key yprk;
 	int r;
-
+	int retries = 0;
 	*outval = NULL;
 	*outvallen = 0;
 
@@ -700,6 +700,11 @@ yp_match(char *indomain, char *inmap, co
 #endif
 
 again:
+	if (retries > MAX_RETRIES) {
+		YPUNLOCK();
+		return (YPERR_RPC);
+	}
+
 	if (_yp_dobind(indomain, &ysd) != 0) {
 		YPUNLOCK();
 		return (YPERR_DOMAIN);
@@ -716,6 +721,7 @@ again:
 	if (r != RPC_SUCCESS) {
 		clnt_perror(ysd->dom_client, "yp_match: clnt_call");
 		_yp_unbind(ysd);
+		retries++;
 		goto again;
 	}
 
@@ -772,7 +778,7 @@ yp_first(char *indomain, char *inmap, ch
 	struct dom_binding *ysd;
 	struct timeval tv;
 	int r;
-
+	int retries = 0;
 	/* Sanity check */
 
 	if (indomain == NULL || !strlen(indomain) ||
@@ -784,6 +790,11 @@ yp_first(char *indomain, char *inmap, ch
 
 	YPLOCK();
 again:
+	if (retries > MAX_RETRIES) {
+		YPUNLOCK();
+		return (YPERR_RPC);
+	}
+
 	if (_yp_dobind(indomain, &ysd) != 0) {
 		YPUNLOCK();
 		return (YPERR_DOMAIN);
@@ -802,6 +813,7 @@ again:
 	if (r != RPC_SUCCESS) {
 		clnt_perror(ysd->dom_client, "yp_first: clnt_call");
 		_yp_unbind(ysd);
+		retries++;
 		goto again;
 	}
 	if (!(r = ypprot_err(yprkv.stat))) {
@@ -844,7 +856,7 @@ yp_next(char *indomain, char *inmap, cha
 	struct dom_binding *ysd;
 	struct timeval tv;
 	int r;
-
+	int retries = 0;
 	/* Sanity check */
 
 	if (inkey == NULL || !strlen(inkey) || inkeylen <= 0 ||
@@ -857,6 +869,11 @@ yp_next(char *indomain, char *inmap, cha
 
 	YPLOCK();
 again:
+	if (retries > MAX_RETRIES) {
+		YPUNLOCK();
+		return (YPERR_RPC);
+	}
+
 	if (_yp_dobind(indomain, &ysd) != 0) {
 		YPUNLOCK();
 		return (YPERR_DOMAIN);
@@ -877,6 +894,7 @@ again:
 	if (r != RPC_SUCCESS) {
 		clnt_perror(ysd->dom_client, "yp_next: clnt_call");
 		_yp_unbind(ysd);
+		retries++;
 		goto again;
 	}
 	if (!(r = ypprot_err(yprkv.stat))) {
@@ -920,7 +938,7 @@ yp_all(char *indomain, char *inmap, stru
 	CLIENT *clnt;
 	u_long status, savstat;
 	int clnt_sock;
-
+	int retries = 0;
 	/* Sanity check */
 
 	if (indomain == NULL || !strlen(indomain) ||
@@ -929,6 +947,10 @@ yp_all(char *indomain, char *inmap, stru
 
 	YPLOCK();
 again:
+	if (retries > MAX_RETRIES) {
+		YPUNLOCK();
+		return (YPERR_RPC);
+	}
 
 	if (_yp_dobind(indomain, &ysd) != 0) {
 		YPUNLOCK();
@@ -958,9 +980,10 @@ again:
 	if (clnt_call(clnt, YPPROC_ALL,
 		(xdrproc_t)xdr_ypreq_nokey, &yprnk,
 		(xdrproc_t)xdr_ypresp_all_seq, &status, tv) != RPC_SUCCESS) {
-			clnt_perror(ysd->dom_client, "yp_all: clnt_call");
+			clnt_perror(clnt, "yp_all: clnt_call");
 			clnt_destroy(clnt);
 			_yp_unbind(ysd);
+			retries++;
 			goto again;
 	}
 



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201511191336.tAJDarqb056295>