PostgreSQL Source Code git master
auth.h File Reference
#include "libpq/libpq-be.h"
Include dependency graph for auth.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Typedefs

typedef void(* ClientAuthentication_hook_type) (Port *, int)
 
typedef char *(* auth_password_hook_typ) (char *input)
 

Functions

void ClientAuthentication (Port *port)
 
void sendAuthRequest (Port *port, AuthRequest areq, const char *extradata, int extralen)
 

Variables

PGDLLIMPORT char * pg_krb_server_keyfile
 
PGDLLIMPORT bool pg_krb_caseins_users
 
PGDLLIMPORT bool pg_gss_accept_delegation
 
PGDLLIMPORT ClientAuthentication_hook_type ClientAuthentication_hook
 
PGDLLIMPORT auth_password_hook_typ ldap_password_hook
 

Typedef Documentation

◆ auth_password_hook_typ

typedef char *(* auth_password_hook_typ) (char *input)

Definition at line 32 of file auth.h.

◆ ClientAuthentication_hook_type

typedef void(* ClientAuthentication_hook_type) (Port *, int)

Definition at line 28 of file auth.h.

Function Documentation

◆ ClientAuthentication()

void ClientAuthentication ( Port port)

Definition at line 382 of file auth.c.

383{
384 int status = STATUS_ERROR;
385 const char *logdetail = NULL;
386
387 /*
388 * Get the authentication method to use for this frontend/database
389 * combination. Note: we do not parse the file at this point; this has
390 * already been done elsewhere. hba.c dropped an error message into the
391 * server logfile if parsing the hba config file failed.
392 */
394
396
397 /*
398 * This is the first point where we have access to the hba record for the
399 * current connection, so perform any verifications based on the hba
400 * options field that should be done *before* the authentication here.
401 */
402 if (port->hba->clientcert != clientCertOff)
403 {
404 /* If we haven't loaded a root certificate store, fail */
407 (errcode(ERRCODE_CONFIG_FILE_ERROR),
408 errmsg("client certificates can only be checked if a root certificate store is available")));
409
410 /*
411 * If we loaded a root certificate store, and if a certificate is
412 * present on the client, then it has been verified against our root
413 * certificate store, and the connection would have been aborted
414 * already if it didn't verify ok.
415 */
416 if (!port->peer_cert_valid)
418 (errcode(ERRCODE_INVALID_AUTHORIZATION_SPECIFICATION),
419 errmsg("connection requires a valid client certificate")));
420 }
421
422 /*
423 * Now proceed to do the actual authentication check
424 */
425 switch (port->hba->auth_method)
426 {
427 case uaReject:
428
429 /*
430 * An explicit "reject" entry in pg_hba.conf. This report exposes
431 * the fact that there's an explicit reject entry, which is
432 * perhaps not so desirable from a security standpoint; but the
433 * message for an implicit reject could confuse the DBA a lot when
434 * the true situation is a match to an explicit reject. And we
435 * don't want to change the message for an implicit reject. As
436 * noted below, the additional information shown here doesn't
437 * expose anything not known to an attacker.
438 */
439 {
440 char hostinfo[NI_MAXHOST];
441 const char *encryption_state;
442
443 pg_getnameinfo_all(&port->raddr.addr, port->raddr.salen,
444 hostinfo, sizeof(hostinfo),
445 NULL, 0,
446 NI_NUMERICHOST);
447
448 encryption_state =
449#ifdef ENABLE_GSS
450 (port->gss && port->gss->enc) ? _("GSS encryption") :
451#endif
452#ifdef USE_SSL
453 port->ssl_in_use ? _("SSL encryption") :
454#endif
455 _("no encryption");
456
459 (errcode(ERRCODE_INVALID_AUTHORIZATION_SPECIFICATION),
460 /* translator: last %s describes encryption state */
461 errmsg("pg_hba.conf rejects replication connection for host \"%s\", user \"%s\", %s",
462 hostinfo, port->user_name,
463 encryption_state)));
464 else
466 (errcode(ERRCODE_INVALID_AUTHORIZATION_SPECIFICATION),
467 /* translator: last %s describes encryption state */
468 errmsg("pg_hba.conf rejects connection for host \"%s\", user \"%s\", database \"%s\", %s",
469 hostinfo, port->user_name,
470 port->database_name,
471 encryption_state)));
472 break;
473 }
474
475 case uaImplicitReject:
476
477 /*
478 * No matching entry, so tell the user we fell through.
479 *
480 * NOTE: the extra info reported here is not a security breach,
481 * because all that info is known at the frontend and must be
482 * assumed known to bad guys. We're merely helping out the less
483 * clueful good guys.
484 */
485 {
486 char hostinfo[NI_MAXHOST];
487 const char *encryption_state;
488
489 pg_getnameinfo_all(&port->raddr.addr, port->raddr.salen,
490 hostinfo, sizeof(hostinfo),
491 NULL, 0,
492 NI_NUMERICHOST);
493
494 encryption_state =
495#ifdef ENABLE_GSS
496 (port->gss && port->gss->enc) ? _("GSS encryption") :
497#endif
498#ifdef USE_SSL
499 port->ssl_in_use ? _("SSL encryption") :
500#endif
501 _("no encryption");
502
503#define HOSTNAME_LOOKUP_DETAIL(port) \
504 (port->remote_hostname ? \
505 (port->remote_hostname_resolv == +1 ? \
506 errdetail_log("Client IP address resolved to \"%s\", forward lookup matches.", \
507 port->remote_hostname) : \
508 port->remote_hostname_resolv == 0 ? \
509 errdetail_log("Client IP address resolved to \"%s\", forward lookup not checked.", \
510 port->remote_hostname) : \
511 port->remote_hostname_resolv == -1 ? \
512 errdetail_log("Client IP address resolved to \"%s\", forward lookup does not match.", \
513 port->remote_hostname) : \
514 port->remote_hostname_resolv == -2 ? \
515 errdetail_log("Could not translate client host name \"%s\" to IP address: %s.", \
516 port->remote_hostname, \
517 gai_strerror(port->remote_hostname_errcode)) : \
518 0) \
519 : (port->remote_hostname_resolv == -2 ? \
520 errdetail_log("Could not resolve client IP address to a host name: %s.", \
521 gai_strerror(port->remote_hostname_errcode)) : \
522 0))
523
526 (errcode(ERRCODE_INVALID_AUTHORIZATION_SPECIFICATION),
527 /* translator: last %s describes encryption state */
528 errmsg("no pg_hba.conf entry for replication connection from host \"%s\", user \"%s\", %s",
529 hostinfo, port->user_name,
530 encryption_state),
532 else
534 (errcode(ERRCODE_INVALID_AUTHORIZATION_SPECIFICATION),
535 /* translator: last %s describes encryption state */
536 errmsg("no pg_hba.conf entry for host \"%s\", user \"%s\", database \"%s\", %s",
537 hostinfo, port->user_name,
538 port->database_name,
539 encryption_state),
541 break;
542 }
543
544 case uaGSS:
545#ifdef ENABLE_GSS
546 /* We might or might not have the gss workspace already */
547 if (port->gss == NULL)
548 port->gss = (pg_gssinfo *)
550 sizeof(pg_gssinfo));
551 port->gss->auth = true;
552
553 /*
554 * If GSS state was set up while enabling encryption, we can just
555 * check the client's principal. Otherwise, ask for it.
556 */
557 if (port->gss->enc)
558 status = pg_GSS_checkauth(port);
559 else
560 {
562 status = pg_GSS_recvauth(port);
563 }
564#else
565 Assert(false);
566#endif
567 break;
568
569 case uaSSPI:
570#ifdef ENABLE_SSPI
571 if (port->gss == NULL)
572 port->gss = (pg_gssinfo *)
574 sizeof(pg_gssinfo));
576 status = pg_SSPI_recvauth(port);
577#else
578 Assert(false);
579#endif
580 break;
581
582 case uaPeer:
583 status = auth_peer(port);
584 break;
585
586 case uaIdent:
587 status = ident_inet(port);
588 break;
589
590 case uaMD5:
591 case uaSCRAM:
592 status = CheckPWChallengeAuth(port, &logdetail);
593 break;
594
595 case uaPassword:
596 status = CheckPasswordAuth(port, &logdetail);
597 break;
598
599 case uaPAM:
600#ifdef USE_PAM
601 status = CheckPAMAuth(port, port->user_name, "");
602#else
603 Assert(false);
604#endif /* USE_PAM */
605 break;
606
607 case uaBSD:
608#ifdef USE_BSD_AUTH
609 status = CheckBSDAuth(port, port->user_name);
610#else
611 Assert(false);
612#endif /* USE_BSD_AUTH */
613 break;
614
615 case uaLDAP:
616#ifdef USE_LDAP
617 status = CheckLDAPAuth(port);
618#else
619 Assert(false);
620#endif
621 break;
622 case uaRADIUS:
623 status = CheckRADIUSAuth(port);
624 break;
625 case uaCert:
626 /* uaCert will be treated as if clientcert=verify-full (uaTrust) */
627 case uaTrust:
628 status = STATUS_OK;
629 break;
630 }
631
632 if ((status == STATUS_OK && port->hba->clientcert == clientCertFull)
633 || port->hba->auth_method == uaCert)
634 {
635 /*
636 * Make sure we only check the certificate if we use the cert method
637 * or verify-full option.
638 */
639#ifdef USE_SSL
640 status = CheckCertAuth(port);
641#else
642 Assert(false);
643#endif
644 }
645
646 if (Log_connections && status == STATUS_OK &&
648 {
649 /*
650 * Normally, if log_connections is set, the call to set_authn_id()
651 * will log the connection. However, if that function is never
652 * called, perhaps because the trust method is in use, then we handle
653 * the logging here instead.
654 */
655 ereport(LOG,
656 errmsg("connection authenticated: user=\"%s\" method=%s "
657 "(%s:%d)",
658 port->user_name, hba_authname(port->hba->auth_method),
659 port->hba->sourcefile, port->hba->linenumber));
660 }
661
663 (*ClientAuthentication_hook) (port, status);
664
665 if (status == STATUS_OK)
667 else
668 auth_failed(port, status, logdetail);
669}
void sendAuthRequest(Port *port, AuthRequest areq, const char *extradata, int extralen)
Definition: auth.c:676
static int CheckPWChallengeAuth(Port *port, const char **logdetail)
Definition: auth.c:822
static int ident_inet(hbaPort *port)
Definition: auth.c:1670
static int CheckRADIUSAuth(Port *port)
Definition: auth.c:2844
static void auth_failed(Port *port, int status, const char *logdetail)
Definition: auth.c:246
ClientAuthentication_hook_type ClientAuthentication_hook
Definition: auth.c:230
static int auth_peer(hbaPort *port)
Definition: auth.c:1855
#define HOSTNAME_LOOKUP_DETAIL(port)
static int CheckPasswordAuth(Port *port, const char **logdetail)
Definition: auth.c:787
bool secure_loaded_verify_locations(void)
Definition: be-secure.c:99
#define STATUS_OK
Definition: c.h:1126
#define Assert(condition)
Definition: c.h:815
#define STATUS_ERROR
Definition: c.h:1127
int errcode(int sqlerrcode)
Definition: elog.c:853
int errmsg(const char *fmt,...)
Definition: elog.c:1070
#define _(x)
Definition: elog.c:90
#define LOG
Definition: elog.h:31
#define FATAL
Definition: elog.h:41
#define ereport(elevel,...)
Definition: elog.h:149
void hba_getauthmethod(hbaPort *port)
Definition: hba.c:3052
const char * hba_authname(UserAuth auth_method)
Definition: hba.c:3065
@ uaBSD
Definition: hba.h:37
@ uaLDAP
Definition: hba.h:38
@ uaPeer
Definition: hba.h:41
@ uaPAM
Definition: hba.h:36
@ uaPassword
Definition: hba.h:31
@ uaCert
Definition: hba.h:39
@ uaMD5
Definition: hba.h:32
@ uaReject
Definition: hba.h:27
@ uaGSS
Definition: hba.h:34
@ uaSCRAM
Definition: hba.h:33
@ uaImplicitReject
Definition: hba.h:28
@ uaRADIUS
Definition: hba.h:40
@ uaIdent
Definition: hba.h:30
@ uaTrust
Definition: hba.h:29
@ uaSSPI
Definition: hba.h:35
@ clientCertOff
Definition: hba.h:69
@ clientCertFull
Definition: hba.h:71
int pg_getnameinfo_all(const struct sockaddr_storage *addr, int salen, char *node, int nodelen, char *service, int servicelen, int flags)
Definition: ip.c:114
void * MemoryContextAllocZero(MemoryContext context, Size size)
Definition: mcxt.c:1215
MemoryContext TopMemoryContext
Definition: mcxt.c:149
#define CHECK_FOR_INTERRUPTS()
Definition: miscadmin.h:122
ClientConnectionInfo MyClientConnectionInfo
Definition: miscinit.c:1066
static int port
Definition: pg_regress.c:115
bool Log_connections
Definition: postmaster.c:240
#define AUTH_REQ_SSPI
Definition: protocol.h:83
#define AUTH_REQ_GSS
Definition: protocol.h:81
#define AUTH_REQ_OK
Definition: protocol.h:74
const char * authn_id
Definition: libpq-be.h:105
bool am_walsender
Definition: walsender.c:115
bool am_db_walsender
Definition: walsender.c:118

References _, am_db_walsender, am_walsender, Assert, auth_failed(), auth_peer(), AUTH_REQ_GSS, AUTH_REQ_OK, AUTH_REQ_SSPI, ClientConnectionInfo::authn_id, CHECK_FOR_INTERRUPTS, CheckPasswordAuth(), CheckPWChallengeAuth(), CheckRADIUSAuth(), ClientAuthentication_hook, clientCertFull, clientCertOff, ereport, errcode(), errmsg(), FATAL, hba_authname(), hba_getauthmethod(), HOSTNAME_LOOKUP_DETAIL, ident_inet(), LOG, Log_connections, MemoryContextAllocZero(), MyClientConnectionInfo, pg_getnameinfo_all(), port, secure_loaded_verify_locations(), sendAuthRequest(), STATUS_ERROR, STATUS_OK, TopMemoryContext, uaBSD, uaCert, uaGSS, uaIdent, uaImplicitReject, uaLDAP, uaMD5, uaPAM, uaPassword, uaPeer, uaRADIUS, uaReject, uaSCRAM, uaSSPI, and uaTrust.

Referenced by PerformAuthentication().

◆ sendAuthRequest()

void sendAuthRequest ( Port port,
AuthRequest  areq,
const char *  extradata,
int  extralen 
)

Definition at line 676 of file auth.c.

677{
679
681
683 pq_sendint32(&buf, (int32) areq);
684 if (extralen > 0)
685 pq_sendbytes(&buf, extradata, extralen);
686
688
689 /*
690 * Flush message so client will see it, except for AUTH_REQ_OK and
691 * AUTH_REQ_SASL_FIN, which need not be sent until we are ready for
692 * queries.
693 */
694 if (areq != AUTH_REQ_OK && areq != AUTH_REQ_SASL_FIN)
695 pq_flush();
696
698}
int32_t int32
Definition: c.h:484
#define pq_flush()
Definition: libpq.h:46
static char * buf
Definition: pg_test_fsync.c:72
void pq_sendbytes(StringInfo buf, const void *data, int datalen)
Definition: pqformat.c:126
void pq_endmessage(StringInfo buf)
Definition: pqformat.c:296
void pq_beginmessage(StringInfo buf, char msgtype)
Definition: pqformat.c:88
static void pq_sendint32(StringInfo buf, uint32 i)
Definition: pqformat.h:144
#define PqMsg_AuthenticationRequest
Definition: protocol.h:50
#define AUTH_REQ_SASL_FIN
Definition: protocol.h:86

References AUTH_REQ_OK, AUTH_REQ_SASL_FIN, buf, CHECK_FOR_INTERRUPTS, pq_beginmessage(), pq_endmessage(), pq_flush, pq_sendbytes(), pq_sendint32(), and PqMsg_AuthenticationRequest.

Referenced by CheckMD5Auth(), CheckPasswordAuth(), CheckRADIUSAuth(), CheckSASLAuth(), and ClientAuthentication().

Variable Documentation

◆ ClientAuthentication_hook

PGDLLIMPORT ClientAuthentication_hook_type ClientAuthentication_hook
extern

Definition at line 230 of file auth.c.

Referenced by _PG_init(), ClientAuthentication(), and sepgsql_init_client_label().

◆ ldap_password_hook

PGDLLIMPORT auth_password_hook_typ ldap_password_hook
extern

Referenced by _PG_init().

◆ pg_gss_accept_delegation

PGDLLIMPORT bool pg_gss_accept_delegation
extern

Definition at line 166 of file auth.c.

Referenced by secure_open_gssapi().

◆ pg_krb_caseins_users

PGDLLIMPORT bool pg_krb_caseins_users
extern

Definition at line 165 of file auth.c.

◆ pg_krb_server_keyfile

PGDLLIMPORT char* pg_krb_server_keyfile
extern

Definition at line 164 of file auth.c.

Referenced by secure_open_gssapi().