LCOV - code coverage report
Current view: top level - gcc/rust/resolve - rust-name-resolver.cc (source / functions) Coverage Total Hit
Test: gcc.info Lines: 89.5 % 342 306
Test Date: 2024-04-13 14:00:49 Functions: 87.5 % 56 49
Legend: Lines: hit not hit | Branches: + taken - not taken # not executed Branches: - 0 0

             Branch data     Line data    Source code
       1                 :             : // Copyright (C) 2020-2024 Free Software Foundation, Inc.
       2                 :             : 
       3                 :             : // This file is part of GCC.
       4                 :             : 
       5                 :             : // GCC is free software; you can redistribute it and/or modify it under
       6                 :             : // the terms of the GNU General Public License as published by the Free
       7                 :             : // Software Foundation; either version 3, or (at your option) any later
       8                 :             : // version.
       9                 :             : 
      10                 :             : // GCC is distributed in the hope that it will be useful, but WITHOUT ANY
      11                 :             : // WARRANTY; without even the implied warranty of MERCHANTABILITY or
      12                 :             : // FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
      13                 :             : // for more details.
      14                 :             : 
      15                 :             : // You should have received a copy of the GNU General Public License
      16                 :             : // along with GCC; see the file COPYING3.  If not see
      17                 :             : // <http://www.gnu.org/licenses/>.
      18                 :             : 
      19                 :             : #include "rust-name-resolver.h"
      20                 :             : #include "rust-ast-full.h"
      21                 :             : 
      22                 :             : namespace Rust {
      23                 :             : namespace Resolver {
      24                 :             : 
      25                 :      141195 : Rib::Rib (CrateNum crateNum, NodeId node_id)
      26                 :      141195 :   : crate_num (crateNum), node_id (node_id)
      27                 :      141195 : {}
      28                 :             : 
      29                 :             : void
      30                 :      121240 : Rib::insert_name (
      31                 :             :   const CanonicalPath &path, NodeId id, location_t locus, bool shadow,
      32                 :             :   ItemType type,
      33                 :             :   std::function<void (const CanonicalPath &, NodeId, location_t)> dup_cb)
      34                 :             : {
      35                 :      121240 :   auto it = path_mappings.find (path);
      36                 :      121240 :   bool path_already_exists = it != path_mappings.end ();
      37                 :      121240 :   if (path_already_exists && !shadow)
      38                 :             :     {
      39                 :          12 :       const auto &decl = decls_within_rib.find (it->second);
      40                 :          12 :       if (decl != decls_within_rib.end ())
      41                 :          12 :         dup_cb (path, it->second, decl->second);
      42                 :             :       else
      43                 :           0 :         dup_cb (path, it->second, locus);
      44                 :             : 
      45                 :          12 :       return;
      46                 :             :     }
      47                 :             : 
      48                 :      121228 :   path_mappings[path] = id;
      49                 :      121228 :   reverse_path_mappings.insert ({id, path});
      50                 :      121228 :   decls_within_rib.insert ({id, locus});
      51                 :      121228 :   references[id] = {};
      52                 :      121228 :   decl_type_mappings.insert ({id, type});
      53                 :             : }
      54                 :             : 
      55                 :             : bool
      56                 :      179311 : Rib::lookup_name (const CanonicalPath &ident, NodeId *id)
      57                 :             : {
      58                 :      179311 :   auto it = path_mappings.find (ident);
      59                 :      179311 :   if (it == path_mappings.end ())
      60                 :             :     return false;
      61                 :             : 
      62                 :       63381 :   *id = it->second;
      63                 :       63381 :   return true;
      64                 :             : }
      65                 :             : 
      66                 :             : void
      67                 :        3009 : Rib::clear_name (const CanonicalPath &ident, NodeId id)
      68                 :             : {
      69                 :        3009 :   auto ii = path_mappings.find (ident);
      70                 :        3009 :   if (ii != path_mappings.end ())
      71                 :        3009 :     path_mappings.erase (ii);
      72                 :             : 
      73                 :        3009 :   auto ij = reverse_path_mappings.find (id);
      74                 :        3009 :   if (ij != reverse_path_mappings.end ())
      75                 :        3009 :     reverse_path_mappings.erase (ij);
      76                 :             : 
      77                 :        3009 :   auto ik = decls_within_rib.find (id);
      78                 :        3009 :   if (ik != decls_within_rib.end ())
      79                 :        3009 :     decls_within_rib.erase (ik);
      80                 :        3009 : }
      81                 :             : 
      82                 :             : void
      83                 :      112741 : Rib::append_reference_for_def (NodeId def, NodeId ref)
      84                 :             : {
      85                 :      112741 :   references[def].insert (ref);
      86                 :      112741 : }
      87                 :             : 
      88                 :             : bool
      89                 :           0 : Rib::have_references_for_node (NodeId def) const
      90                 :             : {
      91                 :           0 :   auto it = references.find (def);
      92                 :           0 :   if (it == references.end ())
      93                 :             :     return false;
      94                 :             : 
      95                 :           0 :   return !it->second.empty ();
      96                 :             : }
      97                 :             : 
      98                 :             : bool
      99                 :      661492 : Rib::decl_was_declared_here (NodeId def) const
     100                 :             : {
     101                 :     5084091 :   for (auto &it : decls_within_rib)
     102                 :             :     {
     103                 :     4584788 :       if (it.first == def)
     104                 :      661492 :         return true;
     105                 :             :     }
     106                 :             :   return false;
     107                 :             : }
     108                 :             : 
     109                 :             : bool
     110                 :          80 : Rib::lookup_decl_type (NodeId def, ItemType *type) const
     111                 :             : {
     112                 :          80 :   auto it = decl_type_mappings.find (def);
     113                 :          80 :   if (it == decl_type_mappings.end ())
     114                 :             :     return false;
     115                 :             : 
     116                 :          80 :   *type = it->second;
     117                 :          80 :   return true;
     118                 :             : }
     119                 :             : 
     120                 :             : void
     121                 :           0 : Rib::debug () const
     122                 :             : {
     123                 :           0 :   fprintf (stderr, "%s\n", debug_str ().c_str ());
     124                 :           0 : }
     125                 :             : 
     126                 :             : std::string
     127                 :           0 : Rib::debug_str () const
     128                 :             : {
     129                 :           0 :   std::string buffer;
     130                 :           0 :   for (const auto &it : path_mappings)
     131                 :             :     {
     132                 :           0 :       buffer += it.first.get () + "=" + std::to_string (it.second);
     133                 :           0 :       buffer += ",";
     134                 :             :     }
     135                 :           0 :   return "{" + buffer + "}";
     136                 :           0 : }
     137                 :             : 
     138                 :       14400 : Scope::Scope (CrateNum crate_num) : crate_num (crate_num) {}
     139                 :             : 
     140                 :             : void
     141                 :       26386 : Scope::insert (
     142                 :             :   const CanonicalPath &ident, NodeId id, location_t locus, bool shadow,
     143                 :             :   Rib::ItemType type,
     144                 :             :   std::function<void (const CanonicalPath &, NodeId, location_t)> dup_cb)
     145                 :             : {
     146                 :       26386 :   peek ()->insert_name (ident, id, locus, shadow, type, dup_cb);
     147                 :       26386 : }
     148                 :             : 
     149                 :             : void
     150                 :       26511 : Scope::insert (const CanonicalPath &ident, NodeId id, location_t locus,
     151                 :             :                Rib::ItemType type)
     152                 :             : {
     153                 :       26511 :   peek ()->insert_name (ident, id, locus, true, type,
     154                 :             :                         [] (const CanonicalPath &, NodeId, location_t) -> void {
     155                 :             :                         });
     156                 :       26511 : }
     157                 :             : 
     158                 :             : bool
     159                 :       68584 : Scope::lookup (const CanonicalPath &ident, NodeId *id)
     160                 :             : {
     161                 :       68584 :   NodeId lookup = UNKNOWN_NODEID;
     162                 :       68584 :   iterate ([&] (Rib *r) mutable -> bool {
     163                 :      179311 :     if (r->lookup_name (ident, &lookup))
     164                 :       63381 :       return false;
     165                 :             :     return true;
     166                 :             :   });
     167                 :             : 
     168                 :       68584 :   *id = lookup;
     169                 :       68584 :   return lookup != UNKNOWN_NODEID;
     170                 :             : }
     171                 :             : 
     172                 :             : bool
     173                 :          80 : Scope::lookup_decl_type (NodeId id, Rib::ItemType *type)
     174                 :             : {
     175                 :          80 :   bool found = false;
     176                 :          80 :   iterate ([&] (const Rib *r) -> bool {
     177                 :         152 :     if (r->decl_was_declared_here (id))
     178                 :             :       {
     179                 :          80 :         bool ok = r->lookup_decl_type (id, type);
     180                 :          80 :         rust_assert (ok);
     181                 :          80 :         found = true;
     182                 :          80 :         return false;
     183                 :             :       }
     184                 :             :     return true;
     185                 :             :   });
     186                 :          80 :   return found;
     187                 :             : }
     188                 :             : 
     189                 :             : bool
     190                 :          80 : Scope::lookup_rib_for_decl (NodeId id, const Rib **rib)
     191                 :             : {
     192                 :          80 :   bool found = false;
     193                 :          80 :   iterate ([&] (const Rib *r) -> bool {
     194                 :         152 :     if (r->decl_was_declared_here (id))
     195                 :             :       {
     196                 :          80 :         *rib = r;
     197                 :          80 :         found = true;
     198                 :          80 :         return false;
     199                 :             :       }
     200                 :             :     return true;
     201                 :             :   });
     202                 :          80 :   return found;
     203                 :             : }
     204                 :             : 
     205                 :             : void
     206                 :      181081 : Scope::iterate (std::function<bool (Rib *)> cb)
     207                 :             : {
     208                 :      717155 :   for (auto it = stack.rbegin (); it != stack.rend (); ++it)
     209                 :             :     {
     210                 :      599615 :       if (!cb (*it))
     211                 :      181081 :         return;
     212                 :             :     }
     213                 :             : }
     214                 :             : 
     215                 :             : void
     216                 :       87435 : Scope::iterate (std::function<bool (const Rib *)> cb) const
     217                 :             : {
     218                 :      279335 :   for (auto it = stack.rbegin (); it != stack.rend (); ++it)
     219                 :             :     {
     220                 :      241188 :       if (!cb (*it))
     221                 :       87435 :         return;
     222                 :             :     }
     223                 :             : }
     224                 :             : 
     225                 :             : Rib *
     226                 :      324740 : Scope::peek ()
     227                 :             : {
     228                 :      324740 :   return stack.back ();
     229                 :             : }
     230                 :             : 
     231                 :             : void
     232                 :      141195 : Scope::push (NodeId id)
     233                 :             : {
     234                 :      141195 :   stack.push_back (new Rib (get_crate_num (), id));
     235                 :      141195 : }
     236                 :             : 
     237                 :             : Rib *
     238                 :      126753 : Scope::pop ()
     239                 :             : {
     240                 :      126753 :   Rib *r = peek ();
     241                 :      126753 :   stack.pop_back ();
     242                 :      126753 :   return r;
     243                 :             : }
     244                 :             : 
     245                 :             : void
     246                 :      112337 : Scope::append_reference_for_def (NodeId refId, NodeId defId)
     247                 :             : {
     248                 :      112337 :   bool ok = false;
     249                 :      112337 :   iterate ([&] (Rib *r) mutable -> bool {
     250                 :      420000 :     if (r->decl_was_declared_here (defId))
     251                 :             :       {
     252                 :      112741 :         ok = true;
     253                 :      112741 :         r->append_reference_for_def (defId, refId);
     254                 :             :       }
     255                 :      420000 :     return true;
     256                 :             :   });
     257                 :      112337 :   rust_assert (ok);
     258                 :      112337 : }
     259                 :             : 
     260                 :             : bool
     261                 :       87435 : Scope::decl_was_declared_here (NodeId def) const
     262                 :             : {
     263                 :       87435 :   bool found = false;
     264                 :       87435 :   iterate ([&] (const Rib *r) -> bool {
     265                 :      241188 :     if (r->decl_was_declared_here (def))
     266                 :             :       {
     267                 :       49288 :         found = true;
     268                 :       49288 :         return false;
     269                 :             :       }
     270                 :             :     return true;
     271                 :             :   });
     272                 :       87435 :   return found;
     273                 :             : }
     274                 :             : 
     275                 :        3600 : Resolver::Resolver ()
     276                 :        3600 :   : mappings (Analysis::Mappings::get ()), tyctx (TypeCheckContext::get ()),
     277                 :        3600 :     name_scope (Scope (mappings->get_current_crate ())),
     278                 :        3600 :     type_scope (Scope (mappings->get_current_crate ())),
     279                 :        3600 :     label_scope (Scope (mappings->get_current_crate ())),
     280                 :        3600 :     macro_scope (Scope (mappings->get_current_crate ())),
     281                 :        7200 :     global_type_node_id (UNKNOWN_NODEID), unit_ty_node_id (UNKNOWN_NODEID)
     282                 :             : {
     283                 :        3600 :   generate_builtins ();
     284                 :        3600 : }
     285                 :             : 
     286                 :             : Resolver *
     287                 :      585727 : Resolver::get ()
     288                 :             : {
     289                 :      585727 :   static Resolver *instance;
     290                 :      585727 :   if (instance == nullptr)
     291                 :        3600 :     instance = new Resolver ();
     292                 :             : 
     293                 :      585727 :   return instance;
     294                 :             : }
     295                 :             : 
     296                 :             : void
     297                 :       33596 : Resolver::push_new_name_rib (Rib *r)
     298                 :             : {
     299                 :       33596 :   rust_assert (name_ribs.find (r->get_node_id ()) == name_ribs.end ());
     300                 :       33596 :   name_ribs[r->get_node_id ()] = r;
     301                 :       33596 : }
     302                 :             : 
     303                 :             : void
     304                 :       37193 : Resolver::push_new_type_rib (Rib *r)
     305                 :             : {
     306                 :       37193 :   if (type_ribs.size () == 0)
     307                 :        3597 :     global_type_node_id = r->get_node_id ();
     308                 :             : 
     309                 :       37193 :   rust_assert (type_ribs.find (r->get_node_id ()) == type_ribs.end ());
     310                 :       37193 :   type_ribs[r->get_node_id ()] = r;
     311                 :       37193 : }
     312                 :             : 
     313                 :             : void
     314                 :       30825 : Resolver::push_new_label_rib (Rib *r)
     315                 :             : {
     316                 :       30825 :   rust_assert (label_ribs.find (r->get_node_id ()) == label_ribs.end ());
     317                 :       30825 :   label_ribs[r->get_node_id ()] = r;
     318                 :       30825 : }
     319                 :             : 
     320                 :             : void
     321                 :       36870 : Resolver::push_new_macro_rib (Rib *r)
     322                 :             : {
     323                 :       36870 :   rust_assert (label_ribs.find (r->get_node_id ()) == label_ribs.end ());
     324                 :       36870 :   macro_ribs[r->get_node_id ()] = r;
     325                 :       36870 : }
     326                 :             : 
     327                 :             : bool
     328                 :          44 : Resolver::find_name_rib (NodeId id, Rib **rib)
     329                 :             : {
     330                 :          44 :   auto it = name_ribs.find (id);
     331                 :          44 :   if (it == name_ribs.end ())
     332                 :             :     return false;
     333                 :             : 
     334                 :          44 :   *rib = it->second;
     335                 :          44 :   return true;
     336                 :             : }
     337                 :             : 
     338                 :             : bool
     339                 :           0 : Resolver::find_type_rib (NodeId id, Rib **rib)
     340                 :             : {
     341                 :           0 :   auto it = type_ribs.find (id);
     342                 :           0 :   if (it == type_ribs.end ())
     343                 :             :     return false;
     344                 :             : 
     345                 :           0 :   *rib = it->second;
     346                 :           0 :   return true;
     347                 :             : }
     348                 :             : 
     349                 :             : bool
     350                 :           0 : Resolver::find_macro_rib (NodeId id, Rib **rib)
     351                 :             : {
     352                 :           0 :   auto it = macro_ribs.find (id);
     353                 :           0 :   if (it == macro_ribs.end ())
     354                 :             :     return false;
     355                 :             : 
     356                 :           0 :   *rib = it->second;
     357                 :           0 :   return true;
     358                 :             : }
     359                 :             : 
     360                 :             : void
     361                 :        3597 : Resolver::insert_builtin_types (Rib *r)
     362                 :             : {
     363                 :        3597 :   auto builtins = get_builtin_types ();
     364                 :       71940 :   for (auto &builtin : builtins)
     365                 :             :     {
     366                 :       68343 :       CanonicalPath builtin_path
     367                 :             :         = CanonicalPath::new_seg (builtin->get_node_id (),
     368                 :       68343 :                                   builtin->as_string ());
     369                 :       68343 :       r->insert_name (builtin_path, builtin->get_node_id (), BUILTINS_LOCATION,
     370                 :             :                       false, Rib::ItemType::Type,
     371                 :             :                       [] (const CanonicalPath &, NodeId, location_t) -> void {
     372                 :             :                       });
     373                 :       68343 :     }
     374                 :        3597 : }
     375                 :             : 
     376                 :             : std::vector<AST::Type *> &
     377                 :        6910 : Resolver::get_builtin_types ()
     378                 :             : {
     379                 :        6910 :   return builtins;
     380                 :             : }
     381                 :             : 
     382                 :             : void
     383                 :        3600 : Resolver::generate_builtins ()
     384                 :             : {
     385                 :        3600 :   auto u8
     386                 :        3600 :     = new TyTy::UintType (mappings->get_next_hir_id (), TyTy::UintType::U8);
     387                 :        3600 :   auto u16
     388                 :        3600 :     = new TyTy::UintType (mappings->get_next_hir_id (), TyTy::UintType::U16);
     389                 :        3600 :   auto u32
     390                 :        3600 :     = new TyTy::UintType (mappings->get_next_hir_id (), TyTy::UintType::U32);
     391                 :        3600 :   auto u64
     392                 :        3600 :     = new TyTy::UintType (mappings->get_next_hir_id (), TyTy::UintType::U64);
     393                 :        3600 :   auto u128
     394                 :        3600 :     = new TyTy::UintType (mappings->get_next_hir_id (), TyTy::UintType::U128);
     395                 :        3600 :   auto i8 = new TyTy::IntType (mappings->get_next_hir_id (), TyTy::IntType::I8);
     396                 :        3600 :   auto i16
     397                 :        3600 :     = new TyTy::IntType (mappings->get_next_hir_id (), TyTy::IntType::I16);
     398                 :        3600 :   auto i32
     399                 :        3600 :     = new TyTy::IntType (mappings->get_next_hir_id (), TyTy::IntType::I32);
     400                 :        3600 :   auto i64
     401                 :        3600 :     = new TyTy::IntType (mappings->get_next_hir_id (), TyTy::IntType::I64);
     402                 :        3600 :   auto i128
     403                 :        3600 :     = new TyTy::IntType (mappings->get_next_hir_id (), TyTy::IntType::I128);
     404                 :        3600 :   auto rbool = new TyTy::BoolType (mappings->get_next_hir_id ());
     405                 :        3600 :   auto f32
     406                 :        3600 :     = new TyTy::FloatType (mappings->get_next_hir_id (), TyTy::FloatType::F32);
     407                 :        3600 :   auto f64
     408                 :        3600 :     = new TyTy::FloatType (mappings->get_next_hir_id (), TyTy::FloatType::F64);
     409                 :        3600 :   auto usize = new TyTy::USizeType (mappings->get_next_hir_id ());
     410                 :        3600 :   auto isize = new TyTy::ISizeType (mappings->get_next_hir_id ());
     411                 :        3600 :   auto char_tyty = new TyTy::CharType (mappings->get_next_hir_id ());
     412                 :        3600 :   auto str = new TyTy::StrType (mappings->get_next_hir_id ());
     413                 :        3600 :   auto never = new TyTy::NeverType (mappings->get_next_hir_id ());
     414                 :             : 
     415                 :        3600 :   setup_builtin ("u8", u8);
     416                 :        3600 :   setup_builtin ("u16", u16);
     417                 :        3600 :   setup_builtin ("u32", u32);
     418                 :        3600 :   setup_builtin ("u64", u64);
     419                 :        3600 :   setup_builtin ("u128", u128);
     420                 :        3600 :   setup_builtin ("i8", i8);
     421                 :        3600 :   setup_builtin ("i16", i16);
     422                 :        3600 :   setup_builtin ("i32", i32);
     423                 :        3600 :   setup_builtin ("i64", i64);
     424                 :        3600 :   setup_builtin ("i128", i128);
     425                 :        3600 :   setup_builtin ("bool", rbool);
     426                 :        3600 :   setup_builtin ("f32", f32);
     427                 :        3600 :   setup_builtin ("f64", f64);
     428                 :        3600 :   setup_builtin ("usize", usize);
     429                 :        3600 :   setup_builtin ("isize", isize);
     430                 :        3600 :   setup_builtin ("char", char_tyty);
     431                 :        3600 :   setup_builtin ("str", str);
     432                 :        3600 :   setup_builtin ("!", never);
     433                 :             : 
     434                 :             :   // unit type ()
     435                 :        3600 :   TyTy::TupleType *unit_tyty
     436                 :        3600 :     = TyTy::TupleType::get_unit_type (mappings->get_next_hir_id ());
     437                 :        3600 :   std::vector<std::unique_ptr<AST::Type> > elems;
     438                 :        3600 :   AST::TupleType *unit_type
     439                 :        3600 :     = new AST::TupleType (std::move (elems), BUILTINS_LOCATION);
     440                 :        3600 :   builtins.push_back (unit_type);
     441                 :        3600 :   tyctx->insert_builtin (unit_tyty->get_ref (), unit_type->get_node_id (),
     442                 :             :                          unit_tyty);
     443                 :        3600 :   set_unit_type_node_id (unit_type->get_node_id ());
     444                 :        3600 : }
     445                 :             : 
     446                 :             : void
     447                 :       64800 : Resolver::setup_builtin (const std::string &name, TyTy::BaseType *tyty)
     448                 :             : {
     449                 :       64800 :   AST::PathIdentSegment seg (name, BUILTINS_LOCATION);
     450                 :       64800 :   auto typePath = ::std::unique_ptr<AST::TypePathSegment> (
     451                 :       64800 :     new AST::TypePathSegment (::std::move (seg), false, BUILTINS_LOCATION));
     452                 :       64800 :   ::std::vector< ::std::unique_ptr<AST::TypePathSegment> > segs;
     453                 :       64800 :   segs.push_back (::std::move (typePath));
     454                 :       64800 :   auto builtin_type
     455                 :       64800 :     = new AST::TypePath (::std::move (segs), BUILTINS_LOCATION, false);
     456                 :       64800 :   builtins.push_back (builtin_type);
     457                 :       64800 :   tyctx->insert_builtin (tyty->get_ref (), builtin_type->get_node_id (), tyty);
     458                 :       64800 :   mappings->insert_node_to_hir (builtin_type->get_node_id (), tyty->get_ref ());
     459                 :       64800 :   mappings->insert_canonical_path (
     460                 :             :     builtin_type->get_node_id (),
     461                 :       64800 :     CanonicalPath::new_seg (builtin_type->get_node_id (), name));
     462                 :       64800 : }
     463                 :             : 
     464                 :             : void
     465                 :       33841 : Resolver::insert_resolved_name (NodeId refId, NodeId defId)
     466                 :             : {
     467                 :       33841 :   resolved_names[refId] = defId;
     468                 :       33841 :   get_name_scope ().append_reference_for_def (refId, defId);
     469                 :       33841 :   insert_captured_item (defId);
     470                 :       33841 : }
     471                 :             : 
     472                 :             : bool
     473                 :      208216 : Resolver::lookup_resolved_name (NodeId refId, NodeId *defId)
     474                 :             : {
     475                 :      208216 :   auto it = resolved_names.find (refId);
     476                 :      208216 :   if (it == resolved_names.end ())
     477                 :             :     return false;
     478                 :             : 
     479                 :      158445 :   *defId = it->second;
     480                 :      158445 :   return true;
     481                 :             : }
     482                 :             : 
     483                 :             : void
     484                 :       75687 : Resolver::insert_resolved_type (NodeId refId, NodeId defId)
     485                 :             : {
     486                 :             :   // auto it = resolved_types.find (refId);
     487                 :             :   // rust_assert (it == resolved_types.end ());
     488                 :             : 
     489                 :       75687 :   resolved_types[refId] = defId;
     490                 :       75687 :   get_type_scope ().append_reference_for_def (refId, defId);
     491                 :       75687 : }
     492                 :             : 
     493                 :             : bool
     494                 :      110985 : Resolver::lookup_resolved_type (NodeId refId, NodeId *defId)
     495                 :             : {
     496                 :      110985 :   auto it = resolved_types.find (refId);
     497                 :      110985 :   if (it == resolved_types.end ())
     498                 :             :     return false;
     499                 :             : 
     500                 :      107295 :   *defId = it->second;
     501                 :      107295 :   return true;
     502                 :             : }
     503                 :             : 
     504                 :             : void
     505                 :          15 : Resolver::insert_resolved_label (NodeId refId, NodeId defId)
     506                 :             : {
     507                 :          15 :   auto it = resolved_labels.find (refId);
     508                 :          15 :   rust_assert (it == resolved_labels.end ());
     509                 :             : 
     510                 :          15 :   resolved_labels[refId] = defId;
     511                 :          15 :   get_label_scope ().append_reference_for_def (refId, defId);
     512                 :          15 : }
     513                 :             : 
     514                 :             : bool
     515                 :          15 : Resolver::lookup_resolved_label (NodeId refId, NodeId *defId)
     516                 :             : {
     517                 :          15 :   auto it = resolved_labels.find (refId);
     518                 :          15 :   if (it == resolved_labels.end ())
     519                 :             :     return false;
     520                 :             : 
     521                 :          15 :   *defId = it->second;
     522                 :          15 :   return true;
     523                 :             : }
     524                 :             : 
     525                 :             : void
     526                 :           0 : Resolver::insert_resolved_macro (NodeId refId, NodeId defId)
     527                 :             : {
     528                 :           0 :   auto it = resolved_macros.find (refId);
     529                 :           0 :   rust_assert (it == resolved_macros.end ());
     530                 :             : 
     531                 :           0 :   resolved_labels[refId] = defId;
     532                 :           0 :   get_label_scope ().append_reference_for_def (refId, defId);
     533                 :           0 : }
     534                 :             : 
     535                 :             : bool
     536                 :           0 : Resolver::lookup_resolved_macro (NodeId refId, NodeId *defId)
     537                 :             : {
     538                 :           0 :   auto it = resolved_macros.find (refId);
     539                 :           0 :   if (it == resolved_macros.end ())
     540                 :             :     return false;
     541                 :             : 
     542                 :           0 :   *defId = it->second;
     543                 :           0 :   return true;
     544                 :             : }
     545                 :             : 
     546                 :             : void
     547                 :           2 : Resolver::insert_resolved_misc (NodeId refId, NodeId defId)
     548                 :             : {
     549                 :           2 :   auto it = misc_resolved_items.find (refId);
     550                 :           2 :   rust_assert (it == misc_resolved_items.end ());
     551                 :             : 
     552                 :           2 :   misc_resolved_items[refId] = defId;
     553                 :           2 : }
     554                 :             : 
     555                 :             : bool
     556                 :           2 : Resolver::lookup_resolved_misc (NodeId refId, NodeId *defId)
     557                 :             : {
     558                 :           2 :   auto it = misc_resolved_items.find (refId);
     559                 :           2 :   if (it == misc_resolved_items.end ())
     560                 :             :     return false;
     561                 :             : 
     562                 :           2 :   *defId = it->second;
     563                 :           2 :   return true;
     564                 :             : }
     565                 :             : 
     566                 :             : void
     567                 :          54 : Resolver::push_closure_context (NodeId closure_expr_id)
     568                 :             : {
     569                 :          54 :   auto it = closures_capture_mappings.find (closure_expr_id);
     570                 :          54 :   rust_assert (it == closures_capture_mappings.end ());
     571                 :             : 
     572                 :          54 :   closures_capture_mappings.insert ({closure_expr_id, {}});
     573                 :          54 :   closure_context.push_back (closure_expr_id);
     574                 :          54 : }
     575                 :             : 
     576                 :             : void
     577                 :          54 : Resolver::pop_closure_context ()
     578                 :             : {
     579                 :          54 :   rust_assert (!closure_context.empty ());
     580                 :          54 :   closure_context.pop_back ();
     581                 :          54 : }
     582                 :             : 
     583                 :             : void
     584                 :       33841 : Resolver::insert_captured_item (NodeId id)
     585                 :             : {
     586                 :             :   // nothing to do unless we are in a closure context
     587                 :       33841 :   if (closure_context.empty ())
     588                 :       33761 :     return;
     589                 :             : 
     590                 :             :   // check that this is a VAR_DECL?
     591                 :          80 :   Scope &name_scope = get_name_scope ();
     592                 :          80 :   Rib::ItemType type = Rib::ItemType::Unknown;
     593                 :          80 :   bool found = name_scope.lookup_decl_type (id, &type);
     594                 :          80 :   if (!found)
     595                 :             :     return;
     596                 :             : 
     597                 :             :   // RIB Function { let a, let b } id = 1;
     598                 :             :   //   RIB Closure { let c } id = 2;
     599                 :             :   //     RIB IfStmt { <bind a>} id = 3;
     600                 :             :   //   RIB ... { ... } id = 4
     601                 :             :   //
     602                 :             :   // if we have a resolved_node_id of 'a' and the current rib is '3' we know
     603                 :             :   // this is binding exists in a rib with id < the closure rib id, other wise
     604                 :             :   // its just a normal binding and we don't care
     605                 :             :   //
     606                 :             :   // Problem the node id's dont work like this because the inner most items are
     607                 :             :   // created first so this means the root will have a larger id and a simple
     608                 :             :   // less than or greater than check wont work for more complex scoping cases
     609                 :             :   // but we can use our current rib context to figure this out by checking if
     610                 :             :   // the rib id the decl we care about exists prior to the rib for the closure
     611                 :             :   // id
     612                 :             : 
     613                 :          80 :   const Rib *r = nullptr;
     614                 :          80 :   bool ok = name_scope.lookup_rib_for_decl (id, &r);
     615                 :          80 :   rust_assert (ok);
     616                 :          80 :   NodeId decl_rib_node_id = r->get_node_id ();
     617                 :             : 
     618                 :             :   // iterate the closure context and add in the mapping for all to handle the
     619                 :             :   // case of nested closures
     620                 :         160 :   for (auto &closure_expr_id : closure_context)
     621                 :             :     {
     622                 :          80 :       if (!decl_needs_capture (decl_rib_node_id, closure_expr_id, name_scope))
     623                 :          73 :         continue;
     624                 :             : 
     625                 :             :       // is this a valid binding to take
     626                 :           7 :       bool is_var_decl_p = type == Rib::ItemType::Var;
     627                 :           7 :       if (!is_var_decl_p)
     628                 :             :         {
     629                 :             :           // FIXME is this an error case?
     630                 :       33761 :           return;
     631                 :             :         }
     632                 :             : 
     633                 :             :       // append it to the context info
     634                 :           7 :       auto it = closures_capture_mappings.find (closure_expr_id);
     635                 :           7 :       rust_assert (it != closures_capture_mappings.end ());
     636                 :             : 
     637                 :           7 :       it->second.insert (id);
     638                 :             :     }
     639                 :             : }
     640                 :             : 
     641                 :             : bool
     642                 :          80 : Resolver::decl_needs_capture (NodeId decl_rib_node_id,
     643                 :             :                               NodeId closure_rib_node_id, const Scope &scope)
     644                 :             : {
     645                 :         313 :   for (const auto &rib : scope.get_context ())
     646                 :             :     {
     647                 :         313 :       bool rib_is_closure = rib->get_node_id () == closure_rib_node_id;
     648                 :         313 :       bool rib_is_decl = rib->get_node_id () == decl_rib_node_id;
     649                 :         313 :       if (rib_is_closure)
     650                 :             :         return false;
     651                 :         240 :       else if (rib_is_decl)
     652                 :             :         return true;
     653                 :             :     }
     654                 :             :   return false;
     655                 :             : }
     656                 :             : 
     657                 :             : const std::set<NodeId> &
     658                 :          53 : Resolver::get_captures (NodeId id) const
     659                 :             : {
     660                 :          53 :   auto it = closures_capture_mappings.find (id);
     661                 :          53 :   rust_assert (it != closures_capture_mappings.end ());
     662                 :          53 :   return it->second;
     663                 :             : }
     664                 :             : 
     665                 :             : } // namespace Resolver
     666                 :             : } // namespace Rust
        

Generated by: LCOV version 2.1-beta

LCOV profile is generated on x86_64 machine using following configure options: configure --disable-bootstrap --enable-coverage=opt --enable-languages=c,c++,fortran,go,jit,lto,rust,m2 --enable-host-shared. GCC test suite is run with the built compiler.