mirror of
https://github.com/coder/coder.git
synced 2025-07-09 11:45:56 +00:00
The path.nsh script in the NSIS installer provided methods for adding paths to the PATH and removing them. It would do this by reading the current PATH value from the registry, adding the new value (if it doesn't exist) and then writing it to the registry. Unfortunately, it would read from the user's PATH and write the updated result to the system PATH, which would remove important PATH entries like the following in the process: - C:\Windows\System32 - C:\Windows - C:\Windows\System32\wbem - C:\Windows\System32\WindowsPowerShell\v1.0 - C:\Windows\System32\OpenSSH - C:\Program Files\NVIDIA Corporation\NVIDIA NvDLISR - C:\Program Files (x86)\NVIDIA Corporation\PhysX\Common and would copy all user environment variables in their place. The variables listed above were the ones missing from my machine when I compared with a friend's machine. Recommended course of action for affected users: 1. Add the paths listed above to your system PATH if they aren't there already and exist on your system. 2. Remove any paths that are in your user's PATH from your system PATH. The existing installers for the last couple of versions of Coder have been yanked from GitHub releases and this message will be included in the release notes for the next patch. Thanks to @cmor for finding and reporting this bug in #5240.
196 lines
4.4 KiB
NSIS
196 lines
4.4 KiB
NSIS
# PATH utilities. Taken from:
|
|
# https://www.smartmontools.org/browser/trunk/smartmontools/os_win32/installer.nsi?rev=5310#L689
|
|
|
|
; os_win32/installer.nsi - smartmontools install NSIS script
|
|
;
|
|
; Home page of code is: https://www.smartmontools.org
|
|
;
|
|
; Copyright (C) 2006-22 Christian Franke
|
|
;
|
|
; SPDX-License-Identifier: GPL-2.0-or-later
|
|
|
|
|
|
;--------------------------------------------------------------------
|
|
; Path functions
|
|
;
|
|
; Based on example from:
|
|
; http://nsis.sourceforge.net/Path_Manipulation
|
|
;
|
|
|
|
|
|
!include "WinMessages.nsh"
|
|
|
|
; Registry Entry for system environment (NT4,2000,XP)
|
|
!define Environ 'HKLM "SYSTEM\CurrentControlSet\Control\Session Manager\Environment"'
|
|
|
|
|
|
; AddToPath - Appends dir to system PATH
|
|
; (does not work on Win9x/ME)
|
|
;
|
|
; Usage:
|
|
; Push "dir"
|
|
; Call AddToPath
|
|
|
|
Function AddToPath
|
|
Exch $0
|
|
Push $1
|
|
Push $2
|
|
Push $3
|
|
Push $4
|
|
|
|
; NSIS ReadRegStr returns empty string on string overflow
|
|
; Native calls are used here to check actual length of PATH
|
|
|
|
; $4 = RegOpenKey(HKEY_CURRENT_USER, "Environment", &$3)
|
|
System::Call "advapi32::RegOpenKey(i 0x80000002, t'SYSTEM\CurrentControlSet\Control\Session Manager\Environment', *i.r3) i.r4"
|
|
IntCmp $4 0 0 done done
|
|
; $4 = RegQueryValueEx($3, "PATH", (DWORD*)0, (DWORD*)0, &$1, ($2=NSIS_MAX_STRLEN, &$2))
|
|
; RegCloseKey($3)
|
|
System::Call "advapi32::RegQueryValueEx(i $3, t'PATH', i 0, i 0, t.r1, *i ${NSIS_MAX_STRLEN} r2) i.r4"
|
|
System::Call "advapi32::RegCloseKey(i $3)"
|
|
|
|
${If} $4 = 234 ; ERROR_MORE_DATA
|
|
DetailPrint "AddToPath: original length $2 > ${NSIS_MAX_STRLEN}"
|
|
MessageBox MB_OK "PATH not updated, original length $2 > ${NSIS_MAX_STRLEN}" /SD IDOK
|
|
Goto done
|
|
${EndIf}
|
|
|
|
${If} $4 <> 0 ; NO_ERROR
|
|
${If} $4 <> 2 ; ERROR_FILE_NOT_FOUND
|
|
DetailPrint "AddToPath: unexpected error code $4"
|
|
Goto done
|
|
${EndIf}
|
|
StrCpy $1 ""
|
|
${EndIf}
|
|
|
|
; Check if already in PATH
|
|
Push "$1;"
|
|
Push "$0;"
|
|
Call StrStr
|
|
Pop $2
|
|
StrCmp $2 "" 0 done
|
|
Push "$1;"
|
|
Push "$0\;"
|
|
Call StrStr
|
|
Pop $2
|
|
StrCmp $2 "" 0 done
|
|
|
|
; Prevent NSIS string overflow
|
|
StrLen $2 $0
|
|
StrLen $3 $1
|
|
IntOp $2 $2 + $3
|
|
IntOp $2 $2 + 2 ; $2 = strlen(dir) + strlen(PATH) + sizeof(";")
|
|
${If} $2 > ${NSIS_MAX_STRLEN}
|
|
DetailPrint "AddToPath: new length $2 > ${NSIS_MAX_STRLEN}"
|
|
MessageBox MB_OK "PATH not updated, new length $2 > ${NSIS_MAX_STRLEN}." /SD IDOK
|
|
Goto done
|
|
${EndIf}
|
|
|
|
; Append dir to PATH
|
|
DetailPrint "Add to PATH: $0"
|
|
StrCpy $2 $1 1 -1
|
|
${If} $2 == ";"
|
|
StrCpy $1 $1 -1 ; remove trailing ';'
|
|
${EndIf}
|
|
${If} $1 != "" ; no leading ';'
|
|
StrCpy $0 "$1;$0"
|
|
${EndIf}
|
|
WriteRegExpandStr ${Environ} "PATH" $0
|
|
SendMessage ${HWND_BROADCAST} ${WM_WININICHANGE} 0 "STR:Environment" /TIMEOUT=5000
|
|
|
|
done:
|
|
Pop $4
|
|
Pop $3
|
|
Pop $2
|
|
Pop $1
|
|
Pop $0
|
|
FunctionEnd
|
|
|
|
|
|
; RemoveFromPath - Removes dir from system PATH
|
|
;
|
|
; Usage:
|
|
; Push "dir"
|
|
; Call RemoveFromPath
|
|
|
|
Function un.RemoveFromPath
|
|
Exch $0
|
|
Push $1
|
|
Push $2
|
|
Push $3
|
|
Push $4
|
|
Push $5
|
|
Push $6
|
|
|
|
ReadRegStr $1 ${Environ} "PATH"
|
|
StrCpy $5 $1 1 -1
|
|
${If} $5 != ";"
|
|
StrCpy $1 "$1;" ; ensure trailing ';'
|
|
${EndIf}
|
|
Push $1
|
|
Push "$0;"
|
|
Call un.StrStr
|
|
Pop $2 ; pos of our dir
|
|
StrCmp $2 "" done
|
|
|
|
DetailPrint "Remove from PATH: $0"
|
|
StrLen $3 "$0;"
|
|
StrLen $4 $2
|
|
StrCpy $5 $1 -$4 ; $5 is now the part before the path to remove
|
|
StrCpy $6 $2 "" $3 ; $6 is now the part after the path to remove
|
|
StrCpy $3 "$5$6"
|
|
StrCpy $5 $3 1 -1
|
|
${If} $5 == ";"
|
|
StrCpy $3 $3 -1 ; remove trailing ';'
|
|
${EndIf}
|
|
WriteRegExpandStr ${Environ} "PATH" $3
|
|
SendMessage ${HWND_BROADCAST} ${WM_WININICHANGE} 0 "STR:Environment" /TIMEOUT=5000
|
|
|
|
done:
|
|
Pop $6
|
|
Pop $5
|
|
Pop $4
|
|
Pop $3
|
|
Pop $2
|
|
Pop $1
|
|
Pop $0
|
|
FunctionEnd
|
|
|
|
|
|
; StrStr - find substring in a string
|
|
;
|
|
; Usage:
|
|
; Push "this is some string"
|
|
; Push "some"
|
|
; Call StrStr
|
|
; Pop $0 ; "some string"
|
|
|
|
!macro StrStr un
|
|
Function ${un}StrStr
|
|
Exch $R1 ; $R1=substring, stack=[old$R1,string,...]
|
|
Exch ; stack=[string,old$R1,...]
|
|
Exch $R2 ; $R2=string, stack=[old$R2,old$R1,...]
|
|
Push $R3
|
|
Push $R4
|
|
Push $R5
|
|
StrLen $R3 $R1
|
|
StrCpy $R4 0
|
|
; $R1=substring, $R2=string, $R3=strlen(substring)
|
|
; $R4=count, $R5=tmp
|
|
${Do}
|
|
StrCpy $R5 $R2 $R3 $R4
|
|
${IfThen} $R5 == $R1 ${|} ${ExitDo} ${|}
|
|
${IfThen} $R5 == "" ${|} ${ExitDo} ${|}
|
|
IntOp $R4 $R4 + 1
|
|
${Loop}
|
|
StrCpy $R1 $R2 "" $R4
|
|
Pop $R5
|
|
Pop $R4
|
|
Pop $R3
|
|
Pop $R2
|
|
Exch $R1 ; $R1=old$R1, stack=[result,...]
|
|
FunctionEnd
|
|
!macroend
|
|
!insertmacro StrStr ""
|
|
!insertmacro StrStr "un."
|