X-Git-Url: https://git.whamcloud.com/?a=blobdiff_plain;f=lustre%2Fptlrpc%2Fsec_lproc.c;h=41ef7e019d7ffb341e5684f4875ca15502165fa4;hb=82b8cb5528f489e9ceb7a1899722fc4108e85739;hp=e602a63d3be18259a62e5036b024eba884ece6fa;hpb=0ad4f8a4227ed7dd93fec99d33c6bb25056473fc;p=fs%2Flustre-release.git diff --git a/lustre/ptlrpc/sec_lproc.c b/lustre/ptlrpc/sec_lproc.c index e602a63..41ef7e0 100644 --- a/lustre/ptlrpc/sec_lproc.c +++ b/lustre/ptlrpc/sec_lproc.c @@ -15,17 +15,15 @@ * * You should have received a copy of the GNU General Public License * version 2 along with this program; If not, see - * http://www.sun.com/software/products/lustre/docs/GPLv2.pdf - * - * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, - * CA 95054 USA or visit www.sun.com if you need additional information or - * have any questions. + * http://www.gnu.org/licenses/gpl-2.0.html * * GPL HEADER END */ /* * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved. * Use is subject to license terms. + * + * Copyright (c) 2014, Intel Corporation. */ /* * This file is part of Lustre, http://www.lustre.org/ @@ -51,11 +49,7 @@ #include "ptlrpc_internal.h" - -struct proc_dir_entry *sptlrpc_proc_root = NULL; -EXPORT_SYMBOL(sptlrpc_proc_root); - -char *sec_flags2str(unsigned long flags, char *buf, int bufsize) +static char *sec_flags2str(unsigned long flags, char *buf, int bufsize) { buf[0] = '\0'; @@ -75,14 +69,16 @@ char *sec_flags2str(unsigned long flags, char *buf, int bufsize) static int sptlrpc_info_lprocfs_seq_show(struct seq_file *seq, void *v) { - struct obd_device *dev = seq->private; - struct client_obd *cli = &dev->u.cli; - struct ptlrpc_sec *sec = NULL; - char str[32]; + struct obd_device *obd = seq->private; + struct client_obd *cli = &obd->u.cli; + struct ptlrpc_sec *sec = NULL; + char str[32]; - LASSERT(strcmp(dev->obd_type->typ_name, LUSTRE_OSC_NAME) == 0 || - strcmp(dev->obd_type->typ_name, LUSTRE_MDC_NAME) == 0 || - strcmp(dev->obd_type->typ_name, LUSTRE_MGC_NAME) == 0); + LASSERT(strcmp(obd->obd_type->typ_name, LUSTRE_OSC_NAME) == 0 || + strcmp(obd->obd_type->typ_name, LUSTRE_MDC_NAME) == 0 || + strcmp(obd->obd_type->typ_name, LUSTRE_MGC_NAME) == 0 || + strcmp(obd->obd_type->typ_name, LUSTRE_LWP_NAME) == 0 || + strcmp(obd->obd_type->typ_name, LUSTRE_OSP_NAME) == 0); if (cli->cl_import) sec = sptlrpc_import_sec_ref(cli->cl_import); @@ -101,26 +97,29 @@ static int sptlrpc_info_lprocfs_seq_show(struct seq_file *seq, void *v) seq_printf(seq, "refcount: %d\n", atomic_read(&sec->ps_refcount)); seq_printf(seq, "nctx: %d\n", atomic_read(&sec->ps_nctx)); - seq_printf(seq, "gc internal %ld\n", sec->ps_gc_interval); - seq_printf(seq, "gc next %ld\n", + seq_printf(seq, "gc internal %lld\n", sec->ps_gc_interval); + seq_printf(seq, "gc next %lld\n", sec->ps_gc_interval ? - sec->ps_gc_next - cfs_time_current_sec() : 0); + (s64)(sec->ps_gc_next - ktime_get_real_seconds()) : 0ll); sptlrpc_sec_put(sec); out: return 0; } + LPROC_SEQ_FOPS_RO(sptlrpc_info_lprocfs); static int sptlrpc_ctxs_lprocfs_seq_show(struct seq_file *seq, void *v) { - struct obd_device *dev = seq->private; - struct client_obd *cli = &dev->u.cli; - struct ptlrpc_sec *sec = NULL; + struct obd_device *obd = seq->private; + struct client_obd *cli = &obd->u.cli; + struct ptlrpc_sec *sec = NULL; - LASSERT(strcmp(dev->obd_type->typ_name, LUSTRE_OSC_NAME) == 0 || - strcmp(dev->obd_type->typ_name, LUSTRE_MDC_NAME) == 0 || - strcmp(dev->obd_type->typ_name, LUSTRE_MGC_NAME) == 0); + LASSERT(strcmp(obd->obd_type->typ_name, LUSTRE_OSC_NAME) == 0 || + strcmp(obd->obd_type->typ_name, LUSTRE_MDC_NAME) == 0 || + strcmp(obd->obd_type->typ_name, LUSTRE_MGC_NAME) == 0 || + strcmp(obd->obd_type->typ_name, LUSTRE_LWP_NAME) == 0 || + strcmp(obd->obd_type->typ_name, LUSTRE_OSP_NAME) == 0); if (cli->cl_import) sec = sptlrpc_import_sec_ref(cli->cl_import); @@ -134,68 +133,250 @@ static int sptlrpc_ctxs_lprocfs_seq_show(struct seq_file *seq, void *v) out: return 0; } + LPROC_SEQ_FOPS_RO(sptlrpc_ctxs_lprocfs); -int sptlrpc_lprocfs_cliobd_attach(struct obd_device *dev) +#if LUSTRE_VERSION_CODE < OBD_OCD_VERSION(2, 16, 53, 0) +static ssize_t sepol_seq_write_old(struct obd_device *obd, + const char __user *buffer, + size_t count) { - int rc; - - if (strcmp(dev->obd_type->typ_name, LUSTRE_OSC_NAME) != 0 && - strcmp(dev->obd_type->typ_name, LUSTRE_MDC_NAME) != 0 && - strcmp(dev->obd_type->typ_name, LUSTRE_MGC_NAME) != 0) { - CERROR("can't register lproc for obd type %s\n", - dev->obd_type->typ_name); - return -EINVAL; - } - - rc = lprocfs_obd_seq_create(dev, "srpc_info", 0444, - &sptlrpc_info_lprocfs_fops, dev); - if (rc) { - CERROR("create proc entry srpc_info for %s: %d\n", - dev->obd_name, rc); - return rc; - } - - rc = lprocfs_obd_seq_create(dev, "srpc_contexts", 0444, - &sptlrpc_ctxs_lprocfs_fops, dev); - if (rc) { - CERROR("create proc entry srpc_contexts for %s: %d\n", - dev->obd_name, rc); - return rc; - } + struct client_obd *cli = &obd->u.cli; + struct obd_import *imp = cli->cl_import; + struct sepol_downcall_data_old *param; + int size = sizeof(*param); + __u16 len; + int rc = 0; - return 0; + if (count < size) { + rc = -EINVAL; + CERROR("%s: invalid data count = %lu, size = %d: rc = %d\n", + obd->obd_name, (unsigned long) count, size, rc); + return rc; + } + + OBD_ALLOC(param, size); + if (param == NULL) + return -ENOMEM; + + if (copy_from_user(param, buffer, size)) { + rc = -EFAULT; + CERROR("%s: bad sepol data: rc = %d\n", obd->obd_name, rc); + GOTO(out, rc); + } + + if (param->sdd_magic != SEPOL_DOWNCALL_MAGIC_OLD) { + rc = -EINVAL; + CERROR("%s: sepol downcall bad params: rc = %d\n", + obd->obd_name, rc); + GOTO(out, rc); + } + + if (param->sdd_sepol_len == 0 || + param->sdd_sepol_len >= sizeof(imp->imp_sec->ps_sepol)) { + rc = -EINVAL; + CERROR("%s: invalid sepol data returned: rc = %d\n", + obd->obd_name, rc); + GOTO(out, rc); + } + len = param->sdd_sepol_len; /* save sdd_sepol_len */ + OBD_FREE(param, size); + size = offsetof(struct sepol_downcall_data_old, + sdd_sepol[len]); + + if (count < size) { + rc = -EINVAL; + CERROR("%s: invalid sepol count = %lu, size = %d: rc = %d\n", + obd->obd_name, (unsigned long) count, size, rc); + return rc; + } + + /* alloc again with real size */ + OBD_ALLOC(param, size); + if (param == NULL) + return -ENOMEM; + + if (copy_from_user(param, buffer, size)) { + rc = -EFAULT; + CERROR("%s: cannot copy sepol data: rc = %d\n", + obd->obd_name, rc); + GOTO(out, rc); + } + + spin_lock(&imp->imp_sec->ps_lock); + snprintf(imp->imp_sec->ps_sepol, param->sdd_sepol_len + 1, "%s", + param->sdd_sepol); + imp->imp_sec->ps_sepol_mtime = ktime_set(param->sdd_sepol_mtime, 0); + spin_unlock(&imp->imp_sec->ps_lock); + +out: + if (param != NULL) + OBD_FREE(param, size); + + return rc ? rc : count; +} +#endif + +static ssize_t +lprocfs_sptlrpc_sepol_seq_write(struct file *file, const char __user *buffer, + size_t count, void *data) +{ + struct seq_file *seq = file->private_data; + struct obd_device *obd = seq->private; + struct client_obd *cli = &obd->u.cli; + struct obd_import *imp = cli->cl_import; + struct sepol_downcall_data *param; + __u32 magic; + int size = sizeof(magic); + __u16 len; + int rc = 0; + + if (count < size) { + rc = -EINVAL; + CERROR("%s: invalid buffer count = %lu, size = %d: rc = %d\n", + obd->obd_name, (unsigned long) count, size, rc); + return rc; + } + + if (copy_from_user(&magic, buffer, size)) { + rc = -EFAULT; + CERROR("%s: bad sepol magic: rc = %d\n", obd->obd_name, rc); + return rc; + } + + if (magic != SEPOL_DOWNCALL_MAGIC) { +#if LUSTRE_VERSION_CODE < OBD_OCD_VERSION(2, 16, 53, 0) + if (magic == SEPOL_DOWNCALL_MAGIC_OLD) { + return sepol_seq_write_old(obd, buffer, count); + } +#endif + rc = -EINVAL; + CERROR("%s: sepol downcall bad magic '%#08x': rc = %d\n", + obd->obd_name, magic, rc); + return rc; + } + + size = sizeof(*param); + if (count < size) { + rc = -EINVAL; + CERROR("%s: invalid data count = %lu, size = %d: rc = %d\n", + obd->obd_name, (unsigned long) count, size, rc); + return rc; + } + + OBD_ALLOC(param, size); + if (param == NULL) + return -ENOMEM; + + if (copy_from_user(param, buffer, size)) { + rc = -EFAULT; + CERROR("%s: bad sepol data: rc = %d\n", obd->obd_name, rc); + GOTO(out, rc); + } + + if (param->sdd_sepol_len == 0 || + param->sdd_sepol_len >= sizeof(imp->imp_sec->ps_sepol)) { + rc = -EINVAL; + CERROR("%s: invalid sepol data returned: rc = %d\n", + obd->obd_name, rc); + GOTO(out, rc); + } + len = param->sdd_sepol_len; /* save sdd_sepol_len */ + OBD_FREE(param, size); + size = offsetof(struct sepol_downcall_data, + sdd_sepol[len]); + + /* alloc again with real size */ + OBD_ALLOC(param, size); + if (param == NULL) + return -ENOMEM; + + if (copy_from_user(param, buffer, size)) { + rc = -EFAULT; + CERROR("%s: cannot copy sepol data: rc = %d\n", + obd->obd_name, rc); + GOTO(out, rc); + } + + spin_lock(&imp->imp_sec->ps_lock); + snprintf(imp->imp_sec->ps_sepol, param->sdd_sepol_len + 1, "%s", + param->sdd_sepol); + imp->imp_sec->ps_sepol_mtime = ktime_set(param->sdd_sepol_mtime, 0); + spin_unlock(&imp->imp_sec->ps_lock); + +out: + if (param != NULL) + OBD_FREE(param, size); + + return rc ? rc : count; +} +LPROC_SEQ_FOPS_WR_ONLY(srpc, sptlrpc_sepol); + +int sptlrpc_lprocfs_cliobd_attach(struct obd_device *obd) +{ + if (strcmp(obd->obd_type->typ_name, LUSTRE_OSC_NAME) != 0 && + strcmp(obd->obd_type->typ_name, LUSTRE_MDC_NAME) != 0 && + strcmp(obd->obd_type->typ_name, LUSTRE_MGC_NAME) != 0 && + strcmp(obd->obd_type->typ_name, LUSTRE_LWP_NAME) != 0 && + strcmp(obd->obd_type->typ_name, LUSTRE_OSP_NAME) != 0) { + CERROR("can't register lproc for obd type %s\n", + obd->obd_type->typ_name); + return -EINVAL; + } + + debugfs_create_file("srpc_info", 0444, obd->obd_debugfs_entry, obd, + &sptlrpc_info_lprocfs_fops); + + debugfs_create_file("srpc_contexts", 0444, obd->obd_debugfs_entry, obd, + &sptlrpc_ctxs_lprocfs_fops); + + debugfs_create_file("srpc_sepol", 0200, obd->obd_debugfs_entry, obd, + &srpc_sptlrpc_sepol_fops); + + return 0; } EXPORT_SYMBOL(sptlrpc_lprocfs_cliobd_attach); -LPROC_SEQ_FOPS_RO(sptlrpc_proc_enc_pool); +LDEBUGFS_SEQ_FOPS_RO(sptlrpc_proc_enc_pool); + static struct lprocfs_vars sptlrpc_lprocfs_vars[] = { { .name = "encrypt_page_pools", .fops = &sptlrpc_proc_enc_pool_fops }, { NULL } }; +struct dentry *sptlrpc_debugfs_dir; +EXPORT_SYMBOL(sptlrpc_debugfs_dir); + +struct proc_dir_entry *sptlrpc_lprocfs_dir; +EXPORT_SYMBOL(sptlrpc_lprocfs_dir); + int sptlrpc_lproc_init(void) { int rc; - LASSERT(sptlrpc_proc_root == NULL); + LASSERT(sptlrpc_debugfs_dir == NULL); - sptlrpc_proc_root = lprocfs_register("sptlrpc", proc_lustre_root, - sptlrpc_lprocfs_vars, NULL); - if (IS_ERR(sptlrpc_proc_root)) { - rc = PTR_ERR(sptlrpc_proc_root); - sptlrpc_proc_root = NULL; - return rc; + sptlrpc_debugfs_dir = debugfs_create_dir("sptlrpc", + debugfs_lustre_root); + ldebugfs_add_vars(sptlrpc_debugfs_dir, sptlrpc_lprocfs_vars, NULL); + + sptlrpc_lprocfs_dir = lprocfs_register("sptlrpc", proc_lustre_root, + NULL, NULL); + if (IS_ERR_OR_NULL(sptlrpc_lprocfs_dir)) { + rc = PTR_ERR(sptlrpc_lprocfs_dir); + rc = sptlrpc_lprocfs_dir ? PTR_ERR(sptlrpc_lprocfs_dir) + : -ENOMEM; + sptlrpc_lprocfs_dir = NULL; } return 0; } void sptlrpc_lproc_fini(void) { - if (sptlrpc_proc_root) { - lprocfs_remove(&sptlrpc_proc_root); - sptlrpc_proc_root = NULL; - } -} + debugfs_remove_recursive(sptlrpc_debugfs_dir); + sptlrpc_debugfs_dir = NULL; + if (!IS_ERR_OR_NULL(sptlrpc_lprocfs_dir)) + lprocfs_remove(&sptlrpc_lprocfs_dir); +}