PostgreSQL Source Code  git master
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros
fe-auth.h File Reference
#include "libpq-fe.h"
#include "libpq-int.h"
Include dependency graph for fe-auth.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Functions

int pg_fe_sendauth (AuthRequest areq, PGconn *conn)
 
char * pg_fe_getauthname (PQExpBuffer errorMessage)
 

Function Documentation

char* pg_fe_getauthname ( PQExpBuffer  errorMessage)

Definition at line 733 of file fe-auth.c.

References libpq_gettext, name, NULL, pglock_thread, pgunlock_thread, pqGetpwuid(), pqStrerror(), printfPQExpBuffer(), and username.

Referenced by connectOptions2(), and conninfo_add_defaults().

734 {
735  char *result = NULL;
736  const char *name = NULL;
737 
738 #ifdef WIN32
739  /* Microsoft recommends buffer size of UNLEN+1, where UNLEN = 256 */
740  char username[256 + 1];
741  DWORD namesize = sizeof(username);
742 #else
743  uid_t user_id = geteuid();
744  char pwdbuf[BUFSIZ];
745  struct passwd pwdstr;
746  struct passwd *pw = NULL;
747  int pwerr;
748 #endif
749 
750  /*
751  * Some users are using configure --enable-thread-safety-force, so we
752  * might as well do the locking within our library to protect
753  * pqGetpwuid(). In fact, application developers can use getpwuid() in
754  * their application if they use the locking call we provide, or install
755  * their own locking function using PQregisterThreadLock().
756  */
757  pglock_thread();
758 
759 #ifdef WIN32
760  if (GetUserName(username, &namesize))
761  name = username;
762  else if (errorMessage)
763  printfPQExpBuffer(errorMessage,
764  libpq_gettext("user name lookup failure: error code %lu\n"),
765  GetLastError());
766 #else
767  pwerr = pqGetpwuid(user_id, &pwdstr, pwdbuf, sizeof(pwdbuf), &pw);
768  if (pw != NULL)
769  name = pw->pw_name;
770  else if (errorMessage)
771  {
772  if (pwerr != 0)
773  printfPQExpBuffer(errorMessage,
774  libpq_gettext("could not look up local user ID %d: %s\n"),
775  (int) user_id,
776  pqStrerror(pwerr, pwdbuf, sizeof(pwdbuf)));
777  else
778  printfPQExpBuffer(errorMessage,
779  libpq_gettext("local user with ID %d does not exist\n"),
780  (int) user_id);
781  }
782 #endif
783 
784  if (name)
785  {
786  result = strdup(name);
787  if (result == NULL && errorMessage)
788  printfPQExpBuffer(errorMessage,
789  libpq_gettext("out of memory\n"));
790  }
791 
792  pgunlock_thread();
793 
794  return result;
795 }
void printfPQExpBuffer(PQExpBuffer str, const char *fmt,...)
Definition: pqexpbuffer.c:234
int uid_t
Definition: win32.h:260
char * pqStrerror(int errnum, char *strerrbuf, size_t buflen)
Definition: thread.c:61
#define pglock_thread()
Definition: libpq-int.h:568
static char * username
Definition: initdb.c:130
#define NULL
Definition: c.h:226
const char * name
Definition: encode.c:521
int pqGetpwuid(uid_t uid, struct passwd *resultbuf, char *buffer, size_t buflen, struct passwd **result)
Definition: thread.c:95
#define pgunlock_thread()
Definition: libpq-int.h:569
#define libpq_gettext(x)
Definition: libpq-int.h:689
int pg_fe_sendauth ( AuthRequest  areq,
PGconn conn 
)

Definition at line 558 of file fe-auth.c.

References AUTH_REQ_CRYPT, AUTH_REQ_GSS, AUTH_REQ_GSS_CONT, AUTH_REQ_KRB4, AUTH_REQ_KRB5, AUTH_REQ_MD5, AUTH_REQ_OK, AUTH_REQ_PASSWORD, AUTH_REQ_SCM_CREDS, AUTH_REQ_SSPI, pg_conn::connhost, pg_conn::errorMessage, libpq_gettext, NULL, password, pg_conn_host::password, pg_conn::password_needed, pg_local_sendauth(), pg_password_sendauth(), pg_strcasecmp(), pglock_thread, pg_conn::pgpass, pgunlock_thread, PQnoPasswordSupplied, printfPQExpBuffer(), STATUS_ERROR, STATUS_OK, and pg_conn::whichhost.

Referenced by PQconnectPoll().

559 {
560  switch (areq)
561  {
562  case AUTH_REQ_OK:
563  break;
564 
565  case AUTH_REQ_KRB4:
567  libpq_gettext("Kerberos 4 authentication not supported\n"));
568  return STATUS_ERROR;
569 
570  case AUTH_REQ_KRB5:
572  libpq_gettext("Kerberos 5 authentication not supported\n"));
573  return STATUS_ERROR;
574 
575 #if defined(ENABLE_GSS) || defined(ENABLE_SSPI)
576  case AUTH_REQ_GSS:
577 #if !defined(ENABLE_SSPI)
578  /* no native SSPI, so use GSSAPI library for it */
579  case AUTH_REQ_SSPI:
580 #endif
581  {
582  int r;
583 
584  pglock_thread();
585 
586  /*
587  * If we have both GSS and SSPI support compiled in, use SSPI
588  * support by default. This is overridable by a connection
589  * string parameter. Note that when using SSPI we still leave
590  * the negotiate parameter off, since we want SSPI to use the
591  * GSSAPI kerberos protocol. For actual SSPI negotiate
592  * protocol, we use AUTH_REQ_SSPI.
593  */
594 #if defined(ENABLE_GSS) && defined(ENABLE_SSPI)
595  if (conn->gsslib && (pg_strcasecmp(conn->gsslib, "gssapi") == 0))
596  r = pg_GSS_startup(conn);
597  else
598  r = pg_SSPI_startup(conn, 0);
599 #elif defined(ENABLE_GSS) && !defined(ENABLE_SSPI)
600  r = pg_GSS_startup(conn);
601 #elif !defined(ENABLE_GSS) && defined(ENABLE_SSPI)
602  r = pg_SSPI_startup(conn, 0);
603 #endif
604  if (r != STATUS_OK)
605  {
606  /* Error message already filled in. */
607  pgunlock_thread();
608  return STATUS_ERROR;
609  }
610  pgunlock_thread();
611  }
612  break;
613 
614  case AUTH_REQ_GSS_CONT:
615  {
616  int r;
617 
618  pglock_thread();
619 #if defined(ENABLE_GSS) && defined(ENABLE_SSPI)
620  if (conn->usesspi)
621  r = pg_SSPI_continue(conn);
622  else
623  r = pg_GSS_continue(conn);
624 #elif defined(ENABLE_GSS) && !defined(ENABLE_SSPI)
625  r = pg_GSS_continue(conn);
626 #elif !defined(ENABLE_GSS) && defined(ENABLE_SSPI)
627  r = pg_SSPI_continue(conn);
628 #endif
629  if (r != STATUS_OK)
630  {
631  /* Error message already filled in. */
632  pgunlock_thread();
633  return STATUS_ERROR;
634  }
635  pgunlock_thread();
636  }
637  break;
638 #else /* defined(ENABLE_GSS) || defined(ENABLE_SSPI) */
639  /* No GSSAPI *or* SSPI support */
640  case AUTH_REQ_GSS:
641  case AUTH_REQ_GSS_CONT:
643  libpq_gettext("GSSAPI authentication not supported\n"));
644  return STATUS_ERROR;
645 #endif /* defined(ENABLE_GSS) || defined(ENABLE_SSPI) */
646 
647 #ifdef ENABLE_SSPI
648  case AUTH_REQ_SSPI:
649 
650  /*
651  * SSPI has it's own startup message so libpq can decide which
652  * method to use. Indicate to pg_SSPI_startup that we want SSPI
653  * negotiation instead of Kerberos.
654  */
655  pglock_thread();
656  if (pg_SSPI_startup(conn, 1) != STATUS_OK)
657  {
658  /* Error message already filled in. */
659  pgunlock_thread();
660  return STATUS_ERROR;
661  }
662  pgunlock_thread();
663  break;
664 #else
665 
666  /*
667  * No SSPI support. However, if we have GSSAPI but not SSPI
668  * support, AUTH_REQ_SSPI will have been handled in the codepath
669  * for AUTH_REQ_GSSAPI above, so don't duplicate the case label in
670  * that case.
671  */
672 #if !defined(ENABLE_GSS)
673  case AUTH_REQ_SSPI:
675  libpq_gettext("SSPI authentication not supported\n"));
676  return STATUS_ERROR;
677 #endif /* !define(ENABLE_GSSAPI) */
678 #endif /* ENABLE_SSPI */
679 
680 
681  case AUTH_REQ_CRYPT:
683  libpq_gettext("Crypt authentication not supported\n"));
684  return STATUS_ERROR;
685 
686  case AUTH_REQ_MD5:
687  case AUTH_REQ_PASSWORD:
688  {
689  char *password;
690 
691  conn->password_needed = true;
692  password = conn->connhost[conn->whichhost].password;
693  if (password == NULL)
694  password = conn->pgpass;
695  if (password == NULL || password[0] == '\0')
696  {
699  return STATUS_ERROR;
700  }
701  if (pg_password_sendauth(conn, password, areq) != STATUS_OK)
702  {
704  "fe_sendauth: error sending password authentication\n");
705  return STATUS_ERROR;
706  }
707  break;
708  }
709 
710  case AUTH_REQ_SCM_CREDS:
711  if (pg_local_sendauth(conn) != STATUS_OK)
712  return STATUS_ERROR;
713  break;
714 
715  default:
717  libpq_gettext("authentication method %u not supported\n"), areq);
718  return STATUS_ERROR;
719  }
720 
721  return STATUS_OK;
722 }
static char password[100]
Definition: streamutil.c:44
#define AUTH_REQ_SSPI
Definition: pqcomm.h:174
void printfPQExpBuffer(PQExpBuffer str, const char *fmt,...)
Definition: pqexpbuffer.c:234
static int pg_local_sendauth(PGconn *conn)
Definition: fe-auth.c:445
bool password_needed
Definition: libpq-int.h:410
#define AUTH_REQ_OK
Definition: pqcomm.h:165
#define AUTH_REQ_GSS
Definition: pqcomm.h:172
static int pg_password_sendauth(PGconn *conn, const char *password, AuthRequest areq)
Definition: fe-auth.c:497
#define STATUS_ERROR
Definition: c.h:972
#define pglock_thread()
Definition: libpq-int.h:568
#define PQnoPasswordSupplied
Definition: libpq-fe.h:512
int pg_strcasecmp(const char *s1, const char *s2)
Definition: pgstrcasecmp.c:36
#define AUTH_REQ_MD5
Definition: pqcomm.h:170
pg_conn_host * connhost
Definition: libpq-int.h:399
#define AUTH_REQ_CRYPT
Definition: pqcomm.h:169
#define STATUS_OK
Definition: c.h:971
#define AUTH_REQ_PASSWORD
Definition: pqcomm.h:168
PQExpBufferData errorMessage
Definition: libpq-int.h:498
#define AUTH_REQ_KRB5
Definition: pqcomm.h:167
#define NULL
Definition: c.h:226
#define AUTH_REQ_KRB4
Definition: pqcomm.h:166
char * pgpass
Definition: libpq-int.h:345
#define AUTH_REQ_GSS_CONT
Definition: pqcomm.h:173
#define pgunlock_thread()
Definition: libpq-int.h:569
int whichhost
Definition: libpq-int.h:398
#define libpq_gettext(x)
Definition: libpq-int.h:689
#define AUTH_REQ_SCM_CREDS
Definition: pqcomm.h:171
char * password
Definition: libpq-int.h:313