]>
Commit | Line | Data |
---|---|---|
0e39a8bb RP |
1 | 1) You should be aware that GNU-C, as with any other decent compiler, |
2 | will do things when optimization is turned on that you may not expect. | |
3 | Sometimes intermediate results are not written to variables, if they are only | |
4 | used in one place, and sometimes variables that are not used at all will not be | |
5 | written to the symbol table. Also, parameters to inline functions are often | |
6 | inaccessible. You can see the assembly code equivalent by using KP7 in the | |
7 | debugger, and from this you can tell if in fact a variable should have the | |
8 | value that you expect. You can find out if a variable lives withing a register | |
9 | by doing a 'show symbol/addr'. | |
10 | ||
11 | 2) Overly complex data types, such as: | |
12 | ||
13 | int (*(*(*(*(*(* sarr6)[1])[1])[2])[3])[4])[5]; | |
14 | ||
15 | will not be debugged properly, since the debugging record overflows an internal | |
16 | debugger buffer. gcc-as will convert these to *void as far as the debugger | |
17 | symbol table is concerned, which will avoid any problems, and the assembler | |
18 | will give you a message informing you that this has happened. | |
19 | ||
20 | 3) You must, of course, compile and link with /debug. If you link | |
21 | without debug, you still get traceback table in the executable, but there is no | |
22 | symbol table for variables. | |
23 | ||
24 | 4) Included in the patches to VMS.C are fixes to two bugs that are | |
25 | unrelated to the changes that I have made. One of these made it impossible to | |
26 | debug small programs sometimes, and the other caused the debugger to become | |
27 | confused about which routine it was in, and give this incorrect info in | |
28 | tracebacks. | |
29 | ||
30 | 5) If you are using the GNU-C++ compiler, you should modify the | |
31 | compiler driver file GNU_CC:[000000]GCC.COM (or GXX.COM). If you have a | |
32 | seperate GXX.COM, then you need to change one line in GXX.COM to: | |
33 | $ if f$locate("D",p2) .ne. P2_Length then Debug = " ""-G0""" | |
34 | Notice zero---> ^ | |
35 | If you are using a GCC.COM that does both C and C++, add the following lines to | |
36 | GCC.COM: | |
37 | ||
38 | $! | |
39 | $! Use old style debugging records for VMS | |
40 | $! | |
41 | $ if (Debug.nes."" ).and. Plus then Debug = " ""-G0""" | |
42 | ||
43 | after the variables Plus and Debug are set. The reason for this, is that C++ | |
44 | compiler by default generates debugging records that are more complex, | |
45 | with many new syntactical elements that allow for the new features of the | |
46 | language. The -G0 switch tells the C++ compiler to use the old style debugging | |
47 | records. Until the debugger understands C++ there is not any point to try and | |
48 | use the expanded syntax. | |
49 | ||
50 | 6) When you have nested scopes, i.e.: | |
51 | main(){ | |
52 | int i; | |
53 | {int i; | |
54 | {int i; | |
55 | };};} | |
56 | and you say "EXAM i" the debugger needs to figure out which variable you | |
57 | actually want to reference. I have arranged things to define a block to the | |
58 | debugger when you use brackets to enter a new scope, so in the example above, | |
59 | the variables would be described as: | |
60 | TEST\main\i | |
61 | TEST\main\$0\i | |
62 | TEST\main\$0\$0\i | |
63 | At each level, the block name is a number with a dollar sign prefix, the | |
64 | numbers start with 0 and count upward. When you say EXAM i, the debugger looks | |
65 | at the current PC, and decides which block it is currently in. It works from | |
66 | the innermost level outward until it finds a block that has the variable "i" | |
67 | defined. You can always specify the scope explicitly. | |
68 | ||
69 | 7) With C++, there can be a lot of inline functions, and it would be | |
70 | rather restrictive to force the user to debug the program by converting all of | |
71 | the inline functions to normal functions. What I have done is to essentially | |
72 | "add" (with the debugger) source lines from the include files that contain the | |
73 | inline functions. Thus when you step into an inline function it appears as if | |
74 | you have called the function, and you can examine variables and so forth. | |
75 | There are several *very* important differences, however. First of all, since | |
76 | there is no function call involved, you cannot step over the inline function | |
77 | call - you always step into it. Secondly, since the same source lines are used | |
78 | in many locations, there is a seperate copy of the source for *each* usage. | |
79 | Without this, breakpoints do not work, since we must have a 1-to-1 mapping | |
80 | between source lines and PC. | |
81 | Since you cannot step over inline function calls, it can be a real pain | |
82 | if you are not really interested in what is going on for that function call. | |
83 | What I have done is to use the "-D" switch for the assembler to toggle the | |
84 | following behavior. With the "-D" switch, all inline functions are included in | |
85 | the object file, and you can debug everything. Without the "-D" switch | |
86 | (default case with VMS implementation), inline functions are included *only* if | |
87 | they did not come from system header files (i.e. from GNU_CC_INCLUDE: or | |
88 | GNU_GXX_INCLUDE:). Thus, without the switch the user only debugs his/her own | |
89 | inline functions, and not the system ones. (This is especially useful if you do | |
90 | a lot of stream I/O in C++). This probably will not provide enough granularity | |
91 | for many users, but for now this is still somewhat experimental, and I would | |
92 | like to reflect upon it and get some feedback before I go any further. | |
93 | Possible solutions include an interactive prompting, a logical name, or a new | |
94 | command line option in gcc.c (which is then passed through somehow to the guts | |
95 | of the assembler). | |
96 | The inline functions from header files appear after the source code | |
97 | for the source file. This has the advantage that the source file itself is | |
98 | numbered with the same line numbers that you get with an editor. In addition, | |
99 | the entire header file is not included, since the assembler makes a list of | |
100 | the min and max source lines that are used, and only includes those lines from | |
101 | the first to the last actually used. (It is easy to change it to include the | |
102 | whole file). | |
103 | ||
104 | 8) When you are debugging C++ objects, the object "this" is refered to | |
105 | as "$this". Actually, the compiler writes it as ".this", but the period is | |
106 | not good for the debugger, so I have a routine to convert it to a $. (It | |
107 | actually converts all periods to $, but only for variables, since this was | |
108 | intended to allow us to access "this". | |
109 | ||
110 | 9) If you use the asm("...") keyword for global symbols, you will not | |
111 | be able to see that symbol with the debugger. The reason is that there are two | |
112 | records for the symbol stored in the data structures of the assembler. One | |
113 | contains the info such as psect number and offset, and the other one contains | |
114 | the information having to do with the data type of the variable. In order to | |
115 | debug as symbol, you need to be able to coorelate these records, and the only | |
116 | way to do this is by name. The record with the storage attributes will take | |
117 | the name used in the asm directive, and the record that specifies the data type | |
118 | has the actual variable name, and thus when you use the asm directive to change | |
119 | a variable name, the symbol becomes invisible. | |
120 | ||
121 | 10) Older versions of the compiler ( GNU-C 1.37.92 and earlier) place | |
122 | global constants in the text psect. This is unfortunate, since to the linker | |
123 | this appears to be an entry point. I sent a patch to the compiler to RMS, | |
124 | which will generate a .const section for these variables, and patched the | |
125 | assembler to put these variables into a psect just like that for normal | |
126 | variables, except that they are marked NOWRT. static constants are still | |
127 | placed in the text psect, since there is no need for any external access. |