Archive: Stack/Register Error: ${GetBetween}: NSIS Website


Stack/Register Error: ${GetBetween}: NSIS Website
The Developer center hosts this macro here:

http://nsis.sourceforge.net/GetBetwe...kers_in_a_file

And if you search for GetBetween on the developer center you will find the page with this code: [ Which I believe results in a stack corruption error of $R1,$R2. If GetBetween is called repeatedly, you endup with your registers very confused. My comments show the analysis of the error. My Solution to the Code is at the bottom:


!macro GetBetween This AndThis In Return
Push "${This}" ; This + Stack
Push "${AndThis}" ; AndThis + This + Stack
Push "${In}" ; In + AndThis + This + Stack
Call GetBetween
Pop "${Return}"
!macroend
!define GetBetween "!insertmacro GetBetween"

Function GetBetween
Exch $R0 ; $R0_Old + AndThis + This + Stack
Exch ; AndThis + $R0_Old + This + Stack
Exch $R1 ; $R1_Old + $R0_Old + This + Stack
Exch 2 ; This + $R0_Old + $R1_Old + Stack
Exch $R2 ; $R2_Old + $R0_OLD + $R1_Old + Stack

## ERROR IS HERE.
Exch 2 ; R1 R0 R2 + stack
Push $R3 ; R3 R1 R0 R2 + stack
Push $R4 ; R4 R3 R1 R0 R2 + stack
Push $R5 ; R5 R4 R3 R1 R0 R2 + stack
Push $R6 ; R6 R5 R4 R3 R1 R0 R2 + stack
Push $R7 ; R7 R6 R5 R4 R3 R1 R0 R2 + stack
Push $R8 ; R8 R7 R6 R5 R4 R3 R1 R0 R2 + stack
## Careful inspection of the rest of the function,
## shows zero stack maniplation to somehow fix
## the linear re-pop of the register list 8-0

FileOpen $R6 $R0 r

StrLen $R4 $R2
StrLen $R3 $R1

StrCpy $R0 ""

Read1:
ClearErrors
FileRead $R6 $R7
IfErrors Done
StrCpy $R5 0

FindMarker1:
IntOp $R5 $R5 - 1
StrCpy $R8 $R7 $R4 $R5
StrCmp $R8 "" Read1
StrCmp $R8 $R2 0 FindMarker1
IntOp $R5 $R5 + $R4
StrCpy $R7 $R7 "" $R5

StrCpy $R5 -1
Goto FindMarker2

Read2:
ClearErrors
FileRead $R6 $R7
IfErrors Done
StrCpy $R5 -1

FindMarker2:
IntOp $R5 $R5 + 1
StrCpy $R8 $R7 $R3 $R5
StrCmp $R8 "" 0 +3
StrCpy $R0 $R0$R7
Goto Read2
StrCmp $R8 $R1 0 FindMarker2
StrCpy $R7 $R7 $R5
StrCpy $R0 $R0$R7

Done:
FileClose $R6

Pop $R8 ;R7 R6 R5 R4 R3 R1 R0 R2 + stack
Pop $R7 ;R6 R5 R4 R3 R1 R0 R2 + stack
Pop $R6 ;R5 R4 R3 R1 R0 R2 + stack
Pop $R5 ;R4 R3 R1 R0 R2 + stack
Pop $R4 ;R3 R1 R0 R2 + stack
Pop $R3 ;R1 R0 R2 + stack
Pop $R2 ;ERROR R0 R2 + stack
Pop $R1 ;ERROR R2 + stack
Exch $R0 ;ERROR + stack
##( One more pop at macro level leaves stack alone,
## but registers are munged. )
FunctionEnd


File Patch Above looks like:
<snip>
Function GetBetween
Exch $R0 ;$R0_Old + AndThis + This + Stack
Exch ;AndThis + $R0_Old + This + Stack
Exch $R1 ;$R1_Old + $R0_Old + This + Stack
Exch 2 ;This + $R0_Old + $R1_Old + Stack
Exch $R2 ;$R2_Old + $R0_OLD + $R1_Old + Stack
Exch 2 ; $R1_Old + $R0_OLD + $R2_Old + Stack
Exch ; $R0_Old + $R1_OLD + $R2_Old + Stack
Exch 2 ; $R2_Old + $R1_OLD + $R0_Old + Stack
Push $R3 ; R3,R2,R1,R0,Stack
Push $R4 ; R4,R3,R2,R1,R0,Stack
Push $R5 ; R5,R4,R3,R2,R1,R0,Stack
Push $R6 ; R6,R5,R4,R3,R2,R1,R0,Stack
Push $R7 ; R7,R6,R5,R4,R3,R2,R1,R0,Stack
Push $R8 ; R8,R7,R6,R5,R4,R3,R2,R1,R0,Stack
</snip>


My VERY humble apologies if I have missed something, but I did the patch on my code and I no longer am having register corruption.


{bump}
Confirmation?


Legit Error On NSIS Site:
This page, needs to be corrected: [ Per my previous post.] Where do I post this, if its not here?


nsis.sourceforge.net/GetBetween:_Get_text_in_between_two_markers_in_a_file

The register order is corrupted when the code that is posted exits the macro.

Thanks_

Andrew Wallo


You can edit the page directly. Make sure to leave a meaningful comment in the edit log.


Finally finishing this thread....
Page edited on the NSIS Wiki. Not sure if I did it correctly. Usually you have a debate page on a wiki.... but I just edited the main content with a proof comment and a patch comment. If the group agrees it can consolodate the edit.

_Thanks.


You have correctly identified and fixed the problem. You should fix the function itself rather than keep it as a patch. I'd just re-order the Pop calls and get rid of any unnecessary Exch calls, but both solutions are good.