Status: | Em desenvolvimento |
Localização: | https://github.com/bdcht/ccrawl |
Versão: | 1.x |
Documento: | http://ccrawl.readthedocs.io/en/latest/index.html |
Ccrawl usa clang para construir um banco de dados relacionado a várias estruturas de dados C/C++ (struct, união, classe, enum, typedef, protótipos e macros) que permite identificar tipos de dados e constantes/macros consultando este banco de dados para propriedades específicas, incluindo propriedades relacionado ao layout de memória de estrutura/classe.
Basicamente permite, por exemplo,
O Ccrawl permite então gerar estruturas encontradas em vários formatos: C/C++, é claro, mas também ctypes ou amoco. A saída ctypes de uma classe C++ corresponde a um layout de instância (objeto) na memória, incluindo todos os ponteiros de tabela virtual (ou VTT) que resultam de possivelmente múltiplas classes pai (possivelmente virtuais).
Finalmente, Ccrawl permite calcular várias estatísticas sobre uma API de biblioteca e permite calcular o gráfico de dependência de qualquer tipo, como por exemplo (veja testes/samples/xxx/graph.h):
A documentação do usuário e a API podem ser encontradas em http://ccrawl.readthedocs.io/en/latest/index.html
Considere a seguinte estrutura C do arquivo samples/simple.h
estrutura S { caracter c; intn; união { caractere não assinado x[2]; shorts não assinados; } você; char (*PtrCharArrayOf3[2])[3]; vazio (*pfunc)(int, int); };
Primeiro, colete a definição da estrutura em um banco de dados local:
$ ccrawl -l test.db -g 'test0' coletar amostras/simple.h [100%] simples.h [2] -------------------------------------------------- ------------------ salvando banco de dados... [2]
Então é possível traduzir a estrutura completa em ctypes
$ ccrawl -l test.db mostrar -r -f ctypes 'struct S' struct_S = type('struct_S',(Estrutura,),{}) union_b0eccf67 = tipo('union_b0eccf67',(União,),{}) union_b0eccf67._fields_ = [("x", c_ubyte*2), ("s", c_ushort)] struct_S._anonymous_ = ("você",) struct_S._fields_ = [("c", c_byte), ("n", c_int), ("você", união_b0eccf67), ("PtrCharArrayOf3",POINTER(c_byte*3)*2), ("pfunc", POINTER(CFUNCTYPE(Nenhum, c_int, c_int)))]
Ou simplesmente para calcular os deslocamentos dos campos
$ ccrawl -l test.db informações 'struct S' identificador: estrutura S classe: cStruct fonte: simple.h etiqueta: teste0 tamanho: 40 deslocamentos: [(0, 1), (4, 4), (8, 2), (16, 16), (32, 8)]
Agora vamos lidar com um exemplo C++ mais complicado:
$ ccrawl -l test.db coletar -a --cxx amostras/shahar.cpp [100%] shahar.cpp [18] -------------------------------------------------- ------------------ salvando banco de dados... [ 18]
Podemos mostrar uma definição completa (recursiva) de uma classe:
$ ccrawl -l test.db show -r 'classe filho' classe Avó { público: void virtual grandparent_foo(); int dados_avós; }; class Parent1: avó público virtual { público: virtual vazio parent1_foo(); int parent1_data; }; class Parent2: avó público virtual { público: virtual vazio parent2_foo(); int parent2_data; }; classe Filho: público Pai1, público Pai2 { público: vazio virtual child_foo(); int dados_filhos; };
E seu layout de memória ctypes:
$ ccrawl -l test.db show -f ctypes 'classe filho' struct___layout$Child = type('struct___layout$Child',(Estrutura,),{}) struct___layout$Child._fields_ = [("__vptr$Parent1", c_void_p), ("parent1_data", c_int), ("__vptr$Parent2", c_void_p), ("parent2_data", c_int), ("dados_filhos", c_int), ("__vptr$Avô", c_void_p), ("dados_davô", c_int)]
Veja a documentação para mais exemplos.