Skip to content

Fix gyroscopic precession sign: roll term (row 0) had the wrong sign#86

Open
Zaffer wants to merge 3 commits into
learnsyslab:mainfrom
Synetic-Labs:fix/gyro-precession-sign
Open

Fix gyroscopic precession sign: roll term (row 0) had the wrong sign#86
Zaffer wants to merge 3 commits into
learnsyslab:mainfrom
Synetic-Labs:fix/gyro-precession-sign

Conversation

@Zaffer

@Zaffer Zaffer commented Jul 8, 2026

Copy link
Copy Markdown

The propeller gyroscopic torque had the wrong sign on the roll axis (row 0 of torque_inertia), in both dynamics (numeric) and symbolic_dynamics in crazyflow/dynamics/first_principles/dynamics.py.

The gyroscopic torque is -ω × h with net rotor angular momentum h = h_z·ẑ, which gives (-q·h_z, +p·h_z, 0) — the roll and pitch rows must have opposite signs (it is a cross product). The code had them with the same leading sign (-q·S, -p·S), so exactly one row is wrong.

The subtlety is which row. S = Σ mixing_matrix[-1]·ω_rotor uses the yaw-torque-direction row, which is the negative of the physical spin direction (the same row that correctly signs the drag reaction and the z spin-up/down term). So h_z = -prop_inertia·S, and substituting:

roll  (x) = -q·h_z = +prop_inertia·ang_vel[1]·S   # code had a leading "-": the bug
pitch (y) = +p·h_z = -prop_inertia·ang_vel[0]·S   # already correct

The z (reaction) row is already correct, and is what pins the convention: it is consistent only with spin = -mixing_matrix[-1]. So the fix is to flip the sign of the roll row, leaving the pitch row unchanged.

Verified numerically against -ω × h to machine precision on all axes; numeric == symbolic still holds for ang_vel_dot. Only matters for non-negligible prop_inertia / larger quads during yaw-type maneuvers; negligible for a Crazyflie.

Note: an earlier revision of this PR flipped the pitch row instead. That was incorrect — it left the roll bug in place and inverted the already-correct pitch term (roughly doubling the error). Now corrected to flip the roll row.

The propeller gyroscopic torque had the wrong sign on the ROLL axis (row 0 of
torque_inertia), in both dynamics (numeric) and symbolic_dynamics.

The gyroscopic torque is -ω × h with net rotor angular momentum h = h_z·ẑ,
giving (-q·h_z, +p·h_z, 0): the roll and pitch rows must have OPPOSITE signs.
The subtlety is that S = Σ mixing_matrix[-1]·ω_rotor uses the yaw-torque-direction
row, i.e. the NEGATIVE of the physical spin, so h_z = -prop_inertia·S. Hence:
  roll  (x) = -q·h_z = +prop_inertia·ang_vel[1]·S   (code had a leading '-', the bug)
  pitch (y) = +p·h_z = -prop_inertia·ang_vel[0]·S   (code was already correct)
The z (spin-up/down reaction) row is already correct, and is in fact what pins
the convention: it is consistent only with spin = -mixing_matrix[-1].

Verified against -ω × h to machine precision on all axes; numeric == symbolic
still holds for ang_vel_dot. Only matters for non-negligible prop_inertia /
larger quads during yaw-type maneuvers; negligible for a Crazyflie.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@Zaffer Zaffer force-pushed the fix/gyro-precession-sign branch from 73c96a6 to 42669d9 Compare July 8, 2026 05:13
@Zaffer Zaffer changed the title Fix gyroscopic precession sign: pitch term opposite roll Fix gyroscopic precession sign: roll term (row 0) had the wrong sign Jul 8, 2026
@amacati amacati requested a review from ratheron July 8, 2026 08:46
@amacati amacati added the bug Something isn't working label Jul 8, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants