I'm sharing here in hopes someone will find it useful or thought provoking.
Typically when you call a defined macro you are confined to the following convention:
${MyMacro} $0 'Some Value' What if we could add stack manipulations to it to avoid excessive pops and pushes by dynamically altering the calls. Say, something like this:${MyMacro} s s Now the macro will use the stack for those values. We can even mix and match.${MyMacro} $0 s
${MyMacro} s 'Some Value' Lets say I have want to add an item to a comma separated list multiple times. Using some fancy macro / stack manipulations I came up with this:!ifmacrondef _CSV
!macro _CSV _ReturnValue _Source _Value
!if `${_Source}` != s
Push `${_Source}`
!if `${_Value}` == s
Exch
!else
Push `${_Value}`
!endif
!else if `${_Value}` != s
Push `${_Value}`
!endif
Call CSV
!if ${_ReturnValue} != s
Pop ${_ReturnValue}
!endif
!macroend
!define CSV `!insertmacro _CSV`
Function CSV
;Stack : _Value _Source
Exch $0 ; $0 _Source
Exch ; _Source $0
Exch $1 ; $1 $0
StrCmp '' $1 StrCmpEnd
StrCpy $0 `$1,$0`
StrCmpEnd:
Pop $1
Exch $0
FunctionEnd
!endif
Section CSV
${CSV} s "" "Hello"
${CSV} s s "World"
${CSV} s s "This"
${CSV} s s "is"
${CSV} s s "a"
${CSV} $0 s "test"
DetailPrint $0
${CSV} $0 $0 "Oh and one more thing!"
DetailPrint $0
SectionEnd Pretty cool eh?Here is an example that is a bit simpler:
!ifmacrondef _Msg
!macro _Msg _ReturnValue _Message
!if `${_Message}` != s
Push `${_Message}`
!endif
Call Msg
!if ${_ReturnValue} != s
Pop ${_ReturnValue}
!endif
!macroend
!define Msg `!insertmacro _Msg`
Function Msg
Exch $0
StrCpy $0 'The Message is "$0"'
Exch $0
FunctionEnd
!endif
Section Msg
${Msg} $R0 "Hello!"
DetailPrint $R0
${Msg} s "Hello There!"
Pop $R1
DetailPrint $R1
Push "Hello World!"
${Msg} s s
Pop $R3
DetailPrint $R3
SectionEnd