4 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License version 2 only,
8 * as published by the Free Software Foundation.
10 * This program is distributed in the hope that it will be useful, but
11 * WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * General Public License version 2 for more details (a copy is included
14 * in the LICENSE file that accompanied this code).
16 * You should have received a copy of the GNU General Public License
17 * version 2 along with this program; If not, see
18 * http://www.gnu.org/licenses/gpl-2.0.html
23 * Copyright (C) 2013, Trustees of Indiana University
25 * Copyright (c) 2014, 2015, Intel Corporation.
27 * Author: Joshua Walgenbach <jjw@iu.edu>
30 #define NODEMAP_LPROC_ID_LEN 16
31 #define NODEMAP_LPROC_FLAG_LEN 2
33 #include <lprocfs_status.h>
34 #include <lustre_net.h>
35 #include <lustre_export.h>
36 #include <obd_class.h>
37 #include <interval_tree.h>
38 #include "nodemap_internal.h"
40 static LIST_HEAD(nodemap_pde_list);
43 * Reads and prints the idmap for the given nodemap.
45 * \param m seq file in proc fs
49 static int nodemap_idmap_show(struct seq_file *m, void *data)
51 struct lu_nodemap *nodemap;
52 struct lu_idmap *idmap;
57 mutex_lock(&active_config_lock);
58 nodemap = nodemap_lookup(m->private);
59 mutex_unlock(&active_config_lock);
60 if (IS_ERR(nodemap)) {
61 rc = PTR_ERR(nodemap);
62 CERROR("cannot find nodemap '%s': rc = %d\n",
63 (char *)m->private, rc);
68 read_lock(&nodemap->nm_idmap_lock);
69 for (node = rb_first(&nodemap->nm_client_to_fs_uidmap); node;
70 node = rb_next(node)) {
74 idmap = rb_entry(node, struct lu_idmap, id_client_to_fs);
76 seq_printf(m, " { idtype: uid, client_id: %u, "
77 "fs_id: %u }", idmap->id_client,
80 for (node = rb_first(&nodemap->nm_client_to_fs_gidmap);
81 node; node = rb_next(node)) {
84 idmap = rb_entry(node, struct lu_idmap, id_client_to_fs);
86 seq_printf(m, " { idtype: gid, client_id: %u, "
87 "fs_id: %u }", idmap->id_client,
90 read_unlock(&nodemap->nm_idmap_lock);
94 nodemap_putref(nodemap);
99 * Attaches nodemap_idmap_show to proc file.
101 * \param inode inode of seq file in proc fs
102 * \param file seq file
105 static int nodemap_idmap_open(struct inode *inode, struct file *file)
107 return single_open(file, nodemap_idmap_show, PDE_DATA(inode));
111 * Reads and prints the NID ranges for the given nodemap.
113 * \param m seq file in proc fs
117 static int nodemap_ranges_show(struct seq_file *m, void *data)
119 struct lu_nodemap *nodemap;
120 struct lu_nid_range *range;
121 struct interval_node_extent ext;
122 char start_nidstr[LNET_NIDSTR_SIZE];
123 char end_nidstr[LNET_NIDSTR_SIZE];
127 mutex_lock(&active_config_lock);
128 nodemap = nodemap_lookup(m->private);
129 if (IS_ERR(nodemap)) {
130 mutex_unlock(&active_config_lock);
131 rc = PTR_ERR(nodemap);
132 CERROR("cannot find nodemap '%s': rc = %d\n",
133 (char *)m->private, rc);
137 seq_printf(m, "[\n");
138 down_read(&active_config->nmc_range_tree_lock);
139 list_for_each_entry(range, &nodemap->nm_ranges, rn_list) {
141 seq_printf(m, ",\n");
143 ext = range->rn_node.in_extent;
144 libcfs_nid2str_r(ext.start, start_nidstr, sizeof(start_nidstr));
145 libcfs_nid2str_r(ext.end, end_nidstr, sizeof(end_nidstr));
146 seq_printf(m, " { id: %u, start_nid: %s, end_nid: %s }",
147 range->rn_id, start_nidstr, end_nidstr);
149 up_read(&active_config->nmc_range_tree_lock);
150 mutex_unlock(&active_config_lock);
152 seq_printf(m, "]\n");
154 nodemap_putref(nodemap);
159 * Connects nodemap_idmap_show to proc file.
161 * \param inode inode of seq file in proc fs
162 * \param file seq file
165 static int nodemap_ranges_open(struct inode *inode, struct file *file)
167 return single_open(file, nodemap_ranges_show, PDE_DATA(inode));
171 * Reads and prints the fileset for the given nodemap.
173 * \param m seq file in proc fs
177 static int nodemap_fileset_seq_show(struct seq_file *m, void *data)
179 struct lu_nodemap *nodemap;
182 mutex_lock(&active_config_lock);
183 nodemap = nodemap_lookup(m->private);
184 mutex_unlock(&active_config_lock);
185 if (IS_ERR(nodemap)) {
186 rc = PTR_ERR(nodemap);
187 CERROR("cannot find nodemap '%s': rc = %d\n",
188 (char *)m->private, rc);
192 rc = seq_printf(m, "%s\n", nodemap->nm_fileset);
193 nodemap_putref(nodemap);
198 * Set a fileset on a nodemap.
200 * \param[in] file proc file
201 * \param[in] buffer string, "<fileset>"
202 * \param[in] count \a buffer length
203 * \param[in] off unused
204 * \retval \a count on success
205 * \retval negative number on error
208 nodemap_fileset_seq_write(struct file *file,
209 const char __user *buffer,
210 size_t count, loff_t *off)
212 struct seq_file *m = file->private_data;
216 rc = nodemap_set_fileset(m->private, buffer);
223 LPROC_SEQ_FOPS(nodemap_fileset);
226 * Reads and prints the exports attached to the given nodemap.
228 * \param m seq file in proc fs, stores nodemap
232 static int nodemap_exports_show(struct seq_file *m, void *data)
234 struct lu_nodemap *nodemap;
235 struct obd_export *exp;
236 char nidstr[LNET_NIDSTR_SIZE] = "<unknown>";
239 mutex_lock(&active_config_lock);
240 nodemap = nodemap_lookup(m->private);
241 mutex_unlock(&active_config_lock);
242 if (IS_ERR(nodemap)) {
243 rc = PTR_ERR(nodemap);
244 CERROR("cannot find nodemap '%s': rc = %d\n",
245 (char *)m->private, rc);
249 seq_printf(m, "[\n");
251 mutex_lock(&nodemap->nm_member_list_lock);
252 list_for_each_entry(exp, &nodemap->nm_member_list,
253 exp_target_data.ted_nodemap_member) {
254 if (exp->exp_connection != NULL)
255 libcfs_nid2str_r(exp->exp_connection->c_peer.nid,
256 nidstr, sizeof(nidstr));
258 seq_printf(m, " { nid: %s, uuid: %s },",
259 nidstr, exp->exp_client_uuid.uuid);
261 mutex_unlock(&nodemap->nm_member_list_lock);
264 seq_printf(m, "]\n");
266 nodemap_putref(nodemap);
271 * Attaches nodemap_idmap_show to proc file.
273 * \param inode inode of seq file in proc fs
274 * \param file seq file
277 static int nodemap_exports_open(struct inode *inode, struct file *file)
279 return single_open(file, nodemap_exports_show, PDE_DATA(inode));
283 * Reads and prints the active flag for the given nodemap.
285 * \param m seq file in proc fs
289 static int nodemap_active_seq_show(struct seq_file *m, void *data)
291 seq_printf(m, "%u\n", (unsigned int)nodemap_active);
296 * Activate/deactivate nodemap.
298 * \param[in] file proc file
299 * \param[in] buffer string, "1" or "0" to activate/deactivate nodemap
300 * \param[in] count \a buffer length
301 * \param[in] off unused
302 * \retval \a count on success
303 * \retval negative number on error
306 nodemap_active_seq_write(struct file *file, const char __user *buffer,
307 size_t count, loff_t *off)
309 char active_string[NODEMAP_LPROC_FLAG_LEN + 1];
310 long unsigned int active;
316 if (count >= sizeof(active_string))
319 if (copy_from_user(active_string, buffer, count))
322 active_string[count] = '\0';
323 rc = kstrtoul(active_string, 10, &active);
327 nodemap_activate(active);
331 LPROC_SEQ_FOPS(nodemap_active);
334 * Reads and prints the nodemap ID for the given nodemap.
336 * \param m seq file in proc fs
340 static int nodemap_id_seq_show(struct seq_file *m, void *data)
342 struct lu_nodemap *nodemap;
344 mutex_lock(&active_config_lock);
345 nodemap = nodemap_lookup(m->private);
346 mutex_unlock(&active_config_lock);
347 if (IS_ERR(nodemap)) {
348 int rc = PTR_ERR(nodemap);
349 CERROR("cannot find nodemap '%s': rc = %d\n",
350 (char *)m->private, rc);
354 seq_printf(m, "%u\n", nodemap->nm_id);
355 nodemap_putref(nodemap);
358 LPROC_SEQ_FOPS_RO(nodemap_id);
361 * Reads and prints the root squash UID for the given nodemap.
363 * \param m seq file in proc fs
367 static int nodemap_squash_uid_seq_show(struct seq_file *m, void *data)
369 struct lu_nodemap *nodemap;
371 mutex_lock(&active_config_lock);
372 nodemap = nodemap_lookup(m->private);
373 mutex_unlock(&active_config_lock);
374 if (IS_ERR(nodemap)) {
375 int rc = PTR_ERR(nodemap);
376 CERROR("cannot find nodemap '%s': rc = %d\n",
377 (char *)m->private, rc);
381 seq_printf(m, "%u\n", nodemap->nm_squash_uid);
382 nodemap_putref(nodemap);
387 * Reads and prints the root squash GID for the given nodemap.
389 * \param m seq file in proc fs
393 static int nodemap_squash_gid_seq_show(struct seq_file *m, void *data)
395 struct lu_nodemap *nodemap;
397 mutex_lock(&active_config_lock);
398 nodemap = nodemap_lookup(m->private);
399 mutex_unlock(&active_config_lock);
400 if (IS_ERR(nodemap)) {
401 int rc = PTR_ERR(nodemap);
402 CERROR("cannot find nodemap '%s': rc = %d\n",
403 (char *)m->private, rc);
407 seq_printf(m, "%u\n", nodemap->nm_squash_gid);
408 nodemap_putref(nodemap);
413 * Reads and prints the trusted flag for the given nodemap.
415 * \param m seq file in proc fs
419 static int nodemap_trusted_seq_show(struct seq_file *m, void *data)
421 struct lu_nodemap *nodemap;
423 mutex_lock(&active_config_lock);
424 nodemap = nodemap_lookup(m->private);
425 mutex_unlock(&active_config_lock);
426 if (IS_ERR(nodemap)) {
427 int rc = PTR_ERR(nodemap);
429 CERROR("cannot find nodemap '%s': rc = %d\n",
430 (char *)m->private, rc);
434 seq_printf(m, "%d\n", (int)nodemap->nmf_trust_client_ids);
435 nodemap_putref(nodemap);
440 * Reads and prints the admin flag for the given nodemap.
442 * \param m seq file in proc fs
446 static int nodemap_admin_seq_show(struct seq_file *m, void *data)
448 struct lu_nodemap *nodemap;
451 mutex_lock(&active_config_lock);
452 nodemap = nodemap_lookup(m->private);
453 mutex_unlock(&active_config_lock);
454 if (IS_ERR(nodemap)) {
455 rc = PTR_ERR(nodemap);
456 CERROR("cannot find nodemap '%s': rc = %d\n",
457 (char *)m->private, rc);
461 seq_printf(m, "%d\n", (int)nodemap->nmf_allow_root_access);
462 nodemap_putref(nodemap);
467 * Reads and prints the deny_unknown flag for the given nodemap.
469 * \param m seq file in proc fs
473 static int nodemap_deny_unknown_seq_show(struct seq_file *m, void *data)
475 struct lu_nodemap *nodemap;
478 mutex_lock(&active_config_lock);
479 nodemap = nodemap_lookup(m->private);
480 mutex_unlock(&active_config_lock);
481 if (IS_ERR(nodemap)) {
482 rc = PTR_ERR(nodemap);
483 CERROR("cannot find nodemap '%s': rc = %d\n",
484 (char *)m->private, rc);
488 seq_printf(m, "%d\n", (int)nodemap->nmf_deny_unknown);
489 nodemap_putref(nodemap);
493 #ifdef NODEMAP_PROC_DEBUG
495 * Helper functions to set nodemap flags.
497 * \param[in] buffer string, which is "1" or "0" to set/unset flag
498 * \param[in] count \a buffer length
499 * \param[out] flag_p where to store flag value
500 * \retval \a count on success
501 * \retval negative number on error
503 static int nodemap_proc_read_flag(const char __user *buffer,
504 unsigned long count, unsigned int *flag_p)
506 char scratch[NODEMAP_LPROC_FLAG_LEN + 1];
507 long unsigned int flag_buf;
513 if (count >= sizeof(scratch))
516 if (copy_from_user(scratch, buffer, count))
519 scratch[count] = '\0';
520 rc = kstrtoul(scratch, 10, &flag_buf);
530 * Set the squash UID.
532 * \param[in] file proc file
533 * \param[in] buffer string representing squash UID to set
534 * \param[in] count \a buffer length
535 * \param[in] off unused
536 * \retval \a count on success
537 * \retval negative number on error
540 nodemap_squash_uid_seq_write(struct file *file, const char __user *buffer,
541 size_t count, loff_t *off)
543 char squash[NODEMAP_LPROC_ID_LEN + 1];
544 struct seq_file *m = file->private_data;
545 long unsigned int squash_uid;
551 if (count >= sizeof(squash))
554 if (copy_from_user(squash, buffer, count))
557 squash[count] = '\0';
558 rc = kstrtoul(squash, 10, &squash_uid);
562 rc = nodemap_set_squash_uid(m->private, squash_uid);
570 * Set the squash GID.
572 * \param[in] file proc file
573 * \param[in] buffer string representing squash GID to set
574 * \param[in] count \a buffer length
575 * \param[in] off unused
576 * \retval \a count on success
577 * \retval negative number on error
580 nodemap_squash_gid_seq_write(struct file *file, const char __user *buffer,
581 size_t count, loff_t *off)
583 char squash[NODEMAP_LPROC_ID_LEN + 1];
584 struct seq_file *m = file->private_data;
585 long unsigned int squash_gid;
591 if (count >= sizeof(squash))
594 if (copy_from_user(squash, buffer, count))
597 squash[count] = '\0';
598 rc = kstrtoul(squash, 10, &squash_gid);
602 rc = nodemap_set_squash_gid(m->private, squash_gid);
610 * Set/unset the trusted flag.
612 * \param[in] file proc file
613 * \param[in] buffer string, "1" or "0"
614 * \param[in] count \a buffer length
615 * \param[in] off unused
616 * \retval \a count on success
617 * \retval negative number on error
620 nodemap_trusted_seq_write(struct file *file, const char __user *buffer,
621 size_t count, loff_t *off)
623 struct seq_file *m = file->private_data;
627 rc = nodemap_proc_read_flag(buffer, count, &flags);
631 rc = nodemap_set_trust_client_ids(m->private, flags);
639 * Set/unset the admin flag.
641 * \param[in] file proc file
642 * \param[in] buffer string, "1" or "0"
643 * \param[in] count \a buffer length
644 * \param[in] off unused
645 * \retval \a count on success
646 * \retval negative number on error
649 nodemap_admin_seq_write(struct file *file, const char __user *buffer,
650 size_t count, loff_t *off)
652 struct seq_file *m = file->private_data;
656 rc = nodemap_proc_read_flag(buffer, count, &flags);
660 rc = nodemap_set_allow_root(m->private, flags);
670 * \param[in] file proc file
671 * \param[in] buffer string, name of the nodemap to add
672 * \param[in] count \a buffer length
673 * \param[in] off unused
674 * \retval \a count on success
675 * \retval negative number on error
678 lprocfs_add_nodemap_seq_write(struct file *file, const char __user *buffer,
679 size_t count, loff_t *off)
681 char nodemap_name[LUSTRE_NODEMAP_NAME_LENGTH + 1];
689 if (count >= sizeof(nodemap_name))
692 if (copy_from_user(nodemap_name, buffer, count))
695 nodemap_name[count] = '\0';
697 cpybuf = nodemap_name;
698 pos = strsep(&cpybuf, " \n");
702 rc = nodemap_add(nodemap_name);
708 LPROC_SEQ_FOPS_WO_TYPE(nodemap, add_nodemap);
713 * \param[in] file proc file
714 * \param[in] buffer string, name of the nodemap to delete
715 * \param[in] count \a buffer length
716 * \param[in] off unused
717 * \retval \a count on success
718 * \retval negative number on error
721 lprocfs_del_nodemap_seq_write(struct file *file, const char __user *buffer,
722 size_t count, loff_t *off)
724 char nodemap_name[LUSTRE_NODEMAP_NAME_LENGTH + 1];
732 if (count >= sizeof(nodemap_name))
735 if (copy_from_user(nodemap_name, buffer, count))
738 nodemap_name[count] = '\0';
740 cpybuf = nodemap_name;
741 pos = strsep(&cpybuf, " \n");
745 rc = nodemap_del(nodemap_name);
752 LPROC_SEQ_FOPS_WO_TYPE(nodemap, del_nodemap);
755 * Helper function to parse a NID string.
757 * \param[in] rangestr string representation of NIDs, see libcfs_str2nid()
758 * \param[out] nids array of two nids
759 * \retval 0 on success
760 * \retval negative number on error
762 static int parse_nids(char *rangestr, lnet_nid_t nids[2])
764 struct list_head nidlist;
765 char nidstr[2][LNET_NIDSTR_SIZE];
766 char nidrange_str[2 * LNET_NIDSTR_SIZE + 2];
769 INIT_LIST_HEAD(&nidlist);
771 if (cfs_parse_nidlist(rangestr, strlen(rangestr),
775 if (!cfs_nidrange_is_contiguous(&nidlist))
778 cfs_nidrange_find_min_max(&nidlist, nidstr[0], nidstr[1],
780 snprintf(nidrange_str, sizeof(nidrange_str), "%s:%s",
781 nidstr[0], nidstr[1]);
783 rc = nodemap_parse_range(nidrange_str, nids);
787 cfs_free_nidlist(&nidlist);
793 * Add a NID range to nodemap.
795 * \param[in] file proc file
796 * \param[in] buffer string, "<nodemap name> <nid range>"
797 * \param[in] count \a buffer length
798 * \param[in] off unused
799 * \retval \a count on success
800 * \retval negative number on error
803 lprocfs_add_nodemap_range_seq_write(struct file *file,
804 const char __user *buffer,
805 size_t count, loff_t *off)
807 char name_range[LUSTRE_NODEMAP_NAME_LENGTH +
808 LNET_NIDSTR_SIZE * 2 + 2];
811 char *rangestr = NULL;
818 if (count >= sizeof(name_range))
819 GOTO(out, rc = -EINVAL);
821 if (copy_from_user(name_range, buffer, count))
822 GOTO(out, rc = -EFAULT);
824 name_range[count] = '\0';
827 name = strsep(&cpybuf, " ");
829 GOTO(out, rc = -EINVAL);
831 rangestr = strsep(&cpybuf, " \n");
832 if (rangestr == NULL)
833 GOTO(out, rc = -EINVAL);
835 rc = parse_nids(rangestr, nids);
839 rc = nodemap_add_range(name, nids);
841 GOTO(out, rc = -EINVAL);
849 LPROC_SEQ_FOPS_WO_TYPE(nodemap, add_nodemap_range);
852 * Delete a NID range from nodemap.
854 * \param[in] file proc file
855 * \param[in] buffer string, "<nodemap name> <nid range>"
856 * \param[in] count \a buffer length
857 * \param[in] off unused
858 * \retval \a count on success
859 * \retval negative number on error
862 lprocfs_del_nodemap_range_seq_write(struct file *file,
863 const char __user *buffer,
864 size_t count, loff_t *off)
866 char name_range[LUSTRE_NODEMAP_NAME_LENGTH +
867 LNET_NIDSTR_SIZE * 2 + 2];
870 char *rangestr = NULL;
877 if (count >= sizeof(name_range))
878 GOTO(out, rc = -EINVAL);
880 if (copy_from_user(name_range, buffer, count))
881 GOTO(out, rc = -EFAULT);
883 name_range[count] = '\0';
886 name = strsep(&cpybuf, " ");
888 GOTO(out, rc = -EINVAL);
890 rangestr = strsep(&cpybuf, " \n");
891 if (rangestr == NULL)
892 GOTO(out, rc = -EINVAL);
894 rc = parse_nids(rangestr, nids);
898 rc = nodemap_del_range(name, nids);
900 GOTO(out, rc = -EINVAL);
908 LPROC_SEQ_FOPS_WO_TYPE(nodemap, del_nodemap_range);
911 * Add an idmap to nodemap.
913 * \param[in] file proc file
914 * \param[in] buffer string, "<nodemap name> <uid|gid> <idmap>"
915 * \param[in] count \a buffer length
916 * \param[in] off unused
917 * \retval \a count on success
918 * \retval negative number on error
921 lprocfs_add_nodemap_idmap_seq_write(struct file *file,
922 const char __user *buffer,
923 size_t count, loff_t *off)
925 char name_idmapstr[LUSTRE_NODEMAP_NAME_LENGTH + 16];
928 char *idtypestr = NULL;
929 char *idmapstr = NULL;
936 if (count >= sizeof(name_idmapstr))
937 GOTO(out, rc = -EINVAL);
939 if (copy_from_user(name_idmapstr, buffer, count))
940 GOTO(out, rc = -EFAULT);
942 name_idmapstr[count] = '\0';
944 cpybuf = name_idmapstr;
945 name = strsep(&cpybuf, " ");
947 GOTO(out, rc = -EINVAL);
949 idtypestr = strsep(&cpybuf, " ");
950 if (idtypestr == NULL)
951 GOTO(out, rc = -EINVAL);
953 idmapstr = strsep(&cpybuf, " \n");
954 if (idmapstr == NULL)
955 GOTO(out, rc = -EINVAL);
957 rc = nodemap_parse_idmap(idmapstr, idmap);
959 GOTO(out, rc = -EINVAL);
961 if (strcmp(idtypestr, "uid") == 0)
962 rc = nodemap_add_idmap(name, NODEMAP_UID, idmap);
963 else if (strcmp(idtypestr, "gid") == 0)
964 rc = nodemap_add_idmap(name, NODEMAP_GID, idmap);
966 GOTO(out, rc = -EINVAL);
969 GOTO(out, rc = -EINVAL);
977 LPROC_SEQ_FOPS_WO_TYPE(nodemap, add_nodemap_idmap);
980 * Delete an idmap from nodemap.
982 * \param[in] file proc file
983 * \param[in] buffer string, "<nodemap name> <uid|gid> <idmap>"
984 * \param[in] count \a buffer length
985 * \param[in] off unused
986 * \retval \a count on success
987 * \retval negative number on error
990 lprocfs_del_nodemap_idmap_seq_write(struct file *file,
991 const char __user *buffer,
992 size_t count, loff_t *off)
994 char name_idmapstr[LUSTRE_NODEMAP_NAME_LENGTH + 16];
997 char *idtypestr = NULL;
998 char *idmapstr = NULL;
1005 if (count >= sizeof(name_idmapstr))
1006 GOTO(out, rc = -EINVAL);
1008 if (copy_from_user(name_idmapstr, buffer, count))
1009 GOTO(out, rc = -EFAULT);
1011 name_idmapstr[count] = '\0';
1013 cpybuf = name_idmapstr;
1014 name = strsep(&cpybuf, " ");
1016 GOTO(out, rc = -EINVAL);
1018 idtypestr = strsep(&cpybuf, " ");
1019 if (idtypestr == NULL)
1020 GOTO(out, rc = -EINVAL);
1022 idmapstr = strsep(&cpybuf, " \n");
1023 if (idmapstr == NULL)
1024 GOTO(out, rc = -EINVAL);
1026 rc = nodemap_parse_idmap(idmapstr, idmap);
1028 GOTO(out, rc = -EINVAL);
1030 if (strcmp(idtypestr, "uid") == 0)
1031 rc = nodemap_del_idmap(name, NODEMAP_UID, idmap);
1032 else if (strcmp(idtypestr, "gid") == 0)
1033 rc = nodemap_del_idmap(name, NODEMAP_GID, idmap);
1035 GOTO(out, rc = -EINVAL);
1038 GOTO(out, rc = -EINVAL);
1046 LPROC_SEQ_FOPS_WO_TYPE(nodemap, del_nodemap_idmap);
1047 #endif /* NODEMAP_PROC_DEBUG */
1049 static struct lprocfs_vars lprocfs_nm_module_vars[] = {
1052 .fops = &nodemap_active_fops,
1054 #ifdef NODEMAP_PROC_DEBUG
1056 .name = "add_nodemap",
1057 .fops = &nodemap_add_nodemap_fops,
1060 .name = "remove_nodemap",
1061 .fops = &nodemap_del_nodemap_fops,
1064 .name = "add_nodemap_range",
1065 .fops = &nodemap_add_nodemap_range_fops,
1068 .name = "del_nodemap_range",
1069 .fops = &nodemap_del_nodemap_range_fops,
1072 .name = "add_nodemap_idmap",
1073 .fops = &nodemap_add_nodemap_idmap_fops,
1076 .name = "del_nodemap_idmap",
1077 .fops = &nodemap_del_nodemap_idmap_fops,
1079 #endif /* NODEMAP_PROC_DEBUG */
1085 #ifdef NODEMAP_PROC_DEBUG
1086 LPROC_SEQ_FOPS(nodemap_trusted);
1087 LPROC_SEQ_FOPS(nodemap_admin);
1088 LPROC_SEQ_FOPS(nodemap_squash_uid);
1089 LPROC_SEQ_FOPS(nodemap_squash_gid);
1091 LPROC_SEQ_FOPS_RO(nodemap_trusted);
1092 LPROC_SEQ_FOPS_RO(nodemap_admin);
1093 LPROC_SEQ_FOPS_RO(nodemap_squash_uid);
1094 LPROC_SEQ_FOPS_RO(nodemap_squash_gid);
1097 LPROC_SEQ_FOPS_RO(nodemap_deny_unknown);
1099 const struct file_operations nodemap_ranges_fops = {
1100 .open = nodemap_ranges_open,
1102 .llseek = seq_lseek,
1103 .release = single_release
1106 const struct file_operations nodemap_idmap_fops = {
1107 .open = nodemap_idmap_open,
1109 .llseek = seq_lseek,
1110 .release = single_release
1113 const struct file_operations nodemap_exports_fops = {
1114 .open = nodemap_exports_open,
1116 .llseek = seq_lseek,
1117 .release = single_release
1120 static struct lprocfs_vars lprocfs_nodemap_vars[] = {
1123 .fops = &nodemap_id_fops,
1126 .name = "trusted_nodemap",
1127 .fops = &nodemap_trusted_fops,
1130 .name = "admin_nodemap",
1131 .fops = &nodemap_admin_fops,
1134 .name = "deny_unknown",
1135 .fops = &nodemap_deny_unknown_fops,
1138 .name = "squash_uid",
1139 .fops = &nodemap_squash_uid_fops,
1142 .name = "squash_gid",
1143 .fops = &nodemap_squash_gid_fops,
1147 .fops = &nodemap_ranges_fops,
1151 .fops = &nodemap_fileset_fops,
1155 .fops = &nodemap_exports_fops,
1159 .fops = &nodemap_idmap_fops,
1166 static struct lprocfs_vars lprocfs_default_nodemap_vars[] = {
1169 .fops = &nodemap_id_fops,
1172 .name = "trusted_nodemap",
1173 .fops = &nodemap_trusted_fops,
1176 .name = "admin_nodemap",
1177 .fops = &nodemap_admin_fops,
1180 .name = "squash_uid",
1181 .fops = &nodemap_squash_uid_fops,
1184 .name = "squash_gid",
1185 .fops = &nodemap_squash_gid_fops,
1189 .fops = &nodemap_exports_fops,
1197 * Initialize the nodemap procfs directory.
1201 int nodemap_procfs_init(void)
1205 proc_lustre_nodemap_root = lprocfs_register(LUSTRE_NODEMAP_NAME,
1207 lprocfs_nm_module_vars,
1209 if (IS_ERR(proc_lustre_nodemap_root)) {
1210 rc = PTR_ERR(proc_lustre_nodemap_root);
1211 CERROR("cannot create 'nodemap' directory: rc = %d\n",
1213 proc_lustre_nodemap_root = NULL;
1219 * Cleanup nodemap proc entry data structures.
1221 void nodemap_procfs_exit(void)
1223 struct nodemap_pde *nm_pde;
1224 struct nodemap_pde *tmp;
1226 lprocfs_remove(&proc_lustre_nodemap_root);
1227 list_for_each_entry_safe(nm_pde, tmp, &nodemap_pde_list,
1229 list_del(&nm_pde->npe_list_member);
1230 OBD_FREE_PTR(nm_pde);
1235 * Remove a nodemap's procfs entry and related data.
1237 void lprocfs_nodemap_remove(struct nodemap_pde *nm_pde)
1239 lprocfs_remove(&nm_pde->npe_proc_entry);
1240 list_del(&nm_pde->npe_list_member);
1241 OBD_FREE_PTR(nm_pde);
1245 * Register the proc directory for a nodemap
1247 * \param nodemap nodemap to make the proc dir for
1248 * \param is_default: 1 if default nodemap
1251 int lprocfs_nodemap_register(struct lu_nodemap *nodemap, bool is_default)
1253 struct nodemap_pde *nm_entry;
1256 OBD_ALLOC_PTR(nm_entry);
1257 if (nm_entry == NULL)
1258 GOTO(out, rc = -ENOMEM);
1260 nm_entry->npe_proc_entry = proc_mkdir(nodemap->nm_name,
1261 proc_lustre_nodemap_root);
1262 if (IS_ERR(nm_entry->npe_proc_entry))
1263 GOTO(out, rc = PTR_ERR(nm_entry->npe_proc_entry));
1265 snprintf(nm_entry->npe_name, sizeof(nm_entry->npe_name), "%s",
1268 /* Use the nodemap name as stored on the PDE as the private data. This
1269 * is so a nodemap struct can be replaced without updating the proc
1272 rc = lprocfs_add_vars(nm_entry->npe_proc_entry,
1273 (is_default ? lprocfs_default_nodemap_vars :
1274 lprocfs_nodemap_vars),
1275 nm_entry->npe_name);
1277 lprocfs_remove(&nm_entry->npe_proc_entry);
1279 list_add(&nm_entry->npe_list_member, &nodemap_pde_list);
1283 CERROR("cannot create 'nodemap/%s': rc = %d\n",
1284 nodemap->nm_name, rc);
1285 if (nm_entry != NULL) {
1286 OBD_FREE_PTR(nm_entry);
1291 nodemap->nm_pde_data = nm_entry;