home *** CD-ROM | disk | FTP | other *** search
/ Club Amiga de Montreal - CAM / CAM_CD_1.iso / files / 157.lha / Arc_Src / arcio.c < prev    next >
Encoding:
C/C++ Source or Header  |  1988-04-27  |  4.7 KB  |  140 lines

  1. /*  ARC - Archive utility - ARCIO
  2.  
  3. System V Version 1.0 based upon:
  4.     Version 2.30, created on 02/03/86 at 22:56:00
  5.  
  6. (C) COPYRIGHT 1985 by System Enhancement Associates; ALL RIGHTS RESERVED
  7.  
  8.     By:  Thom Henderson
  9.  
  10.     Description:
  11.          This file contains the file I/O routines used to manipulate
  12.          an archive.
  13. */
  14. #include "arc.h"
  15.  
  16. INT readhdr(hdr,f)                     /* read a header from an archive */
  17. struct heads *hdr;                     /* storage for header */
  18. FILE *f;                               /* archive to read header from */
  19. {
  20.     unsigned char dummy[28];
  21.     INT i,j,k;
  22.     char name[FNLEN];                  /* filename buffer */
  23.     INT try = 0;                       /* retry counter */
  24.     static INT first = 1;              /* true only on first read */
  25.  
  26.     if(!f)                             /* if archive didn't open */
  27.          return 0;                     /* then pretend it's the end */
  28.     if(feof(f))                        /* if no more data */
  29.          return 0;                     /* then signal end of archive */
  30.  
  31.     if(fgetc(f)!=ARCMARK)              /* check archive validity */
  32.     {    if(warn)
  33.          {    printf("An entry in %s has a bad header.\n",arcname);
  34.               nerrs++;
  35.          }
  36.  
  37.          while(!feof(f))
  38.          {    try++;
  39.               if(fgetc(f)==ARCMARK)
  40.               {    ungetc(hdrver=fgetc(f),f);
  41.                    if(hdrver>=0 && hdrver<=ARCVER)
  42.                         break;
  43.               }
  44.          }
  45.  
  46.          if(feof(f) && first)
  47.               abort("%s is not an archive",arcname);
  48.  
  49.          if(warn)
  50.               printf("  %d bytes skipped.\n",try);
  51.  
  52.          if(feof(f))
  53.               return 0;
  54.     }
  55.  
  56.     hdrver = fgetc(f);                 /* get header version */
  57.     if(hdrver<0)
  58.          abort("Invalid header in archive %s",arcname);
  59.     if(hdrver==0)
  60.          return 0;                     /* note our end of archive marker */
  61.     if(hdrver>ARCVER)
  62.     {    fread(name,sizeof(char),FNLEN,f);
  63.          printf("I don't know how to handle file %s in archive %s\n",
  64.               name,arcname);
  65.          printf("I think you need a newer version of ARC.\n");
  66.          exit(1);
  67.     }
  68.  
  69.     /* amount to read depends on header type */
  70.  
  71.     if(hdrver==1)                      /* old style is shorter */
  72.     {    fread(hdr,sizeof(struct heads)-sizeof(long),1,f);
  73.          hdrver = 2;                   /* convert header to new format */
  74.          hdr->length = hdr->size;      /* size is same when not packed */
  75.     }
  76.     else {
  77.     fread(dummy,27,1,f);
  78.  
  79.     for(i=0;i<13;hdr->name[i]=dummy[i],i++);
  80.     hdr->size = (long)((dummy[16]<<24) + (dummy[15]<<16) + (dummy[14]<<8)
  81.         + dummy[13]);
  82.     hdr->date = (short)((dummy[18]<<8) + dummy[17]);
  83.     hdr->time = (short)((dummy[20]<<8) + dummy[19]);
  84.     hdr->crc  = (short)((dummy[22]<<8) + dummy[21]);
  85.     hdr->length = (long)((dummy[26]<<24) + (dummy[25]<<16)
  86.         + (dummy[24]<<8) + dummy[23]);
  87.     }
  88.  
  89.     first = 0; return 1;               /* we read something */
  90. }
  91.  
  92. INT writehdr(hdr,f)                    /* write a header to an archive */
  93. struct heads *hdr;                     /* header to write */
  94. FILE *f;                               /* archive to write to */
  95. {
  96.     unsigned char dummy[27];
  97.  
  98.     fputc(ARCMARK,f);                  /* write out the mark of ARC */
  99.     fputc(hdrver,f);                   /* write out the header version */
  100.     if(!hdrver)                        /* if that's the end */
  101.          return;                       /* then write no more */
  102.  
  103.     fwrite(hdr->name,1,13,f);
  104.     fputc(hdr->size&255,f);         fputc((hdr->size>>8)&255,f);
  105.     fputc((hdr->size>>16)&255,f);   fputc((hdr->size>>24)&255,f);
  106.     fputc(hdr->date&255,f);         fputc((hdr->date>>8)&255,f);
  107.     fputc(hdr->time&255,f);         fputc((hdr->time>>8)&255,f);
  108.     fputc(hdr->crc&255,f);          fputc((hdr->crc>>8)&255,f);
  109.     fputc(hdr->length&255,f);       fputc((hdr->length>>8)&255,f);
  110.     fputc((hdr->length>>16)&255,f); fputc((hdr->length>>24)&255,f);
  111.  
  112.     /* note the newest file for updating the archive timestamp */
  113.  
  114.     if(hdr->date>arcdate
  115.     ||(hdr->date==arcdate && hdr->time>arctime))
  116.     {    arcdate = hdr->date;
  117.          arctime = hdr->time;
  118.     }
  119. }
  120.  
  121. INT filecopy(f,t,size)                 /* bulk file copier */
  122. FILE *f, *t;                           /* from, to */
  123. long size;                             /* number of bytes */
  124. {
  125.     INT len;                           /* length of a given copy */
  126.     INT putc_tst();
  127.  
  128.     while(size--)                      /* while more bytes to move */
  129.          putc_tst(fgetc(f),t);
  130. }
  131.  
  132. INT putc_tst(c,t)                      /* put a character, with tests */
  133. char c;                                /* character to output */
  134. FILE *t;                               /* file to write to */
  135. {
  136.     if(t)
  137.          if(fputc(c,t)==EOF)
  138.               abort("Write fail (disk full?)");
  139. }
  140.