Useful VS2010 plug-ins

VS2010’s built in extensions manager is a really nice addition. There are already a lot of very good plug-ins available on it. Here are some of the ones I have installed that I find useful, you might too. Normal caveats apply about me not being responsible if one of these plug-ins causes your computer to catch fire and runs off with your wife/husband etc.

image

 

*updated* with new plug-ins.

Setting up Mercurial Under IIS 6

I was just looking at setting up Mercurial on my Windows Home Server and found some good blog articles. My first one was on Jeremy Skinner’s blog here which shows how to configure it under CGI on IIS 7. I’d like to run it as an ISAPI extension though since that would be much faster, I then found this blog article from Matt Hawley which shows how to configure Mercurial as an ISAPI extension under IIS 7.

The final blog article was from another Matt here that shows how to install it under IIS 6. Now I’d already figured out most of this but I was looking for more info because of a little problem, I kept getting 404 errors whenever I accessed the URL. I couldn’t see anything wrong….

Eventually after much wailing and gnashing of teeth I realised my stupidity in a real DOH! moment. I thought I’d share this though since you might also come across this one. I forgot the with IIS 6 it will by default block all ISAPI and CGI extensions unless they are explicitly added into an allow list. I’d forgotten to add the Mercurial DLL into the list. A quick trip to the IIS admin console and the web service extensions section, add in the _hgwebdir_wsgi.dll as an allowed extension and all is now well. Hours wasted to a silly mistake, will remember that one for a while!

Flexible Data Template Support in Silverlight

WPF has a great feature called data templates. These allow you to specify the visual appearance for a data object, you can either place them in a control or put them in a resources section to reuse them for multiple controls.

The real benefit in my opinion of them is that you can tag them with the type of the data object that they display, WPF will then automatically select the appropriate data template when it needs to render an item of that type. This makes building controls that display heterogeneous data structures really easy.

I was recently working on a Silverlight application in which I had a 3 pane view, one of the panes contained the main content and the other two contained navigation elements in a typical master / details type scenario. The items in the navigation pane were are of different types all deriving from a common base class. When I selected the item in the navigation pane I wanted to display the details in the main pane, however since each item was of a different type they needed to display differently in the main pane.

Fantastic I thought, I can use data templates and this’ll be easy. That was when I found out that Silverlight doesn’t support data templates that vary by type. You can define them and share them using a named key but unfortunately you cannot assign a target type to them like you can in WPF.

This wouldn’t be much of a blog article unless I’d found a way around this though so here we go. There are probably several different ways you could do this but this is the way I chose and it seems to work quite nicely, at least for me.

Bring on the converter

What I thought was I can databind the data object to the data template property of the control and implement a converter that yields a data template based on the type of the data object it receives. Ignoring the loading of the resources you can see the code below takes the type of the value passed into the converter and then looks it up in a map to find out the template to use which is then returned.

Convert() method
  1. public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
  2. {
  3.     if(LoadFromApplicationResources && !_loaded)
  4.         LoadFromResources();
  5.  
  6.     if (value != null)
  7.     {
  8.         Type valueType = value.GetType();
  9.  
  10.         return (from template in TemplateMap
  11.                 where template.SourceType == valueType.FullName
  12.                 select template.DataTemplate).FirstOrDefault();
  13.     }
  14.  
  15.     return null;
  16. }

This allows the XAML to look like this. The content control for the main pane binds the content to the current item in my data context (which is a view model), this item has a child property called Item that I want to use to choose the type of data template to use. I then use the converter MainItemTemplates to convert the CurrentItem.Item into a data template for the content control.

Using the converter
  1. <ContentControl Content="{Binding CurrentItem}"
  2.                 ContentTemplate="{Binding CurrentItem.Item,Converter={StaticResource MainItemTemplates}}"
  3.                 />

Declaring the converter in the resources then looks like this. The converter declares (in this case) 4 mappings from various source types into various data templates previously defined in the resources. These data templates are defined as regular keyed resource data templates.

Declaring the converter
  1. <converters:TemplateSelectorConverter x:Key="MainItemTemplates">
  2.     <converters:TemplateMapEntry SourceType="DataItems.QuestionItem" DataTemplate="{StaticResource QuestionItemTemplate}" />
  3.     <converters:TemplateMapEntry SourceType="DataItems.ServiceItem" DataTemplate="{StaticResource ServiceItemTemplate}" />
  4.     <converters:TemplateMapEntry SourceType="DataItems.DownloadItem" DataTemplate="{StaticResource DownloadItemTemplate}" />
  5.     <converters:TemplateMapEntry SourceType="DataItems.LinkItem" DataTemplate="{StaticResource LinkItemTemplate}" />
  6. </converters:TemplateSelectorConverter>


Using attached properties

The above approach is nice since it allows you to have multiple mappings of types to data templates and also allows you to have the data template selector something different from the item being data bound to the content control. One downside to it is that you have to build and maintain the map though.

In order to get a more WPF like effect I introduced an attached property with some behaviour as shown below. I then look for any data templates in the application resources that have this property attached and pre-populate the map from them.

The attached property
  1. public static readonly DependencyProperty SourceTypeProperty =
  2.             DependencyProperty.RegisterAttached("SourceType", typeof(string), typeof(TemplateSelectorConverter),
  3.                                                 new PropertyMetadata(null));

GetSourceType() is the get method for the attached property declared above. Currently GetDataTemplates() only looks in the application resources but later it could check all of the resources in the application.

Pre-populating the map
  1. private void LoadFromResources()
  2. {
  3.     _loaded = true;
  4.  
  5.     var dataTemplates =
  6.         from resource in GetDataTemplates()
  7.         let sourceType = GetSourceType(resource)
  8.         where !string.IsNullOrEmpty(sourceType)
  9.         select new TemplateMapEntry
  10.                {
  11.                    SourceType = sourceType,
  12.                    DataTemplate = resource,
  13.                };
  14.  
  15.     TemplateMap.AddRange(dataTemplates);
  16. }
  17.  
  18. private static IEnumerable<DataTemplate> GetDataTemplates()
  19. {
  20.     return Application.Current.Resources.Values.OfType<DataTemplate>();
  21. }

And (almost) finally to use the attached property in the XAML on a data template.

Using the attached property
  1. <DataTemplate x:Key="QuestionItemTemplate"
  2.               converters:TemplateSelectorConverter.SourceType=
  3.               "DataItems.QuestionItem">

Then declare the converter and tell it to load the map from application resources.

Declaring the converter
  1. <converters:TemplateSelectorConverter x:Key="MainItemTemplates" LoadFromApplicationResources="True"/>


Conclusion

This is just one way of adding support for data templating heterogeneous data structures in Silverlight but it worked quite well for me. Any comments or suggestions how to improve it are welcome.

You can download the sample source for the converter from http://garfoot.com/samples/TemplateSelectorConverter.zip. Please note this is sample code so treat it as such.

Comments are now moderated

Recently I've been getting a lot of spam comments, so unfortunately I've had to turn on moderation on the comments. If it slackens off again I'll look at unmoderating the comments.

Performance Profiling .NET Applications Using the Visual Studio Profiler

When I consult with development teams, at some point performance always rears its ugly head. When I code review something I often find it overly complex with lots of caching, “clever” code etc. and when I ask why the code is this complex the answer is usually for performance, E.g. “we need to cache the results as that’s an expensive operation”.

At this point I usually ask if they have any evidence to show how expensive the operation is, all too often the answer is “no”. Once again another developer is the victim of premature optimisation.

Now don’t get me wrong, optimising code is important, things like caching can indeed help reduce the cost of expensive operations. However, if that operation is only called once is caching really going to help? If the operation is “expensive” but only takes 2ms to execute and is called next to an operation that takes 2s is optimising it really going to help? I hope you all answered no there!

So how do we find out if we need to optimise, where do we focus our effort with limited time and resources to get the best return? That’s where profilers come in. If you’ve not used one before, they are applications that monitor how an application runs, usually capturing data such as number of calls, time taken, memory allocated etc.

Visual Studio comes with some pretty good profiling tools in the Team System version that can really help. There is a nice Performance Wizard on the Analyze menu that does much of the work for you. But as nice as the wizard is, it doesn’t fit all situations. If you need to profile services, code running as different users, on servers without VS installed or just need more control then the command line tools is where it’s at. You can download a standalone version from http://www.microsoft.com/downloads/details.aspx?familyid=fd02c7d6-5306-41f2-a1be-b7dcb74c9c0b&displaylang=en for installation on servers or machines without VS.

In this post I’m going to go through the (simple) steps needed to profile an application, I’ll leave interpreting the reports to another post.

Types of profiling

There are two types of profiling you can do, sampling and instrumentation. I’m going to mainly cover instrumentation as that’s the one I usually use as it’s the most accurate, it is however also the most invasive and requires changing assemblies so isn’t always suitable.

Setting up the profiler

If you have Visual Studio Team System for Developers then you have the profiler installed. The first thing to do is configure the command prompt to let you use the profiling tools. You’ll need to add them into your path. They are located by default in “C:\Program Files\Microsoft Visual Studio 9.0\Team Tools\Performance Tools” but it may be a different location on 64bit (Program Files (x86)) or if you' installed to a none standard location.

Once that’s done you need to enable the environment variables the profiler needs. You can do this with the VSPerfCLREnv command. You want to use /traceon if you are able to trace the application from the command console window by launching it but if you are tracing a service then use /globaltraceon. The global one will most likely need a reboot for the service to pick up the new settings so I usually do that afterwards.

Note if you are using sampling then you use /sampleon and /globalsampleon instead.

Preparing the assemblies

Now that the profiler is configured you need to prep the assemblies as we are instrumenting and not sampling. If you are sampling you can miss this step out.

Build your assemblies as normal, ensure you have pdb files generated though as you’ll need those later to view the source code from the profiling reports.

Now instrument all of the assemblies you want performance data from, you use VSInstr to do this. Simply specify the assembly name and you’ll get a new assembly and pdb file, the original ones get renamed to .orig.

Note that if you do this to a strong named assembly it’ll break the signing, you’ll need to use sn with the –Vr option to skip strong name verification on the assemblies you have instrumented. Don’t forgot to switch it back once you are done.

Profiling

Now you’re all ready to profile. To control the profiler you simply start it using the VSPerfCmd command. You specify the /start:trace option to start instrumenting or /start:sample to start sampling. You will also need /output to set the output filename for the trace results.

E.g. VSPerfCmd /start:trace /output:traceoutput.vsp

If you are tracing a service you’ll also need to add /user: and probably /crosssession as the service will be running as a different user and in a different session from the profiler. You’ll need to have the permissions to do this.

Once the profiler is started simply now run up your application and use it. It's important to make sure that the application is not running until after the profiler is started, this is often missed when profiling IIS, stop the app pool or do an IISReset before starting the profiler.

When you’ve done you need to shutdown the profiler, simply issue VSPerfCmd /shutdown to do that.

You should now have a shiny new .vsp file that contains the trace data. You can open this in Visual Studio, however the chances are you’ll just see stream of hex addresses and no source information.

I’m packing symbols

To make a .vsp file that can link back to source you need symbols, remember I told you that you’ll need these so if you don’t have them go back and start again and tell yourself that you’re a very naughty boy/girl (delete as appropriate).

How do we get the symbols in there or what if I don’t have Visual Studio? You can use the VSPerfReport command to pack the symbols into the .vsp file and to generate a text report of the trace.

You want to ensure you have your symbols set up to pull down from a symbol server to get all of them for the core .NET bits. To do that set the environment variable _NT_SYMBOL_PATH to point to the symbol server and your local cache.

E.g. set _NT_SYMBOL_PATH=symsrv*symsrv.dll*c:\mylocalcache*http://msdl.microsoft.com/download/symbols

See http://support.microsoft.com/kb/311503 for more details on setting the symbol path.

I usually just do a VSPerfReport /packsymbols /summary:function /symbolpath=<path to .instr.pdb files> traceoutput.vsp to get my symbols packed. This will also generate a summary text file, you need to do that even if you don’t need the summary or the symbols will not get packed. If you want a more detailed report then you can use the /summary option to specify what information you want in CSV format.

Comparing runs

Another nice feature of VSPerfReport is the /diff option. This lets you compare two .vsp files and shows the differences, this can be useful for checking against a baselined performance session to see if you’ve made things better or worse.

And finally…

Don’t forget that you want to turn instrumentation off if you are running it on a production server, replace the assemblies with the uninstrumented versions, revert the sn commands if you used them, run VSPerfCLREnv /off to clean up environement variables.

I’ll try and post something about interpreting the reports that the profiler gives you soon, after all doing all of this doesn’t help if you can’t read the data!

Activating AHCI mode after installing Windows on IDE mode

I recently just rebuilt my home PC and installed Winodws 7 on it. It was a nice fast, smooth install and generally went without a hitch.

That is, without a hitch until I discovered I'd installed Windows whilst the motherboard's SATA controller was in IDE mode and not AHCI mode. Why is this important? Well without AHCI you don't get nice things like power saving, native command queuing etc and that impacts the power consumption, speed and noise of your drives.

Of course that does rely on having a drive that supports those features, since like most newish drives mine do, I wanted to benefit.

Unfortunately just changing the setting in the BIOS causes Windows 7 and Windows Vista to both blue screen (BSOD) at boot up with the error STOP 0x0000007B INACCESSABLE_BOOT_DEVICE. That's because Windows doesn't have the drivers for AHCI since I installed it with IDE drivers.

How to get around this? Well it's surprisingly simple. After reading lots of hairy articles about hacking in drivers etc I found this knowledge base article http://support.microsoft.com/kb/922976. One simple registry setting and Windows enables it's default AHCI driver. You can then reboot, change your BIOS settings from IDE to AHCI and Windows will boot and redetect your controller and drives.

Once that's done, I rebooted to finish the install, then I installed the Intel Matrix Raid drivers so I had the actual manufacturers drivers on rather than the generic Windows ones.

All sorted now and it saved me a reinstall. I've just done a copy of 20GB of data from partition to partition on the same drive, much faster and quieter with AHCI than without. I guess that's down to NCQ being able to reorder the reads and writes into something a bit more effiicient.

Moved blogging engine

It’s been a little while since I last blogged. Well I’ve decided to change the blogging engine that I use from Graffiti to Subtext. Why? Well no real reason other than I’m not great at web design and there are more themes available for Subtext that I like. I reserve the right to move back though!

I did have some issues moving posts since Graffiti doesn’t have a BlogML export function, only import. Fortunately I was able to find a little utility on Curt’s blog at http://darkfalz.com/post/2009/04/14/Graffiti-To-BlogML-Exporter.aspx that allowed me to export by blog and comments although it did lose some of the names against the comments, sorry about that those that posted.

Installing CrashPlan on WHS part 2

In my previous post "Installing CrashPlan on WHS" I looked at installing CrashPlan on my home server and making it use UNC paths. In this post I was originally intending to look at what was needed to perform a backup between two home servers using a backup seeded from a portable hard disk.

I did manage to get all of that set up and working and was about to post when my friend noticed a problem. For some reason his backup files got erased and CrashPlan started a full backup over the net, this was going to take nearly 2 months.

After restoring the backup from portable hard disk again and starting things off it did the same thing again. So for now we've decided to uninstall CrashPlan until we have time to look into what's going on.

Installing CrashPlan on WHS

I've been looking at a backup solution for my home server for a bit. Now I'll forgive you at this point if you are thinking why do you need a backup solution for WHS when it does duplication.

Well several reasons but the main one being I want an offsite copy of most of the server contents in case of theft or fire. There are plenty of solutions out there for this but most of them require you to upload your files to the cloud and that is rather slow when trying to send a TB or so over a 800kbps uplink.

CrashPlan has the nice feature that you can back up to a friend's machine and you can seed the backup locally. So the plan is to get a new removable hard disk, backup, take to friends then update over the net.

Installing CrashPlan

I downloaded CrashPlan (www.crashplan.com) and installed it on my home server. I went to add my folders to the sources for backup and immediately hit a problem. CrashPlan doesn't let you specify a UNC path for the source (or the backup archive folder for that matter). Now I could just use D: but recommended practice for WHS is to always access data through the UNC paths so that's what I'd like to do.

The reason for this is that CrashPlan runs as SYSTEM and this account doesn't have network privileges and thus cannot access UNC paths.

To get around this I just changed the service to run as administrator and manually edited the %programfiles%/crashplan/conf/my.service.xml file to use UNC paths. The easiest way to do this is to add a dummy directory using the UI then find it in the config and change it. Use / instead of \ in the config file as it's a Java app and needs that.

I've only tested scanning to see if it can read the files and it seems to work, getting a removable drive and doing a backup is the next step.

Issues

Doing the above has 2 main issues, first you are running a service that provides a remote access interface on the internet as administrator, the second is that administrator may not have permissions to read the files being backed up.

To be honest both of these issues are present with CrashPlan anyway, it runs as SYSTEM and exposes the remote interface and SYSTEM can be denied permission on ACLs and so prevent backups from working. Fortunately WHS seems to create directories with ACLs that have both SYSTEM and Administrator in them with Full Control so it should work, I'll just have to remember not to change the ACLs on any files to remove those permissions.

Ideally the service interface should be running in a separate service with limited permissions and the backup engine service should be running as a user in the backup operators group.

I did initially try creating a new user in the backup operators group and run CrashPlan as that user, unfortunately CrashPlan doesn't use backup semantics when opening the files for backup and as such the ACL bypassing of the backup operators group doesn't kick in and it still can't access protected files.

I have suggested to the developers that the split the remote interface from the backup engine and use backup semantics when calling CreateFile() to access the files during backup. I'll let you know if I hear anything from them.

In the meantime I'm hoping the configuration I've built works ok, I'll follow this post up once I've got my external drive and have a backup done.

Calling WCF services with an invalid SSL certificate

A useful little snippet when using WCF with web services that have test SSL certificates.

When you call a service in WCF it's still using the underlying .NET classes in System.Net so it's actually here that you need to tell to ignore the invalid SSL certificate.

As it turns out this is very easy, all you need is the snippet below and it's good. Obviously you shouldn't deploy to a live environment with this code since it essentially says all certificates are valid but it's a handy trick to get a service working with any SSL certificate for testing.

ServicePointManager.ServerCertificateValidationCallback = (sender, certificate, chain, sslPolicyErrors) => { return true; };