home *** CD-ROM | disk | FTP | other *** search
/ Crazy Collection 12 / CC-12_1.iso / update / doompack / data.a00 / ADE2.ZIP / SOURCE / SOURCE2.ZIP / WADS.C < prev    next >
Encoding:
C/C++ Source or Header  |  1994-12-08  |  18.9 KB  |  734 lines

  1. /*
  2.    Amazing Doom Editor, by Brendon Wyber and RaphaĆ«l Quinet.
  3.  
  4.    You are allowed to use any parts of this code in another program, as
  5.    long as you give credits to the authors in the documentation and in
  6.    the program itself.  Read the file README.1ST for more information.
  7.  
  8.    This program comes with absolutely no warranty.
  9.  
  10.    WAD.C - Wad files routines.
  11. */
  12.  
  13. /* the includes */
  14. #include "deu.h"
  15.  
  16. /* global variables */
  17. WadPtr WadFileList = NULL;       /* linked list of wad files */
  18. MDirPtr MasterDir = NULL;        /* the master directory */
  19.  
  20. int convflag;
  21. int tempint = 0;
  22. Bool buildlev = FALSE;
  23.  
  24. /*
  25.    open the main wad file, read in its directory and create the
  26.    master directory
  27. */
  28.  
  29. void OpenMainWad( char *filename)
  30. {
  31.    MDirPtr lastp, newp;
  32.    long n;
  33.    WadPtr wad;
  34.  
  35.    /* open the wad file */
  36.    printf( "\nLoading main WAD file: %s...\n", filename);
  37.    wad = BasicWadOpen( filename);
  38.    if (strncmp( wad->type, "IWAD", 4))
  39.       ProgError( "\"%s\" is not the main WAD file!", filename);
  40.  
  41.    /* create the master directory */
  42.    lastp = NULL;
  43.    for (n = 0; n < wad->dirsize; n++)
  44.    {
  45.       newp = GetMemory( sizeof( struct MasterDirectory));
  46.       newp->next = NULL;
  47.       newp->wadfile = wad;
  48.       memcpy( &(newp->dir), &(wad->directory[ n]), sizeof( struct Directory));
  49.       if (MasterDir)
  50.          lastp->next = newp;
  51.       else
  52.          MasterDir = newp;
  53.       lastp = newp;
  54.    }
  55.  
  56.    /* check if registered version */
  57.    if (FindMasterDir( MasterDir, "SLIME01") == NULL)
  58.    {
  59.       ProgError( "\"%s\" is not the main Doom II WAD file!", filename);
  60.    }
  61.    else
  62.    {
  63.       if (FindMasterDir( MasterDir, "MAP01") == NULL)
  64.          Registered = FALSE;
  65.       else
  66.       if ((FindMasterDir( MasterDir, "MAP01") != NULL) && (FindMasterDir( MasterDir, "MAP30") != NULL))
  67.          Registered = TRUE;
  68.    }
  69. }
  70.  
  71.  
  72.  
  73. /*
  74.    open a patch wad file, read in its directory and alter the master
  75.    directory
  76. */
  77.  
  78. void OpenPatchWad( char *filename)
  79. {
  80.    WadPtr wad;
  81.    MDirPtr mdir;
  82.    int n, l;
  83.    char entryname[9];
  84.    char newname[9];
  85.    int episode = 0;
  86.    int mission = 0;
  87.    Bool noflag = FALSE;
  88.    char *outfile;
  89.  
  90.    /* ignore the file if it doesn't exist */
  91.    if (! Exists( filename))
  92.    {
  93.       printf( "Warning: patch WAD file \"%s\" doesn't exist.  Ignored.\n", filename);
  94.       return;
  95.    }
  96.  
  97.    /* open the wad file */
  98.    printf( "Loading patch WAD file: %s...\n", filename);
  99.    wad = BasicWadOpen( filename);
  100.    if (strncmp( wad->type, "PWAD", 4))
  101.       ProgError( "\"%s\" is not a patch WAD file", filename);
  102.  
  103.    /* alter the master directory */
  104.    l = 0;
  105.    for (n = 0; n < wad->dirsize; n++)
  106.    {
  107.       strncpy( entryname, wad->directory[ n].name, 8);
  108.       entryname[8] = '\0';
  109.       newname[8] = '\0';
  110.       if (l == 0)
  111.       {
  112.          if (convflag == 1)
  113.             EditLevel( episode, mission, 0);
  114.          mdir = FindMasterDir( MasterDir, wad->directory[ n].name);
  115.          /* if this entry is not in the master directory, then add it */
  116.          if ((mdir == NULL) && (wad->directory[ n].name[ 0] != 'E' && wad->directory[ n].name[ 2] != 'M' && wad->directory[ n].name[ 4] != '\0'))
  117.          {
  118.             printf( "   [Adding new entry %s]\n", entryname);
  119.             mdir = MasterDir;
  120.             while (mdir->next)
  121.                mdir = mdir->next;
  122.             mdir->next = GetMemory( sizeof( struct MasterDirectory));
  123.             mdir = mdir->next;
  124.             mdir->next = NULL;
  125.          }
  126.          /* if this is a level, then copy this entry and the next 10 */
  127.          else if ((wad->directory[ n].name[ 0] == 'M' && wad->directory[ n].name[ 1] == 'A' && wad->directory[ n].name[ 5] == '\0') || (wad->directory[ n].name[ 0] == 'E' && wad->directory[ n].name[ 2] == 'M' && wad->directory[ n].name[ 4] == '\0'))
  128.          {
  129.             convflag = 0;
  130.             if (wad->directory[ n].name[ 0] == 'E' && wad->directory[ n].name[ 2] == 'M' && wad->directory[ n].name[ 4] == '\0')
  131.             {
  132.                InitGfx();
  133.                SelectTranslatedLevel (&episode, &mission, entryname);
  134.                TermGfx();
  135.                sprintf( newname, "MAP%d%d", episode, mission);
  136.                strncpy( wad->directory[ n].name, newname, 8);
  137.                strncpy( mdir->dir.name, newname, 8);
  138.                strncpy( entryname, newname, 8);
  139.                mdir = FindMasterDir( MasterDir, wad->directory[ n].name);
  140.                convflag = 1;
  141.             }
  142.             printf( "   [Updating level %s]\n", entryname);
  143.             l = 10;
  144.          }
  145.          else
  146.             printf( "   [Updating entry %s]\n", entryname);
  147.       }
  148.       else
  149.       {
  150.          mdir = mdir->next;
  151.          /* the level data should replace an existing level */
  152.          if (mdir == NULL || strncmp(mdir->dir.name, wad->directory[ n].name, 8))
  153.             ProgError( "\%s\ is not an understandable PWAD file (error with %s)", filename, entryname);
  154.          l--;
  155.          if (l == 0 && convflag == 1)
  156.          {
  157.             mdir->wadfile = wad;
  158.             memcpy( &(mdir->dir), &(wad->directory[ n]), sizeof( struct Directory));
  159.             EditLevel( episode, mission, 0);
  160.             noflag = TRUE;
  161.             buildlev = TRUE;
  162.          }
  163.       }
  164.       if (noflag == FALSE)
  165.       {
  166.          mdir->wadfile = wad;
  167.          memcpy( &(mdir->dir), &(wad->directory[ n]), sizeof( struct Directory));
  168.       }
  169.       noflag = FALSE;
  170.    }
  171. }
  172.  
  173. void DoBuild()
  174. {
  175.    char *outfile = GetMemory( 80);
  176.    if (buildlev == TRUE)
  177.    {
  178.       buildlev = FALSE;
  179.       InitGfx();
  180.       sprintf( outfile, "OUTPUT.WAD");
  181.       InputFileName( -1, -1, "Save converted WAD as:", 79, outfile);
  182.       if (strlen( outfile) == 0)
  183.          sprintf( outfile, "(null)");
  184.       TermGfx();
  185.       BuildNewMainWad( outfile, TRUE);
  186.    }
  187. }
  188.  
  189. char *GetTemporary()
  190. {
  191.    char *tempfile = GetMemory( 80);
  192.    tempint++;
  193.  
  194.    sprintf( tempfile, "$TMP$%i.WAD", tempint);
  195.    return tempfile;
  196. }
  197.  
  198. /*
  199.    close all the wad files, deallocating the WAD file structures
  200. */
  201.  
  202. void CloseWadFiles()
  203. {
  204.    WadPtr curw, nextw;
  205.    MDirPtr curd, nextd;
  206.  
  207.    /* close the wad files */
  208.    curw = WadFileList;
  209.    WadFileList = NULL;
  210.    while (curw)
  211.    {
  212.       nextw = curw->next;
  213.       fclose( curw->fileinfo);
  214.       FreeMemory( curw->directory);
  215.       FreeMemory( curw);
  216.       curw = nextw;
  217.    }
  218.  
  219.    /* delete the master directory */
  220.    curd = MasterDir;
  221.    MasterDir = NULL;
  222.    while (curd)
  223.    {
  224.       nextd = curd->next;
  225.       FreeMemory( curd);
  226.       curd = nextd;
  227.    }
  228. }
  229.  
  230.  
  231.  
  232. /*
  233.    forget unused patch wad files
  234. */
  235.  
  236. void CloseUnusedWadFiles()
  237. {
  238.    WadPtr curw, prevw;
  239.    MDirPtr mdir;
  240.  
  241.    prevw = NULL;
  242.    curw = WadFileList;
  243.    while (curw)
  244.    {
  245.       /* check if the wad file is used by a directory entry */
  246.       mdir = MasterDir;
  247.       while (mdir && mdir->wadfile != curw)
  248.          mdir = mdir->next;
  249.       if (mdir)
  250.          prevw = curw;
  251.       else
  252.       {
  253.          /* if this wad file is never used, close it */
  254.          if (prevw)
  255.             prevw->next = curw->next;
  256.          else
  257.             WadFileList = curw->next;
  258.          fclose( curw->fileinfo);
  259.          FreeMemory( curw->directory);
  260.          FreeMemory( curw);
  261.       }
  262.       curw = prevw->next;
  263.    }
  264. }
  265.  
  266.  
  267.  
  268. /*
  269.    basic opening of WAD file and creation of node in Wad linked list
  270. */
  271.  
  272. WadPtr BasicWadOpen( char *filename)
  273. {
  274.    WadPtr curw, prevw;
  275.  
  276.    /* find the wad file in the wad file list */
  277.    prevw = WadFileList;
  278.    if (prevw)
  279.    {
  280.       curw = prevw->next;
  281.       while (curw && strcmp( filename, curw->filename))
  282.       {
  283.          prevw = curw;
  284.          curw = prevw->next;
  285.       }
  286.    }
  287.    else
  288.       curw = NULL;
  289.  
  290.    /* if this entry doesn't exist, add it to the WadFileList */
  291.    if (curw == NULL)
  292.    {
  293.       curw = GetMemory( sizeof( struct WadFileInfo));
  294.       if (prevw == NULL)
  295.          WadFileList = curw;
  296.       else
  297.          prevw->next = curw;
  298.       curw->next = NULL;
  299.       curw->filename = filename;
  300.    }
  301.  
  302.    /* open the file */
  303.    if ((curw->fileinfo = fopen( filename, "rb")) == NULL)
  304.       ProgError( "error opening \"%s\"", filename);
  305.  
  306.    /* read in the WAD directory info */
  307.    BasicWadRead( curw, curw->type, 4);
  308.    if (strncmp( curw->type, "IWAD", 4) && strncmp( curw->type, "PWAD", 4))
  309.       ProgError( "\"%s\" is not a valid WAD file", filename);
  310.    BasicWadRead( curw, &curw->dirsize, sizeof( curw->dirsize));
  311.    BasicWadRead( curw, &curw->dirstart, sizeof( curw->dirstart));
  312.  
  313.    /* read in the WAD directory itself */
  314.    curw->directory = GetMemory( sizeof( struct Directory) * curw->dirsize);
  315.    BasicWadSeek( curw, curw->dirstart);
  316.    BasicWadRead( curw, curw->directory, sizeof( struct Directory) * curw->dirsize);
  317.  
  318.    /* all done */
  319.    return curw;
  320. }
  321.  
  322.  
  323.  
  324. /*
  325.    read bytes from a file and store it into an address with error checking
  326. */
  327.  
  328. void BasicWadRead( WadPtr wadfile, void huge *addr, long size)
  329. {
  330.    if (fread( addr, 1, size, wadfile->fileinfo) != size)
  331.       ProgError( "error reading from \"%s\"", wadfile->filename);
  332. }
  333.  
  334.  
  335.  
  336. /*
  337.    go to offset of wad file with error checking
  338. */
  339.  
  340. void BasicWadSeek( WadPtr wadfile, long offset)
  341. {
  342.    if (fseek( wadfile->fileinfo, offset, 0))
  343.       ProgError( "error reading from \"%s\"", wadfile->filename);
  344. }
  345.  
  346.  
  347.  
  348. /*
  349.    find an entry in the master directory
  350. */
  351.  
  352. MDirPtr FindMasterDir( MDirPtr from, char *name)
  353. {
  354.    while (from)
  355.    {
  356.       if (!strncmp( from->dir.name, name, 8))
  357.          break;
  358.       from = from->next;
  359.    }
  360.    return from;
  361. }
  362.  
  363.  
  364.  
  365. /*
  366.    list the master directory
  367. */
  368.  
  369. void ListMasterDirectory( FILE *file)
  370. {
  371.    char dataname[ 9];
  372.    MDirPtr dir;
  373.    char key;
  374.    int lines = 3;
  375.  
  376.    dataname[ 8] = '\0';
  377.    fprintf( file, "The Master Directory\n");
  378.    fprintf( file, "====================\n\n");
  379.    fprintf( file, "NAME____  FILE________________  SIZE__  START____\n");
  380.    for (dir = MasterDir; dir; dir = dir->next)
  381.    {
  382.       strncpy( dataname, dir->dir.name, 8);
  383.       fprintf( file, "%-8s  %-20s  %6ld  x%08lx\n", dataname, dir->wadfile->filename, dir->dir.size, dir->dir.start);
  384.       if (file == stdout && lines++ > 21)
  385.       {
  386.          lines = 0;
  387.          printf( "[Q to abort, any other key to continue]");
  388.          key = bioskey( 0);
  389.          printf( "\r                                       \r");
  390.          if (key == 'Q' || key == 'q')
  391.             break;
  392.       }
  393.    }
  394. }
  395.  
  396.  
  397.  
  398. /*
  399.    list the directory of a file
  400. */
  401.  
  402. void ListFileDirectory( FILE *file, WadPtr wad)
  403. {
  404.    char dataname[ 9];
  405.    char key;
  406.    int lines = 5;
  407.    long n;
  408.  
  409.    dataname[ 8] = '\0';
  410.    fprintf( file, "WAD File Directory\n");
  411.    fprintf( file, "==================\n\n");
  412.    fprintf( file, "Wad File: %s\n\n", wad->filename);
  413.    fprintf( file, "NAME____  SIZE__  START____  END______\n");
  414.    for (n = 0; n < wad->dirsize; n++)
  415.    {
  416.       strncpy( dataname, wad->directory[n].name, 8);
  417.       fprintf( file, "%-8s  %6ld  x%08lx  x%08lx\n", dataname, wad->directory[n].size, wad->directory[n].start, wad->directory[n].size + wad->directory[n].start - 1);
  418.       if (file == stdout && lines++ > 21)
  419.       {
  420.          lines = 0;
  421.          printf( "[Q to abort, any other key to continue]");
  422.          key = bioskey( 0);
  423.          printf( "\r                                       \r");
  424.          if (key == 'Q' || key == 'q')
  425.             break;
  426.       }
  427.    }
  428. }
  429.  
  430.  
  431.  
  432. /*
  433.    build a new wad file from master dictionary
  434. */
  435.  
  436. void BuildNewMainWad( char *filename, Bool patchonly)
  437. {
  438.    FILE *file;
  439.    long counter = 12;
  440.    MDirPtr cur;
  441.    long size;
  442.    long dirstart;
  443.    long dirnum;
  444.  
  445.    /* open the file and store signatures */
  446.    if (patchonly)
  447.       printf( "Building a compound Patch Wad file \"%s\".\n", filename);
  448.    else
  449.       printf( "Building a new Main Wad file \"%s\" (size approx 14000K)\n", filename);
  450.    if ((file = fopen( filename, "wb")) == NULL)
  451.       ProgError( "unable to open file \"%s\"", filename);
  452.    if (patchonly)
  453.       WriteBytes( file, "PWAD", 4);
  454.    else
  455.       WriteBytes( file, "IWAD", 4);
  456.    WriteBytes( file, &counter, 4L);      /* put true value in later */
  457.    WriteBytes( file, &counter, 4L);      /* put true value in later */
  458.  
  459.    /* output the directory data chuncks */
  460.    for (cur = MasterDir; cur; cur = cur->next)
  461.    {
  462.       if (patchonly && cur->wadfile == WadFileList)
  463.          continue;
  464.       size = cur->dir.size;
  465.       counter += size;
  466.       BasicWadSeek( cur->wadfile, cur->dir.start);
  467.       CopyBytes( file, cur->wadfile->fileinfo, size);
  468.       printf( "Size: %dK\r", counter / 1024);
  469.    }
  470.  
  471.    /* output the directory */
  472.    dirstart = counter;
  473.    counter = 12;
  474.    dirnum = 0;
  475.    for (cur = MasterDir; cur; cur = cur->next)
  476.    {
  477.       if (patchonly && cur->wadfile == WadFileList)
  478.          continue;
  479.       if (dirnum % 100 == 0)
  480.          printf( "Outputting directory %04d...\r", dirnum);
  481.       if (cur->dir.start)
  482.          WriteBytes( file, &counter, 4L);
  483.       else
  484.          WriteBytes( file, &(cur->dir.start), 4L);
  485.       WriteBytes( file, &(cur->dir.size), 4L);
  486.       WriteBytes( file, &(cur->dir.name), 8L);
  487.       counter += cur->dir.size;
  488.       dirnum++;
  489.    }
  490.  
  491.    /* fix up the number of entries and directory start information */
  492.    if (fseek( file, 4L, 0))
  493.       ProgError( "error writing to file");
  494.    WriteBytes( file, &dirnum, 4L);
  495.    WriteBytes( file, &dirstart, 4L);
  496.  
  497.    /* close the file */
  498.    printf( "                            \r");
  499.    fclose( file);
  500. }
  501.  
  502.  
  503.  
  504. /*
  505.    output bytes to a binary file with error checking
  506. */
  507.  
  508. void WriteBytes( FILE *file, void huge *addr, long size)
  509. {
  510.    if (! Registered)
  511.       return;
  512.    while (size > 0x8000)
  513.    {
  514.       if (fwrite( addr, 1, 0x8000, file) != 0x8000)
  515.          ProgError( "error writing to file");
  516.       addr = (char huge *)addr + 0x8000;
  517.       size -= 0x8000;
  518.    }
  519.    if (fwrite( addr, 1, size, file) != size)
  520.       ProgError( "error writing to file");
  521. }
  522.  
  523.  
  524.  
  525. /*
  526.    copy bytes from a binary file to another with error checking
  527. */
  528.  
  529. void CopyBytes( FILE *dest, FILE *source, long size)
  530. {
  531.    void huge *data;
  532.  
  533.    if (! Registered)
  534.       return;
  535.    data = GetFarMemory( 0x8000 + 2);
  536.    while (size > 0x8000)
  537.    {
  538.       if (fread( data, 1, 0x8000, source) != 0x8000)
  539.          ProgError( "error reading from file");
  540.       if (fwrite( data, 1, 0x8000, dest) != 0x8000)
  541.          ProgError( "error writing to file");
  542.       size -= 0x8000;
  543.    }
  544.    if (fread( data, 1, size, source) != size)
  545.       ProgError( "error reading from file");
  546.    if (fwrite( data, 1, size, dest) != size)
  547.       ProgError( "error writing to file");
  548.    FreeFarMemory( data);
  549. }
  550.  
  551.  
  552.  
  553. /*
  554.    check if a file exists and is readable
  555. */
  556.  
  557. Bool Exists( char *filename)
  558. {
  559.    FILE *test;
  560.  
  561.    if ((test = fopen( filename, "rb")) == NULL)
  562.       return FALSE;
  563.    fclose( test);
  564.    return TRUE;
  565. }
  566.  
  567.  
  568.  
  569. /*
  570.    dump a directory entry in hex
  571. */
  572.  
  573. void DumpDirectoryEntry( FILE *file, char *entryname)
  574. {
  575.    MDirPtr entry;
  576.    char dataname[ 9];
  577.    char key;
  578.    int lines = 5;
  579.    long n, c, i;
  580.    unsigned char buf[16];
  581.  
  582.  
  583.    c = 0;
  584.    entry = MasterDir;
  585.    while (entry)
  586.    {
  587.       if (!strnicmp( entry->dir.name, entryname, 8))
  588.       {
  589.          strncpy( dataname, entry->dir.name, 8);
  590.          dataname[ 8] = '\0';
  591.          fprintf( file, "Contents of entry %s (size = %ld bytes):\n", dataname, entry->dir.size);
  592.          BasicWadSeek( entry->wadfile, entry->dir.start);
  593.          n = 0;
  594.          i = -1;
  595.          for (c = 0; c < entry->dir.size; c += i)
  596.          {
  597.             fprintf( file, "%04X: ", n);
  598.             for (i = 0; i < 16; i++)
  599.             {
  600.                BasicWadRead( entry->wadfile, &(buf[ i]), 1);
  601.                fprintf( file, " %02X", buf[ i]);
  602.                n++;
  603.             }
  604.             fprintf( file, "   ");
  605.             for (i = 0; i < 16; i++)
  606.             {
  607.                if (buf[ i] >= 32)
  608.                   fprintf( file, "%c", buf[ i]);
  609.                else
  610.                   fprintf( file, " ");
  611.             }
  612.             fprintf( file, "\n");
  613.             if (file == stdout && lines++ > 21)
  614.             {
  615.                lines = 0;
  616.                printf( "[%d%% - Q to abort, S to skip this entry, any other key to continue]", n * 100 / entry->dir.size);
  617.                key = bioskey( 0);
  618.                printf( "\r                                                                    \r");
  619.                if (key == 'S' || key == 's')
  620.                   break;
  621.                if (key == 'Q' || key == 'q')
  622.                   return;
  623.             }
  624.          }
  625.       }
  626.       entry = entry->next;
  627.    }
  628.    if (! c)
  629.    {
  630.       printf( "[Entry not in master directory]\n");
  631.       return;
  632.    }
  633. }
  634.  
  635.  
  636.  
  637. /*
  638.    save a directory entry to disk
  639. */
  640.  
  641. void SaveDirectoryEntry( FILE *file, char *entryname)
  642. {
  643.    MDirPtr entry;
  644.    long    counter;
  645.    long    size;
  646.  
  647.    for (entry = MasterDir; entry; entry = entry->next)
  648.       if (!strnicmp( entry->dir.name, entryname, 8))
  649.          break;
  650.    if (entry)
  651.    {
  652.       WriteBytes( file, "PWAD", 4L);     /* PWAD file */
  653.       counter = 1L;
  654.       WriteBytes( file, &counter, 4L);   /* 1 entry */
  655.       counter = 12L;
  656.       WriteBytes( file, &counter, 4L);
  657.       counter = 28L;
  658.       WriteBytes( file, &counter, 4L);
  659.       size = entry->dir.size;
  660.       WriteBytes( file, &size, 4L);
  661.       WriteBytes( file, &(entry->dir.name), 8L);
  662.       BasicWadSeek( entry->wadfile, entry->dir.start);
  663.       CopyBytes( file, entry->wadfile->fileinfo, size);
  664.    }
  665.    else
  666.    {
  667.       printf( "[Entry not in master directory]\n");
  668.       return;
  669.    }
  670. }
  671.  
  672.  
  673.  
  674. /*
  675.    save a directory entry to disk, without a PWAD header
  676. */
  677.  
  678. void SaveEntryToRawFile( FILE *file, char *entryname)
  679. {
  680.    MDirPtr entry;
  681.  
  682.    for (entry = MasterDir; entry; entry = entry->next)
  683.       if (!strnicmp( entry->dir.name, entryname, 8))
  684.          break;
  685.    if (entry)
  686.    {
  687.       BasicWadSeek( entry->wadfile, entry->dir.start);
  688.       CopyBytes( file, entry->wadfile->fileinfo, entry->dir.size);
  689.    }
  690.    else
  691.    {
  692.       printf( "[Entry not in master directory]\n");
  693.       return;
  694.    }
  695. }
  696.  
  697.  
  698.  
  699. /*
  700.    encapsulate a raw file in a PWAD file
  701. */
  702.  
  703. void SaveEntryFromRawFile( FILE *file, FILE *raw, char *entryname)
  704. {
  705.    long    counter;
  706.    long    size;
  707.    char    name8[ 8];
  708.  
  709.    for (counter = 0L; counter < 8L; counter++)
  710.       name8[ counter] = '\0';
  711.    strncpy( name8, entryname, 8);
  712.    WriteBytes( file, "PWAD", 4L);     /* PWAD file */
  713.    counter = 1L;
  714.    WriteBytes( file, &counter, 4L);   /* 1 entry */
  715.    counter = 12L;
  716.    WriteBytes( file, &counter, 4L);
  717.    counter = 28L;
  718.    WriteBytes( file, &counter, 4L);
  719.    if (fseek( raw, 0L, SEEK_END) != 0)
  720.       ProgError( "error reading from raw file");
  721.    size = ftell( raw);
  722.    if (size < 0)
  723.       ProgError( "error reading from raw file");
  724.    if (fseek( raw, 0L, SEEK_SET) != 0)
  725.       ProgError( "error reading from raw file");
  726.    WriteBytes( file, &size, 4L);
  727.    WriteBytes( file, name8, 8L);
  728.    CopyBytes( file, raw, size);
  729. }
  730.  
  731.  
  732.  
  733. /* end of file */
  734.