gldb-gui — graphical OpenGL debugger
gldb-gui
your-program
[argument
...]
The command above will start gldb-gui, but will not start your program. To do that, use → . Your program will automatically stop if it generates an OpenGL error. You can also stop it manually by selecting → (Ctrl+Break). See the section called “Setting breakpoints” for information on stopping your program when it calls particular OpenGL functions. You can continue your program with → (Ctrl+F9), continue until the next OpenGL function call with → (F8), or kill it with → (Ctrl+F2).
Your program can only be stopped or killed when it calls an OpenGL function. If your program updates its display only when necessary, it may not stop immediately. You can often force it an update by placing another window over your program and then removing it again.
The interface is separated into a number of tabs. You can browse
them at any time, but the information will only be up-to-date when
your program is stopped. When your program is running, the status
bar will contain the text
Running
.
The initial tab is the State tab. It shows all OpenGL state that is textual rather than an image. The state is organised roughly more or less according to the state tables in the OpenGL specification. OpenGL has an overwhelming amount of state, so some tools are provided to make it easier to find answers:
To find a specific state, press Ctrl+F. This opens a text entry box where you can type in the name of the state.
To show only the states that changed since the last time the program was stopped, check the Show only modified checkbox. These states are also shown in bold.
To track only a small set of states, check the checkboxes next to those states, then check the Show only selected checkbox.
To save all the states to an XML file, click the
button.The Buffers tab shows OpenGL buffers (vertex buffer objects). The Buffer combobox allows a buffer to be selected. By default, the buffer is decoded as a sequence of unsigned bytes, but a format specification can be filled in below the combobox to control the decoding. It works best when the entire buffer contains repetitions of repetitions of a single structure format.
Suppose that the buffer contains a sequence of vertices, each
consisting of a 3 GLfloats for the position, 3 unsigned bytes
for a colour, and a byte of padding to make the stride 16
bytes. Then fill in the format field with
fffbbb_
or more compactly,
3f3b_
. A description of the available
letters for specifying types appears below the entry box.
The Textures tab shows OpenGL textures. The Texture combobox allows a texture to be selected, with the currently bound texture of each type shown in bold. For cubemap textures, the Face combobox allows one of the sides to be examined in detail; the default is to show two views of the cube itself. For 3D textures, a slice may be selected with the Z combobox.
The apparent size of the texture is controlled through the
Zoom combobox. Fit
makes the texture as large as possible while still fitting the
window. The other settings set a ratio between texels and
screen pixels. The toolbar also has buttons to
zoom in,
zoom out, set a
1:1 ratio, or
fit to the window size.
The appearance of the texture may be controlled with the Mag filter and Min filter comboboxes. These settings correspond to the GL_TEXTURE_MAG_FILTER and GL_TEXTURE_MIN_FILTER in OpenGL. However, these settings are only used for displaying the texture, and do not affect your program. The Level combobox makes it possible to examine specific texture levels. The default (Auto) uses mipmapping as defined by Min filter.
In some cases, there may not be enough contrast in the
texture to see any details (this is particularly true of
textures that encode non-graphical information, such as lookup
tables). Checking Remap range will scale
the colour range up (or down) to cover the whole [0, 1] range.
To perform more detailed image analysis, use the
button to
copy the texture to the clipboard, and paste it into an
external application such as the GIMP.
The copy feature is only available when compiled with GTK+ 2.6 or later.
Framebuffers may be viewed in much the same way as textures
(see the section called “Examining textures”). The
Framebuffer may be set to either the
current window-system framebuffer, or to a framebuffer
created with glCreateFramebufferEXT
.
Pbuffers that are no the current drawable are not supported.
Within a framebuffer, Buffer may be set to the front buffer, back buffer, depth buffer, stencil buffer or an auxiliary buffer, depending on which buffers actually exist.
The Breakpoints allows breakpoints to be set on specific OpenGL functions. Immediately before calling the function, your program will be stopped and the status bar will indicate which function caused the breakpoint.
Click Enabled checkbox for the function, and select it again later.
to set a new breakpoint, and enter the name of the function into the dialog box that appears. To remove a function from the list, click . If you are likely to want to break on that function later, it is easier to deselect theKeep in mind that a function may have multiple aliases (for
example, glBeginQuery
and
glBeginQueryARB
), and you need to select
the right one.
By default, gldb-gui will stop when a function generates an OpenGL error. This can be disabled by deselecting Break on errors. Note that function breakpoints occur before the function is called, but errors occur afterwards, so gldb-gui may stop twice for the same function.
When your program is stopped, the Backtrace
tab shows the current call stack of your program, as
gdb would. The first few frames (usually those
up to run_filters
) will be internal to
bugle.
To further examine the state of your program, select
xterm and
gdb installed, this will open a terminal window
running gdb, already attached to your program.
Once you have finished, you may either quit gdb
and detach it from your program, or keep it open and
continue
in gdb.
Your program needs to be running from the point of view of gdb for gldb-gui to function correctly.
Debugging on a single machine is not always practical, because the target application may run full-screen, or take over the keyboard or mouse.
Several options exist to use gldb-gui on a separate machine to the target application. However, all of them require trust between the two machines involved as the debugging protocol is not error-checked and so it would be easy for either a rogue target to attack gldb-gui or vice versa.
Regardless of the method used, the GL implementation running the debugger must in some respects be at least as capable as the display running the target application. Specifically, any texture that you view is loaded into an equivalent texture in the debugger, and so the texture target and dimensions must be supported there. Note that even if bugle was built for OpenGL ES, the debugger will use OpenGL.
The easiest and most robust option is to rely on the networking
in the X Windowing System. From the machine containing the
target, start gldb-gui with a suitable
DISPLAY
to place the GUI on a remote machine.
Then go to
→ and set the display to the local machine
(usually :0.0).
Although X11 can directly connect to a remote display over the
network, this is not an encrypted connection and may not be
secure. SSH has an X-forwarding option (-x
),
but with the default setting it does not forward GLX and so it
will not work if you have compiled gldb-gui with OpenGL
support. However, the -Y
forwards the
connection as trusted, and in this mode
GLX is supported. Please see security(7) to understand the
security implications of this before you proceed.
The same setup as above may be used in reverse: the target runs on a remote display, while gldb-gui runs on the local display. The disadvantage of this is that the application is now using indirect rendering, which may affect its performance as well as its behaviour.
This scenario is experimental and fragile. The debugger and target execute on separate machines, and communicate over SSH rather than through a local pipe. Because the debugger protocol was not designed for networking, this currently places severe restrictions on the machines used:
They must use the same byte representations for types. In particular, they must have the same endianness, and it may be necessary for them to have the same word size.
Any types used on the target must also be known
to the debugger. Ideally, one should use the same
version of bugle, compiled with the same compiler and
the same OpenGL headers. In some cases it may be
sufficient to copy src/data/gl.tu
from one build to another and re-build (but do
not run make
clean, as this will cause the copied
file to be regenerated).
The Backtrace tab and the action will not work.
To use this mode, go to Remote via SSH. In the remote host, put the hostname as it will be passed to ssh(1) (it can also contain a username). You must also configure ssh to log into the machine without prompting for a password.
→ and change the mode toThis is similar to the SSH option, but does not require SSH to be available, making it suitable for embedded systems with OpenGL ES. First, start the application on the target, with the following environment variables:
LD_PRELOAD
=libbugle.so
BUGLE_DEBUGGER
=tcp
BUGLE_DEBUGGER_PORT
=port
(optional)BUGLE_DEBUGGER_HOST
=host
This will open a listener on port
.
By default, it will listen on all interfaces, but can be made
to bind to a specific interface by setting
BUGLE_DEBUGGER_HOST
.
Once the target has been started, go to Remote via TCP/IP. You will then be able to fill in the host and port of the target. Once this setup is done, select → to start the debugging session.
→ and change the mode toThis mode does not use any kind of authentication or encryption, so should only be used on a trusted network.