Search code examples
c#windowsinstallationnsiswindowsversion

How to detect windows 7 in NSIS


Right now we are using windows form. NSIS is using for windows form installation. But i need to block installation in windows 7 o.s. How to do that? I am using the below code.

; Script generated by the HM NIS Edit Script Wizard.

; HM NIS Edit Wizard helper defines
!define PRODUCT_TYPE "Home"    ; Home/Clinic ------
!define CONFIG_TYPE "Prod"    ; Release/Local/Devl/Devl_Test/Demo/Test/Prod ------
!define PRODUCT_NAME "nQ Medical ${PRODUCT_TYPE} Keyboard"
!define PRODUCT_VERSION "1.2.0"
!define PRODUCT_PUBLISHER "nQ Medical Inc."
!define PRODUCT_WEB_SITE "https://platform.nq-medical.com"
!define PRODUCT_DIR_REGKEY "Software\Microsoft\Windows\CurrentVersion\App Paths\${APP_NAME}"
!define PRODUCT_UNINST_KEY "Software\Microsoft\Windows\CurrentVersion\Uninstall\${PRODUCT_NAME}"
!define PRODUCT_UNINST_ROOT_KEY "HKLM"
!define APP_NAME "nQKeyboard.exe"

; MUI 1.67 compatible ------
!include "MUI.nsh"
; MUI Settings
!define MUI_ABORTWARNING
!define MUI_ICON "nQKeyboard\iconNQ.ico"
!define MUI_UNICON "${NSISDIR}\Contrib\Graphics\Icons\modern-uninstall.ico"

RequestExecutionLevel admin

; Welcome page
!insertmacro MUI_PAGE_WELCOME
; License page
!insertmacro MUI_PAGE_LICENSE "nQKeyboard\bin\${CONFIG_TYPE}\EULA.txt"
; Directory page
!insertmacro MUI_PAGE_DIRECTORY
; Instfiles page
!insertmacro MUI_PAGE_INSTFILES
; Finish page
!define MUI_FINISHPAGE_RUN "$INSTDIR\${APP_NAME}"
!insertmacro MUI_PAGE_FINISH
; Uninstaller pages
!insertmacro MUI_UNPAGE_INSTFILES
; Language files
!insertmacro MUI_LANGUAGE "English"
; MUI end ------

Name "${PRODUCT_NAME}"
;Currently deploys the installer file to a 'Published' sub-directory in the 'Solution' directory
OutFile "Published\nQ Medical ${PRODUCT_TYPE} Keyboard.exe"
InstallDir "$PROGRAMFILES\nQ Medical Keyboard"
InstallDirRegKey HKLM "${PRODUCT_DIR_REGKEY}" ""
ShowInstDetails show
ShowUnInstDetails show

Section "MainSection" SEC01
  ; Kill the running application
  ExecWait "TaskKill /IM ${APP_NAME} /F"
  SetOutPath "$INSTDIR"
  SetOverwrite try
  File "nQKeyboard\bin\${CONFIG_TYPE}\iconNQ.ico"
  File "nQKeyboard\bin\${CONFIG_TYPE}\Newtonsoft.Json.dll"
  File "nQKeyboard\bin\${CONFIG_TYPE}\RestSharp.dll"
  File "nQKeyboard\bin\${CONFIG_TYPE}\RestSharp.Serializers.NewtonsoftJson.dll"
  File "nQKeyboard\bin\${CONFIG_TYPE}\GraphQL.Client.dll"
  File "nQKeyboard\bin\${CONFIG_TYPE}\GraphQL.Common.dll"
  File "nQKeyboard\bin\${CONFIG_TYPE}\EULA.txt"
  File "nQKeyboard\bin\${CONFIG_TYPE}\${APP_NAME}"
  CreateDirectory "$SMPROGRAMS\nQ Medical Keyboard"
  CreateShortCut "$SMPROGRAMS\nQ Medical Keyboard\nQ Medical Keyboard.lnk" "$INSTDIR\${APP_NAME}"
  CreateShortCut "$DESKTOP\nQ Medical Keyboard.lnk" "$INSTDIR\${APP_NAME}"
  File "nQKeyboard\bin\${CONFIG_TYPE}\${APP_NAME}.config"
SectionEnd.

So How to add code section? ie; if windows 7 is o.s. then installation not takes place. show error message when execute script. how to do that?


Solution

  • NSIS provides the WinVer.nsh header file that helps you detect various Windows versions.

    Version detection might seem simple at first but it is easy to make mistakes and your question does not really provide enough information to write a definitive answer!

    The naïve answer to your question is

    !include WinVer.nsh
    
    Function .onInit
    ${If} ${IsWin7}
        MessageBox MB_ICONSTOP "Windows version blah blah!"
        SetErrorLevel 1150 ; ERROR_OLD_WIN_VERSION
        Quit
    ${EndIf}
    FunctionEnd
    

    This seems fine at first but assuming there is some technical reason why your application cannot run on Windows 7 then you probably also need to block Server 2008 R2 because it is basically the same version of Windows:

    ${If} ${IsWin7}
    ${OrIf} ${IsWin2008R2}
      ...
    

    Most of the time you have some minimum version of Windows that you support and you really should block anything older. The best way to do this is to make sure that you are on a version you support:

    !include WinVer.nsh
    
    Function .onInit
    ${IfNot} ${AtLeastWin8}
        MessageBox MB_ICONSTOP "Windows version blah blah!"
        SetErrorLevel 1150 ; ERROR_OLD_WIN_VERSION
        Quit
    ${EndIf}
    FunctionEnd
    

    If you are really familiar with the various Windows build numbers you can also check that directly:

    ${IfNot} ${AtLeastBuild} 9200
      ...