2

I have the following code to compare numbers and increment a variable if true or false

failcheck1: mov eax, val1 add ebx, 4 cmp eax, 40 jl failinc1 mov eax, passes inc eax mov passes, eax jmp failcheck2 failinc1: mov eax, fails inc eax mov fails, eax failcheck2 : mov eax, val2 add ebx, 4 cmp eax, 40 jl failinc2 mov eax, passes inc eax mov passes, eax jmp failcheck3 failinc2: mov eax, fails inc eax mov fails, eax 

I have 8 such checks. I was wondering if I create a single failinc and passinc subroutine with ret in it how can I call it after cmp ?

5
  • 1
    Same as always, the function itself has to carefully not destroy the flags before it uses them though Commented Mar 2, 2018 at 20:28
  • here is something: youtube.com/watch?v=y2T2V_7RvB4 - you call subroutines using call asm command: call - ret pair - google it Commented Mar 2, 2018 at 20:28
  • @KamilKiełczewski I know that I have to use call but my issue is how to call it only if the cmp eax, 40 is below 40. That is what I am struggling with Commented Mar 2, 2018 at 20:31
  • Wait, you want to call conditionally? That wouldn't even really reduce code.. you'd have the same structure as now but with mov\inc\mov replaced with call. Btw you can inc fails directly. Commented Mar 2, 2018 at 20:33
  • What I am trying to do is reduce failinc1 to failinc8 (which is 8 separate ones) with a single one that is being called and returns to the address of where it was called. Edit - added failinc2 to show you what my code is. That is repeated 8 times total Commented Mar 2, 2018 at 20:37

2 Answers 2

2

Because EBX is independantly incrementing, you can replace the 8 add ebx, 4 by a single addition add ebx, 4*8.

You can avoid all of those ugly and time consuming conditional jumps by using the conditional set instruction setl (Set On Less).

Because fails and passes are mutually exclusive, you can defer from calculating the passes to the very end. e.g. If processing 8 values gave 3 fails then there inevitably have to be 5 passes (is 8 minus 3).

 xor ecx, ecx ;Clear because SETL only operates on a byte xor edx, edx ;Clear temporary counter of fails cmp val1, 40 setl cl add edx, ecx ;Conditionally increment temporary counter cmp val2, 40 setl cl add edx, ecx ;Conditionally increment temporary counter cmp val3, 40 setl cl add edx, ecx ;Conditionally increment temporary counter cmp val4, 40 setl cl add edx, ecx ;Conditionally increment temporary counter cmp val5, 40 setl cl add edx, ecx ;Conditionally increment temporary counter cmp val6, 40 setl cl add edx, ecx ;Conditionally increment temporary counter cmp val7, 40 setl cl add edx, ecx ;Conditionally increment temporary counter cmp val8, 40 setl cl add edx, ecx ;Conditionally increment temporary counter add fails, edx ;Add temporary counter to actual variable sub edx, 8 sub passes, edx ;Add complementary count to other variable (*) add ebx, 4*8 

I was wondering if I create a single failinc and passinc subroutine with ret in it how can I call it after cmp ?

Now the subroutine

AddTempCount: ;On input EFLAGS is set from CMP instruction setl cl add edx, ecx ;Conditionally increment temporary counter ret 

can improve the readability a bit.

 xor ecx, ecx ;Clear because SETL only operates on a byte xor edx, edx ;Clear temporary counter of fails cmp val1, 40 call AddTempCount cmp val2, 40 call AddTempCount cmp val3, 40 call AddTempCount cmp val4, 40 call AddTempCount cmp val5, 40 call AddTempCount cmp val6, 40 call AddTempCount cmp val7, 40 call AddTempCount cmp val8, 40 call AddTempCount add fails, edx ;Add temporary counter to actual variable sub edx, 8 sub passes, edx ;Add complementary count to other variable (*) add ebx, 4*8 

(*) Subtracting a negative count is the same as adding a positive count.

Sign up to request clarification or add additional context in comments.

Comments

0
failcheck: mov eax, [eax] add ebx, 4 cmp eax, ecx jl .L1 incl passes ret .L1: incl fails ret failcheck1: lea eax, val1 mov ecx, 40 call failcheck lea eax, val2 mov ecx, 40 call failcheck 

1 Comment

Instead of incl passes, you may need to use inc dword passes, depending on your assembler.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.