Signed-off-by: Angus Salkeld <asalk...@redhat.com> --- exec/coroipcs.c | 50 +++++++++++++++++++++++++++++++------------------- exec/main.c | 4 +++- exec/util.h | 21 +++++++++++++++++++++ lib/util.h | 6 ++++++ 4 files changed, 61 insertions(+), 20 deletions(-)
diff --git a/exec/coroipcs.c b/exec/coroipcs.c index aca9053..c3cf566 100644 --- a/exec/coroipcs.c +++ b/exec/coroipcs.c @@ -85,6 +85,7 @@ #else #include <sys/sem.h> #endif +#include "util.h" #ifndef MSG_NOSIGNAL #define MSG_NOSIGNAL 0 @@ -761,14 +762,14 @@ retry_send: return (0); } -static int +static cs_error_t req_setup_recv ( struct conn_info *conn_info) { int res; struct msghdr msg_recv; struct iovec iov_recv; - int authenticated = 0; + cs_error_t auth_res = CS_ERR_LIBRARY; #ifdef COROSYNC_LINUX struct cmsghdr *cmsg; @@ -804,7 +805,7 @@ retry_recv: goto retry_recv; } else if (res == -1 && errno != EAGAIN) { - return (0); + return (CS_ERR_LIBRARY); } else if (res == 0) { #if defined(COROSYNC_SOLARIS) || defined(COROSYNC_BSD) || defined(COROSYNC_DARWIN) @@ -812,9 +813,9 @@ retry_recv: * EOF is detected when recvmsg return 0. */ ipc_disconnect (conn_info); - return 0; + return (CS_ERR_LIBRARY); #else - return (-1); + return (CS_ERR_SECURITY); #endif } conn_info->setup_bytes_read += res; @@ -837,7 +838,9 @@ retry_recv: egid = ucred_getegid (uc); conn_info->client_pid = ucred_getpid (uc); if (api->security_valid (euid, egid)) { - authenticated = 1; + auth_res = CS_OK; + } else { + auth_res = hdb_error_to_cs(errno); } ucred_free(uc); } @@ -859,7 +862,9 @@ retry_recv: egid = -1; if (getpeereid (conn_info->fd, &euid, &egid) == 0) { if (api->security_valid (euid, egid)) { - authenticated = 1; + auth_res = CS_OK; + } else { + auth_res = hdb_error_to_cs(errno); } } } @@ -874,29 +879,36 @@ retry_recv: if (cred) { conn_info->client_pid = cred->pid; if (api->security_valid (cred->uid, cred->gid)) { - authenticated = 1; + auth_res = CS_OK; + } else { + auth_res = hdb_error_to_cs(errno); } } #else /* no credentials */ - authenticated = 1; - log_printf (LOGSYS_LEVEL_ERROR, "Platform does not support IPC authentication. Using no authentication\n"); + auth_res = CS_OK; + log_printf (LOGSYS_LEVEL_ERROR, "Platform does not support IPC authentication. Using no authentication\n"); #endif /* no credentials */ - if (authenticated == 0) { - log_printf (LOGSYS_LEVEL_ERROR, "Invalid IPC credentials.\n"); + if (auth_res != CS_OK) { ipc_disconnect (conn_info); - return (-1); - } + if (auth_res == CS_ERR_NO_RESOURCES) { + log_printf (LOGSYS_LEVEL_ERROR, + "Not enough file desciptors for IPC connection.\n"); + } else { + log_printf (LOGSYS_LEVEL_ERROR, "Invalid IPC credentials.\n"); + } + return auth_res; + } if (conn_info->setup_bytes_read == sizeof (mar_req_setup_t)) { #ifdef COROSYNC_LINUX setsockopt(conn_info->fd, SOL_SOCKET, SO_PASSCRED, &off, sizeof (off)); #endif - return (1); + return (CS_OK); } - return (0); + return (CS_ERR_LIBRARY); } static void ipc_disconnect (struct conn_info *conn_info) @@ -1576,10 +1588,10 @@ int coroipcs_handler_dispatch ( * send OK */ res = req_setup_recv (conn_info); - if (res == -1) { - req_setup_send (conn_info, CS_ERR_SECURITY); + if (res != CS_OK && res != CS_ERR_LIBRARY) { + req_setup_send (conn_info, res); } - if (res != 1) { + if (res != CS_OK) { return (0); } diff --git a/exec/main.c b/exec/main.c index d5306a3..58a33a6 100644 --- a/exec/main.c +++ b/exec/main.c @@ -925,7 +925,8 @@ static int corosync_security_valid (int euid, int egid) struct list_head *iter; if (corosync_not_enough_fds_left) { - return 0; + errno = EMFILE; + return (0); } if (euid == 0 || egid == 0) { @@ -942,6 +943,7 @@ static int corosync_security_valid (int euid, int egid) return (1); } + errno = EACCES; return (0); } diff --git a/exec/util.h b/exec/util.h index 7b95536..a3c5ae8 100644 --- a/exec/util.h +++ b/exec/util.h @@ -63,6 +63,27 @@ enum e_ais_done { AIS_DONE_DIR_NOT_PRESENT = 16 }; +static inline cs_error_t hdb_error_to_cs (int res) \ +{ \ + if (res == 0) { \ + return (CS_OK); \ + } else { \ + if (errno == EBADF) { \ + return (CS_ERR_BAD_HANDLE); \ + } else \ + if (errno == ENOMEM) { \ + return (CS_ERR_NO_MEMORY); \ + } else \ + if (errno == EMFILE) { \ + return (CS_ERR_NO_RESOURCES); \ + } else \ + if (errno == EACCES) { \ + return (CS_ERR_SECURITY); \ + } \ + return (CS_ERR_LIBRARY); \ + } \ +} + /* * Compare two names. returns non-zero on match. */ diff --git a/lib/util.h b/lib/util.h index 4a44bba..c228b42 100644 --- a/lib/util.h +++ b/lib/util.h @@ -48,6 +48,12 @@ static inline cs_error_t hdb_error_to_cs (int res) \ } else \ if (errno == ENOMEM) { \ return (CS_ERR_NO_MEMORY); \ + } else \ + if (errno == EMFILE) { \ + return (CS_ERR_NO_RESOURCES); \ + } else \ + if (errno == EACCES) { \ + return (CS_ERR_SECURITY); \ } \ return (CS_ERR_LIBRARY); \ } \ -- 1.7.1 _______________________________________________ Openais mailing list Openais@lists.linux-foundation.org https://lists.linux-foundation.org/mailman/listinfo/openais