| #include "windows.h" | |
| #include "msiquery.h" | |
| /* Print a debug message to the installer log file. | |
| * To see the debug messages, install with | |
| * msiexec /i pythonxy.msi /l*v python.log | |
| */ | |
| static UINT debug(MSIHANDLE hInstall, LPCSTR msg) | |
| { | |
| MSIHANDLE hRec = MsiCreateRecord(1); | |
| if (!hRec || MsiRecordSetStringA(hRec, 1, msg) != ERROR_SUCCESS) { | |
| return ERROR_INSTALL_FAILURE; | |
| } | |
| MsiProcessMessage(hInstall, INSTALLMESSAGE_INFO, hRec); | |
| MsiCloseHandle(hRec); | |
| return ERROR_SUCCESS; | |
| } | |
| /* Check whether the TARGETDIR exists and is a directory. | |
| * Set TargetExists appropriately. | |
| */ | |
| UINT __declspec(dllexport) __stdcall CheckDir(MSIHANDLE hInstall) | |
| { | |
| #define PSIZE 1024 | |
| WCHAR wpath[PSIZE]; | |
| char path[PSIZE]; | |
| UINT result; | |
| DWORD size = PSIZE; | |
| DWORD attributes; | |
| result = MsiGetPropertyW(hInstall, L"TARGETDIR", wpath, &size); | |
| if (result != ERROR_SUCCESS) | |
| return result; | |
| wpath[size] = L'\0'; | |
| path[size] = L'\0'; | |
| attributes = GetFileAttributesW(wpath); | |
| if (attributes == INVALID_FILE_ATTRIBUTES || | |
| !(attributes & FILE_ATTRIBUTE_DIRECTORY)) | |
| { | |
| return MsiSetPropertyA(hInstall, "TargetExists", "0"); | |
| } else { | |
| return MsiSetPropertyA(hInstall, "TargetExists", "1"); | |
| } | |
| } | |
| /* Update the state of the REGISTRY.tcl component according to the | |
| * Extension and TclTk features. REGISTRY.tcl must be installed | |
| * if both features are installed, and must be absent otherwise. | |
| */ | |
| UINT __declspec(dllexport) __stdcall UpdateEditIDLE(MSIHANDLE hInstall) | |
| { | |
| INSTALLSTATE ext_old, ext_new, tcl_old, tcl_new, reg_new; | |
| UINT result; | |
| result = MsiGetFeatureStateA(hInstall, "Extensions", &ext_old, &ext_new); | |
| if (result != ERROR_SUCCESS) | |
| return result; | |
| result = MsiGetFeatureStateA(hInstall, "TclTk", &tcl_old, &tcl_new); | |
| if (result != ERROR_SUCCESS) | |
| return result; | |
| /* If the current state is Absent, and the user did not select | |
| the feature in the UI, Installer apparently sets the "selected" | |
| state to unknown. Update it to the current value, then. */ | |
| if (ext_new == INSTALLSTATE_UNKNOWN) | |
| ext_new = ext_old; | |
| if (tcl_new == INSTALLSTATE_UNKNOWN) | |
| tcl_new = tcl_old; | |
| // XXX consider current state of REGISTRY.tcl? | |
| if (((tcl_new == INSTALLSTATE_LOCAL) || | |
| (tcl_new == INSTALLSTATE_SOURCE) || | |
| (tcl_new == INSTALLSTATE_DEFAULT)) && | |
| ((ext_new == INSTALLSTATE_LOCAL) || | |
| (ext_new == INSTALLSTATE_SOURCE) || | |
| (ext_new == INSTALLSTATE_DEFAULT))) { | |
| reg_new = INSTALLSTATE_SOURCE; | |
| } else { | |
| reg_new = INSTALLSTATE_ABSENT; | |
| } | |
| result = MsiSetComponentStateA(hInstall, "REGISTRY.tcl", reg_new); | |
| return result; | |
| } | |
| BOOL APIENTRY DllMain(HANDLE hModule, | |
| DWORD ul_reason_for_call, | |
| LPVOID lpReserved) | |
| { | |
| return TRUE; | |
| } | |