Deploying Mobile apps the easy way using Inno Setup

Deploying a mobile application is not as simple as just clicking next, next, finish in a msi wizard. As a result a lot of articles have been written on it, searching the web you will find many. One of the most detailed I found was this one on DevExpress. It works well but requires the .net framework 2.0 to be present on the PC from which to install the mobile app. In my case this was a no-go, I’m in a situation where I cannot count on any version of the framework being present and even the usage of msi files is discouraged. Nevertheless it should be possible to install a mobile CF 2 app according to the Mobile logo requirements, that is using ActiveSync with at the utmost two or three OK clicks from the user. Which was in the end, after a lot of analyzing and searching not only possible but even simpler and clearer than the msi way.

Deploying a mobile app boils down to these steps

  • Build a CAB file containing the app and it’s resources. This is a standard project in VS 2005
  • Write an ini file describing the setup
  • Package cab and ini in a redistributable
  • Unpack the files on the client PC to which the device is connected
  • Fire up the CEappmanager, this is the add/remove programs part of ActiveSync
  • Feed the CE app manger the ini file in the command line

To do this in an msi requires adding an afterinstall action to the setup. All this action does is fire up the CEappmanager with the ini file in the command line. Adding a custom action to an msi either requires .net 2.0 which supports the Microsoft installer or doing some low-level editing in a finished msi and adding a custom dll to do the action. The first one is easy following the article (but requires the .net 2.0), the second one a tedious nightmare.

In comes inno setup. Inno setup is freeware and follows a completely different approach to creating a setup. It does so by writing a script. In the script is a list of files to pack, some events to hook into and full custom scripting capability. The nice thing about these scripts is they are in Delphi syntax. Inno setup itself is also written in Delphi, source code is available. Noteworthy is that Delphi versions 2 to 5 are mentioned. I’m not the only one who thinks the real Delphi stopped with that version.

Inno setup produces one executable which contains the compressed files to redistribute and runs the script. Step by step I’ll walk you through a script to deploy a CF application, including the Compact framework itself. Using visual studio I’ve created a cab file which includes the mobile application and will setup some shortcuts on the device.

The first [Setup] part of the script describes the setup with the usual info. The app I’m describing here is a PDA extension to TimeWriter, which is a killer app to keep track of your (billable) time. There is a freeware version available, do give it a try.

AppName=TimeWriter PDA
AppVerName=TimeWriter 1.5

<PNOTICE {pf} constant. It will expand to program files folder on the target machine.

The next section contains the list of files to pack.

Source: “netcf.ini”; DestDir: “{app}”;
Source: “wce400\armv4\”; DestDir: “{app}\wce400\armv4″;
Source: “wce500\armv4i\”; DestDir: “{app}\wce500\armv4i”;
Source: “wce500\armv4i\”; DestDir: “{app}\wce500\armv4i”;

Source: “twPDA.ini”; DestDir: “{app}”;
Source: “”; DestDir: “{app}”;

The first set is the Compact Framework 2. The three cab files are all targeting the arm processor. Although the compact framework does target other processors, for pocket pc 2003 and later an arm is required. So I can skip the other cab’s. The three different cab’s target the different versions of pocket pc and windows mobile running on Windows CE 4 and 5. The netcf.ini  describes them. The second set of files is the TimeWriter app with it’s ini file. Inno setup will place all these files in the the folder on the client PC.

Now everything is ready for the CEappmanager to do the real install. The next section in the script fires any application you need after unpacking the files. In my case I want to fire the CEappmanager twice, first to install the Compact Framework, next to install my app.

FileName: {code:GetCEappManager}; Parameters: {code:GetIniFile|\netcf.ini}
FileName: {code:GetCEappManager}; Parameters: {code:GetIniFile|\twpda.ini}

The CEappmanager requires one parameter with the full path of the ini file to process. I don’t know where the CEappmager is located and I don’t know either where the user has installed the files. In comes the [Code] section, in here you can write full Delphi code to do the work. This code can use functions the inno library but also almost any other Delphi, Win32 or COM (!) function.

function GetCEappManager(Param : string) : string;
var Path: String;
  Path:= ”;
  RegQueryStringValue(HKEY_LOCAL_MACHINE, ‘SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\CEAPPMGR.EXE’,”, Path)
  result:= Path

function GetIniFile(Param : string) : string;
  result:= ExpandConstant(‘”{app}’) + Param + ‘”‘;

The GetCEappManager reads the location from the registry. The getIni file expands the constant {app} to get the directory used for installation and appends the name of the ini file passed in the parameter. Note the quotes, without them a parameter like C:\program files\TwPda\twpda.ini would be interpreted as two command line parameters.

CEappmanager processes the ini file, which looks like this.

Version = 1.0
Component = NETCF

Description = .NET Compact Framework v2.0

It contains a list of cab files. These should located relative to the directory of the ini file. The list in the ini file locates them in the subfolders and should not contain any spaces. The good thing about the CEappmanager is that it knows which cabinet it needs for the specific device. It will only install the one matching the target. To keep a tab on what the appmanager is doing you can add to the registry entry HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows CE Services\AppMgr a DWORD named ReportErrors with the value 1. Some sources state that passing /t in the commandline has the same effect. I cannot confirm that. Now CEappmanager will pop up dialogs telling which files it has found and also info like this:

It has found three cab files for CF 2.0. The 0 in front of the third indicates it will install that one. That’s the one for my device.


Instead of firing the CEappmanager twice you can pass both ini files in one go. This will change the [Run] section to

FileName: {code:GetCEappManager}; Parameters: {code:GetIniFile|\netcf.ini} {code:GetIniFile|\twpda.ini}

This undocumented feature probably explains why passing /T as a debugging parameter does not work. /t is seen as a file.


Having run CEappmanager my app and the needed CF 2 is up and running.

This whole setup script depends totally on the CEappmanager. In case ActiveSync is not installed the appmanger will not be there either and the whole setup is useless as there is no connection to the device. To cancel the script in such a scenario there’s the InitializeSetup event. Also part of the [Code] section. It’s a boolean function telling to proceed or cancel.

function InitializeSetup() : boolean;
   var Path: String;
Path:= ”;
RegQueryStringValue(HKEY_LOCAL_MACHINE, ‘SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\CEAPPMGR.EXE’,”, Path)
if Path = ” then
   MsgBox(‘Activesync not found !’, mbError, MB_OK);
   result:= false;
   result:= true;

You cannot use the other script functions in the section, so the code to dive into the registry has to be duplicated. But the way to fire up a dialog is cool.

There are so many more things you can do with Inno Setup. The tool is very intuitive to use and includes even integrated debugging.

Delphi style, with the exchanged F5 and F9. But instead of wasting more words on it I can only suggest to try it yourself. To get my mobile setup to work took far less and very clear code compared to the msi way. From now on it is going to be part of my toolbox.

This entry was posted in Mobile. Bookmark the permalink. Follow any comments here with the RSS feed for this post.
  • pvanooijen

    My client didn’t want the setup to be dependent on the .NET framework being installed. Yes you can do non .net with VS. Why bother, Inno does it’s job very well.

  • Fella

    Whats the problem with Visual Studio? You can create dll or exe without .NET

    My solution is simple
    1. Application (startce.exe) which finds and runs ceappmgr with setup.ini
    2. Setup project with CABs, setup.ini and startce.exe
    3. In custom action->commit add action to start startce.exe.

    You’ll spend your time only for creating startce.exe, but its few line of code in any language

  • Lexpa Team


    That might be interesting for everybody who would like to use Inno Setup and works in Visual Studio 2005.

    We are working currently on Lexpa – Inno Setup integration for Visual Studio. And maybe somebody would like to join out Beta Tester Community. If so please, check out this site [] for instructions.

    The Lexpa Team

  • pvanooijen

    @Raja, creating a cab is more than just the ini’s. Perhaps you could use VS just for creating the cab. Make the project deploy you NSBasic (on which I’m blank) stuff ?

  • Raja

    Hello i am using NSBasic for creating the mobile device application. how to create the “.cab” files. can you please give me the sample ini files.



  • Mark

    Really good info here! thanks alot!