-
Notifications
You must be signed in to change notification settings - Fork 8.1k
Mark applicable structs as readonly and use in-modifier #13919
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
3e3f879
b16e94a
e3fde33
458d2e6
656a101
bd43a69
301f083
be45267
b5ed5ef
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -488,9 +488,9 @@ public bool WriteMessageEvent(string eventMessage) | |
| /// </param> | ||
| /// <param name="eventPayload"> | ||
| /// </param> | ||
| public bool WriteEvent(ref EventDescriptor eventDescriptor, params object[] eventPayload) | ||
| public bool WriteEvent(in EventDescriptor eventDescriptor, params object[] eventPayload) | ||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Changing the signature on a public method like this is a breaking change
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The compiler doesn't permit overloading on ref/out/in differences, so this change is non-breaking.
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Technically the issue isn't with the compiler, but with the runtime. Modules compiled against the old API surface must continue to work after any changes are made to the API. But I tested it out with a toy project (an exe and a lib, where I built an
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Yeah that's still C# compiler rules, where the compiler statically decides which overload to resolve for a call. My concern was that the resolved method call in the IL might not match what the library was originally compiled against when its loaded at runtime (so even though the original program isn't broken it still requires recompilation, which is a dealbreaker for modules). It makes sense that that's not the case though. |
||
| { | ||
| return WriteTransferEvent(ref eventDescriptor, Guid.Empty, eventPayload); | ||
| return WriteTransferEvent(in eventDescriptor, Guid.Empty, eventPayload); | ||
| } | ||
|
|
||
| /// <summary> | ||
|
|
@@ -504,7 +504,7 @@ public bool WriteEvent(ref EventDescriptor eventDescriptor, params object[] even | |
| /// </param> | ||
| [System.Security.SecurityCritical] | ||
| [SuppressMessage("Microsoft.Usage", "CA2208:InstantiateArgumentExceptionsCorrectly")] | ||
| public bool WriteEvent(ref EventDescriptor eventDescriptor, string data) | ||
| public bool WriteEvent(in EventDescriptor eventDescriptor, string data) | ||
| { | ||
| uint status = 0; | ||
|
|
||
|
|
@@ -534,7 +534,7 @@ public bool WriteEvent(ref EventDescriptor eventDescriptor, string data) | |
| userData.DataPointer = (ulong)pdata; | ||
|
|
||
| status = UnsafeNativeMethods.EventWriteTransfer(_regHandle, | ||
| ref eventDescriptor, | ||
| in eventDescriptor, | ||
| (activityId == Guid.Empty) ? null : &activityId, | ||
| null, | ||
| 1, | ||
|
|
@@ -565,7 +565,7 @@ public bool WriteEvent(ref EventDescriptor eventDescriptor, string data) | |
| /// pointer do the event data | ||
| /// </param> | ||
| [System.Security.SecurityCritical] | ||
| protected bool WriteEvent(ref EventDescriptor eventDescriptor, int dataCount, IntPtr data) | ||
| protected bool WriteEvent(in EventDescriptor eventDescriptor, int dataCount, IntPtr data) | ||
| { | ||
| uint status = 0; | ||
|
|
||
|
|
@@ -575,7 +575,7 @@ protected bool WriteEvent(ref EventDescriptor eventDescriptor, int dataCount, In | |
|
|
||
| status = UnsafeNativeMethods.EventWriteTransfer( | ||
| _regHandle, | ||
| ref eventDescriptor, | ||
| in eventDescriptor, | ||
| (activityId == Guid.Empty) ? null : &activityId, | ||
| null, | ||
| (uint)dataCount, | ||
|
|
@@ -602,7 +602,7 @@ protected bool WriteEvent(ref EventDescriptor eventDescriptor, int dataCount, In | |
| /// <param name="eventPayload"> | ||
| /// </param> | ||
| [System.Security.SecurityCritical] | ||
| public bool WriteTransferEvent(ref EventDescriptor eventDescriptor, Guid relatedActivityId, params object[] eventPayload) | ||
| public bool WriteTransferEvent(in EventDescriptor eventDescriptor, Guid relatedActivityId, params object[] eventPayload) | ||
| { | ||
| uint status = 0; | ||
|
|
||
|
|
@@ -719,7 +719,7 @@ public bool WriteTransferEvent(ref EventDescriptor eventDescriptor, Guid related | |
| } | ||
|
|
||
| status = UnsafeNativeMethods.EventWriteTransfer(_regHandle, | ||
| ref eventDescriptor, | ||
| in eventDescriptor, | ||
| (activityId == Guid.Empty) ? null : &activityId, | ||
| (relatedActivityId == Guid.Empty) ? null : &relatedActivityId, | ||
| (uint)argCount, | ||
|
|
@@ -737,7 +737,7 @@ public bool WriteTransferEvent(ref EventDescriptor eventDescriptor, Guid related | |
| } | ||
|
|
||
| [System.Security.SecurityCritical] | ||
| protected bool WriteTransferEvent(ref EventDescriptor eventDescriptor, Guid relatedActivityId, int dataCount, IntPtr data) | ||
| protected bool WriteTransferEvent(in EventDescriptor eventDescriptor, Guid relatedActivityId, int dataCount, IntPtr data) | ||
| { | ||
| uint status = 0; | ||
|
|
||
|
|
@@ -747,7 +747,7 @@ protected bool WriteTransferEvent(ref EventDescriptor eventDescriptor, Guid rela | |
| { | ||
| status = UnsafeNativeMethods.EventWriteTransfer( | ||
| _regHandle, | ||
| ref eventDescriptor, | ||
| in eventDescriptor, | ||
| (activityId == Guid.Empty) ? null : &activityId, | ||
| &relatedActivityId, | ||
| (uint)dataCount, | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -68,7 +68,7 @@ public interface IDynamicParameters | |
| /// Type used to define a parameter on a cmdlet script of function that | ||
| /// can only be used as a switch. | ||
| /// </summary> | ||
| public struct SwitchParameter | ||
| public readonly struct SwitchParameter | ||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This one could be an issue --
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. But [1] https://blog.paranoidcoding.com/2019/03/27/readonly-struct-breaking-change.html
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Ok I'm fairly convinced by this |
||
| { | ||
| private readonly bool _isPresent; | ||
| /// <summary> | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure about changing public structs to readonly -- existing code that relies on the previous form may be affected
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This struct is immutable by design.