aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDmitry V. Levin <ldv@strace.io>2023-12-24 08:00:00 +0000
committerDmitry V. Levin <ldv@strace.io>2023-12-24 08:00:00 +0000
commitc12a2d00cc560ebdacc53bcedb6ee882baba5b1f (patch)
tree8c2c5bef541db9109b7ff0e2b99d2a3905d3c8fa
parentbb5d0f69c7a29380f9fd05ac9c379c128bccdeca (diff)
downloadpam-c12a2d00cc560ebdacc53bcedb6ee882baba5b1f.tar.gz
pam-c12a2d00cc560ebdacc53bcedb6ee882baba5b1f.tar.bz2
pam-c12a2d00cc560ebdacc53bcedb6ee882baba5b1f.zip
pam_timestamp_check: fix potential null pointer dereferences on error path
* modules/pam_timestamp/pam_timestamp.c [PAM_TIMESTAMP_MAIN] (main): Bail out early in case of initialization errors to avoid potential null pointer dereferences in -d mode.
-rw-r--r--modules/pam_timestamp/pam_timestamp.c53
1 files changed, 24 insertions, 29 deletions
diff --git a/modules/pam_timestamp/pam_timestamp.c b/modules/pam_timestamp/pam_timestamp.c
index 644dfb49..1d624b40 100644
--- a/modules/pam_timestamp/pam_timestamp.c
+++ b/modules/pam_timestamp/pam_timestamp.c
@@ -752,7 +752,7 @@ pam_sm_close_session(pam_handle_t *pamh UNUSED, int flags UNUSED, int argc UNUSE
int
main(int argc, char **argv)
{
- int i, retval = 0, dflag = 0, kflag = 0;
+ int i, retval, dflag = 0, kflag = 0;
const char *target_user = NULL, *user = NULL, *tty = NULL;
struct passwd *pwd;
struct timeval tv;
@@ -797,7 +797,7 @@ main(int argc, char **argv)
if (geteuid() != 0) {
fprintf(stderr, "%s must be setuid root\n",
argv[0]);
- retval = 2;
+ return 2;
}
/* Check that we have a controlling tty. */
@@ -825,43 +825,39 @@ main(int argc, char **argv)
/* Get the name of the target user. */
user = strdup(pwd->pw_name);
if (user == NULL) {
- retval = 4;
- } else {
- target_user = (optind < argc) ? argv[optind] : user;
- if ((strchr(target_user, '.') != NULL) ||
- (strchr(target_user, '/') != NULL) ||
- (strchr(target_user, '%') != NULL)) {
- fprintf(stderr, "unknown user: %s\n",
- target_user);
- retval = 4;
- }
+ fprintf(stderr, "out of memory\n");
+ return 4;
+ }
+ target_user = (optind < argc) ? argv[optind] : user;
+ if ((strchr(target_user, '.') != NULL) ||
+ (strchr(target_user, '/') != NULL) ||
+ (strchr(target_user, '%') != NULL)) {
+ fprintf(stderr, "invalid user: %s\n", target_user);
+ return 4;
}
/* Sanity check the tty to make sure we should be checking
* for timestamps which pertain to it. */
- if (retval == 0) {
- tty = check_tty(tty);
- if (tty == NULL) {
- fprintf(stderr, "invalid tty\n");
- retval = 6;
- }
+ tty = check_tty(tty);
+ if (tty == NULL) {
+ fprintf(stderr, "invalid tty\n");
+ return 6;
}
+ /* Generate the name of the timestamp file. */
+ format_timestamp_name(path, sizeof(path), TIMESTAMPDIR,
+ tty, user, target_user);
+
do {
- /* Sanity check the timestamp directory itself. */
- if (retval == 0) {
+ retval = 0;
+ do {
+ /* Sanity check the timestamp directory itself. */
if (check_dir_perms(NULL, TIMESTAMPDIR) != PAM_SUCCESS) {
retval = 5;
+ break;
}
- }
- if (retval == 0) {
- /* Generate the name of the timestamp file. */
- format_timestamp_name(path, sizeof(path), TIMESTAMPDIR,
- tty, user, target_user);
- }
- if (retval == 0) {
if (kflag) {
/* Remove the timestamp. */
if (lstat(path, &st) != -1) {
@@ -885,7 +881,7 @@ main(int argc, char **argv)
retval = 7;
}
}
- }
+ } while (0);
if (dflag > 0) {
struct timeval now;
@@ -905,7 +901,6 @@ main(int argc, char **argv)
select(STDOUT_FILENO + 1,
NULL, NULL, &write_fds,
&tv);
- retval = 0;
}
} while (dflag > 0);