I've been working on Linux all the time, but I don't have much use for gdb. Because Ping du is using qtcreator to debug the program. Because of the work, it may not be possible to rely on qtcreator again. So I have a good study ~
Before why not deep use of gdb,qtcreator to bring certain convenience is on the one hand, on the other hand, I feel that gdb encountered a vector, map, set, list there is no way to see the data.
Today I studied, in fact, is easy.
Example code:
#include <iostream> #include <string> #include <vector> #include <map>using namespace Std;int Main () {int i1 = 32; int i2 = 45; Double d = i1 + I2/3; Vector<string> Vstr; Vstr.push_back ("Hello"); Vstr.push_back ("World"); Vstr.push_back ("!"); Map<string, int> M_si; m_si["A"] = 12; m_si["D"] = 93; m_si["B"] = 77; return 0;}
Compile the time:
$ g++-O test-gdb test-gdb.cpp-g
In GDB debugging, you can use the Print command to view the values of variables or constants.
It may be that I have installed the GDB version of the higher reason, the native gdb is very supportive of the STL container. Here is the version information for my GDB:
$ gdb--versiongnu gdb (gdb) Red Hat Enterprise Linux (7.2-75.el6) Copyright (C) free software Foundation, inc.license gplv3+: GNU GPL version 3 or later
The support for STL containers is excellent:
(GDB) P vstr$1 = std::vector of length 3, capacity 4 = {"Hello", "World", "!"} (GDB) P m_si$2 = Std::map with 3 elements = {["A"] = A, ["B"] =, ["D"] = 93}
It's really good to see this kind of information.
But my company's system of GDB is not so smart. If you print the vector, you'll get a lot of information. If it's a map, it's even scarier.
< here to show scary tips >
In fact, only a small part of the information is our concern. GDB is very flexible and we can customize the function inside. I can define a function in GDB to extract important information from the vector and display it.
Download a stl-views.gdb file from here. In this article, we define a lot of gdb functions such as Pvector, Pmap, pstring and so on for us to use.
Download this file to your home directory, and then:
$ cat stl-views-1.0.3.gdb >>. Gdbinit
This will automatically load the contents of the ~/.gdbinit file every time gdb is started.
13 vector<string> vstr; (GDB) n14 vstr.push_back ("Hello");(gdb) n15 vstr.push_back ("World");(gdb) n16 vstr.push_ Back ("!");( GDB) p<TAB><TAB>passcount plist_member print pstring pythonpath pmap print-object ptype pbitset pmap_member printf pvector pdequeue ppqueue pset pwd plist pqueue pstack pwstring
After you enter P, a command that starts with P is listed each time you press the TAB key two times in a row. Here we see: pstring, Pvector, pwstring, Pstack, Pmap, Pmap_member and so on.
Let's use Pvector to see what's in Vstr:
(GDB) Pvector Vstrelem[0]: $ $ = "Hello" elem[1]: $4 = "World" elem[2]: $ = "!" Vector size = 3Vector capacity = 4Element type = Std::basic_string<char, std::char_traits<char>, std::allocator& lt;char> > *
This command does print out a lot of valuable information.
Bloggers have a habit, I want not only to know it, I also want to know why. So I took a look at the contents of the. gdbinit file. This function is defined in the ~/.gdbinit. Let's open this file and take a look.
define pvector if $ARGC == 0 help pvector else set $size = $arg 0._m_impl._m_finish - $arg 0._m_impl._m_start set $capacity = $arg 0._m_impl._m_end_of_storage - $arg 0._m_ impl._m_start set $size _max = $size - 1 end if $ARGC == 1 set $i = 0 while $i < $size printf "elem[%u]: ", $i p * ($arg 0._m_impl ._m_start + $i) set $i ++ end end if $ARGC == 2 set $idx = $arg 1 if $idx < 0 | | $IDX > $size _max printf "idx1, idx2 are not in acceptable range: [0..%u].\n", $ size_max else printf "elem[%u]: ", $idx p * ($arg 0._m_impl._m_start + $idx) end end if $argc == 3 set $start _idx = $arg 1 set $stop _idx = $arg 2 if $start _idx > $stop _idx set $tmp _idx = $start _ idx set $start _idx = $stop _idx set $stop _idx = $tmp _idx end if $start _idx < 0 | | $stop _idx < 0 | | $start _idx > $size _max | | $stop _idx > $size _max printf "idx1, idx2 are not in acceptable range: [0..%u].\n ", $size _max else set $i = $start _idx while $i < = $stop _idx printf "elem[%u]: ", $i p * ($arg 0._m_impl ._m_start + $i) set $i + + end end end if $ARGC > 0 printf "vector size = %u\n", $size printf "vector capacity = %u\n", $capacity printf "element " whatis $arg 0._m_ Impl._m_start endenddocument pvector prints std::vector<t> Information. syntax: pvector <vector> <idx1> <idx2 > Note: idx, idx1 and idx2 must be in Acceptable range [0..<vector>.size () -1]. examples: pvector v - prints vector content, size, capacity and t typedef pvector v 0 - prints element[idx] from vector pvector v 1 2 - prints elements in range [idx1. Idx2] from vectorend
Look at all a bit more, we don't look at the part of multiple parameters, we analyze only one part of the parameter:
define pvector if $ARGC == 0 # If there are no parameters, print the Help tip information help pvector else # If there are parameters, then prepare the Size, capacity, size_max These three important parameters. set $size = $arg 0._m_impl._m_finish - $arg 0._m_impl._m_start # arg0 is the first parameter, That is, the Vstr array object. Pay attention to how size is calculated. set $capacity = $arg 0._m_impl._m_end_of_storage - $arg 0._m_impl._m_start set $size _max = $size - 1 end if $ARGC &NBsp;== 1 # If there is only one parameter, Description requires printing out all elements of the vector set $i = 0 while $i < $size # with a while loop, print out all the elements in the list with printf and P printf "elem[%u]: ", $i p * ($arg 0._m_impl._m_start + $i) # Watch!!!! set $i ++ end end
All the instructions are written in the comments above, you have to realize it!
If the print command can be like a template function in C + +, it can be "biased" for a particular type. There is a problem with the above:
In the "P * ($arg 0._m_impl._m_start + $i)" command, what if a member of the vector is still a STL container? It's a question.
Using GDB to tune the C + + standard library