System Center Mobile Device Manager 2008 – Install Guide (No Gateway) – Part 1

I mentioned it only briefly in my last post, but Microsoft has a product in the System Center family that let you take control of your Windows Mobile devices, and make the mobile devices part of the domain just like any other computer in your LAN (and WAN). And obviously once they are part of your network you can distribute software, configure settings on the device, etc. This product has the tongue-twisting name of System Center Mobile Device Manager 2008, or SCMDM2008 for short. (Some refer to it as MDM, but since this acronym can also mean Mobile Device Management in general, it’s better to use it only in a given context where it’s implied there’s an SC in front. Apologies for being a nit-picker 🙂 )

I’m not going into all the features and sales “fluff” here however, and intend to provide a practical and technical hands-on approach instead. If you have no knowledge of what it’s all about I advice you have a few looks on the product page (and then return here):

If you look into the TechNet Library you’ll find lots of documentation on the product, how to plan for implementation, architecture, deploying, reference materials, etc. And the documentation is good, but there’s a lot of it, and if you just want to test drive it for yourself you might not be interested in reading 200 pages of architectural considerations. Participating in the TechNet forums I see a lot of people are having problems evaluating this product since it is a pretty complex solution, with a lot of steps that need to be performed in specific orders. With this in mind I decided to write some how-to’s hopefully helping someone along the way. I don’t claim to have all the answers myself, and I have also struggled with some issues, but I’ll try to produce a guide that will let you set it up in your own lab and actually get it to work 🙂

I’ll probably divide this into several guides, detailing different scenarios, and maybe going in depth regarding some aspects of the solution. In this first scenario I’ll try a very basic scenario:
– All devices connect through LAN. No GPRS, or other external access.
– No gateway or VPN tunnel. All devices connect directly to the Enrollment and Device Management server.
– “Everything” installed on one server. This includes Enrollment Server, Device Management Server, SQL Server and WSUS Server. The exception is the Domain Controller which is a separate server (also hosting a Certificate Authority).
I call this the “SCMDM – No Gateway”-scenario.

One caveat with this scenario is that you will not be able to use the “Wipe now”-feature. Your devices will be wiped on the next scheduled connection to the server. This is because this feature is dependent on the Gateway server. (I will not go into further details, the technical reasoning behind this is explained in the TechNet Library.)

I know there are a lot of different network setups out there, with different firewalls, routers, etc. And this makes writing generic guides difficult. The scenario I walk through here should however be fully reproducible in your lab since it is a very stripped down setup. No firewalls, no routers, no Internet – just two virtual servers and a few innocent mobile devices.

This would be how our tiny little infrastructure looks like 🙂


Some technical details regarding how I configure these “boxes”:
– Everything is virtualized on a single physical computer with one physical NIC, running Windows Server 2008 with Hyper-V. As far as I know it’s not supported in a production environment to do this, but it’s not a problem for lab work. System Center will install with less than the recommended/required 4GB, but obviously the more the better. I’m using a quad-core Xeon with 8GB RAM as the host machine, but I’ve done some testing previously on a Core 2 with 4GB which also works albeit somewhat more “sluggish”.
– The Domain Controller is Windows Server 2003 R2 32-bit Enterprise Edition with 512MB RAM. 32-bit is required to use the Group Policy tools, so unless you have any other compelling reasons to go 64-bit stick with 32-bit for this scenario.
– SCMDM Server is Windows Server 2003 x64 Enterprise Edition with 2GB RAM. 64-bit is a requirement, which means Hyper-V is the only option if you’re using virtualization from Microsoft.

The domain controller has to be Enterprise Edition because of the Enterprise CA we are running. You can install an Enterprise CA on Standard Edition as well, but you will not be able to define your own certificate templates, which is something we need for SCMDM. (The certificates for the mobile devices are based on a custom template generated by the SCMDM install process.)

I’m using the English version of Windows Server 2003, and SCMDM. You can use other languages, but keep in mind that you can’t mix language components. So if you have another language of Windows Server you need to check you are installing the same version of ASP.NET, etc. Since English is the default in a Microsoft world I stick with that all the way through.

The servers have the following network setup:
Domain Name:
Domain Controller name: md-dc-ca
Domain Controller address:
SCMDM Server name: md-scmdm
SCMDM address:
Since it’s all on a LAN without routing you don’t need a default gateway defined.

Getting your Domain Controller ready
– Make sure your domain is at “2003 Functional Level”. (If you installed a new domain it will be at “2000 Functional Level” by default.) Update: Make sure it’s 2003 Native level, not 2003 interim (which is used for support Windows NT 4 servers). Also make sure your Forest Functional level also matches and is running 2000 or 2003 functional level. (If you installed a domain from scratch like I have done in my lab you don’t need to touch the Forest Functional Level.)
– Install IIS.
– Install Certificate Services choosing “Enterprise Root CA” as the type. If you don’t want to get some extra configuration hassle afterwards make sure the previous step is performed before this step – the order of these two steps is not random.
– You’ll need the name of your CA later, so make a note of it – I use “MobilityDojo Root CA”.

Getting your MDM server ready
– Install IIS.
– At this time you should make sure that IIS/.NET is running in 64-bit.
Run the following command (from command prompt):
cscript %SYSTEMDRIVE%\inetpub\adminscripts\adsutil.vbs SET W3SVC/AppPools/Enable32bitAppOnWin64 0
Change to C:\WINDOWS\Microsoft.NET\Framework64\v2.0.50727
Run: aspnet_regiis –i
Run iisreset

– Install SQL Server 2005. Not SQL Server 2008, and not SQL Server Express. Standard Edition should be ok, as well as Enterprise and Developer. Default settings should be good, if you don’t have any preferences stating otherwise.
A few extra steps must be performed on your SQL Server install to enable use for SCMDM.
– Set the “SQL Server Agent” service to “Automatic”.
– Set the “SQL Server Browser” to “Automatic”.
– Enable Remote Connections for TCP/IP. You can do this via “SQL Server Configuration Manager” or “SQL Server Surface Area Configuration”. MS has a good explanation here:

Then there’s some small applications you need in addition (remember to get the 64-bit versions where applicable):
– Install PowerShell 1.0:…/powershell/download.mspx
– Install MMC 3.0 (if necessary – if you’re running 2003 R2 it’s already installed):
– Install Report Viewer 2005 SP1:
– Install MBCA (Microsoft Baseline Configuration Analyzer):

We then proceed to installing WSUS 3.0 SP1. There is an important step in the install wizard – you should create a separate web site for WSUS. If you don’t there’s a chance it will interfere with the enrollment web site we’re creating later. Accept the default port the wizard suggests for the new web site.

All should be good with regards to the software you need before installing SCMDM, but you should run SCMDM BPA, (Best Practice Analyzer), to make sure everything is in order before you start installing. Actually you should go ahead and download all the Resource Kit Tools (only install BPA for the moment):
The type of scan you’ll want is the “Pre-Deployment Scan”. You might get an error stating “Scan failed”. This means you have to change a policy in Powershell. Run the following cmdlet in the Powershell console: “Set-ExecutionPolicy RemoteSigned”.

Make sure you get green lights on the Enrollment and Device Management role. (If you get warnings about CPU and/or RAM ignore this.) In this scenario you might get an error on the SQL role as we are installing SQL on the same box as SCMDM. Also make BPA check that AD and the CA is good to go.

I would have loved to have a screen shot with no warnings, but seems there’s a bug in the RAM detection scheme. I tried upgrading to both 4 and 5 GB temporarily and it still complained I didn’t have 4 GB…

As for SCMDM itself, it’s available on TechNet & MSDN, and as an evaluation version here:

Now that everything is in place we can proceed to the next step – actually installing SCMDM 🙂
This is covered in Part 2:
Part 3:

Provisioning Owner Info

Unless you’ve only used the newer HTC models with TouchFLO that monopolizes almost your entire today screen you’ve probably noticed the field that provides information about the owner of the device. While entering this info, possibly for time number x after another hard reset of your device, you might have been thinking “it shouldn’t be necessary typing this manually every time”. And in a corporate environment you might want to have a company standard for what goes into the fields so users don’t type in “Owner: Batman, Address: Gotham City”.


And, yes, there is a way to do this in a more automated fashion. I’ll present one option here.

Your first step would probably be guessing that this is stored in the registry – and you’d be right. You’ll find some keys in HKCU\ControlPanel\Owner. (You’ll also find HKLM\ControlPanel\Owner – ignore this key.) Unfortunately it’s not as easy as setting the appropriate key “Name”, etc. You see that binary key called ”Owner” – that’s where you want to insert all the info, and the other keys are derived from this. (“Owner Notes” is the “Notes” tab in the configuration on the device.)


If you double click “Owner” you’ll see a pattern:

The solution I will show you here is creating a small C# app that will generate an xml-file that can be provisioned to the device. You could add a step that generates a cab-file for you as well, but for automatic deployment you’d also need to sign it. (A step that could also be automated.) What makes more sense for your scenario depends on whether you have a device management solution, and what options this system allows for provisioning. Maybe you just want to generate cabs and distribute to your users for them to run. With a decent device management solution you should be able to get the system to run the application when the device connects for the first time. Without a DM solution it becomes more of an academic exercise.

If you’re not comfortable with C# it can be done with VBScript as well although I find that to be more of a hassle. (You have to create your own Base64-encoding since it’s not included in VBScript.)

The application takes the username of the device owner as a parameter and fetches the rest of the info from Active Directory. So if you don’t have any info in AD, you’ll have to modify the solution to acquire the info from another source.

So first things first – let’s grab that info from AD:

string outputFile = “ownerinfo.xml”; Stream xmlFile = new FileStream(outputFile, FileMode.OpenOrCreate); StreamWriter output = new StreamWriter(xmlFile);     String ldapPath = “LDAP://dc/CN=Users;DC=Contoso;DC=com”; DirectoryEntry ldapDir = new DirectoryEntry(ldapPath); ldapDir.AuthenticationType = AuthenticationTypes.Secure; DirectorySearcher ldapSearch = new DirectorySearcher(ldapDir); ldapSearch.Filter = “(&(objectCategory=Person)(objectClass=user)(sAMAccountName=” + sAMAccount + “))”; ldapSearch.SearchScope = SearchScope.Subtree; SearchResult ldapResult = ldapSearch.FindOne();

Yes, call me lazy for not implementing a better solution than hard coding the LDAP path 🙂 Create variables for the fields in the User object we care about (obviously it’s recommended you use try-catch for those user objects that turn out to have something missing):

String ownerName = “”; String ownerCompany = “”; String ownerAddress = “”; String ownerPhone = “”; String ownerMail = “”; DirectoryEntry ldapUser = ldapResult.GetDirectoryEntry(); ownerName = ldapUser.Properties[“name”].Value.ToString(); ownerCompany = ldapUser.Properties[“company”].Value.ToString(); ownerAddress = ldapUser.Properties[“streetAddress”].Value.ToString(); ownerPhone = ldapUser.Properties[“mobile”].Value.ToString(); ownerMail = ldapUser.Properties[“mail”].Value.ToString();

The properties are LDAP properties, and you can find the ones you’re interested in using either ADSIEdit or a suitable LDAP browser.

And this is the part you’ll want to take note of if you want to implement this is VBScript or any other choice of script/language. How to prepare the variables, and create an xml-file containing provisioning xml.

// We need to zero-pad the variable. The numbers are taken from a registry that have been populated // by typing in owner info manually. char pad = (char)0; ownerName = ownerName.PadRight(36,pad); ownerCompany = ownerCompany.PadRight(36,pad); ownerAddress = ownerAddress.PadRight(186,pad); ownerPhone = ownerPhone.PadRight(25,pad); ownerMail = ownerMail.PadRight(34,pad); String ownerTotal = ownerName + ownerCompany + ownerAddress + ownerPhone + ownerMail; //We want Unicode and Base64 UnicodeEncoding ownerByte = new UnicodeEncoding(); Byte[] workArray = ownerByte.GetBytes(ownerTotal); String ownerInfo = Convert.ToBase64String(workArray); // Write to file output.WriteLine(“<wap-provisioningdoc>”); output.WriteLine(“<characteristic type=\”Registry\”>”); output.WriteLine(“<characteristic type=\”HKCU\\ControlPanel\\Owner\”>”); output.WriteLine(“<parm name=\”Owner\” value=\”” + ownerInfo + “\” datatype=\”binary\”/>”); output.WriteLine(“</characteristic>”); output.WriteLine(“</characteristic>”); output.WriteLine(“</wap-provisioningdoc>”); output.Close();

The sample code here isn’t performing any error-checking – so if it isn’t working you don’t get any wiser before you include some sanity checks.

Putting it together to a working sample I fire up the command line, run “BuildOwnerXML andreas” and get a file called “OwnerInfo.xml”. For testing purposes I generate a cab file; “makecab _setup.xml”. (Renaming the xml-file so it follows the documented format for makecab. Makecab is included if you have Visual Studio installed, but is also available as a separate free download from MS.)

Copy cab to device, run cab, accept warning (it’s not signed), and you’re done!

Customizing the “Welcome Center” in Windows Mobile 6.1

A new feature that came along in Windows Mobile 6.1 is the “Welcome Center” or “Getting Started” as the icon listed under “Programs” is called. This is a feature that is designed to make it easier for new users to get acquainted with their Windows Mobile devices, and provide a starting point for them.

The default offering looks like this running on a Pocket PC:

If you click an item you are either redirected to a more specific dialog box, or shown a richer description/explanation.

While experienced users might not find this very exciting, it does offer a new possibility since you can modify it for your own needs 🙂 This means you can tailor it for the users in your company if you’re deploying devices in an enterprise scenario, or you can tweak it to your personal liking as a power user.

So how can we customize this new piece of software? It’s basically a “browser light” and the contents make up your own mini web site. The configuration is stored in the registry, and the contents are file-based.

On to the registry first; if you load up your favorite tool for registry editing your device you can navigate to HKLM\System\WelcomeCenter\xxxx where xxxx will be specific to the language of your device. 0409 = English and 0414 = Norwegian. On Pocket PC/Professional you’ll only have to worry about one language so it shouldn’t be a problem locating the proper key. On Smartphone/Standard devices however you may have multiple languages available on your device. (You can have different content for different languages if you like.)

The subkeys make up the items you see in the screenshot above. You can name the subkeys whatever you like, as long as you are able to figure it out when you come back later for maintenance 🙂 (If you want it in alphabetical or numeric order for instance.) It’s the values underneath the subkey that matters. You need to specify the following values:
order [Dword] – A numeric value that is used to determine the order items are listed.
image [String] – Path to an image file that will serve as icon.
name [String] – The name as it appears in the list.
url [String] – Path to the hyperlink.

As an example “Make a call” (see screenshot) have the following values:
order – 16
image – “\Windows\phone_wc.gif”
name – “Make a call”
url – “\Windows\wc_makecall.wcml”

The default items use \Windows as the path for the files, but you can put it in whatever folder you like. Seeing that it’s links you might be able to put them on a web server, but I haven’t tested/tried that myself. (I can see some potential drawbacks to that approach however…)

The file you use for “image” could be a jpg/gif/png/bmp. You might want to use transparency to make it blend with the background.

You might notice that the value of order for the predefined items seem to be “randomized”. I don’t know how they ended up using those specific values, but if you plan on using any of those items you should either alter their order value, or adapt your numbering scheme accordingly.

So, how about a quick example of a custom item:
Create a new key (under HKLM\System\WelcomeCenter\0409) called “Information”
Create the following registry values;
order = 1
image = “\Windows\question.bmp”
name = “Information”
url = “\MyWC\wc_info.wcml”

This could look like the following (the preloaded items have been deleted):

I said earlier that the contents are file-based, so even though this produces something to look at, it will present an error if you try to choose “View”, or click it, since I haven’t created the file referenced in the url value yet. The default content files have the extension .wcml – now I’m not a web designer so I wouldn’t know exactly why Microsoft are using wcml; to me it just looks like plain html 🙂 Of course there’s nothing forcing you to use wcml-files either, the url value could point directly to an exe-file instead.

So fire up Notepad, or your preferred HTML editor. (Off-topic: I’m testing Microsoft Expression Web 2 for the time being.) Create a file called wc_info.wcml, and this would be the markup we need for our little example:

<!DOCTYPE html PUBLIC-//W3C//DTD XHTML 1.0 Transitional//EN” “>
<html lang=”en> <head>
<meta http-equiv=”Content-Typecontent=”text/html; charset=UTF-8/>
<style type=”text/css> .style1 {font-size: 145%;} </style> </head>
<body> <img src=”\MyWC\question.bmp” \img>
<span style=”color;font-size:145%”>&nbsp;</span>
<span lang=”en-us><span class=”style1>Information</span>
</span><br> <span lang=”en-us>Sample info:<br /> This is a text.<br /> <a href=”http://localhost>This is a hyperlink</a>

Create a folder called “MyWc” on the root of your device, and copy the file to the folder. Test that it works starting up the Welcome Center and clicking “View”. (If you edit the registry you should always stop the Welcome Center before performing and registry editing, or you could make the application crash.)

So basically, there you have it, how to create your own Welcome Center. You’d probably want to come up with more elaborate setups than this hopefully 🙂

When it comes to distributing this Welcome Center it’s obvious that registry editing and copying files via ActiveSync for every device wouldn’t cut it – you will need something else. You could either create a cab file containing both files and registry settings, or you could use your favorite Device Management system to transfer files and edit the registry directly. My preferred method is a cab-file preloaded on the device containing a minimum configuration, and making it dynamic through updating via a DM solution. (You could distribute specific settings based on membership in Active Directory groups for instance.)