Correct a problem with parse_data if binary data was not in full bytes.

More properly handle uncompressed file sources, fix the creating and
parsing of Source Directories.
This commit is contained in:
Aric Stewart 2005-05-16 21:37:35 +00:00 committed by Alexandre Julliard
parent 4a0a199fcf
commit 6186b2beaf
2 changed files with 80 additions and 26 deletions

View File

@ -1917,6 +1917,7 @@ static INT load_folder(MSIPACKAGE *package, const WCHAR* dir)
UINT rc; UINT rc;
MSIQUERY * view; MSIQUERY * view;
LPWSTR ptargetdir, targetdir, parent, srcdir; LPWSTR ptargetdir, targetdir, parent, srcdir;
LPWSTR shortname = NULL;
MSIRECORD * row = 0; MSIRECORD * row = 0;
INT index = -1; INT index = -1;
DWORD i; DWORD i;
@ -1982,15 +1983,16 @@ static INT load_folder(MSIPACKAGE *package, const WCHAR* dir)
/* for now only pick long filename versions */ /* for now only pick long filename versions */
if (strchrW(targetdir,'|')) if (strchrW(targetdir,'|'))
{ {
shortname = targetdir;
targetdir = strchrW(targetdir,'|'); targetdir = strchrW(targetdir,'|');
*targetdir = 0; *targetdir = 0;
targetdir ++; targetdir ++;
} }
/* for the sourcedir pick the short filename */
if (srcdir && strchrW(srcdir,'|')) if (srcdir && strchrW(srcdir,'|'))
{ {
srcdir= strchrW(srcdir,'|'); LPWSTR p = strchrW(srcdir,'|');
*srcdir= 0; *p = 0;
srcdir ++;
} }
/* now check for root dirs */ /* now check for root dirs */
@ -2009,9 +2011,12 @@ static INT load_folder(MSIPACKAGE *package, const WCHAR* dir)
if (srcdir) if (srcdir)
package->folders[index].SourceDefault = strdupW(srcdir); package->folders[index].SourceDefault = strdupW(srcdir);
else if (shortname)
package->folders[index].SourceDefault = strdupW(shortname);
else if (targetdir) else if (targetdir)
package->folders[index].SourceDefault = strdupW(targetdir); package->folders[index].SourceDefault = strdupW(targetdir);
HeapFree(GetProcessHeap(), 0, ptargetdir); HeapFree(GetProcessHeap(), 0, ptargetdir);
TRACE(" SourceDefault = %s\n",debugstr_w(package->folders[index].SourceDefault));
parent = load_dynamic_stringW(row,2); parent = load_dynamic_stringW(row,2);
if (parent) if (parent)
@ -2115,6 +2120,7 @@ LPWSTR resolve_folder(MSIPACKAGE *package, LPCWSTR name, BOOL source,
else if (source && package->folders[i].ResolvedSource) else if (source && package->folders[i].ResolvedSource)
{ {
path = strdupW(package->folders[i].ResolvedSource); path = strdupW(package->folders[i].ResolvedSource);
TRACE(" (source)already resolved to %s\n",debugstr_w(path));
return path; return path;
} }
else if (!source && package->folders[i].Property) else if (!source && package->folders[i].Property)
@ -2146,6 +2152,7 @@ LPWSTR resolve_folder(MSIPACKAGE *package, LPCWSTR name, BOOL source,
else else
{ {
path = build_directory_name(3, p, package->folders[i].SourceDefault, NULL); path = build_directory_name(3, p, package->folders[i].SourceDefault, NULL);
TRACE(" (source)resolved into %s\n",debugstr_w(path));
package->folders[i].ResolvedSource = strdupW(path); package->folders[i].ResolvedSource = strdupW(path);
} }
HeapFree(GetProcessHeap(),0,p); HeapFree(GetProcessHeap(),0,p);
@ -2952,8 +2959,8 @@ static BOOL extract_a_cabinet_file(MSIPACKAGE* package, const WCHAR* source,
return ret; return ret;
} }
static UINT ready_media_for_file(MSIPACKAGE *package, UINT sequence, static UINT ready_media_for_file(MSIPACKAGE *package, WCHAR* path,
WCHAR* path, WCHAR* file) MSIFILE* file)
{ {
UINT rc; UINT rc;
MSIQUERY * view; MSIQUERY * view;
@ -2971,14 +2978,21 @@ static UINT ready_media_for_file(MSIPACKAGE *package, UINT sequence,
INT seq; INT seq;
static UINT last_sequence = 0; static UINT last_sequence = 0;
if (sequence <= last_sequence) if (file->Attributes & msidbFileAttributesNoncompressed)
{ {
TRACE("Media already ready (%u, %u)\n",sequence,last_sequence); sz = MAX_PATH;
/*extract_a_cabinet_file(package, source,path,file); */ MSI_GetPropertyW(package, cszSourceDir, path, &sz);
return ERROR_SUCCESS; return ERROR_SUCCESS;
} }
sprintfW(Query,ExecSeqQuery,sequence); if (file->Sequence <= last_sequence)
{
TRACE("Media already ready (%u, %u)\n",file->Sequence,last_sequence);
/*extract_a_cabinet_file(package, source,path,file->File); */
return ERROR_SUCCESS;
}
sprintfW(Query,ExecSeqQuery,file->Sequence);
rc = MSI_DatabaseOpenViewW(package->db, Query, &view); rc = MSI_DatabaseOpenViewW(package->db, Query, &view);
if (rc != ERROR_SUCCESS) if (rc != ERROR_SUCCESS)
@ -3106,12 +3120,10 @@ static UINT ACTION_InstallFiles(MSIPACKAGE *package)
if ((file->State == 1) || (file->State == 2)) if ((file->State == 1) || (file->State == 2))
{ {
LPWSTR p; LPWSTR p;
INT len;
MSICOMPONENT* comp = NULL; MSICOMPONENT* comp = NULL;
TRACE("Installing %s\n",debugstr_w(file->File)); TRACE("Installing %s\n",debugstr_w(file->File));
rc = ready_media_for_file(package,file->Sequence,path_to_source, rc = ready_media_for_file(package, path_to_source, file);
file->File);
/* /*
* WARNING! * WARNING!
* our file table could change here because a new temp file * our file table could change here because a new temp file
@ -3136,11 +3148,18 @@ static UINT ACTION_InstallFiles(MSIPACKAGE *package)
HeapFree(GetProcessHeap(),0,file->TargetPath); HeapFree(GetProcessHeap(),0,file->TargetPath);
file->TargetPath = build_directory_name(2, p, file->FileName); file->TargetPath = build_directory_name(2, p, file->FileName);
HeapFree(GetProcessHeap(),0,p);
if (file->Attributes & msidbFileAttributesNoncompressed)
{
p = resolve_folder(package, comp->Directory, TRUE, FALSE, NULL);
file->SourcePath = build_directory_name(2, p, file->File);
HeapFree(GetProcessHeap(),0,p);
}
else
file->SourcePath = build_directory_name(2, path_to_source,
file->File);
len = strlenW(path_to_source) + strlenW(file->File) + 2;
file->SourcePath = HeapAlloc(GetProcessHeap(),0,len*sizeof(WCHAR));
strcpyW(file->SourcePath, path_to_source);
strcatW(file->SourcePath, file->File);
TRACE("file paths %s to %s\n",debugstr_w(file->SourcePath), TRACE("file paths %s to %s\n",debugstr_w(file->SourcePath),
debugstr_w(file->TargetPath)); debugstr_w(file->TargetPath));
@ -3156,16 +3175,23 @@ static UINT ACTION_InstallFiles(MSIPACKAGE *package)
msiobj_release( &uirow->hdr ); msiobj_release( &uirow->hdr );
ui_progress(package,2,file->FileSize,0,0); ui_progress(package,2,file->FileSize,0,0);
if (!MoveFileW(file->SourcePath,file->TargetPath))
if (file->Attributes & msidbFileAttributesNoncompressed)
rc = CopyFileW(file->SourcePath,file->TargetPath,FALSE);
else
rc = MoveFileW(file->SourcePath, file->TargetPath);
if (!rc)
{ {
rc = GetLastError(); rc = GetLastError();
ERR("Unable to move file (%s -> %s) (error %d)\n", ERR("Unable to move/copy file (%s -> %s) (error %d)\n",
debugstr_w(file->SourcePath), debugstr_w(file->TargetPath), debugstr_w(file->SourcePath), debugstr_w(file->TargetPath),
rc); rc);
if (rc == ERROR_ALREADY_EXISTS && file->State == 2) if (rc == ERROR_ALREADY_EXISTS && file->State == 2)
{ {
CopyFileW(file->SourcePath,file->TargetPath,FALSE); CopyFileW(file->SourcePath,file->TargetPath,FALSE);
DeleteFileW(file->SourcePath); if (!(file->Attributes & msidbFileAttributesNoncompressed))
DeleteFileW(file->SourcePath);
rc = 0; rc = 0;
} }
else if (rc == ERROR_FILE_NOT_FOUND) else if (rc == ERROR_FILE_NOT_FOUND)
@ -3173,14 +3199,17 @@ static UINT ACTION_InstallFiles(MSIPACKAGE *package)
ERR("Source File Not Found! Continuing\n"); ERR("Source File Not Found! Continuing\n");
rc = 0; rc = 0;
} }
else else if (file->Attributes & msidbFileAttributesVital)
{ {
ERR("Ignoring Error and continuing...\n"); ERR("Ignoring Error and continuing (nonvital file)...\n");
rc = 0; rc = 0;
} }
} }
else else
{
file->State = 4; file->State = 4;
rc = ERROR_SUCCESS;
}
} }
} }
@ -3372,21 +3401,35 @@ static LPSTR parse_value(MSIPACKAGE *package, WCHAR *value, DWORD *type,
{ {
LPWSTR ptr; LPWSTR ptr;
CHAR byte[5]; CHAR byte[5];
LPWSTR deformated; LPWSTR deformated = NULL;
int count; int count;
deformat_string(package, &value[2], &deformated); deformat_string(package, &value[2], &deformated);
/* binary value type */ /* binary value type */
ptr = deformated; ptr = deformated;
*type=REG_BINARY; *type = REG_BINARY;
*size = strlenW(ptr)/2; if (strlenW(ptr)%2)
*size = (strlenW(ptr)/2)+1;
else
*size = strlenW(ptr)/2;
data = HeapAlloc(GetProcessHeap(),0,*size); data = HeapAlloc(GetProcessHeap(),0,*size);
byte[0] = '0'; byte[0] = '0';
byte[1] = 'x'; byte[1] = 'x';
byte[4] = 0; byte[4] = 0;
count = 0; count = 0;
/* if uneven pad with a zero in front */
if (strlenW(ptr)%2)
{
byte[2]= '0';
byte[3]= *ptr;
ptr++;
data[count] = (BYTE)strtol(byte,NULL,0);
count ++;
TRACE("Uneven byte count\n");
}
while (*ptr) while (*ptr)
{ {
byte[2]= *ptr; byte[2]= *ptr;

View File

@ -23,6 +23,17 @@
extern "C" { extern "C" {
#endif #endif
enum msidbFileAttributes {
msidbFileAttributesReadOnly = 0x00000001,
msidbFileAttributesHidden = 0x00000002,
msidbFileAttributesSystem = 0x00000004,
msidbFileAttributesVital = 0x00000200,
msidbFileAttributesChecksum = 0x00000400,
msidbFileAttributesPatchAdded = 0x00001000,
msidbFileAttributesNoncompressed = 0x00002000,
msidbFileAttributesCompressed = 0x00004000
};
enum msidbDialogAttributes { enum msidbDialogAttributes {
msidbDialogAttributesVisible = 0x00000001, msidbDialogAttributesVisible = 0x00000001,
msidbDialogAttributesModal = 0x00000002, msidbDialogAttributesModal = 0x00000002,