Skip to content

Commit d66e62a

Browse files
Cherry pick of PR sonic-net#9123
Don't send sshd created bad password to AAA
1 parent c87ec48 commit d66e62a

File tree

2 files changed

+134
-0
lines changed

2 files changed

+134
-0
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,133 @@
1+
From f2687e7a442c83e19190695021fb9a60fe07ba60 Mon Sep 17 00:00:00 2001
2+
From: Renuka Manavalan <[email protected]>
3+
Date: Wed, 17 Nov 2021 02:31:45 +0000
4+
Subject: [PATCH] handle bad password set by sshd
5+
6+
---
7+
pam_tacplus.c | 11 +++++++++--
8+
support.c | 37 +++++++++++++++++++++++++++++++++++++
9+
support.h | 1 +
10+
tacc.c | 4 ++--
11+
4 files changed, 49 insertions(+), 4 deletions(-)
12+
13+
diff --git a/pam_tacplus.c b/pam_tacplus.c
14+
index ec8ea27..014421b 100644
15+
--- a/pam_tacplus.c
16+
+++ b/pam_tacplus.c
17+
@@ -251,6 +251,13 @@ int pam_sm_authenticate (pam_handle_t * pamh, int flags,
18+
return PAM_CRED_INSUFFICIENT;
19+
}
20+
21+
+ if (validate_not_sshd_bad_pass(pass) != PAM_SUCCESS) {
22+
+ syslog(LOG_ERR, "auth fail: Password incorrect");
23+
+ memset(pass, 0, strlen (pass));
24+
+ free(pass);
25+
+ return PAM_AUTH_ERR;
26+
+ }
27+
+
28+
retval = pam_set_item (pamh, PAM_AUTHTOK, pass);
29+
if (retval != PAM_SUCCESS) {
30+
_pam_log(LOG_ERR, "unable to set password");
31+
@@ -483,7 +490,7 @@ int pam_sm_authenticate (pam_handle_t * pamh, int flags,
32+
syslog(LOG_DEBUG, "%s: exit with pam status: %d", __FUNCTION__, status);
33+
34+
if (NULL != pass) {
35+
- bzero(pass, strlen (pass));
36+
+ memset(pass, 0, strlen (pass));
37+
free(pass);
38+
pass = NULL;
39+
}
40+
@@ -979,7 +986,7 @@ finish:
41+
syslog(LOG_DEBUG, "%s: exit with pam status: %d", __FUNCTION__, status);
42+
43+
if (NULL != pass) {
44+
- bzero(pass, strlen(pass));
45+
+ memset(pass, 0, strlen (pass));
46+
free(pass);
47+
pass = NULL;
48+
}
49+
diff --git a/support.c b/support.c
50+
index 3e55e2f..09d09bf 100644
51+
--- a/support.c
52+
+++ b/support.c
53+
@@ -108,6 +108,43 @@ int converse(pam_handle_t * pamh, int nargs, const struct pam_message *message,
54+
return retval;
55+
}
56+
57+
+/*
58+
+ * Ref: From <https://groups.google.com/g/mailing.unix.openssh-dev/c/ViHvtciKYh0>
59+
+ * For future archive searchers:
60+
+ * > Why does OpenSSH replaces the password entered by the user with the
61+
+ * > bad password - "\b\n\r\177INCORRECT
62+
+ *
63+
+ * There are some situations where sshd determines a user can't log in.
64+
+ * Typical samples of that are DenyUsers or PermitRootLogin.
65+
+ * In those cases sshd *still* calls PAM, so that delays set by it are
66+
+ * still performed to the user (without leaking info about accounts
67+
+ * existing, disabled, etc.). But in order to ensure it can't succeed,
68+
+ * replaces the password with that impossible one.
69+
+ *
70+
+ */
71+
+int validate_not_sshd_bad_pass(const char *pass)
72+
+{
73+
+ const char *SSHD_BAD_PASS = "\010\012\015\177INCORRECT";
74+
+ const int SSHD_BAD_PASS_LEN = strlen(SSHD_BAD_PASS);
75+
+
76+
+ int len = strlen(pass);
77+
+ const char *p = pass;
78+
+
79+
+ if (len == 0)
80+
+ return PAM_SUCCESS;
81+
+
82+
+ while (len > 0) {
83+
+ int l = len < SSHD_BAD_PASS_LEN ? len : SSHD_BAD_PASS_LEN;
84+
+
85+
+ if (strncmp(p, SSHD_BAD_PASS, l) != 0)
86+
+ return PAM_SUCCESS;
87+
+
88+
+ len -= l;
89+
+ p += l;
90+
+ }
91+
+ return PAM_AUTH_ERR;
92+
+}
93+
+
94+
/* stolen from pam_stress */
95+
int tacacs_get_password (pam_handle_t * pamh, int flags
96+
,int ctrl, char **password) {
97+
diff --git a/support.h b/support.h
98+
index 09b8a85..cb04a4f 100644
99+
--- a/support.h
100+
+++ b/support.h
101+
@@ -42,6 +42,7 @@ extern struct addrinfo *tac_source_addr;
102+
int _pam_parse (int, const char **);
103+
unsigned long _resolve_name (char *);
104+
unsigned long _getserveraddr (char *serv);
105+
+int validate_not_sshd_bad_pass(const char *pass);
106+
int tacacs_get_password (pam_handle_t *, int, int, char **);
107+
int converse (pam_handle_t *, int, const struct pam_message *, struct pam_response **);
108+
void _pam_log (int, const char *, ...);
109+
diff --git a/tacc.c b/tacc.c
110+
index fcc7d8c..bf0f2a3 100644
111+
--- a/tacc.c
112+
+++ b/tacc.c
113+
@@ -181,7 +181,7 @@ int main(int argc, char **argv) {
114+
break;
115+
case 'L':
116+
// tac_login is a global variable initialized in libtac
117+
- bzero(tac_login, sizeof(tac_login));
118+
+ memset(tac_login, 0, sizeof(tac_login));
119+
strncpy(tac_login, optarg, sizeof(tac_login) - 1);
120+
break;
121+
case 'p':
122+
@@ -312,7 +312,7 @@ int main(int argc, char **argv) {
123+
}
124+
125+
/* we no longer need the password in our address space */
126+
- bzero(pass, strlen(pass));
127+
+ memset(pass, 0, strlen(pass));
128+
pass = NULL;
129+
130+
if (do_account) {
131+
--
132+
2.17.1
133+

src/tacacs/pam/Makefile

+1
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ $(addprefix $(DEST)/, $(MAIN_TARGET)): $(DEST)/% :
2020
git apply ../0004-management-vrf-support.patch
2121
git apply ../0005-pam-Modify-parsing-of-IP-address-and-port-number-to-.patch
2222
git apply ../0006-Add-support-for-source-ip-address.patch
23+
git apply ../0007-handle-bad-password-set-by-sshd.patch
2324

2425
dpkg-buildpackage -rfakeroot -b -us -uc -j$(SONIC_CONFIG_MAKE_JOBS) --admindir $(SONIC_DPKG_ADMINDIR)
2526
popd

0 commit comments

Comments
 (0)