first trial

This commit is contained in:
2024-10-22 12:52:34 +00:00
parent 17816f2bf0
commit 722c1373ac
5 changed files with 42 additions and 4 deletions

View File

@ -13,7 +13,7 @@ build:
@cd $(BUILD_DIR) && $(MAKE) -j4 @cd $(BUILD_DIR) && $(MAKE) -j4
acturalrun: acturalrun:
@cd $(BUILD_DIR) && ./zmxcc /dev/stdin -o /dev/stdout 2>/dev/null @cd $(BUILD_DIR) && ./zmxcc /dev/stdin -o /dev/stdout --optimize-all 2>/dev/null
# 运行目标,运行生成的可执行文件 # 运行目标,运行生成的可执行文件
run: acturalrun run: acturalrun
@cat $(BUILTIN_ASM) >>/dev/stdout @cat $(BUILTIN_ASM) >>/dev/stdout

View File

@ -269,6 +269,8 @@ class CallItem : public ActionItem {
std::vector<LLVMType> args_ty; std::vector<LLVMType> args_ty;
std::vector<std::string> args_val_full; std::vector<std::string> args_val_full;
size_t move_sp_up;
CallItem() = default; CallItem() = default;
void RecursivePrint(std::ostream &os) const { void RecursivePrint(std::ostream &os) const {
if (std::holds_alternative<LLVMVOIDType>(return_type)) { if (std::holds_alternative<LLVMVOIDType>(return_type)) {

View File

@ -160,6 +160,8 @@ inline void FetchValueToReg(std::string original_val, std::string &out_reg, Func
// immediate value // immediate value
out_reg = AllocateTmpReg(available_tmp_regs); out_reg = AllocateTmpReg(available_tmp_regs);
StoreImmToReg(std::stoi(original_val), out_reg, code_lines); StoreImmToReg(std::stoi(original_val), out_reg, code_lines);
} else if (original_val == "null") {
out_reg = "x0";
} else { } else {
throw std::runtime_error("Unknown value type"); throw std::runtime_error("Unknown value type");
} }
@ -412,6 +414,10 @@ inline void GenerateASM(std::shared_ptr<ActionItem> act, std::vector<std::string
} else if (auto call_act = std::dynamic_pointer_cast<CallItem>(act)) { } else if (auto call_act = std::dynamic_pointer_cast<CallItem>(act)) {
// no need to to further process, as callling convention is handled in reg alloc // no need to to further process, as callling convention is handled in reg alloc
code_lines.push_back("call " + call_act->func_name_raw); code_lines.push_back("call " + call_act->func_name_raw);
if (call_act->move_sp_up) {
size_t delta = 4 * call_act->move_sp_up;
code_lines.push_back("addi sp, sp, " + std::to_string(delta));
}
} else if (auto phi_act = std::dynamic_pointer_cast<PhiItem>(act)) { } else if (auto phi_act = std::dynamic_pointer_cast<PhiItem>(act)) {
throw std::runtime_error("Phi should not be in the layout"); throw std::runtime_error("Phi should not be in the layout");
} else if (auto select_act = std::dynamic_pointer_cast<SelectItem>(act)) { } else if (auto select_act = std::dynamic_pointer_cast<SelectItem>(act)) {
@ -440,9 +446,30 @@ inline void GenerateASM(std::shared_ptr<ActionItem> act, std::vector<std::string
WriteToSpilledVar(select_act->result_full, res_reg, layout, code_lines, available_tmp_regs); WriteToSpilledVar(select_act->result_full, res_reg, layout, code_lines, available_tmp_regs);
} }
} else if (auto load_spilled_args_act = std::dynamic_pointer_cast<opt::LoadSpilledArgs>(act)) { } else if (auto load_spilled_args_act = std::dynamic_pointer_cast<opt::LoadSpilledArgs>(act)) {
throw std::runtime_error("Not implemented"); std::string res_reg;
bool need_extra_store = false;
if (load_spilled_args_act->var_full[0] == '$') {
res_reg = ExtractRegName(load_spilled_args_act->var_full);
} else if (load_spilled_args_act->var_full[0] == '#') {
need_extra_store = true;
res_reg = AllocateTmpReg(available_tmp_regs);
} else {
throw std::runtime_error("Unknown result type");
}
size_t offset = 4 * (load_spilled_args_act->arg_id - 8);
code_lines.push_back("lw " + res_reg + ", " + std::to_string(offset) + "(s0)");
if (need_extra_store) {
WriteToSpilledVar(load_spilled_args_act->var_full, res_reg, layout, code_lines, available_tmp_regs);
}
} else if (auto store_spilled_args_act = std::dynamic_pointer_cast<opt::StoreSpilledArgs>(act)) { } else if (auto store_spilled_args_act = std::dynamic_pointer_cast<opt::StoreSpilledArgs>(act)) {
throw std::runtime_error("Not implemented"); if (store_spilled_args_act->move_sp_down) {
size_t delta = 4 * store_spilled_args_act->move_sp_down;
code_lines.push_back("addi sp, sp, -" + std::to_string(delta));
}
std::string val_reg;
FetchValueToReg(store_spilled_args_act->var_full, val_reg, layout, code_lines, available_tmp_regs);
size_t offset = 4 * (store_spilled_args_act->arg_id - 8);
code_lines.push_back("sw " + val_reg + ", " + std::to_string(offset) + "(sp)");
} else if (auto move_act = std::dynamic_pointer_cast<opt::MoveInstruct>(act)) { } else if (auto move_act = std::dynamic_pointer_cast<opt::MoveInstruct>(act)) {
std::string src_reg; std::string src_reg;
FetchValueToReg(move_act->src_full, src_reg, layout, code_lines, available_tmp_regs); FetchValueToReg(move_act->src_full, src_reg, layout, code_lines, available_tmp_regs);

View File

@ -35,6 +35,7 @@ class StoreSpilledArgs : public ActionItem {
size_t arg_id; // [8,+inf) size_t arg_id; // [8,+inf)
std::string var_full; std::string var_full;
LLVMType ty; LLVMType ty;
size_t move_sp_down;
StoreSpilledArgs() = default; StoreSpilledArgs() = default;
void RecursivePrint(std::ostream &os) const { void RecursivePrint(std::ostream &os) const {
os << "[Persudo] store spilled args " << var_full << "with id=" << arg_id << "\n"; os << "[Persudo] store spilled args " << var_full << "with id=" << arg_id << "\n";

View File

@ -100,15 +100,23 @@ void EnforcePhysicalRegs(CFGType &cfg) {
caller_saved_regs_to_process.erase(arg_regs[i]); caller_saved_regs_to_process.erase(arg_regs[i]);
} }
if (call_act->args_val_full.size() > 8) { if (call_act->args_val_full.size() > 8) {
for (size_t i = 8; i < call_act->args_val_full.size(); i++) { for (size_t i = call_act->args_val_full.size() - 1; i >= 8; i--) {
auto new_store = std::make_shared<StoreSpilledArgs>(); auto new_store = std::make_shared<StoreSpilledArgs>();
new_store->arg_id = i; new_store->arg_id = i;
new_store->var_full = call_act->args_val_full[i]; new_store->var_full = call_act->args_val_full[i];
new_store->ty = call_act->args_ty[i]; new_store->ty = call_act->args_ty[i];
block->actions.insert(it_act, new_store); block->actions.insert(it_act, new_store);
if (i == call_act->args_val_full.size() - 1) {
new_store->move_sp_down = call_act->args_val_full.size() - 8;
} else {
new_store->move_sp_down = 0;
}
} }
call_act->move_sp_up = call_act->args_val_full.size() - 8;
call_act->args_val_full.resize(8); call_act->args_val_full.resize(8);
call_act->args_ty.resize(8); call_act->args_ty.resize(8);
} else {
call_act->move_sp_up = 0;
} }
for (auto reg : caller_saved_regs_to_process) { for (auto reg : caller_saved_regs_to_process) {
auto new_def = std::make_shared<ForceDef>(); auto new_def = std::make_shared<ForceDef>();