summaryrefslogtreecommitdiffstats
path: root/rpc/rpc-lib/src/auth-glusterfs.c
diff options
context:
space:
mode:
authorAmar Tumballi <amarts@redhat.com>2017-11-07 00:07:12 +0530
committerRaghavendra G <rgowdapp@redhat.com>2018-01-17 06:00:39 +0000
commit75b063d76d78b5d1e0e53a1be37dc5ad9200f7b2 (patch)
treeae9149d96a2f850c2128de0328e13634fec09a5e /rpc/rpc-lib/src/auth-glusterfs.c
parente3a191a0d3ea0706f4827ebdb6e5161623f2c5f1 (diff)
rpc/*: auth-header changes
Introduce another authentication header which can now send more data. This is useful because this data can be common for all the fops, and we don't need to change all the signatures. As part of this, made rpc-clnt.c little more modular to support multiple authentication structures. stack.h changes are placeholder for the ctime etc, can be moved later based on need. updates #384 Change-Id: I6111c13cfd2ec92e2b4e9295896bf62a8a33b2c7 Signed-off-by: Amar Tumballi <amarts@redhat.com>
Diffstat (limited to 'rpc/rpc-lib/src/auth-glusterfs.c')
-rw-r--r--rpc/rpc-lib/src/auth-glusterfs.c145
1 files changed, 143 insertions, 2 deletions
diff --git a/rpc/rpc-lib/src/auth-glusterfs.c b/rpc/rpc-lib/src/auth-glusterfs.c
index 5670b8e840b..78f283557b0 100644
--- a/rpc/rpc-lib/src/auth-glusterfs.c
+++ b/rpc/rpc-lib/src/auth-glusterfs.c
@@ -16,6 +16,7 @@
#include "xdr-rpc.h"
#include "xdr-common.h"
#include "rpc-common-xdr.h"
+#include "glusterfs4-xdr.h"
/* V1 */
@@ -189,8 +190,10 @@ int auth_glusterfs_v2_authenticate (rpcsvc_request_t *req, void *priv)
req->auxgidcount = au.groups.groups_len;
/* the number of groups and size of lk_owner depend on each other */
- max_groups = GF_AUTH_GLUSTERFS_MAX_GROUPS (req->lk_owner.len);
- max_lk_owner_len = GF_AUTH_GLUSTERFS_MAX_LKOWNER (req->auxgidcount);
+ max_groups = GF_AUTH_GLUSTERFS_MAX_GROUPS (req->lk_owner.len,
+ AUTH_GLUSTERFS_v2);
+ max_lk_owner_len = GF_AUTH_GLUSTERFS_MAX_LKOWNER (req->auxgidcount,
+ AUTH_GLUSTERFS_v2);
if (req->auxgidcount > max_groups) {
gf_log ("", GF_LOG_WARNING,
@@ -263,3 +266,141 @@ rpcsvc_auth_glusterfs_v2_init (rpcsvc_t *svc, dict_t *options)
{
return &rpcsvc_auth_glusterfs_v2;
}
+
+/* V3 */
+
+ssize_t
+xdr_to_glusterfs_auth_v3 (char *buf, struct auth_glusterfs_params_v3 *req)
+{
+ XDR xdr;
+ ssize_t ret = -1;
+
+ if ((!buf) || (!req))
+ return -1;
+
+ xdrmem_create (&xdr, buf, GF_MAX_AUTH_BYTES, XDR_DECODE);
+ if (!xdr_auth_glusterfs_params_v3 (&xdr, req)) {
+ gf_log ("", GF_LOG_WARNING,
+ "failed to decode glusterfs v3 parameters");
+ ret = -1;
+ goto ret;
+ }
+
+ ret = (((size_t)(&xdr)->x_private) - ((size_t)(&xdr)->x_base));
+ret:
+ return ret;
+}
+
+int
+auth_glusterfs_v3_request_init (rpcsvc_request_t *req, void *priv)
+{
+ return 0;
+}
+
+int auth_glusterfs_v3_authenticate (rpcsvc_request_t *req, void *priv)
+{
+ struct auth_glusterfs_params_v3 au = {0,};
+ int ret = RPCSVC_AUTH_REJECT;
+ int i = 0;
+ int max_groups = 0;
+ int max_lk_owner_len = 0;
+
+ if (!req)
+ return ret;
+
+ ret = xdr_to_glusterfs_auth_v3 (req->cred.authdata, &au);
+ if (ret == -1) {
+ gf_log ("", GF_LOG_WARNING,
+ "failed to decode glusterfs credentials");
+ ret = RPCSVC_AUTH_REJECT;
+ goto err;
+ }
+
+ req->pid = au.pid;
+ req->uid = au.uid;
+ req->gid = au.gid;
+ req->lk_owner.len = au.lk_owner.lk_owner_len;
+ req->auxgidcount = au.groups.groups_len;
+
+ /* the number of groups and size of lk_owner depend on each other */
+ max_groups = GF_AUTH_GLUSTERFS_MAX_GROUPS (req->lk_owner.len,
+ AUTH_GLUSTERFS_v3);
+ max_lk_owner_len = GF_AUTH_GLUSTERFS_MAX_LKOWNER (req->auxgidcount,
+ AUTH_GLUSTERFS_v3);
+
+ if (req->auxgidcount > max_groups) {
+ gf_log ("", GF_LOG_WARNING,
+ "more than max aux gids found (%d) , truncating it "
+ "to %d and continuing", au.groups.groups_len,
+ max_groups);
+ req->auxgidcount = max_groups;
+ }
+
+ if (req->lk_owner.len > max_lk_owner_len) {
+ gf_log ("", GF_LOG_WARNING,
+ "lkowner field to big (%d), depends on the number of "
+ "groups (%d), failing authentication",
+ req->lk_owner.len, req->auxgidcount);
+ ret = RPCSVC_AUTH_REJECT;
+ goto err;
+ }
+
+ if (req->auxgidcount > SMALL_GROUP_COUNT) {
+ req->auxgidlarge = GF_CALLOC(req->auxgidcount,
+ sizeof(req->auxgids[0]),
+ gf_common_mt_auxgids);
+ req->auxgids = req->auxgidlarge;
+ } else {
+ req->auxgids = req->auxgidsmall;
+ }
+
+ if (!req->auxgids) {
+ gf_log ("auth-glusterfs-v2", GF_LOG_WARNING,
+ "cannot allocate gid list");
+ ret = RPCSVC_AUTH_REJECT;
+ goto err;
+ }
+
+ for (i = 0; i < req->auxgidcount; ++i)
+ req->auxgids[i] = au.groups.groups_val[i];
+
+ for (i = 0; i < au.lk_owner.lk_owner_len; ++i)
+ req->lk_owner.data[i] = au.lk_owner.lk_owner_val[i];
+
+ /* All new things, starting glusterfs-4.0.0 */
+ req->flags = au.flags;
+ req->ctime.tv_sec = au.ctime_sec;
+ req->ctime.tv_nsec = au.ctime_nsec;
+
+ gf_log (GF_RPCSVC, GF_LOG_TRACE, "Auth Info: pid: %u, uid: %d"
+ ", gid: %d, owner: %s, flags: %d",
+ req->pid, req->uid, req->gid, lkowner_utoa (&req->lk_owner),
+ req->flags);
+ ret = RPCSVC_AUTH_ACCEPT;
+err:
+ /* TODO: instead use alloca() for these variables */
+ free (au.groups.groups_val);
+ free (au.lk_owner.lk_owner_val);
+
+ return ret;
+}
+
+rpcsvc_auth_ops_t auth_glusterfs_ops_v3 = {
+ .transport_init = NULL,
+ .request_init = auth_glusterfs_v3_request_init,
+ .authenticate = auth_glusterfs_v3_authenticate
+};
+
+rpcsvc_auth_t rpcsvc_auth_glusterfs_v3 = {
+ .authname = "AUTH_GLUSTERFS-v3",
+ .authnum = AUTH_GLUSTERFS_v3,
+ .authops = &auth_glusterfs_ops_v3,
+ .authprivate = NULL
+};
+
+
+rpcsvc_auth_t *
+rpcsvc_auth_glusterfs_v3_init (rpcsvc_t *svc, dict_t *options)
+{
+ return &rpcsvc_auth_glusterfs_v3;
+}