lustre/sec/autoMakefile
lustre/sec/gss/Makefile
lustre/sec/gss/autoMakefile
+lustre/sec/gks/Makefile
+lustre/sec/gks/autoMakefile
lustre/smfs/Makefile
lustre/smfs/autoMakefile
lustre/snapfs/Makefile
ea2len = ea2 ? msg->buflens[2] : 0;
rc = md_setattr(cmobd->master_exp, op_data, &iattr,
- ea1, ea1len, ea2, ea2len, &req);
+ ea1, ea1len, ea2, ea2len, NULL, 0, &req);
OBD_FREE(op_data, sizeof(*op_data));
if (req)
static int cobd_md_setattr(struct obd_export *exp, struct mdc_op_data *data,
struct iattr *iattr, void *ea, int ealen, void *ea2,
- int ea2len, struct ptlrpc_request **request)
+ int ea2len, void *ea3, int ea3len,
+ struct ptlrpc_request **request)
{
struct obd_device *obd = class_exp2obd(exp);
struct obd_export *cobd_exp;
}
cobd_exp = cobd_get_exp(obd);
return md_setattr(cobd_exp, data, iattr, ea,
- ealen, ea2, ea2len, request);
+ ealen, ea2, ea2len, ea3, ea3len, request);
}
static int cobd_md_readpage(struct obd_export *exp,
void *it_data;
int it_lock_mode;
int it_int_flags;
+ void *it_key;
+ int it_key_size;
};
#define LUSTRE_IT(it) ((struct lustre_intent_data *)((it)->d.fs_data))
EA_LOV = (1 << 0),
EA_MEA = (1 << 1),
EA_SID = (1 << 2),
- EA_MID = (1 << 3)
+ EA_MID = (1 << 3),
+ EA_KEY = (1 << 4)
};
struct fsfilt_operations {
--- /dev/null
+/* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
+ * vim:expandtab:shiftwidth=8:tabstop=8:
+ *
+ * Copyright (C) 2001-2003 Cluster File Systems, Inc. <info@clusterfs.com>
+ *
+ * This file is part of Lustre, http://www.lustre.org.
+ *
+ * Lustre is free software; you can redistribute it and/or
+ * modify it under the terms of version 2 of the GNU General Public
+ * License as published by the Free Software Foundation.
+ *
+ * Lustre is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Lustre; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ *
+ * GS data structures.
+ * See also lustre_idl.h for wire formats of requests.
+ *
+ */
+
+#ifndef _LUSTRE_GS_H
+#define _LUSTRE_GS_H
+
+#define LUSTRE_GKS_NAME "gks"
+#define LUSTRE_GKT_NAME "gkt"
+#define LUSTRE_GKC_NAME "gkc"
+
+
+/*define gsk type*/
+#define NO_CRYPTO 0
+#define GKS_TYPE 1
+#define MKS_TYPE 2
+
+struct crypto_ops_item {
+ struct crypto_helper_ops *cops;
+ struct list_head clist;
+ char *ctype;
+};
+
+#define DECRYPT_DATA 0x00000001
+#define ENCRYPT_DATA 0x00000002
+struct lustre_key {
+ struct crypto_key lk_ck;
+ atomic_t lk_refcount;
+ __u32 lk_key_type;
+ __u32 lk_flags;
+};
+
+static inline struct lustre_key *
+lustre_key_get(struct lustre_key *lkey)
+{
+ if (lkey) {
+ atomic_inc(&lkey->lk_refcount);
+ }
+ return lkey;
+}
+
+
+static inline void
+lustre_key_release(struct lustre_key *lkey)
+{
+ if (lkey && atomic_dec_and_test(&lkey->lk_refcount))
+ kfree(lkey);
+}
+
+#define SET_CRYPTO_FLAGS(flags, type, offset, width) \
+do { \
+ flags &= ~(((1 << width) - 1) << offset); \
+ flags |= (type & ((1 << width) - 1)) << offset; \
+} while(0)
+
+#define CPT_TYPE_OFFSET 0
+#define CPT_TYPE_WIDTH 2
+#define GKS_CRYPTO_TYPE 1
+#define MKS_CRYPTO_TYPE 2
+
+#define SET_CRYPTO_TYPE(flags, type) \
+SET_CRYPTO_FLAGS(flags, type, CPT_TYPE_OFFSET, CPT_TYPE_WIDTH)
+
+#define IS_GKS_TYPE(flags) \
+(((flags >> CPT_TYPE_OFFSET) & ((1 << CPT_TYPE_WIDTH) - 1)) == GKS_CRYPTO_TYPE)
+
+#define IS_MKS_TYPE(flags) \
+(((flags >> CPT_TYPE_OFFSET) & ((1 << CPT_TYPE_WIDTH) - 1)) == MKS_CRYPTO_TYPE)
+
+#define CPT_ENCRYPT_OFFSET 2
+#define CPT_ENCRYPT_WIDTH 1
+#define ENABLE_ENCRYPT_FLAG 1
+#define DISABLE_ENCRYPT_FLAG 0
+
+#define ENABLE_ENCRYPT(flag) \
+SET_CRYPTO_FLAGS(flag, ENABLE_ENCRYPT_FLAG, CPT_ENCRYPT_OFFSET, CPT_ENCRYPT_WIDTH)
+
+#define DISABLE_ENCRYPT(flag) \
+SET_CRYPTO_FLAGS(flag, DISABLE_ENCRYPT_FLAG, CPT_ENCRYPT_OFFSET, CPT_ENCRYPT_WIDTH)
+
+#define IS_ENABLE_ENCRYPT(flags) \
+(((flags >> CPT_ENCRYPT_OFFSET) & ((1 << CPT_ENCRYPT_WIDTH) - 1)) \
+ == ENABLE_ENCRYPT_FLAG)
+
+#define CPT_DECRYPT_OFFSET 3
+#define CPT_DECRYPT_WIDTH 1
+#define ENABLE_DECRYPT_FLAG 1
+#define DISABLE_DECRYPT_FLAG 2
+
+#define ENABLE_DECRYPT(flag) \
+SET_CRYPTO_FLAGS(flag, ENABLE_DECRYPT_FLAG, CPT_DECRYPT_OFFSET, CPT_DECRYPT_WIDTH)
+
+#define DISABLE_DECRYPT(flag) \
+SET_CRYPTO_FLAGS(flag, DISABLE_DECRYPT_FLAG, CPT_DECRYPT_OFFSET, CPT_DECRYPT_WIDTH)
+
+#define IS_ENABLE_DECRYPT(flags) \
+(((flags >> CPT_DECRYPT_OFFSET) & ((1 << CPT_DECRYPT_WIDTH) - 1)) \
+ == ENABLE_DECRYPT_FLAG)
+
+#define CPT_DECRYPTED_OFFSET 4
+#define CPT_DECRYPTED_WIDTH 1
+#define DECRYPTED_FLAG 1
+#define ENCRYPTED_FLAG 0
+
+#define SET_DECRYPTED(flag) \
+SET_CRYPTO_FLAGS(flag, DECRYPTED_FLAG, CPT_DECRYPTED_OFFSET, CPT_DECRYPTED_WIDTH)
+
+#define SET_UNDECRYPTED(flag) \
+SET_CRYPTO_FLAGS(flag, ENCRYPTED_FLAG, CPT_DECRYPTED_OFFSET, CPT_DECRYPTED_WIDTH)
+
+#define IS_DECRYPTED(flags) \
+(((flags >> CPT_DECRYPTED_OFFSET) & ((1 << CPT_DECRYPTED_WIDTH) - 1)) \
+ == DECRYPTED_FLAG)
+
+
+
+#define MD_KEY_MAGIC 0x19760218
+struct crypto_key_md {
+ struct crypto_key md_ck;
+ __u32 md_magic;
+};
+
+struct key_parms {
+ struct key_context *context;
+ struct key_perm *perm;
+ int context_size;
+ int perm_size;
+};
+
+static inline int crypto_kcontext_size(int acl_count)
+{
+ return (sizeof(struct key_context) + acl_count *
+ sizeof(struct posix_acl_entry));
+}
+static inline int crypto_kperm_size(int acl_count)
+{
+ return (sizeof(struct key_perm) + acl_count *
+ sizeof(struct posix_acl_entry));
+}
+#endif /*LUSTRE_GS_H*/
# include <linux/list.h>
# include <linux/string.h> /* for strncpy, below */
# include <linux/fs.h> /* to check for FMODE_EXEC, dev_t, lest we redefine */
+# include <linux/posix_acl.h>
#else
#ifdef __CYGWIN__
# include <sys/types.h>
#define MGMT_REPLY_PORTAL 25
#define MGMT_CLI_REQUEST_PORTAL 26
#define MGMT_CLI_REPLY_PORTAL 27
+#define GKS_REQUEST_PORTAL 28
+#define GKC_REPLY_PORTAL 29
#define SVC_KILLED 1
#define SVC_EVENT 2
#define LUSTRE_DLM_VERSION 0x00040000
#define LUSTRE_LOG_VERSION 0x00050000
#define LUSTRE_PBD_VERSION 0x00060000
+#define LUSTRE_GKS_VERSION 0x00070000
struct lustre_handle {
__u64 cookie;
#define OBD_MD_FLXATTRLIST (0x0000000200000000LL) /* user xattr list */
#define OBD_MD_FLACL (0x0000000400000000LL) /* acl */
#define OBD_MD_FLRMTACL (0x0000000800000000LL) /* remote acl */
+#define OBD_MD_FLKEY (0x0000001000000000LL) /* mds key extended attributes */
#define OBD_MD_FLNOTOBD (~(OBD_MD_FLBLOCKS | OBD_MD_LINKNAME | \
OBD_MD_FLEASIZE | OBD_MD_FLHANDLE | \
OBD_MD_FLCKSUM | OBD_MD_FLQOS | \
OBD_MD_FLOSCOPQ | OBD_MD_FLCOOKIE | \
OBD_MD_FLXATTR | OBD_MD_FLXATTRLIST | \
- OBD_MD_FLACL | OBD_MD_MDS))
+ OBD_MD_FLACL | OBD_MD_FLKEY | OBD_MD_MDS))
static inline struct lustre_handle *obdo_handle(struct obdo *oa)
{
struct mea *mea;
struct posix_acl *posix_acl;
struct mds_remote_perm *remote_perm;
+ struct lustre_key *key;
};
void lustre_swab_remote_perm(struct mds_remote_perm *p);
#define ATTR_EA 0x00040000
#define ATTR_EA_RM 0x00080000
#define ATTR_EA_CMOBD 0x00100000
+#define ATTR_KEY 0x00200000
+#define ATTR_MAC 0x00400000
extern void lustre_swab_mds_rec_setattr (struct mds_rec_setattr *sa);
#ifndef FMODE_READ
#define MDS_OPEN_DIRECTORY 00200000
#define MDS_OPEN_DELAY_CREATE 0100000000 /* delay initial object create */
+#define MDS_OPEN_HAS_KEY 01000000000 /* just set the EA the obj exist */
#define MDS_OPEN_HAS_EA 010000000000 /* specify object create pattern */
#define MDS_OPEN_HAS_OBJS 020000000000 /* just set the EA the obj exist */
struct lustre_id cr_replayid;
__u64 cr_time;
__u64 cr_rdev;
+ __u64 cr_enkey;
+ __u64 cr_mac;
};
extern void lustre_swab_mds_rec_create (struct mds_rec_create *cr);
SEC_LAST_OPC
} sec_cmd_t;
#define SEC_FIRST_OPC SEC_INIT
+/* GS opcodes*/
+typedef enum {
+ GKS_CONNECT = 700,
+ GKS_DISCONNECT = 701,
+ GKS_GET_KEY = 702,
+ GKS_DECRYPT_KEY = 703,
+ GKS_GET_MAC = 704,
+} gks_cmd_t;
+
+#ifdef __KERNEL__
+#define KEY_SIZE 16
+#define MAC_SIZE 16
+
+struct crypto_key {
+ __u8 ck_mac[MAC_SIZE];
+ __u8 ck_key[KEY_SIZE];
+ __u32 ck_type;
+};
+
+struct key_perm {
+ uid_t kp_uid;
+ gid_t kp_gid;
+ __u32 kp_mode;
+ __u32 kp_acl_count;
+ struct posix_acl_entry kp_acls[0];
+};
+struct key_context {
+ struct crypto_key kc_ck;
+ __u32 kc_command;
+ __u32 kc_valid;
+ struct key_perm kc_perm;
+};
+typedef int (*crypt_cb_t)(struct page *page, __u64 offset, __u64 count,
+ int flags);
+extern void lustre_swab_key_context (struct key_context *kctxt);
+extern void lustre_swab_key_perms (struct key_perm *kperm);
+#endif /*for define __KERNEL*/
extern void lustre_swab_lustre_id(struct lustre_id *id);
extern void lustre_swab_lov_desc(struct lov_desc *desc);
extern void lustre_swab_lustre_stc(struct lustre_stc *stc);
extern void lustre_swab_lustre_fid(struct lustre_fid *fid);
extern void lustre_swab_mds_status_req(struct mds_status_req *r);
-
#endif
__u64 lli_open_fd_write_count;
struct obd_client_handle *lli_mds_exec_och;
__u64 lli_open_fd_exec_count;
-
struct posix_acl *lli_posix_acl;
struct remote_acl *lli_remote_acl;
+ struct lustre_key *lli_key_info;
};
// FIXME: replace the name of this with LL_I to conform to kernel stuff
__u64 it_lock_handle;
void *it_data;
int it_lock_mode;
+ int it_int_flags;
+ void *it_key;
+ int it_key_size;
};
#define LUSTRE_IT(it) ((struct lustre_intent_data *)((it)->d.fs_data))
void *ur_eadata;
int ur_ea2datalen;
void *ur_ea2data;
+ int ur_ea3datalen;
+ void *ur_ea3data;
int ur_cookielen; /* obsolete? */
struct llog_cookie *ur_logcookies; /* obsolete? */
struct iattr ur_iattr;
unsigned int ea_size, struct ptlrpc_request **request);
int mdc_setattr(struct obd_export *exp, struct mdc_op_data *data,
struct iattr *iattr, void *ea, int ealen, void *ea2, int ea2len,
- struct ptlrpc_request **request);
+ void *ea3, int ea3len, struct ptlrpc_request **request);
int mdc_open(struct obd_export *exp, obd_id ino, int type, int flags,
struct lov_mds_md *lmm, int lmm_size, struct lustre_handle *fh,
struct ptlrpc_request **);
OST_MAX_THREADS), 2UL)
#define OST_NBUFS (64 * smp_num_cpus)
#define OST_BUFSIZE (8 * 1024)
+/*GSS service parameters*/
+#define GKS_NBUFS (64 * smp_num_cpus)
+#define GKS_BUFSIZE (8 * 1024)
+#define GKT_MAX_THREADS 32UL
+#define GKT_NUM_THREADS max(min_t(unsigned long, num_physpages / 8192, \
+ GKT_MAX_THREADS), 2UL)
+
+#define GKS_MAXREQSIZE (5 * 1024)
+
+
/* OST_MAXREQSIZE ~= 1640 bytes =
* lustre_msg + obdo + 16 * obd_ioobj + 64 * niobuf_remote
*
int *lens, char **bufs);
void *mdc_setattr_pack(struct lustre_msg *msg, int offset,
struct mdc_op_data *data, struct iattr *iattr,
- void *ea, int ealen, void *ea2, int ea2len);
+ void *ea, int ealen, void *ea2, int ea2len,
+ void *ea3, int ea3len);
void *mdc_create_pack(struct lustre_msg *msg, int offset,
struct mdc_op_data *op_data, __u32 mode,
__u64 rdev, const void *data, int datalen);
struct mdc_op_data *data,
const char *old, int oldlen,
const char *new, int newlen);
+__u32 mds_pack_open_flags(__u32 flags);
/* lustre id helper functions and macros. */
static inline
spinlock_t mds_denylist_lock;
struct list_head mds_denylist;
struct semaphore mds_create_sem;
+ int mds_crypto_type;
};
struct echo_obd {
struct semaphore init_sem;
struct obd_connect_data conn_data;
};
+struct gks_crypto_key {
+ char *key;
+ int len;
+};
+struct gks_obd {
+ struct ptlrpc_service *gks_service;
+ struct crypto_tfm *gks_mac_tfm;
+ struct crypto_tfm *gks_key_tfm;
+ struct gks_crypto_key gks_key;
+};
struct niobuf_local {
__u64 offset;
struct lmv_obd lmv;
struct cm_obd cm;
struct conf_obd conf;
+ struct gks_obd gks;
} u;
/* fields used by LProcFS */
struct ptlrpc_request **);
int (*m_setattr)(struct obd_export *, struct mdc_op_data *,
struct iattr *, void *, int , void *, int,
- struct ptlrpc_request **);
+ void *, int, struct ptlrpc_request **);
int (*m_sync)(struct obd_export *, struct lustre_id *,
struct ptlrpc_request **);
int (*m_readpage)(struct obd_export *, struct lustre_id *,
char *lp_profile;
char *lp_lov;
char *lp_lmv;
+ char *lp_gkc;
};
struct lustre_profile *class_get_profile(char * prof);
static inline int md_setattr(struct obd_export *exp, struct mdc_op_data *data,
struct iattr *iattr, void *ea, int ealen,
- void *ea2, int ea2len,
+ void *ea2, int ea2len, void *ea3, int ea3len,
struct ptlrpc_request **request)
{
int rc;
EXP_CHECK_MD_OP(exp, setattr);
MD_COUNTER_INCREMENT(exp->exp_obd, setattr);
rc = MDP(exp->exp_obd, setattr)(exp, data, iattr, ea, ealen,
- ea2, ea2len, request);
+ ea2, ea2len, ea3, ea3len, request);
RETURN(rc);
}
#define LL_IOC_SETFACL _IOW ('f', 164, long)
#define LL_IOC_FLUSH_CRED _IOW ('f', 170, long)
+#define LL_IOC_KEY_TYPE _IOW ('f', 171, long)
+#define LL_IOC_DISABLE_CRYPTO _IOW ('f', 172, long)
+#define LL_IOC_ENABLE_CRYPTO _IOW ('f', 173, long)
+
#define O_LOV_DELAY_CREATE 0100000000 /* hopefully this does not conflict */
+ * The only thing we can do is just take first
+ * found block(s)
+ */
-+ /*printk(KERN_ERR "EXT3-fs: and someone won our chunk\n");*/
++ printk(KERN_ERR "EXT3-fs: and someone won our chunk\n");
+ ac.ac_b_ex.fe_group = 0;
+ ac.ac_b_ex.fe_start = 0;
+ ac.ac_b_ex.fe_len = 0;
lustre_version.patch
vfs-dcache_locking-vanilla-2.6.10-fc3.patch
vfs-dcache_lustre_invalid-vanilla-2.6.patch
-vfs-intent_api-vanilla-2.6.10-fc3.patch
+vfs-intent_api-vanilla-2.6.10-fc3.patch
vfs-lookup_last-vanilla-2.6.10-fc3.patch
vfs-raw_ops-vanilla-2.6.10-fc3.patch
export-2.6-fc3.patch
#include <linux/lustre_dlm.h>
#include <linux/lustre_net.h>
#include <linux/lustre_sec.h>
+#include <linux/lustre_gs.h>
/* @priority: if non-zero, move the selected to the list head
* @nocreate: if non-zero, only search in existed connections
rq_portal = MGMT_REQUEST_PORTAL;
rp_portal = MGMT_REPLY_PORTAL;
connect_op = MGMT_CONNECT;
+ } else if (!strcmp(name, LUSTRE_GKC_NAME)) {
+ rq_portal = GKS_REQUEST_PORTAL;
+ rp_portal = GKC_REPLY_PORTAL;
+ connect_op = GKS_CONNECT;
+
} else {
CERROR("unknown client OBD type \"%s\", can't setup\n",
name);
while (tmp != &(ns->ns_hash[i])) {
struct ldlm_resource *res;
res = list_entry(tmp, struct ldlm_resource, lr_hash);
+ spin_unlock(&ns->ns_hash_lock);
ldlm_resource_getref(res);
spin_unlock(&ns->ns_hash_lock);
struct obd_uuid ll_sb_uuid;
struct obd_export *ll_md_exp;
struct obd_export *ll_dt_exp;
+ struct obd_export *ll_gt_exp;
obd_id ll_rootino;
int ll_flags;
struct list_head ll_conn_chain;
MODULES := llite
-llite-objs := dcache.o dir.o file.o llite_close.o llite_gns.o llite_lib.o llite_nfs.o rw.o lproc_llite.o namei.o special.o symlink.o llite_mmap.o
+llite-objs := dcache.o dir.o file.o llite_close.o llite_gns.o llite_lib.o llite_nfs.o
+llite-objs += rw.o lproc_llite.o namei.o special.o symlink.o llite_mmap.o llite_gs.o
ifeq ($(PATCHLEVEL),4)
llite-objs += rw24.o super.o
#include <linux/lustre_idl.h>
#include <linux/lustre_dlm.h>
#include <linux/lustre_version.h>
-
#include "llite_internal.h"
/* should NOT be called with the dcache lock, see fs/dcache.c */
void ll_intent_free(struct lookup_intent *it)
{
if (it->d.fs_data) {
+ struct lustre_intent_data *lustre_data =
+ (struct lustre_intent_data *)it->d.fs_data;
+ if (lustre_data->it_key) {
+ OBD_FREE(lustre_data->it_key,
+ lustre_data->it_key_size);
+ lustre_data->it_key = NULL;
+ lustre_data->it_key_size = 0;
+ }
OBD_SLAB_FREE(it->d.fs_data, ll_intent_slab,
sizeof(struct lustre_intent_data));
it->d.fs_data = NULL;
do_lock:
ll_frob_intent(&it, &lookup_it);
LASSERT(it != NULL);
-
+
+ rc = ll_crypto_init_it_key(de->d_inode, it);
+ if (rc)
+ GOTO(out, rc);
+
rc = md_intent_lock(exp, &pid, (char *)de->d_name.name, de->d_name.len,
NULL, 0, &cid, it, flags, &req, ll_mdc_blocking_ast);
/* If req is NULL, then md_intent_lock() only tried to do a lock match;
if (ll_intent_alloc(it))
LBUG();
}
-
+ rc = ll_crypto_init_it_key(de->d_inode, it);
+ if (rc)
+ GOTO(out, rc);
rc = md_intent_lock(exp, &pid, (char *)de->d_name.name, de->d_name.len,
NULL, 0, NULL, it, 0, &req, ll_mdc_blocking_ast);
if (rc >= 0) {
rc = md_setattr(ll_i2sbi(inode)->ll_md_exp, &op_data, &attr,
(void*) XATTR_NAME_LUSTRE_ACL,
sizeof(XATTR_NAME_LUSTRE_ACL),
- (void*) cmd, ioc->cmd_len, &req);
+ (void*) cmd, ioc->cmd_len, NULL, 0, &req);
if (rc) {
CERROR("md_setattr fails: rc = %d\n", rc);
GOTO(out, rc);
obd_ioctl_freedata(buf, len);
return rc;
}
+ case LL_IOC_KEY_TYPE: {
+ char *buf = NULL;
+ char *type;
+ int typelen, rc, len = 0;
+
+ rc = obd_ioctl_getdata(&buf, &len, (void *)arg);
+ if (rc)
+ RETURN(rc);
+ data = (void *)buf;
+
+ type = data->ioc_inlbuf1;
+ typelen = data->ioc_inllen1;
+
+ if (typelen < 1) {
+ CDEBUG(D_INFO, "LL_IOC_KEY_TYPE missing filename\n");
+ GOTO(out_free, rc = -EINVAL);
+ }
+ ll_set_sb_gksinfo(inode->i_sb, type);
+ EXIT;
+ out_free:
+ obd_ioctl_freedata(buf, len);
+ RETURN(rc);
+ }
case LL_IOC_MDC_MKDIRSTRIPE:
RETURN(ll_mkdir_stripe(inode, arg));
case LL_IOC_LOV_SETSTRIPE: {
ll_prepare_mdc_data(op_data, inode, NULL, NULL, 0, 0);
rc = md_setattr(sbi->ll_md_exp, op_data, &attr, &lum,
- sizeof(lum), NULL, 0, &request);
+ sizeof(lum), NULL, 0, NULL, 0, &request);
OBD_FREE(op_data, sizeof(*op_data));
ptlrpc_req_finished(request);
obdo->o_fid = id_fid(&ll_i2info(inode)->lli_id);
obdo->o_mds = id_group(&ll_i2info(inode)->lli_id);
-
obdo->o_valid |= OBD_MD_FLEPOCH;
obdo->o_easize = ll_i2info(inode)->lli_io_epoch;
oit.it_flags |= 2;
it = file->f_it;
-
/*
* sometimes LUSTRE_IT(it) may not be allocated like opening file by
* dentry_open() from GNS stuff.
och_usecount = &lli->lli_open_fd_read_count;
}
+ rc = ll_crypto_decrypt_key(inode, it);
+ if (rc)
+ GOTO(out, rc);
+
down(&lli->lli_och_sem);
if (*och_p) { /* Open handle is present */
if (it_disposition(it, DISP_LOOKUP_POS) && /* Positive lookup */
putname(filename);
return rc;
}
+ case LL_IOC_KEY_TYPE: {
+ struct obd_ioctl_data *data;
+ char *buf = NULL;
+ char *type;
+ int typelen, rc, len = 0;
+
+ rc = obd_ioctl_getdata(&buf, &len, (void *)arg);
+ if (rc)
+ RETURN(rc);
+ data = (void *)buf;
+
+ type = data->ioc_inlbuf1;
+ typelen = data->ioc_inllen1;
+
+ if (typelen < 1) {
+ CDEBUG(D_INFO, "LL_IOC_KEY_TYPE missing filename\n");
+ GOTO(out, rc = -EINVAL);
+ }
+ ll_set_sb_gksinfo(inode->i_sb, type);
+ EXIT;
+ out:
+ obd_ioctl_freedata(buf, len);
+ return rc;
+ }
+
case LL_IOC_LOV_GETSTRIPE:
RETURN(ll_lov_getstripe(inode, arg));
case EXT3_IOC_GETFLAGS:
rc = ll_intent_alloc(&oit);
if (rc)
RETURN(-ENOMEM);
+
+ rc = ll_crypto_init_it_key(inode, &oit);
+ if (rc)
+ GOTO(out, rc);
rc = md_intent_lock(sbi->ll_md_exp, &id, NULL, 0, NULL, 0, &id,
&oit, 0, &req, ll_mdc_blocking_ast);
struct ptlrpc_request *request = NULL;
struct mdc_op_data op_data;
struct iattr attr;
- int rc = 0;
+ void *key = NULL;
+ int rc = 0, key_size = 0;
ENTRY;
CDEBUG(D_VFSTRACE, "VFS Op:inode=%lu\n", inode->i_ino);
attr.ia_valid |= valid;
attr.ia_attr_flags = flags;
+ if (strcmp(name, XATTR_NAME_ACL_ACCESS) == 0) {
+ rc = ll_crypto_get_mac(inode, NULL, (void *)value, size,
+ &key, &key_size);
+ }
+
ll_prepare_mdc_data(&op_data, inode, NULL, NULL, 0, 0);
rc = md_setattr(sbi->ll_md_exp, &op_data, &attr,
- (void*) name, strnlen(name, XATTR_NAME_MAX) + 1,
- (void*) value, size, &request);
- if (rc)
+ (void*) name, strnlen(name, XATTR_NAME_MAX) + 1,
+ (void*) value, size, key, key_size, &request);
+
+ if (key && key_size)
+ OBD_FREE(key, key_size);
+ if (rc) {
+ CERROR("md_setattr fails: rc = %d\n", rc);
GOTO(out, rc);
-
- out:
+ }
+out:
ptlrpc_req_finished(request);
RETURN(rc);
}
ATTR_EA_RM);
}
-static
int ll_getxattr_internal(struct inode *inode, const char *name,
void *value, size_t size, __u64 valid)
{
#include <linux/lustre_mds.h>
#include <linux/lustre_lite.h>
+#include <linux/lustre_gs.h>
#include "llite_internal.h"
/* record that a write is in flight */
--- /dev/null
+/* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
+ * vim:expandtab:shiftwidth=8:tabstop=8:
+ *
+ * Copyright (C) 2004, 2005 Cluster File Systems, Inc.
+ *
+ * This file is part of Lustre, http://www.lustre.org.
+ *
+ * Lustre is free software; you can redistribute it and/or
+ * modify it under the terms of version 2 of the GNU General Public
+ * License as published by the Free Software Foundation.
+ *
+ * Lustre is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Lustre; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+
+#define DEBUG_SUBSYSTEM S_LLITE
+
+#include <linux/fs.h>
+#include <linux/types.h>
+#include <linux/version.h>
+#include <asm/uaccess.h>
+#include <linux/file.h>
+#include <linux/kmod.h>
+#include <linux/posix_acl.h>
+#include <linux/xattr_acl.h>
+
+#include <linux/lustre_acl.h>
+#include <linux/lustre_lite.h>
+#include <linux/lustre_gs.h>
+#include "llite_internal.h"
+
+int ll_gs_intent_init(struct lookup_intent *it)
+{
+ struct lustre_intent_data *lustre_data;
+
+ LASSERT(it->d.fs_data != NULL);
+ lustre_data = (struct lustre_intent_data *)it->d.fs_data;
+ /*set lustre key size when there is gss server
+ *or other configuration*/
+ lustre_data->it_key = NULL;
+ lustre_data->it_key_size = 0;
+ RETURN(0);
+}
+
+static int ll_get_acl_key(struct inode *inode, struct posix_acl **acl,
+ struct lustre_key **lkey)
+{
+ struct lookup_intent it = { .it_op = IT_GETATTR };
+ struct dentry de = { .d_inode = inode };
+ struct ll_sb_info *sbi;
+ struct lustre_id id;
+ struct ptlrpc_request *req = NULL;
+ struct ll_inode_info *lli = ll_i2info(inode);
+ int rc = 0;
+ ENTRY;
+
+ if (lli->lli_posix_acl && lli->lli_key_info) {
+ /*If they are in the local cache, just fetch them*/
+ spin_lock(&lli->lli_lock);
+ *acl = posix_acl_dup(lli->lli_posix_acl);
+ *lkey = lustre_key_get(lli->lli_key_info);
+ spin_unlock(&lli->lli_lock);
+ RETURN(rc);
+ }
+ sbi = ll_i2sbi(inode);
+ ll_inode2id(&id, inode);
+
+ if (ll_intent_alloc(&it))
+ RETURN(-EACCES);
+
+ rc = md_intent_lock(sbi->ll_md_exp, &id, NULL, 0, NULL, 0, &id,
+ &it, 0, &req, ll_mdc_blocking_ast);
+ if (rc < 0) {
+ ll_intent_free(&it);
+ GOTO(out, rc);
+ }
+
+ rc = revalidate_it_finish(req, 1, &it, &de);
+ if (rc) {
+ ll_intent_release(&it);
+ GOTO(out, rc);
+ }
+
+ ll_lookup_finish_locks(&it, &de);
+ ll_intent_free(&it);
+
+ spin_lock(&lli->lli_lock);
+ *acl = posix_acl_dup(lli->lli_posix_acl);
+ *lkey = lustre_key_get(lli->lli_key_info);
+ spin_unlock(&lli->lli_lock);
+out:
+ if (req)
+ ptlrpc_req_finished(req);
+ RETURN(rc);
+}
+
+static int ll_init_key_perm(struct key_perm *kperm, struct posix_acl *acl,
+ __u32 uid, __u32 gid, int mode)
+{
+ if (acl) {
+ kperm->kp_acl_count = acl->a_count;
+ memcpy(kperm->kp_acls, acl->a_entries,
+ acl->a_count * sizeof(struct posix_acl_entry));
+ }
+ kperm->kp_mode = mode;
+ kperm->kp_uid = uid;
+ kperm->kp_gid = gid;
+ RETURN(0);
+}
+
+static int ll_init_key_context(struct key_context *pkc, __u32 uid,
+ __u32 gid, struct crypto_key *ck,
+ struct posix_acl *acl, int mode,
+ int command, int valid)
+{
+ struct key_perm *kperm;
+ ENTRY;
+
+ pkc->kc_command = command;
+ pkc->kc_valid = valid;
+
+ if (ck)
+ memcpy(&pkc->kc_ck, ck, sizeof(*ck));
+
+ kperm = &pkc->kc_perm;
+
+ ll_init_key_perm(kperm, acl, uid, gid, mode);
+ RETURN(0);
+}
+static int ll_get_default_acl(struct inode *inode, struct posix_acl **acl,
+ mode_t mode)
+{
+ int rc = 0, buf_size, ea_size;
+ char *buf = NULL;
+ ENTRY;
+
+ if (!S_ISDIR(inode->i_mode))
+ RETURN(0);
+
+ buf_size = xattr_acl_size(LL_ACL_MAX_ENTRIES);
+ OBD_ALLOC(buf, buf_size);
+ if (!buf)
+ RETURN(-ENOMEM);
+
+ ea_size = ll_getxattr_internal(inode, XATTR_NAME_ACL_DEFAULT,
+ buf, buf_size, OBD_MD_FLXATTR);
+ if (ea_size <= 0) {
+ if (ea_size < 0 && ea_size != -ENODATA)
+ CERROR("get default acl of ino %lu error rc %d \n",
+ inode->i_ino, ea_size);
+ GOTO(out, rc = 0);
+ }
+ *acl = posix_acl_from_xattr(buf, ea_size);
+ if (IS_ERR(*acl)) {
+ rc = PTR_ERR(*acl);
+ CERROR("convert xattr to acl failed: %d\n", rc);
+ GOTO(out, rc);
+ } else if (*acl) {
+ rc = posix_acl_valid(*acl);
+ if (rc) {
+ CERROR("acl valid error: %d\n", rc);
+ posix_acl_release(*acl);
+ GOTO(out, rc);
+ }
+ }
+
+ rc = posix_acl_create_masq(*acl, &mode);
+out:
+ if (buf)
+ OBD_FREE(buf, buf_size);
+ RETURN(rc);
+}
+
+int ll_gks_create_key(struct inode *dir, mode_t mode, void **key,
+ int* key_size)
+{
+ struct obd_export *gs_exp = ll_i2gsexp(dir);
+ struct key_context *kcontext = NULL;
+ struct key_parms kparms;
+ struct posix_acl *default_acl = NULL;
+ int rc = 0;
+ ENTRY;
+
+ OBD_ALLOC(kcontext, sizeof(struct key_context));
+ if (!kcontext)
+ GOTO(out, rc = -ENOMEM);
+
+ rc = ll_get_default_acl(dir, &default_acl, mode);
+ if (rc)
+ GOTO(out, rc);
+
+ ll_init_key_context(kcontext, current->fsuid, current->fsgid,
+ NULL, default_acl, mode, GKS_GET_KEY, 0);
+
+ kparms.context = kcontext;
+ kparms.context_size = sizeof(struct key_context);
+ kparms.perm = NULL;
+
+ *key_size = sizeof(struct crypto_key);
+ OBD_ALLOC(*key, *key_size);
+ if (!*key)
+ GOTO(out, rc = -ENOMEM);
+
+ /*GET an encrypt key from GS server*/
+ rc = obd_get_info(gs_exp, sizeof(struct key_parms), (void *)&kparms,
+ key_size, *key);
+ if (rc) {
+ CERROR("get key error rc %d \n", rc);
+ GOTO(out, rc);
+ }
+ CDEBUG(D_INFO, "Get enkey %s MAC %s from exp %p \n",
+ (char*)((struct crypto_key *)(*key))->ck_key,
+ (char*)((struct crypto_key *)(*key))->ck_mac,
+ gs_exp);
+out:
+ if (kcontext)
+ OBD_FREE(kcontext, sizeof(struct key_context));
+ if (default_acl)
+ posix_acl_release(default_acl);
+ RETURN(rc);
+
+}
+
+int ll_gks_init_it(struct inode *parent, struct lookup_intent *it)
+{
+ struct obd_export *gs_exp = ll_i2gsexp(parent);
+ struct lustre_intent_data *lustre_data;
+ mode_t mode = (it->it_create_mode | S_IFREG) & (~current->fs->umask);
+ void *key = NULL;
+ int key_size = 0, rc = 0;
+ ENTRY;
+
+ if (!gs_exp || !it)
+ RETURN(rc);
+
+ ll_gs_intent_init(it);
+ if (!(it->it_op & IT_CREAT))
+ RETURN(rc);
+
+ LASSERT(it->d.fs_data != NULL);
+ lustre_data = (struct lustre_intent_data *)it->d.fs_data;
+
+ if (lustre_data->it_key) {
+ LASSERT(lustre_data->it_key_size ==
+ sizeof(struct crypto_key));
+ OBD_FREE(lustre_data->it_key, sizeof(struct crypto_key));
+ }
+
+ rc = ll_gks_create_key(parent, mode, &key, &key_size);
+ if (rc)
+ GOTO(out, rc);
+
+ lustre_data->it_key = key;
+ lustre_data->it_key_size = key_size;
+out:
+ if (rc) {
+ if (key && key_size)
+ OBD_FREE(key, key_size);
+ }
+ RETURN(rc);
+}
+
+int ll_gks_decrypt_key(struct inode *inode, struct lookup_intent *it)
+{
+ struct obd_export *gs_exp = ll_i2gsexp(inode);
+ struct ll_inode_info *lli = ll_i2info(inode);
+ struct key_context *kcontext = NULL;
+ struct key_perm *kperm = NULL;
+ struct key_parms kparms;
+ struct lustre_key *lkey = NULL;
+ struct crypto_key *ckey = NULL;
+ struct posix_acl *acl = NULL;
+ __u32 flags = 0;
+ int rc = 0, ck_size = 0, kcontext_size = 0, acl_count;
+
+ ENTRY;
+
+ if (!gs_exp)
+ RETURN(rc);
+
+ rc = ll_get_acl_key(inode, &acl, &lkey);
+ if (rc)
+ GOTO(out, rc);
+ if (!lkey || IS_DECRYPTED(lkey->lk_flags))
+ GOTO(out, rc = 0);
+
+ acl_count = acl ? acl->a_count : 0;
+ kcontext_size = crypto_kcontext_size(acl_count);
+ OBD_ALLOC(kcontext, kcontext_size);
+ if (!kcontext)
+ GOTO(out, rc = -ENOMEM);
+
+ flags = mds_pack_open_flags(it->it_flags);
+
+ spin_lock(&lli->lli_lock);
+ ll_init_key_context(kcontext, inode->i_uid, inode->i_gid, &lkey->lk_ck,
+ acl, inode->i_mode, GKS_DECRYPT_KEY, flags);
+
+ spin_unlock(&lli->lli_lock);
+
+ OBD_ALLOC(kperm, sizeof(struct key_perm));
+ ll_init_key_perm(kperm, NULL, current->uid, current->gid, 0);
+
+ kparms.context = kcontext;
+ kparms.context_size = kcontext_size;
+ kparms.perm = kperm;
+ kparms.perm_size = sizeof(struct key_perm);
+
+ ck_size = sizeof(*ckey);
+ OBD_ALLOC(ckey, ck_size);
+ if (!ckey)
+ GOTO(out, rc = -ENOMEM);
+
+ /*GET an encrypt key from GS server*/
+ rc = obd_get_info(gs_exp, sizeof(struct key_parms), (void *)&kparms,
+ &ck_size, ckey);
+ if (rc) {
+ CERROR("decrypt key error rc %d \n", rc);
+ GOTO(out, rc);
+ }
+ CDEBUG(D_INFO, "decrypt key %s MAC %s from exp %p \n",
+ ckey->ck_mac, ckey->ck_mac, gs_exp);
+
+ /*copy the decrypt key from kcontext to the lustre key*/
+
+ spin_lock(&lli->lli_lock);
+ memcpy(&lkey->lk_ck, ckey, sizeof(*ckey));
+ SET_DECRYPTED(lkey->lk_flags);
+ spin_unlock(&lli->lli_lock);
+out:
+ if (acl)
+ posix_acl_release(acl);
+ if (lkey)
+ lustre_key_release(lkey);
+ if (kperm)
+ OBD_FREE(kperm, sizeof(struct key_perm));
+ if (kcontext)
+ OBD_FREE(kcontext, kcontext_size);
+ if (ckey)
+ OBD_FREE(ckey, ck_size);
+ RETURN(rc);
+}
+
+int ll_gks_get_mac(struct inode *inode, struct iattr *iattr, void *value,
+ int size, void **key, int *key_size)
+{
+ struct ll_inode_info *lli = ll_i2info(inode);
+ struct obd_export *gs_exp = ll_i2gsexp(inode);
+ struct key_context *kcontext = NULL;
+ struct key_perm *kperm = NULL;
+ struct key_parms kparms;
+ struct lustre_key *lkey = NULL;
+ struct posix_acl *acl = NULL, *new_acl = NULL;
+ int rc = 0, kperm_size = 0, kcontext_size = 0;
+ mode_t mac_mode;
+ int acl_count = 0;
+
+ ENTRY;
+
+ if (!gs_exp)
+ RETURN(rc);
+
+ rc = ll_get_acl_key(inode, &acl, &lkey);
+ if (rc)
+ GOTO(out, rc);
+ if (!lkey)
+ RETURN(rc);
+
+ acl_count = acl ? acl->a_count : 0;
+ kcontext_size = crypto_kcontext_size(acl_count);
+ OBD_ALLOC(kcontext, kcontext_size);
+ if (!kcontext)
+ GOTO(out, rc = -ENOMEM);
+ spin_lock(&lli->lli_lock);
+ ll_init_key_context(kcontext, inode->i_uid, inode->i_gid, &lkey->lk_ck,
+ acl, inode->i_mode, GKS_GET_MAC, iattr->ia_valid);
+ spin_unlock(&lli->lli_lock);
+ if (value) {
+ new_acl = posix_acl_from_xattr(value, size);
+ if (IS_ERR(new_acl)) {
+ rc = PTR_ERR(new_acl);
+ CERROR("convert from xattr to acl error: %d",rc);
+ new_acl = NULL;
+ GOTO(out, rc);
+ } else if (new_acl) {
+ rc = posix_acl_valid(new_acl);
+ if (rc) {
+ CERROR("acl valid error: %d", rc);
+ GOTO(out, rc);
+ }
+ }
+ }
+ acl_count = acl ? acl->a_count : 0;
+ kperm_size = crypto_kperm_size(acl_count);
+ OBD_ALLOC(kperm, kperm_size);
+ if (iattr->ia_valid & ATTR_MODE)
+ mac_mode = iattr->ia_mode;
+ else
+ mac_mode = inode->i_mode;
+ ll_init_key_perm(kperm, new_acl, iattr->ia_uid, iattr->ia_gid,
+ mac_mode);
+ kparms.context = kcontext;
+ kparms.context_size = kcontext_size;
+ kparms.perm = kperm;
+ kparms.perm_size = kperm_size;
+
+ *key_size = sizeof(struct crypto_key);
+ OBD_ALLOC(*key, *key_size);
+ if (!*key)
+ GOTO(out, rc = -ENOMEM);
+
+ /*GET an encrypt key from GS server*/
+ rc = obd_get_info(gs_exp, sizeof(struct key_parms), (void *)&kparms,
+ key_size, *key);
+ if (rc) {
+ CERROR("decrypt key error rc %d \n", rc);
+ GOTO(out, rc);
+ }
+ /*copy the decrypt key from kcontext to the lustre key*/
+ spin_lock(&lli->lli_lock);
+ memcpy(&lkey->lk_ck, *key, *key_size);
+ iattr->ia_valid |= ATTR_MAC;
+ spin_unlock(&lli->lli_lock);
+out:
+ if (acl)
+ posix_acl_release(acl);
+ if (new_acl)
+ posix_acl_release(new_acl);
+ if (lkey)
+ lustre_key_release(lkey);
+ if (kperm)
+ OBD_FREE(kperm, kperm_size);
+ if (kcontext)
+ OBD_FREE(kcontext, kcontext_size);
+ RETURN(rc);
+}
+
+/*key function for calculate the key for countermode method*/
+static int ll_crypt_cb(struct page *page, __u64 offset, __u64 count,
+ int flags)
+{
+ struct inode *inode = page->mapping->host;
+ struct ll_inode_info *lli = ll_i2info(inode);
+ struct lustre_key *lkey = ll_i2info(inode)->lli_key_info;
+ unsigned char *ptr;
+ char *key_ptr;
+ int index = page->index;
+ __u64 data_key = 0;
+ int i;
+ ENTRY;
+
+ if (!lkey)
+ RETURN(0);
+ if (!IS_DECRYPTED(lkey->lk_flags))
+ RETURN(-EFAULT);
+ if (flags == ENCRYPT_DATA && !IS_ENABLE_ENCRYPT(lkey->lk_flags))
+ RETURN(-EFAULT);
+ if (flags == DECRYPT_DATA && !IS_ENABLE_DECRYPT(lkey->lk_flags))
+ RETURN(-EFAULT);
+
+ /*FIXME: tmp calculate method, should calculate
+ the key according to KEY_TYPE*/
+
+ spin_lock(&lli->lli_lock);
+ key_ptr = &lkey->lk_ck.ck_key[0];
+ for (i=0; i < KEY_SIZE; i++)
+ data_key += *key_ptr++;
+ spin_unlock(&lli->lli_lock);
+ data_key += index;
+
+ CDEBUG(D_INFO, "data_key is "LPU64" \n", data_key);
+ /*encrypt the data*/
+ ptr = (char *)kmap(page);
+ ptr += offset;
+ CDEBUG(D_INFO, "ptr is %s \n", ptr);
+ for (i = 0; i < count; i++)
+ *ptr++ ^= data_key;
+ CDEBUG(D_INFO, "encrypted ptr is %s \n", ptr);
+ kunmap(page);
+
+ RETURN(0);
+}
+
+int ll_gs_init_inode_key(struct inode *inode, void *mkey)
+{
+ struct ll_inode_info *lli = ll_i2info(inode);
+ struct crypto_key *key = (struct crypto_key*)mkey;
+ struct lustre_key *lkey = NULL;
+ ENTRY;
+
+ if (!key)
+ RETURN(0);
+
+ if (lli->lli_key_info == NULL) {
+ OBD_ALLOC(lkey, sizeof(struct lustre_key));
+ if (!lkey)
+ RETURN(-ENOMEM);
+ memcpy(&lkey->lk_ck, key, sizeof(*key));
+ atomic_set(&lkey->lk_refcount, 1);
+ SET_UNDECRYPTED(lkey->lk_flags);
+ ENABLE_ENCRYPT(lkey->lk_flags);
+ ENABLE_DECRYPT(lkey->lk_flags);
+ spin_lock(&lli->lli_lock);
+ lli->lli_key_info = lkey;
+ spin_unlock(&lli->lli_lock);
+ } else {
+ lkey = lustre_key_get(lli->lli_key_info);
+ if (!IS_DECRYPTED(lkey->lk_flags)) {
+ if (memcmp(&lkey->lk_ck, key, sizeof(*key))) {
+ CWARN("already have key_info %p in ino %ld \n",
+ lli->lli_key_info, inode->i_ino);
+ }
+ } else {
+ spin_lock(&lli->lli_lock);
+ SET_UNDECRYPTED(lkey->lk_flags);
+ memcpy(&lkey->lk_ck, key, sizeof(*key));
+ spin_unlock(&lli->lli_lock);
+ }
+ lustre_key_release(lkey);
+ }
+ CDEBUG(D_INFO, "set key %s mac %s in inode %lu \n",
+ lli->lli_key_info->lk_ck.ck_mac,
+ lli->lli_key_info->lk_ck.ck_key,
+ inode->i_ino);
+ RETURN(0);
+}
+
+static int ll_gs_destroy_key(struct inode *inode)
+{
+ struct ll_inode_info *lli = ll_i2info(inode);
+
+ spin_lock(&lli->lli_lock);
+ if (lli->lli_key_info) {
+ LASSERTF(atomic_read(&lli->lli_key_info->lk_refcount) == 1,
+ "lk_refcount %d != 1 when destory\n",
+ atomic_read(&lli->lli_key_info->lk_refcount));
+ lustre_key_release(lli->lli_key_info);
+ lli->lli_key_info = NULL;
+ }
+ spin_unlock(&lli->lli_lock);
+ RETURN(0);
+}
+
+struct crypto_helper_ops ll_cgs_ops = {
+ .init_it_key = ll_gks_init_it,
+ .create_key = ll_gks_create_key,
+ .init_inode_key = ll_gs_init_inode_key,
+ .get_mac = ll_gks_get_mac,
+ .decrypt_key = ll_gks_decrypt_key,
+ .destroy_key = ll_gs_destroy_key,
+};
+
+int ll_mks_create_key(struct inode *inode, struct lookup_intent *it)
+{
+ struct lustre_intent_data *lustre_data;
+ struct crypto_key *crypto_key;
+ int rc = 0;
+ ENTRY;
+
+ LASSERT(it->d.fs_data != NULL);
+ lustre_data = (struct lustre_intent_data *)it->d.fs_data;
+
+ if (lustre_data->it_key) {
+ OBD_FREE(lustre_data->it_key, sizeof(struct crypto_key));
+ }
+ OBD_ALLOC(crypto_key, sizeof(struct crypto_key));
+
+ lustre_data->it_key = crypto_key;
+ lustre_data->it_key_size = sizeof(struct crypto_key);
+ RETURN(rc);
+}
+
+int ll_mks_init_it(struct inode *parent, struct lookup_intent *it)
+{
+ struct obd_export *gs_exp = ll_i2gsexp(parent);
+ int rc = 0;
+ ENTRY;
+
+ if (!gs_exp || !it)
+ RETURN(0);
+
+ ll_gs_intent_init(it);
+ if (it->it_op & IT_CREAT) {
+ ll_mks_create_key(parent, it);
+ }
+ RETURN(rc);
+}
+
+int ll_mks_decrypt_key(struct inode *inode, struct lookup_intent *it)
+{
+ struct ll_inode_info *lli = ll_i2info(inode);
+ struct obd_export *gs_exp = ll_i2gsexp(inode);
+ struct lustre_key *lkey = NULL;
+ struct posix_acl *acl = NULL;
+ int rc = 0;
+
+ ENTRY;
+
+ if (!gs_exp)
+ RETURN(rc);
+
+ rc = ll_get_acl_key(inode, &acl, &lkey);
+ if (rc || !lkey)
+ RETURN(rc);
+ spin_lock(&lli->lli_lock);
+ SET_DECRYPTED(lkey->lk_flags);
+ spin_unlock(&lli->lli_lock);
+ RETURN(rc);
+}
+struct crypto_helper_ops ll_cmd_ops = {
+ .init_it_key = ll_mks_init_it,
+ .init_inode_key = ll_gs_init_inode_key,
+ .decrypt_key = ll_mks_decrypt_key,
+ .destroy_key = ll_gs_destroy_key,
+};
+
+
+static int ll_register_cops(struct ll_crypto_info *llci, char *type,
+ struct crypto_helper_ops *cops)
+{
+ struct list_head *list = &llci->ll_cops_list;
+ struct crypto_ops_item *opi = NULL, *tmp;
+ char *opi_name = NULL;
+ int rc = 0;
+ ENTRY;
+
+ list_for_each_entry(tmp, list, clist) {
+ if (!strcmp(type, tmp->ctype)) {
+ CWARN("%s is already registered\n", type);
+ rc = -EEXIST;
+ GOTO(exit, rc);
+ }
+ }
+
+ OBD_ALLOC(opi, sizeof(*opi));
+
+ OBD_ALLOC(opi_name, strlen(type) + 1);
+
+ LASSERT(opi && opi_name);
+
+ memcpy(opi_name, type, strlen(type));
+
+ opi->ctype = opi_name;
+ opi->cops = cops;
+
+ list_add_tail(&opi->clist, list);
+exit:
+ RETURN(rc);
+}
+
+static int ll_init_sb_crypto(struct super_block *sb)
+{
+ struct ll_crypto_info *llci = NULL;
+ int rc = 0;
+ ENTRY;
+
+ OBD_ALLOC(llci, sizeof(*llci));
+
+ if (!llci)
+ RETURN(-ENOMEM);
+
+ INIT_LIST_HEAD(&llci->ll_cops_list);
+
+ ll_register_cops(llci, "gks", &ll_cgs_ops);
+ ll_register_cops(llci, "mks", &ll_cmd_ops);
+
+ ll_s2sbi(sb)->ll_crypto_info = llci;
+
+ RETURN(rc);
+}
+
+static int ll_unregister_cops(struct ll_crypto_info *llci)
+{
+ struct list_head *list = &llci->ll_cops_list;
+ struct crypto_ops_item *tmp, *item;
+
+ list_for_each_entry_safe(item, tmp, list, clist) {
+ list_del_init(&item->clist);
+ OBD_FREE(item->ctype, strlen(item->ctype) + 1);
+ OBD_FREE(item, sizeof(*item));
+ }
+ RETURN(0);
+}
+
+int lustre_destroy_crypto(struct super_block *sb)
+{
+ struct ll_crypto_info *llci = ll_s2crpi(sb);
+ ENTRY;
+
+ if (!llci)
+ RETURN(0);
+
+ if (llci->ll_gt_exp)
+ obd_disconnect(llci->ll_gt_exp, 0);
+
+ ll_unregister_cops(llci);
+ OBD_FREE(llci, sizeof(*llci));
+ RETURN(0);
+}
+
+int lustre_init_crypto(struct super_block *sb, char *gkc,
+ struct obd_connect_data *data,
+ int async)
+{
+ struct obd_device *obd = NULL;
+ struct ll_sb_info *sbi = ll_s2sbi(sb);
+ struct lustre_handle gt_conn;
+ int rc = 0;
+ ENTRY;
+
+ rc = ll_init_sb_crypto(sb);
+ if (rc)
+ RETURN(rc);
+
+ if (!gkc || !strcmp(gkc, "null")) {
+ CDEBUG(D_INFO, "No gks Server\n");
+ RETURN(rc);
+ }
+
+ obd = class_name2obd(gkc);
+ if (!obd) {
+ CERROR("GSC %s: not setup or attached\n", gkc);
+ GOTO(out, rc = -EINVAL);
+ }
+
+ obd_set_info(obd->obd_self_export, strlen("async"), "async",
+ sizeof(async), &async);
+
+ rc = obd_connect(>_conn, obd, &sbi->ll_sb_uuid, data,
+ OBD_OPT_REAL_CLIENT);
+ if (rc) {
+ CERROR("cannot connect to %s: rc = %d\n", gkc, rc);
+ GOTO(out, rc);
+ }
+ ll_s2crpi(sb)->ll_gt_exp = class_conn2export(>_conn);
+out:
+ if (rc)
+ lustre_destroy_crypto(sb);
+ RETURN(rc);
+}
+struct crypto_helper_ops *
+ll_gks_find_ops(struct ll_crypto_info *llc_info, char *type)
+{
+ struct list_head *list = &llc_info->ll_cops_list;
+ struct crypto_ops_item *tmp;
+ ENTRY;
+
+ list_for_each_entry(tmp, list, clist) {
+ if (!strcmp(type, tmp->ctype)) {
+ EXIT;
+ return (tmp->cops);
+ }
+ }
+ CERROR("can not find crypto api %s \n", type);
+ RETURN(NULL);
+}
+
+int ll_set_sb_gksinfo(struct super_block *sb, char *type)
+{
+ struct ll_crypto_info *llci = ll_s2crpi(sb);
+ struct obd_export *md_exp = ll_s2mdexp(sb);
+ struct obd_export *dt_exp = ll_s2dtexp(sb);
+ struct crypto_helper_ops *ops;
+ int rc = 0;
+ ENTRY;
+
+ /*try to find the helper ops according to the type*/
+ ops = ll_gks_find_ops(llci, type);
+ if (!ops) {
+ CERROR("can not find the crypto ops by type %s \n", type);
+ RETURN(-EINVAL);
+ }
+ llci->ll_cops = ops;
+ /*set crypto type */
+ rc = obd_set_info(md_exp, strlen("crypto_type"), "crypto_type",
+ strlen(type), type);
+
+ /*set crypt call back func*/
+
+ rc = obd_set_info(dt_exp, strlen("crypto_cb"), "crypto_cb",
+ sizeof(crypt_cb_t), &ll_crypt_cb);
+
+ RETURN(rc);
+}
+
/* mount object entry name */
char ll_gns_oname[PATH_MAX];
+ void *ll_crypto_info;
};
struct ll_gns_ctl {
int ll_readpage(struct file *file, struct page *page);
struct ll_async_page *llap_from_cookie(void *cookie);
struct ll_async_page *llap_from_page(struct page *page, unsigned origin);
-struct ll_async_page *llap_cast_private(struct page *page);
void ll_readahead_init(struct inode *inode, struct ll_readahead_state *ras);
+struct lpage_data *lpd_cast_private(struct page *page);
+
void ll_ra_accounting(struct page *page, struct address_space *mapping);
void ll_truncate(struct inode *inode);
int ll_listxattr(struct dentry *, char *, size_t);
int ll_removexattr(struct dentry *, const char *);
extern int ll_inode_permission(struct inode *, int, struct nameidata *);
+int ll_get_acl(struct inode *, struct posix_acl **acl,
+ struct ptlrpc_request **req);
int ll_refresh_lsm(struct inode *inode, struct lov_stripe_md *lsm);
int ll_extent_lock(struct ll_file_data *, struct inode *,
struct lov_stripe_md *, int mode, ldlm_policy_data_t *,
void ll_och_fill(struct inode *inode, struct lookup_intent *it,
struct obd_client_handle *och);
+int ll_getxattr_internal(struct inode *inode, const char *name,
+ void *value, size_t size, __u64 valid);
#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,5,0))
int ll_getattr(struct vfsmount *mnt, struct dentry *de, struct kstat *stat);
#endif
char *ll_read_opt(const char *opt, char *data);
int ll_set_opt(const char *opt, char *data, int fl);
-void ll_options(char *options, char **ost, char **mds, char **mds_sec,
- char **oss_sec, int *async, int *flags);
+void ll_options(char *options, char **ost, char **mds, char **gss,
+ char **mds_sec, char **oss_sec, int *async, int *flags);
void ll_lli_init(struct ll_inode_info *lli);
int ll_fill_super(struct super_block *sb, void *data, int silent);
int lustre_fill_super(struct super_block *sb, void *data, int silent);
{
return ll_s2mdexp(inode->i_sb);
}
-
static inline int ll_mds_max_easize(struct super_block *sb)
{
return sbi2md(ll_s2sbi(sb))->cl_max_mds_easize;
return ll_i2info(inode)->lli_maxbytes;
}
+
static inline void
ll_inode2id(struct lustre_id *id, struct inode *inode)
{
data->mod_time = LTIME_S(CURRENT_TIME);
}
-/* pass this flag to ll_md_real_close() to send close rpc right away */
-#define FMODE_SYNC 00000010
+struct crypto_helper_ops {
+ int (*init_it_key)(struct inode *inode, struct lookup_intent *it);
+ int (*create_key)(struct inode *dir, mode_t mode, void **key,
+ int* key_size);
+ int (*get_mac)(struct inode *inode, struct iattr *iattr, void*value,
+ int size, void **key, int* key_size);
+ int (*decrypt_key)(struct inode *inode, struct lookup_intent *it);
+ int (*init_inode_key)(struct inode *inode, void *md_key);
+ int (*destroy_key)(struct inode *inode);
+};
+
+/*llite crypto ops for crypto api*/
+struct ll_crypto_info {
+ struct obd_export *ll_gt_exp;
+ struct list_head ll_cops_list;
+ struct crypto_helper_ops *ll_cops;
+ int ll_c_flags;
+};
+#define ll_page2key(page) ((ll_i2info(page->mapping->host))->lli_key_info)
+static inline struct ll_crypto_info* ll_s2crpi(struct super_block *sb)
+{
+ return (struct ll_crypto_info*)ll_s2sbi(sb)->ll_crypto_info;
+}
+static inline struct ll_crypto_info* ll_i2crpi(struct inode *inode)
+{
+ return (struct ll_crypto_info*)ll_i2sbi(inode)->ll_crypto_info;
+}
+
+static inline struct crypto_helper_ops* ll_i2crpops(struct inode *inode)
+{
+ return ll_i2crpi(inode)->ll_cops;
+}
+static inline struct crypto_helper_ops* ll_s2crpops(struct super_block *sb)
+{
+ return ll_s2crpi(sb)->ll_cops;
+}
+static inline struct obd_export *ll_s2gsexp(struct super_block *sb)
+{
+ struct ll_crypto_info *llci = ll_s2crpi(sb);
+ if (llci)
+ return llci->ll_gt_exp;
+ return NULL;
+}
+static inline struct obd_export *ll_i2gsexp(struct inode *inode)
+{
+ return ll_s2gsexp(inode->i_sb);
+}
+
+static inline
+int ll_crypto_init_it_key(struct inode *inode, struct lookup_intent *it)
+{
+ struct ll_crypto_info *lci = ll_i2crpi(inode);
+ if (lci) {
+ struct crypto_helper_ops *ops = lci->ll_cops;;
+ if (ops && ops->init_it_key)
+ return ops->init_it_key(inode, it);
+ }
+ return 0;
+}
+
+static inline
+int ll_crypto_create_key(struct inode *inode, mode_t mode, void **key,
+ int* key_size)
+{
+ struct ll_crypto_info *lci = ll_i2crpi(inode);
+ if (lci) {
+ struct crypto_helper_ops *ops = lci->ll_cops;;
+ if (ops && ops->create_key)
+ return ops->create_key(inode, mode, key, key_size);
+ }
+ return 0;
+}
+
+static inline
+int ll_crypto_get_mac(struct inode *inode, struct iattr *attr, void *acl,
+ int acl_size, void **mac, int *mac_size)
+{
+ struct ll_crypto_info *lci = ll_i2crpi(inode);
+ if (lci) {
+ struct crypto_helper_ops *ops = lci->ll_cops;
+ if (ops && ops->get_mac)
+ return ops->get_mac(inode, attr, acl, acl_size,
+ mac, mac_size);
+ }
+ return 0;
+}
+
+static inline
+int ll_crypto_decrypt_key(struct inode *inode, struct lookup_intent *it)
+{
+ struct ll_crypto_info *lci = ll_i2crpi(inode);
+ if (lci) {
+ struct crypto_helper_ops *ops = lci->ll_cops;
+ if (ops && ops->decrypt_key)
+ return ops->decrypt_key(inode, it);
+ }
+ return 0;
+}
+
+static inline
+int ll_crypto_init_inode_key(struct inode *inode, void *md_key)
+{
+ struct ll_crypto_info *lci = ll_i2crpi(inode);
+ if (lci) {
+ struct crypto_helper_ops *ops = lci->ll_cops;
+ if (ops && ops->init_inode_key)
+ return ops->init_inode_key(inode, md_key);
+ }
+ return 0;
+}
+
+static inline
+int ll_crypto_destroy_inode_key(struct inode *inode)
+{
+ struct ll_crypto_info *lci = ll_i2crpi(inode);
+ if (lci) {
+ struct crypto_helper_ops *ops = lci->ll_cops;
+ if (ops && ops->destroy_key)
+ return ops->destroy_key(inode);
+ }
+ return 0;
+}
+
+int lustre_init_crypto(struct super_block *sb, char *gkc,
+ struct obd_connect_data *data, int async);
+int lustre_destroy_crypto(struct super_block *sb);
+int ll_set_sb_gksinfo(struct super_block *sb, char *type);
+/* pass this flag to ll_md_real_close() to send close rpc right away */
+#define FMODE_SYNC 00000010
#endif /* LLITE_INTERNAL_H */
#include <linux/lustre_dlm.h>
#include <linux/lprocfs_status.h>
#include <linux/lustre_acl.h>
+#include <linux/lustre_gs.h>
#include <linux/lustre_sec.h>
#include "llite_internal.h"
RETURN(rc);
}
-extern struct dentry_operations ll_d_ops;
-
-int lustre_common_fill_super(struct super_block *sb, char *lmv, char *lov,
- int async, char *mds_security, char *oss_security,
- __u32 *nllu, int pag, __u64 *remote)
+static int lustre_connect_mds(struct super_block *sb, char *lmv,
+ struct obd_connect_data *data,
+ char *mds_security, int async, int pag)
{
struct ll_sb_info *sbi = ll_s2sbi(sb);
- struct ptlrpc_request *request = NULL;
- struct lustre_handle dt_conn = {0, };
struct lustre_handle md_conn = {0, };
- struct obd_connect_data *data;
- struct inode *root = NULL;
- struct obd_device *obd;
+ struct obd_device *md_obd;
struct obd_statfs osfs;
- struct lustre_md md;
unsigned long sec_flags;
__u32 valsize;
- int err;
- ENTRY;
-
- obd = class_name2obd(lmv);
- if (!obd) {
+ int err = 0;
+ ENTRY;
+
+ md_obd = class_name2obd(lmv);
+ if (!md_obd) {
CERROR("MDC %s: not setup or attached\n", lmv);
RETURN(-EINVAL);
}
- obd_set_info(obd->obd_self_export, strlen("async"), "async",
- sizeof(async), &async);
- if ((*remote & (OBD_CONNECT_LOCAL | OBD_CONNECT_REMOTE)) ==
- (OBD_CONNECT_LOCAL | OBD_CONNECT_REMOTE)) {
- CERROR("wrong remote flag "LPX64"\n", *remote);
- RETURN(-EINVAL);
- }
-
- OBD_ALLOC(data, sizeof(*data));
- if (!data)
- RETURN(-ENOMEM);
-
- data->ocd_connect_flags |= *remote & (OBD_CONNECT_LOCAL |
- OBD_CONNECT_REMOTE);
- memcpy(data->ocd_nllu, nllu, sizeof(data->ocd_nllu));
-
- if (mds_security == NULL)
- mds_security = "null";
+ obd_set_info(md_obd->obd_self_export, strlen("async"), "async",
+ sizeof(async), &async);
- err = obd_set_info(obd->obd_self_export, strlen("sec"), "sec",
+ err = obd_set_info(md_obd->obd_self_export, strlen("sec"), "sec",
strlen(mds_security), mds_security);
+
if (err) {
CERROR("LMV %s: failed to set security %s, err %d\n",
lmv, mds_security, err);
- OBD_FREE(data, sizeof(*data));
RETURN(err);
}
if (pag) {
sec_flags = PTLRPC_SEC_FL_PAG;
- err = obd_set_info(obd->obd_self_export,
+ err = obd_set_info(md_obd->obd_self_export,
strlen("sec_flags"), "sec_flags",
sizeof(sec_flags), &sec_flags);
if (err) {
}
}
- if (proc_lustre_fs_root) {
- err = lprocfs_register_mountpoint(proc_lustre_fs_root,
- sb, lov, lmv);
- if (err < 0)
- CERROR("could not register mount in /proc/lustre");
- }
-
- err = obd_connect(&md_conn, obd, &sbi->ll_sb_uuid, data,
+ err = obd_connect(&md_conn, md_obd, &sbi->ll_sb_uuid, data,
OBD_OPT_REAL_CLIENT);
if (err == -EBUSY) {
CERROR("An MDS (lmv %s) is performing recovery, of which this"
CERROR("cannot connect to %s: rc = %d\n", lmv, err);
GOTO(out, err);
}
+
sbi->ll_md_exp = class_conn2export(&md_conn);
- err = obd_statfs(obd, &osfs, jiffies - HZ);
+
+ err = obd_statfs(md_obd, &osfs, jiffies - HZ);
if (err)
- GOTO(out_lmv, err);
+ GOTO(out_disconnect, err);
if (!osfs.os_bsize) {
CERROR("Invalid block size is detected.");
- GOTO(out_lmv, err);
+ GOTO(out_disconnect, err);
}
sb->s_magic = LL_SUPER_MAGIC;
&valsize, &sbi->ll_remote);
if (err) {
CERROR("fail to obtain remote flag\n");
- GOTO(out, err);
+ GOTO(out_disconnect, err);
}
+out_disconnect:
+ if (err)
+ obd_disconnect(sbi->ll_md_exp, 0);
+out:
+ RETURN(err);
+}
+static int lustre_connect_ost(struct super_block *sb, char *lov,
+ struct obd_connect_data *data,
+ char *oss_security, int async, int pag)
+{
+ struct ll_sb_info *sbi = ll_s2sbi(sb);
+ struct lustre_handle dt_conn = {0, };
+ struct obd_device *obd = NULL;
+ unsigned long sec_flags;
+ int err, mdsize;
+
obd = class_name2obd(lov);
if (!obd) {
CERROR("OSC %s: not setup or attached\n", lov);
- GOTO(out_lmv, err);
+ GOTO(out, err = -EINVAL);
}
obd_set_info(obd->obd_self_export, strlen("async"), "async",
sizeof(async), &async);
if (err) {
CERROR("LOV %s: failed to set security %s, err %d\n",
lov, oss_security, err);
- OBD_FREE(data, sizeof(*data));
RETURN(err);
}
GOTO(out, err);
} else if (err) {
CERROR("cannot connect to %s: rc = %d\n", lov, err);
- GOTO(out_lmv, err);
+ GOTO(out, err);
}
sbi->ll_dt_exp = class_conn2export(&dt_conn);
err = lustre_init_dt_desc(sbi);
- if (err == 0) {
- int mdsize = obd_size_diskmd(sbi->ll_dt_exp, NULL);
- obd_init_ea_size(sbi->ll_md_exp, mdsize,
- sbi->ll_dt_desc.ld_tgt_count *
- sizeof(struct llog_cookie));
+
+ if (err) {
+ CWARN("init dt_desc error %d \n", err);
+ GOTO(out, err = 0);
}
-
+ mdsize = obd_size_diskmd(sbi->ll_dt_exp, NULL);
+ obd_init_ea_size(sbi->ll_md_exp, mdsize, sbi->ll_dt_desc.ld_tgt_count *
+ sizeof(struct llog_cookie));
+out:
+ RETURN(err);
+}
+
+extern struct dentry_operations ll_d_ops;
+
+static int lustre_init_root_inode(struct super_block *sb)
+{
+ struct ll_sb_info *sbi = ll_s2sbi(sb);
+ struct ptlrpc_request *request = NULL;
+ struct inode *root = NULL;
+ struct lustre_md md;
+ int err = 0;
+ ENTRY;
+
err = md_getstatus(sbi->ll_md_exp, &sbi->ll_rootid);
if (err) {
CERROR("cannot mds_connect: rc = %d\n", err);
- GOTO(out_lov, err);
+ GOTO(out, err);
}
CDEBUG(D_SUPER, "rootid "DLID4"\n", OLID4(&sbi->ll_rootid));
NULL, NULL, 0, 0, &request);
if (err) {
CERROR("md_getattr failed for root: rc = %d\n", err);
- GOTO(out_lov, err);
+ GOTO(out, err);
}
err = mdc_req2lustre_md(sbi->ll_md_exp, request, 0,
if (err) {
CERROR("failed to understand root inode md: rc = %d\n", err);
ptlrpc_req_finished(request);
- GOTO(out_lov, err);
+ GOTO(out, err);
}
LASSERT(id_ino(&sbi->ll_rootid) != 0);
CERROR("lustre_lite: bad iget4 for root\n");
GOTO(out_root, err = -EBADF);
}
+ sb->s_root = d_alloc_root(root);
+ sb->s_root->d_op = &ll_d_ops;
+out_root:
+ if (err)
+ iput(root);
+out:
+ RETURN(err);
+}
+
+int lustre_common_fill_super(struct super_block *sb, char *lmv, char *lov,
+ char *gkc, int async, char *mds_security,
+ char *oss_security, __u32 *nllu, int pag,
+ __u64 *remote)
+{
+ struct ll_sb_info *sbi = ll_s2sbi(sb);
+ struct obd_connect_data *data;
+ int err;
+ ENTRY;
+
+ /*process the connect flags*/
+ if ((*remote & (OBD_CONNECT_LOCAL | OBD_CONNECT_REMOTE)) ==
+ (OBD_CONNECT_LOCAL | OBD_CONNECT_REMOTE)) {
+ CERROR("wrong remote flag "LPX64"\n", *remote);
+ RETURN(-EINVAL);
+ }
+
+ OBD_ALLOC(data, sizeof(*data));
+ if (!data)
+ RETURN(-ENOMEM);
+
+ data->ocd_connect_flags |= *remote & (OBD_CONNECT_LOCAL |
+ OBD_CONNECT_REMOTE);
+ memcpy(data->ocd_nllu, nllu, sizeof(data->ocd_nllu));
+
+ if (proc_lustre_fs_root) {
+ err = lprocfs_register_mountpoint(proc_lustre_fs_root,
+ sb, lov, lmv);
+ if (err < 0)
+ CERROR("could not register mount in /proc/lustre");
+ }
+
+ /*connect mds */
+ err = lustre_connect_mds(sb, lmv, data, mds_security, async, pag);
+ if (err)
+ GOTO(out, err);
+
+ /*connect OST*/
+ err = lustre_connect_ost(sb, lov, data, oss_security, async, pag);
+ if (err)
+ GOTO(out_lmv, err);
+
+ err = lustre_init_crypto(sb, gkc, data, async);
+ if (err) {
+ CERROR("Could not connect to GSS err %d\n", err);
+ err = 0;
+ }
+ /*connect GSS*/
+ err = lustre_init_root_inode(sb);
+ if (err)
+ GOTO(out_gks, err);
err = ll_close_thread_start(&sbi->ll_lcq);
if (err) {
/* bug 2805 - set VM readahead to zero */
vm_max_readahead = vm_min_readahead = 0;
#endif
-
- sb->s_root = d_alloc_root(root);
- sb->s_root->d_op = &ll_d_ops;
-
sb->s_flags |= MS_POSIXACL;
#ifdef S_PDIROPS
CWARN("Enabling PDIROPS\n");
sb->s_flags |= S_PDIROPS;
#endif
-
if (data != NULL)
OBD_FREE(data, sizeof(*data));
RETURN(err);
out_root:
- if (root)
- iput(root);
-out_lov:
- obd_disconnect(sbi->ll_dt_exp, 0);
+ if (sb->s_root)
+ dput(sb->s_root);
+out_gks:
+ lustre_destroy_crypto(sb);
out_lmv:
obd_disconnect(sbi->ll_md_exp, 0);
out:
if (data != NULL)
OBD_FREE(data, sizeof(*data));
lprocfs_unregister_mountpoint(sbi);
- return err;
+ RETURN(err);
}
void lustre_common_put_super(struct super_block *sb)
ll_gns_del_timer(sbi);
ll_close_thread_shutdown(sbi->ll_lcq);
+ lustre_destroy_crypto(sb);
+
list_del(&sbi->ll_conn_chain);
obd_disconnect(sbi->ll_dt_exp, 0);
RETURN(fl);
}
-void ll_options(char *options, char **lov, char **lmv, char **mds_sec,
- char **oss_sec, int *async, int *flags)
+void ll_options(char *options, char **lov, char **lmv, char **gkc,
+ char **mds_sec, char **oss_sec, int *async, int *flags)
{
char *this_char;
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0))
continue;
if (!*lmv && (*lmv = ll_read_opt("mdc", this_char)))
continue;
+ if (!*gkc && (*gkc = ll_read_opt("gkc", this_char)))
+ continue;
if (!strncmp(this_char, "lasync", strlen("lasync"))) {
*async = 1;
continue;
lli->lli_mds_exec_och = NULL;
lli->lli_open_fd_read_count = lli->lli_open_fd_write_count = 0;
lli->lli_open_fd_exec_count = 0;
+ lli->lli_key_info = NULL;
}
int ll_fill_super(struct super_block *sb, void *data, int silent)
{
struct ll_sb_info *sbi;
- char *lov = NULL;
- char *lmv = NULL;
+ char *lov = NULL, *lmv = NULL, *gkc = NULL;
char *mds_sec = NULL;
char *oss_sec = NULL;
int async, err;
RETURN(-ENOMEM);
sbi->ll_flags |= LL_SBI_READAHEAD;
- ll_options(data, &lov, &lmv, &mds_sec, &oss_sec,
+ ll_options(data, &lov, &lmv, &gkc, &mds_sec, &oss_sec,
&async, &sbi->ll_flags);
- if (!lov) {
- CERROR("no osc\n");
- GOTO(out, err = -EINVAL);
- }
-
- if (!lmv) {
- CERROR("no mdc\n");
+ if (!lov || !lmv) {
+ CERROR("no osc %p or no mdc %p\n", lov, lmv);
GOTO(out, err = -EINVAL);
}
- err = lustre_common_fill_super(sb, lmv, lov, async, mds_sec, oss_sec,
- nllu, 0, &remote_flag);
+ err = lustre_common_fill_super(sb, lmv, lov, gkc, async, mds_sec,
+ oss_sec, nllu, 0, &remote_flag);
EXIT;
out:
if (err)
struct obd_device *obd;
int next = 0;
- while ((obd = class_devices_in_group(&sbi->ll_sb_uuid, &next)) != NULL)
- {
+ while ((obd = class_devices_in_group(&sbi->ll_sb_uuid, &next)) != NULL) {
int err;
lustre_cfg_bufs_reset(&bufs, obd->obd_name);
class_del_profile(sbi->ll_lmd->lmd_profile);
}
+static int lustre_process_profile(struct super_block *sb,
+ struct lustre_mount_data *lmd,
+ char **lov, char **lmv, char **gkc)
+{
+ struct ll_sb_info *sbi = ll_s2sbi(sb);
+ struct lustre_profile *lprof;
+ struct config_llog_instance cfg;
+ int len, err = 0;
+
+ ENTRY;
+
+ if (!lmd->lmd_profile)
+ RETURN(0);
+
+ if (lmd->lmd_mds[0] == '\0') {
+ CERROR("no mds name\n");
+ GOTO(out, err = -EINVAL);
+ }
+ lmd->lmd_mds_security[sizeof(lmd->lmd_mds_security) - 1] = 0;
+ lmd->lmd_oss_security[sizeof(lmd->lmd_oss_security) - 1] = 0;
+
+ OBD_ALLOC(sbi->ll_lmd, sizeof(*sbi->ll_lmd));
+ if (sbi->ll_lmd == NULL)
+ GOTO(out, err = -ENOMEM);
+ memcpy(sbi->ll_lmd, lmd, sizeof(*lmd));
+
+ /* generate a string unique to this super, let's try
+ the address of the super itself.*/
+ len = (sizeof(sb) * 2) + 1;
+ OBD_ALLOC(sbi->ll_instance, len);
+ if (sbi->ll_instance == NULL)
+ GOTO(out, err = -ENOMEM);
+ sprintf(sbi->ll_instance, "%p", sb);
+
+ cfg.cfg_instance = sbi->ll_instance;
+ cfg.cfg_uuid = sbi->ll_sb_uuid;
+ cfg.cfg_local_nid = lmd->lmd_local_nid;
+ err = lustre_process_log(lmd, lmd->lmd_profile, &cfg, 0);
+ if (err < 0) {
+ CERROR("Unable to process log: %s\n", lmd->lmd_profile);
+ GOTO(out, err);
+ }
+
+ lprof = class_get_profile(lmd->lmd_profile);
+ if (lprof == NULL) {
+ CERROR("No profile found: %s\n", lmd->lmd_profile);
+ GOTO(out, err = -EINVAL);
+ }
+
+ OBD_ALLOC(*lov, strlen(lprof->lp_lov) +
+ strlen(sbi->ll_instance) + 2);
+ sprintf(*lov, "%s-%s", lprof->lp_lov, sbi->ll_instance);
+
+ OBD_ALLOC(*lmv, strlen(lprof->lp_lmv) +
+ strlen(sbi->ll_instance) + 2);
+ sprintf(*lmv, "%s-%s", lprof->lp_lmv, sbi->ll_instance);
+
+ if (lprof->lp_gkc) {
+ OBD_ALLOC(*gkc, strlen(lprof->lp_gkc) +
+ strlen(sbi->ll_instance) + 2);
+ sprintf(*gkc, "%s-%s", lprof->lp_gkc, sbi->ll_instance);
+ }
+out:
+ RETURN(err);
+}
+
+static int lustre_clean_profile(struct ll_sb_info *sbi, int force_umount)
+{
+ struct lustre_mount_data *lmd = sbi->ll_lmd;
+ struct config_llog_instance cfg;
+ char *cl_prof;
+ int len, err = 0;
+ ENTRY;
+
+ if (!lmd)
+ RETURN(err);
+
+ len = strlen(sbi->ll_lmd->lmd_profile) + sizeof("-clean") + 1;
+
+ if (force_umount) {
+ CERROR("force umount, doing manual cleanup\n");
+ lustre_manual_cleanup(sbi);
+ GOTO(free_lmd, 0);
+
+ }
+ if (sbi->ll_instance != NULL) {
+ cfg.cfg_instance = sbi->ll_instance;
+ cfg.cfg_uuid = sbi->ll_sb_uuid;
+
+ OBD_ALLOC(cl_prof, len);
+ sprintf(cl_prof, "%s-clean", lmd->lmd_profile);
+ err = lustre_process_log(lmd, cl_prof, &cfg, 0);
+ if (err < 0) {
+ CERROR("Unable to process log: %s\n", cl_prof);
+ lustre_manual_cleanup(sbi);
+ }
+ OBD_FREE(cl_prof, len);
+ }
+free_lmd:
+ if (sbi->ll_instance)
+ OBD_FREE(sbi->ll_instance, strlen(sbi->ll_instance) + 1);
+ OBD_FREE(sbi->ll_lmd, sizeof(*sbi->ll_lmd));
+ RETURN(err);
+}
+
int lustre_fill_super(struct super_block *sb, void *data, int silent)
{
struct lustre_mount_data * lmd = data;
- char *lov = NULL, *lmv = NULL;
+ char *lov = NULL, *lmv = NULL, *gkc = NULL;
struct ll_sb_info *sbi;
int err;
ENTRY;
sbi->ll_flags |= LL_SBI_READAHEAD;
- if (lmd->lmd_profile) {
- struct lustre_profile *lprof;
- struct config_llog_instance cfg;
- int len;
-
- if (lmd->lmd_mds[0] == '\0') {
- CERROR("no mds name\n");
- GOTO(out_free, err = -EINVAL);
- }
- lmd->lmd_mds_security[sizeof(lmd->lmd_mds_security) - 1] = 0;
- lmd->lmd_oss_security[sizeof(lmd->lmd_oss_security) - 1] = 0;
-
- OBD_ALLOC(sbi->ll_lmd, sizeof(*sbi->ll_lmd));
- if (sbi->ll_lmd == NULL)
- GOTO(out_free, err = -ENOMEM);
- memcpy(sbi->ll_lmd, lmd, sizeof(*lmd));
-
- /* generate a string unique to this super, let's try
- the address of the super itself.*/
- len = (sizeof(sb) * 2) + 1;
- OBD_ALLOC(sbi->ll_instance, len);
- if (sbi->ll_instance == NULL)
- GOTO(out_free, err = -ENOMEM);
- sprintf(sbi->ll_instance, "%p", sb);
-
- cfg.cfg_instance = sbi->ll_instance;
- cfg.cfg_uuid = sbi->ll_sb_uuid;
- cfg.cfg_local_nid = lmd->lmd_local_nid;
- err = lustre_process_log(lmd, lmd->lmd_profile, &cfg, 0);
- if (err < 0) {
- CERROR("Unable to process log: %s\n", lmd->lmd_profile);
- GOTO(out_free, err);
- }
-
- lprof = class_get_profile(lmd->lmd_profile);
- if (lprof == NULL) {
- CERROR("No profile found: %s\n", lmd->lmd_profile);
- GOTO(out_free, err = -EINVAL);
- }
- if (lov)
- OBD_FREE(lov, strlen(lov) + 1);
- OBD_ALLOC(lov, strlen(lprof->lp_lov) +
- strlen(sbi->ll_instance) + 2);
- sprintf(lov, "%s-%s", lprof->lp_lov, sbi->ll_instance);
-
- if (lmv)
- OBD_FREE(lmv, strlen(lmv) + 1);
- OBD_ALLOC(lmv, strlen(lprof->lp_lmv) +
- strlen(sbi->ll_instance) + 2);
- sprintf(lmv, "%s-%s", lprof->lp_lmv, sbi->ll_instance);
- }
-
- if (!lov) {
- CERROR("no osc\n");
- GOTO(out_free, err = -EINVAL);
+ err = lustre_process_profile(sb, lmd, &lov, &lmv, &gkc);
+ if (err) {
+ CERROR("Can not process the profile err %d \n", err);
+ GOTO(out_free, err);
}
-
- if (!lmv) {
- CERROR("no mdc\n");
+ if (!lov || !lmv) {
+ CERROR("no osc %p or no mdc %p \n", lov, lmv);
GOTO(out_free, err = -EINVAL);
}
- err = lustre_common_fill_super(sb, lmv, lov, lmd->lmd_async,
+ err = lustre_common_fill_super(sb, lmv, lov, gkc, lmd->lmd_async,
lmd->lmd_mds_security,
lmd->lmd_oss_security,
&lmd->lmd_nllu, lmd->lmd_pag,
OBD_FREE(lmv, strlen(lmv) + 1);
if (lov)
OBD_FREE(lov, strlen(lov) + 1);
-
+ if (gkc)
+ OBD_FREE(gkc, strlen(gkc) + 1);
+
RETURN(err);
-
out_free:
- if (sbi->ll_lmd) {
- int len = strlen(sbi->ll_lmd->lmd_profile) + sizeof("-clean")+1;
- int err;
-
- if (sbi->ll_instance != NULL) {
- struct lustre_mount_data *lmd = sbi->ll_lmd;
- struct config_llog_instance cfg;
- char *cl_prof;
-
- cfg.cfg_instance = sbi->ll_instance;
- cfg.cfg_uuid = sbi->ll_sb_uuid;
-
- OBD_ALLOC(cl_prof, len);
- sprintf(cl_prof, "%s-clean", lmd->lmd_profile);
- err = lustre_process_log(lmd, cl_prof, &cfg, 0);
- if (err < 0) {
- CERROR("Unable to process log: %s\n", cl_prof);
- lustre_manual_cleanup(sbi);
- }
- OBD_FREE(cl_prof, len);
- OBD_FREE(sbi->ll_instance, strlen(sbi->ll_instance) + 1);
- }
- OBD_FREE(sbi->ll_lmd, sizeof(*sbi->ll_lmd));
- }
+ lustre_clean_profile(sbi, 0);
lustre_free_sbi(sb);
- goto out_dev;
+ GOTO(out_dev, err);
+
} /* lustre_fill_super */
void lustre_put_super(struct super_block *sb)
obd = NULL;
lustre_common_put_super(sb);
- if (sbi->ll_lmd != NULL) {
- char *cl_prof;
- int len = strlen(sbi->ll_lmd->lmd_profile) + sizeof("-clean")+1;
- int err;
- struct config_llog_instance cfg;
-
- if (force_umount) {
- CERROR("force umount, doing manual cleanup\n");
- lustre_manual_cleanup(sbi);
- GOTO(free_lmd, 0);
- }
-
- cfg.cfg_instance = sbi->ll_instance;
- cfg.cfg_uuid = sbi->ll_sb_uuid;
-
- OBD_ALLOC(cl_prof, len);
- sprintf(cl_prof, "%s-clean", sbi->ll_lmd->lmd_profile);
- err = lustre_process_log(sbi->ll_lmd, cl_prof, &cfg, 0);
- if (err < 0) {
- CERROR("Unable to process log: %s, doing manual cleanup"
- "\n", cl_prof);
- lustre_manual_cleanup(sbi);
- }
-
- OBD_FREE(cl_prof, len);
- free_lmd:
- OBD_FREE(sbi->ll_lmd, sizeof(*sbi->ll_lmd));
- OBD_FREE(sbi->ll_instance, strlen(sbi->ll_instance) + 1);
- }
-
+ lustre_clean_profile(sbi, force_umount);
lustre_free_sbi(sb);
EXIT;
(struct lov_stripe_md **) &lli->lli_mea);
lli->lli_mea = NULL;
}
-
+ ll_crypto_destroy_inode_key(inode);
if (lli->lli_symlink_name) {
OBD_FREE(lli->lli_symlink_name,
strlen(lli->lli_symlink_name) + 1);
* inode ourselves so we can call obdo_from_inode() always. */
if (ia_valid & (lsm ? ~(ATTR_SIZE | ATTR_FROM_OPEN /*| ATTR_RAW*/) : ~0)) {
struct lustre_md md;
+ void *key = NULL;
+ int key_size = 0;
OBD_ALLOC(op_data, sizeof(*op_data));
if (op_data == NULL)
RETURN(-ENOMEM);
ll_prepare_mdc_data(op_data, inode, NULL, NULL, 0, 0);
+ if (ia_valid & (ATTR_UID | ATTR_GID)) {
+ rc = ll_crypto_get_mac(inode, attr, NULL, 0, &key,
+ &key_size);
+ }
rc = md_setattr(sbi->ll_md_exp, op_data,
- attr, NULL, 0, NULL, 0, &request);
+ attr, key, key_size, NULL, 0, NULL,
+ 0, &request);
OBD_FREE(op_data, sizeof(*op_data));
+
+ if (key && key_size)
+ OBD_FREE(key, key_size);
if (rc) {
ptlrpc_req_finished(request);
if (rc != -EPERM && rc != -EACCES)
CERROR("md_setattr fails: rc = %d\n", rc);
RETURN(rc);
}
-
rc = mdc_req2lustre_md(sbi->ll_md_exp, request, 0,
sbi->ll_dt_exp, &md);
if (rc) {
struct mea *mea = md->mea;
struct posix_acl *posix_acl = md->posix_acl;
struct ll_sb_info *sbi = ll_i2sbi(inode);
+ struct lustre_key *mkey = md->key;
ENTRY;
LASSERT((lsm != NULL) == ((body->valid & OBD_MD_FLEASIZE) != 0));
if (body->valid & OBD_MD_FLSIZE)
set_bit(LLI_F_HAVE_MDS_SIZE_LOCK, &lli->lli_flags);
+ if (mkey != NULL) {
+ LASSERT(body->valid & OBD_MD_FLKEY);
+ ll_crypto_init_inode_key(inode, mkey);
+ }
+
#if (LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0))
inode->i_dev = (kdev_t)id_group(&lli->lli_id);
#endif
attr.ia_valid |= ATTR_ATTR_FLAG;
rc = md_setattr(sbi->ll_md_exp, op_data,
- &attr, NULL, 0, NULL, 0, &req);
+ &attr, NULL, 0, NULL, 0, NULL, 0, &req);
OBD_FREE(op_data, sizeof(*op_data));
if (rc) {
ptlrpc_req_finished(req);
return rc;
}
-
int ll_flush_cred(struct inode *inode)
{
struct ll_sb_info *sbi = ll_i2sbi(inode);
icbd.icbd_childp = &dentry;
icbd.icbd_parent = parent;
ll_inode2id(&pid, parent);
-
+
+ /*ONLY need key for open_create file*/
+ rc = ll_crypto_init_it_key(parent, it);
+ if (rc != 0)
+ GOTO(out, retval = ERR_PTR(rc));
+
rc = md_intent_lock(ll_i2mdexp(parent), &pid, (char *)dentry->d_name.name,
dentry->d_name.len, NULL, 0, NULL, it, flags, &req,
ll_mdc_blocking_ast);
struct inode *dir = nd->dentry->d_inode;
struct ll_sb_info *sbi = ll_i2sbi(dir);
struct mdc_op_data *op_data;
- int err = -EMLINK;
+ int err = -EMLINK, key_size = 0;
+ void *key = NULL;
ENTRY;
CDEBUG(D_VFSTRACE, "VFS Op:name=%.*s,dir=%lu/%u(%p)\n",
switch (mode & S_IFMT) {
case 0:
- case S_IFREG:
+ case S_IFREG:
mode |= S_IFREG; /* for mode = 0 case, fallthrough */
+ ll_crypto_create_key(dir, mode, &key, &key_size);
case S_IFCHR:
case S_IFBLK:
case S_IFIFO:
ll_prepare_mdc_data(op_data, dir, NULL,
(char *)nd->last.name,
nd->last.len, 0);
-
- err = md_create(sbi->ll_md_exp, op_data, NULL, 0, mode,
+ err = md_create(sbi->ll_md_exp, op_data, key, key_size, mode,
current->fsuid, current->fsgid, rdev,
&request);
OBD_FREE(op_data, sizeof(*op_data));
default:
err = -EINVAL;
}
+ if (key && key_size)
+ OBD_FREE(key, key_size);
RETURN(err);
}
case 0:
case S_IFREG:
mode |= S_IFREG; /* for mode = 0 case, fallthrough */
+
case S_IFCHR:
case S_IFBLK:
case S_IFIFO:
up(&lli->lli_size_sem);
} /* ll_truncate */
+struct ll_async_page *llap_cast_private(struct page *page)
+{
+ struct ll_async_page *llap = (struct ll_async_page *)page->private;
+
+ LASSERTF(llap == NULL || llap->llap_magic == LLAP_MAGIC,
+ "page %p private %lu gave magic %d which != %d\n",
+ page, page->private, llap->llap_magic, LLAP_MAGIC);
+ return llap;
+}
+
int ll_prepare_write(struct file *file, struct page *page,
unsigned from, unsigned to)
{
};
-struct ll_async_page *llap_cast_private(struct page *page)
-{
- struct ll_async_page *llap = (struct ll_async_page *)page->private;
-
- LASSERTF(llap == NULL || llap->llap_magic == LLAP_MAGIC,
- "page %p private %lu gave magic %d which != %d\n",
- page, page->private, llap->llap_magic, LLAP_MAGIC);
-
- return llap;
-}
-
/* XXX have the exp be an argument? */
struct ll_async_page *llap_from_page(struct page *page, unsigned origin)
{
LASSERTF(origin < LLAP__ORIGIN_MAX, "%u\n", origin);
llap = llap_cast_private(page);
- if (llap != NULL)
+ if (llap != NULL) {
GOTO(out, llap);
-
+ }
exp = ll_i2dtexp(page->mapping->host);
if (exp == NULL)
RETURN(ERR_PTR(-EINVAL));
-
+
OBD_ALLOC(llap, sizeof(*llap));
- if (llap == NULL)
+ if (llap == NULL) {
RETURN(ERR_PTR(-ENOMEM));
+ }
llap->llap_magic = LLAP_MAGIC;
INIT_LIST_HEAD(&llap->llap_pending_write);
rc = obd_prep_async_page(exp, ll_i2info(inode)->lli_smd, NULL, page,
CDEBUG(D_CACHE, "llap %p page %p cookie %p obj off "LPU64"\n", llap,
page, llap->llap_cookie, (obd_off)page->index << PAGE_SHIFT);
- /* also zeroing the PRIVBITS low order bitflags */
+
__set_page_ll_data(page, llap);
+
+ /* also zeroing the PRIVBITS low order bitflags */
llap->llap_page = page;
spin_lock(&sbi->ll_lock);
rc = oig_init(&oig);
if (rc)
GOTO(out, rc);
-
rc = obd_queue_group_io(exp, lsm, NULL, oig, llap->llap_cookie,
OBD_BRW_WRITE, 0, to, 0, ASYNC_READY |
ASYNC_URGENT | ASYNC_COUNT_STABLE |
EXIT;
return;
}
-
llap = llap_from_page(page, 0);
if (IS_ERR(llap)) {
CERROR("page %p ind %lu couldn't find llap: %ld\n", page,
page_cache_get(page);
llap->llap_defer_uptodate = defer;
llap->llap_ra_used = 0;
+
rc = obd_queue_group_io(exp, ll_i2info(page->mapping->host)->lli_smd,
NULL, oig, llap->llap_cookie, OBD_BRW_READ, 0,
PAGE_SIZE, 0, ASYNC_COUNT_STABLE | ASYNC_READY
- | ASYNC_URGENT);
+ | ASYNC_URGENT);
if (rc) {
LL_CDEBUG_PAGE(D_ERROR, page, "read queue failed: rc %d\n", rc);
page_cache_release(page);
llap = llap_from_page(page, LLAP_ORIGIN_READPAGE);
if (IS_ERR(llap))
GOTO(out, rc = PTR_ERR(llap));
-
+
if (ll_i2sbi(inode)->ll_flags & LL_SBI_READAHEAD)
ras_update(ll_i2sbi(inode), &fd->fd_ras, page->index,
llap->llap_defer_uptodate);
static int lmv_setattr(struct obd_export *exp, struct mdc_op_data *data,
struct iattr *iattr, void *ea, int ealen, void *ea2,
- int ea2len, struct ptlrpc_request **request)
+ int ea2len, void *ea3, int ea3len,
+ struct ptlrpc_request **request)
{
struct obd_device *obd = exp->exp_obd;
struct lmv_obd *lmv = &obd->u.lmv;
data->id1 = obj->objs[i].id;
rc = md_setattr(lmv->tgts[id_group(&data->id1)].ltd_exp,
- data, iattr, ea, ealen, ea2, ea2len, &req);
+ data, iattr, ea, ealen, ea2, ea2len,
+ ea3, ea3len, &req);
if (id_equal_fid(&obj->id, &obj->objs[i].id)) {
/*
} else {
LASSERT(id_group(&data->id1) < lmv->desc.ld_tgt_count);
rc = md_setattr(lmv->tgts[id_group(&data->id1)].ltd_exp,
- data, iattr, ea, ealen, ea2, ea2len, request);
+ data, iattr, ea, ealen, ea2, ea2len, ea3,
+ ea3len, request);
if (rc == 0) {
body = lustre_msg_buf((*request)->rq_repmsg, 0,
sizeof(*body));
RETURN(rc);
}
- if ((keylen == strlen("flush_cred") &&
- strcmp(key, "flush_cred") == 0)) {
+ if (((keylen == strlen("flush_cred") &&
+ strcmp(key, "flush_cred") == 0)) ||
+ ((keylen == strlen("crypto_type") &&
+ strcmp(key, "crypto_type") == 0))) {
int rc = 0, i;
for (i = 0, tgt = lmv->tgts; i < lmv->desc.ld_tgt_count;
}
LDLM_ERROR(data->lock, "lock on inode without such object");
dump_lsm(D_ERROR, data->lsm);
+ portals_debug_dumpstack(NULL);
RETURN(-ENXIO);
} else if (keylen >= strlen("size_to_stripe") &&
strcmp(key, "size_to_stripe") == 0) {
spin_unlock(&lov->lov_lock);
RETURN(rc);
- } else if (KEY_IS("flush_cred")) {
+ } else if (KEY_IS("flush_cred") || KEY_IS("crypto_cb")) {
struct lov_tgt_desc *tgt;
int rc = 0, i;
#define XATTR_LUSTRE_MDS_MEA_EA "mea"
#define XATTR_LUSTRE_MDS_MID_EA "mid"
#define XATTR_LUSTRE_MDS_SID_EA "sid"
+#define XATTR_LUSTRE_MDS_KEY_EA "key"
/*
* We don't currently need any additional blocks for rmdir and
XATTR_LUSTRE_MDS_MID_EA,
lmm, lmm_size);
break;
+ case EA_KEY:
+ rc = fsfilt_ext3_set_xattr(inode, handle,
+ XATTR_LUSTRE_MDS_KEY_EA,
+ lmm, lmm_size);
+ break;
default:
return -EINVAL;
}
XATTR_LUSTRE_MDS_MID_EA,
lmm, lmm_size);
break;
+ case EA_KEY:
+ rc = fsfilt_ext3_get_xattr(inode,
+ XATTR_LUSTRE_MDS_KEY_EA,
+ lmm, lmm_size);
+ break;
default:
return -EINVAL;
}
void mdc_getattr_pack(struct lustre_msg *msg, int offset,
__u64 valid, int flags, struct mdc_op_data *data);
+
void mdc_open_pack(struct lustre_msg *msg, int offset,
- struct mdc_op_data *op_data, __u32 mode, __u64 rdev,
- __u32 flags, const void *lmm, int lmmlen);
+ struct mdc_op_data *op_data, __u32 mode,
+ __u64 rdev, __u32 flags, const void *lmm,
+ int lmmlen, void *key, int keylen);
void mdc_readdir_pack(struct ptlrpc_request *req, int req_offset,
__u64 offset, __u32 size, struct lustre_id *mdc_id);
void mdc_close_pack(struct ptlrpc_request *req, int offset, struct obdo *oa,
b->nlink = size; /* !! */
}
-static __u32 mds_pack_open_flags(__u32 flags)
-{
- return
- (flags & (FMODE_READ | FMODE_WRITE | FMODE_EXEC |
- MDS_OPEN_DELAY_CREATE | MDS_OPEN_HAS_EA |
- MDS_OPEN_HAS_OBJS)) |
- ((flags & O_CREAT) ? MDS_OPEN_CREAT : 0) |
- ((flags & O_EXCL) ? MDS_OPEN_EXCL : 0) |
- ((flags & O_TRUNC) ? MDS_OPEN_TRUNC : 0) |
- ((flags & O_APPEND) ? MDS_OPEN_APPEND : 0) |
- ((flags & O_SYNC) ? MDS_OPEN_SYNC : 0) |
- ((flags & O_DIRECTORY) ? MDS_OPEN_DIRECTORY : 0) |
- 0;
-}
-
/* packing of MDS records */
void mdc_open_pack(struct lustre_msg *msg, int offset,
struct mdc_op_data *op_data, __u32 mode,
__u64 rdev, __u32 flags, const void *lmm,
- int lmmlen)
+ int lmmlen, void *key, int keylen)
{
struct mds_rec_create *rec;
char *tmp;
tmp = lustre_msg_buf(msg, offset + 2, lmmlen);
memcpy (tmp, lmm, lmmlen);
}
+ if (key) {
+ rec->cr_flags |= MDS_OPEN_HAS_KEY;
+ tmp = lustre_msg_buf(msg, offset + 3, keylen);
+ memcpy(tmp, key, keylen);
+ }
}
void mdc_getattr_pack(struct lustre_msg *msg, int offset,
#include <linux/lustre_sec.h>
#include <linux/lprocfs_status.h>
#include <linux/lustre_acl.h>
+#include <linux/lustre_gs.h>
#include <linux/lustre_lite.h>
#include "mdc_internal.h"
reqsize[0] = lustre_secdesc_size();
if (it->it_op & IT_OPEN) {
+ struct lustre_intent_data *lustre_data =
+ (struct lustre_intent_data *) it->d.fs_data;
it->it_create_mode |= S_IFREG;
it->it_create_mode &= ~current->fs->umask;
reqsize[req_buffers++] = sizeof(struct mds_rec_create);
reqsize[req_buffers++] = data->namelen + 1;
reqsize[req_buffers++] = obddev->u.cli.cl_max_mds_easize;
-
+ /*pack the lustre key*/
+ if (lustre_data->it_key_size > 0 && lustre_data->it_key)
+ reqsize[req_buffers++] = lustre_data->it_key_size;
+
req = ptlrpc_prep_req(class_exp2cliimp(exp), LUSTRE_DLM_VERSION,
LDLM_ENQUEUE, req_buffers, reqsize, NULL);
if (!req)
/* pack the intended request */
mdc_open_pack(req->rq_reqmsg, MDS_REQ_INTENT_REC_OFF, data,
- it->it_create_mode, 0, it->it_flags, lmm, lmmsize);
+ it->it_create_mode, 0, it->it_flags, lmm, lmmsize,
+ lustre_data->it_key, lustre_data->it_key_size);
/* get ready for the reply */
- repsize[3] = 4;
- repsize[4] = xattr_acl_size(LL_ACL_MAX_ENTRIES);
- reply_buffers = 5;
- req->rq_replen = lustre_msg_size(5, repsize);
+ reply_buffers = 3;
+ repsize[reply_buffers++] = sizeof(int);
+ repsize[reply_buffers++] = xattr_acl_size(LL_ACL_MAX_ENTRIES);
+ repsize[reply_buffers++] = sizeof(int);
+ repsize[reply_buffers++] = sizeof(struct crypto_key);
+ req->rq_replen = lustre_msg_size(reply_buffers, repsize);
} else if (it->it_op & (IT_GETATTR | IT_LOOKUP | IT_CHDIR)) {
__u64 valid = data->valid | OBD_MD_FLNOTOBD | OBD_MD_FLEASIZE |
- OBD_MD_FLACL;
+ OBD_MD_FLACL | OBD_MD_FLKEY;
/* we don't expect xattr retrieve could reach here */
LASSERT(!(valid & (OBD_MD_FLXATTR | OBD_MD_FLXATTRLIST)));
valid, it->it_flags, data);
/* get ready for the reply */
- repsize[3] = 4;
- repsize[4] = xattr_acl_size(LL_ACL_MAX_ENTRIES);
- reply_buffers = 5;
- req->rq_replen = lustre_msg_size(5, repsize);
+ reply_buffers = 3;
+ repsize[reply_buffers++] = sizeof(int);
+ repsize[reply_buffers++] = xattr_acl_size(LL_ACL_MAX_ENTRIES);
+ repsize[reply_buffers++] = sizeof(int);
+ repsize[reply_buffers++] = sizeof(struct crypto_key);
+ req->rq_replen = lustre_msg_size(reply_buffers, repsize);
} else if (it->it_op == IT_READDIR) {
policy.l_inodebits.bits = MDS_INODELOCK_UPDATE;
req = ptlrpc_prep_req(class_exp2cliimp(exp), LUSTRE_DLM_VERSION,
/* We know what to expect, so we do any byte flipping required here */
LASSERT(reply_buffers == 5 || reply_buffers == 4 ||
- reply_buffers == 3 || reply_buffers == 1);
+ reply_buffers == 3 || reply_buffers == 1 ||
+ reply_buffers == 6 || reply_buffers == 7);
if (reply_buffers >= 3) {
struct mds_body *body;
LASSERT(replayea);
memcpy(replayea, eadata, body->eadatasize);
- LASSERT(req->rq_reqmsg->bufcount == 6);
+ LASSERT(req->rq_reqmsg->bufcount == 6 ||
+ req->rq_reqmsg->bufcount == 7);
req->rq_reqmsg->buflens[5] = body->eadatasize;
/* If this isn't the last buffer, we might
* have to shift other data around. */
* setattr portal. */
int mdc_setattr(struct obd_export *exp, struct mdc_op_data *data,
struct iattr *iattr, void *ea, int ealen, void *ea2,
- int ea2len, struct ptlrpc_request **request)
+ int ea2len, void *ea3, int ea3len,
+ struct ptlrpc_request **request)
{
struct ptlrpc_request *req;
struct mds_rec_setattr *rec;
bufcount++;
if (ea2len > 0)
bufcount++;
+ if (ea3len > 0)
+ bufcount++;
}
req = ptlrpc_prep_req(class_exp2cliimp(exp), LUSTRE_MDS_VERSION,
CDEBUG(D_INODE, "setting mtime %lu, ctime %lu\n",
LTIME_S(iattr->ia_mtime), LTIME_S(iattr->ia_ctime));
mdc_setattr_pack(req->rq_reqmsg, 1, data, iattr, ea, ealen,
- ea2, ea2len);
+ ea2, ea2len, ea3, ea3len);
/* prepare the reply buffer
*/
#include <linux/lustre_sec.h>
#include <linux/lprocfs_status.h>
#include <linux/lustre_acl.h>
+#include <linux/lustre_gs.h>
#include "mdc_internal.h"
#define REQUEST_MINOR 244
reqbody = lustre_msg_buf(req->rq_reqmsg, 1, sizeof(*reqbody));
LASSERT(!(reqbody->valid & OBD_MD_FLACL));
+ if (reqbody->valid & OBD_MD_FLKEY) {
+ repsize[bufcount++] = 5;
+ repsize[bufcount++] = sizeof(struct lustre_key);
+ }
+
req->rq_replen = lustre_msg_size(bufcount, repsize);
mdc_get_rpc_lock(exp->exp_obd->u.cli.cl_rpc_lock, NULL);
return 0;
}
+static int mdc_unpack_acl(struct obd_export *exp_lmv, struct ptlrpc_request *req,
+ unsigned int *offset, struct lustre_md *md)
+{
+ struct posix_acl *acl;
+ struct mds_remote_perm *perm;
+ int size, acl_off = 0, rc = 0;
+ void *buf;
+
+ /* if anything wrong when unpacking md, we don't check acl
+ * stuff, for simplicity
+ */
+ if (md->body->valid & OBD_MD_FLACL) {
+ acl_off = *offset;
+ if (md->body->valid & OBD_MD_FLRMTACL) {
+
+ buf = lustre_swab_repbuf(req, acl_off++, sizeof(*perm),
+ lustre_swab_remote_perm);
+ if (buf == NULL) {
+ CERROR("Can't unpack remote perm\n");
+ RETURN(0);
+ }
+ OBD_ALLOC(perm, sizeof(*perm));
+ if (!perm)
+ RETURN(-ENOMEM);
+ memcpy(perm, buf, sizeof(*perm));
+ md->remote_perm = perm;
+ *offset = acl_off;
+ } else {
+ size = le32_to_cpu(*(__u32 *) lustre_msg_buf(
+ req->rq_repmsg, acl_off++, 4));
+ buf = lustre_msg_buf(req->rq_repmsg, acl_off++, size);
+
+ acl = posix_acl_from_xattr(buf, size);
+ *offset = acl_off;
+ if (IS_ERR(acl)) {
+ rc = PTR_ERR(acl);
+ CERROR("convert xattr to acl failed: %d\n", rc);
+ RETURN(0);
+ } else if (acl) {
+ rc = posix_acl_valid(acl);
+ if (rc) {
+ CERROR("acl valid error: %d\n", rc);
+ posix_acl_release(acl);
+ RETURN(0);
+ }
+ }
+ md->posix_acl = acl;
+ }
+ }
+ RETURN(rc);
+}
+static int mdc_unpack_gskey(struct obd_export *exp_lmv, struct ptlrpc_request *req,
+ unsigned int *offset, struct lustre_md *md)
+{
+ int key_off = 0, rc = 0, size = 0;
+ void *buf;
+
+ key_off = *offset;
+ if (md->body->valid & OBD_MD_FLKEY) {
+ size = le32_to_cpu(*(__u32 *) lustre_msg_buf(req->rq_repmsg,
+ key_off++, 4));
+ buf = lustre_msg_buf(req->rq_repmsg, key_off++, size);
+
+ CDEBUG(D_INFO, "buf %p key_off %d size %d \n",
+ buf, key_off, size);
+ md->key = (struct lustre_key *)buf;
+ *offset = key_off;
+ }
+ RETURN(rc);
+}
int mdc_req2lustre_md(struct obd_export *exp_lmv, struct ptlrpc_request *req,
unsigned int offset, struct obd_export *exp_lov,
struct lustre_md *md)
{
struct lov_mds_md *lmm;
- struct posix_acl *acl;
- struct mds_remote_perm *perm;
- void *buf;
- int size, acl_off;
- int rc = 0;
+ int rc = 0, reply_off;
ENTRY;
LASSERT(md != NULL);
S_ISSOCK(md->body->mode));
}
- /* if anything wrong when unpacking md, we don't check acl
- * stuff, for simplicity
- */
- if (rc)
- RETURN(rc);
-
- if (md->body->valid & OBD_MD_FLACL) {
- acl_off = (md->body->valid & OBD_MD_FLEASIZE) ?
+ reply_off = (md->body->valid & OBD_MD_FLEASIZE) ?
(offset + 2) : (offset + 1);
-
- if (md->body->valid & OBD_MD_FLRMTACL) {
-
- buf = lustre_swab_repbuf(req, acl_off, sizeof(*perm),
- lustre_swab_remote_perm);
- if (buf == NULL) {
- CERROR("Can't unpack remote perm\n");
- RETURN(0);
- }
-
- OBD_ALLOC(perm, sizeof(*perm));
- if (!perm)
- RETURN(0);
- memcpy(perm, buf, sizeof(*perm));
-
- md->remote_perm = perm;
- } else {
- size = le32_to_cpu(*(__u32 *) lustre_msg_buf(
- req->rq_repmsg, acl_off, 4));
- buf = lustre_msg_buf(req->rq_repmsg, acl_off + 1, size);
-
- acl = posix_acl_from_xattr(buf, size);
- if (IS_ERR(acl)) {
- rc = PTR_ERR(acl);
- CERROR("convert xattr to acl failed: %d\n", rc);
- RETURN(0);
- } else if (acl) {
- rc = posix_acl_valid(acl);
- if (rc) {
- CERROR("acl valid error: %d\n", rc);
- posix_acl_release(acl);
- RETURN(0);
- }
- }
-
- md->posix_acl = acl;
- }
+ rc = mdc_unpack_acl(exp_lmv, req, &reply_off, md);
+ if (rc) {
+ CERROR("upack acl error %d \n", rc);
+ RETURN(rc);
}
+
+ rc = mdc_unpack_gskey(exp_lmv, req, &reply_off, md);
+ if (rc)
+ RETURN(rc);
RETURN(rc);
}
exp->exp_obd->obd_name,
imp->imp_initial_recov);
RETURN(0);
- } else if (keylen >= strlen("mds_type") &&
- strcmp(key, "mds_type") == 0) {
+ } else if ((keylen >= strlen("crypto_type")) &&
+ strcmp(key, "crypto_type") == 0) {
struct ptlrpc_request *req;
char *bufs[2] = {key, val};
int rc, size[2] = {keylen, vallen};
#include <linux/lprocfs_status.h>
#include <linux/lustre_commit_confd.h>
#include <linux/lustre_acl.h>
+#include <linux/lustre_gs.h>
#include "mds_internal.h"
#include <linux/lustre_sec.h>
}
static
-int mds_pack_posix_acl(struct lustre_msg *repmsg, int offset,
+int mds_pack_posix_acl(struct lustre_msg *repmsg, int *offset,
struct mds_body *body, struct inode *inode)
{
struct dentry de = { .d_inode = inode };
__u32 buflen, *sizep;
void *buf;
- int size;
+ int size, pack_off = *offset;
ENTRY;
+ sizep = lustre_msg_buf(repmsg, pack_off++, 4);
+ if (!sizep) {
+ CERROR("can't locate returned acl size buf\n");
+ RETURN(-EPROTO);
+ }
+
if (!inode->i_op->getxattr)
RETURN(0);
- buflen = repmsg->buflens[offset + 1];
- buf = lustre_msg_buf(repmsg, offset + 1, buflen);
+ buflen = repmsg->buflens[pack_off];
+ buf = lustre_msg_buf(repmsg, pack_off++, buflen);
size = inode->i_op->getxattr(&de, XATTR_NAME_ACL_ACCESS, buf, buflen);
if (size == -ENODATA || size == -EOPNOTSUPP)
if (size < 0)
RETURN(size);
LASSERT(size);
-
- sizep = lustre_msg_buf(repmsg, offset, 4);
- if (!sizep) {
- CERROR("can't locate returned acl size buf\n");
- RETURN(-EPROTO);
- }
-
- *sizep = cpu_to_le32(size);
body->valid |= OBD_MD_FLACL;
+ *sizep = cpu_to_le32(size);
+
+ *offset = pack_off;
RETURN(0);
}
-static
-int mds_pack_remote_perm(struct ptlrpc_request *req, int reply_off,
+int mds_pack_remote_perm(struct ptlrpc_request *req, int *reply_off,
struct mds_body *body, struct inode *inode)
{
struct lustre_sec_desc *lsd;
struct mds_remote_perm *perm;
+ int pack_off = *reply_off;
__u32 lsd_perms;
LASSERT(inode->i_op);
LASSERT(req->rq_export->exp_mds_data.med_remote);
perm = (struct mds_remote_perm *)
- lustre_msg_buf(req->rq_repmsg, reply_off, sizeof(perm));
+ lustre_msg_buf(req->rq_repmsg, pack_off++, sizeof(perm));
if (!perm)
return -EINVAL;
perm->mrp_perm |= MAY_READ;
body->valid |= (OBD_MD_FLACL | OBD_MD_FLRMTACL);
+
+ *reply_off = pack_off;
RETURN(0);
}
-int mds_pack_acl(struct ptlrpc_request *req, int reply_off,
+int mds_pack_acl(struct ptlrpc_request *req, int *reply_off,
struct mds_body *body, struct inode *inode)
{
int rc;
struct mds_export_data *med = &req->rq_export->u.eu_mds_data;
struct inode *inode = dentry->d_inode;
struct mds_body *body;
- int rc = 0;
+ int rc = 0, offset = 0;
ENTRY;
if (inode == NULL && !(dentry->d_flags & DCACHE_CROSS_REF))
rc = mds_pack_xattr_list(dentry, req, body, reply_off);
}
+ offset = reply_off + ((reqbody->valid & OBD_MD_FLEASIZE) ? 2 : 1);
if (reqbody->valid & OBD_MD_FLACL) {
- int inc = (reqbody->valid & OBD_MD_FLEASIZE) ? 2 : 1;
- rc = mds_pack_acl(req, reply_off + inc, body, inode);
- }
+ rc = mds_pack_acl(req, &offset, body, inode);
+ }
+
+ if (reqbody->valid & OBD_MD_FLKEY) {
+ rc = mds_pack_gskey(obd, req->rq_repmsg, &offset,
+ body, inode);
+ }
if (rc == 0)
mds_body_do_reverse_map(med, body);
if (req->rq_export->exp_mds_data.med_remote) {
size[bufcount++] = sizeof(struct mds_remote_perm);
} else {
- size[bufcount++] = 4;
+ size[bufcount++] = sizeof(int);
size[bufcount++] = xattr_acl_size(LL_ACL_MAX_ENTRIES);
}
}
+ if (body->valid & OBD_MD_FLKEY) {
+ size[bufcount++] = sizeof(int);
+ size[bufcount++] = sizeof(struct crypto_key);
+ }
+
if (OBD_FAIL_CHECK(OBD_FAIL_MDS_GETATTR_PACK)) {
CERROR("failed MDS_GETATTR_PACK test\n");
req->rq_status = -ENOMEM;
mds_exit_ucred(&uc);
return rc;
}
-
static int mds_access_check(struct ptlrpc_request *req, int offset)
{
struct obd_device *obd = req->rq_export->exp_obd;
struct lvfs_ucred uc;
int rep_size[2] = {sizeof(*body),
sizeof(struct mds_remote_perm)};
- int rc = 0;
+ int rc = 0, rep_offset;
ENTRY;
if (!req->rq_export->exp_mds_data.med_remote) {
body = lustre_msg_buf(req->rq_repmsg, 0, sizeof(*body));
LASSERT(body);
- rc = mds_pack_remote_perm(req, 1, body, de->d_inode);
+ rep_offset = 1;
+ rc = mds_pack_remote_perm(req, &rep_offset, body, de->d_inode);
+
EXIT;
out_dput:
"mds_conn", valsize, &group);
RETURN(rc);
}
+ if (keylen >= strlen("crypto_type") &&
+ memcmp(key, "crypto_type", keylen) == 0) {
+ rc = mds_set_crypto_type(obd, val, vallen);
+ RETURN(rc);
+ }
+
CDEBUG(D_IOCTL, "invalid key\n");
RETURN(-EINVAL);
}
}
keylen = req->rq_reqmsg->buflens[0];
- if (keylen == strlen("mds_type") &&
- memcmp(key, "mds_type", keylen) == 0) {
+ if ((keylen == strlen("mds_type") &&
+ memcmp(key, "mds_type", keylen) == 0) ||
+ (keylen == strlen("crypto_type") &&
+ memcmp(key, "crypto_type", keylen) == 0)) {
rc = lustre_pack_reply(req, 0, NULL, NULL);
if (rc)
RETURN(rc);
ptlrpc_init_client(LDLM_CB_REQUEST_PORTAL, LDLM_CB_REPLY_PORTAL,
"mds_ldlm_client", &obd->obd_ldlm_client);
obd->obd_replayable = 1;
-
+
+ mds->mds_crypto_type = NO_CRYPTO;
+
rc = mds_postsetup(obd);
if (rc)
GOTO(err_fs, rc);
rep->lock_policy_res1 |= flag;
}
+static int mds_intent_prepare_reply_buffers(struct ptlrpc_request *req,
+ struct ldlm_intent *it)
+{
+ struct mds_obd *mds = &req->rq_export->exp_obd->u.mds;
+ int rc, reply_buffers;
+ int repsize[5] = {sizeof(struct ldlm_reply),
+ sizeof(struct mds_body),
+ mds->mds_max_mdsize};
+ ENTRY;
+
+ reply_buffers = 3;
+ if (it->opc & ( IT_OPEN | IT_GETATTR | IT_LOOKUP | IT_CHDIR )) {
+ if (req->rq_export->exp_mds_data.med_remote) {
+ repsize[reply_buffers++] =
+ sizeof(struct mds_remote_perm);
+ } else {
+ repsize[reply_buffers++] = sizeof(int);
+ repsize[reply_buffers++] =
+ xattr_acl_size(LL_ACL_MAX_ENTRIES);
+ }
+ /*FIXME: ugly here, should be optimize for there
+ * is no crypto key*/
+ repsize[reply_buffers++] = sizeof(int);
+ repsize[reply_buffers++] = sizeof(struct crypto_key);
+ }
+
+ rc = lustre_pack_reply(req, reply_buffers, repsize, NULL);
+
+ RETURN(rc);
+}
+
static int mds_intent_policy(struct ldlm_namespace *ns,
struct ldlm_lock **lockp, void *req_cookie,
ldlm_mode_t mode, int flags, void *data)
struct ptlrpc_request *req = req_cookie;
struct ldlm_lock *lock = *lockp;
struct ldlm_intent *it;
- struct mds_obd *mds = &req->rq_export->exp_obd->u.mds;
struct ldlm_reply *rep;
struct lustre_handle lockh[2] = {{0}, {0}};
struct ldlm_lock *new_lock = NULL;
int getattr_part = MDS_INODELOCK_UPDATE;
- int rc, reply_buffers;
- int repsize[5] = {sizeof(struct ldlm_reply),
- sizeof(struct mds_body),
- mds->mds_max_mdsize};
+ int rc;
int offset = MDS_REQ_INTENT_REC_OFF;
ENTRY;
LDLM_DEBUG(lock, "intent policy, opc: %s", ldlm_it2str(it->opc));
- reply_buffers = 3;
- if (it->opc & ( IT_OPEN | IT_GETATTR | IT_LOOKUP | IT_CHDIR )) {
- if (req->rq_export->exp_mds_data.med_remote) {
- reply_buffers = 4;
- repsize[3] = sizeof(struct mds_remote_perm);
- } else {
- reply_buffers = 5;
- repsize[3] = 4;
- repsize[4] = xattr_acl_size(LL_ACL_MAX_ENTRIES);
- }
- }
+ rc = mds_intent_prepare_reply_buffers(req, it);
- rc = lustre_pack_reply(req, reply_buffers, repsize, NULL);
if (rc)
RETURN(req->rq_status = rc);
struct mds_req_sec_desc *rsd);
void mds_exit_ucred(struct lvfs_ucred *ucred);
+int mds_set_gskey(struct obd_device *obd, void *handle,
+ struct inode *inode, void *key, int key_len, int valid);
+int mds_set_crypto_type(struct obd_device *obd, void *val, __u32 vallen);
+
+int mds_pack_gskey(struct obd_device *obd, struct lustre_msg *repmsg,
+ int *offset, struct mds_body *body, struct inode *inode);
/* mds/mds_unlink_open.c */
int mds_cleanup_orphans(struct obd_device *obd);
struct mds_body *repbody, int req_off, int reply_off);
int mds_pack_xattr_list(struct dentry *dentry, struct ptlrpc_request *req,
struct mds_body *repbody, int reply_off);
-int mds_pack_acl(struct ptlrpc_request *req, int reply_off,
+int mds_pack_acl(struct ptlrpc_request *req, int *reply_off,
struct mds_body *body, struct inode *inode);
+
int mds_pack_inode2id(struct obd_device *, struct lustre_id *,
struct inode *, int);
void mds_pack_dentry2body(struct obd_device *, struct mds_body *b,
struct dentry *, int);
+
#endif
/* mds/mds_lmv.c */
#include <asm/uaccess.h>
#include <linux/slab.h>
#include <asm/segment.h>
+#include <linux/random.h>
#include <linux/obd_support.h>
#include <linux/lustre_lib.h>
#include <linux/lustre_sec.h>
#include <linux/lustre_ucache.h>
+#include <linux/lustre_gs.h>
+#include <linux/lustre_fsfilt.h>
#include "mds_internal.h"
#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,4)
RETURN(rc);
}
+int mds_pack_gskey(struct obd_device *obd, struct lustre_msg *repmsg,
+ int *offset, struct mds_body *body, struct inode *inode)
+{
+ struct mds_obd *mds = &obd->u.mds;
+ struct crypto_key_md *md_key;
+ struct crypto_key *ckey;
+ __u32 buflen, *sizep;
+ void *buf;
+ int size, rc = 0;
+ ENTRY;
+
+ if ((mds->mds_crypto_type != MKS_TYPE &&
+ mds->mds_crypto_type != GKS_TYPE))
+ RETURN(rc);
+
+ sizep = lustre_msg_buf(repmsg, (*offset)++, 4);
+ if (!sizep) {
+ CERROR("can't locate returned ckey size buf\n");
+ RETURN(-EPROTO);
+ }
+ *sizep = cpu_to_le32(sizeof(*ckey));
+
+ OBD_ALLOC(md_key, sizeof(*md_key));
+
+ buflen = repmsg->buflens[*offset];
+ buf = lustre_msg_buf(repmsg, (*offset)++, buflen);
+
+ size = fsfilt_get_md(obd, inode, md_key, sizeof(*md_key),
+ EA_KEY);
+ if (size < 0) {
+ CERROR("Can not get gskey from MDS ino %lu rc %d\n",
+ inode->i_ino, size);
+ GOTO(out, rc = size);
+ }
+ if (le32_to_cpu(md_key->md_magic) != MD_KEY_MAGIC) {
+ CDEBUG(D_INFO, "given match %x != magic %x\n",
+ md_key->md_magic, MD_KEY_MAGIC);
+ GOTO(out, rc = 0);
+ }
+
+ CDEBUG(D_INFO, "get key %s mac %s for ino %lu size %d \n",
+ md_key->md_ck.ck_key, md_key->md_ck.ck_mac, inode->i_ino, size);
+ ckey=(struct crypto_key*)buf;
+
+ memcpy(ckey, &md_key->md_ck, sizeof(*ckey));
+ body->valid |= OBD_MD_FLKEY;
+out:
+ OBD_FREE(md_key, sizeof(*md_key));
+ RETURN(rc);
+}
+
+static int mds_get_gskey(struct inode *inode, struct crypto_key *ckey)
+{
+ LASSERT(ckey);
+ /*tmp create gs key here*/
+ get_random_bytes(ckey->ck_key, KEY_SIZE);
+ ckey->ck_type = MKS_TYPE;
+ RETURN(0);
+}
+
+int mds_set_gskey(struct obd_device *obd, void *handle,
+ struct inode *inode, void *key, int key_len,
+ int valid)
+{
+ struct crypto_key_md *md_key = NULL;
+ struct crypto_key *ckey = (struct crypto_key *)key;
+ struct mds_obd *mds = &obd->u.mds;
+ int rc = 0;
+ ENTRY;
+
+ if ((mds->mds_crypto_type != MKS_TYPE &&
+ mds->mds_crypto_type != GKS_TYPE) || key_len == 0)
+ RETURN(rc);
+
+ OBD_ALLOC(md_key, sizeof(*md_key));
+ LASSERT(ckey != NULL);
+ if (mds->mds_crypto_type == MKS_TYPE) {
+ mds_get_gskey(inode, ckey);
+ }
+ rc = fsfilt_get_md(obd, inode, md_key, sizeof(*md_key),
+ EA_KEY);
+ if (rc < 0)
+ GOTO(free, rc);
+ LASSERT(le32_to_cpu(md_key->md_magic) == MD_KEY_MAGIC ||
+ md_key->md_magic == 0);
+ if (le32_to_cpu(md_key->md_magic) == MD_KEY_MAGIC) {
+ CDEBUG(D_INFO, "reset key %s mac %s", md_key->md_ck.ck_mac,
+ md_key->md_ck.ck_key);
+ }
+
+ md_key->md_magic = cpu_to_le32(MD_KEY_MAGIC);
+ if (valid & ATTR_MAC) {
+ memcpy(md_key->md_ck.ck_mac, ckey->ck_mac, MAC_SIZE);
+ CDEBUG(D_INFO, "set mac %s for ino %lu \n",
+ md_key->md_ck.ck_mac, inode->i_ino);
+ }
+ if (valid & ATTR_KEY) {
+ memcpy(md_key->md_ck.ck_key, ckey->ck_key, KEY_SIZE);
+ CDEBUG(D_INFO, "set key %s for ino %lu \n",
+ md_key->md_ck.ck_key, inode->i_ino);
+ }
+ rc = fsfilt_set_md(obd, inode, handle, md_key,
+ sizeof(*md_key), EA_KEY);
+free:
+ if (md_key)
+ OBD_FREE(md_key, sizeof(*md_key));
+ RETURN(rc);
+}
+
+int mds_set_crypto_type(struct obd_device *obd, void *val, __u32 vallen)
+{
+ struct mds_obd *mds = &obd->u.mds;
+ ENTRY;
+
+ if (vallen >= strlen("mks") &&
+ memcmp(val, "mks", vallen) == 0) {
+ mds->mds_crypto_type = MKS_TYPE;
+ }
+ if (vallen >= strlen("gks") &&
+ memcmp(val, "gks", vallen) == 0) {
+ mds->mds_crypto_type = GKS_TYPE;
+ }
+
+ CDEBUG(D_IOCTL, "invalid key\n");
+ RETURN(0);
+}
/* Note that we can copy all of the fields, just some will not be "valid" */
void mds_pack_inode2body(struct obd_device *obd, struct mds_body *b,
struct inode *inode, int fid)
b->valid |= OBD_MD_FID;
mds_pack_inode2id(obd, &b->id1, inode, fid);
+
}
/* unpacking */
r->ur_ea2datalen = req->rq_reqmsg->buflens[offset + 2];
}
+ if (req->rq_reqmsg->bufcount > offset + 3) {
+ r->ur_ea3data = lustre_msg_buf(req->rq_reqmsg, offset + 3, 0);
+ if (r->ur_ea3data == NULL)
+ RETURN (-EFAULT);
+
+ r->ur_ea3datalen = req->rq_reqmsg->buflens[offset + 3];
+ }
+
RETURN(0);
}
r->ur_rdev = rec->cr_rdev;
r->ur_time = rec->cr_time;
r->ur_flags = rec->cr_flags;
-
+
LASSERT_REQSWAB (req, offset + 1);
r->ur_name = lustre_msg_string (req->rq_reqmsg, offset + 1, 0);
if (r->ur_name == NULL)
r->ur_namelen = req->rq_reqmsg->buflens[offset + 1];
LASSERT_REQSWAB (req, offset + 2);
- if (req->rq_reqmsg->bufcount > offset + 2) {
+
+ if (req->rq_reqmsg->bufcount > offset + 2) {
r->ur_eadata = lustre_msg_buf(req->rq_reqmsg, offset + 2, 0);
if (r->ur_eadata == NULL)
RETURN(-EFAULT);
r->ur_eadatalen = req->rq_reqmsg->buflens[offset + 2];
}
+
+ if (rec->cr_flags & MDS_OPEN_HAS_KEY) {
+ LASSERT(req->rq_reqmsg->bufcount > offset + 3);
+ r->ur_ea2data = lustre_msg_buf(req->rq_reqmsg, offset + 3, 0);
+ r->ur_ea2datalen = req->rq_reqmsg->buflens[offset + 3];
+ }
RETURN(0);
}
#include <linux/obd_lov.h>
#include <linux/lustre_fsfilt.h>
#include <linux/lprocfs_status.h>
+#include <linux/lustre_gs.h>
#include "mds_internal.h"
struct mds_file_data *mfd = NULL;
obd_id *ids = NULL;
unsigned mode;
- int rc = 0;
+ int rc = 0, reply_off;
ENTRY;
/* atomically create objects if necessary */
}
}
}
- rc = mds_pack_acl(req, 3, body, dchild->d_inode);
+
+ reply_off = 3;
+ rc = mds_pack_acl(req, &reply_off, body, dchild->d_inode);
+
if (rc < 0) {
CERROR("pack posix acl: rc = %d\n", rc);
up(&dchild->d_inode->i_sem);
RETURN(rc);
}
+ rc = mds_pack_gskey(obd, req->rq_repmsg, &reply_off, body,
+ dchild->d_inode);
+ if (rc < 0) {
+ CERROR("mds_pack_gskey: rc = %d\n", rc);
+ up(&dchild->d_inode->i_sem);
+ RETURN(rc);
+ }
/* If the inode has no EA data, then MDSs hold size, mtime */
if (S_ISREG(dchild->d_inode->i_mode) &&
!(body->valid & OBD_MD_FLEASIZE)) {
else {
MD_COUNTER_INCREMENT(obd, create);
}
-
+
+ if ((rec->ur_flags & MDS_OPEN_HAS_KEY) ||
+ mds->mds_crypto_type == MKS_TYPE) {
+ rc = mds_set_gskey(obd, handle, dchild->d_inode,
+ rec->ur_ea2data, rec->ur_ea2datalen,
+ ATTR_KEY | ATTR_MAC);
+ if (rc) {
+ CERROR("error in set gs key rc %d\n", rc);
+ }
+ }
if (ino) {
rc = mds_update_inode_sid(obd, dchild->d_inode,
handle, rec->ur_id2);
RETURN(0);
}
+
int mds_done_writing(struct ptlrpc_request *req, int offset)
{
struct mds_body *body;
RETURN(EA_SID);
RETURN(0);
}
+
/* In the raw-setattr case, we lock the child inode.
* In the write-back case or if being called from open, the client holds a lock
* already.
flags);
} else if (rec->ur_iattr.ia_valid & ATTR_EA_RM) {
rc = -EOPNOTSUPP;
- if (!med->med_remote && inode->i_op &&
- inode->i_op->removexattr)
- rc = inode->i_op->removexattr(
- de, rec->ur_eadata);
+ if (inode->i_op && inode->i_op->removexattr)
+ rc = inode->i_op->removexattr(de,
+ rec->ur_eadata);
} else if (rec->ur_iattr.ia_valid & ATTR_EA_CMOBD) {
char *name;
int type;
rec->ur_ea2datalen, type);
if (rc)
GOTO(cleanup, rc);
- } else if (S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode)) {
+ } else if ((S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode)) &&
+ !((rec->ur_iattr.ia_valid & ATTR_KEY) ||
+ (rec->ur_iattr.ia_valid & ATTR_MAC))) {
struct lov_stripe_md *lsm = NULL;
struct lov_user_md *lum = NULL;
GOTO(cleanup, rc);
}
}
- }
+ }
+ if ((rec->ur_iattr.ia_valid & ATTR_KEY) ||
+ (rec->ur_iattr.ia_valid & ATTR_MAC)) {
+ void *key;
+ int keylen;
+ LASSERT(rec->ur_eadatalen || rec->ur_ea3datalen);
+ LASSERT(rec->ur_eadata || rec->ur_ea3data);
+ key = rec->ur_eadata ? rec->ur_eadata : rec->ur_ea3data;
+ keylen = rec->ur_eadatalen ? rec->ur_eadatalen :
+ rec->ur_ea3datalen;
+ mds_set_gskey(obd, handle, inode, key, keylen,
+ rec->ur_iattr.ia_valid);
+ }
}
body = lustre_msg_buf(req->rq_repmsg, 0, sizeof (*body));
if (IS_ERR(handle))
GOTO(cleanup, rc = PTR_ERR(handle));
rc = ll_vfs_create(dir, dchild, rec->ur_mode, NULL);
+ if (rec->ur_eadata && rec->ur_eadatalen &&
+ (rc == 0) && (dchild->d_inode != NULL)) {
+ /*Assumption: When ur_eadata is not NULL,
+ *ur_eadata is crypto key, should fix it later, Wangdi*/
+ mds_set_gskey(obd, handle, dchild->d_inode,
+ rec->ur_eadata, rec->ur_eadatalen,
+ ATTR_MAC | ATTR_KEY);
+ }
EXIT;
break;
}
int class_add_profile(int proflen, char *prof,
int lovlen, char *lov,
- int lmvlen, char *lmv)
+ int lmvlen, char *lmv,
+ int gkclen, char *gkc)
{
struct lustre_profile *lprof;
int err = 0;
GOTO(out, err = -ENOMEM);
memcpy(lprof->lp_lmv, lmv, lmvlen);
}
-
+ if (gkclen > 0 ) {
+ LASSERT(gkclen == (strlen(gkc) + 1));
+ OBD_ALLOC(lprof->lp_gkc, gkclen);
+ if (lprof->lp_gkc == NULL)
+ GOTO(out, err = -ENOMEM);
+ memcpy(lprof->lp_gkc, gkc, gkclen);
+ }
+
list_add(&lprof->lp_list, &lustre_profile_list);
-
out:
RETURN(err);
}
GOTO(out, err);
}
case LCFG_MOUNTOPT: {
- CDEBUG(D_IOCTL, "mountopt: profile %s osc %s mdc %s\n",
+ CDEBUG(D_IOCTL, "mountopt: profile %s osc %s mdc %s gkc %s \n",
lustre_cfg_string(lcfg, 1),
lustre_cfg_string(lcfg, 2),
- lustre_cfg_string(lcfg, 3));
+ lustre_cfg_string(lcfg, 3),
+ lustre_cfg_string(lcfg, 4));
/* set these mount options somewhere, so ll_fill_super
* can find them. */
err = class_add_profile(LUSTRE_CFG_BUFLEN(lcfg, 1),
LUSTRE_CFG_BUFLEN(lcfg, 2),
lustre_cfg_string(lcfg, 2),
LUSTRE_CFG_BUFLEN(lcfg, 3),
- lustre_cfg_string(lcfg, 3));
+ lustre_cfg_string(lcfg, 3),
+ LUSTRE_CFG_BUFLEN(lcfg, 4),
+ lustre_cfg_string(lcfg, 4));
GOTO(out, err);
}
case LCFG_DEL_MOUNTOPT: {
struct filter_obd *filter;
struct ldlm_resource *res;
struct dentry *dentry;
+ obd_uid uid;
+ obd_gid gid;
int rc;
ENTRY;
filter = &exp->exp_obd->u.filter;
push_ctxt(&saved, &exp->exp_obd->obd_lvfs_ctxt, NULL);
-
/* make sure that object is allocated. */
dentry = filter_crow_object(exp->exp_obd, oa);
if (IS_ERR(dentry))
RETURN(dentry);
f_dput(dentry);
-
CDEBUG(D_INODE, "OSS object "LPU64"/"LPU64
" does not exists - allocate it now\n",
oa->o_id, oa->o_gr);
struct fsfilt_objinfo fso;
struct obd_device *obd;
obd_size left;
+ obd_uid uid;
+ obd_gid gid;
void *iobuf;
ENTRY;
obd = exp->exp_obd;
push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
+ uid = oa->o_valid & OBD_MD_FLUID ? oa->o_uid : 0;
+ gid = oa->o_valid & OBD_MD_FLGID ? oa->o_gid : 0;
+
/* make sure that object is already allocated */
dentry = filter_crow_object(obd, oa);
if (IS_ERR(dentry))
spin_unlock(&oscc->oscc_lock);
RETURN(rc);
}
+ while (try_again) {
+ /* If orphans are being recovered, then we must wait until
+ it is finished before we can continue with create. */
+ if (oscc_recovering(oscc)) {
+ struct l_wait_info lwi;
+
+ CDEBUG(D_HA,"%p: oscc recovery in progress, waiting\n",
+ oscc);
+
+ lwi = LWI_TIMEOUT(MAX(obd_timeout*HZ/4, 1), NULL, NULL);
+ rc = l_wait_event(oscc->oscc_waitq,
+ !oscc_recovering(oscc), &lwi);
+ LASSERT(rc == 0 || rc == -ETIMEDOUT);
+ if (rc == -ETIMEDOUT) {
+ CDEBUG(D_ERROR,"%p: timeout waiting on recovery\n",
+ oscc);
+ RETURN(rc);
+ }
+ CDEBUG(D_HA, "%p: oscc recovery over, waking up\n",
+ oscc);
+ }
+
+ spin_lock(&oscc->oscc_lock);
+ if (oscc->oscc_flags & OSCC_FLAG_EXITING) {
+ spin_unlock(&oscc->oscc_lock);
+ break;
+ }
+
+ if (oscc->oscc_flags & OSCC_FLAG_NOSPC) {
+ rc = -ENOSPC;
+ spin_unlock(&oscc->oscc_lock);
+ break;
+ }
+
+ oscc->oscc_next_id++;
+ oa->o_id = oscc->oscc_next_id;
+ try_again = 0;
+ spin_unlock(&oscc->oscc_lock);
+
+ CDEBUG(D_HA, "%s: returning objid "LPU64"\n",
+ oscc->oscc_obd->u.cli.cl_import->imp_target_uuid.uuid,
+ oa->o_id);
+ }
while (try_again) {
/* If orphans are being recovered, then we must wait until
#include <linux/lustre_ha.h>
#include <linux/lprocfs_status.h>
#include <linux/lustre_log.h>
+#include <linux/lustre_gs.h>
#include "osc_internal.h"
/* Pack OSC object metadata for disk storage (LE byte order). */
}
#endif
+#define osc_encrypt_page(page, off, count) \
+ osc_crypt_page(page, off, count, ENCRYPT_DATA)
+#define osc_decrypt_page(page, off, count) \
+ osc_crypt_page(page, off, count, DECRYPT_DATA)
+
+/*Put a global call back var here is Ugly, but put it to client_obd
+ *also seems not a good idea, WangDi*/
+crypt_cb_t osc_crypt_cb = NULL;
+
+static int osc_crypt_page(struct page *page, obd_off page_off, obd_off count,
+ int flags)
+{
+ int rc = 0;
+ ENTRY;
+
+ if (osc_crypt_cb != NULL)
+ rc = osc_crypt_cb(page, page_off, count, flags);
+ if (rc != 0)
+ CERROR("crypt page error %d \n", rc);
+ RETURN(rc);
+}
+
static int osc_brw_prep_request(int cmd, struct obd_import *imp,struct obdo *oa,
struct lov_stripe_md *lsm, obd_count page_count,
struct brw_page *pga, int *requested_nobp,
pg->pg, pg->pg->private, pg->pg->index, pg->disk_offset,
pg_prev->pg, pg_prev->pg->private, pg_prev->pg->index,
pg_prev->disk_offset);
+
+ if (opc == OST_WRITE) {
+ osc_encrypt_page(pg->pg, pg->page_offset, pg->count);
+ }
ptlrpc_prep_bulk_page(desc, pg->pg,
pg->page_offset & ~PAGE_MASK, pg->count);
RETURN(-EPROTO);
}
LASSERT (req->rq_bulk->bd_nob == requested_nob);
-
+ osc_decrypt_page(pga->pg, pga->page_offset,
+ pga->count);
RETURN(check_write_rcs(req, requested_nob, niocount,
page_count, pga));
}
req->rq_import->imp_connection->c_peer.peer_id.nid);
}
#endif
+ osc_decrypt_page(pga->pg, pga->page_offset, pga->count);
RETURN(0);
}
ptlrpcs_import_flush_current_creds(cli->cl_import);
RETURN(0);
}
+ if (keylen == strlen("crypto_cb") &&
+ memcmp(key, "crypto_cb", keylen) == 0) {
+ LASSERT(vallen == sizeof(crypt_cb_t));
+ osc_crypt_cb = (crypt_cb_t)val;
+ RETURN(0);
+ }
if (keylen < strlen("mds_conn") ||
memcmp(key, "mds_conn", keylen) != 0)
case OST_CONNECT: rq_opc = OST_DISCONNECT; break;
case MDS_CONNECT: rq_opc = MDS_DISCONNECT; break;
case MGMT_CONNECT: rq_opc = MGMT_DISCONNECT; break;
+ case GKS_CONNECT: rq_opc = GKS_DISCONNECT; break;
default:
CERROR("don't know how to disconnect from %s (connect_op %d)\n",
imp->imp_target_uuid.uuid, imp->imp_connect_op);
#include <linux/lustre_net.h>
#include <linux/lustre_sec.h>
#include <linux/fcntl.h>
+#include <linux/posix_acl.h>
#define HDR_SIZE(count) \
return ((void*)tmp + size_round(datalen));
}
+__u32 mds_pack_open_flags(__u32 flags)
+{
+ return
+ (flags & (FMODE_READ | FMODE_WRITE | FMODE_EXEC |
+ MDS_OPEN_DELAY_CREATE | MDS_OPEN_HAS_EA |
+ MDS_OPEN_HAS_OBJS)) |
+ ((flags & O_CREAT) ? MDS_OPEN_CREAT : 0) |
+ ((flags & O_EXCL) ? MDS_OPEN_EXCL : 0) |
+ ((flags & O_TRUNC) ? MDS_OPEN_TRUNC : 0) |
+ ((flags & O_APPEND) ? MDS_OPEN_APPEND : 0) |
+ ((flags & O_SYNC) ? MDS_OPEN_SYNC : 0) |
+ ((flags & O_DIRECTORY) ? MDS_OPEN_DIRECTORY : 0) |
+ 0;
+}
+
void *mdc_setattr_pack(struct lustre_msg *msg, int offset,
struct mdc_op_data *data, struct iattr *iattr,
- void *ea, int ealen, void *ea2, int ea2len)
+ void *ea, int ealen, void *ea2, int ea2len,
+ void *ea3, int ea3len)
{
struct mds_rec_setattr *rec = lustre_msg_buf(msg, offset, sizeof(*rec));
char *tmp = NULL;
memcpy(lustre_msg_buf(msg, offset + 2, ea2len), ea2, ea2len);
tmp += size_round(ea2len);
+
+ if (ea3len == 0)
+ return (void*)tmp;
+
+ memcpy(lustre_msg_buf(msg, offset + 3, ea3len), ea3, ea3len);
+ tmp += size_round(ea3len);
+
return (void*)tmp;
}
void lustre_assert_wire_constants(void)
{
}
-
+/* for gks key rec */
+void lustre_swab_key_perms(struct key_perm *kperm)
+{
+ int i;
+ __swab32s(&kperm->kp_uid);
+ __swab32s(&kperm->kp_gid);
+ __swab32s(&kperm->kp_mode);
+ __swab32s(&kperm->kp_acl_count);
+ for (i = 0; i < kperm->kp_acl_count; i++) {
+ __swab16s(&kperm->kp_acls[i].e_tag);
+ __swab16s(&kperm->kp_acls[i].e_perm);
+ __swab32s(&kperm->kp_acls[i].e_id);
+ }
+}
+void lustre_swab_key_context (struct key_context *kctxt)
+{
+ __swab32s (&kctxt->kc_command);
+ __swab32s (&kctxt->kc_valid); /* for use with open */
+ lustre_swab_key_perms(&kctxt->kc_perm);
+}
EXPORT_SYMBOL(lustre_swab_ptlbd_op);
EXPORT_SYMBOL(lustre_swab_ptlbd_niob);
EXPORT_SYMBOL(lustre_swab_ptlbd_rsp);
+EXPORT_SYMBOL(lustre_swab_key_context);
+EXPORT_SYMBOL(lustre_swab_key_perms);
EXPORT_SYMBOL(mdc_create_pack);
EXPORT_SYMBOL(mdc_setattr_pack);
EXPORT_SYMBOL(mdc_unlink_pack);
EXPORT_SYMBOL(mdc_link_pack);
EXPORT_SYMBOL(mdc_rename_pack);
+EXPORT_SYMBOL(mds_pack_open_flags);
/* recover.c */
EXPORT_SYMBOL(ptlrpc_run_recovery_over_upcall);
MODULES := ptlrpcs
ptlrpcs-objs := sec.o sec_null.o svcsec.o svcsec_null.o upcall_cache.o
-@GSS_TRUE@subdir-m += gss
+@GSS_TRUE@subdir-m += gss gks
@INCLUDE_RULES@
# See the file COPYING in this distribution
if GSS
-SUBDIRS = . gss #kcrypto
+SUBDIRS = . gss gks #kcrypto
endif
if LIBLUSTRE
--- /dev/null
+MODULES := gks gkc
+gks-objs := lproc_gks.o gks_server.o
+gkc-objs := lproc_gks.o gks_client.o
+@INCLUDE_RULES@
+
+
--- /dev/null
+# Copyright (C) 2004 Cluster File Systems, Inc.
+#
+# This code is issued under the GNU General Public License.
+# See the file COPYING in this distribution
+
+include $(src)/../../portals/Kernelenv
+
+#obj-y += ptlrpcs_gss.o ptlrpcs_gss_krb5.o
+obj-y += gks.o gkc.o
+gks-objs := lprocfs_gks.o gks_server.o
+gkc-objs := lprofs_gks.o gks_client.o
--- /dev/null
+# Copyright (C) 2004 Cluster File Systems, Inc.
+#
+# This code is issued under the GNU General Public License.
+# See the file COPYING in this distribution
+
+
+if MODULES
+modulefs_DATA = gks$(KMODEXT) gkc$(KMODEXT)
+endif
+
+DIST_SOURCES = gks_client.c gks_server.c lproc_gks.c gks_internal.h
+MOSTLYCLEANFILES := @MOSTLYCLEANFILES@
+
--- /dev/null
+/* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
+ * vim:expandtab:shiftwidth=8:tabstop=8:
+ *
+ * lustre GS client
+ * Copyright (c) 2001-2003 Cluster File Systems, Inc.
+ *
+ * This file is part of Lustre, http://www.lustre.org.
+ *
+ * Lustre is free software; you can redistribute it and/or
+ * modify it under the terms of version 2 of the GNU General Public
+ * License as published by the Free Software Foundation.
+ *
+ * Lustre is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Lustre; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+
+#ifndef EXPORT_SYMTAB
+# define EXPORT_SYMTAB
+#endif
+#define DEBUG_SUBSYSTEM S_GSS
+
+#include <linux/module.h>
+#include <linux/init.h>
+#include <linux/obd_class.h>
+#include <linux/lustre_gs.h>
+
+#include "gks_internal.h"
+
+static int gkc_get_key(struct obd_export *exp, struct key_parms *kparms,
+ struct crypto_key *ckey, int op)
+{
+ struct ptlrpc_request *req;
+ struct crypto_key *rep_key;
+ int rc, bufcount = 1, size[3] = {0, 0, 0};
+ void *buf;
+ ENTRY;
+
+ size[0] = lustre_secdesc_size();
+
+ size[bufcount++] = kparms->context_size;
+ if (kparms->perm && kparms->perm_size > 0) {
+ size[bufcount++] = kparms->perm_size;
+ }
+ req = ptlrpc_prep_req(class_exp2cliimp(exp), LUSTRE_GKS_VERSION,
+ op, bufcount, size, NULL);
+ if (req == NULL)
+ RETURN(-ENOMEM);
+
+ lustre_pack_secdesc(req, size[0]);
+
+ buf = lustre_msg_buf(req->rq_reqmsg, 1, kparms->context_size);
+ memcpy(buf, kparms->context, kparms->context_size);
+
+ if (kparms->perm && kparms->perm_size) {
+ buf = lustre_msg_buf(req->rq_reqmsg, 2, kparms->perm_size);
+ memcpy(buf, kparms->perm, kparms->perm_size);
+ }
+
+ size[0] = sizeof(struct crypto_key);
+ req->rq_replen = lustre_msg_size(1, size);
+
+ rc = ptlrpc_queue_wait(req);
+
+ rep_key = lustre_msg_buf(req->rq_repmsg, 0, sizeof(struct crypto_key));
+
+ memcpy(ckey, rep_key, sizeof(*rep_key));
+
+ CDEBUG(D_INFO, "get enkey %s, mac %s\n", ckey->ck_key, ckey->ck_mac);
+ ptlrpc_req_finished(req);
+
+ RETURN(rc);
+}
+
+static int gkc_set_info(struct obd_export *exp, obd_count keylen,
+ void *key, obd_count vallen, void *val)
+{
+ int rc = -EINVAL;
+ if (keylen == strlen("async") && memcmp(key, "async", keylen) == 0) {
+ struct client_obd *cl = &exp->exp_obd->u.cli;
+ if (vallen != sizeof(int))
+ RETURN(-EINVAL);
+ cl->cl_async = *(int *)val;
+ CDEBUG(D_HA, "%s: set async = %d\n",
+ exp->exp_obd->obd_name, cl->cl_async);
+ RETURN(0);
+ }
+ RETURN(rc);
+}
+
+static int gkc_get_info(struct obd_export *exp, __u32 keylen,
+ void *key, __u32 *vallen, void *val)
+{
+ struct key_parms *kparms = (struct key_parms *)key;
+ struct crypto_key *ckey = (struct crypto_key *)val;
+ int rc = 0;
+
+ ENTRY;
+
+ LASSERT(*vallen == sizeof(*ckey));
+
+ switch (kparms->context->kc_command) {
+ case GKS_GET_KEY:
+ case GKS_DECRYPT_KEY:
+ case GKS_GET_MAC:
+ break;
+ default:
+ CERROR("Unknow op %d \n", kparms->context->kc_command);
+ rc = -EINVAL;
+ RETURN(rc);
+ }
+ rc = gkc_get_key(exp, kparms, ckey, kparms->context->kc_command);
+ RETURN(rc);
+}
+static int gkc_setup(struct obd_device *obd, obd_count len, void *buf)
+{
+ struct client_obd *cli = &obd->u.cli;
+ int rc;
+ ENTRY;
+
+ OBD_ALLOC(cli->cl_rpc_lock, sizeof (*cli->cl_rpc_lock));
+ if (!cli->cl_rpc_lock)
+ RETURN(-ENOMEM);
+ gkc_init_rpc_lock(cli->cl_rpc_lock);
+
+ ptlrpcd_addref();
+
+ rc = client_obd_setup(obd, len, buf);
+ if (rc)
+ GOTO(err_rpc_lock, rc);
+
+ RETURN(rc);
+err_rpc_lock:
+ OBD_FREE(cli->cl_rpc_lock, sizeof (*cli->cl_rpc_lock));
+ ptlrpcd_decref();
+ RETURN(rc);
+}
+
+static int gkc_cleanup(struct obd_device *obd, int flags)
+{
+ struct client_obd *cli = &obd->u.cli;
+
+ OBD_FREE(cli->cl_rpc_lock, sizeof (*cli->cl_rpc_lock));
+
+ ptlrpcd_decref();
+
+ return client_obd_cleanup(obd, 0);
+}
+
+static int gkc_attach(struct obd_device *dev, obd_count len, void *data)
+{
+ struct lprocfs_static_vars lvars;
+
+ lprocfs_init_vars(gkc, &lvars);
+ return lprocfs_obd_attach(dev, lvars.obd_vars);
+}
+
+static int gkc_detach(struct obd_device *dev)
+{
+ return lprocfs_obd_detach(dev);
+}
+
+static struct obd_ops gkc_obd_ops = {
+ .o_owner = THIS_MODULE,
+ .o_connect = client_connect_import,
+ .o_disconnect = client_disconnect_export,
+ .o_attach = gkc_attach,
+ .o_detach = gkc_detach,
+ .o_setup = gkc_setup,
+ .o_cleanup = gkc_cleanup,
+ .o_get_info = gkc_get_info,
+ .o_set_info = gkc_set_info,
+};
+
+static int __init gkc_init(void)
+{
+ struct lprocfs_static_vars lvars;
+
+ lprocfs_init_vars(gkc, &lvars);
+ class_register_type(&gkc_obd_ops, NULL, lvars.module_vars,
+ LUSTRE_GKC_NAME);
+ return 0;
+}
+
+static void gkc_exit(void)
+{
+ class_unregister_type(LUSTRE_GKC_NAME);
+}
+
+MODULE_AUTHOR("Cluster File Systems, Inc. <info@clusterfs.com>");
+MODULE_DESCRIPTION("Lustre GS Client (GS)");
+MODULE_LICENSE("GPL");
+
+module_init(gkc_init);
+module_exit(gkc_exit);
+
--- /dev/null
+/* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
+ * vim:expandtab:shiftwidth=8:tabstop=8:
+ */
+
+#ifndef _GKS_INTERNAL_H
+#define _GKS_INTERNAL_H
+
+#define GKS_SERVICE_WATCHDOG_TIMEOUT 30000
+struct mdc_rpc_lock {
+ struct semaphore rpcl_sem;
+ struct lookup_intent *rpcl_it;
+};
+
+static inline void gkc_init_rpc_lock(struct mdc_rpc_lock *lck)
+{
+ sema_init(&lck->rpcl_sem, 1);
+ lck->rpcl_it = NULL;
+}
+
+static inline void gkc_get_rpc_lock(struct mdc_rpc_lock *lck,
+ struct lookup_intent *it)
+{
+ ENTRY;
+ down(&lck->rpcl_sem);
+ if (it) {
+ lck->rpcl_it = it;
+ }
+}
+
+static inline void gkc_put_rpc_lock(struct mdc_rpc_lock *lck,
+ struct lookup_intent *it)
+{
+ EXIT;
+ if (it == NULL) {
+ LASSERT(it == lck->rpcl_it);
+ up(&lck->rpcl_sem);
+ return;
+ }
+ if (it) {
+ LASSERT(it == lck->rpcl_it);
+ lck->rpcl_it = NULL;
+ up(&lck->rpcl_sem);
+ }
+}
+
+#endif /* _GKS_INTERNAL_H */
--- /dev/null
+/* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
+ * vim:expandtab:shiftwidth=8:tabstop=8:
+ *
+ * lustre GS server
+ * Copyright (c) 2001-2003 Cluster File Systems, Inc.
+ *
+ * This file is part of Lustre, http://www.lustre.org.
+ *
+ * Lustre is free software; you can redistribute it and/or
+ * modify it under the terms of version 2 of the GNU General Public
+ * License as published by the Free Software Foundation.
+ *
+ * Lustre is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Lustre; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+#ifndef EXPORT_SYMTAB
+# define EXPORT_SYMTAB
+#endif
+#define DEBUG_SUBSYSTEM S_GKS
+
+#include <linux/module.h>
+#include <linux/crypto.h>
+#include <linux/random.h>
+#include <linux/init.h>
+#include <linux/obd_class.h>
+#include <linux/lustre_gs.h>
+
+#include "gks_internal.h"
+
+#define GKS_KEY "19760218"
+#define GKS_KEY_LEN 8
+#define GKS_MAC_ALG "sha1"
+#define GKS_KEY_ALG "des"
+#define GKS_KEY_ALG_MODE CRYPTO_TFM_MODE_CBC
+
+static int gks_cleanup(struct obd_device *obd, int flags)
+{
+ struct gks_obd *gks = &obd->u.gks;
+ ENTRY;
+
+ if (gks->gks_mac_tfm) {
+ crypto_free_tfm(gks->gks_mac_tfm);
+ }
+ if (gks->gks_key.key) {
+ OBD_FREE(gks->gks_key.key, gks->gks_key.len);
+ }
+ if (gks->gks_key_tfm) {
+ crypto_free_tfm(gks->gks_key_tfm);
+ }
+
+ RETURN(0);
+}
+
+static int gks_setup(struct obd_device *obd, obd_count len, void *buf)
+{
+ struct gks_obd *gks = &obd->u.gks;
+ int rc = 0;
+
+ gks->gks_mac_tfm = crypto_alloc_tfm(GKS_MAC_ALG, 0);
+ if (!gks->gks_mac_tfm)
+ RETURN(-ENOSYS);
+ /*Now: we only keep an unchanged key in the whole system*/
+ gks->gks_key.len = GKS_KEY_LEN;
+
+ OBD_ALLOC(gks->gks_key.key, GKS_KEY_LEN);
+
+ LASSERT(gks->gks_key.key);
+
+ memcpy(gks->gks_key.key, GKS_KEY, GKS_KEY_LEN);
+ /*set gks cipher type*/
+
+ gks->gks_key_tfm = crypto_alloc_tfm(GKS_KEY_ALG, GKS_KEY_ALG_MODE);
+ if (!gks->gks_key_tfm)
+ GOTO(out, rc = -ENOSYS);
+ if (crypto_cipher_setkey(gks->gks_key_tfm, gks->gks_key.key,
+ gks->gks_key.len))
+ GOTO(out, rc = -ENOSYS);
+out:
+ if (rc) {
+ gks_cleanup(obd, 0);
+ }
+ RETURN(rc);
+}
+
+static int gks_connect(struct lustre_handle *conn, struct obd_device *obd,
+ struct obd_uuid *cluuid, struct obd_connect_data *data,
+ unsigned long flags)
+{
+ int rc;
+ ENTRY;
+
+ if (!conn || !obd || !cluuid)
+ RETURN(-EINVAL);
+
+ rc = class_connect(conn, obd, cluuid);
+
+ RETURN(rc);
+}
+
+static int gks_disconnect(struct obd_export *exp, unsigned long flags)
+{
+ int rc = 0;
+ ENTRY;
+
+ rc = class_disconnect(exp, flags);
+
+ target_destroy_export(exp);
+
+ RETURN(rc);
+}
+
+static int gks_msg_check_version(struct lustre_msg *msg)
+{
+ int rc = 0;
+ ENTRY;
+
+ switch (msg->opc) {
+ case GKS_CONNECT:
+ case GKS_DISCONNECT:
+ rc = lustre_msg_check_version(msg, LUSTRE_OBD_VERSION);
+ if (rc)
+ CERROR("bad opc %u version %08x, expecting %08x\n",
+ msg->opc, msg->version, LUSTRE_OBD_VERSION);
+ break;
+ case GKS_GET_KEY:
+ case GKS_DECRYPT_KEY:
+ case GKS_GET_MAC:
+ rc = lustre_msg_check_version(msg, LUSTRE_GKS_VERSION);
+ if (rc)
+ CERROR("bad opc %u version %08x, expecting %08x\n",
+ msg->opc, msg->version, LUSTRE_GKS_VERSION);
+ break;
+ default:
+ CERROR("GKS unknown opcode %d\n", msg->opc);
+ rc = -ENOTSUPP;
+ break;
+ }
+
+ RETURN(rc);
+}
+
+static int crypto_get_gks_mac(struct ptlrpc_request *req,
+ struct key_perm *kperm,
+ __u8 *hmac)
+{
+ struct obd_device *obd = req->rq_export->exp_obd;
+ struct gks_obd *gks = &obd->u.gks;
+ int perm_size = crypto_kperm_size(kperm->kp_acl_count);
+ struct scatterlist sl = {
+ .page = virt_to_page(kperm),
+ .offset = (unsigned long)(kperm) % PAGE_SIZE,
+ .length = perm_size
+ };
+ __u8 *key = gks->gks_key.key;
+ int keylen = gks->gks_key.len;
+ struct crypto_tfm *tfm = gks->gks_mac_tfm;
+
+ ENTRY;
+ LASSERT(tfm);
+
+ crypto_hmac(tfm, key, &keylen, &sl, 1, hmac);
+
+ CDEBUG(D_INFO, "compute mac mac %s by uid %d gid %d"
+ "mode %d acl_count %d acl %p perm_size %d\n",
+ hmac, kperm->kp_uid, kperm->kp_gid, kperm->kp_mode,
+ kperm->kp_acl_count, kperm->kp_acls, perm_size);
+
+ RETURN(0);
+}
+#define crypto_decrypt_gks_key(req, data, len) \
+crypto_crypt_gks_key(req, data, len, DECRYPT_DATA)
+
+#define crypto_encrypt_gks_key(req, data, len) \
+crypto_crypt_gks_key(req, data, len, ENCRYPT_DATA)
+
+static int crypto_crypt_gks_key(struct ptlrpc_request *req,
+ __u8 *data, int len, int mode)
+{
+ struct obd_device *obd = req->rq_export->exp_obd;
+ struct gks_obd *gks = &obd->u.gks;
+ struct scatterlist sl = {
+ .page = virt_to_page(data),
+ .offset = (unsigned long)(data) % PAGE_SIZE,
+ .length = len
+ };
+ struct crypto_tfm *tfm = gks->gks_key_tfm;
+ __u8 local_iv[16] = {0};
+
+ ENTRY;
+ LASSERT(tfm);
+
+ if (mode == ENCRYPT_DATA)
+ crypto_cipher_encrypt_iv(tfm, &sl, &sl, (unsigned int)len,
+ local_iv);
+ else
+ crypto_cipher_decrypt_iv(tfm, &sl, &sl, (unsigned int)len,
+ local_iv);
+
+ RETURN(0);
+}
+
+static int gks_create_key(struct ptlrpc_request *req, int offset)
+{
+ struct key_context *kctxt;
+ struct crypto_key *ckey;
+
+ kctxt = lustre_swab_reqbuf(req, offset, sizeof (*kctxt),
+ lustre_swab_key_context);
+
+ ckey = (struct crypto_key *)lustre_msg_buf(req->rq_repmsg, 0,
+ sizeof (*ckey));
+
+ crypto_get_gks_mac(req, &kctxt->kc_perm, ckey->ck_mac);
+
+ CDEBUG(D_INFO, "compute mac mac %s by uid %d gid %d mode %d \n",
+ ckey->ck_mac, kctxt->kc_perm.kp_uid, kctxt->kc_perm.kp_gid,
+ kctxt->kc_perm.kp_mode);
+
+ get_random_bytes(ckey->ck_key, KEY_SIZE);
+
+ ckey->ck_type = GKS_TYPE;
+
+ CDEBUG(D_INFO, "get key %s\n", ckey->ck_key);
+
+ crypto_encrypt_gks_key(req, ckey->ck_key, KEY_SIZE);
+
+ CDEBUG(D_INFO, "encrypt key %s\n", ckey->ck_key);
+
+ RETURN(0);
+}
+
+static int gks_mac_verification(struct ptlrpc_request *req,
+ struct crypto_key *key,
+ struct key_perm *kperm)
+{
+ __u8 *tmp_mac;
+ ENTRY;
+
+ OBD_ALLOC(tmp_mac, MAC_SIZE);
+
+ crypto_get_gks_mac(req, kperm, tmp_mac);
+
+ if (!memcmp(tmp_mac, key->ck_mac, MAC_SIZE)) {
+ OBD_FREE(tmp_mac, MAC_SIZE);
+ RETURN(0);
+ }
+ OBD_FREE(tmp_mac, MAC_SIZE);
+ RETURN(-EPERM);
+}
+
+static int gks_permission_check(struct key_context *kctxt,
+ struct key_perm *kperm)
+{
+ RETURN(0);
+}
+
+static int gks_decrypt_key(struct ptlrpc_request *req, int offset)
+{
+ struct key_context *kctxt;
+ struct key_perm *kperm;
+ struct crypto_key *ckey;
+ int rc = 0;
+
+ kctxt = lustre_swab_reqbuf(req, offset, sizeof(*kctxt),
+ lustre_swab_key_context);
+
+ /*authiticating the ops of the mac*/
+ rc = gks_mac_verification(req, &kctxt->kc_ck, &kctxt->kc_perm);
+ if (rc != 0) {
+ CERROR("Not my authorization mac %s\n", kctxt->kc_ck.ck_mac);
+ RETURN(rc);
+ }
+
+ kperm = lustre_swab_reqbuf(req, offset + 1, sizeof(*kperm),
+ lustre_swab_key_perms);
+
+ rc = gks_permission_check(kctxt, kperm);
+ if (rc != 0) {
+ CERROR("permssion check failed\n");
+ RETURN(rc);
+ }
+ ckey = (struct crypto_key *)lustre_msg_buf(req->rq_repmsg, 0,
+ sizeof (*ckey));
+ memcpy(ckey, &kctxt->kc_ck, sizeof(*ckey));
+
+ rc = crypto_decrypt_gks_key(req, ckey->ck_key, KEY_SIZE);
+ if (rc != 0) {
+ CERROR("permssion check failed\n");
+ RETURN(rc);
+ }
+
+ RETURN(0);
+}
+
+static int gks_get_mac(struct ptlrpc_request *req, int offset)
+{
+ struct key_context *kctxt;
+ struct key_perm *kperm;
+ struct crypto_key *ckey;
+ int rc = 0;
+
+ kctxt = lustre_swab_reqbuf(req, offset, sizeof(*kctxt),
+ lustre_swab_key_context);
+
+ /*authiticating the ops of the mac*/
+ rc = gks_mac_verification(req, &kctxt->kc_ck, &kctxt->kc_perm);
+ if (rc != 0) {
+ CERROR("Not my authorization mac %s\n", kctxt->kc_ck.ck_mac);
+ RETURN(rc);
+ }
+
+ kperm = lustre_swab_reqbuf(req, offset + 1, sizeof(*kperm),
+ lustre_swab_key_perms);
+
+ rc = gks_permission_check(kctxt, kperm);
+ if (rc != 0) {
+ CERROR("permssion check failed\n");
+ RETURN(rc);
+ }
+ ckey = (struct crypto_key *)lustre_msg_buf(req->rq_repmsg, 0,
+ sizeof (*ckey));
+
+ memcpy(ckey, &kctxt->kc_ck, sizeof(*ckey));
+
+ rc = crypto_get_gks_mac(req, kperm, ckey->ck_mac);
+ if (rc != 0) {
+ CERROR("get new mac error %d \n", rc);
+ RETURN(rc);
+ }
+
+ RETURN(rc);
+}
+
+int gks_handle(struct ptlrpc_request *req)
+{
+ int fail = OBD_FAIL_MDS_ALL_REPLY_NET;
+ int rc;
+ ENTRY;
+
+ rc = gks_msg_check_version(req->rq_reqmsg);
+ if (rc) {
+ CERROR("GKS drop mal-formed request\n");
+ RETURN(rc);
+ }
+ switch (req->rq_reqmsg->opc) {
+ case GKS_CONNECT:
+ DEBUG_REQ(D_INODE, req, "connect");
+ rc = target_handle_connect(req);
+ req->rq_status = rc; /* superfluous? */
+ break;
+ case GKS_DISCONNECT:
+ DEBUG_REQ(D_INODE, req, "disconnect");
+ rc = target_handle_disconnect(req);
+ req->rq_status = rc; /* superfluous? */
+ break;
+
+ case GKS_GET_KEY: {
+ int size[1] = {sizeof(struct crypto_key)};
+ int bufcount = 1;
+
+ DEBUG_REQ(D_INODE, req, "get_key");
+ lustre_pack_reply(req, bufcount, size, NULL);
+ rc = gks_create_key(req, MDS_REQ_REC_OFF);
+ req->rq_status = rc; /* superfluous? */
+ break;
+ }
+ case GKS_DECRYPT_KEY: {
+ int size[1] = {sizeof(struct crypto_key)};
+ int bufcount = 1;
+
+ DEBUG_REQ(D_INODE, req, "decrypt_key");
+ lustre_pack_reply(req, bufcount, size, NULL);
+ rc = gks_decrypt_key(req, MDS_REQ_REC_OFF);
+ req->rq_status = rc; /* superfluous? */
+ break;
+ }
+ case GKS_GET_MAC: {
+ int size[1] = {sizeof(struct crypto_key)};
+ int bufcount = 1;
+
+ DEBUG_REQ(D_INODE, req, "get_mac");
+ lustre_pack_reply(req, bufcount, size, NULL);
+ rc = gks_get_mac(req, MDS_REQ_REC_OFF);
+ req->rq_status = rc; /* superfluous? */
+ break;
+ }
+ default:
+ req->rq_status = -ENOTSUPP;
+ rc = ptlrpc_error(req);
+ RETURN(rc);
+ }
+ target_send_reply(req, rc, fail);
+ RETURN(rc);
+}
+
+static int gkt_setup(struct obd_device *obd, obd_count len, void *buf)
+{
+ struct gks_obd *gks = &obd->u.gks;
+ int rc = 0;
+ ENTRY;
+
+ gks->gks_service =
+ ptlrpc_init_svc(GKS_NBUFS, GKS_BUFSIZE, GKS_MAXREQSIZE,
+ GKS_REQUEST_PORTAL, GKC_REPLY_PORTAL,
+ GKS_SERVICE_WATCHDOG_TIMEOUT,
+ gks_handle, "gks", obd->obd_proc_entry);
+ if (!gks->gks_service) {
+ CERROR("failed to start service\n");
+ RETURN(-ENOMEM);
+ }
+
+ rc = ptlrpc_start_n_threads(obd, gks->gks_service, GKT_NUM_THREADS,
+ "ll_gkt");
+
+ RETURN(rc);
+}
+
+static int gkt_cleanup(struct obd_device *obd, int flags)
+{
+ struct gks_obd *gks = &obd->u.gks;
+
+ ptlrpc_stop_all_threads(gks->gks_service);
+ ptlrpc_unregister_service(gks->gks_service);
+ RETURN(0);
+}
+
+int gks_attach(struct obd_device *dev, obd_count len, void *data)
+{
+ struct lprocfs_static_vars lvars;
+
+ lprocfs_init_vars(gks, &lvars);
+ return lprocfs_obd_attach(dev, lvars.obd_vars);
+}
+
+int gks_detach(struct obd_device *dev)
+{
+ return lprocfs_obd_detach(dev);
+}
+
+int gkt_attach(struct obd_device *dev, obd_count len, void *data)
+{
+ struct lprocfs_static_vars lvars;
+
+ lprocfs_init_vars(gkt, &lvars);
+ return lprocfs_obd_attach(dev, lvars.obd_vars);
+}
+
+int gkt_detach(struct obd_device *dev)
+{
+ return lprocfs_obd_detach(dev);
+}
+
+static struct obd_ops gks_obd_ops = {
+ .o_owner = THIS_MODULE,
+ .o_attach = gks_attach,
+ .o_detach = gks_detach,
+ .o_setup = gks_setup,
+ .o_cleanup = gks_cleanup,
+ .o_connect = gks_connect,
+ .o_disconnect = gks_disconnect,
+};
+
+static struct obd_ops gkt_obd_ops = {
+ .o_owner = THIS_MODULE,
+ .o_attach = gkt_attach,
+ .o_detach = gkt_detach,
+ .o_setup = gkt_setup,
+ .o_cleanup = gkt_cleanup,
+};
+
+static int __init gks_init(void)
+{
+ struct lprocfs_static_vars lvars;
+
+ lprocfs_init_vars(gks, &lvars);
+ class_register_type(&gks_obd_ops, NULL, lvars.module_vars,
+ LUSTRE_GKS_NAME);
+
+ lprocfs_init_vars(gkt, &lvars);
+ class_register_type(&gkt_obd_ops, NULL, lvars.module_vars,
+ LUSTRE_GKT_NAME);
+ RETURN(0);
+}
+
+static void gks_exit(void)
+{
+ class_unregister_type(LUSTRE_GKS_NAME);
+ class_unregister_type(LUSTRE_GKT_NAME);
+}
+
+MODULE_AUTHOR("Cluster File Systems, Inc. <info@clusterfs.com>");
+MODULE_DESCRIPTION("Lustre GS Server (GS)");
+MODULE_LICENSE("GPL");
+
+module_init(gks_init);
+module_exit(gks_exit);
+
--- /dev/null
+/* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
+ * vim:expandtab:shiftwidth=8:tabstop=8:
+ *
+ * Copyright (C) 2002 Cluster File Systems, Inc.
+ *
+ * This file is part of Lustre, http://www.lustre.org.
+ *
+ * Lustre is free software; you can redistribute it and/or
+ * modify it under the terms of version 2 of the GNU General Public
+ * License as published by the Free Software Foundation.
+ *
+ * Lustre is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Lustre; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ *
+ */
+#define DEBUG_SUBSYSTEM S_CLASS
+
+#include <linux/lprocfs_status.h>
+#include <linux/obd_class.h>
+
+static struct lprocfs_vars lprocfs_gks_module_vars[] = { {0} };
+static struct lprocfs_vars lprocfs_gks_obd_vars[] = { {0} };
+
+static struct lprocfs_vars lprocfs_gkt_module_vars[] = { {0} };
+static struct lprocfs_vars lprocfs_gkt_obd_vars[] = { {0} };
+
+static struct lprocfs_vars lprocfs_gkc_module_vars[] = { {0} };
+static struct lprocfs_vars lprocfs_gkc_obd_vars[] = { {0} };
+
+LPROCFS_INIT_VARS(gks, lprocfs_gks_module_vars, lprocfs_gks_obd_vars)
+LPROCFS_INIT_VARS(gkt, lprocfs_gkt_module_vars, lprocfs_gkt_obd_vars)
+LPROCFS_INIT_VARS(gkc, lprocfs_gkc_module_vars, lprocfs_gkc_obd_vars)
#define XATTR_LUSTRE_MDS_MEA_EA "mea"
#define XATTR_LUSTRE_MDS_MID_EA "mid"
#define XATTR_LUSTRE_MDS_SID_EA "sid"
+#define XATTR_LUSTRE_MDS_KEY_EA "key"
static int fsfilt_smfs_set_md(struct inode *inode, void *handle,
void *lmm, int lmm_size, enum ea_type type)
XATTR_LUSTRE_MDS_MID_EA,
lmm, lmm_size);
break;
+ case EA_KEY:
+ rc = fsfilt_smfs_set_xattr(inode, handle,
+ XATTR_LUSTRE_MDS_KEY_EA,
+ lmm, lmm_size);
+ break;
default:
rc = -EINVAL;
}
LASSERT(kbuf && name);
tmp = mdc_setattr_pack(msg, 0, op_data, NULL, name, strlen(name),
- kbuf->buf, kbuf->buf_size);
+ kbuf->buf, kbuf->buf_size, NULL, 0);
OBD_FREE(op_data, sizeof(*op_data));
rec = (struct mds_rec_setattr *)lustre_msg_buf(msg, 0, 0);
msg = (struct lustre_msg *)(buffer + sizeof(*mkpi));
lustre_init_msg(msg, mkpi->mpi_bufcount, mkpi->mpi_size, NULL);
- tmp = mdc_setattr_pack(msg, 0, op_data, iattr, ea, ealen, NULL, 0);
+ tmp = mdc_setattr_pack(msg, 0, op_data, iattr, ea, ealen,
+ NULL, 0, NULL, 0);
OBD_FREE(op_data, sizeof(*op_data));
/* FIXME-WANGDI: there are maybe some better ways to set the time
ost_HOST=${ost_HOST:-$OSTNODE}
ost2_HOST=${ost2_HOST:-$ost_HOST}
client_HOST=${client_HOST:-$CLIENT}
+gsk_HOST=${gsk_HOST:-$MDSNODE}
+
NETTYPE=${NETTYPE:-tcp}
MOUNT=${MOUNT:-"/mnt/lustre"}
--- /dev/null
+#!/bin/bash
+
+set -e
+
+export PATH=`dirname $0`/../utils:$PATH
+
+config=${1:-lgs.xml}
+
+LMC=${LMC:-lmc}
+TMP=${TMP:-/tmp}
+
+MDSSIZE=${MDSSIZE:-100000}
+MDSCOUNT=${MDSCOUNT:-3}
+OSTDEV=${OSTDEV:-$TMP/ost1-`hostname`}
+OSTSIZE=${OSTSIZE:-200000}
+OSTCOUNT=${OSTCOUNT:-1}
+
+DEF_FSTYPE=`test "x$(uname -r | grep -o '2.6')" = "x2.6" && echo "ldiskfs" || echo "ext3"`
+FSTYPE=${FSTYPE:-$DEF_FSTYPE}
+#used only if FSTYPE == smfs, otherwise ignored by lconf
+MDS_BACKFSTYPE=${MDS_BACKFSTYPE:-$DEF_FSTYPE}
+OST_BACKFSTYPE=${OST_BACKFSTYPE:-$DEF_FSTYPE}
+
+# 1 to config an echo client instead of llite
+ECHO_CLIENT=${ECHO_CLIENT:-}
+
+STRIPE_BYTES=65536
+STRIPES_PER_OBJ=0
+
+MOUNT=${MOUNT:-/mnt/lustre}
+
+# specific journal size for the ost, in MB
+JSIZE=${JSIZE:-0}
+JARG=""
+[ "$JSIZE" -gt 0 ] && JARG="--journal_size $JSIZE"
+
+rm -f $config
+
+# create nodes
+${LMC} -m $config --add node --node localhost || exit 10
+${LMC} -m $config --add net --node localhost --nid `hostname` --nettype tcp || exit 11
+
+# configure mds server
+${LMC} -m $config --add lmv --lmv lmv1 || exit 12
+
+for num in `seq $MDSCOUNT`; do
+ MDSDEV=$TMP/mds${num}-`hostname`
+ ${LMC} -m $config --format --add mds --node localhost --mds mds${num} \
+ --lmv lmv1 --fstype $FSTYPE --backfstype $MDS_BACKFSTYPE --dev $MDSDEV \
+ --size $MDSSIZE || exit 13
+done
+
+${LMC} -m $config --add lov --lov lov1 --lmv lmv1 --stripe_sz $STRIPE_BYTES --stripe_cnt $STRIPES_PER_OBJ --stripe_pattern 0 || exit 20
+
+# configure ost
+for num in `seq $OSTCOUNT`; do
+ OST=ost$num
+ DEVPTR=OSTDEV$num
+ eval $DEVPTR=${!DEVPTR:=$TMP/$OST-`hostname`}
+ ${LMC} -m $config --add ost --node localhost --lov lov1 --ost $OST --fstype $FSTYPE --backfstype $OST_BACKFSTYPE --dev ${!DEVPTR} --size $OSTSIZE $JARG || exit 30
+done
+
+${LMC} -m $config --add gks --gks gks1 --node localhost || exit 13
+
+${LMC} -m $config --add mtpt --node localhost --path $MOUNT --lmv lmv1 --lov lov1 --gks gks1 || exit 40
--- /dev/null
+#!/bin/sh
+
+set -e
+
+#
+# This test needs to be run on the client
+#
+
+LUSTRE=${LUSTRE:-`dirname $0`/..}
+. $LUSTRE/tests/test-framework.sh
+
+init_test_env $@
+
+. ${CONFIG:=$LUSTRE/tests/cfg/lmv.sh}
+
+build_test_filter
+
+assert_env MDSCOUNT
+
+if [ `using_krb5_sec $SECURITY` == 'n' ] ; then
+ ALWAYS_EXCEPT="0c $ALWAYS_EXCEPT"
+fi
+
+
+gen_config() {
+ rm -f $XMLCONFIG
+
+ if [ "$MDSCOUNT" -gt 1 ]; then
+ add_lmv lmv1_svc
+ for mds in `mds_list`; do
+ MDSDEV=$TMP/${mds}-`hostname`
+ add_mds $mds --dev $MDSDEV --size $MDSSIZE --lmv lmv1_svc
+ done
+ add_lov_to_lmv lov1 lmv1_svc --stripe_sz $STRIPE_BYTES \
+ --stripe_cnt $STRIPES_PER_OBJ --stripe_pattern 0
+ MDS=lmv1
+ else
+ add_mds $SINGLEMDS --dev $MDSDEV --size $MDSSIZE
+ if [ ! -z "$$SINGLEMDSfailover_HOST" ]; then
+ add_mdsfailover $SINGLEMDS --dev $MDSDEV --size $MDSSIZE
+ fi
+ add_lov lov1 $SINGLEMDS --stripe_sz $STRIPE_BYTES \
+ --stripe_cnt $STRIPES_PER_OBJ --stripe_pattern 0
+ MDS=$SINGLEMDS_svc
+ fi
+ add_ost ost --lov lov1 --dev $OSTDEV --size $OSTSIZE
+ add_ost ost2 --lov lov1 --dev ${OSTDEV}-2 --size $OSTSIZE
+ add_gsk gsk
+ add_client client $MDS --lov lov1 --gss gsk_svc --path $MOUNT
+}
+
+build_test_filter
+
+cleanup() {
+ # make sure we are using the primary MDS, so the config log will
+ # be able to clean up properly.
+ activemds=`facet_active $SINGLEMDS`
+ if [ $activemds != "$SINGLEMDS" ]; then
+ fail $SINGLEMDS
+ fi
+
+ umount $MOUNT2 || true
+ umount $MOUNT || true
+ rmmod llite
+
+ stop_gsk gsk
+ for mds in `mds_list`; do
+ stop $mds ${FORCE} $MDSLCONFARGS
+ done
+ stop ost2 ${FORCE} --dump cleanup.log
+ stop ost ${FORCE} --dump cleanup.log
+ stop_lgssd
+ stop_lsvcgssd
+}
+
+if [ "$ONLY" == "cleanup" ]; then
+ sysctl -w portals.debug=0 || true
+ cleanup
+ exit
+fi
+
+SETUP=${SETUP:-"setup"}
+CLEANUP=${CLEANUP:-"cleanup"}
+
+setup() {
+ gen_config
+
+ start_krb5_kdc || exit 1
+ start_lsvcgssd || exit 2
+ start_lgssd || exit 3
+ start ost --reformat $OSTLCONFARGS
+ start ost2 --reformat $OSTLCONFARGS
+ [ "$DAEMONFILE" ] && $LCTL debug_daemon start $DAEMONFILE $DAEMONSIZE
+ for mds in `mds_list`; do
+ start $mds --reformat $MDSLCONFARGS
+ done
+ set -vx
+ start_gsk gsk || exit 4
+ set -e
+ grep " $MOUNT " /proc/mounts || zconf_mount `hostname` $MOUNT
+ grep " $MOUNT2 " /proc/mounts || zconf_mount `hostname` $MOUNT2
+}
+
+$SETUP
+
+if [ "$ONLY" == "setup" ]; then
+ exit 0
+fi
+
+mkdir -p $DIR
+$CLEANUP
+
facet=$1
shift
active=`facet_active $facet`
- do_facet $facet $LCONF --select ${facet}_svc=${active}_facet \
+ do_facet $facet $LCONF --select ${facet}_svc=${active}_facet -v \
--node ${active}_facet --ptldebug $PTLDEBUG --subsystem $SUBSYSTEM \
--mds_sec $SECURITY $@ $XMLCONFIG
}
shift
do_lmc --delete ost --node ${facet}_facet --ost ${facet}_svc $*
}
+start_gsk() {
+ facet=$1
+ shift
+ rm -f ${facet}active
+ add_facet $facet
+ do_facet $facet $LCONF --node ${facet}_facet --ptldebug $PTLDEBUG $* $XMLCONFIG
+}
+stop_gsk() {
+ facet=$1
+ shift
+ do_facet $facet $LCONF --node ${facet}_facet --cleanup $* $XMLCONFIG
+}
+
+add_gsk() {
+ facet=$1
+ shift
+ rm -f ${facet}active
+ add_facet $facet
+ do_lmc --add gss --gss ${facet}_svc --node ${facet}_facet $*
+}
add_cmobd() {
facet=$1
cache_facet=$2
return out
# dump mount options
- def mount_option(self, profile, osc, mdc):
+ def mount_option(self, profile, osc, mdc, gkc):
cmds = """
- mount_option %s %s %s
- quit""" % (profile, osc, mdc)
+ mount_option %s %s %s %s
+ quit""" % (profile, osc, mdc, gkc)
self.run(cmds)
# delete mount options
def correct_level(self, level, op=None):
return level
+class GKD(Module):
+ def __init__(self,db):
+ Module.__init__(self, 'GKD', db)
+ target_uuid = self.db.get_first_ref('target')
+ self.target = self.db.lookup(target_uuid)
+ self.name = self.target.getName()
+
+ active_uuid = get_active_target(self.target)
+ if not active_uuid:
+ panic("No target device found:", target_uuid)
+ if active_uuid == self.uuid:
+ self.active = 1
+ else:
+ self.active = 0
+
+ self.uuid = target_uuid
+ def prepare(self):
+ if is_prepared(self.name):
+ return
+ if not self.active:
+ debug(self.uuid, "not active")
+ return
+ run_acceptors()
+
+ lctl.newdev("gks", self.name, self.uuid, setup ="")
+ if not is_prepared('GKT'):
+ lctl.newdev("gkt", 'GKT', 'GKT_UUID', setup ="")
+
+ def cleanup(self):
+ if not self.active:
+ debug(self.uuid, "not active")
+ return
+ self.info()
+ if is_prepared(self.name):
+ try:
+ lctl.cleanup(self.name, self.uuid, config.force,
+ config.failover)
+ except CommandError, e:
+ log(self.module_name, "cleanup failed: ", self.name)
+ e.dump()
+ cleanup_error(e.rc)
+ Module.cleanup(self)
+ if is_prepared('GKT'):
+ try:
+ lctl.cleanup("GKT", "GKT_UUID", config.force,
+ config.failover)
+ except CommandError, e:
+ print "cleanup failed: ", self.name
+ e.dump()
+ cleanup_error(e.rc)
+
+ def add_module(self, manager):
+ if self.active:
+ manager.add_lustre_module('sec/gks', 'gks')
+ manager.add_lustre_module('sec/gks', 'gkc')
+
+ def correct_level(self, level, op=None):
+ return level
+
+
class CONFDEV(Module):
def __init__(self, db, name, target_uuid, uuid):
Module.__init__(self, 'CONFDEV', db)
lctl.clear_log(self.name, self.target.getName())
lctl.record(self.name, self.target.getName())
client.prepare()
- lctl.mount_option(self.target.getName(), client.get_name(), "")
+ lctl.mount_option(self.target.getName(), client.get_name(), "", "")
lctl.end_record()
config.cleanup = 1
e.dump()
cleanup_error(e.rc)
+class GKC(Client):
+ def __init__(self, db, uuid, fs_name):
+ Client.__init__(self, db, uuid, 'gkc', fs_name)
+
+ def permits_inactive(self):
+ return 0
+
class MDC(Client):
def __init__(self, db, uuid, fs_name):
Client.__init__(self, db, uuid, 'mdc', fs_name)
if not self.mds_uuid:
self.mds_uuid = fs.get_first_ref('mds')
self.obd_uuid = fs.get_first_ref('obd')
- client_uuid = generate_client_uuid(self.name)
+ self.gks_uuid =fs.get_first_ref('gks')
+ client_uuid = generate_client_uuid(self.name)
+
+ self.oss_sec = self.db.get_val('oss_sec','null')
+ self.mds_sec = self.db.get_val('mds_sec','null')
+ if config.mds_sec:
+ self.mds_sec = config.mds_sec
+ if config.oss_sec:
+ self.oss_sec = config.oss_sec
self.oss_sec = self.db.get_val('oss_sec','null')
self.mds_sec = self.db.get_val('mds_sec','null')
self.vosc = VOSC(ost, client_uuid, self.name, self.name)
self.vmdc = VMDC(mds, client_uuid, self.name, self.name)
-
+
+ if self.gks_uuid:
+ self.gkc = get_gkc(db, client_uuid, self.name, self.gks_uuid)
def prepare(self):
if not config.record and fs_is_mounted(self.path):
log(self.path, "already mounted.")
self.vosc.prepare()
self.vmdc.prepare()
+ if self.gks_uuid:
+ self.gkc.prepare()
self.info(self.path, self.mds_uuid, self.obd_uuid)
if config.record or config.lctl_dump:
- lctl.mount_option(local_node_name, self.vosc.get_name(),
- self.vmdc.get_name())
- return
+ if self.gks_uuid:
+ lctl.mount_option(local_node_name, self.vosc.get_name(),
+ self.vmdc.get_name(), self.gkc.get_name())
+ else:
+ lctl.mount_option(local_node_name, self.vosc.get_name(),
+ self.vmdc.get_name(), "")
+ return
if config.clientoptions:
if self.clientoptions:
# so replace it with Lustre async
self.clientoptions = string.replace(self.clientoptions, "async", "lasync")
- cmd = "mount -t lustre_lite -o osc=%s,mdc=%s,mds_sec=%s,oss_sec=%s%s %s %s" % \
- (self.vosc.get_name(), self.vmdc.get_name(), self.mds_sec,
+ if self.gks_uuid:
+ gkc_name = self.gkc.get_name();
+ else:
+ gkc_name = "null"
+ cmd = "mount -t lustre_lite -o osc=%s,mdc=%s,gkc=%s,mds_sec=%s,oss_sec=%s%s %s %s" % \
+ (self.vosc.get_name(), self.vmdc.get_name(), gkc_name, self.mds_sec,
self.oss_sec, self.clientoptions, config.config, self.path)
run("mkdir", self.path)
ret, val = run(cmd)
self.vmdc.cleanup()
self.vosc.cleanup()
+ if self.gks_uuid:
+ self.gkc.cleanup()
def add_module(self, manager):
self.vosc.add_module(manager)
self.vmdc.add_module(manager)
manager.add_lustre_module('llite', 'llite')
-
+ if self.gks_uuid:
+ manager.add_lustre_module('sec/gks', 'gkc')
def correct_level(self, level, op=None):
return level
ret = 30
elif type in ('mdsdev',):
ret = 40
- elif type in ('lmv',):
+ elif type in ('lmv', 'cobd',):
ret = 45
+ elif type in ('gkd'):
+ ret = 50
elif type in ('cmobd', 'cobd',):
ret = 60
elif type in ('mountpoint', 'echoclient'):
mdc = MDC(mds_db, mds_uuid, fs_name)
return mdc
+def get_gkc(db, uuid, fs_name, gks_uuid):
+ gks_db = db.lookup(gks_uuid);
+ if not gks_db:
+ error("no gks:", gks_uuid)
+ gkc = GKC(gks_db, uuid, fs_name)
+ return gkc
+
############################################################
# routing ("rooting")
n = ECHO_CLIENT(db)
elif type == 'lmv':
n = LMV(db)
+ elif type == 'gkd':
+ n = GKD(db)
else:
panic ("unknown service type:", type)
return n
"setup mds/ost from the llog file\n"
"usage: start <profilename>"},
{"mount_option", jt_lcfg_mount_option, 0,
- "usage: mount_option profile osc_name [mdc_name] \n"},
+ "usage: mount_option profile osc_name [mdc_name] [gsc_name] \n"},
{"del_mount_option", jt_lcfg_del_mount_option, 0,
"usage: del_mount_option profile\n"},
{"set_timeout", jt_lcfg_set_timeout, 0,
{"llog_remove", jt_llog_remove, 0,
"remove one log from catalog, erase it from disk.\n"
"usage: llog_remove <catalog id|catalog name> <log id>"},
-
+
/* Misc commands */
{"flush_cred", jt_flush_cred, 0,
"flush the client side credential.\n"
"usage: flush_cred [mountpoint]..."},
-
+ {"set_crypt", jt_set_lkey_type, 0,
+ "set lustre key management type, only support gsk and mdk\n"
+ "usage: set_crypt [dir] [gsk|mdk]...."},
+
/* Debug commands */
{"======== debug =========", jt_noop, 0, "debug"},
{"debug_daemon", jt_dbg_debug_daemon, 0,
--master_obd obd_name
--cache_obd obd_name
+--add gks
+ --gks gks_name
+
--commit - Close a configuration version, and start a new one
"""
# lmv
('lmv', "Specify LMV name.", PARAM,""),
+
+ #gks name
+ ('gks', "Specify gks name.", PARAM,""),
+
]
def error(*args):
lmv = self.newService("lmv", name, uuid)
return lmv
+ def gks(self, name, uuid, gkd_uuid):
+ gks = self.newService("gks", name, uuid)
+ gks.appendChild(self.ref("active", gkd_uuid))
+ return gks
+
+ def gkd(self, name, uuid, node_uuid, gks_uuid):
+ gkd = self.newService("gkd", name, uuid)
+ gkd.appendChild(self.ref("node", node_uuid))
+ gkd.appendChild(self.ref("target", gks_uuid))
+ return gkd
+
def mds(self, name, uuid, mdd_uuid, group="", lmv=""):
mds = self.newService("mds", name, uuid)
mds.appendChild(self.ref("active", mdd_uuid))
self.addElement(mtpt, "oss_sec", oss_sec)
return mtpt
- def filesystem(self, name, uuid, mds_uuid, obd_uuid, mgmt_uuid):
+ def filesystem(self, name, uuid, mds_uuid, obd_uuid, mgmt_uuid, gks_uuid):
fs = self.newService("filesystem", name, uuid)
fs.appendChild(self.ref("mds", mds_uuid))
fs.appendChild(self.ref("obd", obd_uuid))
+ fs.appendChild(self.ref("gks", gks_uuid))
if mgmt_uuid:
fs.appendChild(self.ref("mgmt", mgmt_uuid))
return fs
node_add_profile(gen, node, "routetbl", rtbl_uuid)
rtbl.appendChild(gen.route(gw_net_type, gw, gw_cluster_id, tgt_cluster_id,
lo, hi))
+
+def add_gks(gen, lustre, options):
+ """ create a gks """
+ node_name = get_option(options, 'node')
+ gks_name = get_option(options, 'gks')
+ if not gks_name:
+ gks_name = new_name('GKS_'+ node_name)
+
+ gkd_name = new_name("GKD_" + gks_name + "_" + node_name)
+ gkd_uuid = new_uuid(gkd_name)
+
+ gks_uuid = name2uuid(lustre, gks_name, 'gks', fatal=0)
+
+ if not gks_uuid:
+ gks_uuid = new_uuid(gks_name)
+ gks = gen.gks(gks_name, gks_uuid, gkd_uuid)
+ lustre.appendChild(gks)
+ else:
+ gks = lookup(lustre, gks_uuid)
+
+ # add gkd profile
+ node_uuid = name2uuid(lustre, node_name, 'node')
+ node = findByName(lustre, node_name, "node")
+ node_add_profile(gen, node, "gkd", gkd_uuid)
+ net_uuid = get_net_uuid(lustre, node_name)
+ if not net_uuid:
+ error("NODE: ", node_name, "not found")
+
+ gkd = gen.gkd(gkd_name, gkd_uuid, node_uuid, gks_uuid)
+ lustre.appendChild(gkd)
+
def add_mds(gen, lustre, options):
node_name = get_option(options, 'node')
lmv = gen.lmv(name, uuid)
lustre.appendChild(lmv)
-
+
def find_client(lustre, mds_uuid, client_uuid):
mds = lookup(lustre, mds_uuid)
clients = mds.getElementsByTagName('client_ref')
return 1
return 0
-def new_filesystem(gen, lustre, mds_uuid, obd_uuid, mgmt_uuid):
+def new_filesystem(gen, lustre, mds_uuid, obd_uuid, mgmt_uuid, gks_uuid):
fs_name = new_name("FS_fsname")
fs_uuid = new_uuid(fs_name)
mds.appendChild(gen.ref("client", obd_uuid))
fs = gen.filesystem(fs_name, fs_uuid, mds_uuid,
- obd_uuid, mgmt_uuid)
+ obd_uuid, mgmt_uuid, gks_uuid)
lustre.appendChild(fs)
return fs_uuid
-def get_fs_uuid(gen, lustre, mds_name, obd_name, mgmt_name):
+def get_fs_uuid(gen, lustre, mds_name, obd_name, mgmt_name, gks_name):
mds_uuid = name2uuid(lustre, mds_name, tag='mds', fatal=0)
if not mds_uuid:
mds_uuid = name2uuid(lustre, mds_name, tag='lmv', fatal=0)
else:
mgmt_uuid = ''
+ if gks_name:
+ gks_uuid = name2uuid(lustre, gks_name, tag='gks', fatal=1)
+ else:
+ gks_uuid = ''
fs_uuid = lookup_filesystem(lustre, mds_uuid, obd_uuid)
if not fs_uuid:
fs_uuid = new_filesystem(gen, lustre, mds_uuid,
- obd_uuid, mgmt_uuid)
+ obd_uuid, mgmt_uuid, gks_uuid)
return fs_uuid
def add_mtpt(gen, lustre, options):
lov_name = get_option(options, 'lov')
ost_name = get_option(options, 'ost')
mds_name = get_option(options, 'mds')
+ gks_name = get_option(options, 'gks')
if mds_name == '':
mds_name = get_option(options, 'lmv')
if mds_name == '':
if fs_name == '':
mgmt_name = get_option(options, 'mgmt')
- fs_uuid = get_fs_uuid(gen, lustre, mds_name, lov_name, mgmt_name)
+ fs_uuid = get_fs_uuid(gen, lustre, mds_name, lov_name, mgmt_name, gks_name)
else:
fs_uuid = name2uuid(lustre, fs_name, tag='filesystem')
add_mgmt(gen, lustre, options)
elif devtype == 'lmv':
add_lmv(gen, lustre, options)
+ elif devtype == 'gks':
+ add_gks(gen, lustre, options)
else:
error("unknown device type:", devtype)
struct lustre_cfg *lcfg;
int i;
- if (argc < 3 || argc > 4)
+ if (argc < 3 || argc > 5)
return CMD_HELP;
lustre_cfg_bufs_reset(&bufs, lcfg_devname);
return rc;
}
+int jt_set_lkey_type(int argc, char **argv)
+{
+ struct obd_ioctl_data data;
+ char *dir, *type;
+ int rc, fd;
+
+ if (argc < 3 || argc > 4)
+ return CMD_HELP;
+
+ dir = argv[1];
+ type = argv[2];
+
+ IOC_INIT(data);
+
+ data.ioc_inllen1 = strlen(type) + 1;
+ data.ioc_inlbuf1 = type;
+
+ IOC_PACK(argv[0], data);
+
+ fd = open(dir, O_RDONLY);
+ if (fd < 0) {
+ fprintf(stderr, "open \"%s\" failed: %s\n", dir,
+ strerror(errno));
+ return -1;
+ }
+
+ rc = ioctl(fd, LL_IOC_KEY_TYPE, buf);
+ if (rc < 0) {
+ fprintf(stderr, "error: %s: ioctl error: %s\n",
+ jt_cmdname(argv[0]), strerror(rc = errno));
+ }
+ close(fd);
+ return rc;
+}
+
+int jt_disable_crypto(int argc, char **argv)
+{
+ struct obd_ioctl_data data;
+ char *file;
+ int rc, fd;
+
+ if (argc < 2 || argc > 3)
+ return CMD_HELP;
+
+ file = argv[1];
+
+ IOC_INIT(data);
+
+ IOC_PACK(argv[0], data);
+
+ fd = open(file, O_RDONLY);
+ if (fd < 0) {
+ fprintf(stderr, "open \"%s\" failed: %s\n", file,
+ strerror(errno));
+ return -1;
+ }
+
+ rc = ioctl(fd, LL_IOC_DISABLE_CRYPTO, buf);
+ if (rc < 0) {
+ fprintf(stderr, "error: %s: ioctl error: %s\n",
+ jt_cmdname(argv[0]), strerror(rc = errno));
+ }
+ close(fd);
+
+ return rc;
+}
+
+int jt_enable_crypto(int argc, char **argv)
+{
+ struct obd_ioctl_data data;
+ char *file;
+ int rc, fd;
+
+ if (argc < 3 || argc > 4)
+ return CMD_HELP;
+
+ file = argv[1];
+
+ IOC_INIT(data);
+
+ IOC_PACK(argv[0], data);
+
+ fd = open(file, O_RDONLY);
+ if (fd < 0) {
+ fprintf(stderr, "open \"%s\" failed: %s\n", file,
+ strerror(errno));
+ return -1;
+ }
+
+ rc = ioctl(fd, LL_IOC_ENABLE_CRYPTO, buf);
+ if (rc < 0) {
+ fprintf(stderr, "error: %s: ioctl error: %s\n",
+ jt_cmdname(argv[0]), strerror(rc = errno));
+ }
+ close(fd);
+ return rc;
+}
+
int jt_obd_mdc_lookup(int argc, char **argv)
{
int jt_obd_cache_on(int argc, char **argv);
int jt_obd_cache_off(int argc, char **argv);
int jt_obd_snap_add(int argc, char **argv);
-
+int jt_set_lkey_type(int argc, char **argv);
+int jt_disable_crypto(int argc, char **argv);
+int jt_enable_crypto(int argc, char **argv);
int lcfg_ioctl(char * func, int dev_id, struct lustre_cfg *lcfg);
int parse_devname(char *func, char *name);
char *jt_cmdname(char *func);