Rename API, Make emit IR optional
This commit is contained in:
parent
57094c9afe
commit
a9a340f482
@ -20,7 +20,7 @@ file(GLOB MY_HEADERS "include/*.h")
|
|||||||
|
|
||||||
include(formatting.cmake)
|
include(formatting.cmake)
|
||||||
clang_format(format ${MY_SOURCES} ${MY_HEADERS})
|
clang_format(format ${MY_SOURCES} ${MY_HEADERS})
|
||||||
clang_format_check(format_check ${MY_SOURCES} ${MY_HEADERS})
|
# clang_format_check(format_check ${MY_SOURCES} ${MY_HEADERS})
|
||||||
|
|
||||||
add_executable(sysy ${SOURCES})
|
add_executable(sysy ${SOURCES})
|
||||||
# message(STATUS "${SOURCES}")
|
# message(STATUS "${SOURCES}")
|
||||||
|
|||||||
@ -192,10 +192,10 @@ public:
|
|||||||
TypePtr_t element_type;
|
TypePtr_t element_type;
|
||||||
InstGEP(ValuePtr_t pointer, const std::vector<ValuePtr_t> &indices, BasicBlockPtr_t parent_bb)
|
InstGEP(ValuePtr_t pointer, const std::vector<ValuePtr_t> &indices, BasicBlockPtr_t parent_bb)
|
||||||
: Instruction(InstTag::GEP, std::make_shared<PointerType>(extract_type(pointer, indices)), parent_bb) {
|
: Instruction(InstTag::GEP, std::make_shared<PointerType>(extract_type(pointer, indices)), parent_bb) {
|
||||||
if (Value::isValueType<InstGEP>(pointer)) {
|
if (Value::is<InstGEP>(pointer)) {
|
||||||
aim_to = std::dynamic_pointer_cast<InstGEP>(pointer)->aim_to;
|
aim_to = std::dynamic_pointer_cast<InstGEP>(pointer)->aim_to;
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<InstAlloca>(pointer) || Value::isValueType<GlobalVar>(pointer)) {
|
else if (Value::is<InstAlloca>(pointer) || Value::is<GlobalVar>(pointer)) {
|
||||||
aim_to = pointer;
|
aim_to = pointer;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
|||||||
@ -20,7 +20,7 @@ public:
|
|||||||
virtual ~Value() = default;
|
virtual ~Value() = default;
|
||||||
|
|
||||||
template <typename TT>
|
template <typename TT>
|
||||||
static bool isValueType(std::shared_ptr<Value> ptr) {
|
static bool is(std::shared_ptr<Value> ptr) {
|
||||||
if (ptr.get()) {
|
if (ptr.get()) {
|
||||||
// auto &r = *ptr.get();
|
// auto &r = *ptr.get();
|
||||||
// return typeid(r) == typeid(TT);
|
// return typeid(r) == typeid(TT);
|
||||||
@ -33,7 +33,7 @@ public:
|
|||||||
|
|
||||||
// it is caller's duty to check before use `asType`
|
// it is caller's duty to check before use `asType`
|
||||||
template <typename TT>
|
template <typename TT>
|
||||||
static std::shared_ptr<TT> asValueType(std::shared_ptr<Value> ptr) {
|
static std::shared_ptr<TT> as(std::shared_ptr<Value> ptr) {
|
||||||
return std::dynamic_pointer_cast<TT>(ptr);
|
return std::dynamic_pointer_cast<TT>(ptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -94,8 +94,8 @@ public:
|
|||||||
std::vector<std::shared_ptr<Instruction>> inst_list;
|
std::vector<std::shared_ptr<Instruction>> inst_list;
|
||||||
std::shared_ptr<Function> parent;
|
std::shared_ptr<Function> parent;
|
||||||
BasicBlockListNode_t itr;
|
BasicBlockListNode_t itr;
|
||||||
std::vector<std::shared_ptr<BasicBlock>> successors;
|
std::list<std::shared_ptr<BasicBlock>> successors;
|
||||||
std::vector<std::shared_ptr<BasicBlock>> predecessors;
|
std::list<std::shared_ptr<BasicBlock>> predecessors;
|
||||||
BasicBlock(const std::string &name, std::shared_ptr<Function> parent) : Value(name, TypeHelper::TYPE_LABEL) {
|
BasicBlock(const std::string &name, std::shared_ptr<Function> parent) : Value(name, TypeHelper::TYPE_LABEL) {
|
||||||
this->parent = parent;
|
this->parent = parent;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -228,7 +228,7 @@ scheme_ref = {
|
|||||||
|
|
||||||
scheme_my = {
|
scheme_my = {
|
||||||
"name": "my",
|
"name": "my",
|
||||||
"sy_ir": f"build/sysy -S {{sy}} -o {{ir}}",
|
"sy_ir": f"build/sysy -S {{sy}} -o {{ir}} -emit-llvm",
|
||||||
"ir_asm": "llc --march=x86 --relocation-model=pic {ir} -o {asm}",
|
"ir_asm": "llc --march=x86 --relocation-model=pic {ir} -o {asm}",
|
||||||
"asm_obj": "as --32 {asm} -o {obj}",
|
"asm_obj": "as --32 {asm} -o {obj}",
|
||||||
"obj_bin": f"clang -m32 -Ofast -fPIE {{obj}} {LIB_PATH} -o {{bin}}",
|
"obj_bin": f"clang -m32 -Ofast -fPIE {{obj}} {LIB_PATH} -o {{bin}}",
|
||||||
|
|||||||
16
src/main.cpp
16
src/main.cpp
@ -39,6 +39,7 @@ int main(int argc, const char **argv) {
|
|||||||
arg_parser.add_argument("-S").implicit_value(true).help("Useless but required by the contest").required();
|
arg_parser.add_argument("-S").implicit_value(true).help("Useless but required by the contest").required();
|
||||||
arg_parser.add_argument("-o").help("Output file name").required();
|
arg_parser.add_argument("-o").help("Output file name").required();
|
||||||
arg_parser.add_argument("-O1").implicit_value(true).default_value(false).help("Performance mode");
|
arg_parser.add_argument("-O1").implicit_value(true).default_value(false).help("Performance mode");
|
||||||
|
arg_parser.add_argument("-emit-llvm").implicit_value(true).default_value(false).help("Generate llvm ir");
|
||||||
arg_parser.add_argument("--v").default_value(0);
|
arg_parser.add_argument("--v").default_value(0);
|
||||||
try {
|
try {
|
||||||
arg_parser.parse_args(argc, argv);
|
arg_parser.parse_args(argc, argv);
|
||||||
@ -50,6 +51,7 @@ int main(int argc, const char **argv) {
|
|||||||
auto source_file = arg_parser.get<std::string>("source");
|
auto source_file = arg_parser.get<std::string>("source");
|
||||||
auto output_file = arg_parser.get<std::string>("-o");
|
auto output_file = arg_parser.get<std::string>("-o");
|
||||||
auto flg_O1 = arg_parser["-O1"] == true;
|
auto flg_O1 = arg_parser["-O1"] == true;
|
||||||
|
auto emit_llvm = arg_parser["-emit-llvm"] == true;
|
||||||
// std::cout << source_file << " " << output_file << " " << flg_O1 <<
|
// std::cout << source_file << " " << output_file << " " << flg_O1 <<
|
||||||
// std::endl;
|
// std::endl;
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
@ -86,13 +88,15 @@ int main(int argc, const char **argv) {
|
|||||||
auto tree = parser.program();
|
auto tree = parser.program();
|
||||||
Visitor visitor(lexer);
|
Visitor visitor(lexer);
|
||||||
visitor.visitProgram(tree);
|
visitor.visitProgram(tree);
|
||||||
auto llir_file = output_file.substr(0, output_file.rfind(".")) + ".ll";
|
if (emit_llvm) {
|
||||||
std::ofstream ofs_llir_file(llir_file);
|
auto llir_file = output_file.substr(0, output_file.rfind(".")) + ".ll";
|
||||||
if (!ofs_llir_file.good()) {
|
std::ofstream ofs_llir_file(llir_file);
|
||||||
LOG(ERROR) << "Failed to create/overwrite LLIR output file " << llir_file;
|
if (!ofs_llir_file.good()) {
|
||||||
return 1;
|
LOG(ERROR) << "Failed to create/overwrite LLIR output file " << llir_file;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
visitor.llir_gen(ofs_llir_file);
|
||||||
}
|
}
|
||||||
visitor.llir_gen(ofs_llir_file);
|
|
||||||
#if 0
|
#if 0
|
||||||
std::cout << tree->toStringTree(&parser) << std::endl << std::endl;
|
std::cout << tree->toStringTree(&parser) << std::endl << std::endl;
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@ -293,7 +293,7 @@ std::any Visitor::visitInitVal(SysyParser::InitValContext *ctx) {
|
|||||||
if (_state.isGlobalIint) {
|
if (_state.isGlobalIint) {
|
||||||
auto const_value = any_to_Value(visitInitVal(init_val));
|
auto const_value = any_to_Value(visitInitVal(init_val));
|
||||||
// should evaluate to const int
|
// should evaluate to const int
|
||||||
sysy_assert(Value::isValueType<ConstantInt>(const_value));
|
sysy_assert(Value::is<ConstantInt>(const_value));
|
||||||
cur_arr.push_back(const_value);
|
cur_arr.push_back(const_value);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@ -834,6 +834,15 @@ std::any Visitor::visitLVal(SysyParser::LValContext *ctx) {
|
|||||||
pointed_type = array_type->element_type;
|
pointed_type = array_type->element_type;
|
||||||
ptr = build_InstGEP(ptr, {CONST0, CONST0}, _state.current_bb);
|
ptr = build_InstGEP(ptr, {CONST0, CONST0}, _state.current_bb);
|
||||||
}
|
}
|
||||||
|
// for (int i = 0; i < exp_list.size() - 1; ++ i) {
|
||||||
|
// sysy_assert(pointed_type->type_tag == Type::TypeTag::ArrayType);
|
||||||
|
// auto array_type = std::dynamic_pointer_cast<ArrayType>(pointed_type);
|
||||||
|
// auto exp_val = any_to_Value(visitExp(exp_list[i]));
|
||||||
|
// if (Value::isValueType<PointerType>(exp_val)){
|
||||||
|
// exp_val = build_InstLoad(exp_val, pointed_type, _state.current_bb);
|
||||||
|
// }
|
||||||
|
// ptr = build_InstGEP(ptr, {CONST0, exp_val}, _state.current_bb);
|
||||||
|
// }
|
||||||
auto exp_val = any_to_Value(visitExp(exp_list.back()));
|
auto exp_val = any_to_Value(visitExp(exp_list.back()));
|
||||||
auto inst_add = build_InstBinary(InstTag::Add, offset, exp_val, _state.current_bb);
|
auto inst_add = build_InstBinary(InstTag::Add, offset, exp_val, _state.current_bb);
|
||||||
offset = inst_add; // finally, we get the offset
|
offset = inst_add; // finally, we get the offset
|
||||||
@ -887,7 +896,7 @@ std::any Visitor::visitFuncDef(SysyParser::FuncDefContext *ctx) {
|
|||||||
func_obj->bb_list.pop_back();
|
func_obj->bb_list.pop_back();
|
||||||
}
|
}
|
||||||
if (func_obj->bb_list.back()->inst_list.size()==0
|
if (func_obj->bb_list.back()->inst_list.size()==0
|
||||||
|| !Value::isValueType<InstReturn>(func_obj->bb_list.back()->inst_list.back())){
|
|| !Value::is<InstReturn>(func_obj->bb_list.back()->inst_list.back())){
|
||||||
if (func_ret_type->type_tag == Type::TypeTag::VoidType) {
|
if (func_ret_type->type_tag == Type::TypeTag::VoidType) {
|
||||||
build_InstReturn(_state.current_bb);
|
build_InstReturn(_state.current_bb);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -75,8 +75,8 @@ std::shared_ptr<InstBinary> build_InstBinary(
|
|||||||
assert(Type::isType<IntegerType>(op1->type));
|
assert(Type::isType<IntegerType>(op1->type));
|
||||||
assert(Type::isType<IntegerType>(op2->type));
|
assert(Type::isType<IntegerType>(op2->type));
|
||||||
if (!(Type::asType<IntegerType>(op1->type)->int_type == Type::asType<IntegerType>(op2->type)->int_type)) {
|
if (!(Type::asType<IntegerType>(op1->type)->int_type == Type::asType<IntegerType>(op2->type)->int_type)) {
|
||||||
if (!(Value::isValueType<ConstantInt>(op1) && Value::asValueType<ConstantInt>(op1)->value == 0)
|
if (!(Value::is<ConstantInt>(op1) && Value::as<ConstantInt>(op1)->value == 0)
|
||||||
&& !(Value::isValueType<ConstantInt>(op2) && Value::asValueType<ConstantInt>(op2)->value == 0)) {
|
&& !(Value::is<ConstantInt>(op2) && Value::as<ConstantInt>(op2)->value == 0)) {
|
||||||
LOG(ERROR) << op1->to_string() << ",\t" << op2->to_string();
|
LOG(ERROR) << op1->to_string() << ",\t" << op2->to_string();
|
||||||
assert(0);
|
assert(0);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -158,21 +158,21 @@ static void _gen_blocks(std::ostream &ostr, const std::list<BasicBlockPtr_t> &bl
|
|||||||
VLOG(5) << "Build inst" << _inst->ir_seqno << ": " << _inst->to_string();
|
VLOG(5) << "Build inst" << _inst->ir_seqno << ": " << _inst->to_string();
|
||||||
switch (_inst->tag) {
|
switch (_inst->tag) {
|
||||||
case InstTag::Br: {
|
case InstTag::Br: {
|
||||||
auto inst = Value::asValueType<InstBranch>(_inst);
|
auto inst = Value::as<InstBranch>(_inst);
|
||||||
assert(inst->ir_seqno == -1);
|
assert(inst->ir_seqno == -1);
|
||||||
ostr << "br ";
|
ostr << "br ";
|
||||||
if (inst->operand_list.size() == 1) {
|
if (inst->operand_list.size() == 1) {
|
||||||
assert(Value::isValueType<BasicBlock>(inst->operand_list[0]));
|
assert(Value::is<BasicBlock>(inst->operand_list[0]));
|
||||||
auto bb_dest = Value::asValueType<BasicBlock>(inst->operand_list[0]);
|
auto bb_dest = Value::as<BasicBlock>(inst->operand_list[0]);
|
||||||
assert(bb_dest->ir_seqno >= 0);
|
assert(bb_dest->ir_seqno >= 0);
|
||||||
ostr << "label %" << bb_dest->ir_seqno;
|
ostr << "label %" << bb_dest->ir_seqno;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
assert(Value::isValueType<Instruction>(inst->operand_list[0]));
|
assert(Value::is<Instruction>(inst->operand_list[0]));
|
||||||
assert(Type::isType<IntegerType>(inst->operand_list[0]->type));
|
assert(Type::isType<IntegerType>(inst->operand_list[0]->type));
|
||||||
auto cond = Value::asValueType<Instruction>(inst->operand_list[0]);
|
auto cond = Value::as<Instruction>(inst->operand_list[0]);
|
||||||
auto bb_true = Value::asValueType<BasicBlock>(inst->operand_list[1]);
|
auto bb_true = Value::as<BasicBlock>(inst->operand_list[1]);
|
||||||
auto bb_false = Value::asValueType<BasicBlock>(inst->operand_list[2]);
|
auto bb_false = Value::as<BasicBlock>(inst->operand_list[2]);
|
||||||
if (!Type::asType<IntegerType>(cond->type)->isI1()) {
|
if (!Type::asType<IntegerType>(cond->type)->isI1()) {
|
||||||
LOG(ERROR) << "Expect cond evals to i1: " << cond->to_string();
|
LOG(ERROR) << "Expect cond evals to i1: " << cond->to_string();
|
||||||
panic("Grammar check");
|
panic("Grammar check");
|
||||||
@ -185,7 +185,7 @@ static void _gen_blocks(std::ostream &ostr, const std::list<BasicBlockPtr_t> &bl
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case InstTag::Ret: {
|
case InstTag::Ret: {
|
||||||
auto inst = Value::asValueType<InstReturn>(_inst);
|
auto inst = Value::as<InstReturn>(_inst);
|
||||||
assert(inst->ir_seqno == -1);
|
assert(inst->ir_seqno == -1);
|
||||||
ostr << "ret ";
|
ostr << "ret ";
|
||||||
if (inst->operand_list.size() == 0) {
|
if (inst->operand_list.size() == 0) {
|
||||||
@ -193,17 +193,17 @@ static void _gen_blocks(std::ostream &ostr, const std::list<BasicBlockPtr_t> &bl
|
|||||||
ostr << "void";
|
ostr << "void";
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
if (Value::isValueType<Instruction>(inst->operand_list[0])) {
|
if (Value::is<Instruction>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<Instruction>(inst->operand_list[0]);
|
auto op0 = Value::as<Instruction>(inst->operand_list[0]);
|
||||||
assert(op0->ir_seqno >= 0);
|
assert(op0->ir_seqno >= 0);
|
||||||
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno;
|
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno;
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<ConstantInt>(inst->operand_list[0])) {
|
else if (Value::is<ConstantInt>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<ConstantInt>(inst->operand_list[0]);
|
auto op0 = Value::as<ConstantInt>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string();
|
ostr << op0->to_IR_string();
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<FParam>(inst->operand_list[0])) {
|
else if (Value::is<FParam>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<FParam>(inst->operand_list[0]);
|
auto op0 = Value::as<FParam>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string();
|
ostr << op0->to_IR_string();
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@ -214,38 +214,38 @@ static void _gen_blocks(std::ostream &ostr, const std::list<BasicBlockPtr_t> &bl
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case InstTag::Store: {
|
case InstTag::Store: {
|
||||||
auto inst = Value::asValueType<InstStore>(_inst);
|
auto inst = Value::as<InstStore>(_inst);
|
||||||
assert(inst->ir_seqno == -1);
|
assert(inst->ir_seqno == -1);
|
||||||
ostr << "store ";
|
ostr << "store ";
|
||||||
|
|
||||||
if (Value::isValueType<Instruction>(inst->operand_list[0])) {
|
if (Value::is<Instruction>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<Instruction>(inst->operand_list[0]);
|
auto op0 = Value::as<Instruction>(inst->operand_list[0]);
|
||||||
assert(op0->ir_seqno >= 0);
|
assert(op0->ir_seqno >= 0);
|
||||||
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno << ", ";
|
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno << ", ";
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<ConstantInt>(inst->operand_list[0])) {
|
else if (Value::is<ConstantInt>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<ConstantInt>(inst->operand_list[0]);
|
auto op0 = Value::as<ConstantInt>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string() << ", ";
|
ostr << op0->to_IR_string() << ", ";
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<FParam>(inst->operand_list[0])) {
|
else if (Value::is<FParam>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<FParam>(inst->operand_list[0]);
|
auto op0 = Value::as<FParam>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string() << ", ";
|
ostr << op0->to_IR_string() << ", ";
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
LOG(ERROR) << "Unexpected type of op0: " << inst->operand_list[0]->to_string();
|
LOG(ERROR) << "Unexpected type of op0: " << inst->operand_list[0]->to_string();
|
||||||
assert(0);
|
assert(0);
|
||||||
}
|
}
|
||||||
if (Value::isValueType<GlobalVar>(inst->operand_list[1])) {
|
if (Value::is<GlobalVar>(inst->operand_list[1])) {
|
||||||
auto op1 = Value::asValueType<GlobalVar>(inst->operand_list[1]);
|
auto op1 = Value::as<GlobalVar>(inst->operand_list[1]);
|
||||||
ostr << op1->type->to_IR_string() << " @" << op1->name;
|
ostr << op1->type->to_IR_string() << " @" << op1->name;
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<Instruction>(inst->operand_list[1])) {
|
else if (Value::is<Instruction>(inst->operand_list[1])) {
|
||||||
auto op1 = Value::asValueType<Instruction>(inst->operand_list[1]);
|
auto op1 = Value::as<Instruction>(inst->operand_list[1]);
|
||||||
assert(op1->ir_seqno >= 0);
|
assert(op1->ir_seqno >= 0);
|
||||||
ostr << op1->type->to_IR_string() << " %" << op1->ir_seqno;
|
ostr << op1->type->to_IR_string() << " %" << op1->ir_seqno;
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<FParam>(inst->operand_list[0])) {
|
else if (Value::is<FParam>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<FParam>(inst->operand_list[0]);
|
auto op0 = Value::as<FParam>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string();
|
ostr << op0->to_IR_string();
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@ -257,9 +257,9 @@ static void _gen_blocks(std::ostream &ostr, const std::list<BasicBlockPtr_t> &bl
|
|||||||
}
|
}
|
||||||
// Call's seqno is dependent on its return type
|
// Call's seqno is dependent on its return type
|
||||||
case InstTag::Call: {
|
case InstTag::Call: {
|
||||||
auto inst = Value::asValueType<InstCall>(_inst);
|
auto inst = Value::as<InstCall>(_inst);
|
||||||
LOG(DEBUG) << inst->operand_list[0]->to_string();
|
LOG(DEBUG) << inst->operand_list[0]->to_string();
|
||||||
auto func = Value::asValueType<Function>(inst->operand_list[0]);
|
auto func = Value::as<Function>(inst->operand_list[0]);
|
||||||
auto func_type = Type::asType<FunctionType>(func->type);
|
auto func_type = Type::asType<FunctionType>(func->type);
|
||||||
if (Type::isType<VoidType>(func_type->return_type)) {
|
if (Type::isType<VoidType>(func_type->return_type)) {
|
||||||
assert(inst->ir_seqno == -1);
|
assert(inst->ir_seqno == -1);
|
||||||
@ -272,17 +272,17 @@ static void _gen_blocks(std::ostream &ostr, const std::list<BasicBlockPtr_t> &bl
|
|||||||
ostr << func->name << "(";
|
ostr << func->name << "(";
|
||||||
if (inst->operand_list.size() > 1) {
|
if (inst->operand_list.size() > 1) {
|
||||||
for (int i = 1; i < inst->operand_list.size(); ++i) {
|
for (int i = 1; i < inst->operand_list.size(); ++i) {
|
||||||
if (Value::isValueType<Instruction>(inst->operand_list[i])) {
|
if (Value::is<Instruction>(inst->operand_list[i])) {
|
||||||
auto op0 = Value::asValueType<Instruction>(inst->operand_list[i]);
|
auto op0 = Value::as<Instruction>(inst->operand_list[i]);
|
||||||
assert(op0->ir_seqno >= 0);
|
assert(op0->ir_seqno >= 0);
|
||||||
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno;
|
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno;
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<ConstantInt>(inst->operand_list[i])) {
|
else if (Value::is<ConstantInt>(inst->operand_list[i])) {
|
||||||
auto op0 = Value::asValueType<ConstantInt>(inst->operand_list[i]);
|
auto op0 = Value::as<ConstantInt>(inst->operand_list[i]);
|
||||||
ostr << op0->to_IR_string();
|
ostr << op0->to_IR_string();
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<FParam>(inst->operand_list[i])) {
|
else if (Value::is<FParam>(inst->operand_list[i])) {
|
||||||
auto op0 = Value::asValueType<FParam>(inst->operand_list[i]);
|
auto op0 = Value::as<FParam>(inst->operand_list[i]);
|
||||||
ostr << op0->to_IR_string() << ", ";
|
ostr << op0->to_IR_string() << ", ";
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@ -309,36 +309,36 @@ static void _gen_blocks(std::ostream &ostr, const std::list<BasicBlockPtr_t> &bl
|
|||||||
case InstTag::Ne:
|
case InstTag::Ne:
|
||||||
case InstTag::And:
|
case InstTag::And:
|
||||||
case InstTag::Or: {
|
case InstTag::Or: {
|
||||||
auto inst = Value::asValueType<InstBinary>(_inst);
|
auto inst = Value::as<InstBinary>(_inst);
|
||||||
ostr << "%" << inst->ir_seqno << " = " << inst->to_string() << " ";
|
ostr << "%" << inst->ir_seqno << " = " << inst->to_string() << " ";
|
||||||
if (Value::isValueType<Instruction>(inst->operand_list[0])) {
|
if (Value::is<Instruction>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<Instruction>(inst->operand_list[0]);
|
auto op0 = Value::as<Instruction>(inst->operand_list[0]);
|
||||||
assert(op0->ir_seqno >= 0);
|
assert(op0->ir_seqno >= 0);
|
||||||
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno << ", ";
|
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno << ", ";
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<ConstantInt>(inst->operand_list[0])) {
|
else if (Value::is<ConstantInt>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<ConstantInt>(inst->operand_list[0]);
|
auto op0 = Value::as<ConstantInt>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string() << ", ";
|
ostr << op0->to_IR_string() << ", ";
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<FParam>(inst->operand_list[0])) {
|
else if (Value::is<FParam>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<FParam>(inst->operand_list[0]);
|
auto op0 = Value::as<FParam>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string() << ", ";
|
ostr << op0->to_IR_string() << ", ";
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
LOG(ERROR) << "Unexpected type of op0: " << inst->operand_list[0]->to_string();
|
LOG(ERROR) << "Unexpected type of op0: " << inst->operand_list[0]->to_string();
|
||||||
assert(0);
|
assert(0);
|
||||||
}
|
}
|
||||||
if (Value::isValueType<Instruction>(inst->operand_list[1])) {
|
if (Value::is<Instruction>(inst->operand_list[1])) {
|
||||||
auto op1 = Value::asValueType<Instruction>(inst->operand_list[1]);
|
auto op1 = Value::as<Instruction>(inst->operand_list[1]);
|
||||||
assert(op1->ir_seqno >= 0);
|
assert(op1->ir_seqno >= 0);
|
||||||
ostr << "%" << op1->ir_seqno;
|
ostr << "%" << op1->ir_seqno;
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<ConstantInt>(inst->operand_list[1])) {
|
else if (Value::is<ConstantInt>(inst->operand_list[1])) {
|
||||||
auto op1 = Value::asValueType<ConstantInt>(inst->operand_list[1]);
|
auto op1 = Value::as<ConstantInt>(inst->operand_list[1]);
|
||||||
ostr << op1->value;
|
ostr << op1->value;
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<FParam>(inst->operand_list[1])) {
|
else if (Value::is<FParam>(inst->operand_list[1])) {
|
||||||
auto op1 = Value::asValueType<FParam>(inst->operand_list[1]);
|
auto op1 = Value::as<FParam>(inst->operand_list[1]);
|
||||||
ostr << "%" << op1->ir_seqno;
|
ostr << "%" << op1->ir_seqno;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@ -348,21 +348,21 @@ static void _gen_blocks(std::ostream &ostr, const std::list<BasicBlockPtr_t> &bl
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case InstTag::Load: {
|
case InstTag::Load: {
|
||||||
auto inst = Value::asValueType<InstLoad>(_inst);
|
auto inst = Value::as<InstLoad>(_inst);
|
||||||
assert(inst->ir_seqno != -1);
|
assert(inst->ir_seqno != -1);
|
||||||
assert(Type::isType<PointerType>(inst->operand_list[0]->type));
|
assert(Type::isType<PointerType>(inst->operand_list[0]->type));
|
||||||
ostr << "%" << inst->ir_seqno << " = load " << inst->type->to_IR_string() << ", ";
|
ostr << "%" << inst->ir_seqno << " = load " << inst->type->to_IR_string() << ", ";
|
||||||
if (Value::isValueType<GlobalVar>(inst->operand_list[0])) {
|
if (Value::is<GlobalVar>(inst->operand_list[0])) {
|
||||||
auto op1 = Value::asValueType<GlobalVar>(inst->operand_list[0]);
|
auto op1 = Value::as<GlobalVar>(inst->operand_list[0]);
|
||||||
ostr << op1->type->to_IR_string() << " @" << op1->name;
|
ostr << op1->type->to_IR_string() << " @" << op1->name;
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<Instruction>(inst->operand_list[0])) {
|
else if (Value::is<Instruction>(inst->operand_list[0])) {
|
||||||
auto op1 = Value::asValueType<Instruction>(inst->operand_list[0]);
|
auto op1 = Value::as<Instruction>(inst->operand_list[0]);
|
||||||
assert(op1->ir_seqno >= 0);
|
assert(op1->ir_seqno >= 0);
|
||||||
ostr << op1->type->to_IR_string() << " %" << op1->ir_seqno;
|
ostr << op1->type->to_IR_string() << " %" << op1->ir_seqno;
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<FParam>(inst->operand_list[0])) {
|
else if (Value::is<FParam>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<FParam>(inst->operand_list[0]);
|
auto op0 = Value::as<FParam>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string();
|
ostr << op0->to_IR_string();
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@ -372,21 +372,21 @@ static void _gen_blocks(std::ostream &ostr, const std::list<BasicBlockPtr_t> &bl
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case InstTag::GEP: {
|
case InstTag::GEP: {
|
||||||
auto inst = Value::asValueType<InstGEP>(_inst);
|
auto inst = Value::as<InstGEP>(_inst);
|
||||||
|
|
||||||
assert(inst->ir_seqno >= 0);
|
assert(inst->ir_seqno >= 0);
|
||||||
auto pointer_type = Type::asType<PointerType>(inst->operand_list[0]->type);
|
auto pointer_type = Type::asType<PointerType>(inst->operand_list[0]->type);
|
||||||
ostr << "%" << inst->ir_seqno << " = getelementptr " << pointer_type->pointed_type->to_IR_string() << ", ";
|
ostr << "%" << inst->ir_seqno << " = getelementptr " << pointer_type->pointed_type->to_IR_string() << ", ";
|
||||||
if (Value::isValueType<GlobalVar>(inst->operand_list[0])) {
|
if (Value::is<GlobalVar>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<GlobalVar>(inst->operand_list[0]);
|
auto op0 = Value::as<GlobalVar>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string();
|
ostr << op0->to_IR_string();
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<Instruction>(inst->operand_list[0])) {
|
else if (Value::is<Instruction>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<Instruction>(inst->operand_list[0]);
|
auto op0 = Value::as<Instruction>(inst->operand_list[0]);
|
||||||
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno;
|
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno;
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<FParam>(inst->operand_list[0])) {
|
else if (Value::is<FParam>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<FParam>(inst->operand_list[0]);
|
auto op0 = Value::as<FParam>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string();
|
ostr << op0->to_IR_string();
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@ -399,7 +399,7 @@ static void _gen_blocks(std::ostream &ostr, const std::list<BasicBlockPtr_t> &bl
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case InstTag::Alloca: {
|
case InstTag::Alloca: {
|
||||||
auto inst = Value::asValueType<InstAlloca>(_inst);
|
auto inst = Value::as<InstAlloca>(_inst);
|
||||||
assert(inst->ir_seqno != -1);
|
assert(inst->ir_seqno != -1);
|
||||||
auto pointer_type = Type::asType<PointerType>(inst->type);
|
auto pointer_type = Type::asType<PointerType>(inst->type);
|
||||||
ostr << "%" << inst->ir_seqno << " = alloca " << pointer_type->pointed_type->to_IR_string() << ", align 4";
|
ostr << "%" << inst->ir_seqno << " = alloca " << pointer_type->pointed_type->to_IR_string() << ", align 4";
|
||||||
@ -407,20 +407,20 @@ static void _gen_blocks(std::ostream &ostr, const std::list<BasicBlockPtr_t> &bl
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case InstTag::Zext: {
|
case InstTag::Zext: {
|
||||||
auto inst = Value::asValueType<InstZext>(_inst);
|
auto inst = Value::as<InstZext>(_inst);
|
||||||
assert(inst->ir_seqno >= 0);
|
assert(inst->ir_seqno >= 0);
|
||||||
ostr << "%" << inst->ir_seqno << " = zext ";
|
ostr << "%" << inst->ir_seqno << " = zext ";
|
||||||
if (Value::isValueType<Instruction>(inst->operand_list[0])) {
|
if (Value::is<Instruction>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<Instruction>(inst->operand_list[0]);
|
auto op0 = Value::as<Instruction>(inst->operand_list[0]);
|
||||||
assert(op0->ir_seqno >= 0);
|
assert(op0->ir_seqno >= 0);
|
||||||
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno << "to ";
|
ostr << op0->type->to_IR_string() << " %" << op0->ir_seqno << "to ";
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<ConstantInt>(inst->operand_list[0])) {
|
else if (Value::is<ConstantInt>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<ConstantInt>(inst->operand_list[0]);
|
auto op0 = Value::as<ConstantInt>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string() << "to ";
|
ostr << op0->to_IR_string() << "to ";
|
||||||
}
|
}
|
||||||
else if (Value::isValueType<FParam>(inst->operand_list[0])) {
|
else if (Value::is<FParam>(inst->operand_list[0])) {
|
||||||
auto op0 = Value::asValueType<FParam>(inst->operand_list[0]);
|
auto op0 = Value::as<FParam>(inst->operand_list[0]);
|
||||||
ostr << op0->to_IR_string() << "to ";
|
ostr << op0->to_IR_string() << "to ";
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user