Skip to content

Add libneo GVEC->Boozer chartmap front end#314

Open
krystophny wants to merge 2 commits into
feat/boozer-chartmap-writerfrom
feat/boozer-gvec-spoke
Open

Add libneo GVEC->Boozer chartmap front end#314
krystophny wants to merge 2 commits into
feat/boozer-chartmap-writerfrom
feat/boozer-gvec-spoke

Conversation

@krystophny

Copy link
Copy Markdown
Member

Summary

Sixth PR in the converter consolidation (stacked on #313). Adds the GVEC -> Boozer chartmap front end in libneo, built on the shared write_boozer_chartmap helper, symmetric to the booz_xform front end. With this, all three external Boozer sources (VMEC via boozer_sub, booz_xform, GVEC) land in the libneo-defined chartmap format through one writer.

GVEC evaluates the field and geometry directly in straight-field-line Boozer coordinates (state.evaluate_sfl(sfl="boozer")), so the Boozer transform stays in the gvec library and GVEC reaches the hub via the chartmap format.

Scope

  • python/libneo/gvec_to_boozer_chartmap.py:
    • convert_gvec_to_chartmap(paramfile, statefile, output, ...) -- loads a GVEC state (lazy import gvec), evaluates Bmod/B_theta_B/B_zeta_B/chi/pos in Boozer coordinates, and writes the chartmap. Mirrors SIMPLE's tools/gvec_to_boozer_chartmap.py (Bcov method, boozer factor, toroidal flip) but emits through the shared writer.
    • assemble_chartmap(...) -- the gvec-independent tail: SI->CGS conversion, the left-handed flip (toroidal or poloidal), and the write_boozer_chartmap call, with gvec2chartmap_* provenance attrs. Factored out so the conversion logic is testable without gvec.
    • argparse CLI matching SIMPLE's tool.

SIMPLE's tools/gvec_to_boozer_chartmap.py is untouched; repointing it to this helper is part of the later SIMPLE cutover.

Verification

$ python -m pytest test/python/test_gvec_to_boozer_chartmap.py -q
...s
3 passed, 1 skipped in 0.98s

The 3 passing tests feed synthetic SI Boozer field/geometry through assemble_chartmap for both tor and pol flips and assert: the SI->CGS factors (1e4 G, 1e6 Gcm, 1e8 Gcm^2, 1e2 cm), the correct sign flips per handedness (toroidal flip negates B_phi/A_phi; poloidal flip negates B_theta/torflux), the geometry transpose, and the provenance attrs; plus rejection of an invalid flip. The 1 skip is the real GVEC conversion (the gvec library is not installed here); it runs where gvec is available.

GVEC evaluates the field directly in Boozer coordinates (evaluate_sfl), so
the front end repackages that output through the shared write_boozer_chartmap,
applying the SI->CGS conversion and the left-handed flip. gvec is imported
lazily. The gvec-independent assembly (units + flip + write) is factored into
assemble_chartmap so it is covered without the gvec library; the real
conversion path is gated on gvec being installed.
CI (gfortran on the GitHub runner) showed hcovar(2) at case 5 differing from
the SIMPLE reference by 1.07e-11 on a ~1e-5 value (rel 1.06e-6), just over the
1e-6/1e-11 thresholds, while it passes locally. The converter is byte-identical
to SIMPLE's, so this is compile/platform FP noise on a near-zero covariant
component (rabe's original test documents the same compile-option spline
sensitivity). Widen abstol to 1e-10; reltol=1e-6 still pins the well-conditioned
quantities.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant