Проверьте на sgt в инструкции icmp - PullRequest
3 голосов
/ 18 февраля 2012
 %4 = icmp sgt i32 %2, %3

Для приведенной выше инструкции, как я могу проверить, содержит ли инструкция icmp sgt или slt?

Ответы [ 2 ]

7 голосов
/ 18 февраля 2012

Прямой ответ на ваш вопрос - поместить этот код в пользовательский FunctionPass:

virtual bool runOnFunction(Function &F) {
    for (Function::iterator bb = F.begin(), bb_e = F.end(); bb != bb_e; ++bb) {
        for (BasicBlock::iterator ii = bb->begin(), ii_e = bb->end(); ii != ii_e; ++ii) {
            if (CmpInst *cmpInst = dyn_cast<CmpInst>(&*ii)) {
                handle_cmp(cmpInst);
            }
        }
    }
    return false;
}

void handle_cmp(CmpInst *cmpInst) {
    if (cmpInst->getPredicate() == CmpInst::ICMP_SGT) {
        errs() << "In the following instruction, SGT predicate\n";
        cmpInst->dump();
    }
}

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

Каждая инструкция, которую вы видите в LLVM IR, является просто текстовым представлением класса команд, который существует в базе кода LLVM.В этом случае icmp представляет ICmpInst, который является подклассом CmpInst.Как только вы узнаете, что имеете дело с CmpInst, легко увидеть, как получить доступ к его атрибутам, просто прочитав объявление класса в заголовочном файле.Например, очевидно, что параметр «предиката» этой инструкции представляет sgt и другие предикаты.

Но как узнать, на какой класс смотреть.Это легко сделать с помощью бэкэнда LLVM C ++, который выводит эквивалентный код C ++, необходимый для создания некоторого IR.Например, учитывая этот кусок IR:

  %0 = load i32* %argc.addr, align 4
  %cmp = icmp sgt i32 %0, 0

Он сбросит:

  LoadInst* int32_19 = new LoadInst(ptr_argc_addr, "", false, label_entry_15);
  int32_19->setAlignment(4);
  ICmpInst* int1_cmp = new ICmpInst(*label_entry_15, ICmpInst::ICMP_SGT, int32_19, const_int32_8, "cmp");
  BranchInst::Create(label_if_then, label_if_else, int1_cmp, label_entry_15);

Так что, просто взглянув на него, вы знаете, что вам нужно ICmpInst, а такжепредикат ICMP_SGT.

Чтобы запустить бэкэнд C ++ для некоторого текстового IR в .ll файле, вы просто делаете:

llc -march=cpp -cppgen=program irfile.ll

Надеюсь, это поможет!

0 голосов
/ 14 марта 2012

Вот решение для вашего вопроса:

ICmpInst *ICC=dyn_cast<ICmpInst>(inst);
llvm::CmpInst::Predicate pr=ICC->getSignedPredicate();
switch(pr){
     case CmpInst::ICMP_SGT: errs()<<"------>SGT\n"; break;
     case CmpInst::ICMP_SLT: errs()<<"------>SLT\n"; break; 
     case CmpInst::ICMP_SGE: errs()<<"------>SGE\n"; break; 
     case CmpInst::ICMP_SLE: errs()<<"------>SLE\n"; break;
}

Допустим, у вас есть "inst" указатель инструкции, который указывает на эту инструкцию (% 4 = icmp sgt i32% 2,% 3). После выполнения динамического преобразования inst в ICC, который является экземпляром класса ICmpInst. Затем вызовите getSignedPredicate (), как указано выше, он вернет предикат. На основании этого есть корпус переключателя. Надеюсь, это сработает для вас.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...