home *** CD-ROM | disk | FTP | other *** search
/ Crawly Crypt Collection 1 / crawlyvol1.bin / program / compiler / sozobon / scsrc20 / tools / nm.c < prev    next >
C/C++ Source or Header  |  1991-03-01  |  6KB  |  377 lines

  1. /* Copyright (c) 1988,89,91 by Sozobon, Limited.  Author: Johann Ruegg
  2.  *
  3.  * Permission is granted to anyone to use this software for any purpose
  4.  * on any computer system, and to redistribute it freely, with the
  5.  * following restrictions:
  6.  * 1) No charge may be made other than reasonable charges for reproduction.
  7.  * 2) Modified versions must be clearly marked as such.
  8.  * 3) The authors are not responsible for any harmful consequences
  9.  *    of using this software, even if they result from defects in it.
  10.  *
  11.  *    Alternative ST symbol table lister.
  12.  */
  13.  
  14. #include <stdio.h>
  15. #ifndef UNIXHOST
  16. #include <ar.h>
  17. #else
  18. #include "crossar.h"
  19. long crossl();
  20. #endif
  21.  
  22. #ifdef    MINIX
  23.  
  24. #define    RMODE    "r"        /* binary file "read" mode for fopen */
  25. #define MAGIC0    0x410
  26. #define MAGIC    0x0301    /* magic number for an executable */
  27.  
  28. struct hdr_x {
  29.     long magic2;
  30.     long tsize, dsize, bsize;
  31.     long fill;
  32.     long totsize;
  33.     long nsyms;
  34. } h;
  35. #define HDRXLEN    28
  36. #define HDRLONGS    7
  37.  
  38. #else
  39.  
  40. #ifndef UNIXHOST
  41. #define    RMODE    "rb"        /* binary file "read" mode for fopen */
  42. #else
  43. #define RMODE    "r"
  44. #endif
  45. #define MAGIC    0x601a        /* magic number for an executable */
  46.  
  47. /*
  48.  * Executable file header
  49.  */
  50. struct hdr_x {
  51.     long    tsize, dsize, bsize;
  52.     long    nsyms;
  53.     long    f1, f2;        /* filler */
  54.     short    f3;
  55. } h;
  56. #define HDRXLEN    26
  57. #define HDRLONGS    4
  58. #endif
  59.  
  60. #ifndef UNIXHOST
  61. #define SWAPW(a,b)
  62. #define SWAPL(a,b)
  63. #else
  64. #define SWAPW(a,b)    swapw(a,b)
  65. #define SWAPL(a,b)    swapl(a,b)
  66. #endif
  67.  
  68. struct sym {
  69.     char name[8];
  70.     char flags, mode;
  71.     long value;
  72. };
  73. #define SYMSIZE    14
  74. #define SYMVOFFS 10
  75.  
  76. int gflag;
  77. int only8;
  78.  
  79. #define XNAME    "SozobonX"
  80. #define XVALUE    0x87654321
  81. #define XFLAGS    0x42
  82. int havex;
  83.  
  84. main(argc, argv)
  85. char **argv;
  86. {
  87.     int many;
  88.  
  89.     many = argc > 2;
  90.  
  91.     while (--argc) {
  92.         argv++;
  93.         if (*argv[0] == '-')
  94.             doopt(argv[0]);
  95.         else
  96.             doname(argv[0], many);
  97.     }
  98.     exit(0);
  99. }
  100.  
  101. doopt(s)
  102. char *s;
  103. {
  104.     while (*++s)
  105.         switch (*s) {
  106.         case 'g':
  107.         case 'G':
  108.             gflag++;
  109.             break;
  110.         case '8':
  111.             only8++;
  112.             break;
  113.         }
  114. }
  115.  
  116. doname(s, many)
  117. char *s;
  118. {
  119.     FILE *fd, *fopen();
  120.     int i;
  121.  
  122.     fd = fopen(s, RMODE);
  123.     if (fd == NULL) {
  124.         fprintf(stderr, "Can't open %s\n", s);
  125.         return;
  126.     }
  127.  
  128.     if (many)
  129.         printf("\n%s:\n", s);
  130.  
  131.     if (i = dohdr(fd)) {
  132.         if (i == -1)
  133.             doarch(fd);
  134.         else {
  135.             havex = -1;
  136.             while (i)
  137.                 i -= dosym(fd);
  138.         }
  139.     }
  140.         
  141.     fclose(fd);
  142. }
  143.  
  144. dohdr(fd)
  145. FILE *fd;
  146. {
  147.     unsigned short magic = 0;
  148.     int i;
  149.     long len;
  150.  
  151.     fread(&magic, 2, 1, fd);
  152.     SWAPW(&magic, 1);
  153.     if (magic == ARMAG1)
  154.         return -1;
  155.  
  156. #ifdef MINIX
  157.     if (magic != MAGIC0) {
  158.         printf("Bad header\n");
  159.         return 0;
  160.     }
  161.     fread(&magic, 2, 1, fd);
  162.     SWAPW(&magic, 1);
  163. #endif
  164.  
  165.     i = fread(&h, HDRXLEN, 1, fd);
  166.     SWAPL(&h, HDRLONGS);
  167.     if (i != 1 || magic != MAGIC) {
  168.         printf("Bad header\n");
  169.         return 0;
  170.     }
  171.  
  172.     len = h.tsize + h.dsize;
  173.     fseek(fd, len, 1);
  174.     return h.nsyms / SYMSIZE;
  175. }
  176.  
  177. dosym(fd)
  178. FILE *fd;
  179. {
  180.     static struct sym s;
  181.     static int reuse = 0;
  182.     int i, x;
  183.     int n;
  184.  
  185.     if (reuse)
  186.         reuse = 0;
  187.     else {
  188.         i = fread(&s, SYMSIZE, 1, fd);
  189.         if (i != 1)
  190.             return 1;
  191. #ifdef UNIXHOST
  192.         s.value = crossl((char *)&s + SYMVOFFS);
  193. #endif
  194.     }
  195.  
  196.     if (havex == -1) {    /* first symbol */
  197.         if (s.flags == XFLAGS && s.value == XVALUE &&
  198.             strncmp(s.name, XNAME, 8) == 0 && !only8) {
  199.             havex = 1;
  200.             return 1;
  201.         } else
  202.             havex = 0;
  203.     }
  204.  
  205.     if (gflag && not_glob(s.flags))
  206.         return 1;
  207.  
  208.     printf("%8lx ", s.value);
  209.     n = sflags(s.flags) + 1;
  210.     fill8(n);
  211.  
  212.     printf("%.8s", s.name);
  213.  
  214.     if (havex) {
  215.         x = 0;
  216.         for (;;) {
  217.         i = fread(&s, SYMSIZE, 1, fd);
  218.         if (i != 1)
  219.             break;
  220. #ifdef UNIXHOST
  221.         s.value = crossl((char *)&s + SYMVOFFS);
  222. #endif
  223.         if (s.flags != XFLAGS || s.value != XVALUE) {
  224.             reuse = 1;
  225.             break;
  226.         }
  227.         x++;
  228.         printf("%.8s", s.name);
  229.         }
  230.     } else
  231.         x = 0;
  232.  
  233.     putchar('\n');
  234.     return x+1;
  235. }
  236.  
  237. #define MAXTYPE 16
  238.  
  239. fill8(n)
  240. {
  241.     int i;
  242.  
  243.     for (i=n; i<MAXTYPE; i++)
  244.         putchar(' ');
  245. }
  246.  
  247. char *fname[] = {
  248.     "?0?", "bss", "text", "?3?", "data",
  249.     "?5?", "?6?", "?7?"
  250. };
  251.  
  252. not_glob(x)
  253. {
  254.     x &= 0xff;
  255.     if (x & 0x20)
  256.         return 0;
  257.     x &= ~0x20;
  258.     if (x == 0x88)
  259.         return 0;
  260.     return 1;
  261. }
  262.  
  263. sflags(x)
  264. {
  265.     int n = 0;
  266.  
  267.     x &= 0xff;
  268.     if (x & 0x20) {
  269.         printf("glb ");
  270.         n += 4;
  271.     }
  272.     x &= ~0x20;
  273.     if (x == 0x88) {
  274.         printf("ext abs");
  275.         n += 7;
  276.     } else if (x == 0xc0) {
  277.         printf("equ abs");
  278.         n += 7;
  279.     } else if (x == 0xd0) {
  280.         printf("equ reg abs");
  281.         n += 11;
  282.     } else {
  283.         x &= 7;
  284.         printf(fname[x]);
  285.         n += strlen(fname[x]);
  286.     }
  287.     return n;
  288. }
  289.  
  290. doarch(fd)
  291. FILE *fd;
  292. {
  293.     struct ar_hdr a;
  294.     int i;
  295.     long len, ftell();
  296.  
  297. more:
  298.     i = fread(&a, sizeof(a), 1, fd);
  299.     if (i != 1)
  300.         return;
  301.     printf("\n(%.18s):\n", a.ar_name);
  302. #ifndef UNIXHOST
  303.     len = a.ar_size + ftell(fd);
  304. #else
  305.     len = crossl(a.ar_size) + ftell(fd);
  306. #endif
  307.  
  308.     i = dohdr(fd);
  309.     if (i <= 0)
  310.         return;
  311.  
  312.     havex = -1;
  313.     while (i)
  314.         i -= dosym(fd);
  315.     fseek(fd, len, 0);
  316.     goto more;
  317. }
  318.  
  319. #ifdef UNIXHOST
  320. long
  321. crossl(cp)
  322. char *cp;
  323. {
  324.     union {
  325.         long l;
  326.         char c[4];
  327.     } u;
  328.  
  329. #ifdef LITTLE_ENDIAN
  330.     u.c[0] = cp[3];
  331.     u.c[1] = cp[2];
  332.     u.c[2] = cp[1];
  333.     u.c[3] = cp[0];
  334. #else
  335.     u.c[0] = cp[0];
  336.     u.c[1] = cp[1];
  337.     u.c[2] = cp[2];
  338.     u.c[3] = cp[3];
  339. #endif
  340.     return u.l;
  341. }
  342.  
  343. swapw(cp, n)
  344. char *cp;
  345. {
  346. #ifdef LITTLE_ENDIAN
  347.     char t;
  348.  
  349.     while (n--) {
  350.         t = cp[1];
  351.         cp[1] = cp[0];
  352.         cp[0] = t;
  353.         cp += 2;
  354.     }
  355. #endif
  356. }
  357.  
  358. swapl(cp, n)
  359. char *cp;
  360. {
  361. #ifdef LITTLE_ENDIAN
  362.     char t;
  363.  
  364.     while (n--) {
  365.         t = cp[3];
  366.         cp[3] = cp[0];
  367.         cp[0] = t;
  368.  
  369.         t = cp[2];
  370.         cp[2] = cp[1];
  371.         cp[1] = t;
  372.         cp += 4;
  373.     }
  374. #endif
  375. }
  376. #endif
  377.