Files
Interpreter/compiler/include/compiler/MachineConfig.h
T

165 lines
6.7 KiB
C++
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/**
* @file MachineConfig.h
* @brief 机器定义(machine.toml)加载与强校验
* @author
* @date 2026-08-21
*
* @details 见 Doc/isa/指令配置.md
* - 配置只给编译器(toml++ 运行时加载);vm 不读配置(内建全指令集)
* - 强校验 5 项:字段必填 / type.base 命中内建基元·range 合法·tag 契约 /
* op opcode 唯一·类别-格式互锁 / fb.opcode 与 op 一致·字段类型命中 type 表
* - 基元内置(bit/int8..uint64/float32/float64,元数据在代码)
*/
#pragma once
#include <cstdint>
#include <string>
#include <vector>
namespace compiler {
/**
* @brief 内建基元(编译器内建,C 语义)。
* @details 元数据写在代码而非 machine.toml;配置类型的 base 必须命中本表。
*/
struct PrimType {
const char* name; ///< 基元名(bit / int8..uint64 / float32 / float64
uint32_t width; ///< 宽度(字节)
bool is_signed; ///< 是否带符号
bool is_float; ///< 是否浮点
};
/**
* @brief 配置类型 = 基元别名(+ 值域约束 + .stb 契约 tag)。
* @details 对应 machine.toml [[type]] 行:base 必为内建基元名;range 可选且
* min ≤ maxtag 与 .stb 常量表契约一致(0=BOOL、1=INT、2=TIME,唯一)。
*/
struct ConfigType {
std::string name; ///< 配置类型名(大写,如 BOOL/INT/TIME
std::string base; ///< 基元名(命中内建基元表)
bool has_range = false; ///< 是否有值域约束
int64_t range_min = 0; ///< 值域下界(含)
int64_t range_max = 0; ///< 值域上界(含)
uint32_t tag = 0; ///< .stb 常量表契约 tag
};
/**
* @brief 配置指令。
* @details 对应 machine.toml [[op]] 行:opcode 唯一且 0..255class 与 format
* 互锁(INSTANCE ↔ CAL);params 数量与 format 期望一致。
*/
struct ConfigOp {
std::string name; ///< 助记符(与 .stb / isa 一致)
uint32_t opcode = 0; ///< 操作码(0..255,表内唯一)
bool is_instance = false; ///< classinstance / plain
std::string format; ///< 操作数形态:RR/RRR/IMM/SLOT/JMP/JC/CALL/CAL/NONE
std::vector<std::string> params; ///< 参数名(数量与 format 一致)
bool enabled = false; ///< 是否启用
};
/**
* @brief 内建 FB 的一个字段。
*/
struct ConfigFbField {
std::string name; ///< 字段名(如 in/pt/q/et/cu/cv
std::string type; ///< 配置类型名(BOOL/INT/TIME
};
/**
* @brief 内建功能块(FB)布局登记。
* @details 对应 machine.toml [[fb]] 行;opcode 必须命中 instance 类 op 行。
*/
struct ConfigFb {
std::string name; ///< FB 名(小写,如 ton/ctu
uint32_t opcode = 0; ///< 对应 op 行 opcodeCAL_*
std::vector<ConfigFbField> fields; ///< 字段列表(名称唯一,类型命中 type 表)
};
/**
* @brief 机器定义:加载 machine.toml 并做强校验。
* @details 编译器指令集 / 类型的唯一事实来源;校验失败时 ok() 为 false
* err 前缀 "machine error"。vm 不读配置(内建全指令集)。
*/
class MachineConfig {
public:
/**
* @brief 加载 + 强校验。
* @param path machine.toml 路径
* @param err 错误输出;可为 nullptr(静默)
* @return true 成功;falseerr 已写,前缀 "machine error"
* @details 强校验项:字段必填 / type.base 命中内建基元·range 合法·tag 契约 /
* op opcode 唯一·类别-格式互锁 / fb.opcode 与 op 一致·字段类型命中
* type 表(清单见文件头)。
*/
bool load(const std::string& path, std::string* err);
/// @brief 加载是否成功(校验通过)。
bool ok() const { return ok_; }
/// @brief 型号名(meta.name,参与 .stb 型号标识)。
const std::string& model_name() const { return model_name_; }
/// @brief 指令集版本(meta.version,参与 .stb 型号标识)。
uint32_t version() const { return version_; }
/// @brief 配置类型表([[type]])。
const std::vector<ConfigType>& types() const { return types_; }
/// @brief 配置指令表([[op]])。
const std::vector<ConfigOp>& ops() const { return ops_; }
/// @brief 内建 FB 表([[fb]])。
const std::vector<ConfigFb>& fbs() const { return fbs_; }
/**
* @brief 按配置类型名查类型行。
* @param name 配置类型名
* @return 命中指针;未找到返回 nullptr
*/
const ConfigType* find_type(const std::string& name) const;
/**
* @brief 按助记符查指令行。
* @param name 助记符(如 "MOVE"
* @return 命中指针;未找到返回 nullptr
*/
const ConfigOp* find_op(const std::string& name) const;
/**
* @brief 按 opcode 查指令行。
* @param opcode 操作码(0..255
* @return 命中指针;未找到返回 nullptr
*/
const ConfigOp* find_op_by_code(uint32_t opcode) const;
/**
* @brief 查询某 opcode 是否启用。
* @param opcode 操作码
* @return 指令存在且 enabled 为 true;未知 opcode 返回 false
*/
bool op_enabled(uint32_t opcode) const;
/**
* @brief 按名称查内建 FB。
* @param name FB 名(小写,如 "ton"
* @return 命中指针;未找到返回 nullptr
*/
const ConfigFb* find_fb(const std::string& name) const;
/// @brief 内建基元表(bit / int8..uint64 / float32 / float64)。
static const std::vector<PrimType>& prims();
/**
* @brief 按名称查内建基元。
* @param name 基元名
* @return 命中指针;未找到返回 nullptr
*/
static const PrimType* find_prim(const std::string& name);
private:
bool ok_ = false; ///< 加载成功标志
std::string model_name_; ///< 型号名(meta.name
uint32_t version_ = 0; ///< 指令集版本(meta.version
std::vector<ConfigType> types_; ///< 配置类型表
std::vector<ConfigOp> ops_; ///< 配置指令表
std::vector<ConfigFb> fbs_; ///< 内建 FB 表
};
}