1 /* 2 * PgBouncer - Lightweight connection pooler for PostgreSQL. 3 * 4 * Copyright (c) 2007-2009 Marko Kreen, Skype Technologies OÜ 5 * 6 * Permission to use, copy, modify, and/or distribute this software for any 7 * purpose with or without fee is hereby granted, provided that the above 8 * copyright notice and this permission notice appear in all copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 17 */ 18 19 /* 20 * SCRAM support 21 */ 22 23 #include <usual/crypto/sha256.h> 24 25 void free_scram_state(ScramState *scram_state); 26 27 typedef enum PasswordType 28 { 29 PASSWORD_TYPE_PLAINTEXT = 0, 30 PASSWORD_TYPE_MD5, 31 PASSWORD_TYPE_SCRAM_SHA_256 32 } PasswordType; 33 34 PasswordType get_password_type(const char *shadow_pass); 35 36 /* 37 * Functions for communicating as a client with the server 38 */ 39 40 char *build_client_first_message(ScramState *scram_state); 41 char *build_client_final_message(ScramState *scram_state, 42 const PgUser *user, 43 const char *server_nonce, 44 const char *salt, 45 int saltlen, 46 int iterations); 47 48 bool read_server_first_message(PgSocket *server, char *input, 49 char **server_nonce_p, char **salt_p, int *saltlen_p, int *iterations_p); 50 bool read_server_final_message(PgSocket *server, char *input, char *ServerSignature); 51 52 bool verify_server_signature(ScramState *scram_state, const PgUser *user, const char *ServerSignature); 53 54 55 /* 56 * Functions for communicating as a server to the client 57 */ 58 59 bool read_client_first_message(PgSocket *client, char *input, 60 char *cbind_flag_p, 61 char **client_first_message_bare_p, 62 char **client_nonce_p); 63 64 bool read_client_final_message(PgSocket *client, const uint8_t *raw_input, char *input, 65 const char **client_final_nonce_p, 66 char **proof_p); 67 68 char *build_server_first_message(ScramState *scram_state, 69 const char *username, const char *stored_secret); 70 71 char *build_server_final_message(ScramState *scram_state); 72 73 bool verify_final_nonce(const ScramState *scram_state, const char *client_final_nonce); 74 75 bool verify_client_proof(ScramState *state, const char *ClientProof); 76 77 bool scram_verify_plain_password(PgSocket *client, 78 const char *username, const char *password, 79 const char *verifier); 80