If you want to open a .msp file with the Windows Installer APIs, you must pass MSIDBOPEN_PATCHFILE
to the MsiOpenDatabase
function, or ERROR_OPEN_FAILED
(110) is returned. Below is the definition of both MSIDBOPEN_PATCHFILE
and MSIDBOPEN_READONLY
from msiquery.h in the Windows Installer SDK.
#define MSIDBOPEN_READONLY (LPCTSTR)0
#define MSIDBOPEN_PATCHFILE 32/sizeof(*MSIDBOPEN_READONLY)
LPCTSTR
is defined as LPCWSTR
when UNICODE
is defined, which is defined as wchar_t*
. Since sizeof(wchar_t)
is 2, the value of MSIDBOPEN_PATCHFILE
is 16 when UNICODE
is defined. If you pass this to either the MsiOpenDatabaseA
function or the MsiOpenDatabaseW
function ERROR_OPEN_FAILED
is still returned. The value must always be defined as 32.
For the automation method Installer.OpenDatabase
the second parameter must be set to msiOpenDatabaseModePatchFile
to open a patch, which is always defined as 32.
Most developers probably haven’t run into this problem yet because of support for Windows 95, 98, and Me, where Unicode is not natively supported and it’s typically undesirable to have to ship and support two bootstrap applications. Since Windows NT, 2000, XP, 2003, and future platforms support both ANSI and Unicode it makes sense to compile bootstrap applications for ANSI or MBCS. But when you choose to or need to support only Unicode, be sure to pass 32 as the szPersist
parameter to MsiOpenDatabase
.
PMSIDATABASE hDatabase = NULL;
UINT uiError = MsiOpenDatabase(TEXT(“Patch.msp”), (LPCTSTR)32, &hDatabase);
0 comments