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

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