Likely, unlikely macro and built-in GCC functions _ builtin_expect ()

Source: Internet
Author: User


A few times
I recently read the Linux 2.6 kernel. Although I have read a lot of related knowledge before, but I have read it three or three times, I still feel very hard to read the 2.6 kernel. In the face of such a huge kernel of 2.6, the confidence is really not enough, and it seems that there is no good and helpful forum to discuss it together, ah! Now I am watching and reading the latest kernel. Since the publication, there have been many changes in the kernel, which is hard to read! If you read it like this, it's not an easy task!
Back to business
When I was reading Linux/kernel/fork. C, I encountered the unlikely macro definition, followed all the way, and finally found the built-in GCC function _ builtin_expect (). I checked out the GCC manual and found its definition as follows:
Long _ builtin_exact CT (long exp, long c) [built-in function]
You may use _ builtin_predict CT to provide the compiler with branch prediction
Information. In general, you shoshould prefer to use actual profile feedback for this
('-Fprofile-arcs'), as programmers are notoriously bad at predicting how their
Programs actually perform. However, there are applications in which this data is
Hard to collect.
The return value is the value of exp, which shoshould be an integral expression.
Value of C must be a compile-time constant. the semantics of the built-in are that it
Is expected that exp = C. For example:
If (_ builtin_ct (x, 0 ))
Foo ();
Wocould indicate that we do not have CT to call Foo, since we have ct x to be zero. Since
You are limited to integral expressions for exp, you shoshould use constructions such
If (_ builtin_ct (PTR! = NULL, 1 ))
Error ();
When testing pointer or floating-point values.
Generally speaking, because most programmers do poorly in branch prediction, GCC provides this built-in function to help programmers process branch prediction and optimize programs. The first exp parameter is an integer expression, and the returned value of this built-in function is also this exp, while C is a constant during compilation. the semantics of this function is: you expect the EXP expression value to be equal to the constant C, so that GCC will optimize your program and place the branch that meets this condition in the appropriate place.
Because this program only provides integer expressions, you can use pointers to optimize other types of expressions.
The definition of unlikely is as follows:
# Define unlikely (x) _ builtin_exact CT (!! (X), 0)
That is to say, we expect the value of expression X to be 0, so if we use
.......
If (unlikely (x )){
Bar ();
}
To test the conditions, we do not expect bar () function execution, so the macro name is represented by unlikely, which is unlikely.
The likely macro is similar to the time.
In the end, the _ builtin_expect function is used to optimize Branch Programs with high possibility.

++

[Bob]
In fact, I would like to sum up the meaning of the above words:
If you use the IF () statement, just as before, but if you think that if () is 1 is very likely, add a likely () outside the expression (), if the probability is very small (for example, the probability is very small), use the unlikely () package.
When you look at the kernel code, you can see many such examples:
If (likely (CPU = this_cpu) {// pay attention to likely and unlikely usage
// Here we use likely to describe that CPU = this_cpu is very likely
If (! (Clone_flags & clone_vm )){
/*
* The VM isn' t cloned, so we're in a good position
* Do child-runs-first in anticipation of an exec. This
* Usually avoids a lot of cow overhead.
*/
If (unlikely (! Current-> array ))
_ Activate_task (p, rq );
Else {
P-> PRIO = Current-> PRIO;
P-> normal_prio = Current-> normal_prio;
List_add_tail (& P-> run_list, & Current-> run_list );
P-> array = Current-> array;
P-> array-> nr_active ++;
Inc_nr_running (p, rq );
}
Set_need_resched ();
} Else
/* Run child last */
_ Activate_task (p, rq );
/*
* We skip the following code due to CPU = this_cpu
*
* Task_rq_unlock (RQ, & flags );
* This_rq = task_rq_lock (current, & flags );
*/
This_rq = RQ;
} Else {


---

There are a lot of unnecessary things in the kernel code.
The code in the kernel sometimes looks complicated and redundant, but it is really good to take a closer look.
You can always see macros such as bug_on () and warn_on () in the code, similar to assert in our daily programming ).
---> Bug. h
Quote:
Extern void _ warn_on (const char * func, const char * file, const int line );
# Ifdef config_bug
# Ifndef have_arch_bug
# Define bug () do {/
Printk ("bug: failure at % s: % d/% s ()! /N ", _ file __, _ line __, _ function __);/
Panic ("bug! ");/
} While (0)
# Endif
# Ifndef have_arch_bug_on
# Define bug_on (condition) do {If (unlikely (condition )! = 0) Bug ();} while (0)
# Endif
# Ifndef have_arch_warn_on
# Define warn_on (condition) do {/
If (unlikely (condition )! = 0 ))/
_ Warn_on (_ FUNCTION __, _ file __, _ line __);/
} While (0)
# Endif
# Else /*! Config_bug */
# Ifndef have_arch_bug
# Define bug ()
# Endif
# Ifndef have_arch_bug_on
# Define bug_on (condition) do {If (condition);} while (0)
# Endif
# Ifndef have_arch_warn_on
# Define warn_on (condition) do {If (condition);} while (0)
# Endif
# Endif
Examples are used in other kernel codes:
Bug_on (unlikely (atomic_read (& (kioctx)-> Users)
[Copy to clipboard]

[-]
Code:
# Include
# Include
# Define likely (x) _ builtin_exact CT (!! (X), 1)
# Define unlikely (x) _ builtin_exact CT (!! (X), 0)
# Define bug_on (condition) Do/
{If (unlikely (condition )! = 0 ))/
Printf ("bug: failure at % s: % d/% s ()! /N ", _ file __, _ line __, _ function __);/
} While (0)
Int main (void)
{
Int I = 7;
Bug_on (I! = 10 );
Return 0;
}
The output is as follows:
BUG: failure at warn. C: 18/main ()!


 


From: http://hi.baidu.com/zkheartboy/blog/item/92cc373f9b90dfe955e72315.html

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.