trap.gml

来自「开放源码的编译器open watcom 1.6.0版的源代码」· GML 代码 · 共 2,053 行 · 第 1/5 页

GML
2,053
字号
.chap *refid=Introd1 Introduction
The &company debugger consists of a number of separate pieces of code. The
main executable, WD.EXE (wd on UNIX systems), provides a debugging `engine'
and user interface.
When the engine wishes to perform an operation upon the program being
debugged such as reading memory or setting a breakpoint, it creates
a request structure and sends it to the `trap file' (so called because
under DOS, it contains the first level trap handlers). The trap file
examines the request structure, performs the indicated action and returns
a result structure to the debugger. The debugger and trap files also use
Machine Architecture Description (MAD) files which abstract the CPU
architecture.
This design has the following benefits:
:OL.
:LI. OS debugging interfaces tend to be wildly varying in how they are accessed.
By moving all the OS specific interface code into the trap file and having
a defined interface to access it, porting the debugger becomes much easier.
:LI. By abstracting the machine architecture specifics through MAD files, it
becomes possible to use one debugger for several target CPU architectures
(such as x86 and Alpha AXP). Unlike most other debuggers, the &company
debugger is not tied to a single host/target combination and if appropriate
trap and MAD files are available, the debugger running on any host can
remotely debug any target.
:LI. The trap file does not have to actually perform the operation. Instead
it could send the request out to a remote server by a communication link
such as a serial line or LAN. The remote server can retrieve the request,
perform the operation on the remote machine and send the results back
via the link. This enables the debugger to debug applications
in cases where there are memory constraints or other considerations which
prevent the debugger proper from running on the remote system (such as
Novell Netware 386).
:eOL.
:P.
This document describes the interface initially used by version 4.0 of the
WATCOM debugger (shipped with the 10.0 C/C++ and FORTRAN releases). It has
been revised to describe changes incorporated in Watcom 11.0 release, as
well as subsequent Open Watcom releases. It
is expected to be modified in future releases. Where possible, notification
of expected changes are given in the document, but all aspects are subject
to revision.
.section Some Definitions
Next follow some general trap definitions.
.beglevel
.section Byte Order
The trap file interface is defined to use little endian byte order. That is,
the least significant byte is stored at the lowest address. Little endian
byte order was chosen for compatibility with existing trap files and
tools. Fixed byte order also eases network communication between
debuggers and trap files running on machines with different byte order.
.section Pointer Sizes
In a 16-bit hosted environment such as DOS, all pointers used by the trap
file are "far" 16:16 pointers. In a 32-bit environment such as Windows NT
the pointers are "near" 0:32 pointers.
.section Base Types
A number of basic types are used in the interface. They are defined
as follows:
:DL.
:DTHD.Type
:DDHD.Definition
:DT.unsigned_8
:DD.1 byte unsigned quantity
:DT.unsigned_16
:DD.2 byte unsigned quantity
:DT.unsigned_32
:DD.4 byte unsigned quantity
:DT.access_req
:DD.The first field of every request is of this type. It is a 1 byte field
which identifies the request to be performed.
:DT.addr48_ptr
:DD.This type encapsulates the concept of a 16:32 pointer.
All addresses in the debuggee memory
are described with these. The debugger
always acts as if the debuggee were in a 32-bit large model environment since
the 32-bit flat model and all 16-bit memory models are subsets.
The structure is defined as follows:
:XMP.
    typedef struct {
        unsigned_32    offset;
        unsigned_16    segment;
    } addr48_ptr;
:eXMP.
The :F.segment:eF. field contains the segment of the address and the :F.offset:eF.
field stores the offset of the address.
:DT.bytes
:DD.The type :F.bytes:eF. is an array of unsigned_8.
The length is provided
by other means. Typically a field of type :F.bytes:eF. is the last one in
a request and the length is calculated from the total length of the request.
:DT.string
:DD.The type :F.string:eF. is actually an array of characters.
The array is terminated by a null ('\0') character.
The length is provided
by other means. Typically a field of type :F.string:eF. is the last one in
a request and the length is calculated from the total length of the request.
:DT.trap_error
:DD.
Some trap file requests return debuggee operating system error codes, notably
the requests to perform file I/O on the remote system. These error codes are
returned as an unsigned_32. The debugger considers the value zero to indicate
no error.
:DT.trap_phandle
:DD.This is an :F.unsigned_32:eF. which holds process (task) handle. A task
handle is used to uniquely identify a debuggee process.
:DT.trap_mhandle
:DD.This is an :F.unsigned_32:eF. which holds a module handle. Typically the
main executable will be one module, and on systems which support DLLs or
shared libraries, each library will be identified by a unique module handle.
:eDL.
.endlevel
.chap The Request Interface
Next follow detailed description of interface elements.
.section Request Structure.
Each request is a composed of two sequences of bytes provided by the
debugger called messages. The first set contains the actual request
code and whatever
parameters that are required by the request. The second sequence is where
the result of the operation is to be stored by the trap file.
:P.
The two sequences need not be contiguous. The sequences are described
to the trap file through two arrays of message entry structures.
This allows the debugger to avoid unnecessary packing and unpacking of
messages, since :F.mx_entry:eF.'s can be set to point directly at
parameter/result buffers.
:P.
Multiple requests are :HP2.not:eHP2. allowed in a single message. The
:F.mx_entry:eF.'s are only used to provide scatter/gather capabilities for
one request at a time.
:P.
The message entry structure is as follows (defined in :F.trptypes.h:eF.):
:XMP.
    typedef struct {
        void            *ptr;
        unsigned        len;
    } mx_entry;
:eXMP.
:PC.
The :F.ptr:eF. is pointing to a block of data for that message entry.
The :F.len:eF. field gives the length of that block.
One array of :F.mx_entry:eF.'s describes the request message. The second array
describes the return message.
:P.
It is not legal to split a message into arbitrary pieces with mx_entries.
Each request documents where an :F.mx_entry:eF. is allowed to start with a
line of dashes.
.section The Interface Routines
The trap file interface must provide three routines: :F.TrapInit:eF.,
:F.TrapRequest:eF., and :F.TrapFini:eF.. How the debugger determines the
address of these routines after loading a trap file, as well as the calling
convention used, is system dependent and described later. These functions are
prototyped in :F.trpimp.h:eF..
.beglevel
.section TrapInit
This function initializes the environment for proper operation of
:F.TrapRequest:eF..
:XMP.
    trap_version TRAPENTRY TrapInit( char       *parm,
                                     char       *error,
                                     unsigned_8 remote
    );
:eXMP.
:PC.
The :F.parm:eF. is a string that the user passes to the trap file. Its
interpretation is completely up to the trap file. In the case of the
&company debugger,
all the characters following the semicolon in the :F./TRAP:eF. option are
passed as the :F.parm:eF.. For example:
:XMP.
    wd /trap=nov;testing program
:eXMP.
:P.
The :F.parm:eF. would be "testing".
Any error message
will be returned in :F.error:eF.. The :F.remote:eF. field
is a zero if the &company debugger is loading the trap file and a one if a
remote server is loading it.
This function returns a structure :F.trap_version:eF. of the following form
(defined in :F.trptypes.h:eF.):
:XMP.
    typedef struct {
        unsigned_8  major;
        unsigned_8  minor;
        unsigned_8  remote;
    } trap_version;
:eXMP.
:PC.
The :F.major:eF. field contains the major version number of the trap file while
the :F.minor:eF. field tells the minor version number of the trap file.
:F.Major:eF. is changed whenever there is a modification made to the trap file
that is not upwardly compatable with previous versions. :F.Minor:eF.
increments by one whenever a change is made to the trap file that is upwardly
compatible with previous versions.
The current major verion is &trp_majver., the current minor version is &trp_minver..
The :F.remote:eF. field informs the
debugger whether the trap file communicates with a remote machine.
:P.
:F.TrapInit:eF. must be called before using :F.TrapRequest:eF. to send a request.
Failure to do so may result in unpredictable operation of :F.TrapRequest:eF..
.section TrapRequest
All requests between the server and the remote trap file are handled by
TrapRequest.
:XMP.
    unsigned TRAPENTRY TrapRequest( unsigned num_in_mx,
                                    mx_entry *mx_in,
                                    unsigned num_out_mx,
                                    mx_entry *mx_out
    );
:eXMP.
:PC.
The :F.mx_in:eF. points to an array of request mx_entry's.
The :F.num_in_mx:eF.
field contains the number of elements of the array. Similarly,
the :F.mx_out:eF.
will point to an array of return mx_entry's. The number of elements
will be
given by the :F.num_out_mx:eF. field. The total number of bytes actually
filled in to the return message by the trap file is returned by the
function (this may be less than the total number of bytes described by
the :F.mx_out:eF. array).
:P.Since every request must start with an :F.access_req:eF. field, the
minimum size of a request message is one byte.
:P.
Some requests do not require a return message. In this case, the program
invoking TrapRequest :HP2.must:eHP2. pass zero for :F.num_out_mx:eF. and NULL for
:F.mx_out:eF..
.beglevel
.section Request Example
The request REQ_READ_MEM needs the memory address and length
of memory to read as input and will return the memory block in the
output message. To read 30 bytes of memory from address 0x0010:0x8000 into
a buffer, we can write:
:XMP.
    mx_entry        in[1];
    mx_entry        out[1];
    unsigned char   buffer[30];
    struct in_msg_def {
        access_req          req;
        addr48_ptr          addr;
        unsigned_16         len;
    } in_msg = { REQ_READ_MEM, { 0x8000, 0x0010 }, sizeof( buffer ) };

    unsigned_16 mem_blk_len;

    in[0].ptr = &in_msg;
    in[0].len = sizeof( in_msg );
    out[0].ptr = &buffer;
    out[0].len = sizeof( buffer );

    mem_blk_len = TrapRequest( 1, in, 1, out );

    if( mem_blk_length != sizeof( buffer ) ) {
        printf( "Error in reading memory\n" );
    } else {
        printf( "OK\n" );
    }
:eXMP.
:PC.
The program will print "OK" if it has transferred 30 bytes of data from the
debuggee's address space to the :F.buffer:eF. variable. If less than 30
bytes is transfered, an error message is printed out.
.endlevel
.section TrapFini
The function terminates the link between the debugger and the trap file.
It should be called
after finishing all access requests.
:XMP.
    void TRAPENTRY TrapFini( void );
:eXMP.
:PC.
After calling :F.TrapFini:eF., it is illegal to call :F.TrapRequest:eF.
without calling :F.TrapInit:eF. again.
.endlevel
.chap The Requests
This section descibes the individual requests, their parameters, and
their return values. A line of dashes indicates where an :F.mx_entry:eF. is
allowed (but not required) to start.
The debugger allows
(via REQ_GET_SUPPLEMENTARY_SERVICE/REQ_PERFORM_SUPPLEMENTARY_SERVICE) optional
components to be implemented only on specific systems.
:P.
The numeric value of the request which is placed in the :F.req:eF. field
follows the symbolic name in parentheses.
.section Core Requests
These requests need to be implemented in all versions of the trap file,
although some of them may only be stub implementations in some environments.
Note that structures suitable for individual requests are declared in
:F.trpcore.h:eF..
.beglevel
.section REQ_CONNECT (0)
Request to connect to the remote machine. This must be the first request made.
:P.
Request message:
:XMP.
    access_req      req
    unsigned_8      major;   <-+- struct trap_version
    unsigned_8      minor;     |
    unsigned_8      remote;  <-+
:eXMP.
:PC.
The :F.req:eF. field contains the request.
The :F.trap_version:eF.
structure tells the version of the program making the request. The :F.major:eF.
field contains the major version number of the trap file while the :F.minor:eF.
field tells the minor version number of the trap file. The :F.major:eF. is
changed whenever there is a modification made to the trap file that is not
upwardly compatable with previous versions. The :F.minor:eF. increments by one
whenever a change is made to the trap file that is upwardly compatable with
previous versions. The current major version is &trp_majver., the current minor version
is &trp_minver..
The :F.remote:eF. field informs the trap file whether a
remote server is between the &company debugger and the trap file.
:P.
Return message:
:XMP.
    unsigned_16 max_msg_size
    ----------------------------
    string      err_msg
:eXMP.
:PC.
If error has occurred, the :F.err_msg:eF. field will returns the error
message string. If there is no error, :F.error_msg:eF. returns a null character
and the field
:F.max_msg_size:eF. will contain the allowed maximum size of a message in
bytes. Any message
(typically reading/writing memory or files)
which would require more than the maximum number of bytes
to transmit or receive must be broken up into multiple requests.
The minimum acceptable value for this
field is 256.
.section REQ_DISCONNECT (1)
Request to terminate the link between the local and remote machine.
After this request, a REQ_CONNECT must be the next one made.
:P.
Request message:
:XMP.
    access_req      req
:eXMP.
:PC.
The :F.req:eF. field contains the request.
:P.
Return message:
:XMP.
    NONE
:eXMP.
.section REQ_SUSPEND (2)
Request to suspend the link between the server and the remote trap file.
The debugger issues this message just before it spawns a sub-shell (the
"system" command). This allows a remote server to enter a state where
it allows other trap files to connect to it (normally, once a remote server
has connected to a trap file, the remote link will fail any other attempts
to connect to it). This allows the user for instance to start up an RFX
process and transfer any missing files to the remote machine before
continuing the debugging process.
:P.
Request message:
:XMP.
    access_req      req
:eXMP.
:PC.
The :F.req:eF. field contains the request.
:P.
Return message:
:XMP.
    NONE
:eXMP.
.section REQ_RESUME (3)
Request to resume the link between the server and the remote trap file.
The debugger issues this request when the spawned sub-shell exits.
:P.
Request message:
:XMP.
    access_req      req
:eXMP.
:PC.
The :F.req:eF. field contains the request.
:P.
Return message:
:XMP.
    NONE
:eXMP.
.section REQ_GET_SUPPLEMENTARY_SERVICE (4)
Request to obtain a supplementary service id.
:P.
Request message:
:XMP.
    access_req  req
    ------------------------
    string      service_name
:eXMP.
:PC.
The :F.req:eF. field contains the request. The :F.service_name:eF field
contains a string identifying the supplementary service. This string is
case insensitive.
:P.
Return message:
:XMP.
    trap_error      err;
    trap_shandle    id;
:eXMP.
:PC.
The :F.err:eF. field is non-zero if something went wrong in obtaining
or initializing the service.
:F.Id:eF. is the identifier for a particular supplementary service.
It need not be the same from one invocation of the trap file to another.
If both it and the :F.err:eF. field are zero, it means that the
service is not available from this trap file.
:NOTE. In the future, we might allow for user developed add-ons to be
integrated with the debugger. There would be two components, one to be
added to the debugger and one to be added to the trap file. The two
pieces could communicate with each other via the supplementary services
mechanism.
.section REQ_PERFORM_SUPPLEMENTARY_SERVICE (5)

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?