style(ir): 纠正代码位置
This commit is contained in:
@@ -3,3 +3,22 @@
|
||||
// - 维护或可计算前驱/后继关系,用于 CFG 分析与优化
|
||||
|
||||
#include "ir/IR.h"
|
||||
|
||||
#include <utility>
|
||||
|
||||
namespace ir {
|
||||
|
||||
BasicBlock::BasicBlock(std::string name) : name_(std::move(name)) {}
|
||||
|
||||
const std::string& BasicBlock::name() const { return name_; }
|
||||
|
||||
bool BasicBlock::HasTerminator() const {
|
||||
return !instructions_.empty() && instructions_.back()->IsTerminator();
|
||||
}
|
||||
|
||||
const std::vector<std::unique_ptr<Instruction>>& BasicBlock::instructions()
|
||||
const {
|
||||
return instructions_;
|
||||
}
|
||||
|
||||
} // namespace ir
|
||||
|
||||
@@ -20,4 +20,12 @@ BasicBlock* Function::CreateBlock(const std::string& name) {
|
||||
return ptr;
|
||||
}
|
||||
|
||||
BasicBlock* Function::entry() { return entry_; }
|
||||
|
||||
const BasicBlock* Function::entry() const { return entry_; }
|
||||
|
||||
const std::vector<std::unique_ptr<BasicBlock>>& Function::blocks() const {
|
||||
return blocks_;
|
||||
}
|
||||
|
||||
} // namespace ir
|
||||
|
||||
75
src/ir/IR.h
75
src/ir/IR.h
@@ -41,8 +41,8 @@ Context& DefaultContext();
|
||||
class Type {
|
||||
public:
|
||||
enum class Kind { Void, Int32, PtrInt32 };
|
||||
explicit Type(Kind k) : kind_(k) {}
|
||||
Kind kind() const { return kind_; }
|
||||
explicit Type(Kind k);
|
||||
Kind kind() const;
|
||||
static std::shared_ptr<Type> Void();
|
||||
static std::shared_ptr<Type> Int32();
|
||||
static std::shared_ptr<Type> PtrInt32();
|
||||
@@ -53,14 +53,13 @@ class Type {
|
||||
|
||||
class Value {
|
||||
public:
|
||||
Value(std::shared_ptr<Type> ty, std::string name)
|
||||
: type_(std::move(ty)), name_(std::move(name)) {}
|
||||
Value(std::shared_ptr<Type> ty, std::string name);
|
||||
virtual ~Value() = default;
|
||||
const std::shared_ptr<Type>& type() const { return type_; }
|
||||
const std::string& name() const { return name_; }
|
||||
void set_name(std::string n) { name_ = std::move(n); }
|
||||
void AddUser(Instruction* user) { users_.push_back(user); }
|
||||
const std::vector<Instruction*>& users() const { return users_; }
|
||||
const std::shared_ptr<Type>& type() const;
|
||||
const std::string& name() const;
|
||||
void set_name(std::string n);
|
||||
void AddUser(Instruction* user);
|
||||
const std::vector<Instruction*>& users() const;
|
||||
|
||||
protected:
|
||||
std::shared_ptr<Type> type_;
|
||||
@@ -77,16 +76,16 @@ class ConstantInt : public Value {
|
||||
int value_{};
|
||||
};
|
||||
|
||||
// 后续还需要扩展更多指令类型。
|
||||
enum class Opcode { Add, Sub, Mul, Alloca, Load, Store, Ret };
|
||||
|
||||
class Instruction : public Value {
|
||||
public:
|
||||
Instruction(Opcode op, std::shared_ptr<Type> ty, std::string name = "")
|
||||
: Value(std::move(ty), std::move(name)), opcode_(op) {}
|
||||
Opcode opcode() const { return opcode_; }
|
||||
bool IsTerminator() const { return opcode_ == Opcode::Ret; }
|
||||
BasicBlock* parent() const { return parent_; }
|
||||
void set_parent(BasicBlock* parent) { parent_ = parent; }
|
||||
Instruction(Opcode op, std::shared_ptr<Type> ty, std::string name = "");
|
||||
Opcode opcode() const;
|
||||
bool IsTerminator() const;
|
||||
BasicBlock* parent() const;
|
||||
void set_parent(BasicBlock* parent);
|
||||
|
||||
private:
|
||||
Opcode opcode_;
|
||||
@@ -97,8 +96,8 @@ class BinaryInst : public Instruction {
|
||||
public:
|
||||
BinaryInst(Opcode op, std::shared_ptr<Type> ty, Value* lhs, Value* rhs,
|
||||
std::string name);
|
||||
Value* lhs() const { return lhs_; }
|
||||
Value* rhs() const { return rhs_; }
|
||||
Value* lhs() const;
|
||||
Value* rhs() const;
|
||||
|
||||
private:
|
||||
Value* lhs_;
|
||||
@@ -108,7 +107,7 @@ class BinaryInst : public Instruction {
|
||||
class ReturnInst : public Instruction {
|
||||
public:
|
||||
explicit ReturnInst(Value* val);
|
||||
Value* value() const { return value_; }
|
||||
Value* value() const;
|
||||
|
||||
private:
|
||||
Value* value_;
|
||||
@@ -122,7 +121,7 @@ class AllocaInst : public Instruction {
|
||||
class LoadInst : public Instruction {
|
||||
public:
|
||||
LoadInst(Value* ptr, std::string name);
|
||||
Value* ptr() const { return ptr_; }
|
||||
Value* ptr() const;
|
||||
|
||||
private:
|
||||
Value* ptr_;
|
||||
@@ -131,8 +130,8 @@ class LoadInst : public Instruction {
|
||||
class StoreInst : public Instruction {
|
||||
public:
|
||||
StoreInst(Value* val, Value* ptr);
|
||||
Value* value() const { return value_; }
|
||||
Value* ptr() const { return ptr_; }
|
||||
Value* value() const;
|
||||
Value* ptr() const;
|
||||
|
||||
private:
|
||||
Value* value_;
|
||||
@@ -141,14 +140,10 @@ class StoreInst : public Instruction {
|
||||
|
||||
class BasicBlock {
|
||||
public:
|
||||
explicit BasicBlock(std::string name) : name_(std::move(name)) {}
|
||||
const std::string& name() const { return name_; }
|
||||
bool HasTerminator() const {
|
||||
return !instructions_.empty() && instructions_.back()->IsTerminator();
|
||||
}
|
||||
const std::vector<std::unique_ptr<Instruction>>& instructions() const {
|
||||
return instructions_;
|
||||
}
|
||||
explicit BasicBlock(std::string name);
|
||||
const std::string& name() const;
|
||||
bool HasTerminator() const;
|
||||
const std::vector<std::unique_ptr<Instruction>>& instructions() const;
|
||||
template <typename T, typename... Args>
|
||||
T* Append(Args&&... args) {
|
||||
if (HasTerminator()) {
|
||||
@@ -172,11 +167,9 @@ class Function : public Value {
|
||||
// 允许显式指定返回类型,便于后续扩展多种函数签名。
|
||||
Function(std::string name, std::shared_ptr<Type> ret_type);
|
||||
BasicBlock* CreateBlock(const std::string& name);
|
||||
BasicBlock* entry() { return entry_; }
|
||||
const BasicBlock* entry() const { return entry_; }
|
||||
const std::vector<std::unique_ptr<BasicBlock>>& blocks() const {
|
||||
return blocks_;
|
||||
}
|
||||
BasicBlock* entry();
|
||||
const BasicBlock* entry() const;
|
||||
const std::vector<std::unique_ptr<BasicBlock>>& blocks() const;
|
||||
|
||||
private:
|
||||
BasicBlock* entry_ = nullptr;
|
||||
@@ -188,9 +181,7 @@ class Module {
|
||||
// 创建函数时显式传入返回类型,便于在 IRGen 中根据语法树信息选择类型。
|
||||
Function* CreateFunction(const std::string& name,
|
||||
std::shared_ptr<Type> ret_type);
|
||||
const std::vector<std::unique_ptr<Function>>& functions() const {
|
||||
return functions_;
|
||||
}
|
||||
const std::vector<std::unique_ptr<Function>>& functions() const;
|
||||
|
||||
private:
|
||||
std::vector<std::unique_ptr<Function>> functions_;
|
||||
@@ -198,17 +189,15 @@ class Module {
|
||||
|
||||
class IRBuilder {
|
||||
public:
|
||||
explicit IRBuilder(BasicBlock* bb) : insertBlock_(bb) {}
|
||||
void SetInsertPoint(BasicBlock* bb) { insertBlock_ = bb; }
|
||||
BasicBlock* GetInsertBlock() const { return insertBlock_; }
|
||||
explicit IRBuilder(BasicBlock* bb);
|
||||
void SetInsertPoint(BasicBlock* bb);
|
||||
BasicBlock* GetInsertBlock() const;
|
||||
|
||||
// 构造常量、二元运算、返回指令的最小集合。
|
||||
ConstantInt* CreateConstInt(int v);
|
||||
BinaryInst* CreateBinary(Opcode op, Value* lhs, Value* rhs,
|
||||
const std::string& name);
|
||||
BinaryInst* CreateAdd(Value* lhs, Value* rhs, const std::string& name) {
|
||||
return CreateBinary(Opcode::Add, lhs, rhs, name);
|
||||
}
|
||||
BinaryInst* CreateAdd(Value* lhs, Value* rhs, const std::string& name);
|
||||
AllocaInst* CreateAllocaI32(const std::string& name);
|
||||
LoadInst* CreateLoad(Value* ptr, const std::string& name);
|
||||
StoreInst* CreateStore(Value* val, Value* ptr);
|
||||
|
||||
@@ -18,6 +18,12 @@ bool IsPtrInt32Type(const std::shared_ptr<Type>& ty) {
|
||||
|
||||
} // namespace
|
||||
|
||||
IRBuilder::IRBuilder(BasicBlock* bb) : insertBlock_(bb) {}
|
||||
|
||||
void IRBuilder::SetInsertPoint(BasicBlock* bb) { insertBlock_ = bb; }
|
||||
|
||||
BasicBlock* IRBuilder::GetInsertBlock() const { return insertBlock_; }
|
||||
|
||||
ConstantInt* IRBuilder::CreateConstInt(int v) {
|
||||
// 常量不需要挂在基本块里,由 Context 负责去重与生命周期。
|
||||
return DefaultContext().GetConstInt(v);
|
||||
@@ -47,6 +53,11 @@ BinaryInst* IRBuilder::CreateBinary(Opcode op, Value* lhs, Value* rhs,
|
||||
return insertBlock_->Append<BinaryInst>(op, lhs->type(), lhs, rhs, name);
|
||||
}
|
||||
|
||||
BinaryInst* IRBuilder::CreateAdd(Value* lhs, Value* rhs,
|
||||
const std::string& name) {
|
||||
return CreateBinary(Opcode::Add, lhs, rhs, name);
|
||||
}
|
||||
|
||||
AllocaInst* IRBuilder::CreateAllocaI32(const std::string& name) {
|
||||
if (!insertBlock_) {
|
||||
throw std::runtime_error("IRBuilder 未设置插入点");
|
||||
|
||||
@@ -18,6 +18,17 @@ bool IsPtrInt32Type(const std::shared_ptr<Type>& ty) {
|
||||
|
||||
} // namespace
|
||||
|
||||
Instruction::Instruction(Opcode op, std::shared_ptr<Type> ty, std::string name)
|
||||
: Value(std::move(ty), std::move(name)), opcode_(op) {}
|
||||
|
||||
Opcode Instruction::opcode() const { return opcode_; }
|
||||
|
||||
bool Instruction::IsTerminator() const { return opcode_ == Opcode::Ret; }
|
||||
|
||||
BasicBlock* Instruction::parent() const { return parent_; }
|
||||
|
||||
void Instruction::set_parent(BasicBlock* parent) { parent_ = parent; }
|
||||
|
||||
BinaryInst::BinaryInst(Opcode op, std::shared_ptr<Type> ty, Value* lhs,
|
||||
Value* rhs, std::string name)
|
||||
: Instruction(op, std::move(ty), std::move(name)), lhs_(lhs), rhs_(rhs) {
|
||||
@@ -45,6 +56,10 @@ BinaryInst::BinaryInst(Opcode op, std::shared_ptr<Type> ty, Value* lhs,
|
||||
}
|
||||
}
|
||||
|
||||
Value* BinaryInst::lhs() const { return lhs_; }
|
||||
|
||||
Value* BinaryInst::rhs() const { return rhs_; }
|
||||
|
||||
ReturnInst::ReturnInst(Value* val)
|
||||
: Instruction(Opcode::Ret, Type::Void(), ""), value_(val) {
|
||||
if (!value_) {
|
||||
@@ -53,6 +68,8 @@ ReturnInst::ReturnInst(Value* val)
|
||||
value_->AddUser(this);
|
||||
}
|
||||
|
||||
Value* ReturnInst::value() const { return value_; }
|
||||
|
||||
AllocaInst::AllocaInst(std::string name)
|
||||
: Instruction(Opcode::Alloca, Type::PtrInt32(), std::move(name)) {}
|
||||
|
||||
@@ -67,6 +84,8 @@ LoadInst::LoadInst(Value* ptr, std::string name)
|
||||
ptr_->AddUser(this);
|
||||
}
|
||||
|
||||
Value* LoadInst::ptr() const { return ptr_; }
|
||||
|
||||
StoreInst::StoreInst(Value* val, Value* ptr)
|
||||
: Instruction(Opcode::Store, Type::Void(), ""), value_(val), ptr_(ptr) {
|
||||
if (!value_) {
|
||||
@@ -85,4 +104,8 @@ StoreInst::StoreInst(Value* val, Value* ptr)
|
||||
ptr_->AddUser(this);
|
||||
}
|
||||
|
||||
Value* StoreInst::value() const { return value_; }
|
||||
|
||||
Value* StoreInst::ptr() const { return ptr_; }
|
||||
|
||||
} // namespace ir
|
||||
|
||||
@@ -12,4 +12,8 @@ Function* Module::CreateFunction(const std::string& name,
|
||||
return functions_.back().get();
|
||||
}
|
||||
|
||||
const std::vector<std::unique_ptr<Function>>& Module::functions() const {
|
||||
return functions_;
|
||||
}
|
||||
|
||||
} // namespace ir
|
||||
|
||||
@@ -6,6 +6,10 @@
|
||||
|
||||
namespace ir {
|
||||
|
||||
Type::Type(Kind k) : kind_(k) {}
|
||||
|
||||
Type::Kind Type::kind() const { return kind_; }
|
||||
|
||||
std::shared_ptr<Type> Type::Void() { return DefaultContext().Void(); }
|
||||
|
||||
std::shared_ptr<Type> Type::Int32() { return DefaultContext().Int32(); }
|
||||
|
||||
@@ -5,6 +5,19 @@
|
||||
|
||||
namespace ir {
|
||||
|
||||
Value::Value(std::shared_ptr<Type> ty, std::string name)
|
||||
: type_(std::move(ty)), name_(std::move(name)) {}
|
||||
|
||||
const std::shared_ptr<Type>& Value::type() const { return type_; }
|
||||
|
||||
const std::string& Value::name() const { return name_; }
|
||||
|
||||
void Value::set_name(std::string n) { name_ = std::move(n); }
|
||||
|
||||
void Value::AddUser(Instruction* user) { users_.push_back(user); }
|
||||
|
||||
const std::vector<Instruction*>& Value::users() const { return users_; }
|
||||
|
||||
ConstantInt::ConstantInt(int v) : Value(Type::Int32(), ""), value_(v) {}
|
||||
|
||||
} // namespace ir
|
||||
|
||||
Reference in New Issue
Block a user