Page 1 of 1
Out of Range for 'And'
Posted: Sun Jan 22, 2017 4:36 am
by Michael Vogel
Hi, I try to do a little bit tuning and am happy about around 20% more speed for a routine doing some shade effetcs in X86 assembler now.
I see, that I am getting older, because the 8 bit (6502, 8088) and 16 bit (68000) era was perfect for me and I am stumbling around with 32 bit (see code below), but 64 bit is to much for me
I tried to convert my routine to 64 bit by replacing all eax to rax, which I was able to do after a while... but how to deal with the error in the !And rax,$FF000000 line?
Code: Select all
Procedure CustomShadowHeavyDarken(Source,Destination)
EnableASM
CompilerIf #PB_Compiler_Processor = #PB_Processor_x86
!mov eax,[p.v_Source]
!And eax,$FF
!shl eax,24
!CMP eax,[p.v_Destination]
!ja done.l_customshadowheavydarken
!mov eax,[p.v_Destination]
!and eax,$FF000000
!done.l_customshadowheavydarken:
!or eax,[v_ColorIconShadow]
CompilerElse
!mov rax,[p.v_Source]
!And rax,$FF
!shl rax,24
!CMP rax,[p.v_Destination]
!ja done.l_customshadowheavydarken
!mov rax,[p.v_Destination]
!and rax,$FF000000
!done.l_customshadowheavydarken:
!or rax,[v_ColorIconShadow]
CompilerEndIf
DisableASM
ProcedureReturn
EndProcedure
Re: Out of Range for 'And'
Posted: Sun Jan 22, 2017 4:53 am
by Keya
it compiles fine (PBWin64) and your '!and rax,$FF000000" is perfectly valid (it compiles to "!db 0x48, 0x25, 0x00, 0x00, 0x00, 0xFF" if curious) -- are you sure you're not trying to compile with PB32? (hey it is the weekend afterall)

strange it didnt complain about the other ones though!
Re: Out of Range for 'And'
Posted: Sun Jan 22, 2017 12:03 pm
by Michael Vogel
yep, a strange weekend...
Here's a longer version of the code, hopefully it will show the error message now...
Code: Select all
; Define
;DisableDebugger
#IconTemp=0
#ColorOpaque=$FF000000
Global ColorIconShadow
Global CustomRed
Global CustomGreen
Global CustomBlue
Global CustomColor
#X=400
#Y=400
; EndDefine
Procedure CustomShadowHeavyDarken(x,y,Source,Destination)
EnableASM
CompilerIf #PB_Compiler_Processor = #PB_Processor_x86
!mov eax,[p.v_Source]
!And eax,$FF
!shl eax,24
!CMP eax,[p.v_Destination]
!ja done.l_customshadowheavydarken
!mov eax,[p.v_Destination]
!and eax,$FF000000
!done.l_customshadowheavydarken:
!or eax,[v_ColorIconShadow]
CompilerElse
!mov rax,[p.v_Source]
!And rax,$FF
!shl rax,24
!CMP rax,[p.v_Destination]
!ja done.l_customshadowheavydarken
!mov rax,[p.v_Destination]
!and rax,$FF000000
!done.l_customshadowheavydarken:
!or rax,[v_ColorIconShadow]
CompilerEndIf
DisableASM
ProcedureReturn
;ProcedureReturn ColorIconShadow | uMax((Source&$FF)<<24,Destination&$FF000000)
EndProcedure
Procedure Main()
Protected x,y,t,z
OpenWindow(0,0,0,#X,#Y, "-", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
ImageGadget(1,0,0,#X,#Y,0)
CreateImage(1,400,400,32,#PB_Image_Transparent)
CreateImage(2,400,400,32,#PB_Image_Transparent)
CreateImage(0,100,100,32)
ColorIconShadow=$808080
StartDrawing(ImageOutput(2))
x=20
y=320
DrawingMode(#PB_2DDrawing_CustomFilter)
CustomFilterCallback(@CustomShadowHeavyDarken())
DrawImage(ImageID(#IconTemp),x,y)
StopDrawing()
StartDrawing(ImageOutput(1))
DrawAlphaImage(ImageID(2),0,0)
StopDrawing()
SetGadgetState(1,ImageID(1))
Repeat
Select WaitWindowEvent()
Case #PB_Event_CloseWindow,#WM_CHAR
End
EndSelect
ForEver
EndProcedure
Main()
Re: Out of Range for 'And'
Posted: Sun Jan 22, 2017 12:18 pm
by Keya
hah, yes I do get the error now - i didnt before because although i was on Win64 i was running PB32 at the time (SEE what i mean about coding on the weekend!?). Im not sure why fasm is complaining about that, but just replace the !and line with "!db 0x48,0x25,0x00,0x00,0x00,0xFF", which i obtained from x64dbg
Ok im going to make some iced coffee now to ensure this doesn't happen again
btw youre working with 32bits rgb/a vals so although you need to address it via rax you still might only need to be working with eax, might even have problems if using full rax but im not sure, just thinking out loud!
Re: Out of Range for 'And'
Posted: Sun Jan 22, 2017 12:54 pm
by Helle
The error message is correct. "AND Register,Imm32" is CPU-intern sign-extended to 64-bits. Imm64 is not exist (15-Bytes-Rule). A good Compiler/Assembler gives this message.
You must use
Code: Select all
!mov rdx,$FF000000 ;or another free register
!and rax,rdx
@Keya: This is not a good idea

:
Code: Select all
X.q
!mov rax,$FFF000000
;!and rax,$FF000000
!db 0x48,0x25,0x00,0x00,0x00,0xFF
!mov [v_X],rax
Debug Hex(X) ;you expect $FF000000, but... AND-value (32-bit) is sign-extended to 64-bits!
Re: Out of Range for 'And'
Posted: Sun Jan 22, 2017 2:44 pm
by Michael Vogel
That hurts, when using callbacks for custom filter, it seems that only eax can be used without side effects - so I do get strange results here when rdx will be used as well.
A horrible workaround, I shift the register two times to get rid of the problem - I'm quite sure, the 64 bit version will be very slow (must check that now)...
...now everything got even more complicated, the routine seems to calculate correct results, but when using the custom filter, the graphics look weird (and the 64 bit version runs slower than the 32 bit routine)
