IN SHORT: Is there a place to put the [[(un)likely]]
attribute so that the control flow at cond2
is considered likely to take the false branch, without affecting the possibility of branches at cond1
?
if (cond1) {
do {
foo();
} while (cond2);
}
If I put [[unlikely]]
in do [[unlikely]] {
or do { [[unlikely]]
,does it affect cond1
? Since the true-branch of cond1
is the ONLY path that goes into the loop and is the path that ALWAYS goes into the loop, according to cppreference.com:
Applies to a statement to allow the compiler to optimize for the case where paths of execution including that statement are less likely than any alternative path of execution that does not include such a statement.
it seems that cond1
is affected.
If I put [[likely]]
after the loop, e.g. do { foo(); } while(cond2); [[likely]];
, the attribute is applied to the empty statement. This code is unintuitive and become unclearer whether cond2
and/or cond1
are affected.
Btw, the question is infact asking about the semantics of [[(un)likely]]
attribute, not about implementations neither alternatives such as __builtin_expect
or breaking the do-while loop to foo(); while(cond2) [[unlikely]] foo();
.
do { foo(); } while(cond2) [[likely]];
? – Hippodrome__builtin_expect
, e.g.inline bool unlikely_cond(bool cond) { if (cond) [[unlikely]] { return true; } else { return false; } }
, then useunlikely_cond(cond2)
. But I still don't understand the exact semantics of[[(un)likely]]
attributes. – Woodworm