2012-02-01 5 views
6

Ho configurato le stampanti graziose utilizzando http://wiki.eclipse.org/CDT/User/FAQ#How_can_I_inspect_the_contents_of_STL_containers.3F. Funziona con successo per vettori e altri contenitori. Tuttavia non posso arrivare a ispezionare le mappe come nell'esempio qui sotto:Stampanti graziose per le mappe che generano un errore di tipo

#include <map> 
#include <iostream> 

using namespace std; 

int main() 
{ 
map <int, string> mapIntToString; 
map <int, int> mapInt2; 
mapIntToString.insert (map <int, string>::value_type (3, "Three")); 
mapInt2.insert (map <int, int>::value_type (3, 4)); 
return 0; 
} 

ottengo il seguente errore quando si stampa con gdb:

(gdb) p mapInt2 
$1 = std::map with 1 elementsTraceback (most recent call last): 
File "/home/myuser/opt/gdb_printers/python/libstdcxx/v6/printers.py", line 422, in children 
rep_type = find_type(self.val.type, '_Rep_type') 
File "/home/myuser/opt/gdb_printers/python/libstdcxx/v6/printers.py", line 45, in find_type 
raise ValueError, "Cannot find type %s::%s" % (str(orig), name) 
ValueError: Cannot find type std::map<int, int, std::less<int>, std::allocator<std::pair<int const, int> > >::_Rep_type 
+3

Sono venuto per quanto scoprire che '_Rep_type' è [almeno su alcuni sistemi] un typedef privato in std :: map. perhap quell'assunzione non è sempre vera. Ti suggerisco di avvisare gli sviluppatori di belle stampanti. –

risposta

0

Sul mio sistema il tipo _Rep_type non è di tipo pubblico di std::map (è typedef privati) in modo lo script sta cercando di capire un tipo di <yourmap>._M_t variabile che è di tipo _Rep_type ...

ho provato:

typedef std::map<int,int> map_t; 
map_t m; 
m.insert(map_t::value_type(3,4)); 

poi nel gdb posso stampare la chiave 3 come questo (in seguito la funzione di stampa dallo script ho linkato sotto):

p *(int*)(void*)(m._M_t._M_impl._M_header._M_left+1) 

Qualora la _M_t in std::map è di _Rb_tree tipo, ma il tipo di non è pubblico nella mappa (lo puoi vedere nell'intestazione map, in particolare nel file di intestazione <path/to/std-headers/dir/bits/stl_map.h.

Non sono sicuro che questo aiuti un po ', in pratica sembra che ci sia un problema con la bella funzione di stampa che stai caricando.

ho appena provato ad aggiungere a .gdbinit roba da GNU GDB Debugger Command Cheat Sheet from yolinux.com (Ho cercato su google per gdb pretty print) e che ottengo in uscita ragionevole:

(gdb) pmap m int int 
elem[0].left: $3 = 3 
elem[0].right: $4 = 4 
+3

Il fatto che '_Rep_type' sia un typedef privato è irrilevante: GDB conosce * tutti * i tipi (e typedefs) quando sono disponibili informazioni di debug. E 'pmap' è un modo davvero vecchio e goffo per stampare STL. Le stampanti graziose di Python sono * molto * più belle (quando funzionano ;-) –

+0

Bene, mi sembra che per qualche ragione il mio GDB non "conosca" questi tipi. Preferirei restare con le stampanti pretty pitone ma non so come risolvere questo problema. '_Rep_type' è privato in stl_map.h, nel mio caso. – agestrada

+0

Suppongo che sia un problema con lo script python come sopra evidenziato da altri ... – stefanB

18

Che compilatore (e quale versione) hai usato per costruire la vostra fonte di test?

Suppongo che non fosse una versione recente di g++. Ecco quello che ottengo con g++ 4.4.3-4ubuntu5:

$ gdb -q ./a.out 
Reading symbols from /tmp/a.out...done. 
(gdb) b 12 
Breakpoint 1 at 0x400de3: file t.cc, line 12. 
(gdb) r 

Breakpoint 1, main() at t.cc:12 
12 return 0; 
(gdb) p mapInt2 
$1 = std::map with 1 elements = {[3] = 4} 

Aggiornamento:

Questo è ciò che ho per la versione: g ++ (Ubuntu 4.4.3-4ubuntu5) 4.4.3

Vedo il problema. Le istruzioni a cui hai fatto riferimento sono errate.

In particolare, le istruzioni suggeriscono: svn co svn://gcc.gnu.org/svn/gcc/trunk/libstdc++-v3/python, ma il problema è che il codice python raggiunge in libstdc++interni, e quindi deve abbinare a questi interni (questo è il motivo per le stampanti belle sono parte del GCC e non parte di GDB, un fatto bruce.banner si è lamentato).

Quando hai fatto un fresco svn co ..., avete preso una copia del codice Python che non è più corrisponde alla tua libstdc++ interni, e questo è ciò che sta causando problemi.

In particolare, svn log mostra che find_type è stato aggiunto qui:

r183732 | tromey | 2012-01-30 08:25:11 -0800 (Mon, 30 Jan 2012) | 27 lines 

Questo è molto più più tardi gcc-4.4.3. Che cosa si vuole fare, allora, è quello di ottenere abbastanza stampanti che corrispondono la versione di libstdc++, in questo modo:

svn co svn://gcc.gnu.org/svn/gcc/branches/gcc_4_4_3_release/libstdc++-v3/python 

Tranne comando di cui sopra non funziona, perché gcc 4.4.3 precede le stampanti belle.

Non importa, l'attuazione di std::map (e gran parte del resto dei meccanismi interni di STL) non è cambiato tra la 4.4.3 e 4.6, e questo comando fa lavoro:

svn co svn://gcc.gnu.org/svn/gcc/branches/gcc-4_6-branch/libstdc++-v3/python 
+0

Quando creo gdb 7.3 dal sorgente su Ubuntu 7.3 non posso stampare gli elementi di stl di default, devo installare le stampanti carine. Non senti che questo è un passo indietro? –

+0

Questo è quello che ottengo per la versione: g ++ (Ubuntu 4.4.3-4ubuntu5) 4.4.3 – agestrada

+0

Grazie impiegato russo! Ho avuto questo problema nel mio lavoro. Stiamo usando gcc/g ++ che esce dalla scatola con RHEL5 e stavo avendo difficoltà a seguire le istruzioni su come installare PrettyPrinters e stavo ottenendo lo stesso problema di std :: map prima del tuo aiuto! – Setheron