Live data from Hacker News

GCC 7 Release Series – Changes, New Features, and Fixes

gcc.gnu.org

31–40 of 87 posts

Re: GCC 7 Release Series – Changes, New Features, and Fixes

#31

It attempts to move evaluation of expressions executed on all paths to the function *exit* as early as possible, which helps primarily for code size, but can be useful for speed of generated code as well. [Emphasis added.] Typo? PRE hoists upwards, so it would make sense to move closer to entry, not exit.

No, it's correct. It's saying "if they are always computed, we move them up". IE if (a) foo = a + b else b foo = a + b -> foo = a+b if (a) else (b)

How do you move up towards exit?

Re: GCC 7 Release Series – Changes, New Features, and Fixes

#32

Earlier quoted context omitted.

Naive question: if you move towards the exit of a function, wouldn't that be beneficial? That is, if a function terminates early, you're not evaluating the expressions unnecessarily, no?

The point of hoisting towards entry is to reduce code size, as the changelog indicates. It's safe to hoist the expression from program points P_{0..i..n-1} to some point Q that dominates all P_i if the expression is available at each P_i. That reduces the number of occurrences by n - 1. It's a basic corollary of PRE. This is identical to what LLVM's load-store motion does for loads, except for all expressions and not…

  This is identical to what LLVM's load-store motion does for 
  loads, except for all expressions and not just loads.
It's actually not. It's what GVNHoist does, but not MLSM. MLSM only handles diamonds.

In any case, because the GCC implementation is written on top of a sane PRE infrastructure, it is like 50 lines of code to do this :)

Re: GCC 7 Release Series – Changes, New Features, and Fixes

#34
post #14

It's only a matter of time before llvm/clang overshadows gcc in every aspect, if it hasn't already. clang probably has 10x more full-time developers than gcc does.

Maybe, maybe not. I've been seeing this comment for the past 7-6 years, and GCC still delivers better performance on the majority of real-world programs I benchmark (mostly compression). What I find very strange though is that some people seemingly want one of these projects to die. As is evident from many of the replies in this thread, having two great compiler toolchains with which to test your code is a great adva…

>What I find very strange though is that some people seemingly want one of these projects to die.

I'm not sure which side you were addressing here, so I'll cover both

Stallman wants the LLVM project to die for political reasons (he described it as "a terrible setback for our community" [1]). His argument is basically that LLVM can be used by non-free software, so it's mere existence is negative for the world because it enables non-free software. Also obviously it takes away resources that could have gone to improving GCC (although in my opinion a lot of them wouldn't for the reason below). It's an extreme argument, but it's the kind of extreme position Stallman has consistently taken so it's not surprising.

On the other side, one of the problems people have with GCC is that it's run by people who actively want to make worse software for political reasons. i.e. they'd rather software not support something at all if supporting it might benefit non-free software. That's fair enough, but it shouldn't be a surprise when users of the software prefer to use and support a project that isn't deliberately designed to make doing certain tasks very difficult. Academics and other people with an interest in hacking on compilers were obviously going to prefer a project that wasn't architected to try and prevent the very kinds of things they were doing.

The opposition to refactoring tools for emacs based on GCC is the most recent (2015) example of this[2], but the problem is a long standing one. Fundamentally people want to use compilers to do more sophisticated things with their code than just compile it, and that is seen as being incompatible with the political goals of the GCC project.

[1] https://gcc.gnu.org/ml/gcc/2014-01/msg00247.html

[2] https://lists.gnu.org/archive/html/emacs-devel/2015-02/msg00... and the rest of that thread

Re: GCC 7 Release Series – Changes, New Features, and Fixes

#35

Earlier quoted context omitted.

The point of hoisting towards entry is to reduce code size, as the changelog indicates. It's safe to hoist the expression from program points P_{0..i..n-1} to some point Q that dominates all P_i if the expression is available at each P_i. That reduces the number of occurrences by n - 1. It's a basic corollary of PRE. This is identical to what LLVM's load-store motion does for loads, except for all expressions and not…

This is identical to what LLVM's load-store motion does for loads, except for all expressions and not just loads. It's actually not. It's what GVNHoist does, but not MLSM. MLSM only handles diamonds. In any case, because the GCC implementation is written on top of a sane PRE infrastructure, it is like 50 lines of code to do this :)

  It's actually not. It's what GVNHoist does, but not MLSM. MLSM only handles diamonds.
Fine, it's what MLSM aspires to: http://llvm-cs.pcc.me.uk/lib/Transforms/Scalar/MergedLoadSto... (:

Re: GCC 7 Release Series – Changes, New Features, and Fixes

#36

Earlier quoted context omitted.

No, it's correct. It's saying "if they are always computed, we move them up". IE if (a) foo = a + b else b foo = a + b -> foo = a+b if (a) else (b)

How do you move up towards exit?

I think you have to read it like "executed on >all paths to the function exit< as early as possible". As in, if you have an expression that is always executed regardless which path you take before returning. It's useful to move that expression upwards instead of having copies on the different paths to the function exit.

Re: GCC 7 Release Series – Changes, New Features, and Fixes

#37
post #27
post #20

Earlier quoted context omitted.

That's what you get when you prefer programs that are merely open source to free software.

Open-source means the exact same thing as free software, there's just an ideological difference between the two. https://opensource.org/osd

It definitely does not mean the same thing, the OSD is not congruent to the four freedoms. They have significant overlap, but they are not equal sets.[1]

As a dumb example, the Open Watcom license is an "open source" license but is not a free software license because it is too restrictive. In the Open Watcom instance, the OSD does not protect the freedom for users to have private copies of software, the four freedoms do (or at least the modern interpretation does).

There's also the whole TiVo thing, where the modern interpretation of freedom 0 is restricted by DRM while "open source" software does not have any problems with DRM restricting users.

[1]: https://www.gnu.org/philosophy/open-source-misses-the-point....

Re: GCC 7 Release Series – Changes, New Features, and Fixes

#39

It attempts to move evaluation of expressions executed on all paths to the function *exit* as early as possible, which helps primarily for code size, but can be useful for speed of generated code as well. [Emphasis added.] Typo? PRE hoists upwards, so it would make sense to move closer to entry, not exit.

No, it's correct. It's saying "if they are always computed, we move them up". IE if (a) foo = a + b else b foo = a + b -> foo = a+b if (a) else (b)

Possible side effects correction:

    ->
      if (a)
      else (b)
      foo = a+b

Re: GCC 7 Release Series – Changes, New Features, and Fixes

#40
post #19

Earlier quoted context omitted.

My first experience with UB: foo(bar(), bar()); (where bar() was stateful) Discovering that g++ and clang++ compiled to one that did what I wanted and one that didn't was an interesting experience.

It gets even funnier in OCaml where they nominally defined it UB in order to get the freedom to make the only existing implementation always 100% reliably evaluate right-to-left, which reportedly was better for performance or something :) And before somebody wonders about currying and eager evaluation, the problem is not functions but type constructors, which aren't curried.

The functions arguments are pushed onto the stack. From within the function you can think of the stack as an array.

    void test(a, b, c)
        stack[0] == a
        stack[1] == b
        stack[2] == c
But to get the items in the stack in that order you have to...

    puch c
    push b
    push a
If you wanted to do that, and still allow for left to right evaluation you could...

    temp_a = a
    temp_b = b
    temp_c = c

    push c
    puch b
    push a

That would be 2x instructions for every (already expensive at that time) function call. Defining unordered evaluation as UB was to avoid having to do temp_a, temp_b, temp_c. Now compiles can do that and trivially optimize that sort of thing out.
Post reply on HN