Blame SOURCES/autofs-5.1.7-dont-use-realloc-in-host-exports-list-processing.patch

9a499a
autofs-5.1.7 - dont use realloc in host exports list processing
9a499a
9a499a
From: Ian Kent <raven@themaw.net>
9a499a
9a499a
If a server exports list is very large calling realloc(3) for each
9a499a
export is slow. It's better to traverse the exports list twice, once
9a499a
to calculate the length of the mapent then allocate the memory and
9a499a
traverse the exports list again to construct the mapent.
9a499a
9a499a
Signed-off-by: Ian Kent <raven@themaw.net>
9a499a
---
9a499a
 CHANGELOG              |    1 +
9a499a
 modules/lookup_hosts.c |   59 +++++++++++++++++++++---------------------------
9a499a
 2 files changed, 27 insertions(+), 33 deletions(-)
9a499a
9a499a
--- autofs-5.1.4.orig/CHANGELOG
9a499a
+++ autofs-5.1.4/CHANGELOG
9a499a
@@ -1,6 +1,7 @@
9a499a
 
9a499a
 - add xdr_exports().
9a499a
 - remove mount.x and rpcgen dependencies.
9a499a
+- dont use realloc in host exports list processing.
9a499a
 
9a499a
 xx/xx/2018 autofs-5.1.5
9a499a
 - fix flag file permission.
9a499a
--- autofs-5.1.4.orig/modules/lookup_hosts.c
9a499a
+++ autofs-5.1.4/modules/lookup_hosts.c
9a499a
@@ -89,44 +89,40 @@ static char *get_exports(struct autofs_p
9a499a
 	char buf[MAX_ERR_BUF];
9a499a
 	char *mapent;
9a499a
 	struct exportinfo *exp, *this;
9a499a
+	size_t hostlen = strlen(host);
9a499a
+	size_t mapent_len;
9a499a
 
9a499a
 	debug(ap->logopt, MODPREFIX "fetchng export list for %s", host);
9a499a
 
9a499a
 	exp = rpc_get_exports(host, 10, 0, RPC_CLOSE_NOLINGER);
9a499a
 
9a499a
-	mapent = NULL;
9a499a
 	this = exp;
9a499a
+	mapent_len = 0;
9a499a
 	while (this) {
9a499a
-		if (mapent) {
9a499a
-			int len = strlen(mapent) + 1;
9a499a
+		mapent_len += hostlen + 2*(strlen(this->dir) + 2) + 3;
9a499a
+		this = this->next;
9a499a
+	}
9a499a
 
9a499a
-			len += strlen(host) + 2*(strlen(this->dir) + 2) + 3;
9a499a
-			mapent = realloc(mapent, len);
9a499a
-			if (!mapent) {
9a499a
-				char *estr;
9a499a
-				estr = strerror_r(errno, buf, MAX_ERR_BUF);
9a499a
-				error(ap->logopt, MODPREFIX "malloc: %s", estr);
9a499a
-				rpc_exports_free(exp);
9a499a
-				return NULL;
9a499a
-			}
9a499a
-			strcat(mapent, " \"");
9a499a
-			strcat(mapent, this->dir);
9a499a
-			strcat(mapent, "\"");
9a499a
-		} else {
9a499a
-			int len = 2*(strlen(this->dir) + 2) + strlen(host) + 3;
9a499a
-
9a499a
-			mapent = malloc(len);
9a499a
-			if (!mapent) {
9a499a
-				char *estr;
9a499a
-				estr = strerror_r(errno, buf, MAX_ERR_BUF);
9a499a
-				error(ap->logopt, MODPREFIX "malloc: %s", estr);
9a499a
-				rpc_exports_free(exp);
9a499a
-				return NULL;
9a499a
-			}
9a499a
+	mapent = malloc(mapent_len + 1);
9a499a
+	if (!mapent) {
9a499a
+		char *estr;
9a499a
+		estr = strerror_r(errno, buf, MAX_ERR_BUF);
9a499a
+		error(ap->logopt, MODPREFIX "malloc: %s", estr);
9a499a
+		error(ap->logopt, MODPREFIX "exports lookup failed for %s", host);
9a499a
+		rpc_exports_free(exp);
9a499a
+		return NULL;
9a499a
+	}
9a499a
+	*mapent = 0;
9a499a
+
9a499a
+	this = exp;
9a499a
+	while (this) {
9a499a
+		if (!*mapent)
9a499a
 			strcpy(mapent, "\"");
9a499a
-			strcat(mapent, this->dir);
9a499a
-			strcat(mapent, "\"");
9a499a
-		}
9a499a
+		else
9a499a
+			strcat(mapent, " \"");
9a499a
+		strcat(mapent, this->dir);
9a499a
+		strcat(mapent, "\"");
9a499a
+
9a499a
 		strcat(mapent, " \"");
9a499a
 		strcat(mapent, host);
9a499a
 		strcat(mapent, ":");
9a499a
@@ -137,9 +133,6 @@ static char *get_exports(struct autofs_p
9a499a
 	}
9a499a
 	rpc_exports_free(exp);
9a499a
 
9a499a
-	if (!mapent)
9a499a
-		error(ap->logopt, MODPREFIX "exports lookup failed for %s", host);
9a499a
-
9a499a
 	return mapent;
9a499a
 }
9a499a