1 // =================================
  2 // Copyright (c) 2021 Seppo Laakko
  3 // Distributed under the MIT license
  4 // =================================
  5 
  6 #ifndef CMAJOR_SYMBOLS_FUNCTION_SYMBOL_INCLUDED
  7 #define CMAJOR_SYMBOLS_FUNCTION_SYMBOL_INCLUDED
  8 #include <cmajor/symbols/TypeSymbol.hpp>
  9 #include <cmajor/symbols/VariableSymbol.hpp>
 10 #include <cmajor/symbols/Meta.hpp>
 11 #include <sngcm/ast/Function.hpp>
 12 #include <cmajor/ir/GenObject.hpp>
 13 #include <unordered_set>
 14 
 15 namespace cmajor {  namespace symbols {
 16 
 17 using namespace cmajor::ir;
 18 class Value;
 19 class IntrinsicFunction;
 20 
 21 struct FunctionSymbolsEqual 
 22 {
 23     bool operator()(FunctionSymbol* leftFunctionSymbol* right) const;
 24 };
 25 
 26 struct FunctionSymbolHash 
 27 {
 28     size_t operator()(FunctionSymbol* fun) const;
 29 };
 30 
 31 class ViableFunctionSet 
 32 {
 33 public:
 34     const std::std::unordered_set<FunctionSymbol*FunctionSymbolHashFunctionSymbolsEqual>&Get() const{returnset;}
 35     void Insert(FunctionSymbol* fun);
 36 private:
 37     std::unordered_set<FunctionSymbol*FunctionSymbolHashFunctionSymbolsEqual> set;
 38 };
 39 
 40 using AccessCheckFunction = bool (*);
 41 
 42 void SetAccessCheckFunction(AccessCheckFunction accessCheckFunc);
 43 AccessCheckFunction GetAccessCheckFunction();
 44 
 45 class FunctionGroupSymbol public Symbol
 46 {
 47 public:
 48     FunctionGroupSymbol(const Span& span_const boost::uuids::uuid& sourceModuleId_const std::u32string& name_);
 49     bool IsExportSymbol() const override { return false; }
 50     std::string TypeString() const override { return "function_group"; }
 51     void ComputeMangledName() override;
 52     void AddFunction(FunctionSymbol* function);
 53     void RemoveFunction(FunctionSymbol* function);
 54     bool IsEmpty() const;
 55     FunctionSymbol* GetFunction();
 56     void CollectViableFunctions(int arityViableFunctionSet& viableFunctionsModule* module);
 57     bool HasProjectMembers() const override;
 58     void AppendChildElements(sngxml::dom::Element* elementTypeMap& typeMap) const override;
 59     std::u32string Info() const override { return Name(); }
 60     const char* ClassName() const override { return "FunctionGroupSymbol"; }
 61     void Check() override;
 62     void CheckDuplicateFunctionSymbols();
 63     std::string GetSymbolCategoryStr() const override { return "FN"; }
 64     std::string GetSymbolCategoryDescription() const override { return "function"; }
 65     std::string GetSymbolHelp() const override;
 66     bool IsValidCCFunctionGroup(FunctionSymbol* fromFunction) const;
 67     std::string GetOverloadList() const;
 68 private:
 69     std::unordered_map<intstd::std::vector<FunctionSymbol*>>arityFunctionListMap;
 70     std::vector<FunctionSymbol*> varArgFunctions;
 71 };
 72 
 73 enum class ConversionType : uint8_t 
 74 {
 75     implicit_explicit_
 76 };
 77 
 78 enum class FunctionSymbolFlags : uint32_t 
 79 {
 80     none=  0
 81     inline_=  1 << 0
 82     constExpr=  1 << 1
 83     cdecl_=  1 << 2
 84     suppress=  1 << 3
 85     default_=  1 << 4
 86     explicit_=  1 << 5
 87     virtual_=  1 << 6
 88     override_=  1 << 7
 89     abstract_=  1 << 8
 90     new_=  1 << 9
 91     const_=  1 << 10
 92     conversion=  1 << 11
 93     linkOnceOdrLinkage=  1 << 12
 94     templateSpecialization=  1 << 13
 95     hasTry=  1 << 14
 96     hasSource=  1 << 15
 97     includeConstraint=  1 << 16
 98     copy=  1 << 17
 99     varArg=  1 << 18
100     winapi=  1 << 19
101     dontReuse=  1 << 20
102     hasArtificialBody=  1 << 21
103     hasCleanup=  1 << 22
104     systemDefault=  1 << 23
105     immutable=  1 << 24
106 };
107 
108 inline FunctionSymbolFlags operator|(FunctionSymbolFlags leftFunctionSymbolFlags right)
109 {
110     return FunctionSymbolFlags(uint32_t(left) | uint32_t(right));
111 }
112 
113 inline FunctionSymbolFlags operator&(FunctionSymbolFlags leftFunctionSymbolFlags right)
114 {
115     return FunctionSymbolFlags(uint32_t(left) & uint32_t(right));
116 }
117 
118 inline FunctionSymbolFlags operator~(FunctionSymbolFlags flag)
119 {
120     return FunctionSymbolFlags(~uint32_t(flag));
121 }
122 
123 std::string FunctionSymbolFlagStr(FunctionSymbolFlags flags);
124 
125 class ParameterSymbol;
126 class LocalVariableSymbol;
127 class TypeSymbol;
128 class TemplateParameterSymbol;
129 class BoundTemplateParameterSymbol;
130 
131 class FunctionSymbol public ContainerSymbol
132 {
133 public:
134     FunctionSymbol(const Span& span_const boost::uuids::uuid& sourceModuleId_const std::u32string& name_);
135     FunctionSymbol(SymbolType symbolType_const Span& span_const boost::uuids::uuid& sourceModuleId_const std::u32string& name_);
136     FunctionSymbol(const FunctionSymbol&) = delete;
137     FunctionSymbol& operator=(const FunctionSymbol&) = delete;
138     void Write(SymbolWriter& writer) override;
139     void Read(SymbolReader& reader) override;
140     void EmplaceFunction(FunctionSymbol* functionSymbolint index) override;
141     void Accept(SymbolCollector* collector) override;
142     const NodeList<Node>& UsingNodes() const { return usingNodes; }
143     FunctionNode* GetFunctionNode() { return functionNode.get(); }
144     ConstraintNode* Constraint() { return constraint.get(); }
145     void SetConstraint(ConstraintNode* constraint_) { constraint.reset(constraint_); }
146     void EmplaceType(TypeSymbol* typeSymbolint index) override;
147     void AddMember(Symbol* member) override;
148     bool IsFunctionSymbol() const override { return true; }
149     std::string TypeString() const override { return "function"; }
150     bool IsExportSymbol() const override;
151     virtual void ComputeName();
152     std::u32string FullName() const override;
153     std::u32string FullName(bool withParamNames) const;
154     std::u32string FullNameWithSpecifiers() const override;
155     std::u32string DocName() const override;
156     std::u32string CodeName() const override { return groupName; }
157     std::string GetSpecifierStr() const override;
158     std::string Syntax() const override;
159     int32_t GetIndex() const { return index; }
160     void SetIndex(int32_t index_) { index = index_; }
161     virtual ConversionType GetConversionType() const { return ConversionType::implicit_; }
162     virtual uint8_t ConversionDistance() const { return 0; }
163     TypeSymbol* ConversionSourceType() const { return conversionSourceType; }
164     void SetConversionSourceType(TypeSymbol* conversionSourceType_);
165     TypeSymbol* ConversionTargetType() const { return conversionTargetType; }
166     void SetConversionTargetType(TypeSymbol* conversionTargetType_);
167     virtual bool IsBasicTypeOperation() const { return false; }
168     virtual bool IsGeneratedFunction() const { return false; }
169     virtual bool IsLvalueReferenceCopyAssignment() const { return false; }
170     virtual bool IsArrayElementAccess() const { return false; }
171     virtual bool IsCompileTimePrimitiveFunction() const { return false; }
172     virtual bool IsClassToInterfaceTypeConversion() const { return false; }
173     virtual bool IsMemberFunctionToClassDelegateConversion() const { return false; }
174     virtual void GenerateCall(Emitter& emitterstd::std::vector<GenObject*>&genObjectsOperationFlagsflagsconstSpan&spanconstboost::uuids::uuid& moduleId);
175     void GenerateVirtualCall(Emitter& emitterstd::std::vector<GenObject*>&genObjectsOperationFlagsflagsconstSpan&spanconstboost::uuids::uuid& moduleId);
176     virtual std::unique_ptr<Value> ConstructValue(const std::std::vector<std::std::unique_ptr<Value>>&argumentValuesconstSpan&spanconstboost::uuids::uuid&moduleIdValue*receiver) const;
177     virtual std::unique_ptr<Value> ConvertValue(const std::std::unique_ptr<Value>&value) const;
178     virtual ParameterSymbol* GetThisParam() const { return nullptr; }
179     virtual bool IsConstructorDestructorOrNonstaticMemberFunction() const { return false; }
180     virtual bool IsClassDelegateCopyConstructor() const { return false; }
181     void Dump(CodeFormatter& formatter) override;
182     bool IsDefaultConstructor() const;
183     bool IsCopyConstructor() const;
184     bool IsMoveConstructor() const;
185     bool IsCopyAssignment() const;
186     bool IsMoveAssignment() const;
187     virtual int StartParamIndex() const { return 0; }
188     const boost::uuids::uuid& FunctionId() const { Assert(!functionId.is_nil()"function id not initialized");  return functionId; }
189     void SetFunctionId(const boost::uuids::uuid& functionId_) { functionId = functionId_; }
190     const std::u32string& GroupName() const { return groupName; }
191     void SetGroupName(const std::u32string& groupName_);
192     const std::std::vector<TemplateParameterSymbol*>&TemplateParameters() const{returntemplateParameters;}
193     void SetSpecifiers(Specifiers specifiers);
194     bool IsInline() const { return GetFlag(FunctionSymbolFlags::inline_); }
195     void SetInline() { SetFlag(FunctionSymbolFlags::inline_); }
196     bool IsConstExpr() const { return GetFlag(FunctionSymbolFlags::constExpr); }
197     void SetConstExpr() { SetFlag(FunctionSymbolFlags::constExpr); }
198     bool IsCDecl() const { return GetFlag(FunctionSymbolFlags::cdecl_); }
199     void SetCDecl() { SetFlag(FunctionSymbolFlags::cdecl_); }
200     bool IsDefault() const { return GetFlag(FunctionSymbolFlags::default_); }
201     void SetDefault() { SetFlag(FunctionSymbolFlags::default_); }
202     bool IsSuppressed() const { return GetFlag(FunctionSymbolFlags::suppress); }
203     void SetSuppressed() { SetFlag(FunctionSymbolFlags::suppress); }
204     bool IsExplicit() const { return GetFlag(FunctionSymbolFlags::explicit_); }
205     void SetExplicit() { SetFlag(FunctionSymbolFlags::explicit_); }
206     bool IsVirtual() const { return GetFlag(FunctionSymbolFlags::virtual_); }
207     void SetVirtual() { SetFlag(FunctionSymbolFlags::virtual_); }
208     bool IsOverride() const { return GetFlag(FunctionSymbolFlags::override_); }
209     void SetOverride() { SetFlag(FunctionSymbolFlags::override_); }
210     bool IsAbstract() const { return GetFlag(FunctionSymbolFlags::abstract_); }
211     void SetAbstract() { SetFlag(FunctionSymbolFlags::abstract_); }
212     bool IsVirtualAbstractOrOverride() const { return GetFlag(FunctionSymbolFlags::virtual_ | FunctionSymbolFlags::abstract_ | FunctionSymbolFlags::override_); }
213     bool IsNew() const { return GetFlag(FunctionSymbolFlags::new_); }
214     void SetNew() { SetFlag(FunctionSymbolFlags::new_); }
215     bool IsConst() const { return GetFlag(FunctionSymbolFlags::const_); }
216     void SetConst() { SetFlag(FunctionSymbolFlags::const_); }
217     bool IsConversion() const { return GetFlag(FunctionSymbolFlags::conversion); }
218     void SetConversion() { SetFlag(FunctionSymbolFlags::conversion); }
219     bool HasLinkOnceOdrLinkage() const { return GetFlag(FunctionSymbolFlags::linkOnceOdrLinkage);  }
220     void SetLinkOnceOdrLinkage() { SetFlag(FunctionSymbolFlags::linkOnceOdrLinkage); }
221     bool IsTemplateSpecialization() const { return GetFlag(FunctionSymbolFlags::templateSpecialization); }
222     void SetTemplateSpecialization() { SetFlag(FunctionSymbolFlags::templateSpecialization); }
223     bool HasTry() const { return GetFlag(FunctionSymbolFlags::hasTry); }
224     void SetHasTry() { SetFlag(FunctionSymbolFlags::hasTry); }
225     bool IsCopy() const { return GetFlag(FunctionSymbolFlags::copy); }
226     void SetCopy() { SetFlag(FunctionSymbolFlags::copy); }
227     bool IsVarArg() const { return GetFlag(FunctionSymbolFlags::varArg); }
228     void SetVarArg() { SetFlag(FunctionSymbolFlags::varArg); }
229     void SetHasArtificialBody() { SetFlag(FunctionSymbolFlags::hasArtificialBody); }
230     bool HasArtificialBody() const { return GetFlag(FunctionSymbolFlags::hasArtificialBody); }
231     bool HasCleanup() const { return GetFlag(FunctionSymbolFlags::hasCleanup); }
232     void SetHasCleanup() { SetFlag(FunctionSymbolFlags::hasCleanup); }
233     bool IsSystemDefault() const { return GetFlag(FunctionSymbolFlags::systemDefault); }
234     void SetSystemDefault() { SetFlag(FunctionSymbolFlags::systemDefault); }
235     bool IsImmutable() const override { return GetFlag(FunctionSymbolFlags::immutable); }
236     void SetImmutable() { SetFlag(FunctionSymbolFlags::immutable); }
237     void ResetImmutable() { ResetFlag(FunctionSymbolFlags::immutable); }
238     virtual bool DontThrow() const { return (IsNothrow() || IsBasicTypeOperation()) && !HasCleanup(); }
239     FunctionSymbolFlags GetFunctionSymbolFlags() const { return flags; }
240     bool GetFlag(FunctionSymbolFlags flag) const { return (flags & flag) != FunctionSymbolFlags::none; }
241     void SetFlag(FunctionSymbolFlags flag) { flags = flags | flag; }
242     void ResetFlag(FunctionSymbolFlags flag) { flags = flags & ~flag; }
243     void ComputeMangledName() override;
244     int Arity() const { return parameters.size(); }
245     const std::std::vector<ParameterSymbol*>&Parameters() const{returnparameters;}
246     void AddLocalVariable(LocalVariableSymbol* localVariable);
247     const std::std::vector<LocalVariableSymbol*>&LocalVariables() const{returnlocalVariables;}
248     void SetReturnType(TypeSymbol* returnType_) { returnType = returnType_; }
249     TypeSymbol* ReturnType() const { return returnType; }
250     ParameterSymbol* ReturnParam() { return returnParam.get(); }
251     void SetReturnParam(ParameterSymbol* returnParam_);
252     bool ReturnsClassInterfaceOrClassDelegateByValue() const;
253     bool IsFunctionTemplate() const { return !templateParameters.empty(); }
254     void CloneUsingNodes(const std::std::vector<Node*>&usingNodes_);
255     LocalVariableSymbol* CreateTemporary(TypeSymbol* typeconst Span& spanconst boost::uuids::uuid& moduleId);
256     virtual std::vector<LocalVariableSymbol*> CreateTemporariesTo(FunctionSymbol* currentFunction);
257     void* IrType(Emitter& emitter);
258     int32_t VmtIndex() const { return vmtIndex; }
259     void SetVmtIndex(int32_t vmtIndex_) { vmtIndex = vmtIndex_; }
260     int32_t ImtIndex() const { return imtIndex; }
261     void SetImtIndex(int32_t imtIndex_) { imtIndex = imtIndex_; }
262     FunctionGroupSymbol* FunctionGroup() { return functionGroup; }
263     void SetFunctionGroup(FunctionGroupSymbol* functionGroup_) { functionGroup = functionGroup_; }
264     IntrinsicFunction* GetIntrinsic() { return intrinsic.get(); }
265     void SetIntrinsic(IntrinsicFunction* intrinsic_) { intrinsic.reset(intrinsic_); }
266     bool IsProgramMain() const { return isProgramMain; }
267     void SetProgramMain() { isProgramMain = true; }
268     std::unique_ptr<sngxml::dom::Element> CreateDomElement(TypeMap& typeMap) override;
269     std::u32string Info() const override { return groupName; }
270     const char* ClassName() const override { return "FunctionSymbol"; }
271     virtual int ClassArity() const { return 0; }
272     bool HasSource() const { return GetFlag(FunctionSymbolFlags::hasSource) && !IsDefault(); }
273     void SetHasSource() { SetFlag(FunctionSymbolFlags::hasSource); }
274     std::u32string Id() const override;
275     FunctionSymbol* FunctionTemplate() { return functionTemplate; }
276     void SetFunctionTemplate(FunctionSymbol* functionTemplate_) { functionTemplate = functionTemplate_; }
277     void SetTemplateArgumentTypes(const std::std::vector<TypeSymbol*>&templateArgumentTypes_);
278     const std::std::vector<TypeSymbol*>&TemplateArgumentTypes() const{returntemplateArgumentTypes;}
279     void Check() override;
280     FunctionSymbol* Master() const { return master; }
281     void SetMaster(FunctionSymbol* master_) { master = master_; }
282     void SetPrevUnwindInfoVar(LocalVariableSymbol* prevUnwindInfoVar_);
283     LocalVariableSymbol* PrevUnwindInfoVar() const { return prevUnwindInfoVar.get(); }
284     void SetUnwindInfoVar(LocalVariableSymbol* unwindInfoVar_);
285     LocalVariableSymbol* UnwindInfoVar() const { return unwindInfoVar.get(); }
286     int NextTemporaryIndex();
287     void CopyFrom(const Symbol* that) override;
288     virtual FunctionSymbol* Copy() const;
289     std::unique_ptr<Symbol> RemoveFromParent() override;
290     std::string GetSymbolCategoryStr() const override { return "FN"; }
291     std::string GetSymbolCategoryDescription() const override { return "function"; }
292     std::string GetSymbolHelp() const override;
293 private:
294     FunctionSymbol* functionTemplate;
295     FunctionSymbol* master;
296     boost::uuids::uuid functionId;
297     std::u32string groupName;
298     std::vector<TemplateParameterSymbol*> templateParameters;
299     std::vector<TypeSymbol*> templateArgumentTypes;
300     std::vector<ParameterSymbol*> parameters;
301     std::unique_ptr<ParameterSymbol> returnParam;
302     std::vector<LocalVariableSymbol*> localVariables;
303     std::unique_ptr<LocalVariableSymbol> unwindInfoVar;
304     std::unique_ptr<LocalVariableSymbol> prevUnwindInfoVar;
305     TypeSymbol* returnType;
306     FunctionSymbolFlags flags;
307     int32_t index;
308     int32_t vmtIndex;
309     int32_t imtIndex;
310     NodeList<Node> usingNodes;
311     std::unique_ptr<FunctionNode> functionNode;
312     std::unique_ptr<ConstraintNode> constraint;
313     int nextTemporaryIndex;
314     FunctionGroupSymbol* functionGroup;
315     std::unique_ptr<IntrinsicFunction> intrinsic;
316     bool isProgramMain;
317     TypeSymbol* conversionSourceType;
318     TypeSymbol* conversionTargetType;
319 };
320 
321 class StaticConstructorSymbol public FunctionSymbol
322 {
323 public:
324     StaticConstructorSymbol(const Span& span_const boost::uuids::uuid& sourceModuleId_const std::u32string& name_);
325     std::string TypeString() const override { return "static_constructor"; }
326     void Accept(SymbolCollector* collector) override {}
327     void SetSpecifiers(Specifiers specifiers);
328     std::u32string FullNameWithSpecifiers() const override;
329     std::u32string CodeName() const override;
330     std::u32string Info() const override { return std::u32string(); }
331     const char* ClassName() const override { return "StaticConstructorSymbol"; }
332     int StartParamIndex() const override { return 0; }
333     FunctionSymbol* Copy() const override;
334 };
335    
336 class ConstructorSymbol public FunctionSymbol
337 {
338 public:
339     ConstructorSymbol(const Span& span_const boost::uuids::uuid& sourceModuleId_const std::u32string& name_);
340     std::string TypeString() const override;
341     std::u32string DocName() const override;
342     std::u32string CodeName() const override;
343     ParameterSymbol* GetThisParam() const override { return Parameters()[0]; }
344     bool IsConstructorDestructorOrNonstaticMemberFunction() const override { return true; }
345     void SetSpecifiers(Specifiers specifiers);
346     uint8_t ConversionDistance() const override;
347     std::u32string Info() const override { return std::u32string(); }
348     const char* ClassName() const override { return "ConstructorSymbol"; }
349     int StartParamIndex() const override { return 1; }
350     FunctionSymbol* Copy() const override;
351 };
352 
353 class DestructorSymbol public FunctionSymbol
354 {
355 public:
356     DestructorSymbol(const Span& span_const boost::uuids::uuid& sourceModuleId_const std::u32string& name_);
357     void Write(SymbolWriter& writer) override;
358     void Read(SymbolReader& reader) override;
359     bool IsExportSymbol() const override;
360     void Accept(SymbolCollector* collector) override {}
361     std::string TypeString() const override { return "destructor"; }
362     ParameterSymbol* GetThisParam() const override { return Parameters()[0]; }
363     std::u32string CodeName() const override;
364     bool IsConstructorDestructorOrNonstaticMemberFunction() const override { return true; }
365     bool IsGeneratedFunction() const override { return generated; }
366     bool DontThrow() const override;
367     void SetSpecifiers(Specifiers specifiers);
368     void SetGenerated() { generated = true; }
369     std::u32string Info() const override { return std::u32string(); }
370     const char* ClassName() const override { return "DestructorSymbol"; }
371     int StartParamIndex() const override { return 1; }
372     FunctionSymbol* Copy() const override;
373 private:
374     bool generated;
375 };
376 
377 class MemberFunctionSymbol public FunctionSymbol
378 {
379 public:
380     MemberFunctionSymbol(const Span& span_const boost::uuids::uuid& sourceModuleId_const std::u32string& name_);
381     std::string TypeString() const override;
382     std::u32string DocName() const override;
383     ParameterSymbol* GetThisParam() const override { if (IsStatic()) return nullptr; else return Parameters()[0]; }
384     bool IsConstructorDestructorOrNonstaticMemberFunction() const override { return !IsStatic(); }
385     void SetSpecifiers(Specifiers specifiers);
386     const char* ClassName() const override { return "MemberFunctionSymbol"; }
387     int StartParamIndex() const override;
388     FunctionSymbol* Copy() const override;
389 };
390 
391 class ConversionFunctionSymbol public FunctionSymbol
392 {
393 public:
394     ConversionFunctionSymbol(const Span& span_const boost::uuids::uuid& sourceModuleId_const std::u32string& name_);
395     std::string TypeString() const override { return "conversion_function";  }
396     std::u32string DocName() const override;
397     ParameterSymbol* GetThisParam() const override { return Parameters()[0]; }
398     bool IsConstructorDestructorOrNonstaticMemberFunction() const override { return true; }
399     ConversionType GetConversionType() const override { return ConversionType::implicit_; }
400     uint8_t ConversionDistance() const override { return 255; }
401     void SetSpecifiers(Specifiers specifiers);
402     std::unique_ptr<sngxml::dom::Element> CreateDomElement(TypeMap& typeMap) override;
403     std::u32string Info() const override { return std::u32string(); }
404     const char* ClassName() const override { return "ConversionFunctionSymbol"; }
405     int StartParamIndex() const override { return 0; }
406     FunctionSymbol* Copy() const override;
407 };
408 
409 class FunctionGroupTypeSymbol public TypeSymbol
410 {
411 public:
412     FunctionGroupTypeSymbol(FunctionGroupSymbol* functionGroup_void* boundFunctionGroup_);
413     bool IsExportSymbol() const override { return false; }
414     void* IrType(Emitter& emitter) override { Assert(false"tried to get ir type of function group type"); return nullptr; }
415     void* CreateDefaultIrValue(Emitter& emitter) override { Assert(false"tried to get default ir value of function group type"); return nullptr; }
416     const FunctionGroupSymbol* FunctionGroup() const { return functionGroup; }
417     FunctionGroupSymbol* FunctionGroup() { return functionGroup; }
418     void* BoundFunctionGroup() const { return boundFunctionGroup; }
419     const char* ClassName() const override { return "FunctionGroupTypeSymbol"; }
420 private:
421     FunctionGroupSymbol* functionGroup;
422     void* boundFunctionGroup;
423 };
424 
425 class MemberExpressionTypeSymbol public TypeSymbol
426 {
427 public:
428     MemberExpressionTypeSymbol(const Span& span_const boost::uuids::uuid& sourceModuleId_const std::u32string& name_void* boundMemberExpression_);
429     bool IsExportSymbol() const override { return false; }
430     void* IrType(Emitter& emitter) override { Assert(false"tried to get ir type of member expression type");  return nullptr; }
431     void* CreateDefaultIrValue(Emitter& emitter) override { Assert(false"tried to get default ir value of member expression type"); return nullptr; }
432     std::string TypeString() const override { return "member_expression_type"; }
433     void* BoundMemberExpression() const { return boundMemberExpression; }
434     const char* ClassName() const override { return "MemberExpressionTypeSymbol"; }
435 private:
436     void* boundMemberExpression;
437 };
438 
439 void InitFunctionSymbol();
440 void DoneFunctionSymbol();
441 
442 } } // namespace cmajor::symbols
443 
444 #endif // CMAJOR_SYMBOLS_FUNCTION_SYMBOL_INCLUDED