2000-11-04 10:01:08 +00:00
|
|
|
/*
|
|
|
|
* 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
|
|
|
|
*/
|
|
|
|
|
2000-11-04 02:13:13 +00:00
|
|
|
/* Verify that the size of the XFS inode is large enough to hold the XFS
|
|
|
|
* attribute for AFS inode parameters. Check all the mounted /vicep partitions.
|
2001-07-05 17:20:00 +01:00
|
|
|
#include <afsconfig.h>
|
|
|
|
|
|
|
|
|
2000-11-04 02:13:13 +00:00
|
|
|
*/
|
|
|
|
#include <afs/param.h>
|
|
|
|
#ifdef AFS_SGI_XFS_IOPS_ENV
|
|
|
|
#include <errno.h>
|
|
|
|
#include <sys/stat.h>
|
|
|
|
#include <stdio.h>
|
|
|
|
#include <dirent.h>
|
|
|
|
#include <fcntl.h>
|
|
|
|
#include <mntent.h>
|
|
|
|
#include "partition.h"
|
|
|
|
#include <afs/xfsattrs.h>
|
|
|
|
|
|
|
|
char *prog = "xfs_size_check";
|
|
|
|
|
|
|
|
/* Verify that the on disk XFS inodes on the partition are large enough to
|
|
|
|
* hold the AFS attribute. Returns -1 if the attribute can't be set or is
|
|
|
|
* too small to fit in the inode. Returns 0 if the attribute does fit in
|
|
|
|
* the XFS inode.
|
|
|
|
*/
|
|
|
|
#define VERIFY_ERROR -1
|
|
|
|
#define VERIFY_OK 0
|
|
|
|
#define VERIFY_FIX 1
|
2003-07-16 01:28:24 +01:00
|
|
|
static int
|
|
|
|
VerifyXFSInodeSize(char *part)
|
2000-11-04 02:13:13 +00:00
|
|
|
{
|
|
|
|
afs_xfs_attr_t junk;
|
|
|
|
int length = SIZEOF_XFS_ATTR_T;
|
|
|
|
int fd;
|
|
|
|
int code = VERIFY_ERROR;
|
|
|
|
struct fsxattr fsx;
|
|
|
|
|
2003-07-16 01:28:24 +01:00
|
|
|
if (attr_set(part, AFS_XFS_ATTR, &junk, length, ATTR_ROOT) < 0) {
|
2000-11-04 02:13:13 +00:00
|
|
|
if (errno == EPERM) {
|
|
|
|
printf("Must be root to run %s\n", prog);
|
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
return VERIFY_ERROR;
|
|
|
|
}
|
|
|
|
|
2003-07-16 01:28:24 +01:00
|
|
|
if ((fd = open(part, O_RDONLY, 0)) < 0)
|
2000-11-04 02:13:13 +00:00
|
|
|
goto done;
|
|
|
|
|
2003-07-16 01:28:24 +01:00
|
|
|
if (fcntl(fd, F_FSGETXATTRA, &fsx) < 0)
|
2000-11-04 02:13:13 +00:00
|
|
|
goto done;
|
2003-07-16 01:28:24 +01:00
|
|
|
|
2000-11-04 02:13:13 +00:00
|
|
|
if (fsx.fsx_nextents == 0)
|
|
|
|
code = VERIFY_OK;
|
|
|
|
else
|
|
|
|
code = VERIFY_FIX;
|
|
|
|
|
2003-07-16 01:28:24 +01:00
|
|
|
done:
|
|
|
|
if (fd >= 0)
|
2000-11-04 02:13:13 +00:00
|
|
|
close(fd);
|
2003-07-16 01:28:24 +01:00
|
|
|
(void)attr_remove(part, AFS_XFS_ATTR, ATTR_ROOT);
|
2000-11-04 02:13:13 +00:00
|
|
|
|
|
|
|
return code;
|
|
|
|
}
|
|
|
|
|
|
|
|
#define ALLOC_STEP 256
|
|
|
|
#define NAME_SIZE 64
|
|
|
|
typedef struct {
|
|
|
|
char partName[NAME_SIZE];
|
|
|
|
char devName[NAME_SIZE];
|
|
|
|
} partInfo;
|
|
|
|
partInfo *partList = NULL;
|
|
|
|
int nParts = 0;
|
|
|
|
int nAvail = 0;
|
|
|
|
|
2003-07-16 01:28:24 +01:00
|
|
|
int
|
|
|
|
CheckPartitions()
|
|
|
|
{
|
2000-11-04 02:13:13 +00:00
|
|
|
int i;
|
|
|
|
struct mntent *mntent;
|
|
|
|
FILE *mfd;
|
|
|
|
DIR *dirp;
|
|
|
|
struct dirent *dp;
|
|
|
|
struct stat status;
|
|
|
|
int code;
|
|
|
|
|
|
|
|
if ((mfd = setmntent(MOUNTED, "r")) == NULL) {
|
|
|
|
printf("Problems in getting mount entries(setmntent): %s\n",
|
|
|
|
strerror(errno));
|
|
|
|
exit(-1);
|
|
|
|
}
|
|
|
|
while (mntent = getmntent(mfd)) {
|
|
|
|
char *part = mntent->mnt_dir;
|
|
|
|
|
2003-07-16 01:28:24 +01:00
|
|
|
if (!hasmntopt(mntent, MNTOPT_RW))
|
|
|
|
continue;
|
2000-11-04 02:13:13 +00:00
|
|
|
|
2003-07-16 01:28:24 +01:00
|
|
|
if (strncmp(part, VICE_PARTITION_PREFIX, VICE_PREFIX_SIZE)) {
|
2000-11-04 02:13:13 +00:00
|
|
|
continue; /* Non /vicepx; ignore */
|
2003-07-16 01:28:24 +01:00
|
|
|
}
|
2000-11-04 02:13:13 +00:00
|
|
|
if (stat(part, &status) == -1) {
|
|
|
|
printf("Couldn't find file system %s; ignored\n", part);
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
if (!strcmp("xfs", status.st_fstype)) {
|
|
|
|
code = VerifyXFSInodeSize(part);
|
|
|
|
switch (code) {
|
|
|
|
case VERIFY_OK:
|
|
|
|
break;
|
|
|
|
case VERIFY_ERROR:
|
2003-07-16 01:28:24 +01:00
|
|
|
printf("%s: Can't check XFS inode size: %s\n",
|
|
|
|
strerror(errno));
|
2000-11-04 02:13:13 +00:00
|
|
|
break;
|
|
|
|
case VERIFY_FIX:
|
|
|
|
if (nAvail <= nParts) {
|
2003-07-16 01:28:24 +01:00
|
|
|
nAvail += ALLOC_STEP;
|
2000-11-04 02:13:13 +00:00
|
|
|
if (nAvail == ALLOC_STEP)
|
2003-07-16 01:28:24 +01:00
|
|
|
partList =
|
|
|
|
(partInfo *) malloc(nAvail * sizeof(partInfo));
|
2000-11-04 02:13:13 +00:00
|
|
|
else
|
2003-07-16 01:28:24 +01:00
|
|
|
partList =
|
|
|
|
(partInfo *) realloc((char *)partList,
|
|
|
|
nAvail * sizeof(partInfo));
|
2000-11-04 02:13:13 +00:00
|
|
|
if (!partList) {
|
2003-07-16 01:28:24 +01:00
|
|
|
printf
|
|
|
|
("Failed to %salloc %d bytes for partition list.\n",
|
|
|
|
(nAvail == ALLOC_STEP) ? "m" : "re",
|
|
|
|
nAvail * sizeof(partInfo));
|
2000-11-04 02:13:13 +00:00
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
}
|
2003-07-16 01:28:24 +01:00
|
|
|
(void)strcpy(partList[nParts].partName, part);
|
|
|
|
(void)strcpy(partList[nParts].devName, mntent->mnt_fsname);
|
|
|
|
nParts++;
|
2000-11-04 02:13:13 +00:00
|
|
|
break;
|
|
|
|
default:
|
|
|
|
printf("Unknown return code %d from VerifyXFSInodeSize.\n",
|
|
|
|
code);
|
|
|
|
abort();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return nParts;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
main(int ac, char **av)
|
|
|
|
{
|
|
|
|
int i;
|
|
|
|
int code;
|
|
|
|
|
|
|
|
if (getuid()) {
|
|
|
|
printf("Must be root to run %s.\n", prog);
|
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
|
|
|
|
code = CheckPartitions();
|
|
|
|
if (code) {
|
|
|
|
printf("Need to remake the following partitions:\n");
|
2003-07-16 01:28:24 +01:00
|
|
|
for (i = 0; i < nParts; i++) {
|
2000-11-04 02:13:13 +00:00
|
|
|
printf("%s: mkfs -t xfs -i size=512 -l size=4000b %s\n",
|
|
|
|
partList[i].partName, partList[i].devName);
|
|
|
|
}
|
|
|
|
}
|
2003-07-16 01:28:24 +01:00
|
|
|
exit(code ? 1 : 0);
|
2000-11-04 02:13:13 +00:00
|
|
|
}
|
2003-07-16 01:28:24 +01:00
|
|
|
|
2000-11-04 02:13:13 +00:00
|
|
|
|
|
|
|
#else /* AFS_SGI_XFS_IOPS_ENV */
|
2003-07-16 01:28:24 +01:00
|
|
|
main()
|
|
|
|
{
|
|
|
|
printf("%s only runs on XFS platforms.\n, prog");
|
|
|
|
exit(1);
|
|
|
|
}
|
2000-11-04 02:13:13 +00:00
|
|
|
#endif /* AFS_SGI_XFS_IOPS_ENV */
|