Old 1st February 2008, 11:47   #1
Barkruk
Junior Member
 
Barkruk's Avatar
 
Join Date: Feb 2008
Location: The Netherlands
Posts: 5
Summary of files in use

I want to switch from InstallShield to NSIS, but I have one problem;

With InstallShield it is possible to check witch files are in use en show them (see attachment).

I know I can do this also in NSIS with the following code:

Push $R0
ClearErrors
FileOpen
$R0 "file.ext" r
FileClose $R0
IfErrors 0 +2
DetailPrint "file.ext is locked!"
Pop $R0


But with this piece of code I have to specify every single file.

Because the monthly update of our program contains every time much updated, but also new files, I want to check for locked files by specifying only the installdir. Likewise how I install them:

SetOutPath $INSTDIR
File /r "muchfiles\*.*"


How can I make this possible?
Attached Images
File Type: png filesinuse.png (22.9 KB, 181 views)
Barkruk is offline   Reply With Quote
Old 1st February 2008, 13:57   #2
Afrow UK
Moderator
 
Afrow UK's Avatar
 
Join Date: Nov 2002
Location: Surrey, England
Posts: 8,434
Use the LockedList plug-in for an advanced solution, otherwise you can attempt to rename the files which will result in the error flag being set.

Stu
Afrow UK is offline   Reply With Quote
Old 4th February 2008, 10:17   #3
Barkruk
Junior Member
 
Barkruk's Avatar
 
Join Date: Feb 2008
Location: The Netherlands
Posts: 5
I almost have what I want. But for some reason my ErrorFlag is set also when no files are in use. What is wrong?

To test the code below change the INSTDIR in the MAIN section.
code:
Name "Test"
Outfile test.exe
ShowInstDetails show

!include LogicLib.nsh

Function CheckFilesInUse
Recheck:
ClearErrors
FindFirst $0 $1 "$INSTDIR\*.*"
Loop:
StrCmp $1 "" Done
StrCmp $1 "." IsDir
StrCmp $1 ".." IsDir
IfFileExists "$INSTDIR\$1\*.*" IsDir
Push $R0
ClearErrors
FileOpen $R0 "$INSTDIR\$1" a
FileClose $R0
IfErrors 0 Next
DetailPrint "$INSTDIR\$1 is is use."
Pop $R0
Next:
FindNext $0 $1
Goto Loop
IsDir:
ClearErrors
Goto Next
Done:
IfErrors 0 Finish
DetailPrint "$1"
MessageBox MB_RETRYCANCEL "One or more files are in use.\
Close them and retry" IDRETRY Retry
DetailPrint "- Aborted."
Abort
Retry:
DetailPrint "- Retry:"
Goto Recheck
Finish:
DetailPrint "Congrats, no files in use here."
FunctionEnd

Section "Main"
StrCpy $INSTDIR "C:\"
Call CheckFilesInUse
SectionEnd

Barkruk is offline   Reply With Quote
Old 4th February 2008, 15:52   #4
Animaether
Major Dude
 
Join Date: Jun 2001
Posts: 1,173
Quote:
Originally posted by Barkruk
[B]I almost have what I want. But for some reason my ErrorFlag is set also when no files are in use. What is wrong?
I think it's in here:
code:

ClearErrors
Goto Next


You clear the errors, then you go to the Next label. This runs the code:
code:

Next:
FindNext $0 $1
Goto Loop


If no further file is found, the error flag is set.
( "the search is completed (there are no more files), filename_output is set to empty, and the error flag is set." )

You check for this empty string after the Loop tag:
code:

Loop:
StrCmp $1 "" Done



And jump to the Done tag, which is followed by a check for Errors.
code:

Done:
IfErrors 0 Finish



Whoops?
Animaether is offline   Reply With Quote
Old 7th February 2008, 21:53   #5
Barkruk
Junior Member
 
Barkruk's Avatar
 
Join Date: Feb 2008
Location: The Netherlands
Posts: 5
Thanks I've got it working now.

Now my function checks if all files in my instdir are writable, but I only need to know if only the files I want to overwrite are writable.

I have searched the forum, examples and plugins, but I cannot find out how to know what files I have packed.

In short; I want to know what files I'm gonna extract, and before I extract the whole bunch, I want to check if the already existed files are writable. Not all files in instdir, but only the ones I want to overwrite.
Barkruk is offline   Reply With Quote
Old 7th February 2008, 22:41   #6
Animaether
Major Dude
 
Join Date: Jun 2001
Posts: 1,173
Quote:
Originally posted by Barkruk
Thanks I've got it working now.
Excellent


Quote:
Originally posted by Barkruk I have searched the forum, examples and plugins, but I cannot find out how to know what files I have packed.
You'll need a list of the files you're going to extract (along with, probably, where to). You can either...
A. hard-code this in your installer (or in an external file)
B. generate your installer (or aforementioned external file) using another installer or a batch file you'd write that essentially creates the list for you, that you would execute before compiling your installer. (This, iirc, is what is usually recommended).
( http://blogs.oracle.com/duffblog/2006/12/12 )
C. extract your files to a temporary folder first, then use the usual FindFirst etc. to get their filenames. ( you could, later on, use delete+rename to prevent having to extract the files again )
D. try installing the files anyway, now get the installation log file, find out which files failed, and prompt the user about these and try installing again. (or any of many variants on this)

There's probably other methods.. B tends to be the one that gets recommended.
Animaether is offline   Reply With Quote
Old 8th February 2008, 14:59   #7
Barkruk
Junior Member
 
Barkruk's Avatar
 
Join Date: Feb 2008
Location: The Netherlands
Posts: 5
Thanks man, I finally got what I want!

Some code sharing...

My setup.nsi:
code:
!system "CreateHeader.exe" ;Generates MyHeader.nsh

Function MyPrequisites
SetDetailsPrint textonly
Detailprint "Checking for files in use..."
SetDetailsPrint listonly
Loop:
!include MyHeader.nsh
StrCmp $R3 0 EndLoop
;$R3 is set to 1 in the header when a file is in use
MessageBox MB_ICONEXCLAMATION|MB_RETRYCANCEL "Some files \
are in use, please close them." IDRETRY Retry
SetDetailsPrint textonly
Detailprint "The installation is aborted."
SetDetailsPrint listonly
Abort
Retry:
StrCpy $R3 0
DetailPrint ""
SetDetailsPrint both
Detailprint "Rechecking for files in use..."
SetDetailsPrint listonly
DetailPrint ""
Goto Loop
EndLoop:
SetDetailsPrint both
FunctionEnd

Section
Call MyPrequisites
SetOutPath $INSTDIR
File /r "files\*.*"
SectionEnd

And here my CreateHeader.nsi (need to be compiled before compiling the setup):
code:
!define Header 'MyHeader.nsh'

OutFile 'CreateHeader.exe'
silentinstall silent

!include RecFind.nsh

Section
SetOutPath '$EXEDIR'
FileOpen $R2 ${Header} w
${RecFindOpen} "files" $R0 $R1
${RecFindFirst}
FileWrite $R2 'FileOpen $$R0 "$$INSTDIR$R0\$R1" a$\r$\n'
FileWrite $R2 'FileClose $$R0$\r$\n'
FileWrite $R2 'IfErrors 0 +3$\r$\n'
FileWrite $R2 'DetailPrint "File in use: $$INSTDIR$R0\$R1"$\r$\n'
FileWrite $R2 'StrCpy $$R3 1$\r$\n'
${RecFindNext}
${RecFindClose}
FileClose $R2
SectionEnd

And here a piece of the generated Header.nsh:
code:
FileOpen $R0 "$INSTDIR\adres.dll" a
FileClose $R0
IfErrors 0 +3
DetailPrint "File in use: $INSTDIR\adres.dll"
StrCpy $R3 1
FileOpen $R0 "$INSTDIR\agenda.dll" a
FileClose $R0
IfErrors 0 +3
DetailPrint "File in use: $INSTDIR\agenda.dll"
StrCpy $R3 1
FileOpen $R0 "$INSTDIR\alggeg.dll" a
FileClose $R0
IfErrors 0 +3
DetailPrint "File in use: $INSTDIR\alggeg.dll"
StrCpy $R3 1
FileOpen $R0 "$INSTDIR\algm1.dll" a
FileClose $R0
IfErrors 0 +3
DetailPrint "File in use: $INSTDIR\algm1.dll"
StrCpy $R3 1


Last edited by Barkruk; 8th February 2008 at 17:08.
Barkruk is offline   Reply With Quote
Old 8th February 2008, 16:09   #8
Barkruk
Junior Member
 
Barkruk's Avatar
 
Join Date: Feb 2008
Location: The Netherlands
Posts: 5
And see the differences from the attached file and the attached file from the start-post
Attached Images
File Type: png nsis.png (22.9 KB, 140 views)
Barkruk is offline   Reply With Quote
Old 8th February 2008, 19:58   #9
Animaether
Major Dude
 
Join Date: Jun 2001
Posts: 1,173
et voila Glad it worked out for you! NSIS can be a little daunting at first, but once you figure these types of things out, there's very little reason to even ponder an alternative anymore.
Animaether is offline   Reply With Quote
Reply
Go Back   Winamp & Shoutcast Forums > Developer Center > NSIS Discussion

Thread Tools Search this Thread
Search this Thread:

Advanced Search
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump