; GetParent ; input, top of stack (e.g. C:\Program Files\Poop) ; output, top of stack (replaces, with e.g. C:\Program Files) ; modifies no other variables. ; ; Usage: ; Push "C:\Program Files\Directory\Whatever" ; Call GetParent ; Pop $R0 ; ; at this point $R0 will equal "C:\Program Files\Directory" Function GetParent Exch $R0 Push $R1 Push $R2 Push $R3 StrCpy $R1 0 StrLen $R2 $R0 loop: IntOp $R1 $R1 + 1 IntCmp $R1 $R2 get 0 get StrCpy $R3 $R0 1 -$R1 StrCmp $R3 "\" get Goto loop get: StrCpy $R0 $R0 -$R1 Pop $R3 Pop $R2 Pop $R1 Exch $R0 FunctionEnd
; TrimNewlines ; input, top of stack (e.g. whatever$\r$\n) ; output, top of stack (replaces, with e.g. whatever) ; modifies no other variables. Function TrimNewlines Exch $R0 Push $R1 Push $R2 StrCpy $R1 0 loop: IntOp $R1 $R1 - 1 StrCpy $R2 $R0 1 $R1 StrCmp $R2 "$\r" loop StrCmp $R2 "$\n" loop IntOp $R1 $R1 + 1 IntCmp $R1 0 no_trim_needed StrCpy $R0 $R0 $R1 no_trim_needed: Pop $R2 Pop $R1 Exch $R0 FunctionEnd
; GetParameters ; input, none ; output, top of stack (replaces, with e.g. whatever) ; modifies no other variables. Function GetParameters Push $R0 Push $R1 Push $R2 Push $R3 StrCpy $R2 1 StrLen $R3 $CMDLINE ;Check for quote or space StrCpy $R0 $CMDLINE $R2 StrCmp $R0 '"' 0 +3 StrCpy $R1 '"' Goto loop StrCpy $R1 " " loop: IntOp $R2 $R2 + 1 StrCpy $R0 $CMDLINE 1 $R2 StrCmp $R0 $R1 get StrCmp $R2 $R3 get Goto loop get: IntOp $R2 $R2 + 1 StrCpy $R0 $CMDLINE 1 $R2 StrCmp $R0 " " get StrCpy $R0 $CMDLINE "" $R2 Pop $R3 Pop $R2 Pop $R1 Exch $R0 FunctionEnd
; StrStr ; input, top of stack = string to search for ; top of stack-1 = string to search in ; output, top of stack (replaces with the portion of the string remaining) ; modifies no other variables. ; ; Usage: ; Push "this is a long ass string" ; Push "ass" ; Call StrStr ; Pop $R0 ; ($R0 at this point is "ass string") Function StrStr Exch $R1 ; st=haystack,old$R1, $R1=needle Exch ; st=old$R1,haystack Exch $R2 ; st=old$R1,old$R2, $R2=haystack Push $R3 Push $R4 Push $R5 StrLen $R3 $R1 StrCpy $R4 0 ; $R1=needle ; $R2=haystack ; $R3=len(needle) ; $R4=cnt ; $R5=tmp loop: StrCpy $R5 $R2 $R3 $R4 StrCmp $R5 $R1 done StrCmp $R5 "" done IntOp $R4 $R4 + 1 Goto loop done: StrCpy $R1 $R2 "" $R4 Pop $R5 Pop $R4 Pop $R3 Pop $R2 Exch $R1 FunctionEnd
; GetWindowsVersion ; ; Based on Yazno's function, http://yazno.tripod.com/powerpimpit/ ; Updated by Joost Verburg ; ; Returns on top of stack ; ; Windows Version (95, 98, ME, NT x.x, 2000, XP, 2003) ; or ; '' (Unknown Windows Version) ; ; Usage: ; Call GetWindowsVersion ; Pop $R0 ; ; at this point $R0 is "NT 4.0" or whatnot Function GetWindowsVersion Push $R0 Push $R1 ReadRegStr $R0 HKLM \ "SOFTWARE\Microsoft\Windows NT\CurrentVersion" CurrentVersion IfErrors 0 lbl_winnt ; we are not NT ReadRegStr $R0 HKLM \ "SOFTWARE\Microsoft\Windows\CurrentVersion" VersionNumber StrCpy $R1 $R0 1 StrCmp $R1 '4' 0 lbl_error StrCpy $R1 $R0 3 StrCmp $R1 '4.0' lbl_win32_95 StrCmp $R1 '4.9' lbl_win32_ME lbl_win32_98 lbl_win32_95: StrCpy $R0 '95' Goto lbl_done lbl_win32_98: StrCpy $R0 '98' Goto lbl_done lbl_win32_ME: StrCpy $R0 'ME' Goto lbl_done lbl_winnt: StrCpy $R1 $R0 1 StrCmp $R1 '3' lbl_winnt_x StrCmp $R1 '4' lbl_winnt_x StrCpy $R1 $R0 3 StrCmp $R1 '5.0' lbl_winnt_2000 StrCmp $R1 '5.1' lbl_winnt_XP StrCmp $R1 '5.2' lbl_winnt_2003 lbl_error lbl_winnt_x: StrCpy $R0 "NT $R0" 6 Goto lbl_done lbl_winnt_2000: Strcpy $R0 '2000' Goto lbl_done lbl_winnt_XP: Strcpy $R0 'XP' Goto lbl_done lbl_winnt_2003: Strcpy $R0 '2003' Goto lbl_done lbl_error: Strcpy $R0 '' lbl_done: Pop $R1 Exch $R0 FunctionEnd
; GetIEVersion ; ; Based on Yazno's function, http://yazno.tripod.com/powerpimpit/ ; Returns on top of stack ; 1-6 (Installed IE Version) ; or ; '' (IE is not installed) ; ; Usage: ; Call GetIEVersion ; Pop $R0 ; ; at this point $R0 is "5" or whatnot Function GetIEVersion Push $R0 ClearErrors ReadRegStr $R0 HKLM "Software\Microsoft\Internet Explorer" "Version" IfErrors lbl_123 lbl_456 lbl_456: ; ie 4+ Strcpy $R0 $R0 1 Goto lbl_done lbl_123: ; older ie version ClearErrors ReadRegStr $R0 HKLM "Software\Microsoft\Internet Explorer" "IVer" IfErrors lbl_error StrCpy $R0 $R0 3 StrCmp $R0 '100' lbl_ie1 StrCmp $R0 '101' lbl_ie2 StrCmp $R0 '102' lbl_ie2 StrCpy $R0 '3' ; default to ie3 if not 100, 101, or 102. Goto lbl_done lbl_ie1: StrCpy $R0 '1' Goto lbl_done lbl_ie2: StrCpy $R0 '2' Goto lbl_done lbl_error: StrCpy $R0 '' lbl_done: Exch $R0 FunctionEnd
; IsDotNETInstalled ; ; Usage: ; Call IsDotNETInstalled ; Pop $0 ; StrCmp $0 1 found.NETFramework no.NETFramework Function IsDotNETInstalled Push $0 Push $1 Push $2 Push $3 Push $4 ReadRegStr $4 HKEY_LOCAL_MACHINE \ "Software\Microsoft\.NETFramework" "InstallRoot" # remove trailing back slash Push $4 Exch $EXEDIR Exch $EXEDIR Pop $4 # if the root directory doesn't exist .NET is not installed IfFileExists $4 0 noDotNET StrCpy $0 0 EnumStart: EnumRegKey $2 HKEY_LOCAL_MACHINE \ "Software\Microsoft\.NETFramework\Policy" $0 IntOp $0 $0 + 1 StrCmp $2 "" noDotNET StrCpy $1 0 EnumPolicy: EnumRegValue $3 HKEY_LOCAL_MACHINE \ "Software\Microsoft\.NETFramework\Policy\$2" $1 IntOp $1 $1 + 1 StrCmp $3 "" EnumStart IfFileExists "$4\$2.$3" foundDotNET EnumPolicy noDotNET: StrCpy $0 0 Goto done foundDotNET: StrCpy $0 1 done: Pop $4 Pop $3 Pop $2 Pop $1 Exch $0 FunctionEnd
; IsFlashInstalled ; ; By Yazno, http://yazno.tripod.com/powerpimpit/ ; Returns on top of stack ; 0 (Flash is not installed) ; or ; 1 (Flash is installed) ; ; Usage: ; Call IsFlashInstalled ; Pop $R0 ; ; $R0 at this point is "1" or "0" Function IsFlashInstalled Push $R0 ClearErrors ReadRegStr $R0 HKCR "CLSID\{D27CDB6E-AE6D-11cf-96B8-444553540000}" "" IfErrors lbl_na StrCpy $R0 1 Goto lbl_end lbl_na: StrCpy $R0 0 lbl_end: Exch $R0 FunctionEnd
; AddSharedDLL ; ; Increments a shared DLLs reference count. ; Use by passing one item on the stack (the full path of the DLL). ; ; Usage: ; Push $SYSDIR\myDll.dll ; Call AddSharedDLL ; Function AddSharedDLL Exch $R1 Push $R0 ReadRegDword $R0 HKLM Software\Microsoft\Windows\CurrentVersion\SharedDLLs $R1 IntOp $R0 $R0 + 1 WriteRegDWORD HKLM Software\Microsoft\Windows\CurrentVersion\SharedDLLs $R1 $R0 Pop $R0 Pop $R1 FunctionEnd
; un.RemoveSharedDLL ; ; Decrements a shared DLLs reference count, and removes if necessary. ; Use by passing one item on the stack (the full path of the DLL). ; Note: for use in the main installer (not the uninstaller), rename the ; function to RemoveSharedDLL. ; ; Usage: ; Push $SYSDIR\myDll.dll ; Call un.RemoveSharedDLL ; Function un.RemoveSharedDLL Exch $R1 Push $R0 ReadRegDword $R0 HKLM Software\Microsoft\Windows\CurrentVersion\SharedDLLs $R1 StrCmp $R0 "" remove IntOp $R0 $R0 - 1 IntCmp $R0 0 rk rk uk rk: DeleteRegValue HKLM Software\Microsoft\Windows\CurrentVersion\SharedDLLs $R1 goto Remove uk: WriteRegDWORD HKLM Software\Microsoft\Windows\CurrentVersion\SharedDLLs $R1 $R0 Goto noremove remove: Delete /REBOOTOK $R1 noremove: Pop $R0 Pop $R1 FunctionEnd
There is also a copy of this macro in the Include folder, so you only have to include UpgradeDLL.nsh to use it.
; Macro - Upgrade DLL File ; Written by Joost Verburg ; ------------------------ ; ; Parameters: ; LOCALFILE - Location of the new DLL file (on the compiler system) ; DESTFILE - Location of the DLL file that should be upgraded (on the user's system) ; TEMPBASEDIR - Directory on the user's system to store a temporary file when the system has ; to be rebooted. ; For Win9x support, this should be on the same volume as the DESTFILE! ; The Windows temp directory could be located on any volume, so you cannot use ; this directory. ; ; Define UPGRADEDLL_NOREGISTER if you want to upgrade a DLL that does not have to be registered. ; ; Note: If you want to support Win9x, you can only use short filenames (8.3). ; ; Example of usage: ; !insertmacro UpgradeDLL "dllname.dll" "$SYSDIR\dllname.dll" "$SYSDIR" ; !macro UpgradeDLL LOCALFILE DESTFILE TEMPBASEDIR Push $R0 Push $R1 Push $R2 Push $R3 Push $R4 Push $R5 ;------------------------ ;Unique number for labels !define UPGRADEDLL_UNIQUE ${__LINE__} ;------------------------ ;Copy the parameters used on run-time to a variable ;This allows the usage of variables as paramter StrCpy $R4 "${DESTFILE}" StrCpy $R5 "${TEMPBASEDIR}" ;------------------------ ;Check file and version IfFileExists $R4 0 upgradedll.copy_${UPGRADEDLL_UNIQUE} ClearErrors GetDLLVersionLocal "${LOCALFILE}" $R0 $R1 GetDLLVersion $R4 $R2 $R3 IfErrors upgradedll.upgrade_${UPGRADEDLL_UNIQUE} IntCmpU $R0 $R2 0 upgradedll.done_${UPGRADEDLL_UNIQUE} upgradedll.upgrade_${UPGRADEDLL_UNIQUE} IntCmpU $R1 $R3 upgradedll.done_${UPGRADEDLL_UNIQUE} upgradedll.done_${UPGRADEDLL_UNIQUE} \ upgradedll.upgrade_${UPGRADEDLL_UNIQUE} ;------------------------ ;Let's upgrade the DLL! SetOverwrite try upgradedll.upgrade_${UPGRADEDLL_UNIQUE}: !ifndef UPGRADEDLL_NOREGISTER ;Unregister the DLL UnRegDLL $R4 !endif ;------------------------ ;Try to copy the DLL directly ClearErrors StrCpy $R0 $R4 Call :upgradedll.file_${UPGRADEDLL_UNIQUE} IfErrors 0 upgradedll.noreboot_${UPGRADEDLL_UNIQUE} ;------------------------ ;DLL is in use. Copy it to a temp file and Rename it on reboot. GetTempFileName $R0 $R5 Call :upgradedll.file_${UPGRADEDLL_UNIQUE} Rename /REBOOTOK $R0 $R4 ;------------------------ ;Register the DLL on reboot !ifndef UPGRADEDLL_NOREGISTER WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\RunOnce" \ "Register $R4" '"$SYSDIR\rundll32.exe" "$R4",DllRegisterServer' !endif Goto upgradedll.done_${UPGRADEDLL_UNIQUE} ;------------------------ ;DLL does not exist - just extract upgradedll.copy_${UPGRADEDLL_UNIQUE}: StrCpy $R0 $R4 Call :upgradedll.file_${UPGRADEDLL_UNIQUE} ;------------------------ ;Register the DLL upgradedll.noreboot_${UPGRADEDLL_UNIQUE}: !ifndef UPGRADEDLL_NOREGISTER RegDLL $R4 !endif ;------------------------ ;Done upgradedll.done_${UPGRADEDLL_UNIQUE}: Pop $R5 Pop $R4 Pop $R3 Pop $R2 Pop $R1 Pop $R0 ;------------------------ ;End Goto upgradedll.end_${UPGRADEDLL_UNIQUE} ;------------------------ ;Called to extract the DLL upgradedll.file_${UPGRADEDLL_UNIQUE}: File /oname=$R0 "${LOCALFILE}" Return upgradedll.end_${UPGRADEDLL_UNIQUE}: ;------------------------ ;Restore settings SetOverwrite lastused !undef UPGRADEDLL_UNIQUE !macroend
; ConnectInternet (uses Dialer plugin) ; Written by Joost Verburg ; ; This function attempts to make a connection to the internet if there is no ; connection available. If you are not sure that a system using the installer ; has an active internet connection, call this function before downloading ; files with NSISdl. ; ; The function requires Internet Explorer 3, but asks to connect manually if ; IE3 is not installed. Function ConnectInternet Push $R0 ClearErrors Dialer::AttemptConnect IfErrors noie3 Pop $R0 StrCmp $R0 "online" connected MessageBox MB_OK|MB_ICONSTOP "Cannot connect to the internet." Quit ;This will quit the installer. You might want to add your own error handling. noie3: ; IE3 not installed MessageBox MB_OK|MB_ICONINFORMATION "Please connect to the internet now." connected: Pop $R0 FunctionEnd
You can find more useful functions at the NSIS Archive, the NSIS forum and NSIS development page.