On Fri, 2021-06-25 at 20:33 +0530, Ankur Saini wrote:
> AIM for today : 
> 
> - try to create an intra-procedural link between the calls the calling
> and returning snodes
> - figure out the program point where exploded graph would know about
> the function calls
> - figure out how the exploded node will know which function to call
> - create enodes and eedges for the calls
> 
> —
> 
> PROGRESS :
> 
> - I created an intraprocedural link between where the the splitting is 
> happening to connect the call and returning snodes. like this :-
> 
> (in supergraph.cc at "supergraph::supergraph (logger *logger)" )
> ```
> 185             if (cgraph_edge *edge = supergraph_call_edge (fun, stmt))
> 186             {
> 187                m_cgraph_edge_to_caller_prev_node.put(edge, 
> node_for_stmts);
> 188                node_for_stmts = add_node (fun, bb, as_a <gcall *> (stmt), 
> NULL);
> 189                m_cgraph_edge_to_caller_next_node.put (edge, 
> node_for_stmts);
> 190             }
> 191             else
> 192             {
> 193               gcall *call = dyn_cast<gcall *> (stmt);
> 194               if (call)
> 195               {
> 196                 supernode *old_node_for_stmts = node_for_stmts;
> 197                 node_for_stmts = add_node (fun, bb, as_a <gcall *> 
> (stmt), NULL);
                                                          ^^^^^^^^^^^^^^^^^^^^^
Given the dyn_cast of stmt to gcall * at line 193 you can use "call"
here, without the as_a cast, as you've already got "stmt" as a gcall *
as tline 193.

You might need to add a hash_map recording the mapping from such stmts
to the edges, like line 189 does.  I'm not sure, but you may need it
later.


> 198
> 199                 superedge *sedge = new callgraph_superedge 
> (old_node_for_stmts,
> 200                     node_for_stmts,
> 201                     SUPEREDGE_INTRAPROCEDURAL_CALL,
> 202                     NULL);
> 203                 add_edge (sedge);
> 204               }                
> 205             }
> ```
> 
> - now that we have a intraprocedural link between such calls, and the
> analyzer will consider them as “impossible edge” ( whenever a "node-
> >on_edge()” returns false ) while processing worklist, and I think this
> should be the correct place to speculate about the function call by
> creating exploded nodes and edges representing calls ( maybe by adding
> a custom edge info ).
> 
> - after several of failed attempts to do as mentioned above, looks like
> I was looking the wrong way all along. I think I just found out what my
> mentor meant when telling me to look into "calls node->on_edge”. During
> the edge inspection ( in program_point::on_edge() ) , if it’s an
> Intraprocedural s sedge, maybe I can add an extra intraprocedural sedge
> to the correct edge right here with the info state of that program
> point. 

I don't think we need a superedge for such a call, just an
exploded_edge.  (Though perhaps adding a superedge might make things
easier?  I'm not sure, but I'd first try not bothering to add one)

> 
> Q. But even if we find out which function to call, how will the
> analyzer know which snode does that function belong ?

Use this method of supergraph:
  supernode *get_node_for_function_entry (function *fun) const;
to get the supernode for the entrypoint of a given function.

You can get the function * from a fndecl via DECL_STRUCT_FUNCTION.

> Q. on line 461 of program-point.cc 
> 
> ```
> 457             else
> 458               {
> 459                 /* Otherwise, we ignore these edges  */
> 460                 if (logger)
> 461                   logger->log ("rejecting interprocedural edge");
> 462                 return false;
> 463               }
> ```
> why are we rejecting “interprocedural" edge when we are examining an
> “intraprocedural” edge ? or is it for the "cg_sedge->m_cedge” edge,
> which is an interprocedural edge ?

Currently, those interprocedural edges don't do much.  Above the "else"
clause of the lines above the ones you quote is some support for call
summaries.

The idea is that we ought to be able to compute summaries of what a
function call does, and avoid exponential explosions during the
analysis by reusing summaries at a callsite.  But that code doesn't
work well at the moment; see:
  https://gcc.gnu.org/bugzilla/showdependencytree.cgi?id=99390

If you ignore call summaries for now, I think you need to change this
logic so it detects if we have a function pointer that we "know" the
value of from the region_model, and have it generate an exploded_node
and exploded_edge for the call.  Have a look at how SUPEREDGE_CALL is
handled by program_state and program_point; you should implement
something similar, I think.  Given that you need both the super_edge,
point *and* state all together to detect this case, I think the logic
you need to add probably needs to be in exploded_node::on_edge as a
specialcase before the call there to next_point->on_edge.

Hope this is helpful
Dave


> 
> STATUS AT THE END OF THE DAY :- 
> 
> - try to create an intra-procedural link between the calls the calling
> and returning snodes ( Done )
> - figure out the program point where exploded graph would know about
> the function calls ( Done )
> - figure out how the exploded node will know which function to call (
> Pending )
> - create enodes and eedges for the calls ( Pending )
> 
> 
> Thank you
> - Ankur
> 
> > On 25-Jun-2021, at 2:23 AM, David Malcolm <dmalc...@redhat.com>
> > wrote:
> > 
> > On Thu, 2021-06-24 at 19:59 +0530, Ankur Saini wrote:
> > > CURRENT STATUS :
> > > 
> > > analyzer is now splitting nodes even at call sites which doesn’t
> > > have
> > > a cgraph_edge. But as now the call and return nodes are not
> > > connected, the part of the function after such calls becomes
> > > unreachable making them impossible to properly analyse.
> > > 
> > > AIM for today : 
> > > 
> > > - try to create an intra-procedural link between the calls the
> > > calling and returning snodes 
> > > - find the place where the exploded nodes and edges are being
> > > formed 
> > > - figure out the program point where exploded graph would know
> > > about
> > > the function calls
> > > 
> > > —
> > > 
> > > PROGRESS :
> > > 
> > > - I initially tried to connect the calling and returning snodes
> > > with
> > > an intraprocedural sedge but looks like for that only nodes which
> > > have a cgraph_edge or a CFG edge are connected in the supergraph. I
> > > tried a few ways to connect them but at the end thought I would be
> > > better off leaving them like this and connecting them during the
> > > creation of exploded graph itself.
> > > 
> > > - As the exploded graph is created during building and processing
> > > of
> > > the worklist, "build_initial_worklist ()” and “process_worklist()”
> > > should be the interesting areas to analyse, especially the
> > > processing
> > > part.
> > > 
> > > - “build_initial_worklist()” is just creating enodes for functions
> > > that can be called explicitly ( possible entry points ) so I guess
> > > the better place to investigate is “process_worklist ()” function.
> > 
> > Yes.
> > 
> > Have a look at exploded_graph::process_node (which is called by
> > process_worklist).
> > The eedges for calls with supergraph edges happens there in
> > the "case PK_AFTER_SUPERNODE:", which looks at the outgoing
> > superedges
> > from that supernode and calls node->on_edge on them, creating a
> > exploded nodes/exploded edge for each outgoing-superedge.
> > 
> > So you'll need to make some changes there, I think.
> > 
> > > 
> > > —
> > > 
> > > STATUS AT THE END OF THE DAY :- 
> > > 
> > > - try to create an intra-procedural link between the calls the
> > > calling and returning snodes ( Abandoned )
> > 
> > You may find the above useful if you're going to do it based on the
> > code I mentioned above.
> > 
> > > - find the place where the exploded nodes and edges are being
> > > formed
> > > ( Done )
> > > - figure out the program point where exploded graph knows about the
> > > function call ( Pending )
> > > 
> > 
> > Thanks for the update.
> > Hope the above is helpful.
> > 
> > Dave
> 


Reply via email to