Class: Rbind::GeneratorRuby
- Inherits:
-
Object
- Object
- Rbind::GeneratorRuby
- Defined in:
- lib/rbind/generator_ruby.rb
Defined Under Namespace
Classes: HelperBase, RBindHelper, RTypeHelper
Class Attribute Summary collapse
-
.ffi_type_map ⇒ Object
Returns the value of attribute ffi_type_map.
-
.on_normalize_type_name(&block) ⇒ Object
Returns the value of attribute on_normalize_type_name.
-
.ruby_default_value_map ⇒ Object
Returns the value of attribute ruby_default_value_map.
Instance Attribute Summary collapse
-
#compact_namespace ⇒ Object
Returns the value of attribute compact_namespace.
-
#file_prefix ⇒ Object
Returns the value of attribute file_prefix.
-
#library_name ⇒ Object
Returns the value of attribute library_name.
-
#module_name ⇒ Object
Returns the value of attribute module_name.
-
#output_path ⇒ Object
Returns the value of attribute output_path.
-
#required_module_names ⇒ Object
Returns the value of attribute required_module_names.
-
#root ⇒ Object
readonly
Returns the value of attribute root.
Class Method Summary collapse
- .keyword?(name) ⇒ Boolean
- .normalize_arg_name(name) ⇒ Object
- .normalize_basic_type_name_ffi(name) ⇒ Object
- .normalize_default_value(parameter) ⇒ Object
-
.normalize_method_name(orig_name) ⇒ Object
normalize c method to meet ruby conventions see unit tests.
- .normalize_type_name(name) ⇒ Object
Instance Method Summary collapse
- #generate(path = @output_path) ⇒ Object
-
#initialize(root, module_name = "Rbind", library_name = "rbind_lib") ⇒ GeneratorRuby
constructor
A new instance of GeneratorRuby.
Constructor Details
#initialize(root, module_name = "Rbind", library_name = "rbind_lib") ⇒ GeneratorRuby
Returns a new instance of GeneratorRuby.
524 525 526 527 528 529 530 |
# File 'lib/rbind/generator_ruby.rb', line 524 def initialize(root,module_name ="Rbind",library_name="rbind_lib") @root = root @rbind_wrapper = ERB.new(File.open(File.join(File.dirname(__FILE__),"templates","ruby","rbind.rb")).read) @module_name = module_name @library_name = library_name @compact_namespace = true end |
Class Attribute Details
.ffi_type_map ⇒ Object
Returns the value of attribute ffi_type_map.
10 11 12 |
# File 'lib/rbind/generator_ruby.rb', line 10 def ffi_type_map @ffi_type_map end |
.on_normalize_type_name(&block) ⇒ Object
Returns the value of attribute on_normalize_type_name.
9 10 11 |
# File 'lib/rbind/generator_ruby.rb', line 9 def on_normalize_type_name @on_normalize_type_name end |
.ruby_default_value_map ⇒ Object
Returns the value of attribute ruby_default_value_map.
8 9 10 |
# File 'lib/rbind/generator_ruby.rb', line 8 def ruby_default_value_map @ruby_default_value_map end |
Instance Attribute Details
#compact_namespace ⇒ Object
Returns the value of attribute compact_namespace.
517 518 519 |
# File 'lib/rbind/generator_ruby.rb', line 517 def compact_namespace @compact_namespace end |
#file_prefix ⇒ Object
Returns the value of attribute file_prefix.
516 517 518 |
# File 'lib/rbind/generator_ruby.rb', line 516 def file_prefix @file_prefix end |
#library_name ⇒ Object
Returns the value of attribute library_name.
514 515 516 |
# File 'lib/rbind/generator_ruby.rb', line 514 def library_name @library_name end |
#module_name ⇒ Object
Returns the value of attribute module_name.
512 513 514 |
# File 'lib/rbind/generator_ruby.rb', line 512 def module_name @module_name end |
#output_path ⇒ Object
Returns the value of attribute output_path.
515 516 517 |
# File 'lib/rbind/generator_ruby.rb', line 515 def output_path @output_path end |
#required_module_names ⇒ Object
Returns the value of attribute required_module_names.
513 514 515 |
# File 'lib/rbind/generator_ruby.rb', line 513 def required_module_names @required_module_names end |
#root ⇒ Object (readonly)
Returns the value of attribute root.
518 519 520 |
# File 'lib/rbind/generator_ruby.rb', line 518 def root @root end |
Class Method Details
.keyword?(name) ⇒ Boolean
16 17 18 |
# File 'lib/rbind/generator_ruby.rb', line 16 def self.keyword?(name) %w{__FILE__ __LINE__ alias and begin BEGIN break case class def defined? do else elsif end END ensure false for if in module next nil not or redo rescue retry return self super then true undef unless until when while yield}.include? name end |
.normalize_arg_name(name) ⇒ Object
24 25 26 27 28 29 30 31 32 33 34 35 36 37 |
# File 'lib/rbind/generator_ruby.rb', line 24 def self.normalize_arg_name(name) name = name.to_s.sub(/\A#{RBase.cprefix}?/, "").gsub(/(?<!\A)\p{Lu}/u, '_\0').downcase name = if keyword?(name) "#{name}_" else name end # check for digits at the beginning if name =~/\d(.*)/ "_#{name}" else name end end |
.normalize_basic_type_name_ffi(name) ⇒ Object
116 117 118 119 120 121 122 123 124 |
# File 'lib/rbind/generator_ruby.rb', line 116 def self.normalize_basic_type_name_ffi(name) n = ffi_type_map[name] n ||= name if n =~ /\*/ "pointer" else n end end |
.normalize_default_value(parameter) ⇒ Object
39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 |
# File 'lib/rbind/generator_ruby.rb', line 39 def self.normalize_default_value(parameter) return nil unless parameter.default_value val = if parameter.type.basic_type? || parameter.type.ptr? if ruby_default_value_map.has_key?(parameter.default_value) ruby_default_value_map[parameter.default_value] elsif parameter.type.name == "float" parameter.default_value.gsub("f","") elsif parameter.type.name == "double" parameter.default_value.gsub(/\.$/,".0").gsub(/^\./,"0.") else normalize_type_name(parameter.default_value) end else if(parameter.default_value =~ /([\w:]*) *\((.*)\)/) t = parameter.owner.owner.type($1,false) ops = Array(parameter.owner.owner.operation($1,false)) if !t t,ops = if t || !ops.empty? [t,ops] else ns = RBase.namespace($1) name = RBase.basename($1) if ns && name t = parameter.owner.owner.type(ns,false) ops = Array(t.operation(name,false)) if t [t,ops] else [nil,nil] end end if ops && !ops.empty? if t "#{normalize_type_name(t.full_name)}::#{normalize_method_name(ops.first.name)}(#{($2)})" else "#{normalize_method_name(ops.first.name)}(#{($2)})" end elsif t "#{normalize_type_name(t.full_name)}.new(#{($2)})" end else parameter.default_value end end if val val else raise "cannot parse default parameter value #{parameter.default_value} for #{parameter.owner.signature}" end end |
.normalize_method_name(orig_name) ⇒ Object
normalize c method to meet ruby conventions see unit tests
128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 |
# File 'lib/rbind/generator_ruby.rb', line 128 def self.normalize_method_name(orig_name) #remove cprefix and replaced _X with #X name = orig_name.to_s.gsub(/\A#{RBase.cprefix}/, "") .gsub(/_((?<!\A)\p{Lu})/u, '#\1') #replaced X with _x name = name.gsub(/(?<!\A)[\p{Lu}\d]/u, '_\0').downcase #replaced _x_ with #x# name = name.to_s.gsub(/[_#]([a-zA-Z\d])[_#]/u, '#\1#') #replaced _x$ with #x name = name.to_s.gsub(/[_#]([a-zA-Z\d])$/u, '#\1') #replaced ## with _ name = name.gsub(/##/, '_') #replace #xx with _xx name = name.gsub(/#([a-zA-Z\d]{2})/, '_\1') #remove all remaining # name = name.gsub(/#/, '') #replace operatorX with the correct ruby operator name = if name =~/^operator(.*)/ n = $1 if n =~ /\(\)/ raise "forbbiden method name #{name}" elsif n=~ /(.*)(\d)/ if $1 == "[]" "array_operator#{$2}" elsif $1 == "+" "plus_operator#{$2}" elsif $1 == "-" "minus_operator#{$2}" elsif $1 == "*" "mul_operator#{$2}" elsif $1 == "/" "div_operator#{$2}" else raise "forbbiden method name #{name}" end else n end else name end raise "generated empty name for #{orig_name}" if name.empty? name end |
.normalize_type_name(name) ⇒ Object
89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 |
# File 'lib/rbind/generator_ruby.rb', line 89 def self.normalize_type_name(name) # custom normalization if @on_normalize_type_name n = @on_normalize_type_name.call(name) return n if n end if name =~ /^u?int\d*$/ || name =~ /^u?int\d+_t$/ return "Fixnum" end name = name.gsub(/^_/,"") names = name.split("::").map do |n| n.gsub(/^(\w)(.*)/) do $1.upcase+$2 end end n = names.last.split("_").first if n == n.upcase return names.join("::") end names.join("::").split("_").map do |n| n.gsub(/^(\w)(.*)/) do $1.upcase+$2 end end.join("") end |
Instance Method Details
#generate(path = @output_path) ⇒ Object
532 533 534 535 536 537 538 539 540 541 542 |
# File 'lib/rbind/generator_ruby.rb', line 532 def generate(path=@output_path) @output_path = path FileUtils.mkdir_p(path) if path && !File.directory?(path) file_rbind = File.new(File.join(path,"#{file_prefix}.rb"),"w") file_types = File.new(File.join(path,"#{file_prefix}_types.rb"),"w") types = RTypeHelper.new(@module_name,@root,compact_namespace) file_types.write types.result rbind = RBindHelper.new(@module_name,self,compact_namespace) file_rbind.write @rbind_wrapper.result(rbind.binding) end |