aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorCarlos Santos <casantos@redhat.com>2025-06-13 16:39:36 -0300
committerCarlos Santos <casantos@redhat.com>2025-06-13 17:32:17 -0300
commit6b162eeb7ce9a3eaa344cf214a9fab19ab026c20 (patch)
tree55f12cce501afff7e4301cdc359c295db3eeedf1
parentbd46aec401b29b6a3866d70c7022b4b1775cc906 (diff)
downloadtigervnc-6b162eeb7ce9a3eaa344cf214a9fab19ab026c20.tar.gz
tigervnc-6b162eeb7ce9a3eaa344cf214a9fab19ab026c20.zip
Send PAM error messages to VNC clients
Send the generic "Authentication failed" if the PAM module does not pass an error message. Signed-off-by: Carlos Santos <casantos@redhat.com>
-rw-r--r--common/rfb/SSecurityPlain.cxx5
-rw-r--r--common/rfb/SSecurityPlain.h12
-rw-r--r--common/rfb/SSecurityRSAAES.cxx5
-rw-r--r--common/rfb/UnixPasswordValidator.cxx14
-rw-r--r--common/rfb/UnixPasswordValidator.h7
-rw-r--r--common/rfb/WinPasswdValidator.cxx3
-rw-r--r--common/rfb/WinPasswdValidator.h6
7 files changed, 38 insertions, 14 deletions
diff --git a/common/rfb/SSecurityPlain.cxx b/common/rfb/SSecurityPlain.cxx
index 06631f81..4fa63250 100644
--- a/common/rfb/SSecurityPlain.cxx
+++ b/common/rfb/SSecurityPlain.cxx
@@ -113,8 +113,9 @@ bool SSecurityPlain::processMsg()
password[plen] = 0;
username[ulen] = 0;
plen = 0;
- if (!valid->validate(sc, username, password))
- throw auth_error("Authentication failed");
+ std::string msg = "Authentication failed";
+ if (!valid->validate(sc, username, password, msg))
+ throw auth_error(msg);
}
return true;
diff --git a/common/rfb/SSecurityPlain.h b/common/rfb/SSecurityPlain.h
index f2bc3483..4c030455 100644
--- a/common/rfb/SSecurityPlain.h
+++ b/common/rfb/SSecurityPlain.h
@@ -29,14 +29,20 @@ namespace rfb {
class PasswordValidator {
public:
- bool validate(SConnection* sc, const char *username, const char *password)
- { return validUser(username) ? validateInternal(sc, username, password) : false; }
+ bool validate(SConnection* sc,
+ const char *username,
+ const char *password,
+ std::string &msg)
+ { return validUser(username) ? validateInternal(sc, username, password, msg) : false; }
static core::StringListParameter plainUsers;
virtual ~PasswordValidator() { }
protected:
- virtual bool validateInternal(SConnection* sc, const char *username, const char *password)=0;
+ virtual bool validateInternal(SConnection* sc,
+ const char *username,
+ const char *password,
+ std::string &msg) = 0;
static bool validUser(const char* username);
};
diff --git a/common/rfb/SSecurityRSAAES.cxx b/common/rfb/SSecurityRSAAES.cxx
index 6afb52dd..405005ab 100644
--- a/common/rfb/SSecurityRSAAES.cxx
+++ b/common/rfb/SSecurityRSAAES.cxx
@@ -583,9 +583,10 @@ void SSecurityRSAAES::verifyUserPass()
#elif !defined(__APPLE__)
UnixPasswordValidator *valid = new UnixPasswordValidator();
#endif
- if (!valid->validate(sc, username, password)) {
+ std::string msg = "Authentication failed";
+ if (!valid->validate(sc, username, password, msg)) {
delete valid;
- throw auth_error("Authentication failed");
+ throw auth_error(msg);
}
delete valid;
#else
diff --git a/common/rfb/UnixPasswordValidator.cxx b/common/rfb/UnixPasswordValidator.cxx
index bcb759a4..17fab80b 100644
--- a/common/rfb/UnixPasswordValidator.cxx
+++ b/common/rfb/UnixPasswordValidator.cxx
@@ -42,6 +42,7 @@ typedef struct
{
const char *username;
const char *password;
+ std::string &msg;
} AuthData;
#if defined(__sun)
@@ -64,7 +65,13 @@ static int pam_callback(int count, const struct pam_message **in,
resp[i].resp_retcode = PAM_SUCCESS;
switch (in[i]->msg_style) {
case PAM_TEXT_INFO:
+ vlog.info("%s info: %s", (const char *) pamService, in[i]->msg);
+ auth->msg = in[i]->msg;
+ resp[i].resp = nullptr;
+ break;
case PAM_ERROR_MSG:
+ vlog.error("%s error: %s", (const char *) pamService, in[i]->msg);
+ auth->msg = in[i]->msg;
resp[i].resp = nullptr;
break;
case PAM_PROMPT_ECHO_ON: /* Send Username */
@@ -83,12 +90,13 @@ static int pam_callback(int count, const struct pam_message **in,
return PAM_SUCCESS;
}
-bool UnixPasswordValidator::validateInternal(SConnection * /*sc*/,
+bool UnixPasswordValidator::validateInternal(SConnection * /* sc */,
const char *username,
- const char *password)
+ const char *password,
+ std::string &msg)
{
int ret;
- AuthData auth = { username, password };
+ AuthData auth = { username, password, msg };
struct pam_conv conv = {
pam_callback,
&auth
diff --git a/common/rfb/UnixPasswordValidator.h b/common/rfb/UnixPasswordValidator.h
index 4d623d6c..46ad2e06 100644
--- a/common/rfb/UnixPasswordValidator.h
+++ b/common/rfb/UnixPasswordValidator.h
@@ -27,8 +27,11 @@ namespace rfb
{
class UnixPasswordValidator: public PasswordValidator {
protected:
- bool validateInternal(SConnection * sc, const char *username,
- const char *password) override;
+ bool validateInternal(SConnection *sc,
+ const char *username,
+ const char *password,
+ std::string &msg) override;
+
};
}
diff --git a/common/rfb/WinPasswdValidator.cxx b/common/rfb/WinPasswdValidator.cxx
index 84832e81..a6281950 100644
--- a/common/rfb/WinPasswdValidator.cxx
+++ b/common/rfb/WinPasswdValidator.cxx
@@ -30,7 +30,8 @@ using namespace rfb;
// This method will only work for Windows NT, 2000, and XP (and possibly Vista)
bool WinPasswdValidator::validateInternal(rfb::SConnection* /*sc*/,
const char* username,
- const char* password)
+ const char* password,
+ std::string & /* msg */)
{
HANDLE handle;
diff --git a/common/rfb/WinPasswdValidator.h b/common/rfb/WinPasswdValidator.h
index 340a6234..993cafea 100644
--- a/common/rfb/WinPasswdValidator.h
+++ b/common/rfb/WinPasswdValidator.h
@@ -21,6 +21,7 @@
#ifndef __RFB_WINPASSWDVALIDATOR_H__
#define __RFB_WINPASSWDVALIDATOR_H__
+#include <string>
#include <rfb/SSecurityPlain.h>
namespace rfb
@@ -30,7 +31,10 @@ namespace rfb
WinPasswdValidator() {};
virtual ~WinPasswdValidator() {};
protected:
- bool validateInternal(SConnection *sc, const char* username, const char* password) override;
+ bool validateInternal(SConnection *sc,
+ const char *username,
+ const char *password,
+ std::string &msg) override;
};
}