mirror of
https://github.com/postgres/postgres.git
synced 2025-09-02 04:21:28 +03:00
Use MD5 for wire protocol encryption for >= 7.2 client/server.
Allow pg_shadow to be MD5 encrypted. Add ENCRYPTED/UNENCRYPTED option to CREATE/ALTER user. Add password_encryption postgresql.conf option. Update wire protocol version to 2.1.
This commit is contained in:
@@ -4,7 +4,7 @@
|
||||
# Makefile for libpq subsystem (backend half of libpq interface)
|
||||
#
|
||||
# IDENTIFICATION
|
||||
# $Header: /cvsroot/pgsql/src/backend/libpq/Makefile,v 1.24 2000/08/25 10:00:30 petere Exp $
|
||||
# $Header: /cvsroot/pgsql/src/backend/libpq/Makefile,v 1.25 2001/08/15 18:42:14 momjian Exp $
|
||||
#
|
||||
#-------------------------------------------------------------------------
|
||||
|
||||
@@ -15,7 +15,7 @@ include $(top_builddir)/src/Makefile.global
|
||||
# be-fsstubs is here for historical reasons, probably belongs elsewhere
|
||||
|
||||
OBJS = be-fsstubs.o \
|
||||
auth.o crypt.o hba.o password.o \
|
||||
auth.o crypt.o hba.o md5.o password.o \
|
||||
pqcomm.o pqformat.o pqpacket.o pqsignal.o util.o
|
||||
|
||||
|
||||
|
@@ -8,7 +8,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/libpq/auth.c,v 1.56 2001/08/07 10:44:13 petere Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/libpq/auth.c,v 1.57 2001/08/15 18:42:14 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@@ -420,9 +420,8 @@ auth_failed(Port *port)
|
||||
authmethod = "IDENT";
|
||||
break;
|
||||
case uaPassword:
|
||||
authmethod = "Password";
|
||||
break;
|
||||
case uaCrypt:
|
||||
case uaMD5:
|
||||
authmethod = "Password";
|
||||
break;
|
||||
}
|
||||
@@ -507,6 +506,11 @@ ClientAuthentication(Port *port)
|
||||
status = recv_and_check_password_packet(port);
|
||||
break;
|
||||
|
||||
case uaMD5:
|
||||
sendAuthRequest(port, AUTH_REQ_MD5);
|
||||
status = recv_and_check_password_packet(port);
|
||||
break;
|
||||
|
||||
case uaTrust:
|
||||
status = STATUS_OK;
|
||||
break;
|
||||
@@ -532,7 +536,7 @@ sendAuthRequest(Port *port, AuthRequest areq)
|
||||
pq_sendint(&buf, (int32) areq, sizeof(int32));
|
||||
|
||||
/* Add the salt for encrypted passwords. */
|
||||
if (areq == AUTH_REQ_CRYPT)
|
||||
if (areq == AUTH_REQ_CRYPT || areq == AUTH_REQ_MD5)
|
||||
{
|
||||
pq_sendint(&buf, port->salt[0], 1);
|
||||
pq_sendint(&buf, port->salt[1], 1);
|
||||
@@ -557,7 +561,7 @@ recv_and_check_password_packet(Port *port)
|
||||
if (pq_eof() == EOF || pq_getint(&len, 4) == EOF)
|
||||
return STATUS_ERROR; /* client didn't want to send password */
|
||||
initStringInfo(&buf);
|
||||
pq_getstr(&buf);
|
||||
pq_getstr(&buf); /* receive password */
|
||||
|
||||
if (DebugLvl)
|
||||
fprintf(stderr, "received password packet with len=%d, pw=%s\n",
|
||||
@@ -579,7 +583,7 @@ checkPassword(Port *port, char *user, char *password)
|
||||
if (port->auth_arg[0] != '\0')
|
||||
return verify_password(port, user, password);
|
||||
|
||||
return crypt_verify(port, user, password);
|
||||
return md5_crypt_verify(port, user, password);
|
||||
}
|
||||
|
||||
|
||||
@@ -594,7 +598,6 @@ old_be_recvauth(Port *port)
|
||||
MsgType msgtype = (MsgType) port->proto;
|
||||
|
||||
/* Handle the authentication that's offered. */
|
||||
|
||||
switch (msgtype)
|
||||
{
|
||||
case STARTUP_KRB4_MSG:
|
||||
@@ -634,6 +637,7 @@ map_old_to_new(Port *port, UserAuth old, int status)
|
||||
switch (port->auth_method)
|
||||
{
|
||||
case uaCrypt:
|
||||
case uaMD5:
|
||||
case uaReject:
|
||||
status = STATUS_ERROR;
|
||||
break;
|
||||
|
@@ -9,7 +9,7 @@
|
||||
* Dec 17, 1997 - Todd A. Brandys
|
||||
* Orignal Version Completed.
|
||||
*
|
||||
* $Id: crypt.c,v 1.32 2001/06/23 23:26:17 petere Exp $
|
||||
* $Id: crypt.c,v 1.33 2001/08/15 18:42:14 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@@ -19,6 +19,7 @@
|
||||
|
||||
#include "postgres.h"
|
||||
#include "libpq/crypt.h"
|
||||
#include "libpq/md5.h"
|
||||
#include "miscadmin.h"
|
||||
#include "storage/fd.h"
|
||||
#include "utils/nabstime.h"
|
||||
@@ -254,7 +255,7 @@ crypt_getloginfo(const char *user, char **passwd, char **valuntil)
|
||||
/*-------------------------------------------------------------------------*/
|
||||
|
||||
int
|
||||
crypt_verify(const Port *port, const char *user, const char *pgpass)
|
||||
md5_crypt_verify(const Port *port, const char *user, const char *pgpass)
|
||||
{
|
||||
|
||||
char *passwd,
|
||||
@@ -280,9 +281,47 @@ crypt_verify(const Port *port, const char *user, const char *pgpass)
|
||||
* Compare with the encrypted or plain password depending on the
|
||||
* authentication method being used for this connection.
|
||||
*/
|
||||
switch (port->auth_method)
|
||||
{
|
||||
case uaCrypt:
|
||||
crypt_pwd = crypt(passwd, port->salt);
|
||||
break;
|
||||
case uaMD5:
|
||||
crypt_pwd = palloc(MD5_PASSWD_LEN+1);
|
||||
|
||||
crypt_pwd =
|
||||
(port->auth_method == uaCrypt ? crypt(passwd, port->salt) : passwd);
|
||||
if (isMD5(passwd))
|
||||
{
|
||||
if (!EncryptMD5(passwd + strlen("md5"),
|
||||
(char *)port->salt, crypt_pwd))
|
||||
{
|
||||
pfree(crypt_pwd);
|
||||
return STATUS_ERROR;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
char *crypt_pwd2 = palloc(MD5_PASSWD_LEN+1);
|
||||
|
||||
if (!EncryptMD5(passwd, port->user, crypt_pwd2))
|
||||
{
|
||||
pfree(crypt_pwd);
|
||||
pfree(crypt_pwd2);
|
||||
return STATUS_ERROR;
|
||||
}
|
||||
if (!EncryptMD5(crypt_pwd2 + strlen("md5"), port->salt,
|
||||
crypt_pwd))
|
||||
{
|
||||
pfree(crypt_pwd);
|
||||
pfree(crypt_pwd2);
|
||||
return STATUS_ERROR;
|
||||
}
|
||||
pfree(crypt_pwd2);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
crypt_pwd = passwd;
|
||||
break;
|
||||
}
|
||||
|
||||
if (!strcmp(pgpass, crypt_pwd))
|
||||
{
|
||||
@@ -302,9 +341,11 @@ crypt_verify(const Port *port, const char *user, const char *pgpass)
|
||||
retval = STATUS_OK;
|
||||
}
|
||||
|
||||
pfree((void *) passwd);
|
||||
pfree(passwd);
|
||||
if (valuntil)
|
||||
pfree((void *) valuntil);
|
||||
pfree(valuntil);
|
||||
if (port->auth_method == uaMD5)
|
||||
pfree(crypt_pwd);
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
@@ -10,7 +10,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/libpq/hba.c,v 1.61 2001/08/02 14:39:35 tgl Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/libpq/hba.c,v 1.62 2001/08/15 18:42:15 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@@ -203,8 +203,8 @@ free_lines(List **lines)
|
||||
* *error_p. line points to the next token of the line.
|
||||
*/
|
||||
static void
|
||||
parse_hba_auth(List *line, UserAuth *userauth_p, char *auth_arg,
|
||||
bool *error_p)
|
||||
parse_hba_auth(List *line, ProtocolVersion proto, UserAuth *userauth_p,
|
||||
char *auth_arg, bool *error_p)
|
||||
{
|
||||
char *token;
|
||||
|
||||
@@ -227,7 +227,15 @@ parse_hba_auth(List *line, UserAuth *userauth_p, char *auth_arg,
|
||||
else if (strcmp(token, "reject") == 0)
|
||||
*userauth_p = uaReject;
|
||||
else if (strcmp(token, "crypt") == 0)
|
||||
*userauth_p = uaCrypt;
|
||||
{
|
||||
/* if the client supports it, use MD5 */
|
||||
if (PG_PROTOCOL_MAJOR(proto) > 2 ||
|
||||
(PG_PROTOCOL_MAJOR(proto) == 2 &&
|
||||
PG_PROTOCOL_MINOR(proto) >= 1))
|
||||
*userauth_p = uaMD5;
|
||||
else
|
||||
*userauth_p = uaCrypt;
|
||||
}
|
||||
else
|
||||
*error_p = true;
|
||||
line = lnext(line);
|
||||
@@ -285,7 +293,8 @@ parse_hba(List *line, hbaPort *port, bool *found_p, bool *error_p)
|
||||
line = lnext(line);
|
||||
if (!line)
|
||||
goto hba_syntax;
|
||||
parse_hba_auth(line, &port->auth_method, port->auth_arg, error_p);
|
||||
parse_hba_auth(line, port->proto, &port->auth_method,
|
||||
port->auth_arg, error_p);
|
||||
if (*error_p)
|
||||
goto hba_syntax;
|
||||
|
||||
@@ -354,7 +363,8 @@ parse_hba(List *line, hbaPort *port, bool *found_p, bool *error_p)
|
||||
line = lnext(line);
|
||||
if (!line)
|
||||
goto hba_syntax;
|
||||
parse_hba_auth(line, &port->auth_method, port->auth_arg, error_p);
|
||||
parse_hba_auth(line, port->proto, &port->auth_method,
|
||||
port->auth_arg, error_p);
|
||||
if (*error_p)
|
||||
goto hba_syntax;
|
||||
|
||||
|
@@ -2,7 +2,7 @@
|
||||
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
|
||||
* Portions Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
* $Id: password.c,v 1.37 2001/06/18 16:11:30 momjian Exp $
|
||||
* $Id: password.c,v 1.38 2001/08/15 18:42:15 momjian Exp $
|
||||
*
|
||||
*/
|
||||
|
||||
@@ -82,11 +82,14 @@ verify_password(const Port *port, const char *user, const char *password)
|
||||
* the current code needs non-encrypted passwords to
|
||||
* encrypt with a random salt.
|
||||
*/
|
||||
if (port->auth_method == uaCrypt
|
||||
|| test_pw == NULL || test_pw[0] == '\0'
|
||||
|| strcmp(test_pw, "+") == 0)
|
||||
return crypt_verify(port, user, password);
|
||||
if (port->auth_method == uaCrypt ||
|
||||
port->auth_method == uaMD5 ||
|
||||
test_pw == NULL ||
|
||||
test_pw[0] == '\0' ||
|
||||
strcmp(test_pw, "+") == 0)
|
||||
return md5_crypt_verify(port, user, password);
|
||||
|
||||
/* external password file is crypt-only */
|
||||
if (strcmp(crypt(password, test_pw), test_pw) == 0)
|
||||
{
|
||||
/* it matched. */
|
||||
|
@@ -3,7 +3,6 @@
|
||||
#
|
||||
#
|
||||
# This file controls:
|
||||
#
|
||||
# o which hosts are allowed to connect
|
||||
# o how users are authenticated on each host
|
||||
# o databases accessible by each host
|
||||
@@ -24,7 +23,6 @@
|
||||
# ============
|
||||
#
|
||||
# There are three types of records:
|
||||
#
|
||||
# o host
|
||||
# o hostssl
|
||||
# o local
|
||||
@@ -40,7 +38,6 @@
|
||||
# host DBNAME IP_ADDRESS ADDRESS_MASK AUTH_TYPE [AUTH_ARGUMENT]
|
||||
#
|
||||
# DBNAME can be:
|
||||
#
|
||||
# o the name of a PostgreSQL database
|
||||
# o "all" to indicate all databases
|
||||
# o "sameuser" to allow access only to databases with the same
|
||||
@@ -80,7 +77,6 @@
|
||||
# allowed only if this record type appears.
|
||||
#
|
||||
# Format:
|
||||
#
|
||||
# local DBNAME AUTH_TYPE [AUTH_ARGUMENT]
|
||||
#
|
||||
# This format is identical to the "host" record type except the IP_ADDRESS
|
||||
@@ -219,4 +215,3 @@
|
||||
|
||||
local all trust
|
||||
host all 127.0.0.1 255.255.255.255 trust
|
||||
|
||||
|
Reference in New Issue
Block a user