Skip to content

Backport XML documentation for DynamicMethod and DynamicILInfo from dotnet-api-docs#124227

Draft
Copilot wants to merge 15 commits intomainfrom
copilot/backport-xml-doc-comments
Draft

Backport XML documentation for DynamicMethod and DynamicILInfo from dotnet-api-docs#124227
Copilot wants to merge 15 commits intomainfrom
copilot/backport-xml-doc-comments

Conversation

Copy link
Copy Markdown
Contributor

Copilot AI commented Feb 10, 2026

Contributes to dotnet/dotnet-api-docs#12307.

Description

Backported XML documentation comments from dotnet/dotnet-api-docs to the DynamicMethod and DynamicILInfo classes. Per requirements, specific members (constructors, CreateDelegate, GetILGenerator, Invoke, IsSecurityCritical) include remarks linking to supplemental API documentation. Each member links to its specific article in the dotnet/docs repository.

These documents will become available when dotnet/docs#51571 merges.

Changes Made

DynamicMethod Documentation

  • Type-level documentation: Added <summary> and <remarks> with supplemental link to the DynamicMethod class declaration
  • 8 constructor overloads: Full documentation including <summary>, <param>, <exception>, and <remarks> with supplemental links to the parent type article
  • CreateDelegate overloads (2): Documentation with supplemental links to the specific CreateDelegate article in CoreCLR implementation
  • GetILGenerator overloads (2): Documentation with supplemental links to the specific GetILGenerator article for both parameterless and parameterized versions
  • Invoke method: Documentation with supplemental link to the specific Invoke article in CoreCLR implementation
  • IsSecurityCritical property: Documentation with supplemental link to the specific IsSecurityCritical article, including separate value descriptions for .NET (Core) and .NET Framework
  • IsSecuritySafeCritical and IsSecurityTransparent properties: Added remarks with references to IsSecurityCritical for .NET Framework transparency information, including separate value descriptions for .NET (Core) and .NET Framework
  • Other public members: Complete XML documentation with full remarks for all remaining properties and methods (Name, DeclaringType, ReflectedType, Module, Attributes, CallingConvention, GetBaseDefinition, GetParameters, GetMethodImplementationFlags, GetCustomAttributes, IsDefined, ReturnType, ReturnParameter, ReturnTypeCustomAttributes, DefineParameter, ToString, InitLocals, GetDynamicILInfo)

DynamicILInfo Documentation

  • Type-level documentation: Added <summary> and <remarks> with supplemental link to the DynamicILInfo class in CoreCLR implementation
  • DynamicMethod property: Documentation with remarks
  • SetCode overloads (3): Complete documentation with <summary>, <param>, <exception>, and <remarks>
  • SetExceptions method: Documentation with parameters, exceptions, and remarks
  • SetLocalSignature overloads (2): Documentation with parameters, exceptions, and remarks
  • GetTokenFor overloads (7): Documentation with parameters, returns, and remarks for string, byte array, DynamicMethod, RuntimeMethodHandle, RuntimeFieldHandle, and RuntimeTypeHandle

Code Examples

  • Created DynamicMethod.Examples.cs: Separate file in the samples directory containing code examples organized in #region blocks, following the Newtonsoft.Json documentation pattern
  • Example sections: Added <example> sections to 12 DynamicMethod members (Name, DeclaringType, ReflectedType, Module, Attributes, CallingConvention, GetParameters, ReturnType, ReturnTypeCustomAttributes, DefineParameter, ToString, InitLocals) that reference the Examples.cs file using <code lang="cs" source="../../../../samples/System/Reflection/Emit/DynamicMethod.Examples.cs" region="..." />
  • Examples use relative paths from the source file location to the samples directory

Other Changes

  • Mono implementation: Removed duplicate documentation to avoid redundancy, as documentation is provided in CoreCLR implementation
  • Code review fixes: Applied automated code review suggestions for improved documentation accuracy (void keyword usage, ReturnParameter behavior clarification, IsDefined behavior clarification, typo fixes)
  • URL format: Updated all supplemental link URLs to use https://github.com/dotnet/docs/raw/main/ format per guidelines
  • XML syntax: Fixed code element references to use proper <c> tags instead of backticks

Known Issues / Pending Feedback

Several concerns have been raised by @jkotas regarding this PR's approach:

  1. Example quality: Current examples may not provide useful, copy-pasteable usage patterns (comment 2887291111)
  2. Documentation location: Questions whether .NET Framework-specific documentation belongs in docs/fundamentals (comments 2887319023, 2887364803)
  3. Code organization: Suggestion to use partial methods in neutral file rather than documenting in runtime-specific files (comment 2902035158)
  4. Example structure: Concerns about #pragmas and #regions in example files (comment 2887322288)
  5. Legacy content: Questions about including old .NET Core version quirks and .NET Framework-specific details (comments 2887357879, 2887364803)

These concerns may require a fundamental rework of the PR's approach. Awaiting guidance from @gewarren on how to proceed.

Files Modified

  • src/libraries/System.Private.CoreLib/src/System/Reflection/Emit/DynamicMethod.cs - Main file with complete documentation including all remarks and example references (407 lines added)
  • src/libraries/System.Private.CoreLib/samples/System/Reflection/Emit/DynamicMethod.Examples.cs - New file with code examples in #region blocks (143 lines added)
  • src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/DynamicMethod.CoreCLR.cs - CoreCLR-specific members with supplemental links (59 lines added, 11 lines modified)
  • src/coreclr/System.Private.CoreLib/src/System/Reflection/Emit/DynamicILGenerator.cs - DynamicILInfo class documentation (137 lines added)
  • src/mono/System.Private.CoreLib/src/System/Reflection/Emit/DynamicMethod.Mono.cs - Removed duplicate documentation (48 lines removed)
  • src/libraries/System.Reflection.Emit.Lightweight/ref/System.Reflection.Emit.Lightweight.cs - Removed documentation (moved to source implementation)

Total: ~698 net lines added across all implementations with complete remarks and examples backported from dotnet-api-docs.


🔒 GitHub Advanced Security automatically protects Copilot coding agent pull requests. You can protect all pull requests by enabling Advanced Security for your repositories. Learn more about Advanced Security.

Co-authored-by: gewarren <24882762+gewarren@users.noreply.github.com>
Copilot AI changed the title [WIP] Backport XML doc comments from DynamicMethod.xml Add XML documentation to DynamicMethod from dotnet-api-docs Feb 10, 2026
Copilot AI requested a review from gewarren February 10, 2026 15:59
@github-actions github-actions Bot added the needs-area-label An area label is needed to ensure this gets routed to the appropriate area owners label Feb 10, 2026
Copy link
Copy Markdown
Contributor

@gewarren gewarren left a comment

Choose a reason for hiding this comment

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

@copilot Please address all feedback.

Co-authored-by: gewarren <24882762+gewarren@users.noreply.github.com>
Copy link
Copy Markdown
Contributor Author

Copilot AI commented Feb 10, 2026

@copilot Please address all feedback.

All feedback addressed in commit 2f4fe14. Changes include:

  • Removed duplicate documentation from Mono file
  • Fixed all supplemental links to point to specific member articles
  • Added missing remarks to 20+ properties and methods
  • Updated IsSecurityCritical value description to distinguish .NET (Core) vs .NET Framework behavior

Co-authored-by: gewarren <24882762+gewarren@users.noreply.github.com>
Co-authored-by: gewarren <24882762+gewarren@users.noreply.github.com>
Co-authored-by: gewarren <24882762+gewarren@users.noreply.github.com>
Co-authored-by: gewarren <24882762+gewarren@users.noreply.github.com>
@dotnet-policy-service
Copy link
Copy Markdown
Contributor

Tagging subscribers to this area: @dotnet/area-system-reflection-emit
See info in area-owners.md if you want to be subscribed.

@richlander
Copy link
Copy Markdown
Member

Co-authored-by: richlander <2608468+richlander@users.noreply.github.com>
Copy link
Copy Markdown
Contributor Author

Copilot AI commented Feb 12, 2026

@copilot Please switch the URL form.

Bad form: https://raw.githubusercontent.com/dotnet/docs/main/docs/fundamentals/runtime-libraries/system-reflection-emit-dynamicmethod-createdelegate.md
...

Fixed in commit adc7105. Changed all supplemental link URLs from https://raw.githubusercontent.com/dotnet/docs/main/ to https://github.com/dotnet/docs/raw/main/ format across DynamicMethod.cs, DynamicMethod.CoreCLR.cs, and DynamicILGenerator.cs.

Copilot AI requested a review from richlander February 12, 2026 23:54
@gewarren gewarren enabled auto-merge (squash) February 14, 2026 01:22
@teo-tsirpanis teo-tsirpanis removed the needs-area-label An area label is needed to ensure this gets routed to the appropriate area owners label Feb 14, 2026
@gewarren gewarren changed the title Add XML documentation to DynamicMethod and DynamicILInfo from dotnet-api-docs Backport XML documentation for DynamicMethod and DynamicILInfo from dotnet-api-docs Mar 5, 2026
Console.WriteLine("\r\nName: {0}", hello.Name);
#endregion

#region DeclaringType
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

I think about samples as code snippets that demonstrate the typical usage pattern of the API and that one can copy&paste into their code and then modify to suit their needs. Is my thinking correct?

This code snippet is not anything like that. It largely duplicates boring parts of the documentation, e.g. https://learn.microsoft.com/en-us/dotnet/api/system.reflection.emit.dynamicmethod.declaringtype says "Gets the type that declares the method, which is always null for dynamic methods." and this code sample shows that it is the case. It is not useful.

This is what a good basic example for DynamicMethod can look like (generated via "Give me a basic example of DynamicMethod use"):

using System;
using System.Reflection.Emit;

class Program
{
    static void Main()
    {
        // Create a dynamic method that returns int and takes two ints
        DynamicMethod dynamicAdd = new DynamicMethod(
            "AddNumbers",          // method name
            typeof(int),           // return type
            new Type[] { typeof(int), typeof(int) } // parameter types
        );

        // Get IL generator
        ILGenerator il = dynamicAdd.GetILGenerator();

        // Load first argument
        il.Emit(OpCodes.Ldarg_0);

        // Load second argument
        il.Emit(OpCodes.Ldarg_1);

        // Add them
        il.Emit(OpCodes.Add);

        // Return result
        il.Emit(OpCodes.Ret);

        // Create delegate
        var addDelegate = (Func<int, int, int>)dynamicAdd.CreateDelegate(typeof(Func<int, int, int>));

        // Execute dynamic method
        int result = addDelegate(5, 7);

        Console.WriteLine(result); // Output: 12
    }
}

/// .NET Framework: <see langword="true" /> if the current dynamic method is security-critical or security-safe-critical; <see langword="false" /> if it is transparent.
/// </value>
/// <remarks>
/// For more information about this API, see <see href="https://github.com/dotnet/docs/raw/main/docs/fundamentals/runtime-libraries/system-reflection-emit-dynamicmethod-issecuritycritical.md">Supplemental API remarks for DynamicMethod.IsSecurityCritical</see>.
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

I do like the idea of moving the documentation for complicated .NET Framework specific details somewhere else.

docs/fundamentals does not sound like the right directory for that. It is anything but fundamentals. Can it live under directory that suggest it is .NET Framework specific and not really relevant for modern .NET?

// This file contains code examples for XML documentation.
// The examples are referenced by the DynamicMethod class documentation using #region names.

#pragma warning disable CS8321 // Local function is declared but never used
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

The #pragmas and #regions are not pretty. Samples should be nice clean code.

/// <exception cref="InvalidOperationException">The dynamic method has no method body.</exception>
/// <exception cref="ArgumentException"><paramref name="delegateType" /> has the wrong number of parameters or the wrong parameter types.</exception>
/// <remarks>
/// For more information about this API, see <see href="https://github.com/dotnet/docs/raw/main/docs/fundamentals/runtime-libraries/system-reflection-emit-dynamicmethod-createdelegate.md">Supplemental API remarks for DynamicMethod.CreateDelegate</see>.
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Majority of this doc are several samples. Should it live here together with the samples instead?

/// <param name="parameterTypes">An array of <see cref="Type" /> objects specifying the types of the parameters of the dynamic method, or <see langword="null" /> if the method has no parameters.</param>
/// <exception cref="ArgumentException">An element of <paramref name="parameterTypes" /> is <see langword="null" /> or <see cref="Void" />.</exception>
/// <exception cref="ArgumentNullException"><paramref name="name" /> is <see langword="null" />.</exception>
/// <exception cref="NotSupportedException">.NET Framework and .NET Core versions older than 2.1: <paramref name="returnType" /> is a type for which <see cref="Type.IsByRef" /> returns <see langword="true" />.</exception>
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Would be feasible to drop quirks of very old .NET Core versions from the documentation?

/// <exception cref="ArgumentNullException"><paramref name="name" /> is <see langword="null" />.</exception>
/// <exception cref="NotSupportedException">.NET Framework and .NET Core versions older than 2.1: <paramref name="returnType" /> is a type for which <see cref="Type.IsByRef" /> returns <see langword="true" />.</exception>
/// <remarks>
/// For more information about this API, see <see href="https://github.com/dotnet/docs/raw/main/docs/fundamentals/runtime-libraries/system-reflection-emit-dynamicmethod.md">Supplemental API remarks for DynamicMethod</see>.
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Similar to my other comment- most of this doc is .NET Framework specific (all the discussion about obsolete partial trust, reflection permissions, ...).

@jkotas jkotas disabled auto-merge March 5, 2026 03:25
// Delegate and method creation
//

/// <summary>
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

For types and methods that have split runtime-specific, OS-specific or architecture-specific implementation, I think we should add partial methods into the neutral file (DynamicMethod.cs in this case) and keep the documentation there. Otherwise, it is not obvious where the source of truth of the documentation lives.

@gewarren
Copy link
Copy Markdown
Contributor

gewarren commented Mar 9, 2026

@copilot please respond to all feedback.

Copy link
Copy Markdown
Contributor Author

Copilot AI commented Mar 9, 2026

@copilot please respond to all feedback.

I've reviewed all of @jkotas's feedback. The comments raise significant concerns that suggest this PR may need a fundamentally different approach:

Key Issues Identified:

  1. Examples quality (comment 2887291111): The current examples are documentation-verification code rather than useful, copy-pasteable usage patterns. @jkotas provided a better example showing actual DynamicMethod usage.

  2. Documentation location concerns (comments 2887319023, 2887364803): Much of the documentation is .NET Framework-specific (partial trust, reflection permissions, etc.). The docs/fundamentals location may not be appropriate for legacy .NET Framework details.

  3. Code organization (comment 2902035158): For split implementations, documentation should live in the neutral file (DynamicMethod.cs) with partial method declarations, not in CoreCLR-specific files. This is a structural issue affecting multiple files.

  4. Examples file structure (comment 2887322288): The #pragmas and #regions make the examples less clean.

  5. Historical quirks (comments 2887357879, 2887364803): Questions whether old .NET Core version quirks and .NET Framework-specific details should be included.

Recommendation:

These concerns suggest the PR needs substantial rework beyond simple fixes. The fundamental questions are:

  • Should we backport .NET Framework-specific documentation at all?
  • Where should .NET Framework legacy docs live if we do include them?
  • Should examples be complete rewrites rather than backports?
  • Should the code structure be reorganized to use partial methods?

@gewarren, given the scope of these concerns, would you prefer that I:

  1. Close this PR and create a new approach based on @jkotas's feedback?
  2. Attempt to address each concern incrementally in this PR?
  3. Have a discussion with @jkotas about the overall approach before proceeding?

Copilot AI review requested due to automatic review settings April 7, 2026 22:51
Copy link
Copy Markdown
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

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

Comment on lines +729 to +732
/// <exception cref="ArgumentOutOfRangeException">The method has no parameters.
/// -or-
/// <paramref name="position" /> is less than 0.
/// -or-
Copy link

Copilot AI Apr 7, 2026

Choose a reason for hiding this comment

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

DefineParameter throws only when position < 0 or position > _parameterTypes.Length. When there are no parameters (_parameterTypes.Length == 0), position == 0 is valid (it refers to the return value), so the current <exception> text "The method has no parameters" is not always true. Please adjust the exception documentation to match the actual throwing conditions (e.g., mention the position range and/or clarify the no-parameters case applies when position > 0).

Suggested change
/// <exception cref="ArgumentOutOfRangeException">The method has no parameters.
/// -or-
/// <paramref name="position" /> is less than 0.
/// -or-
/// <exception cref="ArgumentOutOfRangeException"><paramref name="position" /> is less than 0.
/// -or-

Copilot uses AI. Check for mistakes.
@@ -3,7 +3,6 @@
<PropertyGroup>
<TargetFramework>$(NetCoreAppCurrent)</TargetFramework>
<IsPartialFacadeAssembly>true</IsPartialFacadeAssembly>
Copy link

Copilot AI Apr 7, 2026

Choose a reason for hiding this comment

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

Removing <UseCompilerGeneratedDocXmlFile>false</UseCompilerGeneratedDocXmlFile> changes how XML docs are produced for this partial facade assembly and makes it inconsistent with other similar libraries (e.g., System.Reflection.Emit.csproj). Unless there's a specific reason to enable compiler-generated doc XML here, consider restoring this property to avoid unexpected doc output changes.

Suggested change
<IsPartialFacadeAssembly>true</IsPartialFacadeAssembly>
<IsPartialFacadeAssembly>true</IsPartialFacadeAssembly>
<UseCompilerGeneratedDocXmlFile>false</UseCompilerGeneratedDocXmlFile>

Copilot uses AI. Check for mistakes.
Comment on lines +7 to +8
#pragma warning disable CS8321 // Local function is declared but never used

Copy link

Copilot AI Apr 7, 2026

Choose a reason for hiding this comment

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

#pragma warning disable CS8321 suppresses "Local function is declared but never used", but this file doesn't declare any local functions (it has an unused private method instead). Consider removing this pragma (or updating it to suppress the actual warning/analyzer you expect) to avoid carrying a no-op suppression.

Suggested change
#pragma warning disable CS8321 // Local function is declared but never used

Copilot uses AI. Check for mistakes.
Comment on lines +19 to +25
// Note: 'hello' represents a DynamicMethod instance used in the examples below

#region Name
// Display the name specified when the dynamic method was created.
// Note that the name can be blank.
Console.WriteLine("\r\nName: {0}", hello.Name);
#endregion
Copy link

Copilot AI Apr 7, 2026

Choose a reason for hiding this comment

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

The example regions reference a hello variable that isn't declared within the region. When these #region blocks are extracted via the <code ... region="..." /> mechanism, the resulting snippets won't compile or be copy/pasteable as-is. Consider making each region self-contained (declare/initialize a DynamicMethod in the region) or include a shared setup region that gets included with each snippet.

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

github-actions Bot commented Apr 7, 2026

🤖 Copilot Code Review — PR #124227

Note

This review was generated by Copilot.

Holistic Assessment

Motivation: This PR backports XML doc comments from the external dotnet-api-docs repository into the source code for DynamicMethod and DynamicILInfo. Placing documentation at the source is a clear improvement — it keeps docs co-located with the code and enables compiler-generated IntelliSense XML. The motivation is well justified.

Approach: The approach is sound: add <summary>, <param>, <returns>, <exception>, <remarks>, and <example> XML doc comments to all public members, remove the UseCompilerGeneratedDocXmlFile=false setting so the compiler generates the doc XML, and move docs from the ref assembly to the source implementations. The supplemental see href links to the dotnet/docs repo all resolve correctly.

Summary: ✅ LGTM. This is a documentation-only change with no behavioral code modifications. The XML doc comments are thorough, follow docs.prompt.md conventions, and the supplemental links are valid. The few minor observations below are non-blocking suggestions.


Detailed Findings

✅ Documentation Completeness — All public members documented

Every public method, property, and constructor on both DynamicMethod and DynamicILInfo has been documented with appropriate <summary>, <param>, <returns>, <exception>, and <remarks> tags. The documentation follows the conventions in .github/prompts/docs.prompt.md:

  • Properties use "Gets..." or "Gets or sets..." phrasing
  • Boolean parameters use the "true to ...; otherwise, false" pattern
  • Exception descriptions state the condition directly without "Thrown if..." prefixes

✅ Supplemental Links — All verified

All see href links to the dotnet/docs repository resolve correctly:

  • system-reflection-emit-dynamicmethod.md
  • system-reflection-emit-dynamicilinfo.md
  • system-reflection-emit-dynamicmethod-createdelegate.md
  • system-reflection-emit-dynamicmethod-invoke.md
  • system-reflection-emit-dynamicmethod-getilgenerator.md
  • system-reflection-emit-dynamicmethod-issecuritycritical.md

The links use the github.com/dotnet/docs/raw/main/ format, consistent with the repository convention.

✅ csproj Change — Correct

Removing <UseCompilerGeneratedDocXmlFile>false</UseCompilerGeneratedDocXmlFile> from System.Reflection.Emit.Lightweight.csproj allows the default (true) to take effect, so the compiler-generated doc XML from the new source comments is used for IntelliSense instead of a pre-authored file.

✅ Ref Assembly — Docs correctly moved to src

The DynamicILInfo docs were properly moved from the ref assembly to the src implementation. The ref assembly retains no XML doc comments, which follows the convention that ref source does not contain documentation.

💡 RuntimeType reference in GetCustomAttributes exception doc — Minor

In DynamicMethod.cs line 630:

/// <exception cref="ArgumentException"><paramref name="attributeType" /> is not a <see cref="RuntimeType" />.</exception>
```

`RuntimeType` is an internal type, so this `cref` may generate a doc-build warning for users trying to look up the type. However, this accurately describes the exception condition and matches the existing dotnet-api-docs content. No change needed, but worth noting if a future pass standardizes doc references.

#### 💡 Legacy `.NET Framework` text in exception docs — Minor

Several constructor docs include:
```
.NET Framework and .NET Core versions older than 2.1: <paramref name="returnType" /> is a type for which ...

This text describes behavior specific to older frameworks. Since this is a faithful backport from the existing docs, it's acceptable. A follow-up could modernize this to note the exception no longer applies on current .NET, but that's out of scope for this PR.

💡 Examples file — First of its kind in System.Private.CoreLib

src/libraries/System.Private.CoreLib/samples/System/Reflection/Emit/DynamicMethod.Examples.cs is the first file in the samples/ directory under System.Private.CoreLib. The code snippets reference a hello variable initialized as null! and are used only as source references in <code> tags for documentation — they are not compiled as part of the project. The #pragma warning disable CS8321 suppression at line 7 appears unnecessary since the file contains a regular private method, not a local function (CS8321 is for unused local functions). This is a trivial observation and non-blocking.

Generated by Code Review for issue #124227 ·

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

6 participants