1# Copyright (c) 2024 Huawei Device Co., Ltd. 2# Licensed under the Apache License, Version 2.0 (the "License"); 3# you may not use this file except in compliance with the License. 4# You may obtain a copy of the License at 5# 6# http://www.apache.org/licenses/LICENSE-2.0 7# 8# Unless required by applicable law or agreed to in writing, software 9# distributed under the License is distributed on an "AS IS" BASIS, 10# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 11# See the License for the specific language governing permissions and 12# limitations under the License. 13 14require 'delegate' 15require 'ostruct' 16 17module Enums 18 class EnumData < SimpleDelegator 19 def type 20 raise 'Unsupported enum kind' unless %w[simple flags].include?(kind) 21 22 kind == 'simple' ? 'int' : 'unsigned' 23 end 24 25 def flags 26 dig(:flags) || [] 27 end 28 29 def flag_unions 30 res = {} 31 dig(:flag_unions)&.each { |union| res[union.name] = union.flags } 32 res 33 end 34 35 def namespace 36 dig(:namespace) 37 end 38 39 def parent_class_name 40 dig(:parent_class_name) 41 end 42 43 def name_to_upper_snake 44 dig(:name)&.gsub(/([A-Z]+)([A-Z][a-z])/, '\1_\2') 45 &.gsub(/([a-z\d])([A-Z])/, '\1_\2') 46 &.upcase 47 end 48 end 49 50 @enums = {} 51 52 def enums 53 @enums 54 end 55 56 def wrap_data(data) 57 return unless data 58 59 data.enums&.each do |enum| 60 @enums[enum.name] = EnumData.new(enum) 61 end 62 63 node_type_enum_flags = [] 64 scope_type_enum_flags = [] 65 data.macros&.each do |macros| 66 case macros.name 67 when 'AST_NODE_MAPPING' 68 node_type_enum_flags.concat(macros.values&.map { |x| x[0] }) 69 when 'AST_NODE_REINTERPRET_MAPPING' 70 node_type_enum_flags.concat(macros.values&.map { |x| x[0..1] }&.flatten) 71 when 'SCOPE_TYPES' 72 scope_type_enum_flags.concat(macros.values&.map { |x| x[0] }) 73 end 74 end 75 data.varbinder&.macros&.each do |macros| 76 case macros.name 77 when 'SCOPE_TYPES' 78 scope_type_enum_flags.concat(macros.values&.map { |x| x[0] }) 79 end 80 end 81 82 return if node_type_enum_flags.empty? 83 84 @enums['AstNodeType'] = EnumData.new(OpenStruct.new({ 'kind' => 'simple', 'flags' => node_type_enum_flags, 85 'namespace' => 'ir', 'name' => 'AstNodeType' })) 86 87 return if scope_type_enum_flags.empty? 88 89 @enums['ScopeType'] = EnumData.new(OpenStruct.new({ 'kind' => 'simple', 'flags' => scope_type_enum_flags, 90 'namespace' => 'varbinder', 'name' => 'ScopeType' })) 91 end 92 93 module_function :wrap_data, :enums 94end 95 96def Gen.on_require(data) 97 Enums.wrap_data(data) 98end 99