| 1 | /* |
| 2 | * Copyright (c) 1992, 1993 |
| 3 | * The Regents of the University of California. All rights reserved. |
| 4 | * |
| 5 | * This code is derived from software contributed to Berkeley by |
| 6 | * Rick Macklem at The University of Guelph. |
| 7 | * |
| 8 | * Redistribution and use in source and binary forms, with or without |
| 9 | * modification, are permitted provided that the following conditions |
| 10 | * are met: |
| 11 | * 1. Redistributions of source code must retain the above copyright |
| 12 | * notice, this list of conditions and the following disclaimer. |
| 13 | * 2. Redistributions in binary form must reproduce the above copyright |
| 14 | * notice, this list of conditions and the following disclaimer in the |
| 15 | * documentation and/or other materials provided with the distribution. |
| 16 | * 3. All advertising materials mentioning features or use of this software |
| 17 | * must display the following acknowledgement: |
| 18 | * This product includes software developed by the University of |
| 19 | * California, Berkeley and its contributors. |
| 20 | * 4. Neither the name of the University nor the names of its contributors |
| 21 | * may be used to endorse or promote products derived from this software |
| 22 | * without specific prior written permission. |
| 23 | * |
| 24 | * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND |
| 25 | * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |
| 26 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE |
| 27 | * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE |
| 28 | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL |
| 29 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS |
| 30 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) |
| 31 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT |
| 32 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY |
| 33 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF |
| 34 | * SUCH DAMAGE. |
| 35 | * |
| 36 | * @(#)nqnfs.h 8.3 (Berkeley) 3/30/95 |
| 37 | * $FreeBSD: src/sys/nfs/nqnfs.h,v 1.22 2000/02/13 03:32:07 peter Exp $ |
| 38 | * $DragonFly: src/sys/vfs/nfs/Attic/nqnfs.h,v 1.6 2004/08/13 17:51:12 dillon Exp $ |
| 39 | */ |
| 40 | |
| 41 | |
| 42 | #ifndef _NFS_NQNFS_H_ |
| 43 | #define _NFS_NQNFS_H_ |
| 44 | |
| 45 | /* |
| 46 | * Definitions for NQNFS (Not Quite NFS) cache consistency protocol. |
| 47 | */ |
| 48 | |
| 49 | /* Tunable constants */ |
| 50 | #define NQ_CLOCKSKEW 3 /* Clock skew factor (sec) */ |
| 51 | #define NQ_WRITESLACK 5 /* Delay for write cache flushing */ |
| 52 | #define NQ_MAXLEASE 60 /* Max lease duration (sec) */ |
| 53 | #define NQ_MINLEASE 5 /* Min lease duration (sec) */ |
| 54 | #define NQ_DEFLEASE 30 /* Default lease duration (sec) */ |
| 55 | #define NQ_RENEWAL 3 /* Time before expiry (sec) to renew */ |
| 56 | #define NQ_TRYLATERDEL 15 /* Initial try later delay (sec) */ |
| 57 | #define NQ_MAXNUMLEASE 2048 /* Upper bound on number of server leases */ |
| 58 | #define NQ_DEADTHRESH NQ_NEVERDEAD /* Default nm_deadthresh */ |
| 59 | #define NQ_NEVERDEAD 9 /* Greater than max. nm_timeouts */ |
| 60 | #define NQLCHSZ 256 /* Server hash table size */ |
| 61 | |
| 62 | #define NQNFS_PROG 300105 /* As assigned by Sun */ |
| 63 | #define NQNFS_VER3 3 |
| 64 | #define NQNFS_EVICTSIZ 156 /* Size of eviction request in bytes */ |
| 65 | |
| 66 | #if defined(_KERNEL) |
| 67 | /* |
| 68 | * Definitions used for saving the "last lease expires" time in Non-volatile |
| 69 | * RAM on the server. The default definitions below assume that NOVRAM is not |
| 70 | * available. |
| 71 | */ |
| 72 | #ifdef HASNVRAM |
| 73 | # undef HASNVRAM |
| 74 | #endif |
| 75 | #define NQSTORENOVRAM(t) |
| 76 | #define NQLOADNOVRAM(t) |
| 77 | |
| 78 | /* |
| 79 | * Defn and structs used on the server to maintain state for current leases. |
| 80 | * The list of host(s) that hold the lease are kept as nqhost structures. |
| 81 | * The first one lives in nqlease and any others are held in a linked |
| 82 | * list of nqm structures hanging off of nqlease. |
| 83 | * |
| 84 | * Each nqlease structure is chained into two lists. The first is a list |
| 85 | * ordered by increasing expiry time for nqsrv_timer() and the second is a chain |
| 86 | * hashed on lc_fh. |
| 87 | */ |
| 88 | #define LC_MOREHOSTSIZ 10 |
| 89 | |
| 90 | struct nqhost { |
| 91 | u_int16_t lph_flag; |
| 92 | u_int16_t lph_port; |
| 93 | struct nfssvc_sock *lph_slp; |
| 94 | |
| 95 | union { |
| 96 | struct { |
| 97 | union nethostaddr udp_haddr; |
| 98 | } un_udp; |
| 99 | struct { |
| 100 | int dummy; |
| 101 | } un_conn; |
| 102 | } lph_un; |
| 103 | }; |
| 104 | #define lph_haddr lph_un.un_udp.udp_haddr |
| 105 | #define lph_inetaddr lph_un.un_udp.udp_haddr.had_inetaddr |
| 106 | |
| 107 | struct nqlease { |
| 108 | LIST_ENTRY(nqlease) lc_hash; /* Fhandle hash list */ |
| 109 | CIRCLEQ_ENTRY(nqlease) lc_timer; /* Timer queue list */ |
| 110 | time_t lc_expiry; /* Expiry time (sec) */ |
| 111 | struct nqhost lc_host; /* Host that got lease */ |
| 112 | struct nqm *lc_morehosts; /* Other hosts that share read lease */ |
| 113 | fsid_t lc_fsid; /* Fhandle */ |
| 114 | char lc_fiddata[MAXFIDSZ]; |
| 115 | struct vnode *lc_vp; /* Soft reference to associated vnode */ |
| 116 | }; |
| 117 | #define lc_flag lc_host.lph_flag |
| 118 | |
| 119 | /* lc_flag bits */ |
| 120 | #define LC_VALID 0x0001 /* Host address valid */ |
| 121 | #define LC_WRITE 0x0002 /* Write cache */ |
| 122 | #define LC_NONCACHABLE 0x0004 /* Non-cachable lease */ |
| 123 | #define LC_LOCKED 0x0008 /* Locked */ |
| 124 | #define LC_WANTED 0x0010 /* Lock wanted */ |
| 125 | #define LC_EXPIREDWANTED 0x0020 /* Want lease when expired */ |
| 126 | #define LC_UDP 0x0040 /* Host address for udp socket */ |
| 127 | /* 0x0080 free */ |
| 128 | #define LC_LOCAL 0x0100 /* Host is server */ |
| 129 | #define LC_VACATED 0x0200 /* Host has vacated lease */ |
| 130 | #define LC_WRITTEN 0x0400 /* Recently wrote to the leased file */ |
| 131 | #define LC_SREF 0x0800 /* Holds a nfssvc_sock reference */ |
| 132 | |
| 133 | struct nqm { |
| 134 | struct nqm *lpm_next; |
| 135 | struct nqhost lpm_hosts[LC_MOREHOSTSIZ]; |
| 136 | }; |
| 137 | |
| 138 | /* |
| 139 | * Special value for slp for local server calls. |
| 140 | */ |
| 141 | #define NQLOCALSLP ((struct nfssvc_sock *) -1) |
| 142 | |
| 143 | /* |
| 144 | * Server side macros. |
| 145 | */ |
| 146 | #define nqsrv_getl(v, l) \ |
| 147 | (void) nqsrv_getlease((v), &nfsd->nd_duration, \ |
| 148 | ((nfsd->nd_flag & ND_LEASE) ? (nfsd->nd_flag & ND_LEASE) : \ |
| 149 | ((l) | ND_CHECK)), \ |
| 150 | slp, td, nfsd->nd_nam, &cache, &frev, cred) |
| 151 | |
| 152 | /* |
| 153 | * Client side macros that check for a valid lease. |
| 154 | */ |
| 155 | #define NQNFS_CKINVALID(v, n, f) \ |
| 156 | ((time_second > (n)->n_expiry && \ |
| 157 | VFSTONFS((v)->v_mount)->nm_timeouts < VFSTONFS((v)->v_mount)->nm_deadthresh) \ |
| 158 | || ((f) == ND_WRITE && ((n)->n_flag & NQNFSWRITE) == 0)) |
| 159 | |
| 160 | #define NQNFS_CKCACHABLE(v, f) \ |
| 161 | ((time_second <= VTONFS(v)->n_expiry || \ |
| 162 | VFSTONFS((v)->v_mount)->nm_timeouts >= VFSTONFS((v)->v_mount)->nm_deadthresh) \ |
| 163 | && (VTONFS(v)->n_flag & NQNFSNONCACHE) == 0 && \ |
| 164 | ((f) == ND_READ || (VTONFS(v)->n_flag & NQNFSWRITE))) |
| 165 | |
| 166 | #define NQNFS_NEEDLEASE(v, p) \ |
| 167 | (time_second > VTONFS(v)->n_expiry ? \ |
| 168 | ((VTONFS(v)->n_flag & NQNFSEVICTED) ? 0 : nqnfs_piggy[p]) : \ |
| 169 | (((time_second + NQ_RENEWAL) > VTONFS(v)->n_expiry && \ |
| 170 | nqnfs_piggy[p]) ? \ |
| 171 | ((VTONFS(v)->n_flag & NQNFSWRITE) ? \ |
| 172 | ND_WRITE : nqnfs_piggy[p]) : 0)) |
| 173 | |
| 174 | /* |
| 175 | * List head for timer queue. |
| 176 | */ |
| 177 | extern CIRCLEQ_HEAD(nqtimerhead, nqlease) nqtimerhead; |
| 178 | |
| 179 | /* |
| 180 | * List head for the file handle hash table. |
| 181 | */ |
| 182 | #define NQFHHASH(f) \ |
| 183 | (&nqfhhashtbl[(*((u_int32_t *)(f))) & nqfhhash]) |
| 184 | extern LIST_HEAD(nqfhhashhead, nqlease) *nqfhhashtbl; |
| 185 | extern u_long nqfhhash; |
| 186 | |
| 187 | /* |
| 188 | * Nqnfs return status numbers. |
| 189 | */ |
| 190 | #define NQNFS_EXPIRED 500 |
| 191 | #define NQNFS_TRYLATER 501 |
| 192 | |
| 193 | int nqnfs_lease_check (struct vnode *, struct thread *, struct ucred *, int); |
| 194 | void nqnfs_lease_updatetime (int); |
| 195 | int nqsrv_getlease (struct vnode *, u_int32_t *, int, |
| 196 | struct nfssvc_sock *, struct thread *, |
| 197 | struct sockaddr *, int *, u_quad_t *, |
| 198 | struct ucred *); |
| 199 | int nqnfs_getlease (struct vnode *,int,struct thread *); |
| 200 | int nqnfs_callback (struct nfsmount *,struct mbuf *,struct mbuf *,caddr_t); |
| 201 | int nqnfs_clientd (struct nfsmount *,struct ucred *,struct nfsd_cargs *,int,caddr_t,struct thread *); |
| 202 | struct nfsnode; |
| 203 | void nqnfs_clientlease (struct nfsmount *, struct nfsnode *, int, int, time_t, u_quad_t); |
| 204 | void nqnfs_serverd (void); |
| 205 | int nqnfsrv_getlease (struct nfsrv_descript *, struct nfssvc_sock *, struct thread *, struct mbuf **); |
| 206 | int nqnfsrv_vacated (struct nfsrv_descript *, struct nfssvc_sock *, struct thread *, struct mbuf **); |
| 207 | #endif |
| 208 | |
| 209 | #endif |