From f84fa0ce6354827d6b2396ca3119c9a8bb7efcfb Mon Sep 17 00:00:00 2001 From: James Hawkins Date: Mon, 7 Aug 2006 11:37:49 -0700 Subject: [PATCH] msi: Fix the compressed files logic. If the compressed file attribute is not set, use the Word Count property to determine if files are compressed. --- dlls/msi/action.c | 16 ++++++++++++++++ dlls/msi/action.h | 1 + dlls/msi/files.c | 6 +++--- dlls/msi/msipriv.h | 8 ++++++++ dlls/msi/package.c | 31 +++++++++++++++++++++++++++++++ 5 files changed, 59 insertions(+), 3 deletions(-) diff --git a/dlls/msi/action.c b/dlls/msi/action.c index e2d78b1b712..a90096e2f93 100644 --- a/dlls/msi/action.c +++ b/dlls/msi/action.c @@ -1326,7 +1326,23 @@ static UINT load_file(MSIRECORD *row, LPVOID param) file->state = msifs_invalid; + /* if the compressed bits are not set in the file attributes, + * then read the information from the package word count property + */ if (file->Attributes & msidbFileAttributesCompressed) + { + file->IsCompressed = TRUE; + } + else if (file->Attributes & msidbFileAttributesNoncompressed) + { + file->IsCompressed = FALSE; + } + else + { + file->IsCompressed = package->WordCount & MSIWORDCOUNT_COMPRESSED; + } + + if (file->IsCompressed) { file->Component->ForceLocalState = TRUE; file->Component->Action = INSTALLSTATE_LOCAL; diff --git a/dlls/msi/action.h b/dlls/msi/action.h index 93d28c6a5ec..22ad1beb98e 100644 --- a/dlls/msi/action.h +++ b/dlls/msi/action.h @@ -120,6 +120,7 @@ typedef struct tagMSIFILE msi_file_state state; LPWSTR SourcePath; LPWSTR TargetPath; + BOOL IsCompressed; } MSIFILE; typedef struct tagMSITEMPFILE diff --git a/dlls/msi/files.c b/dlls/msi/files.c index 36caba734f1..914b699372f 100644 --- a/dlls/msi/files.c +++ b/dlls/msi/files.c @@ -330,7 +330,7 @@ static BOOL extract_cabinet_file(MSIPACKAGE* package, LPCWSTR source, static VOID set_file_source(MSIPACKAGE* package, MSIFILE* file, MSICOMPONENT* comp, LPCWSTR path) { - if (!(file->Attributes & msidbFileAttributesCompressed)) + if (!file->IsCompressed) { LPWSTR p, path; p = resolve_folder(package, comp->Directory, TRUE, FALSE, NULL); @@ -419,7 +419,7 @@ static UINT ready_media_for_file( MSIPACKAGE *package, struct media_info *mi, msi_free(mi->last_path); mi->last_path = NULL; - if (!(file->Attributes & msidbFileAttributesCompressed)) + if (!file->IsCompressed) { mi->last_path = resolve_folder(package, comp->Directory, TRUE, FALSE, NULL); set_file_source(package,file,comp,mi->last_path); @@ -605,7 +605,7 @@ UINT ACTION_InstallFiles(MSIPACKAGE *package) continue; /* compressed files are extracted in ready_media_for_file */ - if (file->Attributes & msidbFileAttributesCompressed) + if (file->IsCompressed) { if (INVALID_FILE_ATTRIBUTES == GetFileAttributesW(file->TargetPath)) ERR("compressed file wasn't extracted (%s)\n", diff --git a/dlls/msi/msipriv.h b/dlls/msi/msipriv.h index 5d2c21ea72b..c565b67a4ee 100644 --- a/dlls/msi/msipriv.h +++ b/dlls/msi/msipriv.h @@ -39,6 +39,12 @@ #define MSITYPE_NULLABLE 0x1000 #define MSITYPE_KEY 0x2000 +/* Word Count masks */ +#define MSIWORDCOUNT_SHORTFILENAMES 0x0001 +#define MSIWORDCOUNT_COMPRESSED 0x0002 +#define MSIWORDCOUNT_ADMINISTRATIVE 0x0004 +#define MSIWORDCOUNT_PRIVILEGES 0x0008 + #define MSITYPE_IS_BINARY(type) (((type) & ~MSITYPE_NULLABLE) == (MSITYPE_STRING|MSITYPE_VALID)) struct tagMSITABLE; @@ -223,6 +229,8 @@ typedef struct tagMSIPACKAGE UINT CurrentInstallState; msi_dialog *dialog; LPWSTR next_dialog; + + UINT WordCount; struct list subscriptions; } MSIPACKAGE; diff --git a/dlls/msi/package.c b/dlls/msi/package.c index 283b0a64e06..4065ffb8d52 100644 --- a/dlls/msi/package.c +++ b/dlls/msi/package.c @@ -40,6 +40,7 @@ #include "shlobj.h" #include "wine/unicode.h" #include "objbase.h" +#include "msidefs.h" #include "msipriv.h" #include "action.h" @@ -376,6 +377,34 @@ static VOID set_installer_properties(MSIPACKAGE *package) ReleaseDC(0, dc); } +static UINT msi_get_word_count( MSIPACKAGE *package ) +{ + UINT rc; + INT word_count; + MSIHANDLE suminfo; + MSIHANDLE hdb = alloc_msihandle( &package->db->hdr ); + + rc = MsiGetSummaryInformationW( hdb, NULL, 0, &suminfo ); + MsiCloseHandle(hdb); + if (rc != ERROR_SUCCESS) + { + ERR("Unable to open Summary Information\n"); + return 0; + } + + rc = MsiSummaryInfoGetPropertyW( suminfo, PID_WORDCOUNT, NULL, + &word_count, NULL, NULL, NULL ); + if (rc != ERROR_SUCCESS) + { + ERR("Unable to query word count\n"); + MsiCloseHandle(suminfo); + return 0; + } + + MsiCloseHandle(suminfo); + return word_count; +} + MSIPACKAGE *MSI_CreatePackage( MSIDATABASE *db ) { static const WCHAR szLevel[] = { 'U','I','L','e','v','e','l',0 }; @@ -411,6 +440,8 @@ MSIPACKAGE *MSI_CreatePackage( MSIDATABASE *db ) list_init( &package->progids ); list_init( &package->RunningActions ); + package->WordCount = msi_get_word_count( package ); + /* OK, here is where we do a slew of things to the database to * prep for all that is to come as a package */