Thanks for the interest. A few things to read before opening a PR.
| Topic | Where |
|---|---|
| Code style | .editorconfig + CLAUDE.md |
AOT discipline (what's banned in Sources/Main) |
Sources/Main/BannedSymbols.txt |
| Hot-path conservatism rules | Sources/Main/README.md |
Test layout + [LongFact] policy |
Tests/README.md |
| File header template (run before PR) | update-code-headers.cmd |
| Architecture overview | docs/TECHNICAL.md, CLAUDE.md |
- Block-scoped namespaces. Sorted
usingdirectives. No separate import groups. - File headers are templated via
.editorconfigIDE0073 — runupdate-code-headers.cmdbefore submitting. IDisposableAnalyzerswarnings inSources/Mainare effectively errors — this codebase leans on explicitusingblocks and pooled buffers.
Two independent guards:
1. Banned symbols, checked at every build. Microsoft.CodeAnalysis.BannedApiAnalyzers with RS0030 promoted to error in .editorconfig enforces Sources/Main/BannedSymbols.txt (authoritative live list). Forbidden in Sources/Main:
System.Linq(the namespace is also<Using Remove="System.Linq" />inMain.csproj).System.ReflectionandSystem.Linq.Expressions.Expression.System.Activator.Array.Copy— useSpan<T>.CopyToinstead.- Raw
ArrayPool<T>.Shared— usePooledBuffer<T>, scoped viausingfor method-local scratch or held as a field and disposed by its owner for class-lifetime buffers.
2. Actual Native AOT publish, checked in CI. Tests/AotSmokeTest is a thin console exe referencing DevOnBike.Overfit. The aot-guard job in .github/workflows/ci.yml publishes it under -p:PublishAot=true -p:TreatWarningsAsErrors=true on Ubuntu and then runs the produced native binary. Libraries cannot be Native-AOT compiled directly (no entry point), so the smoketest is the real AOT consumer — ILCompiler actually runs, IL2026 / IL3050 / IL31xx warnings on reachable code become errors, and a non-zero exit from the binary fails the job.
Tests and benchmarks are unconstrained — LINQ is fine there.
Use explicit for / foreach over Span<T>, delegates over reflection, explicit new over Activator. If your library change touches a code path reachable from Tests/AotSmokeTest/Program.cs and introduces a trim warning, the CI publish will fail — either fix the warning in the library or scope a [RequiresDynamicCode] / [RequiresUnreferencedCode] attribute (sparingly).
- All test commands use
-c Release— never Debug. - Tests must stay fast. Long-running ones use
[LongFact](auto-skipped by default; flip back to[Fact]to run locally). - See
Tests/README.mdfor layout conventions and the[LongFact]vs[Fact(Skip=...)]policy. The two have different semantics —[LongFact]is for runtime,[Fact(Skip=...)]is for tracked bugs / numerical instability with a preserved "why". - One public class per test file, named after the subject under test.
- Keep commits focused and reviewable.
- Match the one-line subject style of existing history (no enforced format).
- Sign-off (
Signed-off-by:) is not required, but a Contributor License Agreement (CLA) is — see below.
Overfit is dual-licensed under AGPLv3 and a commercial license (see LICENSE.md). To accept external contributions while preserving the ability to offer commercial licenses, all contributors must sign a CLA before their pull request is merged.
The CLA grants the project:
- The right to distribute the contribution under AGPLv3.
- The right to distribute the contribution under the commercial license.
- A confirmation that the contribution is the contributor's own work, or properly attributed.
The CLA is signed once per contributor, not per PR. CLA Assistant will prompt you on your first PR with a one-click sign-off. If you decline the CLA, you can still file bug reports, feature requests, and discussions — only merged code contributions require it.
If your employer holds copyright on your work, your employer must sign the CLA, not you personally.
Yes please:
- Bug fixes — with a regression test that fails without the fix.
- New model architecture loaders — follow the existing GGUF / safetensors loader patterns; validate against a real checkpoint with bit-parity or coherent-generation evidence.
- Performance improvements — BenchmarkDotNet evidence required, both single-thread and (where relevant) multi-thread.
- Documentation — scenario doc updates, README clarifications, capability table updates that match shipped reality.
- Diagnostics / test fixtures — under
Tests/**/Diagnostics/with[LongFact].
Please discuss first (open an issue or discussion):
- Large refactors — anything touching multiple subsystems.
- New public API — must fit the existing facade style; breaking the public surface needs a versioning plan.
- New NuGet dependencies —
NuGetAuditis strict; every dep is weighted on attack surface and trim/AOT compatibility.
Probably not accepted:
- Code introducing LINQ / reflection /
Activator/Expression/Array.Copy/ rawArrayPool<T>.SharedintoSources/Main. - Mocked dependencies in tests where a real component is feasible (see
Tests/README.md). - Half-finished features, scaffolding without implementation, or speculative abstractions.
Do not open public issues for security vulnerabilities. See SECURITY.md.
Open a GitHub discussion or email devonbike@gmail.com.