1 // =================================
   2 // Copyright (c) 2021 Seppo Laakko
   3 // Distributed under the MIT license
   4 // =================================
   5 
   6 #include <cmajor/symbols/Symbol.hpp>
   7 #include <cmajor/symbols/SymbolWriter.hpp>
   8 #include <cmajor/symbols/SymbolReader.hpp>
   9 #include <cmajor/symbols/BasicTypeSymbol.hpp>
  10 #include <cmajor/symbols/BasicTypeOperation.hpp>
  11 #include <cmajor/symbols/ArrayTypeSymbol.hpp>
  12 #include <cmajor/symbols/DerivedTypeSymbol.hpp>
  13 #include <cmajor/symbols/NamespaceSymbol.hpp>
  14 #include <cmajor/symbols/FunctionSymbol.hpp>
  15 #include <cmajor/symbols/ClassTypeSymbol.hpp>
  16 #include <cmajor/symbols/InterfaceTypeSymbol.hpp>
  17 #include <cmajor/symbols/DelegateSymbol.hpp>
  18 #include <cmajor/symbols/TypedefSymbol.hpp>
  19 #include <cmajor/symbols/VariableSymbol.hpp>
  20 #include <cmajor/symbols/ConstantSymbol.hpp>
  21 #include <cmajor/symbols/EnumSymbol.hpp>
  22 #include <cmajor/symbols/Exception.hpp>
  23 #include <cmajor/symbols/TemplateSymbol.hpp>
  24 #include <cmajor/symbols/ConceptSymbol.hpp>
  25 #include <cmajor/symbols/FunctionSymbol.hpp>
  26 #include <cmajor/symbols/StringFunctions.hpp>
  27 #include <cmajor/symbols/Module.hpp>
  28 #include <cmajor/symbols/ModuleCache.hpp>
  29 #include <soulng/util/Unicode.hpp>
  30 #include <soulng/util/Sha1.hpp>
  31 #ifdef _WIN32
  32 #include <cmajor/symbols/Trap.hpp>
  33 #endif
  34 
  35 namespace cmajor { namespace symbols {
  36 
  37 using namespace soulng::unicode;
  38 
  39 const char* symbolTypeStr[uint8_t(SymbolType::maxSymbol)] =
  40 {
  41     "boolTypeSymbol""sbyteTypeSymbol""byteTypeSymbol""shortTypeSymbol""ushortTypeSymbol""intTypeSymbol""uintTypeSymbol""longTypeSymbol""ulongTypeSymbol""floatTypeSymbol""doubleTypeSymbol"
  42     "charTypeSymbol""wcharTypeSymbol""ucharTypeSymbol""voidTypeSymbol""nullPtrTypeSymbol"
  43     "arrayTypeSymbol""derivedTypeSymbol"
  44     "namespaceSymbol""functionSymbol""staticConstructorSymbol""constructorSymbol""destructorSymbol""memberFunctionSymbol""conversionFunctionSymbol""functionGroupSymbol"
  45     "classGroupTypeSymbol""classTypeSymbol""interfaceTypeSymbol""conceptGroupSymbol""conceptSymbol"
  46     "delegateTypeSymbol""classDelegateTypeSymbol""declarationBlock""typedefSymbol""constantSymbol""enumTypeSymbol""enumConstantSymbol"
  47     "templateParameterSymbol""boundTemplateParameterSymbol""parameterSymbol""localVariableSymbol""memberVariableSymbol"
  48     "basicTypeUnaryPlus""basicTypeIntUnaryMinus""basicTypeFloatUnaryMinus""basicTypeComplement""basicTypeAdd""basicTypeFAdd""basicTypeSub""basicTypeFSub""basicTypeMul""basicTypeFMul"
  49     "basicTypeSDiv""basicTypeUDiv""basicTypeFDiv""basicTypeSRem""basicTypeURem""basicTypeAnd""basicTypeOr""basicTypeXor""basicTypeShl""basicTypeAShr""basicTypeLShr"
  50     "basicTypeNot""basicTypeIntegerEquality""basicTypeUnsignedIntegerLessThan""basicTypeSignedIntegerLessThan""basicTypeFloatingEquality""basicTypeFloatingLessThan"
  51     "defaultInt1""defaultInt8""defaultInt16""defaultInt32""defaultInt64""defaultFloat""defaultDouble""basicTypeCopyCtor""basicTypeMoveCtor"
  52     "basicTypeCopyAssignment""basicTypeMoveAssignment""basicTypeReturn"
  53     "basicTypeImplicitSignExtension""basicTypeImplicitZeroExtension""basicTypeExplicitSignExtension""basicTypeExplicitZeroExtension""basicTypeTruncation""basicTypeBitCast"
  54     "basicTypeImplicitUnsignedIntToFloating""basicTypeImplicitSignedIntToFloating""basicTypeExplicitUnsignedIntToFloating""basicTypeExplicitSignedIntToFloating"
  55     "basicTypeFloatingToUnsignedInt""basicTypeFloatingToSignedInt""basicTypeFloatingExtension""basicTypeFloatingTruncation""trap"
  56     "enumTypeDefaultConstructor""enumTypeCopyConstructor""enumTypeMoveConstructor""enumTypeCopyAssignment""enumTypeMoveAssignment""enumTypeReturn""enumTypeEquality"
  57     "enumTypeToUnderlyingType""underlyingToEnumType"
  58     "delegateTypeDefaultConstructor""delegateTypeCopyConstructor""delegateTypeMoveConstructor""delegateTypeCopyAssignment""delegateTypeMoveAssignment""delegateTypeReturn"
  59     "delegateTypeEquality""functionToDelegateSymbol"
  60     "classDelegateTypeDefaultConstructor""classDelegateTypeCopyConstructor""classDelegateTypeMoveConstructor""classDelegateTypeCopyAssignment""classDelegateTypeMoveAssignment"
  61     "classDelegateTypeEquality""memberFunctionToClassDelegateSymbol"
  62     "arrayLengthFunctionSymbol""arrayBeginFunctionSymbol""arrayEndFunctionSymbol""arrayCBeginFunctionSymbol""arrayCEndFunctionSymbol"
  63     "namespaceTypeSymbol""functionGroupTypeSymbol""memberExpressionTypeSymbol""variableValueSymbol""globalVariableSymbol""globalVariableGroupSymbol"
  64     "stringFunctionContainerSymbol""stringLengthFunctionSymbol""axiomSymbol"
  65 };
  66 
  67 std::string SymbolTypeStr(SymbolType symbolType)
  68 {
  69     return symbolTypeStr[static_cast<uint8_t>(symbolType)];
  70 }
  71 
  72 std::string SymbolFlagStr(SymbolFlags symbolFlags)
  73 {
  74     return SymbolFlagStr(symbolFlagsfalse);
  75 }
  76 
  77 std::string SymbolFlagStr(SymbolFlags symbolFlagsbool noAccess)
  78 {
  79     std::string s;
  80     if (!noAccess)
  81     {
  82         SymbolAccess access = SymbolAccess(symbolFlags & SymbolFlags::access);
  83         switch (access)
  84         {
  85             case SymbolAccess::private_: s.append("private"); break;
  86             case SymbolAccess::protected_: s.append("protected"); break;
  87             case SymbolAccess::internal_: s.append("internal"); break;
  88             case SymbolAccess::public_: s.append("public"); break;
  89         }
  90     }
  91     if ((symbolFlags & SymbolFlags::static_) != SymbolFlags::none)
  92     {
  93         if (!s.empty())
  94         {
  95             s.append(1' ');
  96         }
  97         s.append("static");
  98     }
  99     if ((symbolFlags & SymbolFlags::external) != SymbolFlags::none)
 100     {
 101         if (!s.empty())
 102         {
 103             s.append(1' ');
 104         }
 105         s.append("extern");
 106     }
 107     if ((symbolFlags & SymbolFlags::nothrow_) != SymbolFlags::none)
 108     {
 109         if (!s.empty())
 110         {
 111             s.append(1' ');
 112         }
 113         s.append("nothrow");
 114     }
 115     if ((symbolFlags & SymbolFlags::project) != SymbolFlags::none)
 116     {
 117         if (!s.empty())
 118         {
 119             s.append(1' ');
 120         }
 121         s.append("project");
 122     }
 123     if ((symbolFlags & SymbolFlags::bound) != SymbolFlags::none)
 124     {
 125         if (!s.empty())
 126         {
 127             s.append(1' ');
 128         }
 129         s.append("bound");
 130     }
 131     if ((symbolFlags & SymbolFlags::installed) != SymbolFlags::none)
 132     {
 133         if (!s.empty())
 134         {
 135             s.append(1' ');
 136         }
 137         s.append("installed");
 138     }
 139     return s;
 140 }
 141 
 142 uint32_t AccessFlag(Emitter& emitterSymbolAccess access)
 143 {
 144     switch (access)
 145     {
 146         case SymbolAccess::private_:
 147         {
 148             return emitter.GetPrivateFlag();
 149         }
 150         case SymbolAccess::protected_:
 151         {
 152             return emitter.GetProtectedFlag();
 153         }
 154         case SymbolAccess::public_:
 155         {
 156             return emitter.GetPublicFlag();
 157         }
 158     }
 159     return emitter.GetNoFlags();
 160 }
 161 
 162 bool operator==(const SymbolLocation& leftconst SymbolLocation& right)
 163 {
 164     return left.moduleId == right.moduleId && left.fileIndex == right.fileIndex && left.line == right.line && left.scol == right.scol && left.ecol == right.ecol;
 165 }
 166 
 167 bool operator<(const SymbolLocation& leftconst SymbolLocation& right)
 168 {
 169     if (left.moduleId < right.moduleId) return true;
 170     if (left.moduleId > right.moduleId) return false;
 171     if (left.fileIndex < right.fileIndex) return true;
 172     if (left.fileIndex > right.fileIndex) return false;
 173     if (left.line < right.line) return true;
 174     if (left.line > right.line) return false;
 175     if (left.scol < right.scol) return true;
 176     if (left.scol > right.scol) return false;
 177     return left.ecol < right.ecol;
 178 }
 179 
 180 SymbolLocation MakeSymbolLocation(const Span& spanModule* module)
 181 {
 182     int32_t scol = 0;
 183     int32_t ecol = 0;
 184     module->GetColumns(spanscolecol);
 185     return SymbolLocation(module->Id()span.fileIndexspan.linescolecol);
 186 }
 187 
 188 Symbol::Symbol(SymbolType symbolType_const Span& span_const boost::uuids::uuid& sourceModuleId_const std::u32string& name_) :
 189     symbolType(symbolType_)span(span_)sourceModuleId(sourceModuleId_)name(name_)flags(SymbolFlags::project)parent(nullptr)module(nullptr)compileUnit(nullptr)symbolIndex(-1)
 190 {
 191 }
 192 
 193 Symbol::~Symbol()
 194 {
 195 }
 196 
 197 void Symbol::Write(SymbolWriter& writer)
 198 {
 199     SymbolFlags f = flags & ~(SymbolFlags::project | SymbolFlags::installed);
 200     writer.GetBinaryWriter().Write(static_cast<uint8_t>(f));
 201     writer.GetBinaryWriter().Write(mangledName);
 202     bool hasAttributes = attributes != nullptr;
 203     writer.GetBinaryWriter().Write(hasAttributes);
 204     if (hasAttributes)
 205     {
 206         writer.GetAstWriter().Write(attributes.get());
 207     }
 208 }
 209 
 210 void Symbol::Read(SymbolReader& reader)
 211 {
 212     flags = static_cast<SymbolFlags>(reader.GetBinaryReader().ReadByte());
 213     if (reader.SetProjectBit())
 214     {
 215         flags = flags | SymbolFlags::project;
 216     }
 217     mangledName = reader.GetBinaryReader().ReadUtf32String();
 218     bool hasAttributes = reader.GetBinaryReader().ReadBool();
 219     if (hasAttributes)
 220     {
 221         attributes.reset(reader.GetAstReader().ReadAttributesNode());
 222     }
 223 }
 224 
 225 const ContainerScope* Symbol::GetContainerScope() const
 226 {
 227     return parent ? parent->GetContainerScope() : nullptr;
 228 }
 229 
 230 ContainerScope* Symbol::GetContainerScope()
 231 {
 232     return parent ? parent->GetContainerScope() : nullptr;
 233 }
 234 
 235 const ContainerScope* Symbol::GetTypeScope() const
 236 {
 237     return GetContainerScope();
 238 }
 239 
 240 ContainerScope* Symbol::GetTypeScope()
 241 {
 242     return GetContainerScope();
 243 }
 244 
 245 ContainerScope* Symbol::GetArrowScope()
 246 {
 247     return module->GetSymbolTable().GlobalNs().GetContainerScope();
 248 }
 249 
 250 const ContainerScope* Symbol::GetArrowScope() const
 251 {
 252     return module->GetSymbolTable().GlobalNs().GetContainerScope();
 253 }
 254 
 255 std::u32string Symbol::FullName() const
 256 {
 257     std::u32string fullName;
 258     if (parent)
 259     {
 260         fullName.append(parent->FullName());
 261     }
 262     if (!fullName.empty())
 263     {
 264         fullName.append(1'.');
 265     }
 266     fullName.append(Name());
 267     return fullName;
 268 }
 269 
 270 std::u32string Symbol::FullNameWithSpecifiers() const
 271 {
 272     std::u32string fullNameWithSpecifiers = ToUtf32(SymbolFlagStr(GetStableSymbolFlags()));
 273     if (!fullNameWithSpecifiers.empty())
 274     {
 275         fullNameWithSpecifiers.append(1U' ');
 276     }
 277     fullNameWithSpecifiers.append(FullName());
 278     return fullNameWithSpecifiers;
 279 }
 280 
 281 void* Symbol::IrObject(Emitter& emitter)
 282 {
 283     return emitter.GetIrObject(this);
 284 }
 285 
 286 void Symbol::ComputeMangledName()
 287 {
 288     mangledName = ToUtf32(TypeString());
 289     mangledName.append(1U'_').append(SimpleName());
 290     mangledName.append(1U'_').append(ToUtf32(GetSha1MessageDigest(ToUtf8(FullNameWithSpecifiers()))));
 291 }
 292 
 293 std::string Symbol::GetSpecifierStr() const
 294 {
 295     return SymbolFlagStr(flags);
 296 }
 297 
 298 std::string Symbol::Syntax() const
 299 {
 300     std::string syntax;
 301     syntax.append(GetSpecifierStr());
 302     if (!syntax.empty())
 303     {
 304         syntax.append(1' ');
 305     }
 306     syntax.append(TypeString());
 307     syntax.append(1' ');
 308     syntax.append(ToUtf8(DocName()));
 309     syntax.append(1';');
 310     return syntax;
 311 }
 312 
 313 void Symbol::CopyFrom(const Symbol* that)
 314 {
 315     symbolType = that->symbolType;
 316     span = that->span;
 317     sourceModuleId = that->sourceModuleId;
 318     name = that->name;
 319     flags = that->flags;
 320     mangledName = that->mangledName;
 321     parent = that->parent;
 322     module = that->module;
 323     compileUnit = that->compileUnit;
 324     if (that->attributes)
 325     {
 326         CloneContext cloneContext;
 327         attributes.reset(static_cast<AttributesNode*>(that->attributes->Clone(cloneContext)));
 328     }
 329 }
 330 
 331 void Symbol::Check()
 332 {
 333 }
 334 
 335 void Symbol::SetMangledName(const std::u32string& mangledName_)
 336 {
 337     mangledName = mangledName_;
 338 }
 339 
 340 void Symbol::SetAccess(Specifiers accessSpecifiers)
 341 {
 342     ContainerSymbol* cls = ContainingClassNoThrow();
 343     SymbolAccess access = SymbolAccess::private_;
 344     bool classMember = true;
 345     if (!cls)
 346     {
 347         if (this->IsGlobalVariableSymbol())
 348         {
 349             access = SymbolAccess::private_;
 350         }
 351         else
 352         {
 353             access = SymbolAccess::internal_;
 354         }
 355         classMember = false;
 356         ContainerSymbol* intf = ContainingInterfaceNoThrow();
 357         if (intf)
 358         {
 359             access = SymbolAccess::public_;
 360         }
 361     }
 362     if (accessSpecifiers == Specifiers::public_)
 363     {
 364         access = SymbolAccess::public_;
 365     }
 366     else if (accessSpecifiers == Specifiers::protected_)
 367     {
 368         if (classMember)
 369         {
 370             access = SymbolAccess::protected_;
 371         }
 372         else
 373         {
 374             throw Exception("only class members can have protected access"GetSpan()SourceModuleId());
 375         }
 376     }
 377     else if (accessSpecifiers == Specifiers::internal_)
 378     {
 379         access = SymbolAccess::internal_;
 380     }
 381     else if (accessSpecifiers == Specifiers::private_)
 382     {
 383         if (classMember || this->IsGlobalVariableSymbol())
 384         {
 385             access = SymbolAccess::private_;
 386         }
 387         else
 388         {
 389             throw Exception("only class members and global variables can have private access"GetSpan()SourceModuleId());
 390         }
 391     }
 392     else if (accessSpecifiers != Specifiers::none)
 393     {
 394         throw Exception("invalid combination of access specifiers: " + SpecifierStr(accessSpecifiers)GetSpan()SourceModuleId());
 395     }
 396     SetAccess(access);
 397 }
 398 
 399 bool Symbol::IsSameParentOrAncestorOf(const Symbol* that) const
 400 {
 401     if (!that)
 402     {
 403         return false;
 404     }
 405     else if (this == that)
 406     {
 407         return true;
 408     }
 409     else if (this->IsTypeSymbol() && that->IsTypeSymbol() && TypesEqual(static_cast<const TypeSymbol*>(this)static_cast<const TypeSymbol*>(that)))
 410     {
 411         return true;
 412     }
 413     else if (that->parent)
 414     {
 415         return IsSameParentOrAncestorOf(that->parent);
 416     }
 417     else
 418     {
 419         return false;
 420     }
 421 }
 422 
 423 const NamespaceSymbol* Symbol::Ns() const
 424 {
 425     if (symbolType == SymbolType::namespaceSymbol)
 426     {
 427         if (!GetModule()->IsRootModule())
 428         {
 429             Module* rootModule = GetRootModuleForCurrentThread();
 430             NamespaceSymbol* mappedNs = rootModule->GetSymbolTable().GetMappedNs(const_cast<NamespaceSymbol*>(static_cast<const NamespaceSymbol*>(this)));
 431             if (mappedNs)
 432             {
 433                 return mappedNs;
 434             }
 435         }
 436         return static_cast<const NamespaceSymbol*>(this);
 437     }
 438     else
 439     {
 440         if (parent)
 441         {
 442             return parent->Ns();
 443         }
 444         else
 445         {
 446             throw Exception("namespace symbol not found"GetSpan()SourceModuleId());
 447         }
 448     }
 449 }
 450 
 451 NamespaceSymbol* Symbol::Ns()
 452 {
 453     if (symbolType == SymbolType::namespaceSymbol)
 454     {
 455         if (!GetModule()->IsRootModule())
 456         {
 457             Module* rootModule = GetRootModuleForCurrentThread();
 458             NamespaceSymbol* mappedNs = rootModule->GetSymbolTable().GetMappedNs(static_cast<NamespaceSymbol*>(this));
 459             if (mappedNs)
 460             {
 461                 return mappedNs;
 462             }
 463         }
 464         return static_cast<NamespaceSymbol*>(this);
 465     }
 466     else
 467     {
 468         if (parent)
 469         {
 470             return parent->Ns();
 471         }
 472         else
 473         {
 474             throw Exception("namespace symbol not found"GetSpan()SourceModuleId());
 475         }
 476     }
 477 }
 478 
 479 const ClassTypeSymbol* Symbol::ClassNoThrow() const
 480 {
 481     if (IsClassTypeSymbol())
 482     {
 483         return static_cast<const ClassTypeSymbol*>(this);
 484     }
 485     else
 486     {
 487         if (parent)
 488         {
 489             return parent->ClassNoThrow();
 490         }
 491         else
 492         {
 493             return nullptr;
 494         }
 495     }
 496 }
 497 
 498 ClassTypeSymbol* Symbol::ClassNoThrow()
 499 {
 500     if (IsClassTypeSymbol())
 501     {
 502         return static_cast<ClassTypeSymbol*>(this);
 503     }
 504     else
 505     {
 506         if (parent)
 507         {
 508             return parent->ClassNoThrow();
 509         }
 510         else
 511         {
 512             return nullptr;
 513         }
 514     }
 515 }
 516 
 517 const ContainerSymbol* Symbol::ClassOrNsNoThrow() const
 518 {
 519     if (symbolType == SymbolType::namespaceSymbol)
 520     {
 521         if (!GetModule()->IsRootModule())
 522         {
 523             Module* rootModule = GetRootModuleForCurrentThread();
 524             NamespaceSymbol* mappedNs = rootModule->GetSymbolTable().GetMappedNs(const_cast<NamespaceSymbol*>(static_cast<const NamespaceSymbol*>(this)));
 525             if (mappedNs)
 526             {
 527                 return mappedNs;
 528             }
 529         }
 530         return static_cast<const NamespaceSymbol*>(this);
 531     }
 532     else if (IsClassTypeSymbol())
 533     {
 534         return static_cast<const ClassTypeSymbol*>(this);
 535     }
 536     else
 537     {
 538         if (parent)
 539         {
 540             return parent->ClassOrNsNoThrow();
 541         }
 542         else
 543         {
 544             return nullptr;
 545         }
 546     }
 547 }
 548 
 549 ContainerSymbol* Symbol::ClassOrNsNoThrow()
 550 {
 551     if (symbolType == SymbolType::namespaceSymbol)
 552     {
 553         if (!GetModule()->IsRootModule())
 554         {
 555             Module* rootModule = GetRootModuleForCurrentThread();
 556             NamespaceSymbol* mappedNs = rootModule->GetSymbolTable().GetMappedNs(static_cast<NamespaceSymbol*>(this));
 557             if (mappedNs)
 558             {
 559                 return mappedNs;
 560             }
 561         }
 562         return static_cast<NamespaceSymbol*>(this);
 563     }
 564     else if (IsClassTypeSymbol())
 565     {
 566         return static_cast<ClassTypeSymbol*>(this);
 567     }
 568     else
 569     {
 570         if (parent)
 571         {
 572             return parent->ClassOrNsNoThrow();
 573         }
 574         else
 575         {
 576             return nullptr;
 577         }
 578     }
 579 }
 580 
 581 const ContainerSymbol* Symbol::ClassInterfaceOrNsNoThrow() const
 582 {
 583     if (symbolType == SymbolType::namespaceSymbol)
 584     {
 585         if (!GetModule()->IsRootModule())
 586         {
 587             Module* rootModule = GetRootModuleForCurrentThread();
 588             NamespaceSymbol* mappedNs = rootModule->GetSymbolTable().GetMappedNs(const_cast<NamespaceSymbol*>(static_cast<const NamespaceSymbol*>(this)));
 589             if (mappedNs)
 590             {
 591                 return mappedNs;
 592             }
 593         }
 594         return static_cast<const NamespaceSymbol*>(this);
 595     }
 596     else if (symbolType == SymbolType::interfaceTypeSymbol)
 597     {
 598         return static_cast<const InterfaceTypeSymbol*>(this);
 599     }
 600     else if (IsClassTypeSymbol())
 601     {
 602         return static_cast<const ClassTypeSymbol*>(this);
 603     }
 604     else
 605     {
 606         if (parent)
 607         {
 608             return parent->ClassInterfaceOrNsNoThrow();
 609         }
 610         else
 611         {
 612             return nullptr;
 613         }
 614     }
 615 }
 616 
 617 ContainerSymbol* Symbol::ClassInterfaceOrNsNoThrow()
 618 {
 619     if (symbolType == SymbolType::namespaceSymbol)
 620     {
 621         if (!GetModule()->IsRootModule())
 622         {
 623             Module* rootModule = GetRootModuleForCurrentThread();
 624             NamespaceSymbol* mappedNs = rootModule->GetSymbolTable().GetMappedNs(static_cast<NamespaceSymbol*>(this));
 625             if (mappedNs)
 626             {
 627                 return mappedNs;
 628             }
 629         }
 630         return static_cast<NamespaceSymbol*>(this);
 631     }
 632     else if (symbolType == SymbolType::interfaceTypeSymbol)
 633     {
 634         return static_cast<InterfaceTypeSymbol*>(this);
 635     }
 636     else if (IsClassTypeSymbol())
 637     {
 638         return static_cast<ClassTypeSymbol*>(this);
 639     }
 640     else
 641     {
 642         if (parent)
 643         {
 644             return parent->ClassInterfaceOrNsNoThrow();
 645         }
 646         else
 647         {
 648             return nullptr;
 649         }
 650     }
 651 }
 652 
 653 const ContainerSymbol* Symbol::ClassInterfaceEnumDelegateOrNsNoThrow() const
 654 {
 655     if (symbolType == SymbolType::namespaceSymbol)
 656     {
 657         if (!GetModule()->IsRootModule())
 658         {
 659             Module* rootModule = GetRootModuleForCurrentThread();
 660             NamespaceSymbol* mappedNs = rootModule->GetSymbolTable().GetMappedNs(const_cast<NamespaceSymbol*>(static_cast<const NamespaceSymbol*>(this)));
 661             if (mappedNs)
 662             {
 663                 return mappedNs;
 664             }
 665         }
 666         return static_cast<const NamespaceSymbol*>(this);
 667     }
 668     else if (symbolType == SymbolType::interfaceTypeSymbol)
 669     {
 670         return static_cast<const InterfaceTypeSymbol*>(this);
 671     }
 672     else if (symbolType == SymbolType::enumTypeSymbol)
 673     {
 674         return static_cast<const EnumTypeSymbol*>(this);
 675     }
 676     else if (symbolType == SymbolType::delegateTypeSymbol)
 677     {
 678         return static_cast<const DelegateTypeSymbol*>(this);
 679     }
 680     else if (symbolType == SymbolType::classDelegateTypeSymbol)
 681     {
 682         return static_cast<const ClassDelegateTypeSymbol*>(this);
 683     }
 684     else if (symbolType == SymbolType::memberExpressionTypeSymbol)
 685     {
 686         return static_cast<const MemberExpressionTypeSymbol*>(this);
 687     }
 688     else if (IsClassTypeSymbol())
 689     {
 690         return static_cast<const ClassTypeSymbol*>(this);
 691     }
 692     else
 693     {
 694         if (parent)
 695         {
 696             return parent->ClassInterfaceEnumDelegateOrNsNoThrow();
 697         }
 698         else
 699         {
 700             return nullptr;
 701         }
 702     }
 703 }
 704 
 705 ContainerSymbol* Symbol::ClassInterfaceEnumDelegateOrNsNoThrow()
 706 {
 707     if (symbolType == SymbolType::namespaceSymbol)
 708     {
 709         if (!GetModule()->IsRootModule())
 710         {
 711             Module* rootModule = GetRootModuleForCurrentThread();
 712             NamespaceSymbol* mappedNs = rootModule->GetSymbolTable().GetMappedNs(static_cast<NamespaceSymbol*>(this));
 713             if (mappedNs)
 714             {
 715                 return mappedNs;
 716             }
 717         }
 718         return static_cast<NamespaceSymbol*>(this);
 719     }
 720     else if (symbolType == SymbolType::interfaceTypeSymbol)
 721     {
 722         return static_cast<InterfaceTypeSymbol*>(this);
 723     }
 724     else if (symbolType == SymbolType::enumTypeSymbol)
 725     {
 726         return static_cast<EnumTypeSymbol*>(this);
 727     }
 728     else if (symbolType == SymbolType::delegateTypeSymbol)
 729     {
 730         return static_cast<DelegateTypeSymbol*>(this);
 731     }
 732     else if (symbolType == SymbolType::classDelegateTypeSymbol)
 733     {
 734         return static_cast<ClassDelegateTypeSymbol*>(this);
 735     }
 736     else if (symbolType == SymbolType::memberExpressionTypeSymbol)
 737     {
 738         return static_cast<MemberExpressionTypeSymbol*>(this);
 739     }
 740     else if (IsClassTypeSymbol())
 741     {
 742         return static_cast<ClassTypeSymbol*>(this);
 743     }
 744     else
 745     {
 746         if (parent)
 747         {
 748             return parent->ClassInterfaceEnumDelegateOrNsNoThrow();
 749         }
 750         else
 751         {
 752             return nullptr;
 753         }
 754     }
 755 }
 756 
 757 const ClassTypeSymbol* Symbol::Class() const
 758 {
 759     const ClassTypeSymbol* cls = ClassNoThrow();
 760     if (cls)
 761     {
 762         return cls;
 763     }
 764     else
 765     {
 766         throw Exception("class type symbol not found"GetSpan()SourceModuleId());
 767     }
 768 }
 769 
 770 ClassTypeSymbol* Symbol::Class()
 771 {
 772     ClassTypeSymbol* cls = ClassNoThrow();
 773     if (cls)
 774     {
 775         return cls;
 776     }
 777     else
 778     {
 779         throw Exception("class type symbol not found"GetSpan()SourceModuleId());
 780     }
 781 }
 782 
 783 const ClassTypeSymbol* Symbol::ContainingClassNoThrow() const
 784 {
 785     if (parent)
 786     {
 787         return parent->ClassNoThrow();
 788     }
 789     else
 790     {
 791         return nullptr;
 792     }
 793 }
 794 
 795 ClassTypeSymbol* Symbol::ContainingClassNoThrow()
 796 {
 797     if (parent)
 798     {
 799         return parent->ClassNoThrow();
 800     }
 801     else
 802     {
 803         return nullptr;
 804     }
 805 }
 806 
 807 const InterfaceTypeSymbol* Symbol::InterfaceNoThrow() const
 808 {
 809     if (symbolType == SymbolType::interfaceTypeSymbol)
 810     {
 811         return static_cast<const InterfaceTypeSymbol*>(this);
 812     }
 813     else
 814     {
 815         if (parent)
 816         {
 817             return parent->InterfaceNoThrow();
 818         }
 819         else
 820         {
 821             return nullptr;
 822         }
 823     }
 824 }
 825 
 826 InterfaceTypeSymbol* Symbol::InterfaceNoThrow()
 827 {
 828     if (symbolType == SymbolType::interfaceTypeSymbol)
 829     {
 830         return static_cast<InterfaceTypeSymbol*>(this);
 831     }
 832     else
 833     {
 834         if (parent)
 835         {
 836             return parent->InterfaceNoThrow();
 837         }
 838         else
 839         {
 840             return nullptr;
 841         }
 842     }
 843 }
 844 
 845 const InterfaceTypeSymbol* Symbol::ContainingInterfaceNoThrow() const
 846 {
 847     if (parent)
 848     {
 849         return parent->InterfaceNoThrow();
 850     }
 851     else
 852     {
 853         return nullptr;
 854     }
 855 }
 856 
 857 InterfaceTypeSymbol* Symbol::ContainingInterfaceNoThrow()
 858 {
 859     if (parent)
 860     {
 861         return parent->InterfaceNoThrow();
 862     }
 863     else
 864     {
 865         return nullptr;
 866     }
 867 }
 868 
 869 const FunctionSymbol* Symbol::FunctionNoThrow() const
 870 {
 871     if (IsFunctionSymbol())
 872     {
 873         return static_cast<const FunctionSymbol*>(this);
 874     }
 875     else
 876     {
 877         if (parent)
 878         {
 879             return parent->FunctionNoThrow();
 880         }
 881         else
 882         {
 883             return nullptr;
 884         }
 885     }
 886 }
 887 
 888 FunctionSymbol* Symbol::FunctionNoThrow()
 889 {
 890     if (IsFunctionSymbol())
 891     {
 892         return static_cast<FunctionSymbol*>(this);
 893     }
 894     else
 895     {
 896         if (parent)
 897         {
 898             return parent->FunctionNoThrow();
 899         }
 900         else
 901         {
 902             return nullptr;
 903         }
 904     }
 905 }
 906 
 907 const FunctionSymbol* Symbol::Function() const
 908 {
 909     const FunctionSymbol* function = FunctionNoThrow();
 910     if (function)
 911     {
 912         return function;
 913     }
 914     else
 915     {
 916         throw Exception("function symbol not found"GetSpan()SourceModuleId());
 917     }
 918 }
 919 
 920 FunctionSymbol* Symbol::Function()
 921 {
 922     FunctionSymbol* function = FunctionNoThrow();
 923     if (function)
 924     {
 925         return function;
 926     }
 927     else
 928     {
 929         throw Exception("function symbol not found"GetSpan()SourceModuleId());
 930     }
 931 }
 932 
 933 const FunctionSymbol* Symbol::ContainingFunctionNoThrow() const
 934 {
 935     if (parent)
 936     {
 937         return parent->FunctionNoThrow();
 938     }
 939     else
 940     {
 941         return nullptr;
 942     }
 943 }
 944 
 945 FunctionSymbol* Symbol::ContainingFunctionNoThrow()
 946 {
 947     if (parent)
 948     {
 949         return parent->FunctionNoThrow();
 950     }
 951     else
 952     {
 953         return nullptr;
 954     }
 955 }
 956 
 957 const ContainerScope* Symbol::ClassOrNsScope() const
 958 {
 959     const ContainerSymbol* classOrNs = ClassOrNsNoThrow();
 960     if (classOrNs)
 961     {
 962         return classOrNs->GetContainerScope();
 963     }
 964     else
 965     {
 966         throw Exception("class or namespace scope not found"GetSpan()SourceModuleId());
 967     }
 968 }
 969 
 970 ContainerScope* Symbol::ClassOrNsScope()
 971 {
 972     ContainerSymbol* classOrNs = ClassOrNsNoThrow();
 973     if (classOrNs)
 974     {
 975         return classOrNs->GetContainerScope();
 976     }
 977     else
 978     {
 979         throw Exception("class or namespace scope not found"GetSpan()SourceModuleId());
 980     }
 981 }
 982 
 983 const ContainerScope* Symbol::ClassInterfaceOrNsScope() const
 984 {
 985     const ContainerSymbol* classInterfaceOrNs = ClassInterfaceOrNsNoThrow();
 986     if (classInterfaceOrNs)
 987     {
 988         return classInterfaceOrNs->GetContainerScope();
 989     }
 990     else
 991     {
 992         throw Exception("class, interface or namespace scope not found"GetSpan()SourceModuleId());
 993     }
 994 }
 995 
 996 ContainerScope* Symbol::ClassInterfaceOrNsScope()
 997 {
 998     ContainerSymbol* classInterfaceOrNs = ClassInterfaceOrNsNoThrow();
 999     if (classInterfaceOrNs)
1000     {
1001         return classInterfaceOrNs->GetContainerScope();
1002     }
1003     else
1004     {
1005         throw Exception("class, interface or namespace scope not found"GetSpan()SourceModuleId());
1006     }
1007 }
1008 
1009 const ContainerScope* Symbol::ClassInterfaceEnumDelegateOrNsScope() const
1010 {
1011     const ContainerSymbol* classInterfaceEnumDelegateOrNs = ClassInterfaceEnumDelegateOrNsNoThrow();
1012     if (classInterfaceEnumDelegateOrNs)
1013     {
1014         return classInterfaceEnumDelegateOrNs->GetContainerScope();
1015     }
1016     else
1017     {
1018         throw Exception("class, interface, enumeration, delegate, class delegate or namespace scope not found"GetSpan()SourceModuleId());
1019     }
1020 }
1021 
1022 ContainerScope* Symbol::ClassInterfaceEnumDelegateOrNsScope()
1023 {
1024     ContainerSymbol* classInterfaceEnumDelegateOrNs = ClassInterfaceEnumDelegateOrNsNoThrow();
1025     if (classInterfaceEnumDelegateOrNs)
1026     {
1027         return classInterfaceEnumDelegateOrNs->GetContainerScope();
1028     }
1029     else
1030     {
1031         throw Exception("class, interface, enumeration, delegate, class delegate or namespace scope not found"GetSpan()SourceModuleId());
1032     }
1033 }
1034 
1035 void Symbol::SetAttributes(std::std::unique_ptr<AttributesNode>&&attributes_)
1036 {
1037     attributes = std::move(attributes_);
1038 }
1039 
1040 std::std::unique_ptr<sngxml::dom::Element>Symbol::ToDomElement(TypeMap&typeMap)
1041 {
1042     std::unique_ptr<sngxml::dom::Element> element = CreateDomElement(typeMap);
1043     if (element)
1044     {
1045         std::u32string info = Info();
1046         if (!info.empty())
1047         {
1048             element->SetAttribute(U"info"info);
1049         }
1050         AppendChildElements(element.get()typeMap);
1051     }
1052     return element;
1053 }
1054 
1055 std::std::unique_ptr<sngxml::dom::Element>Symbol::CreateDomElement(TypeMap&typeMap)
1056 {
1057     return std::unique_ptr<sngxml::dom::Element>(new sngxml::dom::Element(ToUtf32(ClassName())));
1058 }
1059 
1060 sngxml::dom::Element* Symbol::ToCCElement(int ccPrefixLengthconst std::u32string& replacementconst std::u32string& functionGroup) const
1061 {
1062     sngxml::dom::Element* ccElement = new sngxml::dom::Element(U"symbol");
1063     ccElement->SetAttribute(U"prefixLength"ToUtf32(std::to_string(ccPrefixLength)));
1064     ccElement->SetAttribute(U"category"ToUtf32(GetSymbolCategoryStr()));
1065     ccElement->SetAttribute(U"help"ToUtf32(GetSymbolHelp()));
1066     ccElement->SetAttribute(U"completion"Name());
1067     ccElement->SetAttribute(U"replacement"replacement);
1068     ccElement->SetAttribute(U"functionGroup"functionGroup);
1069     return ccElement;
1070 }
1071 
1072 std::string Symbol::GetSymbolHelp() const
1073 {
1074     std::string help = "(";
1075     help.append(GetSymbolCategoryDescription()).append(") ");
1076     help.append(ToUtf8(FullName()));
1077     return help;
1078 }
1079 
1080 bool Symbol::GetLocation(SymbolLocation& definitionLocation) const
1081 {
1082     Module* sourceModule = GetModuleById(sourceModuleId);
1083     if (!sourceModule) return false;
1084     int32_t scol = 0;
1085     int32_t ecol = 0;
1086     sourceModule->GetColumns(spanscolecol);
1087     definitionLocation = SymbolLocation(sourceModule->Id()span.fileIndexspan.linescolecol);
1088     return true;
1089 }
1090 
1091 std::std::unique_ptr<Symbol>Symbol::RemoveMember(intsymbolIndex)
1092 {
1093     return std::unique_ptr<Symbol>();
1094 }
1095 
1096 std::std::unique_ptr<Symbol>Symbol::RemoveFromParent()
1097 {
1098     std::unique_ptr<Symbol> symbol = parent->RemoveMember(symbolIndex);
1099     return symbol;
1100 }
1101 
1102 SymbolCreator::~SymbolCreator()
1103 {
1104 }
1105 
1106 template<typename SymbolT>
1107 class ConcreteSymbolCreator public SymbolCreator
1108 {
1109 public:
1110     Symbol* CreateSymbol(const Span& spanconst boost::uuids::uuid& sourceModuleIdconst std::u32string& name) override
1111     {
1112         return new SymbolT(spansourceModuleIdname);
1113     }
1114 };
1115 
1116 void SymbolFactory::Init()
1117 {
1118     instance.reset(new SymbolFactory());
1119 }
1120 
1121 void SymbolFactory::Done()
1122 {
1123     instance.reset();
1124 }
1125 
1126 std::unique_ptr<SymbolFactory> SymbolFactory::instance;
1127 
1128 SymbolFactory::SymbolFactory()
1129 {
1130     symbolCreators.resize(static_cast<uint8_t>(SymbolType::maxSymbol));
1131     Register(SymbolType::boolTypeSymbolnew ConcreteSymbolCreator<BoolTypeSymbol>());
1132     Register(SymbolType::sbyteTypeSymbolnew ConcreteSymbolCreator<SByteTypeSymbol>());
1133     Register(SymbolType::byteTypeSymbolnew ConcreteSymbolCreator<ByteTypeSymbol>());
1134     Register(SymbolType::shortTypeSymbolnew ConcreteSymbolCreator<ShortTypeSymbol>());
1135     Register(SymbolType::ushortTypeSymbolnew ConcreteSymbolCreator<UShortTypeSymbol>());
1136     Register(SymbolType::intTypeSymbolnew ConcreteSymbolCreator<IntTypeSymbol>());
1137     Register(SymbolType::uintTypeSymbolnew ConcreteSymbolCreator<UIntTypeSymbol>());
1138     Register(SymbolType::longTypeSymbolnew ConcreteSymbolCreator<LongTypeSymbol>());
1139     Register(SymbolType::ulongTypeSymbolnew ConcreteSymbolCreator<ULongTypeSymbol>());
1140     Register(SymbolType::floatTypeSymbolnew ConcreteSymbolCreator<FloatTypeSymbol>());
1141     Register(SymbolType::doubleTypeSymbolnew ConcreteSymbolCreator<DoubleTypeSymbol>());
1142     Register(SymbolType::charTypeSymbolnew ConcreteSymbolCreator<CharTypeSymbol>());
1143     Register(SymbolType::wcharTypeSymbolnew ConcreteSymbolCreator<WCharTypeSymbol>());
1144     Register(SymbolType::ucharTypeSymbolnew ConcreteSymbolCreator<UCharTypeSymbol>());
1145     Register(SymbolType::voidTypeSymbolnew ConcreteSymbolCreator<VoidTypeSymbol>());
1146     Register(SymbolType::nullPtrTypeSymbolnew ConcreteSymbolCreator<NullPtrType>());
1147     Register(SymbolType::arrayTypeSymbolnew ConcreteSymbolCreator<ArrayTypeSymbol>());
1148     Register(SymbolType::derivedTypeSymbolnew ConcreteSymbolCreator<DerivedTypeSymbol>());
1149     Register(SymbolType::namespaceSymbolnew ConcreteSymbolCreator<NamespaceSymbol>());
1150     Register(SymbolType::functionSymbolnew ConcreteSymbolCreator<FunctionSymbol>());
1151     Register(SymbolType::staticConstructorSymbolnew ConcreteSymbolCreator<StaticConstructorSymbol>());
1152     Register(SymbolType::constructorSymbolnew ConcreteSymbolCreator<ConstructorSymbol>());
1153     Register(SymbolType::destructorSymbolnew ConcreteSymbolCreator<DestructorSymbol>());
1154     Register(SymbolType::memberFunctionSymbolnew ConcreteSymbolCreator<MemberFunctionSymbol>());
1155     Register(SymbolType::conversionFunctionSymbolnew ConcreteSymbolCreator<ConversionFunctionSymbol>());
1156     Register(SymbolType::functionGroupSymbolnew ConcreteSymbolCreator<FunctionGroupSymbol>());
1157     Register(SymbolType::classGroupTypeSymbolnew ConcreteSymbolCreator<ClassGroupTypeSymbol>());
1158     Register(SymbolType::classTypeSymbolnew ConcreteSymbolCreator<ClassTypeSymbol>());
1159     Register(SymbolType::classTemplateSpecializationSymbolnew ConcreteSymbolCreator<ClassTemplateSpecializationSymbol>());
1160     Register(SymbolType::interfaceTypeSymbolnew ConcreteSymbolCreator<InterfaceTypeSymbol>());
1161     Register(SymbolType::conceptGroupSymbolnew ConcreteSymbolCreator<ConceptGroupSymbol>());
1162     Register(SymbolType::conceptSymbolnew ConcreteSymbolCreator<ConceptSymbol>());
1163     Register(SymbolType::delegateTypeSymbolnew ConcreteSymbolCreator<DelegateTypeSymbol>());
1164     Register(SymbolType::classDelegateTypeSymbolnew ConcreteSymbolCreator<ClassDelegateTypeSymbol>());
1165     Register(SymbolType::declarationBlocknew ConcreteSymbolCreator<DeclarationBlock>());
1166     Register(SymbolType::typedefSymbolnew ConcreteSymbolCreator<TypedefSymbol>());
1167     Register(SymbolType::constantSymbolnew ConcreteSymbolCreator<ConstantSymbol>());
1168     Register(SymbolType::enumTypeSymbolnew ConcreteSymbolCreator<EnumTypeSymbol>());
1169     Register(SymbolType::enumConstantSymbolnew ConcreteSymbolCreator<EnumConstantSymbol>());
1170     Register(SymbolType::templateParameterSymbolnew ConcreteSymbolCreator<TemplateParameterSymbol>());
1171     Register(SymbolType::boundTemplateParameterSymbolnew ConcreteSymbolCreator<BoundTemplateParameterSymbol>());
1172     Register(SymbolType::parameterSymbolnew ConcreteSymbolCreator<ParameterSymbol>());
1173     Register(SymbolType::localVariableSymbolnew ConcreteSymbolCreator<LocalVariableSymbol>());
1174     Register(SymbolType::memberVariableSymbolnew ConcreteSymbolCreator<MemberVariableSymbol>());
1175     Register(SymbolType::basicTypeUnaryPlusnew ConcreteSymbolCreator<BasicTypeUnaryPlusOperation>());
1176     Register(SymbolType::basicTypeIntUnaryMinusnew ConcreteSymbolCreator<BasicTypeIntUnaryMinusOperation>());
1177     Register(SymbolType::basicTypeFloatUnaryMinusnew ConcreteSymbolCreator<BasicTypeFloatUnaryMinusOperation>());
1178     Register(SymbolType::basicTypeComplementnew ConcreteSymbolCreator<BasicTypeComplementOperation>());
1179     Register(SymbolType::basicTypeAddnew ConcreteSymbolCreator<BasicTypeAddOperation>());
1180     Register(SymbolType::basicTypeFAddnew ConcreteSymbolCreator<BasicTypeFAddOperation>());
1181     Register(SymbolType::basicTypeSubnew ConcreteSymbolCreator<BasicTypeSubOperation>());
1182     Register(SymbolType::basicTypeFSubnew ConcreteSymbolCreator<BasicTypeFSubOperation>());
1183     Register(SymbolType::basicTypeMulnew ConcreteSymbolCreator<BasicTypeMulOperation>());
1184     Register(SymbolType::basicTypeFMulnew ConcreteSymbolCreator<BasicTypeFMulOperation>());
1185     Register(SymbolType::basicTypeSDivnew ConcreteSymbolCreator<BasicTypeSDivOperation>());
1186     Register(SymbolType::basicTypeUDivnew ConcreteSymbolCreator<BasicTypeUDivOperation>());
1187     Register(SymbolType::basicTypeFDivnew ConcreteSymbolCreator<BasicTypeFDivOperation>());
1188     Register(SymbolType::basicTypeSRemnew ConcreteSymbolCreator<BasicTypeSRemOperation>());
1189     Register(SymbolType::basicTypeURemnew ConcreteSymbolCreator<BasicTypeURemOperation>());
1190     Register(SymbolType::basicTypeAndnew ConcreteSymbolCreator<BasicTypeAndOperation>());
1191     Register(SymbolType::basicTypeOrnew ConcreteSymbolCreator<BasicTypeOrOperation>());
1192     Register(SymbolType::basicTypeXornew ConcreteSymbolCreator<BasicTypeXorOperation>());
1193     Register(SymbolType::basicTypeShlnew ConcreteSymbolCreator<BasicTypeShlOperation>());
1194     Register(SymbolType::basicTypeAShrnew ConcreteSymbolCreator<BasicTypeAShrOperation>());
1195     Register(SymbolType::basicTypeLShrnew ConcreteSymbolCreator<BasicTypeLShrOperation>());
1196     Register(SymbolType::basicTypeNotnew ConcreteSymbolCreator<BasicTypeNotOperation>());
1197     Register(SymbolType::basicTypeIntegerEqualitynew ConcreteSymbolCreator<BasicTypeIntegerEqualityOperation>());
1198     Register(SymbolType::basicTypeUnsignedIntegerLessThannew ConcreteSymbolCreator<BasicTypeUnsignedIntegerLessThanOperation>());
1199     Register(SymbolType::basicTypeSignedIntegerLessThannew ConcreteSymbolCreator<BasicTypeSignedIntegerLessThanOperation>());
1200     Register(SymbolType::basicTypeFloatingEqualitynew ConcreteSymbolCreator<BasicTypeFloatingEqualityOperation>());
1201     Register(SymbolType::basicTypeFloatingLessThannew ConcreteSymbolCreator<BasicTypeFloatingLessThanOperation>());
1202     Register(SymbolType::defaultInt1new ConcreteSymbolCreator<BasicTypeDefaultInt1Operation>());
1203     Register(SymbolType::defaultSInt8new ConcreteSymbolCreator<BasicTypeDefaultSInt8Operation>());
1204     Register(SymbolType::defaultUInt8new ConcreteSymbolCreator<BasicTypeDefaultUInt8Operation>());
1205     Register(SymbolType::defaultSInt16new ConcreteSymbolCreator<BasicTypeDefaultSInt16Operation>());
1206     Register(SymbolType::defaultUInt16new ConcreteSymbolCreator<BasicTypeDefaultUInt16Operation>());
1207     Register(SymbolType::defaultSInt32new ConcreteSymbolCreator<BasicTypeDefaultSInt32Operation>());
1208     Register(SymbolType::defaultUInt32new ConcreteSymbolCreator<BasicTypeDefaultUInt32Operation>());
1209     Register(SymbolType::defaultSInt64new ConcreteSymbolCreator<BasicTypeDefaultSInt64Operation>());
1210     Register(SymbolType::defaultUInt64new ConcreteSymbolCreator<BasicTypeDefaultUInt64Operation>());
1211     Register(SymbolType::defaultFloatnew ConcreteSymbolCreator<BasicTypeDefaultFloatOperation>());
1212     Register(SymbolType::defaultDoublenew ConcreteSymbolCreator<BasicTypeDefaultDoubleOperation>());
1213     Register(SymbolType::defaultCharnew ConcreteSymbolCreator<BasicTypeDefaultCharOperation>());
1214     Register(SymbolType::defaultWCharnew ConcreteSymbolCreator<BasicTypeDefaultWCharOperation>());
1215     Register(SymbolType::defaultUCharnew ConcreteSymbolCreator<BasicTypeDefaultUCharOperation>());
1216     Register(SymbolType::basicTypeCopyCtornew ConcreteSymbolCreator<BasicTypeCopyCtor>());
1217     Register(SymbolType::basicTypeMoveCtornew ConcreteSymbolCreator<BasicTypeMoveCtor>());
1218     Register(SymbolType::basicTypeCopyAssignmentnew ConcreteSymbolCreator<BasicTypeCopyAssignment>());
1219     Register(SymbolType::basicTypeMoveAssignmentnew ConcreteSymbolCreator<BasicTypeMoveAssignment>());
1220     Register(SymbolType::basicTypeReturnnew ConcreteSymbolCreator<BasicTypeReturn>());
1221     Register(SymbolType::basicTypeImplicitSignExtensionnew ConcreteSymbolCreator<BasicTypeImplicitSignExtensionOperation>());
1222     Register(SymbolType::basicTypeImplicitZeroExtensionnew ConcreteSymbolCreator<BasicTypeImplicitZeroExtensionOperation>());
1223     Register(SymbolType::basicTypeExplicitSignExtensionnew ConcreteSymbolCreator<BasicTypeExplicitSignExtensionOperation>());
1224     Register(SymbolType::basicTypeExplicitZeroExtensionnew ConcreteSymbolCreator<BasicTypeExplicitZeroExtensionOperation>());
1225     Register(SymbolType::basicTypeTruncationnew ConcreteSymbolCreator<BasicTypeTruncationOperation>());
1226     Register(SymbolType::basicTypeBitCastnew ConcreteSymbolCreator<BasicTypeBitCastOperation>());
1227     Register(SymbolType::basicTypeImplicitUnsignedIntToFloatingnew ConcreteSymbolCreator<BasicTypeImplicitUnsignedIntToFloatingOperation>());
1228     Register(SymbolType::basicTypeImplicitSignedIntToFloatingnew ConcreteSymbolCreator<BasicTypeImplicitSignedIntToFloatingOperation>());
1229     Register(SymbolType::basicTypeExplicitUnsignedIntToFloatingnew ConcreteSymbolCreator<BasicTypeExplicitUnsignedIntToFloatingOperation>());
1230     Register(SymbolType::basicTypeExplicitSignedIntToFloatingnew ConcreteSymbolCreator<BasicTypeExplicitSignedIntToFloatingOperation>());
1231     Register(SymbolType::basicTypeFloatingToUnsignedIntnew ConcreteSymbolCreator<BasicTypeFloatingToUnsignedIntOperation>());
1232     Register(SymbolType::basicTypeFloatingToSignedIntnew ConcreteSymbolCreator<BasicTypeFloatingToSignedIntOperation>());
1233     Register(SymbolType::basicTypeFloatingExtensionnew ConcreteSymbolCreator<BasicTypeFloatingExtensionOperation>());
1234     Register(SymbolType::basicTypeFloatingTruncationnew ConcreteSymbolCreator<BasicTypeFloatingTruncationOperation>());
1235     Register(SymbolType::enumTypeDefaultConstructornew ConcreteSymbolCreator<EnumTypeDefaultConstructor>());
1236     Register(SymbolType::enumTypeCopyConstructornew ConcreteSymbolCreator<EnumTypeCopyConstructor>());
1237     Register(SymbolType::enumTypeMoveConstructornew ConcreteSymbolCreator<EnumTypeMoveConstructor>());
1238     Register(SymbolType::enumTypeCopyAssignmentnew ConcreteSymbolCreator<EnumTypeCopyAssignment>());
1239     Register(SymbolType::enumTypeMoveAssignmentnew ConcreteSymbolCreator<EnumTypeMoveAssignment>());
1240     Register(SymbolType::enumTypeReturnnew ConcreteSymbolCreator<EnumTypeReturn>());
1241     Register(SymbolType::enumTypeEqualitynew ConcreteSymbolCreator<EnumTypeEqualityOp>());
1242     Register(SymbolType::enumTypeToUnderlyingTypenew ConcreteSymbolCreator<EnumTypeToUnderlyingTypeConversion>());
1243     Register(SymbolType::underlyingToEnumTypenew ConcreteSymbolCreator<UnderlyingTypeToEnumTypeConversion>());
1244     Register(SymbolType::delegateTypeDefaultConstructornew ConcreteSymbolCreator<DelegateTypeDefaultConstructor>());
1245     Register(SymbolType::delegateTypeCopyConstructornew ConcreteSymbolCreator<DelegateTypeCopyConstructor>());
1246     Register(SymbolType::delegateTypeMoveConstructornew ConcreteSymbolCreator<DelegateTypeMoveConstructor>());
1247     Register(SymbolType::delegateTypeCopyAssignmentnew ConcreteSymbolCreator<DelegateTypeCopyAssignment>());
1248     Register(SymbolType::delegateTypeMoveAssignmentnew ConcreteSymbolCreator<DelegateTypeMoveAssignment>());
1249     Register(SymbolType::delegateTypeReturnnew ConcreteSymbolCreator<DelegateTypeReturn>());
1250     Register(SymbolType::delegateTypeEqualitynew ConcreteSymbolCreator<DelegateTypeEquality>());
1251     Register(SymbolType::functionToDelegateSymbolnew ConcreteSymbolCreator<FunctionToDelegateConversion>());
1252     Register(SymbolType::classDelegateTypeDefaultConstructornew ConcreteSymbolCreator<ClassDelegateTypeDefaultConstructor>());
1253     Register(SymbolType::classDelegateTypeCopyConstructornew ConcreteSymbolCreator<ClassDelegateTypeCopyConstructor>());
1254     Register(SymbolType::classDelegateTypeMoveConstructornew ConcreteSymbolCreator<ClassDelegateTypeMoveConstructor>());
1255     Register(SymbolType::classDelegateTypeCopyAssignmentnew ConcreteSymbolCreator<ClassDelegateTypeCopyAssignment>());
1256     Register(SymbolType::classDelegateTypeMoveAssignmentnew ConcreteSymbolCreator<ClassDelegateTypeMoveAssignment>());
1257     Register(SymbolType::classDelegateTypeEqualitynew ConcreteSymbolCreator<ClassDelegateTypeEquality>());
1258     Register(SymbolType::memberFunctionToClassDelegateSymbolnew ConcreteSymbolCreator<MemberFunctionToClassDelegateConversion>());
1259     Register(SymbolType::arrayLengthFunctionSymbolnew ConcreteSymbolCreator<ArrayLengthFunction>());
1260     Register(SymbolType::arrayBeginFunctionSymbolnew ConcreteSymbolCreator<ArrayBeginFunction>())
1261     Register(SymbolType::arrayEndFunctionSymbolnew ConcreteSymbolCreator<ArrayEndFunction>());
1262     Register(SymbolType::arrayCBeginFunctionSymbolnew ConcreteSymbolCreator<ArrayCBeginFunction>());
1263     Register(SymbolType::arrayCEndFunctionSymbolnew ConcreteSymbolCreator<ArrayCEndFunction>());
1264     Register(SymbolType::globalVariableSymbolnew ConcreteSymbolCreator<GlobalVariableSymbol>());
1265     Register(SymbolType::stringFunctionContainerSymbolnew ConcreteSymbolCreator<StringFunctionContainerSymbol>());
1266     Register(SymbolType::stringLengthFunctionSymbolnew ConcreteSymbolCreator<StringLengthFunction>());
1267     Register(SymbolType::axiomSymbolnew ConcreteSymbolCreator<AxiomSymbol>());
1268 #ifdef _WIN32
1269 
1270 #endif
1271 }
1272 
1273 Symbol* SymbolFactory::CreateSymbol(SymbolType symbolTypeconst Span& spanconst boost::uuids::uuid& sourceModuleIdconst std::u32string& name)
1274 {
1275     const std::std::unique_ptr<SymbolCreator>&symbolCreator=symbolCreators[static_cast<uint8_t>(symbolType)];
1276     if (symbolCreator)
1277     {
1278         Symbol* symbol = symbolCreator->CreateSymbol(spansourceModuleIdname);
1279         if (symbol)
1280         {
1281             return symbol;
1282         }
1283         else
1284         {
1285             throw std::runtime_error("could not create symbol");
1286         }
1287     }
1288     else
1289     {
1290         throw std::runtime_error("no creator for symbol type '" + SymbolTypeStr(symbolType) + "'");
1291     }
1292 }
1293 
1294 void SymbolFactory::Register(SymbolType symbolTypeSymbolCreator* creator)
1295 {
1296     symbolCreators[static_cast<uint8_t>(symbolType)] = std::unique_ptr<SymbolCreator>(creator);
1297 }
1298 
1299 void InitSymbol()
1300 {
1301     SymbolFactory::Init();
1302 }
1303 
1304 void DoneSymbol()
1305 {
1306     SymbolFactory::Done();
1307 }
1308 
1309 } } // namespace cmajor::symbols