Document revision date: 19 July 1999 | |
Previous | Contents | Index |
On Alpha, to request an interrupt, perform the following steps:
^P |
>>> DEP SIRR E |
>>> CONT |
The process should enter XDELTA as soon as IPL drops to 14.
The following message is displayed:
Brk 0 at address address! instruction |
At this point, the exception frame is on the stack. The saved PC/PS in
the exception frame tells you where you were in the program when you
requested the interrupt.
1.8 Accessing the Initial Breakpoint
On Alpha and VAX, when debugging a program, you can set a breakpoint in the code so that XDELTA gains control of program execution.
To set a breakpoint, place a call to the system routine INI$BRK in the source code.
The INI$BRK routine contains two instructions: BPT and a second instruction that is specific to the hardware system. On systems that are not booted with XDELTA, the BPT instruction in INI$BRK is replaced with a NOP instruction.
You can use the INI$BRK routine as a debugging tool, placing calls to this routine in any part of the source code you want to debug.
On VAX, the second instruction in INI$BRK is RSB. After the break is taken, the return address (the address in the program to which control returns when you proceed from the breakpoint) is on the top of the stack.
The following command calls the INI$BRK system routine to reach the breakpoint:
JSB G^INI$BRK |
On Alpha, the second instruction in INI$BRK is JSR R31,(R26). After the break is taken, the return address (the address in the program to which control returns when you proceed from the breakpoint) is in R26.
The following C routine calls the INI$BRK system routine to reach the breakpoint:
extern void ini$brk(void); main() { ini$brk(); } |
On VAX, when XDELTA reaches one of its breakpoints, it displays the following message:
1 BRK AT nnnnnnnn address/instruction operands |
On Alpha, when XDELTA reaches one of its breakpoints, it displays the following message:
BRK 1 AT nnnnnnnn address!instruction operands |
On Alpha and VAX multiprocessor computers, the XDELTA breakpoint is taken on the processor upon which the XDELTA software interrupt was requested, which is generally the primary processor. At this point, XDELTA is waiting for input. If you want to proceed with program execution, enter the ;P command. If you want to do step-by-step program execution, enter the S command. If you know where you have set breakpoints, examine them using the ;B command. You can also set additional breakpoints or modify existing ones.
If you entered the ;P command to proceed with program execution and the system halts with a fatal bugcheck, the system prints the bugcheck information on the console terminal. Bugcheck information consists of the following:
The contents of the program counter (PC) and the stack indicate where
the failure was detected. Then, if the system parameter BUGREBOOT was
set to 0, XDELTA issues a prompt. You can examine the system's state
further by entering XDELTA commands.
1.10 Exiting from XDELTA
On Alpha and VAX, XDELTA remains in memory with the operating system until you reboot without it.
This chapter describes how to form the symbolic expressions used as
arguments to many DELTA and XDELTA commands.
2.1 Symbols Supplied by DELTA and XDELTA
DELTA and XDELTA define symbols that are useful in forming expressions and referring to registers. These symbols are described in Table 2-1.
Symbol | Description |
---|---|
. | The address of the current location. The value of this symbol is set by the Open Location and Display Contents (/), Open Location and Display Instruction (!), and the Open Location and Display Indirect (TAB) commands. |
Q | The last value displayed. The value of Q is set by every command that causes DELTA or XDELTA to display the contents of memory or the value of an expression. |
+Xn |
Base register
n, where
n can range from 0 to F (hexadecimal). These registers are
used for storing values, most often the base addresses of data
structures in memory.
For XDELTA only, XE and XF contain the addresses of two command strings that XDELTA stores in memory. See the Execute Command String (;E) command for more information. For XDELTA only, registers X4 and X5 contain specific addresses. X4 contains the address of the location that contains the PCB address of the current process on the current processor. The address that X4 contains is that of the per-CPU database for the current processor. X5 contains SCH$GL_PCBVEC, the symbolic address of the start of the PCB vector, and the list of PCB slots. |
++Xn |
Base register
n, where
n can range from 0 to 15 (decimal). These registers are used
for storing values, most often the base addresses of data structures in
memory.
For XDELTA only, X14 and X15 contain the addresses of two command strings that XDELTA stores in memory. See the Execute Command String (;E) command for more information. For XDELTA only, registers X4 and X5 contain specific addresses. X4 contains the address of the location that contains the PCB address of the current process on the current processor. The address that X4 contains is that of the per-CPU database for the current processor. X5 contains SCH$GL_PCBVEC, the symbolic address of the start of the PCB vector, and the list of PCB slots. |
+Rn | General register n, where n can range from 0 to F (hexadecimal). RF+4 is the processor status longword (PSL), RE is the stack pointer, and RF is the program counter (PC). |
++Rn | General register n, where n can range from 0 to 31 (decimal). PS is the processor status and PC is the program counter. |
+Pn | The internal processor register at processor address n, where n can range from 0 to 3F (hexadecimal). See the VAX Architecture Reference Manual for a description of these processor registers. |
++P(IPR name) | The internal processor register at processor address IPR name. See the Alpha Architecture Reference Manual for the names and descriptions of these processor registers. |
++FPCR | The floating-point control register. |
+G | ^X80000000, the prefix for system space addresses. G2E, for example, is equivalent to ^X8000002E. |
++G | ^XFFFFFFFF80000000, the prefix for system space addresses. |
H | ^X7FFE0000, the prefix for addresses in the control region (P1 space). H2E, for example, is equivalent to ^X7FFE002E. |
++PID:Rn | The internal PID of another process that you want to look at. Rn represents the register that you want to read or write. Rn applies to R0-R29, PC, and PS. An address or address range can be specified instead of Rn for the / command, as described in Chapter 4. |
On OpenVMS Alpha, floating-point registers can be accessed from DELTA and from XDELTA but only if floating-point arithmetic is enabled in the current process.
DELTA runs in the context of a process. Access to floating-point registers is enabled as soon as the first floating-point instruction in the code being examined is executed. Access is disabled as soon as that image completes execution.
When the system enters XDELTA, it may not be obvious which process is
the current process. If the current process happens to have floating
point enabled (because a floating-point instruction has executed and
the image containing the floating-point instruction is still
executing), then you can access the floating-point registers.
Otherwise, you cannot. XDELTA checks the FEN (floating-point enable)
IPR (internal processor register) to see whether it needs to provide
access to floating-point registers.
2.3 Forming Numeric Expressions
Expressions are combinations of numbers, symbols that have numeric values, and arithmetic operators.
On VAX, both DELTA and XDELTA store and display all numbers in hexadecimal. They also interpret all numbers as hexadecimal.
On Alpha, all numbers except integer and floating-point registers are stored and displayed in hexadecimal. These registers are stored and displayed in decimal.
On Alpha and VAX, expressions are formed using regular (infix) notation. Both DELTA and XDELTA ignore operators that trail the expression. The following is a typical expression (in hexadecimal):
G4A32+24 |
DELTA and XDELTA recognize five binary arithmetic operators, one of which also acts as a unary operator. They are listed in Table 2-2.
Operator | Action |
---|---|
+ or SPACE | Addition |
- | Subtraction when used as a binary operator, or negation when used as a unary operator |
* | Multiplication |
% | Division |
@ | Arithmetic shift |
The following example shows the arguments required by the arithmetic-shift operator:
n@j |
In this example, n is the number to be shifted, and j is the number of bits to shift it. If j is positive, n is shifted to the left; if j is negative, n is shifted to the right. Argument j must be less than 2016 and greater than -2016. Bits shifted beyond the limit of the longword are lost; therefore, the result must fit into a longword.
When you use DELTA or XDELTA, there are no prompts, few symbols, and one error message. You move through program code by referring directly to address locations. This chapter provides directions for the following actions:
For examples of DELTA debugging sessions on VAX and Alpha, refer
respectively to Appendix A and Appendix B.
3.1 Referencing Addresses
When using DELTA or XDELTA to debug programs, you move through the code by referring to addresses. To help you identify address locations within your program, use a list file and a map file. The list file (.LIS) lists each instruction and its offset value from the base address of the program section. The full map file (.MAP) lists the base addresses for each section of your program. To determine the base address of a device driver program, refer to the OpenVMS VAX Device Support Manual.
Once you have the base addresses of the program sections, locate the instruction in the list file where you want to start the debugging work. Add the offset from the list program to the base address from the map file. Remember that all calculations of address locations are done in hexadecimal. You can use DELTA/XDELTA to do the calculations for you with the = command.
To make address referencing easier, you can use offsets to a base address. Then you do not have to calculate all address locations. First, place the base address into a base register. Then move to a location using the offset to the base address stored in the register.
Whenever DELTA/XDELTA displays an address, it will display a relative
address if the offset falls within the permitted range (see the ;X
command in Chapter 4).
3.1.1 Referencing Addresses (VAX Only)
On VAX, to reference addresses during a DELTA debug session, use the following example as a guide. The example uses a simple VAX MACRO program (EXAMPLE.MAR). You can also use the same commands in an XDELTA debugging session.
0000 1 .title example 0000 2 0000 3 .entry start ^M<r3,r4> 0002 4 clrl r3 0004 5 movl #5,r4 0007 6 10$: addl r4,r3 000A 7 sobgtr r4,10$ 000D 8 ret 000E 9 000E 10 .end start |
The following procedure generates information to assist you with address referencing:
$ MACRO/LIST EXAMPLE |
$ LINK/MAP EXAMPLE |
+--------------------------+ ! Program Section Synopsis ! +--------------------------+ Psect Name Module Name Base End Length ---------- ----------- ---- --- ------ . BLANK . 00000200 0000020D 0000000E ( 14.) EXAMPLE 00000200 0000020D 0000000E ( 14.) |
$ DEFINE LIB$DEBUG SYS$LIBRARY:DELTA $ RUN/DEBUG EXAMPLE |
200,0;X [Return] |
204;B [Return] |
X0+4;B [Return] |
Reverse this technique to find an instruction displayed by DELTA/XDELTA in the .LIS file, as follows:
20A! sobgtr r4,00000207 |
10$: addl r4,r3 |
On Alpha, to reference addresses during a DELTA debug session, use the following example as a guide. The example uses a simple C program (HELLO.C). You can also use the same commands in an XDELTA debug session.
#include <stdio.h> main() { printf("Hello world\n"); } |
The following procedure generates information to assist you with the address referencing:
$ cc/list/machine_code hello |
.PSECT $CODE, OCTA, PIC, CON, REL, LCL, SHR,- EXE, NORD, NOWRT 0000 main:: ; 000335 0000 LDA SP, -32(SP) ; SP, -32(SP) 0004 LDA R16, 48(R27) ; R16, 48(R27) ; 000337 0008 STQ R27, (SP) ; R27, (SP) ; 000335 000C MOV 1, R25 ; 1, R25 ; 000337 0010 STQ R26, 8(SP) ; R26, 8(SP) ; 000335 0014 STQ FP, 16(SP) ; FP, 16(SP) 0018 LDQ R26, 32(R27) ; R26, 32(R27) ; 000337 001C MOV SP, FP ; SP, FP ; 000335 0020 LDQ R27, 40(R27) ; R27, 40(R27) ; 000337 0024 JSR R26, DECC$GPRINTF ; R26, R26 0028 MOV FP, SP ; FP, SP ; 000338 002C LDQ R28, 8(FP) ; R28, 8(FP) 0030 LDQ FP, 16(FP) ; FP, 16(FP) 0034 MOV 1, R0 ; 1, R0 0038 LDA SP, 32(SP) ; SP, 32(SP) 003C RET R28 ; R28 |
335 main() 336 { 337 printf("Hello world\n"); 338 } |
$ LINK/MAP/FULL HELLO |
+--------------------------+ ! Program Section Synopsis ! +--------------------------+ Psect Name Module Name Base End Length ---------- ----------- ---- --- ------ $LINKAGE 00010000 0001007F 00000080 ( 128.) HELLO 00010000 0001007F 00000080 ( 128.) $CODE 00020000 000200BB 000000BC ( 188.) HELLO 00020000 000200BB 000000BC ( 188.) |
printf("Hello world\n"); |
$ DEFINE LIB$DEBUG SYS$LIBRARY:DELTA $ RUN/DEBUG HELLO |
20000,0;X |
20004;B |
Previous | Next | Contents | Index |
privacy and legal statement | ||
4540PRO_001.HTML |