Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0
0002 /*
0003  * Documentation/ABI/stable/sysfs-fs-orangefs:
0004  *
0005  * What:        /sys/fs/orangefs/perf_counter_reset
0006  * Date:        June 2015
0007  * Contact:     Mike Marshall <hubcap@omnibond.com>
0008  * Description:
0009  *          echo a 0 or a 1 into perf_counter_reset to
0010  *          reset all the counters in
0011  *          /sys/fs/orangefs/perf_counters
0012  *          except ones with PINT_PERF_PRESERVE set.
0013  *
0014  *
0015  * What:        /sys/fs/orangefs/perf_counters/...
0016  * Date:        Jun 2015
0017  * Contact:     Mike Marshall <hubcap@omnibond.com>
0018  * Description:
0019  *          Counters and settings for various caches.
0020  *          Read only.
0021  *
0022  *
0023  * What:        /sys/fs/orangefs/perf_time_interval_secs
0024  * Date:        Jun 2015
0025  * Contact:     Mike Marshall <hubcap@omnibond.com>
0026  * Description:
0027  *          Length of perf counter intervals in
0028  *          seconds.
0029  *
0030  *
0031  * What:        /sys/fs/orangefs/perf_history_size
0032  * Date:        Jun 2015
0033  * Contact:     Mike Marshall <hubcap@omnibond.com>
0034  * Description:
0035  *          The perf_counters cache statistics have N, or
0036  *          perf_history_size, samples. The default is
0037  *          one.
0038  *
0039  *          Every perf_time_interval_secs the (first)
0040  *          samples are reset.
0041  *
0042  *          If N is greater than one, the "current" set
0043  *          of samples is reset, and the samples from the
0044  *          other N-1 intervals remain available.
0045  *
0046  *
0047  * What:        /sys/fs/orangefs/op_timeout_secs
0048  * Date:        Jun 2015
0049  * Contact:     Mike Marshall <hubcap@omnibond.com>
0050  * Description:
0051  *          Service operation timeout in seconds.
0052  *
0053  *
0054  * What:        /sys/fs/orangefs/slot_timeout_secs
0055  * Date:        Jun 2015
0056  * Contact:     Mike Marshall <hubcap@omnibond.com>
0057  * Description:
0058  *          "Slot" timeout in seconds. A "slot"
0059  *          is an indexed buffer in the shared
0060  *          memory segment used for communication
0061  *          between the kernel module and userspace.
0062  *          Slots are requested and waited for,
0063  *          the wait times out after slot_timeout_secs.
0064  *
0065  * What:        /sys/fs/orangefs/cache_timeout_msecs
0066  * Date:        Mar 2018
0067  * Contact:     Martin Brandenburg <martin@omnibond.com>
0068  * Description:
0069  *          Time in milliseconds between which
0070  *          orangefs_revalidate_mapping will invalidate the page
0071  *          cache.
0072  *
0073  * What:        /sys/fs/orangefs/dcache_timeout_msecs
0074  * Date:        Jul 2016
0075  * Contact:     Martin Brandenburg <martin@omnibond.com>
0076  * Description:
0077  *          Time lookup is valid in milliseconds.
0078  *
0079  * What:        /sys/fs/orangefs/getattr_timeout_msecs
0080  * Date:        Jul 2016
0081  * Contact:     Martin Brandenburg <martin@omnibond.com>
0082  * Description:
0083  *          Time getattr is valid in milliseconds.
0084  *
0085  * What:        /sys/fs/orangefs/readahead_count
0086  * Date:        Aug 2016
0087  * Contact:     Martin Brandenburg <martin@omnibond.com>
0088  * Description:
0089  *          Readahead cache buffer count.
0090  *
0091  * What:        /sys/fs/orangefs/readahead_size
0092  * Date:        Aug 2016
0093  * Contact:     Martin Brandenburg <martin@omnibond.com>
0094  * Description:
0095  *          Readahead cache buffer size.
0096  *
0097  * What:        /sys/fs/orangefs/readahead_count_size
0098  * Date:        Aug 2016
0099  * Contact:     Martin Brandenburg <martin@omnibond.com>
0100  * Description:
0101  *          Readahead cache buffer count and size.
0102  *
0103  * What:        /sys/fs/orangefs/readahead_readcnt
0104  * Date:        Jan 2017
0105  * Contact:     Martin Brandenburg <martin@omnibond.com>
0106  * Description:
0107  *          Number of buffers (in multiples of readahead_size)
0108  *          which can be read ahead for a single file at once.
0109  *
0110  * What:        /sys/fs/orangefs/acache/...
0111  * Date:        Jun 2015
0112  * Contact:     Martin Brandenburg <martin@omnibond.com>
0113  * Description:
0114  *          Attribute cache configurable settings.
0115  *
0116  *
0117  * What:        /sys/fs/orangefs/ncache/...
0118  * Date:        Jun 2015
0119  * Contact:     Mike Marshall <hubcap@omnibond.com>
0120  * Description:
0121  *          Name cache configurable settings.
0122  *
0123  *
0124  * What:        /sys/fs/orangefs/capcache/...
0125  * Date:        Jun 2015
0126  * Contact:     Mike Marshall <hubcap@omnibond.com>
0127  * Description:
0128  *          Capability cache configurable settings.
0129  *
0130  *
0131  * What:        /sys/fs/orangefs/ccache/...
0132  * Date:        Jun 2015
0133  * Contact:     Mike Marshall <hubcap@omnibond.com>
0134  * Description:
0135  *          Credential cache configurable settings.
0136  *
0137  */
0138 
0139 #include <linux/fs.h>
0140 #include <linux/kobject.h>
0141 #include <linux/string.h>
0142 #include <linux/sysfs.h>
0143 #include <linux/module.h>
0144 #include <linux/init.h>
0145 
0146 #include "protocol.h"
0147 #include "orangefs-kernel.h"
0148 #include "orangefs-sysfs.h"
0149 
0150 #define ORANGEFS_KOBJ_ID "orangefs"
0151 #define ACACHE_KOBJ_ID "acache"
0152 #define CAPCACHE_KOBJ_ID "capcache"
0153 #define CCACHE_KOBJ_ID "ccache"
0154 #define NCACHE_KOBJ_ID "ncache"
0155 #define PC_KOBJ_ID "pc"
0156 #define STATS_KOBJ_ID "stats"
0157 
0158 /*
0159  * Every item calls orangefs_attr_show and orangefs_attr_store through
0160  * orangefs_sysfs_ops. They look at the orangefs_attributes further below to
0161  * call one of sysfs_int_show, sysfs_int_store, sysfs_service_op_show, or
0162  * sysfs_service_op_store.
0163  */
0164 
0165 struct orangefs_attribute {
0166     struct attribute attr;
0167     ssize_t (*show)(struct kobject *kobj,
0168             struct orangefs_attribute *attr,
0169             char *buf);
0170     ssize_t (*store)(struct kobject *kobj,
0171              struct orangefs_attribute *attr,
0172              const char *buf,
0173              size_t count);
0174 };
0175 
0176 static ssize_t orangefs_attr_show(struct kobject *kobj,
0177                   struct attribute *attr,
0178                   char *buf)
0179 {
0180     struct orangefs_attribute *attribute;
0181 
0182     attribute = container_of(attr, struct orangefs_attribute, attr);
0183     if (!attribute->show)
0184         return -EIO;
0185     return attribute->show(kobj, attribute, buf);
0186 }
0187 
0188 static ssize_t orangefs_attr_store(struct kobject *kobj,
0189                    struct attribute *attr,
0190                    const char *buf,
0191                    size_t len)
0192 {
0193     struct orangefs_attribute *attribute;
0194 
0195     if (!strcmp(kobj->name, PC_KOBJ_ID) ||
0196         !strcmp(kobj->name, STATS_KOBJ_ID))
0197         return -EPERM;
0198 
0199     attribute = container_of(attr, struct orangefs_attribute, attr);
0200     if (!attribute->store)
0201         return -EIO;
0202     return attribute->store(kobj, attribute, buf, len);
0203 }
0204 
0205 static const struct sysfs_ops orangefs_sysfs_ops = {
0206     .show = orangefs_attr_show,
0207     .store = orangefs_attr_store,
0208 };
0209 
0210 static ssize_t sysfs_int_show(struct kobject *kobj,
0211     struct orangefs_attribute *attr, char *buf)
0212 {
0213     int rc = -EIO;
0214 
0215     gossip_debug(GOSSIP_SYSFS_DEBUG, "sysfs_int_show: id:%s:\n",
0216         kobj->name);
0217 
0218     if (!strcmp(kobj->name, ORANGEFS_KOBJ_ID)) {
0219         if (!strcmp(attr->attr.name, "op_timeout_secs")) {
0220             rc = scnprintf(buf,
0221                        PAGE_SIZE,
0222                        "%d\n",
0223                        op_timeout_secs);
0224             goto out;
0225         } else if (!strcmp(attr->attr.name,
0226                    "slot_timeout_secs")) {
0227             rc = scnprintf(buf,
0228                        PAGE_SIZE,
0229                        "%d\n",
0230                        slot_timeout_secs);
0231             goto out;
0232         } else if (!strcmp(attr->attr.name,
0233                    "cache_timeout_msecs")) {
0234             rc = scnprintf(buf,
0235                        PAGE_SIZE,
0236                        "%d\n",
0237                        orangefs_cache_timeout_msecs);
0238             goto out;
0239         } else if (!strcmp(attr->attr.name,
0240                    "dcache_timeout_msecs")) {
0241             rc = scnprintf(buf,
0242                        PAGE_SIZE,
0243                        "%d\n",
0244                        orangefs_dcache_timeout_msecs);
0245             goto out;
0246         } else if (!strcmp(attr->attr.name,
0247                    "getattr_timeout_msecs")) {
0248             rc = scnprintf(buf,
0249                        PAGE_SIZE,
0250                        "%d\n",
0251                        orangefs_getattr_timeout_msecs);
0252             goto out;
0253         } else {
0254             goto out;
0255         }
0256 
0257     } else if (!strcmp(kobj->name, STATS_KOBJ_ID)) {
0258         if (!strcmp(attr->attr.name, "reads")) {
0259             rc = scnprintf(buf,
0260                        PAGE_SIZE,
0261                        "%lu\n",
0262                        orangefs_stats.reads);
0263             goto out;
0264         } else if (!strcmp(attr->attr.name, "writes")) {
0265             rc = scnprintf(buf,
0266                        PAGE_SIZE,
0267                        "%lu\n",
0268                        orangefs_stats.writes);
0269             goto out;
0270         } else {
0271             goto out;
0272         }
0273     }
0274 
0275 out:
0276 
0277     return rc;
0278 }
0279 
0280 static ssize_t sysfs_int_store(struct kobject *kobj,
0281     struct orangefs_attribute *attr, const char *buf, size_t count)
0282 {
0283     int rc = 0;
0284 
0285     gossip_debug(GOSSIP_SYSFS_DEBUG,
0286              "sysfs_int_store: start attr->attr.name:%s: buf:%s:\n",
0287              attr->attr.name, buf);
0288 
0289     if (!strcmp(attr->attr.name, "op_timeout_secs")) {
0290         rc = kstrtoint(buf, 0, &op_timeout_secs);
0291         goto out;
0292     } else if (!strcmp(attr->attr.name, "slot_timeout_secs")) {
0293         rc = kstrtoint(buf, 0, &slot_timeout_secs);
0294         goto out;
0295     } else if (!strcmp(attr->attr.name, "cache_timeout_msecs")) {
0296         rc = kstrtoint(buf, 0, &orangefs_cache_timeout_msecs);
0297         goto out;
0298     } else if (!strcmp(attr->attr.name, "dcache_timeout_msecs")) {
0299         rc = kstrtoint(buf, 0, &orangefs_dcache_timeout_msecs);
0300         goto out;
0301     } else if (!strcmp(attr->attr.name, "getattr_timeout_msecs")) {
0302         rc = kstrtoint(buf, 0, &orangefs_getattr_timeout_msecs);
0303         goto out;
0304     } else {
0305         goto out;
0306     }
0307 
0308 out:
0309     if (rc)
0310         rc = -EINVAL;
0311     else
0312         rc = count;
0313 
0314     return rc;
0315 }
0316 
0317 /*
0318  * obtain attribute values from userspace with a service operation.
0319  */
0320 static ssize_t sysfs_service_op_show(struct kobject *kobj,
0321     struct orangefs_attribute *attr, char *buf)
0322 {
0323     struct orangefs_kernel_op_s *new_op = NULL;
0324     int rc = 0;
0325     char *ser_op_type = NULL;
0326     __u32 op_alloc_type;
0327 
0328     gossip_debug(GOSSIP_SYSFS_DEBUG,
0329              "sysfs_service_op_show: id:%s:\n",
0330              kobj->name);
0331 
0332     if (strcmp(kobj->name, PC_KOBJ_ID))
0333         op_alloc_type = ORANGEFS_VFS_OP_PARAM;
0334     else
0335         op_alloc_type = ORANGEFS_VFS_OP_PERF_COUNT;
0336 
0337     new_op = op_alloc(op_alloc_type);
0338     if (!new_op)
0339         return -ENOMEM;
0340 
0341     /* Can't do a service_operation if the client is not running... */
0342     rc = is_daemon_in_service();
0343     if (rc) {
0344         pr_info_ratelimited("%s: Client not running :%d:\n",
0345             __func__,
0346             is_daemon_in_service());
0347         goto out;
0348     }
0349 
0350     if (strcmp(kobj->name, PC_KOBJ_ID))
0351         new_op->upcall.req.param.type = ORANGEFS_PARAM_REQUEST_GET;
0352 
0353     if (!strcmp(kobj->name, ORANGEFS_KOBJ_ID)) {
0354         /* Drop unsupported requests first. */
0355         if (!(orangefs_features & ORANGEFS_FEATURE_READAHEAD) &&
0356             (!strcmp(attr->attr.name, "readahead_count") ||
0357             !strcmp(attr->attr.name, "readahead_size") ||
0358             !strcmp(attr->attr.name, "readahead_count_size") ||
0359             !strcmp(attr->attr.name, "readahead_readcnt"))) {
0360             rc = -EINVAL;
0361             goto out;
0362         }
0363 
0364         if (!strcmp(attr->attr.name, "perf_history_size"))
0365             new_op->upcall.req.param.op =
0366                 ORANGEFS_PARAM_REQUEST_OP_PERF_HISTORY_SIZE;
0367         else if (!strcmp(attr->attr.name,
0368                  "perf_time_interval_secs"))
0369             new_op->upcall.req.param.op =
0370                 ORANGEFS_PARAM_REQUEST_OP_PERF_TIME_INTERVAL_SECS;
0371         else if (!strcmp(attr->attr.name,
0372                  "perf_counter_reset"))
0373             new_op->upcall.req.param.op =
0374                 ORANGEFS_PARAM_REQUEST_OP_PERF_RESET;
0375 
0376         else if (!strcmp(attr->attr.name,
0377                  "readahead_count"))
0378             new_op->upcall.req.param.op =
0379                 ORANGEFS_PARAM_REQUEST_OP_READAHEAD_COUNT;
0380 
0381         else if (!strcmp(attr->attr.name,
0382                  "readahead_size"))
0383             new_op->upcall.req.param.op =
0384                 ORANGEFS_PARAM_REQUEST_OP_READAHEAD_SIZE;
0385 
0386         else if (!strcmp(attr->attr.name,
0387                  "readahead_count_size"))
0388             new_op->upcall.req.param.op =
0389                 ORANGEFS_PARAM_REQUEST_OP_READAHEAD_COUNT_SIZE;
0390 
0391         else if (!strcmp(attr->attr.name,
0392                  "readahead_readcnt"))
0393             new_op->upcall.req.param.op =
0394                 ORANGEFS_PARAM_REQUEST_OP_READAHEAD_READCNT;
0395     } else if (!strcmp(kobj->name, ACACHE_KOBJ_ID)) {
0396         if (!strcmp(attr->attr.name, "timeout_msecs"))
0397             new_op->upcall.req.param.op =
0398                 ORANGEFS_PARAM_REQUEST_OP_ACACHE_TIMEOUT_MSECS;
0399 
0400         if (!strcmp(attr->attr.name, "hard_limit"))
0401             new_op->upcall.req.param.op =
0402                 ORANGEFS_PARAM_REQUEST_OP_ACACHE_HARD_LIMIT;
0403 
0404         if (!strcmp(attr->attr.name, "soft_limit"))
0405             new_op->upcall.req.param.op =
0406                 ORANGEFS_PARAM_REQUEST_OP_ACACHE_SOFT_LIMIT;
0407 
0408         if (!strcmp(attr->attr.name, "reclaim_percentage"))
0409             new_op->upcall.req.param.op =
0410               ORANGEFS_PARAM_REQUEST_OP_ACACHE_RECLAIM_PERCENTAGE;
0411 
0412     } else if (!strcmp(kobj->name, CAPCACHE_KOBJ_ID)) {
0413         if (!strcmp(attr->attr.name, "timeout_secs"))
0414             new_op->upcall.req.param.op =
0415                 ORANGEFS_PARAM_REQUEST_OP_CAPCACHE_TIMEOUT_SECS;
0416 
0417         if (!strcmp(attr->attr.name, "hard_limit"))
0418             new_op->upcall.req.param.op =
0419                 ORANGEFS_PARAM_REQUEST_OP_CAPCACHE_HARD_LIMIT;
0420 
0421         if (!strcmp(attr->attr.name, "soft_limit"))
0422             new_op->upcall.req.param.op =
0423                 ORANGEFS_PARAM_REQUEST_OP_CAPCACHE_SOFT_LIMIT;
0424 
0425         if (!strcmp(attr->attr.name, "reclaim_percentage"))
0426             new_op->upcall.req.param.op =
0427               ORANGEFS_PARAM_REQUEST_OP_CAPCACHE_RECLAIM_PERCENTAGE;
0428 
0429     } else if (!strcmp(kobj->name, CCACHE_KOBJ_ID)) {
0430         if (!strcmp(attr->attr.name, "timeout_secs"))
0431             new_op->upcall.req.param.op =
0432                 ORANGEFS_PARAM_REQUEST_OP_CCACHE_TIMEOUT_SECS;
0433 
0434         if (!strcmp(attr->attr.name, "hard_limit"))
0435             new_op->upcall.req.param.op =
0436                 ORANGEFS_PARAM_REQUEST_OP_CCACHE_HARD_LIMIT;
0437 
0438         if (!strcmp(attr->attr.name, "soft_limit"))
0439             new_op->upcall.req.param.op =
0440                 ORANGEFS_PARAM_REQUEST_OP_CCACHE_SOFT_LIMIT;
0441 
0442         if (!strcmp(attr->attr.name, "reclaim_percentage"))
0443             new_op->upcall.req.param.op =
0444               ORANGEFS_PARAM_REQUEST_OP_CCACHE_RECLAIM_PERCENTAGE;
0445 
0446     } else if (!strcmp(kobj->name, NCACHE_KOBJ_ID)) {
0447         if (!strcmp(attr->attr.name, "timeout_msecs"))
0448             new_op->upcall.req.param.op =
0449                 ORANGEFS_PARAM_REQUEST_OP_NCACHE_TIMEOUT_MSECS;
0450 
0451         if (!strcmp(attr->attr.name, "hard_limit"))
0452             new_op->upcall.req.param.op =
0453                 ORANGEFS_PARAM_REQUEST_OP_NCACHE_HARD_LIMIT;
0454 
0455         if (!strcmp(attr->attr.name, "soft_limit"))
0456             new_op->upcall.req.param.op =
0457                 ORANGEFS_PARAM_REQUEST_OP_NCACHE_SOFT_LIMIT;
0458 
0459         if (!strcmp(attr->attr.name, "reclaim_percentage"))
0460             new_op->upcall.req.param.op =
0461               ORANGEFS_PARAM_REQUEST_OP_NCACHE_RECLAIM_PERCENTAGE;
0462 
0463     } else if (!strcmp(kobj->name, PC_KOBJ_ID)) {
0464         if (!strcmp(attr->attr.name, ACACHE_KOBJ_ID))
0465             new_op->upcall.req.perf_count.type =
0466                 ORANGEFS_PERF_COUNT_REQUEST_ACACHE;
0467 
0468         if (!strcmp(attr->attr.name, CAPCACHE_KOBJ_ID))
0469             new_op->upcall.req.perf_count.type =
0470                 ORANGEFS_PERF_COUNT_REQUEST_CAPCACHE;
0471 
0472         if (!strcmp(attr->attr.name, NCACHE_KOBJ_ID))
0473             new_op->upcall.req.perf_count.type =
0474                 ORANGEFS_PERF_COUNT_REQUEST_NCACHE;
0475 
0476     } else {
0477         gossip_err("sysfs_service_op_show: unknown kobj_id:%s:\n",
0478                kobj->name);
0479         rc = -EINVAL;
0480         goto out;
0481     }
0482 
0483 
0484     if (strcmp(kobj->name, PC_KOBJ_ID))
0485         ser_op_type = "orangefs_param";
0486     else
0487         ser_op_type = "orangefs_perf_count";
0488 
0489     /*
0490      * The service_operation will return an errno return code on
0491      * error, and zero on success.
0492      */
0493     rc = service_operation(new_op, ser_op_type, ORANGEFS_OP_INTERRUPTIBLE);
0494 
0495 out:
0496     if (!rc) {
0497         if (strcmp(kobj->name, PC_KOBJ_ID)) {
0498             if (new_op->upcall.req.param.op ==
0499                 ORANGEFS_PARAM_REQUEST_OP_READAHEAD_COUNT_SIZE) {
0500                 rc = scnprintf(buf, PAGE_SIZE, "%d %d\n",
0501                     (int)new_op->downcall.resp.param.u.
0502                     value32[0],
0503                     (int)new_op->downcall.resp.param.u.
0504                     value32[1]);
0505             } else {
0506                 rc = scnprintf(buf, PAGE_SIZE, "%d\n",
0507                     (int)new_op->downcall.resp.param.u.value64);
0508             }
0509         } else {
0510             rc = scnprintf(
0511                 buf,
0512                 PAGE_SIZE,
0513                 "%s",
0514                 new_op->downcall.resp.perf_count.buffer);
0515         }
0516     }
0517 
0518     op_release(new_op);
0519 
0520     return rc;
0521 
0522 }
0523 
0524 /*
0525  * pass attribute values back to userspace with a service operation.
0526  *
0527  * We have to do a memory allocation, an sscanf and a service operation.
0528  * And we have to evaluate what the user entered, to make sure the
0529  * value is within the range supported by the attribute. So, there's
0530  * a lot of return code checking and mapping going on here.
0531  *
0532  * We want to return 1 if we think everything went OK, and
0533  * EINVAL if not.
0534  */
0535 static ssize_t sysfs_service_op_store(struct kobject *kobj,
0536     struct orangefs_attribute *attr, const char *buf, size_t count)
0537 {
0538     struct orangefs_kernel_op_s *new_op = NULL;
0539     int val = 0;
0540     int rc = 0;
0541 
0542     gossip_debug(GOSSIP_SYSFS_DEBUG,
0543              "sysfs_service_op_store: id:%s:\n",
0544              kobj->name);
0545 
0546     new_op = op_alloc(ORANGEFS_VFS_OP_PARAM);
0547     if (!new_op)
0548         return -EINVAL; /* sic */
0549 
0550     /* Can't do a service_operation if the client is not running... */
0551     rc = is_daemon_in_service();
0552     if (rc) {
0553         pr_info("%s: Client not running :%d:\n",
0554             __func__,
0555             is_daemon_in_service());
0556         goto out;
0557     }
0558 
0559     /*
0560      * The value we want to send back to userspace is in buf, unless this
0561      * there are two parameters, which is specially handled below.
0562      */
0563     if (strcmp(kobj->name, ORANGEFS_KOBJ_ID) ||
0564         strcmp(attr->attr.name, "readahead_count_size")) {
0565         rc = kstrtoint(buf, 0, &val);
0566         if (rc)
0567             goto out;
0568     }
0569 
0570     new_op->upcall.req.param.type = ORANGEFS_PARAM_REQUEST_SET;
0571 
0572     if (!strcmp(kobj->name, ORANGEFS_KOBJ_ID)) {
0573         /* Drop unsupported requests first. */
0574         if (!(orangefs_features & ORANGEFS_FEATURE_READAHEAD) &&
0575             (!strcmp(attr->attr.name, "readahead_count") ||
0576             !strcmp(attr->attr.name, "readahead_size") ||
0577             !strcmp(attr->attr.name, "readahead_count_size") ||
0578             !strcmp(attr->attr.name, "readahead_readcnt"))) {
0579             rc = -EINVAL;
0580             goto out;
0581         }
0582 
0583         if (!strcmp(attr->attr.name, "perf_history_size")) {
0584             if (val > 0) {
0585                 new_op->upcall.req.param.op =
0586                   ORANGEFS_PARAM_REQUEST_OP_PERF_HISTORY_SIZE;
0587             } else {
0588                 rc = 0;
0589                 goto out;
0590             }
0591         } else if (!strcmp(attr->attr.name,
0592                    "perf_time_interval_secs")) {
0593             if (val > 0) {
0594                 new_op->upcall.req.param.op =
0595                 ORANGEFS_PARAM_REQUEST_OP_PERF_TIME_INTERVAL_SECS;
0596             } else {
0597                 rc = 0;
0598                 goto out;
0599             }
0600         } else if (!strcmp(attr->attr.name,
0601                    "perf_counter_reset")) {
0602             if ((val == 0) || (val == 1)) {
0603                 new_op->upcall.req.param.op =
0604                     ORANGEFS_PARAM_REQUEST_OP_PERF_RESET;
0605             } else {
0606                 rc = 0;
0607                 goto out;
0608             }
0609         } else if (!strcmp(attr->attr.name,
0610                    "readahead_count")) {
0611             if ((val >= 0)) {
0612                 new_op->upcall.req.param.op =
0613                 ORANGEFS_PARAM_REQUEST_OP_READAHEAD_COUNT;
0614             } else {
0615                 rc = 0;
0616                 goto out;
0617             }
0618         } else if (!strcmp(attr->attr.name,
0619                    "readahead_size")) {
0620             if ((val >= 0)) {
0621                 new_op->upcall.req.param.op =
0622                 ORANGEFS_PARAM_REQUEST_OP_READAHEAD_SIZE;
0623             } else {
0624                 rc = 0;
0625                 goto out;
0626             }
0627         } else if (!strcmp(attr->attr.name,
0628                    "readahead_count_size")) {
0629             int val1, val2;
0630             rc = sscanf(buf, "%d %d", &val1, &val2);
0631             if (rc < 2) {
0632                 rc = 0;
0633                 goto out;
0634             }
0635             if ((val1 >= 0) && (val2 >= 0)) {
0636                 new_op->upcall.req.param.op =
0637                 ORANGEFS_PARAM_REQUEST_OP_READAHEAD_COUNT_SIZE;
0638             } else {
0639                 rc = 0;
0640                 goto out;
0641             }
0642             new_op->upcall.req.param.u.value32[0] = val1;
0643             new_op->upcall.req.param.u.value32[1] = val2;
0644             goto value_set;
0645         } else if (!strcmp(attr->attr.name,
0646                    "readahead_readcnt")) {
0647             if ((val >= 0)) {
0648                 new_op->upcall.req.param.op =
0649                 ORANGEFS_PARAM_REQUEST_OP_READAHEAD_READCNT;
0650             } else {
0651                 rc = 0;
0652                 goto out;
0653             }
0654         }
0655 
0656     } else if (!strcmp(kobj->name, ACACHE_KOBJ_ID)) {
0657         if (!strcmp(attr->attr.name, "hard_limit")) {
0658             if (val > -1) {
0659                 new_op->upcall.req.param.op =
0660                   ORANGEFS_PARAM_REQUEST_OP_ACACHE_HARD_LIMIT;
0661             } else {
0662                 rc = 0;
0663                 goto out;
0664             }
0665         } else if (!strcmp(attr->attr.name, "soft_limit")) {
0666             if (val > -1) {
0667                 new_op->upcall.req.param.op =
0668                   ORANGEFS_PARAM_REQUEST_OP_ACACHE_SOFT_LIMIT;
0669             } else {
0670                 rc = 0;
0671                 goto out;
0672             }
0673         } else if (!strcmp(attr->attr.name,
0674                    "reclaim_percentage")) {
0675             if ((val > -1) && (val < 101)) {
0676                 new_op->upcall.req.param.op =
0677                   ORANGEFS_PARAM_REQUEST_OP_ACACHE_RECLAIM_PERCENTAGE;
0678             } else {
0679                 rc = 0;
0680                 goto out;
0681             }
0682         } else if (!strcmp(attr->attr.name, "timeout_msecs")) {
0683             if (val > -1) {
0684                 new_op->upcall.req.param.op =
0685                   ORANGEFS_PARAM_REQUEST_OP_ACACHE_TIMEOUT_MSECS;
0686             } else {
0687                 rc = 0;
0688                 goto out;
0689             }
0690         }
0691 
0692     } else if (!strcmp(kobj->name, CAPCACHE_KOBJ_ID)) {
0693         if (!strcmp(attr->attr.name, "hard_limit")) {
0694             if (val > -1) {
0695                 new_op->upcall.req.param.op =
0696                   ORANGEFS_PARAM_REQUEST_OP_CAPCACHE_HARD_LIMIT;
0697             } else {
0698                 rc = 0;
0699                 goto out;
0700             }
0701         } else if (!strcmp(attr->attr.name, "soft_limit")) {
0702             if (val > -1) {
0703                 new_op->upcall.req.param.op =
0704                   ORANGEFS_PARAM_REQUEST_OP_CAPCACHE_SOFT_LIMIT;
0705             } else {
0706                 rc = 0;
0707                 goto out;
0708             }
0709         } else if (!strcmp(attr->attr.name,
0710                    "reclaim_percentage")) {
0711             if ((val > -1) && (val < 101)) {
0712                 new_op->upcall.req.param.op =
0713                   ORANGEFS_PARAM_REQUEST_OP_CAPCACHE_RECLAIM_PERCENTAGE;
0714             } else {
0715                 rc = 0;
0716                 goto out;
0717             }
0718         } else if (!strcmp(attr->attr.name, "timeout_secs")) {
0719             if (val > -1) {
0720                 new_op->upcall.req.param.op =
0721                   ORANGEFS_PARAM_REQUEST_OP_CAPCACHE_TIMEOUT_SECS;
0722             } else {
0723                 rc = 0;
0724                 goto out;
0725             }
0726         }
0727 
0728     } else if (!strcmp(kobj->name, CCACHE_KOBJ_ID)) {
0729         if (!strcmp(attr->attr.name, "hard_limit")) {
0730             if (val > -1) {
0731                 new_op->upcall.req.param.op =
0732                   ORANGEFS_PARAM_REQUEST_OP_CCACHE_HARD_LIMIT;
0733             } else {
0734                 rc = 0;
0735                 goto out;
0736             }
0737         } else if (!strcmp(attr->attr.name, "soft_limit")) {
0738             if (val > -1) {
0739                 new_op->upcall.req.param.op =
0740                   ORANGEFS_PARAM_REQUEST_OP_CCACHE_SOFT_LIMIT;
0741             } else {
0742                 rc = 0;
0743                 goto out;
0744             }
0745         } else if (!strcmp(attr->attr.name,
0746                    "reclaim_percentage")) {
0747             if ((val > -1) && (val < 101)) {
0748                 new_op->upcall.req.param.op =
0749                   ORANGEFS_PARAM_REQUEST_OP_CCACHE_RECLAIM_PERCENTAGE;
0750             } else {
0751                 rc = 0;
0752                 goto out;
0753             }
0754         } else if (!strcmp(attr->attr.name, "timeout_secs")) {
0755             if (val > -1) {
0756                 new_op->upcall.req.param.op =
0757                   ORANGEFS_PARAM_REQUEST_OP_CCACHE_TIMEOUT_SECS;
0758             } else {
0759                 rc = 0;
0760                 goto out;
0761             }
0762         }
0763 
0764     } else if (!strcmp(kobj->name, NCACHE_KOBJ_ID)) {
0765         if (!strcmp(attr->attr.name, "hard_limit")) {
0766             if (val > -1) {
0767                 new_op->upcall.req.param.op =
0768                   ORANGEFS_PARAM_REQUEST_OP_NCACHE_HARD_LIMIT;
0769             } else {
0770                 rc = 0;
0771                 goto out;
0772             }
0773         } else if (!strcmp(attr->attr.name, "soft_limit")) {
0774             if (val > -1) {
0775                 new_op->upcall.req.param.op =
0776                   ORANGEFS_PARAM_REQUEST_OP_NCACHE_SOFT_LIMIT;
0777             } else {
0778                 rc = 0;
0779                 goto out;
0780             }
0781         } else if (!strcmp(attr->attr.name,
0782                    "reclaim_percentage")) {
0783             if ((val > -1) && (val < 101)) {
0784                 new_op->upcall.req.param.op =
0785                     ORANGEFS_PARAM_REQUEST_OP_NCACHE_RECLAIM_PERCENTAGE;
0786             } else {
0787                 rc = 0;
0788                 goto out;
0789             }
0790         } else if (!strcmp(attr->attr.name, "timeout_msecs")) {
0791             if (val > -1) {
0792                 new_op->upcall.req.param.op =
0793                   ORANGEFS_PARAM_REQUEST_OP_NCACHE_TIMEOUT_MSECS;
0794             } else {
0795                 rc = 0;
0796                 goto out;
0797             }
0798         }
0799 
0800     } else {
0801         gossip_err("sysfs_service_op_store: unknown kobj_id:%s:\n",
0802                kobj->name);
0803         rc = -EINVAL;
0804         goto out;
0805     }
0806 
0807     new_op->upcall.req.param.u.value64 = val;
0808 value_set:
0809 
0810     /*
0811      * The service_operation will return a errno return code on
0812      * error, and zero on success.
0813      */
0814     rc = service_operation(new_op, "orangefs_param", ORANGEFS_OP_INTERRUPTIBLE);
0815 
0816     if (rc < 0) {
0817         gossip_err("sysfs_service_op_store: service op returned:%d:\n",
0818             rc);
0819         rc = 0;
0820     } else {
0821         rc = count;
0822     }
0823 
0824 out:
0825     op_release(new_op);
0826 
0827     if (rc == -ENOMEM || rc == 0)
0828         rc = -EINVAL;
0829 
0830     return rc;
0831 }
0832 
0833 static struct orangefs_attribute op_timeout_secs_attribute =
0834     __ATTR(op_timeout_secs, 0664, sysfs_int_show, sysfs_int_store);
0835 
0836 static struct orangefs_attribute slot_timeout_secs_attribute =
0837     __ATTR(slot_timeout_secs, 0664, sysfs_int_show, sysfs_int_store);
0838 
0839 static struct orangefs_attribute cache_timeout_msecs_attribute =
0840     __ATTR(cache_timeout_msecs, 0664, sysfs_int_show, sysfs_int_store);
0841 
0842 static struct orangefs_attribute dcache_timeout_msecs_attribute =
0843     __ATTR(dcache_timeout_msecs, 0664, sysfs_int_show, sysfs_int_store);
0844 
0845 static struct orangefs_attribute getattr_timeout_msecs_attribute =
0846     __ATTR(getattr_timeout_msecs, 0664, sysfs_int_show, sysfs_int_store);
0847 
0848 static struct orangefs_attribute readahead_count_attribute =
0849     __ATTR(readahead_count, 0664, sysfs_service_op_show,
0850            sysfs_service_op_store);
0851 
0852 static struct orangefs_attribute readahead_size_attribute =
0853     __ATTR(readahead_size, 0664, sysfs_service_op_show,
0854            sysfs_service_op_store);
0855 
0856 static struct orangefs_attribute readahead_count_size_attribute =
0857     __ATTR(readahead_count_size, 0664, sysfs_service_op_show,
0858            sysfs_service_op_store);
0859 
0860 static struct orangefs_attribute readahead_readcnt_attribute =
0861     __ATTR(readahead_readcnt, 0664, sysfs_service_op_show,
0862            sysfs_service_op_store);
0863 
0864 static struct orangefs_attribute perf_counter_reset_attribute =
0865     __ATTR(perf_counter_reset,
0866            0664,
0867            sysfs_service_op_show,
0868            sysfs_service_op_store);
0869 
0870 static struct orangefs_attribute perf_history_size_attribute =
0871     __ATTR(perf_history_size,
0872            0664,
0873            sysfs_service_op_show,
0874            sysfs_service_op_store);
0875 
0876 static struct orangefs_attribute perf_time_interval_secs_attribute =
0877     __ATTR(perf_time_interval_secs,
0878            0664,
0879            sysfs_service_op_show,
0880            sysfs_service_op_store);
0881 
0882 static struct attribute *orangefs_default_attrs[] = {
0883     &op_timeout_secs_attribute.attr,
0884     &slot_timeout_secs_attribute.attr,
0885     &cache_timeout_msecs_attribute.attr,
0886     &dcache_timeout_msecs_attribute.attr,
0887     &getattr_timeout_msecs_attribute.attr,
0888     &readahead_count_attribute.attr,
0889     &readahead_size_attribute.attr,
0890     &readahead_count_size_attribute.attr,
0891     &readahead_readcnt_attribute.attr,
0892     &perf_counter_reset_attribute.attr,
0893     &perf_history_size_attribute.attr,
0894     &perf_time_interval_secs_attribute.attr,
0895     NULL,
0896 };
0897 ATTRIBUTE_GROUPS(orangefs_default);
0898 
0899 static struct kobj_type orangefs_ktype = {
0900     .sysfs_ops = &orangefs_sysfs_ops,
0901     .default_groups = orangefs_default_groups,
0902 };
0903 
0904 static struct orangefs_attribute acache_hard_limit_attribute =
0905     __ATTR(hard_limit,
0906            0664,
0907            sysfs_service_op_show,
0908            sysfs_service_op_store);
0909 
0910 static struct orangefs_attribute acache_reclaim_percent_attribute =
0911     __ATTR(reclaim_percentage,
0912            0664,
0913            sysfs_service_op_show,
0914            sysfs_service_op_store);
0915 
0916 static struct orangefs_attribute acache_soft_limit_attribute =
0917     __ATTR(soft_limit,
0918            0664,
0919            sysfs_service_op_show,
0920            sysfs_service_op_store);
0921 
0922 static struct orangefs_attribute acache_timeout_msecs_attribute =
0923     __ATTR(timeout_msecs,
0924            0664,
0925            sysfs_service_op_show,
0926            sysfs_service_op_store);
0927 
0928 static struct attribute *acache_orangefs_default_attrs[] = {
0929     &acache_hard_limit_attribute.attr,
0930     &acache_reclaim_percent_attribute.attr,
0931     &acache_soft_limit_attribute.attr,
0932     &acache_timeout_msecs_attribute.attr,
0933     NULL,
0934 };
0935 ATTRIBUTE_GROUPS(acache_orangefs_default);
0936 
0937 static struct kobj_type acache_orangefs_ktype = {
0938     .sysfs_ops = &orangefs_sysfs_ops,
0939     .default_groups = acache_orangefs_default_groups,
0940 };
0941 
0942 static struct orangefs_attribute capcache_hard_limit_attribute =
0943     __ATTR(hard_limit,
0944            0664,
0945            sysfs_service_op_show,
0946            sysfs_service_op_store);
0947 
0948 static struct orangefs_attribute capcache_reclaim_percent_attribute =
0949     __ATTR(reclaim_percentage,
0950            0664,
0951            sysfs_service_op_show,
0952            sysfs_service_op_store);
0953 
0954 static struct orangefs_attribute capcache_soft_limit_attribute =
0955     __ATTR(soft_limit,
0956            0664,
0957            sysfs_service_op_show,
0958            sysfs_service_op_store);
0959 
0960 static struct orangefs_attribute capcache_timeout_secs_attribute =
0961     __ATTR(timeout_secs,
0962            0664,
0963            sysfs_service_op_show,
0964            sysfs_service_op_store);
0965 
0966 static struct attribute *capcache_orangefs_default_attrs[] = {
0967     &capcache_hard_limit_attribute.attr,
0968     &capcache_reclaim_percent_attribute.attr,
0969     &capcache_soft_limit_attribute.attr,
0970     &capcache_timeout_secs_attribute.attr,
0971     NULL,
0972 };
0973 ATTRIBUTE_GROUPS(capcache_orangefs_default);
0974 
0975 static struct kobj_type capcache_orangefs_ktype = {
0976     .sysfs_ops = &orangefs_sysfs_ops,
0977     .default_groups = capcache_orangefs_default_groups,
0978 };
0979 
0980 static struct orangefs_attribute ccache_hard_limit_attribute =
0981     __ATTR(hard_limit,
0982            0664,
0983            sysfs_service_op_show,
0984            sysfs_service_op_store);
0985 
0986 static struct orangefs_attribute ccache_reclaim_percent_attribute =
0987     __ATTR(reclaim_percentage,
0988            0664,
0989            sysfs_service_op_show,
0990            sysfs_service_op_store);
0991 
0992 static struct orangefs_attribute ccache_soft_limit_attribute =
0993     __ATTR(soft_limit,
0994            0664,
0995            sysfs_service_op_show,
0996            sysfs_service_op_store);
0997 
0998 static struct orangefs_attribute ccache_timeout_secs_attribute =
0999     __ATTR(timeout_secs,
1000            0664,
1001            sysfs_service_op_show,
1002            sysfs_service_op_store);
1003 
1004 static struct attribute *ccache_orangefs_default_attrs[] = {
1005     &ccache_hard_limit_attribute.attr,
1006     &ccache_reclaim_percent_attribute.attr,
1007     &ccache_soft_limit_attribute.attr,
1008     &ccache_timeout_secs_attribute.attr,
1009     NULL,
1010 };
1011 ATTRIBUTE_GROUPS(ccache_orangefs_default);
1012 
1013 static struct kobj_type ccache_orangefs_ktype = {
1014     .sysfs_ops = &orangefs_sysfs_ops,
1015     .default_groups = ccache_orangefs_default_groups,
1016 };
1017 
1018 static struct orangefs_attribute ncache_hard_limit_attribute =
1019     __ATTR(hard_limit,
1020            0664,
1021            sysfs_service_op_show,
1022            sysfs_service_op_store);
1023 
1024 static struct orangefs_attribute ncache_reclaim_percent_attribute =
1025     __ATTR(reclaim_percentage,
1026            0664,
1027            sysfs_service_op_show,
1028            sysfs_service_op_store);
1029 
1030 static struct orangefs_attribute ncache_soft_limit_attribute =
1031     __ATTR(soft_limit,
1032            0664,
1033            sysfs_service_op_show,
1034            sysfs_service_op_store);
1035 
1036 static struct orangefs_attribute ncache_timeout_msecs_attribute =
1037     __ATTR(timeout_msecs,
1038            0664,
1039            sysfs_service_op_show,
1040            sysfs_service_op_store);
1041 
1042 static struct attribute *ncache_orangefs_default_attrs[] = {
1043     &ncache_hard_limit_attribute.attr,
1044     &ncache_reclaim_percent_attribute.attr,
1045     &ncache_soft_limit_attribute.attr,
1046     &ncache_timeout_msecs_attribute.attr,
1047     NULL,
1048 };
1049 ATTRIBUTE_GROUPS(ncache_orangefs_default);
1050 
1051 static struct kobj_type ncache_orangefs_ktype = {
1052     .sysfs_ops = &orangefs_sysfs_ops,
1053     .default_groups = ncache_orangefs_default_groups,
1054 };
1055 
1056 static struct orangefs_attribute pc_acache_attribute =
1057     __ATTR(acache,
1058            0664,
1059            sysfs_service_op_show,
1060            NULL);
1061 
1062 static struct orangefs_attribute pc_capcache_attribute =
1063     __ATTR(capcache,
1064            0664,
1065            sysfs_service_op_show,
1066            NULL);
1067 
1068 static struct orangefs_attribute pc_ncache_attribute =
1069     __ATTR(ncache,
1070            0664,
1071            sysfs_service_op_show,
1072            NULL);
1073 
1074 static struct attribute *pc_orangefs_default_attrs[] = {
1075     &pc_acache_attribute.attr,
1076     &pc_capcache_attribute.attr,
1077     &pc_ncache_attribute.attr,
1078     NULL,
1079 };
1080 ATTRIBUTE_GROUPS(pc_orangefs_default);
1081 
1082 static struct kobj_type pc_orangefs_ktype = {
1083     .sysfs_ops = &orangefs_sysfs_ops,
1084     .default_groups = pc_orangefs_default_groups,
1085 };
1086 
1087 static struct orangefs_attribute stats_reads_attribute =
1088     __ATTR(reads,
1089            0664,
1090            sysfs_int_show,
1091            NULL);
1092 
1093 static struct orangefs_attribute stats_writes_attribute =
1094     __ATTR(writes,
1095            0664,
1096            sysfs_int_show,
1097            NULL);
1098 
1099 static struct attribute *stats_orangefs_default_attrs[] = {
1100     &stats_reads_attribute.attr,
1101     &stats_writes_attribute.attr,
1102     NULL,
1103 };
1104 ATTRIBUTE_GROUPS(stats_orangefs_default);
1105 
1106 static struct kobj_type stats_orangefs_ktype = {
1107     .sysfs_ops = &orangefs_sysfs_ops,
1108     .default_groups = stats_orangefs_default_groups,
1109 };
1110 
1111 static struct kobject *orangefs_obj;
1112 static struct kobject *acache_orangefs_obj;
1113 static struct kobject *capcache_orangefs_obj;
1114 static struct kobject *ccache_orangefs_obj;
1115 static struct kobject *ncache_orangefs_obj;
1116 static struct kobject *pc_orangefs_obj;
1117 static struct kobject *stats_orangefs_obj;
1118 
1119 int orangefs_sysfs_init(void)
1120 {
1121     int rc = -EINVAL;
1122 
1123     gossip_debug(GOSSIP_SYSFS_DEBUG, "orangefs_sysfs_init: start\n");
1124 
1125     /* create /sys/fs/orangefs. */
1126     orangefs_obj = kzalloc(sizeof(*orangefs_obj), GFP_KERNEL);
1127     if (!orangefs_obj)
1128         goto out;
1129 
1130     rc = kobject_init_and_add(orangefs_obj,
1131                   &orangefs_ktype,
1132                   fs_kobj,
1133                   ORANGEFS_KOBJ_ID);
1134 
1135     if (rc)
1136         goto ofs_obj_bail;
1137 
1138     kobject_uevent(orangefs_obj, KOBJ_ADD);
1139 
1140     /* create /sys/fs/orangefs/acache. */
1141     acache_orangefs_obj = kzalloc(sizeof(*acache_orangefs_obj), GFP_KERNEL);
1142     if (!acache_orangefs_obj) {
1143         rc = -EINVAL;
1144         goto ofs_obj_bail;
1145     }
1146 
1147     rc = kobject_init_and_add(acache_orangefs_obj,
1148                   &acache_orangefs_ktype,
1149                   orangefs_obj,
1150                   ACACHE_KOBJ_ID);
1151 
1152     if (rc)
1153         goto acache_obj_bail;
1154 
1155     kobject_uevent(acache_orangefs_obj, KOBJ_ADD);
1156 
1157     /* create /sys/fs/orangefs/capcache. */
1158     capcache_orangefs_obj =
1159         kzalloc(sizeof(*capcache_orangefs_obj), GFP_KERNEL);
1160     if (!capcache_orangefs_obj) {
1161         rc = -EINVAL;
1162         goto acache_obj_bail;
1163     }
1164 
1165     rc = kobject_init_and_add(capcache_orangefs_obj,
1166                   &capcache_orangefs_ktype,
1167                   orangefs_obj,
1168                   CAPCACHE_KOBJ_ID);
1169     if (rc)
1170         goto capcache_obj_bail;
1171 
1172     kobject_uevent(capcache_orangefs_obj, KOBJ_ADD);
1173 
1174     /* create /sys/fs/orangefs/ccache. */
1175     ccache_orangefs_obj =
1176         kzalloc(sizeof(*ccache_orangefs_obj), GFP_KERNEL);
1177     if (!ccache_orangefs_obj) {
1178         rc = -EINVAL;
1179         goto capcache_obj_bail;
1180     }
1181 
1182     rc = kobject_init_and_add(ccache_orangefs_obj,
1183                   &ccache_orangefs_ktype,
1184                   orangefs_obj,
1185                   CCACHE_KOBJ_ID);
1186     if (rc)
1187         goto ccache_obj_bail;
1188 
1189     kobject_uevent(ccache_orangefs_obj, KOBJ_ADD);
1190 
1191     /* create /sys/fs/orangefs/ncache. */
1192     ncache_orangefs_obj = kzalloc(sizeof(*ncache_orangefs_obj), GFP_KERNEL);
1193     if (!ncache_orangefs_obj) {
1194         rc = -EINVAL;
1195         goto ccache_obj_bail;
1196     }
1197 
1198     rc = kobject_init_and_add(ncache_orangefs_obj,
1199                   &ncache_orangefs_ktype,
1200                   orangefs_obj,
1201                   NCACHE_KOBJ_ID);
1202 
1203     if (rc)
1204         goto ncache_obj_bail;
1205 
1206     kobject_uevent(ncache_orangefs_obj, KOBJ_ADD);
1207 
1208     /* create /sys/fs/orangefs/perf_counters. */
1209     pc_orangefs_obj = kzalloc(sizeof(*pc_orangefs_obj), GFP_KERNEL);
1210     if (!pc_orangefs_obj) {
1211         rc = -EINVAL;
1212         goto ncache_obj_bail;
1213     }
1214 
1215     rc = kobject_init_and_add(pc_orangefs_obj,
1216                   &pc_orangefs_ktype,
1217                   orangefs_obj,
1218                   "perf_counters");
1219 
1220     if (rc)
1221         goto pc_obj_bail;
1222 
1223     kobject_uevent(pc_orangefs_obj, KOBJ_ADD);
1224 
1225     /* create /sys/fs/orangefs/stats. */
1226     stats_orangefs_obj = kzalloc(sizeof(*stats_orangefs_obj), GFP_KERNEL);
1227     if (!stats_orangefs_obj) {
1228         rc = -EINVAL;
1229         goto pc_obj_bail;
1230     }
1231 
1232     rc = kobject_init_and_add(stats_orangefs_obj,
1233                   &stats_orangefs_ktype,
1234                   orangefs_obj,
1235                   STATS_KOBJ_ID);
1236 
1237     if (rc)
1238         goto stats_obj_bail;
1239 
1240     kobject_uevent(stats_orangefs_obj, KOBJ_ADD);
1241     goto out;
1242 
1243 stats_obj_bail:
1244         kobject_put(stats_orangefs_obj);
1245 pc_obj_bail:
1246         kobject_put(pc_orangefs_obj);
1247 ncache_obj_bail:
1248         kobject_put(ncache_orangefs_obj);
1249 ccache_obj_bail:
1250         kobject_put(ccache_orangefs_obj);
1251 capcache_obj_bail:
1252         kobject_put(capcache_orangefs_obj);
1253 acache_obj_bail:
1254         kobject_put(acache_orangefs_obj);
1255 ofs_obj_bail:
1256         kobject_put(orangefs_obj);
1257 out:
1258     return rc;
1259 }
1260 
1261 void orangefs_sysfs_exit(void)
1262 {
1263     gossip_debug(GOSSIP_SYSFS_DEBUG, "orangefs_sysfs_exit: start\n");
1264     kobject_put(acache_orangefs_obj);
1265     kobject_put(capcache_orangefs_obj);
1266     kobject_put(ccache_orangefs_obj);
1267     kobject_put(ncache_orangefs_obj);
1268     kobject_put(pc_orangefs_obj);
1269     kobject_put(stats_orangefs_obj);
1270     kobject_put(orangefs_obj);
1271 }