Skip to content

Commit 384a2e1

Browse files
committed
fix: align action contract pins and integrate current main
2 parents da2f7b6 + 86db625 commit 384a2e1

99 files changed

Lines changed: 8807 additions & 2389 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

‎.config/dotnet-tools.json‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,11 @@
33
"isRoot": true,
44
"tools": {
55
"dotnet-coverage": {
6-
"version": "18.11.2",
6+
"version": "18.12.0",
77
"commands": [
88
"dotnet-coverage"
99
],
1010
"rollForward": false
1111
}
1212
}
13-
}
13+
}

‎.github/workflows/ci.yml‎

Lines changed: 478 additions & 459 deletions
Large diffs are not rendered by default.

‎.github/workflows/codeql.yml‎

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@ jobs:
3838
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
3939
with:
4040
fetch-depth: 0 # MinVer computes the package version from the tag history
41+
submodules: recursive
4142
persist-credentials: false
4243

4344
- name: Set up .NET and restore the product graph (locked)

‎.github/workflows/dependency-submission.yml‎

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ jobs:
4040
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
4141
with:
4242
ref: ${{ github.event.pull_request.head.sha || github.sha }}
43+
submodules: recursive
4344
persist-credentials: false
4445

4546
- name: Set up .NET and restore (locked)

‎.github/workflows/release.yml‎

Lines changed: 989 additions & 988 deletions
Large diffs are not rendered by default.

‎.github/workflows/sonar.yml‎

Lines changed: 236 additions & 237 deletions
Large diffs are not rendered by default.

‎.gitmodules‎

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
[submodule "externals/CheatEngine.SDK"]
2+
path = externals/CheatEngine.SDK
3+
url = https://github.com/CheatEngineNet/CheatEngine.SDK.git

‎CHANGELOG.md‎

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,8 +25,18 @@ ship.
2525

2626
### Added
2727

28+
- **Pinned SDK submodule.** Repository builds, tests, plugin fixtures and PR CI build `externals/CheatEngine.SDK`
29+
through project references, with separate source lock files. Parent workspaces can override `CheatEngineSdkSourceRoot`.
30+
Source builds record the SDK Engine version and Git commit from its PE metadata, preserve plugin profile checks,
31+
and reject mismatched runtime identities. NuGet packaging and package-consumer checks run on the production release
32+
path with `CheatEngineSdkSourceMode=false`; SDK remains a separate published dependency.
33+
2834
### Changed
2935

36+
- **Local process enumeration.** Ignore nonpositive operating-system process IDs, including the Windows idle
37+
pseudo-process, before filtering and truncation. Unfiltered listings now return attachable process identities
38+
instead of failing when the local catalog contains PID 0.
39+
3040
### Security
3141

3242
### Deployment

‎CONTRIBUTING.md‎

Lines changed: 28 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,24 +1,25 @@
11
# Contributing to CheatEngine.Client
22

33
Thanks for contributing. CheatEngine.Client is a Windows x64, .NET 10 layer for in-process Cheat Engine 7.7 plugins,
4-
built on the `CheatEngine.SDK` package. Keep changes focused, preserve existing patterns, and update the documentation
4+
built on the pinned `CheatEngine.SDK` Git submodule. Keep changes focused, preserve existing patterns, and update the documentation
55
and tests that describe the behavior you change.
66

77
## Prerequisites
88

99
- Windows x64
10-
- .NET SDK 10.0.401 exactly, as pinned in [`global.json`](global.json). `rollForward` is `disable`, so any other
10+
- .NET SDK 10.0.402 exactly, as pinned in [`global.json`](global.json). `rollForward` is `disable`, so any other
1111
SDK, a newer one included, stops the build with the install command:
12-
`winget install Microsoft.DotNet.SDK.10 --version 10.0.401`
12+
`winget install Microsoft.DotNet.SDK.10 --version 10.0.402`
1313
- PowerShell 7.4 or later, to run the CI checks locally (actionlint, zizmor, the lock-file check)
1414
- Git
1515

1616
## Build and test
1717

1818
Run these commands from the repository root before every commit. Restores are locked: they fail when a project's
19-
dependencies no longer match its committed `packages.lock.json`.
19+
dependencies no longer match the committed source locks in `eng/locks/source/`.
2020

2121
```powershell
22+
git submodule update --init --recursive
2223
dotnet restore CheatEngine.Client.slnx --locked-mode
2324
dotnet build CheatEngine.Client.slnx -c Debug --no-restore
2425
dotnet test --solution CheatEngine.Client.slnx -c Debug --no-build --fail-skips on --filter-not-trait "Category=PackageConsumption" --filter-not-trait "Category=LiveQualification"
@@ -27,23 +28,27 @@ dotnet build CheatEngine.Client.slnx -c Release --no-restore
2728

2829
The test command is the one of the CI Debug leg: it runs every test except the package consumption tests
2930
(`Category=PackageConsumption`) and the live qualification tests (`Category=LiveQualification`); the Release build
30-
compiles the configuration that is packed. A skipped test fails the run: an environment-dependent test is fixed or
31+
also builds the submodule graph. Normal PR CI tests both configurations without package consumption. A skipped test fails the run: an environment-dependent test is fixed or
3132
deleted, never skipped. The live qualification tests start a sandboxed Cheat Engine, so every command here, like CI,
3233
excludes them by trait; run without that filter, they fail with the instructions of their opt-in (see
3334
[Live qualification](#live-qualification)).
3435

35-
The package consumption tests consume the exact packages you pack, as the CI Release leg does. Run them as well when a
36-
change reaches what is packed: a project file, `eng/`, `Directory.Build.*`, `Directory.Packages.props`, `templates/`,
37-
a packed README, or a public API that the template or a README snippet uses. The Native AOT probe completes the set:
36+
NuGet and package-consumption tests belong to production release validation. The release workflow enables
37+
`production-packages` and requires the exact packages it packs to pass consumption checks. Before preparing a release,
38+
update the separate SDK NuGet pin to a published version containing every API used by Client, then validate this graph:
3839

3940
```powershell
40-
Remove-Item artifacts/nuget -Recurse -Force -ErrorAction SilentlyContinue
41+
$env:CheatEngineSdkSourceMode = 'false'
42+
dotnet restore CheatEngine.Client.slnx --locked-mode
43+
dotnet build CheatEngine.Client.slnx -c Release --no-restore
4144
dotnet pack CheatEngine.Client.slnx -c Release --no-build -o artifacts/nuget
4245
$env:CHEATENGINE_CLIENT_PACKAGE_SOURCE = (Resolve-Path artifacts/nuget).Path
4346
dotnet test --solution CheatEngine.Client.slnx -c Release --no-build --fail-skips on --filter-not-trait "Category=LiveQualification"
4447
Remove-Item Env:CHEATENGINE_CLIENT_PACKAGE_SOURCE
48+
dotnet restore tests/CheatEngine.Client.AotProbe/CheatEngine.Client.AotProbe.csproj --locked-mode
4549
dotnet publish tests/CheatEngine.Client.AotProbe/CheatEngine.Client.AotProbe.csproj -c Release --no-restore -o artifacts/aot-probe
4650
./artifacts/aot-probe/CheatEngine.Client.AotProbe.exe
51+
Remove-Item Env:CheatEngineSdkSourceMode
4752
```
4853

4954
Without `CHEATENGINE_CLIENT_PACKAGE_SOURCE`, the package consumption tests pack the repository themselves, which is
@@ -84,7 +89,11 @@ version.
8489

8590
### The consumed CheatEngine.SDK
8691

87-
The Client consumes exactly one `CheatEngine.SDK` package, pinned in the single reviewed source
92+
Ordinary builds consume the SDK submodule. Review its changes, check out the intended commit, regenerate affected
93+
source locks one project at a time, and commit the gitlink together with those locks. Parent workspaces can select
94+
another SDK checkout as described in the README; standalone CI always uses the committed submodule.
95+
96+
Production releases consume exactly one `CheatEngine.SDK` package, pinned in the single reviewed source
8897
[`eng/CheatEngineSdk.props`](eng/CheatEngineSdk.props): never write an SDK version literal anywhere else. There is no
8998
script for the bump; the props file's own header documents the procedure, all of it in one pull request: update
9099
`CheatEngineSdkVersion`, update the reviewed identity literals it names
@@ -131,11 +140,11 @@ on every push, including on drafts, but it is advisory: it never blocks a merge
131140
| Check (`CI / ...`) | Runner | What it does |
132141
|--------------------------------|----------------|-----------------------------------------------------------------------------------------------------------------------------------|
133142
| `Build and test (Debug)` | `windows-2025` | Locked restore, build, one `dotnet test --solution` run with coverage (package consumption and live qualification tests excluded by trait) |
134-
| `Build and test (Release)` | `windows-2025` | Locked restore, build, pack (exact package set, embedded SBOM), benchmark discovery, one test run against the packed packages (live qualification tests excluded by trait) |
143+
| `Build and test (Release)` | `windows-2025` | Locked restore, source build, benchmark discovery and portable tests. Production releases additionally pack and validate the exact package set and embedded SBOM. |
135144
| `Native AOT publication probe` | `windows-2025` | Publishes and runs `tests/CheatEngine.Client.AotProbe`: trim and Native AOT compatibility of the Client graph, not a Cheat Engine load |
136145
| `Sonar / Analyze` | `windows-2025` | SonarQube Cloud CI-based analysis with the Debug coverage; waits for the quality gate except on pushes to `main` |
137146
| `Lint` | `ubuntu-24.04` | actionlint and the offline zizmor audits over the workflows |
138-
| `Format` | `ubuntu-24.04` | `dotnet format whitespace . --folder --verify-no-changes --exclude artifacts` |
147+
| `Format` | `ubuntu-24.04` | `dotnet format whitespace . --folder --verify-no-changes --exclude artifacts externals` |
139148
| `Dependency review` | `ubuntu-24.04` | On pull requests, reviews dependency changes against `.github/dependency-review-config.yml`; a notice on other events |
140149
| `Lock files` | `windows-2025` | `dotnet restore CheatEngine.Client.slnx --locked-mode` |
141150
| `Gate` | `ubuntu-24.04` | The required check described above |
@@ -284,6 +293,9 @@ loaded; it reads assembly attributes only. Its reason says whether the loaded as
284293
a distinction the qualification gate needs (a receipt covers only the tuple it was produced with). A build that cannot
285294
embed that identity fails with `CHEATENGINECLIENT9050`.
286295

296+
Source builds instead embed the Engine assembly's exact version and Git commit with `Kind=source` and no NuGet hash.
297+
The runtime gate requires that exact source identity. The source build does not inherit package qualification evidence.
298+
287299
**Instructions** (`CECLIENT5003`): the internal `AssemblyClient` runs each call in one dispatched callback behind one
288300
`LuaAdmission`, observes the instruction profile once (`InstructionProfiles.TryObserveCurrent`), refuses an address
289301
wider than that profile before any instruction function of Cheat Engine is called, and passes the same profile to
@@ -415,6 +427,10 @@ runs in CI.
415427

416428
### Live qualification
417429

430+
This runner qualifies production packages and templates only. It requires an explicit
431+
`CHEATENGINE_CLIENT_PACKAGE_SOURCE` artifact directory as well as the live-operation opt-in; it never self-packs
432+
the development checkout. Source fixture builds and portable tests do not produce live qualification receipts.
433+
418434
The live qualification tests (`tests/CheatEngine.Client.Tests/LiveQualification`, `Category=LiveQualification`) build
419435
plugins from the packed Client packages, load them into a sandboxed copy of Cheat Engine 7.7.0.10621 x64 and drive
420436
disposable gtutorial targets. They run only on a maintainer workstation that opts in, with the operator present, never

‎Directory.Build.targets‎

Lines changed: 21 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,23 @@
11
<Project>
2+
<!-- NuGet adds transitive ProjectReferences during execution, after the project body's direct references.
3+
Normalize both sets before MSBuild assigns configurations. The global override must also reach references
4+
inside the SDK, whose projects are not listed in Client's solution. -->
5+
<Target Name="CheatEngineClientNormalizeSourceSdkReferences" AfterTargets="IncludeTransitiveProjectReferences"
6+
Condition="'$(CheatEngineSdkSourceMode)' == 'true'">
7+
<ItemGroup>
8+
<ProjectReference Update="@(ProjectReference)"
9+
Condition="$([System.String]::Copy('%(ProjectReference.Filename)').StartsWith('CheatEngine.SDK.'))">
10+
<SetPlatform>Platform=AnyCPU</SetPlatform>
11+
<SetConfiguration>Configuration=$(Configuration)</SetConfiguration>
12+
<AdditionalProperties>%(ProjectReference.AdditionalProperties);ShouldUnsetParentConfigurationAndPlatform=false</AdditionalProperties>
13+
</ProjectReference>
14+
</ItemGroup>
15+
</Target>
16+
<Target Name="CheatEngineClientRefuseSourceDependencyPackage" BeforeTargets="Pack;GenerateNuspec"
17+
Condition="'$(CheatEngineSdkSourceMode)' == 'true'">
18+
<Error Code="CHEATENGINECLIENT9051"
19+
Text="Source SDK mode builds and tests the pinned submodule. For production packaging, restore, build and pack with CheatEngineSdkSourceMode=false to validate the reviewed NuGet dependency graph."/>
20+
</Target>
221
<!-- Imported after the project body and the SDK targets, so conditions here see final property values. -->
322

423
<Target Name="CheatEngineClientRequireProjectReadme"
@@ -69,7 +88,7 @@
6988
<Error Condition="'$(MSBuildProjectName)' == 'CheatEngine.Client' and '$(_CheatEngineClientProjectReferences)' != 'CheatEngine.Client.Fluent;CheatEngine.Client.Hosting'"
7089
Code="CHEATENGINECLIENT9015"
7190
Text="CheatEngine.Client must reference only CheatEngine.Client.Fluent and CheatEngine.Client.Hosting."/>
72-
<Error Condition="('$(MSBuildProjectName)' == 'CheatEngine.Client.Abstractions' or '$(MSBuildProjectName)' == 'CheatEngine.Client.Core' or '$(MSBuildProjectName)' == 'CheatEngine.Client.Hosting') and '@(_CheatEngineClientSdkRangeReference)' == ''"
91+
<Error Condition="'$(CheatEngineSdkSourceMode)' != 'true' and ('$(MSBuildProjectName)' == 'CheatEngine.Client.Abstractions' or '$(MSBuildProjectName)' == 'CheatEngine.Client.Core' or '$(MSBuildProjectName)' == 'CheatEngine.Client.Hosting') and '@(_CheatEngineClientSdkRangeReference)' == ''"
7392
Code="CHEATENGINECLIENT9016"
7493
Text="SDK-facing published packages must declare CheatEngine.SDK as $(CheatEngineSdkVersionRange), the range of eng/CheatEngineSdk.props."/>
7594
</Target>
@@ -200,7 +219,7 @@
200219
TypeLoadException, which neither package validation nor the public API baselines can see. The seven packages share
201220
one version (CHEATENGINECLIENT9019), so each one requires exactly that version of every Client package it depends on.
202221
203-
The .NET SDK 10.0.401 pack targets (NuGet.Build.Tasks.Pack.targets, internal and undocumented; eng/CheatEngineSdk.props
222+
The .NET SDK 10.0.402 pack targets (NuGet.Build.Tasks.Pack.targets, internal and undocumented; eng/CheatEngineSdk.props
204223
asks for a re-check after a .NET SDK bump): GenerateNuspec depends on _GetProjectReferenceVersions, which reads the
205224
project references of project.assets.json, calls _GetProjectVersion on each and collects the results as
206225
_ProjectReferencesWithVersions items, whose ProjectVersion metadata is the referenced project's $(PackageVersion).

0 commit comments

Comments
 (0)