|
|
1.1 root 1: /*
2: * siz286.c
3: * 1/31/84
4: * Usage: siz286 [ file ... ]
5: *
6: * Reads Intel 80286 OMF from standard input or given files,
7: * writes segment sizes on standard output.
8: * Currently understands only about linkable modules.
9: * Prints all numbers in hex.
10: *
11: * Reference: "The Concrete Representation of 80286
12: * Object Module Formats", Rev. 1.91 (c) Intel 1983.
13: */
14:
15: #include <stdio.h>
16:
17: #define VERSION "1.2" /* version number */
18: #ifdef UDI
19: #define VFLAG "-v" /* version flag must be l.c. for UDI */
20: #else
21: #define VFLAG "-V"
22: #endif
23: #ifdef vax
24: #include <ssdef.h>
25: #include <stsdef.h>
26: #define SRMODE "r"
27: #define OK (STS$M_INHIB_MSG|SS$_NORMAL)
28: #define BAD (STS$M_INHIB_MSG|SS$_ABORT)
29: #else
30: #define SRMODE "rb"
31: #define OK 0
32: #define BAD 1
33: #endif
34:
35: #define LNKMOD 0xA0 /* linkable module */
36: #define MHDLEN 111 /* module header length */
37: #define EXTMSK 0x40 /* SEGDEF external attribute mask */
38:
39: extern unsigned int geti();
40: extern unsigned long getl();
41: long len;
42:
43: main (argc, argv)
44: int argc;
45: register char **argv;
46: {
47: if (strcmp(*++argv, VFLAG) == 0) {
48: ++argv;
49: fprintf (stderr, "siz286: V%s\n", VERSION);
50: }
51: if (*argv == NULL)
52: printsize();
53: else {
54: while (*argv != NULL) {
55: printf("%s:\n", *argv);
56: if (freopen(*argv, SRMODE, stdin) == NULL)
57: fatal ("open for input failed");
58: printsize();
59: argv++;
60: }
61: }
62: exit (OK);
63: }
64:
65: /*
66: * Read an OMF286 object file from stdin and print its size.
67: */
68: printsize()
69: {
70: register unsigned int n;
71: int nsegs = 0; /* number of segments */
72: long size; /* segment size */
73: long segloc; /* location of SEGDEF section */
74: long seglen; /* length of SEGDEF section */
75: long total = 0L; /* sum of segment lengths */
76: if (getb() != LNKMOD) /* Read file type. */
77: fatal ("object is not a linkable file");
78: ignore(MHDLEN); /* Ignore module header. */
79: segloc = getl(); /* Get SEGDEF location. */
80: seglen = getl(); /* Get SEGDEF length. */
81: ignore(segloc - (long)(MHDLEN+8)); /* Seek to start of SEGDEF section. */
82: len = seglen;
83: while (len) { /* Process segment definitions. */
84: ++nsegs;
85: n = geti()&EXTMSK; /* Get attributes, mask to external. */
86: size = geti(); /* Get slimit. */
87: if (n == 0)
88: size++; /* slimit=length-1 for nonexternals. */
89: total += size; /* Bump the sum. */
90: printf("\t0x%04lx\t", size); /* Print the size. */
91: ignore(4); /* Ignore dlength and LDT position. */
92: n = getb(); /* Get name length. */
93: while (n--)
94: putchar (getb()); /* Print the name. */
95: putchar('\n');
96: }
97: if (nsegs > 1) { /* Print the sum. */
98: printf("\t0x%04lx\tTotal (hex)\n", total);
99: printf("\t%6ld\tTotal (decimal)\n", total);
100: }
101: }
102:
103: /*
104: * Read a byte from standard input, update len.
105: */
106: getb()
107: {
108: register int i;
109: if ((i = getchar()) == EOF)
110: fatal ("premature EOF");
111: --len;
112: return (i);
113: }
114:
115: /*
116: * Read a word and return it.
117: */
118: unsigned int
119: geti()
120: {
121: register int i = getb();
122: return (i | (getb() << 8));
123: }
124:
125: /*
126: * Read a long and return it.
127: */
128: unsigned long
129: getl()
130: {
131: register long l = geti();
132: return (l | (((long) geti()) << 16));
133: }
134:
135: /*
136: * Read and ignore n characters.
137: */
138: ignore(n)
139: register int n;
140: {
141: while (n--)
142: getb();
143: }
144:
145: /*
146: * Print error message and exit.
147: */
148: fatal (s)
149: register char *s;
150: {
151: fprintf (stderr, "siz286: %s\n", s);
152: exit(BAD);
153: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.