/* * Set up a cell for dynroot if it's not there yet. */ static int afs_dynrootCellInit(void) { if (!afs_dynrootCell) { afs_int32 cellHosts[AFS_MAXCELLHOSTS]; struct cell *tc; int code; memset(cellHosts, 0, sizeof(cellHosts)); code = afs_NewCell(AFS_DYNROOT_CELLNAME, cellHosts, CNoSUID | CNoAFSDB, NULL, 0, 0, 0); if (code) return code; tc = afs_GetCellByName(AFS_DYNROOT_CELLNAME, READ_LOCK); if (!tc) return ENODEV; afs_dynrootCell = tc->cellNum; afs_PutCell(tc, READ_LOCK); } return 0; }
/*! * \brief Entry point for user-space AFSDB request handler. * Reads cell data from kerlenMsg and add new cell, or alias. * \param acellName Cell name. If a cell is found, it's name will be filled in here. * \param acellNameLen Cell name length. * \param kernelMsg Buffer containing data about host count, time out, and cell hosts ids. * \return 0 for success, < 0 for error. */ int afs_AFSDBHandler(char *acellName, int acellNameLen, afs_int32 * kernelMsg) { afs_int32 timeout, code; afs_int32 cellHosts[AFS_MAXCELLHOSTS]; if (afsdb_handler_shutdown) return -2; afsdb_handler_running = 1; ObtainSharedLock(&afsdb_req_lock, 683); if (afsdb_req.pending) { int i, hostCount; UpgradeSToWLock(&afsdb_req_lock, 684); hostCount = kernelMsg[0]; timeout = kernelMsg[1]; if (timeout) timeout += osi_Time(); for (i = 0; i < AFS_MAXCELLHOSTS; i++) { if (i >= hostCount) cellHosts[i] = 0; else cellHosts[i] = kernelMsg[2 + i]; } if (hostCount) code = afs_NewCell(acellName, cellHosts, CNoSUID, NULL, 0, 0, timeout); if (!hostCount || (code && code != EEXIST)) /* null out the cellname if the lookup failed */ afsdb_req.cellname = NULL; else /* If we found an alias, create it */ if (afs_strcasecmp(afsdb_req.cellname, acellName)) afs_NewCellAlias(afsdb_req.cellname, acellName); /* Request completed, wake up the relevant thread */ afsdb_req.pending = 0; afsdb_req.complete = 1; afs_osi_Wakeup(&afsdb_req); ConvertWToSLock(&afsdb_req_lock); } ConvertSToRLock(&afsdb_req_lock); /* Wait for a request */ while (afsdb_req.pending == 0 && afs_termState != AFSOP_STOP_AFSDB) { ReleaseReadLock(&afsdb_req_lock); afs_osi_Sleep(&afsdb_req); ObtainReadLock(&afsdb_req_lock); } /* Check if we're shutting down */ if (afs_termState == AFSOP_STOP_AFSDB) { ReleaseReadLock(&afsdb_req_lock); /* Inform anyone waiting for us that we're going away */ afsdb_handler_shutdown = 1; afsdb_handler_running = 0; afs_osi_Wakeup(&afsdb_req); afs_termState = AFSOP_STOP_RXEVENT; afs_osi_Wakeup(&afs_termState); return -2; } /* Return the lookup request to userspace */ strncpy(acellName, afsdb_req.cellname, acellNameLen); ReleaseReadLock(&afsdb_req_lock); return 0; }