llvm::Value * Generator::visit(FunctionCall & node) { auto function = module->getFunction(node.getVirtualName()); if (function == nullptr) { if (funcAlias.find(node.getVirtualName()) == funcAlias.end()) { throw std::runtime_error("Function not defined: " + node.name); } function = funcAlias[node.getVirtualName()]; } // TODO: check arg compatibility. std::vector<llvm::Value *> values; for (auto i : node.arguments) { auto value = i->accept(this); // variadic function promotion. if (function->isVarArg() && value->getType()->isFloatTy()) { value = typeSys.cast(value, typeSys.doubleTy, builder.GetInsertBlock()); } values.push_back(value); } return builder.CreateCall(function, values); }
std::size_t FunctionAttributes::hash() const { Hasher hasher; hasher.add(isVarArg()); hasher.add(isMethod()); hasher.add(isTemplated()); hasher.add(noExceptPredicate()); return hasher.get(); }
std::string FunctionAttributes::toString() const { return makeString("FunctionAttributes(" "isVarArg: %s, " "isMethod: %s, " "isTemplated: %s, " "noExceptPredicate: %s)", isVarArg() ? "true" : "false", isMethod() ? "true" : "false", isTemplated() ? "true" : "false", noExceptPredicate().toString().c_str()); }
bool FunctionAttributes::operator==(const FunctionAttributes& other) const { return isVarArg() == other.isVarArg() && isMethod() == other.isMethod() && isTemplated() == other.isTemplated() && noExceptPredicate() == other.noExceptPredicate(); }
FunctionAttributes FunctionAttributes::copy() const { return FunctionAttributes(isVarArg(), isMethod(), isTemplated(), noExceptPredicate().copy()); }