On Wed, Feb 13, 2019 at 5:21 PM Ian Lance Taylor <i...@golang.org> wrote:
>
> Nikhil Benesch noticed that changes in the GCC backend were making the
> use of defer functions that call recover less efficient.  A defer
> thunk is a generated function that looks like this (this is the entire
> function body):
>
>     if !runtime.setdeferretaddr(&L) {
>         deferredFunction()
>     }
> L:
>
> The idea is that the address of the label passed to setdeferretaddr is
> the address to which deferredFunction returns.  The code in canrecover
> compares the return address of the function to this saved address to
> see whether the recover function can return non-nil.  This is
> explained in marginally more detail at
> https://www.airs.com/blog/archives/376 .
>
> When the return address does not match, the canrecover code does a
> more costly check that requires unwinding the stack.  What Nikhil
> Benesch noticed is that we were always taking that fallback.
>
> It turned out that the label address passed to setdeferretaddr was not
> the label to which the deferred function would return.  And that was
> because the epilogue was being duplicated by the bb-reorder pass, and
> the label was moved to one copy of the epilogue while the deferred
> function returned to the other epilogue.
>
> Of course there is no reason to duplicate the epilogue in such a small
> function.  One easy way to disable that epilogue duplication is to
> compile the function with -Os.  That is what this patch does.  This
> patch compiles all thunks, not just defer thunks, with -Os, but since
> they are all small that does no harm.
>
> Bootstrapped and ran Go testsuite on x86_64-pc-linux-gnu.  Committed
> to mainline.
>
> Ian
>
> 2019-02-13  Ian Lance Taylor  <i...@golang.org>
>
> * go-gcc.cc: #include "opts.h".
> (Gcc_backend::function): Compile thunks with -Os.

This change revealed that changing function optimization attributes
can cause the compiler to switch to the options stored in
optimization_default_node.  That caused the change to
flag_strict_aliasing in go_imported_unsafe to be lost.  I fixed that
with this patch, which simply updates optimization_default_node.  I
don't know if there is a better way to do this.  For this patch
bootstrapped and ran Go testsuite on x86_64-pc-linux-gnu.  Committed
to mainline.

Ian

2019-02-14  Ian Lance Taylor  <i...@golang.org>

* go-backend.c (go_imported_unsafe): Update
optimization_default_node.
Index: go-backend.c
===================================================================
--- go-backend.c        (revision 268917)
+++ go-backend.c        (working copy)
@@ -89,6 +89,7 @@ void
 go_imported_unsafe (void)
 {
   flag_strict_aliasing = false;
+  TREE_OPTIMIZATION (optimization_default_node)->x_flag_strict_aliasing = 
false;
 
   /* Let the backend know that the options have changed.  */
   targetm.override_options_after_change ();

Reply via email to