diff --git a/docs/ECOGEN_Cpp_Source_Study.md b/docs/ECOGEN_Cpp_Source_Study.md new file mode 100644 index 000000000..21230a16f --- /dev/null +++ b/docs/ECOGEN_Cpp_Source_Study.md @@ -0,0 +1,179 @@ +# ECOGEN C++ 源码学习文档(结构与内容导读) + +> 目标:帮助你快速建立“ECOGEN C++ 源码结构 + 运行主流程 + 关键模块职责”的整体认知,为后续深入阅读与二次开发打基础。 + +## 1. 项目定位与总体结构 + +ECOGEN 是一个面向可压缩多相流的 CFD 平台,采用 C++ 面向对象设计,官方 README 给出了项目定位与外部文档入口(用户文档与 API 文档)。【F:README.md†L1-L14】 + +从构建层面看,`CMakeLists.txt` 将 `src` 下的所有 `*.cpp` 作为可执行文件的源代码,项目名为 `ECOGEN`,强制使用 C++11,并依赖 MPI。【F:CMakeLists.txt†L1-L36】 + +**结构总览(以源码目录为核心):** +- `src/`:主要 C++ 源码与模块目录(核心逻辑)。【F:CMakeLists.txt†L27-L36】 +- `libEOS/`、`libMeshes/`、`libTests/` 等:配套库与测试资源(详细内容需按需深入)。 +- `docs/`:现有文档与生成的 API/手册。 + +> 本学习文档重点聚焦 `src/` 的核心结构与主流程。 + +## 2. 入口与主流程:`main.cpp` + +`main.cpp` 是程序入口,负责: +- 初始化 MPI; +- 解析 `ECOGEN.xml` 主配置文件; +- 遍历 `testCase` 列表逐个执行; +- 每个测试用例通过 `Run` 生命周期:`initialize()` → `solver()` → `finalize()`; +- 捕获输入异常与运行时异常,并进行输出和清理。【F:src/main.cpp†L33-L154】 + +关键流程片段: +1. MPI 初始化与 rank/size 获取。【F:src/main.cpp†L49-L57】 +2. 通过 `tinyxml2` 解析 `ECOGEN.xml` 并定位 `` 列表。【F:src/main.cpp†L65-L99】 +3. 对每个 `testCase`:构造 `Run`,执行 `initialize/solver/finalize`。【F:src/main.cpp†L90-L117】 +4. 错误处理分为输入异常与运行时异常,分别处理与释放资源。【F:src/main.cpp†L121-L153】 + +## 3. 核心调度类:`Run` + +`Run` 是一次模拟的中心对象,聚合了**网格、物理模型、流体状态、IO、时间推进、额外物理、源项、并行通信**等关键组件。【F:src/Run.h】 + +### 3.1 `Run` 的职责 +- **初始化**:读入输入文件、创建网格与物理模型、初始化状态等。 +- **求解**:包含双曲项、额外物理、源项、松弛等过程(由内部函数分层调用)。【F:src/Run.h】 +- **收尾**:释放资源、整理输出。 + +### 3.2 `Run` 关联的关键对象(学习重点) +`Run` 内部持有的重要指针/成员,指明了系统的核心协作关系: +- **Mesh**:`m_mesh`(网格对象,包含几何信息)。【F:src/Run.h】 +- **Model**:`m_model`(物理模型与状态演化逻辑)。【F:src/Run.h】 +- **Gradient/Limiter**:梯度与限制器用于高阶空间离散。【F:src/Run.h】 +- **Cells & Interfaces**:`Cell`/`CellInterface` 是网格上的物理状态承载体。【F:src/Run.h】 +- **EoS / AddPhys / Sources / Relaxations**:方程状态、附加物理、源项、松弛机制。【F:src/Run.h】 +- **Input/Output**:输入解析与输出文件管理。【F:src/Run.h】 +- **Parallel**:并行通信由 `Parallel` 实例负责(见下文)。【F:src/Run.h】【F:src/Parallel/Parallel.h†L1-L120】 + +> 阅读建议:先从 `Run` 的构造/初始化实现(`Run.cpp`)入手,理解每个模块如何被创建与串联,再深入模块内部。 + +## 4. 输入/输出:`Input` 与 `Output` + +`Input` 负责解析 XML 输入与组件创建流程,包括主配置、网格、模型、EOS、初始条件等。【F:src/InputOutput/Input.h†L41-L74】 + +关键入口函数: +- `inputMain()`:读取主配置文件; +- `inputMesh()`:读取网格; +- `inputModel()`:读取物理模型; +- `inputEOS()`:创建并配置 EOS; +- `inputInitialConditions()`:初始化物理状态; +- `verifyCompatibilityInput()`:验证输入一致性。【F:src/InputOutput/Input.h†L48-L66】 + +`Input` 与 `Run` 互相引用:`Input` 保存 `Run*`,并直接访问其成员以填充运行环境。【F:src/InputOutput/Input.h†L69-L78】 + +## 5. 关键模块目录导图(以“Header*”为注册入口) + +项目采用“**HeaderXXX.h 作为模块注册表**”的组织方式,通过包含具体类头文件统一暴露接口,便于扩展新增类型。 + +### 5.1 网格(Meshes) +`Meshes/HeaderMesh.h` 中注册了笛卡尔网格、非结构网格等具体实现:【F:src/Meshes/HeaderMesh.h†L33-L41】 +- `MeshCartesian`、`MeshCartesianAMR` +- `MeshUnStruct`(含 Gmsh 读取支持) + +### 5.2 物理模型(Models) +`Models/HeaderModel.h` 注册多种模型(Euler、PUEq、Korteweg 等),并提供扩展入口。【F:src/Models/HeaderModel.h†L33-L43】 + +### 5.3 状态方程(EoS) +`Eos/HeaderEquationOfState.h` 注册多种 EOS:理想气体、SG、NASG、VDW、多项式等。【F:src/Eos/HeaderEquationOfState.h†L33-L40】 + +### 5.4 边界条件(BoundConds) +`BoundConds/HeaderBoundCond.h` 注册多种边界条件(非反射、入口、壁面、对称、出口等)。【F:src/BoundConds/HeaderBoundCond.h†L33-L47】 + +### 5.5 梯度与限制器(Gradients / Order2) +- `Gradients/HeaderGradient.h` 注册梯度计算方法(有限差分、Green-Gauss)。【F:src/Gradients/HeaderGradient.h†L33-L37】 +- `Order2/HeaderLimiter.h` 注册二阶空间限制器(Minmod、VanLeer 等)。【F:src/Order2/HeaderLimiter.h†L33-L41】 + +### 5.6 附加物理(AdditionalPhysics) +`AdditionalPhysics/HeaderAddPhys.h` 通过模型类型细分附加物理(粘性、导热、表面张力等)。【F:src/AdditionalPhysics/HeaderAddPhys.h†L33-L45】 + +### 5.7 源项(Sources) +`Sources/HeaderSources.h` 注册数值源项(重力、加热、旋转参考系、声学脉冲等)。【F:src/Sources/HeaderSources.h†L33-L40】 + +### 5.8 松弛过程(Relaxations) +`Relaxations/HeaderRelaxations.h` 注册多种松弛机制(速度、压力、热力学等)。【F:src/Relaxations/HeaderRelaxations.h†L33-L40】 + +## 6. 并行模块:`Parallel` + +并行通信集中在 `Parallel` 类中,提供多种数据类型的通信接口(原始变量、斜率、矢量、AMR 等),并维护 MPI 请求与缓冲区。【F:src/Parallel/Parallel.h†L29-L120】 + +程序入口 `main.cpp` 初始化 MPI 并获取 `rankCpu`/`Ncpu`,与 `Parallel` 模块协作。【F:src/main.cpp†L49-L57】【F:src/Parallel/Parallel.h†L113-L120】 + +## 7. 错误处理框架 + +`Errors.h` 定义了基础错误类 `Errors` 以及异常体系 `ErrorECOGEN` / `ErrorInput` 等,用于统一输出和错误码管理。【F:src/Errors.h†L52-L172】 + +在 `main.cpp` 中,输入异常与运行异常被分开捕获并打印信息,配合 `Run::finalize()` 做资源清理。【F:src/main.cpp†L121-L153】 + +## 8. 推荐的学习路线(逐层深入) + +1. **入口 + Run 框架**:先读 `main.cpp` 和 `Run.h/Run.cpp`,弄清“整体流程与对象关系”。【F:src/main.cpp†L33-L154】【F:src/Run.h†L54-L176】 +2. **输入解析链路**:从 `Input` 看 XML → 模型/网格/初始条件构建过程。【F:src/InputOutput/Input.h†L41-L78】 +3. **核心计算单元**:从 `Cell`、`CellInterface` 了解状态量的存储与更新(在 `Order1/`)。【F:src/Run.h†L106-L112】 +4. **模型/EOS/网格**:通过 `HeaderXXX.h` 定位具体模型类,再深入对应实现文件。【F:src/Models/HeaderModel.h†L33-L43】【F:src/Eos/HeaderEquationOfState.h†L33-L40】【F:src/Meshes/HeaderMesh.h†L33-L41】 +5. **高阶/附加物理/源项**:结合 `Limiter`、`Gradient`、`AddPhys`、`Sources` 阅读其实现与调用路径。【F:src/Gradients/HeaderGradient.h†L33-L37】【F:src/Order2/HeaderLimiter.h†L33-L41】【F:src/AdditionalPhysics/HeaderAddPhys.h†L33-L45】【F:src/Sources/HeaderSources.h†L33-L40】 +6. **并行与性能**:阅读 `Parallel` 与 `timeStats`,理解通信、统计与 MPI 协作。【F:src/Parallel/Parallel.h†L29-L120】 + +--- + +## 9. 关键组件源码导读(从接口到实现的切入点) + +下面补充对关键组件源码的“读代码路线图”,帮助你从接口定位到实现文件,并建立“数据结构 → 计算步骤 → 交互关系”的理解框架。 + +### 9.1 `Run`:调度核心的实现关注点 +建议在 `Run.cpp` 中重点关注以下几类函数: +- **初始化链路**:对应 `Run::initialize()`,观察它如何调用 `Input` 读取并构建 `Mesh`、`Model`、`Eos`、`Cell` 等对象。【F:src/Run.h†L54-L121】 +- **时间推进链路**:`Run::solver()` 触发实际的时间步推进,进一步分解为双曲项、源项、附加物理、松弛等子步骤(`solveHyperbolic`、`solveSourceTerms` 等)。【F:src/Run.h†L70-L92】 +- **数据组织方式**:`m_cellsLvl` / `m_cellInterfacesLvl` 以层级(AMR level)方式管理 cell 与 interface,读取这些成员可帮助理解空间离散的数据布局。【F:src/Run.h†L127-L130】 + +### 9.2 `Cell` 与 `CellInterface`:数值状态承载体 +`Cell`/`CellInterface` 是数值计算的核心承载单元,典型阅读方式: +1. 先从 `Order1/` 目录中找到 `Cell.h` / `Cell.cpp`,理解**状态量存储结构**(相变量、混合量、守恒量/原始量等)。【F:src/Run.h†L127-L130】 +2. 关注与 `Model` 的协作接口:例如从 `Model` 获取通量、更新状态、重构变量等。 +3. 若开启二阶方案,`Order2/` 中的 `Limiter` 和 `Gradient` 会对 `Cell` 的梯度重构进行修改(见下节)。 + +### 9.3 `Model`:物理模型与数值方法的核心 +`Models/` 目录中每个模型(例如 `Euler`、`PUEq`)都有自己的实现文件。学习时可以: +1. 从 `HeaderModel.h` 找到模型入口类名(例如 `ModEuler`),再跳到对应的 `.h/.cpp` 实现文件阅读。【F:src/Models/HeaderModel.h†L33-L43】 +2. 重点理解:**守恒变量与原始变量的定义**、**通量计算**、**Riemann 求解或数值通量**、**源项耦合**。 +3. 对多相模型,重点关注相变量的组织方式以及相间耦合关系。 + +### 9.4 `Eos`:状态方程的实现策略 +`Eos/` 中包含多个状态方程实现(IG、SG、NASG、VDW、多项式等),阅读重点包括: +- **热力学变量计算接口**:如压强、声速、温度的计算关系; +- **多相模型中的调用关系**:某个 `Model` 如何选择并调用不同 `Eos` 类型。【F:src/Eos/HeaderEquationOfState.h†L33-L40】 + +### 9.5 网格与几何:`Mesh` 与 `Geometries` +建议先阅读 `Meshes/HeaderMesh.h` 确认可用网格类型,再进入具体实现: +- `MeshCartesian` / `MeshCartesianAMR`:结构化网格与 AMR; +- `MeshUnStruct`:非结构网格,含 Gmsh 相关解析; +- 同时在 `Geometries/` 中查看几何域描述,用于初始条件与区域设置。【F:src/Meshes/HeaderMesh.h†L33-L41】 + +### 9.6 边界条件:`BoundConds` +`BoundConds/HeaderBoundCond.h` 汇集多种边界条件实现,阅读方式: +- 先确定 XML 输入中配置的边界类型; +- 在对应 `BoundCondXXX` 中查看实际处理逻辑(反射、入口、壁面等)。【F:src/BoundConds/HeaderBoundCond.h†L33-L47】 + +### 9.7 高阶与梯度重构:`Gradients` + `Limiter` +高阶空间精度依赖梯度与限制器: +- `Gradients/` 实现梯度计算方式(有限差分、Green-Gauss)。 +- `Order2/` 中 `Limiter` 对梯度/斜率进行限制,抑制数值震荡。 +- 阅读时关注:**重构变量的选择**、**限制器作用对象**、**在 `Run` 中的调用顺序**。【F:src/Gradients/HeaderGradient.h†L33-L37】【F:src/Order2/HeaderLimiter.h†L33-L41】【F:src/Run.h†L105-L131】 + +### 9.8 附加物理、源项与松弛过程 +- **附加物理**(`AdditionalPhysics`):粘性、导热、表面张力等,通常在每步时间推进的特定阶段调用。【F:src/AdditionalPhysics/HeaderAddPhys.h†L33-L45】 +- **源项**(`Sources`):重力、加热、旋转参考系、特定激励;多用于外部强迫与测试基准。【F:src/Sources/HeaderSources.h†L33-L40】 +- **松弛**(`Relaxations`):相间压力/速度/热力学平衡过程,用于多相模型的稳定推进。【F:src/Relaxations/HeaderRelaxations.h†L33-L40】 + +### 9.9 并行通信:`Parallel` +`Parallel` 提供了细粒度的数据通信接口(primitive/gradient/transport/AMR 等),学习路径: +1. 先阅读接口(`Parallel.h`)理解 API 分类; +2. 再在对应 `.cpp` 中看每种通信的缓冲区、请求管理与时序。 +该模块与 `Run` 的多级 cell 数据结构紧密相关。【F:src/Parallel/Parallel.h†L29-L120】【F:src/Run.h†L106-L112】 + +--- + +如果你希望进一步扩展此文档(例如加入“每个模型的控制方程”、“输入文件模板拆解”或“某个具体测试用例的运行路径”),欢迎通过提交 Issue 或 Pull Request 的方式提出建议或直接补充内容。