2 * Copyright 2000, International Business Machines Corporation and others.
5 * This software has been released under the terms of the IBM Public
6 * License. For details, see the LICENSE file in the top-level source
7 * directory or online at http://www.openafs.org/dl/license10.html
10 #include "fs_stats.h" /*File Server stats package */
12 #ifdef AFS_PTHREAD_ENV
14 * There are three locks in the host package.
15 * the global hash lock protects hash chains.
16 * the global list lock protects the list of hosts.
17 * a mutex in each host structure protects the structure.
18 * precedence is host_listlock_mutex, host->mutex, host_glock_mutex.
20 #include <rx/rx_globals.h>
23 extern pthread_mutex_t host_glock_mutex;
25 assert(pthread_mutex_lock(&host_glock_mutex) == 0)
27 assert(pthread_mutex_unlock(&host_glock_mutex) == 0)
28 #else /* AFS_PTHREAD_ENV */
31 #endif /* AFS_PTHREAD_ENV */
33 #define h_MAXHOSTTABLEENTRIES 1000
34 #define h_HASHENTRIES 256 /* Power of 2 */
35 #define h_MAXHOSTTABLES 200
36 #define h_HTSPERBLOCK 512 /* Power of 2 */
37 #define h_HTSHIFT 9 /* log base 2 of HTSPERBLOCK */
39 #define h_threadsPerSlot 32 /* bits per afs_int32 */
40 #define h_threadsShift 5 /* for multiply/divide */
41 #define h_threadsMask 31 /* for remainder */
43 /* size of the hold array for each host */
44 #define h_maxSlots (((MAX_FILESERVER_THREAD+h_threadsPerSlot-1)>>h_threadsShift)+1)
47 char valid; /* zero if UUID is unknown */
52 afs_uint32 addr; /* in network byte order */
53 afs_uint16 port; /* in network byte order */
58 int numberOfInterfaces;
59 struct AddrPort interface[1];/* there are actually more than one here */
60 /* in network byte order */
63 struct host *next, *prev; /* linked list of all hosts */
64 struct rx_connection *callback_rxcon; /* rx callback connection */
65 afs_int32 holds[h_maxSlots];
66 /* holds on this host; 1 bit per lwp.
67 * A hold prevents this structure and
68 * inferior structures from disappearing */
69 afs_uint32 host; /* IP address of host interface that is
70 * currently being used, in network
72 afs_uint16 port; /* port address of host */
73 char Console; /* XXXX This host is a console */
74 unsigned short hostFlags; /* bit map */
76 char InSameNetwork; /*Is host's addr in the same network as
77 * the File Server's? */
78 char dummy[3]; /* for padding */
79 #endif /* FS_STATS_DETAILED */
80 char hcpsfailed; /* Retry the cps call next time */
81 prlist hcps; /* cps for hostip acls */
82 afs_uint32 LastCall; /* time of last call from host */
83 afs_uint32 ActiveCall; /* time of any call but gettime,
84 getstats and getcaps */
85 struct client *FirstClient; /* first connection from host */
86 afs_uint32 cpsCall; /* time of last cps call from this host */
87 struct Interface *interface; /* all alternate addr for client */
88 afs_uint32 cblist; /* Call back list for this host */
90 * These don't get zeroed, keep them at the end. If index doesn't
91 * follow an unsigned short then we need to pad to ensure that
92 * the index fields isn't zeroed. XXX
94 afs_uint32 index; /* Host table index, for vicecb.c */
95 struct Lock lock; /* Write lock for synchronization of
97 #ifdef AFS_PTHREAD_ENV
98 pthread_cond_t cond; /* used to wait on hcpsValid */
99 #endif /* AFS_PTHREAD_ENV */
102 /* * Don't zero the index, lock or condition varialbles */
103 #define HOST_TO_ZERO(H) (int)(((char *)(&((H)->index))-(char *)(H)))
106 struct host *hostPtr;
107 struct h_hashChain *next;
113 struct client *next; /* next client entry for host */
114 struct host *host; /* ptr to parent host entry */
115 afs_int32 sid; /* Connection number from this host */
116 struct rx_connection *tcon; /* most recent server connection
117 * associated with this client */
118 prlist CPS; /* cps for authentication */
119 int ViceId; /* Vice ID of user */
120 afs_int32 expTime; /* RX-only: expiration time */
121 afs_uint32 LastCall; /* time of last call */
122 afs_uint32 VenusEpoch; /* Venus start time--used to identify
123 * venus. Actually, now an extension of the
124 * sid, which is why it moved.
126 afs_int32 refCount; /* reference count */
127 char deleted; /* True if this client should be deleted
128 * when there are no more users of the
130 char authClass; /* auth type, RX-only */
131 char prfail; /* True if prserver couldn't be contacted */
132 #if FS_STATS_DETAILED
133 char InSameNetwork; /* Is client's IP address in the same
134 * network as ours? */
135 #else /* FS_STATS_DETAILED */
136 char dummy; /* For padding */
137 #endif /* FS_STATS_DETAILED */
138 struct Lock lock; /* lock to ensure CPS valid if entry
139 * on host's clients list. */
142 /* Don't zero the lock */
143 #define CLIENT_TO_ZERO(C) ((int)(((char *)(&((C)->lock))-(char *)(C))))
146 * key for the client structure stored in connection specific data
148 extern int rxcon_client_key;
150 /* Some additional functions to get at client information. Client must have
151 an active connection for this to work. If a lwp is working on a request
152 for the client, then the client must have a connection */
153 /* N.B. h_UserName returns pointer to static data; also relatively expensive */
154 extern char *h_UserName(struct client *client);
156 /* all threads whose thread-id is greater than the size of the hold array,
157 ** then use the most significant bit in the 'hold' field in the host structure
159 #ifdef AFS_PTHREAD_ENV
160 #define h_lwpIndex() ( ((long)(pthread_getspecific(rx_thread_id_key)) > \
161 ((h_maxSlots << h_threadsShift)-1)) ? \
162 (h_maxSlots << h_threadsShift) -1 : \
163 (long)(pthread_getspecific(rx_thread_id_key)) )
164 #else /* AFS_PTHREAD_ENV */
165 #define h_lwpIndex() ( (LWP_Index() > ((h_maxSlots << h_threadsShift)-1)) ? \
166 (h_maxSlots << h_threadsShift) -1 : \
168 #endif /* AFS_PTHREAD_ENV */
169 #define h_holdIndex()( h_lwpIndex() & h_threadsMask)
170 #define h_holdSlot() ( h_lwpIndex() >> h_threadsShift) /*index in 'holds' */
171 #define h_holdbit() ( 1<<h_holdIndex() )
173 #define h_Hold_r(host) ((host)->holds[h_holdSlot()] |= h_holdbit())
174 extern int h_Release(register struct host *host);
175 extern int h_Release_r(register struct host *host);
177 #define h_Held_r(host) ((h_holdbit() & (host)->holds[h_holdSlot()]) != 0)
178 extern int h_OtherHolds_r(register struct host *host);
179 #define h_Lock(host) ObtainWriteLock(&(host)->lock)
180 extern int h_Lock_r(register struct host *host);
181 #define h_Unlock(host) ReleaseWriteLock(&(host)->lock)
182 #define h_Unlock_r(host) ReleaseWriteLock(&(host)->lock)
184 #define AddCallBack(host, fid) AddCallBack1((host), (fid), (afs_uint32 *)0, 1/*CB_NORMAL*/, 0)
185 #define AddVolCallBack(host, fid) AddCallBack1((host), (fid), (afs_uint32 *)0, 3/*CB_VOLUME*/, 0)
186 #define AddBulkCallBack(host, fid) AddCallBack1((host), (fid), (afs_uint32 *)0, 4/*CB_BULK*/, 0)
188 /* operations on the global linked list of hosts */
189 #define h_InsertList_r(h) (h)->next = hostList; \
191 hostList ? (hostList->prev = (h)):0; \
194 #define h_DeleteList_r(h) assert(hostCount>0); \
196 (h)->next ? ((h)->next->prev = (h)->prev):0;\
197 (h)->prev ? ((h)->prev->next = (h)->next):0;\
198 ( h == hostList )? (hostList = h->next):0;
200 extern int DeleteAllCallBacks_r(struct host *host, int deletefe);
201 extern int DeleteCallBack(struct host *host, AFSFid * fid);
202 extern int MultiProbeAlternateAddress_r(struct host *host);
203 extern int BreakDelayedCallBacks_r(struct host *host);
204 extern int AddCallBack1(struct host *host, AFSFid * fid, afs_uint32 * thead, int type,
206 extern int BreakCallBack(struct host *xhost, AFSFid * fid, int flag);
207 extern int DeleteFileCallBacks(AFSFid * fid);
208 extern int CleanupTimedOutCallBacks(void);
209 extern int CleanupTimedOutCallBacks_r(void);
210 extern int MultiBreakCallBackAlternateAddress(struct host *host, struct AFSCBFids *afidp);
211 extern int MultiBreakCallBackAlternateAddress_r(struct host *host,
212 struct AFSCBFids *afidp);
213 extern int DumpCallBackState(void);
214 extern int PrintCallBackStats(void);
215 extern int ShutDown(void);
216 extern void ShutDownAndCore(int dopanic);
218 extern struct host *h_Alloc(register struct rx_connection *r_con);
219 extern struct host *h_Alloc_r(register struct rx_connection *r_con);
220 extern struct host *h_Lookup_r(afs_uint32 hostaddr, afs_uint16 hport,
222 extern void hashInsert_r(afs_uint32 addr, afs_uint16 port,
224 extern struct host *h_LookupUuid_r(afsUUID * uuidp);
225 extern int h_FreeConnection(struct rx_connection *tcon);
226 extern void h_Enumerate(int (*proc) (), char *param);
227 extern void h_Enumerate_r(int (*proc) (), struct host *enumstart, char *param);
228 extern struct host *h_GetHost_r(struct rx_connection *tcon);
229 extern struct client *h_FindClient_r(struct rx_connection *tcon);
230 extern int h_ReleaseClient_r(struct client *client);
231 extern struct client *h_ID2Client(afs_int32 vid);
232 extern int GetClient(struct rx_connection *tcon, struct client **cp);
233 extern int PutClient(struct client **cp);
234 extern void h_PrintStats();
235 extern void h_PrintClients();
236 extern void h_GetWorkStats();
237 extern void h_flushhostcps(register afs_uint32 hostaddr,
238 register afs_uint16 hport);
239 extern void h_GetHostNetStats(afs_int32 * a_numHostsP, afs_int32 * a_sameNetOrSubnetP,
240 afs_int32 * a_diffSubnetP, afs_int32 * a_diffNetworkP);
241 extern int h_NBLock_r(register struct host *host);
242 extern void h_DumpHosts();
243 extern void h_InitHostPackage();
244 extern void h_CheckHosts();
245 struct Interface *MultiVerifyInterface_r();
246 extern int initInterfaceAddr_r(struct host *host, struct interfaceAddr *interf);
248 struct host *(hosttableptrs[h_MAXHOSTTABLES]); /* Used by h_itoh */
249 #define h_htoi(host) ((host)->index) /* index isn't zeroed, no need to lock */
250 #define h_itoh(hostindex) (hosttableptrs[(hostindex)>>h_HTSHIFT]+((hostindex)&(h_HTSPERBLOCK-1)))
252 #define rxr_GetEpoch(aconn) (((struct rx_connection *)(aconn))->epoch)
254 #define rxr_CidOf(aconn) (((struct rx_connection *)(aconn))->cid)
256 #define rxr_PortOf(aconn) \
257 rx_PortOf(rx_PeerOf(((struct rx_connection *)(aconn))))
259 #define rxr_HostOf(aconn) \
260 rx_HostOf(rx_PeerOf((struct rx_connection *)(aconn)))
262 #define HCPS_INPROGRESS 0x01 /*set when CPS is being updated */
263 #define HCPS_WAITING 0x02 /*waiting for CPS to get updated */
264 #define ALTADDR 0x04 /*InitCallBack is being done */
265 #define VENUSDOWN 0x08 /* venus CallBack failed */
266 #define HOSTDELETED 0x10 /* host delated */
267 #define CLIENTDELETED 0x20 /* client deleted */
268 #define RESETDONE 0x40 /* callback reset done */
269 #define HFE_LATER 0x80 /* host has FE_LATER callbacks */
270 #define HERRORTRANS 0x100 /* do error translation */