volser-dumpstuff-log-errors-20081010
[openafs.git] / src / volser / dumpstuff.c
index fc16c52..5f824e4 100644 (file)
@@ -17,6 +17,7 @@ RCSID
 #include <ctype.h>
 #include <stdio.h>
 #include <errno.h>
+#include <string.h>
 #ifdef AFS_NT40_ENV
 #include <fcntl.h>
 #else
@@ -26,13 +27,6 @@ RCSID
 #include <netinet/in.h>
 #include <unistd.h>
 #endif
-#ifdef HAVE_STRING_H
-#include <string.h>
-#else
-#ifdef HAVE_STRINGS_H
-#include <strings.h>
-#endif
-#endif
 #include <sys/stat.h>
 #ifdef AFS_PTHREAD_ENV
 #include <assert.h>
@@ -83,7 +77,7 @@ struct iod {
     struct rx_call *call;      /* call to which to write, might be an array */
     int device;                        /* dump device ID for volume */
     int parentId;              /* dump parent ID for volume */
-    struct DiskPartition *dumpPartition;       /* Dump partition. */
+    struct DiskPartition64 *dumpPartition;     /* Dump partition. */
     struct rx_call **calls;    /* array of pointers to calls */
     int ncalls;                        /* how many calls/codes in array */
     int *codes;                        /* one return code for each call */
@@ -212,9 +206,13 @@ ReadShort(register struct iod *iodp, register unsigned short *sp)
 {
     register b1, b0;
     b1 = iod_getc(iodp);
+    if (b1 == EOF)
+       return 0;
     b0 = iod_getc(iodp);
+    if (b0 == EOF)
+       return 0;
     *sp = (b1 << 8) | b0;
-    return b0 != EOF;
+    return 1;
 }
 
 static int
@@ -222,24 +220,38 @@ ReadInt32(register struct iod *iodp, afs_uint32 * lp)
 {
     afs_uint32 register b3, b2, b1, b0;
     b3 = iod_getc(iodp);
+    if (b3 == EOF)
+       return 0;
     b2 = iod_getc(iodp);
+    if (b2 == EOF)
+       return 0;
     b1 = iod_getc(iodp);
+    if (b1 == EOF)
+       return 0;
     b0 = iod_getc(iodp);
+    if (b0 == EOF)
+       return 0;
     *lp = (((((b3 << 8) | b2) << 8) | b1) << 8) | b0;
-    return b0 != EOF;
+    return 1;
 }
 
 static void
 ReadString(register struct iod *iodp, register char *to, register int maxa)
 {
     register int c;
+    int first = 1;
+
+    *to = '\0';
+    if (maxa == 0)
+       return;
+
     while (maxa--) {
-       if ((*to++ = iod_getc(iodp)) == 0)
+       if ((*to++ = c = iod_getc(iodp)) == 0 || c == EOF)
            break;
     }
     if (to[-1]) {
        while ((c = iod_getc(iodp)) && c != EOF);
-       to[-1] = 0;
+       to[-1] = '\0';
     }
 }
 
@@ -506,9 +518,10 @@ DumpByteString(register struct iod *iodp, char tag, register byte * bs,
 static int
 DumpFile(struct iod *iodp, int vnode, FdHandle_t * handleP)
 {
-    int code = 0, lcode = 0, error = 0;
+    int code = 0, error = 0;
     afs_int32 pad = 0, offset;
     afs_sfsize_t n, nbytes, howMany, howBig;
+    afs_foff_t lcode = 0;
     byte *p;
 #ifndef AFS_NT40_ENV
     struct afs_stat status;
@@ -516,7 +529,12 @@ DumpFile(struct iod *iodp, int vnode, FdHandle_t * handleP)
     afs_sfsize_t size;
 #ifdef AFS_AIX_ENV
 #include <sys/statfs.h>
+#if defined(AFS_AIX52_ENV) && defined(AFS_LARGEFILE_ENV)
+    struct statfs64 tstatfs;
+#else /* !AFS_AIX52_ENV || !AFS_LARGEFILE_ENV */
     struct statfs tstatfs;
+#endif /* !AFS_AIX52_ENV || !AFS_LARGEFILE_ENV */
+    int statfs_code;
 #endif
 
 #ifdef AFS_NT40_ENV
@@ -531,8 +549,16 @@ DumpFile(struct iod *iodp, int vnode, FdHandle_t * handleP)
     /* Unfortunately in AIX valuable fields such as st_blksize are 
      * gone from the stat structure.
      */
-    fstatfs(handleP->fd_fd, &tstatfs);
-    howMany = tstatfs.f_bsize;
+#if defined(AFS_AIX52_ENV) && defined(AFS_LARGEFILE_ENV)
+    statfs_code = fstatfs64(handleP->fd_fd, &tstatfs);
+#else /* !AFS_AIX52_ENV || !AFS_LARGEFILE_ENV */
+    statfs_code = fstatfs(handleP->fd_fd, &tstatfs);
+#endif /* !AFS_AIX52_ENV || !AFS_LARGEFILE_ENV */
+    if (statfs_code != 0) {
+        Log("DumpFile: fstatfs returned error code %d on descriptor %d\n", errno, handleP->fd_fd);
+       return VOLSERDUMPERROR;
+    }
+    howMany = (afs_sfsize_t) tstatfs.f_bsize;
 #else
     howMany = status.st_blksize;
 #endif /* AFS_AIX_ENV */
@@ -557,9 +583,9 @@ DumpFile(struct iod *iodp, int vnode, FdHandle_t * handleP)
        return VOLSERDUMPERROR;
     }
 
-    p = (unsigned char *)malloc(howMany);
+    p = (unsigned char *)malloc((size_t)howMany);
     if (!p) {
-       Log("1 Volser: DumpFile: no memory");
+       Log("1 Volser: DumpFile: not enough memory to allocate %u bytes\n", howMany);
        return VOLSERDUMPERROR;
     }
 
@@ -568,7 +594,7 @@ DumpFile(struct iod *iodp, int vnode, FdHandle_t * handleP)
            howMany = nbytes;
 
        /* Read the data - unless we know we can't */
-       n = (lcode ? 0 : FDH_READ(handleP, p, howMany));
+       n = (lcode ? 0 : FDH_READ(handleP, p, (size_t)howMany));
 
        /* If read any good data and we null padded previously, log the
         * amount that we had null padded.
@@ -602,7 +628,7 @@ DumpFile(struct iod *iodp, int vnode, FdHandle_t * handleP)
            /* Now seek over the data we could not get. An error here means we
             * can't do the next read.
             */
-           lcode = FDH_SEEK(handleP, ((size - nbytes) + howMany), SEEK_SET);
+           lcode = FDH_SEEK(handleP, (size_t)((size - nbytes) + howMany), SEEK_SET);
            if (lcode != ((size - nbytes) + howMany)) {
                if (lcode < 0) {
                    Log("1 Volser: DumpFile: Error %d seeking in inode %s for vnode %d\n", errno, PrintInode(NULL, handleP->fd_ih->ih_ino), vnode);
@@ -616,7 +642,7 @@ DumpFile(struct iod *iodp, int vnode, FdHandle_t * handleP)
        }
 
        /* Now write the data out */
-       if (iod_Write(iodp, (char *)p, howMany) != howMany)
+       if (iod_Write(iodp, (char *)p, (size_t)howMany) != howMany)
            error = VOLSERDUMPERROR;
 #ifndef AFS_PTHREAD_ENV
        IOMGR_Poll();
@@ -961,9 +987,16 @@ ProcessIndex(Volume * vp, VnodeClass class, afs_int32 ** Bufp, int *sizep,
            (size <=
             vcp->diskSize ? 0 : size - vcp->diskSize) >> vcp->logSize;
        if (nVnodes > 0) {
+           if (DoLogging) {
+               Log("RestoreVolume ProcessIndex: Set up %d inodes for volume %d\n",
+                   nVnodes, V_id(vp));
+           }
            Buf = (afs_int32 *) malloc(nVnodes * sizeof(afs_int32));
-           if (Buf == NULL)
-               return 1;
+           if (Buf == NULL) {
+               STREAM_CLOSE(afile);
+               FDH_CLOSE(fdP);
+               return -1;
+           }
            memset((char *)Buf, 0, nVnodes * sizeof(afs_int32));
            STREAM_SEEK(afile, offset = vcp->diskSize, 0);
            while (1) {
@@ -977,6 +1010,9 @@ ProcessIndex(Volume * vp, VnodeClass class, afs_int32 ** Bufp, int *sizep,
                }
                offset += vcp->diskSize;
            }
+           if (DoLogging) {
+               Log("RestoreVolume ProcessIndex: found %d inodes\n", cnt);
+           }
            *Bufp = Buf;
            *sizep = nVnodes;
        }
@@ -998,13 +1034,14 @@ RestoreVolume(register struct rx_call *call, Volume * avp, int incremental,
     register Volume *vp;
     struct iod iod;
     register struct iod *iodp = &iod;
-    afs_int32 *b1 = 0, *b2 = 0;
+    afs_int32 *b1 = NULL, *b2 = NULL;
     int s1 = 0, s2 = 0, delo = 0, tdelo;
     int tag;
 
     iod_Init(iodp, call);
 
     vp = avp;
+
     if (!ReadDumpHeader(iodp, &header)) {
        Log("1 Volser: RestoreVolume: Error reading header file for dump; aborted\n");
        return VOLSERREAD_DUMPERROR;
@@ -1016,15 +1053,14 @@ RestoreVolume(register struct rx_call *call, Volume * avp, int incremental,
     if (ReadVolumeHeader(iodp, &vol) == VOLSERREAD_DUMPERROR)
        return VOLSERREAD_DUMPERROR;
 
-    delo = ProcessIndex(vp, vLarge, &b1, &s1, 0);
+    if (!delo)
+       delo = ProcessIndex(vp, vLarge, &b1, &s1, 0);
     if (!delo)
        delo = ProcessIndex(vp, vSmall, &b2, &s2, 0);
-    if (delo) {
-       if (b1)
-           free((char *)b1);
-       if (b2)
-           free((char *)b2);
-       b1 = b2 = 0;
+    if (delo < 0) {
+       Log("1 Volser: RestoreVolume: ProcessIndex failed; not restored\n");
+       error = VOLSERREAD_DUMPERROR;
+       goto out;
     }
 
     strncpy(vol.name, cookie->name, VOLSER_OLDMAXVOLNAME);
@@ -1032,7 +1068,6 @@ RestoreVolume(register struct rx_call *call, Volume * avp, int incremental,
     vol.cloneId = cookie->clone;
     vol.parentId = cookie->parent;
 
-
     tdelo = delo;
     while (1) {
        if (ReadVnodes(iodp, vp, 0, b1, s1, b2, s2, tdelo)) {
@@ -1042,11 +1077,11 @@ RestoreVolume(register struct rx_call *call, Volume * avp, int incremental,
        tag = iod_getc(iodp);
        if (tag != D_VOLUMEHEADER)
            break;
+
        if (ReadVolumeHeader(iodp, &vol) == VOLSERREAD_DUMPERROR) {
            error = VOLSERREAD_DUMPERROR;
            goto out;
        }
-       tdelo = -1;
     }
     if (tag != D_DUMPEND || !ReadInt32(iodp, &endMagic)
        || endMagic != DUMPENDMAGIC) {
@@ -1063,8 +1098,13 @@ RestoreVolume(register struct rx_call *call, Volume * avp, int incremental,
     }
 
     if (!delo) {
-       ProcessIndex(vp, vLarge, &b1, &s1, 1);
-       ProcessIndex(vp, vSmall, &b2, &s2, 1);
+       delo = ProcessIndex(vp, vLarge, &b1, &s1, 1);
+       if (!delo)
+           delo = ProcessIndex(vp, vSmall, &b2, &s2, 1);
+       if (delo < 0) {
+           error = VOLSERREAD_DUMPERROR;
+           goto clean;
+       }
     }
 
   clean:
@@ -1111,7 +1151,12 @@ ReadVnodes(register struct iod *iodp, Volume * vp, int incremental,
        if (!ReadInt32(iodp, (afs_uint32 *) & vnodeNumber))
            break;
 
-       ReadInt32(iodp, &vnode->uniquifier);
+       if (!ReadInt32(iodp, &vnode->uniquifier))
+           return VOLSERREAD_DUMPERROR;
+
+       if (DoLogging) {
+           Log("ReadVnodes: setup %d/%d\n", vnodeNumber, vnode->uniquifier);
+       }
        while ((tag = iod_getc(iodp)) > D_MAX && tag != EOF) {
            haveStuff = 1;
            switch (tag) {
@@ -1121,36 +1166,45 @@ ReadVnodes(register struct iod *iodp, Volume * vp, int incremental,
            case 'l':
                {
                    unsigned short tlc;
-                   ReadShort(iodp, &tlc);
+                   if (!ReadShort(iodp, &tlc))
+                       return VOLSERREAD_DUMPERROR;
                    vnode->linkCount = (signed int)tlc;
                }
                break;
            case 'v':
-               ReadInt32(iodp, &vnode->dataVersion);
+               if (!ReadInt32(iodp, &vnode->dataVersion))
+                   return VOLSERREAD_DUMPERROR;
                break;
            case 'm':
-               ReadInt32(iodp, &vnode->unixModifyTime);
+               if (!ReadInt32(iodp, &vnode->unixModifyTime))
+                   return VOLSERREAD_DUMPERROR;
                break;
            case 's':
-               ReadInt32(iodp, &vnode->serverModifyTime);
+               if (!ReadInt32(iodp, &vnode->serverModifyTime))
+                   return VOLSERREAD_DUMPERROR;
                break;
            case 'a':
-               ReadInt32(iodp, &vnode->author);
+               if (!ReadInt32(iodp, &vnode->author))
+                   return VOLSERREAD_DUMPERROR;
                break;
            case 'o':
-               ReadInt32(iodp, &vnode->owner);
+               if (!ReadInt32(iodp, &vnode->owner))
+                   return VOLSERREAD_DUMPERROR;
                break;
            case 'g':
-               ReadInt32(iodp, (afs_uint32 *) & vnode->group);
+               if (!ReadInt32(iodp, (afs_uint32 *) & vnode->group))
+                   return VOLSERREAD_DUMPERROR;
                break;
            case 'b':{
                    unsigned short modeBits;
-                   ReadShort(iodp, &modeBits);
+                   if (!ReadShort(iodp, &modeBits))
+                       return VOLSERREAD_DUMPERROR;
                    vnode->modeBits = (unsigned int)modeBits;
                    break;
                }
            case 'p':
-               ReadInt32(iodp, &vnode->parent);
+               if (!ReadInt32(iodp, &vnode->parent))
+                   return VOLSERREAD_DUMPERROR;
                break;
            case 'A':
                ReadByteString(iodp, (byte *) VVnodeDiskACL(vnode),
@@ -1171,8 +1225,8 @@ ReadVnodes(register struct iod *iodp, Volume * vp, int incremental,
                                  V_parentId(vp), vnodeNumber,
                                  vnode->uniquifier, vnode->dataVersion);
                    if (!VALID_INO(ino)) {
-                       perror("unable to allocate inode");
-                       Log("1 Volser: ReadVnodes: Restore aborted\n");
+                       Log("1 Volser: ReadVnodes: IH_CREATE: %s - restore aborted\n",
+                            afs_error_message(errno));
                        return VOLSERREAD_DUMPERROR;
                    }
                    nearInode = ino;
@@ -1180,6 +1234,8 @@ ReadVnodes(register struct iod *iodp, Volume * vp, int incremental,
                    IH_INIT(tmpH, vp->device, V_parentId(vp), ino);
                    fdP = IH_OPEN(tmpH);
                    if (fdP == NULL) {
+                       Log("1 Volser: ReadVnodes: IH_OPEN: %s - restore aborted\n",
+                            afs_error_message(errno));
                        IH_RELEASE(tmpH);
                        return VOLSERREAD_DUMPERROR;
                    }
@@ -1250,7 +1306,6 @@ ReadVnodes(register struct iod *iodp, Volume * vp, int incremental,
     }
     iod_ungetc(iodp, tag);
 
-
     return 0;
 }
 
@@ -1264,6 +1319,7 @@ volser_WriteFile(int vn, struct iod *iodp, FdHandle_t * handleP, int tag,
                 Error * status)
 {
     afs_int32 code;
+    afs_sfsize_t lcode;
     afs_fsize_t filesize;
     afs_fsize_t written = 0;
     register afs_uint32 size = 8192;
@@ -1309,11 +1365,11 @@ volser_WriteFile(int vn, struct iod *iodp, FdHandle_t * handleP, int tag,
            *status = 3;
            break;
        }
-       code = FDH_WRITE(handleP, p, size);
-       if (code > 0)
-           written += code;
-       if (code != size) {
-           Log("1 Volser: WriteFile: Error creating file in volume; restore aborted\n");
+       lcode = FDH_WRITE(handleP, p, size);
+       if (lcode > 0)
+           written += lcode;
+       if (lcode != size) {
+           Log("1 Volser: WriteFile: Error writing (%d,%u) bytes to vnode %d; restore aborted\n", (int)(lcode>>32), (int)(lcode & 0xffffffff), vn);
            *status = 4;
            break;
        }