HP OpenVMS Systems Documentation

Content starts here

HP OpenVMS Delta/XDelta Debugger Manual


Previous Contents Index


Appendix B
Sample DELTA Debug Session on Alpha

This appendix gives an example of using DELTA to debug a program on OpenVMS Alpha. The C program named LOG uses the system service SYS$GETJPIW to obtain the PID, process name, and login time of each process. Although this is an example of using DELTA, most of the commands in the example could be used in an XDELTA debugging session.

To run this program without error, you need WORLD privilege.

The listing file for LOG is shown in two parts. The C source code part is shown in Example B-1. The machine code part is shown in Example B-2.

Example B-1 Listing File for LOG: C Source Code


1    #include <descrip.h>
434  #include <jpidef.h>
581  #include <ssdef.h>
1233 #include <starlet.h>
3784 #include <stdio.h>
4117 #include <stdlib.h>
4345
4346 void print_line(unsigned long int pid, char *process_name,
4347   unsigned long int *time_buffer);
4348
4349 typedef struct {
4350   unsigned short int il3_buffer_len;
4351   unsigned short int il3_item_code;
4352   void *il3_buffer_ptr;
4353   unsigned short int *il3_return_len_ptr;
4354         } item_list_3;
4355
4356 #define NUL '\0'
4357
4358 main()
4359   {
4360  static char name_buf[16];
4361  static unsigned long int pid, time_buf[2];
4362  static unsigned short int name_len;
4363
4364  unsigned short int pidadr[2] = {-1, -1};
4365  unsigned long int ss_sts;
4366  item_list_3 jpi_itmlst[] = {
4367          /* Get's login time */
4368          {sizeof(time_buf),
4369           JPI$_LOGINTIM,
4370           (void *) time_buf,
4371           NULL},
4372
4373          /* Get's process name */
4374          {sizeof(name_buf) - 1,
4375           JPI$_PRCNAM,
4376           (void *) name_buf,
4377           &name_len},
4378
4379          /* Get's process ID (PID) */
4380          {sizeof(pid),
4381           JPI$_PID,
4382           (void *) &pid,
4383           NULL},
4384
4385          /* End of list */
4386          {0,
4387           0,
4388           NULL,
4389           NULL}
4390         };
4391
4392 /*
4393 While there's more GETJPI information to process and a catastrophic
4394 error has not occurred then
4395     If GETJPI was successful then
4396         NUL terminate the process name string and
4397  print the information returned by GETJPI
4398 */
4399
4400  while(
4401           (ss_sts = sys$getjpiw(0, &pidadr, 0, &jpi_itmlst, 0, 0, 0)) != SS$_NOMOREPROC &&
4402    ss_sts != SS$_BADPARAM &&
4403    ss_sts != SS$_ACCVIO)
4404    {
4405   if (ss_sts == SS$_NORMAL)
4406     {
4407    *(name_buf + name_len) = NUL;
4408    print_line(pid, name_buf, time_buf);
4409     }
4410    }
4411  exit(EXIT_SUCCESS);
4412   }
4413
4414 void print_line(unsigned long int pid, char *process_name,
4415   unsigned long int *time_buffer)
4416   {
4417  static char ascii_time[12];
4418
4419  struct dsc$descriptor_s time_dsc = {
4420           sizeof(ascii_time) - 1,
4421                  DSC$K_DTYPE_T,
4422                  DSC$K_CLASS_S,
4423                  ascii_time
4424               };
4425  unsigned short int time_len;
4426
4427 /*
4428 Convert the logged in time to ASCII and NUL terminate it
4429 */
4430  sys$asctim(&time_len, &time_dsc, time_buffer, 1);
4431  *(ascii_time + time_len) = NUL;
4432
4433 /*
4434 Output the PID, process name and logged in time
4435 */
4436  printf("\n\tPID= %08.8X\t\tPRCNAM= %s\tLOGINTIM= %s", pid,
4437    process_name, ascii_time);
4438
4439  return;
4440   }
4441 __main(void *p1, void *p2, void *p3, void *p4, void *p5, void *p6)
4442 {
4443     void decc$exit(int);
4444     void decc$main(void *, void *, void *, void *, void *, void *, int *, void **, void **);
4445     int status;
4446     int argc;
4447     void *argv;
4448     void *envp;
4449
4450     decc$main(p1, p2, p3, p4, p5, p6, &argc, &argv, &envp);
4451
4452     status = main
4453                  (
4454
4455
4456
4457                  );
4458
4459     decc$exit(status);
4460 }

Example B-2 Listing File for LOG: Machine Code


                        .PSECT  $CODE, OCTA, PIC, CON, REL, LCL, SHR,-
                                EXE, NORD, NOWRT
0000    print_line::                                            ; 004414
0000            LDA     SP, -80(SP)             ; SP, -80(SP)
0004            MOV     1, R19                  ; 1, R19        ; 004430
0008            STQ     R27, (SP)               ; R27, (SP)     ; 004414
000C            MOV     4, R25                  ; 4, R25        ; 004430
0010            STQ     R26, 32(SP)             ; R26, 32(SP)   ; 004414
0014            STQ     R2, 40(SP)              ; R2, 40(SP)
0018            STQ     R3, 48(SP)              ; R3, 48(SP)
001C            STQ     R4, 56(SP)              ; R4, 56(SP)
0020            STQ     FP, 64(SP)              ; FP, 64(SP)
0024            MOV     SP, FP                  ; SP, FP
0028            MOV     R27, R2                 ; R27, R2
002C            STL     R17, process_name       ; R17, 16(FP)
0030            LDQ     R0, 40(R2)              ; R0, 40(R2)    ; 004419
0034            MOV     R16, pid                ; R16, R3       ; 004414
0038            LDQ     R26, 48(R2)             ; R26, 48(R2)   ; 004430
003C            LDA     R16, time_len           ; R16, 8(FP)
0040            LDQ     R4, 32(R2)              ; R4, 32(R2)    ; 004423
0044            LDA     R17, time_dsc           ; R17, 24(FP)   ; 004430
0048            STQ     R0, time_dsc            ; R0, 24(FP)    ; 004419
004C            LDQ     R27, 56(R2)             ; R27, 56(R2)   ; 004430
0050            STL     R4, 28(FP)              ; R4, 28(FP)    ; 004419
0054            JSR     R26, SYS$ASCTIM         ; R26, R26      ; 004430
0058            LDL     R0, time_len            ; R0, 8(FP)     ; 004431
005C            MOV     pid, R17                ; R3, R17       ; 004436
0060            LDQ     R27, 88(R2)             ; R27, 88(R2)
0064            MOV     R4, R19                 ; R4, R19
0068            LDQ     R26, 80(R2)             ; R26, 80(R2)
006C            MOV     4, R25                  ; 4, R25
0070            ZEXTW   R0, R0                  ; R0, R0        ; 004431
0074            ADDQ    R4, R0, R0              ; R4, R0, R0
0078            LDQ_U   R16, (R0)               ; R16, (R0)
007C            MSKBL   R16, R0, R16            ; R16, R0, R16
0080            STQ_U   R16, (R0)               ; R16, (R0)
0084            LDQ     R16, 64(R2)             ; R16, 64(R2)   ; 004436
0088            LDL     R18, process_name       ; R18, 16(FP)
008C            JSR     R26, DECC$GPRINTF       ; R26, R26
0090            MOV     FP, SP                  ; FP, SP        ; 004439
0094            LDQ     R28, 32(FP)             ; R28, 32(FP)
0098            LDQ     R2, 40(FP)              ; R2, 40(FP)
009C            LDQ     R3, 48(FP)              ; R3, 48(FP)
00A0            LDQ     R4, 56(FP)              ; R4, 56(FP)
00A4            LDQ     FP, 64(FP)              ; FP, 64(FP)
00A8            LDA     SP, 80(SP)              ; SP, 80(SP)
00AC            RET     R28                     ; R28

Routine Size: 176 bytes,    Routine Base: $CODE + 0000
00B0     main::                                                 ; 004358
00B0            LDA     SP, -144(SP)            ; SP, -144(SP)
00B4            MOV     48, R17                 ; 48, R17       ; 004366
00B8            STQ     R27, (SP)               ; R27, (SP)     ; 004358
00BC            STQ     R26, 64(SP)             ; R26, 64(SP)
00C0            STQ     R2, 72(SP)              ; R2, 72(SP)
00C4            STQ     R3, 80(SP)              ; R3, 80(SP)
00C8            STQ     R4, 88(SP)              ; R4, 88(SP)
00CC            STQ     R5, 96(SP)              ; R5, 96(SP)
00D0            STQ     R6, 104(SP)             ; R6, 104(SP)
00D4            STQ     R7, 112(SP)             ; R7, 112(SP)
00D8            STQ     R8, 120(SP)             ; R8, 120(SP)
00DC            STQ     FP, 128(SP)             ; FP, 128(SP)
00E0            MOV     SP, FP                  ; SP, FP
00E4            MOV     R27, R2                 ; R27, R2
00E8            LDA     SP, -16(SP)             ; SP, -16(SP)
00EC            LDQ     R26, 40(R2)             ; R26, 40(R2)   ; 004366
00F0            LDQ     R18, 64(R2)             ; R18, 64(R2)
00F4            LDA     R16, jpi_itmlst         ; R16, 16(FP)
00F8            JSR     R26, OTS$MOVE           ; R26, R26
00FC            LDA     R6, jpi_itmlst          ; R6, 16(FP)    ; 004401
0100            LDQ     R3, -64(R2)             ; R3, -64(R2)   ; 004370
0104            LDA     R7, pidadr              ; R7, 8(FP)     ; 004401
0108            LDQ     R0, 32(R2)              ; R0, 32(R2)    ; 004364
010C            MOV     2472, R8                ; 2472, R8      ; 004401
0110            STL     R0, pidadr              ; R0, 8(FP)     ; 004364
0114            LDA     R3, time_buf            ; R3, 16(R3)    ; 004370
0118            MOV     R3, R5                  ; R3, R5
011C            STL     R5, 20(FP)              ; R5, 20(FP)    ; 004366
0120            LDA     R4, 8(R3)               ; R4, 8(R3)     ; 004376
0124            STL     R4, 32(FP)              ; R4, 32(FP)    ; 004366
0128            LDA     R17, 24(R3)             ; R17, 24(R3)
012C            STL     R17, 36(FP)             ; R17, 36(FP)
0130            LDA     R19, 28(R3)             ; R19, 28(R3)
0134            STL     R19, 44(FP)             ; R19, 44(FP)
0138    L$6:                                                    ; 004400
0138            LDQ     R26, 48(R2)             ; R26, 48(R2)   ; 004401
013C            CLR     R16                     ; R16
0140            LDQ     R27, 56(R2)             ; R27, 56(R2)
0144            MOV     R7,  R17                ; R7, R17
0148            STQ     R31, (SP)               ; R31, (SP)
014C            CLR     R18                     ; R18
0150            MOV     R6, R19                 ; R6, R19
0154            CLR     R20                     ; R20
0158            CLR     R21                     ; R21
015C            MOV     7, R25                  ; 7, R25
0160            JSR     R26, SYS$GETJPIW        ; R26, R26
0164            CMPEQ   ss_sts, 20, R16         ; R0, 20, R16   ; 004402
0168            CMPEQ   ss_sts, R8, R17         ; R0, R8, R17   ; 004401
016C            CMPEQ   ss_sts, 12, R18         ; R0, 12, R18   ; 004403
0170            BIS     R17, R16, R17           ; R17, R16, R17 ; 004401
0174            BIS     R17, R18, R18           ; R17, R18, R18
0178            BNE     R18, L$10               ; R18, L$10     ; 004400
017C            CMPEQ   ss_sts, 1, R0           ; R0, 1, R0     ; 004405
0180            BEQ     R0, L$6                 ; R0, L$6
0184            MOV     R4, R17                 ; R4, R17       ; 004408
0188            LDQ_U   R19, 24(R3)             ; R19, 24(R3)   ; 004407
018C            MOV     R5, R18                 ; R5, R18       ; 004408
0190            LDA     R27, -96(R2)            ; R27, -96(R2)
0194            EXTWL   R19, R3, R19            ; R19, R3, R19  ; 004407
0198            ADDQ    R4, R19, R19            ; R4, R19, R19
019C            LDQ_U   R22, (R19)              ; R22, (R19)
01A0            MSKBL   R22, R19, R22           ; R22, R19, R22
01A4            STQ_U   R22, (R19)              ; R22, (R19)
01A8            LDL     R16, 28(R3)             ; R16, 28(R3)   ; 004408
01AC            BSR     R26, print_line         ; R26, print_line
01B0            BR      L$6                     ; L$6           ; 004405
01B4            NOP                             ;
01B8    L$10:                                                   ; 004400
01B8            LDQ     R26, 80(R2)             ; R26, 80(R2)   ; 004411
01BC            CLR     R16                     ; R16
01C0            LDQ     R27, 88(R2)             ; R27, 88(R2)
01C4            MOV     1, R25                  ; 1, R25
01C8            JSR     R26, DECC$EXIT          ; R26, R26
01CC            MOV     FP, SP                  ; FP, SP        ; 004412
01D0            LDQ     R28, 64(FP)             ; R28, 64(FP)
01D4            MOV     1, R0                   ; 1, R0
01D8            LDQ     R2, 72(FP)              ; R2, 72(FP)
01DC            LDQ     R3, 80(FP)              ; R3, 80(FP)
01E0            LDQ     R4, 88(FP)              ; R4, 88(FP)
01E4            LDQ     R5, 96(FP)              ; R5, 96(FP)
01E8            LDQ     R6, 104(FP)             ; R6, 104(FP)
01EC            LDQ     R7, 112(FP)             ; R7, 112(FP)
01F0            LDQ     R8, 120(FP)             ; R8, 120(FP)
01F4            LDQ     FP, 128(FP)             ; FP, 128(FP)
01F8            LDA     SP, 144(SP)             ; SP, 144(SP)
01FC            RET     R28                     ; R28

Routine Size: 336 bytes,    Routine Base: $CODE + 00B0
0200    __main::                                                ; 004441
0200            LDA     SP, -48(SP)             ; SP, -48(SP)
0204            MOV     9, R25                  ; 9, R25        ; 004450
0208            STQ     R27, (SP)               ; R27, (SP)     ; 004441
020C            STQ     R26, 24(SP)             ; R26, 24(SP)
0210            STQ     R2, 32(SP)              ; R2, 32(SP)
0214            STQ     FP, 40(SP)              ; FP, 40(SP)
0218            MOV     SP, FP                  ; SP, FP
021C            LDA     SP, -32(SP)             ; SP, -32(SP)
0220            MOV     R27, R2                 ; R27, R2
0224            LDA     R0, argc                ; R0, 16(FP) ; 004450
0228            LDQ     R26, 48(R2)             ; R26, 48(R2)
022C            LDA     R1, argv                ; R1, 12(FP)
0230            STQ     R0, (SP)                ; R0, (SP)
0234            LDA     R0, envp                ; R0, 8(FP)
0238            STQ     R1, 8(SP)               ; R1, 8(SP)
023C            LDQ     R27, 56(R2)             ; R27, 56(R2)
0240            STQ     R0, 16(SP)              ; R0, 16(SP)
0244            JSR     R26, DECC$MAIN          ; R26, R26
0248            LDA     R27, -96(R2)            ; R27, -96(R2) ; 004452
024C            BSR     R26, main               ; R26, main
0250            LDQ     R27, 40(R2)             ; R27, 40(R2)   ; 004459
0254            MOV     status, R16             ; R0, R16
0258            MOV     1, R25                  ; 1, R25
025C            LDQ     R26, 32(R2)             ; R26, 32(R2)
0260            JSR     R26, DECC$EXIT          ; R26, R26
0264            MOV     FP, SP                  ; FP, SP        ; 004460
0268            LDQ     R28, 24(FP)             ; R28, 24(FP)
026C            LDQ     R2, 32(FP)              ; R2, 32(FP)
0270            LDQ     FP, 40(FP)              ; FP, 40(FP)
0274            LDA     SP, 48(SP)              ; SP, 48(SP)
0278            RET     R28                     ; R28

Routine Size: 124 bytes,    Routine Base: $CODE + 0200

The .MAP file for the sample program is shown in Example B-3. Only the Program Section Synopsis with the psect, module, base address, end address, and length are listed.

Example B-3 .MAP File for the Sample Program

                                            +--------------------------+
                                            ! Program Section Synopsis !
                                            +--------------------------+

Psect Name      Module Name       Base     End           Length
----------      -----------       ----     ---           ------

$LINKAGE                        00010000 000100FF 00000100 (        256.)
                LOG             00010000 000100FF 00000100 (        256.)

$LITERAL                        00010100 00010158 00000059 (         89.)
                LOG             00010100 00010158 00000059 (         89.)

$READONLY                       00010160 00010160 00000000 (          0.)
                LOG             00010160 00010160 00000000 (          0.)

$INIT                           00020000 00020000 00000000 (          0.)
                LOG             00020000 00020000 00000000 (          0.)

$UNINIT                         00020000 0002002F 00000030 (         48.)
                LOG             00020000 0002002F 00000030 (         48.)

$CODE                           00030000 0003027B 0000027C (        636.)
                LOG             00030000 0003027B 0000027C (        636.)

The DELTA debug session is shown in Example B-4.

Example B-4 DELTA Debugging Session of the Sample Program


$ DEFINE LIB$DEBUG SYS$LIBRARY:DELTA  (1)
$ RUN/DEBUG LOG  (2)
Alpha/VMS DELTA Version 1.5   (3)

Brk 0 at 00030200

00030200!    LDA         SP,#XFFD0(SP)  30000,1;X
X1 164! CMPEQ           R0,#X14,R16  .;B (4)


X1 1AC! BSR             R26,#XFFFF94  .;B  (5)

;P

Brk 1 at 00030164    (6)

X1+00000164!    CMPEQ           R0,#X14,R16  R0/ 00000001 ;P

Brk 2 at 000301AC

X1+000001AC!    BSR             R26,#XFFFF94  O

        PID= 00000021           PRCNAM= SWAPPER LOGINTIM= 00:00:00.00  (7)
X1+000001B0!    BR              R31,#XFFFFE1  ;P

Brk 1 at 00030164

X1+00000164!    CMPEQ           R0,#X14,R16  R0/ 00000001 ;P

Brk 2 at 000301AC

X1+000001AC!    BSR             R26,#XFFFF94  O (8)
        PID= 00000024           PRCNAM= ERRFMT  LOGINTIM= 16:24:01.03
X1+000001B0!    BR              R31,#XFFFFE1  ;P

Brk 1 at 00030164

X1+00000164!    CMPEQ           R0,#X14,R16

;B
 1 00030164
 2 000301AC

0,1;B

;B
 2 000301AC

;P

Brk 2 at 000301AC   (9)

X1+000001AC!    BSR             R26,#XFFFF94  O
        PID= 00000025           PRCNAM= OPCOM   LOGINTIM= 16:24:02.56
X1+000001B0!    BR              R31,#XFFFFE1  ;P

Brk 2 at 000301AC    (10)

X1+000001AC!    BSR             R26,#XFFFF94  O
      PID= 00000026          PRCNAM= AUDIT_SERVER    LOGINTIM=16:24:03.66
X1+000001B0!    BR              R31,#XFFFFE1  ;P

Brk 2 at 000301AC  (11)

X1+000001AC!    BSR         R26,#XFFFF94 X1 84!  LDQ   R16,#X0040(R2)
[Linefeed] (12)


X1+00000088!    LDL             R18,#X0010(FP)  [Linefeed]


X1+0000008C!    JSR             R26,(R26)  .;B (13)

;B
 1 0003008C
 2 000301AC

;P (14)

Brk 1 at 0003008C    (15)

X1+0000008C!    JSR             R26,(R26)  O
     PID= 00000027           PRCNAM= JOB_CONTROL     LOGINTIM= 16:24:06.83
X1+00000090!    BIS             R31,FP,SP  ;P

Brk 2 at 000301AC

X1+000001AC!    BSR             R26,#XFFFF94  ;P
Brk 1 at 0003008C (16)

X1+0000008C!    JSR             R26,(R26)  O
     PID= 00000028           PRCNAM= NETACP  LOGINTIM= 16:24:22.86
X1+00000090!    BIS             R31,FP,SP  ;P

Brk 2 at 000301AC

X1+000001AC!    BSR             R26,#XFFFF94

;B
 1 0003008C
 2 000301AC

0,2;B

0,1;B

;B

;P

        PID= 00000029        PRCNAM= EVL     LOGINTIM= 16:24:26.67
        PID= 0000002A        PRCNAM= REMACP  LOGINTIM= 16:24:38.21
        PID= 0000002B        PRCNAM= LATACP  LOGINTIM= 16:24:43.18
        PID= 0000004C        PRCNAM= GODDARD LOGINTIM= 07:40:49.34
        PID= 0000002D        PRCNAM= SYMBIONT_0001   LOGINTIM= 16:25:47.54
        PID= 0000002F        PRCNAM= MCCORMICK       LOGINTIM= 16:27:45.27
Exit 00000001

8002228C!       ADDL            R15,SP,SP EXIT

  1. DELTA is enabled as the debugger.
  2. The example program LOG is invoked with DELTA.
  3. DELTA displays a version number and the first executable instruction. The base address of the program (determined from the map file) is virtual address 30000. The base address is placed in base register 1 with ;X. Now references to an address can use the address offset notation. For example, a reference to the first instruction is X1+200 (or the base address 30000 + offset 200). Also, DELTA displays some address locations as offsets to the base address.
  4. The instruction at address 30164 is displayed in instruction mode using !. Its address location is expressed as the base address plus an offset. In the listing file, the offset is 164. (This is the point where the return status from SYS$GETJPIW is checked.) The base address in base address register X1 is 30000. The address reference, then, is X1+164. Note the + sign is implied when not specified.
    A simple breakpoint is set at that address using the ;B command. The address reference for ;B is the . symbol, representing the current address. X1+164;B would have done the same thing.
  5. The same commands (! command to view the instruction and ;B to set a breakpoint) are repeated for the instruction at offset 1AC. (This is the point at which the print_line function is called.)
  6. Program execution halts at the first breakpoint. DELTA displays the breakpoint message (Brk 1 at 00030164) with the breakpoint number 1 and the virtual address. The virtual address is 30164, which is the base address (30000) plus the offset 164. DELTA then displays the instruction in instruction mode (CMPEQ R0,#X14,R16). The contents of the general register 0 are displayed with the / command. DELTA displays the contents of R0, which is 1. Program execution continues using the ;P command.
  7. The function print_line is executed, and the output (PID, process name, and login time) is displayed.
  8. The O command halts program execution at the instruction where the function returns control (BR R31,#XFFFFE1). (This is the point at which control passes to checking the conditions of the while loop.) Program execution continues with ;P.
  9. Breakpoint 2 is encountered. DELTA displays the breakpoint message, and the instruction. The function is executed with the O command and the function output is displayed. The next instruction where the function returns control is displayed. Program execution continues with the ;P command.
  10. Breakpoint 2 is encountered again. DELTA displays the breakpoint message, and the instruction. The function is executed with the O command and the function output is displayed. The next instruction where the function returns control is displayed. Program execution continues with the ;P command.
  11. Breakpoint 2 is encountered again. The instruction at offset 84 (in print_line) is displayed using !. This instruction is part of the setup for the call to the printf function.
  12. Successive address locations are displayed by pressing the Linefeed key two times. These instructions are the remainder of the setup and the call to printf.
  13. A breakpoint at X1+8C (the current address) is set using the ;B command. This breakpoint is in the function print_line. The . symbol represents the current address. Note that breakpoint 1 was cleared earlier and is now reused by DELTA for the new breakpoint.
  14. Program execution continues with the ;P command.
  15. Program execution stops at the new breakpoint 1, which is in the print_line function. DELTA displays the breakpoint message and the instruction at the new breakpoint. The O command halts program execution at the instruction where the function returns control, stepping over the routine call. Note the O command must be used in this case, as opposed to the ;P command, because the printf function resides in read-only protected memory. Program execution is continued with the ;P command.
  16. Program execution stops at breakpoint 1 in the print_line function. Program execution is continued using a combination of the O and ;P commands.


Index Contents