This commit is contained in:
blue-lemon0104
2026-04-07 13:35:22 +08:00
commit 0120fa9ce3
1530 changed files with 424864 additions and 0 deletions

29
db_include/libpq/auth.h Executable file
View File

@@ -0,0 +1,29 @@
/*-------------------------------------------------------------------------
*
* auth.h
* Definitions for network authentication routines
*
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/auth.h
*
*-------------------------------------------------------------------------
*/
#ifndef AUTH_H
#define AUTH_H
#include "libpq/libpq-be.h"
extern char *pg_krb_server_keyfile;
extern bool pg_krb_caseins_users;
extern char *pg_krb_realm;
extern void ClientAuthentication(Port *port);
/* Hook for plugins to get control in ClientAuthentication() */
typedef void (*ClientAuthentication_hook_type) (Port *, int);
extern PGDLLIMPORT ClientAuthentication_hook_type ClientAuthentication_hook;
#endif /* AUTH_H */

32
db_include/libpq/be-fsstubs.h Executable file
View File

@@ -0,0 +1,32 @@
/*-------------------------------------------------------------------------
*
* be-fsstubs.h
*
*
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/be-fsstubs.h
*
*-------------------------------------------------------------------------
*/
#ifndef BE_FSSTUBS_H
#define BE_FSSTUBS_H
/*
* These are not fmgr-callable, but are available to C code.
* Probably these should have had the underscore-free names,
* but too late now...
*/
extern int lo_read(int fd, char *buf, int len);
extern int lo_write(int fd, const char *buf, int len);
/*
* Cleanup LOs at xact commit/abort
*/
extern void AtEOXact_LargeObject(bool isCommit);
extern void AtEOSubXact_LargeObject(bool isCommit, SubTransactionId mySubid,
SubTransactionId parentSubid);
#endif /* BE_FSSTUBS_H */

View File

@@ -0,0 +1,30 @@
/*-------------------------------------------------------------------------
*
* be-gssapi-common.h
* Definitions for GSSAPI authentication and encryption handling
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/be-gssapi-common.h
*
*-------------------------------------------------------------------------
*/
#ifndef BE_GSSAPI_COMMON_H
#define BE_GSSAPI_COMMON_H
#ifdef ENABLE_GSS
#if defined(HAVE_GSSAPI_H)
#include <gssapi.h>
#else
#include <gssapi/gssapi.h>
#endif
extern void pg_GSS_error(const char *errmsg,
OM_uint32 maj_stat, OM_uint32 min_stat);
#endif /* ENABLE_GSS */
#endif /* BE_GSSAPI_COMMON_H */

46
db_include/libpq/crypt.h Executable file
View File

@@ -0,0 +1,46 @@
/*-------------------------------------------------------------------------
*
* crypt.h
* Interface to libpq/crypt.c
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/crypt.h
*
*-------------------------------------------------------------------------
*/
#ifndef PG_CRYPT_H
#define PG_CRYPT_H
#include "datatype/timestamp.h"
/*
* Types of password hashes or secrets.
*
* Plaintext passwords can be passed in by the user, in a CREATE/ALTER USER
* command. They will be encrypted to MD5 or SCRAM-SHA-256 format, before
* storing on-disk, so only MD5 and SCRAM-SHA-256 passwords should appear
* in pg_authid.rolpassword. They are also the allowed values for the
* password_encryption GUC.
*/
typedef enum PasswordType
{
PASSWORD_TYPE_PLAINTEXT = 0,
PASSWORD_TYPE_MD5,
PASSWORD_TYPE_SCRAM_SHA_256
} PasswordType;
extern PasswordType get_password_type(const char *shadow_pass);
extern char *encrypt_password(PasswordType target_type, const char *role,
const char *password);
extern char *get_role_password(const char *role, char **logdetail);
extern int md5_crypt_verify(const char *role, const char *shadow_pass,
const char *client_pass, const char *md5_salt,
int md5_salt_len, char **logdetail);
extern int plain_crypt_verify(const char *role, const char *shadow_pass,
const char *client_pass, char **logdetail);
#endif

147
db_include/libpq/hba.h Executable file
View File

@@ -0,0 +1,147 @@
/*-------------------------------------------------------------------------
*
* hba.h
* Interface to hba.c
*
*
* src/include/libpq/hba.h
*
*-------------------------------------------------------------------------
*/
#ifndef HBA_H
#define HBA_H
#include "libpq/pqcomm.h" /* pgrminclude ignore */ /* needed for NetBSD */
#include "nodes/pg_list.h"
#include "regex/regex.h"
/*
* The following enum represents the authentication methods that
* are supported by PostgreSQL.
*
* Note: keep this in sync with the UserAuthName array in hba.c.
*/
typedef enum UserAuth
{
uaReject,
uaImplicitReject, /* Not a user-visible option */
uaTrust,
uaIdent,
uaPassword,
uaMD5,
uaSCRAM,
uaGSS,
uaSSPI,
uaPAM,
uaBSD,
uaLDAP,
uaCert,
uaRADIUS,
uaPeer
#define USER_AUTH_LAST uaPeer /* Must be last value of this enum */
} UserAuth;
/*
* Data structures representing pg_hba.conf entries
*/
typedef enum IPCompareMethod
{
ipCmpMask,
ipCmpSameHost,
ipCmpSameNet,
ipCmpAll
} IPCompareMethod;
typedef enum ConnType
{
ctLocal,
ctHost,
ctHostSSL,
ctHostNoSSL,
ctHostGSS,
ctHostNoGSS,
} ConnType;
typedef enum ClientCertMode
{
clientCertOff,
clientCertCA,
clientCertFull
} ClientCertMode;
typedef enum ClientCertName
{
clientCertCN,
clientCertDN
} ClientCertName;
typedef struct HbaLine
{
int linenumber;
char *rawline;
ConnType conntype;
List *databases;
List *roles;
struct sockaddr_storage addr;
int addrlen; /* zero if we don't have a valid addr */
struct sockaddr_storage mask;
int masklen; /* zero if we don't have a valid mask */
IPCompareMethod ip_cmp_method;
char *hostname;
UserAuth auth_method;
char *usermap;
char *pamservice;
bool pam_use_hostname;
bool ldaptls;
char *ldapscheme;
char *ldapserver;
int ldapport;
char *ldapbinddn;
char *ldapbindpasswd;
char *ldapsearchattribute;
char *ldapsearchfilter;
char *ldapbasedn;
int ldapscope;
char *ldapprefix;
char *ldapsuffix;
ClientCertMode clientcert;
ClientCertName clientcertname;
char *krb_realm;
bool include_realm;
bool compat_realm;
bool upn_username;
List *radiusservers;
char *radiusservers_s;
List *radiussecrets;
char *radiussecrets_s;
List *radiusidentifiers;
char *radiusidentifiers_s;
List *radiusports;
char *radiusports_s;
} HbaLine;
typedef struct IdentLine
{
int linenumber;
char *usermap;
char *ident_user;
char *pg_role;
regex_t re;
} IdentLine;
/* kluge to avoid including libpq/libpq-be.h here */
typedef struct Port hbaPort;
extern bool load_hba(void);
extern bool load_ident(void);
extern const char *hba_authname(UserAuth auth_method);
extern void hba_getauthmethod(hbaPort *port);
extern int check_usermap(const char *usermap_name,
const char *pg_role, const char *auth_user,
bool case_sensitive);
extern bool pg_isblank(const char c);
#endif /* HBA_H */

30
db_include/libpq/ifaddr.h Executable file
View File

@@ -0,0 +1,30 @@
/*-------------------------------------------------------------------------
*
* ifaddr.h
* IP netmask calculations, and enumerating network interfaces.
*
* Copyright (c) 2003-2021, PostgreSQL Global Development Group
*
* src/include/libpq/ifaddr.h
*
*-------------------------------------------------------------------------
*/
#ifndef IFADDR_H
#define IFADDR_H
#include "libpq/pqcomm.h" /* pgrminclude ignore */
typedef void (*PgIfAddrCallback) (struct sockaddr *addr,
struct sockaddr *netmask,
void *cb_data);
extern int pg_range_sockaddr(const struct sockaddr_storage *addr,
const struct sockaddr_storage *netaddr,
const struct sockaddr_storage *netmask);
extern int pg_sockaddr_cidr_mask(struct sockaddr_storage *mask,
char *numbits, int family);
extern int pg_foreach_ifaddr(PgIfAddrCallback callback, void *cb_data);
#endif /* IFADDR_H */

344
db_include/libpq/libpq-be.h Executable file
View File

@@ -0,0 +1,344 @@
/*-------------------------------------------------------------------------
*
* libpq-be.h
* This file contains definitions for structures and externs used
* by the postmaster during client authentication.
*
* Note that this is backend-internal and is NOT exported to clients.
* Structs that need to be client-visible are in pqcomm.h.
*
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/libpq-be.h
*
*-------------------------------------------------------------------------
*/
#ifndef LIBPQ_BE_H
#define LIBPQ_BE_H
#include <sys/time.h>
#ifdef USE_OPENSSL
#include <openssl/ssl.h>
#include <openssl/err.h>
#endif
#ifdef HAVE_NETINET_TCP_H
#include <netinet/tcp.h>
#endif
#ifdef ENABLE_GSS
#if defined(HAVE_GSSAPI_H)
#include <gssapi.h>
#else
#include <gssapi/gssapi.h>
#endif /* HAVE_GSSAPI_H */
/*
* GSSAPI brings in headers that set a lot of things in the global namespace on win32,
* that doesn't match the msvc build. It gives a bunch of compiler warnings that we ignore,
* but also defines a symbol that simply does not exist. Undefine it again.
*/
#ifdef _MSC_VER
#undef HAVE_GETADDRINFO
#endif
#endif /* ENABLE_GSS */
#ifdef ENABLE_SSPI
#define SECURITY_WIN32
#if defined(WIN32) && !defined(_MSC_VER)
#include <ntsecapi.h>
#endif
#include <security.h>
#undef SECURITY_WIN32
#ifndef ENABLE_GSS
/*
* Define a fake structure compatible with GSSAPI on Unix.
*/
typedef struct
{
void *value;
int length;
} gss_buffer_desc;
#endif
#endif /* ENABLE_SSPI */
#include "datatype/timestamp.h"
#include "libpq/hba.h"
#include "libpq/pqcomm.h"
typedef enum CAC_state
{
CAC_OK,
CAC_STARTUP,
CAC_SHUTDOWN,
CAC_RECOVERY,
CAC_NOTCONSISTENT,
CAC_TOOMANY,
CAC_SUPERUSER
} CAC_state;
/*
* GSSAPI specific state information
*/
#if defined(ENABLE_GSS) | defined(ENABLE_SSPI)
typedef struct
{
gss_buffer_desc outbuf; /* GSSAPI output token buffer */
#ifdef ENABLE_GSS
gss_cred_id_t cred; /* GSSAPI connection cred's */
gss_ctx_id_t ctx; /* GSSAPI connection context */
gss_name_t name; /* GSSAPI client name */
char *princ; /* GSSAPI Principal used for auth, NULL if
* GSSAPI auth was not used */
bool auth; /* GSSAPI Authentication used */
bool enc; /* GSSAPI encryption in use */
#endif
} pg_gssinfo;
#endif
/*
* This is used by the postmaster in its communication with frontends. It
* contains all state information needed during this communication before the
* backend is run. The Port structure is kept in malloc'd memory and is
* still available when a backend is running (see MyProcPort). The data
* it points to must also be malloc'd, or else palloc'd in TopMemoryContext,
* so that it survives into PostgresMain execution!
*
* remote_hostname is set if we did a successful reverse lookup of the
* client's IP address during connection setup.
* remote_hostname_resolv tracks the state of hostname verification:
* +1 = remote_hostname is known to resolve to client's IP address
* -1 = remote_hostname is known NOT to resolve to client's IP address
* 0 = we have not done the forward DNS lookup yet
* -2 = there was an error in name resolution
* If reverse lookup of the client IP address fails, remote_hostname will be
* left NULL while remote_hostname_resolv is set to -2. If reverse lookup
* succeeds but forward lookup fails, remote_hostname_resolv is also set to -2
* (the case is distinguishable because remote_hostname isn't NULL). In
* either of the -2 cases, remote_hostname_errcode saves the lookup return
* code for possible later use with gai_strerror.
*/
typedef struct Port
{
pgsocket sock; /* File descriptor */
bool noblock; /* is the socket in non-blocking mode? */
ProtocolVersion proto; /* FE/BE protocol version */
SockAddr laddr; /* local addr (postmaster) */
SockAddr raddr; /* remote addr (client) */
char *remote_host; /* name (or ip addr) of remote host */
char *remote_hostname; /* name (not ip addr) of remote host, if
* available */
int remote_hostname_resolv; /* see above */
int remote_hostname_errcode; /* see above */
char *remote_port; /* text rep of remote port */
CAC_state canAcceptConnections; /* postmaster connection status */
/*
* Information that needs to be saved from the startup packet and passed
* into backend execution. "char *" fields are NULL if not set.
* guc_options points to a List of alternating option names and values.
*/
char *database_name;
char *user_name;
char *cmdline_options;
List *guc_options;
/*
* The startup packet application name, only used here for the "connection
* authorized" log message. We shouldn't use this post-startup, instead
* the GUC should be used as application can change it afterward.
*/
char *application_name;
/*
* Information that needs to be held during the authentication cycle.
*/
HbaLine *hba;
/*
* Authenticated identity. The meaning of this identifier is dependent on
* hba->auth_method; it is the identity (if any) that the user presented
* during the authentication cycle, before they were assigned a database
* role. (It is effectively the "SYSTEM-USERNAME" of a pg_ident usermap
* -- though the exact string in use may be different, depending on pg_hba
* options.)
*
* authn_id is NULL if the user has not actually been authenticated, for
* example if the "trust" auth method is in use.
*/
const char *authn_id;
/*
* TCP keepalive and user timeout settings.
*
* default values are 0 if AF_UNIX or not yet known; current values are 0
* if AF_UNIX or using the default. Also, -1 in a default value means we
* were unable to find out the default (getsockopt failed).
*/
int default_keepalives_idle;
int default_keepalives_interval;
int default_keepalives_count;
int default_tcp_user_timeout;
int keepalives_idle;
int keepalives_interval;
int keepalives_count;
int tcp_user_timeout;
/*
* GSSAPI structures.
*/
#if defined(ENABLE_GSS) || defined(ENABLE_SSPI)
/*
* If GSSAPI is supported and used on this connection, store GSSAPI
* information. Even when GSSAPI is not compiled in, store a NULL pointer
* to keep struct offsets the same (for extension ABI compatibility).
*/
pg_gssinfo *gss;
#else
void *gss;
#endif
/*
* SSL structures.
*/
bool ssl_in_use;
char *peer_cn;
char *peer_dn;
bool peer_cert_valid;
/*
* OpenSSL structures. (Keep these last so that the locations of other
* fields are the same whether or not you build with SSL enabled.)
*/
#ifdef USE_OPENSSL
SSL *ssl;
X509 *peer;
#endif
} Port;
#ifdef USE_SSL
/*
* Hardcoded DH parameters, used in ephemeral DH keying. (See also
* README.SSL for more details on EDH.)
*
* This is the 2048-bit DH parameter from RFC 3526. The generation of the
* prime is specified in RFC 2412 Appendix E, which also discusses the
* design choice of the generator. Note that when loaded with OpenSSL
* this causes DH_check() to fail on DH_NOT_SUITABLE_GENERATOR, where
* leaking a bit is preferred.
*/
#define FILE_DH2048 \
"-----BEGIN DH PARAMETERS-----\n\
MIIBCAKCAQEA///////////JD9qiIWjCNMTGYouA3BzRKQJOCIpnzHQCC76mOxOb\n\
IlFKCHmONATd75UZs806QxswKwpt8l8UN0/hNW1tUcJF5IW1dmJefsb0TELppjft\n\
awv/XLb0Brft7jhr+1qJn6WunyQRfEsf5kkoZlHs5Fs9wgB8uKFjvwWY2kg2HFXT\n\
mmkWP6j9JM9fg2VdI9yjrZYcYvNWIIVSu57VKQdwlpZtZww1Tkq8mATxdGwIyhgh\n\
fDKQXkYuNs474553LBgOhgObJ4Oi7Aeij7XFXfBvTFLJ3ivL9pVYFxg5lUl86pVq\n\
5RXSJhiY+gUQFXKOWoqsqmj//////////wIBAg==\n\
-----END DH PARAMETERS-----\n"
/*
* These functions are implemented by the glue code specific to each
* SSL implementation (e.g. be-secure-openssl.c)
*/
/*
* Initialize global SSL context.
*
* If isServerStart is true, report any errors as FATAL (so we don't return).
* Otherwise, log errors at LOG level and return -1 to indicate trouble,
* preserving the old SSL state if any. Returns 0 if OK.
*/
extern int be_tls_init(bool isServerStart);
/*
* Destroy global SSL context, if any.
*/
extern void be_tls_destroy(void);
/*
* Attempt to negotiate SSL connection.
*/
extern int be_tls_open_server(Port *port);
/*
* Close SSL connection.
*/
extern void be_tls_close(Port *port);
/*
* Read data from a secure connection.
*/
extern ssize_t be_tls_read(Port *port, void *ptr, size_t len, int *waitfor);
/*
* Write data to a secure connection.
*/
extern ssize_t be_tls_write(Port *port, void *ptr, size_t len, int *waitfor);
/*
* Return information about the SSL connection.
*/
extern int be_tls_get_cipher_bits(Port *port);
extern const char *be_tls_get_version(Port *port);
extern const char *be_tls_get_cipher(Port *port);
extern void be_tls_get_peer_subject_name(Port *port, char *ptr, size_t len);
extern void be_tls_get_peer_issuer_name(Port *port, char *ptr, size_t len);
extern void be_tls_get_peer_serial(Port *port, char *ptr, size_t len);
/*
* Get the server certificate hash for SCRAM channel binding type
* tls-server-end-point.
*
* The result is a palloc'd hash of the server certificate with its
* size, and NULL if there is no certificate available.
*
* This is not supported with old versions of OpenSSL that don't have
* the X509_get_signature_nid() function.
*/
#if defined(USE_OPENSSL) && defined(HAVE_X509_GET_SIGNATURE_NID)
#define HAVE_BE_TLS_GET_CERTIFICATE_HASH
extern char *be_tls_get_certificate_hash(Port *port, size_t *len);
#endif
/* init hook for SSL, the default sets the password callback if appropriate */
#ifdef USE_OPENSSL
typedef void (*openssl_tls_init_hook_typ) (SSL_CTX *context, bool isServerStart);
extern PGDLLIMPORT openssl_tls_init_hook_typ openssl_tls_init_hook;
#endif
#endif /* USE_SSL */
#ifdef ENABLE_GSS
/*
* Return information about the GSSAPI authenticated connection
*/
extern bool be_gssapi_get_auth(Port *port);
extern bool be_gssapi_get_enc(Port *port);
extern const char *be_gssapi_get_princ(Port *port);
/* Read and write to a GSSAPI-encrypted connection. */
extern ssize_t be_gssapi_read(Port *port, void *ptr, size_t len);
extern ssize_t be_gssapi_write(Port *port, void *ptr, size_t len);
#endif /* ENABLE_GSS */
extern ProtocolVersion FrontendProtocol;
/* TCP keepalives configuration. These are no-ops on an AF_UNIX socket. */
extern int pq_getkeepalivesidle(Port *port);
extern int pq_getkeepalivesinterval(Port *port);
extern int pq_getkeepalivescount(Port *port);
extern int pq_gettcpusertimeout(Port *port);
extern int pq_setkeepalivesidle(int idle, Port *port);
extern int pq_setkeepalivesinterval(int interval, Port *port);
extern int pq_setkeepalivescount(int count, Port *port);
extern int pq_settcpusertimeout(int timeout, Port *port);
#endif /* LIBPQ_BE_H */

24
db_include/libpq/libpq-fs.h Executable file
View File

@@ -0,0 +1,24 @@
/*-------------------------------------------------------------------------
*
* libpq-fs.h
* definitions for using Inversion file system routines (ie, large objects)
*
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/libpq-fs.h
*
*-------------------------------------------------------------------------
*/
#ifndef LIBPQ_FS_H
#define LIBPQ_FS_H
/*
* Read/write mode flags for inversion (large object) calls
*/
#define INV_WRITE 0x00020000
#define INV_READ 0x00040000
#endif /* LIBPQ_FS_H */

143
db_include/libpq/libpq.h Executable file
View File

@@ -0,0 +1,143 @@
/*-------------------------------------------------------------------------
*
* libpq.h
* POSTGRES LIBPQ buffer structure definitions.
*
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/libpq.h
*
*-------------------------------------------------------------------------
*/
#ifndef LIBPQ_H
#define LIBPQ_H
#include <netinet/in.h>
#include "lib/stringinfo.h"
#include "libpq/libpq-be.h"
#include "storage/latch.h"
/*
* Callers of pq_getmessage() must supply a maximum expected message size.
* By convention, if there's not any specific reason to use another value,
* use PQ_SMALL_MESSAGE_LIMIT for messages that shouldn't be too long, and
* PQ_LARGE_MESSAGE_LIMIT for messages that can be long.
*/
#define PQ_SMALL_MESSAGE_LIMIT 10000
#define PQ_LARGE_MESSAGE_LIMIT (MaxAllocSize - 1)
typedef struct
{
void (*comm_reset) (void);
int (*flush) (void);
int (*flush_if_writable) (void);
bool (*is_send_pending) (void);
int (*putmessage) (char msgtype, const char *s, size_t len);
void (*putmessage_noblock) (char msgtype, const char *s, size_t len);
} PQcommMethods;
extern const PGDLLIMPORT PQcommMethods *PqCommMethods;
#define pq_comm_reset() (PqCommMethods->comm_reset())
#define pq_flush() (PqCommMethods->flush())
#define pq_flush_if_writable() (PqCommMethods->flush_if_writable())
#define pq_is_send_pending() (PqCommMethods->is_send_pending())
#define pq_putmessage(msgtype, s, len) \
(PqCommMethods->putmessage(msgtype, s, len))
#define pq_putmessage_noblock(msgtype, s, len) \
(PqCommMethods->putmessage_noblock(msgtype, s, len))
/*
* External functions.
*/
/*
* prototypes for functions in pqcomm.c
*/
extern WaitEventSet *FeBeWaitSet;
#define FeBeWaitSetSocketPos 0
#define FeBeWaitSetLatchPos 1
extern int StreamServerPort(int family, const char *hostName,
unsigned short portNumber, const char *unixSocketDir,
pgsocket ListenSocket[], int MaxListen);
extern int StreamConnection(pgsocket server_fd, Port *port);
extern void StreamClose(pgsocket sock);
extern void TouchSocketFiles(void);
extern void RemoveSocketFiles(void);
extern void pq_init(void);
extern int pq_getbytes(char *s, size_t len);
extern void pq_startmsgread(void);
extern void pq_endmsgread(void);
extern bool pq_is_reading_msg(void);
extern int pq_getmessage(StringInfo s, int maxlen);
extern int pq_getbyte(void);
extern int pq_peekbyte(void);
extern int pq_getbyte_if_available(unsigned char *c);
extern bool pq_buffer_has_data(void);
extern int pq_putmessage_v2(char msgtype, const char *s, size_t len);
extern bool pq_check_connection(void);
/*
* prototypes for functions in be-secure.c
*/
extern char *ssl_library;
extern char *ssl_cert_file;
extern char *ssl_key_file;
extern char *ssl_ca_file;
extern char *ssl_crl_file;
extern char *ssl_crl_dir;
extern char *ssl_dh_params_file;
extern PGDLLIMPORT char *ssl_passphrase_command;
extern PGDLLIMPORT bool ssl_passphrase_command_supports_reload;
#ifdef USE_SSL
extern bool ssl_loaded_verify_locations;
#endif
extern int secure_initialize(bool isServerStart);
extern bool secure_loaded_verify_locations(void);
extern void secure_destroy(void);
extern int secure_open_server(Port *port);
extern void secure_close(Port *port);
extern ssize_t secure_read(Port *port, void *ptr, size_t len);
extern ssize_t secure_write(Port *port, void *ptr, size_t len);
extern ssize_t secure_raw_read(Port *port, void *ptr, size_t len);
extern ssize_t secure_raw_write(Port *port, const void *ptr, size_t len);
/*
* prototypes for functions in be-secure-gssapi.c
*/
#ifdef ENABLE_GSS
extern ssize_t secure_open_gssapi(Port *port);
#endif
/* GUCs */
extern char *SSLCipherSuites;
extern char *SSLECDHCurve;
extern bool SSLPreferServerCiphers;
extern int ssl_min_protocol_version;
extern int ssl_max_protocol_version;
enum ssl_protocol_versions
{
PG_TLS_ANY = 0,
PG_TLS1_VERSION,
PG_TLS1_1_VERSION,
PG_TLS1_2_VERSION,
PG_TLS1_3_VERSION,
};
/*
* prototypes for functions in be-secure-common.c
*/
extern int run_ssl_passphrase_command(const char *prompt, bool is_server_start,
char *buf, int size);
extern bool check_ssl_key_file_permissions(const char *ssl_key_file,
bool isServerStart);
#endif /* LIBPQ_H */

194
db_include/libpq/pqcomm.h Executable file
View File

@@ -0,0 +1,194 @@
/*-------------------------------------------------------------------------
*
* pqcomm.h
* Definitions common to frontends and backends.
*
* NOTE: for historical reasons, this does not correspond to pqcomm.c.
* pqcomm.c's routines are declared in libpq.h.
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/pqcomm.h
*
*-------------------------------------------------------------------------
*/
#ifndef PQCOMM_H
#define PQCOMM_H
#include <sys/socket.h>
#include <netdb.h>
#ifdef HAVE_SYS_UN_H
#include <sys/un.h>
#endif
#include <netinet/in.h>
#ifdef HAVE_STRUCT_SOCKADDR_STORAGE
#ifndef HAVE_STRUCT_SOCKADDR_STORAGE_SS_FAMILY
#ifdef HAVE_STRUCT_SOCKADDR_STORAGE___SS_FAMILY
#define ss_family __ss_family
#else
#error struct sockaddr_storage does not provide an ss_family member
#endif
#endif
#ifdef HAVE_STRUCT_SOCKADDR_STORAGE___SS_LEN
#define ss_len __ss_len
#define HAVE_STRUCT_SOCKADDR_STORAGE_SS_LEN 1
#endif
#else /* !HAVE_STRUCT_SOCKADDR_STORAGE */
/* Define a struct sockaddr_storage if we don't have one. */
struct sockaddr_storage
{
union
{
struct sockaddr sa; /* get the system-dependent fields */
int64 ss_align; /* ensures struct is properly aligned */
char ss_pad[128]; /* ensures struct has desired size */
} ss_stuff;
};
#define ss_family ss_stuff.sa.sa_family
/* It should have an ss_len field if sockaddr has sa_len. */
#ifdef HAVE_STRUCT_SOCKADDR_SA_LEN
#define ss_len ss_stuff.sa.sa_len
#define HAVE_STRUCT_SOCKADDR_STORAGE_SS_LEN 1
#endif
#endif /* HAVE_STRUCT_SOCKADDR_STORAGE */
typedef struct
{
struct sockaddr_storage addr;
ACCEPT_TYPE_ARG3 salen;
} SockAddr;
/* Configure the UNIX socket location for the well known port. */
#define UNIXSOCK_PATH(path, port, sockdir) \
(AssertMacro(sockdir), \
AssertMacro(*(sockdir) != '\0'), \
snprintf(path, sizeof(path), "%s/.s.PGSQL.%d", \
(sockdir), (port)))
/*
* The maximum workable length of a socket path is what will fit into
* struct sockaddr_un. This is usually only 100 or so bytes :-(.
*
* For consistency, always pass a MAXPGPATH-sized buffer to UNIXSOCK_PATH(),
* then complain if the resulting string is >= UNIXSOCK_PATH_BUFLEN bytes.
* (Because the standard API for getaddrinfo doesn't allow it to complain in
* a useful way when the socket pathname is too long, we have to test for
* this explicitly, instead of just letting the subroutine return an error.)
*/
#define UNIXSOCK_PATH_BUFLEN sizeof(((struct sockaddr_un *) NULL)->sun_path)
/*
* A host that looks either like an absolute path or starts with @ is
* interpreted as a Unix-domain socket address.
*/
static inline bool
is_unixsock_path(const char *path)
{
return is_absolute_path(path) || path[0] == '@';
}
/*
* These manipulate the frontend/backend protocol version number.
*
* The major number should be incremented for incompatible changes. The minor
* number should be incremented for compatible changes (eg. additional
* functionality).
*
* If a backend supports version m.n of the protocol it must actually support
* versions m.[0..n]. Backend support for version m-1 can be dropped after a
* `reasonable' length of time.
*
* A frontend isn't required to support anything other than the current
* version.
*/
#define PG_PROTOCOL_MAJOR(v) ((v) >> 16)
#define PG_PROTOCOL_MINOR(v) ((v) & 0x0000ffff)
#define PG_PROTOCOL(m,n) (((m) << 16) | (n))
/*
* The earliest and latest frontend/backend protocol version supported.
* (Only protocol version 3 is currently supported)
*/
#define PG_PROTOCOL_EARLIEST PG_PROTOCOL(3,0)
#define PG_PROTOCOL_LATEST PG_PROTOCOL(3,0)
typedef uint32 ProtocolVersion; /* FE/BE protocol version number */
typedef ProtocolVersion MsgType;
/*
* Packet lengths are 4 bytes in network byte order.
*
* The initial length is omitted from the packet layouts appearing below.
*/
typedef uint32 PacketLen;
extern bool Db_user_namespace;
/*
* In protocol 3.0 and later, the startup packet length is not fixed, but
* we set an arbitrary limit on it anyway. This is just to prevent simple
* denial-of-service attacks via sending enough data to run the server
* out of memory.
*/
#define MAX_STARTUP_PACKET_LENGTH 10000
/* These are the authentication request codes sent by the backend. */
#define AUTH_REQ_OK 0 /* User is authenticated */
#define AUTH_REQ_KRB4 1 /* Kerberos V4. Not supported any more. */
#define AUTH_REQ_KRB5 2 /* Kerberos V5. Not supported any more. */
#define AUTH_REQ_PASSWORD 3 /* Password */
#define AUTH_REQ_CRYPT 4 /* crypt password. Not supported any more. */
#define AUTH_REQ_MD5 5 /* md5 password */
#define AUTH_REQ_SCM_CREDS 6 /* transfer SCM credentials */
#define AUTH_REQ_GSS 7 /* GSSAPI without wrap() */
#define AUTH_REQ_GSS_CONT 8 /* Continue GSS exchanges */
#define AUTH_REQ_SSPI 9 /* SSPI negotiate without wrap() */
#define AUTH_REQ_SASL 10 /* Begin SASL authentication */
#define AUTH_REQ_SASL_CONT 11 /* Continue SASL authentication */
#define AUTH_REQ_SASL_FIN 12 /* Final SASL message */
typedef uint32 AuthRequest;
/*
* A client can also send a cancel-current-operation request to the postmaster.
* This is uglier than sending it directly to the client's backend, but it
* avoids depending on out-of-band communication facilities.
*
* The cancel request code must not match any protocol version number
* we're ever likely to use. This random choice should do.
*/
#define CANCEL_REQUEST_CODE PG_PROTOCOL(1234,5678)
typedef struct CancelRequestPacket
{
/* Note that each field is stored in network byte order! */
MsgType cancelRequestCode; /* code to identify a cancel request */
uint32 backendPID; /* PID of client's backend */
uint32 cancelAuthCode; /* secret key to authorize cancel */
} CancelRequestPacket;
/*
* A client can also start by sending a SSL or GSSAPI negotiation request to
* get a secure channel.
*/
#define NEGOTIATE_SSL_CODE PG_PROTOCOL(1234,5679)
#define NEGOTIATE_GSS_CODE PG_PROTOCOL(1234,5680)
#endif /* PQCOMM_H */

210
db_include/libpq/pqformat.h Executable file
View File

@@ -0,0 +1,210 @@
/*-------------------------------------------------------------------------
*
* pqformat.h
* Definitions for formatting and parsing frontend/backend messages
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/pqformat.h
*
*-------------------------------------------------------------------------
*/
#ifndef PQFORMAT_H
#define PQFORMAT_H
#include "lib/stringinfo.h"
#include "mb/pg_wchar.h"
#include "port/pg_bswap.h"
extern void pq_beginmessage(StringInfo buf, char msgtype);
extern void pq_beginmessage_reuse(StringInfo buf, char msgtype);
extern void pq_endmessage(StringInfo buf);
extern void pq_endmessage_reuse(StringInfo buf);
extern void pq_sendbytes(StringInfo buf, const char *data, int datalen);
extern void pq_sendcountedtext(StringInfo buf, const char *str, int slen,
bool countincludesself);
extern void pq_sendtext(StringInfo buf, const char *str, int slen);
extern void pq_sendstring(StringInfo buf, const char *str);
extern void pq_send_ascii_string(StringInfo buf, const char *str);
extern void pq_sendfloat4(StringInfo buf, float4 f);
extern void pq_sendfloat8(StringInfo buf, float8 f);
/*
* Append a [u]int8 to a StringInfo buffer, which already has enough space
* preallocated.
*
* The use of pg_restrict allows the compiler to optimize the code based on
* the assumption that buf, buf->len, buf->data and *buf->data don't
* overlap. Without the annotation buf->len etc cannot be kept in a register
* over subsequent pq_writeintN calls.
*
* The use of StringInfoData * rather than StringInfo is due to MSVC being
* overly picky and demanding a * before a restrict.
*/
static inline void
pq_writeint8(StringInfoData *pg_restrict buf, uint8 i)
{
uint8 ni = i;
Assert(buf->len + (int) sizeof(uint8) <= buf->maxlen);
memcpy((char *pg_restrict) (buf->data + buf->len), &ni, sizeof(uint8));
buf->len += sizeof(uint8);
}
/*
* Append a [u]int16 to a StringInfo buffer, which already has enough space
* preallocated.
*/
static inline void
pq_writeint16(StringInfoData *pg_restrict buf, uint16 i)
{
uint16 ni = pg_hton16(i);
Assert(buf->len + (int) sizeof(uint16) <= buf->maxlen);
memcpy((char *pg_restrict) (buf->data + buf->len), &ni, sizeof(uint16));
buf->len += sizeof(uint16);
}
/*
* Append a [u]int32 to a StringInfo buffer, which already has enough space
* preallocated.
*/
static inline void
pq_writeint32(StringInfoData *pg_restrict buf, uint32 i)
{
uint32 ni = pg_hton32(i);
Assert(buf->len + (int) sizeof(uint32) <= buf->maxlen);
memcpy((char *pg_restrict) (buf->data + buf->len), &ni, sizeof(uint32));
buf->len += sizeof(uint32);
}
/*
* Append a [u]int64 to a StringInfo buffer, which already has enough space
* preallocated.
*/
static inline void
pq_writeint64(StringInfoData *pg_restrict buf, uint64 i)
{
uint64 ni = pg_hton64(i);
Assert(buf->len + (int) sizeof(uint64) <= buf->maxlen);
memcpy((char *pg_restrict) (buf->data + buf->len), &ni, sizeof(uint64));
buf->len += sizeof(uint64);
}
/*
* Append a null-terminated text string (with conversion) to a buffer with
* preallocated space.
*
* NB: The pre-allocated space needs to be sufficient for the string after
* converting to client encoding.
*
* NB: passed text string must be null-terminated, and so is the data
* sent to the frontend.
*/
static inline void
pq_writestring(StringInfoData *pg_restrict buf, const char *pg_restrict str)
{
int slen = strlen(str);
char *p;
p = pg_server_to_client(str, slen);
if (p != str) /* actual conversion has been done? */
slen = strlen(p);
Assert(buf->len + slen + 1 <= buf->maxlen);
memcpy(((char *pg_restrict) buf->data + buf->len), p, slen + 1);
buf->len += slen + 1;
if (p != str)
pfree(p);
}
/* append a binary [u]int8 to a StringInfo buffer */
static inline void
pq_sendint8(StringInfo buf, uint8 i)
{
enlargeStringInfo(buf, sizeof(uint8));
pq_writeint8(buf, i);
}
/* append a binary [u]int16 to a StringInfo buffer */
static inline void
pq_sendint16(StringInfo buf, uint16 i)
{
enlargeStringInfo(buf, sizeof(uint16));
pq_writeint16(buf, i);
}
/* append a binary [u]int32 to a StringInfo buffer */
static inline void
pq_sendint32(StringInfo buf, uint32 i)
{
enlargeStringInfo(buf, sizeof(uint32));
pq_writeint32(buf, i);
}
/* append a binary [u]int64 to a StringInfo buffer */
static inline void
pq_sendint64(StringInfo buf, uint64 i)
{
enlargeStringInfo(buf, sizeof(uint64));
pq_writeint64(buf, i);
}
/* append a binary byte to a StringInfo buffer */
static inline void
pq_sendbyte(StringInfo buf, uint8 byt)
{
pq_sendint8(buf, byt);
}
/*
* Append a binary integer to a StringInfo buffer
*
* This function is deprecated; prefer use of the functions above.
*/
static inline void
pq_sendint(StringInfo buf, uint32 i, int b)
{
switch (b)
{
case 1:
pq_sendint8(buf, (uint8) i);
break;
case 2:
pq_sendint16(buf, (uint16) i);
break;
case 4:
pq_sendint32(buf, (uint32) i);
break;
default:
elog(ERROR, "unsupported integer size %d", b);
break;
}
}
extern void pq_begintypsend(StringInfo buf);
extern bytea *pq_endtypsend(StringInfo buf);
extern void pq_puttextmessage(char msgtype, const char *str);
extern void pq_putemptymessage(char msgtype);
extern int pq_getmsgbyte(StringInfo msg);
extern unsigned int pq_getmsgint(StringInfo msg, int b);
extern int64 pq_getmsgint64(StringInfo msg);
extern float4 pq_getmsgfloat4(StringInfo msg);
extern float8 pq_getmsgfloat8(StringInfo msg);
extern const char *pq_getmsgbytes(StringInfo msg, int datalen);
extern void pq_copymsgbytes(StringInfo msg, char *buf, int datalen);
extern char *pq_getmsgtext(StringInfo msg, int rawbytes, int *nbytes);
extern const char *pq_getmsgstring(StringInfo msg);
extern const char *pq_getmsgrawstring(StringInfo msg);
extern void pq_getmsgend(StringInfo msg);
#endif /* PQFORMAT_H */

24
db_include/libpq/pqmq.h Executable file
View File

@@ -0,0 +1,24 @@
/*-------------------------------------------------------------------------
*
* pqmq.h
* Use the frontend/backend protocol for communication over a shm_mq
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/pqmq.h
*
*-------------------------------------------------------------------------
*/
#ifndef PQMQ_H
#define PQMQ_H
#include "lib/stringinfo.h"
#include "storage/shm_mq.h"
extern void pq_redirect_to_shm_mq(dsm_segment *seg, shm_mq_handle *mqh);
extern void pq_set_parallel_leader(pid_t pid, BackendId backend_id);
extern void pq_parse_errornotice(StringInfo str, ErrorData *edata);
#endif /* PQMQ_H */

42
db_include/libpq/pqsignal.h Executable file
View File

@@ -0,0 +1,42 @@
/*-------------------------------------------------------------------------
*
* pqsignal.h
* Backend signal(2) support (see also src/port/pqsignal.c)
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/pqsignal.h
*
*-------------------------------------------------------------------------
*/
#ifndef PQSIGNAL_H
#define PQSIGNAL_H
#include <signal.h>
#ifndef WIN32
#define PG_SETMASK(mask) sigprocmask(SIG_SETMASK, mask, NULL)
#else
/* Emulate POSIX sigset_t APIs on Windows */
typedef int sigset_t;
extern int pqsigsetmask(int mask);
#define PG_SETMASK(mask) pqsigsetmask(*(mask))
#define sigemptyset(set) (*(set) = 0)
#define sigfillset(set) (*(set) = ~0)
#define sigaddset(set, signum) (*(set) |= (sigmask(signum)))
#define sigdelset(set, signum) (*(set) &= ~(sigmask(signum)))
#endif /* WIN32 */
extern sigset_t UnBlockSig,
BlockSig,
StartupBlockSig;
extern void pqinitmask(void);
/* pqsigfunc is declared in src/include/port.h */
extern pqsigfunc pqsignal_pm(int signo, pqsigfunc func);
#endif /* PQSIGNAL_H */

37
db_include/libpq/scram.h Executable file
View File

@@ -0,0 +1,37 @@
/*-------------------------------------------------------------------------
*
* scram.h
* Interface to libpq/scram.c
*
* Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* src/include/libpq/scram.h
*
*-------------------------------------------------------------------------
*/
#ifndef PG_SCRAM_H
#define PG_SCRAM_H
#include "lib/stringinfo.h"
#include "libpq/libpq-be.h"
/* Status codes for message exchange */
#define SASL_EXCHANGE_CONTINUE 0
#define SASL_EXCHANGE_SUCCESS 1
#define SASL_EXCHANGE_FAILURE 2
/* Routines dedicated to authentication */
extern void pg_be_scram_get_mechanisms(Port *port, StringInfo buf);
extern void *pg_be_scram_init(Port *port, const char *selected_mech, const char *shadow_pass);
extern int pg_be_scram_exchange(void *opaq, const char *input, int inputlen,
char **output, int *outputlen, char **logdetail);
/* Routines to handle and check SCRAM-SHA-256 secret */
extern char *pg_be_scram_build_secret(const char *password);
extern bool parse_scram_secret(const char *secret, int *iterations, char **salt,
uint8 *stored_key, uint8 *server_key);
extern bool scram_verify_plain_password(const char *username,
const char *password, const char *secret);
#endif /* PG_SCRAM_H */