Skip to content

Commit 6871e4f

Browse files
committed
fix: bound the resolved radian rotor angle, not the raw input
The 90 deg physical guard compared the raw cone / uptilt value to 90, which is only meaningful when the input is in degrees. Under angle_units=rad a 2.0 rad (~114 deg) angle passed the 2.0 < 90 check and assembled a plausible RNA for a non-physical geometry. Resolve to radians first, then bound the magnitude at pi/2, so the 90 deg limit holds whether the file was rad or deg.
1 parent e3d6d81 commit 6871e4f

2 files changed

Lines changed: 24 additions & 6 deletions

File tree

src/pybmodes/io/windio.py

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -764,15 +764,19 @@ def _windio_rotor_angles(
764764
if units == "auto":
765765
biggest = max(abs(cone), abs(uptilt))
766766
units = "deg" if biggest > 0.5 else "rad"
767-
if max(abs(cone), abs(uptilt)) > 90.0:
767+
if units == "deg":
768+
cone_rad, uptilt_rad = float(np.radians(cone)), float(np.radians(uptilt))
769+
else:
770+
cone_rad, uptilt_rad = cone, uptilt
771+
# Bound the resolved radian value (not the raw input, whose scale depends
772+
# on the unit), so a 90 deg limit holds whether the file was rad or deg.
773+
if max(abs(cone_rad), abs(uptilt_rad)) > np.pi / 2:
768774
raise ValueError(
769775
f"rotor precone / shaft tilt (cone_angle={cone!r}, uptilt="
770-
f"{uptilt!r}) is non-physical in {units}; expected values well "
771-
f"under 90 deg."
776+
f"{uptilt!r}, units={units}) resolves to more than 90 deg, which "
777+
f"is non-physical."
772778
)
773-
if units == "deg":
774-
return float(np.radians(cone)), float(np.radians(uptilt))
775-
return cone, uptilt
779+
return cone_rad, uptilt_rad
776780

777781

778782
def _positive_mass(value: Any, what: str) -> float:

tests/test_windio_rna.py

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -293,6 +293,20 @@ def test_rna_rejects_nonphysical_angle(tmp_path: pathlib.Path) -> None:
293293
read_windio_rna(_write(o, tmp_path, "cone_bad.yaml"))
294294

295295

296+
def test_rna_rejects_over_90deg_explicit_radians(tmp_path: pathlib.Path) -> None:
297+
"""The 90 deg physical bound is applied to the resolved radian value, so a
298+
2.0 rad (~114 deg) cone under angle_units='rad' is rejected rather than
299+
slipping past a raw < 90 comparison (Codex review on #130)."""
300+
pytest.importorskip("yaml")
301+
from pybmodes.io.windio import read_windio_rna
302+
303+
o = _base_ontology()
304+
o["components"]["hub"]["cone_angle"] = 2.0 # rad (~114 deg), non-physical
305+
p = _write(o, tmp_path, "cone_2rad.yaml")
306+
with pytest.raises(ValueError, match="non-physical"):
307+
read_windio_rna(p, angle_units="rad")
308+
309+
296310
@pytest.mark.parametrize("n_bl", [1, 2])
297311
def test_rna_rejects_one_or_two_bladed_rotor(
298312
tmp_path: pathlib.Path, n_bl: int

0 commit comments

Comments
 (0)