Я пишу ModulePass и мне нужно проанализировать каждый структура определена в данном модуле.
Я понимаю, что идентифицированные структуры с именем вставляются в ValueSymbolTable, но как я могу перебрать все другие структуры (идентифицированные без имени и буквальных структур)?
Правильный способ сделать это:
#include "llvm/IR/TypeFinder.h"
llvm::TypeFinder StructTypes;
StructTypes.run(M, true);
for (auto *STy : StructTypes)
STy->dump();
Вы не должны использовать какие-либо закрытые / непрозрачные типы (например, LLVMContextImpl), заголовки которых не публикуются.
LLVMContextImpl
Экземпляр, связанный с вашим текущим контекстом, должен иметь две структуры данных, одна из которых содержит все идентифицированные структуры в текущем контексте (независимо от того, имеют ли они явное имя или нет), а другая содержит все литеральные структуры.
Чтобы получить LLVMContextImpl
пример:
Module& M = ...
LLVMContextImpl* C = M.getContext().pImpl;
Для выявленных структур:
C->NamedStructTypes
Для буквальных структур:
C->AnonStructTypes
Оба возвращают итерируемые типы (StringMap
для первого, DenseMap
для второго), позволяя вам перебирать их и выводить все типы.
В дополнение к ответу Оука, вот более полный пример кода:
Module& M = ...
LLVMContextImpl* C = M.getContext().pImpl;
for (StringMap<StructType *>::iterator i = C->NamedStructTypes.begin(); i != C->NamedStructTypes.end(); ++i)
{
StructType *t = i->getValue();
t->dump(); fprintf(stderr, "\n");
}
LLVMContextImpl.h, будучи заголовком для частной реализации, не является одним из публичных заголовков LLVM. Вы можете получить его из исходного кода LLVM — либо скопируйте его оттуда в путь поиска заголовка, либо, для быстрого & грязное тестирование, сделайте:
#include "/path/to/llvm/src/lib/VMCore/LLVMContextImpl.h"
bool runOnModule(Module &M) override
{
for(auto *S : M.getIdentifiedStructTypes())
{
S->dump();
}
return false;
}