Disadvantage of using 'inline'

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • Method Man

    Disadvantage of using 'inline'

    If I don't care about the size of my executable or compile time, is there
    any reason why I wouldn't want to inline every function in my code to make
    the program run more efficient?


  • Dan Pop

    #2
    Re: Disadvantage of using 'inline'

    In <flS4d.1112$By5 .199776@read2.c gocable.net> "Method Man" <a@b.c> writes:
    [color=blue]
    >If I don't care about the size of my executable or compile time, is there
    >any reason why I wouldn't want to inline every function in my code to make
    >the program run more efficient?[/color]

    1. inline is not a portable feature of C.

    2. There is no guarantee that inlining everything is going to speed up
    your code. Larger executable means less efficient usage of the
    processor cache.

    Dan
    --
    Dan Pop
    DESY Zeuthen, RZ group
    Email: Dan.Pop@ifh.de
    Currently looking for a job in the European Union

    Comment

    • Andrey Tarasevich

      #3
      Re: Disadvantage of using 'inline'

      Method Man wrote:[color=blue]
      > If I don't care about the size of my executable or compile time, is there
      > any reason why I wouldn't want to inline every function in my code to make
      > the program run more efficient?[/color]

      Thoughtless inlining might easily cause code bloat, which will make your
      program run _less_ efficiently.

      --
      Best regards,
      Andrey Tarasevich

      Comment

      • kyle york

        #4
        Re: Disadvantage of using 'inline'

        Greetings,

        Dan Pop wrote:[color=blue]
        > In <flS4d.1112$By5 .199776@read2.c gocable.net> "Method Man" <a@b.c> writes:
        >
        >[color=green]
        >>If I don't care about the size of my executable or compile time, is there
        >>any reason why I wouldn't want to inline every function in my code to make
        >>the program run more efficient?[/color]
        >
        >
        > 1. inline is not a portable feature of C.[/color]

        Odd, I must be horribly misreading 6.7.4: Function specifiers


        --
        Kyle A. York
        Sr. Subordinate Grunt, SC

        Comment

        • Keith Thompson

          #5
          Re: Disadvantage of using 'inline'

          kyle york <kyork@cisco.co m> writes:[color=blue]
          > Greetings,
          > Dan Pop wrote:[color=green]
          >> In <flS4d.1112$By5 .199776@read2.c gocable.net> "Method Man" <a@b.c> writes:
          >>[color=darkred]
          >>>If I don't care about the size of my executable or compile time, is there
          >>>any reason why I wouldn't want to inline every function in my code to make
          >>>the program run more efficient?[/color]
          >> 1. inline is not a portable feature of C.[/color]
          >
          > Odd, I must be horribly misreading 6.7.4: Function specifiers[/color]

          His point is that "inline" is a new feature in C99, not supported by
          C90, and that C99 compilers are not yet widespread enough for code
          that depends on C99-specific features to be considered portable.

          On the other hand, many compilers that don't support all of C99 do
          support inline (whether they do so in a way that's 100% compatible
          with the C99 specification is another question).

          --
          Keith Thompson (The_Other_Keit h) kst-u@mib.org <http://www.ghoti.net/~kst>
          San Diego Supercomputer Center <*> <http://users.sdsc.edu/~kst>
          We must do something. This is something. Therefore, we must do this.

          Comment

          • Derrick Coetzee

            #6
            Re: Disadvantage of using 'inline'

            Method Man wrote:[color=blue]
            > If I don't care about the size of my executable or compile time, is there
            > any reason why I wouldn't want to inline every function in my code to make
            > the program run more efficient?[/color]

            Disclaimer: Parts of this response may be platform-specific.

            Actually, many compilers *do* aggressively inline small functions within
            a module at high optimization levels, even if you don't explicitly ask
            them to. For example, gcc does this at -O3 (which includes the flag
            -finline-functions, the primary difference from -O2).

            No good compiler will inline a large function, though, even if you ask
            it to, not only because of the large space overhead in doing so but
            because the purpose of inlining is to eliminate function call overhead,
            and this is simply relatively insigificant if enough time is spent
            inside the function called (even a small function with a long loop
            doesn't benefit from inlining).

            Placing the inline keyword on all static (module-local) functions is an
            okay thing to do, if you trust your compiler; it'll figure out when not
            to do it, although you can't take an inline function's address to call
            it indirectly, and you'll look a bit silly. Trouble starts when you
            attempt to export an inline function, though, and use it in multiple
            modules. Such an inline function has to include its definition in every
            module using it, usually via a header. If the compiler ends up not
            inlining it, for whatever reason, this may result in a copy of its code
            being placed in every module that uses it. Thus you should only export
            small inline functions.
            --
            Derrick Coetzee
            I grant this newsgroup posting into the public domain. I disclaim all
            express or implied warranty and all liability. I am not a professional.

            Comment

            • Andrey Tarasevich

              #7
              Re: Disadvantage of using 'inline'

              Derrick Coetzee wrote:[color=blue]
              > ...
              > Placing the inline keyword on all static (module-local) functions is an
              > okay thing to do, if you trust your compiler; it'll figure out when not
              > to do it, although you can't take an inline function's address to call
              > it indirectly, and you'll look a bit silly.[/color]

              While it is true that an indirect call cannot be inlined (for obvious
              reasons), there is absolutely no problem with taking an address of an
              inline function. You seem to be mistaking two different things: inline
              functions and inlined calls to functions.
              [color=blue]
              > Trouble starts when you
              > attempt to export an inline function, though, and use it in multiple
              > modules. Such an inline function has to include its definition in every
              > module using it, usually via a header. If the compiler ends up not
              > inlining it, for whatever reason, this may result in a copy of its code
              > being placed in every module that uses it. Thus you should only export
              > small inline functions.[/color]

              That would be true in C++, but that's not necessarily true in C (C99).
              An inline function with external linkage in C can have external
              definition in addition to inline definition. The external definition can
              be reached from other translation units (by non-inline calls, of course).

              --
              Best regards,
              Andrey Tarasevich

              Comment

              • E. Robert Tisdale

                #8
                Re: Disadvantage of using 'inline'

                Method Man wrote:
                [color=blue]
                > If I don't care about the size of my executable or compile time,
                > is there any reason why I wouldn't want to inline every function in my code
                > to make the program run more efficient?[/color]

                No.
                You may find that you want to define than as "inline static"
                in a header file so that you don't get "multiply defined references".

                The idea behind inline functions is to encourage programmers
                to decompose functions into smaller functions
                and let the compiler "inline" them automatically
                instead of inlining them manually.
                This should result in code
                that is easier to read, understand and maintain
                while maximizing performance and efficiency.

                Comment

                • CBFalconer

                  #9
                  Re: Disadvantage of using 'inline'

                  "E. Robert Tisdale" wrote:[color=blue]
                  > Method Man wrote:
                  >[color=green]
                  >> If I don't care about the size of my executable or compile time,
                  >> is there any reason why I wouldn't want to inline every function
                  >> in my code to make the program run more efficient?[/color]
                  >
                  > No.
                  > You may find that you want to define than as "inline static"
                  > in a header file so that you don't get "multiply defined references".[/color]

                  If the function is static there is no point in mentioning it in
                  any header file. Headers should be used solely to export things
                  from a compilation unit. Static functions are not accessible
                  outside the compilation unit.
                  [color=blue]
                  >
                  > The idea behind inline functions is to encourage programmers to
                  > decompose functions into smaller functions and let the compiler
                  > "inline" them automatically instead of inlining them manually.
                  > This should result in code that is easier to read, understand and
                  > maintain while maximizing performance and efficiency.[/color]

                  This is accurate.

                  --
                  "It is not a question of staying the course, but of changing
                  the course" - John Kerry, 2004-09-20
                  "Ask any boat owner the eventual result of continuing the
                  present course indefinitely" - C.B. Falconer, 2004-09-20


                  Comment

                  • Mark F. Haigh

                    #10
                    Re: Disadvantage of using 'inline'

                    Dan.Pop@cern.ch (Dan Pop) wrote in message news:<cj0v6s$bo q$2@sunnews.cer n.ch>...[color=blue]
                    > In <flS4d.1112$By5 .199776@read2.c gocable.net> "Method Man" <a@b.c> writes:
                    >[color=green]
                    > >If I don't care about the size of my executable or compile time, is there
                    > >any reason why I wouldn't want to inline every function in my code to make
                    > >the program run more efficient?[/color]
                    >
                    > 1. inline is not a portable feature of C.
                    >
                    > 2. There is no guarantee that inlining everything is going to speed up
                    > your code. Larger executable means less efficient usage of the
                    > processor cache.
                    >[/color]

                    A larger executable may mean less efficient usage of the processor
                    cache, but it may not. As an obvious example, judicious loop
                    unrolling (by the compiler) often causes larger code, but faster code.
                    Of course, everything in moderation: if you unroll too much you will
                    cause icache (or trace cache) thrashing because your working sets keep
                    pushing each other out. That's really the essence of what Dan was
                    getting at.

                    As usual, there's a bunch of competing factors. Inlining small,
                    frequently *called* functions may be beneficial because it eliminates
                    function call overhead and allows CSE and other optimizations to be
                    performed within the context of the caller. This could translate to
                    fewer branches, which reduces the likelihood of mispredicted branches,
                    which can be costly.

                    Now I just said small, frequently *called* functions, but I did not
                    mean frequently *used* functions, unless they're so small that
                    function call overhead is more than, or a significant percentage of,
                    their execution time. By frequently used functions, I mean the ones
                    you find sprinkled all over the code, but not typically in performance
                    sensitive areas. These are what you do not want to inline, because
                    the code bloat is not worth it.

                    One big problem is that your inline function looks like a function to
                    you, and in the source code, but not to the processor. Inline
                    functions will not cause a hot spot in the cache. They decrease
                    locality. If your program calls a frequently used inline function
                    twice reasonably near each other, for example, the second call will
                    *not* find the function already sitting in cache, ready to go.
                    Granted, hardware prefetch may cause this to be a moot point in some
                    cases, but then again, the hardware prefetch would then be fetching
                    something that should already be in the cache, and displacing
                    something else that may be beneficial.

                    So what can you inline? Well, the best functions to inline are the
                    ones that are used exactly once and are static. It's hard to go wrong
                    with that. With anything else, you need to profile your code and be
                    familiar with the relative costs your architecture imposes on you. As
                    always, when in doubt, check your compiler's assembly output. You may
                    be pleasantly surprised to find that your compiler is good at figuring
                    out which functions to inline for you, under certain optimization
                    levels. And if you religiously use static functions, as you should,
                    the compiler has a much easier time at doing just that.

                    If you're serious about code performance, you need to be familiar with
                    the applicable profiling tools and with the increasingly popular
                    profile driven optimization. Profile driven optimization gives the
                    compiler a much better idea of which branches are taken and which are
                    not, so that it can output the best possible assembly. Now when you
                    combine that with profiling and subsequent inlining and tweaking, you
                    have the possibility of some very well performing code. But you're
                    not going to get that by simply inlining everything, that's for sure.


                    Mark F. Haigh
                    mfhaigh@sbcglob al.net

                    Comment

                    • Chris Barts

                      #11
                      Re: Disadvantage of using 'inline'

                      On Fri, 24 Sep 2004 17:49:12 -0700, Andrey Tarasevich wrote:
                      [color=blue]
                      > Derrick Coetzee wrote:[color=green]
                      >> ...
                      >> Placing the inline keyword on all static (module-local) functions is an
                      >> okay thing to do, if you trust your compiler; it'll figure out when not
                      >> to do it, although you can't take an inline function's address to call
                      >> it indirectly, and you'll look a bit silly.[/color]
                      >
                      > While it is true that an indirect call cannot be inlined (for obvious
                      > reasons), there is absolutely no problem with taking an address of an
                      > inline function. You seem to be mistaking two different things: inline
                      > functions and inlined calls to functions.
                      >[/color]

                      This seems odd to me, too: If the function `should' be inlined (and,
                      therefore, have no independent existence), what is the rationale for
                      allowing programmers to take its address? Wouldn't that pretty much defeat
                      the purpose, by forcing the compiler to generate code for the function at
                      a specific location?

                      My point of reference isn't C++, but the C `register' keyword. It turns
                      out that C compilers are under no obligation to listen to the programmer
                      about which variables to try and place in registers (and on plenty of
                      machines, there are so few registers that tying one up is stupid), but the
                      compiler is obligated to act as if it had by disallowing the taking of the
                      address of a register-qualified variable.

                      Comment

                      • Andrey Tarasevich

                        #12
                        Re: Disadvantage of using 'inline'

                        Chris Barts wrote:[color=blue][color=green][color=darkred]
                        >>> ...
                        >>> Placing the inline keyword on all static (module-local) functions is an
                        >>> okay thing to do, if you trust your compiler; it'll figure out when not
                        >>> to do it, although you can't take an inline function's address to call
                        >>> it indirectly, and you'll look a bit silly.[/color]
                        >>
                        >> While it is true that an indirect call cannot be inlined (for obvious
                        >> reasons), there is absolutely no problem with taking an address of an
                        >> inline function. You seem to be mistaking two different things: inline
                        >> functions and inlined calls to functions.
                        >>[/color]
                        >
                        > This seems odd to me, too: If the function `should' be inlined (and,
                        > therefore, have no independent existence), what is the rationale for
                        > allowing programmers to take its address?[/color]

                        Declaring a function as 'inline' never meant that is has no "independen t
                        existence".

                        The decision to inline a call is made by the compiler on a per-call
                        basis. Nothing in the language specification says that a function should
                        be either always inlined or never inlined. This has never been the
                        intention with inline functions. The compiler is completely free to
                        choose which concrete calls to inline and which not to inline.

                        It is obvious that in general case indirect calls cannot be inlined.
                        This, however, doesn't in any way prevent direct calls from being inlined.
                        [color=blue]
                        > Wouldn't that pretty much defeat
                        > the purpose, by forcing the compiler to generate code for the function at
                        > a specific location?[/color]

                        No. Why? Direct calls that have access to the inline definition of the
                        function can still be perfectly inlined. No problems here. Other calls
                        (indirect calls or calls that have no access to the inline definition)
                        are made in the "traditiona l" way. It is up to you to design and
                        organize your program the way that maximizes inlining (if that's what
                        you wish to achieve).
                        [color=blue]
                        > My point of reference isn't C++, but the C `register' keyword. It turns
                        > out that C compilers are under no obligation to listen to the programmer
                        > about which variables to try and place in registers (and on plenty of
                        > machines, there are so few registers that tying one up is stupid), but the
                        > compiler is obligated to act as if it had by disallowing the taking of the
                        > address of a register-qualified variable.[/color]

                        It is a bad analogy. The fundamental difference between function and
                        variables that makes this a bad analogy is that functions are "frozen",
                        they don't change. If some entity is "frozen", there's no problem in
                        keeping and using several copies of that entity - no one would ever
                        notice and no one would ever know which copy is being used in each
                        particular case.

                        With functions the property of being 'inline' is a property of the
                        function itself, while the property of being actually _inlined_ is a
                        property of a concrete function call. Different calls to the same
                        function can have different properties (i.e. they can be inlined or they
                        can be directed to a "regular" function body), they don't conflict with
                        each other. It is a very natural separation, it requires relatively
                        little effort from the compiler and imposes no performance penalties.

                        Variables, on the other hand, can change their values. In order to keep
                        several copies of a variable (a 'register' copy and a normal copy in
                        memory, to allow address taking) the program will have to make sure that
                        values stored in these copies are carefully synchronized. This is very
                        difficult, if at all possible (frankly, I don't think it is). And in any
                        case this will impose significant run-time performance penalty.

                        Now, with _const-qualified objects declared with 'register' keyword
                        address-taking would be easy to implement, just because constants are
                        similar to functions - they don't change.

                        --
                        Best regards,
                        Andrey Tarasevich

                        Comment

                        • Andrey Tarasevich

                          #13
                          Re: Disadvantage of using 'inline'

                          Chris Barts wrote:
                          [color=blue][color=green][color=darkred]
                          >>>>>> ...
                          >>>>>> Placing the inline keyword on all static (module-local) functions[/color][/color][/color]
                          is an[color=blue][color=green][color=darkred]
                          >>>>>> okay thing to do, if you trust your compiler; it'll figure out[/color][/color][/color]
                          when not[color=blue][color=green][color=darkred]
                          >>>>>> to do it, although you can't take an inline function's address to[/color][/color][/color]
                          call[color=blue][color=green][color=darkred]
                          >>>>>> it indirectly, and you'll look a bit silly.[/color]
                          >>[color=darkred]
                          >>>>
                          >>>> While it is true that an indirect call cannot be inlined (for obvious
                          >>>> reasons), there is absolutely no problem with taking an address of an
                          >>>> inline function. You seem to be mistaking two different things: inline
                          >>>> functions and inlined calls to functions.
                          >>>>[/color][/color]
                          >[color=green]
                          >>
                          >> This seems odd to me, too: If the function `should' be inlined (and,
                          >> therefore, have no independent existence), what is the rationale for
                          >> allowing programmers to take its address?[/color][/color]


                          Declaring a function as 'inline' never meant that is has no "independen t
                          existence".

                          The decision to inline a call is made by the compiler on a per-call
                          basis. Nothing in the language specification says that a function should
                          be either always inlined or never inlined. This has never been the
                          intention with inline functions. The compiler is completely free to
                          choose which concrete calls to inline and which not to inline.

                          It is obvious that in general case indirect calls cannot be inlined.
                          This, however, doesn't in any way prevent direct calls from being inlined.

                          [color=blue][color=green]
                          >> Wouldn't that pretty much defeat
                          >> the purpose, by forcing the compiler to generate code for the function at
                          >> a specific location?[/color][/color]


                          No. Why? Direct calls that have access to the inline definition of the
                          function can still be perfectly inlined. No problems here. Other calls
                          (indirect calls or calls that have no access to the inline definition)
                          are made in the "traditiona l" way. It is up to you to design and
                          organize your program the way that maximizes inlining (if that's what
                          you wish to achieve).

                          [color=blue][color=green]
                          >> My point of reference isn't C++, but the C `register' keyword. It turns
                          >> out that C compilers are under no obligation to listen to the programmer
                          >> about which variables to try and place in registers (and on plenty of
                          >> machines, there are so few registers that tying one up is stupid),[/color][/color]
                          but the[color=blue][color=green]
                          >> compiler is obligated to act as if it had by disallowing the taking[/color][/color]
                          of the[color=blue][color=green]
                          >> address of a register-qualified variable.[/color][/color]


                          It is a bad analogy. The fundamental difference between function and
                          variables that makes this a bad analogy is that functions are "frozen",
                          they don't change. If some entity is "frozen", there's no problem in
                          keeping and using several copies of that entity - no one would ever
                          notice and no one would ever know which copy is being used in each
                          particular case.

                          With functions the property of being 'inline' is a property of the
                          function itself, while the property of being actually _inlined_ is a
                          property of a concrete function call. Different calls to the same
                          function can have different properties (i.e. they can be inlined or they
                          can be directed to a "regular" function body), they don't conflict with
                          each other. It is a very natural separation, it requires relatively
                          little effort from the compiler and imposes no performance penalties.

                          Variables, on the other hand, can change their values. In order to keep
                          several copies of a variable (a 'register' copy and a normal copy in
                          memory, to allow address taking) the program will have to make sure that
                          values stored in these copies are carefully synchronized. This is very
                          difficult, if at all possible (frankly, I don't think it is). And in any
                          case this will impose significant run-time performance penalty.

                          Now, with _const-qualified objects declared with 'register' keyword
                          address-taking would be easy to implement, just because constants are
                          similar to functions - they don't change.

                          --
                          Best regards,
                          Andrey Tarasevich

                          Comment

                          • E. Robert Tisdale

                            #14
                            Re: Disadvantage of using 'inline'

                            CBFalconer wrote:
                            [color=blue]
                            > E. Robert Tisdale wrote:
                            >[color=green]
                            >>Method Man wrote:
                            >>[color=darkred]
                            >>>If I don't care about the size of my executable or compile time,
                            >>>is there any reason why I wouldn't want to inline every function
                            >>>in my code to make the program run more efficient?[/color]
                            >>
                            >>No.
                            >>You may find that you want to define than as "inline static"
                            >>in a header file so that you don't get "multiply defined references".[/color]
                            >
                            > If the function is static,
                            > there is no point in mentioning it in any header file.
                            > Headers should be used solely to export things from a compilation unit.
                            > Static functions are not accessible outside the compilation unit.[/color]
                            [color=blue]
                            > cat file.h[/color]
                            #ifndef GUARD_FILE_H
                            #define GUARD_FILE_H 1

                            inline
                            double f(double x) {
                            return x*(x + 2.0) + 1.0;
                            }

                            double g(double x);

                            #endif//GUARD_FILE_H
                            [color=blue]
                            > cat file.c[/color]
                            #include "file.h"

                            double g(double x) {
                            return f(x);
                            }
                            [color=blue]
                            > cat main.c[/color]
                            #include <stdio.h>
                            #include "file.h"

                            int main(int argc, char* argv[]) {
                            fprintf(stdout, "f(13.0) = %f\n", f(13.0));
                            fprintf(stdout, "g(13.0) = %f\n", g(13.0));
                            return 0;
                            }
                            [color=blue]
                            > gcc -Wall -std=c99 -pedantic -o main main.c file.c[/color]
                            /tmp/ccCBkYgj.o(.tex t+0x0): In function `f':
                            : multiple definition of `f'
                            /tmp/ccqaborv.o(.tex t+0x0): first defined here
                            collect2: ld returned 1 exit status

                            The definition of f(double)
                            must appear in both translation units if it is to be inlined
                            but the link editor will see multiple definitions
                            unless it is also static.

                            Comment

                            • Yevgen Muntyan

                              #15
                              Re: Disadvantage of using 'inline'

                              E. Robert Tisdale wrote:[color=blue]
                              >[/color]
                              ....[color=blue]
                              >[color=green]
                              > > gcc -Wall -std=c99 -pedantic -o main main.c file.c[/color]
                              > /tmp/ccCBkYgj.o(.tex t+0x0): In function `f':
                              > : multiple definition of `f'
                              > /tmp/ccqaborv.o(.tex t+0x0): first defined here
                              > collect2: ld returned 1 exit status
                              >
                              > The definition of f(double)
                              > must appear in both translation units if it is to be inlined
                              > but the link editor will see multiple definitions
                              > unless it is also static.[/color]



                              Comment

                              Working...