cheatah
Struct

space::irbem::Rotations

cheatah-space v0.1.0-alpha — Biome Standard 0.6.5-alpha

Every rotation among the Cartesian frames, for ONE epoch and one dipole.

This is the object the whole header exists to produce. Building it costs the sidereal time, the solar ephemeris and about a dozen trigonometric calls; transforming a position afterwards costs a 3×3 matrix–vector product. Build one per epoch, then transform the whole ephemeris against it — never rebuild it per point.

Only eight matrices are stored, because these are orthogonal: the inverse of each is its transpose, which rotation_matrix takes rather than storing a second copy that could drift. Sixteen directed transforms therefore come out of eight stored ones, and R·Rᵀ = I holds to roundoff by construction rather than by arithmetic luck.

The construction chain, with Hapgood 1992's equation numbers:

matrix

Hapgood

definition

gei_to_geo

T1, eq. 2

rotate about Z by the Greenwich sidereal time

gei_to_gse

T2, eq. 3

rotate about X by the obliquity, then about Z by the solar longitude

gse_to_gsm

T3, eq. 6

rotate about X until the dipole has no GSE-Y component

gsm_to_sm

T4, eq. 11

rotate about Y by the dipole tilt

geo_to_mag

T5, eq. 12

rotate about Z to the pole's longitude, then about Y to its latitude

The three composites are products of those: geo_to_gse = T2·T1ᵀ, geo_to_gsm = T3·geo_to_gse, geo_to_sm = T4·geo_to_gsm. They are stored, not recomputed, so that GEO — the frame ephemerides arrive in — reaches every other frame in a single product.

Note

The pairs that are NOT stored (GEI↔GSM, GEI↔SM, GEI↔MAG, GSE↔SM, GSE↔MAG, GSM↔MAG, SM↔MAG) are a compile error rather than a silent chain through an intermediate frame. Compose them explicitly through GEO if they are needed; making that visible is the point.

Functions

fn static Rotations at(double jd_ut1, const DipoleCoefficients &dipole, GmstModel model=GmstModel::Iau1982) #

Build the rotations for one epoch and one dipole.

This is where every transcendental in the module is spent. The steps, in order: T1 from the sidereal time; T2 from the solar ephemeris; the dipole axis carried from GEO into GSE through T2·T1ᵀ; ψ and T3 as the rotation about X that kills the dipole's GSE-Y component (Hapgood eqs. 9–10, which is precisely the statement that GSM's Z axis lies in the plane of the dipole and the Sun); μ and T4 as the rotation about Y that carries the remaining tilt onto Z (his eq. 11, so SM's Z axis IS the dipole axis); and T5 from the pole's own latitude and longitude.

Parameters
jd_ut1

the epoch as a UT1 Julian date.

dipole

the degree-1 IGRF coefficients for the epoch.

model

which sidereal-time series to use; the IAU 1982 one unless a bit-comparison against a Hapgood-based implementation is wanted.

Returns

the fully populated rotation set.

Complexity

O(1) — a fixed ~14 transcendental calls and four 3×3 products, independent of how many points will later be transformed with it.

Allocation

none. Every intermediate is an inline-storage fixarray value.

Constants & variables

var double jd_ut1 #

The epoch these matrices were built for, as a UT1 Julian date.

var double gmst_deg #

Greenwich Mean Sidereal Time at the epoch, in degrees.

var double sun_ecliptic_longitude_deg #

The Sun's apparent ecliptic longitude λ☉, in degrees.

var double obliquity_deg #

The obliquity of the ecliptic ε, in degrees.

var double dipole_tilt_deg #

The geodipole tilt μ: the angle of the dipole axis from the GSM Z axis, positive when the north dipole leans sunward.

Ranges about ±35° over a year.

var double gsm_dipole_angle_deg #

Hapgood's ψ: the angle of the dipole's projection in the GSE Y–Z plane, measured from Z toward Y.

This is the angle gse_to_gsm undoes.

var fixarray::vec3d dipole_geo #

The dipole axis (toward the north geomagnetic pole), unit, in GEO.

var fixarray::vec3d dipole_gse #

The same axis in GSE — the vector ψ and μ are read off.

var fixarray::mat3d gei_to_geo #

Hapgood T1: inertial to Earth-fixed.

var fixarray::mat3d gei_to_gse #

Hapgood T2: inertial to solar-ecliptic.

var fixarray::mat3d gse_to_gsm #

Hapgood T3: solar-ecliptic to solar-magnetospheric.

var fixarray::mat3d gsm_to_sm #

Hapgood T4: solar-magnetospheric to solar-magnetic.

var fixarray::mat3d geo_to_mag #

Hapgood T5: Earth-fixed to centred-dipole geomagnetic.

var fixarray::mat3d geo_to_gse #

T2·T1ᵀ, precomputed: the ephemeris frame to solar-ecliptic.

var fixarray::mat3d geo_to_gsm #

T3·T2·T1ᵀ, precomputed: the ephemeris frame to the frame every external field model is defined in.

var fixarray::mat3d geo_to_sm #

T4·T3·T2·T1ᵀ, precomputed: the ephemeris frame to the frame drift shells are traced in.