Linker (light)

The Windows Installer XML linker is exposed by light.exe. Light is responsible for processing one or more .wixobj files, retrieving metadata from various external files and creating a Windows Installer database (MSI or MSM). When necessary, light will also create cabinets and embed streams in the created Windows Installer database.

The linker begins by searching the set of object files provided on the command line to find the entry section. If more than one entry section is found, light fails with an error. This failure is necessary because the entry section defines what type of Windows Installer database is being created, a MSI or MSM. It is not possible to create two databases from a single link operation.

While the linker was determining the entry section, the symbols defined in each object file are stored in a symbol table. After the entry section is found, the linker attempts to resolve all of the references in the section by finding symbols in the symbol table. When a symbol is found in a different section, the linker recursively attempts to resolve references in the new section. This process of gathering the sections necessary to resolve all of the references continues until all references are satisfied. If a symbol cannot be found in any of the provided object files, the linker aborts processing with an error indicating the undefined symbol.

After all of the sections have been found, complex and reverse references are processed. This processing is where Components and Merge Modules are hooked to their parent Features or, in the case of Merge Modules, Components are added to the ModuleComponents table. The reverse reference processing adds the appropriate Feature identifier to the necessary fields for elements like, Shortcut, Class, and TypeLib.

Once all of the references are resolved, the linker processes all of the rows retrieving the language, version, and hash for referenced files, calculating the media layout, and including the necessary standard actions to ensure a successful installation sequence. This part of the processing typically ends up generating additional rows that get added associated with the entry section to ensure they are included in the final Windows Installer database.

Finally, light works through the mechanics of generating IDT files and importing them into the Windows Installer database. After the database is fully created, the final post processing is done to merge in any Merge Modules and create a cabinet if necessary. The result is a fully functional Windows Installer database.

Usage Information

light.exe [-?] [-b basePath] [-nologo] [-out outputFile] objectFile [objectFile ...] [@responseFile]

Light supports the following command line parameters:

Switch

Meaning

-ai

Allow identical rows; identical rows will be treated as a warning.

-au

Allow unresolved references; this will cause invalid output to be created.

-b <path>

Specify a base path to locate all files; the default value is the current working directory.

-bcgg

Use backwards compatible guid generation algorithm (rarely needed).

-bf

Bind files into a wixout; this switch is only valid when also providing the -xo option.

-binder <classname>

Specify a specific custom binder to use provided by an extension.

-cc

Specify a path to cache built cabinet files; the path will not be deleted after linking.

-ct <N>

Specify the number of threads to use when creating cabinets; the default is the %NUMBER_OF_PROCESSORS% environment variable.

-cultures:<cultures>

Specifies a semicolon or comma delimited list of localized string cultures to load from .wxl files and libraries. Precedence of cultures is from left to right. For more information see Specifying cultures to build.

-cub

Provide a .cub file containing additional internal consistency evaluators (ICEs) to run.

-d<name>=<value>

Define a WiX variable.

-dcl:level

Set the default cabinet compression level. Possible values are low, medium, high, none, and mszip (default).

-dut

Drop unreal tables from the output image.

-eav

Exact assembly versions. If this option is not specified, the assembly version is padded with zeros in certain cases to work around a bug that exists in the initial release of the .NET Framework 1.1. This bug was subsequently fixed in the .NET Framework 1.1 SP1. Use this option if you require non-padded assembly versions in the MsiAssemblyName table (or in relevant bind variables), and do not mind if your MSI is incompatible with the initial release of the .NET Framework 1.1. For more information, see this blog post.

Note that when using this option, your setup will still be compatible with the .NET Framework 1.0 RTM, .NET Framework 1.1 SP1, .NET Framework 2.0, and later versions of the .NET Framework.

This property is available starting with WiX v3.5.

-ext

Specify an extension assembly.

-fv

Add a FileVersion attribute to each assembly in the MsiAssemblyName table (rarely needed).

-ice: <ICE>

Specify a specific internal consistency evaluator (ICE) to run.

-loc <loc.wxl>

Provide a .wxl file to read localization strings from.

-nologo

Skip printing Light logo information.

-notidy

Prevent Light from deleting temporary files after linking is complete (useful for debugging).

-O1

Optimize smart cabbing for smallest cabinets (deprecated).

-O2

Optimize smart cabbing for faster install time (deprecated).

-out

Specify an output file; by default, Light will write to the current working directory.

-pdbout <output.wixpdb>

Save the wixpdb to a specific file. The default is the same name as the output with the wixpdb extension.

-pedantic

Display pedantic output messages.

-reusecab

Reuse cabinets from the cabinet cache instead of rebuilding cabinets.

-sa

Suppress assemblies: do not get assembly name information for assemblies.

-sacl

Suppress resetting ACLs (useful when laying out an image to a network share).

-sadmin

Suppress adding default Admin sequence actions.

-sadv

Suppress adding default Advt sequence actions.

-sloc

Suppress localization.

-sice:<ICE>

Suppress running internal consistency evaluators (ICEs) with specific IDs.

-sma

Suppress processing the data in the MsiAssembly table.

-sf

Suppress files: do not get any file information; this switch is equivalent to the combination of the -sa and -sh switches.

-sh

Suppress file information: do not get hash, version, language and other file properties.

-sl

Suppress layout creation.

-spdb

Suppress outputting the wixpdb.

-ss

Suppress schema validation for documents; this switch provides a performance boost during linking.

-sts

Suppress tagging sectionId attribute on rows.

-sui

Suppress adding default UI sequence actions.

-sv

Suppress intermediate file version mismatch checking.

-sval

Suppress MSI/MSM validation.

-sw<N>

Suppress warnings with specific message IDs.

-swall

Suppress all warnings (deprecated).

-usf <output.xml>

Specify an unreferenced symbols file.

-v

Generate verbose output.

-wx <N>

Treat warnings as errors.

-wxall

Treat all warnings as errors (deprecated).

-xo

Generate XML output instead of an MSI.

-?

Display Light help information.

Binder Variables

Standard Binder Variables

Some properties are not available until the linker is about to generate, or bind, the final output. These variables are called binder variables and supported binder variables are listed below.

All Versioned Files

The following standard binder variables are available for all versioned binaries.

Variable name

Example usage

Example value

bind.fileLanguage.FileID

!(bind.fileLanguage.MyFile)

1033

bind.fileVersion.FileID

!(bind.fileVersion.MyFile)

1.0.0.0

Assemblies

The following standard binder variables are available for all managed and native assemblies (except where noted), where the File/@Assembly attribute is set to ".net" or "win32".

Variable name

Example usage

Example value

bind.assemblyCulture.FileID
(managed only)

!(bind.assemblyCulture.MyAssembly)

neutral

bind.assemblyFileVersion.FileID

!(bind.assemblyFileVersion.MyAssembly)

1.0.0.0

bind.assemblyFullName.FileID
(managed only)

!(bind.assemblyFullName.MyAssembly)

MyAssembly, version=1.0.0.0, culture=neutral, publicKeyToken=0123456789ABCDEF, processorArchitecture=MSIL

Note: The publicKeyToken value is uppercased.

bind.assemblyFullNamePreservedCase.FileID
(managed only)

!(bind.assemblyFullNamePreservedCase.MyAssembly)

MyAssembly, version=1.0.0.0, culture=neutral, publicKeyToken=0123456789abcdef, processorArchitecture=MSIL

Note: The publicKeyToken value's casing is preserved.

bind.assemblyName.FileID

!(bind.assemblyName.MyAssembly)

MyAssembly

bind.assemblyProcessorArchitecture.FileID

!(bind.assemblyProcessorArchitecture.MyAssembly)

MSIL

bind.assemblyPublicKeyToken.FileID

!(bind.assemblyPublicKeyToken.MyAssembly)

0123456789abcdef

Note: The value is uppercased for managed assemblies.

bind.assemblyPublicKeyTokenPreservedCase.FileID
(managed only)

!(bind.assemblyPublicKeyTokenPreservedCase.MyAssembly)

0123456789abcdef

Note: The value's casing is preserved.

bind.assemblyType.FileID
(native only)

!(bind.assemblyType.MyAssembly)

win32

bind.assemblyVersion.FileID

!(bind.assemblyVersion.MyAssembly)

1.0.0.0

Properties

You can also reference property values from the Property table at bind time; however, you cannot reference properties as binder variables within other properties, including the attributes on the Product element - many of which are compiled into the Property table. You can reference other binder variables like file information above in properties, or even localization and custom binder variables documented below.

Specializations for each field of the ProductVersion property are also provided as shown below. If you have defined properties like ProductVersion.Major in your package authoring they will not be overwritten, but will be used instead of the automatic binder variables with the same name.

Variable name

Example usage

Example value

bind.property.Property

!(bind.property.ProductVersion)

1.2.3.4

bind.property.ProductVersion.Major

!(bind.property.ProductVersion.Major)

1

bind.property.ProductVersion.Minor

!(bind.property.ProductVersion.Minor)

2

bind.property.ProductVersion.Build

!(bind.property.ProductVersion.Build)

3

bind.property.ProductVersion.Revision

!(bind.property.ProductVersion.Revision)

4

Package Properties

You can reference the following properties from packages in your bundle. This allows developers to use property values already defined in their packages to set attributes in their bundle.

Variable name

Example usage

Example value

bind.packageDescription.PackageID

!(bind.packageDescription.MyProduct)

Description of My Product

bind.packageLanguage.PackageID

!(bind.packageLanguage.MyProduct)

1033

bind.packageManufacturer.PackageID

!(bind.packageManufacturer.MyProduct)

My Company

bind.packageName.PackageID

!(bind.packageName.MyProduct)

My Product

bind.packageVersion.PackageID

!(bind.packageVersion.MyProduct)

1.2.3.4

Localization Variables

Variables can be passed in before binding the output file from a WiX localization file, or .wxl file. This process allows the developer to link one or more .wixobj files together with diferent .wxl files to produce different localized packages.

Localization variables are in the following format:

!(loc.VariableName)

Custom Binder Variables

You can create your own binder variables using the WixVariable element or by simply typing your own variable name in the following format:

!(bind.VariableName)

Custom binder variables allow you to use the same .wixobj files but specify different values when linking, similar to how localization variables are used. You might use binder variables for different builds, like varying the target processor architecture.