From c7a7ef2b4882a2804144abae391bbbaebb8ef6c5 Mon Sep 17 00:00:00 2001 From: sksat Date: Sun, 28 Jun 2026 01:08:41 +0900 Subject: [PATCH] [add] CLAUDE.md (working guidelines for Claude Code) Meta-first guidance for future Claude Code sessions: consult the smart-friend skill for a second opinion on design/debugging, work test-first, verify before claiming, the PR/merge conventions, and the durable non-obvious pitfalls (Eigen auto use-after-scope, quaternion scalar-first vs Eigen coeffs, TOML int/float arrays). Deliberately omits obvious build commands and easily-discoverable, fast-changing code structure; keeps a short "physics lives in do_step()" orientation instead. Co-Authored-By: Claude Opus 4.8 (1M context) Claude-Session: https://claude.ai/code/session_01LiKBVgTqjZV84zcMVY3w46 --- CLAUDE.md | 25 +++++++++++++++++++++++++ 1 file changed, 25 insertions(+) create mode 100644 CLAUDE.md diff --git a/CLAUDE.md b/CLAUDE.md new file mode 100644 index 0000000..7d74eb6 --- /dev/null +++ b/CLAUDE.md @@ -0,0 +1,25 @@ +# CLAUDE.md + +This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository. + +trochia is a C++20 rocket flight simulator. + +## How to work here + +- **Get a second opinion.** For non-trivial design decisions and tricky debugging, consult the **smart-friend** skill — a knowledgeable second opinion. Bring it the problem and the options before committing to an approach, decide with it, then implement. +- **Test-driven.** Every fix/feature is test-first: write a failing test (red), then make it pass (green). Don't just assert "it runs" — assert the quantitative physics invariant (terminal velocity, bounded angle of attack, apogee, etc.), and lean on the sanitizer build for UB. Prefer tests that fail on the bug and pass on the fix. +- **Verify before claiming.** Run CI / tests / the sanitizer and read the output before saying something works; don't write comments asserting behavior you haven't observed. +- **Fine-grained PRs to `master`**, one concern each (don't mix build/CI changes with source changes). Merges are **merge-commit only** (squash and rebase are disabled on the repo). PR titles in English, bodies in Japanese, with a real explanation (symptom → root cause → fix → evidence). To illustrate a PR's effect, prefer citing an image in the PR description over committing a throwaway plot. +- **Plot with gnuplot; manage Python deps with uv** (not matplotlib / not bare pip). + +## Non-obvious pitfalls (durable) + +- **Eigen + `auto`:** never bind an Eigen product/expression to `auto` when an operand is a temporary — it keeps a lazy expression template referencing freed memory (use-after-scope). Use the concrete type or `.eval()`. +- **Quaternion ordering:** `math::quat2vec`/`vec2quat` are **scalar-first** `[w,x,y,z]`, but Eigen's `coeffs()` is scalar-last `[x,y,z,w]`. Mixing them silently corrupts attitude. +- **TOML number types:** wind `ground.dir`/`speed` *arrays* must be float literals (`[0.0, 15.0]`, not `[0, 15]`) or toml11 aborts; scalar fields accept int or float via the `as_number` helper. + +## Orientation + +All the flight physics is in one place: `do_step()` in `src/simulation.cpp`. It runs once per timestep (forces → moments → rail constraint → recovery), and the generic RK4 in `src/solver.hpp` integrates the `Object` state from `src/object.hpp`. The rest of `src/` is header-only support (coordinate frames, atmosphere/gravity/wind, the rocket/engine models). Start from `do_step()` for anything dynamics-related. + +Tests live in `test/` and run without the main build's heavy dependencies — `./test/run_tests.sh` is the fast path (system googletest + Eigen). `config-example.toml` documents the input schema; `examples/` has runnable, plotted cases.