Rem
Rem dbmspb.sql
Rem 
Rem  Copyright (c) Oracle Corporation 1995, 1996, 1997, 1998, 1999. All Rights Reserved.
Rem
Rem    NAME
Rem      dbmspb.sql - ProBe (PL/SQL debugger) server-side package.
Rem
Rem   NOTES
Rem     This package (DBMS_DEBUG) provides debugging facilities for 
Rem     server-side PL/SQL.
Rem
Rem    MODIFIED   (MM/DD/YY)
Rem    dbronnik    08/03/99 - 778426: set breakpoints and show source by frame#
Rem    jmallory    05/21/99 - Add exception info, OER breakpoints, etc.
Rem    jmallory    05/14/99 - Add set_timeout_behaviour
Rem    jmallory    03/18/99 - Add target_program_running
Rem    jmallory    02/24/99 - Package variables
Rem    jmallory    11/17/98 - Add cursor constants
Rem    jmallory    10/07/98 - Remove execute_without_results
Rem    jmallory    09/14/98 - Add diagnostics
Rem    jmallory    07/16/98 - Make DBMS_DEBUG public
Rem
Rem
Rem OVERVIEW
Rem   DBMS_DEBUG is a PL/SQL API to the PL/SQL debugger layer ('Probe') in 
Rem   the Oracle server.  It is intended mainly for vendors implementing 
Rem   server-side debuggers, and provides a way to debug server-side PL/SQL 
Rem   (procedures, functions, packages, triggers, anonymous blocks, types,
Rem    etc.)
Rem   DBMS_DEBUG uses a 'pull' event model: in order to debug server-side
Rem   code it is necessary to have two database sessions: a session in which
Rem   the code will be executed in debug-mode (known as the target session),
Rem   and a second session (known as the debug session) to supervise the 
Rem   target session.
Rem
Rem   To use DBMS_DEBUG, the target session first makes the appropriate calls 
Rem   to initialize itself (described later).  This marks the session so that
Rem   the PL/SQL interpreter runs in debug-mode and generates debug events
Rem   (described later).  As debug events are generated, they are posted from
Rem   the session.  In most cases, debug events require return notification:
Rem   the interpreter pauses awaiting a reply.
Rem   Meanwhile the debug session must also initialize itself via DBMS_DEBUG:
Rem   this tells it what target session to supervise.  The debug session may
Rem   then call entrypoints in DBMS_DEBUG to read events that were posted
Rem   from the target session and to communicate with the target session.
Rem
Rem   In order to inspect or modify the values of variables or parameters, 
Rem   Probe requires the existence of debug information, which is optionally
Rem   generated by the PL/SQL compiler.  To explicitly generate debug 
Rem   information for an existing program unit, the syntax is:
Rem       ALTER [PROCEDURE | FUNCTION | PACKAGE | TRIGGER | TYPE] <name> 
Rem           COMPILE DEBUG;
Rem   To recompile a package body or type body, the syntax is:
Rem       ALTER [PACKAGE | TYPE] <name> COMPILE DEBUG BODY;
Rem   Alternatively, there is a session switch that the compiler checks when
Rem   deciding whether to generate debug information.  Setting this switch
Rem   will cause all future compilations in the session to generate debug
Rem   information.  The syntax is:
Rem       ALTER SESSION SET PLSQL_DEBUG = true;
Rem
Rem The diagrams below give the general idea.  
Rem Each box contains a description and the appropriate DBMS_DEBUG call.
Rem
Rem                             Target Session
Rem                             **************
Rem                  +--------------------------------------+
Rem                  | Initialize session for debugging,    |
Rem                  | and generate/specify unique debugID. |
Rem                  | DBMS_DEBUG.initialize()              |
Rem                  +--------------------------------------+
Rem                                       |
Rem   +---------------------------------->|
Rem   |                                   V
Rem   |              +--------------------+-----------------+
Rem   |              V                    |                 V
Rem   |   +-----------------------+       |      +------------------------+
Rem   |   | Start debugging       |       |      | Stop debugging         |
Rem   |   | DBMS_DEBUG.debug_on() |       |      | DBMS_DEBUG.debug_off() |
Rem   |   +-----------------------+       |      +------------------------+
Rem   |              V                    V                 V
Rem   |              +--------------------+-----------------+
Rem   |                                   V
Rem   |                      +-------------------------+
Rem   |                      | Execute PL/SQL programs |
Rem   |                      +-------------------------+
Rem   |                                   V
Rem   +-----------------------------------+
Rem
Rem
Rem
Rem                             Debug Session
Rem                             *************
Rem                         +-----------------------------+
Rem    Input:               | Initialize                  |
Rem      debugID from   --> | DBMS_DEBUG.attach_session() |
Rem      target session     +-----------------------------+
Rem                                       |
Rem +------------------------------------>|
Rem |                +-------------------<+<------------------+
Rem |                |                    |                   |
Rem |                |   +--------------------------------+   |
Rem |                |   | Manipulate breakpoints         |   |
Rem |                |   | DBMS_DEBUG.set_breakpoint()    |   |
Rem |                |   | DBMS_DEBUG.delete_breakpoint() |   |
Rem |                |   | DBMS_DEBUG.disable_breakpoint()|   |
Rem |                |   | DBMS_DEBUG.enable_breakpoint() |   |
Rem |                |   | DBMS_DEBUG.show_breakpoints()  |   |
Rem |                |   +--------------------------------+   |
Rem |                |                    V                   |
Rem |                +------------------->+>------------------+
Rem |                                     |
Rem |                                     V
Rem |                +--------------------------------------+
Rem |                | Read first event from target session |
Rem |                | DBMS_DEBUG.synchronize()             |
Rem |                +--------------------------------------+
Rem |                           |
Rem |   +---------------------->|
Rem |   |   +------------------>|
Rem |   |   |                   V
Rem |   |   |                   +----------------------->+
Rem |   |   |                   |                        |
Rem |   |   |                   V                        |
Rem |   |   |   +------------------------------+         |
Rem |   |   |   | Show stack                   |-------->+
Rem |   |   |   | DBMS_DEBUG.print_backtrace() |         V
Rem |   |   |   +------------------------------+         |
Rem |   |   |                                            |
Rem |   |   |                  +------------------------<+
Rem |   |   |                  V                         V
Rem |   |   |   +------------------------+               |
Rem |   |   |   | Get/set values         |               |
Rem |   |   |   | DBMS_DEBUG.get_value() |-------------->+
Rem |   |   |   | DBMS_DEBUG.set_value() |               V
Rem |   |   |   +------------------------+               |
Rem |   |   |                                            |
Rem |   |   |               +---------------------------<+
Rem |   |   |               V                            V
Rem |   |   |   +------------------------+               |
Rem |   |   |   | Manipulate breakpoints |-------------->+
Rem |   |   |   +------------------------+               V
Rem |   |   |                                            |
Rem |   |   |                +--------------------------<+
Rem |   |   |                V                           V
Rem |   |   |   +--------------------------------+       |
Rem |   |   |   | Show source                    |------>+
Rem |   |   |   | DBMS_DEBUG.show_source()       |       V
Rem |   |   |   | DBMS_DEBUG.show_frame_source() |       |
Rem |   |   |   +--------------------------------+       |
Rem |   |   |                                            |
Rem |   |   +----------------------<+-------------------<+
Rem |   |                           |
Rem |   |                           V 
Rem |   |      +--------------------------------------------+
Rem |   |      | Continue execution and wait for next event |
Rem |   |      | DBMS_DEBUG.continue()                      |
Rem |   |      +--------------------------------------------+
Rem |                           |
Rem |   |       +---------------------------------------+
Rem |   +- No - | Program terminated?                   |
Rem |           | (event is DBMS_DEBUG.reason_knl_exit) |
Rem |           +---------------------------------------+
Rem |                           |
Rem |                          Yes
Rem +---------------------------+
Rem  next program to debug      V 
Rem                             |
Rem                +-----------------------------+
Rem                | Detach session              |
Rem                | DBMS_DEBUG.detach_session() |
Rem                +-----------------------------+
Rem
Rem Control of the interpreter
Rem   The interpreter will pause execution in the following places:
Rem     1. At startup (so that any deferred breakpoints may be installed
Rem        prior to execution)
Rem     2. At any line containing an enabled breakpoint
Rem     3. At any line where an 'interesting' event occurs.  The set of
Rem        interesting events is specified by the flags passed to
Rem        DBMS_DEBUG.continue (in the 'breakflags' parameter).
Rem        See the section on 'Break Flags' below for more details.
Rem
Rem Terminology
Rem   + Program unit - a PL/SQL program of any kind (procedure, function, 
Rem     package, package body, trigger, anonymous block, object type, or
Rem     object type body).
Rem
Rem General notes:
Rem   + Session termination
Rem     There is no event for session termination.  Therefore it is the
Rem     responsibility of the debug session to check and make sure that 
Rem     the target session has not terminated.  A call to 
Rem     dbms_debug.synchronize() after the target session has terminated
Rem     will cause the debug session to hang until it times out.
Rem
Rem   + Deferred operations
Rem     If no target session exists (or is waiting) when set_breakpoint() is
Rem     called, the breakpoint request will be deferred until the target
Rem     session is available.  Note the following restrictions:
Rem       1. set_breakpoint() does not return the breakpoint number (it can be
Rem          obtained later from show_breakpoints() if necesary)
Rem       2. set_breakpoint() does not validate the breakpoint request: if
Rem          the requested source line does not exist then the error will
Rem          silently occur at synchronization and no breakpoint will be 
Rem          set.
Rem
Rem   + Stepping into packages.  
Rem     Packages are instantiated upon first use, and any initialization
Rem     code (in either the package spec or body) is executed at that time.
Rem     Thus a call to a procedure/function in a package may look to the
Rem     debugger like several calls all on the same line (one call to 
Rem     initialize the spec if necessary, one to initialize the body if
Rem     necessary, and one to call the desired entrypoint).
Rem
Rem   + Diagnostic output
Rem     To debug Probe, there are 'diagnostics' parameters to some of the
Rem     calls in DBMS_DEBUG.  These parameters specify whether to place
Rem     diagnostic output in the rdbms tracefile.  (If output to the rdbms
Rem     tracefile is disabled then these parameters will be no-ops.)
Rem
Rem   + PL/SQL Exceptions
Rem     Exceptions that are declared in PL/SQL programs are known as
Rem     user-defined exceptions (UDE's).  In addition, there are Oracle
Rem     Errors (OERs) that are returned from the Oracle kernel.  To tie
Rem     the two mechanisms together, PL/SQL provides the 'exception_init'
Rem     pragma, which turns a user-defined exception into an OER, so that
Rem     a PL/SQL handler may be used for it, and so that the PL/SQL
Rem     engine can return OERs to the Oracle kernel.  As of the current
Rem     release (8.1.6), the only information available about an OER is
Rem     its number.  If two user-defined exceptions are exception_init'd
Rem     to the same OER, they are indistinguishable.


Rem Wishlist (in no particular order)
Rem  1. Ability for debug session to put target session into diagnostic mode.
Rem  2. Better handling of deferred breakpoints (in set_breakpoint, to 
Rem     indicate that the breakpoint not be deferred; at transmission time
Rem     if the breakpoint can't be set)
Rem  3. Interface to access the debug information ("describe" interface)
Rem  4. Access to sqlerrm
Rem  5. Access to %OLD, %NEW in triggers
Rem  6. Watchpoints
Rem  7. Exception information, and ability to break on specific exception
Rem  8. Ability to get/set bind variables
 


Rem ----------------- Public ADTs used by DBMS_DEBUG --------------------
Rem DBMS_DEBUG_VC2COLL is used in dbms_debug.execute to pass data back to
Rem the caller.  Native dynamic SQL requires it to be a SQL type (as does
Rem DBMS_SQL).
Rem
CREATE OR REPLACE TYPE dbms_debug_vc2coll is table of varchar2(1000)
/
Rem show errors
GRANT EXECUTE on dbms_debug_vc2coll to public
/


CREATE OR REPLACE PACKAGE DBMS_DEBUG IS 

   ------------------------------
   --  PUBLIC CONSTANTS and TYPES

   ----------------------------- PROGRAM_INFO ---------------------
   -- Specifies a program location - a line number in a program unit.
   -- Used for stack backtraces and for setting and examining breakpoints.
   --
   -- The read-only fields are currently ignored by Probe for breakpoint
   -- operations.  They are set by Probe only for stack backtraces.
   --    EntrypointName - null unless this is a nested procedure/function
   --    LibunitType    - to disambiguate among objects that share the same
   --                     namespace (eg. procedure and package spec).  See
   --                     the LibunitType_* constants below.
   --
   TYPE program_info IS RECORD
   (
       -- The following fields are used when setting a breakpoint
       Namespace        BINARY_INTEGER,  -- See 'NAMESPACES' section below.
       Name             VARCHAR2(30),  -- name of the program unit
       Owner            VARCHAR2(30),  -- owner of the program unit
       Dblink           VARCHAR2(30),  -- database link, if remote
       Line#            BINARY_INTEGER,

       -- Read-only fields (set by Probe when doing a stack backtrace)
       LibunitType      BINARY_INTEGER,   -- ie. kglobtyp
       EntrypointName   VARCHAR2(30)
   );

   ------------------------------- RUNTIME_INFO -----------------------
   -- Runtime_info gives context information about the running program.
   --
   -- Probe v2.4:
   --   Added oer.  It gets set if info_getOerInfo is set.  The oer
   --   is a positive number.  It can be translated into SQLCODE by
   --   translating 1403 to 100, 6510 to 1, and negating any other value.
   --
   TYPE runtime_info IS RECORD
   (
       Line#            BINARY_INTEGER,  -- (duplicate of program.line#)
       Terminated       BINARY_INTEGER,  -- has the program terminated?
       Breakpoint       BINARY_INTEGER,  -- breakpoint number
       StackDepth       BINARY_INTEGER,  -- number of frames on the stack
       InterpreterDepth BINARY_INTEGER,  -- <reserved field>
       Reason           BINARY_INTEGER,  -- reason for suspension
       Program          program_info,    -- source location

       -- Following fields were added in Probe v2.4
       oer              PLS_INTEGER      -- OER (exception), if any
   );

   ---------------------------- BREAKPOINT_INFO ----------------------------
   -- Information about a breakpoint: its current status and the program unit
   -- in which it was placed.
   --
   -- (The reason for duplicating fields from the 'program_info' record is
   --  that PL/SQL doesn't yet support tables of composite records, and 
   --  show_breakpoints is going to build a table of these records.)
   --
   TYPE breakpoint_info IS RECORD
   (
      -- These fields are duplicates of 'program_info':
      Name        VARCHAR2(30),
      Owner       VARCHAR2(30),
      DbLink      VARCHAR2(30),
      Line#       BINARY_INTEGER,
      LibunitType BINARY_INTEGER,

      Status      BINARY_INTEGER   -- see breakpoint_status_* below
   );

   -- Breakpoint statuses.  
   --   breakpoint_status_unused - the breakpoint is not in use.
   --
   -- Otherwise the status is a mask of the following values:
   --   breakpoint_status_active - this is a line breakpoint
   --   breakpoint_status_active2 - this is an entry breakpoint (deprecated
   --                               functionality)
   --   breakpoints_status_disabled - this breakpoint is currently disabled
   --   breakpoint_status_remote - this is a 'shadow' breakpoint (a local
   --          representation of a remote breakpoint).
   --    
   -- (Internal note: these map to the PBBPT constants)
   --
   breakpoint_status_unused    CONSTANT BINARY_INTEGER := 0;
   breakpoint_status_active    CONSTANT BINARY_INTEGER := 1;
   breakpoint_status_active2   CONSTANT BINARY_INTEGER := 2;
   breakpoint_status_disabled  CONSTANT BINARY_INTEGER := 4;
   breakpoint_status_remote    CONSTANT BINARY_INTEGER := 8;


   ------------------------------ INDEX_TABLE ------------------------------
   -- Used by get_indexes to return the available indexes for a given
   -- indexed table.  See get_indexes for more details.
   --
   TYPE index_table IS table of BINARY_INTEGER index by BINARY_INTEGER;

   ---------------------------- BACKTRACE_TABLE ----------------------------
   -- Used by print_backtrace.
   TYPE backtrace_table IS TABLE OF program_info INDEX BY BINARY_INTEGER;

   --------------------------- BREAKPOINT_TABLE ---------------------------
   -- Used by show_breakpoints.
   TYPE breakpoint_table IS TABLE OF breakpoint_info INDEX BY BINARY_INTEGER;

   ------------------------------- VC2_TABLE -------------------------------
   -- Used by show_source.
   TYPE vc2_table IS table of varchar2(90) index by BINARY_INTEGER;

   ------------------------------- oer_table -------------------------------
   -- Used by show_breakpoints
   -- VERSION 
   --    Probe v2.4
   TYPE oer_table IS TABLE OF PLS_INTEGER INDEX BY BINARY_INTEGER;

   ------------------------------- NAMESPACES -----------------------------
   -- Program units on the server reside in different namespaces.  When
   -- setting a breakpoint it is necessary to specify the desired namespace
   -- (to distinguish between a package spec and a package body, for example).
   --
   -- 1. Namespace_cursor contains cursors (anonymous blocks)
   -- 2. Namespace_pgkspec_or_toplevel contains:
   --       + package specifications
   --       + procedures and functions (that are not nested inside other
   --                                   packages/procedures/functions)
   --       + object types 
   -- 3. Namespace_pkg_body contains package bodies and type bodies.
   -- 4. Namespace_trigger contains triggers.
   -- 5. Namespace_none is used to describe a frame by number,
   --    currently supported by set_breakpoint only.
   --
   -- (Internal note: these map to the KGLN constants)
   --
   namespace_cursor               CONSTANT BINARY_INTEGER := 0;
   namespace_pkgspec_or_toplevel  CONSTANT BINARY_INTEGER := 1;
   namespace_pkg_body             CONSTANT BINARY_INTEGER := 2;
   namespace_trigger              CONSTANT BINARY_INTEGER := 3;
   namespace_none                 CONSTANT BINARY_INTEGER := 127;

   ----------------------------- LIBUNIT TYPES -----------------------------
   -- These provide an itemization of the actual type of a stack frame,
   -- rather than just the namespace in which it resides.  This information
   -- is helpful sometimes when presenting a stack backtrace to the user,
   -- and is written into the LibunitType field of program_info.
   --
   -- In retrospect, it probably would have been cleaner not to expose
   -- namespaces at all and to use libunit types instead.  This might be
   -- done in a future release (via overloading).
   --
   -- (Internal note: these map to the KGLT constants).
   --
   LibunitType_cursor             CONSTANT BINARY_INTEGER :=  0;
   LibunitType_procedure          CONSTANT BINARY_INTEGER :=  7;
   LibunitType_function           CONSTANT BINARY_INTEGER :=  8;
   LibunitType_package            CONSTANT BINARY_INTEGER :=  9;
   LibunitType_package_body       CONSTANT BINARY_INTEGER := 11;
   LibunitType_trigger            CONSTANT BINARY_INTEGER := 12;
   LibunitType_Unknown            CONSTANT BINARY_INTEGER := -1;


   --------------------------- BREAK FLAGS --------------------------------
   -- Values to use for the 'breakflags' parameter to continue(), in order
   -- to tell Probe what events are of interest to the client.
   -- These flags may be combined.
   --
   -- (Internal note: these map to the PEDE constants)
   --
   -- Line stepping:
   --   break_next_line - break at next source line (step over calls)
   --   break_any_call  - break at next source line (step into calls)
   --   break_any_return - break after returning from current entrypoint 
   --        (skip over any entrypoints that are called from the current)
   --   break_return     - break the next time an entrypoint gets ready to
   --         return (note that this includes entrypoints called from the
   --         current one.  If interpreter is executing Proc1, which calls
   --         Proc2, then break_return will stop at the end of Proc2.)
   --
   --  (Yes, break_any_return and break_return are backwards.  Too late to
   --   fix it now that we have existing clients...)
   --
   -- Exceptions:
   --   break_exception - break when an exception is raised
   --   break_handler   - break when an exception handler is executed
   --
   -- Execution termination:
   --   abort_execution  - terminate execution and force an 'exit' event
   --     as soon as DBMS_DEBUG.continue is called
   --
   break_exception      CONSTANT PLS_INTEGER :=    2;
   break_any_call       CONSTANT PLS_INTEGER :=   12;  -- 4 | 8
   break_return         CONSTANT PLS_INTEGER :=   16;
   break_next_line      CONSTANT PLS_INTEGER :=   32;
   break_any_return     CONSTANT PLS_INTEGER :=  512;
   break_handler        CONSTANT PLS_INTEGER := 2048;
   abort_execution      CONSTANT PLS_INTEGER := 8192;

   -- Not supported yet:
   --   break_control_c - break when a control-C is issued by the client
   --   break_RPC       - break when executing an RPC
   break_control_c  CONSTANT BINARY_INTEGER :=  256;
   break_RPC        CONSTANT BINARY_INTEGER := 4096;
  
   -- Reserved internal values:
   --   4 and 8 for CALL/XCAL
   --   64 and 128 for ICD enter/return

   ------------------------- INFORMATION FLAGS ---------------------------
   -- These are flags that can be passed as the 'info_requested' parameter
   -- to synchronize, continue, and get_runtime_info.
   -- 
   -- (Internal note: these map to the PBBA constants)
   --
   info_getStackDepth    CONSTANT PLS_INTEGER := 2;  -- get stack depth
   info_getBreakpoint    CONSTANT PLS_INTEGER := 4;  -- get breakpoint number
   info_getLineinfo      CONSTANT PLS_INTEGER := 8;  -- get program info
   info_getOerInfo       CONSTANT PLS_INTEGER := 32; -- (Probe v2.4)


   ------------------------- REASONS -------------------------------------
   -- Reasons for suspension. After continue is executed, the program will
   -- either run to completion or break on some line. 
   --
   -- (Internal note: these map to the PBEVN constants)
   --
   reason_none        CONSTANT BINARY_INTEGER :=  0;
   reason_interpreter_starting CONSTANT BINARY_INTEGER :=  2;
   reason_breakpoint  CONSTANT BINARY_INTEGER :=  3; -- at a breakpoint
   reason_enter       CONSTANT BINARY_INTEGER :=  6; -- procedure entry
   reason_return      CONSTANT BINARY_INTEGER :=  7; -- procedure return
   reason_finish      CONSTANT BINARY_INTEGER :=  8; -- procedure is finished
   reason_line        CONSTANT BINARY_INTEGER :=  9; -- reached a new line
   reason_interrupt   CONSTANT BINARY_INTEGER := 10; -- an interrupt occurred
   reason_exception   CONSTANT BINARY_INTEGER := 11; -- an exception was raised
   reason_exit        CONSTANT BINARY_INTEGER := 15; -- interpreter is exiting
   reason_handler     CONSTANT BINARY_INTEGER := 16; -- start exception-handler
   reason_timeout     CONSTANT BINARY_INTEGER := 17; -- a timeout occurred
   reason_instantiate CONSTANT BINARY_INTEGER := 20; -- instantiation block
   reason_abort       CONSTANT BINARY_INTEGER := 21; -- interpeter is aborting
   reason_knl_exit    CONSTANT BINARY_INTEGER := 25; -- interpreter is exiting

   -- Not yet supported:
   reason_sql         CONSTANT BINARY_INTEGER :=  4; -- executing SQL
   reason_watch       CONSTANT BINARY_INTEGER := 14; -- watched value changed
   reason_rpc         CONSTANT BINARY_INTEGER := 18; -- an RPC started
   reason_unhandled   CONSTANT BINARY_INTEGER := 19; -- unhandled exception

   -- Reserved internal values:
   --   1  for internal bootstrapping init
   --   5  unused
   reason_ICD_call    CONSTANT BINARY_INTEGER := 12;
   reason_ICD_return  CONSTANT BINARY_INTEGER := 13;

   -- Added in Probe v2.4
   reason_oer_breakpoint   CONSTANT BINARY_INTEGER := 26;

   ------------------------------ ERROR CODES ------------------------------
   -- These values are returned by the various functions that are called in
   -- the debug session (synchronize, continue, set_breakpoint, etc).
   --
   -- (If PL/SQL exceptions worked across client/server and server/server
   --  boundaries then these would all be exceptions rather than error 
   --  codes.)
   --
   -- (Internal note: these map to the PBERR constants)
   --
   success               CONSTANT binary_integer :=  0;
   -- Statuses returned by GET_VALUE and SET_VALUE:
   error_bogus_frame     CONSTANT binary_integer :=  1;  -- no such frame
   error_no_debug_info   CONSTANT binary_integer :=  2;  -- debuginfo missing
   error_no_such_object  CONSTANT binary_integer :=  3;  -- no such var/parm
   error_unknown_type    CONSTANT binary_integer :=  4;  -- debuginfo garbled
   error_indexed_table   CONSTANT binary_integer := 18;  -- Can't get/set an
                                                         -- entire collection at
                                                         -- once
   error_illegal_index   CONSTANT binary_integer := 19;  -- illegal collection
                                                         -- index (V8)
   error_nullcollection  CONSTANT binary_integer := 40;  -- collection is 
                                                         -- atomically null (V8)
   error_nullvalue     CONSTANT binary_integer := 32;    -- value is null

   -- Statuses returned by set_value:
   error_illegal_value   CONSTANT binary_integer :=  5;  -- constraint violation
   error_illegal_null    CONSTANT binary_integer :=  6;  -- constraint violation
   error_value_malformed CONSTANT binary_integer :=  7;  -- bad value
   error_other           CONSTANT binary_integer :=  8;  -- unknown error
   error_name_incomplete CONSTANT binary_integer := 11;  -- not a scalar lvalue

   -- Statuses returned by the breakpoint functions:
   error_illegal_line    CONSTANT binary_integer := 12;  -- no such line
   error_no_such_breakpt CONSTANT binary_integer := 13;  -- no such breakpoint
   error_idle_breakpt    CONSTANT binary_integer := 14;  -- unused breakpoint
   error_stale_breakpt   CONSTANT binary_integer := 15;  -- pu changed under bpt
   error_bad_handle      CONSTANT binary_integer := 16;  -- can't set bpt there

   -- General error codes (returned by many of the dbms_debug routines)
   error_unimplemented   CONSTANT binary_integer := 17;  -- NYI functionality
   error_deferred        CONSTANT binary_integer := 27; -- request was deferred
                                                        -- (currently unused)
   error_exception     CONSTANT binary_integer := 28; -- exception inside Probe
   error_communication CONSTANT binary_integer := 29; -- generic pipe error
   error_timeout       CONSTANT binary_integer := 31; -- timeout


   -- Error codes that only apply to client-side PL/SQL
   error_pbrun_mismatch  CONSTANT binary_integer :=  9;
   error_no_rph          CONSTANT binary_integer := 10;
   error_probe_invalid   CONSTANT binary_integer := 20;
   error_upierr          CONSTANT binary_integer := 21;
   error_noasync         CONSTANT binary_integer := 22;
   error_nologon         CONSTANT binary_integer := 23;
   error_reinit          CONSTANT binary_integer := 24;
   error_unrecognized    CONSTANT binary_integer := 25;
   error_synch           CONSTANT binary_integer := 26;
   error_incompatible    CONSTANT binary_integer := 30;


   ----------------------------- CURSOR FLAGS -----------------------------
   --   The 'value' of a cursor returned by GET_VALUE is a string of the 
   --   following form:
   --      'flags:<f>, rowcount:<r>'                  [Probe v2.2 and earlier]
   --      'flags:<f>, rowcount:<r>, knlflags:<k>'    [Probe v2.2+ and later]
   --   which the caller is expected to parse.
   --
   --   - The rowcount <r> is the cursor's rowcount.
   --
   --   - The flags <f> are a bitmask of the following values:
   --        cflags_open           - %OPEN
   --        cflags_found          - %FOUND
   --        cflags_notfound       - %NOTFOUND
   --        cflags_recursive      - recursive cursor
   --        cflags_uninitialized  - uninitialized refcursor
   --        cflags_refcur_bind    - refcursor bind variable
   --        cflags_first_iter     - first iteration of cursor
   --        cflags_dynamic_sql    - this is a dynamic SQL cursor
   --        cflags_dynamic_open   - dynamic OPEN statement
   --     This is not an exhaustive listing of the possible flags, but the
   --     other values are used temporarily by the interpreter and can not
   --     be relied on.  Probe does not strip these undocumented values out 
   --     since they are useful internally for debugging the interpreter.
   --     See more notes in the comments for GET_VALUE.
   --
   --   - The flags <k> are a bitmask of UPI flags (the UOPF_* values in
   --     upidef.h), and are a kind of scratchpad indicating what operations
   --     the kernel must do on the cursor.  For example if they include
   --     UOPF_EXE then this is a note indicating that the cursor must be
   --     executed prior to use.  These flags are only valid once a cursor
   --     has been opened - up to that point they will be zero.
   --     Since they already exist in a public header (rdbms/include/upidef.h),
   --     they are not duplicated in DBMS_DEBUG.  
   --     They include the following:
   --        UOPF_PRS  parse
   --        UOPF_EXE  execute
   --        UOPF_FCH  fetch
   --        UOPF_DSL  describe select list
   --        UOPF_DBL  describe bind list
   --        UOPF_BND  bind
   --        UOPF_DFN  define
   --        UOPF_CAN  cancel after fetch
   --        UOPF_FEX  exact fetch
   --        UOPF_OPN  open
   --        UOPF_CLO  close

   cflags_open           CONSTANT BINARY_INTEGER :=     1;
   cflags_found          CONSTANT BINARY_INTEGER :=     2;
   cflags_notfound       CONSTANT BINARY_INTEGER :=     4;
   cflags_uninitialized  CONSTANT BINARY_INTEGER :=    32;
   cflags_recursive      CONSTANT BINARY_INTEGER :=   128;
   cflags_refcur_bind    CONSTANT BINARY_INTEGER :=  1024;
   cflags_dynamic_sql    CONSTANT BINARY_INTEGER :=  2048;
   cflags_first_iter     CONSTANT BINARY_INTEGER :=  4096;
   cflags_dynamic_open   CONSTANT BINARY_INTEGER := 16384;
   

   --------------------------- TIMEOUT OPTIONS ---------------------------
   -- Timeout options for the target session are registered with the
   -- target session by calling set_timeout_behaviour.
   --
   -- retry_on_timeout - Retry.  Timeout has no effect.  This is like
   --    setting the timeout to an infinitely large value.
   --
   -- continue_on_timeout - Continue execution, using same event flags.
   --
   -- nodebug_on_timeout - Turn debug-mode OFF (ie. call debug_off) and
   --    then continue execution.  No more events will be generated
   --    by this target session unless it is reinitialized by calling
   --    debug_on.
   --
   -- abort_on_timeout - Continue execution, using the abort_execution
   --    flag, which should cause the program to abort immediately.  The
   --    session remains in debug-mode.
   --
   retry_on_timeout      CONSTANT BINARY_INTEGER := 0;
   continue_on_timeout   CONSTANT BINARY_INTEGER := 1;
   nodebug_on_timeout    CONSTANT BINARY_INTEGER := 2;
   abort_on_timeout      CONSTANT BINARY_INTEGER := 3;


   ------------------------------
   --  EXCEPTIONS
   illegal_init         EXCEPTION;  -- DEBUG_ON called prior to INITIALIZE

   -- Following 5 are raised by procedure self_check.
   pipe_creation_failure   EXCEPTION;  -- can't create a secure pipe
   pipe_send_failure       EXCEPTION;  -- can't send to the pipe
   pipe_receive_failure    EXCEPTION;  -- can't receive from the pipe
   pipe_datatype_mismatch  EXCEPTION;  -- datatype mismatch in pipe
   pipe_data_error         EXCEPTION;  -- message garbled across pipe
   
   -- Functionality that is no longer supported.  (Some calls in the 
   -- underlying packages are replaced with calls in dbms_debug.)
   desupported             EXCEPTION;

   unimplemented           EXCEPTION;   -- Not yet implemented.
   target_error            EXCEPTION;   -- problem in target session

   no_target_program       EXCEPTION;   -- target is not running

   ------------------------------
   --  PUBLIC VARIABLES

   -- The timeout value (used by both sessions).
   -- The smallest possible timeout is 1 second - if default_timeout is
   -- set to 0 then a large value (3600) will be used.
   --
   default_timeout  BINARY_INTEGER := 3600;  -- 60 minutes

   -- Whether to dump diagnostic output to the tracefile (for debugging
   -- Probe).  Do not reset this value unless instructed by Oracle personnel.
   diagnostic_level  BINARY_INTEGER := 0;
   full_diagnostics  CONSTANT BINARY_INTEGER := 1;


------------------------ COMMON Section -----------------------------
-- These functions/procedures may be called in either the target or
-- debug session.

    -------------------------- PROBE_VERSION -------------------------
    -- Return the version number of DBMS_DEBUG on the server.
    --
    -- PARAMETERS
    --   major - major version number.
    --   minor - minor version number.  Incremented as functionality is added
    --           to DBMS_DEBUG.
    --
    -- Version history:
    --    1.0 was the alpha version of Probe.
    --    2.0 was the first version of DBMS_DEBUG.
    --    2.1 includes get_indexes and the indexed-table versions of 
    --          print_backtrace, show_breakpoints, and show_source.
    --    2.2 contains the 'immediate' version of debug_on, and the
    --         get/set_value package variable fix for AppServer
    --    2.3 execute, plus cflags_* constants
    --    2.4 print_instantiations
    --        target_program_running
    --        get_encoded_pkgvars_for_client
    --        set_timeout_behaviour, get_timeout_behaviour
    --        ping
    --        set_oer_breakpoint, delete_oer_breakpoint, show_breakpoints
    --        added oer to runtime_info and added flag info_getOerInfo
    --        added reason_oer_breakpoint event
    --        added show_frame_source
    --        added frame# support in set_breakpoint
    --
    PROCEDURE probe_version(major out BINARY_INTEGER,
                            minor out BINARY_INTEGER);

    ------------------------------ SELF_CHECK ------------------------------
    -- Perform an internal consistency check.  
    -- If self_check does not return successfully then an incorrect version
    -- of DBMS_DEBUG was probably installed on this server.  The solution
    -- is to install the correct version.
    -- (pbload.sql loads DBMS_DEBUG and the other relevant packages).
    --
    -- Self_check also runs a communications test (to ensure that the Probe
    --   processes will be able to communicate).
    --
    -- PARAMETERS
    --    timeout - Timeout to use for the communication test.  (Default
    --              60 seconds).
    --
    -- Exceptions
    --   OER-6516 - Probe version is inconsistent
    --   pipe_creation_failure  - couldn't create a pipe
    --   pipe_send_failure      - couldn't write data to the pipe
    --   pipe_receive_failure   - couldn't read data from the pipe
    --   pipe_datatype_mismatch - datatype in the pipe was wrong
    --   pipe_data_error        - data got garbled in the pipe
    --
    -- All of these exceptions are FATAL.  They indicate a serious problem
    -- with Probe that will prevent it from working correctly.
    --
    PROCEDURE self_check(timeout IN binary_integer := 60);

    ------------------------------ SET_TIMEOUT ------------------------------
    -- Set the timeout value.
    --
    -- PARAMETERS
    --   timeout - the timeout value to set.  If 0, then uses default_timeout
    --
    -- RETURNS 
    --   the new timeout value.
    --
    FUNCTION set_timeout(timeout BINARY_INTEGER) RETURN BINARY_INTEGER;
   
    ------------------------- SET_DIAGNOSTIC_LEVEL -------------------------
    -- Set diagnostic output to a given level.  Similar to the 'diagnostics'
    -- parameter to initialize() and attach_session.
    -- Diagnostic output goes to the rdbms tracefile.  Ordinarily the
    -- diagnostic level should remain at 0.
    --
    -- PARAMETERS
    --   dlevel - the diagnostic level to switch to
    --
    PROCEDURE set_diagnostic_level(dlevel IN BINARY_INTEGER);

------------------------ TARGET SESSION Section ------------------------
--
-- These functions and procedures are to be executed in the target session
-- (the session that is to be debugged).
--

    ----------------------- INITIALIZE ---------------------------
    -- Initializes the target session by registering a debugID.
    --
    -- PARAMETERS
    --   debug_session_id - A session-id name to identify the target session.
    --                      If null, a unique ID will be generated.
    --   diagnostics      - whether to dump diagnostic output to the tracefile
    --                      0 = no output, 1 = minimal output
    --
    -- RETURNS
    --   the newly-registered debug-session-id (debugID)
    --
    FUNCTION initialize(debug_session_id  IN VARCHAR2       := NULL, 
                        diagnostics       in BINARY_INTEGER := 0)
    RETURN VARCHAR2;

    ----------------------- DEBUG_ON -----------------------------
    -- Mark the target session so that all PL/SQL is executed in
    -- debug mode.  This must be done before any debugging can take 
    -- place.
    -- 
    -- PARAMETERS
    --    no_client_side_plsql_engine - whether this debugging session
    --         is standalone or results from a client-side PL/SQL session.
    --         (Client-side PL/SQL uses different entrypoints into the 
    --         server, and therefore has restricted use of dbms_debug.)
    --    immediate - whether to switch into debug mode immediately, or
    --         to wait until the call has completed.  If TRUE, then a
    --         debug session will be required in order to complete the call.
    --         This parameter was added in Probe V2.2.  
    --
    -- NOTES
    --   If in doubt, use the default parameter values.
    --
    PROCEDURE debug_on(no_client_side_plsql_engine BOOLEAN := TRUE,
                       immediate                   BOOLEAN := FALSE);

    ----------------------- DEBUG_OFF ----------------------------  
    -- Notify the target session that debugging is no longer to take
    -- place in that session.
    -- It is not necessary to call this function before logging the
    -- session off.
    --
    -- NOTES
    --   The server does not handle this entrypoint specially.  Therefore
    --   it will attempt to debug this entrypoint.
    --
    PROCEDURE debug_off;


    --------------------- SET_TIMEOUT_BEHAVIOUR ------------------
    -- Tell Probe what to do with the target session when a timeout
    -- occurs.
    --
    -- VERSION
    --    Probe v2.4
    --
    -- PARAMETERS
    --    behaviour - one of the following (see descriptions above):
    --       retry_on_timeout
    --       continue_on_timeout
    --       nodebug_on_timeout
    --       abort_on_timeout
    --
    -- EXCEPTIONS
    --    unimplemented - the requested behaviour is not recognized
    --
    -- NOTES
    --    The default behaviour (if this procedure is not called)
    --    is continue_on_timeout, since it allows a debugger client
    --    to re-establish control (at the next event) but does not
    --    cause the target session to hang indefinitely.
    --
    PROCEDURE set_timeout_behaviour(behaviour IN PLS_INTEGER);


    --------------------- GET_TIMEOUT_BEHAVIOUR ------------------
    -- Return the current timeout behaviour.
    --
    -- VERSION
    --    Probe v2.4
    --
    FUNCTION get_timeout_behaviour RETURN BINARY_INTEGER;


------------------------- DEBUG SESSION Section -------------------------
--
-- These functions and procedures are to be executed in the debug session
-- only.
--

    ----------------------- ATTACH_SESSION -----------------------  
    -- Notify the debug session about the target program.
    --
    -- PARAMETERS
    --   debug_session_id - the debugID from a call to initialize()
    --   diagnostics      - generate diagnostic output (in the rdbms
    --                      tracefile)? 0 = no output, 1 = minimal output
    --
    PROCEDURE attach_session(debug_session_id  IN VARCHAR2,
                             diagnostics       IN BINARY_INTEGER := 0);


    ------------------------------ SYNCHRONIZE ------------------------------
    -- This function:
    --   1. Waits until the target program signals an event.
    --   2. Calls get_runtime_info
    --
    -- PARAMETERS
    --   run_info -  structure in which to write information about the program
    --             By default this will include information about what program
    --             is executing and at which line execution has paused.
    --   info_requested -  optional bit-field in which to request information
    --           other than the default (which is info_getStackDepth +
    --           info_getLineInfo).  0 means that no information is requested.
    --
    -- RETURNS
    --    success
    --    error_timeout   - timed out before the program started execution
    --    error_communication - other communication error
    --
    FUNCTION synchronize(run_info       OUT  runtime_info,
                         info_requested IN   BINARY_INTEGER := NULL)
    RETURN BINARY_INTEGER;

    -------------------------- SHOW_FRAME_SOURCE ----------------------------
    -- Get frame source. The only time where this really has to be used 
    -- is when backtrace shows anonymous unit is executing at a given
    -- frame position and source is required for viewing and possibly
    -- setting a breakpoint.
    --
    -- If frame number is top of the stack and it's an anonymous block
    -- then show_source can also be used.
    -- 
    -- If it's a stored PLSQL package/function/procedure then use SQL
    -- as described in the comment to show_source below.
    --
    -- PARAMETERS
    --   first_line - line number of first line to fetch.  (PL/SQL programs
    --                always start at line 1, and have no holes.)
    --   last_line  - line number of last line to fetch.  No lines will be
    --                fetched past the end of the program.
    --   source     - the resulting table, indexed by line-number (starting
    --                with first_line).  On error, the table will be empty.
    --   frame_num  - 1-based frame number
    --
    PROCEDURE show_frame_source(first_line  IN     BINARY_INTEGER,
                                last_line   IN     BINARY_INTEGER,
                                source      IN OUT NOCOPY vc2_table,
                                frame_num   IN     BINARY_INTEGER);

    ------------------------------ SHOW_SOURCE ------------------------------
    -- The best way to get the source code (for a program that is being
    -- executed) is to use SQL - ie. select from all_source, using 
    -- the owner, name and line# in the program_info record:
    --
    --    SELECT text INTO <buffer> FROM all_source
    --    WHERE owner = info.Program.Owner
    --      AND name  = info.Program.Name
    --      AND line  = info.Line#;
    --
    -- This wont work for non-persistent programs however (anonymous blocks
    -- and trigger invocation blocks, for example) - in that case you can
    -- call show_source.  There are two flavours - one returns an indexed 
    -- table of source lines and the other returns a packed (and formatted) 
    -- buffer.
    --
    -- PARAMETERS
    --   first_line - line number of first line to fetch.  (PL/SQL programs
    --                always start at line 1, and have no holes.)
    --   last_line  - line number of last line to fetch.  No lines will be
    --                fetched past the end of the program.
    --   source     - the resulting table, indexed by line-number (starting
    --                with first_line).  On error, the table will be empty.
    --
    PROCEDURE show_source(first_line  IN     BINARY_INTEGER,
                          last_line   IN     BINARY_INTEGER,
                          source      IN OUT NOCOPY vc2_table);

    -- VERSION
    --    Probe v2.1
    --
    -- This second overloading of show_source returns the source in a
    -- formatted buffer, complete with line-numbers.  It is faster than
    -- the indexed table version, but it doesn't guarantee to fetch all
    -- the source.
    -- If the source doesn't fit in bufferlength (buflen) then additional
    -- pieces can be retrieved using the 'get_more_source' procedure
    -- ('pieces' will return the additional number of pieces that need to 
    -- be retrieved).
    --
    -- PARAMETERS
    --   first_line  - smallest line-number to print
    --   last_line   - largest line-number to print
    --   window      - 'window' of lines - the number of lines around the
    --                 current source line.
    --   print_arrow - non-zero means to print an arrow before the current line
    --   buffer      - buffer in which to place the source listing
    --   buflen      - length of buffer
    --   pieces      - set to non-zero if not all the source could be placed
    --                 into the given buffer
    --
    PROCEDURE show_source(first_line   IN     BINARY_INTEGER,
                          last_line    IN     BINARY_INTEGER,
                          window       IN     BINARY_INTEGER,
                          print_arrow  IN     BINARY_INTEGER,
                          buffer       IN OUT VARCHAR2,
                          buflen       IN     BINARY_INTEGER,
                          pieces       OUT    BINARY_INTEGER);
  
    ----------------------- GET_MORE_SOURCE -------------------  
    -- When source doesn't fit in buffer provided in the "show_source"
    -- procedure, this procedure provides additional source.
    PROCEDURE get_more_source(buffer          IN OUT VARCHAR2,
                              buflen          IN BINARY_INTEGER,
                              piece#          IN BINARY_INTEGER);


    ---------------------- PRINT_BACKTRACE -------------------
    -- Print a backtrace listing of the current execution stack.
    -- Should only be called if a program is currently executing.
    --
    -- PARAMETERS
    --    listing - A formatted character buffer with embedded newlines
    --
    PROCEDURE print_backtrace(listing IN OUT VARCHAR2);

    -- VERSION
    --    Probe v2.1
    --
    -- PARAMETERS
    --   backtrace - 1-based indexed table of backtrace entries.  The
    --        currently-executing procedure is the last entry in the
    --        table (ie. the frame numbering is the same as that used by
    --        get_value).  Entry 1 is the oldest procedure on the stack.
    --        
    PROCEDURE print_backtrace(backtrace OUT backtrace_table);

    ----------------------- CONTINUE --------------------------  
    -- Continue execution of the target program.
    --
    -- This function:
    --   1. Passes the given breakflags (a mask of the events that are
    --      of interest) to Probe in the target process.
    --   2. Tells Probe to continue execution of the target process.
    --   3. Waits until the target process either runs to completion or
    --      signals an event.
    --   4. If info_requested is not 0 and program has not terminated, 
    --      calls get_runtime_info.
    -- 
    -- PARAMETERS
    --   run_info       - information about the new state of the program
    --   breakflags     - mask of events that are of interest
    --   info_requested - what information should be returned in 'run_info'
    --                    when the program stops.  See 'information flags'
    --                    0 means no information.  Null means default info.
    -- RETURNS
    --    success
    --    error_timeout       - timeout while waiting for target session
    --    error_communication - other communication error
    --
    -- HANDLING TIMEOUTS
    --    If this function returns with a timeout then the target session
    --    either terminated abnormally or is still running.  If it is still
    --    running, and the client wishes to continue waiting for it, then
    --    'synchronize' should be called.
    --
    --    One way to determine whether a session is alive is to use 
    --    dbms_session.is_session_alive, which takes as a parameter the 
    --    uniqueID for the session (which may be obtained via 
    --    dbms_session.unique_session_id).  Note that the uniqueID and 
    --    the debugID are not necessarily the same, for security reasons,
    --    so Probe does not automatically check for target session death
    --    when a timeout occurs.
    --
    FUNCTION continue(run_info       IN OUT runtime_info,
                      breakflags     IN     BINARY_INTEGER,
                      info_requested IN     BINARY_INTEGER := null)
      RETURN BINARY_INTEGER;

    -------------------------- SET_BREAKPOINT ----------------------
    -- Set a breakpoint in a program unit, which persists for the current
    -- session.  Execution will pause if the target program reaches the
    -- breakpoint.
    --
    -- PARAMETERS
    --   program      Information about the program unit in which the 
    --                breakpoint is to be set.  
    --                (In version 2.1 and later, the namespace, name, owner,
    --                 and dblink may be set to NULL, in which case the 
    --                 breakpoint will be placed in the currently-executing 
    --                 program unit.)
    --                (In version 2.4 and later namespace can be set to 
    --                 namespace_none and name to a frame number to set
    --                 a breakpoint in one of the currently executing frames)
    --   line#        The line at which the breakpoint is to be set.
    --   breakpoint#  On successful completion, will contain the unique
    --                breakpoint number by which to refer to the breakpoint.
    --   fuzzy        Only applicable if there is no executable code at
    --                the specified line:
    --                  0 means return error_illegal_line.
    --                  1 means search forward for an adjacent line at which
    --                    to place the breakpoint.
    --                 -1 means search backwards for an adjacent line at
    --                    which to place the breakpoint.
    --   iterations   The number of times to wait before signalling this
    --                breakpoint.
    --
    -- RETURNS
    --   success
    --   error_illegal_line  - can't set a breakpoint at that line
    --   error_bad_handle    - no such program unit exists
    --
    -- RESTRICTIONS/BUGS
    --   'fuzzy' and 'iterations' not yet implemented.
    --
    FUNCTION set_breakpoint(program     IN  program_info,
                            line#       IN  BINARY_INTEGER,
                            breakpoint# OUT BINARY_INTEGER,
                            fuzzy       IN  BINARY_INTEGER := 0,
                            iterations  IN  BINARY_INTEGER := 0)
      RETURN BINARY_INTEGER;
      
    -------------------------- DELETE_BREAKPOINT ----------------------
    -- Deletes a breakpoint.
    --
    -- PARAMETERS
    --   breakpoint - a breakpoint number returned by SET_BREAKPOINT
    --
    -- RETURNS
    --   success
    --   error_no_such_breakpt - no such breakpoint exists
    --   error_idle_breakpt    - breakpoint was already deleted
    --   error_stale_breakpt   - the program unit was redefined since the
    --                           breakpoint was set
    --
    FUNCTION delete_breakpoint(breakpoint IN BINARY_INTEGER)
        RETURN BINARY_INTEGER;


    ------------------------- SET_OER_BREAKPOINT ----------------------
    -- Set a breakpoint on an OER.  The breakpoint persists for the 
    -- session (or until deleted), as with code breakpoints.
    --
    -- VERSION
    --    Probe v2.4
    --
    -- PARAMETERS
    --    oer - the OER (a 4-byte positive number)
    --
    -- RETURNS
    --    success
    --
    -- NOTES
    --   Less functionality is supported on OER breakpoints than on
    --   code breakpoints.  In particular, note that:
    --     1. No 'breakpoint number' is returned - the number of the OER
    --        is used instead.  Thus it is impossible to set duplicate
    --        breakpoints on a given OER (it is a no-op).
    --     2. It is not possible to disable an OER breakpoint (although
    --        clients are free to simulate this by deleting it).
    --     3. OER breakpoints are deleted via delete_oer_breakpoint.
    --
    FUNCTION set_oer_breakpoint(oer IN PLS_INTEGER) RETURN PLS_INTEGER;


    ---------------------- DELETE_OER_BREAKPOINT ----------------------
    -- Delete an OER breakpoint.
    --
    -- VERSION
    --    Probe v2.4
    --
    -- PARAMETERS
    --    oer - the OER (positive 4-byte number) to delete
    --
    -- RETURNS
    --   success
    --   error_no_such_breakpt - no such OER breakpoint exists
    --
    FUNCTION delete_oer_breakpoint(oer IN PLS_INTEGER) RETURN PLS_INTEGER;


    -------------------------- DISABLE_BREAKPOINT ----------------------
    -- With this procedure the breakpoint will still be there, but not be 
    -- active. After disabling the breakpoint needs to be enabled to make it
    -- active
    --
    -- PARAMETERS
    --   breakpoint - a breakpoint number returned by SET_BREAKPOINT
    --
    -- RETURNS
    --   success
    --   error_no_such_breakpt - no such breakpoint exists
    --   error_idle_breakpt    - breakpoint was already deleted
    --   error_stale_breakpt   - the program unit was redefined since the
    --                           breakpoint was set
    --   
    FUNCTION disable_breakpoint(breakpoint IN BINARY_INTEGER)
        RETURN BINARY_INTEGER;

    -------------------------- ENABLE_BREAKPOINT ----------------------
    -- Reverse of disabling. This procedure "activates" an exsiting breakpoint
    --
    -- PARAMETERS
    --   breakpoint - a breakpoint number returned by SET_BREAKPOINT
    --
    -- RETURNS
    --   success
    --   error_no_such_breakpt - no such breakpoint exists
    --   error_idle_breakpt    - breakpoint was already deleted
    --   error_stale_breakpt   - the program unit was redefined since the
    --                           breakpoint was set
    --
    FUNCTION enable_breakpoint(breakpoint IN BINARY_INTEGER)
        RETURN BINARY_INTEGER;

    -------------------------- SHOW_BREAKPOINTS ----------------------
    -- Return a listing of the current breakpoints.
    --
    -- PARAMETERS
    --  listing - a formatted buffer (including newlines) of the breakpoints
    PROCEDURE show_breakpoints(listing    IN OUT VARCHAR2);

    -- VERSION
    --    Probe v2.1
    --
    -- PARAMETERS
    --   listing - indexed table of breakpoint entries.  The
    --       breakpoint number is indicated by the index into the table.
    --       Breakpoint numbers start at 1 and are reused when deleted.
    --
    PROCEDURE show_breakpoints(listing  OUT breakpoint_table);


    -- VERSION
    --    Probe v2.4
    --
    -- PARAMETERS
    --   code_breakpoints - indexed table of breakpoint entries, indexed
    --                      by breakpoint number (starting at 1).
    --   oer_breakpoints - indexed table of OER breakpoints, indexed by
    --                     OER.
    --
    PROCEDURE show_breakpoints(code_breakpoints OUT breakpoint_table,
                               oer_breakpoints  OUT oer_table);


    ------------------------------- GET_VALUE -------------------------------
    -- Get a value from the currently-executing program.
    --
    -- PARAMETERS
    --  variable_name  the name of the variable or parameter
    --  frame#         the frame in which it lives (0 means the current 
    --                   procedure)
    --  scalar_value   its value
    --  format         an optional date format to use, if meaningful.
    --
    -- RETURNS
    --   success
    --   error_bogus_frame    - frame# does not exist
    --   error_no_debug_info  - entrypoint has no debug information
    --   error_no_such_object - variable_name does not exist in frame#
    --   error_unknown_type   - the type information in the debug information
    --                          is illegible
    --   error_nullvalue      - value is null
    --
    -- NOTES
    --   If the variable is a cursor, then a special string value is returned,
    --   which the caller is expected to parse.  See the comments at the
    --   'Cursor flags' section above.
    --
    -- BUGS
    --   - There are situations when the cursor flags may appear to be 
    --     incorrect: one common case is recursive cursors (ie. a procedure 
    --     containing a cursor, where the procedure calls itself recursively).
    --     On return from the recursive call the cursor flags are *not* 
    --     restored, even though the interpreter behaves correctly.  
    --     The difficulty is that both PL/SQL and the kernel maintain their
    --     own cursor-caches, and it is difficult for Probe to follow the 
    --     mapping in these situations.  
    --     This will be fixed in a later release.
    --
    FUNCTION get_value(variable_name  IN  VARCHAR2,
                       frame#         IN  BINARY_INTEGER,
                       scalar_value   OUT VARCHAR2,
                       format         IN  VARCHAR2 := NULL)
       RETURN BINARY_INTEGER;

    --
    -- This form of get_value is for fetching package variables.
    -- Instead of a frame#, it takes a handle, which describes the package
    -- containing the variable.
    --
    -- VERSION
    --    Probe v2.2
    --
    -- PARAMETERS
    --    (See description above for the other parameters.)
    --    handle -  package description.  The 'Name,' 'Owner,' and Namespace 
    --              fields  must be initialized appopriately.
    --
    -- RETURNS
    --   error_no_such_object if:
    --       1. the package does not exist
    --       2. the package is not instantiated
    --       3. the user does not have privileges to debug the package
    --       4. the object does not exist in the package
    --
    -- EXAMPLE
    --   Given a package PACK in schema SCOTT, containing variable VAR,
    --   do the following to get its value:
    --
    --   DECLARE
    --      handle     dbms_debug.program_info;
    --      resultbuf  VARCHAR2(500);
    --   BEGIN
    --      handle.Owner := 'SCOTT';
    --      handle.Name  := 'PACK';
    --      handle.namespace := dbms_debug.namespace_pkgspec_or_toplevel;
    --      retval := dbms_debug.get_value('VAR', handle, resultbuf, NULL);
    --   END;
    --
    FUNCTION get_value(variable_name  IN  VARCHAR2,
                       handle         IN  program_info,
                       scalar_value   OUT VARCHAR2,
                       format         IN  VARCHAR2 := NULL)
       RETURN BINARY_INTEGER;

    -------------------------- SET_VALUE ----------------------------
    -- Set a value in the currently-executing program.
    --
    -- PARAMETERS
    --   frame#  -   the frame in which the value is to be set (0 means the
    --               currently executing frame.
    --   assignment_statement - an assignment statement (which must be legal
    --                         PL/SQL) to execute in order to set the value.
    --                         For example, 'x := 3;'
    --                         Note that only scalar values are supported in
    --                         this release - the right hand side of the
    --                         assignment statement must be a scalar.
    --
    -- RETURNS
    --   success
    --   error_illegal_value   - constraint violation
    --   error_illegal_null    - constraint violation (object is 'not null')
    --   error_value_malformed - value is not a scalar
    --   error_name_incomplete - the assignment statement does not resolve to
    --                           a scalar.  For example 'x := 3;', if x is
    --                           a record.
    --   error_other
    --
    FUNCTION set_value(frame#               IN binary_integer,
                       assignment_statement IN varchar2) 
    RETURN BINARY_INTEGER;

    -- This form sets the value of a package variable.
    --
    -- VERSION
    --    Probe v2.2
    --
    -- RETURNS
    --   error_no_such_object if:
    --       1. the package does not exist
    --       2. the package is not instantiated
    --       3. the user does not have privileges to debug the package
    --       4. the object does not exist in the package
    --
    -- In some cases the PL/SQL compiler uses temporaries to access package
    -- variables, and Probe does not guarantee to update such temporaries.
    -- So the possibility exists (although it is unlikely) for the user to
    -- update a package variable and the new value not 'take effect' for a
    -- line or two.
    --
    -- EXAMPLE
    --   To set the value of SCOTT.PACK.var to 6:
    --
    --   DECLARE
    --      handle  dbms_debug.program_info;
    --   BEGIN
    --      handle.Owner := 'SCOTT';
    --      handle.Name  := 'PACK';
    --      handle.namespace := dbms_debug.namespace_pkgspec_or_toplevel;
    --      retval := dbms_debug.set_value(handle, 'var := 6;');
    --   END;
    --
    FUNCTION set_value(handle               IN program_info,
                       assignment_statement IN varchar2) 
    RETURN BINARY_INTEGER;

    -------------------------------- ABORT --------------------------------
    -- Abort the currently-executing program.
    --
    -- NOT YET SUPPORTED.  To abort a program call 'continue' with
    --   execution flags 'abort_execution'.
    --
    FUNCTION abort return BINARY_INTEGER;

    -------------------------- DETACH_SESSION ----------------------
    -- Detach from the currently attached session - ie. stop debugging
    -- the target program.  This procedure may be called at any time,
    -- but it does not notify the target session that the debug session
    -- is detaching itself, and it does not abort execution of the target
    -- session.  Therefore care should be taken to ensure that the target
    -- session does not hang itself.
    --
    PROCEDURE detach_session;
  
    --------------------------- GET_RUNTIME_INFO ---------------------------
    -- This function returns information about the current program.  It is
    -- only needed if the 'info_requested' parameter to synchronize or
    -- continue was set to 0.
    --
    -- Currently only used by client-side PL/SQL.
    --
    -- PARAMETERS
    --   info_requested - bitmask of the information to fetch.  0 means nothing,
    --                    null means 'default information.'
    --   run_info - location in which to stash the requested information.
    --
    -- RETURNS
    --   success
    --   error_timeout       - pipe timed out
    --   error_communication - other communication error
    --
    FUNCTION get_runtime_info(info_requested  IN  BINARY_INTEGER,
                              run_info        OUT runtime_info)
      return BINARY_INTEGER;

    ------------------------------ GET_INDEXES ------------------------------
    -- Given a name (of a variable or parameter), return the set of its
    -- indexes if it is an indexed table.  Error if it is not an indexed
    -- table.
    --
    -- VERSION
    --    Probe v2.1
    --
    -- PARAMETERS
    --   varname - name of the variable to get index information about
    --   frame#  - number of frame in which the variable/parameter resides.
    --             Pass in NULL if you want a package variable.
    --   handle  - package description (if object is a package variable)
    --   entries - 1-based table of the indexes.  If non-null, then
    --             entries(1) contains the first index of the table, 
    --             entries(2) contains the second index, etc.
    --
    -- RETURNS
    --   error_no_such_object if varname is not an indexed table.
    --
    FUNCTION get_indexes(
        varname   IN  VARCHAR2,
        frame#    IN  BINARY_INTEGER,
        handle    IN  program_info,
        entries   OUT index_table
        ) RETURN BINARY_INTEGER;

    --------------------- GET_ENCODED_STACK_FOR_CLIENT ---------------------
    --
    -- ***********************************************************************
    -- ** This function is only usable if the caller is client-side PL/SQL. **
    -- ** If you do not have client-side PL/SQL then you cannot use it.     **
    -- ***********************************************************************
    --
    -- Return an encoded form of one or more stack frames.  Only useful if
    -- the caller is client-side PL/SQL, since the decoder is built into the
    -- PL/SQL engine.
    --
    -- PARAMETERS
    --   start_frame
    --   frame_count       - number of frames to fetch
    --   flags             - currently unused
    --   max_string_length - truncate strings at this value (NYI)
    --   max_index_values  - only fetch this many index table elements (NYI)
    --   pbrun_version     - client version
    --   tidl_buf          - buffer in which to place encoded TIDL
    --   tidl_version      - version-number of the generated TIDL
    --
    PROCEDURE get_encoded_stack_for_client(
         start_frame       IN     BINARY_INTEGER,
         frame_count       IN     BINARY_INTEGER,
         flags             IN     BINARY_INTEGER,
         max_string_length IN     BINARY_INTEGER,
         max_index_values  IN     BINARY_INTEGER,
         pbrun_version     IN     BINARY_INTEGER,
         tidl_buf          IN OUT VARCHAR2,
         tidl_version         OUT BINARY_INTEGER
         );

    -- VERSION
    --    Probe v2.4
    --
    -- Get_encoded_pkgvars_for_client is similar to the previous
    -- procedure, but with the following additional parameters:
    --   handle  - description of package
    --   status  - error-code, in case package doesn't exist, doesn't
    --             contain debug info, or hasn't been instantiated
    --
    PROCEDURE get_encoded_pkgvars_for_client(
         handle            IN     program_info,
         flags             IN     BINARY_INTEGER,
         pbrun_version     IN     BINARY_INTEGER,
         status            IN OUT BINARY_INTEGER,
         tidl_buf          IN OUT VARCHAR2,
         tidl_version         OUT BINARY_INTEGER
         );


    ---------------------------- EXECUTE ------------------------------
    -- Execute some SQL or PL/SQL code in target session.  Program is 
    -- assumed to be suspended in the target session awaiting commands.
    --
    -- VERSION
    --    Probe v2.3
    --
    -- PARAMETERS
    --   what    - the SQL or PL/SQL source to execute
    --   frame#  - the context in which to execute it.  
    --             Only -1 (global context) is supported at this time.
    --   bind_results - whether the source wants to bind results (0=no, 1=yes).
    --             Binding is to 'results' (see next parameter), and is done
    --             only once.
    --   results - a collection where output may be placed (see bind_results).
    --   errm    - error message, if an error occurred.  Otherwise null.
    --
    -- EXCEPTIONS
    --    unimplemented   - frame# other than -1
    --    target_error    - a communication problem of some kind
    --
    -- RESTRICTIONS
    --   1. User's code ('what') must allocate space in 'results' (ie. call
    --      results.EXTEND) either implicitly or explicitly prior to use.
    --   2. Rows in 'results' are expected to be adjacent - 'what' should not
    --      delete interior rows.
    --   3. User's code runs with the privileges of the current user (in the
    --      program that is suspended), and name-resolution is done in the
    --      context of that user.
    --   4. If 'bind_results' is 1, then 'results' will always be a non-null
    --      collection on successful termination.  This is true even if 'what'
    --      nulls it out.
    --
    -- SAMPLE USE:
    --   1. SQL:
    --      DECLARE
    --         coll sys.dbms_debug_vc2coll; -- results (unused)
    --         errm VARCHAR2(100);          
    --      BEGIN
    --         dbms_debug.execute('insert into emp(ename,empno,deptno) ' ||
    --                            'values(''LJE'', 1, 1)',
    --                            -1, 0, coll, errm);
    --         IF (errm IS NOT NULL) THEN
    --            :oops := errm;
    --         END IF;
    --      END;
    --
    --      Note that there is NO SEMI-COLON at the end of the insert statement.
    --      Otherwise the kernel will return ORA-00911 (invalid character).
    --
    --   2. PL/SQL (with autonomous transaction):
    --      DECLARE
    --         coll sys.dbms_debug_vc2coll;  -- results (unused)
    --         errm VARCHAR2(100);
    --      BEGIN
    --         dbms_debug.execute(
    --            'DECLARE PRAGMA autonomous_transaction; ' ||
    --             'BEGIN ' ||
    --             '   insert into emp(ename, empno, deptno) ' ||
    --             '   values(''LJE'', 1, 1); ' ||
    --             '   COMMIT; ' ||
    --             'END;',
    --             -1, 0, coll, errm);
    --      END;
    --
    --   3. PL/SQL (with results)
    --      DECLARE
    --         my_vc2coll sys.dbms_debug_vc2coll;
    --         errm       VARCHAR2(100);
    --         each       PLS_INTEGER;
    --      BEGIN
    --         dbms_debug.execute(
    --            'DECLARE ' ||
    --            '   vc  SYS.dbms_debug_vc2coll := SYS.dbms_debug_vc2coll();'||
    --            '   len PLS_INTEGER; ' ||
    --            '   i   PLS_INTEGER := 1; ' ||
    --            'BEGIN ' ||
    --            '   SELECT COUNT(*) INTO len FROM emp; ' ||
    --            '   vc.EXTEND(len * 6); ' ||
    --            '   FOR c IN (SELECT * FROM emp) LOOP ' ||
    --            '      vc(i) := ''Ename: '' || c.ename; i := i+1; ' ||
    --            '      vc(i) := ''Empno: '' || c.empno; i := i+1; ' ||
    --            '      vc(i) := ''Job:   '' || c.job;   i := i+1; ' ||
    --            '      vc(i) := ''Mgr:   '' || c.mgr;   i := i+1; ' ||
    --            '      vc(i) := ''Sal:   '' || c.sal;   i := i+1; ' ||
    --            '      vc(i) := null;                   i := i+1; ' ||
    --            '   END LOOP; ' ||
    --            '   :1 := vc;' ||
    --            'END;',
    --             -1, 1, my_vc2coll, errm);
    --         IF (errm IS NOT NULL) THEN
    --            :oops := errm;
    --         END IF;
    --         each := my_vc2coll.FIRST;
    --         WHILE (each IS NOT NULL) LOOP
    --            dosomething(my_vc2coll(each));
    --            each := myvc2_coll.NEXT(each);
    --         END LOOP;
    --      END;
    --
    PROCEDURE execute(what         IN VARCHAR2,
                      frame#       IN BINARY_INTEGER,
                      bind_results IN BINARY_INTEGER,
                      results      IN OUT NOCOPY dbms_debug_vc2coll,
                      errm         IN OUT NOCOPY VARCHAR2);


    ------------------------ TARGET_PROGRAM_RUNNING ------------------------
    -- Return TRUE if the target session is currently executing a stored
    -- procedure, or FALSE if it is not.
    --
    -- VERSION
    --    Probe v2.4
    --
    FUNCTION target_program_running RETURN BOOLEAN;


    ------------------------- PRINT_INSTANTIATIONS -------------------------
    -- Return a listing of the packages that have been instantiated in the
    -- current session.
    --
    -- VERSION
    --    Probe v2.4
    --
    -- PARAMETERS
    --   pkgs  - the instantiated packages (OUT)
    --   flags - bitmask of options:
    --            1 - show specs
    --            2 - show bodies
    --            4 - show local instantiations
    --            8 - show remote instantiations (NYI)
    --           16 - do a fast job (dont test to see if debug info exists or
    --                whether the libunit is shrink-wrapped)
    --
    -- EXCEPTIONS
    --   no_target_program - target session is not currently executing
    --
    -- NOTES
    --   On return, pkgs contains a program_info for each instantiation.
    --   The valid fields are Namespace, Name, Owner, and LibunitType.
    --   In addition, Line# contains a bitmask of:
    --     1 - the libunit contains debug info
    --     2 - the libunit is shrink-wrapped
    --
    PROCEDURE print_instantiations(pkgs  IN OUT NOCOPY backtrace_table,
                                   flags IN BINARY_INTEGER);


    ------------------------------- PING ---------------------------------
    -- Ping the target session, to prevent it from timing out.  This
    -- procedure is intended for use when execution is suspended in the
    -- target session (for example at a breakpoint).
    --
    -- If the timeout_behaviour is set to retry_on_timeout then this
    -- procedure is not strictly necessary.  
    --
    -- VERSION
    --    Probe v2.4
    --
    -- EXCEPTIONS
    --   no_target_program will be raised if there is no target program
    --      or if the target session is not currently waiting for input
    --      from the debug session.
    --
    PROCEDURE ping;

END DBMS_DEBUG;
/
Rem show errors


grant execute on DBMS_DEBUG to public;
drop public synonym DBMS_DEBUG;
create public synonym DBMS_DEBUG for sys.DBMS_DEBUG;

