[SOLVED] Trying to make AbsInt()

Bare metal programming in PureBasic, for experienced users
User avatar
Mijikai
Addict
Addict
Posts: 1032
Joined: Sun Sep 11, 2016 2:17 pm

[SOLVED] Trying to make AbsInt()

Post by Mijikai »

I cant get my AbsInt() macro to work :?
Can someone pls point out my mistake :)

Code:

Code: Select all

EnableExplicit

Global dummy.i

Macro AbsInt(_val_)
  CompilerIf #PB_Compiler_Processor = #PB_Processor_x86
    !cmp dword[v_#_val_],0x0
    !jae @f
    !neg dword[v_#_val_]
    !@@:
  CompilerElse
    !cmp qword[v_#_val_],0x0
    !jae @f
    !neg qword[v_#_val_]
    !@@:
  CompilerEndIf
EndMacro

dummy = -42
AbsInt(dummy)

Debug dummy

End
Last edited by Mijikai on Sun Sep 26, 2021 4:56 pm, edited 1 time in total.
BarryG
Addict
Addict
Posts: 1718
Joined: Thu Apr 18, 2019 8:17 am

Re: Trying to make AbsInt()

Post by BarryG »

Is this no good for some reason?

Code: Select all

dummy.i = -42
dummy = Abs(dummy)
Debug dummy ; 42
User avatar
Mijikai
Addict
Addict
Posts: 1032
Joined: Sun Sep 11, 2016 2:17 pm

Re: Trying to make AbsInt()

Post by Mijikai »

BarryG wrote: Sun Sep 26, 2021 1:25 pm Is this no good for some reason?
...
That function is for floats and doubles.
It is not made for ints.
User avatar
STARGÅTE
Addict
Addict
Posts: 1619
Joined: Thu Jan 10, 2008 1:30 pm
Location: Germany, Glienicke
Contact:

Re: Trying to make AbsInt()

Post by STARGÅTE »

Such macro in combination with ASM would not work like you expected.
The name "v_var" is only right if var is a global variable. If it is in a procedure it would named like p.v_var etc.

I would recommend to use a normal procedure, which is fast enough:

Code: Select all

Procedure.i AbsInt(Var.i)
	If Var < 0
		ProcedureReturn -Var
	Else
		ProcedureReturn Var
	EndIf
EndProcedure

Debug AbsInt(-43)
Edit: corrected
PB 5.73 ― Win 10, 20H2 ― Ryzen 9 3900X ― Radeon RX 5600 XT ITX ― Vivaldi 4.0 ― www.unionbytes.de
Lizard - Script language for symbolic calculations and moreTypeface - Sprite-based font include/module
User avatar
Mijikai
Addict
Addict
Posts: 1032
Joined: Sun Sep 11, 2016 2:17 pm

Re: Trying to make AbsInt()

Post by Mijikai »

STARGÅTE wrote: Sun Sep 26, 2021 4:17 pm Such macro in combination with ASM would work like you expected.
...
Thanks for the reply.

Now im even more confused, did the macro work for you?
It fails on the !cmp line for me and i cant figure out why.
Result is still -42
User avatar
STARGÅTE
Addict
Addict
Posts: 1619
Joined: Thu Jan 10, 2008 1:30 pm
Location: Germany, Glienicke
Contact:

Re: Trying to make AbsInt()

Post by STARGÅTE »

Mijikai wrote: Sun Sep 26, 2021 4:48 pm
STARGÅTE wrote: Sun Sep 26, 2021 4:17 pm Such macro in combination with ASM would work like you expected.
...
Thanks for the reply.

Now im even more confused, did the macro work for you?
It fails on the !cmp line for me and i cant figure out why.
Result is still -42
You have to compare with signed-values (JGE) instead of unsigned values (JAE):
PB 5.73 ― Win 10, 20H2 ― Ryzen 9 3900X ― Radeon RX 5600 XT ITX ― Vivaldi 4.0 ― www.unionbytes.de
Lizard - Script language for symbolic calculations and moreTypeface - Sprite-based font include/module
User avatar
Mijikai
Addict
Addict
Posts: 1032
Joined: Sun Sep 11, 2016 2:17 pm

Re: Trying to make AbsInt()

Post by Mijikai »

Omg :shock: thank you :oops:
User avatar
Kiffi
Addict
Addict
Posts: 1206
Joined: Tue Mar 02, 2004 1:20 pm
Location: Amphibios 9

Re: [SOLVED] Trying to make AbsInt()

Post by Kiffi »

Cheers!
Image
(SCNR)
Hygge
User avatar
Mijikai
Addict
Addict
Posts: 1032
Joined: Sun Sep 11, 2016 2:17 pm

Re: [SOLVED] Trying to make AbsInt()

Post by Mijikai »

:mrgreen:
Sometimes u just 404
BarryG
Addict
Addict
Posts: 1718
Joined: Thu Apr 18, 2019 8:17 am

Re: Trying to make AbsInt()

Post by BarryG »

Mijikai wrote: Sun Sep 26, 2021 2:19 pmThat function is for floats and doubles.
It is not made for ints.
But I just did it with an integer? My dummy variable was not of double or float type.
User avatar
STARGÅTE
Addict
Addict
Posts: 1619
Joined: Thu Jan 10, 2008 1:30 pm
Location: Germany, Glienicke
Contact:

Re: [SOLVED] Trying to make AbsInt()

Post by STARGÅTE »

BarryG wrote: Sun Sep 26, 2021 9:53 pm
Mijikai wrote: Sun Sep 26, 2021 2:19 pmThat function is for floats and doubles.
It is not made for ints.
But I just did it with an integer? My dummy variable was not of double or float type.
Interesting. Also the large Quads are handled correctly. But it wasn't always like that. And is dosn't work in the new c-backend

Code: Select all

Define Quad.q   = -9000000000000001234
Define Double.d = -9000000000000001234

Debug Quad
Debug Double
Quad   = Abs(Quad)
Double = Abs(Double)
Debug Quad
Debug Double
Asm-backend:
-9000000000000001234
-9000000000000001000.0
9000000000000001234 ; Abs used quads instead of double
9000000000000001000.0
C-backend:
-9000000000000001234
-9000000000000001000.0
9000000000000001024 ; << last digits are wrong.
9000000000000001000.0
PB 5.73 ― Win 10, 20H2 ― Ryzen 9 3900X ― Radeon RX 5600 XT ITX ― Vivaldi 4.0 ― www.unionbytes.de
Lizard - Script language for symbolic calculations and moreTypeface - Sprite-based font include/module
User avatar
idle
Addict
Addict
Posts: 3651
Joined: Fri Sep 21, 2007 5:52 am
Location: New Zealand

Re: [SOLVED] Trying to make AbsInt()

Post by idle »

This should work out better than a conditional jmp

Code: Select all

Macro mabsint(var) 
  EnableASM
  mov rdx, var
  mov rax, rdx 
  neg rax
  CMOVl rax,rdx
  mov var,rax
  DisableASM 
EndMacro   

Procedure absint(a.i)  
  !mov rdx,[p.v_a]
  !mov rax, rdx 
  !neg rax
  !CMOVl rax,rdx
  ProcedureReturn 
EndProcedure 

a=-42 
mabsint(a)
Debug a 
Debug absint(-42)  
davido
Addict
Addict
Posts: 1852
Joined: Fri Nov 09, 2012 11:04 pm
Location: Uttoxeter, UK

Re: [SOLVED] Trying to make AbsInt()

Post by davido »

@idle,
Thank you for sharing.
DE AA EB
User avatar
Mijikai
Addict
Addict
Posts: 1032
Joined: Sun Sep 11, 2016 2:17 pm

Re: [SOLVED] Trying to make AbsInt()

Post by Mijikai »

Nice examples thanks for sharing everyone.
Im surprised that the simple function Stargate posted is so fast.

Here is another variant:

Code: Select all

Macro AbsInt(_val_)
  (1 - (Bool(_val_ < 0) << 1)) * _val_
EndMacro

There is also the msvcrt way (from the forum somewhere):

Code: Select all

EnableExplicit

Import "msvcrt.lib"
  CompilerIf #PB_Compiler_Processor = #PB_Processor_x64
    AbsInt.i(Value.i) As "_abs64"
  CompilerElse
    AbsInt.i(Value.i) As "_labs"
  CompilerEndIf
EndImport

Debug  AbsInt(-42)

End
User avatar
Michael Vogel
Addict
Addict
Posts: 2576
Joined: Thu Feb 09, 2006 11:27 pm
Contact:

Re: [SOLVED] Trying to make AbsInt()

Post by Michael Vogel »

Interesing thread! Actually I've a lot of assembler routines for dealing with integers (iMin, iMax, iLimit, uMin, uMax, iAbs, iSign,...), strings (StringLen, StringFind, StringCrypt,...), doing faster image processing (ColorMix, ColorScale, MergePixel, MergeLine,...) and many other things.

The (only) reason for me using assembler code is s p e e d . So it will be interesting how to migrate all these functions to PB V6, I am not sure if the C-backend will be fast enough to get rid of all assembler routines.
Post Reply