Skip to content

PInvoke skill test *IGNORE THIS*#58

Merged
12 commits merged intomainfrom
arobins/interop_skill
Feb 20, 2026
Merged

PInvoke skill test *IGNORE THIS*#58
12 commits merged intomainfrom
arobins/interop_skill

Conversation

@adityamandaleeka
Copy link
Member

No description provided.

Copilot AI review requested due to automatic review settings February 20, 2026 05:30
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Adds a new dotnet-pinvoke skill with supporting reference documentation and a basic evaluation test suite to validate expected P/Invoke declarations across TFMs.

Changes:

  • Introduces dotnet-pinvoke skill guide (SKILL.md) covering signatures, marshalling, lifetime, SafeHandle, and diagnostics.
  • Adds reference docs for native-to-.NET type mapping and common diagnostics/pitfalls.
  • Adds an eval scenario file to test LibraryImport vs DllImport expectations.

Reviewed changes

Copilot reviewed 4 out of 4 changed files in this pull request and generated 6 comments.

File Description
src/dotnet/tests/dotnet-pinvoke/eval.yaml Adds eval scenarios for generating P/Invoke declarations for .NET 8 and .NET Framework
src/dotnet/skills/dotnet-pinvoke/SKILL.md New skill documentation for P/Invoke/LibraryImport workflow and best practices
src/dotnet/skills/dotnet-pinvoke/references/type-mapping.md New reference table for native-to-.NET type mappings and struct layout guidance
src/dotnet/skills/dotnet-pinvoke/references/diagnostics.md New reference for common P/Invoke pitfalls and debugging approach
Comments suppressed due to low confidence (1)

src/dotnet/skills/dotnet-pinvoke/references/type-mapping.md:26

  • This reference recommends CLong/CULong for C long, but those types are .NET 7+ and won’t be available when targeting .NET Framework. Since this doc/skill explicitly covers .NET Framework, please add a framework-specific note (e.g., conditional compilation using int on Windows and long on Unix, or a custom typedef/struct approach) so readers don’t end up with uncompilable signatures.
| C / Win32 Type | .NET Type | Why It's Dangerous |
|----------------|-----------|-------------------|
| `long` | **`CLong`** | C `long` is 32-bit on Windows, 64-bit on 64-bit Unix — never use `int` or `long`. With `LibraryImport`, requires `[assembly: DisableRuntimeMarshalling]` or you get SYSLIB1051. With `DllImport`, works without it |
| `size_t` | `nuint` | Pointer-sized. Never use `ulong` — causes stack corruption on 32-bit |

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +61 to +65
```csharp
[DllImport("mylib")]
private static extern int ProcessRecords(
[In] Record[] records, nuint count, out uint outProcessed);
```
Copy link

Copilot AI Feb 20, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Several DllImport examples use nuint for size_t (e.g., ProcessRecords). That won’t compile for .NET Framework consumers of this guidance; nuint is .NET 5+/C# 9+. Consider documenting UIntPtr as the .NET Framework/legacy equivalent (and nuint for modern TFMs), or show framework-specific variants so the examples are accurate for both targets.

Copilot uses AI. Check for mistakes.
Comment on lines +25 to +28
| `long` | **`CLong`** | C `long` is 32-bit on Windows, 64-bit on 64-bit Unix — never use `int` or `long`. With `LibraryImport`, requires `[assembly: DisableRuntimeMarshalling]` or you get SYSLIB1051. With `DllImport`, works without it |
| `size_t` | `nuint` | Pointer-sized. Never use `ulong` — causes stack corruption on 32-bit |
| `intptr_t` | `nint` | Pointer-sized |
| `BOOL` (Win32) | `int` | Not `bool` — Win32 `BOOL` is 4 bytes |
Copy link

Copilot AI Feb 20, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The type mapping table unconditionally maps size_t to nuint and intptr_t to nint, but those types don’t exist on .NET Framework. Add a note/row for legacy TFMs (e.g., map to UIntPtr/IntPtr) so the reference remains correct when the target framework is .NET Framework.

This issue also appears on line 23 of the same file.

Copilot uses AI. Check for mistakes.

| Pitfall | Impact | Solution |
|---------|--------|----------|
| `int` for `size_t` | Stack corruption on 64-bit | Use `nuint` |
Copy link

Copilot AI Feb 20, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Diagnostics table recommends nuint as the fix for size_t misuse, but for .NET Framework (and other pre-.NET 5 TFMs) the appropriate fix is UIntPtr. Consider updating this row to mention both (nuint on .NET 5+; UIntPtr on .NET Framework) to avoid generating uncompilable guidance.

Suggested change
| `int` for `size_t` | Stack corruption on 64-bit | Use `nuint` |
| `int` for `size_t` | Stack corruption on 64-bit | Use `nuint` (.NET 5+) or `UIntPtr` (pre-.NET 5, including .NET Framework) |

Copilot uses AI. Check for mistakes.
@@ -0,0 +1,55 @@
scenarios:
- name: "Generate LibraryImport declaration from C header (.NET Core 5+)"
Copy link

Copilot AI Feb 20, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Scenario name says ".NET Core 5+" but the prompt targets .NET 8 and the assertions require LibraryImport, which is only available on .NET 7+. This mismatch makes the scenario requirements unclear; update the scenario name (and/or prompt) to align with the minimum TFM for LibraryImport.

Suggested change
- name: "Generate LibraryImport declaration from C header (.NET Core 5+)"
- name: "Generate LibraryImport declaration from C header (.NET 8+)"

Copilot uses AI. Check for mistakes.
Comment on lines +47 to +52
value: "nuint"
- type: "output_contains"
value: "static extern"
rubric:
- "Uses DllImport instead of LibraryImport since the target is .NET Framework"
- "Maps size_t to nuint, not ulong"
Copy link

Copilot AI Feb 20, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The .NET Framework (x86) scenario asserts and rubrics for nuint, but nuint/nint are not available in .NET Framework/C# versions typically used there. For Framework guidance/tests, size_t should be represented as UIntPtr (or uint if you truly want x86-only). Update the assertions/rubric to match the correct type for .NET Framework.

Suggested change
value: "nuint"
- type: "output_contains"
value: "static extern"
rubric:
- "Uses DllImport instead of LibraryImport since the target is .NET Framework"
- "Maps size_t to nuint, not ulong"
value: "UIntPtr"
- type: "output_contains"
value: "static extern"
rubric:
- "Uses DllImport instead of LibraryImport since the target is .NET Framework"
- "Maps size_t to UIntPtr, not ulong"

Copilot uses AI. Check for mistakes.
| **Mechanism** | Runtime marshalling | Source generator (compile-time) |
| **AOT / Trim safe** | No | Yes |
| **String marshalling** | `CharSet` enum | `StringMarshalling` enum |
| **Error handling** | `SetLastError` | `SetLastPInvokeError` |
Copy link

Copilot AI Feb 20, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LibraryImportAttribute uses SetLastError = true (same property name as DllImport); SetLastPInvokeError is not a valid attribute argument and will not compile in the examples. Replace SetLastPInvokeError with SetLastError throughout, while keeping Marshal.GetLastPInvokeError() for retrieval on .NET 7+.

Suggested change
| **Error handling** | `SetLastError` | `SetLastPInvokeError` |
| **Error handling** | `SetLastError` | `SetLastError` |

Copilot uses AI. Check for mistakes.
@github-actions
Copy link
Contributor

Skill Validation Results

Skill Scenario Baseline With Skill Δ Verdict
csharp-scripts Test a C# language feature with a script 2.8/5 5.0/5 +2.2
dotnet-pinvoke Generate LibraryImport declaration from C header (.NET Core 5+) 4.0/5 5.0/5 +1.0
dotnet-pinvoke Generate LibraryImport declaration from C header (.NET Framework) 3.0/5 5.0/5 +2.0

Model: claude-opus-4.6 | Judge: claude-opus-4.6

Full results

@AaronRobinsonMSFT AaronRobinsonMSFT closed this pull request by merging all changes into main in 5e0845e Feb 20, 2026
@AaronRobinsonMSFT AaronRobinsonMSFT deleted the arobins/interop_skill branch February 20, 2026 22:01
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants