Programming in C#, Java, and god knows what not

Resolving Embedded XML

Illustration

One of my fetishes is including as much resources as possible within the executable. This is fairly easy to do with Visual Studio. Just select desired file and change Build Action property to Embedded Resource.

Biggest benefit is that you can count on file always being there. There is no need to add file to installer nor to do error handling. And, even when you need to have user-modifiable files, you can always tuck away safe defaults far out of reach of an inexperienced user.

When you have XML file stored as this, loading is as easy as it gets:

var doc = new XmlDocument();
var stream = Assembly.GetExecutingAssembly().GetManifestResourceStream("project.example.xml");
doc.Load(stream);

However, when you have that same file linked to it’s DTD (Document Type Definition) things get ugly. Only thing that we get with our function is FileNotFoundException with Could not find file 'C:\somepath\example.dtd'. Things do not change even when DTD is embedded next to XML. As you can see from exception, our XmlDocument is stubbornly reading DTD from disk instead from resources.

Easiest solution is to delete referring DOCTYPE from XML document. However, that is double-edged sword since that also means that you lose quite a good helping hand in detecting early errors. I will not even go into how (properly created) DTD can be huge help with intellisense during XML editing.

Better solution would be to use XmlDocument’s existing XmlResolver property. XmlResolver is what actually handles from where each stream is read. If we inherit that class we can make critical change to read DTD from resource stream instead from file system. And it all fits in single overridden function:

public override object GetEntity(Uri absoluteUri, string role, Type ofObjectToReturn) {
    var fileName = absoluteUri.Segments[absoluteUri.Segments.Length - 1];
    var resourceName = "project." + fileName;
    var resourceStream = Assembly.GetExecutingAssembly().GetManifestResourceStream(resourceName);
    return resourceStream;
}

Code will just check which file name is required and return matching embedded resource stream. Loading XML stays almost same:

var doc = new XmlDocument();
doc.XmlResolver = MyResolver();
var stream = Assembly.GetExecutingAssembly().GetManifestResourceStream("project.example.xml");
doc.Load(stream);

P.S. Do notice that above are excerpts from little bit bigger code. Full sample is available for download.

IPv6 Multicast

Last post dealt with sending same message to multiple clients in IPv4. Since IPv4 pool is almost gone, we might as well see how to do it in IPv6.

Believe it or not, code is virtually identical:

this.Socket = new Socket(AddressFamily.InterNetworkV6, SocketType.Dgram, ProtocolType.Udp);
this.Socket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
this.Socket.Bind(new IPEndPoint(IPAddress.IPv6Any, 65535));
this.Socket.SetSocketOption(SocketOptionLevel.IPv6, SocketOptionName.AddMembership, new IPv6MulticastOption(IPAddress.Parse("ff08::1")));

Just use socket as you would normally do.

Code example is available for download.

P.S. For this example I used ff08::1 as multicast address. You might want to change this to something not as usual as this (but compliant to ffx8::/16). E.g. ff28::1:2:3:4:5 might do the trick.

Multicast

Whenever there is need to distribute same data to multiple applications over network I tend to see same thing. Everybody just makes broadcast socket. That is usually wrong way to do it.

From the very beginning of IP, there is special class called multicast addresses. Idea is simple: you “join” multicast address and whatever you send to it is received by everybody else who joined.

While this might seem a lot like broadcast, it is not the same thing. If you have network of 100 computers and only two need to talk, broadcast will send same data to 100 of them anyway. In multicast case switch can optimize this and send data only to two computers that need it.

Even in case of dumb switch which behaves with multicast in same manner as with broadcast, there is benefit. Since multicast addresses reside in completely different range, there is no fear that we will interfere with any normal socket that is listening on same port. Yes, we might stumble at another multicast group by accident but chances are pretty slim.

Creation of multicast socket is quite similar to creation of any other socket:

this.Socket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
this.Socket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
this.Socket.Bind(new IPEndPoint(IPAddress.Any, 65535));
this.Socket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.AddMembership, new MulticastOption(IPAddress.Parse("239.192.0.1"), IPAddress.Any));

As you can see, only real difference is in additional socket option that adds our socket to multicast group (do not forget do remove it on application exit).

And that is it. Everything else works as it would with “normal” socket.

Code example is available for download.

P.S. For this example I use multicast address of 239.192.0.1. You might want to change this to something not as usual as this (but still in 239.192.0.0 range).

SQL Server 2012

If you happen to be MSDN subscriber, there is new treat for you. SQL Server 2012 is available for download.

For those as cheap as me, there is SQL Server 2012 Express. For some reason it is still listed as beta, but I expect to see RTM version soon enough.

Biggest feature in my book would be LocalDB. On first glance it would be same thing as SQL Server Compact. However, if you dig a bit deeper, you will see that it has few subtle differences.

For me LocalDB is missing link that brings SQL Server data and TSQL without need for full-blown SQL Server install. Compared to Compact, it is bigger and not as easily distributed. On other hand, upgrade between LocalDB and full SQL Server should be a breeze. This one goes on my system immediately. Check more details.

Yes, there are other changes, but I will leave each one of you to pick a favorite.

Shield Button

Windows Vista introduced us to UAC. One cornerstone for developers was displaying shield next to a button that requires elevation. And it is shame that most application still don’t draw it.

Code is really simple:

var hIcon = NativeMethods.LoadImageW(IntPtr.Zero, NativeMethods.IDI_SHIELD, NativeMethods.IMAGE_ICON, 24, 24, NativeMethods.LR_DEFAULTCOLOR);
if (!hIcon.Equals(System.IntPtr.Zero)) {
    var icon = System.Drawing.Icon.FromHandle(hIcon);
    if (icon != null) {
        this.TextImageRelation = TextImageRelation.ImageBeforeText;
        this.Image = icon.ToBitmap();
    }
}

As you can see, all things are done in first line. Using Interop we request for a system’s shield icon, sized 24x24 pixels in default color. All other lines are there just to be sure that something was loaded and you are not crashing if not (e.g. if you are running XP).

Notice that one could use SystemInformation.SmallIcon to determine “proper” icon size. Unfortunately that will not have nice result for icon sizes that are not 16x16, 24x24 and 32x32. You could always do some fancy smoothing but at such small icon sizes I think it is best to go for something that is of native size.

As example I took liberty to make Button control with UAC shield. Full source is available for download.

IsRunning

In quite a lot of code I see following check for whether thread is running or not:

public bool IsRunning {
    get {
        return (this.Thread != null)
               && (this.Thread.ThreadState == ThreadState.Running);
    }
}

This code has big chance of working except in one quite often used case - if you have Sleep() inside of your code. Once that enters your main thread loop, you cannot count on your thread being in Running state all of the time. And Sleep() might not even be in your code (e.g. it might be in some external library).

Better check would be:

public bool IsRunning {
    get {
        return (this.Thread != null)
               && ((this.Thread.ThreadState == ThreadState.Running)
               || (this.Thread.ThreadState == ThreadState.WaitSleepJoin));
    }
}

P.S. If you like to mess with IsBackground thread property, also check for ThreadState.Background.

Simplest Service

Windows service is somewhat considered relic of the past. It is just not sexy enough for users. More often than not I see business applications that need to be always on sitting in tray processing their data. And there is mandatory “do not log off” paper sitting on keyboard.

And I always hear same excuses. My version of Visual Studio does not support it (from Express clan); It is very hard to debug it; It is confusing; etc. Worst thing is that Windows services made is C# is neither hard to create nor it is (too) hard to debug. You just need to do things your way.

First thing to keep in mind is that service is just simple Windows Form application. There is no reason why you need to debug it any differently. Just go into properties and set Program.cs (or App.cs, as I like to name it) to be startup object. When code starts running, just check for command line parameter (I like to use /Interactive). If that parameter is present DO NOT use ServiceBase.Run but start background thread manually.

Other annoying thing about services is installing them via installutil. You do not need to do that either. For install just execute:

ManagedInstallerClass.InstallHelper(new string[] { Assembly.GetExecutingAssembly().Location });

For uninstall it is:

ManagedInstallerClass.InstallHelper(new string[] { "/u", Assembly.GetExecutingAssembly().Location });

Of course, that can be done with /Install and /Uninstall parameters on command line.

As far as threading goes there is no escape. You must have your code in different thread in order to run a service. Windows Service Manager will call your OnStart and OnStop methods but it will not wait forever for result. My preferred method is just creating static class with methods Start, Stop and Run. Start gets called from OnStart and it starts a thread that executes private Run method (new Thread(Run)). Stop method gets called from OnStop to kill the party. Yes, there is some signaling needed for properly canceling everything but there is not much more to it.

Jut check sample application and happy background grinding.

Avoiding COMException

Illustration

Imagine following scenario. You are minding your own business and calling some nice COM function. Suddenly you got COMException going on. And it is not your fault. Code is perfect, women are nice and all you have in that line is simple check (e.g. myCom.Show(handle) == NativeMethods.S_OK). To make things worse you get also “The operation was canceled by the user. (Exception from HRESULT: 0x800704C7)” (or something similar).

Ok, you admit to your self, I did press the cancel button. But this function clearly says that it will return code different than S_OK. It never says anything about any exceptions. And can COM even raise exception in my code? Aha! Real culprit must sit in COM interop layer.

Precise dose of googling (or binging) gives source of misery. Some helpful soul in .NET design team decided that COMException will be thrown whenever HRESULT returns anything that is not success. And thus, something that ought to handled by simple conditional statement (formerly known as if) is now trashing our carefully woven code. Fortunately, smart guy from same team gave us antidote in form of PreserveSig attribute. Small dose of said attribute at function call alleviates all issues.

P.S. Normal person would just say to apply PreserveSig attribute to any function whose result code is handled within your code.

P.P.S. Even smarter person would give you the code:

[MethodImpl(MethodImplOptions.InternalCall, MethodCodeType = MethodCodeType.Runtime)]
[PreserveSig()]
uint Show([In, Optional] IntPtr hwndOwner);

Running .NET 3.5 Application on .NET 4 (And Beyond)

Illustration

Few days ago I tried to get my VHD Attach to run on Windows Thin PC.

Initial diagnosis was easy - there was no .NET Framework installed. While there is no way to install .NET Framework 3.5 on Windows Thin PC, .NET Framework 4.0 installs just fine.

Next run gave us another clue with System.IO.FileNotFoundException: Could not load file or assembly 'System.ServiceModel, Version=3.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089' or one of its dependencies. The system cannot find the file specified.

While .NET 4 is backward compatible, Microsoft made intentional decision that it will not run applications made with earlier runtimes. This is not a big issue in Windows 7. There you have 2.0, 3.5 and 4.0 installed side-by-side and each application can pick whatever it needs. However, in Windows Thin PC there is only 2.0 and 4.0. Notice that one version is missing and it was the one I needed.

To make long story short, there is solution that does not involve recompiling. Just add Application Configuration Files (App.config) and put following text into it:

<?xml version="1.0"?>
<configuration>
    <startup>
        <supportedRuntime version="v4.0" />
        <supportedRuntime version="v2.0.50727" />
    </startup>
</configuration>

This will tell application to run on .NET 4 if possible and to fallback to 3.5, 3.0 and 2.0 as a backup solution. This might not be most beautiful solution but it is a solution that works.

P.S. Yes, supportedRuntime cannot distinguish between .NET 2.0, 3.0 and 3.5.

Renaming a File

Renaming a file is quite simple job in C#. You can just call File.Move(oldPath, newPath) and it works. That is until it doesn’t. Problem with this function is that it cannot rename file that differs only in case. E.g. test cannot be renamed to Test. And believe it or not, people sometime want to change case of their file.

Solution that first comes to mind is renaming file to something temporary and then back. E.g. test will be renamed to test-temp and then back to Test. While this solution works it makes exception handling annoying. Just what are you supposed to do if there is exception after you already created test-temp?

Fortunatelly Windows API is not so restrictive. Things can be as simple as calling MoveFile function. Or in our case MoveFileEx with parameters that ensure that we can move between volumes (MOVEFILE_COPY_ALLOWED) and that function returns only after work is done (MOVEFILE_WRITE_THROUGH). Quite straightforward code indeed:

public static void MovePath(string currentPath, string newPath) {
    if (currentPath.StartsWith(@"\\?\", StringComparison.Ordinal) == false) { currentPath = @"\\?\" + currentPath; }
    if (newPath.StartsWith(@"\\?\", StringComparison.Ordinal) == false) { newPath = @"\\?\" + newPath; }
    if (NativeMethods.MoveFileExW(currentPath, newPath, NativeMethods.MOVEFILE_COPY_ALLOWED | NativeMethods.MOVEFILE_WRITE_THROUGH) ==  false) {
        var ex = new Win32Exception();
        throw new IOException(ex.Message, ex);
    }
}

internal static class NativeMethods {
    public const uint MOVEFILE_COPY_ALLOWED = 0x02;
    public const uint MOVEFILE_WRITE_THROUGH = 0x08;


    [DllImportAttribute("kernel32.dll", EntryPoint = "MoveFileExW", SetLastError=true)]
    [return: MarshalAsAttribute(UnmanagedType.Bool)]
    public static extern bool MoveFileExW([InAttribute()] [MarshalAsAttribute(UnmanagedType.LPWStr)] string lpExistingFileName, [InAttribute()] [MarshalAsAttribute(UnmanagedType.LPWStr)] string lpNewFileName, uint dwFlags);
}