This commit is contained in:
@@ -0,0 +1,159 @@
|
||||
# Agent guidelines
|
||||
|
||||
These rules apply throughout this repository. Keep purpose, status, usage, and
|
||||
development instructions in `README.md`; keep agent workflow rules here. Neither
|
||||
file is a session log.
|
||||
|
||||
## Scope and repository map
|
||||
|
||||
This is a WIP .NET double-double arithmetic library, not arbitrary-precision math.
|
||||
Do not claim API completeness or accuracy beyond tested contracts.
|
||||
|
||||
- `0-source/Just.PreciseMath/`: library implementation and package metadata.
|
||||
- `1-tests/Just.PreciseMath.Tests/`: xUnit v3 tests, Shouldly assertions, and
|
||||
Microsoft.Testing.Platform (MTP) with `coverlet.MTP` coverage.
|
||||
- `2-benchmarks/Just.PreciseMath.Benchmarks/`: source-free BenchmarkDotNet library
|
||||
scaffold, not yet a runnable benchmark suite.
|
||||
- Root `Directory.Build.props` holds shared settings. Each numbered directory's
|
||||
props explicitly imports it; preserve this import chain.
|
||||
- `review-legacy/`: optional local reference material, excluded by `.gitignore`.
|
||||
Start with `review-legacy/Review-Revisited-DoubleDouble.md` when present. The code
|
||||
and proposed fixes contain known defects: reproduce findings against current
|
||||
code rather than treating them as correctness oracles. Do not compile, copy
|
||||
wholesale, or force-add these files. If absent, proceed without them; do not
|
||||
invent their contents or make validation depend on them.
|
||||
- Use the ignored, repository-local `.hermes/` directory for plans, checklists,
|
||||
investigation notes, and handoff context. Create or update notes as useful;
|
||||
keep them concise and revalidate them against current files. Optional
|
||||
`.hermes/project-context.md` holds setup and review background. Do not store
|
||||
secrets, force-add this directory, or make builds or tests depend on it.
|
||||
|
||||
## Working rules
|
||||
|
||||
- Check both staged and unstaged changes before starting. Preserve the user's
|
||||
work and index; do not stage, commit, push, publish packages, or rewrite history
|
||||
without an explicit request. Do not read or expose credentials.
|
||||
- Read definitions, callers, tests, and relevant configuration before editing.
|
||||
Limit changes to the request; do not implement the roadmap or repair unrelated WIP code.
|
||||
- Reproduce numerical bugs with a failing regression test before fixing them.
|
||||
For new behavior, define the contract and test cases before implementation.
|
||||
Exercise sibling overloads and operand orders that can share the defect.
|
||||
- Do not weaken analyzers, nullable checks, warnings-as-errors, or assertions to
|
||||
get a green build. Explain necessary policy changes before making them.
|
||||
- Keep dependencies minimal. Check existing references, compatibility, and current
|
||||
stable releases before adding or upgrading packages.
|
||||
|
||||
## C# conventions
|
||||
|
||||
Follow `.editorconfig`, not incidental style in unfinished code.
|
||||
|
||||
- Use file-scoped namespaces, explicit types rather than `var`, and block-bodied
|
||||
methods. Preserve the configured expression-bodied property/accessor preferences.
|
||||
- Use `_camelCase` for non-public instance fields, including internal fields;
|
||||
`s_camelCase` for non-public mutable static fields; PascalCase for constants
|
||||
and static readonly fields. Do not rename internal fields to remove underscores.
|
||||
- Preserve parentheses that make mathematical grouping readable. `IDE0047` is
|
||||
intentionally disabled; do not re-enable it or remove grouping as style cleanup.
|
||||
- Document public APIs and non-obvious numerical preconditions. Explain algorithms,
|
||||
error behavior, and range constraints rather than narrating syntax.
|
||||
- Tests and benchmarks already have internal access through `InternalsVisibleTo`;
|
||||
do not widen the public API merely to make a helper testable.
|
||||
|
||||
## Numerical correctness
|
||||
|
||||
- Treat floating-point evaluation order as part of the algorithm. Do not reassociate
|
||||
expressions, discard residuals, replace fused multiply-add with multiply-plus-add,
|
||||
or simplify error-free transforms without justification and regression tests.
|
||||
Mathematically equivalent formulas can round differently.
|
||||
- State and verify algorithm preconditions, especially magnitude ordering for
|
||||
quick-sum transforms, normalization assumptions, and overflow/underflow limits.
|
||||
- The internal two-component `DoubleDouble` constructor currently does not normalize.
|
||||
Do not assume arbitrary pairs are canonical. Establish the intended normalization,
|
||||
NaN, infinity, and signed-zero contracts before changing construction, equality,
|
||||
hashing, ordering, or classification; keep those operations consistent.
|
||||
- For affected operations, cover cancellation, widely separated magnitudes, zero
|
||||
and signed zero, subnormals, extreme finite values, infinities, and NaNs. Check
|
||||
intermediate overflow/underflow even when the final result is representable.
|
||||
- Derive expected values from independent high-precision references or exact
|
||||
binary/rational cases, never from the implementation under test. Record the
|
||||
reference source or reproducible derivation and justify tolerances.
|
||||
- Do not collapse both components to `double` or `decimal` to validate double-double
|
||||
accuracy: that can discard precisely the bits being tested. Use component-aware
|
||||
or higher-precision comparisons, and inspect sign bits when testing signed zero.
|
||||
- Smoke tests, coverage percentages, and benchmark output are not proof of
|
||||
numerical correctness.
|
||||
|
||||
## Build and verification
|
||||
|
||||
Run commands from the repository root. Read SDK and runner selection from
|
||||
`global.json`; read framework, language, and dependency versions from project and
|
||||
props files rather than duplicating version pins here.
|
||||
|
||||
For documentation-only changes, validate referenced paths and any new or changed
|
||||
commands, then run `git diff --check`.
|
||||
|
||||
Report commands actually run, their outcomes, and anything not verified. Distinguish
|
||||
pre-existing failures from failures introduced by the change.
|
||||
|
||||
### Code or build changes
|
||||
|
||||
Use targeted tests while iterating, then run the full sequence:
|
||||
|
||||
```sh
|
||||
dotnet restore Just.PreciseMath.slnx --locked-mode
|
||||
dotnet build Just.PreciseMath.slnx -c Release --no-restore
|
||||
dotnet test --solution Just.PreciseMath.slnx -c Release --no-build --minimum-expected-tests 1
|
||||
dotnet format Just.PreciseMath.slnx --verify-no-changes --no-restore
|
||||
git diff --check
|
||||
```
|
||||
|
||||
Use verify-only formatting first. Report unrelated existing violations separately
|
||||
and validate the changed files; do not reformat the repository to hide failures.
|
||||
|
||||
### Test or coverage pipeline changes
|
||||
|
||||
After the code/build checks, also run:
|
||||
|
||||
```sh
|
||||
dotnet test --solution Just.PreciseMath.slnx -c Release --no-build --minimum-expected-tests 1 --report-xunit-trx --coverlet --coverlet-output-format cobertura --coverlet-include "[Just.PreciseMath]*"
|
||||
```
|
||||
|
||||
Keep MTP-native options and the empty-suite failure. Do not substitute VSTest
|
||||
collector commands or remove compile assets from `coverlet.MTP`; generated MTP
|
||||
registration requires them. Inspect actual TRX and Cobertura output, including
|
||||
failed-test behavior when changing report collection.
|
||||
|
||||
### Packaging changes
|
||||
|
||||
After the code/build checks, run:
|
||||
|
||||
```sh
|
||||
dotnet pack 0-source/Just.PreciseMath/Just.PreciseMath.csproj -c Release --no-build
|
||||
```
|
||||
|
||||
Inspect package metadata and the included `README.md` and `LICENSE`. Do not publish.
|
||||
|
||||
### Dependency changes
|
||||
|
||||
For intentional dependency changes, run `dotnet restore --force-evaluate` and review
|
||||
all affected `packages.lock.json` files before the locked restore above. Include
|
||||
lock-file updates in the change; never regenerate them to bypass unexpected restore failures.
|
||||
|
||||
## CI and benchmarks
|
||||
|
||||
- `.gitea/workflows/test-dotnet.yaml` is the CI source of truth. Keep reports
|
||||
artifact-only: no badges, publication branches, or repository-write publishing jobs.
|
||||
- Preserve upload-on-failure and both report globs: `1-tests/**/TestResults/**/*.trx`
|
||||
and `1-tests/**/TestResults/**/*cobertura*.xml`. Cobertura filenames can be timestamped;
|
||||
`*.cobertura.xml` alone will miss them.
|
||||
- Cache NuGet packages, not `bin/` or `obj/`; restore remains necessary on a cache hit.
|
||||
A local restore does not prove CI cache reuse or remote artifact upload succeeded.
|
||||
- Before upgrading actions, check each action's required Node runtime against both
|
||||
the Gitea runner and job image. A recent runner can still launch an old Node image;
|
||||
`ubuntu-latest` is a configured label, not a guarantee of GitHub's environment.
|
||||
- Do not add an empty benchmark job. When benchmarks are introduced, add an executable
|
||||
entry point and cases, then smoke-run them in Release with BenchmarkDotNet's Dry job.
|
||||
Require discovered/executed cases and verify that benchmark failures fail CI.
|
||||
- Keep smoke validation separate from performance measurement. Do not gate timing
|
||||
regressions on a shared runner or compare coverage-instrumented measurements.
|
||||
Use controlled, repeatable baseline/candidate runs before proposing performance gates.
|
||||
Reference in New Issue
Block a user