home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Frozen Fish 1: Amiga
/
FrozenFish-Apr94.iso
/
bbs
/
alib
/
d1xx
/
d162
/
iffar.lha
/
Iffar
/
toc.c
< prev
Wrap
C/C++ Source or Header
|
1988-10-02
|
4KB
|
157 lines
/* iffar - IFF CAT archiver table of contents functions
By Karl Lehenbauer, version 1.2, release date 5/9/88.
This code is released to the public domain.
See the README file for more information.
*/
#include <exec/types.h>
#include <exec/memory.h>
#include <stdio.h>
#include <fcntl.h>
#include "assert.h"
#include "iff.h"
#define ID_NAME MakeID('N','A','M','E')
#define ID_AUTH MakeID('A','U','T','H')
#define ID_ANNO MakeID('A','N','N','O')
#define ID_Copyright MakeID('(','c',')',' ')
extern long lseek();
extern ULONG nextchunk();
int table_of_contents(fname)
char *fname;
{
int fd;
ULONG cat_type, chunkid, innerchunkid, subtype;
long chunksize, innerchunksize, filesize;
char namebuf[256];
extern int verbose;
if ((fd = OpenCAT(fname,&cat_type,&filesize)) == -1)
{
fprintf(stderr,"Can't open archive '%s'\n",fname);
return(0);
}
if (verbose)
{
fprintf(stderr,"CAT subtype is ");
PutID(cat_type);
fprintf(stderr,"\n");
}
while ((chunkid = nextCATchunk(fd,&subtype,&namebuf[0],&chunksize,&filesize)) != 0L)
{
/* if the chunk type isn't FORM, CAT or LIST, skip it */
if (chunkid != ID_FORM && chunkid != ID_CAT && chunkid != ID_LIST)
{
if (verbose)
{
PutID(chunkid);
fprintf(stderr," chunk is being skipped\n");
}
skipchunk(fd,chunksize,&filesize);
goto bigchunkdone;
}
if (namebuf[0] == '\0')
{
fprintf(stderr,"CAT entry didn't contain a FNAM chunk - skipping\n");
skipchunk(fd,chunksize,&filesize);
goto bigchunkdone;
}
PutID(chunkid);
fprintf(stderr," ");
/* print out the chunk length */
PutID(subtype);
fprintf(stderr," %6ld %s\n",chunksize, namebuf);
/* if verbose isn't selected, skip the rest of the chunks in the
* embedded FORM, CAT or LIST
*/
if (!verbose)
{
skipchunk(fd,chunksize,&filesize);
goto bigchunkdone;
}
/* else verbose is selected, dive down into the embedded FORM,
* CAT or LIST and print chunks found there and their contents
* when they're known to be text.
*/
/* follow a good neighbor policy by reducing our (the parent's)
* chunk size by the size we've found - since we'll be moving
* through the embedded FORM effectively recursively; that is,
* we'll be using the same nextchunk, skipchunk, readchunk
* routines on the chunk nextchunk got for us, we'll
* decrease parent chunk size by the size we've found,
* as, when calling nextchunk, skipchunk and readchunk below,
* we'll be concerned with keeping track of the form's chunk length
* as a virtual EOF, rather than the whole CAT's as above
*/
filesize -= chunksize;
if (chunksize & 1)
filesize--;
while (chunksize != 0)
{
/* get the type and size of the inner chunk */
innerchunkid = nextchunk(fd,&innerchunksize,&chunksize);
if (chunksize == 0)
break;
/* print some presumably useful information */
fprintf(stderr," ");
PutID(innerchunkid);
switch(innerchunkid)
{
case ID_FNAM:
panic("more than one FNAM chunk in an embedded FORM");
case ID_NAME:
case ID_AUTH:
case ID_ANNO:
case ID_Copyright:
if (innerchunksize >= sizeof(namebuf))
{
fprintf(stderr,"[too long]\n");
skipchunk(fd,innerchunksize,&chunksize);
}
else
{
if (!readchunk(fd,namebuf,innerchunksize,&chunksize))
{
fprintf(stderr,"got into trouble reading chunk text\n");
return(0);
}
namebuf[innerchunksize] = '\0';
fprintf(stderr,", %s\n",namebuf);
}
break;
default:
fprintf(stderr,", size %ld\n",innerchunksize);
/* skip the body of the subchunk */
skipchunk(fd,innerchunksize,&chunksize);
}
}
/* we make it to here if the length of all the subchunks equalled
* the length of their superchunk
*/
bigchunkdone: ;
}
close(fd);
}
/* end of toc.c */