Inline Function in C - GeeksforGeeks
- ️Mon Dec 03 2018
Last Updated : 17 Jan, 2025
In C, an inline function is a special type of function whose function call is replaced with the actual code of the function rather than being invoked through the usual function call mechanism, potentially improving performance by reducing function call overhead. It is declared using inline keyword and generally used for small and frequently used functions.
Let’s take below example:
C#include <stdio.h>
// Inline function to calculate the square of a number
inline int square(int x) {
return x * x;
}
int main() {
int n = 5;
// The compiler will replace square(n) with (n * n)
int res = square(n);
printf("%d", res);
return 0;
}
Output
25
The above function may not compile is some compiler such as GCC. It is because GCC implement inlining feature as a part of optimization. If all the optimization flags are off, then this inline keyword work differently.
Syntax
To declare a function as inline, the keyword inline is placed before the function’s return type.
inline return_type function_name(parameters) {
// Function body
}
Behaviour of Inline Functions
Inline is just a suggestion to the compiler, it does not force the compiler. The behaviour of inline depends on how it is being used and how inline optimization is implemented by the compiler.
1. Inline without GCC Optimization
When inline is used for a function in a C source file and compiled without any optimization flag, it throws an error as shown:
C#include <stdio.h>
// Inline function in C
inline int foo() {
return 2;
}
int main() {
int res;
// inline function call
res = foo();
printf("%d", res);
return 0;
}
Output
/usr/bin/ld: /tmp/ccBVKkSP.o: in function `main':
solution.c:(.text+0x12): undefined reference to `foo'
collect2: error: ld returned 1 exit status
This is one of the side effects of how GCC handles inline functions. When compiled, GCC performs inline substitution as part of its optimization process. As a result, the symbol for the function is not created in the symbol table because the code is directly replaced with the function’s body during compilation. Please check below assembly code which compiler will generate.
Now, as substitution is not performed, and the symbol is not generated, the linker cannot link the function definition with the call. It then searches for the given function in other translation unit’s symbol table (kind of external linkage), which is also not found here, causing the linker error mentioned above.
2. Inline With GCC Optimization
The first solution to above problem is to turn on the GCC optimization using optimization flag passed during program’s compilation command.
gcc solution.c -o solution -O1
Any optimization level greater than O0 will turn on the inline optimization in GCC.
C++#include <stdio.h>
// Inline function in C
inline int foo() {
return 2;
}
int main() {
int res;
// inline function call
res = foo();
printf("%d", res);
return 0;
}
3. Static Inline Function
We can use the static keyword before the inline function. This forces the compiler to treat the function with internal linkage and ensures that it is considered during the linking process, allowing the program to compile and run successfully. Though the inlining still depends on the compiler’s optimization level.
C#include <stdio.h>
// Inline function in C
static inline int foo() {
return 2;
}
int main() {
int res;
// inline function call
res = foo();
printf("%d", res);
return 0;
}
4. Inline with Forward Declaration
If the function is declared separately, then it will be added to the symbol table. Later on, it can be defined as inline, and the compiler will consider it for inlining if the optimization level is O1 or above. But if the optimization is O0, then this function will not be inlined but still will be able to be executed as a normal function.
C#include <stdio.h>
// Forward declaration
int foo();
// Inline function in C
inline int foo() {
return 2;
}
int main() {
int res;
// Inline function call
res = foo();
printf("%d", res);
return 0;
}
5. Extern Inline Function
If the function is defined with external linkage, then the compiler will try to find its definition in other translation units. If found, inlining will still depend on the optimization flag. But the function will be executed in both cases. It will not throw an error.
At the end of the day, inlining is dependent on the compiler optimization schemes. All the other cases are just fallback measures to keep the program from throwing the error.
Inline Function vs. Macro
An inline function is similar to a macro in that it can substitute the function call with actual code. However, there are some key differences:
Feature | Inline Function | Macro |
---|---|---|
Type Safety | Type-checked, respects data types. | No type-checking, can lead to unexpected results. |
Debugging | Easier to debug, behaves like a regular function. | Harder to debug, errors may not be clear. |
Parameter Evaluation | Parameters are evaluated once. | Parameters may be evaluated multiple times. |
Recursion Support | Can be recursive. | Cannot be recursive. |
When to use Inline Functions?
The use of inline function is preferred for:
- Small Functions: Inline functions are best suited for small, frequently used functions where the performance improvement from avoiding function calls is significant.
- Time-Critical Code: Use inline functions in scenarios where performance is critical, such as embedded systems.
- Type-Sensitive Operations: Inline functions are preferred over macros because they respect type safety and scope.