Imported Upstream version 2.6.0p2
[debian/amanda] / tape-src / tapetype.c
index dd4758187b91b398b3cb48265c3bc71dcefbe222..012840117e0ba92d22ce244966666afebfd50d30 100644 (file)
  *                        University of Maryland at College Park
  */
 /*
- * $Id: tapetype.c,v 1.24 2006/03/10 11:56:06 martinea Exp $
+ * $Id: tapetype.c,v 1.27 2006/08/24 01:57:16 paddy_s Exp $
  *
  * tests a tape in a given tape unit and prints a tapetype entry for
  * it.  */
 #include "amanda.h"
+#include "conffile.h"
 
 #include "tapeio.h"
 
@@ -41,11 +42,10 @@ static char *sProgName;
 static char *tapedev;
 static int fd;
 
-static int blockkb = 32;
-static int blocksize;
+static size_t blockkb = 32;
+static size_t blocksize;
 
 static char *randombytes = (char *) NULL;
-static char *prandombytes = (char *) NULL;
 
 #if USE_RAND
 /* If the C library does not define random(), try to use rand() by
@@ -56,43 +56,65 @@ static char *prandombytes = (char *) NULL;
 #define srandom(seed) srand(seed)
 #endif
 
-static void allocrandombytes() {
-  int i, j, page_size;
-  char *p;
+static char *getrandombytes(void);
+static int writeblock(int fd);
+static off_t writeblocks(int fd, off_t nblks);
+static void allocrandombytes(void);
+static void do_pass0(off_t size, time_t *seconds, int dorewind);
+static void do_pass(off_t size, off_t *blocks, off_t *files, time_t *seconds);
+static void help(void);
+static void initnotrandombytes(void);
+static void initrandombytes(void);
+static void show_progress(off_t *blocks, off_t *files);
+static void usage(void);
+
+int main(int argc, char **argv);
+
+static void
+allocrandombytes(void)
+{
+  size_t i;
+  size_t j;
+  size_t page_size;
+  char   *p;
 
   if (randombytes == (char *)NULL) {
 #if defined(HAVE_GETPAGESIZE)
-    page_size = getpagesize();
+    page_size = (size_t)getpagesize();
 #else
-    page_size = 1024;
+    page_size = (size_t)1024;
 #endif
     j = (NBLOCKS * blocksize) + page_size;     /* buffer space plus one page */
     j = am_round(j, page_size);                        /* even number of pages */
-    p = alloc(j);
-    i = (p - (char *)0) & (page_size - 1);     /* page boundary offset */
+    p = (char *)alloc(j);
+    i = (size_t)(p - (char *)0) & (page_size - 1);/* page boundary offset */
     if(i != 0) {
-      randombytes = p + page_size - i;         /* round up to page boundary */
+      randombytes = p + (page_size - i);       /* round up to page boundary */
     } else {
       randombytes = p;                         /* alloc already on boundary */
     }
-    prandombytes = p;
   }
 }
 
-static void initnotrandombytes() {
-  int i, j;
+static void
+initnotrandombytes(void)
+{
+  unsigned long i;
+  unsigned long j;
   char *p;
 
   allocrandombytes();
-  j =NBLOCKS * blocksize;
+  j = NBLOCKS * blocksize;
   p = randombytes;
   for(i=0; i < j; ++i) {
     *p++ = (char) (i % 256);
   }
 }
 
-static void initrandombytes() {
-  int i, j;
+static void
+initrandombytes(void)
+{
+  unsigned long i, j;
   char *p;
 
   allocrandombytes();
@@ -103,20 +125,23 @@ static void initrandombytes() {
   }
 }
 
-static char *getrandombytes() {
-  static int counter = 0;
+static char *
+getrandombytes(void)
+{
+  static unsigned long counter = 0;
 
   return randombytes + ((counter++ % NBLOCKS) * blocksize);
 }
 
 static int short_write;
 
-int writeblock(fd)
-     int fd;
+static int
+writeblock(
+    int                fd)
 {
-  size_t w;
+  ssize_t w;
 
-  if ((w = tapefd_write(fd, getrandombytes(), blocksize)) == blocksize) {
+  if ((w = tapefd_write(fd, getrandombytes(), blocksize)) == (ssize_t)blocksize) {
     return 1;
   }
   if (w >= 0) {
@@ -129,73 +154,96 @@ int writeblock(fd)
 
 
 /* returns number of blocks actually written */
-size_t writeblocks(int fd, size_t nblks)
+static off_t
+writeblocks(
+    int                fd,
+    off_t      nblks)
 {
-  size_t blks = 0;
+  off_t blks = (off_t)0;
 
   while (blks < nblks) {
     if (! writeblock(fd)) {
-      return 0;
+      return (off_t)0;
     }
-    blks++;
+    blks += (off_t)1;
   }
 
   return blks;
 }
 
 
-void usage()
+static void
+usage(void)
 {
-  fputs("usage: ", stderr);
+  fputs(_("usage: "), stderr);
   fputs(sProgName, stderr);
-  fputs(" [-h]", stderr);
-  fputs(" [-c]", stderr);
-  fputs(" [-o]", stderr);
-  fputs(" [-b blocksize]", stderr);
-  fputs(" [-e estsize]", stderr);
-  fputs(" [-f tapedev]", stderr);
-  fputs(" [-t typename]", stderr);
+  fputs(_(" [-h]"), stderr);
+  fputs(_(" [-c]"), stderr);
+  fputs(_(" [-o]"), stderr);
+  fputs(_(" [-b blocksize]"), stderr);
+  fputs(_(" -e estsize"), stderr);
+  fputs(_(" [-f tapedev]"), stderr);
+  fputs(_(" [-t typename]"), stderr);
   fputc('\n', stderr);
 }
 
-void help()
+static void
+help(void)
 {
   usage();
-  fputs("\
-  -h                   display this message\n\
-  -c                   run hardware compression detection test only\n\
-  -o                   overwrite amanda tape\n\
-  -b blocksize         record block size (default: 32k)\n\
-  -e estsize           estimated tape size (default: 1g == 1024m)\n\
-  -f tapedev           tape device name (default: $TAPE)\n\
-  -t typename          tapetype name (default: unknown-tapetype)\n\
-\n\
-Note: disable hardware compression when running this program.\n\
-", stderr);
+  fputs(_("-h                  display this message\n"
+         "-c                   run hardware compression detection test only\n"
+         "-o                   overwrite amanda tape\n"
+         "-b blocksize         record block size (default: 32k)\n"
+         "-e estsize           estimated tape size (No default!)\n"
+         "-f tapedev           tape device name (default: $TAPE)\n"
+         "-t typename          tapetype name (default: unknown-tapetype)\n"
+         "\n"
+         "Note: disable hardware compression when running this program.\n"),
+       stderr);
 }
 
 
 int do_tty;
 
-void show_progress(blocks, files)
-  size_t *blocks, *files;
+static void
+show_progress(
+    off_t *    blocks,
+    off_t *    files)
 {
-  fprintf(stderr, "wrote %ld %dKb block%s in %ld file%s",
-         (long)*blocks, blockkb, (*blocks == 1) ? "" : "s",
-         (long)*files, (*files == 1) ? "" : "s");
+    g_fprintf(stderr,
+           plural(_("wrote %lld %zu Kb block"),
+                  _("wrote %lld %zu Kb blocks"),
+                  *blocks),
+           (long long)*blocks,
+           blockkb);
+    g_fprintf(stderr,
+           plural(_(" in %lld file"),
+                  _(" in %lld files"),
+                  *files),
+           (long long)*files);
 }
 
 
-void do_pass(size, blocks, files, seconds)
-  size_t size, *blocks, *files;
-  time_t *seconds;
+static void
+do_pass(
+    off_t      size,
+    off_t *    blocks,
+    off_t *    files,
+    time_t *   seconds)
 {
-  size_t blks;
+  off_t blks;
   time_t start, end;
   int save_errno;
 
   if (tapefd_rewind(fd) == -1) {
-    fprintf(stderr, "%s: could not rewind %s: %s\n",
+    g_fprintf(stderr, _("%s: could not rewind %s: %s\n"),
+           sProgName, tapedev, strerror(errno));
+    exit(1);
+  }
+  if (((-1 == tapefd_close(fd)) ||
+       (-1 == (fd = tape_open(tapedev, O_RDWR))))) {
+    g_fprintf(stderr, "%s: could not re-open %s: %s\n",
            sProgName, tapedev, strerror(errno));
     exit(1);
   }
@@ -204,10 +252,10 @@ void do_pass(size, blocks, files, seconds)
 
   while(1) {
 
-    if ((blks = writeblocks(fd, size)) <= 0 || tapefd_weof(fd, 1) != 0)
+    if ((blks = writeblocks(fd, size)) <= (off_t)0 || tapefd_weof(fd, (off_t)1) != 0)
       break;
     *blocks += blks;
-    (*files)++;
+    *files += (off_t)1;
     if(do_tty) {
       putc('\r', stderr);
       show_progress(blocks, files);
@@ -217,9 +265,9 @@ void do_pass(size, blocks, files, seconds)
 
   time(&end);
 
-  if (*blocks == 0) {
-    fprintf(stderr, "%s: could not write any data in this pass: %s\n",
-           sProgName, short_write ? "short write" : strerror(save_errno));
+  if (*blocks == (off_t)0) {
+    g_fprintf(stderr, _("%s: could not write any data in this pass: %s\n"),
+           sProgName, short_write ? _("short write") : strerror(save_errno));
     exit(1);
   }
 
@@ -236,39 +284,52 @@ void do_pass(size, blocks, files, seconds)
     putc('\r', stderr);
   }
   show_progress(blocks, files);
-  fprintf(stderr, " in %ld second%s (%s)\n",
-         (long)*seconds, ((long)*seconds == 1) ? "" : "s",
-         short_write ? "short write" : strerror(save_errno));
+  g_fprintf(stderr,
+         plural(_(" in %jd second (%s)\n"),
+                _(" in %jd seconds (%s)\n"),
+                *seconds),
+         (intmax_t)*seconds,
+         short_write ? _("short write") : strerror(save_errno));
 }
 
 
-void do_pass0(size, seconds, dorewind)
-  size_t size;
-  time_t *seconds;
-  int dorewind;
+static void
+do_pass0(
+    off_t      size,
+    time_t *   seconds,
+    int                dorewind)
 {
-  size_t blks;
+  off_t blks;
   time_t start, end;
   int save_errno;
 
   if (dorewind  &&  tapefd_rewind(fd) == -1) {
-    fprintf(stderr, "%s: could not rewind %s: %s\n",
+    g_fprintf(stderr, _("%s: could not rewind %s: %s\n"),
            sProgName, tapedev, strerror(errno));
     exit(1);
   }
 
+  if (dorewind &&
+      ((-1 == tapefd_close(fd)) ||
+       (-1 == (fd = tape_open(tapedev, O_RDWR))))) {
+    g_fprintf(stderr, "%s: could not re-open %s: %s\n",
+           sProgName, tapedev, strerror(errno));
+    exit(1);
+  }
+
+
   time(&start);
 
   blks = writeblocks(fd, size);
-  tapefd_weof(fd, 1);
+  tapefd_weof(fd, (off_t)1);
 
   save_errno = errno;
 
   time(&end);
 
-  if (blks <= 0) {
-    fprintf(stderr, "%s: could not write any data in this pass: %s\n",
-           sProgName, short_write ? "short write" : strerror(save_errno));
+  if (blks <= (off_t)0) {
+    g_fprintf(stderr, _("%s: could not write any data in this pass: %s\n"),
+           sProgName, short_write ? _("short write") : strerror(save_errno));
     exit(1);
   }
 
@@ -284,29 +345,30 @@ void do_pass0(size, seconds, dorewind)
 }
 
 
-int main(argc, argv)
-     int argc;
-     char *argv[];
+int
+main(
+    int                argc,
+    char **    argv)
 {
-  size_t pass1blocks = 0;
-  size_t pass2blocks = 0;
+  off_t pass1blocks = (off_t)0;
+  off_t pass2blocks = (off_t)0;
   time_t pass1time;
   time_t pass2time;
   time_t timediff;
-  size_t pass1files = 0;
-  size_t pass2files = 0;
-  size_t estsize;
-  size_t pass0size;
-  size_t pass1size;
-  size_t pass2size;
-  size_t blockdiff;
-  size_t filediff;
-  long filemark;
-  long speed;
-  size_t size;
+  off_t pass1files = (off_t)0;
+  off_t pass2files = (off_t)0;
+  off_t estsize;
+  off_t pass0size;
+  off_t pass1size;
+  off_t pass2size;
+  off_t blockdiff;
+  off_t filediff;
+  size_t filemark;
+  unsigned long speed;
+  off_t size;
   char *sizeunits;
   int ch;
-  char *suffix;
+  char *suffix = NULL;
   char *typename;
   time_t now;
   int hwcompr = 0;
@@ -317,6 +379,16 @@ int main(argc, argv)
   char *datestamp = NULL;
   char *label = NULL;
 
+  /*
+   * Configure program for internationalization:
+   *   1) Only set the message locale for now.
+   *   2) Set textdomain for all amanda related programs to "amanda"
+   *      We don't want to be forced to support dozens of message catalogs.
+   */  
+  setlocale(LC_MESSAGES, "C");
+  textdomain("amanda"); 
+
+  config_init(0, NULL);
 
   if ((sProgName = strrchr(*argv, '/')) == NULL) {
     sProgName = *argv;
@@ -327,74 +399,99 @@ int main(argc, argv)
   /* Don't die when child closes pipe */
   signal(SIGPIPE, SIG_IGN);
 
-  estsize = 1024 * 1024;                       /* assume 1 GByte for now */
+  estsize = (off_t)0;
   tapedev = getenv("TAPE");
   typename = "unknown-tapetype";
 
   while ((ch = getopt(argc, argv, "b:e:f:t:hco")) != EOF) {
     switch (ch) {
     case 'b':
-      blockkb = strtol(optarg, &suffix, 0);
-      if (*suffix == '\0' || *suffix == 'k' || *suffix == 'K') {
-      } else if (*suffix == 'm' || *suffix == 'M') {
-       blockkb *= 1024;
-      } else if (*suffix == 'g' || *suffix == 'G') {
-       blockkb *= 1024 * 1024;
-      } else {
-       fprintf(stderr, "%s: unknown size suffix \'%c\'\n", sProgName, *suffix);
-       return 1;
+      blockkb = (size_t)strtol(optarg, &suffix, 0);
+      if (!(*suffix == '\0' || *suffix == 'k' || *suffix == 'K')) {
+       if (*suffix == 'm' || *suffix == 'M') {
+         blockkb *= 1024;
+       } else if (*suffix == 'g' || *suffix == 'G') {
+         blockkb *= (1024 * 1024);
+       } else {
+         g_fprintf(stderr, _("%s: unknown size suffix \'%c\'\n"),
+                 sProgName, *suffix);
+         return 1;
+       }
       }
       break;
     case 'e':
-      estsize = strtol(optarg, &suffix, 0);
-      if (*suffix == '\0' || *suffix == 'k' || *suffix == 'K') {
-      } else if (*suffix == 'm' || *suffix == 'M') {
-       estsize *= 1024;
-      } else if (*suffix == 'g' || *suffix == 'G') {
-       estsize *= 1024 * 1024;
-      } else {
-       fprintf(stderr, "%s: unknown size suffix \'%c\'\n", sProgName, *suffix);
-       return 1;
+      estsize = OFF_T_STRTOL(optarg, &suffix, 0);
+      if (!(*suffix == '\0' || *suffix == 'k' || *suffix == 'K')) {
+       if (*suffix == 'm' || *suffix == 'M') {
+         estsize *= (off_t)1024;
+       } else if (*suffix == 'g' || *suffix == 'G') {
+         estsize *= (off_t)(1024 * 1024);
+       } else {
+         g_fprintf(stderr, _("%s: unknown size suffix \'%c\'\n"),
+                 sProgName, *suffix);
+         return 1;
+       }
       }
       break;
+
     case 'f':
       tapedev = stralloc(optarg);
       break;
+
     case 't':
       typename = stralloc(optarg);
       break;
+
     case 'c':
       comprtstonly = 1;
       break;
+
     case 'h':
       help();
       return 1;
-      break;
+
     case 'o':
       overwrite_label=1;
       break;
+
     default:
-      fprintf(stderr, "%s: unknown option \'%c\'\n", sProgName, ch);
-      /* fall through to ... */
+      g_fprintf(stderr, _("%s: unknown option \'%c\'\n"), sProgName, ch);
+      /*FALLTHROUGH*/
+
     case '?':
       usage();
       return 1;
-      break;
     }
   }
   blocksize = blockkb * 1024;
 
-  if (tapedev == NULL || optind < argc) {
+  if (tapedev == NULL) {
+    g_fprintf(stderr, _("%s: No tapedev specified\n"), sProgName);
     usage();
     return 1;
   }
+  if (optind < argc) {
+    usage();
+    return 1;
+  }
+
+  if (estsize == 0) {
+    if (comprtstonly) {
+      estsize = (off_t)(1024 * 1024);          /* assume 1 GByte for now */
+    } else {
+      g_fprintf(stderr, _("%s: please specify estimated tape capacity (e.g. '-e 4g')\n"), sProgName);
+      usage();
+      return 1;
+    }
+  }
+
 
 /* verifier tape */
 
 
-  fd = tape_open(tapedev, O_RDONLY);
+  fd = tape_open(tapedev, O_RDONLY, 0);
   if (fd == -1) {
-    fprintf(stderr, "%s: could not open %s: %s\n",
+    g_fprintf(stderr, _("%s: could not open %s: %s\n"),
            sProgName, tapedev, strerror(errno));
     return 1;
   }
@@ -402,12 +499,12 @@ int main(argc, argv)
   if((result = tapefd_rdlabel(fd, &datestamp, &label)) == NULL) {
     is_labeled = 1;
   }
-  else if (strcmp(result,"not an amanda tape") == 0) {
+  else if (strcmp(result,_("not an amanda tape")) == 0) {
     is_labeled = 2;
   }
 
   if(tapefd_rewind(fd) == -1) {
-    fprintf(stderr, "%s: could not rewind %s: %s\n",
+    g_fprintf(stderr, _("%s: could not rewind %s: %s\n"),
            sProgName, tapedev, strerror(errno));
     tapefd_close(fd);
     return 1;
@@ -416,19 +513,19 @@ int main(argc, argv)
   tapefd_close(fd);
 
   if(is_labeled == 1 && overwrite_label == 0) {
-    fprintf(stderr, "%s: The tape is an amanda tape, use -o to overwrite the tape\n",
+    g_fprintf(stderr, _("%s: The tape is an amanda tape, use -o to overwrite the tape\n"),
            sProgName);
     return 1;
   }
   else if(is_labeled == 2 && overwrite_label == 0) {
-    fprintf(stderr, "%s: The tape is already used, use -o to overwrite the tape\n",
+    g_fprintf(stderr, _("%s: The tape is already used, use -o to overwrite the tape\n"),
            sProgName);
     return 1;
   }
 
-  fd = tape_open(tapedev, O_RDWR);
+  fd = tape_open(tapedev, O_RDWR, 0);
   if (fd == -1) {
-    fprintf(stderr, "%s: could not open %s: %s\n",
+    g_fprintf(stderr, _("%s: could not open %s: %s\n"),
            sProgName, tapedev, strerror(errno));
     return 1;
   }
@@ -445,8 +542,8 @@ int main(argc, argv)
 
   initnotrandombytes();
 
-  fprintf(stderr, "Estimate phase 1...");
-  pass0size = 8 * 1024 / blockkb;
+  g_fprintf(stderr, _("Estimate phase 1..."));
+  pass0size = (off_t)(8 * 1024 / blockkb);
   pass1time = 0;
   pass2time = 0;
   /*
@@ -459,11 +556,11 @@ int main(argc, argv)
    */ 
   while (pass1time < 25 || ((100*(pass2time-pass1time)/pass2time) >= 10) ) {
     if (pass1time != 0) {
-      int i = pass1time;
+      time_t t = pass1time;
       do {
-         pass0size *= 2;
-         i *= 2;
-      } while (i < 25);
+         pass0size *= (off_t)2;
+         t *= 2;
+      } while (t < 25);
     }
     /*
      * first a dummy pass to rewind, stop, start and
@@ -471,27 +568,33 @@ int main(argc, argv)
      */
     do_pass0(pass0size, &pass2time, 1);
     do_pass0(pass0size, &pass1time, 0);
-    if (pass0size >= 10 * 1024 * 1024) {
-      fprintf(stderr,
-       "\rTape device is too fast to detect hardware compression...\n");
+    if (pass0size >= (off_t)(10 * 1024 * 1024)) {
+      g_fprintf(stderr, "\r");
+      g_fprintf(stderr,
+       _("Tape device is too fast to detect hardware compression...\n"));
       break;   /* avoid loops if tape is superfast or broken */
     }
   }
-  fprintf(stderr, "\rWriting %d Mbyte   compresseable data:  %d sec\n",
-       (int)(blockkb * pass0size / 1024), (int)pass1time);
+  g_fprintf(stderr, "\r");
+  g_fprintf(stderr,
+       _("Writing %lld Mbyte   compresseable data:  %jd sec\n"),
+       (long long)((off_t)blockkb * pass0size / (off_t)1024),
+       (intmax_t)pass1time);
 
   /*
    * now generate uncompressable data and try again
    */
   time(&now);
-  srandom(now);
+  srandom((unsigned)now);
   initrandombytes();
 
-  fprintf(stderr, "Estimate phase 2...");
+  g_fprintf(stderr, _("Estimate phase 2..."));
   do_pass0(pass0size, &pass2time, 1);  /* rewind and get drive streaming */
   do_pass0(pass0size, &pass2time, 0);
-  fprintf(stderr, "\rWriting %d Mbyte uncompresseable data:  %d sec\n",
-       (int)(blockkb * pass0size / 1024), (int)pass2time);
+  g_fprintf(stderr, "\r");
+  g_fprintf(stderr, _("Writing %lld Mbyte uncompresseable data: %jd sec\n"),
+       (long long)((off_t)blockkb * pass0size / (off_t)1024),
+       (intmax_t)pass2time);
 
   /*
    * Compute the time difference between writing the compressable and
@@ -508,18 +611,21 @@ int main(argc, argv)
     timediff = pass2time - pass1time;
   }
   if (((100 * timediff) / pass2time) >= 20) {  /* 20% faster? */
-    fprintf(stderr, "WARNING: Tape drive has hardware compression enabled\n");
+    g_fprintf(stderr, _("WARNING: Tape drive has hardware compression enabled\n"));
     hwcompr = 1;
   }
 
   /*
    * Inform about estimated time needed to run the remaining of this program
    */
-  fprintf(stderr, "Estimated time to write 2 * %lu Mbyte: ", (unsigned long) (estsize / 1024));
-  pass1time = (time_t)(2.0 * pass2time * estsize / (1.0 * pass0size * blockkb));
+  g_fprintf(stderr, _("Estimated time to write 2 * %lu Mbyte: "), (unsigned long) (estsize / (off_t)1024));
+  pass1time = (time_t)(2.0 * (double)pass2time * (double)estsize /
+               (1.0 * (double)pass0size * (double)blockkb));
        /* avoid overflow and underflow by doing math in floating point */
-  fprintf(stderr, "%ld sec = ", pass1time);
-  fprintf(stderr, "%ld h %ld min\n", (pass1time/3600), ((pass1time%3600) / 60));
+  g_fprintf(stderr, _("%jd sec = %jd h %jd min\n"),
+         (intmax_t)pass1time,
+         (intmax_t)(pass1time/(time_t)3600),
+         (intmax_t)((pass1time%(time_t)3600) / (time_t)60));
 
   if (comprtstonly) {
        exit(hwcompr);
@@ -529,16 +635,16 @@ int main(argc, argv)
   /*
    * Do pass 1 -- write files that are 1% of the estimated size until error.
    */
-  pass1size = (estsize * 0.01) / blockkb;      /* 1% of estimate */
-  if(pass1size <= 0) {
-    pass1size = 2;                             /* strange end case */
+  pass1size = (off_t)(((double)estsize * 0.01) / (double)blockkb); /* 1% of estimate */
+  if(pass1size <= (off_t)0) {
+    pass1size = (off_t)2;                              /* strange end case */
   }
   do_pass(pass1size, &pass1blocks, &pass1files, &pass1time);
 
   /*
    * Do pass 2 -- write smaller files until error.
    */
-  pass2size = pass1size / 2;
+  pass2size = pass1size / (off_t)2;
   do_pass(pass2size, &pass2blocks, &pass2files, &pass2time);
 
   /*
@@ -554,7 +660,7 @@ int main(argc, argv)
      * 2 than in pass 1 since we wrote twice as many tape marks.  But
      * odd things happen, so make sure the result does not go negative.
      */
-    blockdiff = 0;
+    blockdiff = (off_t)0;
   } else {
     blockdiff = pass1blocks - pass2blocks;
   }
@@ -562,23 +668,24 @@ int main(argc, argv)
     /*
      * This should not happen, but just in case ...
      */
-    filediff = 1;
+    filediff = (off_t)1;
   } else {
     filediff = pass2files - pass1files;
   }
-  filemark = blockdiff * blockkb / filediff;
+  filemark = (size_t)((blockdiff * (off_t)blockkb) / filediff);
 
   /*
    * Compute the length as the average of the two pass sizes including
    * tape marks.
    */
-  size = ((pass1blocks * blockkb + filemark * pass1files)
-           + (pass2blocks * blockkb + filemark * pass2files)) / 2;
-  if (size >= 1024 * 1024 * 1000) {
-    size /= 1024 * 1024;
+  size = ((pass1blocks * (off_t)blockkb + (off_t)filemark * pass1files)
+           + (pass2blocks * (off_t)blockkb + (off_t)filemark * pass2files))
+          / (off_t)2;
+  if (size >= (off_t)(1024 * 1024 * 1000)) {
+    size /= (off_t)(1024 * 1024);
     sizeunits = "gbytes";
-  } else if (size >= 1024 * 1000) {
-    size /= 1024;
+  } else if (size >= (off_t)(1024 * 1000)) {
+    size /= (off_t)1024;
     sizeunits = "mbytes";
   } else {
     sizeunits = "kbytes";
@@ -587,34 +694,32 @@ int main(argc, argv)
   /*
    * Compute the speed as the average of the two passes.
    */
-  speed = (((double)pass1blocks * blockkb / pass1time)
-           + ((double)pass2blocks * blockkb / pass2time)) / 2;
+  speed = (unsigned long)((((double)pass1blocks
+          * (double)blockkb / (double)pass1time)
+           + ((double)pass2blocks * (double)blockkb / (double)pass2time)) / 2.0);
 
   /*
    * Dump the tapetype.
    */
-  printf("define tapetype %s {\n", typename);
-  printf("    comment \"just produced by tapetype prog (hardware compression %s)\"\n",
-       hwcompr ? "on" : "off");
-  printf("    length %ld %s\n", (long)size, sizeunits);
-  printf("    filemark %ld kbytes\n", filemark);
-  printf("    speed %ld kps\n", speed);
-  printf("}\n");
+  g_printf("define tapetype %s {\n", typename);
+  g_printf(_("    comment \"just produced by tapetype prog (hardware compression %s)\"\n"),
+       hwcompr ? _("on") : _("off"));
+  g_printf("    length %lld %s\n", (long long)size, sizeunits);
+  g_printf("    filemark %zu kbytes\n", filemark);
+  g_printf("    speed %lu kps\n", speed);
+  g_printf("}\n");
 
   if (tapefd_rewind(fd) == -1) {
-    fprintf(stderr, "%s: could not rewind %s: %s\n",
+    g_fprintf(stderr, _("%s: could not rewind %s: %s\n"),
            sProgName, tapedev, strerror(errno));
-    free(randombytes);
     return 1;
   }
 
   if (tapefd_close(fd) == -1) {
-    fprintf(stderr, "%s: could not close %s: %s\n",
+    g_fprintf(stderr, _("%s: could not close %s: %s\n"),
            sProgName, tapedev, strerror(errno));
-    free(randombytes);
     return 1;
   }
 
-  free(randombytes);
   return 0;
 }