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 <afs/param.h>
26 osi_rwlock_t cm_cellLock;
28 cm_cell_t *cm_allCellsp;
30 /* function called as callback proc from cm_SearchCellFile. Return 0 to
31 * continue processing.
33 long cm_AddCellProc(void *rockp, struct sockaddr_in *addrp, char *namep)
41 /* if this server was previously created by fs setserverprefs */
42 if ( tsp = cm_FindServer(addrp, CM_SERVER_VLDB))
48 tsp = cm_NewServer(addrp, CM_SERVER_VLDB, cellp);
50 /* Insert the vlserver into a sorted list, sorted by server rank */
51 tsrp = cm_NewServerRef(tsp);
52 cm_InsertServerList(&cellp->vlServersp, tsrp);
57 /* load up a cell structure from the cell database, afsdcell.ini */
58 cm_cell_t *cm_GetCell(char *namep, long flags)
60 return cm_GetCell_Gen(namep, NULL, flags);
63 cm_cell_t *cm_GetCell_Gen(char *namep, char *newnamep, long flags)
67 static cellCounter = 1; /* locked by cm_cellLock */
71 lock_ObtainWrite(&cm_cellLock);
72 for(cp = cm_allCellsp; cp; cp=cp->nextp) {
73 if (strcmp(namep, cp->namep) == 0) {
74 strcpy(fullname, cp->namep);
79 if ((!cp && (flags & CM_FLAG_CREATE))
81 /* if it's from DNS, see if it has expired */
82 || (cp && (cp->flags & CM_CELLFLAG_DNS) && (time(0) > cp->timeout))
85 if (!cp) cp = malloc(sizeof(*cp));
86 memset(cp, 0, sizeof(*cp));
87 code = cm_SearchCellFile(namep, fullname, cm_AddCellProc, cp);
90 if (cm_dnsEnabled /*&& cm_DomainValid(namep)*/)
91 code = cm_SearchCellByDNS(namep, fullname, &ttl, cm_AddCellProc, cp);
99 else { /* got cell from DNS */
100 cp->flags |= CM_CELLFLAG_DNS;
101 cp->timeout = time(0) + ttl;
106 /* randomise among those vlservers having the same rank*/
107 cm_RandomizeServer(&cp->vlServersp);
109 /* otherwise we found the cell, and so we're nearly done */
110 lock_InitializeMutex(&cp->mx, "cm_cell_t mutex");
113 cp->namep = malloc(strlen(fullname)+1);
114 strcpy(cp->namep, fullname);
116 /* thread on global list */
117 cp->nextp = cm_allCellsp;
120 cp->cellID = cellCounter++;
124 /* fullname is not valid if cp == NULL */
126 strcpy(newnamep, fullname);
127 lock_ReleaseWrite(&cm_cellLock);
131 cm_cell_t *cm_FindCellByID(long cellID)
137 lock_ObtainWrite(&cm_cellLock);
138 for(cp = cm_allCellsp; cp; cp=cp->nextp) {
139 if (cellID == cp->cellID) break;
143 /* if it's from DNS, see if it has expired */
144 if (cp && cm_dnsEnabled && (cp->flags & CM_CELLFLAG_DNS) && (time(0) > cp->timeout)) {
145 code = cm_SearchCellByDNS(cp->namep, NULL, &ttl, cm_AddCellProc, cp);
146 if (code == 0) { /* got cell from DNS */
147 cp->flags |= CM_CELLFLAG_DNS;
149 fprintf(stderr, "cell %s: ttl=%d\n", cp->namep, ttl);
151 cp->timeout = time(0) + ttl;
153 /* if we fail to find it this time, we'll just do nothing and leave the
154 current entry alone */
156 #endif /* AFS_AFSDB_ENV */
158 lock_ReleaseWrite(&cm_cellLock);
163 void cm_InitCell(void)
165 static osi_once_t once;
167 if (osi_Once(&once)) {
168 lock_InitializeRWLock(&cm_cellLock, "cell global lock");
173 void cm_ChangeRankCellVLServer(cm_server_t *tsp)
178 cp = tsp->cellp; /* cell that this vlserver belongs to */
181 lock_ObtainMutex(&cp->mx);
182 code = cm_ChangeRankServer(&cp->vlServersp, tsp);
184 if ( !code ) /* if the server list was rearranged */
185 cm_RandomizeServer(&cp->vlServersp);
187 lock_ReleaseMutex(&cp->mx);