From d54c2c4edc406b71c092c7f0ec2b4b05da4b8878 Mon Sep 17 00:00:00 2001 From: Konstantin Kritsin Date: Wed, 22 Jul 2026 10:56:14 +0300 Subject: [PATCH 1/4] Preserve metadata constructor for Native AOT --- .github/workflows/test.yml | 30 +++++++++++++++++++ .../MaxMind.Db.NativeAot.Test.csproj | 24 +++++++++++++++ MaxMind.Db.NativeAot.Test/Program.cs | 13 ++++++++ MaxMind.Db.sln | 6 ++++ MaxMind.Db/Reader.cs | 8 +++++ 5 files changed, 81 insertions(+) create mode 100644 MaxMind.Db.NativeAot.Test/MaxMind.Db.NativeAot.Test.csproj create mode 100644 MaxMind.Db.NativeAot.Test/Program.cs diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 7ab64ff1..162fdd63 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -44,3 +44,33 @@ jobs: run: dotnet test env: MAXMIND_TEST_BASE_DIR: ${{ github.workspace }}/MaxMind.Db.Test + + native-aot: + runs-on: ubuntu-latest + name: Native AOT smoke test + steps: + - uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 # v7.0.0 + with: + submodules: true + persist-credentials: false + + - name: Setup .NET + uses: actions/setup-dotnet@26b0ec14cb23fa6904739307f278c14f94c95bf1 # v5.4.0 + with: + dotnet-version: 10.0.x + + - name: Install Native AOT prerequisites + run: sudo apt-get update && sudo apt-get install --yes clang zlib1g-dev + + - name: Publish Native AOT smoke test + run: >- + dotnet publish + MaxMind.Db.NativeAot.Test/MaxMind.Db.NativeAot.Test.csproj + --configuration Release + --framework net10.0 + --runtime linux-x64 + --self-contained true + --output ${{ runner.temp }}/native-aot + + - name: Run Native AOT smoke test + run: ${{ runner.temp }}/native-aot/MaxMind.Db.NativeAot.Test diff --git a/MaxMind.Db.NativeAot.Test/MaxMind.Db.NativeAot.Test.csproj b/MaxMind.Db.NativeAot.Test/MaxMind.Db.NativeAot.Test.csproj new file mode 100644 index 00000000..5a319fae --- /dev/null +++ b/MaxMind.Db.NativeAot.Test/MaxMind.Db.NativeAot.Test.csproj @@ -0,0 +1,24 @@ + + + + Exe + net10.0 + enable + enable + true + true + + + + + + + + + + + diff --git a/MaxMind.Db.NativeAot.Test/Program.cs b/MaxMind.Db.NativeAot.Test/Program.cs new file mode 100644 index 00000000..ccebf743 --- /dev/null +++ b/MaxMind.Db.NativeAot.Test/Program.cs @@ -0,0 +1,13 @@ +using MaxMind.Db; +using System.Net; + +var databasePath = Path.Combine(AppContext.BaseDirectory, "MaxMind-DB-test-decoder.mmdb"); +using var reader = new Reader(databasePath); +var record = reader.Find>(IPAddress.Parse("::1.1.1.0")); + +if (record is null || !Equals(record["utf8_string"], "unicode! ☯ - ♫")) +{ + throw new InvalidOperationException("Native AOT lookup returned an unexpected record."); +} + +Console.WriteLine("Native AOT lookup passed."); diff --git a/MaxMind.Db.sln b/MaxMind.Db.sln index c0403cb2..da36078d 100644 --- a/MaxMind.Db.sln +++ b/MaxMind.Db.sln @@ -9,6 +9,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MaxMind.Db.Benchmark", "Max EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MaxMind.Db.Test", "MaxMind.Db.Test\MaxMind.Db.Test.csproj", "{15A04FFF-BCC5-45F9-84E2-AB51B567E3E9}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MaxMind.Db.NativeAot.Test", "MaxMind.Db.NativeAot.Test\MaxMind.Db.NativeAot.Test.csproj", "{BECF3189-DFD7-43E3-8269-D4ED8D315D81}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -27,6 +29,10 @@ Global {F1051D87-38BE-4E9C-B7B3-9FA2DFB4FB56}.Debug|Any CPU.Build.0 = Debug|Any CPU {F1051D87-38BE-4E9C-B7B3-9FA2DFB4FB56}.Release|Any CPU.ActiveCfg = Release|Any CPU {F1051D87-38BE-4E9C-B7B3-9FA2DFB4FB56}.Release|Any CPU.Build.0 = Release|Any CPU + {BECF3189-DFD7-43E3-8269-D4ED8D315D81}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {BECF3189-DFD7-43E3-8269-D4ED8D315D81}.Debug|Any CPU.Build.0 = Debug|Any CPU + {BECF3189-DFD7-43E3-8269-D4ED8D315D81}.Release|Any CPU.ActiveCfg = Release|Any CPU + {BECF3189-DFD7-43E3-8269-D4ED8D315D81}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/MaxMind.Db/Reader.cs b/MaxMind.Db/Reader.cs index 9c256c6f..0b22f958 100644 --- a/MaxMind.Db/Reader.cs +++ b/MaxMind.Db/Reader.cs @@ -2,6 +2,9 @@ using System; using System.Collections.Generic; +#if NET +using System.Diagnostics.CodeAnalysis; +#endif using System.IO; using System.Net; using System.Net.Sockets; @@ -138,6 +141,11 @@ public Reader(Stream stream) : this(new MemoryMapBuffer(stream), null) { } +#if NET + // Metadata is instantiated through the reflection-based decoder. Keep its + // attributed constructor when the reader is trimmed or compiled with Native AOT. + [DynamicDependency(DynamicallyAccessedMemberTypes.PublicConstructors, typeof(Metadata))] +#endif private Reader(MemoryMapBuffer buffer, string? file) { _fileName = file; From 851540d2623155a6d5a8247453cde7641ba4cb27 Mon Sep 17 00:00:00 2001 From: Konstantin Kritsin Date: Wed, 22 Jul 2026 12:11:14 +0300 Subject: [PATCH 2/4] Format Native AOT workflow --- .github/workflows/test.yml | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 162fdd63..7143dc12 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -66,11 +66,8 @@ jobs: run: >- dotnet publish MaxMind.Db.NativeAot.Test/MaxMind.Db.NativeAot.Test.csproj - --configuration Release - --framework net10.0 - --runtime linux-x64 - --self-contained true - --output ${{ runner.temp }}/native-aot + --configuration Release --framework net10.0 --runtime linux-x64 + --self-contained true --output ${{ runner.temp }}/native-aot - name: Run Native AOT smoke test run: ${{ runner.temp }}/native-aot/MaxMind.Db.NativeAot.Test From 0d339419af69e84da695d5114b350ab09736a65b Mon Sep 17 00:00:00 2001 From: Konstantin Kritsin Date: Wed, 22 Jul 2026 12:19:10 +0300 Subject: [PATCH 3/4] Initialize submodules for CodeQL --- .github/workflows/codeql-analysis.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/workflows/codeql-analysis.yml b/.github/workflows/codeql-analysis.yml index d29a7117..b3ec76cc 100644 --- a/.github/workflows/codeql-analysis.yml +++ b/.github/workflows/codeql-analysis.yml @@ -22,6 +22,7 @@ jobs: # We must fetch at least the immediate parents so that if this is # a pull request then we can checkout the head. fetch-depth: 2 + submodules: true persist-credentials: false # If this run was triggered by a pull request event, then checkout From 9138fe1b91b0eb842f7b7816d8ae10cd24f4a859 Mon Sep 17 00:00:00 2001 From: Konstantin Kritsin Date: Wed, 22 Jul 2026 12:44:10 +0300 Subject: [PATCH 4/4] Enable quality checks for AOT smoke test --- .../MaxMind.Db.NativeAot.Test.csproj | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/MaxMind.Db.NativeAot.Test/MaxMind.Db.NativeAot.Test.csproj b/MaxMind.Db.NativeAot.Test/MaxMind.Db.NativeAot.Test.csproj index 5a319fae..63e2522e 100644 --- a/MaxMind.Db.NativeAot.Test/MaxMind.Db.NativeAot.Test.csproj +++ b/MaxMind.Db.NativeAot.Test/MaxMind.Db.NativeAot.Test.csproj @@ -4,7 +4,15 @@ Exe net10.0 enable + 14.0 enable + latest + true + true + true + + $(WarningsNotAsErrors);IL2067;IL2070;IL3050 true true