LCOV - code coverage report
Current view: top level - src/torque - declarations.cc (source / functions) Hit Total Coverage
Test: app.info Lines: 125 145 86.2 %
Date: 2019-02-19 Functions: 38 42 90.5 %

          Line data    Source code
       1             : // Copyright 2017 the V8 project authors. All rights reserved.
       2             : // Use of this source code is governed by a BSD-style license that can be
       3             : // found in the LICENSE file.
       4             : 
       5             : #include "src/torque/declarations.h"
       6             : #include "src/torque/declarable.h"
       7             : #include "src/torque/global-context.h"
       8             : #include "src/torque/type-oracle.h"
       9             : 
      10             : namespace v8 {
      11             : namespace internal {
      12             : namespace torque {
      13             : 
      14       47980 : DEFINE_CONTEXTUAL_VARIABLE(GlobalContext)
      15             : 
      16             : namespace {
      17             : 
      18             : template <class T>
      19       16950 : std::vector<T> EnsureNonempty(std::vector<T> list, const std::string& name,
      20             :                               const char* kind) {
      21       16950 :   if (list.empty()) {
      22           0 :     ReportError("there is no ", kind, " named ", name);
      23             :   }
      24       16950 :   return std::move(list);
      25             : }
      26             : 
      27             : template <class T, class Name>
      28      115713 : T EnsureUnique(const std::vector<T>& list, const Name& name, const char* kind) {
      29      115713 :   if (list.empty()) {
      30           0 :     ReportError("there is no ", kind, " named ", name);
      31             :   }
      32      115713 :   if (list.size() >= 2) {
      33           0 :     ReportError("ambiguous reference to ", kind, " ", name);
      34             :   }
      35      115713 :   return list.front();
      36             : }
      37             : 
      38             : template <class T>
      39        5075 : void CheckAlreadyDeclared(const std::string& name, const char* new_type) {
      40             :   std::vector<T*> declarations =
      41       15225 :       FilterDeclarables<T>(Declarations::TryLookupShallow(QualifiedName(name)));
      42        5075 :   if (!declarations.empty()) {
      43           0 :     Scope* scope = CurrentScope::Get();
      44           0 :     ReportError("cannot redeclare ", name, " (type ", new_type, scope, ")");
      45             :   }
      46        5075 : }
      47             : 
      48             : }  // namespace
      49             : 
      50      100836 : std::vector<Declarable*> Declarations::LookupGlobalScope(
      51             :     const std::string& name) {
      52             :   std::vector<Declarable*> d =
      53      302508 :       GlobalContext::GetDefaultNamespace()->Lookup(QualifiedName(name));
      54      100836 :   if (d.empty()) {
      55           0 :     std::stringstream s;
      56           0 :     s << "cannot find \"" << name << "\" in global scope";
      57           0 :     ReportError(s.str());
      58             :   }
      59      100836 :   return d;
      60             : }
      61             : 
      62       13893 : const Type* Declarations::LookupType(const QualifiedName& name) {
      63       13893 :   TypeAlias* declaration =
      64       41679 :       EnsureUnique(FilterDeclarables<TypeAlias>(Lookup(name)), name, "type");
      65       13893 :   return declaration->type();
      66             : }
      67             : 
      68        1670 : const Type* Declarations::LookupType(std::string name) {
      69        3340 :   return LookupType(QualifiedName(std::move(name)));
      70             : }
      71             : 
      72      100836 : const Type* Declarations::LookupGlobalType(const std::string& name) {
      73      100836 :   TypeAlias* declaration = EnsureUnique(
      74      302508 :       FilterDeclarables<TypeAlias>(LookupGlobalScope(name)), name, "type");
      75      100836 :   return declaration->type();
      76             : }
      77             : 
      78       12189 : const Type* Declarations::GetType(TypeExpression* type_expression) {
      79       12189 :   if (auto* basic = BasicTypeExpression::DynamicCast(type_expression)) {
      80             :     std::string name =
      81       12124 :         (basic->is_constexpr ? CONSTEXPR_TYPE_PREFIX : "") + basic->name;
      82       36372 :     return LookupType(QualifiedName{basic->namespace_qualification, name});
      83          65 :   } else if (auto* union_type = UnionTypeExpression::cast(type_expression)) {
      84             :     return TypeOracle::GetUnionType(GetType(union_type->a),
      85          54 :                                     GetType(union_type->b));
      86             :   } else {
      87             :     auto* function_type_exp = FunctionTypeExpression::cast(type_expression);
      88             :     TypeVector argument_types;
      89          55 :     for (TypeExpression* type_exp : function_type_exp->parameters) {
      90          66 :       argument_types.push_back(GetType(type_exp));
      91             :     }
      92             :     return TypeOracle::GetBuiltinPointerType(
      93          22 :         argument_types, GetType(function_type_exp->return_type));
      94             :   }
      95             : }
      96             : 
      97          10 : Builtin* Declarations::FindSomeInternalBuiltinWithType(
      98         287 :     const BuiltinPointerType* type) {
      99       20782 :   for (auto& declarable : GlobalContext::AllDeclarables()) {
     100       21585 :     if (Builtin* builtin = Builtin::DynamicCast(declarable.get())) {
     101        2089 :       if (!builtin->IsExternal() && builtin->kind() == Builtin::kStub &&
     102        1428 :           builtin->signature().return_type == type->return_type() &&
     103         152 :           builtin->signature().parameter_types.types ==
     104         152 :               type->parameter_types()) {
     105             :         return builtin;
     106             :       }
     107             :     }
     108             :   }
     109             :   return nullptr;
     110             : }
     111             : 
     112         889 : Value* Declarations::LookupValue(const QualifiedName& name) {
     113        2667 :   return EnsureUnique(FilterDeclarables<Value>(Lookup(name)), name, "value");
     114             : }
     115             : 
     116         962 : Macro* Declarations::TryLookupMacro(const std::string& name,
     117             :                                     const TypeVector& types) {
     118        1924 :   std::vector<Macro*> macros = TryLookup<Macro>(QualifiedName(name));
     119        2518 :   for (auto& m : macros) {
     120         594 :     auto signature_types = m->signature().GetExplicitTypes();
     121         594 :     if (signature_types == types && !m->signature().parameter_types.var_args) {
     122           0 :       return m;
     123             :     }
     124             :   }
     125             :   return nullptr;
     126             : }
     127             : 
     128         984 : base::Optional<Builtin*> Declarations::TryLookupBuiltin(
     129             :     const QualifiedName& name) {
     130         984 :   std::vector<Builtin*> builtins = TryLookup<Builtin>(name);
     131         984 :   if (builtins.empty()) return base::nullopt;
     132           8 :   return EnsureUnique(builtins, name.name, "builtin");
     133             : }
     134             : 
     135       16950 : std::vector<Generic*> Declarations::LookupGeneric(const std::string& name) {
     136             :   return EnsureNonempty(FilterDeclarables<Generic>(Lookup(QualifiedName(name))),
     137       67800 :                         name, "generic");
     138             : }
     139             : 
     140          87 : Generic* Declarations::LookupUniqueGeneric(const QualifiedName& name) {
     141             :   return EnsureUnique(FilterDeclarables<Generic>(Lookup(name)), name,
     142         261 :                       "generic");
     143             : }
     144             : 
     145          22 : Namespace* Declarations::DeclareNamespace(const std::string& name) {
     146          66 :   return Declare(name, std::unique_ptr<Namespace>(new Namespace(name)));
     147             : }
     148             : 
     149         123 : const AbstractType* Declarations::DeclareAbstractType(
     150             :     const std::string& name, bool transient, const std::string& generated,
     151             :     base::Optional<const AbstractType*> non_constexpr_version,
     152         123 :     const base::Optional<std::string>& parent) {
     153         123 :   CheckAlreadyDeclared<TypeAlias>(name, "type");
     154             :   const Type* parent_type = nullptr;
     155         123 :   if (parent) {
     156         136 :     parent_type = LookupType(QualifiedName{*parent});
     157             :   }
     158             :   const AbstractType* type = TypeOracle::GetAbstractType(
     159         369 :       parent_type, name, transient, generated, non_constexpr_version);
     160         123 :   DeclareType(name, type, false);
     161         123 :   return type;
     162             : }
     163             : 
     164        4833 : void Declarations::DeclareType(const std::string& name, const Type* type,
     165             :                                bool redeclaration) {
     166        4833 :   CheckAlreadyDeclared<TypeAlias>(name, "type");
     167       14499 :   Declare(name, std::unique_ptr<TypeAlias>(new TypeAlias(type, redeclaration)));
     168        4833 : }
     169             : 
     170          32 : StructType* Declarations::DeclareStruct(const std::string& name) {
     171          32 :   StructType* new_type = TypeOracle::GetStructType(name);
     172          32 :   DeclareType(name, new_type, false);
     173          32 :   return new_type;
     174             : }
     175             : 
     176          19 : ClassType* Declarations::DeclareClass(const Type* super_type,
     177             :                                       const std::string& name, bool is_extern,
     178             :                                       bool transient,
     179             :                                       const std::string& generates) {
     180             :   ClassType* new_type = TypeOracle::GetClassType(super_type, name, is_extern,
     181          19 :                                                  transient, generates);
     182          19 :   DeclareType(name, new_type, false);
     183          19 :   return new_type;
     184             : }
     185             : 
     186         917 : Macro* Declarations::CreateMacro(
     187             :     std::string external_name, std::string readable_name,
     188         917 :     base::Optional<std::string> external_assembler_name, Signature signature,
     189             :     bool transitioning, base::Optional<Statement*> body) {
     190         917 :   if (!external_assembler_name) {
     191        1048 :     external_assembler_name = CurrentNamespace()->ExternalName();
     192             :   }
     193             :   return RegisterDeclarable(std::unique_ptr<Macro>(
     194             :       new Macro(std::move(external_name), std::move(readable_name),
     195             :                 std::move(*external_assembler_name), std::move(signature),
     196        5502 :                 transitioning, body)));
     197             : }
     198             : 
     199         711 : Macro* Declarations::DeclareMacro(
     200             :     const std::string& name,
     201             :     base::Optional<std::string> external_assembler_name,
     202             :     const Signature& signature, bool transitioning,
     203         711 :     base::Optional<Statement*> body, base::Optional<std::string> op) {
     204        1422 :   if (TryLookupMacro(name, signature.GetExplicitTypes())) {
     205             :     ReportError("cannot redeclare macro ", name,
     206           0 :                 " with identical explicit parameters");
     207             :   }
     208             :   Macro* macro = CreateMacro(name, name, std::move(external_assembler_name),
     209        3555 :                              signature, transitioning, body);
     210         711 :   Declare(name, macro);
     211         711 :   if (op) {
     212         502 :     if (TryLookupMacro(*op, signature.GetExplicitTypes())) {
     213             :       ReportError("cannot redeclare operator ", name,
     214           0 :                   " with identical explicit parameters");
     215             :     }
     216             :     DeclareOperator(*op, macro);
     217             :   }
     218         711 :   return macro;
     219             : }
     220             : 
     221          44 : Method* Declarations::CreateMethod(AggregateType* container_type,
     222             :                                    const std::string& name, Signature signature,
     223             :                                    bool transitioning, Statement* body) {
     224          44 :   std::string generated_name{container_type->GetGeneratedMethodName(name)};
     225             :   Method* result = RegisterDeclarable(std::unique_ptr<Method>(
     226             :       new Method(container_type, container_type->GetGeneratedMethodName(name),
     227             :                  name, CurrentNamespace()->ExternalName(), std::move(signature),
     228         264 :                  transitioning, body)));
     229             :   container_type->RegisterMethod(result);
     230          44 :   return result;
     231             : }
     232             : 
     233          66 : Intrinsic* Declarations::CreateIntrinsic(const std::string& name,
     234             :                                          const Signature& signature) {
     235             :   Intrinsic* result = RegisterDeclarable(std::unique_ptr<Intrinsic>(
     236         264 :       new Intrinsic(std::move(name), std::move(signature))));
     237          66 :   return result;
     238             : }
     239             : 
     240           0 : Intrinsic* Declarations::DeclareIntrinsic(const std::string& name,
     241             :                                           const Signature& signature) {
     242           0 :   Intrinsic* result = CreateIntrinsic(std::move(name), std::move(signature));
     243           0 :   Declare(name, result);
     244           0 :   return result;
     245             : }
     246             : 
     247         150 : Builtin* Declarations::CreateBuiltin(std::string external_name,
     248             :                                      std::string readable_name,
     249             :                                      Builtin::Kind kind, Signature signature,
     250             :                                      bool transitioning,
     251             :                                      base::Optional<Statement*> body) {
     252             :   return RegisterDeclarable(std::unique_ptr<Builtin>(
     253             :       new Builtin(std::move(external_name), std::move(readable_name), kind,
     254         750 :                   std::move(signature), transitioning, body)));
     255             : }
     256             : 
     257           0 : Builtin* Declarations::DeclareBuiltin(const std::string& name,
     258             :                                       Builtin::Kind kind,
     259             :                                       const Signature& signature,
     260             :                                       bool transitioning,
     261             :                                       base::Optional<Statement*> body) {
     262           0 :   CheckAlreadyDeclared<Builtin>(name, "builtin");
     263             :   return Declare(
     264           0 :       name, CreateBuiltin(name, name, kind, signature, transitioning, body));
     265             : }
     266             : 
     267          14 : RuntimeFunction* Declarations::DeclareRuntimeFunction(
     268             :     const std::string& name, const Signature& signature, bool transitioning) {
     269          14 :   CheckAlreadyDeclared<RuntimeFunction>(name, "runtime function");
     270             :   return Declare(name,
     271             :                  RegisterDeclarable(std::unique_ptr<RuntimeFunction>(
     272          42 :                      new RuntimeFunction(name, signature, transitioning))));
     273             : }
     274             : 
     275          81 : void Declarations::DeclareExternConstant(const std::string& name,
     276             :                                          const Type* type, std::string value) {
     277          81 :   CheckAlreadyDeclared<Value>(name, "constant");
     278         243 :   ExternConstant* result = new ExternConstant(name, type, value);
     279         162 :   Declare(name, std::unique_ptr<Declarable>(result));
     280          81 : }
     281             : 
     282          24 : NamespaceConstant* Declarations::DeclareNamespaceConstant(
     283             :     const std::string& name, const Type* type, Expression* body) {
     284          24 :   CheckAlreadyDeclared<Value>(name, "constant");
     285          48 :   NamespaceConstant* result = new NamespaceConstant(name, type, body);
     286          48 :   Declare(name, std::unique_ptr<Declarable>(result));
     287          24 :   return result;
     288             : }
     289             : 
     290          50 : Generic* Declarations::DeclareGeneric(const std::string& name,
     291             :                                       GenericDeclaration* generic) {
     292         150 :   return Declare(name, std::unique_ptr<Generic>(new Generic(name, generic)));
     293             : }
     294             : 
     295         326 : std::string Declarations::GetGeneratedCallableName(
     296             :     const std::string& name, const TypeVector& specialized_types) {
     297         326 :   std::string result = name;
     298        1118 :   for (auto type : specialized_types) {
     299         466 :     std::string type_string = type->MangledName();
     300         932 :     result += std::to_string(type_string.size()) + type_string;
     301             :   }
     302         326 :   return result;
     303             : }
     304             : 
     305           0 : Macro* Declarations::DeclareOperator(const std::string& name, Macro* m) {
     306         251 :   GlobalContext::GetDefaultNamespace()->AddDeclarable(name, m);
     307           0 :   return m;
     308             : }
     309             : 
     310             : }  // namespace torque
     311             : }  // namespace internal
     312        9114 : }  // namespace v8

Generated by: LCOV version 1.10