From ebe1da11c890f022a3e254d9f5f4cdec284a368e Mon Sep 17 00:00:00 2001 From: "j.ps@openmailbox.org" Date: Tue, 21 Jul 2015 10:54:05 +0100 Subject: "ss -p" segfaults Patch for 4.1.1. Essentially all that is needed to get rid of this issue is the addition of: memset(u, 0, sizeof(*u)); after: if (!(u = malloc(sizeof(*u)))) break; Also patched some other situations (strcpy and sprintf uses) that potentially produce the same results. Signed-off-by: Jose P Santos [ wt: made Jose's patch slightly simpler, all credits to him for the diag ] Signed-off-by: Willy Tarreau --- misc/ss.c | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/misc/ss.c b/misc/ss.c index 748e693..6ce68ca 100644 --- a/misc/ss.c +++ b/misc/ss.c @@ -456,7 +456,9 @@ static void user_ent_hash_build(void) user_ent_hash_build_init = 1; - strcpy(name, root); + strncpy(name, root, sizeof(name)-1); + name[sizeof(name)-1] = 0; + if (strlen(name) == 0 || name[strlen(name)-1] != '/') strcat(name, "/"); @@ -480,7 +482,7 @@ static void user_ent_hash_build(void) if (getpidcon(pid, &pid_context) != 0) pid_context = strdup(no_ctx); - sprintf(name + nameoff, "%d/fd/", pid); + snprintf(name + nameoff, sizeof(name) - nameoff, "%d/fd/", pid); pos = strlen(name); if ((dir1 = opendir(name)) == NULL) continue; @@ -499,7 +501,7 @@ static void user_ent_hash_build(void) if (sscanf(d1->d_name, "%d%c", &fd, &crap) != 1) continue; - sprintf(name+pos, "%d", fd); + snprintf(name+pos, sizeof(name) - pos, "%d", fd); link_len = readlink(name, lnk, sizeof(lnk)-1); if (link_len == -1) @@ -2719,7 +2721,7 @@ static int unix_show(struct filter *f) struct sockstat *u, **insp; int flags; - if (!(u = malloc(sizeof(*u)))) + if (!(u = calloc(1, sizeof(*u)))) break; if (sscanf(buf, "%x: %x %x %x %x %x %d %s", @@ -3064,11 +3066,13 @@ static int netlink_show_one(struct filter *f, strncpy(procname, "kernel", 6); } else if (pid > 0) { FILE *fp; - sprintf(procname, "%s/%d/stat", + snprintf(procname, sizeof(procname), "%s/%d/stat", getenv("PROC_ROOT") ? : "/proc", pid); if ((fp = fopen(procname, "r")) != NULL) { if (fscanf(fp, "%*d (%[^)])", procname) == 1) { - sprintf(procname+strlen(procname), "/%d", pid); + snprintf(procname+strlen(procname), + sizeof(procname)-strlen(procname), + "/%d", pid); done = 1; } fclose(fp); -- 1.7.12.1