On 26/08/2020 10:36, Erick Ochoa wrote:


On 25/08/2020 22:03, Richard Biener wrote:
On August 25, 2020 6:36:19 PM GMT+02:00, Erick Ochoa <erick.oc...@theobroma-systems.com> wrote:


On 25/08/2020 17:19, Erick Ochoa wrote:


On 25/08/2020 17:10, Richard Biener wrote:
On August 25, 2020 3:09:13 PM GMT+02:00, Erick Ochoa
<erick.oc...@theobroma-systems.com> wrote:
Hi,

I'm trying to understand how the escape analysis in IPA-PTA works.
I
was
testing a hypothesis where if a structure contains an array of
characters and this array of characters is passed to fopen, the
structure and all subfields will escape.

To do this, I made a program that has a global structure variable
foo2
that is has a field passed as an argument to fopen. I also made
another

variable foo whose array is initialized by the result of rand.

However, after compiling this program with -flto
-flto-partition=none
-fipa -fdump-ipa-pta -fdump-tree-all-all -Ofast (gcc --version
10.2.0)

E.g.

#include <stdio.h>
#include <math.h>
#include <string.h>

struct foo_t {
    char buffer1[100];
    char buffer2[100];
};

struct foo_t foo;
struct foo_t foo2;

int
main(int argc, char** argv)
{

    fopen(foo2.buffer1, "r");
    for (int i = 0; i < 100; i++)
    {
      foo.buffer1[i] = rand();
    }
    int i = rand();
    int retval = foo.buffer1[i % 100];
    return retval;
}

I see the PTA dump state the following:

ESCAPED = { STRING ESCAPED NONLOCAL foo2 }
foo = { ESCAPED NONLOCAL }
foo2 = { ESCAPED NONLOCAL }

which I understand as
* something externally visible might point to foo2
* foo2 might point to something externally visible
* foo might point to something externally visible

Yes. So it's exactly as your hypothesis.

I have seen that global variables are stored in the .gnu.lto_.decls
LTO

file section. In the passes I have worked on I have ignored global
variables. But can foo and foo2 be marked as escaping because the
declarations are not streamed in yet? Or is there another reason I
am
not seeing? I am aware of aware of the several TODOs at the
beginning
of
gcc/tree-ssa-structalias.c but I am unsure if they contribute to
these
variables being marked as escaping. (Maybe TODO 1 and TODO 2?)

Not sure what the problem is. Foo2 escapes because it's address is
passed to a function.


foo2 is not the problem, it is foo. foo is not passed to a function
and
it is also escaping.


Sorry, I meant: foo might point to something which is externally
visible. Which I don't think is the case in the program. I understand
this might be due to the imprecision in the escape-analysis and what
I'm
trying to find out is the source of imprecision.

Foo is exported and thus all function calls can store to it making it point to escaped and nonlocal variables.

Hi Richard,

I'm still not sure why foo can point to escaped and nonlocal variables.

My understanding is that ipa-visibility can mark variables and functions as not externally visible. Which I think is equivalent to excluding these symbols from the export table. I have printed the results of vnode->externally_visible and vnode->externally_visible_p() of foo and foo2 and both predicates return 0. (This is in a pass just before IPA-PTA). I think this means that both variables are not exported. IPA-PTA still says that foo can point to escaped memory.

ESCAPED = { NULL STRING ESCAPED NONLOCAL foo2 } // correct
foo = { ESCAPED NONLOCAL } same as _4 // my question
foo2 = { ESCAPED NONLOCAL } // correct

I then later declared foo as static. Which I think should mark the variable for internal linkage only. IPA-PTA still says that foo can point to escaped memory.

I also used the -fwhole-program flag and IPA-PTA still says that foo can point to escaped memory.

Am I failing to specify that foo must *not* be exported? Or IPA-PTA does not considering the visibility of symbols? Or there is something else I'm missing?

Hi Richard,

I think the reason why the global variables escape is because probably is_ipa_escape_point is not being used in all the places. According to the comments in tree-ssa-structalias.c

   The is_global_var bit which marks escape points is overly conservative
   in IPA mode.  Split it to is_escape_point and is_global_var - only
   externally visible globals are escape points in IPA mode.
   There is now is_ipa_escape_point but this is only used in a few
   selected places.

I had read this before, but the test I had made originally tested to see if a subfield escapes the whole global structure also escapes. I think there's another comment in tree-ssa-structalias.c that comments on this:

      /* ???  Force us to not use subfields for globals in IPA mode.
         Else we'd have to parse arbitrary initializers.  */

Thanks!



Thanks!


Richard.


?

Richard.

Just FYI, I've been reading:
* Structure Aliasing in GCC
* Gimple Alias Improvements for GCC 4.5
* Memory SSA - A Unified Approach for Sparsely Representing Memory
Operations

Thanks, I appreciate all help!


Reply via email to