Summary of the cbl-gdb debugging commands
December 18, 2021
At the present time, development on the package has outstripped the documentation. We are working on updated documentation information, but it’s a work in progress. So, only a few commands are listed here.
When the debugging package launches, it presents this list of command
help <command> information is available.
Right now those help commands are your best source of information.
cprint cwatch cbreak ctbreak ccondition add-symbol-file-cobol cstart cnext cup cup-silently cdown cdown-silently cfinish finish-out-of-line-perform finish-module until-cobol list-section local-backtrace cbacktrace auto-step
Help is available for all of those command inside GDB. Issue, for
help cprint to see that information.
Possibly the simplest command, and in some ways the most convenient,
CStart command. When issued, it launches execution
of the program from the very beginning, and automatically stops
execution at the first COBOL instruction.
It can optionally take parameters. If there are any, those parameters are passed to the executable as if they had been issued on the command line for the executable.
Users familiar with GDB know the difference between the
next commands. When the next
instruction to be executed is a function call,
execution to proceed into the function, while
causes execution to pass over the function. That is: the
function is called, and execution stops at the instruction after the
COBOL, however, has a feature that has no parallel in C/C++. COBOL
has the concept of paragraphs, and the COBOL instruction
PERFORM <paragraph> causes
<paragraph> to be executed in a manner very much like
a C function is executed. But paragraphs are not implemented as
subroutines, and consequently the native GDB
can’t pass over the invocation; either
next will take you to the first instruction of
Which is why we created the
cnext command. It detects
that the instruction about to be executed is a PERFORM, and sets a
temporary breakpoint so that the entire paragraph is invoked and the
execution stops at the statement after the PERFORM.
cnext can take a parameter:
cnext 5 will
cnext instructions to be issued.
cwatch <var> -- sets a watchpoint on <var> -- execution halts when the value of <var> changes
cbreak command is currently under development. The
basic construction is
cbreak nnn if a == b
which means, “Every time we arrive at line
nnn, check to
a == b and, if so, stop execution.
help cbreak at the GDB command line to see the
help cprint at the GDB command line to see the
See also the discussion in the Walkthrough
When a debuggable COBOL program has been launched by GDB and
execution has been stopped, the
cprint command is used to
access COBOL variables by name.
Because GDB allows trailing characters of commands to be omitted (as
long as the resulting abbreviated command is unambiguous),
cp is the same as
Considerable flexibility is provided for finding variables within the context of the heirarchical description of COBOL variables.
10 USER. 20 NAME. 30 FIRST PIC X(20). 30 LAST PIC X(20). 10 AGENT. 20 NAME. 30 FIRST PIC X(20). 30 LAST PIC X(20).
cprint first will report that there are two
Tell the debugger that you want to see both of them by tacking an
exclamation point on with
cprint first! (We chose that
because it can be convenient: after being told there are N
possibilities, most Linux systems will let you press up-arrow to bring
back the previous command, at which point you can press ‘!’ and Enter to
1 : 30 FIRST/NAME/USER/program-id : "first name" 2 : 30 FIRST/NAME/AGENT/program-id : "first name"
Once this list has been shown to you, you can reference one of the results by number:
cprint #1 shows you
30 FIRST/NAME/USER/program-id : "first name"
You can also use COBOL-like references:
cprint 1 cprint first of user cprint first in user cprint first/user (deprecated) cprint first.user (deprecated)
Those all result in the same output:
30 FIRST/NAME/USER/program-id : "first name"
cprint command is also used for altering variables.
cprint 1 = "newval" cprint first of user = "newval" cprint first in user = "newval" cprint first/user = "newval" cprint first.user = "newval"
are all equivalent, They all result in
30 FIRST/NAME/USER/program-id : "newval"
The right-hand-side, as shown here, can be a literal. It can also be another COBOL variable.
There are some environment variables that control how the Python extension loads:
CPRINT_R=N -- Changes default "p ?" to +/- N CPRINT_V=[0|1|2] -- Changes default /v formatting to v0, v1, or v2