Инструкция вызова llvm irbuilder выдает исключение при проходе встраивания функции

Я новичок в LLVM. Я использую API Clang C++ для компиляции нескольких файлов-заглушек (в c) в IR, а затем склеиваю их вместе с помощью IR Builder (после их связывания), чтобы в конечном итоге запустить через JIT.

Все это прекрасно работает, если только я не добавлю проход functionInlining к своим оптимизациям, после чего один из этих вызовов функций, сделанных в IR Builder, вызовет следующее исключение при запуске диспетчера проходов:

Assertion failed: (New->getType() == getType() && "replaceAllUses of value with new value of different type!"), function replaceAllUsesWith, file /Users/mike/Development/llvm/llvm/lib/IR/Value.cpp, line 356.

Вот как я делаю инструкцию вызова (довольно прямолинейно):

Function *kernelFunc = mModule->getFunction( (kernel->Name() + StringRef("_") + StringRef(funcName)).str());
if (kernelFunc){
    CallInst* newInst = builder.CreateCall(kernelFunc, args);
}

Позже модуль оптимизируется:

legacy::PassManager passMan;
PassManagerBuilder Builder;
Builder.OptLevel = 3;
//Builder.Inliner = llvm::createFunctionInliningPass(); //commenting this back in trigger the exception
Builder.populateModulePassManager(passMan);

passMan.run( *mModule ); //exception occurs before this call returns

Есть идеи, что искать?


person Mike Woodworth    schedule 19.12.2015    source источник


Ответы (2)


Попробуйте запустить llvm::verifyModule на своем модуле, чтобы убедиться, что он правильный. Возможно, у вас есть ошибка, и вам повезло заранее, но что-то сработало во встроенном файле.

В общем, утверждения проверяют подмножество вещей, которые могут быть неправильными в вашем модуле, но проверка проверяет гораздо больше.

Это может быть ошибка в LLVM, но, скорее всего, это плохой модуль, это легко сделать.

person Colin LeMahieu    schedule 19.12.2015
comment
Спасибо, я не знал о verifyModule. К сожалению, этот модуль проходит проверку без ошибок и по-прежнему выдает проход встраивания. - person Mike Woodworth; 20.12.2015

Итак, я наконец настроил свою среду разработки, чтобы я мог проверить вызов утверждения в отладчике. Оказывается, заменяемый базовый блок имел контекст, отличный от того, которым он заменялся. вернувшись назад и убедившись, что IRBuilder использует тот же контекст, что и парсеры IR, решили проблему.

person Mike Woodworth    schedule 21.01.2016