char fullname[200]="";
lock_ObtainWrite(&cm_cellLock);
- for(cp = cm_allCellsp; cp; cp=cp->nextp) {
+ for (cp = cm_allCellsp; cp; cp=cp->nextp) {
if (strcmp(namep, cp->namep) == 0) {
strcpy(fullname, cp->namep);
break;
if ((!cp && (flags & CM_FLAG_CREATE))
#ifdef AFS_AFSDB_ENV
/* if it's from DNS, see if it has expired */
- || (cp && (cp->flags & CM_CELLFLAG_DNS) && (time(0) > cp->timeout))
+ || (cp && (cp->flags & CM_CELLFLAG_DNS)
+ && ((cp->flags & CM_CELLFLAG_VLSERVER_INVALID) || (time(0) > cp->timeout)))
#endif
) {
int dns_expired = 0;
afsi_log("in cm_GetCell_gen cm_SearchCellByDNS(%s) returns code= %d fullname= %s",
namep, code, fullname);
if (dns_expired) {
- if ( cm_allCellsp == cp )
- cm_allCellsp = cp->nextp;
- else {
- cm_cell_t *tcp;
-
- for(tcp = cm_allCellsp; tcp->nextp; tcp=tcp->nextp) {
- if ( tcp->nextp == cp ) {
- tcp->nextp = cp->nextp;
- break;
- }
- }
- }
-
- lock_FinalizeMutex(&cp->mx);
- free(cp->namep);
- }
+ cp->flags |= CM_CELLFLAG_VLSERVER_INVALID;
+ cp = NULL; /* set cp to NULL to indicate error */
+ }
}
else { /* got cell from DNS */
cp->flags |= CM_CELLFLAG_DNS;
+ cp->flags &= ~CM_CELLFLAG_VLSERVER_INVALID;
cp->timeout = time(0) + ttl;
}
}
#endif
- if (code) {
+ if (cp && code) { /* free newly allocated memory */
free(cp);
cp = NULL;
goto done;
{
cm_cell_t *cp;
int ttl;
- int code;
+ int code;
lock_ObtainWrite(&cm_cellLock);
for(cp = cm_allCellsp; cp; cp=cp->nextp) {
#ifdef AFS_AFSDB_ENV
/* if it's from DNS, see if it has expired */
- if (cp && cm_dnsEnabled && (cp->flags & CM_CELLFLAG_DNS) && (time(0) > cp->timeout)) {
- code = cm_SearchCellByDNS(cp->namep, NULL, &ttl, cm_AddCellProc, cp);
- if (code == 0) { /* got cell from DNS */
- cp->flags |= CM_CELLFLAG_DNS;
+ if (cp && cm_dnsEnabled && (cp->flags & CM_CELLFLAG_DNS) &&
+ ((cp->flags & CM_CELLFLAG_VLSERVER_INVALID) || (time(0) > cp->timeout))) {
+ /* must empty cp->vlServersp */
+ cm_FreeServerList(&cp->vlServersp);
+ cp->vlServersp = NULL;
+
+ code = cm_SearchCellByDNS(cp->namep, NULL, &ttl, cm_AddCellProc, cp);
+ if (code == 0) { /* got cell from DNS */
+ cp->flags |= CM_CELLFLAG_DNS;
+ cp->flags &= ~CM_CELLFLAG_VLSERVER_INVALID;
#ifdef DEBUG
- fprintf(stderr, "cell %s: ttl=%d\n", cp->namep, ttl);
+ fprintf(stderr, "cell %s: ttl=%d\n", cp->namep, ttl);
#endif
- cp->timeout = time(0) + ttl;
- }
- /* if we fail to find it this time, we'll just do nothing and leave the
- current entry alone */
+ cp->timeout = time(0) + ttl;
+ } else {
+ cp->flags |= CM_CELLFLAG_VLSERVER_INVALID;
+ cp = NULL; /* return NULL to indicate failure */
+ }
+ /* if we fail to find it this time, we'll just do nothing and leave the
+ * current entry alone
+ */
}
#endif /* AFS_AFSDB_ENV */
{
static osi_once_t once;
- if (osi_Once(&once)) {
+ if (osi_Once(&once)) {
lock_InitializeRWLock(&cm_cellLock, "cell global lock");
- cm_allCellsp = NULL;
+ cm_allCellsp = NULL;
osi_EndOnce(&once);
- }
+ }
}
void cm_ChangeRankCellVLServer(cm_server_t *tsp)
{
osi_mutex_t cm_Afsdsbmt_Lock;
extern afs_int32 cryptall;
+extern char cm_NetbiosName[];
void cm_InitIoctl(void)
{
long cm_ParseIoctlPath(smb_ioctl_t *ioctlp, cm_user_t *userp, cm_req_t *reqp,
cm_scache_t **scpp)
{
- extern char cm_NetbiosName[];
long code;
cm_scache_t *substRootp;
char * relativePath = ioctlp->inDatap;
code = cm_NameI(cm_rootSCachep, ioctlp->prefix->data,
CM_FLAG_CASEFOLD | CM_FLAG_FOLLOW,
userp, shareName, reqp, &substRootp);
- free(sharePath);
if (code) return code;
code = cm_NameI(substRootp, p, CM_FLAG_CASEFOLD | CM_FLAG_FOLLOW,
cm_scache_t **scpp, char *leafp)
{
long code;
- char tbuffer[1024];
- char *tp, *jp;
+ char tbuffer[1024];
+ char *tp, *jp;
cm_scache_t *substRootp;
strcpy(tbuffer, ioctlp->inDatap);
- tp = strrchr(tbuffer, '\\');
+ tp = strrchr(tbuffer, '\\');
jp = strrchr(tbuffer, '/');
if (!tp)
tp = jp;
else if (jp && (tp - tbuffer) < (jp - tbuffer))
tp = jp;
- if (!tp) {
- strcpy(tbuffer, "\\");
- if (leafp) strcpy(leafp, ioctlp->inDatap);
- }
- else {
- *tp = 0;
- if (leafp) strcpy(leafp, tp+1);
+ if (!tp) {
+ strcpy(tbuffer, "\\");
+ if (leafp)
+ strcpy(leafp, ioctlp->inDatap);
}
+ else {
+ *tp = 0;
+ if (leafp)
+ strcpy(leafp, tp+1);
+ }
+
+ if (tbuffer[0] == tbuffer[1] &&
+ tbuffer[1] == '\\' &&
+ !_strnicmp(cm_NetbiosName,tbuffer+2,strlen(cm_NetbiosName)))
+ {
+ char shareName[256];
+ char *sharePath;
+ int shareFound, i;
- code = cm_NameI(cm_rootSCachep, ioctlp->prefix->data,
- CM_FLAG_CASEFOLD | CM_FLAG_FOLLOW,
- userp, ioctlp->tidPathp, reqp, &substRootp);
- if (code) return code;
+ /* We may have found a UNC path.
+ * If the first component is the NetbiosName,
+ * then throw out the second component (the submount)
+ * since it had better expand into the value of ioctl->tidPathp
+ */
+ char * p;
+ p = tbuffer + 2 + strlen(cm_NetbiosName) + 1;
+ if ( !_strnicmp("all", p, 3) )
+ p += 4;
+
+ for (i = 0; *p && *p != '\\'; i++,p++ ) {
+ shareName[i] = *p;
+ }
+ p++; /* skip past trailing slash */
+ shareName[i] = 0; /* terminate string */
+
+ shareFound = smb_FindShare(ioctlp->fidp->vcp, ioctlp->uidp, shareName, &sharePath);
+ if ( shareFound ) {
+ /* we found a sharename, therefore use the resulting path */
+ code = cm_NameI(cm_rootSCachep, ioctlp->prefix->data,
+ CM_FLAG_CASEFOLD | CM_FLAG_FOLLOW,
+ userp, sharePath, reqp, &substRootp);
+ free(sharePath);
+ if (code) return code;
+
+ code = cm_NameI(substRootp, p, CM_FLAG_CASEFOLD | CM_FLAG_FOLLOW,
+ userp, NULL, reqp, scpp);
+ if (code) return code;
+ } else {
+ /* otherwise, treat the name as a cellname mounted off the afs root.
+ * This requires that we reconstruct the shareName string with
+ * leading and trailing slashes.
+ */
+ p = tbuffer + 2 + strlen(cm_NetbiosName) + 1;
+ if ( !_strnicmp("all", p, 3) )
+ p += 4;
+
+ shareName[0] = '/';
+ for (i = 1; *p && *p != '\\'; i++,p++ ) {
+ shareName[i] = *p;
+ }
+ p++; /* skip past trailing slash */
+ shareName[i++] = '/'; /* add trailing slash */
+ shareName[i] = 0; /* terminate string */
+
+ code = cm_NameI(cm_rootSCachep, ioctlp->prefix->data,
+ CM_FLAG_CASEFOLD | CM_FLAG_FOLLOW,
+ userp, shareName, reqp, &substRootp);
+ if (code) return code;
+
+ code = cm_NameI(substRootp, p, CM_FLAG_CASEFOLD | CM_FLAG_FOLLOW,
+ userp, NULL, reqp, scpp);
+ if (code) return code;
+ }
+ } else {
+ code = cm_NameI(cm_rootSCachep, ioctlp->prefix->data,
+ CM_FLAG_CASEFOLD | CM_FLAG_FOLLOW,
+ userp, ioctlp->tidPathp, reqp, &substRootp);
+ if (code) return code;
code = cm_NameI(substRootp, tbuffer, CM_FLAG_FOLLOW,
- userp, NULL, reqp, scpp);
- if (code) return code;
-
+ userp, NULL, reqp, scpp);
+ if (code) return code;
+ }
+
/* # of bytes of path */
code = strlen(ioctlp->inDatap) + 1;
ioctlp->inDatap += code;
for(cp = cm_allCellsp; cp; cp=cp->nextp)
{
long code;
- top:
/* delete all previous server lists - cm_FreeServerList will ask for write on cm_ServerLock*/
cm_FreeServerList(&cp->vlServersp);
cp->vlServersp = NULL;
code = cm_SearchCellFile(cp->namep, cp->namep, cm_AddCellProc, cp);
- if (code) {
#ifdef AFS_AFSDB_ENV
+ if (code) {
if (cm_dnsEnabled) {
int ttl;
code = cm_SearchCellByDNS(cp->namep, cp->namep, &ttl, cm_AddCellProc, cp);
- if ( code ) {
- if ( cm_allCellsp == cp )
- cm_allCellsp = cp->nextp;
- else {
- for(tcp = cm_allCellsp; tcp->nextp; tcp=tcp->nextp) {
- if ( tcp->nextp == cp ) {
- tcp->nextp = cp->nextp;
- break;
- }
- }
- }
-
- lock_FinalizeMutex(&cp->mx);
- free(cp->namep);
- }
- else { /* got cell from DNS */
+ if ( code == 0 ) { /* got cell from DNS */
cp->flags |= CM_CELLFLAG_DNS;
+ cp->flags &= ~CM_CELLFLAG_VLSERVER_INVALID;
cp->timeout = time(0) + ttl;
}
}
-#endif /* AFS_AFSDB_ENV */
+ }
+ else {
+ cp->flags &= ~CM_CELLFLAG_DNS;
}
+#endif /* AFS_AFSDB_ENV */
if (code) {
- tcp = cp;
- cp = cp->nextp;
- free(tcp);
- goto top;
+ cp->flags |= CM_CELLFLAG_VLSERVER_INVALID;
}
- else
+ else {
+ cp->flags &= ~CM_CELLFLAG_VLSERVER_INVALID;
cm_RandomizeServer(&cp->vlServersp);
+ }
}
lock_ReleaseWrite(&cm_cellLock);