/*
* Copyright 2000, International Business Machines Corporation and others.
* All Rights Reserved.
- *
+ *
* This software has been released under the terms of the IBM Public
* License. For details, see the LICENSE file in the top-level source
* directory or online at http://www.openafs.org/dl/license10.html
#include <ws2tcpip.h>
extern "C" {
+#include <afsconfig.h>
#include <afs/param.h>
+#include <roken.h>
#include <afs/stds.h>
}
extern "C" {
#include <rx/rx_globals.h>
-#include "fs.h"
#include "fs_utils.h"
+#include "fs_acl.h"
#include <afs/afsint.h>
#include <afs/afs_consts.h>
#include <afs/cellconfig.h>
+#include <afs/ptserver.h>
+#include <afs/ptuser.h>
#include <afs/vldbint.h>
#include <afs/volser.h>
#include <afs/auth.h>
#include <cm_user.h>
#include <cm_scache.h>
#include <cm_ioctl.h>
+#include <cm_config.h>
}
#define STRSAFE_NO_DEPRECATE
#include <strsafe.h>
+/*
+ * the NO_CALLER symbol is used to document functions
+ * that are present in this file but have no caller
+ */
+#define NO_CALLER
+
+
#define PCCHAR(str) ((char *)(const char *)(str))
#define VL_NOENT (363524L)
#define MAXHOSTCHARS 64
#define MAXHOSTSPERCELL 8
-static char space[AFS_PIOCTL_MAXSIZE];
-static char tspace[1024];
-
static struct ubik_client *uclient;
static int rxInitDone = 0;
static char pn[] = "fs";
}
};
-long pioctl_T(const CString& path, long opcode, struct ViceIoctl * blob, int follow)
+long
+pioctl_T(const CString& path, long opcode, struct ViceIoctl * blob, int follow)
{
CStringUtf8 upath(path);
#define Utf8ToCString(cs) (cs)
#endif
-
-
-static int
+static int NO_CALLER
VLDBInit(int noAuthFlag, struct afsconf_cell *info)
{
afs_int32 code;
- code = ugen_ClientInit(noAuthFlag, (char *)AFSDIR_CLIENT_ETC_DIRPATH,
- info->name, 0, &uclient,
+ code = ugen_ClientInit(noAuthFlag, (char *)AFSDIR_CLIENT_ETC_DIRPATH,
+ info->name, 0, &uclient,
NULL, pn, rxkad_clear,
VLDB_MAXSERVERS, AFSCONF_VLDBSERVICE, 50,
0, 0, USER_SERVICE_ID);
FILE *fp;
code = GetWindowsDirectoryA(wdir, sizeof(wdir));
- if (code == 0 || code > sizeof(wdir))
+ if (code == 0 || code > sizeof(wdir))
return FALSE;
/* add trailing backslash, if required */
fp = fopen(wdir, rwp);
return fp;
-}
+}
-CString StripPath(CString& strPath)
+CString StripPath(const CString& strPath)
{
int nIndex = strPath.ReverseFind('\\');
return strFile;
}
-CStringArray& StripPath(CStringArray& files)
+CStringArray&
+StripPath(CStringArray& files)
{
for (int i = 0; i < files.GetSize(); i++)
files[i] = StripPath(files[i]);
return files;
}
-void Flush(const CStringArray& files)
+void
+Flush(const CStringArray& files)
{
LONG code;
struct ViceIoctl blob;
error = 1;
if (errno == EMFILE)
ShowMessageBox(IDS_FLUSH_FAILED, MB_ICONERROR, IDS_FLUSH_FAILED, files[i]);
- else
+ else
ShowMessageBox(IDS_FLUSH_ERROR, MB_ICONERROR, IDS_FLUSH_ERROR, files[i], strerror(errno));
}
- }
+ }
if (!error)
ShowMessageBox(IDS_FLUSH_OK, MB_ICONINFORMATION, IDS_FLUSH_OK);
-}
+}
-void FlushVolume(const CStringArray& files)
+void
+FlushVolume(const CStringArray& files)
{
LONG code;
struct ViceIoctl blob;
error = 1;
ShowMessageBox(IDS_FLUSH_VOLUME_ERROR, MB_ICONERROR, IDS_FLUSH_VOLUME_ERROR, files[i], strerror(errno));
}
- }
+ }
if (!code)
ShowMessageBox(IDS_FLUSH_VOLUME_OK, MB_ICONINFORMATION, IDS_FLUSH_VOLUME_OK);
-}
+}
-void WhichCell(CStringArray& files)
+void NO_CALLER
+WhichCell(CStringArray& files)
{
LONG code;
struct ViceIoctl blob;
HOURGLASS hourglass;
for (int i = 0; i < files.GetSize(); i++) {
+ char space[AFS_PIOCTL_MAXSIZE];
+
blob.in_size = 0;
blob.out_size = AFS_PIOCTL_MAXSIZE;
blob.out = space;
space[AFS_PIOCTL_MAXSIZE - 1] = '\0';
results.Add(Utf8ToCString(space));
}
- }
+ }
LoadString (str, IDS_SHOW_CELL);
LoadString (str2, IDS_SHOW_CELL_COLUMN);
dlg.DoModal();
}
-void WSCellCmd()
+void NO_CALLER
+WSCellCmd(void)
{
+ char space[AFS_PIOCTL_MAXSIZE];
LONG code;
struct ViceIoctl blob;
-
+
HOURGLASS hourglass;
blob.in_size = 0;
code = pioctl((char *) 0, VIOC_GET_WS_CELL, &blob, 1);
- if (code) {
- //Die(errno, (char *) 0);
- }
- //else
- //printf("This workstation belongs to cell '%s'\n", space);
+ /*
+ * Cell name is left in 'space' as side effect.
+ * At present no callers of this function.
+ */
}
-BOOL CheckVolumes()
+BOOL NO_CALLER
+CheckVolumes(void)
{
LONG code;
struct ViceIoctl blob;
-
+
blob.in_size = 0;
blob.out_size = 0;
code = pioctl(0, VIOCCKBACK, &blob, 1);
return TRUE;
}
-void SetCacheSizeCmd(LONG nNewCacheSize)
+void NO_CALLER
+SetCacheSizeCmd(LONG nNewCacheSize)
{
LONG code;
struct ViceIoctl blob;
-
+
HOURGLASS hourglass;
blob.in = (char *) &nNewCacheSize;
blob.out_size = 0;
code = pioctl(0, VIOCSETCACHESIZE, &blob, 1);
- //if (code)
- // Die(errno, (char *) 0);
- //else
- // printf("New cache size set.\n");
+
+ /* error handling? */
}
-void WhereIs(CStringArray& files)
+void NO_CALLER
+WhereIs(CStringArray& files)
{
LONG code;
struct ViceIoctl blob;
HOURGLASS hourglass;
for (int i = 0; i < files.GetSize(); i++) {
+ char space[AFS_PIOCTL_MAXSIZE];
+
blob.out_size = AFS_PIOCTL_MAXSIZE;
blob.in_size = 0;
blob.out = space;
CResultsDlg dlg(SHOW_FILE_SERVERS_HELP_ID);
dlg.SetContents(str, str2, resultFiles, servers);
dlg.DoModal();
-}
+}
static int
CMtoUNIXerror(int cm_code)
}
}
-CString GetAfsError(int code, const TCHAR *filename)
+CString
+GetAfsError(int code, const TCHAR *filename)
{
CString strMsg;
if (code == EINVAL) {
if (filename)
strMsg.Format(_T("Invalid argument; it is possible that the file is not in AFS"));
- else
+ else
strMsg.Format(_T("Invalid argument"));
} else if (code == ENOENT) {
- if (filename)
+ if (filename)
strMsg.Format(_T("The file does not exist"));
- else
+ else
strMsg.Format(_T("No such file returned"));
} else if (code == EROFS) {
strMsg.Format(_T("You can not change a backup or readonly volume"));
}
-/************************************************************************
-************************** ACL Code *************************************
-************************************************************************/
-
-typedef char sec_rgy_name_t[1025]; /* A DCE definition */
-
-struct AclEntry {
- struct AclEntry *next;
- char name[MAXNAME];
- LONG rights;
-};
-
-struct Acl {
- int dfs; // Originally true if a dfs acl; now also the type
- // of the acl (1, 2, or 3, corresponding to object,
- // initial dir, or initial object).
- sec_rgy_name_t cell; // DFS cell name
- int nplus;
- int nminus;
- struct AclEntry *pluslist;
- struct AclEntry *minuslist;
-};
-
-int foldcmp (char *a, char *b)
+static int
+foldcmp (char *a, char *b)
{
char t, u;
while (1) {
}
}
-extern "C" void ZapList(struct AclEntry *alist)
-{
- struct AclEntry *tp, *np;
-
- for (tp = alist; tp; tp = np) {
- np = tp->next;
- free(tp);
- }
-}
-
-extern "C" void ZapAcl (struct Acl *acl)
-{
- ZapList(acl->pluslist);
- ZapList(acl->minuslist);
- free(acl);
-}
-
-extern "C" int PruneList (struct AclEntry **ae, int dfs)
-{
- struct AclEntry **lp = ae;
- struct AclEntry *te, *ne;
- LONG ctr = 0;
-
- for (te = *ae; te; te = ne) {
- if ((!dfs && te->rights == 0) || te->rights == -1) {
- *lp = te->next;
- ne = te->next;
- free(te);
- ctr++;
- }
- else {
- ne = te->next;
- lp = &te->next;
- }
- }
-
- return ctr;
-}
-
-char *SkipLine (char *astr)
-{
- while (*astr != '\n')
- astr++;
-
- astr++;
-
- return astr;
-}
-
-/* tell if a name is 23 or -45 (digits or minus digits), which are bad names we must prune */
-static int BadName(char *aname)
-{
- int tc;
-
- /* all must be '-' or digit to be bad */
- while (tc = *aname++) {
- if ((tc != '-') && (tc < '0' || tc > '9'))
- return 0;
- }
-
- return 1;
-}
-
-CString GetRightsString(LONG arights, int dfs)
+CString
+GetRightsString(LONG arights, int dfs)
{
CString str;
if (arights & DFS_DELETE) str += _T("d"); else printf(_T("-"));
if (arights & (DFS_USRALL)) str += _T("+");
*/
- }
+ }
return str;
}
-char *AclToString(struct Acl *acl)
-{
- static char mydata[AFS_PIOCTL_MAXSIZE];
- char tstring[AFS_PIOCTL_MAXSIZE];
- char dfsstring[30];
- struct AclEntry *tp;
-
- if (acl->dfs)
- sprintf(dfsstring, " dfs:%d %s", acl->dfs, acl->cell);
- else
- dfsstring[0] = '\0';
- sprintf(mydata, "%d%s\n%d\n", acl->nplus, dfsstring, acl->nminus);
-
- for(tp = acl->pluslist; tp; tp = tp->next) {
- sprintf(tstring, "%s %d\n", tp->name, tp->rights);
- strcat(mydata, tstring);
- }
-
- for(tp = acl->minuslist; tp; tp = tp->next) {
- sprintf(tstring, "%s %d\n", tp->name, tp->rights);
- strcat(mydata, tstring);
- }
-
- return mydata;
-}
-
-struct Acl *EmptyAcl(const CString& strCellName)
+struct Acl *
+EmptyAcl(const CString& strCellName)
{
struct Acl *tp;
CStringUtf8 ustrCell(strCellName);
-
+
tp = (struct Acl *)malloc(sizeof (struct Acl));
tp->nplus = tp->nminus = 0;
tp->pluslist = tp->minuslist = 0;
return tp;
}
-struct Acl *EmptyAcl(char *astr)
-{
- struct Acl *tp;
- int junk;
-
- tp = (struct Acl *)malloc(sizeof (struct Acl));
- tp->nplus = tp->nminus = 0;
- tp->pluslist = tp->minuslist = 0;
- tp->dfs = 0;
- if (astr == NULL || sscanf(astr, "%d dfs:%d %s", &junk, &tp->dfs, tp->cell) <= 0) {
- tp->dfs = 0;
- tp->cell[0] = '\0';
- }
- return tp;
-}
-
-struct Acl *
-ParseAcl (char *astr)
-{
- int nplus, nminus, i, trights, ret;
- char tname[MAXNAME];
- struct AclEntry *first, *next, *last, *tl;
- struct Acl *ta;
-
- ta = EmptyAcl(NULL);
- if (astr == NULL || strlen(astr) == 0)
- return ta;
-
- ret = sscanf(astr, "%d dfs:%d %s", &ta->nplus, &ta->dfs, ta->cell);
- if (ret <= 0) {
- free(ta);
- return NULL;
- }
- astr = SkipLine(astr);
- ret = sscanf(astr, "%d", &ta->nminus);
- if (ret <= 0) {
- free(ta);
- return NULL;
- }
- astr = SkipLine(astr);
-
- nplus = ta->nplus;
- nminus = ta->nminus;
-
- last = 0;
- first = 0;
- for(i=0;i<nplus;i++) {
- ret = sscanf(astr, "%100s %d", tname, &trights);
- if (ret <= 0)
- goto nplus_err;
- astr = SkipLine(astr);
- tl = (struct AclEntry *) malloc(sizeof (struct AclEntry));
- if (tl == NULL)
- goto nplus_err;
- if (!first)
- first = tl;
- strcpy(tl->name, tname);
- tl->rights = trights;
- tl->next = 0;
- if (last)
- last->next = tl;
- last = tl;
- }
- ta->pluslist = first;
-
- last = 0;
- first = 0;
- for(i=0;i<nminus;i++) {
- ret = sscanf(astr, "%100s %d", tname, &trights);
- if (ret <= 0)
- goto nminus_err;
- astr = SkipLine(astr);
- tl = (struct AclEntry *) malloc(sizeof (struct AclEntry));
- if (tl == NULL)
- goto nminus_err;
- if (!first)
- first = tl;
- strcpy(tl->name, tname);
- tl->rights = trights;
- tl->next = 0;
- if (last)
- last->next = tl;
- last = tl;
- }
- ta->minuslist = first;
-
- return ta;
-
- nminus_err:
- for (;first; first = next) {
- next = first->next;
- free(first);
- }
- first = ta->pluslist;
-
- nplus_err:
- for (;first; first = next) {
- next = first->next;
- free(first);
- }
- free(ta);
- return NULL;
-}
-
-/* clean up an access control list of its bad entries; return 1 if we made
- any changes to the list, and 0 otherwise */
-extern "C" int CleanAcl(struct Acl *aa)
-{
- struct AclEntry *te, **le, *ne;
- int changes;
-
- HOURGLASS hourglass;
-
- /* Don't correct DFS ACL's for now */
- if (aa->dfs)
- return 0;
-
- /* prune out bad entries */
- changes = 0; /* count deleted entries */
- le = &aa->pluslist;
- for(te = aa->pluslist; te; te = ne) {
- ne = te->next;
- if (BadName(te->name)) {
- /* zap this dude */
- *le = te->next;
- aa->nplus--;
- free(te);
- changes++;
- }
- else
- le = &te->next;
- }
-
- le = &aa->minuslist;
-
- for(te = aa->minuslist; te; te = ne) {
- ne = te->next;
- if (BadName(te->name)) {
- /* zap this dude */
- *le = te->next;
- aa->nminus--;
- free(te);
- changes++;
- }
- else
- le = &te->next;
- }
-
- return changes;
-}
-
-void CleanACL(CStringArray& names)
+void
+CleanACL(CStringArray& names)
{
LONG code;
struct Acl *ta;
HOURGLASS hourglass;
for (int i = 0; i < names.GetSize(); i++) {
+ char space[AFS_PIOCTL_MAXSIZE];
+
blob.out_size = AFS_PIOCTL_MAXSIZE;
blob.in_size = 0;
blob.out = space;
continue;
}
- ta = ParseAcl(space);
+ ta = ParseAcl(space, AFS_PIOCTL_MAXSIZE);
if (ta == NULL) {
ShowMessageBox(IDS_INVALID_ACL_DATA, MB_ICONERROR, IDS_INVALID_ACL_DATA);
continue;
continue;
}
- changes = CleanAcl(ta);
+ changes = CleanAcl(ta, NULL);
if (!changes)
continue;
blob.in = AclToString(ta);
blob.in_size = strlen((char *)blob.in) + 1;
blob.out_size = 0;
-
+
code = pioctl_T(names[i], VIOCSETAL, &blob, 1);
if (code) {
if (errno == EINVAL) {
}
}
}
-}
+}
// Derived from fs.c's ListAclCmd
-BOOL GetRights(const CString& strDir, CStringArray& strNormal, CStringArray& strNegative)
+BOOL
+GetRights(const CString& strDir, CStringArray& strNormal, CStringArray& strNegative)
{
LONG code;
struct Acl *ta;
struct ViceIoctl blob;
struct AclEntry *te;
int idf = 0; //getidf(as, parm_listacl_id);
-
+ char space[AFS_PIOCTL_MAXSIZE];
HOURGLASS hourglass;
blob.out_size = AFS_PIOCTL_MAXSIZE;
blob.in_size = idf;
blob.in = blob.out = space;
-
+
code = pioctl_T(strDir, VIOCGETAL, &blob, 1);
if (code) {
ShowMessageBox(IDS_GETRIGHTS_ERROR, MB_ICONERROR, IDS_GETRIGHTS_ERROR, strDir, GetAfsError(errno));
return FALSE;
}
- ta = ParseAcl(space);
+ ta = ParseAcl(space, AFS_PIOCTL_MAXSIZE);
if (ta == NULL) {
ShowMessageBox(IDS_INVALID_ACL_DATA, MB_ICONERROR, IDS_INVALID_ACL_DATA);
return FALSE;
return TRUE;
}
-struct AclEntry *FindList(struct AclEntry *pCurEntry, const char *entryName)
+struct AclEntry *
+FindList(struct AclEntry *pCurEntry, const char *entryName)
{
while (pCurEntry) {
if (!foldcmp(pCurEntry->name, PCCHAR(entryName)))
return pCurEntry;
pCurEntry = pCurEntry->next;
}
-
+
return 0;
}
-void ChangeList(struct Acl *pAcl, BYTE bNormalRights, const CString & entryName, LONG nEntryRights)
+void
+ChangeList(struct Acl *pAcl, BYTE bNormalRights, const CString & entryName, LONG nEntryRights)
{
ASSERT(pAcl);
ASSERT(entryName);
-
+
struct AclEntry *pEntry;
CStringUtf8 uEntryName(entryName);
/* Otherwise we make a new item and plug in the new data. */
pEntry = (struct AclEntry *) malloc(sizeof (struct AclEntry));
ASSERT(pEntry);
-
+
strcpy(pEntry->name, uEntryName);
pEntry->rights = nEntryRights;
-
+
if (bNormalRights) {
pEntry->next = pAcl->pluslist;
pAcl->pluslist = pEntry;
}
}
-enum rtype {add, destroy, deny};
-
-static LONG Convert(const CString& strRights, int dfs, enum rtype *rtypep)
+static LONG
+Convert(const CString& strRights, int dfs, enum rtype *rtypep)
{
int i, len;
LONG mode;
*rtypep = add; /* add rights, by default */
- if (strRights == _T("read"))
+ if (strRights == _T("read"))
return PRSFS_READ | PRSFS_LOOKUP;
- if (strRights == _T("write"))
+ if (strRights == _T("write"))
return PRSFS_READ | PRSFS_LOOKUP | PRSFS_INSERT | PRSFS_DELETE | PRSFS_WRITE | PRSFS_LOCK;
- if (strRights == _T("mail"))
+ if (strRights == _T("mail"))
return PRSFS_INSERT | PRSFS_LOCK | PRSFS_LOOKUP;
- if (strRights == _T("all"))
+ if (strRights == _T("all"))
return PRSFS_READ | PRSFS_LOOKUP | PRSFS_INSERT | PRSFS_DELETE | PRSFS_WRITE | PRSFS_LOCK | PRSFS_ADMINISTER;
-
+
if (strRights == _T("none")) {
*rtypep = destroy; /* Remove entire entry */
return 0;
fprintf(stderr, "illegal rights character '%c'.\n", c);
exit(1);
}
- }
+ }
return mode;
}
-BOOL SaveACL(const CString& strCellName, const CString& strDir, const CStringArray& normal, const CStringArray& negative)
+BOOL
+SaveACL(const CString& strCellName, const CString& strDir, const CStringArray& normal, const CStringArray& negative)
{
LONG code;
struct ViceIoctl blob;
ShowMessageBox(IDS_SAVE_ACL_EINVAL_ERROR, MB_ICONERROR, IDS_SAVE_ACL_EINVAL_ERROR, strDir);
else
ShowMessageBox(IDS_SAVE_ACL_ERROR, MB_ICONERROR, IDS_SAVE_ACL_ERROR, strDir, GetAfsError(errno, strDir));
- }
+ }
ZapAcl(pAcl);
return (code == 0);
}
-BOOL CopyACL(const CString& strToDir, const CStringArray& normal, const CStringArray& negative, BOOL bClear)
+BOOL
+CopyACL(const CString& strToDir, const CStringArray& normal, const CStringArray& negative, BOOL bClear)
{
LONG code;
struct ViceIoctl blob;
struct Acl *pToAcl;
int idf = 0; // getidf(as, parm_copyacl_id);
-
+ char space[AFS_PIOCTL_MAXSIZE];
HOURGLASS hourglass;
// Get ACL to copy to
blob.out_size = AFS_PIOCTL_MAXSIZE;
blob.in_size = idf;
blob.in = blob.out = space;
-
+
code = pioctl_T(strToDir, VIOCGETAL, &blob, 1);
if (code) {
ShowMessageBox(IDS_ACL_READ_ERROR, MB_ICONERROR, IDS_ACL_READ_ERROR, strToDir, GetAfsError(errno, strToDir));
return FALSE;
}
-
- if (bClear)
+
+ if (bClear)
pToAcl = EmptyAcl(space);
- else
- pToAcl = ParseAcl(space);
+ else
+ pToAcl = ParseAcl(space, AFS_PIOCTL_MAXSIZE);
if (pToAcl == NULL) {
ShowMessageBox(IDS_INVALID_ACL_DATA, MB_ICONERROR, IDS_INVALID_ACL_DATA);
return FALSE;
}
- CleanAcl(pToAcl);
+ CleanAcl(pToAcl, NULL);
if (pToAcl->dfs) {
ShowMessageBox(IDS_NO_DFS_COPY_ACL, MB_ICONERROR, IDS_NO_DFS_COPY_ACL, strToDir);
ZapAcl(pToAcl);
if (errno == EINVAL)
ShowMessageBox(IDS_COPY_ACL_EINVAL_ERROR, MB_ICONERROR, IDS_COPY_ACL_EINVAL_ERROR, strToDir);
- else
+ else
ShowMessageBox(IDS_COPY_ACL_ERROR, MB_ICONERROR, IDS_COPY_ACL_ERROR, strToDir, GetAfsError(errno, strToDir));
return FALSE;
}
return TRUE;
}
-CString ParseMountPoint(const CString strFile, CString strMountPoint)
+CString
+ParseMountPoint(const CString strFile, CString strMountPoint)
{
CString strType;
CString strVolume;
if (nColon >= 0) {
strCell = strMountPoint.Mid(1, nColon - 1);
strVolume = strMountPoint.Mid(nColon + 1);
- } else
+ } else {
strVolume = strMountPoint.Mid(1);
+ strCell = _T("(local)");
+ }
- strMountPointInfo = strFile + _T("\t") + strVolume + _T("\t") + strCell + _T("\t") + strType;
+ strMountPointInfo = _T("=> ") + strVolume + _T(" : ") + strCell + _T(" cell [") + strType + _T("]");
return strMountPointInfo;
-}
+}
-CString ParseSymlink(const CString strFile, CString strSymlink)
+CString
+ParseSymlink(const CString strFile, CString strSymlink)
{
CString strSymlinkInfo;
- strSymlinkInfo = strFile + _T("\t") + strSymlink;
+ strSymlinkInfo = _T("-> ") + strSymlink;
return strSymlinkInfo;
-}
+}
-BOOL IsPathInAfs(const CString & strPath)
+BOOL
+GetFID(const CString& path, CString& fidstring, BOOL bLiteral)
+{
+ struct ViceIoctl blob;
+ cm_ioctlQueryOptions_t options;
+ cm_fid_t fid;
+ int code;
+
+ memset(&options, 0, sizeof(options));
+ options.size = sizeof(options);
+ options.field_flags |= CM_IOCTL_QOPTS_FIELD_LITERAL;
+ options.literal = bLiteral ? 1 : 0;
+ blob.in_size = options.size; /* no variable length data */
+ blob.in = &options;
+ blob.out_size = sizeof(cm_fid_t);
+ blob.out = (char *) &fid;
+
+ code = pioctl_T(path, VIOCGETFID, &blob, 1);
+ fidstring.Empty();
+ if (code == 0) {
+ fidstring.Format( TEXT("%lu.%lu.%lu"),
+ fid.volume,
+ fid.vnode,
+ fid.unique);
+ return TRUE;
+ }
+ return FALSE;
+}
+
+BOOL
+IsPathInAfs(const CString & strPath)
{
struct ViceIoctl blob;
cm_ioctlQueryOptions_t options;
return TRUE;
}
-static int
+static int
IsFreelanceRoot(const CString& apath)
{
struct ViceIoctl blob;
afs_int32 code;
+ char space[AFS_PIOCTL_MAXSIZE];
blob.in_size = 0;
blob.out_size = AFS_PIOCTL_MAXSIZE;
return 1; /* assume it is because it is more restrictive that way */
}
-static const char * NetbiosName(void)
+static const char *
+NetbiosName(void)
{
static char buffer[1024] = "AFS";
HKEY parmKey;
return buffer;
}
-static void FixNetbiosPath(CString& path)
+static void
+FixNetbiosPath(CString& path)
{
if (!IsPathInAfs(path)) {
CString nbroot;
const char * nbname = NetbiosName();
-#ifdef UNICODE
- nbroot.Format(_T("\\\\%S\\"), nbname);
-#else
nbroot.Format(_T("\\\\%s\\"), nbname);
-#endif
if (nbroot.CompareNoCase(path) == 0) {
path.Append(_T("all\\"));
#define AFSCLIENT_ADMIN_GROUPNAME "AFS Client Admins"
-static BOOL IsAdmin (void)
+static BOOL
+IsAdmin (void)
{
static BOOL fAdmin = FALSE;
static BOOL fTested = FALSE;
pszRefDomain = (TCHAR *)malloc(dwSize2);
if (!LookupAccountName(NULL, pszAdminGroup, psidAdmin, &dwSize, pszRefDomain, &dwSize2, &snu)) {
- /* We can't lookup the group now even though we looked it up earlier.
+ /* We can't lookup the group now even though we looked it up earlier.
Could this happen? */
fAdmin = TRUE;
} else {
return fAdmin;
}
-CString Parent(const CString& path)
+CString
+Parent(const CString& path)
{
int last_slash = path.ReverseFind(_T('\\'));
}
}
}
-
-CString LastComponent(const CString& path)
+
+CString
+LastComponent(const CString& path)
{
int last_slash = path.ReverseFind(_T('\\'));
}
static CString
-GetCell(const CString & path)
+GetCell(const CString & path, BOOL bFollow = TRUE);
+
+static CString
+GetCell(const CString & path, BOOL bFollow)
{
char cellname[MAXCELLCHARS];
afs_int32 code;
}
-BOOL ListMount(CStringArray& files)
+BOOL
+ListMount(CStringArray& files)
{
LONG code;
struct ViceIoctl blob;
CStringUtf8 last_component; /* Last component of true name */
CStringArray mountPoints;
-
+
HOURGLASS hourglass;
error = 0;
for (int i = 0; i < files.GetSize(); i++) {
int last_slash = files[i].ReverseFind(_T('\\'));
+ char space[AFS_PIOCTL_MAXSIZE];
if (last_slash != -1) {
last_component.SetString( files[i].Mid(last_slash + 1) );
ShowMessageBox(IDS_MOUNT_POINT_ERROR, MB_ICONERROR, IDS_MOUNT_POINT_ERROR, GetAfsError(errno, strDir));
return FALSE;
}
-
+
return TRUE;
}
-/*
-*/
-long fs_ExtractDriveLetter(const char *inPathp, char *outPathp)
-{
- if (inPathp[0] != 0 && inPathp[1] == ':') {
- /* there is a drive letter */
- *outPathp++ = *inPathp++;
- *outPathp++ = *inPathp++;
- *outPathp++ = 0;
- }
- else *outPathp = 0;
-
- return 0;
-}
-
-/* strip the drive letter from a component */
-long fs_StripDriveLetter(const char *inPathp, char *outPathp, long outSize)
-{
- char tempBuffer[1000];
- strcpy(tempBuffer, inPathp);
- if (tempBuffer[0] != 0 && tempBuffer[1] == ':') {
- /* drive letter present */
- strcpy(outPathp, tempBuffer+2);
- }
- else {
- /* no drive letter present */
- strcpy(outPathp, tempBuffer);
- }
- return 0;
-}
-
-
-BOOL RemoveSymlink(const CString& strName)
+BOOL
+RemoveSymlink(const CString& strName)
{
BOOL error = FALSE;
INT code=0;
struct ViceIoctl blob;
char lsbuffer[1024];
-
+
HOURGLASS hourglass;
CString strParent = Parent(strName);
ustrLast.ReleaseBuffer();
return (code == 0);
-}
+}
-BOOL IsSymlink(const CString& strName)
+BOOL
+IsSymlink(const CString& strName)
{
struct ViceIoctl blob;
int code;
-
+ char space[AFS_PIOCTL_MAXSIZE];
HOURGLASS hourglass;
CStringUtf8 ustrLast(LastComponent(strName));
ustrLast.ReleaseBuffer();
return (code==0);
-}
+}
-BOOL IsMountPoint(const CString& path)
+BOOL
+IsMountPoint(const CString& path)
{
LONG code = 0;
struct ViceIoctl blob;
mountpoint.ReleaseBuffer();
return (code==0);
-}
+}
/*
* (or ``.'' if none is provided)
* tp: Set to point to the actual name of the mount point to nuke.
*/
-BOOL RemoveMount(CStringArray& files)
+BOOL
+RemoveMount(CStringArray& files)
{
LONG code = 0;
struct ViceIoctl blob;
results.Add(GetMessageString(IDS_ERROR, GetAfsError(errno, StripPath(files[i]))));
} else
results.Add(GetMessageString(IDS_DELETED));
- }
+ }
LoadString (str, IDS_REMOVE_MP);
LoadString (str2, IDS_REMOVE_MP_COLUMN);
return !error;
}
-BOOL GetVolumeInfo(CString strFile, CVolInfo& volInfo)
+BOOL
+GetVolumeInfo(CString strFile, CVolInfo& volInfo, BOOL bFollow)
{
LONG code;
struct ViceIoctl blob;
struct VolumeStatus *status;
char *name;
-
+ char space[AFS_PIOCTL_MAXSIZE];
HOURGLASS hourglass;
+ CString strTarget = bFollow ? strFile : Parent(strFile);
- volInfo.m_strFilePath = strFile;
- volInfo.m_strFileName = StripPath(strFile);
+ volInfo.m_strFilePath = strTarget;
+ volInfo.m_strFileName = StripPath(strTarget);
/*
volInfo.m_strName = "VolumeName";
blob.in_size = 0;
blob.out = space;
- code = pioctl_T(strFile, VIOCGETVOLSTAT, &blob, 1);
+ code = pioctl_T(strTarget, VIOCGETVOLSTAT, &blob, 1);
if (code || blob.out_size < sizeof(*status)) {
- volInfo.m_strErrorMsg = GetAfsError(errno, strFile);
+ volInfo.m_strErrorMsg = GetAfsError(errno, strTarget);
return FALSE;
}
volInfo.m_nPartFree = status->PartBlocksAvail;
volInfo.m_nDup = -1;
+ errno = 0;
+ code = pioctl_T(strTarget, VIOC_PATH_AVAILABILITY, &blob, 1);
+ switch (errno) {
+ case 0:
+ volInfo.m_strAvail =_T("Online");
+ break;
+ case ENXIO:
+ volInfo.m_strAvail = _T("Offline");
+ break;
+ case ENOSYS:
+ volInfo.m_strAvail = _T("Unreachable");
+ break;
+ case EBUSY:
+ volInfo.m_strAvail = _T("Busy");
+ break;
+ default:
+ volInfo.m_strAvail = _T("Unknown");
+ }
+
return TRUE;
}
-
-BOOL SetVolInfo(CVolInfo& volInfo)
+
+BOOL
+SetVolInfo(CVolInfo& volInfo)
{
LONG code;
struct ViceIoctl blob;
struct VolumeStatus *status;
char *input;
-
+ char space[AFS_PIOCTL_MAXSIZE];
HOURGLASS hourglass;
blob.out_size = AFS_PIOCTL_MAXSIZE;
status = (VolumeStatus *)space;
status->MinQuota = -1;
status->MaxQuota = volInfo.m_nNewQuota;
-
+
input = (char *)status + sizeof(*status);
*(input++) = '\0'; /* never set name: this call doesn't change vldb */
*(input++) = '\0'; // No offmsg
fprintf(fp, "\t\t\tOther status fields aren't set\n");
fprintf(fp, "\t\t\t3 nulls follow the VolumeStatus structure.\n");
fprintf(fp, "\tfollow = 1\n");
- fclose(fp);
+ fclose(fp);
}
#endif
return TRUE;
}
-void GetCellName(const CString& cellNamep, struct afsconf_cell *infop)
+void
+GetCellName(const CString& cellNamep, struct afsconf_cell *infop)
{
CStringUtf8 uCellName(cellNamep);
StringCbCopyA(infop->name, sizeof(infop->name), uCellName);
}
-BOOL CheckServers(const CString& strCellName, WHICH_CELLS nCellsToCheck, BOOL bFast)
+BOOL NO_CALLER
+CheckServers(const CString& strCellName, WHICH_CELLS nCellsToCheck, BOOL bFast)
{
LONG code;
struct ViceIoctl blob;
LONG temp = 0;
struct afsconf_cell info;
struct chservinfo checkserv;
-
+ char space[AFS_PIOCTL_MAXSIZE];
HOURGLASS hourglass;
memset(&checkserv, 0, sizeof(struct chservinfo));
}
if (bFast)
temp |= 1; /* set fast flag */
-
+
checkserv.magic = 0x12345678; /* XXX */
checkserv.tflags = temp;
checkserv.tinterval = -1; /* don't change current interval */
dlg.DoModal();
return TRUE;
-}
+}
-BOOL GetTokenInfo(CStringArray& tokenInfo)
+BOOL
+GetTokenInfo(CStringArray& tokenInfo)
{
int cellNum;
int rc;
else {
rc = ktc_GetToken(&serviceName, &token, sizeof(token), &clientName);
if (rc) {
- ShowMessageBox(IDS_GET_TOKENS_UNEXPECTED_ERROR2, MB_ICONERROR, IDS_GET_TOKENS_UNEXPECTED_ERROR2,
+ ShowMessageBox(IDS_GET_TOKENS_UNEXPECTED_ERROR2, MB_ICONERROR, IDS_GET_TOKENS_UNEXPECTED_ERROR2,
serviceName.name, serviceName.instance, serviceName.cell, rc);
continue;
}
else
strUserName = userName;
// printf("User %s's tokens", userName);
-
+
// printf(" for %s%s%s@%s ", serviceName.name, serviceName.instance[0] ? "." : "", serviceName.instance, serviceName.cell);
strCellName = serviceName.cell;
-
+
if (tokenExpireTime <= current_time)
strExpir = "[>> Expired <<]";
// printf("[>> Expired <<]\n");
return TRUE;
}
-UINT MakeSymbolicLink(const CString& strName, const CString& strTarget)
+UINT
+MakeSymbolicLink(const CString& strName, const CString& strTarget)
{
struct ViceIoctl blob;
UINT code;
return 0;
}
-void ListSymbolicLinkPath(const char *strName,char *strPath,UINT nlenPath)
+void NO_CALLER
+ListSymbolicLinkPath(const char *strName,char *strPath,UINT nlenPath)
{
ASSERT(nlenPath<MAX_PATH);
struct ViceIoctl blob;
char true_name[MAX_PATH+1]; /*``True'' dirname (e.g., symlink target)*/
char parent_dir[MAX_PATH+1]; /*Parent directory of true name*/
char *last_component; /*Last component of true name*/
- UINT code;
-
+ UINT code;
+ char space[AFS_PIOCTL_MAXSIZE];
HOURGLASS hourglass;
strcpy(orig_name, strName);
strcpy(space,"???");
ASSERT(strlen(space)<MAX_PATH);
strncpy(strPath,space,nlenPath);
-}
+}
-BOOL ListSymlink(CStringArray& files)
+BOOL NO_CALLER
+ListSymlink(CStringArray& files)
{
LONG code;
struct ViceIoctl blob;
int error;
CStringArray symlinks;
-
+ char space[AFS_PIOCTL_MAXSIZE];
HOURGLASS hourglass;
error = 0;
return !error;
}
+CString
+GetCellName( const CString& strPath, BOOL bFollow )
+{
+ return GetCell(bFollow ? strPath : Parent(strPath));
+}
+
+CString
+GetServer( const CString& strPath, BOOL bFollow )
+{
+ LONG code;
+ struct ViceIoctl blob;
+ CString server;
+ char space[AFS_PIOCTL_MAXSIZE];
+
+ blob.out_size = AFS_PIOCTL_MAXSIZE;
+ blob.in_size = 0;
+ blob.out = space;
+ memset(space, 0, sizeof(space));
+
+ code = pioctl_T(bFollow ? strPath : Parent(strPath), VIOCWHEREIS, &blob, 1);
+ if (code) {
+ server=GetAfsError(errno);
+ } else {
+ LONG *hosts = (LONG *)space;
+
+ for (int j = 0; j < AFS_MAXHOSTS; j++) {
+ if (hosts[j] == 0)
+ break;
+ char *hostName = hostutil_GetNameByINet(hosts[j]);
+ server=hostName;
+ }
+ }
+
+ return server;
+}
+
+void
+GetServers( const CString& strPath, CStringArray& servers, BOOL bFollow )
+{
+ LONG code;
+ struct ViceIoctl blob;
+ char space[AFS_PIOCTL_MAXSIZE];
+
+ blob.out_size = AFS_PIOCTL_MAXSIZE;
+ blob.in_size = 0;
+ blob.out = space;
+ memset(space, 0, sizeof(space));
+
+ code = pioctl_T(bFollow ? strPath : Parent(strPath), VIOCWHEREIS, &blob, 1);
+ if (code) {
+ servers.Add(GetAfsError(errno));
+ } else {
+ LONG *hosts = (LONG *)space;
+
+ for (int j = 0; j < AFS_MAXHOSTS; j++) {
+ if (hosts[j] == 0)
+ break;
+ char *hostName = hostutil_GetNameByINet(hosts[j]);
+ servers.Add(hostName);
+ }
+ }
+}
+
+CString
+GetOwner( const CString& strPath, BOOL bFollow )
+{
+ LONG code;
+ struct ViceIoctl blob;
+ afs_int32 owner[2];
+ CString ret = TEXT("(unknown)");
+
+ blob.in_size = 0;
+ blob.out_size = 2 * sizeof(afs_int32);
+ blob.out = (char *) &owner;
+
+ code = pioctl_T(bFollow ? strPath : Parent(strPath), VIOCGETOWNER, &blob, 1);
+ if (code == 0 && blob.out_size == 2 * sizeof(afs_int32)) {
+ char oname[PR_MAXNAMELEN] = "(unknown)";
+ char confDir[257];
+ CStringUtf8 cell;
+
+ cell = GetCell(strPath, bFollow);
+
+ /* Go to the PRDB and see if this all number username is valid */
+ cm_GetConfigDir(confDir, sizeof(confDir));
+
+ pr_Initialize(1, confDir, PCCHAR(cell));
+ pr_SIdToName(owner[0], oname);
+
+ ret.Empty();
+ ret.Format(TEXT("%s [%d]"), (LPCTSTR)CString(oname), owner[0]);
+ }
+
+ return ret;
+}
+
+CString
+GetGroup( const CString& strPath, BOOL bFollow )
+{
+ LONG code;
+ struct ViceIoctl blob;
+ afs_int32 owner[2];
+ CString ret = TEXT("(unknown)");
+
+ blob.in_size = 0;
+ blob.out_size = 2 * sizeof(afs_int32);
+ blob.out = (char *) &owner;
+
+ code = pioctl_T(bFollow ? strPath : Parent(strPath), VIOCGETOWNER, &blob, 1);
+ if (code == 0 && blob.out_size == 2 * sizeof(afs_int32)) {
+ char gname[PR_MAXNAMELEN] = "(unknown)";
+ char confDir[257];
+ CStringUtf8 cell;
+
+ cell = GetCell(strPath, bFollow);
+
+ /* Go to the PRDB and see if this all number username is valid */
+ cm_GetConfigDir(confDir, sizeof(confDir));
+
+ pr_Initialize(1, confDir, PCCHAR(cell));
+ pr_SIdToName(owner[1], gname);
+
+ ret.Empty();
+ ret.Format(TEXT("%s [%d]"), (LPCTSTR)CString(gname), owner[1]);
+ }
+
+ return ret;
+}
+
+BOOL
+GetUnixModeBits( const CString& strPath, CString& user, CString& group, CString& other, CString& suid )
+{
+ // the strings must match the unix ls command output: "rwx" means read/write/execute permissions
+
+ LONG code;
+ struct ViceIoctl blob;
+ afs_uint32 unixModeBits;
+ CString ret = TEXT("(unknown)");
+
+ user.Empty();
+ group.Empty();
+ other.Empty();
+ suid.Empty();
+
+ blob.in_size = 0;
+ blob.out_size = sizeof(afs_int32);
+ blob.out = (char *) &unixModeBits;
+
+ code = pioctl_T(strPath, VIOC_GETUNIXMODE, &blob, 1);
+ if (code == 0 && blob.out_size == sizeof(afs_uint32)) {
+ if (unixModeBits & S_IRUSR)
+ user += _T("r");
+ if (unixModeBits & S_IWUSR)
+ user += _T("w");
+ if (unixModeBits & S_IXUSR)
+ user += _T("x");
+
+ if (unixModeBits & S_IRGRP)
+ group += _T("r");
+ if (unixModeBits & S_IWGRP)
+ group += _T("w");
+ if (unixModeBits & S_IXGRP)
+ group += _T("x");
+
+ if (unixModeBits & S_IROTH)
+ other += _T("r");
+ if (unixModeBits & S_IWOTH)
+ other += _T("w");
+ if (unixModeBits & S_IXOTH)
+ other += _T("x");
+
+ if (unixModeBits & S_ISUID)
+ suid += _T("s");
+ if (unixModeBits & S_ISGID)
+ suid += _T("g");
+ if (unixModeBits & S_ISVTX)
+ suid += _T("v");
+
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+void
+SetUnixModeBits( const CStringArray& files, const CString& user, const CString& group, const CString& other, const CString& suid )
+{
+ // set the unix file attributes for all paths in 'files'.
+ LONG code;
+ struct ViceIoctl blob;
+ struct {
+ cm_ioctlQueryOptions_t options;
+ afs_uint32 unixModeBits;
+ } inData;
+
+ memset(&inData, 0, sizeof(inData));
+ inData.options.size = sizeof(inData.options);
+ inData.options.field_flags = 0;
+ inData.options.literal = 0; /* always applying to target */
+ blob.in_size = sizeof(inData); /* no variable length data */
+ blob.in = &inData;
+ blob.out = NULL;
+ blob.out_size = 0;
+ inData.unixModeBits = 0;
+
+ if (user.Find(_T('r')) != -1)
+ inData.unixModeBits |= S_IRUSR;
+ if (user.Find(_T('w')) != -1)
+ inData.unixModeBits |= S_IWUSR;
+ if (user.Find(_T('x')) != -1)
+ inData.unixModeBits |= S_IXUSR;
+
+ if (group.Find(_T('r')) != -1)
+ inData.unixModeBits |= S_IRGRP;
+ if (group.Find(_T('w')) != -1)
+ inData.unixModeBits |= S_IWGRP;
+ if (group.Find(_T('x')) != -1)
+ inData.unixModeBits |= S_IXGRP;
+
+ if (other.Find(_T('r')) != -1)
+ inData.unixModeBits |= S_IROTH;
+ if (other.Find(_T('w')) != -1)
+ inData.unixModeBits |= S_IWOTH;
+ if (other.Find(_T('x')) != -1)
+ inData.unixModeBits |= S_IXOTH;
+
+ if (suid.Find(_T('s')) != -1)
+ inData.unixModeBits |= S_ISUID;
+ if (suid.Find(_T('g')) != -1)
+ inData.unixModeBits |= S_ISGID;
+ if (suid.Find(_T('v')) != -1)
+ inData.unixModeBits |= S_ISVTX;
+
+ for (int i = 0; i < files.GetSize(); i++)
+ code = pioctl_T(files[i], VIOC_SETUNIXMODE, &blob, 1);
+}
+
+CString GetMountpoint( const CString& strPath )
+{
+ LONG code;
+ struct ViceIoctl blob;
+ char space[AFS_PIOCTL_MAXSIZE];
+ CString parent_dir; /* Parent directory of true name */
+ CStringUtf8 last_component; /* Last component of true name */
+
+ CString mountPoint;
+
+
+ int last_slash = strPath.ReverseFind(_T('\\'));
+
+ if (last_slash != -1) {
+ last_component.SetString( strPath.Mid(last_slash + 1) );
+ parent_dir.SetString( strPath.Left(last_slash + 1) );
+ FixNetbiosPath(parent_dir);
+ } else {
+ // The path is of the form "C:foo" or just "foo". If
+ // there is a drive, then use the current directory of
+ // that drive. Otherwise we just use '.'.
+
+ if (strPath.GetLength() >= 2 && strPath[1] == _T(':')) {
+ parent_dir.Format(_T("%c:."), strPath[0]);
+ last_component.SetString( strPath.Mid(2) );
+ } else {
+ parent_dir.SetString( _T("."));
+ last_component.SetString( strPath );
+ }
+ }
+
+ blob.in_size = last_component.GetLength() + 1;
+ blob.in = last_component.GetBuffer();
+ blob.out_size = AFS_PIOCTL_MAXSIZE;
+ blob.out = space;
+ memset(space, 0, AFS_PIOCTL_MAXSIZE);
+
+ code = pioctl_T(parent_dir, VIOC_AFS_STAT_MT_PT, &blob, 1);
+
+ last_component.ReleaseBuffer();
+
+ if (code == 0) {
+ int nPos;
+ space[AFS_PIOCTL_MAXSIZE - 1] = '\0';
+ nPos = strlen(space) - 1;
+ if (space[nPos] == '.')
+ space[nPos] = 0;
+ mountPoint = ParseMountPoint(StripPath(strPath), Utf8ToCString(space));
+ } else {
+ if (errno == EINVAL)
+ mountPoint = GetMessageString(IDS_NOT_MOUNT_POINT_ERROR, StripPath(strPath));
+ else
+ mountPoint = GetMessageString(IDS_LIST_MOUNT_POINT_ERROR, GetAfsError(errno, StripPath(strPath)));
+ }
+
+ return mountPoint;
+}
+
+CString GetSymlink( const CString& strPath )
+{
+ LONG code;
+ struct ViceIoctl blob;
+ CString symlink;
+ char space[AFS_PIOCTL_MAXSIZE];
+
+ CString strParent = Parent(strPath);
+ CStringUtf8 ustrLast(LastComponent(strPath));
+
+ FixNetbiosPath(strParent);
+
+ blob.in_size = ustrLast.GetLength() + 1;
+ blob.in = ustrLast.GetBuffer();
+ blob.out_size = AFS_PIOCTL_MAXSIZE;
+ blob.out = space;
+ memset(space, 0, AFS_PIOCTL_MAXSIZE);
+
+ code = pioctl_T(strParent, VIOC_LISTSYMLINK, &blob, 1);
+
+ ustrLast.ReleaseBuffer();
+
+ if (code == 0) {
+ CString syml;
+ int len;
+
+ space[AFS_PIOCTL_MAXSIZE - 1] = '\0';
+ syml = Utf8ToCString(space);
+ len = syml.GetLength();
+
+ if (len > 0) {
+ if (syml[len - 1] == _T('.'))
+ syml.Truncate(len - 1);
+ }
+
+ symlink = ParseSymlink(StripPath(strPath), syml);
+
+ } else {
+ if (errno == EINVAL)
+ symlink = GetMessageString(IDS_NOT_SYMLINK_ERROR, StripPath(strPath));
+ else
+ symlink = GetMessageString(IDS_LIST_MOUNT_POINT_ERROR, GetAfsError(errno, StripPath(strPath)));
+ }
+
+
+ return symlink;
+}