|
|
1.1 root 1: // File: dbh.C
2: //
3: // Purpose: main file for C++ debugger
4:
5:
6: // ----------------------------------------------------------------------
7: // Includes.
8:
9: #include <coff.h>
10: #include <fcntl.h>
11: #include <stdio.h>
12: #include <stdlib.h>
13: #include <stream.h>
14: #include <string.h>
15: #include "sys.h"
16:
17: // ----------------------------------------------------------------------
18: // Definitions.
19: // Constants.
20: // Macros with argument lists.
21: // Typedefs.
22: // Enums.
23:
24: const int STR_LEN = 256; // general-purpose buffer length
25: const int MAX_ARGS = 10; // limit on number of args, minus switches
26:
27: // command syntax in effect (command line parser selects one of these)
28: const int DBH_NULL = 0; // no valid syntax
29: const int DBH_COFF = 1; // dbh <coff file>
30:
31: // Class for keeping track of the main coff file under investigation.
32: class CoffObj {
33: public: // public fields
34: char * fname; // file name
35: public: // constructors/destructors
36: CoffObj(void): fname(NULL) {}
37: };
38:
39: // Class for command line parser.
40: class DbhCmd {
41: public: // public fields
42: int cmdSyntax;
43: const char * args[MAX_ARGS];
44:
45: public: // constructors/destructors
46: DbhCmd(void): cmdSyntax(DBH_NULL) { args[0] = NULL; }
47: };
48:
49: // ----------------------------------------------------------------------
50: // Functions.
51: // Import Functions.
52: // Export Functions.
53: // Local Functions.
54:
55: void coffLoad(const char *);
56: void cmdLine(int argc, char * argv[], DbhCmd &);
57: void dbhCoff(DbhCmd &);
58: void doCmd(const char *);
59: void doCmdStr(const char *);
60: void fatal(const char *);
61: void usage(void);
62:
63: // ----------------------------------------------------------------------
64: // Global Data.
65: // Import Variables.
66: // Export Variables.
67: // Local Variables.
68:
69: const char * cmd; // alias for argv[0]
70: char errstr[STR_LEN]; // error message buffer
71:
72: // ----------------------------------------------------------------------
73: // Code.
74:
75: // command line forms:
76: // dbh <coff file>
77:
78: int main(int argc, char * argv[]) {
79:
80: DbhCmd dbhCmd;
81:
82: // process command line
83: cmdLine(argc, argv, dbhCmd);
84:
85: // do whatever command syntax dictates
86: switch(dbhCmd.cmdSyntax) {
87: case DBH_COFF: // dbh <coff file>
88: dbhCoff(dbhCmd);
89: break;
90: }
91: }
92:
93: // Print a string to stderr and abort the debug session.
94: void
95: fatal(const char * msg) {
96: cerr << cmd << " error: " << msg << endl;
97: exit(1);
98: }
99:
100: // Given raw command arguments, process switches and parse
101: // the line to determine the type of db session. Return
102: // parse info in "dbhCmd".
103: void
104: cmdLine(int argc, char * argv[], DbhCmd & dbhCmd) {
105:
106: // copy command name to "cmd", mainly for error messages
107: cmd = argv[0];
108:
109: // check number of arguments
110: if (argc != 2) {
111: usage();
112: }
113:
114: // get command syntax and set args for subcommand
115: dbhCmd.cmdSyntax = DBH_COFF;
116: dbhCmd.args[0] = argv[1];
117: }
118:
119: // Display usage message and abort the debug session.
120: void
121: usage(void) {
122: cerr << "Usage:\t" << cmd << " <coff program>" << endl;
123: exit(1);
124: }
125:
126: // Run a dbh session for command syntax
127: // dbh <coff file>
128: void
129: dbhCoff(DbhCmd & dbhCmd) {
130: // get needed info from coff file
131: coffLoad(dbhCmd.args[0]);
132:
133: // enter command loop
134: doCmdStr(":x");
135: }
136:
137: // Load info from COFF binary.
138: void
139: coffLoad(const char * fname) {
140: FILEHDR coffh;
141: int coff_fd;
142:
143: if ((coff_fd = open(fname, O_RDONLY)) == -1) {
144: sprintf(errstr, "Can't open object file %s", fname);
145: fatal(errstr);
146: }
147:
148: if (read(coff_fd, &coffh, sizeof(coffh)) != sizeof(coffh)) {
149: sprintf(errstr, "Can't read object file %s", fname);
150: fatal(errstr);
151: }
152:
153: if (coffh.f_magic != C_386_MAGIC) {
154: sprintf(errstr, "Object file %s is not COFF", fname);
155: fatal(errstr);
156: }
157:
158: getCoffSyms(coff_fd);
159:
160: getCoffSegs(coff_fd);
161:
162: close(coff_fd);
163: }
164:
165: // Perform a db command string.
166: // String consists of zero or more commands separated by newlines.
167: void
168: doCmdStr(const char * cmdStr) {
169: char cmd1[STR_LEN];
170:
171: // copy each line, minus trailing newline, into "cmd1"
172: // and invoke single command processor
173: for (const char * cp = cmdStr; cp < cmdStr + strlen(cmdStr);) {
174: const char * delim = strchr(cp, '\n');
175: if (delim) {
176: int copyLen = STR_LEN;
177: if (delim - cp < copyLen)
178: copyLen = delim - cp;
179: strncpy(cmd1, cp, copyLen);
180: doCmd(cmd1);
181: cp = delim + 1;
182: } else {
183: strncpy(cmd1, cp, STR_LEN);
184: doCmd(cmd1);
185: break;
186: }
187: }
188: }
189:
190: // Do a single db command.
191: void
192: doCmd(const char * cmdStr) {
193: cout << cmdStr << endl;
194: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.