aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTobias Stoeckmann <tobias@stoeckmann.org>2023-12-15 10:14:11 +0100
committerDmitry V. Levin <ldv@strace.io>2023-12-19 12:22:59 +0000
commit2e375aad04d047e12468f93300ad7e42a8a03ff3 (patch)
tree29f31fa0bf4700476eccd4a307ef6638d9707851
parentc2fafe1be0fb72aa1bd521efe2f524074bf143c7 (diff)
downloadpam-2e375aad04d047e12468f93300ad7e42a8a03ff3.tar.gz
pam-2e375aad04d047e12468f93300ad7e42a8a03ff3.tar.bz2
pam-2e375aad04d047e12468f93300ad7e42a8a03ff3.zip
treewide: use asprintf to construct strings
The asprintf function is considered as given for current code already. Use it instead of calling malloc + strcpy + strcat manually. Reported-by: Benny Baumann <BenBE@geshi.org> Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org>
-rw-r--r--conf/pam_conv1/pam_conv_y.y15
-rw-r--r--modules/pam_faillock/faillock.c16
-rw-r--r--modules/pam_filter/pam_filter.c64
-rw-r--r--modules/pam_issue/pam_issue.c15
-rw-r--r--modules/pam_namespace/pam_namespace.c26
-rw-r--r--modules/pam_unix/md5_crypt.c20
-rw-r--r--modules/pam_unix/support.c7
-rw-r--r--modules/pam_xauth/pam_xauth.c45
8 files changed, 66 insertions, 142 deletions
diff --git a/conf/pam_conv1/pam_conv_y.y b/conf/pam_conv1/pam_conv_y.y
index 72a5dab3..e2cf85c3 100644
--- a/conf/pam_conv1/pam_conv_y.y
+++ b/conf/pam_conv1/pam_conv_y.y
@@ -78,8 +78,10 @@ line
/* $1 = service-name */
yyerror("Appending to " PAM_D "/%s", $1);
- filename = malloc(strlen($1) + sizeof(PAM_D) + 6);
- sprintf(filename, PAM_D_FILE_FMT, $1);
+ if (asprintf(&filename, PAM_D_FILE_FMT, $1) < 0) {
+ yyerror("unable to create filename - aborting");
+ exit(1);
+ }
conf = fopen(filename, "r");
if (conf == NULL) {
/* new file */
@@ -140,12 +142,11 @@ tokenls
$$=NULL;
}
| tokenls tok {
- int len;
-
if ($1) {
- len = strlen($1) + strlen($2) + 2;
- $$ = malloc(len);
- sprintf($$,"%s %s",$1,$2);
+ if (asprintf(&$$, "%s %s", $1, $2) < 0) {
+ yyerror("failed to assemble tokenls");
+ exit(1);
+ }
free($1);
free($2);
} else {
diff --git a/modules/pam_faillock/faillock.c b/modules/pam_faillock/faillock.c
index 091f253a..1d2057e7 100644
--- a/modules/pam_faillock/faillock.c
+++ b/modules/pam_faillock/faillock.c
@@ -36,6 +36,7 @@
#include "config.h"
#include <string.h>
+#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
@@ -55,23 +56,20 @@ open_tally (const char *dir, const char *user, uid_t uid, int create)
{
char *path;
int flags = O_RDWR;
- int fd;
+ int fd, r;
if (dir == NULL || strstr(user, "../") != NULL)
/* just a defensive programming as the user must be a
* valid user on the system anyway
*/
return -1;
- path = malloc(strlen(dir) + strlen(user) + 2);
- if (path == NULL)
+ if (*dir && dir[strlen(dir) - 1] != '/')
+ r = asprintf(&path, "%s/%s", dir, user);
+ else
+ r = asprintf(&path, "%s%s", dir, user);
+ if (r < 0)
return -1;
- strcpy(path, dir);
- if (*dir && dir[strlen(dir) - 1] != '/') {
- strcat(path, "/");
- }
- strcat(path, user);
-
if (create) {
flags |= O_CREAT;
if (access(dir, F_OK) != 0) {
diff --git a/modules/pam_filter/pam_filter.c b/modules/pam_filter/pam_filter.c
index 72c3b480..4e614498 100644
--- a/modules/pam_filter/pam_filter.c
+++ b/modules/pam_filter/pam_filter.c
@@ -138,82 +138,46 @@ static int process_args(pam_handle_t *pamh
/* the "SERVICE" variable */
-#define SERVICE_NAME "SERVICE="
-#define SERVICE_OFFSET (sizeof(SERVICE_NAME) - 1)
-
retval = pam_get_item(pamh, PAM_SERVICE, &tmp);
if (retval != PAM_SUCCESS || tmp == NULL) {
pam_syslog(pamh, LOG_CRIT, "service name not found");
- if (levp) {
- free(levp[0]);
- free(levp);
- }
+ free(levp[0]);
+ free(levp);
return -1;
}
- size = SERVICE_OFFSET+strlen(tmp);
- levp[1] = malloc(size+1);
- if (levp[1] == NULL) {
+ if (asprintf(&levp[1], "SERVICE=%s", (const char *) tmp) < 0) {
pam_syslog(pamh, LOG_CRIT, "no memory for service name");
- if (levp) {
- free(levp[0]);
- free(levp);
- }
+ free(levp[0]);
+ free(levp);
return -1;
}
- strcpy(levp[1], SERVICE_NAME);
- strcpy(levp[1]+SERVICE_OFFSET, tmp);
- levp[1][size] = '\0'; /* <NUL> terminate */
-
/* the "USER" variable */
-#define USER_NAME "USER="
-#define USER_OFFSET (sizeof(USER_NAME) - 1)
-
if (pam_get_user(pamh, &user, NULL) != PAM_SUCCESS) {
user = "<unknown>";
}
- size = USER_OFFSET+strlen(user);
- levp[2] = malloc(size+1);
- if (levp[2] == NULL) {
+ if (asprintf(&levp[2], "USER=%s", user) < 0) {
pam_syslog(pamh, LOG_CRIT, "no memory for user's name");
- if (levp) {
- free(levp[1]);
- free(levp[0]);
- free(levp);
- }
+ free(levp[1]);
+ free(levp[0]);
+ free(levp);
return -1;
}
- strcpy(levp[2], USER_NAME);
- strcpy(levp[2]+USER_OFFSET, user);
- levp[2][size] = '\0'; /* <NUL> terminate */
-
/* the "USER" variable */
-#define TYPE_NAME "TYPE="
-#define TYPE_OFFSET (sizeof(TYPE_NAME) - 1)
-
- size = TYPE_OFFSET+strlen(type);
-
- levp[3] = malloc(size+1);
- if (levp[3] == NULL) {
+ if (asprintf(&levp[3], "TYPE=%s", type) < 0) {
pam_syslog(pamh, LOG_CRIT, "no memory for type");
- if (levp) {
- free(levp[2]);
- free(levp[1]);
- free(levp[0]);
- free(levp);
- }
+ free(levp[2]);
+ free(levp[1]);
+ free(levp[0]);
+ free(levp);
return -1;
}
- strcpy(levp[3], TYPE_NAME);
- strcpy(levp[3]+TYPE_OFFSET, type);
- levp[3][size] = '\0'; /* <NUL> terminate */
-
levp[4] = NULL; /* end list */
*evp = levp;
diff --git a/modules/pam_issue/pam_issue.c b/modules/pam_issue/pam_issue.c
index c08f90c3..aade642e 100644
--- a/modules/pam_issue/pam_issue.c
+++ b/modules/pam_issue/pam_issue.c
@@ -240,7 +240,6 @@ pam_sm_authenticate(pam_handle_t *pamh, int flags UNUSED,
const char *issue_file = NULL;
int parse_esc = 1;
const void *item = NULL;
- const char *cur_prompt;
char *issue_prompt = NULL;
/* If we've already set the prompt, don't set it again */
@@ -277,10 +276,6 @@ pam_sm_authenticate(pam_handle_t *pamh, int flags UNUSED,
return retval;
}
- cur_prompt = item;
- if (cur_prompt == NULL)
- cur_prompt = "";
-
if (parse_esc)
retval = read_issue_quoted(pamh, fp, &issue_prompt);
else
@@ -291,11 +286,10 @@ pam_sm_authenticate(pam_handle_t *pamh, int flags UNUSED,
if (retval != PAM_SUCCESS)
goto out;
- {
- size_t size = strlen(issue_prompt) + strlen(cur_prompt) + 1;
- char *new_prompt = realloc(issue_prompt, size);
-
- if (new_prompt == NULL) {
+ if (item != NULL) {
+ const char *cur_prompt = item;
+ char *new_prompt;
+ if (asprintf(&new_prompt, "%s%s", issue_prompt, cur_prompt) < 0) {
pam_syslog(pamh, LOG_CRIT, "out of memory");
retval = PAM_BUF_ERR;
goto out;
@@ -303,7 +297,6 @@ pam_sm_authenticate(pam_handle_t *pamh, int flags UNUSED,
issue_prompt = new_prompt;
}
- strcat(issue_prompt, cur_prompt);
retval = pam_set_item(pamh, PAM_USER_PROMPT,
(const void *) issue_prompt);
out:
diff --git a/modules/pam_namespace/pam_namespace.c b/modules/pam_namespace/pam_namespace.c
index d78111b3..1c42b0f4 100644
--- a/modules/pam_namespace/pam_namespace.c
+++ b/modules/pam_namespace/pam_namespace.c
@@ -592,26 +592,20 @@ static int process_line(char *line, const char *home, const char *rhome,
* Populate polyinstantiated directory structure with appropriate
* pathnames and the method with which to polyinstantiate.
*/
- if (strlen(dir) >= sizeof(poly->dir)
- || strlen(rdir) >= sizeof(poly->rdir)
- || strlen(instance_prefix) >= sizeof(poly->instance_prefix)) {
- pam_syslog(idata->pamh, LOG_NOTICE, "Pathnames too long");
- goto skipping;
- }
- strcpy(poly->dir, dir);
- strcpy(poly->rdir, rdir);
- strcpy(poly->instance_prefix, instance_prefix);
-
if (parse_method(method, poly, idata) != 0) {
goto skipping;
}
- if (poly->method == TMPDIR) {
- if (sizeof(poly->instance_prefix) - strlen(poly->instance_prefix) < 7) {
- pam_syslog(idata->pamh, LOG_NOTICE, "Pathnames too long");
- goto skipping;
- }
- strcat(poly->instance_prefix, "XXXXXX");
+#define COPY_STR(dst, src, apd) \
+ (snprintf((dst), sizeof(dst), "%s%s", (src), (apd)) != \
+ (ssize_t) (strlen(src) + strlen(apd)))
+
+ if (COPY_STR(poly->dir, dir, "")
+ || COPY_STR(poly->rdir, rdir, "")
+ || COPY_STR(poly->instance_prefix, instance_prefix,
+ poly->method == TMPDIR ? "XXXXXX" : "")) {
+ pam_syslog(idata->pamh, LOG_NOTICE, "Pathnames too long");
+ goto skipping;
}
/*
diff --git a/modules/pam_unix/md5_crypt.c b/modules/pam_unix/md5_crypt.c
index c3e77c9d..a5720999 100644
--- a/modules/pam_unix/md5_crypt.c
+++ b/modules/pam_unix/md5_crypt.c
@@ -13,6 +13,7 @@
*/
#include <string.h>
+#include <stdio.h>
#include <stdlib.h>
#include "md5.h"
#include "pam_inline.h"
@@ -41,6 +42,7 @@ char *MD5Name(crypt_md5)(const char *pw, const char *salt)
* it this way, we can get better later on */
char *passwd, *p;
const char *sp, *ep;
+ char buf[23];
unsigned char final[16];
int sl, pl, i, j;
MD5_CTX ctx, ctx1;
@@ -49,12 +51,6 @@ char *MD5Name(crypt_md5)(const char *pw, const char *salt)
/* Refine the Salt first */
sp = salt;
- /* TODO: now that we're using malloc'ed memory, get rid of the
- strange constant buffer size. */
- passwd = malloc(120);
- if (passwd == NULL)
- return NULL;
-
/* If it starts with the magic string, then skip that */
if ((ep = pam_str_skip_prefix_len(sp, magic, strlen(magic))) != NULL)
sp = ep;
@@ -96,11 +92,6 @@ char *MD5Name(crypt_md5)(const char *pw, const char *salt)
else
MD5Name(MD5Update)(&ctx, (unsigned const char *)pw+j, 1);
- /* Now make the output string */
- strcpy(passwd, magic);
- strncat(passwd, sp, sl);
- strcat(passwd, "$");
-
MD5Name(MD5Final)(final,&ctx);
/*
@@ -128,7 +119,7 @@ char *MD5Name(crypt_md5)(const char *pw, const char *salt)
MD5Name(MD5Final)(final,&ctx1);
}
- p = passwd + strlen(passwd);
+ p = buf;
l = (final[0] << 16) | (final[6] << 8) | final[12];
to64(p, l, 4);
@@ -150,7 +141,12 @@ char *MD5Name(crypt_md5)(const char *pw, const char *salt)
p += 2;
*p = '\0';
+ /* Now make the output string */
+ if (asprintf(&passwd, "%s%.*s$%s", magic, sl, sp, buf) < 0)
+ passwd = NULL;
+
/* Don't leave anything around in vm they could use. */
+ pam_overwrite_array(buf);
pam_overwrite_array(final);
return passwd;
diff --git a/modules/pam_unix/support.c b/modules/pam_unix/support.c
index 9d8cac7d..49807873 100644
--- a/modules/pam_unix/support.c
+++ b/modules/pam_unix/support.c
@@ -722,12 +722,9 @@ int _unix_verify_password(pam_handle_t * pamh, const char *name
retval = get_pwd_hash(pamh, name, &pwd, &salt);
- data_name = malloc(sizeof(FAIL_PREFIX) + strlen(name));
- if (data_name == NULL) {
+ if (asprintf(&data_name, "%s%s", FAIL_PREFIX, name) < 0) {
pam_syslog(pamh, LOG_CRIT, "no memory for data-name");
- } else {
- strcpy(data_name, FAIL_PREFIX);
- strcpy(data_name + sizeof(FAIL_PREFIX) - 1, name);
+ data_name = NULL;
}
if (p != NULL && strlen(p) > PAM_MAX_RESP_SIZE) {
diff --git a/modules/pam_xauth/pam_xauth.c b/modules/pam_xauth/pam_xauth.c
index ed86130e..20ae3e6b 100644
--- a/modules/pam_xauth/pam_xauth.c
+++ b/modules/pam_xauth/pam_xauth.c
@@ -505,16 +505,9 @@ pam_sm_open_session (pam_handle_t *pamh, int flags UNUSED,
retval = PAM_SESSION_ERR;
goto cleanup;
}
- } else {
- cookiefile = malloc(strlen(rpwd->pw_dir) + 1 +
- strlen(XAUTHDEF) + 1);
- if (cookiefile == NULL) {
- retval = PAM_SESSION_ERR;
- goto cleanup;
- }
- strcpy(cookiefile, rpwd->pw_dir);
- strcat(cookiefile, "/");
- strcat(cookiefile, XAUTHDEF);
+ } else if (asprintf(&cookiefile, "%s/%s", rpwd->pw_dir, XAUTHDEF) < 0) {
+ retval = PAM_SESSION_ERR;
+ goto cleanup;
}
if (debug) {
pam_syslog(pamh, LOG_DEBUG, "reading keys from `%s'",
@@ -544,29 +537,18 @@ pam_sm_open_session (pam_handle_t *pamh, int flags UNUSED,
if (((cookie == NULL) || (strlen(cookie) == 0)) &&
(pam_str_skip_prefix(display, "localhost:") != NULL ||
pam_str_skip_prefix(display, "localhost/unix:") != NULL)) {
- char *t, *screen;
- size_t tlen, slen;
+ char hostname[HOST_NAME_MAX + 1];
/* Free the useless cookie string. */
free(cookie);
cookie = NULL;
- /* Allocate enough space to hold an adjusted name. */
- tlen = strlen(display) + LINE_MAX + 1;
- t = calloc(1, tlen);
- if (t != NULL) {
- if (gethostname(t, tlen - 1) != -1) {
- /* Append the protocol and then the
- * screen number. */
- if (strlen(t) < tlen - 6) {
- strcat(t, "/unix:");
- }
- screen = strchr(display, ':');
- if (screen != NULL) {
- screen++;
- slen = strlen(screen);
- if (strlen(t) + slen < tlen) {
- strcat(t, screen);
- }
- }
+ if (gethostname(hostname, sizeof(hostname)) != -1) {
+ const char *screen;
+ char *t;
+
+ /* Append protocol and screen number to host. */
+ screen = display + strcspn(display, ":");
+ if (asprintf(&t, "%s/unix%s",
+ hostname, screen) >= 0) {
if (debug) {
pam_syslog(pamh, LOG_DEBUG,
"no key for `%s', "
@@ -592,9 +574,8 @@ pam_sm_open_session (pam_handle_t *pamh, int flags UNUSED,
xauth, (const char *[]) {
xauth, "-f", cookiefile,
"nlist", t, NULL});
+ free(t);
}
- free(t);
- t = NULL;
}
}