Go to main content
Oracle® Developer Studio 12.6: Debugging a Program with dbx

Exit Print View

Updated: June 2017
 
 

Using Pretty-Printing

Pretty-printing enables your program to provide its own rendition of an expression's value through a function call. dbx supports two mechanisms for pretty-printing : call-based pretty-printing and filter-based pretty-printing. The older, call-based mechanism works by calling functions defined in the debuggee, which conform to a certain pattern. The current version of dbx now supports Python-based filters, allowing the user to create filters that transform values from one form to another.

dbx determines which mechanism to use with the dbxenv variable output_pretty_print_mode. If set to call, call-based pretty-printers are sought. If set to filter, Python-based pretty-printers are sought. If set to filter_unless_call, call-based pretty-printers take precedence over filters.

Pretty-printers, regardless of type,are invoked if you specify the –p option to the print command, rprint command, display command, or watch command. For more about invocation of pretty-printers, see Invoking Pretty-Printing.

If the dbxenv variable output_pretty_print is set to on, –p is passed to the print command, rprint command, or display command as the default. Use +p to override this behavior. In addition, output_pretty_print controls pretty-printing for IDE locals, balloon evaluation, and watches.

Invoking Pretty-Printing

Pretty-print functions are invoked for the following:

  • print –p or if the dbxenv variable output_pretty_print is set to on.

  • display –p or if the dbxenv variable output_pretty_print is set to on.

  • watch –p or if the dbxenv variable output_pretty_print is set to on.

  • Balloon evaluation if the dbxenv variable output_pretty_print is set to on.

  • Local variable if the dbxenv variable output_pretty_print is set to on.

Pretty-print functions are not invoked for the following:

  • $[]. $[] is intended to be used in scripts, therefore the scripts should be predictable.

  • The dump command. dump uses the same simplified formatting as the where command, which might be converted to use pretty-printing in later releases. This limitation does not apply to the Local Variables window in the IDE.

Call-Based Pretty-Printing

Call-based pretty-printing enables an application to provide its own rendition of an expression's value through a function call. If you specify the –p option to the print command, rprint command, display command, or watch command, dbx searches for a function of the form const chars *db_pretty_print(const T *, int flags, const char *fmt) and calls it, substituting the returned value for print or display.

The value passed in the flags argument of the function is bit-wise or one of the following:

FVERBOSE
0x1
Not currently implemented, always set
FDYNAMIC
0x2
-d
FRECURSE
0x4
-r
FFORMAT
0x8
-f (if set, fmt is the format part)
FLITERAL
0x10
-l

The db_pretty_print() function can be either a static member function or a standalone function.

    When pretty-printing, also consider the following information:

  • Possible Failures

  • Pretty-Printing Function Considerations

  • Prior to dbx version 8.0 pretty-printing was based on a ksh implementation of prettyprint. While this ksh function (and its pre-defined alias pp) still exist, most of the semantics have been reimplemented inside dbx with the following results:

    • For the IDE, watches, local variables, and balloon evaluation can use pretty-printing.

    • In the print command, display command, and watch command, the –p option uses the native route.

    • Better scalability, especially now that pretty-printing can be called quite often, especially for watches and local variables.

    • Better opportunity to derive addresses from expressions.

    • Better error recovery.

  • Nested values will not be pretty-printed because dbx does not have the infrastructure to calculate the addresses of nested fields.

  • The dbxenv variable output_pretty_print_fallback is set by default to on, which means that dbx will fall back on regular formatting if pretty-printing fails. If pretty-printing fails while i the environment variable is set to off, dbx will still issue an error message.

Pretty-Printing Function Considerations

When using the pretty-printing functions, you will need to consider the following:

  • For const/volatile unqualified types, in general, functions such as db_pretty_print(int *, ...) and db_pretty_print(const int *, ...) are considered distinct. The overload resolution approach of dbx is discerning but non-enforcing:

    • Discerning – If you have defined variables declared both int and const int, each will be routed to the appropriate function.

    • Non-enforcing – If you have only one int or const int variable defined, they will match with both functions. This behavior is not specific to pretty-printing and applies to any calls.

  • The db_pretty_print() function must be compiled with the –g option because dbx needs access to parameter signatures.

  • The db_pretty_print() function is allowed to return NULL.

  • The main pointer passed to the db_pretty_print() function is guaranteed to be non-NULL but otherwise it might still point to a poorly initialized object.

  • The db_pretty_print() function needs to be disambiguated based on the type of its first parameter. In C, you can overload functions by writing them as file statics.

Possible Failures

Pretty-printing might fail for one of these detectable and recoverable reasons:

  • No pretty-print function found.

  • The expression to be pretty-printed cannot have its address taken.

  • The function call did not immediately return, which would imply a segmentation fault resulting when the pretty-print function is not robust when encountering bad objects. It could also imply a user breakpoint.

  • The pretty-print function returned NULL.

  • The pretty-print function returned a pointer that dbx fails to indirect through.

  • A core file is being debugged.

For all cases except the function call not immediately returning, these failures are silent and dbx falls back on regular formatting. But if the output_pretty_print_fallback dbxenv variable is set to off, dbx will issue an error message if pretty-printing fails.

If you use the print –p command rather than setting the dbxenv variable output_pretty_print to on, dbx stops in the broken function to enable you to diagnose the cause of failure. You can then use the pop –c command to clean up the call.

Python Pretty-Print Filters

The pretty-printing filter feature enables you to write filters in Python which can transform a Value from one form to another.


Note -  Python pretty-print filters can only be used in C and C++ code, not Fortran.

Filters are built in for select classes in 4 implementations of the C++ Standard Template Library. The following table specifies the library name and the compiler option for that library:

Compiler option for Library
Library Name
–library=Cstd (default)
libCstd.so.1
–library=stlport4
libstlport.so.1
–library=stdcxx4
libstdcxx4.so.4.**
–library=stdcpp (default when using the –std=c++11 option)
libstdc++.so.6.*

The following table specifies which classes the pretty-print filters can be used for in the C++ Standard Template Library and whether index and slice can be printed:

Classes
Index and Slice Availability
C++ Compatibility
string
No
Yes
pair
No
Yes
vector
Yes
Yes
list
Yes
Yes
set
Yes
Yes
bitset
Yes
Yes
map
Yes
Yes
stack
Yes
Yes
priority queue
Yes
Yes
queue
Yes
Yes
multimap
Yes
Yes
tuple
No
C++11 only
unique_ptr
No
C++11 only
forward_list
Yes
C++11 only
unordered_map
Yes
C++11 only
unordered_multimap
Yes
C++11 only
unordered_set
Yes
C++11 only
unordered_multiset
Yes
C++11 only
array
Yes
C++11 only
initializer_list
Yes
C++11 only
Example 1  Pretty-Printing with Filters

The following output is an example of printing a list using the print command in dbx:

(dbx) dbxenv output_pretty_print off
(dbx) print list10
list10 = {
   __buffer-size = 32U       
   __buffer-list = {
     __data_ = 0x654a8
   }
   __free-list   = (nil)
   __next-avail  = 0x67334
   __last     = 0x67448
   __node     = 0x48830
   __length   = 10U
   }

The following is the same list printed in dbx, but using pretty-printing filters:

(dbx) print -p list10
list10 = (200, 201, 202, 203, 204, 205, 206, 207, 208, 209)

(dbx) print -p list10[5]
list10[5] = 205

(dbx) print -p list10[1..100:2]
list10[1..100:2] =
[1] = 202
[3] = 204
[5] = 206
[7] = 208

Using Python

Python pretty-print filters and the python command is available on Oracle Solaris, Oracle Linux 6 for 32-bit and 64 bit applications using Python 2.6, and Oracle Linux 7 for 64-bit applications using Python 2.7. For more information on pretty-printing and Python with dbx, see dbx Limitations and Incompatibilities in Oracle Developer Studio 12.6: Release Notes.

To start the built-in Python interpreter, type python. To evaluate your Python code, type python python-code. A nascent Python plugin API is available. However, its primary purpose is writing pretty-printer filters that get invoked as callbacks. Therefore the python command mainly serves testing and diagnostic purposes.

Python Pretty-Print API Documentation

To generate the Python pretty-print API documentation, use the python-docs command. For more information, see the python-docs topic in the help.