Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Starting a function with a branch

From optimization and branch predictor point of view, is there any difference between those two codes?

First:

void think_and_do(){
    if(expression){
        //Set_A of instructions
    }
    else{
         //Set_B of instructions
    }
}

int main(){
    think_and_do();
}

Second:

void do_A(){
    //Set_A of instructions
}

void do_B(){
    //Set_B of instructions
}

int main(){
    if(expression){
        do_A();
    }
    else{
        do_B();
    }
}
like image 778
Humam Helfawi Avatar asked Oct 17 '22 23:10

Humam Helfawi


1 Answers

I've made an test on godbolt.org think_and_do and in main

First observation, if your examples are trivial they mostly get optimized away. Without the cin both examples should have compiled to:

    xor     eax, eax
    add     rsp, 8 #may or may not be present.
    ret 

Second observation is that the code is exactly the same in main: and none of the functions are called, everything is inlined.

Third observation is that both examples makes the following code

    mov     edx, DWORD PTR a[rip]
    mov     eax, DWORD PTR b[rip]
    cmp     edx, eax
    je      .L8

That is they fill one cycle of 4 instruction to make the most of issuing (and ignore the possibility of macro-fusion of the cmp and jump).

If they had started with an

    cmp     edx, eax
    je      .L8

Half of the issue bandwidth would potentially have been wasted.

like image 52
Surt Avatar answered Oct 21 '22 05:10

Surt