HP3000-L Archives

October 1996, Week 4

HP3000-L@RAVEN.UTC.EDU

Options: Use Monospaced Font
Show Text Part by Default
Show All Mail Headers

Message: [<< First] [< Prev] [Next >] [Last >>]
Topic: [<< First] [< Prev] [Next >] [Last >>]
Author: [<< First] [< Prev] [Next >] [Last >>]

Print Reply
Subject:
From:
Stan Sieler <[log in to unmask]>
Reply To:
Stan Sieler <[log in to unmask]>
Date:
Wed, 23 Oct 1996 16:53:53 -0700
Content-Type:
text/plain
Parts/Attachments:
text/plain (290 lines)
Michael writes:
>When you examine another process's stack and find that it is waiting on an
>intrinsic call, how do you determine what parameters the program has passed to
>the intrinsic?  For instance, suppose you see that a process is waiting on an
>FREAD and you want to know what file number it is FREADing on.
>How do you find out?
>
>Using the above example what I would normally do is go to the ?FREAD level and
>then do a DR and see if any of the registers look like either
...
>I am hoping that someone has a better method for
>reading intrinsic parameters off of another persons stack.
...
>BTW, I have demoed the CSEQ product from Lund, and althought it gives register
>and memory addresses for intrinsic parameters, they seem to be only good if
> you are running the program yourself and set a breakpoint on the
> intrinsic you are trying to examine.
>
>Any help in this matter would be appreciated....ok Stan???? :)

Although CSEQ has other features (e.g., for AIF:PE use), the primary purpose
is to show you where parameters to intrinsics are located when you
are "sitting" at the start of the procedure (via a breakpoint).  Of course,
they are only "good" at that spot ... prior to calling the intrinsic, your
code hasn't loaded the registers, and after entering it, the intrinsic's
code changes the registers.

So...let's take the FREAD example Michael asked about.  Note: FREAD is
nasty, as it is optimized code that doesn't happen to store the
register-based parameters into memory at the entry of the procedure.


Assuming PIN #232 is waiting on an FREAD...

I logon as MANAGER.SYS and:

   :debug
   pin #232;tr,i,d
       PC=a.0017170c enable_int+$2c
NM* 0) SP=41837ec8 RP=a.0108c6b0 notify_dispatcher.block_current_process+$31c
NM  1) SP=41837ec8 RP=a.0108eb10 notify_dispatcher+$264
NM  2) SP=41837e48 RP=a.001a1bd0 wait_for_active_port+$ec
NM  3) SP=41837d48 RP=a.001a2850 receive_from_port+$534
NM  4) SP=41837cc8 RP=a.003381e8 extend_receive+$494
NM  5) SP=41837ac8 RP=a.00326cc4 rendezvousio.get_specific+$158
NM  6) SP=41837948 RP=a.00327028 rendezvousio+$1d8
NM  7) SP=41837888 RP=a.00322180 waitforio+$150
NM  8) SP=41837508 RP=a.0032201c ?waitforio+$8
         export stub: a.00e1a9c4 arg_regs+$28
NM  9) SP=418373c8 RP=a.00ddd4ec nm_switch_code+$94c
NM  a) SP=41837298 RP=a.00dc9bec Compatability_Mode
       (switch marker frame)
   CM       SYS  % 226.404    SWITCH'TO'NM'+%4       (Mitroc CCG)  SUSER1
   CM *  0) SYS  % 226.404    SWITCH'TO'NM'+%4       (Mitroc CCG)  SUSER1
   CM    1) SYS  % 162.10557  WAITFORIO+%36          (Mitroc CCG)  CMSWITCH
   CM    2) SYS  % 165.5657   IOMOVE+%1137           (Mitroc CCG)  FSSEG1
   CM    3) SYS  % 165.2521   F'READ'+%410           (MitroC CCL)  FSSEG1
   CM    4) switch marker                            (Mitroc CCG)
NM  b) SP=41836f58 RP=a.00a2017c invoke_cm_procedure+$11c
NM  c) SP=41836d68 RP=a.00b1be30 tm_cms_type_mgr.tm_fread_cms+$218
NM  d) SP=41836ca8 RP=a.00b1f2a4 tm_cms_type_mgr+$190
NM  e) SP=41836b68 RP=a.00bebb18 tm_tape+$84
NM  f) SP=41836ae8 RP=a.01110e14 fread_nm+$810
NM 10) SP=41836a28 RP=a.00e0a788 FREAD+$d4
NM 11) SP=41836628 RP=a.00e0a680 ?FREAD+$8
         export stub: 691.00056124
NM 12) SP=418364e8 RP=691.0005a468
NM 13) SP=418362c8 RP=691.00000000
     (end of NM stack)

Note that my instance of Debug didn't know the name for the
last couple of code addresses (691.00056124 and 691.0005a468) ...
that's because they're addresses within whatever program
PIN #232 is running ... *NOT* within the process my Debug is
running from.

If I'd said, gee..PIN #232 is the program FSYS.PUB.SIELER.  Let's
do the debugging this way:

   :run fsys.pub.sieler; debug
   pin #232; tr,i,d

I'd get:

   ...(same as before)...
NM 10) SP=41836a28 RP=a.00e0a788 FREAD+$d4
NM 11) SP=41836628 RP=a.00e0a680 ?FREAD+$8
         export stub: 691.00056124 test+$35a4
NM 12) SP=418364e8 RP=691.0005a468 EX_PROGRAM
NM 13) SP=418362c8 RP=691.00000000
     (end of NM stack)

Ok...let's determine the file# that FREAD was passed.

According to CSEQ, FREAD looks like:

   :cseq fread
   Function FREAD (
   filenum      :        int16   ;        {R26}
   target       : anyvar record  ;        {(skip R25)
                                           R23, R24}
                                          {Address type = LongAddr}
   tcount       :        int16   )        {SP-$0032}
      := length : int16     {R28}
      { CCE: ok                                                  }
      { CCG: denied, EOF encountered                             }
      { CCL: error                                               }
   {tcount is > 0 for 16-bit words, < 0 for bytes                      }
   {length: 0 is returned for NOWAIT files.                            }
   {   length is always non-negative, and in whatever                  }
   {   units tcount was in.                                            }
      uncheckable_anyvar

so, the file number is in R26 *when we are at the entry of FREAD*.

Are we at the entry of FREAD?  No. ... at best, we can ask the
debugger to logically position us at FREAD+$d4 ... but by that spot in
the code, the register R26 might no longer contain the file #.

Let's check:

   dc FREAD, d4 / 4 + 1

SYS $a.e0a6b4
00e0a6b4  FREAD         0000400e  BREAK    (nmdebug bp)
00e0a6b8  FREAD+$4      6fc30280  STWM     3,320(0,30)
00e0a6bc  FREAD+$8      6bc43d89  STW      4,-316(0,30)
00e0a6c0  FREAD+$c      6bc53d91  STW      5,-312(0,30)
00e0a6c4  FREAD+$10     6bd73d21  STW      23,-368(0,30)
00e0a6c8  FREAD+$14     6bd83d29  STW      24,-364(0,30)
00e0a6cc  FREAD+$18     08000240  OR       0,0,0
00e0a6d0  FREAD+$1c     6bc03e29  STW      0,-236(0,30)
00e0a6d4  FREAD+$20     37c33d81  LDO      -320(30),3
00e0a6d8  FREAD+$24     90786000  COMICLR,<=0,3,24
00e0a6dc  FREAD+$28     34180002  LDO      1(0),24
00e0a6e0  FREAD+$2c     c7f840ca  BB,<,N   24,31,FREAD+$98
00e0a6e4  FREAD+$30     d4a61bde  ZDEPI    3,1,2,5
00e0a6e8  FREAD+$34     40b92122  LDB      4241(0,5),25
00e0a6ec  FREAD+$38     c7f9c0b2  BB,>=,N  25,31,FREAD+$98
00e0a6f0  FREAD+$3c     341f2000  LDO      4096(0),31
00e0a6f4  FREAD+$40     00009820  MTSP     0,2
00e0a6f8  FREAD+$44     4bfd8008  LDW      4(2,31),29
00e0a6fc  FREAD+$48     6bdd3e51  STW      29,-216(0,30)
00e0a700  FREAD+$4c     4bdf3e51  LDW      -216(0,30),31
00e0a704  FREAD+$50     4bd93e59  LDW      -212(0,30),25
00e0a708  FREAD+$54     47fc07dc  LDH      1006(0,31),28
00e0a70c  FREAD+$58     4bf70070  LDW      56(0,31),23
00e0a710  FREAD+$5c     37810002  LDO      1(28),1
00e0a714  FREAD+$60     67e107dc  STH      1,1006(0,31)
00e0a718  FREAD+$64     47f607dc  LDH      1006(0,31),22
00e0a71c  FREAD+$68     6be000e0  STW      0,112(0,31)
00e0a720  FREAD+$6c     8ec22048  COMIBF,= 1,22,FREAD+$98
00e0a724  FREAD+$70     6be000e8  STW      0,116(0,31)
00e0a728  FREAD+$74     42e4000c  LDB      6(0,23),4
00e0a72c  FREAD+$78     d49f1cdf  DEPI     -1,25,1,4
00e0a730  FREAD+$7c     0ee4120c  STBS     4,6(0,23)
00e0a734  FREAD+$80     43f506a6  LDB      851(0,31),21
00e0a738  FREAD+$84     63e006a0  STB      0,848(0,31)
00e0a73c  FREAD+$88     63e006a2  STB      0,849(0,31)
00e0a740  FREAD+$8c     63e006a4  STB      0,850(0,31)
00e0a744  FREAD+$90     d6a00cff  DEP      0,24,1,21
00e0a748  FREAD+$94     63f506a6  STB      21,851(0,31)
00e0a74c  FREAD+$98     d35a1ff0  EXTRS    26,31,16,26    <--a usage of r26
00e0a750  FREAD+$9c     4bd73d21  LDW      -368(0,30),23
00e0a754  FREAD+$a0     4bd83d29  LDW      -364(0,30),24
00e0a758  FREAD+$a4     47d43d1d  LDH      -370(0,30),20
00e0a75c  FREAD+$a8     4bc43d59  LDW      -340(0,30),4
00e0a760  FREAD+$ac     d2831ff0  EXTRS    20,31,16,3
00e0a764  FREAD+$b0     d4421a1f  ZDEPI    1,15,1,2
00e0a768  FREAD+$b4     d0851bfe  EXTRU    4,31,2,5
00e0a76c  FREAD+$b8     6bc03f89  STW      0,-60(0,30)
00e0a770  FREAD+$bc     6bc33f91  STW      3,-56(0,30)
00e0a774  FREAD+$c0     6bc23f99  STW      2,-52(0,30)
00e0a778  FREAD+$c4     6bc53f81  STW      5,-64(0,30)
00e0a77c  FREAD+$c8     23f4a014  LDIL     $aa9000,31
00e0a780  FREAD+$cc     e7e02cb0  BLE      1624(4,31)  <-- call to fread_nm
00e0a784  FREAD+$d0     081f0242  OR       31,0,2
00e0a788  FREAD+$d4     081c0243  OR       28,0,3   <-- return from fread_nm

Examining the code at the very start (first 3 to 20 instructions), we
see that the parameters in registers R23 and R24 are saved into the
stack (FREAD+$10 and FREAD+$14), *but* R26 isn't saved into the stack :(

Instead, we see that R26 is used once (sign extended from 16-bit integer
to 32-bit integer) at FREAD+$98, and then "passed" into fread_nm.
(BTW, AVATAR would have shown FREAD+$cc as a call to fread_nm).

We can't just do:

   lev 11
   = r26

to find out what R26 is, because the "lev" command in Debug (which
logically "unwinds" the stack), can only "restore" some of the
registers (basically R3..R18, R27, R30, SR4)....but not R23..R26.

So, to find out what R26 was at the entry, we can either look to see
what was passed to fread_nm in R26 (hoping that fread_nm saved it), *or*
look at the code that generated the value in R26 and then called FREAD.

Let's do the latter...

   lev 12           /* look at code that called FREAD */
   dc pc - 40, 44/4        /* display prior 14 or so instructions */

PROG $691.560e4
000560e4  test+$3564   44960110  LDH      136(0,4),22
000560e8  test+$3568   d2d61ff0  EXTRS    22,31,16,22
000560ec  test+$356c   0ac00416  SUB      0,22,22
000560f0  test+$3570   64b6004c  STH      22,38(0,5)
000560f4  test+$3574   d2c81ff0  EXTRS    22,31,16,8
000560f8  test+$3578   44b30060  LDH      48(0,5),19
000560fc  test+$357c   449400f0  LDH      120(0,4),20
00056100  test+$3580   08940654  SH1ADD   20,4,20
00056104  test+$3584   028010b5  LDSID    (0,20),21
00056108  test+$3588   44b6004c  LDH      38(0,5),22
0005610c  test+$358c   6bd63f99  STW      22,-52(0,30)
00056110  test+$3590   08140258  OR       20,0,24
00056114  test+$3594   08150257  OR       21,0,23
00056118  test+$3598   d27a1ff0  EXTRS    19,31,16,26
0005611c  test+$359c   e8590bfb  BL,N     ?HELP+$35c,2     <-- call to FREAD
00056120  test+$35a0   08000240  OR       0,0,0
00056124  test+$35a4   d39c1ff0  EXTRS    28,31,16,28

Well, test+$3598 built the value passed to FREAD in r26...by taking the
value in R19.  Looking backwards further, we see that test+$3578
build the value in R19 (assuming some code we don't see didn't branch into
the middle of the above code).  It got R19 by loading a 16-bit value (LDH)
from R5 + #48 ... alright! Let's look at that memory address, and hope
that no one changed that halfword of memory since the LDH:

   dv r5+#48
VIRT $101.4163991c $ 000b0000

$000b000 looks like a BIG file number...but wait, the "dv" command always
takes the virtual address, rounds down to a multiple of 4, and displays
data in groups of 4 bytes at a time.   To get just the 16-bits we want
(probably either $000b or $0000), we could look at the value of the
address r5+#48, and determine which half of the 32-bit word is being
loaded, or we could let Debug do it for us:

   = [s16 r5+#48]
   $b

So...file $b (probably).

We can double check this by looking in the opposite direction.  FREAD
called fread_nm, passing the file number in R26.  The first few
instructions in fread_nm are:

   dc fread_nm, 10
SYS $a.1110604
01110604  fread_nm         6bc23fd9  STW      2,-20(0,30)
01110608  fread_nm+$4      6fc30800  STWM     3,1024(0,30)
0111060c  fread_nm+$8      6bc43809  STW      4,-1020(0,30)
01110610  fread_nm+$c      6bc53811  STW      5,-1016(0,30)
01110614  fread_nm+$10     6bc63819  STW      6,-1012(0,30)
01110618  fread_nm+$14     6bc73821  STW      7,-1008(0,30)
0111061c  fread_nm+$18     6bc83829  STW      8,-1004(0,30)
01110620  fread_nm+$1c     6bc93831  STW      9,-1000(0,30)
01110624  fread_nm+$20     6bca3839  STW      10,-996(0,30)
01110628  fread_nm+$24     6bcb3841  STW      11,-992(0,30)
0111062c  fread_nm+$28     6bcc3849  STW      12,-988(0,30)
01110630  fread_nm+$2c     6bcd3851  STW      13,-984(0,30)
01110634  fread_nm+$30     6bce3859  STW      14,-980(0,30)
01110638  fread_nm+$34     6bcf3861  STW      15,-976(0,30)
0111063c  fread_nm+$38     6bd03869  STW      16,-972(0,30)
01110640  fread_nm+$3c     67da37bd  STH      26,-1058(0,30)

Notice fread_nm+$3c...it stores R26 into memory!  If we assume that the
value hasn't changed since then (probably a safe assumption), we
can do:

   lev 10
   dc pc              /* to visually verify that Debug positioned
                      /* us in the "fread_nm" area
SYS $a.1110e14
01110e14  fread_nm+$810    4bdf38d9  LDW      -916(0,30),31
                      /* Yep...we got the right "lev" level

   = [s16 sp-#1058]
   $b

This confirms that the file# is $b (or #11).


--
Stan Sieler                                          [log in to unmask]
                                     http://www.allegro.com/sieler.html

ATOM RSS1 RSS2