60 const char **logdetail);
68#define IDENT_USERNAME_MAX 512
88#ifdef HAVE_PAM_PAM_APPL_H
89#include <pam/pam_appl.h>
91#ifdef HAVE_SECURITY_PAM_APPL_H
92#include <security/pam_appl.h>
95#define PGSQL_PAM_SERVICE "postgresql"
98#ifdef _PAM_LEGACY_NONCONST
101#define PG_PAM_CONST const
140#define LDAP_DEPRECATED 1
150#ifndef LDAP_OPT_DIAGNOSTIC_MESSAGE
151#define LDAP_OPT_DIAGNOSTIC_MESSAGE LDAP_OPT_ERROR_STRING
258 switch (
port->hba->auth_method)
305 errstr =
gettext_noop(
"authentication failed for user \"%s\": invalid authentication method");
310 port->hba->sourcefile,
port->hba->linenumber,
354 (
errmsg(
"authentication identifier set more than once"),
355 errdetail_log(
"previous identifier: \"%s\"; new identifier: \"%s\"",
365 errmsg(
"connection authenticated: identity=\"%s\" method=%s "
369 port->hba->sourcefile,
port->hba->linenumber));
382 const char *logdetail =
NULL;
405 errmsg(
"client certificates can only be checked if a root certificate store is available")));
413 if (!
port->peer_cert_valid)
416 errmsg(
"connection requires a valid client certificate")));
422 switch (
port->hba->auth_method)
447 (
port->gss &&
port->gss->enc) ?
_(
"GSS encryption") :
450 port->ssl_in_use ?
_(
"SSL encryption") :
458 errmsg(
"pg_hba.conf rejects replication connection for host \"%s\", user \"%s\", %s",
465 errmsg(
"pg_hba.conf rejects connection for host \"%s\", user \"%s\", database \"%s\", %s",
493 (
port->gss &&
port->gss->enc) ?
_(
"GSS encryption") :
496 port->ssl_in_use ?
_(
"SSL encryption") :
500#define HOSTNAME_LOOKUP_DETAIL(port) \
501 (port->remote_hostname ? \
502 (port->remote_hostname_resolv == +1 ? \
503 errdetail_log("Client IP address resolved to \"%s\", forward lookup matches.", \
504 port->remote_hostname) : \
505 port->remote_hostname_resolv == 0 ? \
506 errdetail_log("Client IP address resolved to \"%s\", forward lookup not checked.", \
507 port->remote_hostname) : \
508 port->remote_hostname_resolv == -1 ? \
509 errdetail_log("Client IP address resolved to \"%s\", forward lookup does not match.", \
510 port->remote_hostname) : \
511 port->remote_hostname_resolv == -2 ? \
512 errdetail_log("Could not translate client host name \"%s\" to IP address: %s.", \
513 port->remote_hostname, \
514 gai_strerror(port->remote_hostname_errcode)) : \
516 : (port->remote_hostname_resolv == -2 ? \
517 errdetail_log("Could not resolve client IP address to a host name: %s.", \
518 gai_strerror(port->remote_hostname_errcode)) : \
525 errmsg(
"no pg_hba.conf entry for replication connection from host \"%s\", user \"%s\", %s",
533 errmsg(
"no pg_hba.conf entry for host \"%s\", user \"%s\", database \"%s\", %s",
548 port->gss->auth =
true;
657 errmsg(
"connection authenticated: user=\"%s\" method=%s "
660 port->hba->sourcefile,
port->hba->linenumber));
664 (*ClientAuthentication_hook) (
port, status);
726 errmsg(
"expected password response, got message type %d",
747 errmsg(
"invalid password packet size")));
765 errmsg(
"empty password returned by client")));
893 (
errmsg(
"could not generate random MD5 salt")));
944 errmsg(
"could not set environment: %m")));
962 port->gss->delegated_creds =
false;
983 errmsg(
"expected GSS response, got message type %d",
1001 elog(
DEBUG4,
"processing received GSS token of length %zu",
1019 elog(
DEBUG5,
"gss_accept_sec_context major: %u, "
1020 "minor: %u, outlen: %zu, outflags: %x",
1029 port->gss->delegated_creds =
true;
1032 if (
port->gss->outbuf.length != 0)
1037 elog(
DEBUG4,
"sending GSS response token of length %zu",
1038 port->gss->outbuf.length);
1041 port->gss->outbuf.value,
port->gss->outbuf.length);
1127 if (!
port->hba->include_realm)
1145 "GSSAPI realm (%s) and configured realm (%s) don't match",
1146 cp,
port->hba->krb_realm);
1155 "GSSAPI did not return realm but realm matching was requested");
1261 errmsg(
"expected SSPI response, got message type %d",
1293 outbuf.cBuffers = 1;
1297 elog(
DEBUG4,
"processing received SSPI token of length %u",
1298 (
unsigned int)
buf.len);
1313 if (outbuf.cBuffers > 0 && outbuf.pBuffers[0].cbBuffer > 0)
1318 elog(
DEBUG4,
"sending SSPI response token of length %u",
1319 (
unsigned int) outbuf.pBuffers[0].cbBuffer);
1321 port->gss->outbuf.length = outbuf.pBuffers[0].cbBuffer;
1322 port->gss->outbuf.value = outbuf.pBuffers[0].pvBuffer;
1325 port->gss->outbuf.value,
port->gss->outbuf.length);
1339 _(
"could not accept SSPI security context"), r);
1353 (
errmsg(
"out of memory")));
1380 _(
"could not get token from SSPI security context"), r);
1391 (
errmsg_internal(
"could not get token information buffer size: error code %lu",
1397 (
errmsg(
"out of memory")));
1414 if (!
port->hba->compat_realm)
1417 domainname,
sizeof(domainname),
1418 port->hba->upn_username);
1431 if (
port->hba->compat_realm)
1454 "SSPI domain (%s) and configured domain (%s) don't match",
1455 domainname,
port->hba->krb_realm);
1467 if (
port->hba->include_realm)
1516 errmsg(
"could not translate name")));
1530 if (!res || p ==
NULL)
1535 errmsg(
"could not translate name")));
1548 errmsg(
"realm name too long")));
1553 strcpy(domainname, p + 1);
1563 errmsg(
"translated account name too long")));
1589 return c ==
' ' ||
c ==
'\t';
1705 remote_port,
sizeof(remote_port),
1716 hints.ai_protocol = 0;
1717 hints.ai_addrlen = 0;
1732 hints.ai_protocol = 0;
1733 hints.ai_addrlen = 0;
1751 errmsg(
"could not create socket for Ident connection: %m")));
1766 errmsg(
"could not bind to local address \"%s\": %m",
1778 errmsg(
"could not connect to Ident server at address \"%s\", port %s: %m",
1800 errmsg(
"could not send query to Ident server at address \"%s\", port %s: %m",
1817 errmsg(
"could not receive response from Ident server at address \"%s\", port %s: %m",
1827 (
errmsg(
"invalidly formatted response from Ident server: \"%s\"",
1883 errmsg(
"peer authentication is not supported on this platform")));
1887 errmsg(
"could not get peer credentials: %m")));
1897 errmsg(
"could not look up local user ID %ld: %m", (
long) uid));
1903 errmsg(
"local user with ID %ld does not exist", (
long) uid));
1968 errmsg(
"out of memory")));
2003 (
errmsg(
"error from underlying PAM layer: %s",
2014 (
errmsg(
"unsupported PAM conversation %d/\"%s\"",
2016 msg[
i]->msg ? msg[
i]->msg :
"(none)")));
2061 if (
port->hba->pamservice &&
port->hba->pamservice[0] !=
'\0')
2071 (
errmsg(
"could not create PAM authenticator: %s",
2082 (
errmsg(
"pam_set_item(PAM_USER) failed: %s",
2093 if (
port->hba->pam_use_hostname)
2114 (
errmsg(
"pam_set_item(PAM_RHOST) failed: %s",
2126 (
errmsg(
"pam_set_item(PAM_CONV) failed: %s",
2139 (
errmsg(
"pam_authenticate failed: %s",
2152 (
errmsg(
"pam_acct_mgmt failed: %s",
2163 (
errmsg(
"could not release PAM authenticator: %s",
2243 (
errmsg(
"could not initialize LDAP: error code %lu",
2249#ifdef HAVE_LDAP_INITIALIZE
2272 if (!
port->hba->ldapserver ||
port->hba->ldapserver[0] ==
'\0')
2280 (
errmsg(
"could not extract domain name from ldapbasedn")));
2288 (
errmsg(
"LDAP authentication could not find DNS SRV records for \"%s\"",
2290 (
errhint(
"Set an LDAP server name explicitly."))));
2303 p =
port->hba->ldapserver;
2342 (
errmsg(
"could not initialize LDAP: %s",
2352 (
errmsg(
"ldaps not supported with this LDAP library")));
2360 (
errmsg(
"could not initialize LDAP: %m")));
2370 (
errmsg(
"could not set LDAP protocol version: %s",
2377 if (
port->hba->ldaptls)
2386 (
errmsg(
"could not start LDAP TLS session: %s",
2398#define LPH_USERNAME "$username"
2399#define LPH_USERNAME_LEN (sizeof(LPH_USERNAME) - 1)
2402#ifndef LDAP_NO_ATTRS
2403#define LDAP_NO_ATTRS "1.1"
2408#define LDAPS_PORT 636
2427 while (*pattern !=
'\0')
2451 const char *server_name;
2453#ifdef HAVE_LDAP_INITIALIZE
2459 if ((!
port->hba->ldapserver ||
port->hba->ldapserver[0] ==
'\0') &&
2460 (!
port->hba->ldapbasedn ||
port->hba->ldapbasedn[0] ==
'\0'))
2463 (
errmsg(
"LDAP server not specified, and no ldapbasedn")));
2467 if (!
port->hba->ldapserver ||
port->hba->ldapserver[0] ==
'\0')
2470 (
errmsg(
"LDAP server not specified")));
2479 server_name =
port->hba->ldapserver ?
port->hba->ldapserver :
"";
2481 if (
port->hba->ldapport == 0)
2483 if (
port->hba->ldapscheme !=
NULL &&
2503 if (
port->hba->ldapbasedn)
2523 for (
c =
port->user_name; *
c;
c++)
2532 (
errmsg(
"invalid character in user name for LDAP authentication")));
2544 port->hba->ldapbinddn ?
port->hba->ldapbinddn :
"",
2549 (
errmsg(
"could not perform initial LDAP bind for ldapbinddn \"%s\" on server \"%s\": %s",
2550 port->hba->ldapbinddn ?
port->hba->ldapbinddn :
"",
2560 if (
port->hba->ldapsearchfilter)
2562 else if (
port->hba->ldapsearchattribute)
2563 filter =
psprintf(
"(%s=%s)",
port->hba->ldapsearchattribute,
port->user_name);
2569 port->hba->ldapbasedn,
2570 port->hba->ldapscope,
2579 (
errmsg(
"could not search LDAP for filter \"%s\" on server \"%s\": %s",
2595 (
errmsg(
"LDAP user \"%s\" does not exist",
port->user_name),
2596 errdetail(
"LDAP search for filter \"%s\" on server \"%s\" returned no entries.",
2597 filter, server_name)));
2600 (
errmsg(
"LDAP user \"%s\" is not unique",
port->user_name),
2601 errdetail_plural(
"LDAP search for filter \"%s\" on server \"%s\" returned %d entry.",
2602 "LDAP search for filter \"%s\" on server \"%s\" returned %d entries.",
2604 filter, server_name, count)));
2621 (
errmsg(
"could not get dn for the first entry matching \"%s\" on server \"%s\": %s",
2622 filter, server_name,
2639 port->hba->ldapprefix ?
port->hba->ldapprefix :
"",
2641 port->hba->ldapsuffix ?
port->hba->ldapsuffix :
"");
2648 (
errmsg(
"LDAP login failed for user \"%s\" on server \"%s\": %s",
2680 errdetail(
"LDAP diagnostics: %s", message);
2704 switch (
port->hba->clientcertname)
2718 (
errmsg(
"certificate authentication failed for user \"%s\": client certificate contains no user name",
2739 (
errmsg(
"certificate authentication failed for user \"%s\": unable to retrieve subject DN",
2758 switch (
port->hba->clientcertname)
2762 (
errmsg(
"certificate validation (clientcert=verify-full) failed for user \"%s\": DN mismatch",
2767 (
errmsg(
"certificate validation (clientcert=verify-full) failed for user \"%s\": CN mismatch",
2786#define RADIUS_VECTOR_LENGTH 16
2787#define RADIUS_HEADER_LENGTH 20
2788#define RADIUS_MAX_PASSWORD_LENGTH 128
2791#define RADIUS_BUFFER_SIZE 1024
2811#define RADIUS_ACCESS_REQUEST 1
2812#define RADIUS_ACCESS_ACCEPT 2
2813#define RADIUS_ACCESS_REJECT 3
2816#define RADIUS_USER_NAME 1
2817#define RADIUS_PASSWORD 2
2818#define RADIUS_SERVICE_TYPE 6
2819#define RADIUS_NAS_IDENTIFIER 32
2822#define RADIUS_AUTHENTICATE_ONLY 8
2825#define RADIUS_TIMEOUT 3
2841 "adding attribute code %d with length %d to radius packet would create oversize packet, ignoring",
2866 if (
port->hba->radiusservers ==
NIL)
2869 (
errmsg(
"RADIUS server not specified")));
2873 if (
port->hba->radiussecrets ==
NIL)
2876 (
errmsg(
"RADIUS secret not specified")));
2901 foreach(server,
port->hba->radiusservers)
2938 radiusports =
lnext(
port->hba->radiusports, radiusports);
2940 identifiers =
lnext(
port->hba->radiusidentifiers, identifiers);
2983 MemSet(&hint, 0,
sizeof(hint));
2992 (
errmsg(
"could not translate RADIUS server name \"%s\" to address: %s",
3006 (
errmsg(
"could not generate random encryption vector")));
3043 (
errmsg(
"could not perform MD5 encryption of password: %s",
3070 (
errmsg(
"could not create RADIUS socket: %m")));
3086 (
errmsg(
"could not bind local RADIUS socket: %m")));
3096 (
errmsg(
"could not send RADIUS packet: %m")));
3130 (
errmsg(
"timeout waiting for RADIUS response from %s",
3149 (
errmsg(
"could not check status on RADIUS socket: %m")));
3156 (
errmsg(
"timeout waiting for RADIUS response from %s",
3179 (
errmsg(
"could not read RADIUS response: %m")));
3187 (
errmsg(
"RADIUS response from %s was sent from incorrect port: %d",
3202 (
errmsg(
"RADIUS response from %s has corrupt length: %d (actual length %d)",
3210 (
errmsg(
"RADIUS response from %s is to a different request: %d (should be %d)",
3237 (
errmsg(
"could not perform MD5 encryption of received packet: %s",
3247 (
errmsg(
"RADIUS response from %s has incorrect MD5 signature",
3265 (
errmsg(
"RADIUS response from %s has invalid code (%d) for user \"%s\"",
const pg_be_sasl_mech pg_be_oauth_mech
int CheckSASLAuth(const pg_be_sasl_mech *mech, Port *port, char *shadow_pass, const char **logdetail)
const pg_be_sasl_mech pg_be_scram_mech
void sendAuthRequest(Port *port, AuthRequest areq, const void *extradata, int extralen)
static void radius_add_attribute(radius_packet *packet, uint8 type, const unsigned char *data, int len)
#define RADIUS_HEADER_LENGTH
static int CheckPWChallengeAuth(Port *port, const char **logdetail)
#define RADIUS_AUTHENTICATE_ONLY
static int auth_peer(Port *port)
char * pg_krb_server_keyfile
#define IDENT_USERNAME_MAX
#define RADIUS_ACCESS_REQUEST
bool pg_krb_caseins_users
static char * recv_password_packet(Port *port)
#define RADIUS_NAS_IDENTIFIER
#define RADIUS_SERVICE_TYPE
bool pg_gss_accept_delegation
static int CheckRADIUSAuth(Port *port)
static void auth_failed(Port *port, int status, const char *logdetail)
#define RADIUS_MAX_PASSWORD_LENGTH
ClientAuthentication_hook_type ClientAuthentication_hook
void ClientAuthentication(Port *port)
#define RADIUS_ACCESS_REJECT
static int CheckMD5Auth(Port *port, char *shadow_pass, const char **logdetail)
void set_authn_id(Port *port, const char *id)
static bool is_ident_whitespace(const char c)
#define RADIUS_ACCESS_ACCEPT
static int ident_inet(Port *port)
static int PerformRadiusTransaction(const char *server, const char *secret, const char *portstr, const char *identifier, const char *user_name, const char *passwd)
#define RADIUS_VECTOR_LENGTH
static bool interpret_ident_response(const char *ident_response, char *ident_user)
#define HOSTNAME_LOOKUP_DETAIL(port)
static int CheckPasswordAuth(Port *port, const char **logdetail)
#define RADIUS_BUFFER_SIZE
PGDLLIMPORT auth_password_hook_typ ldap_password_hook
void(* ClientAuthentication_hook_type)(Port *, int)
char *(* auth_password_hook_typ)(char *input)
#define PG_MAX_AUTH_TOKEN_LENGTH
Datum now(PG_FUNCTION_ARGS)
@ LOG_CONNECTION_AUTHENTICATION
void pg_store_delegated_credential(gss_cred_id_t cred)
void pg_GSS_error(const char *errmsg, OM_uint32 maj_stat, OM_uint32 min_stat)
bool secure_loaded_verify_locations(void)
#define unconstify(underlying_type, expr)
#define Assert(condition)
#define FLEXIBLE_ARRAY_MEMBER
#define MemSet(start, val, len)
int md5_crypt_verify(const char *role, const char *shadow_pass, const char *client_pass, const uint8 *md5_salt, int md5_salt_len, const char **logdetail)
int plain_crypt_verify(const char *role, const char *shadow_pass, const char *client_pass, const char **logdetail)
char * get_role_password(const char *role, const char **logdetail)
PasswordType get_password_type(const char *shadow_pass)
int errcode_for_socket_access(void)
int errmsg_internal(const char *fmt,...)
int errdetail_internal(const char *fmt,...)
int errdetail(const char *fmt,...)
int errdetail_plural(const char *fmt_singular, const char *fmt_plural, unsigned long n,...)
int errhint(const char *fmt,...)
int errcode(int sqlerrcode)
int errmsg(const char *fmt,...)
int errdetail_log(const char *fmt,...)
#define ereport(elevel,...)
#define ERRCODE_INVALID_PASSWORD
int check_usermap(const char *usermap_name, const char *pg_user, const char *system_user, bool case_insensitive)
void hba_getauthmethod(Port *port)
const char * hba_authname(UserAuth auth_method)
void pg_freeaddrinfo_all(int hint_ai_family, struct addrinfo *ai)
int pg_getnameinfo_all(const struct sockaddr_storage *addr, int salen, char *node, int nodelen, char *service, int servicelen, int flags)
int pg_getaddrinfo_all(const char *hostname, const char *servname, const struct addrinfo *hintp, struct addrinfo **result)
char * MemoryContextStrdup(MemoryContext context, const char *string)
void * MemoryContextAllocZero(MemoryContext context, Size size)
char * pstrdup(const char *in)
void pfree(void *pointer)
MemoryContext TopMemoryContext
bool pg_md5_binary(const void *buff, size_t len, uint8 *outbuf, const char **errstr)
#define CHECK_FOR_INTERRUPTS()
ClientConnectionInfo MyClientConnectionInfo
static int list_length(const List *l)
static ListCell * list_head(const List *l)
static ListCell * lnext(const List *l, const ListCell *c)
static char buf[DEFAULT_XLOG_SEG_SIZE]
bool pg_strong_random(void *buf, size_t len)
int pg_strcasecmp(const char *s1, const char *s2)
int getpeereid(int sock, uid_t *uid, gid_t *gid)
int pq_getmessage(StringInfo s, int maxlen)
void pq_startmsgread(void)
#define PqMsg_GSSResponse
#define PqMsg_AuthenticationRequest
#define AUTH_REQ_PASSWORD
#define AUTH_REQ_GSS_CONT
#define PqMsg_PasswordMessage
#define AUTH_REQ_SASL_FIN
char * psprintf(const char *fmt,...)
const char * gai_strerror(int errcode)
void appendStringInfo(StringInfo str, const char *fmt,...)
void appendBinaryStringInfo(StringInfo str, const void *data, int datalen)
void appendStringInfoString(StringInfo str, const char *s)
void appendStringInfoChar(StringInfo str, char ch)
void initStringInfo(StringInfo str)
uint8 data[FLEXIBLE_ARRAY_MEMBER]
#define bind(s, addr, addrlen)
#define recv(s, buf, len, flags)
#define send(s, buf, len, flags)
#define socket(af, type, protocol)
#define connect(s, name, namelen)
#define select(n, r, w, e, timeout)
int gettimeofday(struct timeval *tp, void *tzp)