在使用flex和野牛的C编译器中,编写LLVM IR代码将整数添加到变量的正确方法是什么?

eqoofvh9  于 2023-05-28  发布在  其他
关注(0)|答案(1)|浏览(114)

我正在使用flex野牛和llvm编写自己的编译器。但是,当我想为一个简单函数示例生成ir时

int jia (int a){
    a=a+1;
    return a;
}

结果是:

; ModuleID = 'main'
source_filename = "main"

define i32 @jia(i32 %a) {
entry:
  %0 = alloca i32
  store i32 %a, i32* %0
  %tmp = load i32, i32* %0
  %tmp1 = load i32, i32* %0
  %addtmp = add i32 %tmp1, i32 1
  store i32 %addtmp, i32* %0
  %tmp2 = load i32, i32* %0
  ret i32 %tmp2
}

我使用Lli来执行IR代码。但显示enter image description here时出错
所以我用一个很好的demo来生成同样的函数,ir是

define i32 @jia(i32 %a) {
entry:
  %0 = alloca i32
  store i32 %a, i32* %0
  %arrayPtr = load i32, i32* %0
  %1 = load i32, i32* %0
  %addtmp = add i32 %1, 1
  store i32 %addtmp, i32* %0
  %arrayPtr1 = load i32, i32* %0
  %2 = load i32, i32* %0
  ret i32 %2
}

所以重点是“%addtmp = add i32%1,1”和“%addtmp = add i32%tmp1,i32 1”为什么第一个可以执行。下一个不能这样做。以及指令%addtmp = add i32%1,1中的1的类型是什么
我希望有人能告诉我为什么我在1之前多了一个“i32”。以及如何生成正确的代码。
我使用的代码:

llvm::Value* int_num_node::codegen(CodeGenerator & generator){
    cout<<"[ast.cpp line93 int_num_node::codegen]NInteger"<<endl; 
    return ConstantInt::get(Type::getInt32Ty(TheContext), this->number, true);

    //return TheBuilder.getInt32(this->number);
    
}
llvm::Value* op_node::codegen(CodeGenerator & generator){
    cout<<"[ast.cpp line73 op_node::codegen]NBexpression"<<endl; 
    llvm::Value* left_value = this->LHS->codegen(generator);
    llvm::Value* right_value = this->RHS->codegen(generator);
    if(left_value==NULL) return nullptr;
    if(right_value==NULL) return nullptr;
    cout<<"[ast.cpp line83 op_node::codegen]this->op_code: "<<this->op_code<<endl;
    switch(this->op_code){
        //add
        case '+':
            return TheBuilder.CreateAdd(left_value,right_value,"addtmp");
        case '-':
            return TheBuilder.CreateSub(left_value,right_value,"subtmp");
        case '*':
            return TheBuilder.CreateMul(left_value,right_value,"multmp");
        case '/':
            return TheBuilder.CreateSDiv(left_value,right_value,"divtmp");
        
    }
}
ss2ws0br

ss2ws0br1#

add的语法如下所示:

<result> = add <ty> <op1>, <op2>          ; yields ty:result
<result> = add nuw <ty> <op1>, <op2>      ; yields ty:result
<result> = add nsw <ty> <op1>, <op2>      ; yields ty:result
<result> = add nuw nsw <ty> <op1>, <op2>  ; yields ty:result

add的两个参数必须是整数,并且必须具有相同的类型,这就是为什么只指定一次type的原因。

相关问题