[LLVMdev] insert printf into IR
Frits van Bommel
fvbommel at gmail.com
Thu Mar 31 23:35:23 PDT 2011
On Fri, Apr 1, 2011 at 7:46 AM, George Baah <georgebaah at gmail.com> wrote:
> Hi All,
> I am trying to insert printf ("%d", v), where v is an integer param, into
> the IR.
> I am doing something wrong because I keep getting segfaults.
> Below is my code. Thanks.
>
> vector<const Type *> params;
> params.push_back(Type::getInt8PtrTy(M.getContext()));
> params.push_back(Type::getInt32Ty(M.getContext()));
You don't need the i32 type as an explicit parameter; the 'true'
isVarArg argument to FunctionType::get() below allows the call to
handle the int parameter.
> FunctionType *fType =
> FunctionType::get(Type::getInt32Ty(M.getContext()), params, true);
> Constant *temp = M.getOrInsertFunction("printf",fType);
> if(!temp){
> errs() << "printf function not in symbol table\n";
> exit(1);
> }
> Function *f = cast<Function>(temp);
Because you were providing a non-standard parameter list above,
getOrInsertFunction() returned a bitcast'ed function, not a "raw"
function (if there was already a declaration/definition of printf()
available)
In general, you can't be sure it returns a Function*.
> f->setCallingConv(CallingConv::C);
Also, the C calling convention is the default and if there's an
existing declaration it should already be correct, hopefully.
> Value *intparam = ...
> Value *strPtr = builder.CreateGlobalStringPtr(str,"");
> builder.CreateCall2(PrintF, strPtr, intparam,"tmp6");
If there *were* a need to set the calling convention, you'd also want
to set it on the call. But as I said, the C calling convention is the
default.
If this code produced segfaults instead of producing assertion
failures, that means you compiled without assertions enabled. I
recommend recompiling with assertions enabled, it really helps catch
these kinds of mistakes.
More information about the llvm-dev
mailing list