Home | History | Annotate | Download | only in nfs
      1 /*
      2  * CDDL HEADER START
      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  * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
     23  * Use is subject to license terms.
     24  */
     25 
     26 #ifndef _NFS4_H
     27 #define	_NFS4_H
     28 
     29 #include <sys/types.h>
     30 #include <sys/vnode.h>
     31 #include <sys/fem.h>
     32 #include <rpc/rpc.h>
     33 #include <nfs/nfs.h>
     34 #include <nfs/nnode.h>
     35 
     36 #ifdef _KERNEL
     37 #include <nfs/nfs4_kprot.h>
     38 #include <sys/nvpair.h>
     39 #else
     40 #include <rpcsvc/nfs4_prot.h>
     41 #endif
     42 #include <nfs/nfs4_attr.h>
     43 #include <sys/acl.h>
     44 #include <sys/list.h>
     45 
     46 #ifdef	__cplusplus
     47 extern "C" {
     48 #endif
     49 
     50 #define	NFS4_MAX_UTF8STRING	65536
     51 #define	NFS4_MAX_PATHNAME4	65536
     52 #define	NFS4_MAX_SECOID4	65536
     53 
     54 #ifdef _KERNEL
     55 
     56 struct nfs4_fhandle {
     57 	int fh_len;
     58 	char fh_buf[NFS4_FHSIZE];
     59 };
     60 typedef struct nfs4_fhandle nfs4_fhandle_t;
     61 
     62 #define	NFS4_MINOR_v0 0
     63 #define	NFS4_MINOR_v1 1
     64 
     65 #define	CB4_MINOR_v0  0
     66 #define	CB4_MINOR_v1  1
     67 
     68 /*
     69  * Set the fattr4_change variable using a time struct. Note that change
     70  * is 64 bits, but timestruc_t is 128 bits in a 64-bit kernel.
     71  */
     72 #define	NFS4_SET_FATTR4_CHANGE(change, ts)			\
     73 {							\
     74 	change = (ts).tv_sec;				\
     75 	change <<= 32;					\
     76 	change |= (uint32_t)((ts).tv_nsec);		\
     77 }
     78 
     79 /*
     80  * Server lease period.  Value is in seconds;  Also used for grace period
     81  */
     82 extern time_t rfs4_lease_time;
     83 
     84 /*
     85  * This set of typedefs and interfaces represent the core or base set
     86  * of functionality that backs the NFSv4 server's state related data
     87  * structures.  Since the NFSv4 server needs inter-RPC state to be
     88  * available that is unrelated to the filesystem (in other words,
     89  * soft-state), this functionality is needed to maintain that and is
     90  * written to be somewhat flexible to adapt to the various types of
     91  * data structures contained within the server.
     92  *
     93  * The basic structure at this level is that the server maintains a
     94  * global "database" which consists of a set of tables.  Each table
     95  * contains a set of like data structures.  Each table is indexed by
     96  * at least one hash function and in most cases two hashes.  Each
     97  * table's characteristics is set when it is created at run-time via
     98  * rfs4_table_create().  All table creation and related functions are
     99  * located in nfs4_state.c.  The generic database functionality is
    100  * located in nfs4_db.c.
    101  */
    102 
    103 typedef struct rfs4_dbe		rfs4_dbe_t;	 /* basic opaque db entry */
    104 typedef struct rfs4_table	rfs4_table_t;	 /* basic table type */
    105 typedef struct rfs4_index	rfs4_index_t;	 /* index */
    106 typedef struct rfs4_database	rfs4_database_t; /* and database */
    107 
    108 typedef struct {		/* opaque entry type for later use */
    109 	rfs4_dbe_t *dbe;
    110 } *rfs4_entry_t;
    111 
    112 struct mds_layout_grant;
    113 
    114 typedef struct rfs41_grant_list {
    115 	struct rfs41_grant_list *next;
    116 	struct rfs41_grant_list *prev;
    117 	struct mds_layout_grant	*lg;
    118 } rfs41_grant_list_t;
    119 
    120 /*
    121  * Minimal server stable storage.
    122  *
    123  * Currently the NFSv4 server will only save the client
    124  * ID (the long version) so that it will be able to
    125  * grant possible reclaim requests during the infamous
    126  * grace_period.
    127  */
    128 
    129 #define	RFS4_SS_DIRSIZE	64 * 1024
    130 
    131 /* handy pathname structure */
    132 typedef struct ss_pn {
    133 	char *leaf;
    134 	char pn[MAXPATHLEN];
    135 } rfs4_ss_pn_t;
    136 
    137 /*
    138  * The server will build this link list on startup. It represents the
    139  * clients that have had valid state on the server in a prior instance.
    140  *
    141  */
    142 typedef struct {
    143 	list_node_t  	reclaim_list;
    144 	rfs4_ss_pn_t	*ss_pn;
    145 	nfs_client_id4	cl_id4;
    146 } rfs4_reclaim_t;
    147 
    148 /*
    149  *  The state id between NFS v4.0 and V4.1 are
    150  *  different. v4_bits describes the v4.0 version:
    151  *
    152  *  chgseq	State changes / protocol's seqid
    153  *  boottime	The instance start time.
    154  *  type	Stateid type as defined below
    155  *  clnodeid	cluster server nodeid
    156  *  state_ident 2^22-1 openowner x fhs
    157  *  pid 	process id to corresponding lock owner
    158  */
    159 typedef struct {
    160 	uint32_t chgseq;
    161 	uint32_t boottime;
    162 	uint32_t type:2;
    163 	uint32_t clnodeid:8;
    164 	uint32_t state_ident:22;
    165 	pid_t	 pid;
    166 } v4_bits_t;
    167 
    168 /*
    169  *  v41_bits describes the v4.1 version:
    170  *
    171  *  chgseq	State changes / protocol's seqid
    172  *  boottime	The instance start time.
    173  *  type	Stateid type as defined below
    174  *  state_ident 2^22-1 openowner x fhs
    175  *  pid 	process id to corresponding lock owner
    176  */
    177 typedef struct {
    178 	uint32_t chgseq;
    179 	uint32_t boottime;
    180 	uint32_t type:4;
    181 	uint32_t state_ident:28;
    182 	pid_t	 pid;
    183 } v41_bits_t;
    184 
    185 /*
    186  * This union is used to overlay the server's internal treatment of
    187  * the protocols stateid4 datatype.  Therefore, "bits" must not exceed
    188  * the size of stateid4 and more importantly should match the size of
    189  * stateid4.  The chgseq field must the first entry since it overlays
    190  * stateid4.seqid.
    191  */
    192 typedef union {
    193 	stateid4 stateid;
    194 	v4_bits_t v4_bits;
    195 	v41_bits_t v41_bits;
    196 } stateid_t;
    197 
    198 /*
    199  * !! Note !!
    200  *
    201  * The way the type field above is defined for NFSv4.0 (2 bits)
    202  * only open,lock and delegation stateid types are supported.
    203  * NFSv4.1 has more stateids and so will support up to 4 bits.
    204  *
    205  */
    206 typedef enum {
    207     OPENID,
    208     LOCKID,
    209     DELEGID,
    210     LAYOUTID
    211 } stateid_type_t;
    212 
    213 
    214 /*
    215  * Set of RPC credentials used for a particular operation.
    216  * Used for operations like SETCLIENTID_CONFIRM where the
    217  * credentials needs to match those used at SETCLIENTID.
    218  */
    219 typedef void *cred_set_t;		/* For now XXX */
    220 
    221 typedef struct {
    222 	cred_t	*cp_cr;
    223 	int	 cp_aflavor;
    224 	int	 cp_secmod;
    225 	caddr_t	 cp_princ;
    226 } cred_princ_t;
    227 
    228 /*
    229  * "wait" struct for use in the open open and lock owner state
    230  * structures to provide serialization between server threads that are
    231  * handling requests for the same open owner or lock stateid.  This
    232  * way only one thread will be updating things like sequence ids,
    233  * replay cache and stateid at a time.
    234  */
    235 typedef struct rfs4_state_wait {
    236 	uint32_t		sw_active;
    237 	uint32_t		sw_wait_count;
    238 	kmutex_t		sw_cv_lock[1];
    239 	kcondvar_t		sw_cv[1];
    240 } rfs4_state_wait_t;
    241 
    242 extern void	rfs4_sw_enter(rfs4_state_wait_t *);
    243 extern void	rfs4_sw_exit(rfs4_state_wait_t *);
    244 
    245 /*
    246  * This enum and the following rfs4_cbinfo_t struct are used to
    247  * maintain information about the callback path used from the server
    248  * to client for operations like CB_GETATTR and CB_RECALL.  The
    249  * rfs4_cbinfo_t struct is meant to be encompassed in the client
    250  * struct and managed within that structure's locking scheme.
    251  *
    252  * The various states of the callback path are used by the server to
    253  * determine if delegations should initially be provided to a client
    254  * and then later on if connectivity has been lost and delegations
    255  * should be revoked.
    256  */
    257 
    258 /*
    259  * CB_NOCHANGE - Special value used for interfaces within the delegation
    260  *		code to signify that "no change" has occurred to the
    261  *		callback path
    262  * CB_UNINIT	- No callback info provided by the client
    263  * CB_NONE	- Callback info provided but CB_NULL call
    264  *		  has yet to be attempted
    265  * CB_OK	- Callback path tested with CB_NULL with success
    266  * CB_INPROG	- Callback path currently being tested with CB_NULL
    267  * CB_FAILED	- Callback path was == CB_OK but has failed
    268  *		  with timeout/rpc error
    269  * CB_BAD	- Callback info provided but CB_NULL failed
    270  */
    271 typedef enum {
    272 	CB_NOCHANGE = 0,
    273 	CB_UNINIT = 1,
    274 	CB_NONE = 2,
    275 	CB_OK = 3,
    276 	CB_INPROG = 4,
    277 	CB_FAILED = 5,
    278 	CB_BAD = 6
    279 } rfs4_cbstate_t;
    280 
    281 #define	RFS4_CBCH_MAX	10	/* size callback client handle cache */
    282 /*
    283  * Callback info for a client.
    284  * Client only provides: cb_client4 and cb_ident
    285  * The rest of the information is used to track callback path status
    286  * and usage.
    287  *
    288  * cb_state - used as comments for the rfs4_cbstate_t enum indicate
    289  * cb_notified_of_cb_path_down - if the callback path was once CB_OK and
    290  *	has hence CB_FAILED, the client needs to be notified via RENEW.
    291  * cb_timefailed - current time when cb_state transitioned from
    292  *	CB_OK -> CB_FAILED.  Meant for observability.  When did that happen?
    293  * cb_chc_free/cb_chc - cache of client handles for the callback path
    294  * cb_ident - SETCLIENTID provided callback_ident value
    295  * callback - SETCLIENTID provided cb_client4 value
    296  * cb_refcnt - current number of users of this structure's content
    297  *	protected by cb_lock
    298  * cb_badbehavior - how many times did a client do something we didn't like?
    299  * cb_lock - lock for contents of cbinfo
    300  * cb_cv - used to allow threads to wait on CB_NULL completion
    301  * cb_nullcaller - is there a thread currently taking care of
    302  *	new callback information?
    303  * cb_cv_nullcaller - used by the thread doing CB_NULL to wait on
    304  *	threads that may be using client handles of the current
    305  *	client handle cache.
    306  * newer - new callback info provided by a client and awaiting
    307  *	CB_NULL testing and move to regular cbinfo.
    308  */
    309 typedef struct {
    310 	rfs4_cbstate_t	cb_state;
    311 	unsigned	cb_notified_of_cb_path_down:1;
    312 	time_t		cb_timefailed;
    313 	int		cb_chc_free;
    314 	CLIENT		*cb_chc[RFS4_CBCH_MAX];
    315 	uint32_t	cb_ident;
    316 	cb_client4	cb_callback;
    317 	uint32_t	cb_refcnt;
    318 	uint32_t	cb_badbehavior;
    319 	kmutex_t	cb_lock[1];
    320 	kcondvar_t	cb_cv[1];
    321 	bool_t		cb_nullcaller;
    322 	kcondvar_t	cb_cv_nullcaller[1];
    323 	struct {
    324 		bool_t		cb_new;
    325 		bool_t		cb_confirmed;
    326 		uint32_t	cb_ident;
    327 		cb_client4	cb_callback;
    328 	} cb_newer;
    329 } rfs4_cbinfo_t;
    330 
    331 /*
    332  * DSS: distributed stable storage
    333  */
    334 typedef struct rfs4_dss_path {
    335 	struct rfs4_dss_path	*next; /* for insque/remque */
    336 	struct rfs4_dss_path	*prev; /* for insque/remque */
    337 	char			*path;
    338 	unsigned		index; /* offset in servinst's array */
    339 } rfs4_dss_path_t;
    340 
    341 /* array of paths passed-in from nfsd command-line; stored in nvlist */
    342 char		**rfs4_dss_newpaths;
    343 uint_t		rfs4_dss_numnewpaths;
    344 
    345 /*
    346  * Circular doubly-linked list of paths for currently-served RGs.
    347  * No locking required: only changed on warmstart. Managed with insque/remque.
    348  */
    349 rfs4_dss_path_t	*rfs4_dss_pathlist;
    350 
    351 /* nvlists of all DSS paths: current, and before last warmstart */
    352 nvlist_t *rfs4_dss_paths, *rfs4_dss_oldpaths;
    353 
    354 /*
    355  * Per-(SEQ4 Status Bit) accounting info
    356  */
    357 #define	WORDSZ		sizeof (uint32_t)
    358 #define	BITS_PER_WORD	(WORDSZ * 8)
    359 
    360 typedef struct {
    361 	uint32_t	ba_bit;
    362 	uint32_t	ba_refcnt;
    363 	time_t		ba_trigger;
    364 	uint32_t	ba_sonly;
    365 } bit_attr_t;
    366 
    367 extern uint32_t	pow2(uint32_t);
    368 extern uint32_t	log2(uint32_t);
    369 extern void	rfs41_seq4_hold(void *, uint32_t);
    370 extern void	rfs41_seq4_rele(void *, uint32_t);
    371 
    372 /*
    373  * NFSv4.1: slot support (nfs41_slrc)
    374  */
    375 
    376 /* se_state values */
    377 #define	SLRC_EMPTY_SLOT		0x00000001
    378 #define	SLRC_CACHED_OKAY	0x00000002
    379 #define	SLRC_CACHED_PURGING	0x00000004
    380 #define	SLRC_INPROG_NEWREQ	0x00000008
    381 #define	SLRC_INPROG_REPLAY	0x00000010
    382 #define	SLOT_FREE		0x00000020
    383 #define	SLOT_ERROR		0x00000040
    384 #define	SLOT_INUSE		0x00000080
    385 #define	SLOT_RECALLED		0x00000100
    386 
    387 /* Slot entry structure */
    388 typedef struct slot_ent {
    389 	avl_node_t	  se_node;
    390 	slotid4		  se_sltno;
    391 	uint32_t	  se_state;
    392 	nfsstat4	  se_status;
    393 	sequenceid4	  se_seqid;
    394 	COMPOUND4res_srv  se_buf; /* Buf for slot and replays */
    395 	void		  *se_p;   /* Call-back race detection info buf */
    396 	kmutex_t	  se_lock;
    397 	kcondvar_t	  se_wait;
    398 } slot_ent_t;
    399 
    400 /* Slot table token */
    401 typedef struct slot_tab_token {
    402 	uint_t		  st_currw;	/* current width of slot table */
    403 	uint_t		  st_fslots;	/* current # of available slots */
    404 	avl_tree_t	  *st_sltab;	/* tree of 'currw' pointers */
    405 	kmutex_t	  st_lock;	/* cache lock; resize or destroy */
    406 	kcondvar_t	  st_wait;
    407 } stok_t;
    408 
    409 typedef enum {
    410 	SLT_NOSLEEP	= 0,
    411 	SLT_SLEEP	= 1
    412 } slt_wait_t;
    413 
    414 #define	SA_SLOT_ANY	0x0001
    415 #define	SA_SLOT_SPEC	0x0002
    416 
    417 typedef struct {
    418 	slotid4		sa_sltno;
    419 	uint16_t	sa_flags;
    420 } slt_arg_t;
    421 
    422 typedef enum {
    423 	SLT_MAXSLOT	= 1
    424 } slt_query_t;
    425 
    426 /*
    427  * NFSv4.1 Sessions
    428  */
    429 
    430 typedef struct rfs41_csr_slot {
    431 	uint_t			state;
    432 	nfsstat4		 status;
    433 	sequenceid4		 seqid;
    434 	COMPOUND4res_srv	 res;
    435 	void			*p;
    436 } rfs41_csr_slot_t;
    437 
    438 /*
    439  * 4.1 only: delegation recallable state info.
    440  * struct contents meaningful iff refcnt > 0
    441  */
    442 typedef struct {
    443 	uint32_t	refcnt;
    444 	sessionid4	sessid;
    445 	sequenceid4	seqid;
    446 	slotid4		slotno;
    447 } rfs41_drs_info_t;
    448 
    449 typedef struct rfs41_csr {	/* contrived create_session result */
    450 	sequenceid4		xi_sid;		/* seqid response to EXCHG_ID */
    451 	rfs41_csr_slot_t	cs_slot;	/* slot cache of size 1 */
    452 	CREATE_SESSION4resok	cs_res;		/* cached results if NFS4_OK */
    453 } rfs41_csr_t;
    454 
    455 /*
    456  * Sessions Callback Infrastructure
    457  *
    458  * Locking:
    459  *
    460  * . cn_lock protects all fields in sess_channel_t, but since
    461  *   fore/back and dir don't change often, we serialize only
    462  *   the occasional update.
    463  *
    464  * cn_lock:	cn_lock
    465  * bsd_rwlock:	cn_lock -> bsd_rwlock
    466  */
    467 typedef enum {
    468 	CB_PING_INIT	= 0,
    469 	CB_PING_OK	= 1,
    470 	CB_PING_NEEDED	= 2,
    471 	CB_PING_INPROG	= 3,
    472 	CB_PING_FAILED	= 4
    473 } cb_ping_state_t;
    474 
    475 typedef enum {
    476 	SN_CHAN_FORE	= 0,
    477 	SN_CHAN_BACK	= 1,
    478 	SN_CHAN_BOTH	= 2
    479 } sn_chan_dir_t;
    480 
    481 #define		MAX_CH_CACHE	10
    482 typedef struct {				/* Back Chan Specific Data */
    483 	stok_t			 *bsd_stok;	/* opaque token for slot tab */
    484 	nfsstat4		  bsd_stat;
    485 	krwlock_t		  bsd_rwlock;	/* protect slot tab info */
    486 	uint64_t		  bsd_idx;	/* Index of next spare CLNT */
    487 	uint64_t		  bsd_cur;	/* Most recent added CLNT */
    488 	int			  bsd_ch_free;
    489 	CLIENT			 *bsd_clnt[MAX_CH_CACHE];
    490 } sess_bcsd_t;
    491 
    492 typedef struct {
    493 	channel_dir_from_server4  cn_dir;		/* Chan Direction */
    494 	channel_attrs4		  cn_attrs;		/* chan Attrs */
    495 	void			 *cn_csd;		/* Chan Specific Data */
    496 	krwlock_t		  cn_lock;
    497 } sess_channel_t;
    498 
    499 /*
    500  * callers of CTO*SD macros MUST have cn_lock acquired
    501  */
    502 #define	CTOBSD(c)	((sess_bcsd_t *)c->cn_csd)
    503 #define	SNTOBC(s)	((sess_channel_t *)(((mds_session_t *)(s))->sn_back))
    504 
    505 #define	MAXSLOTS	1024			/* XXX - For now */
    506 
    507 typedef struct {
    508 	state_protect_how4	 sp_type;
    509 } rfs41_sprot_t;
    510 
    511 typedef struct {
    512 	uint_t			 dig_len;
    513 	char			*dig_val;
    514 } rfs41_digest_t;
    515 
    516 typedef enum {
    517 	SEQRES_INTERROR		= -1,   /* Internal Error */
    518 	SEQRES_NEWREQ		= 0,    /* New Request */
    519 	SEQRES_REPLAY		= 1,    /* Replay/Retransmission */
    520 	SEQRES_MISORD_NEWREQ	= 2,    /* Misordered New Request */
    521 	SEQRES_MISORD_REPLAY	= 3,    /* Misordered Replay/Retransmission */
    522 	SEQRES_BADSESSION	= 4	/* Bad sessionid provided */
    523 } slrc_stat_t;
    524 
    525 /*
    526  * trunk info entry
    527  */
    528 typedef struct rfs41_tie {
    529 	list_node_t	 t_link;
    530 	t_scalar_t	 t_xtype;	/* T_COTS_ORD or T_RDMA */
    531 	sa_family_t	 t_famly;	/* AF_INET or AF_INET6 */
    532 	struct netbuf	*t_netbf;	/* our copy of netbuf */
    533 	union {				/* shortcut to ip addr */
    534 		struct in_addr  ip4;
    535 		struct in6_addr ip6;
    536 	}		 t_ipaddr_u;
    537 } rfs41_tie_t;
    538 
    539 struct rfs4_deleg_state;
    540 #include <nfs/nfs_serv_inst.h>
    541 
    542 extern void rfs4_hold_deleg_policy(nfs_server_instance_t *);
    543 extern void rfs4_rele_deleg_policy(nfs_server_instance_t *);
    544 
    545 /* database, table, index creation entry points */
    546 extern rfs4_database_t *rfs4_database_create();
    547 extern void		rfs4_database_shutdown(rfs4_database_t *);
    548 extern void		rfs4_database_destroy(rfs4_database_t *);
    549 
    550 extern void		rfs4_database_destroy(rfs4_database_t *);
    551 
    552 extern rfs4_table_t	*rfs4_table_create(nfs_server_instance_t *,
    553 			    char *, time_t, uint32_t,
    554 			bool_t (*create)(rfs4_entry_t, void *),
    555 			void (*destroy)(rfs4_entry_t),
    556 			bool_t (*expiry)(rfs4_entry_t),
    557 			uint32_t, uint32_t, uint32_t, id_t);
    558 extern void		rfs4_table_destroy(rfs4_database_t *, rfs4_table_t *);
    559 extern rfs4_index_t	*rfs4_index_create(rfs4_table_t *, char *,
    560 			    uint32_t (*hash)(void *),
    561 			    bool_t (compare)(rfs4_entry_t, void *),
    562 			    void *(*mkkey)(rfs4_entry_t), bool_t);
    563 extern void		rfs4_index_destroy(rfs4_index_t *);
    564 
    565 /* Type used to direct rfs4_dbsearch() in what types of records to inspect */
    566 typedef enum {RFS4_DBS_VALID, RFS4_DBS_INVALID} rfs4_dbsearch_type_t;
    567 /* search and db entry manipulation entry points */
    568 extern rfs4_entry_t	rfs4_dbsearch(rfs4_index_t *, void *,
    569 				bool_t *, void *, rfs4_dbsearch_type_t);
    570 extern rfs4_entry_t	rfs4_dbcreate(rfs4_index_t *, void *);
    571 extern void		rfs4_dbe_lock(rfs4_dbe_t *);
    572 extern void		rfs4_dbe_unlock(rfs4_dbe_t *);
    573 extern clock_t		rfs4_dbe_twait(rfs4_dbe_t *, clock_t);
    574 extern void		rfs4_dbe_cv_broadcast(rfs4_dbe_t *);
    575 extern void		rfs4_dbe_hold(rfs4_dbe_t *);
    576 extern void		rfs4_dbe_hold_nolock(rfs4_dbe_t *);
    577 extern void		rfs4_dbe_rele_nolock(rfs4_dbe_t *);
    578 extern void		rfs4_dbe_rele(rfs4_dbe_t *);
    579 extern uint32_t	rfs4_dbe_refcnt(rfs4_dbe_t *);
    580 extern id_t		rfs4_dbe_getid(rfs4_dbe_t *);
    581 extern void		rfs4_dbe_invalidate(rfs4_dbe_t *);
    582 extern bool_t		rfs4_dbe_is_invalid(rfs4_dbe_t *);
    583 extern bool_t		rfs4_dbe_skip_or_invalid(rfs4_dbe_t *);
    584 extern time_t		rfs4_dbe_get_timerele(rfs4_dbe_t *);
    585 extern void		rfs4_dbe_hide(rfs4_dbe_t *);
    586 extern void		rfs4_dbe_unhide(rfs4_dbe_t *);
    587 #ifdef DEBUG
    588 extern bool_t		rfs4_dbe_islocked(rfs4_dbe_t *);
    589 #endif
    590 extern void		rfs4_dbe_walk(rfs4_table_t *,
    591 			void (*callout)(rfs4_entry_t, void *), void *);
    592 /*
    593  * The server maintains a set of state on a per client basis that
    594  * matches that of the protocol requirements.  A client's state is
    595  * rooted with the rfs4_client_t struct of which there is one per
    596  * client and is created when SETCLIENTID/SETCLIENTID_CONFIRM are
    597  * received.  From there, the server then creates rfs4_openowner_t
    598  * structs for each new open owner from that client and are initiated
    599  * at OPEN/OPEN_CONFIRM (when the open owner is new to the server).
    600  * At OPEN, at least two other structures are created, and potentially a
    601  * third.  rfs4_state_t is created to track the association between an
    602  * open owner and a particular file. An rfs4_file_t struct may be
    603  * created (if the file is not already open) at OPEN as well.  The
    604  * rfs4_file_t struct is the only one that is per server and not per
    605  * client.  The rfs4_deleg_state_t struct is created in the
    606  * instance that the server is going to provide a delegation for the
    607  * file being OPENed.  Finally, the rfs4_lockowner_t is created at the
    608  * first use of a lock owner at the server and is a result of the LOCK
    609  * operation.  The rfs4_lo_state_t struct is then created to represent
    610  * the relation between the lock owner and the file.
    611  *
    612  */
    613 /*
    614  * The following ascii art represents each of these data structs and
    615  * their references to each other.  Note: "<-(x)->" represents the
    616  * doubly link lists defined above.
    617  *
    618  *                          ____________________       ..................
    619  *                         |                    |      :                :
    620  *                         |    rfs4_client_t   |<-----: rfs4_session_t :
    621  *                       ->|         (1),(2)    |<-    :     NFSv4.1    :
    622  *                      /  |____________________|  \   :................:
    623  *                     /              ^             \
    624  *                    /               |              \
    625  *  ____________________    ____________________    ____________________
    626  * |                    |  |                    |  |                    |
    627  * |  rfs4_lockowner_t  |  |  rfs4_openowner_t  |  | rfs4_deleg_state_t |
    628  * |                    |  |     (3)    <-(1)-> |  |            <-(2)-> |
    629  * |____________________|  |____________________|  |____________________|
    630  *           ^                        ^                       |
    631  *           |                        |                       V
    632  *  ____________________    ____________________    ____________________
    633  * |                    |  |                    |  |                    |
    634  * |  rfs4_lo_state_t   |->|    rfs4_state_t    |->|     rfs4_file_t    |
    635  * |            <-(4)-> |  |     (4)    <-(3)-> |  |                    |
    636  * |____________________|  |____________________|  |____________________|
    637  */
    638 /*
    639  * Each of these data types are kept in a separate rfs4_table_t and is
    640  * actually encapsulated within a rfs4_dbe_t struct.  The various
    641  * tables and their construction is done in nfs4_state.c but
    642  * documented here to completeness.
    643  *
    644  * Table		Data struct stored	Indexed by
    645  * -----		------------------	----------
    646  * rfs4_client_tab	rfs4_client_t		nfs_client_id4
    647  *						clientid4
    648  *
    649  * rfs4_openowner_tab	rfs4_openowner_t	open_owner4
    650  *
    651  * rfs4_state_tab	rfs4_state_t		open_owner4 | file
    652  *						stateid
    653  *
    654  * rfs4_lo_state_tab	rfs4_lo_state_t		lockowner | stateid
    655  *						lock_stateid
    656  *
    657  * rfs4_lockowner_tab	rfs4_lockowner_t	lockowner
    658  *						pid
    659  *
    660  * rfs4_file_tab	rfs4_file_t		filehandle
    661  *
    662  * rfs4_deleg_state_tab	rfs4_deleg_state_t	clientid4 | file
    663  *						deleg_stateid
    664  */
    665 
    666 /*
    667  * The client struct, it is the root of all state for a particular
    668  * client.  The client is identified by the nfs_client_id4 via
    669  * SETCLIENTID and the server returns the clientid4 as short hand reference
    670  */
    671 /*
    672  * Client struct - as mentioned above it is the root of all state for
    673  * a single client as identified by the client supplied nfs_client_id4
    674  *
    675  * dbe - encapsulation struct
    676  * clientid - server assigned short hand reference to client
    677  * nfs_client - client supplied identifier for itself
    678  * confirm_verf - the value provided to the client for SETCLIENTID_CONFIRM
    679  * need_confirm - does this client need to be SETCLIENTID_CONFIRMed?
    680  *
    681  * unlksys_completed - has an F_UNLKSYS been done for this client which
    682  *		says that the use of cleanlocks() on individual files
    683  *		is not required?
    684  * can_reclaim - indicates if client is allowed to reclaim after server
    685  * 		start-up (client had previous state at server)
    686  * ss_remove - indicates that the rfs4_client_destroy function should
    687  * 		clean up stable storage file.
    688  * forced_expire - set if the sysadmin has used clear_locks for this client.
    689  * deleg_revoked - how many delegations have been revoked for this client?
    690  *
    691  * cp_confirmed - this refers to a confirmed client struct that has
    692  * the same nfs_client_id4 as this client struct.  When/if this client
    693  * struct is confirmed via SETCLINETID_CONFIRM, the previously
    694  * confirmed client struct will be "closed" and hence this reference.
    695  *
    696  * last_access - used to determine if the client has let its lease expire
    697  * cbinfo - struct containing all callback related information
    698  * cr_set - credentials used for the SETCLIENTID/SETCLIENTID_CONFIRM pair
    699  * sysid - the lock manager sysid allocated for this client's file locks
    700  * openownerlist - root of openowners list associated with this client
    701  * ss_pn - Pathname to the stable storage file.
    702  * cl_addr - Clients network address.
    703  * contrived -  NFSv4.1 create_session res
    704  * state_prot - NFSv4.1 state protection
    705  * clid_scope - NFSv4.1 scope of client id (DS, MDS or BOTH)
    706  * seq4 - NFSv4.1 sequence result bit accounting info (client scope)
    707  *	CB_PATH_DOWN, EXPIRED_ALL_STATE_REVOKED, EXPIRED_SOME_STATE_REVOKED,
    708  *	ADMIN_STATE_REVOKED, RECALLABLE_STATE_REVOKED, LEASE_MOVED,
    709  *	RESTART_RECLAIM_NEEDED, DEVID_CHANGED, DEVID_DELETED
    710  */
    711 typedef struct rfs4_client {
    712 	rfs4_dbe_t		*rc_dbe;
    713 	clientid4		rc_clientid;
    714 	nfs_client_id4		rc_nfs_client;
    715 	verifier4		rc_confirm_verf;
    716 	unsigned		rc_need_confirm:1;
    717 	unsigned		rc_unlksys_completed:1;
    718 	unsigned		rc_can_reclaim:1;
    719 	unsigned 		rc_ss_remove:1;
    720 	unsigned		rc_forced_expire:1;
    721 	unsigned		rc_reclaim_completed:1;
    722 	uint_t			rc_deleg_revoked;
    723 	struct rfs4_client	*rc_cp_confirmed;
    724 	time_t			rc_last_access;
    725 	rfs4_cbinfo_t		rc_cbinfo;
    726 	cred_princ_t		*rc_cr_set;
    727 	sysid_t			rc_sysidt;
    728 	list_t			rc_openownerlist;
    729 	rfs4_ss_pn_t		*rc_ss_pn;
    730 	struct sockaddr_storage rc_addr;
    731 	rfs41_csr_t		rc_contrived;
    732 	rfs41_sprot_t		rc_state_prot;
    733 	struct rfs41_grant_list	rc_clientgrantlist;
    734 	int			rc_bulk_recall;
    735 	int			rc_clid_scope;
    736 	bit_attr_t		rc_seq4[BITS_PER_WORD];
    737 	list_t			rc_trunkinfo;
    738 } rfs4_client_t;
    739 
    740 /*
    741  * The openowner contains the client supplied open_owner4 as well as
    742  * the matching sequence id and is used to track the client's usage of
    743  * the open_owner4.  Note that a reply is saved here as well for
    744  * processing of retransmissions.
    745  *
    746  * dbe - encapsulation struct
    747  * client - reference to rfs4_client_t for this openowner
    748  * owner - actual client supplied open_owner4
    749  * need_confirm - does this openowner need to be OPEN_CONFIRMed
    750  * postpone_confirm - set if error received on first use of open_owner
    751  * state2confirm - what stateid4 should be used on the OPEN_CONFIRM
    752  * open_seqid - what is the next open_seqid expected for this openowner
    753  * oo_sw - used to serialize access to the open seqid/reply handling
    754  * cr_set - credential used for the OPEN
    755  * statelist - root of state struct list associated with this openowner
    756  * node - node for client struct list of openowners
    757  * reply_fh - open replay processing needs the filehandle so that it is
    758  *	able to reset the current filehandle for appropriate compound
    759  *	processing and reply.
    760  * reply - last reply sent in relation to this openowner
    761  */
    762 typedef struct rfs4_openowner {
    763 	rfs4_dbe_t		*ro_dbe;
    764 	rfs4_client_t		*ro_client;
    765 	open_owner4		ro_owner;
    766 	unsigned		ro_need_confirm:1;
    767 	unsigned		ro_postpone_confirm:1;
    768 	seqid4			ro_open_seqid;
    769 	rfs4_state_wait_t	ro_sw;
    770 	cred_princ_t		*ro_cr_set;
    771 	list_t			ro_statelist;
    772 	list_node_t		ro_node;
    773 	nfs_fh4			ro_reply_fh;
    774 	nfs_resop4		ro_reply[1];
    775 } rfs4_openowner_t;
    776 
    777 /*
    778  * This state struct represents the association between an openowner
    779  * and a file that has been OPENed by that openowner.
    780  *
    781  * dbe - encapsulation struct
    782  * stateid - server provided stateid
    783  * owner - reference back to the openowner for this state
    784  * finfo - reference to the open file for this state
    785  * share_access - how did the openowner OPEN the file (access)
    786  * share_deny - how did the openowner OPEN the file (deny)
    787  * opened - has VOP_OPEN been done
    788  * closed - has this file been closed?
    789  * lostatelist - root of list of lo_state associated with this state/file
    790  * node - node for state struct list of states
    791  */
    792 typedef struct rfs4_state {
    793 	rfs4_dbe_t		*rs_dbe;
    794 	stateid_t		rs_stateid;
    795 	rfs4_openowner_t	*rs_owner;
    796 	struct rfs4_file	*rs_finfo;
    797 	uint32_t		rs_share_access;
    798 	uint32_t		rs_share_deny;
    799 	unsigned		rs_opened:1;
    800 	unsigned		rs_closed:1;
    801 	list_t			rs_lostatelist;
    802 	list_node_t		rs_node;
    803 } rfs4_state_t;
    804 
    805 /*
    806  * Lockowner - track the lockowner and its related info
    807  *
    808  * dbe - encapsulation struct
    809  * client - reference to the client
    810  * owner - lockowner supplied by the client
    811  * pid - local identifier used for file locking
    812  */
    813 typedef struct rfs4_lockowner {
    814 	rfs4_dbe_t		*rl_dbe;
    815 	rfs4_client_t		*rl_client;
    816 	lock_owner4		rl_owner;
    817 	pid_t			rl_pid;
    818 } rfs4_lockowner_t;
    819 
    820 /*
    821  * Lockowner_state associated with a state struct and lockowner
    822  *
    823  * dbe - encapsulation struct
    824  * state - reference back to state struct for open file
    825  * lockid - stateid for this lockowner/state
    826  * locker - reference to lockowner
    827  * seqid - sequence id for this lockowner/state
    828  * skip_seqid_check - used on initialization of struct
    829  * locks_cleaned - have all locks been released for this lockowner/file?
    830  * lock_completed - successful LOCK with lockowner/file?
    831  * ls_sw - used to serialize update seqid/reply/stateid handling
    832  * node - node for state struct list of lo_states
    833  * reply - last reply sent in relation to this lockowner/state
    834  */
    835 typedef struct rfs4_lo_state {
    836 	rfs4_dbe_t		*rls_dbe;
    837 	rfs4_state_t		*rls_state;
    838 	stateid_t		rls_lockid;
    839 	rfs4_lockowner_t	*rls_locker;
    840 	seqid4			rls_seqid;
    841 	unsigned		rls_skip_seqid_check:1;
    842 	unsigned		rls_locks_cleaned:1;
    843 	unsigned		rls_lock_completed:1;
    844 	rfs4_state_wait_t	rls_sw;
    845 	list_node_t		rls_node;
    846 	nfs_resop4		rls_reply;
    847 } rfs4_lo_state_t;
    848 
    849 /*
    850  * Delegation state - per client
    851  *
    852  * dbe - encapsulation struct
    853  * dtype - type of delegation (NONE, READ, WRITE)
    854  * delegid - stateid for this delegation
    855  * time_granted - time this delegation was assigned to client
    856  * time_recalled - time when the server started recall process
    857  * time_revoked - if revoked, time that the revoke occurred
    858  * finfo - reference to the file associated with this delegation
    859  * client - reference to client for which this delegation is associated
    860  * node - list of delegations for the file (WRITE == 1, READ == )
    861  */
    862 typedef struct rfs4_deleg_state {
    863 	rfs4_dbe_t		*rds_dbe;
    864 	open_delegation_type4	rds_dtype;
    865 	stateid_t		rds_delegid;
    866 	time_t			rds_time_granted;
    867 	time_t			rds_time_recalled;
    868 	time_t			rds_time_revoked;
    869 	struct rfs4_file	*rds_finfo;
    870 	rfs4_client_t		*rds_client;
    871 	list_node_t		rds_node;
    872 	rfs41_drs_info_t	rds_rs;			/* 4.1 only */
    873 } rfs4_deleg_state_t;
    874 
    875 
    876 /*
    877  * Delegation info associated with the file
    878  *
    879  * dtype - type of delegation for file (NONE, READ, WRITE)
    880  * time_returned - time that last delegation was returned for file
    881  * time_recalled - time that recall sequence started
    882  * time_lastgrant - time that last delegation was provided to a client
    883  * time_lastwrite - time of last write to use the delegation stateid
    884  * time_rm_delayed - time of last remove/rename which was DELAYed
    885  * rdgrants - how many read delegations have been provided for this file
    886  * wrgrants - how many write delegations provided (can only be one)
    887  * recall_count - how many recall threads are outstanding
    888  * recall_lock - lock to protect contents of this struct
    889  * recall_cv - condition var for the "parent" thread to wait upon
    890  * deleg_change_grant - value for change attribute at time of write grant
    891  * deleg_change - most recent value of change obtained from client
    892  * deleg_change_ts - time of last deleg_change update
    893  * ever_recalled - has this particular delegation ever been recalled?
    894  * hold_grant - file deletion is impending, don't grant a delegation
    895  * conflicted_client - clientid of the client that caused a CB_RECALL
    896  *	to occur. This is used for delegation policy (should a delegation
    897  *	be granted shortly after it has been returned?)
    898  */
    899 typedef struct rfs4_dinfo {
    900 	open_delegation_type4 rd_dtype;
    901 	time_t		rd_time_returned;
    902 	time_t		rd_time_recalled;
    903 	time_t		rd_time_lastgrant;
    904 	time_t		rd_time_lastwrite;
    905 	time_t		rd_time_rm_delayed;
    906 	uint32_t	rd_rdgrants;
    907 	uint32_t	rd_wrgrants;
    908 	int32_t		rd_recall_count;
    909 	kmutex_t	rd_recall_lock[1];
    910 	kcondvar_t	rd_recall_cv[1];
    911 	bool_t		rd_ever_recalled;
    912 	uint32_t	rd_hold_grant;
    913 	clientid4	rd_conflicted_client;
    914 } rfs4_dinfo_t;
    915 
    916 /*
    917  * File
    918  *
    919  * dbe - encapsulation struct
    920  * vp - vnode for the file that is open or has a delegation
    921  * filehandle - the filehandle generated by the server for this file
    922  * delegstatelist - root of delegation list for this file
    923  * dinfo - see struct definition above
    924  * share_deny - union of all deny modes on file
    925  * share_access - union of all access modes on file
    926  * access_read - count of read access
    927  * access_write - count of write access
    928  * deny_read - count of deny reads
    929  * deny_write - count of deny writes
    930  * file_rwlock - lock for serializing the removal of a file while
    931  *	the state structures are active within the server
    932  *
    933  * 	The only requirement for locking file_rwlock is that the
    934  * 	caller have a reference to the containing rfs4_file.  The dbe
    935  * 	lock may or may not be held for lock/unlock of file_rwlock.
    936  * 	As mentioned above, the file_rwlock is used for serialization
    937  * 	of file removal and more specifically reference to the held
    938  * 	vnode (e.g. vp).
    939  * flp  - File layout pointer..
    940  */
    941 struct mds_layout;
    942 
    943 typedef struct rfs4_file {
    944 	rfs4_dbe_t	*rf_dbe;
    945 	vnode_t		*rf_vp;
    946 	nfs_fh4		rf_filehandle;
    947 	list_t		rf_delegstatelist;
    948 	rfs4_dinfo_t	rf_dinfo[1];
    949 	uint32_t	rf_share_deny;
    950 	uint32_t	rf_share_access;
    951 	uint32_t	rf_access_read;
    952 	uint32_t	rf_access_write;
    953 	uint32_t	rf_deny_read;
    954 	uint32_t	rf_deny_write;
    955 	krwlock_t	rf_file_rwlock;
    956 	struct rfs41_grant_list rf_lo_grant_list;
    957 	struct mds_layout    *rf_mlo;
    958 } rfs4_file_t;
    959 
    960 /*
    961  * NFSv4.1 Sessions (cont'd)
    962  *
    963  *   mds_session_t             rfs4_client_t
    964  *   +-------------+           +--------------------+
    965  *   | sn_sessid   |           | clientid           |
    966  *   | sn_clnt *  -|---------->|    :               |
    967  *   | sn_fore     |           +--------------------+
    968  *   | sn_back     |
    969  *   | sn_replay* -|---------> +--------------------------------+
    970  *   |    .        |           | st_currw                       |
    971  *   |    :        |           | st_fslots                      |
    972  *   +-------------+           | st_sltab  (slot_ent_t)         |
    973  *                             |  +----------------------------+|
    974  *                             |  | status, slot, seqid, resp *||------><Res>
    975  *                             |  +----------------------------+|
    976  *                             |  | status, slot, seqid, resp *||
    977  *                             |  +----------------------------+|
    978  *                             |  | status, slot, seqid, resp *||
    979  *                             |  +----------------------------+|
    980  *			       | .				|
    981  *			       | : 				|
    982  *                             +--------------------------------+
    983  *                             stok_t
    984  */
    985 typedef struct {
    986 	nfsstat4		 cs_error;
    987 	rfs4_client_t		*cs_client;
    988 	struct svc_req		*cs_req;
    989 	CREATE_SESSION4args	 cs_aotw;
    990 } session41_create_t;
    991 
    992 /*
    993  * sn_seq4 - sequence result bit accounting info (session scope)
    994  *	CB_PATH_DOWN_SESSION, CB_GSS_CONTEXT_EXPIRING,
    995  *	CB_GSS_CONTEXT_EXPIRED, BACKCHANNEL_FAULT
    996  */
    997 typedef struct mds_session {
    998 	rfs4_dbe_t		*sn_dbe;
    999 	sessionid4		 sn_sessid;	/* session id */
   1000 	rfs4_client_t		*sn_clnt;	/* back ptr to client state */
   1001 	sess_channel_t		*sn_fore;	/* fore chan for this session */
   1002 	sess_channel_t		*sn_back;	/* back chan for this session */
   1003 	stok_t			*sn_replay;	/* slot replay cache */
   1004 	rfs41_digest_t		 sn_digest;	/* digest; for use in SSV op */
   1005 	time_t			 sn_laccess;	/* struct was last accessed */
   1006 	int			 sn_csflags;	/* create_session only flags */
   1007 	bool_t			 sn_bdrpc;
   1008 	uint32_t		 sn_flags;	/* SEQ4 status bits */
   1009 	struct	{
   1010 		uint32_t	pngcnt;		/* conn pings outstanding */
   1011 		uint32_t	paths;		/* callback paths verified */
   1012 		uint32_t	progno;		/* cb_program number */
   1013 		csa_sec_parms_t	secprms;	/* csa_sec_params */
   1014 		uint32_t	failed:1;	/* TRUE if no cb path avail */
   1015 		uint32_t	pnginprog:1;
   1016 		uint32_t	_reserved:30;
   1017 	} sn_bc;
   1018 	bit_attr_t		 sn_seq4[BITS_PER_WORD];
   1019 } mds_session_t;
   1020 
   1021 #define	SN_CB_CHAN_EST(x)	(((mds_session_t *)(x))->sn_back != NULL)
   1022 #define	SN_CB_CHAN_OK(x)	(((mds_session_t *)(x))->sn_bc.failed == 0)
   1023 #define	CLID_REC_CONFIRMED(cp)	((cp)->rc_need_confirm == FALSE)
   1024 
   1025 struct mds_lorec {
   1026 	mds_session_t		*lor_sess;
   1027 	layoutrecall_type4	 lor_type;
   1028 	fsid4			 lor_fsid;
   1029 	nfs4_fhandle_t		 lor_fh;
   1030 	stateid4		 lor_stid;
   1031 	vnode_t			*lor_vp;
   1032 	struct mds_layout_grant	*lor_lg;
   1033 };
   1034 typedef struct mds_lorec mds_lorec_t;
   1035 
   1036 
   1037 extern void	rfs4_reclaim_list_init(nfs_server_instance_t *, int);
   1038 extern void	rfs4_reclaim_list_destroy(nfs_server_instance_t *);
   1039 extern int	rfs4_clnt_in_grace(rfs4_client_t *);
   1040 extern int	rfs4_in_grace(nfs_server_instance_t *);
   1041 extern int	rfs4_grace_new(nfs_server_instance_t *);
   1042 extern void	rfs4_grace_start(nfs_server_instance_t *);
   1043 extern void	rfs4_grace_start_new(nfs_server_instance_t *);
   1044 extern void	rfs4_grace_reset_all(nfs_server_instance_t *);
   1045 extern void	rfs4_ss_oldclients(rfs4_reclaim_t *, char *, char *);
   1046 extern void	rfs4_dss_readstate(nfs_server_instance_t *, int, char **);
   1047 
   1048 extern void rfs4_disable_delegation(nfs_server_instance_t *);
   1049 extern void rfs4_enable_delegation(nfs_server_instance_t *);
   1050 
   1051 /*
   1052  * Request types for delegation. These correspond with
   1053  * open_delegation_type4 with the addition of a new value, DELEG_ANY,
   1054  * to reqequest any delegation.
   1055  */
   1056 typedef enum {
   1057 	DELEG_NONE = 0,		/* Corresponds to OPEN_DELEG_NONE */
   1058 	DELEG_READ = 1,		/* Corresponds to OPEN_DELEG_READ */
   1059 	DELEG_WRITE = 2,	/* Corresponds to OPEN_DELEG_WRITE */
   1060 	DELEG_ANY = -1		/* New value to request any delegation type */
   1061 } delegreq_t;
   1062 
   1063 #define	NFS4_DELEG4TYPE2REQTYPE(x) (delegreq_t)(x)
   1064 
   1065 /*
   1066  * Various interfaces to manipulate the state structures introduced
   1067  * above
   1068  */
   1069 extern	void		sstor_clean_state_exi(struct exportinfo *exi);
   1070 extern	void		rfs4_free_reply(nfs_resop4 *);
   1071 extern	void		rfs4_copy_reply(nfs_resop4 *, nfs_resop4 *);
   1072 
   1073 /* rfs4_client_t handling */
   1074 extern	rfs4_client_t	*findclient(nfs_server_instance_t *, nfs_client_id4 *,
   1075 					bool_t *, rfs4_client_t *);
   1076 extern	rfs4_client_t	*findclient_by_id(nfs_server_instance_t *, clientid4);
   1077 extern	rfs4_client_t	*rfs4_findclient_by_id(nfs_server_instance_t *,
   1078     clientid4, bool_t);
   1079 extern	void		rfs4_client_rele(rfs4_client_t *);
   1080 extern	void		rfs4_client_close(rfs4_client_t *);
   1081 extern	void		rfs4_client_state_remove(rfs4_client_t *);
   1082 extern	void		rfs4_client_scv_next(rfs4_client_t *);
   1083 extern	void		rfs4_update_lease(rfs4_client_t *);
   1084 extern	bool_t		rfs4_lease_expired(rfs4_client_t *);
   1085 extern	nfsstat4	rfs4_check_clientid(nfs_server_instance_t *,
   1086 			    clientid4 *);
   1087 extern	rfs4_client_t	*findclient(nfs_server_instance_t *, nfs_client_id4 *,
   1088 			    bool_t *, rfs4_client_t *);
   1089 extern	void		 rfs4_free_cred_princ(rfs4_client_t *);
   1090 extern	char		*kstrdup(const char *);
   1091 
   1092 /* mds_session_t */
   1093 extern	mds_session_t	*mds_findsession_by_id(nfs_server_instance_t *,
   1094 	    sessionid4);
   1095 extern	mds_session_t	*mds_findsession_by_clid(nfs_server_instance_t *,
   1096 	    clientid4);
   1097 extern	mds_session_t	*mds_createsession(nfs_server_instance_t *,
   1098 			    session41_create_t *);
   1099 extern	nfsstat4	 mds_destroysession(mds_session_t *);
   1100 extern	sess_channel_t	*rfs41_create_session_channel(channel_dir_from_server4);
   1101 extern	void		 rfs41_destroy_session_channel(mds_session_t *,
   1102 			    channel_dir_from_server4);
   1103 
   1104 extern	void		 rfs41_session_rele(mds_session_t *);
   1105 extern	void	rfs41_cb_chflush(mds_session_t *);
   1106 extern	CLIENT	*rfs41_cb_getch(mds_session_t *);
   1107 extern	void	rfs41_cb_freech(mds_session_t *, CLIENT *);
   1108 
   1109 /* rfs4_openowner_t handling */
   1110 extern	rfs4_openowner_t *rfs4_findopenowner(nfs_server_instance_t *,
   1111     open_owner4 *, bool_t *, seqid4);
   1112 extern	void		rfs4_update_open_sequence(rfs4_openowner_t *);
   1113 extern	void		rfs4_update_open_resp(rfs4_openowner_t *,
   1114 					nfs_resop4 *, nfs_fh4 *);
   1115 extern	void		rfs4_openowner_rele(rfs4_openowner_t *);
   1116 extern	void		rfs4_free_opens(rfs4_openowner_t *, bool_t, bool_t);
   1117 
   1118 /* rfs4_lockowner_t handling */
   1119 extern	rfs4_lockowner_t *findlockowner(nfs_server_instance_t *, lock_owner4 *,
   1120 			    bool_t *);
   1121 extern	rfs4_lockowner_t *findlockowner_by_pid(nfs_server_instance_t *, pid_t);
   1122 extern	void		rfs4_lockowner_rele(rfs4_lockowner_t *);
   1123 
   1124 /* rfs4_state_t handling */
   1125 extern	void		rfs4_state_rele(rfs4_state_t *);
   1126 extern	void		rfs4_state_close(rfs4_state_t *, bool_t,
   1127 					bool_t, cred_t *);
   1128 extern	void		rfs4_release_share_lock_state(rfs4_state_t *,
   1129 					cred_t *, bool_t);
   1130 extern	void		rfs4_close_all_state(rfs4_file_t *);
   1131 
   1132 /* rfs4_lo_state_t handling */
   1133 extern	rfs4_lo_state_t *findlo_state_by_owner(rfs4_lockowner_t *,
   1134 						rfs4_state_t *, bool_t *);
   1135 extern	rfs4_lo_state_t *rfs4_findlo_state_by_owner(nfs_server_instance_t *,
   1136 	rfs4_lockowner_t *, rfs4_state_t *, bool_t *);
   1137 extern	void		rfs4_lo_state_rele(rfs4_lo_state_t *, bool_t);
   1138 extern	void		rfs4_update_lock_sequence(rfs4_lo_state_t *);
   1139 extern	void		rfs4_update_lock_resp(rfs4_lo_state_t *,
   1140 					nfs_resop4 *);
   1141 
   1142 /* rfs4_file_t handling */
   1143 extern	rfs4_file_t	*rfs4_findfile(nfs_server_instance_t *,
   1144 			    vnode_t *, nfs_fh4 *, bool_t *);
   1145 extern	rfs4_file_t	*rfs4_findfile_withlock(nfs_server_instance_t *,
   1146 						vnode_t *, nfs_fh4 *,
   1147 						bool_t *);
   1148 extern	void		rfs4_file_rele(rfs4_file_t *);
   1149 extern	void		rfs4_file_rele_withunlock(rfs4_file_t *);
   1150 
   1151 /* General collection of "get state" functions */
   1152 extern	int		rfs4_check_stateid_seqid(rfs4_state_t *, stateid4 *);
   1153 extern	int		rfs4_check_lo_stateid_seqid(rfs4_lo_state_t *,
   1154 					stateid4 *);
   1155 extern	int		mds_check_stateid_seqid(rfs4_state_t *, stateid4 *);
   1156 
   1157 extern nfs_server_instance_t *dbe_to_instp(rfs4_dbe_t *);
   1158 
   1159 extern void nsi_walk(void (*)(nfs_server_instance_t *, void *), void *);
   1160 
   1161 /* return values for rfs4_check_stateid_seqid() */
   1162 #define	NFS4_CHECK_STATEID_OKAY	1
   1163 #define	NFS4_CHECK_STATEID_OLD	2
   1164 #define	NFS4_CHECK_STATEID_BAD	3
   1165 #define	NFS4_CHECK_STATEID_EXPIRED	4
   1166 #define	NFS4_CHECK_STATEID_REPLAY	5
   1167 #define	NFS4_CHECK_STATEID_CLOSED	6
   1168 #define	NFS4_CHECK_STATEID_UNCONFIRMED	7
   1169 
   1170 /* delay() time that server is willing to briefly wait for a delegreturn */
   1171 #define	NFS4_DELEGATION_CONFLICT_DELAY	(hz/10)
   1172 
   1173 /*
   1174  * Interfaces for handling of callback's client handle cache and
   1175  * callback interfaces themselves.
   1176  */
   1177 extern	void		rfs4_cbinfo_free(rfs4_cbinfo_t *);
   1178 extern	void		rfs4_client_setcb(rfs4_client_t *, cb_client4 *,
   1179 					uint32_t);
   1180 extern	void		rfs4_deleg_cb_check(rfs4_client_t *);
   1181 extern	nfsstat4	rfs4_vop_getattr(vnode_t *, vattr_t *, int, cred_t *);
   1182 
   1183 /* rfs4_deleg_state_t handling and other delegation interfaces */
   1184 extern	bool_t		rfs4_check_recall(rfs4_state_t *, uint32_t);
   1185 extern	void		rfs4_recall_deleg(rfs4_file_t *,
   1186 				bool_t, rfs4_client_t *);
   1187 extern	int		rfs4_get_deleg(rfs4_state_t *,  open_delegation_type4,
   1188 			open_delegation_type4 (*policy)(rfs4_state_t *,
   1189 				open_delegation_type4 dtype));
   1190 extern	void		rfs4_set_deleg_response(rfs4_deleg_state_t *,
   1191 				open_delegation4 *, nfsace4 *, int);
   1192 extern	void		rfs4_return_deleg(rfs4_deleg_state_t *, bool_t);
   1193 extern	bool_t		rfs4_is_deleg(rfs4_state_t *);
   1194 extern	void		rfs4_deleg_state_rele(rfs4_deleg_state_t *);
   1195 extern	bool_t		rfs4_check_delegated_byfp(nfs_server_instance_t *,
   1196 					int, rfs4_file_t *,
   1197 					bool_t, bool_t, bool_t, clientid4 *);
   1198 extern	void	rfs4_clear_dont_grant(nfs_server_instance_t *, rfs4_file_t *);
   1199 
   1200 /*
   1201  * nfs4 monitored operations.
   1202  */
   1203 extern int deleg_rd_open(femarg_t *, int, cred_t *, caller_context_t *);
   1204 extern int deleg_wr_open(femarg_t *, int, cred_t *, caller_context_t *);
   1205 extern int deleg_wr_read(femarg_t *, uio_t *, int, cred_t *,
   1206 	    caller_context_t *);
   1207 extern int deleg_rd_write(femarg_t *, uio_t *, int, cred_t *,
   1208 	    caller_context_t *);
   1209 extern int deleg_wr_write(femarg_t *, uio_t *, int, cred_t *,
   1210 	    caller_context_t *);
   1211 extern int deleg_rd_setattr(femarg_t *, vattr_t *, int, cred_t *,
   1212 		caller_context_t *);
   1213 extern int deleg_wr_setattr(femarg_t *, vattr_t *, int, cred_t *,
   1214 		caller_context_t *);
   1215 extern int deleg_rd_rwlock(femarg_t *, int, caller_context_t *);
   1216 extern int deleg_wr_rwlock(femarg_t *, int, caller_context_t *);
   1217 extern int deleg_rd_space(femarg_t *, int, flock64_t *, int, offset_t, cred_t *,
   1218 		caller_context_t *);
   1219 extern int deleg_wr_space(femarg_t *, int, flock64_t *, int, offset_t, cred_t *,
   1220 		caller_context_t *);
   1221 extern int deleg_rd_setsecattr(femarg_t *, vsecattr_t *, int, cred_t *,
   1222 		caller_context_t *);
   1223 extern int deleg_wr_setsecattr(femarg_t *, vsecattr_t *, int, cred_t *,
   1224 		caller_context_t *);
   1225 extern int deleg_rd_vnevent(femarg_t *, vnevent_t, vnode_t *, char *,
   1226 		caller_context_t *);
   1227 extern int deleg_wr_vnevent(femarg_t *, vnevent_t, vnode_t *, char *,
   1228 		caller_context_t *);
   1229 
   1230 extern void rfs4_mon_hold(void *);
   1231 extern void rfs4_mon_rele(void *);
   1232 
   1233 extern fem_t	*deleg_rdops;
   1234 extern fem_t	*deleg_wrops;
   1235 
   1236 extern	int	rfs4_share(rfs4_state_t *, uint32_t, uint32_t);
   1237 extern	int	rfs4_unshare(rfs4_state_t *);
   1238 extern	void	rfs4_set_deleg_policy(nfs_server_instance_t *,
   1239     srv_deleg_policy_t);
   1240 #ifdef DEBUG
   1241 #define	NFS4_DEBUG(var, args) if (var) cmn_err args
   1242 
   1243 extern int rfs4_debug;
   1244 extern int nfs4_client_attr_debug;
   1245 extern int nfs4_client_state_debug;
   1246 extern int nfs4_client_shadow_debug;
   1247 extern int nfs4_client_lock_debug;
   1248 extern int nfs4_client_lease_debug;
   1249 extern int nfs4_seqhb_debug;
   1250 extern int nfs4_seqid_sync;
   1251 extern int nfs4_client_map_debug;
   1252 extern int nfs4_client_inactive_debug;
   1253 extern int nfs4_client_recov_debug;
   1254 extern int nfs4_client_failover_debug;
   1255 extern int nfs4_client_call_debug;
   1256 extern int nfs4_client_foo_debug;
   1257 extern int nfs4_client_zone_debug;
   1258 extern int nfs4_lost_rqst_debug;
   1259 extern int nfs4_open_stream_debug;
   1260 extern int nfs4_client_open_dg;
   1261 extern int nfs4_srvmnt_debug;
   1262 extern int nfs4_utf8_debug;
   1263 
   1264 
   1265 #ifdef NFS4_DEBUG_MUTEX
   1266 void nfs4_debug_mutex_enter(kmutex_t *, char *, int);
   1267 void nfs4_debug_mutex_exit(kmutex_t *, char *, int);
   1268 
   1269 #define	mutex_enter(m) nfs4_debug_mutex_enter((m), __FILE__, __LINE__)
   1270 #define	mutex_exit(m) nfs4_debug_mutex_exit((m), __FILE__, __LINE__)
   1271 #endif /* NFS4_DEBUG_MUTEX */
   1272 
   1273 #else  /* ! DEBUG */
   1274 #define	NFS4_DEBUG(var, args)
   1275 #endif /* DEBUG */
   1276 
   1277 /*
   1278  * XXX - temporary for testing of volatile fh
   1279  */
   1280 
   1281 #ifdef VOLATILE_FH_TEST
   1282 
   1283 struct nfs_fh4_fmt {
   1284 	fhandle4_t	fh4_i;
   1285 	uint32_t	fh4_flag;
   1286 	uint32_t	fh4_volatile_id;
   1287 };
   1288 
   1289 #else /* VOLATILE_FH_TEST */
   1290 
   1291 struct nfs_fh4_fmt {
   1292 	fhandle4_t	fh4_i;
   1293 	uint32_t	fh4_flag;
   1294 };
   1295 
   1296 #endif /* VOLATILE_FH_TEST */
   1297 
   1298 #define	FH4_NAMEDATTR	1
   1299 #define	FH4_ATTRDIR	2
   1300 
   1301 #define	fh4_fsid	fh4_i.fhx_fsid
   1302 #define	fh4_len		fh4_i.fhx_len 	/* fid length */
   1303 #define	fh4_data	fh4_i.fhx_data 	/* fid bytes */
   1304 #define	fh4_xlen	fh4_i.fhx_xlen
   1305 #define	fh4_xdata	fh4_i.fhx_xdata
   1306 typedef struct nfs_fh4_fmt nfs_fh4_fmt_t;
   1307 
   1308 #define	FH4_TO_FMT4(fh4p) ((nfs_fh4_fmt_t *)(fh4p)->nfs_fh4_val)
   1309 #define	FH4_GET_FLAG(fh4p, flag) ((FH4_TO_FMT4(fh4p)->fh4_flag) & (flag))
   1310 #define	FH4_SET_FLAG(fh4p, flag) ((FH4_TO_FMT4(fh4p)->fh4_flag) |= (flag))
   1311 #define	FH4_CLR_FLAG(fh4p, flag) ((FH4_TO_FMT4(fh4p)->fh4_flag) &= ~(flag))
   1312 
   1313 #define	NFS_FH4_LEN	sizeof (nfs_fh4_fmt_t)
   1314 
   1315 /*
   1316  * Copy fields from external (fhandle_t) to in-memory (nfs_fh4_fmt_t)
   1317  * format to support export info checking.  It does not copy over
   1318  * the complete filehandle, just the fsid, xlen and xdata.  It may
   1319  * need to be changed to be used in other places.
   1320  *
   1321  * NOTE: The macro expects the space to be  pre-allocated for
   1322  * the contents of nfs_fh4_fmt_t.
   1323  */
   1324 #define	FH_TO_FMT4(exifh, nfs_fmt) {				\
   1325 	bzero((nfs_fmt), NFS_FH4_LEN);				\
   1326 	(nfs_fmt)->fh4_fsid = (exifh)->fh_fsid;			\
   1327 	(nfs_fmt)->fh4_xlen = (exifh)->fh_xlen;			\
   1328 	bcopy((exifh)->fh_xdata, (nfs_fmt)->fh4_xdata,		\
   1329 	    (exifh)->fh_xlen);					\
   1330 }
   1331 
   1332 /*
   1333  * A few definitions of repeatedly used constructs for nfsv4
   1334  */
   1335 #define	UTF8STRING_FREE(str)					\
   1336 	if ((str).utf8string_val != NULL) {			\
   1337 		kmem_free((str).utf8string_val,			\
   1338 		    (str).utf8string_len);			\
   1339 		(str).utf8string_val = NULL;			\
   1340 	}							\
   1341 	(str).utf8string_len = 0;
   1342 
   1343 #define	UTF8STRING_NULL(str)					\
   1344 	(str).utf8string_val == NULL
   1345 
   1346 /*
   1347  * NFS4_VOLATILE_FH yields non-zero if the filesystem uses non-persistent
   1348  * filehandles.
   1349  */
   1350 #define	NFS4_VOLATILE_FH(mi)					\
   1351 	((mi)->mi_fh_expire_type &				\
   1352 	(FH4_VOLATILE_ANY | FH4_VOL_MIGRATION | FH4_VOL_RENAME))
   1353 
   1354 /*
   1355  * NFS_IS_DOTNAME checks if the name given represents a dot or dotdot entry
   1356  */
   1357 #define	NFS_IS_DOTNAME(name)					\
   1358 	(((name)[0] == '.') &&					\
   1359 	(((name)[1] == '\0') || (((name)[1] == '.') && ((name)[2] == '\0'))))
   1360 
   1361 /*
   1362  * Define the number of bits in a bitmap word (uint32)
   1363  */
   1364 #define	NFS4_BITMAP4_BITSPERWORD	(sizeof (uint32_t) * 8)
   1365 
   1366 /*
   1367  * Define the value for the access field of the compound_state structure
   1368  * based on the result of nfsauth access checking.
   1369  */
   1370 #define	CS_ACCESS_OK		0x1
   1371 #define	CS_ACCESS_DENIED	0x2
   1372 #define	CS_ACCESS_LIMITED	0x4
   1373 
   1374 /*
   1375  * compound state in nfsv4 server
   1376  */
   1377 typedef struct compound_state {
   1378 	struct exportinfo *exi;
   1379 	struct exportinfo *saved_exi;	/* export struct for saved_vp */
   1380 	cred_t 		*basecr;	/* UNIX cred:  only RPC request */
   1381 	caddr_t 	principal;
   1382 	int 		nfsflavor;
   1383 	cred_t 		*cr;		/* UNIX cred: RPC request and */
   1384 					/* target export */
   1385 	bool_t		cont;
   1386 	uint_t 		access;		/* access perm on vp per request */
   1387 	bool_t 		deleg;		/* TRUE if current fh has */
   1388 					/* write delegated */
   1389 	nnode_t		*nn;
   1390 	vnode_t 	*vp;		/* modified by PUTFH, and by ops that */
   1391 					/* input to GETFH */
   1392 	bool_t 		mandlock;	/* Is mandatory locking in effect */
   1393 					/* for vp */
   1394 	vnode_t 	*saved_vp;	/* modified by SAVEFH, copied to */
   1395 					/* vp by RESTOREFH */
   1396 	nfsstat4 	*statusp;
   1397 	nfs_fh4 	fh;		/* ditto. valid only if vp != NULL */
   1398 	nfs_fh4 	saved_fh;	/* ditto. valid only if */
   1399 					/* 	saved_vp != NULL */
   1400 	struct svc_req	*req;
   1401 	char 		fhbuf[NFS4_FHSIZE];
   1402 
   1403 	/* additions for NFSv4.1 */
   1404 	slotid4		slotno;
   1405 	sequenceid4	seqid;
   1406 	int		sequenced;
   1407 	mds_session_t	*sp;
   1408 	rfs4_client_t   *cp;
   1409 	int		op_ndx;
   1410 	int 		op_len;
   1411 	nfs_server_instance_t *instp;
   1412 	int		sact;		/* sa_cachethis */
   1413 	size_t		rqst_sz;	/* request size */
   1414 	size_t		resp_sz;	/* response size */
   1415 	int		post_proc;
   1416 } compound_state_t;
   1417 
   1418 void rfs41_compound_free(COMPOUND4res *, compound_state_t *);
   1419 extern	void		rfs4_init_compound_state(struct compound_state *);
   1420 extern	compound_state_t *
   1421     rfs41_compound_state_alloc(nfs_server_instance_t *);
   1422 extern	void rfs41_compound_state_free(compound_state_t *);
   1423 extern	rfs4_state_t	*rfs4_findstate_by_owner_file(
   1424     struct compound_state *cs, rfs4_openowner_t *,
   1425     rfs4_file_t *, bool_t *);
   1426 
   1427 extern	nfsstat4	rfs4_get_state(struct compound_state *, stateid4 *,
   1428     rfs4_state_t **, rfs4_dbsearch_type_t);
   1429 
   1430 extern	nfsstat4	check_stateid(int, struct compound_state *,
   1431     vnode_t *, stateid4 *, bool_t, bool_t *,
   1432     bool_t, caller_context_t *, clientid4 *);
   1433 
   1434 extern	nfsstat4 rfs4_get_deleg_state(struct compound_state *, stateid4 *,
   1435     rfs4_deleg_state_t **);
   1436 
   1437 extern	nfsstat4	rfs4_get_lo_state(struct compound_state *, stateid4 *,
   1438     rfs4_lo_state_t **, bool_t);
   1439 
   1440 extern	rfs4_deleg_state_t *rfs4_finddeleg(struct compound_state *,
   1441     rfs4_state_t *, bool_t *);
   1442 extern	rfs4_deleg_state_t *rfs4_finddelegstate(struct compound_state *,
   1443     stateid_t *);
   1444 extern	rfs4_deleg_state_t *rfs4_grant_delegation(struct compound_state *,
   1445     delegreq_t, rfs4_state_t *, int *);
   1446 
   1447 /*
   1448  * Operation Dispatch Table flags.
   1449  */
   1450 typedef enum {
   1451 	DISP_OP_BAD,
   1452 	DISP_OP_MDS,
   1453 	DISP_OP_DS,
   1454 	DISP_OP_BOTH
   1455 } op_disp_valid_t;
   1456 
   1457 typedef struct {
   1458 	void    (*dis_op)(nfs_argop4 *, nfs_resop4 *, struct svc_req *,
   1459 	    compound_state_t *);
   1460 	void    (*dis_resfree)(nfs_resop4 *, compound_state_t *);
   1461 	op_disp_valid_t	op_flag;
   1462 	char    *op_name;
   1463 } op_disp_tbl_t;
   1464 
   1465 /*
   1466  * Conversion commands for nfsv4 server attr checking
   1467  */
   1468 enum nfs4_attr_cmd {
   1469 	NFS4ATTR_SUPPORTED = 0,		/* check which attrs supported */
   1470 	NFS4ATTR_GETIT = 1,		/* getattr - sys to fattr4 (r) */
   1471 	NFS4ATTR_SETIT = 2,		/* setattr - fattr4 to sys (w) */
   1472 	NFS4ATTR_VERIT = 3,		/* verify - fattr4 to sys (r) */
   1473 	NFS4ATTR_FREEIT = 4		/* free any alloc'd space for attr */
   1474 };
   1475 
   1476 typedef enum nfs4_attr_cmd nfs4_attr_cmd_t;
   1477 
   1478 struct nfs4_svgetit_arg {
   1479 	nfs4_attr_cmd_t op;		/* getit or setit */
   1480 	struct compound_state *cs;
   1481 	struct statvfs64 *sbp;
   1482 	uint_t 		flag;		/* VOP_GETATTR/VOP_SETATTR flag */
   1483 	uint_t 		xattr;		/* object is xattr */
   1484 	bool_t 		rdattr_error_req; /* if readdir & client wants */
   1485 						/* rdattr_error */
   1486 	nfsstat4	rdattr_error;	/* used for per-entry status */
   1487 					/* (if rdattr_err) */
   1488 	bool_t		mntdfid_set;
   1489 	fattr4_mounted_on_fileid
   1490 			mounted_on_fileid;
   1491 					/* readdir op can always return	*/
   1492 					/* d_ino from server fs dirent  */
   1493 					/* for mounted_on_fileid attr.	*/
   1494 					/* This field holds d_ino so	*/
   1495 					/* srv attr conv code can avoid */
   1496 					/* doing an untraverse.		*/
   1497 	file_layouthint4
   1498 			file_layouthint;
   1499 	vattr_t		vap[1];
   1500 };
   1501 
   1502 struct nfs4_ntov_map {
   1503 	attrmap4	fbit; 		/* FATTR4_XXX_MASKY */
   1504 	uint_t 		vbit; 		/* AT_XXX */
   1505 	bool_t 		vfsstat;
   1506 	bool_t 		mandatory; 	/* attribute mandatory to implement? */
   1507 	uint_t 		nval;
   1508 	int		xdr_size;	/* Size of XDR'd attr */
   1509 	xdrproc_t 	xfunc;
   1510 	int (*sv_getit)(nfs4_attr_cmd_t, struct nfs4_svgetit_arg *,
   1511 		union nfs4_attr_u *);	/* subroutine for getting attr. */
   1512 	char 		*prtstr;	/* string attr for printing */
   1513 };
   1514 
   1515 struct nfs4attr_to_vattr {
   1516 	vnode_t 	*vp;
   1517 	vattr_t 	*vap;
   1518 	nfs_fh4   	*fhp;
   1519 	nfsstat4	rdattr_error;
   1520 	uint32_t	flag;
   1521 	fattr4_change	change;
   1522 	fattr4_fsid	srv_fsid;
   1523 	fattr4_mounted_on_fileid	mntd_fid;
   1524 };
   1525 
   1526 typedef struct nfs4attr_to_vattr ntov4_t;
   1527 
   1528 /*
   1529  * nfs4attr_to_vattr flags
   1530  */
   1531 #define	NTOV_FHP_VALID			0x01
   1532 #define	NTOV_RDATTR_ERROR_VALID		0x02
   1533 #define	NTOV_CHANGE_VALID		0x04
   1534 #define	NTOV_SUPP_VALID			0x08
   1535 #define	NTOV_SRV_FSID_VALID		0x10
   1536 #define	NTOV_MOUNTED_ON_FILEID_VALID	0x20
   1537 
   1538 
   1539 
   1540 struct nfs4attr_to_osattr {
   1541 	void *attrconv_arg;
   1542 	uint_t mask;
   1543 };
   1544 
   1545 struct mntinfo4;
   1546 
   1547 /*
   1548  * lkp4_attr_setup lists the different options for attributes when calling
   1549  * nfs4lookup_setup - either no attributes (just lookups - e.g., secinfo),
   1550  * one component only (normal component lookup), get attributes for the
   1551  * last component (e.g., mount), attributes for each component (e.g.,
   1552  * failovers later), just the filehandle for the last component (e.g.,
   1553  * volatile filehandle recovery), or stuff that needs OPENATTR (e.g.
   1554  * looking up a named attribute or it's hidden directory).
   1555  */
   1556 typedef enum lkp4_attr_setup {
   1557 	LKP4_NO_ATTRIBUTES = 0,		/* no attrs or filehandles */
   1558 	LKP4_ALL_ATTRIBUTES = 3,	/* multi-comp: attrs for all comps */
   1559 	LKP4_LAST_NAMED_ATTR = 5,	/* multi-comp: named attr & attrdir */
   1560 	LKP4_LAST_ATTRDIR = 6,		/* multi-comp: just attrdir */
   1561 	LKP4_ALL_ATTR_SECINFO = 7	/* multi-comp: attrs for all comp and */
   1562 					/*	secinfo for last comp */
   1563 } lkp4_attr_setup_t;
   1564 
   1565 #define	NFS4_FATTR4_FINISH	-1	/* fattr4 index indicating finish */
   1566 
   1567 typedef int (*nfs4attr_to_os_t)(int, union nfs4_attr_u *,
   1568 		struct nfs4attr_to_osattr *);
   1569 
   1570 /*
   1571  * The nfs4_error_t is the basic structure to return error values
   1572  * from rfs4call.  It encapsulates the unix errno
   1573  * value, the nfsstat4 value and the rpc status value into a single
   1574  * structure.
   1575  *
   1576  * If error is set, then stat is ignored and rpc_status may be
   1577  * set if the error occurred as the result of a CLNT_CALL.  If
   1578  * stat is set, then rpc request succeeded, error and
   1579  * rpc_status are set to 0 and stat contains the result of
   1580  * operation, NFS4_OK or one of the NFS4ERR_* values.
   1581  *
   1582  * Functions which want to generate errors independently from
   1583  * rfs4call should set error to the desired errno value and
   1584  * set stat and rpc_status to 0.  nfs4_error_init() is a
   1585  * convenient function to do this.
   1586  */
   1587 typedef struct {
   1588 	int		error;
   1589 	nfsstat4	stat;
   1590 	enum clnt_stat	rpc_status;
   1591 } nfs4_error_t;
   1592 
   1593 /*
   1594  * Shared functions
   1595  */
   1596 extern void	rfs4_op_getattr_free(nfs_resop4 *);
   1597 extern void	rfs4_op_getfh_free(nfs_resop4 *);
   1598 extern void	lock_denied_free(nfs_resop4 *);
   1599 extern void	rfs4_op_read_free(nfs_resop4 *);
   1600 extern void	rfs4_op_readdir_free(nfs_resop4 *);
   1601 extern void	rfs4_op_readlink_free(nfs_resop4 *);
   1602 extern void	rfs4_op_secinfo_free(nfs_resop4 *);
   1603 extern void	rfs4_free_reply(nfs_resop4 *);
   1604 extern void	rfs4_op_readdir(nfs_argop4 *, nfs_resop4 *,
   1605 			struct svc_req *, struct compound_state *);
   1606 extern void	nfs_fh4_copy(nfs_fh4 *, nfs_fh4 *);
   1607 extern void	nfs4_fattr4_free(fattr4 *);
   1608 extern void	nfs4_getattr_otw_norecovery(vnode_t *,
   1609 			nfs4_ga_res_t *, nfs4_error_t *, cred_t *, int);
   1610 extern int	nfs4_getattr_otw(vnode_t *, nfs4_ga_res_t *, cred_t *, int);
   1611 extern int	nfs4cmpfh(const nfs_fh4 *, const nfs_fh4 *);
   1612 extern int	nfs4cmpfhandle(nfs4_fhandle_t *, nfs4_fhandle_t *);
   1613 extern int	nfs4getattr(vnode_t *, struct vattr *, cred_t *);
   1614 extern int	nfs4_waitfor_purge_complete(vnode_t *);
   1615 extern int	nfs4_validate_caches(vnode_t *, cred_t *);
   1616 extern int	nfs4init(int, char *);
   1617 extern void	nfs4fini(void);
   1618 extern int	nfs4_vfsinit(void);
   1619 extern void	nfs4_vfsfini(void);
   1620 
   1621 extern void	nfs4_vnops_init(void);
   1622 extern void	nfs4_vnops_fini(void);
   1623 extern void	nfs_idmap_init(void);
   1624 extern void	nfs_idmap_flush(int);
   1625 extern void	nfs_idmap_fini(void);
   1626 extern int	nfs4_rnode_init(void);
   1627 extern int	nfs4_rnode_fini(void);
   1628 extern int	nfs4_shadow_init(void);
   1629 extern int	nfs4_shadow_fini(void);
   1630 extern int	nfs4_acache_init(void);
   1631 extern int	nfs4_acache_fini(void);
   1632 extern int	nfs4_subr_init(void);
   1633 extern int	nfs4_subr_fini(void);
   1634 extern void	nfs4_acl_init(void);
   1635 extern void	nfs4_acl_free_cache(vsecattr_t *);
   1636 extern void	nfs4_pnfs_init(void);
   1637 extern void	nfs4_pnfs_fini(void);
   1638 extern void	nfs4_pnfs_init_mi(struct mntinfo4 *);
   1639 extern void	nfs4_pnfs_fini_mi(struct mntinfo4 *);
   1640 
   1641 extern int	geterrno4(nfsstat4);
   1642 extern nfsstat4	puterrno4(int);
   1643 extern int	nfs4_need_to_bump_seqid(COMPOUND4res_clnt *);
   1644 extern int	nfs4tsize(void);
   1645 extern int	checkauth4(struct compound_state *, struct svc_req *);
   1646 extern nfsstat4 call_checkauth4(struct compound_state *, struct svc_req *);
   1647 extern int	is_exported_sec(int, struct exportinfo *);
   1648 extern void	nfs4_vmask_to_nmask(uint_t, attrmap4 *, int);
   1649 extern void	nfs4_vmask_to_nmask_set(uint_t, attrmap4 *);
   1650 extern int	nfs_idmap_str_uid(utf8string *u8s, uid_t *, bool_t);
   1651 extern int	nfs_idmap_str_gid(utf8string *u8s, gid_t *, bool_t);
   1652 extern int	nfs_idmap_uid_str(uid_t, utf8string *u8s, bool_t);
   1653 extern int	nfs_idmap_gid_str(gid_t gid, utf8string *u8s, bool_t);
   1654 extern int	nfs4_time_ntov(nfstime4 *, timestruc_t *);
   1655 extern int	nfs4_time_vton(timestruc_t *, nfstime4 *);
   1656 extern char	*utf8_to_str(utf8string *, uint_t *, char *);
   1657 extern char	*utf8_to_fn(utf8string *, uint_t *, char *);
   1658 extern utf8string *str_to_utf8(char *, utf8string *);
   1659 extern utf8string *utf8_copy(utf8string *, utf8string *);
   1660 extern int	utf8_compare(const utf8string *, const utf8string *);
   1661 extern int	utf8_dir_verify(utf8string *);
   1662 extern char	*utf8_strchr(utf8string *, const char);
   1663 extern int	ln_ace4_cmp(nfsace4 *, nfsace4 *, int);
   1664 extern int	vs_aent_to_ace4(vsecattr_t *, vsecattr_t *, int, int);
   1665 extern int	vs_ace4_to_aent(vsecattr_t *, vsecattr_t *, uid_t, gid_t,
   1666     int, int, int);
   1667 extern int	vs_ace4_to_acet(vsecattr_t *, vsecattr_t *, uid_t, gid_t,
   1668     int, int);
   1669 extern int	vs_acet_to_ace4(vsecattr_t *, vsecattr_t *, int);
   1670 extern void	vs_acet_destroy(vsecattr_t *);
   1671 extern void	vs_ace4_destroy(vsecattr_t *);
   1672 extern void	vs_aent_destroy(vsecattr_t *);
   1673 struct rnode4;
   1674 extern void	pnfs_getdevicelist(struct mntinfo4 *, cred_t *);
   1675 
   1676 extern void	pnfs_layout_set(struct mntinfo4 *, struct rnode4 *);
   1677 #define	LR_ASYNC	0
   1678 #define	LR_SYNC		1
   1679 
   1680 extern void	layoutreturn_all(struct vfs *, cred_t *);
   1681 extern int	pnfs_read(vnode_t *, caddr_t, offset_t, int, size_t *,
   1682     cred_t *, bool_t, struct uio *);
   1683 extern int	pnfs_write(vnode_t *, caddr_t, u_offset_t, int,
   1684     cred_t *, stable_how4 *);
   1685 extern int	pnfs_commit(vnode_t *, page_t *, offset4, count4, cred_t *);
   1686 extern stateid4 pnfs_get_losid(struct rnode4 *);
   1687 
   1688 extern int	stateid4_cmp(stateid4 *, stateid4 *);
   1689 
   1690 extern vtype_t	nf4_to_vt[];
   1691 
   1692 extern struct nfs4_ntov_map nfs40_ntov_map[];
   1693 extern struct nfs4_ntov_map nfs41_ntov_map[];
   1694 
   1695 extern kstat_named_t	*rfsproccnt_v4_ptr;
   1696 
   1697 extern struct vfsops	*nfs4_vfsops;
   1698 extern struct vnodeops	*nfs4_vnodeops;
   1699 extern const struct	fs_operation_def nfs4_vnodeops_template[];
   1700 extern vnodeops_t	*nfs4_trigger_vnodeops;
   1701 extern const struct	fs_operation_def nfs4_trigger_vnodeops_template[];
   1702 
   1703 extern uint_t nfs4_tsize(struct knetconfig *);
   1704 extern uint_t rfs4_tsize(struct svc_req *);
   1705 
   1706 extern bool_t	xdr_inline_decode_nfs_fh4(uint32_t *, nfs_fh4_fmt_t *,
   1707 			uint32_t);
   1708 extern bool_t	xdr_inline_encode_nfs_fh4(uint32_t **, uint32_t *,
   1709 			nfs_fh4_fmt_t *);
   1710 
   1711 extern void		 rfs41_deleg_rs_hold(rfs4_deleg_state_t *);
   1712 extern void		 rfs41_deleg_rs_rele(rfs4_deleg_state_t *);
   1713 extern void		 rfs41_set_client_sessions(rfs4_client_t *, uint32_t);
   1714 extern void		 rfs41_cb_path_down(mds_session_t *, uint32_t);
   1715 
   1716 
   1717 void rfs41_srvrinit(void);
   1718 void rfs41_dispatch_init(void);
   1719 
   1720 /* NFSv4.1: slot support */
   1721 extern void		 sltab_create(stok_t **, int);
   1722 extern int		 sltab_resize(stok_t *, int);
   1723 extern void		 sltab_query(stok_t *, slt_query_t, void *);
   1724 extern void		 sltab_destroy(stok_t *);
   1725 extern int		 slot_alloc(stok_t *, slt_wait_t, slot_ent_t **);
   1726 extern void		 slot_free(stok_t *, slot_ent_t *);
   1727 extern int		 slot_mark(stok_t *, slotid4, sequenceid4);
   1728 extern void		 slot_set_state(slot_ent_t *, int);
   1729 extern void		 slot_error_to_inuse(slot_ent_t *);
   1730 extern nfsstat4		 slot_cb_status(stok_t *);
   1731 extern slotid4		 svc_slot_maxslot(mds_session_t *);
   1732 extern slot_ent_t	*svc_slot_alloc(mds_session_t *);
   1733 extern void		 svc_slot_free(mds_session_t *, slot_ent_t *);
   1734 extern void		 svc_slot_cb_seqid(CB_COMPOUND4res *, slot_ent_t *);
   1735 
   1736 #ifdef DEBUG
   1737 extern int		rfs4_do_pre_op_attr;
   1738 extern int		rfs4_do_post_op_attr;
   1739 #endif
   1740 
   1741 extern stateid4 clnt_special0;
   1742 extern stateid4 clnt_special1;
   1743 #define	CLNT_ISSPECIAL(id) (stateid4_cmp(id, &clnt_special0) || \
   1744 				stateid4_cmp(id, &clnt_special1))
   1745 
   1746 /*
   1747  * The NFS Version 4 service procedures.
   1748  */
   1749 
   1750 extern void	rfs4_compound(COMPOUND4args *, COMPOUND4res *,
   1751 		    struct exportinfo *, struct svc_req *, int *);
   1752 extern void	rfs4_compound_free(COMPOUND4res *);
   1753 extern void	rfs4_compound_flagproc(COMPOUND4args *, int *);
   1754 
   1755 extern int	rfs4_srvrinit(void);
   1756 extern void	rfs4_srvrfini(nfs_server_instance_t *);
   1757 extern void	rfs4_sstor_init(nfs_server_instance_t *);
   1758 extern void	mds_sstor_init(nfs_server_instance_t *);
   1759 extern void	mds_compound_free(COMPOUND4res *);
   1760 extern void	rfs4_state_fini(nfs_server_instance_t *);
   1761 
   1762 struct nfs4_fsidlt;
   1763 struct nfs4_server;
   1764 
   1765 extern void   pnfs_layoutreturn_bulk(struct mntinfo4 *, cred_t *, int,
   1766     struct nfs4_server *, struct nfs4_fsidlt *);
   1767 
   1768 extern void	pnfs_trash_devtree(struct nfs4_server *);
   1769 
   1770 struct notify_deviceid_change4;
   1771 struct notify_deviceid_delete4;
   1772 extern nfsstat4	pnfs_change_device(struct nfs4_server *,
   1773     struct notify_deviceid_change4 *);
   1774 extern nfsstat4	pnfs_delete_device(struct nfs4_server *,
   1775     struct notify_deviceid_delete4 *);
   1776 
   1777 extern void	 rfs41_lo_seqid(stateid_t *);
   1778 extern void	 rfs4freeargres(CB_COMPOUND4args *, CB_COMPOUND4res *);
   1779 extern char	*nfs41_strerror(nfsstat4);
   1780 extern char	*nfs4_op_to_str(nfs_opnum4);
   1781 extern void	 mds_clean_up_sessions(rfs4_client_t *);
   1782 extern void	 mds_clean_up_grants(rfs4_client_t *);
   1783 extern void	 mds_clean_up_trunkinfo(rfs4_client_t *);
   1784 extern char	*tohex(const void *, int);
   1785 extern nfsstat4	 sess_chan_limits(sess_channel_t *);
   1786 
   1787 /*
   1788  * NFS4.1 Slot replay cache.
   1789  */
   1790 void	slrc_table_create(stok_t **, int);
   1791 void	slot_table_create(stok_t **, int);
   1792 uint_t	slrc_slot_alloc(stok_t *, slotid4, sequenceid4, slot_ent_t **);
   1793 void	slot_incr_seq(slot_ent_t *, int);
   1794 void	slrc_table_destroy(stok_t *);
   1795 void	slot_table_destroy(stok_t *);
   1796 void	slrc_table_query(stok_t *, slt_query_t, void *);
   1797 void	slot_table_query(stok_t *, slt_query_t, void *);
   1798 slot_ent_t	*slot_get(stok_t *, slotid4);
   1799 slot_ent_t	*slrc_slot_get(stok_t *, slotid4);
   1800 
   1801 /*
   1802  * Internal helper routines.
   1803  */
   1804 int slot_delete(stok_t *handle, slot_ent_t *node);
   1805 #endif
   1806 #ifdef	__cplusplus
   1807 }
   1808 #endif
   1809 
   1810 #endif /* _NFS4_H */
   1811