• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /**
2  * Copyright (c) 2021-2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  * http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #ifndef ASSEMBLER_META_H
17 #define ASSEMBLER_META_H
18 
19 #include <memory>
20 #include <stack>
21 #include <tuple>
22 #include <unordered_map>
23 #include <unordered_set>
24 #include <variant>
25 #include <vector>
26 
27 #include "annotation.h"
28 #include "modifiers.h"
29 
30 #include "assembly-type.h"
31 
32 namespace panda::pandasm {
33 
34 class Metadata {
35 public:
36     class Error {
37     public:
38         enum class Type {
39             INVALID_VALUE,
40             MISSING_ATTRIBUTE,
41             MISSING_VALUE,
42             MULTIPLE_ATTRIBUTE,
43             UNEXPECTED_ATTRIBUTE,
44             UNEXPECTED_VALUE,
45             UNKNOWN_ATTRIBUTE
46         };
47 
Error(std::string msg,Type type)48         Error(std::string msg, Type type) : msg_(std::move(msg)), type_(type) {}
49         ~Error() = default;
50         DEFAULT_MOVE_SEMANTIC(Error);
51         DEFAULT_COPY_SEMANTIC(Error);
52 
GetMessage()53         std::string GetMessage() const
54         {
55             return msg_;
56         }
57 
GetType()58         Type GetType() const
59         {
60             return type_;
61         }
62 
63     private:
64         std::string msg_;
65         Type type_;
66     };
67 
68     Metadata() = default;
69 
70     virtual ~Metadata() = default;
71 
SetAttribute(std::string_view attribute)72     std::optional<Error> SetAttribute(std::string_view attribute)
73     {
74         auto err = Validate(attribute);
75         if (err) {
76             return err;
77         }
78 
79         SetFlags(attribute);
80 
81         return Store(attribute);
82     }
83 
RemoveAttribute(const std::string & attribute)84     void RemoveAttribute(const std::string &attribute)
85     {
86         RemoveFlags(attribute);
87 
88         set_attributes_.erase(attribute);
89     }
90 
GetAttribute(const std::string & attribute)91     bool GetAttribute(const std::string &attribute) const
92     {
93         return set_attributes_.find(attribute) != set_attributes_.cend();
94     }
95 
SetAttributeValue(std::string_view attribute,std::string_view value)96     std::optional<Error> SetAttributeValue(std::string_view attribute, std::string_view value)
97     {
98         auto err = Validate(attribute, value);
99         if (err) {
100             return err;
101         }
102 
103         SetFlags(attribute, value);
104 
105         return StoreValue(attribute, value);
106     }
107 
GetAttributeValues(const std::string & attribute)108     std::vector<std::string> GetAttributeValues(const std::string &attribute) const
109     {
110         auto it = attributes_.find(attribute);
111         if (it == attributes_.cend()) {
112             return {};
113         }
114 
115         return it->second;
116     }
117 
GetAttributeValue(const std::string & attribute)118     std::optional<std::string> GetAttributeValue(const std::string &attribute) const
119     {
120         auto values = GetAttributeValues(attribute);
121         if (!values.empty()) {
122             return values.front();
123         }
124 
125         return {};
126     }
127 
GetBoolAttributes()128     const std::unordered_set<std::string> &GetBoolAttributes() const
129     {
130         return set_attributes_;
131     }
132 
GetAttributes()133     const std::unordered_map<std::string, std::vector<std::string>> &GetAttributes() const
134     {
135         return attributes_;
136     }
137 
ValidateData()138     virtual std::optional<Error> ValidateData()
139     {
140         return {};
141     }
142 
143     DEFAULT_COPY_SEMANTIC(Metadata);
144 
145     DEFAULT_MOVE_SEMANTIC(Metadata);
146 
147 protected:
148     virtual std::optional<Error> Validate(std::string_view attribute) const = 0;
149 
150     virtual std::optional<Error> Validate(std::string_view attribute, std::string_view value) const = 0;
151 
StoreValue(std::string_view attribute,std::string_view value)152     virtual std::optional<Error> StoreValue(std::string_view attribute, std::string_view value)
153     {
154         std::string key(attribute);
155         auto it = attributes_.find(key);
156         if (it == attributes_.cend()) {
157             std::tie(it, std::ignore) = attributes_.try_emplace(key);
158         }
159 
160         it->second.emplace_back(value);
161 
162         return {};
163     }
164 
Store(std::string_view attribute)165     virtual std::optional<Error> Store(std::string_view attribute)
166     {
167         set_attributes_.emplace(attribute);
168 
169         return {};
170     }
171 
172     virtual void SetFlags(std::string_view attribute) = 0;
173 
174     virtual void SetFlags(std::string_view attribute, std::string_view value) = 0;
175 
176     virtual void RemoveFlags(std::string_view attribute) = 0;
177 
178     virtual void RemoveFlags(std::string_view attribute, std::string_view value) = 0;
179 
HasAttribute(std::string_view attribute)180     bool HasAttribute(std::string_view attribute) const
181     {
182         std::string key(attribute);
183         return GetAttribute(key) || GetAttributeValue(key);
184     }
185 
186     std::optional<Error> ValidateSize(std::string_view value) const;
187 
188 private:
189     std::unordered_set<std::string> set_attributes_;
190     std::unordered_map<std::string, std::vector<std::string>> attributes_;
191 };
192 
193 class AnnotationMetadata : public Metadata {
194 public:
GetAnnotations()195     const std::vector<AnnotationData> &GetAnnotations() const
196     {
197         return annotations_;
198     }
199 
SetAnnotations(std::vector<AnnotationData> && annotations)200     void SetAnnotations(std::vector<AnnotationData> &&annotations)
201     {
202         annotations_ = std::forward<std::vector<AnnotationData>>(annotations);
203     }
204 
AddAnnotations(const std::vector<AnnotationData> & annotations)205     void AddAnnotations(const std::vector<AnnotationData> &annotations)
206     {
207         annotations_.insert(annotations_.end(), annotations.begin(), annotations.end());
208     }
209 
SetOrAddAnnotationElementByIndex(size_t anno_idx,size_t ele_idx,AnnotationElement && element)210     void SetOrAddAnnotationElementByIndex(size_t anno_idx, size_t ele_idx, AnnotationElement &&element)
211     {
212         ASSERT(anno_idx < annotations_.size());
213         annotations_[anno_idx].SetOrAddElementByIndex(ele_idx, std::forward<AnnotationElement>(element));
214     }
215 
216     std::optional<Error> ValidateData() override;
217 
218 protected:
219     std::optional<Error> Store(std::string_view attribute) override;
220 
221     std::optional<Error> StoreValue(std::string_view attribute, std::string_view value) override;
222 
IsAnnotationRecordAttribute(std::string_view attribute)223     virtual bool IsAnnotationRecordAttribute([[maybe_unused]] std::string_view attribute) const
224     {
225         return false;
226     }
227 
IsAnnotationIdAttribute(std::string_view attribute)228     virtual bool IsAnnotationIdAttribute([[maybe_unused]] std::string_view attribute) const
229     {
230         return false;
231     }
232 
IsAnnotationElementTypeAttribute(std::string_view attribute)233     virtual bool IsAnnotationElementTypeAttribute([[maybe_unused]] std::string_view attribute) const
234     {
235         return false;
236     }
237 
IsAnnotationElementArrayComponentTypeAttribute(std::string_view attribute)238     virtual bool IsAnnotationElementArrayComponentTypeAttribute([[maybe_unused]] std::string_view attribute) const
239     {
240         return false;
241     }
242 
IsAnnotationElementNameAttribute(std::string_view attribute)243     virtual bool IsAnnotationElementNameAttribute([[maybe_unused]] std::string_view attribute) const
244     {
245         return false;
246     }
247 
IsAnnotationElementValueAttribute(std::string_view attribute)248     virtual bool IsAnnotationElementValueAttribute([[maybe_unused]] std::string_view attribute) const
249     {
250         return false;
251     }
252 
253 private:
254     class AnnotationElementBuilder {
255     public:
Initialize(std::string_view name)256         void Initialize(std::string_view name)
257         {
258             name_ = name;
259             is_initialized_ = true;
260         }
261 
Reset()262         void Reset()
263         {
264             name_.clear();
265             values_.clear();
266             type_ = {};
267             component_type_ = {};
268             is_initialized_ = false;
269         }
270 
SetType(Value::Type type)271         void SetType(Value::Type type)
272         {
273             type_ = type;
274         }
275 
SetComponentType(Value::Type type)276         void SetComponentType(Value::Type type)
277         {
278             ASSERT(type != Value::Type::ARRAY);
279             component_type_ = type;
280         }
281 
282         std::optional<Error> AddValue(
283             std::string_view value,
284             const std::unordered_map<std::string, std::unique_ptr<AnnotationData>> &annotation_id_map);
285 
CreateAnnotationElement()286         AnnotationElement CreateAnnotationElement()
287         {
288             if (IsArray()) {
289                 return AnnotationElement(name_,
290                                          std::make_unique<ArrayValue>(component_type_.value(), std::move(values_)));
291             }
292 
293             return AnnotationElement(name_, std::make_unique<ScalarValue>(values_.front()));
294         }
295 
IsArray()296         bool IsArray() const
297         {
298             return type_.value() == Value::Type::ARRAY;
299         }
300 
IsTypeSet()301         bool IsTypeSet() const
302         {
303             return type_.has_value();
304         }
305 
IsComponentTypeSet()306         bool IsComponentTypeSet() const
307         {
308             return component_type_.has_value();
309         }
310 
IsInitialized()311         bool IsInitialized() const
312         {
313             return is_initialized_;
314         }
315 
IsCompleted()316         bool IsCompleted() const
317         {
318             if (!IsTypeSet()) {
319                 return false;
320             }
321 
322             if (IsArray() && !IsComponentTypeSet()) {
323                 return false;
324             }
325 
326             if (!IsArray() && values_.empty()) {
327                 return false;
328             }
329 
330             return true;
331         }
332 
333     private:
334         bool is_initialized_ {false};
335         std::string name_;
336         std::optional<Value::Type> type_;
337         std::optional<Value::Type> component_type_;
338         std::vector<ScalarValue> values_;
339     };
340 
341     class AnnotationBuilder {
342     public:
Initialize(std::string_view name)343         void Initialize(std::string_view name)
344         {
345             name_ = name;
346             is_initialized_ = true;
347         }
348 
Reset()349         void Reset()
350         {
351             name_.clear();
352             elements_.clear();
353             id_ = {};
354             is_initialized_ = false;
355         }
356 
SetId(std::string_view id)357         void SetId(std::string_view id)
358         {
359             id_ = id;
360         }
361 
GetId()362         std::string GetId() const
363         {
364             ASSERT(HasId());
365             return id_.value();
366         }
367 
AddElement(AnnotationElement && element)368         void AddElement(AnnotationElement &&element)
369         {
370             elements_.push_back(std::forward<AnnotationElement>(element));
371         }
372 
CreateAnnotationData()373         std::unique_ptr<AnnotationData> CreateAnnotationData()
374         {
375             return std::make_unique<AnnotationData>(name_, std::move(elements_));
376         };
377 
AddAnnnotationDataToVector(std::vector<AnnotationData> * annotations)378         void AddAnnnotationDataToVector(std::vector<AnnotationData> *annotations)
379         {
380             annotations->emplace_back(name_, std::move(elements_));
381         }
382 
HasId()383         bool HasId() const
384         {
385             return id_.has_value();
386         }
387 
IsInitialized()388         bool IsInitialized() const
389         {
390             return is_initialized_;
391         }
392 
393     private:
394         std::string name_;
395         std::optional<std::string> id_;
396         std::vector<AnnotationElement> elements_;
397         bool is_initialized_ {false};
398     };
399 
400     std::optional<Metadata::Error> MeetExpRecordAttribute(std::string_view attribute, std::string_view value);
401     std::optional<Metadata::Error> MeetExpIdAttribute(std::string_view attribute, std::string_view value);
402     std::optional<Metadata::Error> MeetExpElementNameAttribute(std::string_view attribute, std::string_view value);
403     std::optional<Metadata::Error> MeetExpElementTypeAttribute(std::string_view attribute, std::string_view value);
404     std::optional<Metadata::Error> MeetExpElementArrayComponentTypeAttribute(std::string_view attribute,
405                                                                              std::string_view value);
406     std::optional<Metadata::Error> MeetExpElementValueAttribute(std::string_view attribute, std::string_view value);
407 
InitializeAnnotationBuilder(std::string_view name)408     void InitializeAnnotationBuilder(std::string_view name)
409     {
410         if (IsParseAnnotation()) {
411             ResetAnnotationBuilder();
412         }
413 
414         annotation_builder_.Initialize(name);
415     }
416 
ResetAnnotationBuilder()417     void ResetAnnotationBuilder()
418     {
419         ASSERT(IsParseAnnotation());
420 
421         if (IsParseAnnotationElement() && annotation_element_builder_.IsCompleted()) {
422             ResetAnnotationElementBuilder();
423         }
424 
425         if (annotation_builder_.HasId()) {
426             id_map_.insert({annotation_builder_.GetId(), annotation_builder_.CreateAnnotationData()});
427         } else {
428             annotation_builder_.AddAnnnotationDataToVector(&annotations_);
429         }
430 
431         annotation_builder_.Reset();
432     }
433 
IsParseAnnotation()434     bool IsParseAnnotation() const
435     {
436         return annotation_builder_.IsInitialized();
437     }
438 
InitializeAnnotationElementBuilder(std::string_view name)439     void InitializeAnnotationElementBuilder(std::string_view name)
440     {
441         if (IsParseAnnotationElement() && annotation_element_builder_.IsCompleted()) {
442             ResetAnnotationElementBuilder();
443         }
444 
445         annotation_element_builder_.Initialize(name);
446     }
447 
ResetAnnotationElementBuilder()448     void ResetAnnotationElementBuilder()
449     {
450         ASSERT(IsParseAnnotationElement());
451         ASSERT(annotation_element_builder_.IsCompleted());
452 
453         annotation_builder_.AddElement(annotation_element_builder_.CreateAnnotationElement());
454 
455         annotation_element_builder_.Reset();
456     }
457 
IsParseAnnotationElement()458     bool IsParseAnnotationElement() const
459     {
460         return annotation_element_builder_.IsInitialized();
461     }
462 
463     AnnotationBuilder annotation_builder_;
464     AnnotationElementBuilder annotation_element_builder_;
465     std::vector<AnnotationData> annotations_;
466     std::unordered_map<std::string, std::unique_ptr<AnnotationData>> id_map_;
467 };
468 
469 class ItemMetadata : public AnnotationMetadata {
470 public:
GetAccessFlags()471     uint32_t GetAccessFlags() const
472     {
473         return access_flags_;
474     }
475 
SetAccessFlags(uint32_t access_flags)476     void SetAccessFlags(uint32_t access_flags)
477     {
478         access_flags_ = access_flags;
479     }
480 
481     bool IsForeign() const;
482 
483 private:
484     uint32_t access_flags_ {0};
485 };
486 
487 class RecordMetadata : public ItemMetadata {
488 public:
489     virtual std::string GetBase() const;
490 
491     virtual std::vector<std::string> GetInterfaces() const;
492 
493     virtual bool IsAnnotation() const;
494 
495     virtual bool IsRuntimeAnnotation() const;
496 
497     virtual bool IsTypeAnnotation() const;
498 
499     virtual bool IsRuntimeTypeAnnotation() const;
500 
501 protected:
502     std::optional<Error> Validate(std::string_view attribute) const override;
503 
504     std::optional<Error> Validate(std::string_view attribute, std::string_view value) const override;
505 
506     void SetFlags(std::string_view attribute) override;
507 
508     void SetFlags(std::string_view attribute, std::string_view value) override;
509 
510     void RemoveFlags(std::string_view attribute) override;
511 
512     void RemoveFlags(std::string_view attribute, std::string_view value) override;
513 };
514 
515 class FieldMetadata : public ItemMetadata {
516 public:
SetFieldType(const Type & type)517     void SetFieldType(const Type &type)
518     {
519         field_type_ = type;
520     }
521 
GetFieldType()522     Type GetFieldType() const
523     {
524         return field_type_;
525     }
526 
SetValue(const ScalarValue & value)527     void SetValue(const ScalarValue &value)
528     {
529         value_ = value;
530     }
531 
GetValue()532     std::optional<ScalarValue> GetValue() const
533     {
534         return value_;
535     }
536 
537 protected:
538     std::optional<Error> StoreValue(std::string_view attribute, std::string_view value) override;
539 
540     std::optional<Error> Validate(std::string_view attribute) const override;
541 
542     std::optional<Error> Validate(std::string_view attribute, std::string_view value) const override;
543 
544     void SetFlags(std::string_view attribute) override;
545 
546     void SetFlags(std::string_view attribute, std::string_view value) override;
547 
548     void RemoveFlags(std::string_view attribute) override;
549 
550     void RemoveFlags(std::string_view attribute, std::string_view value) override;
551 
IsValueAttribute(std::string_view attribute)552     virtual bool IsValueAttribute(std::string_view attribute)
553     {
554         return attribute == "value";
555     }
556 
557 private:
558     Type field_type_;
559     std::optional<ScalarValue> value_;
560 };
561 
562 class FunctionMetadata : public ItemMetadata {
563 public:
564     virtual bool IsCtor() const;
565 
566     virtual bool IsCctor() const;
567 
568 protected:
569     std::optional<Error> Validate(std::string_view attribute) const override;
570 
571     std::optional<Error> Validate(std::string_view attribute, std::string_view value) const override;
572 
573     void SetFlags(std::string_view attribute) override;
574 
575     void SetFlags(std::string_view attribute, std::string_view value) override;
576 
577     void RemoveFlags(std::string_view attribute) override;
578 
579     void RemoveFlags(std::string_view attribute, std::string_view value) override;
580 };
581 
582 class ParamMetadata : public AnnotationMetadata {
583 protected:
584     std::optional<Error> Validate(std::string_view attribute) const override;
585 
586     std::optional<Error> Validate(std::string_view attribute, std::string_view value) const override;
587 
588     void SetFlags(std::string_view attribute) override;
589 
590     void SetFlags(std::string_view attribute, std::string_view value) override;
591 
592     void RemoveFlags(std::string_view attribute) override;
593 
594     void RemoveFlags(std::string_view attribute, std::string_view value) override;
595 };
596 
597 }  // namespace panda::pandasm
598 
599 #endif  // ASSEMBLER_META_H
600