Print this page
11083 support NFS server in zone
Portions contributed by: Dan Kruchinin <dan.kruchinin@nexenta.com>
Portions contributed by: Stepan Zastupov <stepan.zastupov@gmail.com>
Portions contributed by: Joyce McIntosh <joyce.mcintosh@nexenta.com>
Portions contributed by: Mike Zeller <mike@mikezeller.net>
Portions contributed by: Dan McDonald <danmcd@joyent.com>
Portions contributed by: Gordon Ross <gordon.w.ross@gmail.com>
Portions contributed by: Vitaliy Gusev <gusev.vitaliy@gmail.com>
Reviewed by: Rick McNeal <rick.mcneal@nexenta.com>
Reviewed by: Rob Gittins <rob.gittins@nexenta.com>
Reviewed by: Sanjay Nadkarni <sanjay.nadkarni@nexenta.com>
Reviewed by: Jason King <jbk@joyent.com>
Reviewed by: C Fraire <cfraire@me.com>
Change-Id: I22f289d357503f9b48a0bc2482cc4328a6d43d16


   3  *
   4  * The contents of this file are subject to the terms of the
   5  * Common Development and Distribution License (the "License").
   6  * You may not use this file except in compliance with the License.
   7  *
   8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9  * or http://www.opensolaris.org/os/licensing.
  10  * See the License for the specific language governing permissions
  11  * and limitations under the License.
  12  *
  13  * When distributing Covered Code, include this CDDL HEADER in each
  14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15  * If applicable, add the following below this CDDL HEADER, with the
  16  * fields enclosed by brackets "[]" replaced with your own identifying
  17  * information: Portions Copyright [yyyy] [name of copyright owner]
  18  *
  19  * CDDL HEADER END
  20  */
  21 
  22 /*
  23  * Copyright 2015 Nexenta Systems, Inc.  All rights reserved.

  24  */
  25 
  26 /*
  27  * Copyright 2010 Sun Microsystems, Inc.  All rights reserved.
  28  * Use is subject to license terms.
  29  */
  30 
  31 #ifndef _NFS4_H
  32 #define _NFS4_H
  33 
  34 #include <sys/types.h>
  35 #include <sys/vnode.h>
  36 #include <sys/fem.h>
  37 #include <rpc/rpc.h>
  38 #include <nfs/nfs.h>
  39 
  40 #ifdef _KERNEL
  41 #include <nfs/nfs4_kprot.h>

  42 #include <sys/nvpair.h>
  43 #else
  44 #include <rpcsvc/nfs4_prot.h>
  45 #endif
  46 #include <nfs/nfs4_attr.h>
  47 #include <sys/acl.h>
  48 #include <sys/list.h>
  49 
  50 #ifdef  __cplusplus
  51 extern "C" {
  52 #endif
  53 
  54 #define NFS4_MAX_SECOID4        65536
  55 #define NFS4_MAX_UTF8STRING     65536
  56 #define NFS4_MAX_LINKTEXT4      65536
  57 #define NFS4_MAX_PATHNAME4      65536
  58 
  59 struct nfs_fsl_info {
  60         uint_t netbuf_len;
  61         uint_t netnm_len;


 102  *
 103  * The basic structure at this level is that the server maintains a
 104  * global "database" which consists of a set of tables.  Each table
 105  * contains a set of like data structures.  Each table is indexed by
 106  * at least one hash function and in most cases two hashes.  Each
 107  * table's characteristics is set when it is created at run-time via
 108  * rfs4_table_create().  All table creation and related functions are
 109  * located in nfs4_state.c.  The generic database functionality is
 110  * located in nfs4_db.c.
 111  */
 112 
 113 typedef struct rfs4_dbe rfs4_dbe_t;             /* basic opaque db entry */
 114 typedef struct rfs4_table rfs4_table_t;         /* basic table type */
 115 typedef struct rfs4_index rfs4_index_t;         /* index */
 116 typedef struct rfs4_database rfs4_database_t;   /* and database */
 117 
 118 typedef struct {                /* opaque entry type for later use */
 119         rfs4_dbe_t *dbe;
 120 } *rfs4_entry_t;
 121 
 122 extern rfs4_table_t *rfs4_client_tab;














 123 
 124 /* database, table, index creation entry points */
 125 extern rfs4_database_t *rfs4_database_create(uint32_t);
 126 extern void             rfs4_database_shutdown(rfs4_database_t *);
 127 extern void             rfs4_database_destroy(rfs4_database_t *);
 128 
 129 extern void             rfs4_database_destroy(rfs4_database_t *);
 130 


 131 extern rfs4_table_t     *rfs4_table_create(rfs4_database_t *, char *,
 132                                 time_t, uint32_t,
 133                                 bool_t (*create)(rfs4_entry_t, void *),
 134                                 void (*destroy)(rfs4_entry_t),
 135                                 bool_t (*expiry)(rfs4_entry_t),
 136                                 uint32_t, uint32_t, uint32_t, id_t);
 137 extern void             rfs4_table_destroy(rfs4_database_t *, rfs4_table_t *);
 138 extern rfs4_index_t     *rfs4_index_create(rfs4_table_t *, char *,
 139                                 uint32_t (*hash)(void *),
 140                                 bool_t (compare)(rfs4_entry_t, void *),
 141                                 void *(*mkkey)(rfs4_entry_t), bool_t);
 142 extern void             rfs4_index_destroy(rfs4_index_t *);
 143 
 144 /* Type used to direct rfs4_dbsearch() in what types of records to inspect */
 145 typedef enum {RFS4_DBS_VALID, RFS4_DBS_INVALID} rfs4_dbsearch_type_t;
 146 /* search and db entry manipulation entry points */
 147 extern rfs4_entry_t     rfs4_dbsearch(rfs4_index_t *, void *,
 148                                 bool_t *, void *, rfs4_dbsearch_type_t);
 149 extern void             rfs4_dbe_lock(rfs4_dbe_t *);
 150 extern void             rfs4_dbe_unlock(rfs4_dbe_t *);


 352         struct rfs4_servinst    *next;
 353         struct rfs4_servinst    *prev;
 354 } rfs4_servinst_t;
 355 
 356 /*
 357  * DSS: distributed stable storage
 358  */
 359 
 360 typedef struct rfs4_dss_path {
 361         struct rfs4_dss_path    *next; /* for insque/remque */
 362         struct rfs4_dss_path    *prev; /* for insque/remque */
 363         char                    *path;
 364         struct rfs4_servinst    *sip;
 365         unsigned                index; /* offset in servinst's array */
 366 } rfs4_dss_path_t;
 367 
 368 /* array of paths passed-in from nfsd command-line; stored in nvlist */
 369 char            **rfs4_dss_newpaths;
 370 uint_t          rfs4_dss_numnewpaths;
 371 
 372 /*
 373  * Circular doubly-linked list of paths for currently-served RGs.
 374  * No locking required: only changed on warmstart. Managed with insque/remque.
 375  */
 376 rfs4_dss_path_t *rfs4_dss_pathlist;
 377 
 378 /* nvlists of all DSS paths: current, and before last warmstart */
 379 nvlist_t *rfs4_dss_paths, *rfs4_dss_oldpaths;
 380 
 381 /*
 382  * The server maintains a set of state on a per client basis that
 383  * matches that of the protocol requirements.  A client's state is
 384  * rooted with the rfs4_client_t struct of which there is one per
 385  * client and is created when SETCLIENTID/SETCLIENTID_CONFIRM are
 386  * received.  From there, the server then creates rfs4_openowner_t
 387  * structs for each new open owner from that client and are initiated
 388  * at OPEN/OPEN_CONFIRM (when the open owner is new to the server).
 389  * At OPEN, at least two other structures are created, and potentially a
 390  * third.  rfs4_state_t is created to track the association between an
 391  * open owner and a particular file. An rfs4_file_t struct may be
 392  * created (if the file is not already open) at OPEN as well.  The
 393  * rfs4_file_t struct is the only one that is per server and not per
 394  * client.  The rfs4_deleg_state_t struct is created in the
 395  * instance that the server is going to provide a delegation for the
 396  * file being OPENed.  Finally, the rfs4_lockowner_t is created at the
 397  * first use of a lock owner at the server and is a result of the LOCK


 723  *      lock may or may not be held for lock/unlock of file_rwlock.
 724  *      As mentioned above, the file_rwlock is used for serialization
 725  *      of file removal and more specifically reference to the held
 726  *      vnode (e.g. vp).
 727  */
 728 typedef struct rfs4_file {
 729         rfs4_dbe_t      *rf_dbe;
 730         vnode_t         *rf_vp;
 731         nfs_fh4         rf_filehandle;
 732         list_t          rf_delegstatelist;
 733         rfs4_dinfo_t    rf_dinfo;
 734         uint32_t        rf_share_deny;
 735         uint32_t        rf_share_access;
 736         uint32_t        rf_access_read;
 737         uint32_t        rf_access_write;
 738         uint32_t        rf_deny_read;
 739         uint32_t        rf_deny_write;
 740         krwlock_t       rf_file_rwlock;
 741 } rfs4_file_t;
 742 
 743 extern int      rfs4_seen_first_compound;       /* set first time we see one */
 744 
 745 extern rfs4_servinst_t  *rfs4_cur_servinst;     /* current server instance */
 746 extern kmutex_t         rfs4_servinst_lock;     /* protects linked list */
 747 extern void             rfs4_servinst_create(int, int, char **);
 748 extern void             rfs4_servinst_destroy_all(void);
 749 extern void             rfs4_servinst_assign(rfs4_client_t *,
 750                             rfs4_servinst_t *);
 751 extern rfs4_servinst_t  *rfs4_servinst(rfs4_client_t *);
 752 extern int              rfs4_clnt_in_grace(rfs4_client_t *);
 753 extern int              rfs4_servinst_in_grace(rfs4_servinst_t *);
 754 extern int              rfs4_servinst_grace_new(rfs4_servinst_t *);
 755 extern void             rfs4_grace_start(rfs4_servinst_t *);
 756 extern void             rfs4_grace_start_new(void);
 757 extern void             rfs4_grace_reset_all(void);
 758 extern void             rfs4_ss_oldstate(rfs4_oldstate_t *, char *, char *);
 759 extern void             rfs4_dss_readstate(int, char **);
 760 
 761 /*
 762  * rfs4_deleg_policy is used to signify the server's global delegation
 763  * policy.  The default is to NEVER delegate files and the
 764  * administrator must configure the server to enable delegations.
 765  *
 766  * The disable/enable delegation functions are used to eliminate a
 767  * race with exclusive creates.
 768  */
 769 typedef enum {
 770         SRV_NEVER_DELEGATE = 0,
 771         SRV_NORMAL_DELEGATE = 1
 772 } srv_deleg_policy_t;
 773 
 774 extern srv_deleg_policy_t rfs4_deleg_policy;
 775 extern kmutex_t rfs4_deleg_lock;
 776 extern void rfs4_disable_delegation(void), rfs4_enable_delegation(void);
 777 
 778 /*
 779  * Request types for delegation. These correspond with
 780  * open_delegation_type4 with the addition of a new value, DELEG_ANY,
 781  * to reqequest any delegation.
 782  */
 783 typedef enum {
 784         DELEG_NONE = 0,         /* Corresponds to OPEN_DELEG_NONE */
 785         DELEG_READ = 1,         /* Corresponds to OPEN_DELEG_READ */
 786         DELEG_WRITE = 2,        /* Corresponds to OPEN_DELEG_WRITE */
 787         DELEG_ANY = -1          /* New value to request any delegation type */
 788 } delegreq_t;
 789 
 790 #define NFS4_DELEG4TYPE2REQTYPE(x) (delegreq_t)(x)
 791 
 792 /*



















































































































 793  * Various interfaces to manipulate the state structures introduced
 794  * above
 795  */
 796 extern  kmutex_t        rfs4_state_lock;
 797 extern  void            rfs4_clean_state_exi(struct exportinfo *exi);
 798 extern  void            rfs4_free_reply(nfs_resop4 *);
 799 extern  void            rfs4_copy_reply(nfs_resop4 *, nfs_resop4 *);
 800 
 801 /* rfs4_client_t handling */
 802 extern  rfs4_client_t   *rfs4_findclient(nfs_client_id4 *,
 803                                         bool_t *, rfs4_client_t *);
 804 extern  rfs4_client_t   *rfs4_findclient_by_id(clientid4, bool_t);
 805 extern  rfs4_client_t   *rfs4_findclient_by_addr(struct sockaddr *);
 806 extern  void            rfs4_client_rele(rfs4_client_t *);
 807 extern  void            rfs4_client_close(rfs4_client_t *);
 808 extern  void            rfs4_client_state_remove(rfs4_client_t *);
 809 extern  void            rfs4_client_scv_next(rfs4_client_t *);
 810 extern  void            rfs4_update_lease(rfs4_client_t *);
 811 extern  bool_t          rfs4_lease_expired(rfs4_client_t *);
 812 extern  nfsstat4        rfs4_check_clientid(clientid4 *, int);
 813 
 814 /* rfs4_clntip_t handling */
 815 extern  rfs4_clntip_t   *rfs4_find_clntip(struct sockaddr *, bool_t *);
 816 extern  void            rfs4_invalidate_clntip(struct sockaddr *);
 817 


 929                 caller_context_t *);
 930 extern int deleg_wr_space(femarg_t *, int, flock64_t *, int, offset_t, cred_t *,
 931                 caller_context_t *);
 932 extern int deleg_rd_setsecattr(femarg_t *, vsecattr_t *, int, cred_t *,
 933                 caller_context_t *);
 934 extern int deleg_wr_setsecattr(femarg_t *, vsecattr_t *, int, cred_t *,
 935                 caller_context_t *);
 936 extern int deleg_rd_vnevent(femarg_t *, vnevent_t, vnode_t *, char *,
 937                 caller_context_t *);
 938 extern int deleg_wr_vnevent(femarg_t *, vnevent_t, vnode_t *, char *,
 939                 caller_context_t *);
 940 
 941 extern void rfs4_mon_hold(void *);
 942 extern void rfs4_mon_rele(void *);
 943 
 944 extern fem_t    *deleg_rdops;
 945 extern fem_t    *deleg_wrops;
 946 
 947 extern int rfs4_share(rfs4_state_t *, uint32_t, uint32_t);
 948 extern int rfs4_unshare(rfs4_state_t *);
 949 extern  void            rfs4_set_deleg_policy(srv_deleg_policy_t);



 950 #ifdef DEBUG
 951 #define NFS4_DEBUG(var, args) if (var) cmn_err args
 952 
 953 extern int rfs4_debug;
 954 extern int nfs4_client_attr_debug;
 955 extern int nfs4_client_state_debug;
 956 extern int nfs4_client_shadow_debug;
 957 extern int nfs4_client_lock_debug;
 958 extern int nfs4_client_lease_debug;
 959 extern int nfs4_seqid_sync;
 960 extern int nfs4_client_map_debug;
 961 extern int nfs4_client_inactive_debug;
 962 extern int nfs4_client_recov_debug;
 963 extern int nfs4_client_failover_debug;
 964 extern int nfs4_client_call_debug;
 965 extern int nfs4_client_foo_debug;
 966 extern int nfs4_client_zone_debug;
 967 extern int nfs4_lost_rqst_debug;
 968 extern int nfs4_open_stream_debug;
 969 extern int nfs4_client_open_dg;


1331     int, int);
1332 extern int      vs_ace4_to_acet(vsecattr_t *, vsecattr_t *, uid_t, gid_t,
1333     int);
1334 extern int      vs_acet_to_ace4(vsecattr_t *, vsecattr_t *, int);
1335 extern void     vs_acet_destroy(vsecattr_t *);
1336 extern void     vs_ace4_destroy(vsecattr_t *);
1337 extern void     vs_aent_destroy(vsecattr_t *);
1338 
1339 extern int      vn_find_nfs_record(vnode_t *, nvlist_t **, char **, char **);
1340 extern int      vn_is_nfs_reparse(vnode_t *, cred_t *);
1341 extern fs_locations4 *fetch_referral(vnode_t *, cred_t *);
1342 extern char     *build_symlink(vnode_t *, cred_t *, size_t *);
1343 
1344 extern int      stateid4_cmp(stateid4 *, stateid4 *);
1345 
1346 extern vtype_t  nf4_to_vt[];
1347 
1348 extern struct nfs4_ntov_map nfs4_ntov_map[];
1349 extern uint_t nfs4_ntov_map_size;
1350 
1351 extern kstat_named_t    *rfsproccnt_v4_ptr;
1352 extern struct vfsops    *nfs4_vfsops;
1353 extern struct vnodeops  *nfs4_vnodeops;
1354 extern const struct     fs_operation_def nfs4_vnodeops_template[];
1355 extern vnodeops_t       *nfs4_trigger_vnodeops;
1356 extern const struct     fs_operation_def nfs4_trigger_vnodeops_template[];
1357 
1358 extern uint_t nfs4_tsize(struct knetconfig *);
1359 extern uint_t rfs4_tsize(struct svc_req *);
1360 
1361 extern bool_t   xdr_inline_decode_nfs_fh4(uint32_t *, nfs_fh4_fmt_t *,
1362                         uint32_t);
1363 extern bool_t   xdr_inline_encode_nfs_fh4(uint32_t **, uint32_t *,
1364                         nfs_fh4_fmt_t *);
1365 
1366 #ifdef DEBUG
1367 extern int              rfs4_do_pre_op_attr;
1368 extern int              rfs4_do_post_op_attr;
1369 #endif
1370 
1371 extern stateid4 clnt_special0;
1372 extern stateid4 clnt_special1;
1373 #define CLNT_ISSPECIAL(id) (stateid4_cmp(id, &clnt_special0) || \
1374                                 stateid4_cmp(id, &clnt_special1))
1375 
1376 /*
1377  * The NFS Version 4 service procedures.
1378  */
1379 

1380 extern void     rfs4_compound(COMPOUND4args *, COMPOUND4res *,
1381                         struct exportinfo *, struct svc_req *, cred_t *, int *);
1382 extern void     rfs4_compound_free(COMPOUND4res *);
1383 extern void     rfs4_compound_flagproc(COMPOUND4args *, int *);
1384 
1385 extern int      rfs4_srvrinit(void);
1386 extern void     rfs4_srvrfini(void);
1387 extern void     rfs4_state_init(void);
1388 extern void     rfs4_state_fini(void);





1389 
1390 #endif
1391 #ifdef  __cplusplus
1392 }
1393 #endif
1394 
1395 #endif /* _NFS4_H */


   3  *
   4  * The contents of this file are subject to the terms of the
   5  * Common Development and Distribution License (the "License").
   6  * You may not use this file except in compliance with the License.
   7  *
   8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9  * or http://www.opensolaris.org/os/licensing.
  10  * See the License for the specific language governing permissions
  11  * and limitations under the License.
  12  *
  13  * When distributing Covered Code, include this CDDL HEADER in each
  14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15  * If applicable, add the following below this CDDL HEADER, with the
  16  * fields enclosed by brackets "[]" replaced with your own identifying
  17  * information: Portions Copyright [yyyy] [name of copyright owner]
  18  *
  19  * CDDL HEADER END
  20  */
  21 
  22 /*
  23  * Copyright 2010 Sun Microsystems, Inc.  All rights reserved.
  24  * Use is subject to license terms.
  25  */
  26 
  27 /*
  28  * Copyright 2018 Nexenta Systems, Inc.
  29  * Copyright 2019 Nexenta by DDN, Inc.
  30  */
  31 
  32 #ifndef _NFS4_H
  33 #define _NFS4_H
  34 
  35 #include <sys/types.h>
  36 #include <sys/vnode.h>
  37 #include <sys/fem.h>
  38 #include <rpc/rpc.h>
  39 #include <nfs/nfs.h>
  40 
  41 #ifdef _KERNEL
  42 #include <nfs/nfs4_kprot.h>
  43 #include <nfs/nfs4_drc.h>
  44 #include <sys/nvpair.h>
  45 #else
  46 #include <rpcsvc/nfs4_prot.h>
  47 #endif
  48 #include <nfs/nfs4_attr.h>
  49 #include <sys/acl.h>
  50 #include <sys/list.h>
  51 
  52 #ifdef  __cplusplus
  53 extern "C" {
  54 #endif
  55 
  56 #define NFS4_MAX_SECOID4        65536
  57 #define NFS4_MAX_UTF8STRING     65536
  58 #define NFS4_MAX_LINKTEXT4      65536
  59 #define NFS4_MAX_PATHNAME4      65536
  60 
  61 struct nfs_fsl_info {
  62         uint_t netbuf_len;
  63         uint_t netnm_len;


 104  *
 105  * The basic structure at this level is that the server maintains a
 106  * global "database" which consists of a set of tables.  Each table
 107  * contains a set of like data structures.  Each table is indexed by
 108  * at least one hash function and in most cases two hashes.  Each
 109  * table's characteristics is set when it is created at run-time via
 110  * rfs4_table_create().  All table creation and related functions are
 111  * located in nfs4_state.c.  The generic database functionality is
 112  * located in nfs4_db.c.
 113  */
 114 
 115 typedef struct rfs4_dbe rfs4_dbe_t;             /* basic opaque db entry */
 116 typedef struct rfs4_table rfs4_table_t;         /* basic table type */
 117 typedef struct rfs4_index rfs4_index_t;         /* index */
 118 typedef struct rfs4_database rfs4_database_t;   /* and database */
 119 
 120 typedef struct {                /* opaque entry type for later use */
 121         rfs4_dbe_t *dbe;
 122 } *rfs4_entry_t;
 123 
 124 /*
 125  * NFSv4 server state databases
 126  *
 127  * Initialized when the module is loaded and used by NFSv4 state tables.
 128  * These kmem_cache free pools are used globally, the NFSv4 state tables
 129  * which make use of these kmem_cache free pools are per zone.
 130  */
 131 extern kmem_cache_t *rfs4_client_mem_cache;
 132 extern kmem_cache_t *rfs4_clntIP_mem_cache;
 133 extern kmem_cache_t *rfs4_openown_mem_cache;
 134 extern kmem_cache_t *rfs4_openstID_mem_cache;
 135 extern kmem_cache_t *rfs4_lockstID_mem_cache;
 136 extern kmem_cache_t *rfs4_lockown_mem_cache;
 137 extern kmem_cache_t *rfs4_file_mem_cache;
 138 extern kmem_cache_t *rfs4_delegstID_mem_cache;
 139 
 140 /* database, table, index creation entry points */
 141 extern rfs4_database_t *rfs4_database_create(uint32_t);
 142 extern void             rfs4_database_shutdown(rfs4_database_t *);
 143 extern void             rfs4_database_destroy(rfs4_database_t *);
 144 
 145 extern void             rfs4_database_destroy(rfs4_database_t *);
 146 
 147 extern kmem_cache_t     *nfs4_init_mem_cache(char *, uint32_t, uint32_t,
 148                                 uint32_t);
 149 extern rfs4_table_t     *rfs4_table_create(rfs4_database_t *, char *,
 150                                 time_t, uint32_t,
 151                                 bool_t (*create)(rfs4_entry_t, void *),
 152                                 void (*destroy)(rfs4_entry_t),
 153                                 bool_t (*expiry)(rfs4_entry_t),
 154                                 uint32_t, uint32_t, uint32_t, id_t);
 155 extern void             rfs4_table_destroy(rfs4_database_t *, rfs4_table_t *);
 156 extern rfs4_index_t     *rfs4_index_create(rfs4_table_t *, char *,
 157                                 uint32_t (*hash)(void *),
 158                                 bool_t (compare)(rfs4_entry_t, void *),
 159                                 void *(*mkkey)(rfs4_entry_t), bool_t);
 160 extern void             rfs4_index_destroy(rfs4_index_t *);
 161 
 162 /* Type used to direct rfs4_dbsearch() in what types of records to inspect */
 163 typedef enum {RFS4_DBS_VALID, RFS4_DBS_INVALID} rfs4_dbsearch_type_t;
 164 /* search and db entry manipulation entry points */
 165 extern rfs4_entry_t     rfs4_dbsearch(rfs4_index_t *, void *,
 166                                 bool_t *, void *, rfs4_dbsearch_type_t);
 167 extern void             rfs4_dbe_lock(rfs4_dbe_t *);
 168 extern void             rfs4_dbe_unlock(rfs4_dbe_t *);


 370         struct rfs4_servinst    *next;
 371         struct rfs4_servinst    *prev;
 372 } rfs4_servinst_t;
 373 
 374 /*
 375  * DSS: distributed stable storage
 376  */
 377 
 378 typedef struct rfs4_dss_path {
 379         struct rfs4_dss_path    *next; /* for insque/remque */
 380         struct rfs4_dss_path    *prev; /* for insque/remque */
 381         char                    *path;
 382         struct rfs4_servinst    *sip;
 383         unsigned                index; /* offset in servinst's array */
 384 } rfs4_dss_path_t;
 385 
 386 /* array of paths passed-in from nfsd command-line; stored in nvlist */
 387 char            **rfs4_dss_newpaths;
 388 uint_t          rfs4_dss_numnewpaths;
 389 






 390 /* nvlists of all DSS paths: current, and before last warmstart */
 391 nvlist_t *rfs4_dss_paths, *rfs4_dss_oldpaths;
 392 
 393 /*
 394  * The server maintains a set of state on a per client basis that
 395  * matches that of the protocol requirements.  A client's state is
 396  * rooted with the rfs4_client_t struct of which there is one per
 397  * client and is created when SETCLIENTID/SETCLIENTID_CONFIRM are
 398  * received.  From there, the server then creates rfs4_openowner_t
 399  * structs for each new open owner from that client and are initiated
 400  * at OPEN/OPEN_CONFIRM (when the open owner is new to the server).
 401  * At OPEN, at least two other structures are created, and potentially a
 402  * third.  rfs4_state_t is created to track the association between an
 403  * open owner and a particular file. An rfs4_file_t struct may be
 404  * created (if the file is not already open) at OPEN as well.  The
 405  * rfs4_file_t struct is the only one that is per server and not per
 406  * client.  The rfs4_deleg_state_t struct is created in the
 407  * instance that the server is going to provide a delegation for the
 408  * file being OPENed.  Finally, the rfs4_lockowner_t is created at the
 409  * first use of a lock owner at the server and is a result of the LOCK


 735  *      lock may or may not be held for lock/unlock of file_rwlock.
 736  *      As mentioned above, the file_rwlock is used for serialization
 737  *      of file removal and more specifically reference to the held
 738  *      vnode (e.g. vp).
 739  */
 740 typedef struct rfs4_file {
 741         rfs4_dbe_t      *rf_dbe;
 742         vnode_t         *rf_vp;
 743         nfs_fh4         rf_filehandle;
 744         list_t          rf_delegstatelist;
 745         rfs4_dinfo_t    rf_dinfo;
 746         uint32_t        rf_share_deny;
 747         uint32_t        rf_share_access;
 748         uint32_t        rf_access_read;
 749         uint32_t        rf_access_write;
 750         uint32_t        rf_deny_read;
 751         uint32_t        rf_deny_write;
 752         krwlock_t       rf_file_rwlock;
 753 } rfs4_file_t;
 754 


















 755 /*
 756  * nfs4_deleg_policy is used to signify the server's global delegation
 757  * policy.  The default is to NEVER delegate files and the
 758  * administrator must configure the server to enable delegations.
 759  *
 760  * The disable/enable delegation functions are used to eliminate a
 761  * race with exclusive creates.
 762  */
 763 typedef enum {
 764         SRV_NEVER_DELEGATE = 0,
 765         SRV_NORMAL_DELEGATE = 1
 766 } srv_deleg_policy_t;
 767 


 768 extern void rfs4_disable_delegation(void), rfs4_enable_delegation(void);
 769 
 770 /*
 771  * Request types for delegation. These correspond with
 772  * open_delegation_type4 with the addition of a new value, DELEG_ANY,
 773  * to reqequest any delegation.
 774  */
 775 typedef enum {
 776         DELEG_NONE = 0,         /* Corresponds to OPEN_DELEG_NONE */
 777         DELEG_READ = 1,         /* Corresponds to OPEN_DELEG_READ */
 778         DELEG_WRITE = 2,        /* Corresponds to OPEN_DELEG_WRITE */
 779         DELEG_ANY = -1          /* New value to request any delegation type */
 780 } delegreq_t;
 781 
 782 #define NFS4_DELEG4TYPE2REQTYPE(x) (delegreq_t)(x)
 783 
 784 /*
 785  * Zone global variables of NFSv4 server
 786  */
 787 typedef struct nfs4_srv {
 788         /* Unique write verifier */
 789         verifier4       write4verf;
 790         /* Delegation lock */
 791         kmutex_t        deleg_lock;
 792         /* Used to serialize create/destroy of nfs4_server_state database */
 793         kmutex_t        state_lock;
 794         rfs4_database_t *nfs4_server_state;
 795         /* Used to manage access to server instance linked list */
 796         kmutex_t        servinst_lock;
 797         rfs4_servinst_t *nfs4_cur_servinst;
 798         /* Used to manage access to nfs4_deleg_policy */
 799         krwlock_t       deleg_policy_lock;
 800         srv_deleg_policy_t nfs4_deleg_policy;
 801         /* Set first time we see one */
 802         int             seen_first_compound;
 803         /*
 804          * Circular double-linked list of paths for currently-served RGs.
 805          * No locking required -- only changed on server start.
 806          * Managed with insque/remque.
 807          */
 808         rfs4_dss_path_t *dss_pathlist;
 809         /* Duplicate request cache */
 810         rfs4_drc_t      *nfs4_drc;
 811         /* nfsv4 server start time */
 812         time_t rfs4_start_time;
 813         /* Used to serialize lookups of clientids */
 814         krwlock_t rfs4_findclient_lock;
 815 
 816         /* NFSv4 server state client tables */
 817         /* table expiry times */
 818         time_t rfs4_client_cache_time;
 819         time_t rfs4_openowner_cache_time;
 820         time_t rfs4_state_cache_time;
 821         time_t rfs4_lo_state_cache_time;
 822         time_t rfs4_lockowner_cache_time;
 823         time_t rfs4_file_cache_time;
 824         time_t rfs4_deleg_state_cache_time;
 825         time_t rfs4_clntip_cache_time;
 826         /* tables and indexes */
 827         /* client table */
 828         rfs4_table_t *rfs4_client_tab;
 829         rfs4_index_t *rfs4_clientid_idx;
 830         rfs4_index_t *rfs4_nfsclnt_idx;
 831         /* client IP table */
 832         rfs4_table_t *rfs4_clntip_tab;
 833         rfs4_index_t *rfs4_clntip_idx;
 834         /* Open Owner table */
 835         rfs4_table_t *rfs4_openowner_tab;
 836         rfs4_index_t *rfs4_openowner_idx;
 837         /* Open State ID table */
 838         rfs4_table_t *rfs4_state_tab;
 839         rfs4_index_t *rfs4_state_idx;
 840         rfs4_index_t *rfs4_state_owner_file_idx;
 841         rfs4_index_t *rfs4_state_file_idx;
 842         /* Lock State ID table */
 843         rfs4_table_t *rfs4_lo_state_tab;
 844         rfs4_index_t *rfs4_lo_state_idx;
 845         rfs4_index_t *rfs4_lo_state_owner_idx;
 846         /* Lock owner table */
 847         rfs4_table_t *rfs4_lockowner_tab;
 848         rfs4_index_t *rfs4_lockowner_idx;
 849         rfs4_index_t *rfs4_lockowner_pid_idx;
 850         /* File table */
 851         rfs4_table_t *rfs4_file_tab;
 852         rfs4_index_t *rfs4_file_idx;
 853         /* Deleg State table */
 854         rfs4_table_t *rfs4_deleg_state_tab;
 855         rfs4_index_t *rfs4_deleg_idx;
 856         rfs4_index_t *rfs4_deleg_state_idx;
 857 
 858         /* client stable storage */
 859         int rfs4_ss_enabled;
 860 } nfs4_srv_t;
 861 
 862 /*
 863  * max length of the NFSv4 server database name
 864  */
 865 #define RFS4_MAX_MEM_CACHE_NAME 48
 866 
 867 /*
 868  * global NFSv4 server kmem caches
 869  * r_db_name - The name of the state database and the table that will use it
 870  *             These tables are defined in nfs4_srv_t
 871  * r_db_mem_cache - The kmem cache associated with the state database name
 872  */
 873 typedef struct rfs4_db_mem_cache {
 874         char            r_db_name[RFS4_MAX_MEM_CACHE_NAME];
 875         kmem_cache_t    *r_db_mem_cache;
 876 } rfs4_db_mem_cache_t;
 877 
 878 #define RFS4_DB_MEM_CACHE_NUM 8
 879 
 880 rfs4_db_mem_cache_t rfs4_db_mem_cache_table[RFS4_DB_MEM_CACHE_NUM];
 881 
 882 
 883 extern srv_deleg_policy_t nfs4_get_deleg_policy();
 884 
 885 extern void             rfs4_servinst_create(nfs4_srv_t *, int, int, char **);
 886 extern void             rfs4_servinst_destroy_all(nfs4_srv_t *);
 887 extern void             rfs4_servinst_assign(nfs4_srv_t *, rfs4_client_t *,
 888                             rfs4_servinst_t *);
 889 extern rfs4_servinst_t  *rfs4_servinst(rfs4_client_t *);
 890 extern int              rfs4_clnt_in_grace(rfs4_client_t *);
 891 extern int              rfs4_servinst_in_grace(rfs4_servinst_t *);
 892 extern int              rfs4_servinst_grace_new(rfs4_servinst_t *);
 893 extern void             rfs4_grace_start(rfs4_servinst_t *);
 894 extern void             rfs4_grace_start_new(nfs4_srv_t *);
 895 extern void             rfs4_grace_reset_all(nfs4_srv_t *);
 896 extern void             rfs4_ss_oldstate(rfs4_oldstate_t *, char *, char *);
 897 extern void             rfs4_dss_readstate(nfs4_srv_t *, int, char **);
 898 
 899 /*
 900  * Various interfaces to manipulate the state structures introduced
 901  * above
 902  */


 903 extern  void            rfs4_free_reply(nfs_resop4 *);
 904 extern  void            rfs4_copy_reply(nfs_resop4 *, nfs_resop4 *);
 905 
 906 /* rfs4_client_t handling */
 907 extern  rfs4_client_t   *rfs4_findclient(nfs_client_id4 *,
 908                                         bool_t *, rfs4_client_t *);
 909 extern  rfs4_client_t   *rfs4_findclient_by_id(clientid4, bool_t);
 910 extern  rfs4_client_t   *rfs4_findclient_by_addr(struct sockaddr *);
 911 extern  void            rfs4_client_rele(rfs4_client_t *);
 912 extern  void            rfs4_client_close(rfs4_client_t *);
 913 extern  void            rfs4_client_state_remove(rfs4_client_t *);
 914 extern  void            rfs4_client_scv_next(rfs4_client_t *);
 915 extern  void            rfs4_update_lease(rfs4_client_t *);
 916 extern  bool_t          rfs4_lease_expired(rfs4_client_t *);
 917 extern  nfsstat4        rfs4_check_clientid(clientid4 *, int);
 918 
 919 /* rfs4_clntip_t handling */
 920 extern  rfs4_clntip_t   *rfs4_find_clntip(struct sockaddr *, bool_t *);
 921 extern  void            rfs4_invalidate_clntip(struct sockaddr *);
 922 


1034                 caller_context_t *);
1035 extern int deleg_wr_space(femarg_t *, int, flock64_t *, int, offset_t, cred_t *,
1036                 caller_context_t *);
1037 extern int deleg_rd_setsecattr(femarg_t *, vsecattr_t *, int, cred_t *,
1038                 caller_context_t *);
1039 extern int deleg_wr_setsecattr(femarg_t *, vsecattr_t *, int, cred_t *,
1040                 caller_context_t *);
1041 extern int deleg_rd_vnevent(femarg_t *, vnevent_t, vnode_t *, char *,
1042                 caller_context_t *);
1043 extern int deleg_wr_vnevent(femarg_t *, vnevent_t, vnode_t *, char *,
1044                 caller_context_t *);
1045 
1046 extern void rfs4_mon_hold(void *);
1047 extern void rfs4_mon_rele(void *);
1048 
1049 extern fem_t    *deleg_rdops;
1050 extern fem_t    *deleg_wrops;
1051 
1052 extern int rfs4_share(rfs4_state_t *, uint32_t, uint32_t);
1053 extern int rfs4_unshare(rfs4_state_t *);
1054 extern void rfs4_set_deleg_policy(nfs4_srv_t *, srv_deleg_policy_t);
1055 extern void rfs4_hold_deleg_policy(nfs4_srv_t *);
1056 extern void rfs4_rele_deleg_policy(nfs4_srv_t *);
1057 
1058 #ifdef DEBUG
1059 #define NFS4_DEBUG(var, args) if (var) cmn_err args
1060 
1061 extern int rfs4_debug;
1062 extern int nfs4_client_attr_debug;
1063 extern int nfs4_client_state_debug;
1064 extern int nfs4_client_shadow_debug;
1065 extern int nfs4_client_lock_debug;
1066 extern int nfs4_client_lease_debug;
1067 extern int nfs4_seqid_sync;
1068 extern int nfs4_client_map_debug;
1069 extern int nfs4_client_inactive_debug;
1070 extern int nfs4_client_recov_debug;
1071 extern int nfs4_client_failover_debug;
1072 extern int nfs4_client_call_debug;
1073 extern int nfs4_client_foo_debug;
1074 extern int nfs4_client_zone_debug;
1075 extern int nfs4_lost_rqst_debug;
1076 extern int nfs4_open_stream_debug;
1077 extern int nfs4_client_open_dg;


1439     int, int);
1440 extern int      vs_ace4_to_acet(vsecattr_t *, vsecattr_t *, uid_t, gid_t,
1441     int);
1442 extern int      vs_acet_to_ace4(vsecattr_t *, vsecattr_t *, int);
1443 extern void     vs_acet_destroy(vsecattr_t *);
1444 extern void     vs_ace4_destroy(vsecattr_t *);
1445 extern void     vs_aent_destroy(vsecattr_t *);
1446 
1447 extern int      vn_find_nfs_record(vnode_t *, nvlist_t **, char **, char **);
1448 extern int      vn_is_nfs_reparse(vnode_t *, cred_t *);
1449 extern fs_locations4 *fetch_referral(vnode_t *, cred_t *);
1450 extern char     *build_symlink(vnode_t *, cred_t *, size_t *);
1451 
1452 extern int      stateid4_cmp(stateid4 *, stateid4 *);
1453 
1454 extern vtype_t  nf4_to_vt[];
1455 
1456 extern struct nfs4_ntov_map nfs4_ntov_map[];
1457 extern uint_t nfs4_ntov_map_size;
1458 

1459 extern struct vfsops    *nfs4_vfsops;
1460 extern struct vnodeops  *nfs4_vnodeops;
1461 extern const struct     fs_operation_def nfs4_vnodeops_template[];
1462 extern vnodeops_t       *nfs4_trigger_vnodeops;
1463 extern const struct     fs_operation_def nfs4_trigger_vnodeops_template[];
1464 
1465 extern uint_t nfs4_tsize(struct knetconfig *);
1466 extern uint_t rfs4_tsize(struct svc_req *);
1467 
1468 extern bool_t   xdr_inline_decode_nfs_fh4(uint32_t *, nfs_fh4_fmt_t *,
1469                         uint32_t);
1470 extern bool_t   xdr_inline_encode_nfs_fh4(uint32_t **, uint32_t *,
1471                         nfs_fh4_fmt_t *);
1472 
1473 #ifdef DEBUG
1474 extern int              rfs4_do_pre_op_attr;
1475 extern int              rfs4_do_post_op_attr;
1476 #endif
1477 
1478 extern stateid4 clnt_special0;
1479 extern stateid4 clnt_special1;
1480 #define CLNT_ISSPECIAL(id) (stateid4_cmp(id, &clnt_special0) || \
1481                                 stateid4_cmp(id, &clnt_special1))
1482 
1483 /*
1484  * The NFS Version 4 service procedures.
1485  */
1486 
1487 extern void     rfs4_do_server_start(int, int, int);
1488 extern void     rfs4_compound(COMPOUND4args *, COMPOUND4res *,
1489                         struct exportinfo *, struct svc_req *, cred_t *, int *);
1490 extern void     rfs4_compound_free(COMPOUND4res *);
1491 extern void     rfs4_compound_flagproc(COMPOUND4args *, int *);
1492 
1493 extern void     rfs4_srvrinit(void);
1494 extern void     rfs4_srvrfini(void);
1495 extern void     rfs4_srv_zone_init(nfs_globals_t *);
1496 extern void     rfs4_srv_zone_fini(nfs_globals_t *);
1497 extern void     rfs4_state_g_init(void);
1498 extern void     rfs4_state_zone_init(nfs4_srv_t *);
1499 extern void     rfs4_state_g_fini(void);
1500 extern void     rfs4_state_zone_fini(void);
1501 extern nfs4_srv_t *nfs4_get_srv(void);
1502 
1503 #endif
1504 #ifdef  __cplusplus
1505 }
1506 #endif
1507 
1508 #endif /* _NFS4_H */