Print this page
Fix NFS design problems re. multiple zone keys
Make NFS server zone-specific data all have the same lifetime
Fix rfs4_clean_state_exi
Fix exi_cache_reclaim
Fix mistakes in zone keys work
More fixes re. exi_zoneid and exi_tree
(danmcd -> Keep some ASSERT()s around for readability.)

*** 1131,1141 **** */ void rfs4_clear_client_state(struct nfs4clrst_args *clr) { nfs4_srv_t *nsrv4; ! nsrv4 = zone_getspecific(rfs4_zone_key, curzone); (void) rfs4_dbe_walk(nsrv4->rfs4_client_tab, rfs4_client_scrub, clr); } /* * Used to initialize the NFSv4 server's state or database. All of --- 1131,1141 ---- */ void rfs4_clear_client_state(struct nfs4clrst_args *clr) { nfs4_srv_t *nsrv4; ! nsrv4 = nfs4_get_srv(); (void) rfs4_dbe_walk(nsrv4->rfs4_client_tab, rfs4_client_scrub, clr); } /* * Used to initialize the NFSv4 server's state or database. All of
*** 1490,1500 **** void rfs4_state_zone_fini() { rfs4_database_t *dbp; nfs4_srv_t *nsrv4; ! nsrv4 = zone_getspecific(rfs4_zone_key, curzone); rfs4_set_deleg_policy(nsrv4, SRV_NEVER_DELEGATE); /* * Clean up any dangling stable storage structures BEFORE calling --- 1490,1500 ---- void rfs4_state_zone_fini() { rfs4_database_t *dbp; nfs4_srv_t *nsrv4; ! nsrv4 = nfs4_get_srv(); rfs4_set_deleg_policy(nsrv4, SRV_NEVER_DELEGATE); /* * Clean up any dangling stable storage structures BEFORE calling
*** 1666,1676 **** * since the state files are written to all DSS * paths we must remove this leaf file instance * from all server instances. */ ! nsrv4 = zone_getspecific(rfs4_zone_key, curzone); mutex_enter(&nsrv4->servinst_lock); for (sip = nsrv4->nfs4_cur_servinst; sip != NULL; sip = sip->prev) { /* remove the leaf file associated with this server instance */ rfs4_dss_remove_leaf(sip, NFS4_DSS_STATE_LEAF, leaf); } --- 1666,1676 ---- * since the state files are written to all DSS * paths we must remove this leaf file instance * from all server instances. */ ! nsrv4 = nfs4_get_srv(); mutex_enter(&nsrv4->servinst_lock); for (sip = nsrv4->nfs4_cur_servinst; sip != NULL; sip = sip->prev) { /* remove the leaf file associated with this server instance */ rfs4_dss_remove_leaf(sip, NFS4_DSS_STATE_LEAF, leaf); }
*** 1742,1752 **** struct sockaddr *ca; cid *cidp; scid_confirm_verf *scvp; nfs4_srv_t *nsrv4; ! nsrv4 = zone_getspecific(rfs4_zone_key, curzone); /* Get a clientid to give to the client */ cidp = (cid *)&cp->rc_clientid; cidp->impl_id.start_time = nsrv4->rfs4_start_time; cidp->impl_id.c_id = (uint32_t)rfs4_dbe_getid(cp->rc_dbe); --- 1742,1752 ---- struct sockaddr *ca; cid *cidp; scid_confirm_verf *scvp; nfs4_srv_t *nsrv4; ! nsrv4 = nfs4_get_srv(); /* Get a clientid to give to the client */ cidp = (cid *)&cp->rc_clientid; cidp->impl_id.start_time = nsrv4->rfs4_start_time; cidp->impl_id.c_id = (uint32_t)rfs4_dbe_getid(cp->rc_dbe);
*** 1836,1846 **** rfs4_client_t * rfs4_findclient(nfs_client_id4 *client, bool_t *create, rfs4_client_t *oldcp) { rfs4_client_t *cp; nfs4_srv_t *nsrv4; ! nsrv4 = zone_getspecific(rfs4_zone_key, curzone); if (oldcp) { rw_enter(&nsrv4->rfs4_findclient_lock, RW_WRITER); rfs4_dbe_hide(oldcp->rc_dbe); --- 1836,1846 ---- rfs4_client_t * rfs4_findclient(nfs_client_id4 *client, bool_t *create, rfs4_client_t *oldcp) { rfs4_client_t *cp; nfs4_srv_t *nsrv4; ! nsrv4 = nfs4_get_srv(); if (oldcp) { rw_enter(&nsrv4->rfs4_findclient_lock, RW_WRITER); rfs4_dbe_hide(oldcp->rc_dbe);
*** 1863,1873 **** rfs4_findclient_by_id(clientid4 clientid, bool_t find_unconfirmed) { rfs4_client_t *cp; bool_t create = FALSE; cid *cidp = (cid *)&clientid; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); /* If we're a cluster and the nodeid isn't right, short-circuit */ if (cluster_bootflags & CLUSTER_BOOTED && foreign_clientid(cidp)) return (NULL); --- 1863,1873 ---- rfs4_findclient_by_id(clientid4 clientid, bool_t find_unconfirmed) { rfs4_client_t *cp; bool_t create = FALSE; cid *cidp = (cid *)&clientid; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); /* If we're a cluster and the nodeid isn't right, short-circuit */ if (cluster_bootflags & CLUSTER_BOOTED && foreign_clientid(cidp)) return (NULL);
*** 1984,1994 **** rfs4_find_clntip(struct sockaddr *addr, bool_t *create) { rfs4_clntip_t *cp; nfs4_srv_t *nsrv4; ! nsrv4 = zone_getspecific(rfs4_zone_key, curzone); rw_enter(&nsrv4->rfs4_findclient_lock, RW_READER); cp = (rfs4_clntip_t *)rfs4_dbsearch(nsrv4->rfs4_clntip_idx, addr, create, addr, RFS4_DBS_VALID); --- 1984,1994 ---- rfs4_find_clntip(struct sockaddr *addr, bool_t *create) { rfs4_clntip_t *cp; nfs4_srv_t *nsrv4; ! nsrv4 = nfs4_get_srv(); rw_enter(&nsrv4->rfs4_findclient_lock, RW_READER); cp = (rfs4_clntip_t *)rfs4_dbsearch(nsrv4->rfs4_clntip_idx, addr, create, addr, RFS4_DBS_VALID);
*** 2001,2011 **** void rfs4_invalidate_clntip(struct sockaddr *addr) { rfs4_clntip_t *cp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); rw_enter(&nsrv4->rfs4_findclient_lock, RW_READER); cp = (rfs4_clntip_t *)rfs4_dbsearch(nsrv4->rfs4_clntip_idx, addr, &create, NULL, RFS4_DBS_VALID); --- 2001,2011 ---- void rfs4_invalidate_clntip(struct sockaddr *addr) { rfs4_clntip_t *cp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); rw_enter(&nsrv4->rfs4_findclient_lock, RW_READER); cp = (rfs4_clntip_t *)rfs4_dbsearch(nsrv4->rfs4_clntip_idx, addr, &create, NULL, RFS4_DBS_VALID);
*** 2162,2172 **** rfs4_openowner_t *argp = (rfs4_openowner_t *)arg; open_owner4 *openowner = &argp->ro_owner; seqid4 seqid = argp->ro_open_seqid; rfs4_client_t *cp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); rw_enter(&nsrv4->rfs4_findclient_lock, RW_READER); cp = (rfs4_client_t *)rfs4_dbsearch(nsrv4->rfs4_clientid_idx, &openowner->clientid, --- 2162,2172 ---- rfs4_openowner_t *argp = (rfs4_openowner_t *)arg; open_owner4 *openowner = &argp->ro_owner; seqid4 seqid = argp->ro_open_seqid; rfs4_client_t *cp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); rw_enter(&nsrv4->rfs4_findclient_lock, RW_READER); cp = (rfs4_client_t *)rfs4_dbsearch(nsrv4->rfs4_clientid_idx, &openowner->clientid,
*** 2212,2222 **** rfs4_openowner_t * rfs4_findopenowner(open_owner4 *openowner, bool_t *create, seqid4 seqid) { rfs4_openowner_t *oo; rfs4_openowner_t arg; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); arg.ro_owner = *openowner; arg.ro_open_seqid = seqid; /* CSTYLED */ oo = (rfs4_openowner_t *)rfs4_dbsearch(nsrv4->rfs4_openowner_idx, openowner, --- 2212,2222 ---- rfs4_openowner_t * rfs4_findopenowner(open_owner4 *openowner, bool_t *create, seqid4 seqid) { rfs4_openowner_t *oo; rfs4_openowner_t arg; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); arg.ro_owner = *openowner; arg.ro_open_seqid = seqid; /* CSTYLED */ oo = (rfs4_openowner_t *)rfs4_dbsearch(nsrv4->rfs4_openowner_idx, openowner,
*** 2360,2370 **** { rfs4_lockowner_t *lo = (rfs4_lockowner_t *)u_entry; lock_owner4 *lockowner = (lock_owner4 *)arg; rfs4_client_t *cp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); rw_enter(&nsrv4->rfs4_findclient_lock, RW_READER); cp = (rfs4_client_t *)rfs4_dbsearch(nsrv4->rfs4_clientid_idx, &lockowner->clientid, --- 2360,2370 ---- { rfs4_lockowner_t *lo = (rfs4_lockowner_t *)u_entry; lock_owner4 *lockowner = (lock_owner4 *)arg; rfs4_client_t *cp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); rw_enter(&nsrv4->rfs4_findclient_lock, RW_READER); cp = (rfs4_client_t *)rfs4_dbsearch(nsrv4->rfs4_clientid_idx, &lockowner->clientid,
*** 2389,2399 **** rfs4_lockowner_t * rfs4_findlockowner(lock_owner4 *lockowner, bool_t *create) { rfs4_lockowner_t *lo; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); /* CSTYLED */ lo = (rfs4_lockowner_t *)rfs4_dbsearch(nsrv4->rfs4_lockowner_idx, lockowner, create, lockowner, RFS4_DBS_VALID); --- 2389,2399 ---- rfs4_lockowner_t * rfs4_findlockowner(lock_owner4 *lockowner, bool_t *create) { rfs4_lockowner_t *lo; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); /* CSTYLED */ lo = (rfs4_lockowner_t *)rfs4_dbsearch(nsrv4->rfs4_lockowner_idx, lockowner, create, lockowner, RFS4_DBS_VALID);
*** 2403,2413 **** rfs4_lockowner_t * rfs4_findlockowner_by_pid(pid_t pid) { rfs4_lockowner_t *lo; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); lo = (rfs4_lockowner_t *)rfs4_dbsearch(nsrv4->rfs4_lockowner_pid_idx, (void *)(uintptr_t)pid, &create, NULL, RFS4_DBS_VALID); return (lo); --- 2403,2413 ---- rfs4_lockowner_t * rfs4_findlockowner_by_pid(pid_t pid) { rfs4_lockowner_t *lo; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); lo = (rfs4_lockowner_t *)rfs4_dbsearch(nsrv4->rfs4_lockowner_pid_idx, (void *)(uintptr_t)pid, &create, NULL, RFS4_DBS_VALID); return (lo);
*** 2516,2526 **** rfs4_file_t * rfs4_findfile(vnode_t *vp, nfs_fh4 *fh, bool_t *create) { rfs4_file_t *fp; rfs4_fcreate_arg arg; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); arg.vp = vp; arg.fh = fh; if (*create == TRUE) --- 2516,2526 ---- rfs4_file_t * rfs4_findfile(vnode_t *vp, nfs_fh4 *fh, bool_t *create) { rfs4_file_t *fp; rfs4_fcreate_arg arg; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); arg.vp = vp; arg.fh = fh; if (*create == TRUE)
*** 2558,2568 **** rfs4_findfile_withlock(vnode_t *vp, nfs_fh4 *fh, bool_t *create) { rfs4_file_t *fp; rfs4_fcreate_arg arg; bool_t screate = *create; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); if (screate == FALSE) { mutex_enter(&vp->v_vsd_lock); fp = (rfs4_file_t *)vsd_get(vp, nfs4_srv_vkey); if (fp) { --- 2558,2568 ---- rfs4_findfile_withlock(vnode_t *vp, nfs_fh4 *fh, bool_t *create) { rfs4_file_t *fp; rfs4_fcreate_arg arg; bool_t screate = *create; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); if (screate == FALSE) { mutex_enter(&vp->v_vsd_lock); fp = (rfs4_file_t *)vsd_get(vp, nfs4_srv_vkey); if (fp) {
*** 2745,2755 **** static rfs4_lo_state_t * rfs4_findlo_state(stateid_t *id, bool_t lock_fp) { rfs4_lo_state_t *lsp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); lsp = (rfs4_lo_state_t *)rfs4_dbsearch(nsrv4->rfs4_lo_state_idx, id, &create, NULL, RFS4_DBS_VALID); if (lock_fp == TRUE && lsp != NULL) rw_enter(&lsp->rls_state->rs_finfo->rf_file_rwlock, RW_READER); --- 2745,2755 ---- static rfs4_lo_state_t * rfs4_findlo_state(stateid_t *id, bool_t lock_fp) { rfs4_lo_state_t *lsp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); lsp = (rfs4_lo_state_t *)rfs4_dbsearch(nsrv4->rfs4_lo_state_idx, id, &create, NULL, RFS4_DBS_VALID); if (lock_fp == TRUE && lsp != NULL) rw_enter(&lsp->rls_state->rs_finfo->rf_file_rwlock, RW_READER);
*** 2786,2796 **** rfs4_findlo_state_by_owner(rfs4_lockowner_t *lo, rfs4_state_t *sp, bool_t *create) { rfs4_lo_state_t *lsp; rfs4_lo_state_t arg; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); arg.rls_locker = lo; arg.rls_state = sp; lsp = (rfs4_lo_state_t *)rfs4_dbsearch(nsrv4->rfs4_lo_state_owner_idx, --- 2786,2796 ---- rfs4_findlo_state_by_owner(rfs4_lockowner_t *lo, rfs4_state_t *sp, bool_t *create) { rfs4_lo_state_t *lsp; rfs4_lo_state_t arg; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); arg.rls_locker = lo; arg.rls_state = sp; lsp = (rfs4_lo_state_t *)rfs4_dbsearch(nsrv4->rfs4_lo_state_owner_idx,
*** 2803,2813 **** get_stateid(id_t eid) { stateid_t id; nfs4_srv_t *nsrv4; ! nsrv4 = zone_getspecific(rfs4_zone_key, curzone); id.bits.boottime = nsrv4->rfs4_start_time; id.bits.ident = eid; id.bits.chgseq = 0; id.bits.type = 0; --- 2803,2813 ---- get_stateid(id_t eid) { stateid_t id; nfs4_srv_t *nsrv4; ! nsrv4 = nfs4_get_srv(); id.bits.boottime = nsrv4->rfs4_start_time; id.bits.ident = eid; id.bits.chgseq = 0; id.bits.type = 0;
*** 3061,3071 **** rfs4_deleg_state_t * rfs4_finddeleg(rfs4_state_t *sp, bool_t *create) { rfs4_deleg_state_t ds, *dsp; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); ds.rds_client = sp->rs_owner->ro_client; ds.rds_finfo = sp->rs_finfo; dsp = (rfs4_deleg_state_t *)rfs4_dbsearch(nsrv4->rfs4_deleg_idx, &ds, --- 3061,3071 ---- rfs4_deleg_state_t * rfs4_finddeleg(rfs4_state_t *sp, bool_t *create) { rfs4_deleg_state_t ds, *dsp; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); ds.rds_client = sp->rs_owner->ro_client; ds.rds_finfo = sp->rs_finfo; dsp = (rfs4_deleg_state_t *)rfs4_dbsearch(nsrv4->rfs4_deleg_idx, &ds,
*** 3077,3087 **** rfs4_deleg_state_t * rfs4_finddelegstate(stateid_t *id) { rfs4_deleg_state_t *dsp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); dsp = (rfs4_deleg_state_t *)rfs4_dbsearch(nsrv4->rfs4_deleg_state_idx, id, &create, NULL, RFS4_DBS_VALID); return (dsp); --- 3077,3087 ---- rfs4_deleg_state_t * rfs4_finddelegstate(stateid_t *id) { rfs4_deleg_state_t *dsp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); dsp = (rfs4_deleg_state_t *)rfs4_dbsearch(nsrv4->rfs4_deleg_state_idx, id, &create, NULL, RFS4_DBS_VALID); return (dsp);
*** 3199,3209 **** rfs4_findstate_by_owner_file(rfs4_openowner_t *oo, rfs4_file_t *fp, bool_t *create) { rfs4_state_t *sp; rfs4_state_t key; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); key.rs_owner = oo; key.rs_finfo = fp; sp = (rfs4_state_t *)rfs4_dbsearch(nsrv4->rfs4_state_owner_file_idx, --- 3199,3209 ---- rfs4_findstate_by_owner_file(rfs4_openowner_t *oo, rfs4_file_t *fp, bool_t *create) { rfs4_state_t *sp; rfs4_state_t key; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); key.rs_owner = oo; key.rs_finfo = fp; sp = (rfs4_state_t *)rfs4_dbsearch(nsrv4->rfs4_state_owner_file_idx,
*** 3215,3225 **** /* This returns ANY state struct that refers to this file */ static rfs4_state_t * rfs4_findstate_by_file(rfs4_file_t *fp) { bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); return ((rfs4_state_t *)rfs4_dbsearch(nsrv4->rfs4_state_file_idx, fp, &create, fp, RFS4_DBS_VALID)); } --- 3215,3225 ---- /* This returns ANY state struct that refers to this file */ static rfs4_state_t * rfs4_findstate_by_file(rfs4_file_t *fp) { bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); return ((rfs4_state_t *)rfs4_dbsearch(nsrv4->rfs4_state_file_idx, fp, &create, fp, RFS4_DBS_VALID)); }
*** 3268,3278 **** static rfs4_state_t * rfs4_findstate(stateid_t *id, rfs4_dbsearch_type_t find_invalid, bool_t lock_fp) { rfs4_state_t *sp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = zone_getspecific(rfs4_zone_key, curzone); sp = (rfs4_state_t *)rfs4_dbsearch(nsrv4->rfs4_state_idx, id, &create, NULL, find_invalid); if (lock_fp == TRUE && sp != NULL) rw_enter(&sp->rs_finfo->rf_file_rwlock, RW_READER); --- 3268,3278 ---- static rfs4_state_t * rfs4_findstate(stateid_t *id, rfs4_dbsearch_type_t find_invalid, bool_t lock_fp) { rfs4_state_t *sp; bool_t create = FALSE; ! nfs4_srv_t *nsrv4 = nfs4_get_srv(); sp = (rfs4_state_t *)rfs4_dbsearch(nsrv4->rfs4_state_idx, id, &create, NULL, find_invalid); if (lock_fp == TRUE && sp != NULL) rw_enter(&sp->rs_finfo->rf_file_rwlock, RW_READER);
*** 3340,3350 **** rfs4_check_clientid(clientid4 *cp, int setclid_confirm) { cid *cidp = (cid *) cp; nfs4_srv_t *nsrv4; ! nsrv4 = zone_getspecific(rfs4_zone_key, curzone); /* * If we are booted as a cluster node, check the embedded nodeid. * If it indicates that this clientid was generated on another node, * inform the client accordingly. --- 3340,3350 ---- rfs4_check_clientid(clientid4 *cp, int setclid_confirm) { cid *cidp = (cid *) cp; nfs4_srv_t *nsrv4; ! nsrv4 = nfs4_get_srv(); /* * If we are booted as a cluster node, check the embedded nodeid. * If it indicates that this clientid was generated on another node, * inform the client accordingly.
*** 3372,3382 **** static nfsstat4 what_stateid_error(stateid_t *id, stateid_type_t type) { nfs4_srv_t *nsrv4; ! nsrv4 = zone_getspecific(rfs4_zone_key, curzone); /* If we are booted as a cluster node, was stateid locally generated? */ if ((cluster_bootflags & CLUSTER_BOOTED) && foreign_stateid(id)) return (NFS4ERR_STALE_STATEID); --- 3372,3382 ---- static nfsstat4 what_stateid_error(stateid_t *id, stateid_type_t type) { nfs4_srv_t *nsrv4; ! nsrv4 = nfs4_get_srv(); /* If we are booted as a cluster node, was stateid locally generated? */ if ((cluster_bootflags & CLUSTER_BOOTED) && foreign_stateid(id)) return (NFS4ERR_STALE_STATEID);
*** 4106,4137 **** /* * Given a directory that is being unexported, cleanup/release all * state in the server that refers to objects residing underneath this * particular export. The ordering of the release is important. * Lock_owner, then state and then file. */ void ! rfs4_clean_state_exi(struct exportinfo *exi) { nfs4_srv_t *nsrv4; ! /* curzone mightn't be exi_zone, so use exi_zone instead. */ ! ASSERT(exi->exi_zone == curzone || curzone == global_zone); ! nsrv4 = zone_getspecific(rfs4_zone_key, exi->exi_zone); ! if (nsrv4 == NULL) /* NOTE: NFSv4 cleanup MAY have already happened. */ ! return; mutex_enter(&nsrv4->state_lock); if (nsrv4->nfs4_server_state == NULL) { mutex_exit(&nsrv4->state_lock); return; } ! /* CSTYLED */ ! rfs4_dbe_walk(nsrv4->rfs4_lo_state_tab, rfs4_lo_state_walk_callout, exi); rfs4_dbe_walk(nsrv4->rfs4_state_tab, rfs4_state_walk_callout, exi); ! /* CSTYLED */ ! rfs4_dbe_walk(nsrv4->rfs4_deleg_state_tab, rfs4_deleg_state_walk_callout, exi); rfs4_dbe_walk(nsrv4->rfs4_file_tab, rfs4_file_walk_callout, exi); mutex_exit(&nsrv4->state_lock); } --- 4106,4141 ---- /* * Given a directory that is being unexported, cleanup/release all * state in the server that refers to objects residing underneath this * particular export. The ordering of the release is important. * Lock_owner, then state and then file. + * + * NFS zones note: nfs_export.c:unexport() calls this from a + * thread in the global zone for NGZ data structures, so we + * CANNOT use zone_getspecific anywhere in this code path. */ void ! rfs4_clean_state_exi(nfs_export_t *ne, struct exportinfo *exi) { + nfs_globals_t *ng; nfs4_srv_t *nsrv4; ! ng = ne->ne_globals; ! ASSERT(ng->nfs_zoneid == exi->exi_zoneid); ! nsrv4 = ng->nfs4_srv; ! mutex_enter(&nsrv4->state_lock); if (nsrv4->nfs4_server_state == NULL) { mutex_exit(&nsrv4->state_lock); return; } ! rfs4_dbe_walk(nsrv4->rfs4_lo_state_tab, ! rfs4_lo_state_walk_callout, exi); rfs4_dbe_walk(nsrv4->rfs4_state_tab, rfs4_state_walk_callout, exi); ! rfs4_dbe_walk(nsrv4->rfs4_deleg_state_tab, ! rfs4_deleg_state_walk_callout, exi); rfs4_dbe_walk(nsrv4->rfs4_file_tab, rfs4_file_walk_callout, exi); mutex_exit(&nsrv4->state_lock); }