Douglas Walls' Weblog

« Finding the canonica... | Main | The real story on... »
20060522 Monday May 22, 2006

C99 inline function and the Sun C Compiler
Note, the C standard says that inline is only a suggestion to the C compiler.  The C compiler can choose not to inline anything, and attempt to call the actual function.

The Sun C compiler does not inline C function calls unless optimizing at -xO3 or above.  And that inlining is done by the backends.  And then only if the backend's heuristics decide it is profitable to do so.  The Sun C compiler gives no way to force a function to be inlined.

For static inline functions it is simple.  Either a function defined with the inline function specifier is inlined at a reference or a call is made to the actual function.  The compiler can choose which to do at each reference.  The Sun C compiler decides if it is profitable to inline at -xO3 and above.  When not profitable to inline, or at an optimization of less than -xO3 a reference to the actual function will be generated.  If any reference to the actual function is generated the function definition will be generated in the object code.  Note if the address of the function is taken, the actual function will be generated in the object code.

Extern inline functions are more complicated.  There are two types of extern inline functions, an inline definition which never provides an extern (global) definition of the function and an extern inline function which always provide a global definition of the function.  To quote the C99 standard:

       [#6]  Any  function  with  internal linkage can be an inline
function. For a function with external linkage, the
following restrictions apply: If a function is declared with
an inline function specifier, then it shall also be defined
in the same translation unit. If all of the file scope
declarations for a function in a translation unit include
the inline function specifier without extern, then the
definition in that translation unit is an inline definition.
An inline definition does not provide an external definition
for the function, and does not forbid an external definition
in another translation unit. An inline definition provides
an alternative to an external definition, which a translator
may use to implement any call to the function in the same
translation unit. It is unspecified whether a call to the
function uses the inline definition or the external
definition.

[#7] EXAMPLE The declaration of an inline function with
external linkage can result in either an external
definition, or a definition available for use only within
the translation unit. A file scope declaration with extern
creates an external definition. The following example shows
an entire translation unit.

inline double fahr(double t)
{
return (9.0 * t) / 5.0 + 32.0;
}

inline double cels(double t)
{
return (5.0 * (t - 32.0)) / 9.0;
}

extern double fahr(double); // creates an external definition

double convert(int is_fahr, double temp)
{
/* A translator may perform inline substitutions */
return is_fahr ? cels(temp) : fahr(temp);
}

[#8] Note that the definition of fahr is an external
definition because fahr is also declared with extern, but
the definition of cels is an inline definition. Because
cels has external linkage and is referenced, an external
definition has to appear in another translation unit (see
6.9); the inline definition and the external definition are
distinct and either may be used for the call.

So, for an inline definition, the programmer is required to supply an extern definition of the function in another translation-unit for references to the function that are not inlined.

For an inline definition, the compiler must not create a global definition of the function.  That means any reference to an inline definition that is not inlined must be a reference to a global function defined elsewhere.  Put another way, the object file produced by compiling this translation unit will not contain a global symbol for the inline definition.  And any reference to the function that is not inlined will be to an extern (global) symbol provided by some other object file or library at link time.

For an extern inline function declared by a file scope declaration with the extern storage-class-specifier (i.e. the function definition and/or prototype), the compiler must provide a global definition of the function in the resulting object file.  The compiler can choose to inline any references to that function seen in the translation unit where the function definition has been provided, or the compiler can choose to call the global function.

The behavior of any program that relies on whether or not a function call is actually inlined, is undefined.

Note also an inline function with external linkage may not declare or reference a static variable anywhere in the translation-unit.

Definition of translation-unit: A source file and all of its includes, recursively.

Like it does for static functions, the Sun C compiler decides if it is profitable to inline a reference to an inline definition or an extern inline function at -xO3 and above.  When not profitable to inline, or at an optimization of less than -xO3 a reference to the global function will be generated.  Likewise a reference to the address of the function is always a reference to the global function.

The rules for C++ differ: a function which is inline anywhere must be inline everywhere and must be defined identically in all the translation units that use it.

gcc

The GNU C rules differ and are described in the GNU C manual, which can be found here http://gcc.gnu.org.

Sun C compiler gcc compatibility for inline functions

To obtain behavior from the Sun C compiler that is compatible with gcc's implementation of extern inline functions for most programs, use the -features=no%extinl flag.  When this flag is specified the Sun C compiler will treat the function as if it was declared as a static inline function.

The one place this is not compatible will be when the address of the function is taken.  With gcc this will be an address of a global function, and with Sun's compiler the local static definition address will be used.

( May 22 2006, 08:11:19 AM PDT ) Permalink Comments [1]

Trackback URL: http://blogs.sun.com/dew/entry/c99_inline_function
Comments:

thanks, it helps me a lot!

Posted by overcomeunicom on May 06, 2008 at 10:57 PM PDT #

Post a Comment:

Name:
E-Mail:
URL:

Your Comment:

HTML Syntax: NOT allowed

Search

Calendar

Links

Navigation

Referers