!include ..\..\..\NSIS.definitions.nsh Name "@CPACK_PACKAGE_NAME@" BrandingText "@CPACK_PACKAGE_FILE_NAME@" OutFile "@CPACK_TOPLEVEL_DIRECTORY@/@CPACK_OUTPUT_FILE_NAME@" !define INST_DIR "@CPACK_TEMPORARY_DIRECTORY@" RequestExecutionlevel admin SetCompressor LZMA Var NormalDestDir Var PortableDestDir Var PortableMode Var ReinstallMode !include LogicLib.nsh !include FileFunc.nsh !include MUI2.nsh !include x64.nsh !define MUI_ABORTWARNING !define MUI_WELCOMEFINISHPAGE_BITMAP "${NSIS_SOURCE_PATH}\cmake\leftimage.bmp" !define MUI_UNWELCOMEFINISHPAGE_BITMAP "${NSIS_SOURCE_PATH}\cmake\leftimage.bmp" !define MUI_HEADERIMAGE !define MUI_HEADERIMAGE_BITMAP "${NSIS_SOURCE_PATH}\cmake\headerimage.bmp" !define MUI_HEADERIMAGE_UNBITMAP "${NSIS_SOURCE_PATH}\cmake\headerimage.bmp" !define MUI_WELCOMEPAGE_TEXT "This wizard will guide you through the installation of Cockatrice.$\r$\n$\r$\nClick Next to continue." !define MUI_FINISHPAGE_RUN "$INSTDIR/cockatrice.exe" !define MUI_FINISHPAGE_RUN_TEXT "Run 'Cockatrice' now" !define MUI_ICON "${NSIS_SOURCE_PATH}\cockatrice\resources\appicon.ico" !define MUI_PAGE_CUSTOMFUNCTION_PRE SkipIfReinstall !insertmacro MUI_PAGE_WELCOME !define MUI_PAGE_CUSTOMFUNCTION_PRE SkipIfReinstall !insertmacro MUI_PAGE_LICENSE "${NSIS_SOURCE_PATH}\LICENSE" Page Custom PortableModePageCreate PortableModePageLeave !define MUI_PAGE_CUSTOMFUNCTION_PRE componentsPagePre !insertmacro MUI_PAGE_COMPONENTS !define MUI_PAGE_CUSTOMFUNCTION_PRE SkipIfReinstall !insertmacro MUI_PAGE_DIRECTORY !define MUI_PAGE_CUSTOMFUNCTION_PRE SkipIfReinstall !insertmacro MUI_PAGE_INSTFILES !define MUI_PAGE_CUSTOMFUNCTION_PRE SkipIfReinstall !insertmacro MUI_PAGE_FINISH !insertmacro MUI_UNPAGE_CONFIRM !insertmacro MUI_UNPAGE_COMPONENTS !insertmacro MUI_UNPAGE_INSTFILES !insertmacro MUI_UNPAGE_FINISH !insertmacro MUI_LANGUAGE English Function .onInit ${If} ${NSIS_IS_64_BIT} == 1 #NSIS 64bit ${IfNot} ${RunningX64} MessageBox MB_OK|MB_ICONSTOP "This version of Cockatrice requires a 64-bit Windows system." Abort ${EndIf} StrCpy $NormalDestDir "$ProgramFiles64\Cockatrice" SetRegView 64 ${Else} #NSIS 32bit ${If} ${RunningX64} MessageBox MB_OK|MB_ICONEXCLAMATION \ "You are about to install a 32-bit version of Cockatrice on a 64-bit Windows system.$\n\ We advise you to use the correct 64-bit installer instead to get around potential issues.$\n$\n\ Download from our webpage: https://cockatrice.github.io" ${EndIf} StrCpy $NormalDestDir "$ProgramFiles\Cockatrice" ${EndIf} StrCpy $PortableDestDir "$Desktop\CockatricePortable" ${GetParameters} $9 ClearErrors ${GetOptions} $9 "/?" $8 ${IfNot} ${Errors} MessageBox MB_ICONINFORMATION|MB_SETFOREGROUND "\ /PORTABLE : Install in portable mode$\n\ /S : Silent install$\n\ /R : Silent upgrade$\n\ /D=%directory% : Specify destination directory$\n" Quit ${EndIf} ClearErrors ${GetOptions} $9 "/PORTABLE" $8 ${IfNot} ${Errors} StrCpy $PortableMode 1 StrCpy $0 $PortableDestDir ${Else} StrCpy $PortableMode 0 StrCpy $0 $NormalDestDir ${If} ${Silent} Call RequireAdmin ${EndIf} ${EndIf} ClearErrors ${GetOptions} $9 "/R" $8 ${IfNot} ${Errors} StrCpy $ReinstallMode 1 SetSilent silent SetAutoClose true ${Else} StrCpy $ReinstallMode 0 ${EndIf} ${If} $InstDir == "" ; User did not use /D to specify a directory, ; we need to set a default based on the install mode StrCpy $InstDir $0 ${EndIf} ; --- Detect portable install when using /R (must come BEFORE SetModeDestinationFromInstdir) --- ${If} $ReinstallMode = 1 IfFileExists "$InstDir\portable.dat" 0 not_portable StrCpy $PortableMode 1 Goto portable_done not_portable: StrCpy $PortableMode 0 portable_done: ${EndIf} ; Now that $PortableMode reflects reality, commit InstDir into the correct slot Call SetModeDestinationFromInstdir ; Make sure no application instance is still running (and holding file locks) ; before the previous version is uninstalled or new files are installed. ; On a silent update (/R /S) running processes are asked to close gracefully ; and waited for, then force-closed only on timeout. On interactive installs ; the user is prompted to close them instead. Call EnsureAppsNotRunning ${If} $ReinstallMode = 1 ${AndIf} $PortableMode = 0 Call AutoUninstallIfNeeded ${EndIf} FunctionEnd Function un.onInit ${If} ${NSIS_IS_64_BIT} == 1 SetRegView 64 ${EndIf} ; Ensure no application instance is still running before removing files. Call un.EnsureAppsNotRunning FunctionEnd Function RequireAdmin UserInfo::GetAccountType Pop $8 ${If} $8 != "admin" MessageBox MB_ICONSTOP "You need administrator rights to install Cockatrice" SetErrorLevel 740 ;ERROR_ELEVATION_REQUIRED Abort ${EndIf} FunctionEnd Function SetModeDestinationFromInstdir ${If} $PortableMode = 0 StrCpy $NormalDestDir $InstDir ${Else} StrCpy $PortableDestDir $InstDir ${EndIf} FunctionEnd Function SkipIfReinstall ${If} $ReinstallMode = 1 Abort ${EndIf} FunctionEnd Function AutoUninstallIfNeeded SetShellVarContext all ; --- 32-bit uninstall --- SetRegView 32 ReadRegStr $R0 HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "QuietUninstallString" StrCmp $R0 "" done32 DetailPrint "Removing previous version (32-bit)..." ExecWait '$R0' done32: ; --- 64-bit uninstall --- ${If} ${RunningX64} SetRegView 64 ReadRegStr $R0 HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "QuietUninstallString" StrCmp $R0 "" done64 DetailPrint "Removing previous version (64-bit)..." ExecWait '$R0' done64: ${EndIf} FunctionEnd ; --- Running instance handling --- ; Cockatrice, Oracle and Servatrice must not be running while files are ; replaced or deleted. A still-running process holds locks on its .exe and ; Qt runtime DLLs, so a silent upgrade could otherwise end up with a mix of ; old and new Qt DLLs next to the new executable, failing with ; "The procedure entry point X could not be located in the dynamic link ; library ...Qt6Network.dll" on the next start. ; ; Processes are matched by image name AND by their executable path living ; under $INSTDIR, so unrelated processes that merely share an image name ; (e.g. the Oracle DB instance "oracle.exe") are never touched. ; usage: set $R2 to the base image name (without extension, e.g. "cockatrice", ; as accepted by Get-Process -Name), call this, result in $R0 ; (1 = running from $INSTDIR, 0 = not running) Function IsAppRunning nsExec::ExecToLog 'powershell -NoProfile -Command "Get-Process -Name $\'$R2$\' -ErrorAction SilentlyContinue | Where-Object { $$_.Path -like $\'$INSTDIR\*$\' } | Select-Object -First 1"' Pop $R0 ${If} $R0 = 0 StrCpy $R0 1 ${Else} StrCpy $R0 0 ${EndIf} FunctionEnd Function CloseMatchingApps ; gracefully ask every matching instance to close (sends WM_CLOSE) nsExec::ExecToLog 'powershell -NoProfile -Command "Get-Process -Name $\'$R2$\' -ErrorAction SilentlyContinue | Where-Object { $$_.Path -like $\'$INSTDIR\*$\' } | ForEach-Object { $$null = $$_.CloseMainWindow() }"' Pop $R3 FunctionEnd Function ForceCloseMatchingApps nsExec::ExecToLog 'powershell -NoProfile -Command "Get-Process -Name $\'$R2$\' -ErrorAction SilentlyContinue | Where-Object { $$_.Path -like $\'$INSTDIR\*$\' } | Stop-Process -Force -ErrorAction SilentlyContinue"' Pop $R3 FunctionEnd Function WaitForAppToClose ; usage: set $R1 to the display name (e.g. "cockatrice.exe") and $R2 to the ; base image name (e.g. "cockatrice") Call IsAppRunning ${If} $R0 = 0 Return ${EndIf} ${If} ${Silent} ; ask the application to close gracefully (WM_CLOSE), then wait for it to exit DetailPrint "Closing $R1 ..." Call CloseMatchingApps StrCpy $R8 0 ck_wait_loop: Sleep 500 IntOp $R8 $R8 + 1 Call IsAppRunning ${If} $R0 = 0 DetailPrint "$R1 closed." Return ${EndIf} ${If} $R8 < 60 Goto ck_wait_loop ${EndIf} ; give up waiting, force close DetailPrint "Force closing $R1 ..." Call ForceCloseMatchingApps Sleep 500 ${Else} ck_wait_prompt: MessageBox MB_RETRYCANCEL|MB_ICONEXCLAMATION|MB_DEFBUTTON1 \ "$R1 is still running.$\r$\n$\r$\nPlease close it, then click Retry.$\r$\nClick Cancel to abort." \ IDCANCEL ck_abort_install Call IsAppRunning ${If} $R0 = 0 Return ${EndIf} Goto ck_wait_prompt ck_abort_install: Abort ${EndIf} FunctionEnd Function EnsureAppsNotRunning StrCpy $R1 "cockatrice.exe" StrCpy $R2 "cockatrice" Call WaitForAppToClose StrCpy $R1 "oracle.exe" StrCpy $R2 "oracle" Call WaitForAppToClose StrCpy $R1 "servatrice.exe" StrCpy $R2 "servatrice" Call WaitForAppToClose FunctionEnd ; Uninstaller copies of the same routines (the uninstaller gets its own ; function set compiled in, it cannot call the installer functions). Function un.IsAppRunning nsExec::ExecToLog 'powershell -NoProfile -Command "Get-Process -Name $\'$R2$\' -ErrorAction SilentlyContinue | Where-Object { $$_.Path -like $\'$INSTDIR\*$\' } | Select-Object -First 1"' Pop $R0 ${If} $R0 = 0 StrCpy $R0 1 ${Else} StrCpy $R0 0 ${EndIf} FunctionEnd Function un.CloseMatchingApps nsExec::ExecToLog 'powershell -NoProfile -Command "Get-Process -Name $\'$R2$\' -ErrorAction SilentlyContinue | Where-Object { $$_.Path -like $\'$INSTDIR\*$\' } | ForEach-Object { $$null = $$_.CloseMainWindow() }"' Pop $R3 FunctionEnd Function un.ForceCloseMatchingApps nsExec::ExecToLog 'powershell -NoProfile -Command "Get-Process -Name $\'$R2$\' -ErrorAction SilentlyContinue | Where-Object { $$_.Path -like $\'$INSTDIR\*$\' } | Stop-Process -Force -ErrorAction SilentlyContinue"' Pop $R3 FunctionEnd Function un.WaitForAppToClose Call un.IsAppRunning ${If} $R0 = 0 Return ${EndIf} ${If} ${Silent} DetailPrint "Closing $R1 ..." Call un.CloseMatchingApps StrCpy $R8 0 un_ck_wait_loop: Sleep 500 IntOp $R8 $R8 + 1 Call un.IsAppRunning ${If} $R0 = 0 DetailPrint "$R1 closed." Return ${EndIf} ${If} $R8 < 60 Goto un_ck_wait_loop ${EndIf} DetailPrint "Force closing $R1 ..." Call un.ForceCloseMatchingApps Sleep 500 ${Else} un_ck_wait_prompt: MessageBox MB_RETRYCANCEL|MB_ICONEXCLAMATION|MB_DEFBUTTON1 \ "$R1 is still running.$\r$\n$\r$\nPlease close it, then click Retry.$\r$\nClick Cancel to abort." \ IDCANCEL un_ck_abort_install Call un.IsAppRunning ${If} $R0 = 0 Return ${EndIf} Goto un_ck_wait_prompt un_ck_abort_install: Abort ${EndIf} FunctionEnd Function un.EnsureAppsNotRunning StrCpy $R1 "cockatrice.exe" StrCpy $R2 "cockatrice" Call un.WaitForAppToClose StrCpy $R1 "oracle.exe" StrCpy $R2 "oracle" Call un.WaitForAppToClose StrCpy $R1 "servatrice.exe" StrCpy $R2 "servatrice" Call un.WaitForAppToClose FunctionEnd Function PortableModePageCreate ${If} $ReinstallMode = 1 Abort ${EndIf} Call SetModeDestinationFromInstdir ; If the user clicks BACK on the directory page we will remember their mode specific directory !insertmacro MUI_HEADER_TEXT "Install Mode" "Choose how you want to install Cockatrice." nsDialogs::Create 1018 Pop $0 ${NSD_CreateLabel} 0 10u 100% 24u "Select install mode:" Pop $0 ${NSD_CreateRadioButton} 30u 50u -30u 8u "Normal installation" Pop $1 ${NSD_CreateRadioButton} 30u 70u -30u 8u "Portable mode (all files in a single folder)" Pop $2 ${If} $PortableMode = 0 SendMessage $1 ${BM_SETCHECK} ${BST_CHECKED} 0 ${Else} SendMessage $2 ${BM_SETCHECK} ${BST_CHECKED} 0 ${EndIf} nsDialogs::Show FunctionEnd Function PortableModePageLeave ${NSD_GetState} $1 $0 ${If} $0 <> ${BST_UNCHECKED} StrCpy $PortableMode 0 StrCpy $InstDir $NormalDestDir Call RequireAdmin ${Else} StrCpy $PortableMode 1 StrCpy $InstDir $PortableDestDir ${EndIf} FunctionEnd Function componentsPagePre ${If} $ReinstallMode = 1 Return ${EndIf} ${If} $PortableMode = 0 SetShellVarContext all # uninstall 32bit version SetRegView 32 ReadRegStr $R0 HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "UninstallString" StrCmp $R0 "" done32 ${If} $ReinstallMode = 0 MessageBox MB_OKCANCEL|MB_ICONEXCLAMATION "A previous version of Cockatrice must be uninstalled before installing the new one." IDOK uninst32 Abort ${Else} Goto uninst32 ${EndIf} uninst32: ClearErrors ExecWait "$R0" done32: # uninstall 64bit version ${If} ${NSIS_IS_64_BIT} == 1 SetRegView 64 ReadRegStr $R0 HKLM "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "UninstallString" StrCmp $R0 "" done64 ${If} $ReinstallMode = 0 MessageBox MB_OKCANCEL|MB_ICONEXCLAMATION "A previous version of Cockatrice must be uninstalled before installing the new one." IDOK uninst64 Abort ${Else} Goto uninst64 ${EndIf} uninst64: ClearErrors ExecWait "$R0" done64: ${EndIf} ${Else} Abort ${EndIf} FunctionEnd Section "Application" SecApplication SetShellVarContext all SetOutPath "$INSTDIR" ${If} $PortableMode = 1 ${AndIf} ${FileExists} "$INSTDIR\portable.dat" ; upgrade portable mode RMDir /r "$INSTDIR\plugins" RMDir /r "$INSTDIR\sounds" RMDir /r "$INSTDIR\themes" RMDir /r "$INSTDIR\translations" Delete "$INSTDIR\uninstall.exe" Delete "$INSTDIR\cockatrice.exe" Delete "$INSTDIR\oracle.exe" Delete "$INSTDIR\servatrice.exe" Delete "$INSTDIR\Qt*.dll" Delete "$INSTDIR\libmysql.dll" Delete "$INSTDIR\icu*.dll" Delete "$INSTDIR\libeay32.dll" Delete "$INSTDIR\ssleay32.dll" Delete "$INSTDIR\qt.conf" Delete "$INSTDIR\qdebug.txt" Delete "$INSTDIR\servatrice.sql" Delete "$INSTDIR\servatrice.ini.example" Delete "$INSTDIR\zlib*.dll" RMDir "$INSTDIR" ${EndIf} ; Belt and braces: the old uninstaller may have already run in the /R path, so ; ensure no application instance is still holding file locks, then remove any ; runtime DLLs left over from older versions. A mismatched Qt/OpenSSL set next ; to the new executable is what causes "The procedure entry point X could not be ; located in the dynamic link library ...Qt6Network.dll" after an update. Call EnsureAppsNotRunning ${If} $PortableMode = 0 ${AndIf} ${FileExists} "$INSTDIR\cockatrice.exe" RMDir /r "$INSTDIR\Plugins" Delete "$INSTDIR\Qt*.dll" Delete "$INSTDIR\libcrypto*.dll" Delete "$INSTDIR\libssl*.dll" Delete "$INSTDIR\zlib*.dll" Delete "$INSTDIR\libmysql.dll" Delete "$INSTDIR\icu*.dll" Delete "$INSTDIR\libeay32.dll" Delete "$INSTDIR\ssleay32.dll" ${EndIf} @CPACK_NSIS_EXTRA_PREINSTALL_COMMANDS@ @CPACK_NSIS_FULL_INSTALL@ ${If} $PortableMode = 0 WriteUninstaller "$INSTDIR\uninstall.exe" ${GetSize} "$INSTDIR" "/S=0K" $0 $1 $2 IntFmt $0 "0x%08X" $0 ; Enable Windows User-Mode Dumps ; https://learn.microsoft.com/en-us/windows/win32/wer/collecting-user-mode-dumps WriteRegExpandStr HKLM "Software\Microsoft\Windows\Windows Error Reporting\LocalDumps\cockatrice.exe" "DumpFolder" "%LOCALAPPDATA%\CrashDumps\Cockatrice" WriteRegDWORD HKLM "Software\Microsoft\Windows\Windows Error Reporting\LocalDumps\cockatrice.exe" "DumpCount" "5" WriteRegDWORD HKLM "Software\Microsoft\Windows\Windows Error Reporting\LocalDumps\cockatrice.exe" "DumpType" "2" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "DisplayIcon" "$INSTDIR\cockatrice.exe" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "DisplayName" "Cockatrice" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "DisplayVersion" "@CPACK_PACKAGE_VERSION_MAJOR@.@CPACK_PACKAGE_VERSION_MINOR@.@CPACK_PACKAGE_VERSION_PATCH@" WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "EstimatedSize" "$0" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "InstallLocation" "$INSTDIR" WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "NoModify" "1" WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "NoRepair" "1" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "Publisher" "Cockatrice team" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "QuietUninstallString" "$\"$INSTDIR\uninstall.exe$\" /S" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "UninstallString" "$\"$INSTDIR\uninstall.exe$\"" WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "VersionMajor" "@CPACK_PACKAGE_VERSION_MAJOR@" WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" "VersionMinor" "@CPACK_PACKAGE_VERSION_MINOR@" IfFileExists "$INSTDIR\vc_redist.x86.exe" VcRedist86Exists PastVcRedist86Check VcRedist86Exists: ExecWait '"$INSTDIR\vc_redist.x86.exe" /passive /norestart' DetailPrint "Wait to ensure unlock of vc_redist file after installation..." Sleep 3000 Delete "$INSTDIR\vc_redist.x86.exe" PastVcRedist86Check: IfFileExists "$INSTDIR\vc_redist.x64.exe" VcRedist64Exists PastVcRedist64Check VcRedist64Exists: ExecWait '"$INSTDIR\vc_redist.x64.exe" /passive /norestart' DetailPrint "Sleep to ensure unlock of vc_redist file after installation..." Sleep 3000 Delete "$INSTDIR\vc_redist.x64.exe" PastVcRedist64Check: ${Else} ; Create the file the application uses to detect portable mode FileOpen $0 "$INSTDIR\portable.dat" w FileWrite $0 "PORTABLE" FileClose $0 ${EndIf} ${If} $ReinstallMode = 1 IfFileExists "$INSTDIR\cockatrice.exe" 0 +2 Exec '"$INSTDIR\cockatrice.exe"' ${EndIf} SectionEnd Section "Start menu item" SecStartMenu ${If} $PortableMode = 0 SetShellVarContext all createDirectory "$SMPROGRAMS\Cockatrice" createShortCut "$SMPROGRAMS\Cockatrice\Cockatrice.lnk" "$INSTDIR\cockatrice.exe" createShortCut "$SMPROGRAMS\Cockatrice\Oracle.lnk" "$INSTDIR\oracle.exe" createShortCut "$SMPROGRAMS\Cockatrice\Servatrice.lnk" "$INSTDIR\servatrice.exe" ${EndIf} SectionEnd Section "un.Application" UnSecApplication SetShellVarContext all ; Remove the entire application directory so any file that is not part of ; the installed payload (e.g. build-tree artifacts such as *.dir folders, ; *_autogen and *.tlog files from a build) cannot survive between an ; uninstall and a fresh reinstall. RMDir /r "$INSTDIR" RMDir /r "$SMPROGRAMS\Cockatrice" DeleteRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\Cockatrice" SectionEnd ; unselected because it is /o Section /o "un.Configurations, decks, cards, pics" UnSecConfiguration SetShellVarContext current DeleteRegKey HKCU "Software\Cockatrice" RMDir /r "$LOCALAPPDATA\Cockatrice" SectionEnd LangString DESC_SecApplication ${LANG_ENGLISH} "Cockatrice program files" LangString DESC_SecStartMenu ${LANG_ENGLISH} "Create start menu items for Cockatrice and Oracle." !insertmacro MUI_FUNCTION_DESCRIPTION_BEGIN !insertmacro MUI_DESCRIPTION_TEXT ${SecApplication} $(DESC_SecApplication) !insertmacro MUI_DESCRIPTION_TEXT ${SecStartMenu} $(DESC_SecStartMenu) !insertmacro MUI_FUNCTION_DESCRIPTION_END LangString DESC_UnSecApplication ${LANG_ENGLISH} "Cockatrice program files and start menu items" LangString DESC_UnSecConfiguration ${LANG_ENGLISH} "Configurations, decks, card database, pictures" !insertmacro MUI_UNFUNCTION_DESCRIPTION_BEGIN !insertmacro MUI_DESCRIPTION_TEXT ${UnSecApplication} $(DESC_UnSecApplication) !insertmacro MUI_DESCRIPTION_TEXT ${UnSecConfiguration} $(DESC_UnSecConfiguration) !insertmacro MUI_UNFUNCTION_DESCRIPTION_END