home *** CD-ROM | disk | FTP | other *** search
/ back2roots/padua / padua.7z / padua / amix / AmigaDOS-Emu.zoo / loadseg.c < prev    next >
C/C++ Source or Header  |  1992-01-14  |  5KB  |  215 lines

  1. #include <stdio.h>
  2.  
  3. extern char *Malloc(), *Realloc(), *Calloc();
  4.  
  5. typedef unsigned long ULONG;
  6.  
  7. #include "load.h"
  8.  
  9. #define Vprintf if (0) (void)
  10.  
  11.  
  12. static int fskip(fp, offset)
  13. FILE *fp;
  14. long offset;
  15. {
  16.     while (--offset>=0)
  17.     if (getc(fp)==EOF)
  18.         return ferror(fp) ? -1 : 0;
  19.     return 1;
  20. }
  21.  
  22.  
  23. #define ABORT goto errexit
  24.  
  25. ULONG *adosload(fp, name, verbose)
  26. FILE *fp;
  27. char *name;
  28. int verbose;
  29. {
  30.     ULONG **hunktab;
  31.     register i;
  32.     int len, curhunk, numhunks;
  33.     int name_len=20;
  34.     char *name_buf = Malloc(20);
  35.     ULONG hunktype, count, first, last, offset;
  36.     static char *segtypes[] =
  37.     {
  38.     "code", "data", "bss",
  39.     };
  40.  
  41.     while ((len=fread(&hunktype, sizeof hunktype, 1, fp))==1)
  42.     switch (hunktype)
  43.     {
  44.         ULONG tmp;
  45.     case hunk_symbol:
  46.         while ((len=fread(&count, sizeof count, 1, fp))==1 &&
  47.            count)
  48.         (void)fskip(fp, (count+1)*4);
  49.         break;
  50.     case hunk_unit:
  51.         if ((len=fread(&count, sizeof count, 1, fp))!=1)
  52.         ABORT;
  53.         count /= 4;
  54.         if (count>name_len)
  55.         name_buf = Realloc(name_buf, name_len=count);
  56.         if (fread(name_buf, (int)count, 1, fp)!=1)
  57.         ABORT;
  58.         Vprintf("hunk_unit: `%.*s'\n", (int)count, name_buf);
  59.         break;
  60.     case hunk_header:
  61.         Vprintf("hunk_header:\n");
  62.         while (1)
  63.         {
  64.         if ((len=fread(&count, sizeof count, 1, fp))!=1)
  65.             ABORT;
  66.         if (count==0L)
  67.             break;
  68.         count *= 4;
  69.         if (count>name_len)
  70.             name_buf = Realloc(name_buf, name_len=count);
  71.         if (fread(name_buf, (int)count, 1, fp)!=1)
  72.             ABORT;
  73.         Vprintf("\tlibname: `%.*s'\n", (int)count, name_buf);
  74.         }
  75.         if ((len=fread(&numhunks , sizeof numhunks, 1, fp))!=1)
  76.         ABORT;
  77.         Vprintf("\tHunk count: %ld\n", numhunks);
  78.         hunktab = (ULONG **)Calloc(numhunks, sizeof (ULONG));
  79.         if ((len=fread(&first, sizeof first, 1, fp))!=1)
  80.         ABORT;
  81.         Vprintf("\tFirst hunk: %ld\n", first);
  82.         curhunk = first;
  83.         if ((len=fread(&last, sizeof last, 1, fp))!=1)
  84.         ABORT;
  85.         Vprintf("\tLast hunk: %ld\n", last);
  86.         for ( i=first ; i<=last ; ++i )
  87.         {
  88.         if ((len=fread(&count, sizeof count, 1, fp))!=1)
  89.             ABORT;
  90.         tmp = count & 0xC0000000;
  91.         count &= 0x3FFFFFFF;
  92.         Vprintf("\tHunk %d size: 0x%06lx bytes in ", i, count*4);
  93.         switch (tmp)
  94.         {
  95.         case 0x80000000:
  96.             Vprintf("FAST");
  97.             break;
  98.         case 0x40000000:
  99.             Vprintf("CHIP");
  100.             break;
  101.         default:
  102.             Vprintf("ANY");
  103.             break;
  104.         }
  105.         Vprintf(" memory\n");
  106.         hunktab[i] = (ULONG *)Calloc(count+2, 4);
  107.         hunktab[i][0] = count;
  108.         if (i>0)
  109.             hunktab[i-1][1] = (ULONG)(&hunktab[i][1]);
  110.         }
  111.         break;
  112.     case hunk_code:
  113.     case hunk_data:
  114.     case hunk_bss:
  115.         if ((len=fread(&count, sizeof count, 1, fp))!=1)
  116.         ABORT;
  117.         tmp = count & 0xC0000000;
  118.         count &= 0x3FFFFFFF;
  119.         Vprintf("hunk_%s(%d): Length: 0x%06lx bytes in ",
  120.            segtypes[hunktype-hunk_code], curhunk, count*4);
  121.         switch (tmp)
  122.         {
  123.         case 0x80000000:
  124.         Vprintf("FAST");
  125.         break;
  126.         case 0x40000000:
  127.         Vprintf("CHIP");
  128.         break;
  129.         default:
  130.         Vprintf("ANY");
  131.         break;
  132.         }
  133.         Vprintf(" memory\n");
  134.  
  135.         if (hunktype != hunk_bss && count)
  136.         if ((len=fread(hunktab[curhunk]+2, count*4, 1, fp))!=1)
  137.             ABORT;
  138.         break;
  139.     case hunk_reloc32:
  140.         Vprintf("hunk_reloc(32):\n");
  141.         while (1)
  142.         {
  143.         ULONG *addr;
  144.         if ((len=fread(&count, sizeof count, 1, fp))!=1)
  145.             ABORT;
  146.         if (count==0L)
  147.             break;
  148.         i = count;
  149.         if ((len=fread(&count, sizeof count, 1, fp))!=1)
  150.             ABORT;
  151.         Vprintf("\tHunk #%ld:\n", count);
  152.         while (i>0)
  153.         {
  154.             if ((len=fread(&offset, sizeof offset, 1, fp))!=1)
  155.             ABORT;
  156.             Vprintf("\t\t0x%06lx\n", offset);
  157.             addr = (ULONG *)((unsigned char *)(&hunktab[curhunk][2])
  158.                      + offset);
  159.             *addr += (ULONG)(hunktab[count]+2);
  160.             --i;
  161.         }
  162.         }
  163.         break;
  164.     case hunk_end:
  165.         Vprintf("hunk_end\n");
  166.         ++curhunk;
  167.         break;
  168.     case hunk_reloc16:
  169.     case hunk_reloc8:
  170.     case hunk_name:
  171.     case hunk_ext:
  172.     case hunk_debug:
  173.     case hunk_overlay:
  174.     case hunk_break:
  175.     default:
  176.         if (verbose)
  177.         fprintf(stderr, "adosload: Invalid hunk type 0x%08lX in %s\n",
  178.             hunktype, name);
  179.         return 0;
  180.     }
  181.  
  182.     if (!ferror(fp))
  183.     return hunktab[0]+1;
  184.  
  185. errexit:
  186.     if (verbose)
  187.     if (len==0)
  188.     {
  189.         fprintf(stderr, "adosload: unexpected EOF in %06lx hunk in %s\n",
  190.             hunktype, name);
  191.     }
  192.     else
  193.     {
  194.         char buf[BUFSIZ];
  195.         sprintf(buf, "adosload: read error in %06lx hunk in %s",
  196.             hunktype, name);
  197.         perror(buf);
  198.     }
  199.     return 0;
  200. }
  201.  
  202.  
  203. ULONG *LoadSeg(name)
  204. char *name;
  205. {
  206.     FILE *fp;
  207.     ULONG *seg;
  208.  
  209.     if ( (fp=fopen(name, "r")) == NULL )
  210.     return (ULONG *)0;
  211.     seg = adosload(fp, name, 1);
  212.     fclose(fp);
  213.     return seg;
  214. }
  215.