Writing .NET Framework Applications for Windows XP Embedded


Mike Hall
Microsoft Corporation

November 19, 2003

Summary: Describes the steps needed to build and deploy a Windows XP Embedded operating system image that contains a Visual Studio .NET 2003 managed application. (6 printed pages)

This month we're taking a look at how to write Microsoft® .NET Framework applications for Microsoft Windows® XP Embedded. This might seem to be fairly straight forward, but there is a gotcha! I don't typically write the Windows XP Embedded Get Embedded articles.

Nevertheless, something happened in the speaker lounge at the Windows Embedded Essentials event in San Jose that prompted me to put pen to paper (actually fingers to keyboard). One of the speakers at the event was giving a talk on application development, hoping to discuss Microsoft Win32®, MFC (and some ATL), and managed code development, covering both Windows CE .NET and Windows XP Embedded. That was quite a tall order considering we only have one hour per breakout session at the conference.

Most of the demo code used during the session was going to be written in C# using the Windows CE .NET Emulator as the target platform. To digress from my story for a moment, interestingly, a .NET Compact Framework application also runs (with some restrictions, such as not calling out to Windows CE-only APIs) on Windows XP. How can that be? Well, hopefully you've been reading Jon Fincher's Windows XP Embedded Get Embedded articles, and by now you know that Windows XP Embedded uses the same unmodified binaries as Windows XP SP1 on the desktop. This means, of course, that you have application compatibility between Windows XP and Windows XP Embedded. Any application that runs on Windows XP SP1 desktop should run on Windows XP Embedded SP1. Since our C# .NET Compact Framework application is an MSIL (MicroSoft Intermediate Language) binary, this is not tied to a specific processor or operating system. So applications should run on Windows CE .NET and Windows XP. (How very cool is that!)

Okay, so back to San Jose... Our mystery speaker was using Microsoft® Visual Studio® .NET 2003 to write Win32, MFC, and C# "scribble" applications and show these to the audience. The plan was to show the tradeoff between writing very small/fast code (Win32, no underlying runtime) and rapid application development using C# (with a sizable framework underneath the application). The final demo for the session was going to be running a C# desktop application on a Windows XP Embedded SP1, but the application didn't run—shock, horror, probe! The application runs just fine on the desktop—we could even set breakpoints and single step the code from Visual Studio—so why wouldn't the application run on Windows XP Embedded?

Windows XP Embedded SP1 ships with the .NET Framework 1.0; the application we'd built from Visual Studio .NET 2003 was built to run against the .NET Framework 1.1. Therefore the application failed to start. So, we now have a choice: We could either write our application using the "old" version of Visual Studio—but who wants to use last year's development tools? Or, we could have Visual Studio .NET 2003 mark our application as supporting the 1.0 Framework.

Again, interestingly enough, I'd half seen a demo of this (means I wasn't paying much attention) at a conference a few weeks before. I vaguely remembered that the developer created a .config file called "MyApp.exe.config" (where MyApp is the name of the application you're building). The .config file is an XML file (no surprises there) that maps the required assemblies to the appropriate version. Unfortunately, I hadn't been paying attention at the critical part of the demo, which showed how to create the .config file, so I searched the Web looking for documentation that showed how this file was structured. I planned on using Visual Notepad .NET <g>, or a similar tool to handcraft a .config file, or even better, snatching an example file from MSDN or other location and modifying this to suit the needs of my application. As it turns out, the process is even simpler than I expected. Take a look at this MSDN document. This shows that Visual Studio .NET can create the file at application build time. You simply need to set the properties for the application, build, and you're all set.

Okay, time to test the theory. I'm going to write a fairly simple C# desktop application that consumes an XML Web service. (Weather is always a good choice, especially since it's so cold in Redmond at the moment. We even had a light dusting of snow over the weekend!) Anyhow, on to the application, and the Windows XP Embedded image.

My development PC is configured to have two hard-drive partitions, one for my development tools, and a 700 MB second partition I use to build and test Windows XP Embedded operating system images. I use a modified boot.ini to give me the operating system choice at boot time. I've been through all the usual steps to run TAP on my development PC, generate a "hardware" component based on the "selector prototype" and import this into the component database. I've also built and booted my Windows XP Embedded image—the operating system runs just fine, but doesn't include the .NET Framework or application.

Now let's write and test the application. There are a bunch of XML Web services we could use, and thankfully, there's also a collection of pointers to existing .WSDL (Web Service Description Language) files on this Web site. I chose to use a temperature service, http://www.xmethods.net/sd/2001/TemperatureService.wsdl. Okay, let's build the application.

Here's the C# code to call the XML Web service and get the current temperature for Redmond...

private void button1_Click(object sender, System.EventArgs e)
   Temp.TemperatureService Foo=new Temp.TemperatureService( );
   textBox1.Text=Foo.getTemp("98052").ToString( );

Just two lines of code needed to call the XML Web service and return the current temperature information. Here's how the finished application looks (yes, I know the UI could do with some work, but it runs just fine):

Figure 1. The managed application

Okay, so that's all the application work completed. Now you just need to configure the .config file to make your application work with Windows XP Embedded; this is all handled from Visual Studio .NET 2003.

Click Project and then Properties. Expand Common Properties and click General.

Figure 2. Visual Studio .NET project properties

You can now see a number of properties, including Supported Runtimes, which defaults to supporting the .NET Framework 1.1. Click Supported Runtimes. This will display the following dialog:

Figure 3. Setting .NET Framework options

Click the Microsoft .NET Framework 1.0 (advanced) option and click Update.

Now, let's rebuild the application. This will regenerate the .exe, and also generate the all-new .config file.

Since my development workstation and Windows XP Embedded image are on the same PC, I can test out the application without needing to build a Windows XP Embedded component. I can reboot my PC into the Windows XP Embedded image, locate the demo application on my C: drive, and run the application. Once I've tested out the application features, I can then build a component to wrap up the application.

There are a number of things I want to do with this component. First, the component needs to include the application and .config file. Second, since I might be handing this component off to other developers to use in their embedded systems (okay, okay, I know no one would use this application as their embedded shell, but bear with me; the article will be over soon enough!), I also need to set the application dependencies. In this case I will need to include the .NET Framework component as a dependency. Finally, I might (but won't for this article) want to set the properties of this component to be a custom shell. This is documented in Creating a Windows XP Embedded Shell, just in case you want to try this out for yourself.

So, let's go ahead and build the component. I'm going to set up a repository, add the two files that make up my application and its .config file, and add component dependency for the .NET Framework. Remember, if you are using a shared Microsoft® SQL Server™ to store your components, someone else might well select your all-new Seattle Weather shell component and wonder why the application doesn't work. Of course this would be because you didn't include the dependency information needed to wrap up this component. We're not going to spend time on how to build the component, as this is already covered in some depth in the Component Designer: Casting the Mold articles.

Here's how my component looks in Component Designer:

Figure 4. Component Designerthe custom component

So, all that remains is to build my custom Windows XP Embedded operating system and try out my application. Here is the end result, a C# .NET Framework 1.0 application built using Visual Studio .NET 2003 and running on Windows XP Embedded.

Figure 5. The finished application


Even though Visual Studio .NET 2003 builds applications which, by default run against the .NET Framework 1.1, it is possible to build and run applications on Windows XP Embedded that run against the .NET Framework 1.0. Of course you also have the ability to install the .NET Framework 1.1 on your Windows XP Embedded device, and run .NET Framework 1.1 compatible applications on your device.


Get Embedded

Mike Hall is a Product Manager in the Microsoft Embedded and Appliance Platform Group (EAPG). Mike has been working with Windows CE since 1996—in developer support, Embedded System Engineering, and the Embedded product group. When not at the office, Mike can be found with his family, working on Skunk projects, or riding a Honda ST1100.