Tuesday, February 20, 2007

All .NET developers, proceed immediately to Lutz Roeder's site (remember, I have his office shelves) and download Reflector 5.0.  It has a ton of new features.  So many that I won't attempt to list them here.

This tool was a part of my programmer's arsenal before I came to MS, and I still use it daily to spelunk around the managed code in the CLR and framework, even though I have access to the source code. It is an incredibly powerful tool that combines static analysis, documentation, disassembly (into multiple languages), search, etc.

If you're looking to get into C# for the first time (and I know several of you are), it is helpful to be able to look at your code as if it has been written in C#, or look at code that was written in C# in another language so you can see how C#'s constructs are saving you time (over some languages).

Ok, I said I wasn't going to list features, but I know some of you won't click through the powerpoint deck.  The new version can fold anonymous delegates, and even C# 3.0 lambdas and LINQ queries back into their original syntax.  Of course it's configurable, so you can still see what the compiler's doing for you.  It also adds proper Vista support.  It also adds support for code:// urls (Ex. code://mscorlib/System.Object). Oh, and the Add-Ins are hosted on CodePlex now.  Tons more stuff.  Get it now. No excuses.

posted on Tuesday, February 20, 2007 8:39:40 AM (Pacific Standard Time, UTC-08:00)  #    Comments [0]
 Monday, February 19, 2007

I'll take a break from the technical posts for a moment.  Friday night, I helped out with a youth lock-in up at the church.  It was just like old times (except no spitting ice down the stairs).

The youth group at our church is decidedly smaller than at our church in Austin.  But, it makes sense because the actual church is much smaller than our church in Austin.  There were about 8 guys there (the girls were elsewhere).  We pretty much played video games all night.  We had 2 Wii's, a PS2, an XBox and an XBox360.  We also played some (outdoor) capture the flag.  It was a variant that I hadn't played before in Texas, and I didn't really understand it.

The highlight of the night was linking the xbox and the 360 and playing some 4 vs. 4 Halo 2.  I don't like to brag, but I did pretty well.  Mainly it was fun because they were trash-talking pretty bad about how they were going to beat me.  One game in particular (4v4 Team Slayer on Beaver Creek) I lead my team to victory with 35 kills and only 3 deaths.

It was cool to connect with the guys in that way. They are having a "ski day" on Wednesday, and I'm bummed that I have to work.  The whole concept of a day trip for snow skiing is completely foreign and bizarre to me.

posted on Monday, February 19, 2007 11:43:11 AM (Pacific Standard Time, UTC-08:00)  #    Comments [3]
 Friday, February 16, 2007

So, my last post talked about delegates.  In it, I mentioned some compiler trickery involved in declaring events, but I didn't bother explaining it.  After reading it over again, and getting some feedback, I felt bad about glossing over what is pretty much the mainline scenario for delegates. So, what is an event?

An event is kind of like a broadcast. It enables an object to notifiy subscribers when some "event" occurs, give them relevant information about the event, and allow them to do something in response.  And, you guessed it, delegates are at the core of making this work.

Fundamentally, events are a callback mechanism, and could be implemented without delegates using anything from raw function pointers to interfaces, and the CLR doesn't keep you from doing either of those, but there's value in a consistent pattern.  In fact, the designers of the CLR felt so strongly about the value of this particular pattern, that it is part of the CLI spec (along with properties, another pattern that is implemented by other more fundamental constructs).

So, how do you make an event?  Well, in C#, you declare an event like you would declare a field whose type is some delegate and you add the "event" keyword.  So, somewhere in a type, you would have something like:

public event EventHandler Click;

Whether or not it's public depends on how you expect the event to be used.  EventHandler is a delegate with the following signature:

void EventHandler(object sender, EventArgs e);

This signature is another pattern that I'll talk about later.  For now, lets look at what the compiler does for our event declaration.  The compiler gives 3 things (if you don't count the things it already did for the delegate EventHandler):

  • A private field whose type is the delegate EventHandler
  • A (public in this case) method "accessor" for adding delegate callbacks: add_Click //Click comes from the event name
  • A (public in this case) method "accessor" for removing delegate callbacks: remove_Click

When other code wants to hook up to your event, they use the += operator on your event.  This is really syntax sugar for calling the add_Click method.  And, conversely the -= operator calls the remove accessor.

Interestingly, you can write your own implementation for the event pattern.  You might want to do this to save size in a possibly large tree structure with lots of events at each node.  ASP.net does this with controls.  Rather than every Control having tons of fields for each event, it has a sparse dictionary of event delegates, that is only populated for events that have "subscribers".  With a tree that can easily have thousands of controls per page view, this results in a sizeable savings.  How do you do this?  Well, in C#, you use the little known syntax:

public event EventHandler Click {

add {/* do something with value in here */}

remove {/* do something with value in here */}

}

Looks like a property eh? This causes the compiler not to create the 3 things I mentioned above. Instead, it calls your add and remove accesors to do the adding and removing (via the value keyword just like properties).  In it, you can do anything you want, although it's advisable to keep the same semantics as the default implementations.

So, lets talk a little bit about what happens when an event happens and it is called.  Let's say that several other classes have registered for your event (via the += syntax or whatever the compiler supports).  Inside your class, you simply call the delegate (there's a recommended pattern for this as well).  But wait, there's more than 1 subscriber!  Remember, delegates aren't just function pointers, and they are more powerful than using interfaces alone.  If you'll recall in the last post, I said that when you create a delegate, you're really getting a MulticastDelegate, which tracks an invocation list of delegates to run. (this is why the standard event pattern returns void, otherwise, you've got the weird situation of multiple return values from what appears to be a single call).  Under normal circumstances, each delegate in the invocation list is called and execution resumes.

posted on Friday, February 16, 2007 10:36:02 AM (Pacific Standard Time, UTC-08:00)  #    Comments [0]
 Thursday, February 15, 2007

Soon, my ownership area will extend to include delegates.  Since I'm fairly excited about this, I thought I'd celebrate by writing a little something about them.  So, what are delegates?  A casual observer might be tempted to write off delegates as a sort of managed function pointer.  While this comparison is certainly accurate, there's much more to explaining the power of delegates.

In general, delegates are a sort of universal method dispatch mechanism.  Initially, the scenario they supported was callbacks.  Delegates are one of the things that distinguish the CLR from other VMs like Java.  Java requires the use of interfaces to implement callbacks. (I'm only calling that out as a distinction, not saying the Java way is bad. although personally I like what delegates bring to the table)  So, delegates let you wrap up a method as an object to pass around, with the expectation that it will be called from another context.

Its sort of hard to talk about delegates because the discussion is often framed by the language that's exposing them.  Currently, no managed language exposes them in the way that they are represented in IL.  In C# and VB, you declare a delegate by simply defining a method signature.  From an IL perspective, the compilers generate a class that inherits from MulticastDelegate (another story I'll get to later), with an Invoke method that matches your signature, and some various constructors to support different things.  (You also usually get the corresponding asynchronous calling pattern support methods, but I don't want to get into that)  Some other delegate-related compiler trickery is involved in declaring events, which I'll cover later.

Under the covers, a delegate [conceptually] contains 2 things:

  • A target object
  • A target method

Now, generally speaking, the target method is the method to be run, and the target object is the object on which the target method will be run, but there are cases where this line is blurred a bit.  For instance, when a delegate is pointing to a static method, the target object is conceptually null (internally it's not, but that's an implementation detail).  I'll get into the other cases later.

So now you're saying, "Yup, that's a delegate.  Big deal.  What's so cool about that?"  What's cool about that, my friend is that delegates are the things that power virtually all of the coolest new language features that came out in v2.0 and will be coming out, including all the dynamic language goodness like IronPython.  It's the dynamic stuff that is really exciting, so let's talk about how delegates enable dynamic languages on top of a statically typed system.

(To be fair, Jim Hugunin did his initial Iron Python work before these features were available, but they now play a big role)  One of the pieces of work done in v2.0 was called delegate relaxation.  Previously, the target method had to match the delegate signature exactly.  Now, as you might expect intuitively, the signature can be relaxed such that the target method can have "more general" parameters and return something "more specific" than the delegate's signature.  This is typically defined in terms of covariance and contravariance, terms that even people who understand them get confused.  Here's the way I usually remember it: If I could wrap the target method with a method having the delegate's signature without casting, it will work. Anyway, this feature makes delegates quite a bit more flexible.

Before I go into the other features, lets talk a little about implementation. In normal method calling in the CLR, the first parameter becomes the "this" object.  (Which is why you see ldarg.0 in IL to put it on the stack.)  So, conceptually, the target object represents the first argument for the method. (There is an implementation detail that allows static methods to be called using the same convention, which is a really elegant solution) So, by extending this idea of the target object simply being the first argument, we get a couple of interesting variants.

The first is what is called "closed" static delegates.  This allows you to specify the first argument of a static method at delegate creation rather than at the callsite.  Notice this maps quite nicely to the dynamic language concept of adding a method to an existing instance of an object.  The language runtime just needs to be able to track these extra methods as part of its method dispatch logic.

The second feature is "open" instance delegates.  This allows you to create a delegate that points to an instance method, but doesn't define the target object.  Instead, the delegate signature can have an extra first argument that will specify the target object at the callsite.  When used with LCG (DynamicMethod), this can be used to implement things like adding a method to an existing type.  Again, the language runtime merely needs to add the logic to method dispatch.

These 2 features are intriguing to me because they are not directly exposed from VB or C#.  I believe VB9 exposes these, but they are not accessible in an early bound way in C#.  You can, however, create them via Delegate.CreateDelegate() using reflection, or use Reflection.Emit to generate the corresponding IL.

Hopefully, I'll have some time in the future to do some samples of these as well as discuss more about how these improve the dynamic language support in the CLR.

posted on Thursday, February 15, 2007 2:32:53 PM (Pacific Standard Time, UTC-08:00)  #    Comments [1]
 Monday, January 29, 2007

I dealt with several situations in the past months where the crux of the problem was confusion over assemblyname and filename.  Let's define what we're talking about:

  • Filename - The name of a file in the filesystem, such as System.dll
  • Assemblyname - The name given to an assembly to establish its identity.  In this case, we'll only concern ourselves with the "simple" name. such as System

Usually, any confusion that arises between the two can be resolved by reminding people that a filesystem is just one of the places you can get an assembly from.  For instance there are APIs for getting assemblies from byte arrays.

For those that still do see it... In the managed world, the assemblyname gives identity to the code that resides in the assembly.  If you have 2 assemblies with the same assemblyname, you expect them to represent the same identity (perhaps different versions, build flavors, bitness, etc.).  If we relied on the filesystem name, the identity of the code could change just by changing the filename.  That's not the semantics we expect.

So, why does the filename matter?  Why do we recommend keeping them the same?  Some of the reasons are simple convenience.  It's nice to look at a file and know what it is without cracking it open.  If the names are different, it's like me going to a party and wearing a nametag that says, "Peter".  While there is nothing keeping me from doing it, it causes confusion.  However, another more important reason to keep them the same is that assemblies are rarely loaded by filename.  References and most dynamic loads are done by assemblyname.  You don't take a reference to System.dll, you take a reference to System.  At some point, the loader has to find an appropriate file to load to satisfy that reference.  If System's filename is Peter.dll, then it's going to have a difficult time finding it to load.  This is actually the very reason that gacutil will not let you install an assembly into the global assembly cache if the filename doesn't match the assemblyname.  However, I think it's silly that it doesn't just fix the name for you.

What about multi-module assemblies?  Well, it's the module with the assembly manifest that matters.  It's the one that should match.  Then the rest of the files need to match the assembly manifest :). But, if you're using multi-module assemblies, let me know.  I'd like to know why.

posted on Monday, January 29, 2007 12:46:56 PM (Pacific Standard Time, UTC-08:00)  #    Comments [1]
 Thursday, January 25, 2007

Yup, it's that time again.  Today is my birthday.  I was lucky enough to get a Wii, which has been quite enjoyable.  Now I just need to get the component cables so I can stand to look at it. :)

posted on Thursday, January 25, 2007 9:05:54 AM (Pacific Standard Time, UTC-08:00)  #    Comments [2]
 Monday, January 22, 2007

I've mentioned before that one of my ownership areas at MS is the CLR "shim".  Most people I've said that to ask me, "What's that?".  I usually reply that generally, it's mscoree.dll, to which they typically respond, "Oh yeah.  What does that do?"  In general terms, the shim is in charge of firing up the runtime in a process.  In addition, it exposes all the hosting APIs and other stuff you need to do stuff with the CLR from unmanaged code. If you look at a managed app, you will see that it has a dependency on mscoree.dll, and nothing else CLR-related.  Ater the runtime is spun up, most of the things that mscoree exposes are simply forwarded calls into the mscorwks.dll of the runtime you have installed.

What's interesting about mscoree.dll, is that it is the only piece of the runtime that doesn't run side by side.  You can have v1.1 and v2.0 installed on the machine, but you will only have one mscoree.dll.  You always have the version of mscoree.dll that corresponds to the latest version of the runtime installed on your machine (unless you have installed a patch or something that services mscoree, in which case you may have a v2.0 shim even though only v1.1 is installed on your machine).

So, naturally, backwards compatibility is extremely important in the Shim.  When you start up managed code, the Shim decides which version of the CLR to fire up based on lots of different things.  These things are all fairly well documented and all have a specific scenario they enable, but by their nature they are very confusing.

Aside: When I was job hunting, I interviewed at several companies other than Microsoft.  During some of those other interviews, I was asked questions about what runtime would be started under certain conditions. The rules are so confusing, that some of the interviewers, although all extremely smart people, had formed incorrect models of what the rules were.  Some told me I had the wrong answer to their question, when if fact it was correct. (that's not to say that I knew the correct answers to all of them.)

I'm not certain that I can clear up the confusion, but I do hope to have a series of posts in the coming months on why the shim does what it does under certain circumstances.  Then, at least you might understand what's going on when it happens.

posted on Monday, January 22, 2007 10:50:36 AM (Pacific Standard Time, UTC-08:00)  #    Comments [0]
 Tuesday, January 09, 2007

I have had occasion recently to play with the latest (December 2006) CTP of WPF/e.  It's a really cool technology that I think is poised to change the way people write rich web apps.  It's cross-platform (Windows and MacOS at the moment) and cross-browser (IE5-7, Firefox, and Safari at the moment).

The CTP has some limitations at the moment that are keeping it from really being a replacement for HTML-based web apps (It's missing the WPF layout manager for one), but it certainly doesn't keep you from doing some really cool stuff with it.

Rather than just point you to the existing samples (scroll down to see them), I thought I'd put together one of my own.  I created a proof of concept replacement for my blog's header that shows my photos from Flickr as if they were hundreds of polaroids strewn about and panning by.  You'll need to go to the WPF/e site and download the plugin that's appropriate for your OS (look under Top Downloads on the right). After you've done that, click the image below to see the demo.

Click to see demo

It consists of:

  • A xaml file with the "background" (some of which is in the foreground) and some general declarative animation instructions.
  • An html file with some script infrastructure for pulling JSON data from the Flickr APIs and turning them into visual elements.
  • The provided WPF/e scripts for instantiating the control
  • the MicrosoftAjax.js file from the AJAX library.
  • A little .ashx proxy for routing the async calls to Flickr (to avoid cross-domain scripting issues)

If you watch long enough, it should scroll through all 7,140 of my pictures (with some gaps in between while loading new images), and then start over.

All in all, it was really easy to do.  There are some problems I need to address before it could realistically take over as the header for my blog, but I think it shows some real promise.  I can't wait for the actual WPF/e release.

posted on Tuesday, January 09, 2007 2:52:10 PM (Pacific Standard Time, UTC-08:00)  #    Comments [1]