Hi,
currently in trunk, every edge contains a 16 bit field called
callback_id, which is used to link callback edges to their attributes,
from which all additional information is calculated as is needed.

This patch adds a new summary struct for callback edges, called
callback_info.  It allows us to remove callback_id from the main class
and aggregate all relevant information, without having to calculate
every single time.  Contents of the summary are up for debate, the main
focus of this patch is to get rid of callback_id, it's a waste of memory
of most edges.

Bootstrapped, LTO-bootstrapped and regtested on x86_64-linux without
issues.  Bootstrap with --enable-checking=valgrind is currently
underway. I am not sure if there is any other way to check for memleaks.

OK for master, or is it more of a stage1 contribution?

Best regards,
Josef

gcc/ChangeLog:

        * Makefile.in: Add callback-info.o to OBJS.
        * attr-callback.cc (callback_fetch_attr_by_edge): Use id in
        callback_info summary.
        (callback_get_arg_mapping): Delete, replaced by
        callback_get_arg_mapping_from_attr and the summary field.
        (callback_get_arg_mapping_from_attr): New function, parses the
        attribute and returns the computed argument mapping.
        (callback_fetch_fn_position): Delete, obsoleted by the summary.
        (callback_edge_useful_p): Check for redirected flag in the
        summary instead of cgraph_node fields.
        * attr-callback.h (enum callback_position): Add
        CB_UNKNOWN_POS_IDX for better readability.
        (callback_get_arg_mapping): Delete.
        (callback_fetch_fn_position): Delete.
        (callback_get_arg_mapping_from_attr): New function decl.
        * cgraph.cc (symbol_table::create_edge): Remove callback_id
        initializer.
        (cgraph_edge::make_callback): Likewise.
        (cgraph_edge::redirect_callee): Set redirected flag in the
        summary when redirecting a callback edge.
        (cgraph_edge::redirect_call_stmt_to_callee): Utilize the
        summary.
        (cgraph_node::verify_node): Remove callback_id sanity checks.
        (cgraph_cc_finalize): Free callback summaries.
        * cgraph.h: Remove the callback_id field.
        * cgraphclones.cc (cgraph_edge::clone): Remove callback_id.
        * ipa-cp.cc (ipcp_driver): Initialize the summary sum.
        * ipa-prop.cc (init_callback_edge_summary): Initialize the
        summary.
        (ipa_compute_jump_functions_for_edge): Remove callback_id,
        utilize the summary information.
        (ipa_analyze_node): Initialize the summary sum.
        (ipa_register_cgraph_hooks): Likewise.
        * lto-cgraph.cc (lto_output_edge): Remove callback_id, stream
        out the summary.
        (output_symtab): Initialize the summary sum.
        (input_edge): Remove callback_id, stream in the summary.
        (input_cgraph_1): Initialize the summary sum.
        * callback-info.cc: New file.
        * callback-info.h: New file.

Signed-off-by: Josef Melcr <[email protected]>
---
 gcc/Makefile.in      |  3 +-
 gcc/attr-callback.cc | 40 +++++-------------
 gcc/attr-callback.h  | 17 ++++----
 gcc/callback-info.cc | 98 ++++++++++++++++++++++++++++++++++++++++++++
 gcc/callback-info.h  | 69 +++++++++++++++++++++++++++++++
 gcc/cgraph.cc        | 25 ++++-------
 gcc/cgraph.h         |  6 +--
 gcc/cgraphclones.cc  |  1 -
 gcc/ipa-cp.cc        |  3 ++
 gcc/ipa-prop.cc      | 31 +++++++++-----
 gcc/lto-cgraph.cc    | 17 +++++++-
 11 files changed, 234 insertions(+), 76 deletions(-)
 create mode 100644 gcc/callback-info.cc
 create mode 100644 gcc/callback-info.h

diff --git a/gcc/Makefile.in b/gcc/Makefile.in
index d62314505c9..60a15ee315f 100644
--- a/gcc/Makefile.in
+++ b/gcc/Makefile.in
@@ -1854,6 +1854,7 @@ OBJS = \
        wide-int.o \
        wide-int-print.o \
        attr-callback.o \
+       callback-info.o \
        $(out_object_file) \
        $(ANALYZER_OBJS) \
        $(EXTRA_OBJS) \
@@ -3165,7 +3166,7 @@ ALL_GTFILES_H := $(sort $(GTFILES_H) $(GTFILES_LANG_H))
 $(ALL_GTFILES_H) gtype-desc.cc gtype-desc.h gtype.state: s-gtype ; @true
 
 ### Common flags to gengtype [e.g. -v or -B backupdir]
-GENGTYPE_FLAGS= 
+GENGTYPE_FLAGS=
 
 gtyp-input.list: s-gtyp-input ; @true
 s-gtyp-input: Makefile
diff --git a/gcc/attr-callback.cc b/gcc/attr-callback.cc
index f116f0472f3..76374f1e6b1 100644
--- a/gcc/attr-callback.cc
+++ b/gcc/attr-callback.cc
@@ -31,7 +31,10 @@
 #include "options.h"
 #include "gimple-range.h"
 #include "attribs.h"
+#include "symbol-summary.h"
+#include "lto-streamer.h"
 #include "attr-callback.h"
+#include "callback-info.h"
 
 /* Returns a callback attribute with callback index FN_IDX, and ARG_COUNT
    arguments specified by VA_ARGS.  */
@@ -116,12 +119,13 @@ callback_fetch_attr_by_edge (cgraph_edge *e, cgraph_edge 
*carrying)
   tree cb_attr = lookup_attribute (CALLBACK_ATTR_IDENT,
                                   DECL_ATTRIBUTES (carrying->callee->decl));
   gcc_checking_assert (cb_attr);
+  callback_info *ci = callback_info_sum->get (e);
   tree res = NULL_TREE;
   for (; cb_attr;
        cb_attr = lookup_attribute (CALLBACK_ATTR_IDENT, TREE_CHAIN (cb_attr)))
     {
       unsigned id = callback_get_fn_index (cb_attr);
-      if (id == e->callback_id)
+      if (id == ci->id)
        {
          res = cb_attr;
          break;
@@ -131,15 +135,11 @@ callback_fetch_attr_by_edge (cgraph_edge *e, cgraph_edge 
*carrying)
   return res;
 }
 
-/* Given an instance of callback attribute, return the 0-base indices
-   of arguments passed to the callback.  For a callback function taking
-   n parameters, returns a vector of n indices of their values in the parameter
-   list of it's caller.  Indices with unknown positions contain -1.  */
+/* Returns the argument mapping from the dispatching function to the callback
+   function parsed from the attribute.  */
 auto_vec<int>
-callback_get_arg_mapping (cgraph_edge *e, cgraph_edge *carrying)
+callback_get_arg_mapping_from_attr (tree attr)
 {
-  tree attr = callback_fetch_attr_by_edge (e, carrying);
-  gcc_checking_assert (attr);
   tree args = TREE_VALUE (attr);
   auto_vec<int> res;
   tree it;
@@ -158,15 +158,6 @@ callback_get_arg_mapping (cgraph_edge *e, cgraph_edge 
*carrying)
   return res;
 }
 
-/* For a callback pair, returns the 0-based index of the address of
-   E's callee in the argument list of CARRYING's callee decl.  */
-int
-callback_fetch_fn_position (cgraph_edge *e, cgraph_edge *carrying)
-{
-  tree attr = callback_fetch_attr_by_edge (e, carrying);
-  return callback_get_fn_index (attr);
-}
-
 /* Returns the element at index idx in the list or NULL_TREE if
    the list isn't long enough.  NULL_TREE is used as the endpoint.  */
 static tree
@@ -353,19 +344,8 @@ bool
 callback_edge_useful_p (cgraph_edge *e)
 {
   gcc_checking_assert (e->callback);
-  /* If the edge is pointing towards a clone, it is useful.  */
-  if (e->callee->clone_of)
-    return true;
-
-  /* If the callee has been produced by icf, the edge is useful, as it will be
-     used to for the redirection.  */
-  if (e->callee->icf_merged)
-    return true;
-
-  /* In case some future pass redirects edges, it should be added as a case
-     here.  */
-
-  return false;
+  callback_info *ci = callback_info_sum->get (e);
+  return ci->redirected;
 }
 
 /* Returns the number of arguments the callback function described by ATTR
diff --git a/gcc/attr-callback.h b/gcc/attr-callback.h
index 39a4fe8ac94..34e4e08d665 100644
--- a/gcc/attr-callback.h
+++ b/gcc/attr-callback.h
@@ -25,7 +25,10 @@ enum callback_position
 {
   /* Value used when an argument of a callback function
      is unknown or when multiple values may be used. */
-  CB_UNKNOWN_POS = 0
+  CB_UNKNOWN_POS = 0,
+  /* Value representing an unknown argument position in the arg_mapping
+     vector.  */
+  CB_UNKNOWN_POS_IDX = -1
 };
 
 #define CALLBACK_ATTR_IDENT " callback"
@@ -54,15 +57,9 @@ int callback_get_fn_index (tree cb_attr);
    to create E from the callee of CARRYING.  */
 tree callback_fetch_attr_by_edge (cgraph_edge *e, cgraph_edge *carrying);
 
-/* Given an instance of callback attribute, return the 0-base indices
-   of arguments passed to the callback.  For a callback function taking
-   n parameters, returns a vector of n indices of their values in the parameter
-   list of it's caller.  Indices with unknown positions contain -1.  */
-auto_vec<int> callback_get_arg_mapping (cgraph_edge *e, cgraph_edge *carrying);
-
-/* For a callback pair, returns the 0-based index of the address of
-   E's callee in the argument list of CARRYING's callee decl.  */
-int callback_fetch_fn_position (cgraph_edge *e, cgraph_edge *carrying);
+/* Returns the argument mapping from the dispatching function to the callback
+   function parsed from the attribute.  */
+auto_vec<int> callback_get_arg_mapping_from_attr (tree attr);
 
 /* Handle a "callback" attribute; arguments as in
    struct attribute_spec.handler.  */
diff --git a/gcc/callback-info.cc b/gcc/callback-info.cc
new file mode 100644
index 00000000000..cec44937c25
--- /dev/null
+++ b/gcc/callback-info.cc
@@ -0,0 +1,98 @@
+/* Callback attribute summary
+   Copyright (C) 2025 Free Software Foundation, Inc.
+   Contributed by Josef Melcr <[email protected]>
+
+   This file is part of GCC.
+
+   GCC is free software; you can redistribute it and/or modify
+   under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 3 of the License, or
+   (at your option) any later version.
+
+   GCC is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with GCC; see the file COPYING3.  If not see
+   <http://www.gnu.org/licenses/>.  */
+
+#include "config.h"
+#include "system.h"
+#include "coretypes.h"
+#include "backend.h"
+#include "tree.h"
+#include "gimple.h"
+#include "alloc-pool.h"
+#include "cgraph.h"
+#include "diagnostic.h"
+#include "builtins.h"
+#include "options.h"
+#include "gimple-range.h"
+#include "attribs.h"
+#include "symbol-summary.h"
+#include "data-streamer.h"
+#include "callback-info.h"
+
+callback_info_sum_t *callback_info_sum = NULL;
+
+void
+callback_info::stream_out (lto_simple_output_block *ob) const
+{
+  streamer_write_uhwi_stream (ob->main_stream, id);
+  streamer_write_uhwi_stream (ob->main_stream, fn_idx);
+  streamer_write_uhwi_stream (ob->main_stream, arg_mapping.length ());
+
+  for (int idx : arg_mapping)
+    streamer_write_hwi_stream (ob->main_stream, idx);
+
+  bitpack_d bp = bitpack_create (ob->main_stream);
+  bp_pack_value (&bp, redirected, 1);
+  streamer_write_bitpack (&bp);
+}
+
+void
+callback_info::stream_in (lto_input_block *ib)
+{
+  id = streamer_read_uhwi (ib);
+  fn_idx = streamer_read_uhwi (ib);
+  unsigned length = streamer_read_uhwi (ib);
+  arg_mapping.reserve (length);
+
+  for (unsigned i = 0; i < length; i++)
+    {
+      int idx = streamer_read_hwi (ib);
+      arg_mapping.safe_push (idx);
+    }
+
+  bitpack_d bp = streamer_read_bitpack (ib);
+  redirected = bp_unpack_value (&bp, 1);
+}
+
+void
+callback_info_sum_t::check_create_info_sum (void)
+{
+  if (!callback_info_sum)
+    callback_info_sum = new callback_info_sum_t (symtab, false);
+}
+
+void
+callback_info_sum_t::free_info_sum (void)
+{
+  if (callback_info_sum)
+    delete callback_info_sum;
+  callback_info_sum = NULL;
+}
+
+void
+callback_info_sum_t::duplicate (cgraph_edge *, cgraph_edge *,
+                               callback_info *src_s, callback_info *dst_s)
+{
+  dst_s->id = src_s->id;
+  dst_s->fn_idx = src_s->fn_idx;
+  /* Might need to be adjusted in the future, if argument modifications are
+     implemented.  */
+  dst_s->arg_mapping = src_s->arg_mapping.copy ();
+  dst_s->redirected = src_s->redirected;
+}
diff --git a/gcc/callback-info.h b/gcc/callback-info.h
new file mode 100644
index 00000000000..1745e7f83d6
--- /dev/null
+++ b/gcc/callback-info.h
@@ -0,0 +1,69 @@
+/* Callback attribute summary
+   Copyright (C) 2025 Free Software Foundation, Inc.
+   Contributed by Josef Melcr <[email protected]>
+
+   This file is part of GCC.
+
+   GCC is free software; you can redistribute it and/or modify
+   under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 3 of the License, or
+   (at your option) any later version.
+
+   GCC is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with GCC; see the file COPYING3.  If not see
+   <http://www.gnu.org/licenses/>.  */
+
+#ifndef CALLBACK_INFO_H
+#define CALLBACK_INFO_H
+
+/* Summary aggregating all information relevant to callback edges.  Most of the
+   information can be calculated from the attribute as well, but keeping it
+   separate allows us to modify the info without touching the underlying
+   attribute.  */
+class callback_info
+{
+public:
+  /* Callback attribute identifier, currently the fn index.  */
+  unsigned id;
+  /* Index of the callback function in the argument list.  */
+  unsigned fn_idx;
+  /* Mapping from the dispatching function's arguments to the callback 
function.
+   */
+  auto_vec<int> arg_mapping;
+  /* TRUE iff the associated callback edge was redirected.  */
+  bool redirected;
+
+  /* Stream in callback_info.  */
+  void stream_in (lto_input_block *ib);
+
+  /* Stream out callback_info.  */
+  void stream_out (lto_simple_output_block *ib) const;
+};
+
+
+class callback_info_sum_t : public call_summary<callback_info *>
+{
+public:
+  callback_info_sum_t (symbol_table *table, bool ggc)
+    : call_summary<callback_info *> (table, ggc)
+  {}
+
+  /* Populates the callback_info_sum if it's NULL.  */
+  static void check_create_info_sum ();
+
+  /* Frees the callback_info_sum pointer.  */
+  static void free_info_sum ();
+
+  /* Duplication function for the cgraph_edge duplication hook.  */
+  void duplicate (cgraph_edge *src, cgraph_edge *dst, callback_info *src_s,
+                 callback_info *dst_s) override;
+};
+
+extern callback_info_sum_t *callback_info_sum;
+
+#endif /* CALLBACK_INFO_H */
diff --git a/gcc/cgraph.cc b/gcc/cgraph.cc
index 1a7d49922e0..315b4de15b7 100644
--- a/gcc/cgraph.cc
+++ b/gcc/cgraph.cc
@@ -70,6 +70,7 @@ along with GCC; see the file COPYING3.  If not see
 #include "symtab-thunks.h"
 #include "symtab-clones.h"
 #include "attr-callback.h"
+#include "callback-info.h"
 
 /* FIXME: Only for PROP_loops, but cgraph shouldn't have to know about this.  
*/
 #include "tree-pass.h"
@@ -1107,7 +1108,6 @@ symbol_table::create_edge (cgraph_node *caller, 
cgraph_node *callee,
   edge->speculative = false;
   edge->has_callback = false;
   edge->callback = false;
-  edge->callback_id = 0;
   edge->indirect_unknown_callee = indir_unknown_callee;
   if (call_stmt && caller->call_site_hash)
     cgraph_add_edge_to_call_site_hash (edge);
@@ -1341,13 +1341,10 @@ cgraph_edge::make_speculative (cgraph_node *n2, 
profile_count direct_count,
    the callback-carrying edge, which is the instance this method
    is called on.
 
-   callback_id is used to pair the returned edge with the attribute that
-   originated it.
-
    Return the resulting callback edge.  */
 
 cgraph_edge *
-cgraph_edge::make_callback (cgraph_node *n2, unsigned int callback_id)
+cgraph_edge::make_callback (cgraph_node *n2)
 {
   cgraph_node *n = caller;
   cgraph_edge *e2;
@@ -1362,7 +1359,6 @@ cgraph_edge::make_callback (cgraph_node *n2, unsigned int 
callback_id)
       callee->dump_name ());
   e2->inline_failed = CIF_CALLBACK_EDGE;
   e2->callback = true;
-  e2->callback_id = callback_id;
   if (TREE_NOTHROW (n2->decl))
     e2->can_throw_external = false;
   else
@@ -1692,7 +1688,7 @@ cgraph_edge::redirect_callee (cgraph_node *n)
       /* When redirecting a callback callee, redirect its ref as well.  */
       ipa_ref *old_ref = caller->find_reference (old_callee, call_stmt,
                                                 lto_stmt_uid, IPA_REF_ADDR);
-      gcc_checking_assert(old_ref);
+      gcc_checking_assert (old_ref);
       old_ref->remove_reference ();
       ipa_ref *new_ref = caller->create_reference (n, IPA_REF_ADDR, call_stmt);
       new_ref->lto_stmt_uid = lto_stmt_uid;
@@ -1702,6 +1698,8 @@ cgraph_edge::redirect_callee (cgraph_node *n)
       if (!old_callee->iterate_referring (0, old_ref))
        old_callee->address_taken = 0;
       n->mark_address_taken ();
+      callback_info *ci = callback_info_sum->get (this);
+      ci->redirected = true;
     }
 
   if (!inline_failed)
@@ -1833,11 +1831,11 @@ cgraph_edge::redirect_call_stmt_to_callee (cgraph_edge 
*e,
           signature, as the indices wouldn't be correct anymore.  These edges
           will get cleaned up later, ignore their redirection for now.  */
        return e->call_stmt;
-      int fn_idx = callback_fetch_fn_position (e, carrying);
-      tree previous_arg = gimple_call_arg (e->call_stmt, fn_idx);
+      callback_info *ci = callback_info_sum->get (e);
+      tree previous_arg = gimple_call_arg (e->call_stmt, ci->fn_idx);
       location_t loc = EXPR_LOCATION (previous_arg);
       tree new_addr = build_fold_addr_expr_loc (loc, e->callee->decl);
-      gimple_call_set_arg (e->call_stmt, fn_idx, new_addr);
+      gimple_call_set_arg (e->call_stmt, ci->fn_idx, new_addr);
       return e->call_stmt;
     }
 
@@ -4328,12 +4326,6 @@ cgraph_node::verify_node (void)
 
       for (e = callees; e; e = e->next_callee)
        {
-         if (!e->callback && e->callback_id)
-           {
-             error ("non-callback edge has callback_id set");
-             error_found = true;
-           }
-
          if (e->callback && e->has_callback)
            {
              error ("edge has both callback and has_callback set");
@@ -4645,6 +4637,7 @@ cgraph_cc_finalize (void)
   nested_function_info::release ();
   thunk_info::release ();
   clone_info::release ();
+  callback_info_sum_t::free_info_sum ();
   symtab = NULL;
 
   x_cgraph_nodes_queue = NULL;
diff --git a/gcc/cgraph.h b/gcc/cgraph.h
index 313610fbe2c..0276e7652c8 100644
--- a/gcc/cgraph.h
+++ b/gcc/cgraph.h
@@ -1792,7 +1792,7 @@ public:
      passed to a function by argument.  Sets has_callback flag of the original
      edge. Both edges are attached to the same call statement.  Returns created
      callback edge.  */
-  cgraph_edge *make_callback (cgraph_node *n2, unsigned int callback_hash);
+  cgraph_edge *make_callback (cgraph_node *n2);
 
   /* Returns the callback-carrying edge of a callback edge or NULL, if such 
edge
      cannot be found.  An edge is considered callback-carrying, if it has it's
@@ -2048,10 +2048,6 @@ public:
      that the callee of this edge takes a function and it's parameters by
      argument and calls it at a later time.  */
   unsigned int has_callback : 1;
-  /* Used to pair callback edges and the attributes that originated them
-     together.  Currently the index of the callback argument, retrieved
-     from the attribute.  */
-  unsigned int callback_id : 16;
   /* Set to true when caller is a constructor or destructor of polymorphic
      type.  */
   unsigned in_polymorphic_cdtor : 1;
diff --git a/gcc/cgraphclones.cc b/gcc/cgraphclones.cc
index 816fc53c28a..a21e86740e8 100644
--- a/gcc/cgraphclones.cc
+++ b/gcc/cgraphclones.cc
@@ -146,7 +146,6 @@ cgraph_edge::clone (cgraph_node *n, gcall *call_stmt, 
unsigned stmt_uid,
   new_edge->speculative = speculative;
   new_edge->callback = callback;
   new_edge->has_callback = has_callback;
-  new_edge->callback_id = callback_id;
   new_edge->in_polymorphic_cdtor = in_polymorphic_cdtor;
 
   /* Update IPA profile.  Local profiles need no updating in original.  */
diff --git a/gcc/ipa-cp.cc b/gcc/ipa-cp.cc
index 2105c9a2ef7..d6a73d04f98 100644
--- a/gcc/ipa-cp.cc
+++ b/gcc/ipa-cp.cc
@@ -132,6 +132,8 @@ along with GCC; see the file COPYING3.  If not see
 #include "symtab-clones.h"
 #include "gimple-range.h"
 #include "attr-callback.h"
+#include "lto-streamer.h"
+#include "callback-info.h"
 
 /* Allocation pools for values and their sources in ipa-cp.  */
 
@@ -6478,6 +6480,7 @@ ipcp_driver (void)
 
   ipa_check_create_node_params ();
   ipa_check_create_edge_args ();
+  callback_info_sum_t::check_create_info_sum ();
   clone_num_suffixes = new hash_map<const char *, unsigned>;
 
   if (dump_file)
diff --git a/gcc/ipa-prop.cc b/gcc/ipa-prop.cc
index 2debbe10de3..5dac5e578b8 100644
--- a/gcc/ipa-prop.cc
+++ b/gcc/ipa-prop.cc
@@ -63,6 +63,7 @@ along with GCC; see the file COPYING3.  If not see
 #include "lto-streamer.h"
 #include "attribs.h"
 #include "attr-callback.h"
+#include "callback-info.h"
 
 /* Function summary where the parameter infos are actually stored. */
 ipa_node_params_t *ipa_node_params_sum = NULL;
@@ -2426,12 +2427,18 @@ skip_a_safe_conversion_op (tree t)
    This primarily means allocating the correct amount of jump functions.  */
 
 static inline void
-init_callback_edge_summary (struct cgraph_edge *cbe, tree attr)
+init_callback_edge_summary (struct cgraph_edge *cbe, unsigned id,
+                           unsigned fn_idx, tree attr)
 {
+  callback_info *ci = callback_info_sum->get_create (cbe);
+  ci->id = id;
+  ci->fn_idx = fn_idx;
+  ci->arg_mapping = callback_get_arg_mapping_from_attr (attr);
+  ci->redirected = false;
+
   ipa_edge_args *cb_args = ipa_edge_args_sum->get_create (cbe);
-  size_t jf_vec_length = callback_num_args(attr);
-  vec_safe_grow_cleared (cb_args->jump_functions,
-                        jf_vec_length, true);
+  vec_safe_grow_cleared (cb_args->jump_functions, ci->arg_mapping.length (),
+                        true);
 }
 
 /* Compute jump function for all arguments of callsite CS and insert the
@@ -2580,10 +2587,10 @@ ipa_compute_jump_functions_for_edge (struct 
ipa_func_body_info *fbi,
                    {
                      cgraph_node *kernel_node
                        = cgraph_node::get_create (pointee);
-                     unsigned callback_id = n;
-                     cgraph_edge *cbe
-                       = cs->make_callback (kernel_node, callback_id);
-                     init_callback_edge_summary (cbe, callback_attr);
+                     cgraph_edge *cbe = cs->make_callback (kernel_node);
+                     /* Callbck attribute's id is currently the function's
+                        index.  */
+                     init_callback_edge_summary (cbe, n, n, callback_attr);
                      callback_edges.safe_push (cbe);
                    }
                }
@@ -2659,12 +2666,12 @@ ipa_compute_jump_functions_for_edge (struct 
ipa_func_body_info *fbi,
          cgraph_edge *callback_edge = callback_edges[j];
          ipa_edge_args *cb_summary
            = ipa_edge_args_sum->get_create (callback_edge);
-         auto_vec<int> arg_mapping
-           = callback_get_arg_mapping (callback_edge, cs);
+         callback_info *ci = callback_info_sum->get (callback_edge);
+         auto_vec<int> &arg_mapping = ci->arg_mapping;
          unsigned i;
          for (i = 0; i < arg_mapping.length (); i++)
            {
-             if (arg_mapping[i] == -1)
+             if (arg_mapping[i] == CB_UNKNOWN_POS_IDX)
                continue;
              class ipa_jump_func *src
                = ipa_get_ith_jump_func (args, arg_mapping[i]);
@@ -3365,6 +3372,7 @@ ipa_analyze_node (struct cgraph_node *node)
 
   ipa_check_create_node_params ();
   ipa_check_create_edge_args ();
+  callback_info_sum_t::check_create_info_sum ();
   info = ipa_node_params_sum->get_create (node);
 
   if (info->analysis_done)
@@ -4943,6 +4951,7 @@ ipa_register_cgraph_hooks (void)
 {
   ipa_check_create_node_params ();
   ipa_check_create_edge_args ();
+  callback_info_sum_t::check_create_info_sum ();
 
   function_insertion_hook_holder =
       symtab->add_cgraph_insertion_hook (&ipa_add_new_function, NULL);
diff --git a/gcc/lto-cgraph.cc b/gcc/lto-cgraph.cc
index 4c60bf0dd74..ed89b48333b 100644
--- a/gcc/lto-cgraph.cc
+++ b/gcc/lto-cgraph.cc
@@ -44,6 +44,7 @@ along with GCC; see the file COPYING3.  If not see
 #include "symbol-summary.h"
 #include "symtab-thunks.h"
 #include "symtab-clones.h"
+#include "callback-info.h"
 
 static void output_cgraph_opt_summary (void);
 static void input_cgraph_opt_summary (vec<symtab_node *>  nodes);
@@ -278,7 +279,6 @@ lto_output_edge (struct lto_simple_output_block *ob, struct 
cgraph_edge *edge,
   bp_pack_value (&bp, edge->speculative, 1);
   bp_pack_value (&bp, edge->callback, 1);
   bp_pack_value (&bp, edge->has_callback, 1);
-  bp_pack_value (&bp, edge->callback_id, 16);
   bp_pack_value (&bp, edge->call_stmt_cannot_inline_p, 1);
   gcc_assert (!edge->call_stmt_cannot_inline_p
              || edge->inline_failed != CIF_BODY_NOT_AVAILABLE);
@@ -304,6 +304,11 @@ lto_output_edge (struct lto_simple_output_block *ob, 
struct cgraph_edge *edge,
                     16);
     }
   streamer_write_bitpack (&bp);
+  if (edge->callback)
+    {
+      callback_info *ci = callback_info_sum->get (edge);
+      ci->stream_out (ob);
+    }
 }
 
 /* Return if NODE contain references from other partitions.  */
@@ -1035,6 +1040,7 @@ output_symtab (void)
        lto_output_varpool_node (ob, vnode, encoder);
     }
 
+  callback_info_sum_t::check_create_info_sum ();
   /* Go over the nodes in SET again to write edges.  */
   for (int i = 0; i < lto_symtab_encoder_size (encoder); i++)
     {
@@ -1554,7 +1560,13 @@ input_edge (class lto_input_block *ib, vec<symtab_node 
*> nodes,
   edge->speculative = bp_unpack_value (&bp, 1);
   edge->callback = bp_unpack_value(&bp, 1);
   edge->has_callback = bp_unpack_value(&bp, 1);
-  edge->callback_id = bp_unpack_value(&bp, 16);
+
+  if (edge->callback)
+    {
+      callback_info *ci = callback_info_sum->get_create (edge);
+      ci->stream_in (ib);
+    }
+
   edge->lto_stmt_uid = stmt_id;
   edge->speculative_id = speculative_id;
   edge->inline_failed = inline_failed;
@@ -1597,6 +1609,7 @@ input_cgraph_1 (struct lto_file_decl_data *file_data,
   tag = streamer_read_enum (ib, LTO_symtab_tags, LTO_symtab_last_tag);
   file_data->order_base = symtab->order;
   file_data->unit_base = symtab->max_unit + 1;
+  callback_info_sum_t::check_create_info_sum ();
   while (tag)
     {
       if (tag == LTO_symtab_edge)
-- 
2.52.0

Reply via email to