<?xml version="1.0" encoding="UTF-8" ?>
<?xml-stylesheet type="text/xsl" href="http://blogs.msdn.com/utility/FeedStylesheets/rss.xsl" media="screen"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:wfw="http://wellformedweb.org/CommentAPI/"><channel><title>Sam Ng's Blog : CLR</title><link>http://blogs.msdn.com/samng/archive/tags/CLR/default.aspx</link><description>Tags: CLR</description><dc:language>en-US</dc:language><generator>CommunityServer 2.1 SP1 (Build: 61025.2)</generator><item><title>Optional Modifiers and Overload Resolution</title><link>http://blogs.msdn.com/samng/archive/2008/03/05/optional-modifiers-and-overload-resolution.aspx</link><pubDate>Wed, 05 Mar 2008 09:12:24 GMT</pubDate><guid isPermaLink="false">91d46819-8472-40ad-a661-2c78acb4018c:8046170</guid><dc:creator>samng</dc:creator><slash:comments>3</slash:comments><comments>http://blogs.msdn.com/samng/comments/8046170.aspx</comments><wfw:commentRss>http://blogs.msdn.com/samng/commentrss.aspx?PostID=8046170</wfw:commentRss><description>&lt;p&gt;Optional Modifiers (or &lt;em&gt;modopts&lt;/em&gt;) are CLR constructs that allow types to be annotated with optional information. This allows compiler writers to annotate their types with additional information that may not have a direct CLR representation. The managed C++ compiler for instance, uses modopts to represent const types. &lt;/p&gt;  &lt;p&gt;The C# compiler does not use modopts for anything - rather, we generally use attributes to augment code. For instance, the difference between &lt;em&gt;out &lt;/em&gt;and &lt;em&gt;ref &lt;/em&gt;is simply an attribute applied to the parameter - &lt;em&gt;out&lt;/em&gt; is just &lt;em&gt;ref&lt;/em&gt; with an attribute tacked onto it. Since the CLR does not consider attributes on parameters or return types as part of the method signature, methods that differ only in &lt;em&gt;out&lt;/em&gt; and &lt;em&gt;ref&lt;/em&gt; look the same. This is why the C# language does not allow you to have two overloads which differ only in their &lt;em&gt;out&lt;/em&gt; and &lt;em&gt;ref&lt;/em&gt;-ness.&lt;/p&gt;  &lt;p&gt;The same is not true of modopts, however. The CLR &lt;em&gt;does&lt;/em&gt; allow you to differentiate methods by their modopts. The following type is a fragment from a perfectly legal and verifiable assembly:&lt;/p&gt;  &lt;p&gt;&lt;font class="code"&gt;.class public auto ansi beforefieldinit Modopt      &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160; extends [mscorlib]System.Object       &lt;br /&gt;{       &lt;br /&gt;&amp;#160; .method public hidebysig instance void       &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160; Foo(int32 x) cil managed       &lt;br /&gt;&amp;#160; {       &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; ...       &lt;br /&gt;&amp;#160; } // end of method Modopt::Foo       &lt;br /&gt;&amp;#160; .method public hidebysig instance void       &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160;&amp;#160; Foo(int32 modopt([mscorlib]IsConst) x) cil managed       &lt;br /&gt;&amp;#160; {       &lt;br /&gt;&amp;#160;&amp;#160;&amp;#160; ...       &lt;br /&gt;&amp;#160; } // end of method Modopt::Foo       &lt;br /&gt;&amp;#160; ...       &lt;br /&gt;} // end of class Modopt&lt;/font&gt;&lt;/p&gt;  &lt;p&gt;Regardless of the fact that none of the Microsoft .NET languages allow creation of such assemblies (ie C++ does not allow you to distinguish methods only by their &lt;em&gt;const&lt;/em&gt;-ness), the CLR allows this, and so compiler implementers that target the CLR must have some story when dealing with these assemblies.&lt;/p&gt;  &lt;p&gt;The C# compiler does not understand any modopts. When we encounter assemblies which contain modopts, we simply ignore them and import them as if they were regular members.&lt;/p&gt;  &lt;p&gt;When we import methods, we import each methods regardless of whether or not it has any modopts in it. We keep a note of the number of modopts in the method signature, but do not report any errors, even if there exist two imported methods which differ only in the modopts on their signature. &lt;/p&gt;  &lt;p&gt;At overload resolution time, we consider each method whose name matches that which we're resolving, and add it to the candidate set. We then filter the candidate set based on arguments and conversions, applying the algorithm described in section 7.4.2 of the &lt;a href="http://download.microsoft.com/download/3/8/8/388e7205-bc10-4226-b2a8-75351c669b09/CSharp%20Language%20Specification.doc" target="_blank"&gt;C# specification&lt;/a&gt;. At that point, if we're left with a candidate set in which all of the methods in the set are identical in signature with the exception of modopts, then we apply the rule that the method with the least number of modopts wins. If there is a tie between two or more methods with the minimal number of modopts, then the compiler reports an ambiguity error.&lt;/p&gt;  &lt;p&gt;This has several ramifications.&lt;/p&gt;  &lt;p&gt;Firstly, it allows methods with modopts not understood by the compiler to be called from the user's C# code. This has the arguable semantics of allowing the user to call a C++ function which expects a &lt;em&gt;const &lt;/em&gt;argument with one which is not &lt;em&gt;const&lt;/em&gt;, for instance. The philosophy of whether or not this is desirable can be argued, but by definition, these constructs are &lt;em&gt;optional&lt;/em&gt;, so according to the definition, this behavior is perfectly acceptable.&lt;/p&gt;  &lt;p&gt;Secondly, it allows importing assemblies which have the illegal-in-C# behavior of being overloaded only by modopts, and allows calling these methods from C# assemblies. Since the compiler doesn't understand the modopts, applying a simple deterministic heuristic seems as good behavior as one can expect.&lt;/p&gt;  &lt;p&gt;&amp;quot;Why can't we do better than applying a heuristic?&amp;quot; you ask. Well, we &lt;em&gt;could&lt;/em&gt; do better than that. We &lt;em&gt;could&lt;/em&gt; note which modopt type is used for each parameter, and despite not understanding it, use it as part of the better-ness algorithm in overload resolution. That would allow the compiler to do something like the following:&lt;/p&gt;  &lt;p&gt;In some assembly created from some other language:&lt;/p&gt;  &lt;blockquote&gt;   &lt;p&gt;&lt;font class="code"&gt;modopt(MyModopt) Foo();        &lt;br /&gt;void Bar(modopt(MyModopt) int x) { ... }         &lt;br /&gt;void Bar(int x) { ... }&lt;/font&gt;&lt;/p&gt; &lt;/blockquote&gt;  &lt;p&gt;And then in C#, for the call &lt;font class="code"&gt;Bar(Foo())&lt;/font&gt; we could determine that the modopt-ed Bar should be called because the return type of Foo has the matching modopt. However, as my colleague &lt;a href="http://blogs.msdn.com/ericlippert" target="_blank"&gt;Eric Lippert&lt;/a&gt; noted, &amp;quot;C# is not a glue language. If you want a glue-language, use VBA or something&amp;quot;. Nicely put. :)&lt;/p&gt;&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=8046170" width="1" height="1"&gt;</description><category domain="http://blogs.msdn.com/samng/archive/tags/CLR/default.aspx">CLR</category><category domain="http://blogs.msdn.com/samng/archive/tags/Optional+Modifiers/default.aspx">Optional Modifiers</category><category domain="http://blogs.msdn.com/samng/archive/tags/Overload+Resolution/default.aspx">Overload Resolution</category><category domain="http://blogs.msdn.com/samng/archive/tags/ModOpts/default.aspx">ModOpts</category></item><item><title>Generic Method Substitutions and Unification - Part two</title><link>http://blogs.msdn.com/samng/archive/2008/03/04/generic-method-substitutions-and-unification-part-two.aspx</link><pubDate>Tue, 04 Mar 2008 07:24:56 GMT</pubDate><guid isPermaLink="false">91d46819-8472-40ad-a661-2c78acb4018c:8018693</guid><dc:creator>samng</dc:creator><slash:comments>2</slash:comments><comments>http://blogs.msdn.com/samng/comments/8018693.aspx</comments><wfw:commentRss>http://blogs.msdn.com/samng/commentrss.aspx?PostID=8018693</wfw:commentRss><description>&lt;p&gt;Last time we talked about generic method substitutions which resulted in types being declared with more than one method with identical constructed signatures. After thinking long and hard about this problem, we've come to a conclusion as to how to resolve this issue in the next release. &lt;/p&gt;  &lt;p&gt;First, lets recap what we know about the problem.&lt;/p&gt;  &lt;ol&gt;   &lt;li&gt;We currently produce code which causes the CLR to throw TypeLoadExceptions at runtime. &lt;/li&gt;    &lt;li&gt;Code that falls into this scenario can be easily fixed by a simple rename &lt;/li&gt;    &lt;li&gt;It is a corner case - typical coding practices will not get you into this scenario &lt;/li&gt;    &lt;li&gt;The code written is not CLS-compliant &lt;/li&gt; &lt;/ol&gt;  &lt;p&gt;The following is a general set of categories that can result in this scenario occurring:&lt;/p&gt;  &lt;pre class="code"&gt;&lt;span style="color: green"&gt;// Same class
&lt;/span&gt;&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;Base&lt;/span&gt;&amp;lt;T&amp;gt;
{
    &lt;span style="color: blue"&gt;void &lt;/span&gt;Foo(T t);
    &lt;span style="color: blue"&gt;void &lt;/span&gt;Foo(&lt;span style="color: blue"&gt;int &lt;/span&gt;t);
}
 
&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;C &lt;/span&gt;: &lt;span style="color: #2b91af"&gt;Base&lt;/span&gt;&amp;lt;&lt;span style="color: blue"&gt;int&lt;/span&gt;&amp;gt; { }
 
&lt;span style="color: green"&gt;// Inherited from base class
&lt;/span&gt;&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;A
&lt;/span&gt;{
    &lt;span style="color: blue"&gt;void &lt;/span&gt;Foo(&lt;span style="color: blue"&gt;int &lt;/span&gt;i) { }
}
 
&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;B&lt;/span&gt;&amp;lt;T&amp;gt; : &lt;span style="color: #2b91af"&gt;A
&lt;/span&gt;{
    &lt;span style="color: blue"&gt;void &lt;/span&gt;Foo(T t) { }
}
 
&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;C &lt;/span&gt;: &lt;span style="color: #2b91af"&gt;B&lt;/span&gt;&amp;lt;&lt;span style="color: blue"&gt;int&lt;/span&gt;&amp;gt; { }
 
&lt;span style="color: green"&gt;// Outer class
&lt;/span&gt;&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;A&lt;/span&gt;&amp;lt;T&amp;gt;
{
    &lt;span style="color: blue"&gt;private void &lt;/span&gt;Foo(T t) { }
    &lt;span style="color: blue"&gt;private void &lt;/span&gt;Foo(&lt;span style="color: blue"&gt;int &lt;/span&gt;i) { }
 
    &lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;C &lt;/span&gt;: &lt;span style="color: #2b91af"&gt;A&lt;/span&gt;&amp;lt;&lt;span style="color: blue"&gt;int&lt;/span&gt;&amp;gt; { }
}
 
&lt;span style="color: green"&gt;// Outer class and its base class
&lt;/span&gt;&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;A&lt;/span&gt;&amp;lt;T&amp;gt;
{
    &lt;span style="color: blue"&gt;public void &lt;/span&gt;Foo(T t) { }
}
 
&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;B&lt;/span&gt;&amp;lt;T&amp;gt; : &lt;span style="color: #2b91af"&gt;A&lt;/span&gt;&amp;lt;T&amp;gt;
{
    &lt;span style="color: blue"&gt;private void &lt;/span&gt;Foo(&lt;span style="color: blue"&gt;int &lt;/span&gt;i) { }
    &lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;C &lt;/span&gt;: &lt;span style="color: #2b91af"&gt;B&lt;/span&gt;&amp;lt;&lt;span style="color: blue"&gt;int&lt;/span&gt;&amp;gt; { }
}&lt;/pre&gt;

&lt;p&gt;Given the above points, we've decided to take the following action:&lt;/p&gt;

&lt;ol&gt;
  &lt;li&gt;If the user specifies that the type is CLS-compliant (via the CLSCompliantAttribute attribute), the compiler will produce a warning indicating that the constructed type is not CLS-compliant &lt;/li&gt;

  &lt;li&gt;If the user does not specify CLS compliance, or specifies that the type is &lt;em&gt;not&lt;/em&gt; CLS-compliant, then we will keep our current behavior, allow the type to be emitted, and produce an assembly that will throw a runtime exception. &lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;This behavior will make it into the next release of the compiler. Until then, don't write code like this if you want it to work! Stay tuned for my investigations on the C# Compiler and modopts!&lt;/p&gt;&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=8018693" width="1" height="1"&gt;</description><category domain="http://blogs.msdn.com/samng/archive/tags/Generics/default.aspx">Generics</category><category domain="http://blogs.msdn.com/samng/archive/tags/CLR/default.aspx">CLR</category><category domain="http://blogs.msdn.com/samng/archive/tags/CLS+compliance/default.aspx">CLS compliance</category></item><item><title>generic method substitutions and unification</title><link>http://blogs.msdn.com/samng/archive/2008/02/13/generic-method-substitutions-and-unification.aspx</link><pubDate>Wed, 13 Feb 2008 20:17:03 GMT</pubDate><guid isPermaLink="false">91d46819-8472-40ad-a661-2c78acb4018c:7677853</guid><dc:creator>samng</dc:creator><slash:comments>6</slash:comments><comments>http://blogs.msdn.com/samng/comments/7677853.aspx</comments><wfw:commentRss>http://blogs.msdn.com/samng/commentrss.aspx?PostID=7677853</wfw:commentRss><description>&lt;p&gt;It's been a while since I've last written - my apologies. We've been hard at work figuring out what the next release of C# will look like, and I'm happy to say that I'm &lt;em&gt;very&lt;/em&gt; excited about what we're working on. Great minds are at work figuring out things like integration of C# with the DLR, dynamic late binding, and better debugging experiences as we speak. Don't worry, I'll be sure to report to you about what &lt;em&gt;they&lt;/em&gt; determine. :)&lt;/p&gt;  &lt;p&gt;I'm always fascinated by discovering subtle details in the language that baffle me. Today I came across such a case. Consider the following code:&lt;/p&gt;  &lt;pre class="code"&gt;&lt;span style="color: blue"&gt;using &lt;/span&gt;System;

&lt;span style="color: blue"&gt;abstract class &lt;/span&gt;A&amp;lt;T&amp;gt;
{
    &lt;span style="color: blue"&gt;public abstract void &lt;/span&gt;Foo(T x);
}

&lt;span style="color: blue"&gt;abstract class &lt;/span&gt;B&amp;lt;T, S&amp;gt; : A&amp;lt;T&amp;gt;
{
    &lt;span style="color: blue"&gt;public virtual void &lt;/span&gt;Foo(S x){}
}

&lt;span style="color: blue"&gt;abstract class &lt;/span&gt;C&amp;lt;T, S&amp;gt; : B&amp;lt;T, S&amp;gt;
{
    &lt;span style="color: blue"&gt;public abstract override void &lt;/span&gt;Foo(T x);
}

&lt;span style="color: blue"&gt;class &lt;/span&gt;D : C&amp;lt;&lt;span style="color: blue"&gt;int&lt;/span&gt;, &lt;span style="color: blue"&gt;int&lt;/span&gt;&amp;gt;
{
    &lt;span style="color: blue"&gt;public override void &lt;/span&gt;Foo(&lt;span style="color: blue"&gt;int &lt;/span&gt;x) {}

    &lt;span style="color: blue"&gt;static void &lt;/span&gt;Main()
    {
        &lt;span style="color: blue"&gt;new &lt;/span&gt;D().Foo(1);
    }
}&lt;/pre&gt;
&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;

&lt;p&gt;What happens here?&lt;/p&gt;

&lt;p&gt;Well, on the surface, this looks like it should be correct right? A's Foo and B's Foo are different, since they have different generic type parameters, and C clearly overrides A's Foo. But the weird part is D's Foo. Does it override A::Foo? Or B::Foo?&lt;/p&gt;

&lt;p&gt;Well, it turns out that the specification outlines that when we look up members to override, we look from our current parent up - that is, when we find a method in one base class, we use that, regardless of other matches in higher ancestral classes. So since C is D's direct base class, D::Foo overrides C::Foo, which overrides the abstract A::Foo.&lt;/p&gt;

&lt;p&gt;So we should be good here right? A::Foo has an implementation in D::Foo, and B::Foo has its own implementation as well. But we're not. We get a runtime type load exception, which complains that D has a method Foo with no body.&lt;/p&gt;

&lt;p&gt;Well that's odd! I thought we just said that everything has an implementation!&lt;/p&gt;

&lt;p&gt;So, being the inquisitive minded person that I am, (and of course, having a bug open to fix this issue), I went and poked around, and discovered that we could fix this problem by having the compiler emit the .override instruction, so that the CLR will know exactly which method we're overriding.&lt;/p&gt;

&lt;p&gt;Well neat, that fixes that problem. Or so I thought!&lt;/p&gt;

&lt;p&gt;Bug number two looks a little different, but very similar. &lt;/p&gt;

&lt;pre class="code"&gt;&lt;span style="color: blue"&gt;using &lt;/span&gt;System;

&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;A&lt;/span&gt;&amp;lt;T&amp;gt;
{
    &lt;span style="color: blue"&gt;protected virtual void &lt;/span&gt;Foo(T x){}
}

&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;B&lt;/span&gt;&amp;lt;T, S&amp;gt; : &lt;span style="color: #2b91af"&gt;A&lt;/span&gt;&amp;lt;T&amp;gt;
{
    &lt;span style="color: blue"&gt;public virtual void &lt;/span&gt;Foo(S x) {}
}

&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;C&lt;/span&gt;&amp;lt;T, S&amp;gt; : &lt;span style="color: #2b91af"&gt;B&lt;/span&gt;&amp;lt;T, S&amp;gt;
{
    &lt;span style="color: blue"&gt;protected override void &lt;/span&gt;Foo(T x) { }
}

&lt;span style="color: blue"&gt;class &lt;/span&gt;&lt;span style="color: #2b91af"&gt;D &lt;/span&gt;: &lt;span style="color: #2b91af"&gt;C&lt;/span&gt;&amp;lt;&lt;span style="color: blue"&gt;int&lt;/span&gt;, &lt;span style="color: blue"&gt;int&lt;/span&gt;&amp;gt;
{
    &lt;span style="color: blue"&gt;protected override void &lt;/span&gt;Foo(&lt;span style="color: blue"&gt;int &lt;/span&gt;x) {}
    
    &lt;span style="color: blue"&gt;static void &lt;/span&gt;Main()
    {
        &lt;span style="color: blue"&gt;new &lt;/span&gt;&lt;span style="color: #2b91af"&gt;D&lt;/span&gt;();
    }
}&lt;/pre&gt;
&lt;a href="http://11011.net/software/vspaste"&gt;&lt;/a&gt;

&lt;p&gt;In this scenario, the compiler again allows us to compile the code without problems, and once again we get a runtime exception. This time, we get an exception saying that we're attempting to lower the access of B::Foo. Interesting. This looks like my first bug! So what do I do? I apply the fix to my first bug and see what happens.&lt;/p&gt;

&lt;p&gt;No luck. &lt;/p&gt;

&lt;p&gt;&amp;quot;But why not?&amp;quot;, you ask? Well, after more digging (and finding the right contacts on the CLR team to chat with), we discovered that the initial fix was wrong! It turns out that by specifying the .override command, we tell the CLR to override A::Foo, but the CLR also finds B::Foo and tells D:Foo to override that as well. &lt;/p&gt;

&lt;p&gt;At the end of it all, we discovered that the entire scenario is an error. Why? The CLI spec, chapter 11.9.9 &amp;quot;Inheritance and overriding&amp;quot; outlines:&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;h6&gt;Type definitions are invalid if, after substituting base class generic arguments, two methods result in the same name and signature (including return type). The following illustrates this point:&lt;/h6&gt;

&lt;h6&gt;[&lt;i&gt;Example:&lt;/i&gt;&lt;/h6&gt;

&lt;h6&gt;.class B`1&amp;lt;T&amp;gt;&lt;/h6&gt;

&lt;h6&gt;{ .method public virtual void V(!0 t) { &amp;#8230; }&lt;/h6&gt;

&lt;h6&gt;.method public virtual void V(string x) { &amp;#8230; }&lt;/h6&gt;

&lt;h6&gt;}&lt;/h6&gt;

&lt;h6&gt;.class D extends B`1&amp;lt;string&amp;gt; { } // Invalid&lt;/h6&gt;

&lt;h6&gt;Class D is invalid, because it will inherit from B&amp;lt;string&amp;gt; two methods with identical signatures:&lt;/h6&gt;

&lt;h6&gt;void V(string)&lt;/h6&gt;

&lt;p&gt;At the end of it all, we discovered that we have a disconnect between the CLR and the C# compiler here. We're currently working on determining what C# spec changes we'll need to make to clarify this case, and from there we'll put a fix together.&lt;/p&gt;

&lt;p&gt;So what did I learn today? Two things:&lt;/p&gt;

&lt;p&gt;1) Our customer that found this bug (I only know them as nikov) is great at finding an exploit, and then massaging it in all possible ways to find other problems (which I might add, is &lt;em&gt;phenomenal). &lt;/em&gt;&lt;/p&gt;

&lt;p&gt;2) People should just not code like this cause its confusing and doesn't work :)&lt;/p&gt;&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=7677853" width="1" height="1"&gt;</description><category domain="http://blogs.msdn.com/samng/archive/tags/Generics/default.aspx">Generics</category><category domain="http://blogs.msdn.com/samng/archive/tags/CLR/default.aspx">CLR</category></item></channel></rss>