- Timestamp:
- Nov 22, 2022, 10:18:04 AM (3 years ago)
- Branches:
- ADT, ast-experimental, master
- Children:
- 20cf96d
- Parents:
- 1553a55 (diff), d41735a (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the(diff)
links above to see all the changes relative to each parent. - Location:
- src
- Files:
-
- 24 edited
- 1 moved
Legend:
- Unmodified
- Added
- Removed
-
src/AST/Convert.cpp
r1553a55 r29702ad 236 236 } 237 237 238 // Inline ValueDecl vanish after EnumAndPointerDecay pass so no necessary to implement NewToOld239 const ast::DeclWithType * visit( const ast::Inline ValueDecl * node ) override final {238 // InlineMemberDecl vanish after EnumAndPointerDecay pass so no necessary to implement NewToOld 239 const ast::DeclWithType * visit( const ast::InlineMemberDecl * node ) override final { 240 240 assert( false ); 241 241 (void) node; … … 1764 1764 { old->linkage.val }, 1765 1765 GET_ACCEPT_1(base, Type), 1766 old->hide == EnumDecl::EnumHiding::Hide ? ast::EnumDecl::EnumHiding::Hide : ast::EnumDecl::EnumHiding::Visible, 1766 1767 old->enumValues 1767 1768 ); … … 1869 1870 } 1870 1871 1871 virtual void visit( const Inline ValueDecl * old ) override final {1872 virtual void visit( const InlineMemberDecl * old ) override final { 1872 1873 if ( inCache( old ) ) { 1873 1874 return; … … 1875 1876 auto&& type = GET_ACCEPT_1(type, Type); 1876 1877 auto&& attr = GET_ACCEPT_V(attributes, Attribute); 1877 1878 auto decl = new ast::Inline ValueDecl(1878 1879 auto decl = new ast::InlineMemberDecl( 1879 1880 old->location, 1880 1881 old->name, -
src/AST/Decl.hpp
r1553a55 r29702ad 315 315 // enum (type_optional) Name {...} 316 316 ptr<Type> base; // if isTyped == true && base.get() == nullptr, it is a "void" type enum 317 318 EnumDecl( const CodeLocation& loc, const std::string& name, bool isTyped = false, 317 enum class EnumHiding { Visible, Hide } hide; 318 319 EnumDecl( const CodeLocation& loc, const std::string& name, bool isTyped = false, 319 320 std::vector<ptr<Attribute>>&& attrs = {}, Linkage::Spec linkage = Linkage::Cforall, 320 Type const * base = nullptr, 321 Type const * base = nullptr, EnumHiding hide = EnumHiding::Hide, 321 322 std::unordered_map< std::string, long long > enumValues = std::unordered_map< std::string, long long >() ) 322 : AggregateDecl( loc, name, std::move(attrs), linkage ), isTyped(isTyped), base(base), enumValues(enumValues) {}323 : AggregateDecl( loc, name, std::move(attrs), linkage ), isTyped(isTyped), base(base), hide(hide), enumValues(enumValues) {} 323 324 324 325 /// gets the integer value for this enumerator, returning true iff value found … … 397 398 }; 398 399 400 /// Static Assertion `_Static_assert( ... , ... );` 399 401 class StaticAssertDecl : public Decl { 400 402 public: … … 411 413 }; 412 414 413 class InlineValueDecl final : public DeclWithType { 415 /// Inline Member Declaration `inline TypeName;` 416 class InlineMemberDecl final : public DeclWithType { 414 417 public: 415 418 ptr<Type> type; 416 419 417 Inline ValueDecl( const CodeLocation & loc, const std::string & name, const Type * type,420 InlineMemberDecl( const CodeLocation & loc, const std::string & name, const Type * type, 418 421 Storage::Classes storage = {}, Linkage::Spec linkage = Linkage::Cforall, 419 422 std::vector< ptr<Attribute> > && attrs = {}, Function::Specs fs = {} ) … … 425 428 const DeclWithType * accept( Visitor& v ) const override { return v.visit( this ); } 426 429 private: 427 InlineValueDecl * clone() const override { return new InlineValueDecl{ *this }; } 428 MUTATE_FRIEND 429 }; 430 InlineMemberDecl * clone() const override { return new InlineMemberDecl{ *this }; } 431 MUTATE_FRIEND 432 }; 433 430 434 } 431 435 -
src/AST/Fwd.hpp
r1553a55 r29702ad 37 37 class DirectiveDecl; 38 38 class StaticAssertDecl; 39 class Inline ValueDecl;39 class InlineMemberDecl; 40 40 41 41 class Stmt; -
src/AST/Pass.hpp
r1553a55 r29702ad 141 141 const ast::DirectiveDecl * visit( const ast::DirectiveDecl * ) override final; 142 142 const ast::StaticAssertDecl * visit( const ast::StaticAssertDecl * ) override final; 143 const ast::DeclWithType * visit( const ast::Inline ValueDecl* ) override final;143 const ast::DeclWithType * visit( const ast::InlineMemberDecl * ) override final; 144 144 const ast::CompoundStmt * visit( const ast::CompoundStmt * ) override final; 145 145 const ast::Stmt * visit( const ast::ExprStmt * ) override final; -
src/AST/Pass.impl.hpp
r1553a55 r29702ad 686 686 687 687 if ( __visit_children() ) { 688 // unlike structs, traits, and unions, enums inject their members into the global scope 689 maybe_accept( node, &EnumDecl::base ); 690 maybe_accept( node, &EnumDecl::params ); 691 maybe_accept( node, &EnumDecl::members ); 692 maybe_accept( node, &EnumDecl::attributes ); 688 if ( node->hide == ast::EnumDecl::EnumHiding::Hide ) { 689 guard_symtab guard { *this }; 690 maybe_accept( node, &EnumDecl::base ); 691 maybe_accept( node, &EnumDecl::params ); 692 maybe_accept( node, &EnumDecl::members ); 693 maybe_accept( node, &EnumDecl::attributes ); 694 } else { 695 maybe_accept( node, &EnumDecl::base ); 696 maybe_accept( node, &EnumDecl::params ); 697 maybe_accept( node, &EnumDecl::members ); 698 maybe_accept( node, &EnumDecl::attributes ); 699 } 693 700 } 694 701 … … 803 810 804 811 //-------------------------------------------------------------------------- 805 // DeclWithType806 template< typename core_t > 807 const ast::DeclWithType * ast::Pass< core_t >::visit( const ast::Inline ValueDecl * node ) {808 VISIT_START( node ); 809 810 if ( __visit_children() ) { 811 { 812 guard_symtab guard { *this }; 813 maybe_accept( node, &Inline ValueDecl::type );812 // InlineMemberDecl 813 template< typename core_t > 814 const ast::DeclWithType * ast::Pass< core_t >::visit( const ast::InlineMemberDecl * node ) { 815 VISIT_START( node ); 816 817 if ( __visit_children() ) { 818 { 819 guard_symtab guard { *this }; 820 maybe_accept( node, &InlineMemberDecl::type ); 814 821 } 815 822 } -
src/AST/Print.cpp
r1553a55 r29702ad 401 401 } 402 402 403 virtual const ast::DeclWithType * visit( const ast::Inline ValueDecl * node ) override final {403 virtual const ast::DeclWithType * visit( const ast::InlineMemberDecl * node ) override final { 404 404 os << "inline "; 405 405 if ( ! node->name.empty() ) os << node->name; -
src/AST/Visitor.hpp
r1553a55 r29702ad 33 33 virtual const ast::DirectiveDecl * visit( const ast::DirectiveDecl * ) = 0; 34 34 virtual const ast::StaticAssertDecl * visit( const ast::StaticAssertDecl * ) = 0; 35 virtual const ast::DeclWithType * visit( const ast::Inline ValueDecl* ) = 0;35 virtual const ast::DeclWithType * visit( const ast::InlineMemberDecl * ) = 0; 36 36 virtual const ast::CompoundStmt * visit( const ast::CompoundStmt * ) = 0; 37 37 virtual const ast::Stmt * visit( const ast::ExprStmt * ) = 0; -
src/CodeGen/CodeGenerator.cc
r1553a55 r29702ad 290 290 if ( obj->get_init() ) { 291 291 obj->get_init()->accept( *visitor ); 292 last_val = ((ConstantExpr *)(((SingleInit *)(obj->init))->value))->constant.get_ival(); 292 Expression* expr = ((SingleInit *)(obj->init))->value; 293 while ( auto temp = dynamic_cast<CastExpr *>(expr) ) { 294 expr = temp->arg; 295 } 296 last_val = ((ConstantExpr *)expr)->constant.get_ival(); 293 297 } else { 294 298 output << ++last_val; -
src/Common/CodeLocationTools.cpp
r1553a55 r29702ad 111 111 macro(DirectiveDecl, DirectiveDecl) \ 112 112 macro(StaticAssertDecl, StaticAssertDecl) \ 113 macro(Inline ValueDecl, DeclWithType) \113 macro(InlineMemberDecl, DeclWithType) \ 114 114 macro(CompoundStmt, CompoundStmt) \ 115 115 macro(ExprStmt, Stmt) \ -
src/Common/PassVisitor.h
r1553a55 r29702ad 81 81 virtual void visit( StaticAssertDecl * assertDecl ) override final; 82 82 virtual void visit( const StaticAssertDecl * assertDecl ) override final; 83 virtual void visit( Inline ValueDecl * valueDecl ) override final;84 virtual void visit( const Inline ValueDecl * valueDecl ) override final;83 virtual void visit( InlineMemberDecl * valueDecl ) override final; 84 virtual void visit( const InlineMemberDecl * valueDecl ) override final; 85 85 86 86 virtual void visit( CompoundStmt * compoundStmt ) override final; … … 275 275 virtual DirectiveDecl * mutate( DirectiveDecl * directiveDecl ) override final; 276 276 virtual StaticAssertDecl * mutate( StaticAssertDecl * assertDecl ) override final; 277 virtual DeclarationWithType * mutate( Inline ValueDecl * valueDecl ) override final;277 virtual DeclarationWithType * mutate( InlineMemberDecl * valueDecl ) override final; 278 278 279 279 virtual CompoundStmt * mutate( CompoundStmt * compoundStmt ) override final; -
src/Common/PassVisitor.impl.h
r1553a55 r29702ad 1047 1047 1048 1048 //-------------------------------------------------------------------------- 1049 // Inline ValueDecl1050 template< typename pass_type > 1051 void PassVisitor< pass_type >::visit( Inline ValueDecl * node ) {1049 // InlineMemberDecl 1050 template< typename pass_type > 1051 void PassVisitor< pass_type >::visit( InlineMemberDecl * node ) { 1052 1052 VISIT_START( node ); 1053 1053 … … 1058 1058 1059 1059 template< typename pass_type > 1060 void PassVisitor< pass_type >::visit( const Inline ValueDecl * node ) {1060 void PassVisitor< pass_type >::visit( const InlineMemberDecl * node ) { 1061 1061 VISIT_START( node ); 1062 1062 … … 1067 1067 1068 1068 template< typename pass_type > 1069 DeclarationWithType * PassVisitor< pass_type >::mutate( Inline ValueDecl * node ) {1069 DeclarationWithType * PassVisitor< pass_type >::mutate( InlineMemberDecl * node ) { 1070 1070 MUTATE_START( node ); 1071 1071 -
src/Common/utility.h
r1553a55 r29702ad 461 461 Iterables iterables; 462 462 463 // Getting the iterator and value types this way preserves const. 463 464 template<size_t I> using Iter = decltype(std::get<I>(iterables).begin()); 464 465 template<size_t I> using Data = decltype(*std::get<I>(iterables).begin()); 465 466 template<typename> struct base_iterator; 466 467 467 template<std::size_t... Is> 468 struct base_iterator<std::integer_sequence<std::size_t, Is...>> { 469 using value_type = std::tuple< Data<Is>... >; 470 std::tuple<Iter<Is>...> iterators; 471 472 base_iterator( Iter<Is>... is ) : iterators( is... ) {} 468 // This inner template puts the sequence of `0, 1, ... sizeof...(Args)-1` 469 // into a pack. These are the indexes into the tuples, so unpacking can 470 // go over each element of the tuple. 471 // The std::integer_sequence is just used to build that sequence. 472 // A library reference will probably explain it better than I can. 473 template<std::size_t... Indices> 474 struct base_iterator<std::integer_sequence<std::size_t, Indices...>> { 475 using value_type = std::tuple< Data<Indices>... >; 476 std::tuple<Iter<Indices>...> iterators; 477 478 base_iterator( Iter<Indices>... is ) : iterators( is... ) {} 473 479 base_iterator operator++() { 474 return base_iterator( ++std::get<I s>( iterators )... );480 return base_iterator( ++std::get<Indices>( iterators )... ); 475 481 } 476 482 bool operator!=( const base_iterator& other ) const { … … 478 484 } 479 485 value_type operator*() const { 480 return std::tie( *std::get<I s>( iterators )... );486 return std::tie( *std::get<Indices>( iterators )... ); 481 487 } 482 488 483 489 static base_iterator make_begin( Iterables & data ) { 484 return base_iterator( std::get<I s>( data ).begin()... );490 return base_iterator( std::get<Indices>( data ).begin()... ); 485 491 } 486 492 static base_iterator make_end( Iterables & data ) { 487 return base_iterator( std::get<I s>( data ).end()... );493 return base_iterator( std::get<Indices>( data ).end()... ); 488 494 } 489 495 }; -
src/GenPoly/ErasableScopedMap.h
r1553a55 r29702ad 23 23 24 24 namespace GenPoly { 25 /// A map where the items are placed into nested scopes; 26 /// inserted items are placed into the innermost scope, lookup looks from the innermost scope outward; 27 /// erasing a key means that find() will no longer report any instance of the key in a scope further 28 /// out, but the erasure itself is scoped. Key erasure works by inserting a sentinal value into the 29 /// value field, and thus only works for Value types where a meaningful sentinal can be chosen. 30 template<typename Key, typename Value> 31 class ErasableScopedMap { 32 typedef std::map< Key, Value > Scope; 33 typedef std::vector< Scope > ScopeList; 34 35 ScopeList scopes; ///< scoped list of maps 36 Value erased; ///< sentinal value for erased keys 37 public: 38 typedef typename Scope::key_type key_type; 39 typedef typename Scope::mapped_type mapped_type; 40 typedef typename Scope::value_type value_type; 41 typedef typename ScopeList::size_type size_type; 42 typedef typename ScopeList::difference_type difference_type; 43 typedef typename Scope::reference reference; 44 typedef typename Scope::const_reference const_reference; 45 typedef typename Scope::pointer pointer; 46 typedef typename Scope::const_pointer const_pointer; 47 48 class iterator : public std::iterator< std::bidirectional_iterator_tag, 49 value_type > { 50 friend class ErasableScopedMap; 51 friend class const_iterator; 52 typedef typename std::map< Key, Value >::iterator wrapped_iterator; 53 typedef typename std::vector< std::map< Key, Value > > scope_list; 54 typedef typename scope_list::size_type size_type; 55 56 /// Checks if this iterator points to a valid item 57 bool is_valid() const { 58 return it != map->scopes[i].end() && it->second != map->erased; 25 26 /// A map where the items are placed into nested scopes. 27 /// Inserted items are placed into the innermost scope, lookup looks from the 28 /// innermost scope outward. Erasing a key means that find() will no longer 29 /// report any instance of the key in a scope further out, but the erasure 30 /// itself is scoped. Key erasure works by inserting a sentinal value into 31 /// the value field, and thus only works for Value types where a meaningful 32 /// sentinal can be chosen. 33 template<typename Key, typename Value> 34 class ErasableScopedMap { 35 typedef std::map< Key, Value > Scope; 36 typedef std::vector< Scope > ScopeList; 37 38 /// Scoped list of maps. 39 ScopeList scopes; 40 /// Sentinal value for erased keys. 41 Value erased; 42 public: 43 typedef typename Scope::key_type key_type; 44 typedef typename Scope::mapped_type mapped_type; 45 typedef typename Scope::value_type value_type; 46 typedef typename ScopeList::size_type size_type; 47 typedef typename ScopeList::difference_type difference_type; 48 typedef typename Scope::reference reference; 49 typedef typename Scope::const_reference const_reference; 50 typedef typename Scope::pointer pointer; 51 typedef typename Scope::const_pointer const_pointer; 52 53 // Both iterator types are complete bidirection iterators, defined below. 54 class iterator; 55 class const_iterator; 56 57 /// Starts a new scope 58 void beginScope() { 59 Scope scope; 60 scopes.push_back(scope); 61 } 62 63 /// Ends a scope; invalidates any iterators pointing to elements of that scope 64 void endScope() { 65 scopes.pop_back(); 66 assert( ! scopes.empty() ); 67 } 68 69 /// Default constructor initializes with one scope 70 ErasableScopedMap( const Value &erased_ ) : erased( erased_ ) { beginScope(); } 71 72 iterator begin() { return iterator(*this, scopes.back().begin(), scopes.size()-1).next_valid(); } 73 const_iterator begin() const { return const_iterator(*this, scopes.back().begin(), scopes.size()-1).next_valid(); } 74 const_iterator cbegin() const { return const_iterator(*this, scopes.back().begin(), scopes.size()-1).next_valid(); } 75 iterator end() { return iterator(*this, scopes[0].end(), 0); } 76 const_iterator end() const { return const_iterator(*this, scopes[0].end(), 0); } 77 const_iterator cend() const { return const_iterator(*this, scopes[0].end(), 0); } 78 79 /// Gets the index of the current scope (counted from 1) 80 size_type currentScope() const { return scopes.size(); } 81 82 /// Finds the given key in the outermost scope it occurs; returns end() for none such 83 iterator find( const Key &key ) { 84 for ( size_type i = scopes.size() - 1; ; --i ) { 85 typename Scope::iterator val = scopes[i].find( key ); 86 if ( val != scopes[i].end() ) { 87 return val->second == erased ? end() : iterator( *this, val, i ); 59 88 } 60 61 /// Increments on invalid 62 iterator& next_valid() { 63 if ( ! is_valid() ) { ++(*this); } 64 return *this; 89 if ( i == 0 ) break; 90 } 91 return end(); 92 } 93 const_iterator find( const Key &key ) const { 94 return const_iterator( const_cast< ErasableScopedMap< Key, Value >* >(this)->find( key ) ); 95 } 96 97 /// Finds the given key in the outermost scope inside the given scope where it occurs 98 iterator findNext( const_iterator &it, const Key &key ) { 99 if ( it.i == 0 ) return end(); 100 for ( size_type i = it.i - 1; ; --i ) { 101 typename Scope::iterator val = scopes[i].find( key ); 102 if ( val != scopes[i].end() ) { 103 return val->second == erased ? end() : iterator( *this, val, i ); 65 104 } 66 67 /// Decrements on invalid 68 iterator& prev_valid() { 69 if ( ! is_valid() ) { --(*this); } 70 return *this; 71 } 72 73 iterator(ErasableScopedMap< Key, Value > const &_map, const wrapped_iterator &_it, size_type _i) 74 : map(&_map), it(_it), i(_i) {} 75 76 public: 77 iterator(const iterator &that) : map(that.map), it(that.it), i(that.i) {} 78 iterator& operator= (const iterator &that) { 79 map = that.map; i = that.i; it = that.it; 80 return *this; 81 } 82 83 reference operator* () { return *it; } 84 pointer operator-> () { return it.operator->(); } 85 86 iterator& operator++ () { 87 if ( it == map->scopes[i].end() ) { 88 if ( i == 0 ) return *this; 89 --i; 90 it = map->scopes[i].begin(); 91 } else { 92 ++it; 93 } 94 return next_valid(); 95 } 96 iterator& operator++ (int) { iterator tmp = *this; ++(*this); return tmp; } 97 98 iterator& operator-- () { 99 // may fail if this is the begin iterator; allowed by STL spec 100 if ( it == map->scopes[i].begin() ) { 101 ++i; 102 it = map->scopes[i].end(); 103 } 104 --it; 105 return prev_valid(); 106 } 107 iterator& operator-- (int) { iterator tmp = *this; --(*this); return tmp; } 108 109 bool operator== (const iterator &that) { 110 return map == that.map && i == that.i && it == that.it; 111 } 112 bool operator!= (const iterator &that) { return !( *this == that ); } 113 114 private: 115 ErasableScopedMap< Key, Value > const *map; 116 wrapped_iterator it; 117 size_type i; 118 }; 119 120 class const_iterator : public std::iterator< std::bidirectional_iterator_tag, 121 value_type > { 122 friend class ErasableScopedMap; 123 typedef typename std::map< Key, Value >::iterator wrapped_iterator; 124 typedef typename std::map< Key, Value >::const_iterator wrapped_const_iterator; 125 typedef typename std::vector< std::map< Key, Value > > scope_list; 126 typedef typename scope_list::size_type size_type; 127 128 /// Checks if this iterator points to a valid item 129 bool is_valid() const { 130 return it != map->scopes[i].end() && it->second != map->erased; 131 } 132 133 /// Increments on invalid 134 const_iterator& next_valid() { 135 if ( ! is_valid() ) { ++(*this); } 136 return *this; 137 } 138 139 /// Decrements on invalid 140 const_iterator& prev_valid() { 141 if ( ! is_valid() ) { --(*this); } 142 return *this; 143 } 144 145 const_iterator(ErasableScopedMap< Key, Value > const &_map, const wrapped_const_iterator &_it, size_type _i) 146 : map(&_map), it(_it), i(_i) {} 147 public: 148 const_iterator(const iterator &that) : map(that.map), it(that.it), i(that.i) {} 149 const_iterator(const const_iterator &that) : map(that.map), it(that.it), i(that.i) {} 150 const_iterator& operator= (const iterator &that) { 151 map = that.map; i = that.i; it = that.it; 152 return *this; 153 } 154 const_iterator& operator= (const const_iterator &that) { 155 map = that.map; i = that.i; it = that.it; 156 return *this; 157 } 158 159 const_reference operator* () { return *it; } 160 const_pointer operator-> () { return it.operator->(); } 161 162 const_iterator& operator++ () { 163 if ( it == map->scopes[i].end() ) { 164 if ( i == 0 ) return *this; 165 --i; 166 it = map->scopes[i].begin(); 167 } else { 168 ++it; 169 } 170 return next_valid(); 171 } 172 const_iterator& operator++ (int) { const_iterator tmp = *this; ++(*this); return tmp; } 173 174 const_iterator& operator-- () { 175 // may fail if this is the begin iterator; allowed by STL spec 176 if ( it == map->scopes[i].begin() ) { 177 ++i; 178 it = map->scopes[i].end(); 179 } 180 --it; 181 return prev_valid(); 182 } 183 const_iterator& operator-- (int) { const_iterator tmp = *this; --(*this); return tmp; } 184 185 bool operator== (const const_iterator &that) { 186 return map == that.map && i == that.i && it == that.it; 187 } 188 bool operator!= (const const_iterator &that) { return !( *this == that ); } 189 190 private: 191 ErasableScopedMap< Key, Value > const *map; 192 wrapped_const_iterator it; 193 size_type i; 194 }; 195 196 /// Starts a new scope 197 void beginScope() { 198 Scope scope; 199 scopes.push_back(scope); 200 } 201 202 /// Ends a scope; invalidates any iterators pointing to elements of that scope 203 void endScope() { 204 scopes.pop_back(); 205 assert( ! scopes.empty() ); 206 } 207 208 /// Default constructor initializes with one scope 209 ErasableScopedMap( const Value &erased_ ) : erased( erased_ ) { beginScope(); } 210 211 iterator begin() { return iterator(*this, scopes.back().begin(), scopes.size()-1).next_valid(); } 212 const_iterator begin() const { return const_iterator(*this, scopes.back().begin(), scopes.size()-1).next_valid(); } 213 const_iterator cbegin() const { return const_iterator(*this, scopes.back().begin(), scopes.size()-1).next_valid(); } 214 iterator end() { return iterator(*this, scopes[0].end(), 0); } 215 const_iterator end() const { return const_iterator(*this, scopes[0].end(), 0); } 216 const_iterator cend() const { return const_iterator(*this, scopes[0].end(), 0); } 217 218 /// Gets the index of the current scope (counted from 1) 219 size_type currentScope() const { return scopes.size(); } 220 221 /// Finds the given key in the outermost scope it occurs; returns end() for none such 222 iterator find( const Key &key ) { 223 for ( size_type i = scopes.size() - 1; ; --i ) { 224 typename Scope::iterator val = scopes[i].find( key ); 225 if ( val != scopes[i].end() ) { 226 return val->second == erased ? end() : iterator( *this, val, i ); 227 } 228 if ( i == 0 ) break; 229 } 230 return end(); 231 } 232 const_iterator find( const Key &key ) const { 233 return const_iterator( const_cast< ErasableScopedMap< Key, Value >* >(this)->find( key ) ); 234 } 235 236 /// Finds the given key in the outermost scope inside the given scope where it occurs 237 iterator findNext( const_iterator &it, const Key &key ) { 238 if ( it.i == 0 ) return end(); 239 for ( size_type i = it.i - 1; ; --i ) { 240 typename Scope::iterator val = scopes[i].find( key ); 241 if ( val != scopes[i].end() ) { 242 return val->second == erased ? end() : iterator( *this, val, i ); 243 } 244 if ( i == 0 ) break; 245 } 246 return end(); 247 } 248 const_iterator findNext( const_iterator &it, const Key &key ) const { 249 return const_iterator( const_cast< ErasableScopedMap< Key, Value >* >(this)->findNext( it, key ) ); 250 } 251 252 /// Inserts the given key-value pair into the outermost scope 253 std::pair< iterator, bool > insert( const value_type &value ) { 254 std::pair< typename Scope::iterator, bool > res = scopes.back().insert( value ); 255 return std::make_pair( iterator(*this, res.first, scopes.size()-1), res.second ); 256 } 257 std::pair< iterator, bool > insert( const Key &key, const Value &value ) { return insert( std::make_pair( key, value ) ); } 258 259 /// Marks the given element as erased from this scope inward; returns 1 for erased an element, 0 otherwise 260 size_type erase( const Key &key ) { 261 typename Scope::iterator val = scopes.back().find( key ); 262 if ( val != scopes.back().end() ) { 263 val->second = erased; 264 return 1; 265 } else { 266 scopes.back().insert( val, std::make_pair( key, erased ) ); 267 return 0; 268 } 269 } 270 271 Value& operator[] ( const Key &key ) { 272 iterator slot = find( key ); 273 if ( slot != end() ) return slot->second; 274 return insert( key, Value() ).first->second; 275 } 276 }; 105 if ( i == 0 ) break; 106 } 107 return end(); 108 } 109 const_iterator findNext( const_iterator &it, const Key &key ) const { 110 return const_iterator( const_cast< ErasableScopedMap< Key, Value >* >(this)->findNext( it, key ) ); 111 } 112 113 /// Inserts the given key-value pair into the outermost scope 114 std::pair< iterator, bool > insert( const value_type &value ) { 115 std::pair< typename Scope::iterator, bool > res = scopes.back().insert( value ); 116 return std::make_pair( iterator(*this, res.first, scopes.size()-1), res.second ); 117 } 118 std::pair< iterator, bool > insert( const Key &key, const Value &value ) { return insert( std::make_pair( key, value ) ); } 119 120 /// Marks the given element as erased from this scope inward; returns 1 for erased an element, 0 otherwise 121 size_type erase( const Key &key ) { 122 typename Scope::iterator val = scopes.back().find( key ); 123 if ( val != scopes.back().end() ) { 124 val->second = erased; 125 return 1; 126 } else { 127 scopes.back().insert( val, std::make_pair( key, erased ) ); 128 return 0; 129 } 130 } 131 132 Value& operator[] ( const Key &key ) { 133 iterator slot = find( key ); 134 if ( slot != end() ) return slot->second; 135 return insert( key, Value() ).first->second; 136 } 137 }; 138 139 template<typename Key, typename Value> 140 class ErasableScopedMap<Key, Value>::iterator : 141 public std::iterator< std::bidirectional_iterator_tag, value_type > { 142 friend class ErasableScopedMap; 143 typedef typename std::map< Key, Value >::iterator wrapped_iterator; 144 typedef typename std::vector< std::map< Key, Value > > scope_list; 145 typedef typename scope_list::size_type size_type; 146 147 /// Checks if this iterator points to a valid item 148 bool is_valid() const { 149 return it != map->scopes[i].end() && it->second != map->erased; 150 } 151 152 /// Increments on invalid 153 iterator& next_valid() { 154 if ( ! is_valid() ) { ++(*this); } 155 return *this; 156 } 157 158 /// Decrements on invalid 159 iterator& prev_valid() { 160 if ( ! is_valid() ) { --(*this); } 161 return *this; 162 } 163 164 iterator(ErasableScopedMap< Key, Value > const &_map, const wrapped_iterator &_it, size_type _i) 165 : map(&_map), it(_it), i(_i) {} 166 167 public: 168 iterator(const iterator &that) : map(that.map), it(that.it), i(that.i) {} 169 iterator& operator= (const iterator &that) { 170 map = that.map; i = that.i; it = that.it; 171 return *this; 172 } 173 174 reference operator* () { return *it; } 175 pointer operator-> () { return it.operator->(); } 176 177 iterator& operator++ () { 178 if ( it == map->scopes[i].end() ) { 179 if ( i == 0 ) return *this; 180 --i; 181 it = map->scopes[i].begin(); 182 } else { 183 ++it; 184 } 185 return next_valid(); 186 } 187 188 iterator& operator++ (int) { iterator tmp = *this; ++(*this); return tmp; } 189 190 iterator& operator-- () { 191 // may fail if this is the begin iterator; allowed by STL spec 192 if ( it == map->scopes[i].begin() ) { 193 ++i; 194 it = map->scopes[i].end(); 195 } 196 --it; 197 return prev_valid(); 198 } 199 iterator& operator-- (int) { iterator tmp = *this; --(*this); return tmp; } 200 201 bool operator== (const iterator &that) { 202 return map == that.map && i == that.i && it == that.it; 203 } 204 bool operator!= (const iterator &that) { return !( *this == that ); } 205 206 private: 207 ErasableScopedMap< Key, Value > const *map; 208 wrapped_iterator it; 209 size_type i; 210 }; 211 212 template<typename Key, typename Value> 213 class ErasableScopedMap<Key, Value>::const_iterator : 214 public std::iterator< std::bidirectional_iterator_tag, value_type > { 215 friend class ErasableScopedMap; 216 typedef typename std::map< Key, Value >::iterator wrapped_iterator; 217 typedef typename std::map< Key, Value >::const_iterator wrapped_const_iterator; 218 typedef typename std::vector< std::map< Key, Value > > scope_list; 219 typedef typename scope_list::size_type size_type; 220 221 /// Checks if this iterator points to a valid item 222 bool is_valid() const { 223 return it != map->scopes[i].end() && it->second != map->erased; 224 } 225 226 /// Increments on invalid 227 const_iterator& next_valid() { 228 if ( ! is_valid() ) { ++(*this); } 229 return *this; 230 } 231 232 /// Decrements on invalid 233 const_iterator& prev_valid() { 234 if ( ! is_valid() ) { --(*this); } 235 return *this; 236 } 237 238 const_iterator(ErasableScopedMap< Key, Value > const &_map, const wrapped_const_iterator &_it, size_type _i) 239 : map(&_map), it(_it), i(_i) {} 240 public: 241 const_iterator(const iterator &that) : map(that.map), it(that.it), i(that.i) {} 242 const_iterator(const const_iterator &that) : map(that.map), it(that.it), i(that.i) {} 243 const_iterator& operator= (const iterator &that) { 244 map = that.map; i = that.i; it = that.it; 245 return *this; 246 } 247 const_iterator& operator= (const const_iterator &that) { 248 map = that.map; i = that.i; it = that.it; 249 return *this; 250 } 251 252 const_reference operator* () { return *it; } 253 const_pointer operator-> () { return it.operator->(); } 254 255 const_iterator& operator++ () { 256 if ( it == map->scopes[i].end() ) { 257 if ( i == 0 ) return *this; 258 --i; 259 it = map->scopes[i].begin(); 260 } else { 261 ++it; 262 } 263 return next_valid(); 264 } 265 const_iterator& operator++ (int) { const_iterator tmp = *this; ++(*this); return tmp; } 266 267 const_iterator& operator-- () { 268 // may fail if this is the begin iterator; allowed by STL spec 269 if ( it == map->scopes[i].begin() ) { 270 ++i; 271 it = map->scopes[i].end(); 272 } 273 --it; 274 return prev_valid(); 275 } 276 const_iterator& operator-- (int) { const_iterator tmp = *this; --(*this); return tmp; } 277 278 bool operator== (const const_iterator &that) { 279 return map == that.map && i == that.i && it == that.it; 280 } 281 bool operator!= (const const_iterator &that) { return !( *this == that ); } 282 283 private: 284 ErasableScopedMap< Key, Value > const *map; 285 wrapped_const_iterator it; 286 size_type i; 287 }; 288 277 289 } // namespace GenPoly 278 290 -
src/Parser/DeclarationNode.cc
r1553a55 r29702ad 27 27 #include "SynTree/LinkageSpec.h" // for Spec, linkageName, Cforall 28 28 #include "SynTree/Attribute.h" // for Attribute 29 #include "SynTree/Declaration.h" // for TypeDecl, ObjectDecl, Inline ValueDecl, Declaration29 #include "SynTree/Declaration.h" // for TypeDecl, ObjectDecl, InlineMemberDecl, Declaration 30 30 #include "SynTree/Expression.h" // for Expression, ConstantExpr 31 31 #include "SynTree/Statement.h" // for AsmStmt … … 254 254 } // DeclarationNode::newAggregate 255 255 256 DeclarationNode * DeclarationNode::newEnum( const string * name, DeclarationNode * constants, bool body, bool typed, DeclarationNode * base ) {256 DeclarationNode * DeclarationNode::newEnum( const string * name, DeclarationNode * constants, bool body, bool typed, DeclarationNode * base, EnumHiding hiding ) { 257 257 DeclarationNode * newnode = new DeclarationNode; 258 258 newnode->type = new TypeData( TypeData::Enum ); … … 262 262 newnode->type->enumeration.anon = name == nullptr; 263 263 newnode->type->enumeration.typed = typed; 264 newnode->type->enumeration.hiding = hiding; 264 265 if ( base && base->type) { 265 266 newnode->type->base = base->type; … … 1166 1167 } // if 1167 1168 if ( enumInLine ) { 1168 return new Inline ValueDecl( *name, storageClasses, linkage, nullptr );1169 return new InlineMemberDecl( *name, storageClasses, linkage, nullptr ); 1169 1170 } // if 1170 1171 assertf( name, "ObjectDecl must a have name\n" ); -
src/Parser/ParseNode.h
r1553a55 r29702ad 239 239 static DeclarationNode * newFunction( const std::string * name, DeclarationNode * ret, DeclarationNode * param, StatementNode * body ); 240 240 static DeclarationNode * newAggregate( AggregateDecl::Aggregate kind, const std::string * name, ExpressionNode * actuals, DeclarationNode * fields, bool body ); 241 static DeclarationNode * newEnum( const std::string * name, DeclarationNode * constants, bool body, bool typed, DeclarationNode * base = nullptr );241 static DeclarationNode * newEnum( const std::string * name, DeclarationNode * constants, bool body, bool typed, DeclarationNode * base = nullptr, EnumHiding hiding = EnumHiding::Visible ); 242 242 static DeclarationNode * newEnumConstant( const std::string * name, ExpressionNode * constant ); 243 243 static DeclarationNode * newEnumValueGeneric( const std::string * name, InitializerNode * init ); -
src/Parser/TypeData.cc
r1553a55 r29702ad 923 923 buildList( td->enumeration.constants, ret->get_members() ); 924 924 list< Declaration * >::iterator members = ret->get_members().begin(); 925 ret->hide = td->enumeration.hiding == EnumHiding::Hide ? EnumDecl::EnumHiding::Hide : EnumDecl::EnumHiding::Visible; 925 926 for ( const DeclarationNode * cur = td->enumeration.constants; cur != nullptr; cur = dynamic_cast< DeclarationNode * >( cur->get_next() ), ++members ) { 926 927 if ( cur->enumInLine ) { -
src/Parser/TypeData.h
r1553a55 r29702ad 60 60 bool anon; 61 61 bool typed; 62 EnumHiding hiding; 62 63 }; 63 64 -
src/Parser/parser.yy
r1553a55 r29702ad 10 10 // Created On : Sat Sep 1 20:22:55 2001 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Wed Nov 2 21:31:21202213 // Update Count : 58 1012 // Last Modified On : Mon Nov 21 22:34:30 2022 13 // Update Count : 5848 14 14 // 15 15 … … 383 383 %type<ifctl> conditional_declaration 384 384 %type<fctl> for_control_expression for_control_expression_list 385 %type<compop> up down updowneq downupdowneq385 %type<compop> upupeq updown updowneq downupdowneq 386 386 %type<en> subrange 387 387 %type<decl> asm_name_opt … … 489 489 %type<decl> type_parameter type_parameter_list type_initializer_opt 490 490 491 %type<en> type_parameters_opt type_list 491 %type<en> type_parameters_opt type_list array_type_list 492 492 493 493 %type<decl> type_qualifier type_qualifier_name forall type_qualifier_list_opt type_qualifier_list … … 2558 2558 { typedefTable.makeTypedef( *$3 ); } 2559 2559 hide_opt '{' enumerator_list comma_opt '}' 2560 { $$ = DeclarationNode::newEnum( $3, $7, true, false)->addQualifiers( $2 ); }2560 { $$ = DeclarationNode::newEnum( $3, $7, true, false, nullptr, $5 )->addQualifiers( $2 ); } 2561 2561 | ENUM attribute_list_opt typedef_name // unqualified type name 2562 2562 hide_opt '{' enumerator_list comma_opt '}' 2563 { $$ = DeclarationNode::newEnum( $3->name, $6, true, false )->addQualifiers( $2 ); }2563 { $$ = DeclarationNode::newEnum( $3->name, $6, true, false, nullptr, $4 )->addQualifiers( $2 ); } 2564 2564 | ENUM '(' cfa_abstract_parameter_declaration ')' attribute_list_opt '{' enumerator_list comma_opt '}' 2565 2565 { … … 2580 2580 hide_opt '{' enumerator_list comma_opt '}' 2581 2581 { 2582 $$ = DeclarationNode::newEnum( $6, $11, true, true, $3 )->addQualifiers( $5 )->addQualifiers( $7 );2582 $$ = DeclarationNode::newEnum( $6, $11, true, true, $3, $9 )->addQualifiers( $5 )->addQualifiers( $7 ); 2583 2583 } 2584 2584 | ENUM '(' ')' attribute_list_opt identifier attribute_list_opt 2585 2585 hide_opt '{' enumerator_list comma_opt '}' 2586 2586 { 2587 $$ = DeclarationNode::newEnum( $5, $9, true, true, nullptr )->addQualifiers( $4 )->addQualifiers( $6 );2587 $$ = DeclarationNode::newEnum( $5, $9, true, true, nullptr, $7 )->addQualifiers( $4 )->addQualifiers( $6 ); 2588 2588 } 2589 2589 | ENUM '(' cfa_abstract_parameter_declaration ')' attribute_list_opt typedef_name attribute_list_opt 2590 2590 hide_opt '{' enumerator_list comma_opt '}' 2591 2591 { 2592 $$ = DeclarationNode::newEnum( $6->name, $10, true, true, $3 )->addQualifiers( $5 )->addQualifiers( $7 );2592 $$ = DeclarationNode::newEnum( $6->name, $10, true, true, $3, $8 )->addQualifiers( $5 )->addQualifiers( $7 ); 2593 2593 } 2594 2594 | ENUM '(' ')' attribute_list_opt typedef_name attribute_list_opt 2595 2595 hide_opt '{' enumerator_list comma_opt '}' 2596 2596 { 2597 $$ = DeclarationNode::newEnum( $5->name, $9, true, true, nullptr )->addQualifiers( $4 )->addQualifiers( $6 );2597 $$ = DeclarationNode::newEnum( $5->name, $9, true, true, nullptr, $7 )->addQualifiers( $4 )->addQualifiers( $6 ); 2598 2598 } 2599 2599 | enum_type_nobody … … 3653 3653 | '[' ']' multi_array_dimension 3654 3654 { $$ = DeclarationNode::newArray( 0, 0, false )->addArray( $3 ); } 3655 | '[' push assignment_expression pop ',' comma_expression ']' 3655 // Cannot use constant_expression because of tuples => semantic check 3656 | '[' push assignment_expression pop ',' comma_expression ']' // CFA 3656 3657 { $$ = DeclarationNode::newArray( $3, 0, false )->addArray( DeclarationNode::newArray( $6, 0, false ) ); } 3657 3658 // { SemanticError( yylloc, "New array dimension is currently unimplemented." ); $$ = nullptr; } 3659 | '[' push array_type_list pop ']' // CFA 3660 { SemanticError( yylloc, "Type array dimension is currently unimplemented." ); $$ = nullptr; } 3658 3661 | multi_array_dimension 3659 3662 ; 3663 3664 array_type_list: 3665 basic_type_name 3666 { $$ = new ExpressionNode( new TypeExpr( maybeMoveBuildType( $1 ) ) ); } 3667 | type_name 3668 { $$ = new ExpressionNode( new TypeExpr( maybeMoveBuildType( $1 ) ) ); } 3669 | assignment_expression upupeq assignment_expression 3670 | array_type_list ',' basic_type_name 3671 { $$ = (ExpressionNode *)($1->set_last( new ExpressionNode( new TypeExpr( maybeMoveBuildType( $3 ) ) ) )); } 3672 | array_type_list ',' type_name 3673 { $$ = (ExpressionNode *)($1->set_last( new ExpressionNode( new TypeExpr( maybeMoveBuildType( $3 ) ) ) )); } 3674 | array_type_list ',' assignment_expression upupeq assignment_expression 3675 ; 3676 3677 upupeq: 3678 '~' 3679 { $$ = OperKinds::LThan; } 3680 | ErangeUpEq 3681 { $$ = OperKinds::LEThan; } 3682 ; 3660 3683 3661 3684 multi_array_dimension: -
src/SynTree/Declaration.h
r1553a55 r29702ad 340 340 bool isTyped; 341 341 Type * base; 342 enum EnumHiding { Visible, Hide } hide; 342 343 343 344 EnumDecl( const std::string & name, … … 345 346 bool isTyped = false, LinkageSpec::Spec linkage = LinkageSpec::Cforall, 346 347 Type * baseType = nullptr ) 347 : Parent( name, attributes, linkage ), isTyped(isTyped), base( baseType ) {}348 : Parent( name, attributes, linkage ), isTyped(isTyped), base( baseType ) {} 348 349 EnumDecl( const EnumDecl & other ) 349 350 : Parent( other ), isTyped( other.isTyped), base( other.base ) {} … … 450 451 451 452 452 class Inline ValueDecl : public DeclarationWithType {453 class InlineMemberDecl : public DeclarationWithType { 453 454 typedef DeclarationWithType Parent; 454 455 public: 455 456 Type * type; 456 457 457 Inline ValueDecl( const std::string & name, Type::StorageClasses scs, LinkageSpec::Spec linkage, Type * type,458 InlineMemberDecl( const std::string & name, Type::StorageClasses scs, LinkageSpec::Spec linkage, Type * type, 458 459 const std::list< Attribute * > attributes = std::list< Attribute * >(), Type::FuncSpecifiers fs = Type::FuncSpecifiers() ); 459 Inline ValueDecl( const InlineValueDecl & other );460 virtual ~Inline ValueDecl();460 InlineMemberDecl( const InlineMemberDecl & other ); 461 virtual ~InlineMemberDecl(); 461 462 462 463 virtual Type * get_type() const override { return type; } 463 464 virtual void set_type(Type * newType) override { type = newType; } 464 465 465 static Inline ValueDecl * newInlineValueDecl( const std::string & name, Type * type );466 467 virtual Inline ValueDecl * clone() const override { return new InlineValueDecl( *this ); }466 static InlineMemberDecl * newInlineMemberDecl( const std::string & name, Type * type ); 467 468 virtual InlineMemberDecl * clone() const override { return new InlineMemberDecl( *this ); } 468 469 virtual void accept( Visitor & v ) override { v.visit( this ); } 469 470 virtual void accept( Visitor & v ) const override { v.visit( this ); } -
src/SynTree/InlineMemberDecl.cc
r1553a55 r29702ad 9 9 #include "Type.h" // for Type, Type::StorageClasses, Type::Fu... 10 10 11 Inline ValueDecl::InlineValueDecl( const std::string &name, Type::StorageClasses scs, LinkageSpec::Spec linkage,11 InlineMemberDecl::InlineMemberDecl( const std::string &name, Type::StorageClasses scs, LinkageSpec::Spec linkage, 12 12 Type * type, const std::list< Attribute * >attributes, Type::FuncSpecifiers fs) 13 13 : Parent( name, scs, linkage, attributes, fs ), type( type ) {} 14 14 15 Inline ValueDecl::InlineValueDecl( const InlineValueDecl &other)15 InlineMemberDecl::InlineMemberDecl( const InlineMemberDecl &other) 16 16 : Parent( other), type( maybeClone( other.type ) ) {} 17 17 18 Inline ValueDecl::~InlineValueDecl() { delete type; }18 InlineMemberDecl::~InlineMemberDecl() { delete type; } 19 19 20 Inline ValueDecl * InlineValueDecl::newInlineValueDecl( const std::string &name, Type * type ) {21 return new Inline ValueDecl( name, Type::StorageClasses(), LinkageSpec::C, type );20 InlineMemberDecl * InlineMemberDecl::newInlineMemberDecl( const std::string &name, Type * type ) { 21 return new InlineMemberDecl( name, Type::StorageClasses(), LinkageSpec::C, type ); 22 22 } 23 23 24 void Inline ValueDecl::print( std::ostream &os, Indenter indent ) const {24 void InlineMemberDecl::print( std::ostream &os, Indenter indent ) const { 25 25 if ( name != "" ) os << name << ": "; 26 26 … … 44 44 } 45 45 46 void Inline ValueDecl::printShort( std::ostream &os, Indenter indent ) const {46 void InlineMemberDecl::printShort( std::ostream &os, Indenter indent ) const { 47 47 if ( name != "" ) os << name << ": "; 48 48 -
src/SynTree/Mutator.h
r1553a55 r29702ad 36 36 virtual DirectiveDecl * mutate( DirectiveDecl * directiveDecl ) = 0; 37 37 virtual StaticAssertDecl * mutate( StaticAssertDecl * assertDecl ) = 0; 38 virtual DeclarationWithType * mutate( Inline ValueDecl * inlineValueDecl ) = 0;38 virtual DeclarationWithType * mutate( InlineMemberDecl * InlineMemberDecl ) = 0; 39 39 40 40 virtual CompoundStmt * mutate( CompoundStmt * compoundStmt ) = 0; -
src/SynTree/SynTree.h
r1553a55 r29702ad 38 38 class DirectiveDecl; 39 39 class StaticAssertDecl; 40 class Inline ValueDecl;40 class InlineMemberDecl; 41 41 42 42 class Statement; -
src/SynTree/Visitor.h
r1553a55 r29702ad 49 49 virtual void visit( StaticAssertDecl * node ) { visit( const_cast<const StaticAssertDecl *>(node) ); } 50 50 virtual void visit( const StaticAssertDecl * assertDecl ) = 0; 51 virtual void visit( Inline ValueDecl * node ) { visit( const_cast<const InlineValueDecl *>(node) ); }52 virtual void visit( const Inline ValueDecl * valueDecl ) = 0;51 virtual void visit( InlineMemberDecl * node ) { visit( const_cast<const InlineMemberDecl *>(node) ); } 52 virtual void visit( const InlineMemberDecl * valueDecl ) = 0; 53 53 54 54 virtual void visit( CompoundStmt * node ) { visit( const_cast<const CompoundStmt *>(node) ); } -
src/SynTree/module.mk
r1553a55 r29702ad 42 42 SynTree/Initializer.cc \ 43 43 SynTree/Initializer.h \ 44 SynTree/Inline ValueDecl.cc \44 SynTree/InlineMemberDecl.cc \ 45 45 SynTree/Label.h \ 46 46 SynTree/LinkageSpec.cc \ -
src/Validate/EnumAndPointerDecay.cpp
r1553a55 r29702ad 41 41 auto mut = ast::mutate( decl ); 42 42 std::vector<ast::ptr<ast::Decl>> buffer; 43 for ( auto it = decl->members.begin(); it != decl->members.end(); ++it ) { 44 if ( ast::ObjectDecl const * object = (*it).as<ast::ObjectDecl>() ) { 45 buffer.push_back( ast::mutate_field( object, &ast::ObjectDecl::type, new ast::EnumInstType( decl, ast::CV::Const ) ) ); 46 } else if ( ast::InlineValueDecl const * value = (*it).as<ast::InlineValueDecl>() ) { 43 for ( auto member : decl->members ) { 44 if ( ast::ObjectDecl const * object = member.as<ast::ObjectDecl>() ) { 45 buffer.push_back( ast::mutate_field( object, 46 &ast::ObjectDecl::type, 47 new ast::EnumInstType( decl, ast::CV::Const ) ) ); 48 } else if ( auto value = member.as<ast::InlineMemberDecl>() ) { 47 49 if ( auto targetEnum = symtab.lookupEnum( value->name ) ) { 48 for ( auto singleMember : targetEnum->members ) {49 auto copyingMember = singleMember.as<ast::ObjectDecl>();50 for ( auto enumMember : targetEnum->members ) { 51 auto enumObject = enumMember.strict_as<ast::ObjectDecl>(); 50 52 buffer.push_back( new ast::ObjectDecl( 51 value->location, // use the "inline" location 52 copyingMember->name, 53 // Get the location from the "inline" declaration. 54 value->location, 55 enumObject->name, 56 // Construct a new EnumInstType as the type. 53 57 new ast::EnumInstType( decl, ast::CV::Const ), 54 // Construct a new EnumInstType as the type 55 copyingMember->init, 56 copyingMember->storage, 57 copyingMember->linkage, 58 copyingMember->bitfieldWidth, 58 enumObject->init, 59 enumObject->storage, 60 enumObject->linkage, 61 enumObject->bitfieldWidth, 59 62 {}, 60 copyingMember->funcSpec63 enumObject->funcSpec 61 64 ) ); 62 65 }
Note:
See TracChangeset
for help on using the changeset viewer.