msi: Load the folder property if available and requested.
diff --git a/dlls/msi/action.c b/dlls/msi/action.c
index b328e5d..51d827e 100644
--- a/dlls/msi/action.c
+++ b/dlls/msi/action.c
@@ -1043,7 +1043,7 @@
         return ERROR_SUCCESS;
     }
 
-    full_path = resolve_folder(package,dir,FALSE,FALSE,&folder);
+    full_path = resolve_folder(package,dir,FALSE,FALSE,TRUE,&folder);
     if (!full_path)
     {
         ERR("Unable to resolve folder id %s\n",debugstr_w(dir));
@@ -1074,7 +1074,7 @@
     MSIFOLDER *folder;
     LPWSTR install_path;
 
-    install_path = resolve_folder(package, dir, FALSE, FALSE, &folder);
+    install_path = resolve_folder(package, dir, FALSE, FALSE, TRUE, &folder);
     if (!install_path)
         return ERROR_FUNCTION_FAILED; 
 
@@ -1898,7 +1898,7 @@
 
     /* This helper function now does ALL the work */
     TRACE("Dir %s ...\n",debugstr_w(name));
-    path = resolve_folder(package,name,FALSE,TRUE,NULL);
+    path = resolve_folder(package,name,FALSE,TRUE,TRUE,NULL);
     TRACE("resolves to %s\n",debugstr_w(path));
     msi_free(path);
 
@@ -1981,7 +1981,7 @@
             comp->ForceLocalState = TRUE;
 
         /* calculate target */
-        p = resolve_folder(package, comp->Directory, FALSE, FALSE, NULL);
+        p = resolve_folder(package, comp->Directory, FALSE, FALSE, TRUE, NULL);
 
         msi_free(file->TargetPath);
 
@@ -2519,7 +2519,7 @@
 {
 
     if (!cmp->KeyPath)
-        return resolve_folder(package,cmp->Directory,FALSE,FALSE,NULL);
+        return resolve_folder(package,cmp->Directory,FALSE,FALSE,TRUE,NULL);
 
     if (cmp->Attributes & msidbComponentAttributesRegistryKeyPath)
     {
@@ -2909,7 +2909,7 @@
             helpid = MSI_RecordGetString(row,6);
 
             if (helpid)
-                help = resolve_folder(package,helpid,FALSE,FALSE,NULL);
+                help = resolve_folder(package,helpid,FALSE,FALSE,TRUE,NULL);
             res = RegisterTypeLib(tl_struct.ptLib,tl_struct.path,help);
             msi_free(help);
 
@@ -3008,7 +3008,7 @@
     }
 
     buffer = MSI_RecordGetString(row,2);
-    target_folder = resolve_folder(package, buffer,FALSE,FALSE,NULL);
+    target_folder = resolve_folder(package, buffer,FALSE,FALSE,TRUE,NULL);
 
     /* may be needed because of a bug somehwere else */
     create_full_pathW(target_folder);
@@ -3084,7 +3084,7 @@
     {
         LPWSTR Path;
         buffer = MSI_RecordGetString(row,12);
-        Path = resolve_folder(package, buffer, FALSE, FALSE, NULL);
+        Path = resolve_folder(package, buffer, FALSE, FALSE, TRUE, NULL);
         if (Path)
             IShellLinkW_SetWorkingDirectory(sl,Path);
         msi_free(Path);
@@ -3348,7 +3348,7 @@
 
     if (dirproperty)
     {
-        folder = resolve_folder(package, dirproperty, FALSE, FALSE, NULL);
+        folder = resolve_folder(package, dirproperty, FALSE, FALSE, TRUE, NULL);
         if (!folder)
             folder = msi_dup_property( package, dirproperty );
     }
diff --git a/dlls/msi/custom.c b/dlls/msi/custom.c
index 1e3a866..48a0769 100644
--- a/dlls/msi/custom.c
+++ b/dlls/msi/custom.c
@@ -826,7 +826,7 @@
 
     memset(&si,0,sizeof(STARTUPINFOW));
 
-    filename = resolve_folder(package, source, FALSE, FALSE, NULL);
+    filename = resolve_folder(package, source, FALSE, FALSE, TRUE, NULL);
 
     if (!filename)
         return ERROR_FUNCTION_FAILED;
diff --git a/dlls/msi/files.c b/dlls/msi/files.c
index eb5e456..e9f1043 100644
--- a/dlls/msi/files.c
+++ b/dlls/msi/files.c
@@ -446,7 +446,7 @@
     if (!file->IsCompressed)
     {
         LPWSTR p, path;
-        p = resolve_folder(package, file->Component->Directory, TRUE, FALSE, NULL);
+        p = resolve_folder(package, file->Component->Directory, TRUE, FALSE, TRUE, NULL);
         path = build_directory_name(2, p, file->ShortName);
         if (INVALID_FILE_ATTRIBUTES == GetFileAttributesW( path ))
         {
@@ -845,7 +845,7 @@
     {
         LPCWSTR destkey;
         destkey = MSI_RecordGetString(row,5);
-        dest_path = resolve_folder(package, destkey, FALSE,FALSE,NULL);
+        dest_path = resolve_folder(package, destkey, FALSE, FALSE, TRUE, NULL);
         if (!dest_path)
         {
             /* try a Property */
diff --git a/dlls/msi/format.c b/dlls/msi/format.c
index 4cb802e..2ea6e23 100644
--- a/dlls/msi/format.c
+++ b/dlls/msi/format.c
@@ -122,7 +122,7 @@
     comp = get_loaded_component(package,key);
     if (comp)
     {
-        value = resolve_folder(package, comp->Directory, FALSE, FALSE, NULL);
+        value = resolve_folder(package, comp->Directory, FALSE, FALSE, TRUE, NULL);
         *sz = (strlenW(value)) * sizeof(WCHAR);
     }
 
diff --git a/dlls/msi/helpers.c b/dlls/msi/helpers.c
index b2968f1..7357bd7 100644
--- a/dlls/msi/helpers.c
+++ b/dlls/msi/helpers.c
@@ -221,7 +221,7 @@
 }
 
 LPWSTR resolve_folder(MSIPACKAGE *package, LPCWSTR name, BOOL source, 
-                      BOOL set_prop, MSIFOLDER **folder)
+                      BOOL set_prop, BOOL load_prop, MSIFOLDER **folder)
 {
     MSIFOLDER *f;
     LPWSTR p, path = NULL, parent;
@@ -293,6 +293,13 @@
         return path;
     }
 
+    if (!source && load_prop && (path = msi_dup_property( package, name )))
+    {
+        f->ResolvedTarget = strdupW( path );
+        TRACE("   property set to %s\n", debugstr_w(path));
+        return path;
+    }
+
     if (!f->Parent)
         return path;
 
@@ -300,7 +307,7 @@
 
     TRACE(" ! Parent is %s\n", debugstr_w(parent));
 
-    p = resolve_folder(package, parent, source, set_prop, NULL);
+    p = resolve_folder(package, parent, source, set_prop, load_prop, NULL);
     if (!source)
     {
         TRACE("   TargetDefault = %s\n", debugstr_w(f->TargetDefault));
diff --git a/dlls/msi/install.c b/dlls/msi/install.c
index ff6e21f..b6cff6d 100644
--- a/dlls/msi/install.c
+++ b/dlls/msi/install.c
@@ -163,7 +163,7 @@
     if (!package)
         return ERROR_INVALID_HANDLE;
 
-    path = resolve_folder( package, szFolder, FALSE, FALSE, NULL );
+    path = resolve_folder( package, szFolder, FALSE, FALSE, TRUE, NULL );
     msiobj_release( &package->hdr );
 
     if (!path)
@@ -241,7 +241,7 @@
         return ERROR_INVALID_PARAMETER;
     }
 
-    path = resolve_folder(package, szFolder, TRUE, FALSE, NULL);
+    path = resolve_folder(package, szFolder, TRUE, FALSE, TRUE, NULL);
     msiobj_release( &package->hdr );
 
     TRACE("path = %s\n",debugstr_w(path));
@@ -340,7 +340,7 @@
            attrib & FILE_ATTRIBUTE_READONLY))
         return ERROR_FUNCTION_FAILED;
 
-    path = resolve_folder(package,szFolder,FALSE,FALSE,&folder);
+    path = resolve_folder(package,szFolder,FALSE,FALSE,FALSE,&folder);
     if (!path)
         return ERROR_DIRECTORY;
 
@@ -355,7 +355,7 @@
          */
         msi_free(folder->ResolvedTarget);
         folder->ResolvedTarget = NULL;
-        path2 = resolve_folder(package,szFolder,FALSE,TRUE,NULL);
+        path2 = resolve_folder(package,szFolder,FALSE,TRUE,FALSE,NULL);
         msi_free(path2);
     }
     else
@@ -370,7 +370,7 @@
 
         LIST_FOR_EACH_ENTRY( f, &package->folders, MSIFOLDER, entry )
         {
-            path2 = resolve_folder(package, f->Directory, FALSE, TRUE, NULL);
+            path2 = resolve_folder(package, f->Directory, FALSE, TRUE, FALSE, NULL);
             msi_free(path2);
         }
 
@@ -382,7 +382,7 @@
             if (!comp)
                 continue;
 
-            p = resolve_folder(package, comp->Directory, FALSE, FALSE, NULL);
+            p = resolve_folder(package, comp->Directory, FALSE, FALSE, FALSE, NULL);
             msi_free(file->TargetPath);
 
             file->TargetPath = build_directory_name(2, p, file->FileName);
diff --git a/dlls/msi/msipriv.h b/dlls/msi/msipriv.h
index d61eab9..55dd2fa 100644
--- a/dlls/msi/msipriv.h
+++ b/dlls/msi/msipriv.h
@@ -755,7 +755,7 @@
 extern LPWSTR msi_dup_property(MSIPACKAGE *package, LPCWSTR prop);
 extern int msi_get_property_int( MSIPACKAGE *package, LPCWSTR prop, int def );
 extern LPWSTR resolve_folder(MSIPACKAGE *package, LPCWSTR name, BOOL source,
-                      BOOL set_prop, MSIFOLDER **folder);
+                      BOOL set_prop, BOOL load_prop, MSIFOLDER **folder);
 extern MSICOMPONENT *get_loaded_component( MSIPACKAGE* package, LPCWSTR Component );
 extern MSIFEATURE *get_loaded_feature( MSIPACKAGE* package, LPCWSTR Feature );
 extern MSIFILE *get_loaded_file( MSIPACKAGE* package, LPCWSTR file );
diff --git a/dlls/msi/tests/install.c b/dlls/msi/tests/install.c
index 6e42696..426e1ec 100644
--- a/dlls/msi/tests/install.c
+++ b/dlls/msi/tests/install.c
@@ -266,6 +266,25 @@
                                     "Media\tDiskId\n"
                                     "1\t1\t\t\tDISK1\t\n";
 
+static const CHAR sdp_install_exec_seq_dat[] = "Action\tCondition\tSequence\n"
+                                               "s72\tS255\tI2\n"
+                                               "InstallExecuteSequence\tAction\n"
+                                               "AllocateRegistrySpace\tNOT Installed\t1550\n"
+                                               "CostFinalize\t\t1000\n"
+                                               "CostInitialize\t\t800\n"
+                                               "FileCost\t\t900\n"
+                                               "InstallFiles\t\t4000\n"
+                                               "InstallFinalize\t\t6600\n"
+                                               "InstallInitialize\t\t1500\n"
+                                               "InstallValidate\t\t1400\n"
+                                               "LaunchConditions\t\t100\n"
+                                               "SetDirProperty\t\t950";
+
+static const CHAR sdp_custom_action_dat[] = "Action\tType\tSource\tTarget\tISComments\n"
+                                            "s72\ti2\tS64\tS0\tS255\n"
+                                            "CustomAction\tAction\n"
+                                            "SetDirProperty\t51\tMSITESTDIR\t[CommonFilesFolder]msitest\\\t\n";
+
 typedef struct _msi_table
 {
     const CHAR *filename;
@@ -376,6 +395,19 @@
     ADD_TABLE(property),
 };
 
+static const msi_table sdp_tables[] =
+{
+    ADD_TABLE(rof_component),
+    ADD_TABLE(directory),
+    ADD_TABLE(rof_feature),
+    ADD_TABLE(rof_feature_comp),
+    ADD_TABLE(rof_file),
+    ADD_TABLE(sdp_install_exec_seq),
+    ADD_TABLE(sdp_custom_action),
+    ADD_TABLE(rof_media),
+    ADD_TABLE(property),
+};
+
 /* cabinet definitions */
 
 /* make the max size large so there is only one cab file */
@@ -1195,7 +1227,6 @@
     lstrcat(path, "\\maximus");
     file = CreateFile(path, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE,
                       NULL, CREATE_NEW, FILE_ATTRIBUTE_READONLY, NULL);
-    if (file == INVALID_HANDLE_VALUE) printf("didn't work here: %d\n", GetLastError());
 
     WriteFile(file, "readonlyfile", 20, &size, NULL);
     CloseHandle(file);
@@ -1212,6 +1243,24 @@
     DeleteFile(msifile);
 }
 
+static void test_setdirproperty(void)
+{
+    UINT r;
+
+    CreateDirectoryA("msitest", NULL);
+    create_file("msitest\\maximus", 500);
+    create_database(msifile, sdp_tables, sizeof(sdp_tables) / sizeof(msi_table));
+
+    MsiSetInternalUI(INSTALLUILEVEL_NONE, NULL);
+
+    r = MsiInstallProductA(msifile, NULL);
+    ok(r == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %u\n", r);
+    ok(delete_pf("Common Files\\msitest\\maximus", TRUE), "File not installed\n");
+    ok(delete_pf("Common Files\\msitest", FALSE), "File not installed\n");
+
+    DeleteFile(msifile);
+}
+
 START_TEST(install)
 {
     DWORD len;
@@ -1238,6 +1287,7 @@
     test_samesequence();
     test_uiLevelFlags();
     test_readonlyfile();
+    test_setdirproperty();
 
     SetCurrentDirectoryA(prev_path);
 }