# MuPRO SDK Migration Plan Snapshot

Last updated: 2026-05-26

This document records the accepted migration direction after the initial `openmupro` consolidation and platform baseline work. It is a stable internal snapshot; `TASK.md` remains the live task tracker.

## Accepted Direction

| ID | Decision | Status |
| --- | --- | --- |
| PLAN-MIG-001 | Use a single private `muprosdk` repository as the primary engineering home. | Accepted |
| PLAN-MIG-002 | Remove standalone `openmupro` as an active package and fold needed L0/L1 runtime code into `library/`. | Implemented for active build graph |
| PLAN-MIG-003 | Do not migrate `desktop/`; desktop or GUI workflows will be redesigned in separate software later. | Accepted |
| PLAN-MIG-004 | Keep app submodules unchanged for now; handle app repository consolidation during app refactors. | Accepted |
| PLAN-MIG-005 | Do not rely on outside users contributing code. Users should provide requirements, issues, logs, examples, and feedback; MuPRO maintains and releases code. | Accepted |
| PLAN-MIG-006 | Keep Fortran as the primary scientific implementation language, with a future C ABI boundary for multi-language hosts. | Accepted |
| PLAN-MIG-007 | Use C/C++/CUDA/HIP selectively for solver hotspots or algebra kernels when GPU acceleration is justified. | Deferred |
| PLAN-MIG-008 | Establish solver-level and scenario-level benchmark standards before risky solver refactors. | Standard skeleton implemented; reference outputs pending |
| PLAN-MIG-009 | Adopt OpenUSD as the future high-level case input package while keeping large numerical data in scientific/native formats. | Accepted direction |
| PLAN-MIG-010 | Keep MuPRO core CLI/TUI-first; leave full GUI, visual pre/post-processing, and broader workflow tooling to external SimViz-style software. | Accepted direction |
| PLAN-MIG-011 | Own smoke/unit/MPI/integration/regression/benchmark tests inside each `library/<module>/tests` directory; equation-solving modules also own validation tests. | Accepted direction |
| PLAN-MIG-012 | Keep root free of test source directories; `library/` owns library-level tests and apps own their own benchmark/validation/regression checks. | Accepted direction |

## Current Build Baseline

- Linux and Windows remain the official oneAPI/oneMKL routes.
- macOS is development-only and CPU-only, using Homebrew `gfortran`, OpenBLAS, FFTW, and OpenMPI.
- FFTW is never bundled into SDK packages.
- The repository root now has a migration CMake entrypoint that builds `license`, `library`, `examples/demo1`, and `examples/c_api_tdgl` together, but it owns no test source directory.
- Root CTest aggregates child tests from `library/`; the current checks cover C ABI, runtime, status, L0 Base, L0 Log, all current L1 module directories, and a library-level configure smoke.
- Current unit test source ownership is module-local under `library/<module>/tests/unit`, `library/runtime/tests/unit`, and `library/c_api/tests/unit`; root CTest aggregates registered tests.
- Modules can now add `smoke`, `mpi`, `integration`, `regression`, `benchmark`, and `validation` categories without touching root CMake; benchmark and validation categories are opt-in through `MUPRO_BUILD_BENCHMARKS` and `MUPRO_BUILD_VALIDATION`.
- The minimal C ABI skeleton is implemented with installed `mupro.h`, opaque runtime/TDGL handles, `mupro_status_t`, TDGL setup/solve signatures, and documented array layout.
- The runtime context skeleton now lives under `library/runtime`; the C ABI bridge delegates size and MPI ownership to `mod_mupro_runtime`, which preserves legacy `mod_base_size` and `mod_base_mpi` compatibility.
- FFT lifecycle is now an optional runtime capability: `runtime_setup` does not initialize FFT, and FFT-based solvers must request `mupro_runtime_setup_fft` or `mupro_runtime_ensure_fft`.
- TDGL has a structured validation/status-return path, targeted macOS compile coverage, and an optional C adapter through `MUPRO_BUILD_TDGL=ON`.
- `library` can build the L0/L1 macOS development route with `MUPRO_BUILD_SOLVERS=OFF`.
- `examples/demo1` is now a downstream SDK example under `examples/demo1`; the first C ABI example is under `examples/c_api_tdgl`.
- Benchmark standards, catalogs, and result metadata templates are under `benchmarks/`.
- OpenUSD case workflow direction is recorded in `docs/internal/openusd-case-workflow.md`.
- Current build/test baseline and known blockers are recorded in `docs/internal/baseline-build-test.md`.

## Current Repository State

- `openmupro` has been removed from the main repository index and `.gitmodules`.
- Active build files no longer reference `find_package(openmupro)`, `openmupro_DIR`, or `mupro::openmupro`.
- `apps/muFerro` and `apps/muPREDICT` have local submodule edits from the cleanup. These are intentionally deferred until app refactoring.

## Next Engineering Phases

1. Add explicit MPI smoke beyond single-process runtime initialization.
2. Add concrete module-local benchmark, regression, integration, and validation cases using the standard category layout.
3. Assign benchmark reference owners and confirm trusted outputs.
4. Refactor solver/app code in narrow slices, using reference outputs from `reference/` and benchmark cases.

## Test Topology Direction

The migration bootstrap used root-level `tests/unit` to quickly establish a non-empty CTest gate. That placement has now been replaced for current module/API/runtime checks.

Target layout:

- `library/<module>/tests/unit`: deterministic function-level and small API checks owned by the module.
- `library/<module>/tests/smoke`: minimal build/run checks for module entrypoints.
- `library/<module>/tests/mpi`: MPI-specific checks for modules with distributed behavior.
- `library/<module>/tests/integration`: small examples that depend on a minimal set of neighboring modules.
- `library/<module>/tests/regression`: historical behavior compatibility checks.
- `library/<module>/tests/benchmark`: module performance and efficiency checks. These are opt-in through `MUPRO_BUILD_BENCHMARKS`.
- `library/<module>/tests/validation`: accuracy checks for equation-solving modules with references, tolerances, and provenance. These are opt-in through `MUPRO_BUILD_VALIDATION`.
- `library/tests`: assembled library-level checks, such as configure/install/export/package smoke or cross-module ABI/runtime behavior.
- `apps/<app>/benchmark`: app-level performance and efficiency checks.
- `apps/<app>/validation`: app-level accuracy or literature/reference checks.
- `apps/<app>/regression`: app-level historical compatibility checks.

Root CTest remains useful, but only as an aggregator: it adds child targets from `library/` and later apps rather than owning test source files. This keeps each module and app close to independently verifiable and makes future refactor safer.

## L0/L1 Boundary Assessment

The current L0/L1 split is usable for migration, but it is not the final architecture.

- `L0_Base` is currently a compatibility container for precision/constants/status, MPI/global size, TOML, expression evaluation, and umbrella exports. This is acceptable during migration, but the long-term split should separate true base types, runtime ownership, and input parsing.
- `L0_Log` is reasonably placed at L0, but fatal stop/finalize paths should gradually move behind structured status/runtime control instead of being called directly from utilities or solvers.
- `L0_FFT` is a valid low-level runtime dependency today, but plan/size/wave-vector ownership should eventually move into runtime/backend context instead of global module state.
- `L1_Utilities` is still broad. It mixes generic numerical helpers, ferroelectric/domain helpers, and legacy error handling. Keep it stable behind tests first, then split by responsibility.
- `L1_IO`, `L1_Transform`, PostProcess, structure/material helpers, and Film now have module-local smoke or deterministic coverage. Their internal boundaries still need later cleanup.

The L0/L1 migration coverage gate is now in place. Broad L2 work should still remain narrow until runtime ownership and benchmark coverage are stronger.

## Current L0/L1 Test Gate

The root macOS development CTest gate currently passes with thirteen aggregated tests, where all test source files live under `library/`:

- `library.configure_smoke`
- `unit.c_api`
- `unit.runtime`
- `unit.status`
- `unit.l0_base`
- `unit.l0_log`
- `unit.l1_io`
- `unit.l1_transform`
- `unit.l1_utilities`
- `unit.l1_post_process`
- `unit.l1_structure_generator`
- `unit.l1_material_generator`
- `unit.l1_film`

Coverage added in the L0/L1 stabilization slice:

- L0 Log: scalar logging and time-dependent header/row output.
- L1 Utilities: 1x21/6x6 conversion, LAPACK-backed matrix inverse, fixed-seed random helpers, and `sumBox`.
- L1 Transform: zero-angle Euler identity and cubic tensor Voigt roundtrip.
- L1 I/O: serial DAT/VTK output smoke, time-dependent CSV parsing, and single-process MPI-style 3D/4D/5D roundtrip.
- L1 PostProcess: uniform domain classification over a tiny 3D box.
- L1 StructureGenerator: round-pillar center-line generation on a 3x3x3 grid.
- L1 MaterialGenerator: scalar and rank-2 property assignment from phase labels.
- L1 Film: constant-field fitted derivative through runtime-owned FFT setup.
- Runtime: context skeleton, size setup/query through legacy global compatibility, backend defaults, setup/finalize, MPI initialization/finalization, and optional FFT setup/finalize/re-setup.

With this gate in place, narrow L2 adapter work is no longer blocked by unfinished L1 migration coverage. Broad solver refactors still require benchmark-linked references.

The standalone `library` macOS development CTest gate also passes with the same thirteen library-owned tests.

## Current C ABI Gate

The first C ABI skeleton is in place:

- Header: `library/c_api/include/mupro.h`
- Implementation: `library/c_api/src/mupro_c_api.c`
- Unit test: `library/c_api/tests/unit`
- Example: `examples/c_api_tdgl`
- Design note: `docs/internal/c-api.md`

The current C API can create/destroy runtime and TDGL handles, set runtime size through the Fortran `mod_mupro_runtime` bridge, initialize/query MPI rank/process through the runtime-owned `mpi_setup` path, store TDGL setup parameters, validate TDGL solve pointer/shape/stride metadata, and return structured status. In default L0/L1 builds, `mupro_tdgl_solve` returns `MUPRO_STATUS_NOT_SETUP` because TDGL is not present in that build. With `MUPRO_BUILD_TDGL=ON`, `mupro_tdgl_setup/solve` route through an optional Fortran TDGL adapter and request runtime FFT lazily. FFT is runtime-owned internally but is not exposed through the public C API yet.

Runtime limitation: `mod_mupro_runtime` still writes legacy Fortran global state. Treat the process as having one active MuPRO runtime until solver internals stop depending on global size, MPI, and FFT state.
