crystalizer 0.2.2
Sign up to get free protection for your applications and to get access to all the features.
- data/Changelog +27 -0
- data/README +79 -0
- data/Rakefile +24 -0
- data/TODO +14 -0
- data/VERSION +1 -0
- data/benchmarks/bench.rb +129 -0
- data/benchmarks/concretize_test.rb +26 -0
- data/benchmarks/extconf.rb +10 -0
- data/benchmarks/tak_rb.rb +7 -0
- data/benchmarks/tak_so.rb +7 -0
- data/benchmarks/tak_source.rb +16 -0
- data/bin/rb2cx +162 -0
- data/doc/eval2c.txt +246 -0
- data/doc/gen_html.rb +26 -0
- data/doc/html_template +10 -0
- data/doc/index.txt +169 -0
- data/doc/limitations.txt +529 -0
- data/doc/optimizations.txt +185 -0
- data/doc/rb2cx.txt +130 -0
- data/doc/style.css +27 -0
- data/lib/concretizer.rb +3 -0
- data/lib/ruby2cext/c_function.rb +617 -0
- data/lib/ruby2cext/common_node_comp.rb +1412 -0
- data/lib/ruby2cext/compiler.rb +311 -0
- data/lib/ruby2cext/concretize.rb +269 -0
- data/lib/ruby2cext/error.rb +15 -0
- data/lib/ruby2cext/eval2c.rb +126 -0
- data/lib/ruby2cext/parser.rb +36 -0
- data/lib/ruby2cext/plugin.rb +24 -0
- data/lib/ruby2cext/plugins/builtin_methods.rb +817 -0
- data/lib/ruby2cext/plugins/cache_call.rb +293 -0
- data/lib/ruby2cext/plugins/case_optimize.rb +102 -0
- data/lib/ruby2cext/plugins/const_cache.rb +36 -0
- data/lib/ruby2cext/plugins/direct_self_call.rb +70 -0
- data/lib/ruby2cext/plugins/inline_builtin.rb +797 -0
- data/lib/ruby2cext/plugins/inline_methods.rb +68 -0
- data/lib/ruby2cext/plugins/ivar_cache.rb +147 -0
- data/lib/ruby2cext/plugins/require_include.rb +69 -0
- data/lib/ruby2cext/plugins/util.rb +154 -0
- data/lib/ruby2cext/plugins/warnings.rb +121 -0
- data/lib/ruby2cext/scopes.rb +225 -0
- data/lib/ruby2cext/str_to_c_strlit.rb +12 -0
- data/lib/ruby2cext/tools.rb +80 -0
- data/lib/ruby2cext/version.rb +22 -0
- data/results +68 -0
- data/setup.rb +1585 -0
- data/stuff/builtin_methods.rb +69 -0
- data/stuff/builtin_methods_test.rb +37 -0
- data/test/bootstrap.rb +10 -0
- data/test/causes_crash_all_opts.rb +1165 -0
- data/test/eval2c/test_eval2c.rb +37 -0
- data/test/temp_17.rb +16 -0
- data/test/temp_18.rb +8 -0
- data/test/temp_19.rb +8 -0
- data/test/temp_2.rb +7 -0
- data/test/temp_20.rb +5 -0
- data/test/temp_21.rb +161 -0
- data/test/temp_22.rb +7 -0
- data/test/temp_23.rb +7 -0
- data/test/temp_24.rb +219 -0
- data/test/temp_25.rb +7 -0
- data/test/temp_26.rb +11 -0
- data/test/temp_27.rb +11 -0
- data/test/temp_28.rb +9 -0
- data/test/temp_29.rb +9 -0
- data/test/temp_3.rb +0 -0
- data/test/temp_30.rb +0 -0
- data/test/temp_31.rb +10 -0
- data/test/temp_32.rb +10 -0
- data/test/temp_33.rb +15 -0
- data/test/temp_34.rb +15 -0
- data/test/temp_35.rb +7 -0
- data/test/temp_36.rb +7 -0
- data/test/temp_37.rb +10 -0
- data/test/temp_38.rb +10 -0
- data/test/temp_39.rb +0 -0
- data/test/temp_4.rb +7 -0
- data/test/temp_40.rb +50 -0
- data/test/temp_41.rb +50 -0
- data/test/temp_42.rb +8 -0
- data/test/temp_43.rb +8 -0
- data/test/temp_44.rb +0 -0
- data/test/temp_48.rb +7 -0
- data/test/temp_49.rb +7 -0
- data/test/temp_5.rb +7 -0
- data/test/temp_59.rb +7 -0
- data/test/temp_6.rb +7 -0
- data/test/temp_60.rb +7 -0
- data/test/temp_68.rb +239 -0
- data/test/temp_7.rb +7 -0
- data/test/temp_70.rb +7 -0
- data/test/temp_71.rb +7 -0
- data/test/temp_72.rb +13 -0
- data/test/temp_73.rb +7 -0
- data/test/temp_74.rb +7 -0
- data/test/temp_76.rb +7 -0
- data/test/temp_77.rb +13 -0
- data/test/temp_79.rb +7 -0
- data/test/temp_8.rb +14 -0
- data/test/temp_81.rb +14 -0
- data/test/temp_83.rb +0 -0
- data/test/temp_84.rb +7 -0
- data/test/temp_85.rb +7 -0
- data/test/temp_86.rb +14 -0
- data/test/temp_87.rb +7 -0
- data/test/temp_88.rb +7 -0
- data/test/temp_89.rb +7 -0
- data/test/temp_9.rb +14 -0
- data/test/temp_90.rb +0 -0
- data/test/temp_91.rb +7 -0
- data/test/temp_92.rb +7 -0
- data/test/temp_93.rb +7 -0
- data/test/temp_94.rb +7 -0
- data/test/temp_95.rb +7 -0
- data/test/temp_96.rb +0 -0
- data/test/temp_97.rb +0 -0
- data/test/temp_98.rb +7 -0
- data/test/temp_99.rb +7 -0
- data/test/test_concretize.rb +132 -0
- data/test/test_concretize_all.rb +15 -0
- data/test/test_crystalize_block.rb +73 -0
- data/test/test_files/test.rb +615 -0
- data/test/test_files/vmode_test.rb +73 -0
- data/test/test_files/warn_test.rb +35 -0
- data/test/test_syntax.rb +25 -0
- metadata +268 -0
data/doc/eval2c.txt
ADDED
@@ -0,0 +1,246 @@
|
|
1
|
+
|
2
|
+
h1. Eval2C
|
3
|
+
|
4
|
+
Eval2C is a class that allows the compilation of Ruby code to a C extension at
|
5
|
+
runtime. The compiled C extension will be <code>require</code>d automatically
|
6
|
+
and the compiled code will be available as a Proc.
|
7
|
+
|
8
|
+
It is easy to integrate Eval2C into existing scripts or libraries to improve
|
9
|
+
performance. It is also pretty simple to provide fallback code for when
|
10
|
+
Ruby2CExtension is not available.
|
11
|
+
|
12
|
+
|
13
|
+
h2. Basic Usage
|
14
|
+
|
15
|
+
Here is an example:
|
16
|
+
|
17
|
+
PRE
|
18
|
+
require "ruby2cext/eval2c"
|
19
|
+
|
20
|
+
$e2c = Ruby2CExtension::Eval2C.new
|
21
|
+
|
22
|
+
$e2c.toplevel_eval("puts 'hello'") # prints hello
|
23
|
+
PREEND
|
24
|
+
|
25
|
+
First you need to create an Eval2C instance, this instance basically stores
|
26
|
+
the options/configuration. In the above example no options were given, so the
|
27
|
+
defaults are used. The available options are explained below.
|
28
|
+
|
29
|
+
The last line of the example does what the method name suggests: the string of
|
30
|
+
Ruby code is evaluated at the toplevel (i.e. not inside any class scope). To
|
31
|
+
be more precise, that last line is equivalent to this Ruby code:
|
32
|
+
|
33
|
+
PRE
|
34
|
+
$some_global_var = proc { puts 'hello' }
|
35
|
+
$some_global_var.call
|
36
|
+
PREEND
|
37
|
+
|
38
|
+
The proc is compiled to a C extension, that C expension is then
|
39
|
+
<code>require</code>d and finally the proc is called.
|
40
|
+
|
41
|
+
The implementation of @toplevel_eval@ is actually pretty simple:
|
42
|
+
|
43
|
+
PRE
|
44
|
+
def toplevel_eval(code_str)
|
45
|
+
compile_to_proc(code_str).call
|
46
|
+
end
|
47
|
+
PREEND
|
48
|
+
|
49
|
+
So the main work is done by @compile_to_proc@, which can also be used
|
50
|
+
directly:
|
51
|
+
|
52
|
+
PRE
|
53
|
+
$e2c.compile_to_proc("|a,b| a+b").call(2, 3) # => 5
|
54
|
+
PREEND
|
55
|
+
|
56
|
+
There are some things to note: The proc won't have access to local variables
|
57
|
+
and it will be defined at toplevel, which is important for constant lookup:
|
58
|
+
|
59
|
+
PRE
|
60
|
+
SOME_CONST = :toplevel
|
61
|
+
|
62
|
+
class A
|
63
|
+
SOME_CONST = :A
|
64
|
+
$e2c.compile_to_proc("SOME_CONST").call # => :toplevel, not :A!
|
65
|
+
end
|
66
|
+
PREEND
|
67
|
+
|
68
|
+
Eval2C also offers equivalents to Ruby's @module_eval@/@class_eval@ and
|
69
|
+
@instance_eval@:
|
70
|
+
|
71
|
+
PRE
|
72
|
+
class A
|
73
|
+
$e2c.module_eval(self, %{
|
74
|
+
def initialize(x)
|
75
|
+
@x = x
|
76
|
+
end
|
77
|
+
def foo(y)
|
78
|
+
@x + y
|
79
|
+
end
|
80
|
+
})
|
81
|
+
end
|
82
|
+
|
83
|
+
A.new(5).foo(6) # => 11
|
84
|
+
|
85
|
+
$e2c.instance_eval("4321", "reverse") # => "1234"
|
86
|
+
PREEND
|
87
|
+
|
88
|
+
Their implementations also use @compile_to_proc@ and they are very similar to
|
89
|
+
the implementation of @toplevel_eval@:
|
90
|
+
|
91
|
+
PRE
|
92
|
+
def module_eval(mod, code_str)
|
93
|
+
mod.module_eval(&compile_to_proc(code_str))
|
94
|
+
end
|
95
|
+
alias :class_eval :module_eval
|
96
|
+
|
97
|
+
def instance_eval(object, code_str)
|
98
|
+
object.instance_eval(&compile_to_proc(code_str))
|
99
|
+
end
|
100
|
+
PREEND
|
101
|
+
|
102
|
+
With @module_eval@/@class_eval@ it is possible to selectively compile some
|
103
|
+
performance critical methods to C and leave the rest in Ruby.
|
104
|
+
|
105
|
+
But there is one more thing: @compile_methods@.
|
106
|
+
|
107
|
+
Defining the methods using @module_eval@ as in the last example, has at least
|
108
|
+
one downside: it won't play nice with syntax-highlighting text editors,
|
109
|
+
because the code of the methods is actually in a string. It would be much
|
110
|
+
nicer to @def@ the methods the normal way and then just compile them
|
111
|
+
afterwards.
|
112
|
+
|
113
|
+
Thanks to @compile_methods@ this is possible:
|
114
|
+
|
115
|
+
PRE
|
116
|
+
class A
|
117
|
+
def initialize(x)
|
118
|
+
@x = x
|
119
|
+
end
|
120
|
+
def foo(y)
|
121
|
+
@x + y
|
122
|
+
end
|
123
|
+
|
124
|
+
$e2c.compile_methods(self, :initialize, :foo)
|
125
|
+
end
|
126
|
+
|
127
|
+
A.new(5).foo(6) # => 11
|
128
|
+
PREEND
|
129
|
+
|
130
|
+
@compile_methods@ will grab the methods' node trees using RubyNode, compile
|
131
|
+
them to C and then replace the old methods with the C versions. The visibility
|
132
|
+
of the old methods will be preserved.
|
133
|
+
|
134
|
+
There are some limitations: @compile_methods@ only works with methods defined
|
135
|
+
using @def@ and the methods must not need a cref (for more informations on
|
136
|
+
what crefs are please see the respective section in
|
137
|
+
"limitations":limitations.html). This mainly means that constants must be
|
138
|
+
prefixed with a double colon: @Array@ needs a cref, while @::Array@ does not.
|
139
|
+
|
140
|
+
|
141
|
+
h2. Options
|
142
|
+
|
143
|
+
Eval2C is configured with an option hash, the available options are:
|
144
|
+
|
145
|
+
* @:path@: this is the path where the compiled extensions are stored, the
|
146
|
+
default is the directory @.ruby2cext@ in the current users home dir.
|
147
|
+
* @:prefix@: this is the prefix for the names of the generated extensions, the
|
148
|
+
names of the extensions are generated from this prefix and a SHA1 digest of
|
149
|
+
the code and options. The default is @"eval2c"@ and it is generally not
|
150
|
+
necessary to change it.
|
151
|
+
* @:plugins@: this is used to configure the options for the compilation
|
152
|
+
(compare "rb2cx":rb2cx.html) and it is another option hash. The default is
|
153
|
+
<code>{:optimizations => :all}</code>, but all of the following keys are
|
154
|
+
possible:
|
155
|
+
** @:warnings@: if set to @true@, then warnings about possible problems will
|
156
|
+
be sent to the logger (see below).
|
157
|
+
** @:require_include@: can be set to a single search path or an array of
|
158
|
+
search paths (equivalent to the @-I@ option of @rb2cx@).
|
159
|
+
** @:optimizations@: yet another option hash to configure the
|
160
|
+
"optimizations":optimizations.html. The valid keys are @:const_cache@,
|
161
|
+
@:builtin_methods@, @:inline_methods@ and @:case_optimize@, each with
|
162
|
+
@true@ or @false@ as value. To just use all optimizations it is also
|
163
|
+
possible to just use the symbol @:all@ instead of the hash.
|
164
|
+
* @:logger@: used for log messages, can be either @nil@ or an instance of
|
165
|
+
@Logger@ (<code>require "logger"</code>). The default is @nil@, which means
|
166
|
+
that no output is generated.
|
167
|
+
* @:force_recompile@: if this is set to @true@, then each generated extension
|
168
|
+
is (re)compiled, even if it is already available from a previous run. The
|
169
|
+
default is @false@.
|
170
|
+
|
171
|
+
Some examples:
|
172
|
+
|
173
|
+
PRE
|
174
|
+
Eval2C.new(:path => ".", :plugins => {})
|
175
|
+
Eval2C.new(:plugins => {:require_include=>[".", "../lib"], :optimizations=>:all})
|
176
|
+
Eval2C.new(:plugins => {:warnings=>true, :optimizations=>{:builtin_methods=>true}})
|
177
|
+
Eval2C.new(:prefix => "my_lib_name", :logger => Logger.new(STDOUT))
|
178
|
+
PREEND
|
179
|
+
|
180
|
+
|
181
|
+
h2. Implementation Details
|
182
|
+
|
183
|
+
The @compile_to_proc@ method works as follows:
|
184
|
+
|
185
|
+
# The name of the extension is determined from the given prefix combined with
|
186
|
+
the SHA1 digest of the Ruby code and some extra data (Ruby version,
|
187
|
+
Ruby2CExtension version and plugin options). So the code determines the
|
188
|
+
extension name and if the same code is compiled with the same version and
|
189
|
+
settings, the name will be the same. This allows very simple and efficient
|
190
|
+
caching of the compiled extensions.
|
191
|
+
# From the extension name a global variable name is constructed. The compiled
|
192
|
+
proc will be stored in that global variable by the generated C extension.
|
193
|
+
# If the extension with the generated name already exists, then we are
|
194
|
+
basically done and can skip this step. Otherwise the Ruby proc code is
|
195
|
+
translated to C and compiled to a C extension in the specified path.
|
196
|
+
# The generated or already existing C extension is <code>require</code>d.
|
197
|
+
# The global variable that now contains the compiled proc is read and the
|
198
|
+
result is returned.
|
199
|
+
|
200
|
+
The @compile_methods@ method works similar.
|
201
|
+
|
202
|
+
As mentioned above, this scheme allows very efficient caching of the C
|
203
|
+
extensions. Basically each extension is only compiled once when the
|
204
|
+
program/library is executed for the first time. In later runs the extension
|
205
|
+
will already exist and just be <code>require</code>d.
|
206
|
+
|
207
|
+
Adding the Ruby version and the Ruby2CExtension version to the digest avoids
|
208
|
+
problems if multiple versions of Ruby or Ruby2CExtension are installed and
|
209
|
+
used in parallel and it also guarantees that the extensions are automatically
|
210
|
+
recompiled if Ruby or Ruby2CExtension are updated.
|
211
|
+
|
212
|
+
|
213
|
+
h2. Using Eval2C Only When It Is Available
|
214
|
+
|
215
|
+
Having Ruby2CExtension as a hard dependency just for some speedup might not
|
216
|
+
be acceptable for many projects, in particular since Ruby2CExtension requires
|
217
|
+
that a C compiler is available at runtime.
|
218
|
+
|
219
|
+
An alternative that avoids the hard dependency is to use Ruby2CExtension only
|
220
|
+
if it is installed anyway and otherwise just execute the Ruby code as usual.
|
221
|
+
This works works very well if Eval2C and @compile_methods@ is used, for
|
222
|
+
example:
|
223
|
+
|
224
|
+
PRE
|
225
|
+
begin
|
226
|
+
require "ruby2cext/eval2c"
|
227
|
+
$e2c = Ruby2CExtension::Eval2C.new
|
228
|
+
rescue LoadError
|
229
|
+
$e2c = nil
|
230
|
+
end
|
231
|
+
|
232
|
+
class A
|
233
|
+
def initialize(x)
|
234
|
+
@x = x
|
235
|
+
end
|
236
|
+
def foo(y)
|
237
|
+
@x + y
|
238
|
+
end
|
239
|
+
|
240
|
+
$e2c && $e2c.compile_methods(self, :initialize, :foo)
|
241
|
+
end
|
242
|
+
PREEND
|
243
|
+
|
244
|
+
So if Ruby2CExtension is available, then the methods will be compiled and
|
245
|
+
fast, otherwise the Ruby code will just work as usual (but it might be a bit
|
246
|
+
slower of course).
|
data/doc/gen_html.rb
ADDED
@@ -0,0 +1,26 @@
|
|
1
|
+
require "redcloth"
|
2
|
+
|
3
|
+
Dir.chdir(File.dirname(__FILE__))
|
4
|
+
|
5
|
+
template = File.read("html_template")
|
6
|
+
|
7
|
+
Dir["*.txt"].each { |fn|
|
8
|
+
txt = File.read(fn)
|
9
|
+
title = txt[/^h1. (.+?)$/, 1]
|
10
|
+
txt.gsub!(/^PRE\n/m, "<pre><code>")
|
11
|
+
txt.gsub!(/^PREEND$/, "</code></pre>")
|
12
|
+
cnt = 0
|
13
|
+
sections = []
|
14
|
+
txt.gsub!(/^h2\.\s(.+)$/) { sections << $1; "h2(#section#{cnt+=1}). #$1" }
|
15
|
+
unless sections.empty?
|
16
|
+
sect_list = "\nSections: "
|
17
|
+
cnt = 0
|
18
|
+
sect_list << sections.map { |s| "\"#{s}\":#section#{cnt+=1}" }.join(", ")
|
19
|
+
sect_list << ".\n\n"
|
20
|
+
txt.sub!(/\nh2\(/m, sect_list << "h2(")
|
21
|
+
end
|
22
|
+
html = RedCloth.new(txt).to_html
|
23
|
+
File.open("#{File.basename(fn, ".txt")}.html", "w") { |f|
|
24
|
+
f.puts(template % [title, html])
|
25
|
+
}
|
26
|
+
}
|
data/doc/html_template
ADDED
data/doc/index.txt
ADDED
@@ -0,0 +1,169 @@
|
|
1
|
+
|
2
|
+
h1. Ruby2CExtension
|
3
|
+
|
4
|
+
Ruby2CExtension is a Ruby to C extension translator/compiler. It takes any
|
5
|
+
Ruby source file, parses it using Ruby's builtin parser and then translates
|
6
|
+
the abstract syntax tree into "equivalent" C extension code.
|
7
|
+
|
8
|
+
Let's say you have a Ruby file @foo.rb@. To translate it to a C extension and
|
9
|
+
then compile it, just run:
|
10
|
+
|
11
|
+
PRE
|
12
|
+
rb2cx foo.rb
|
13
|
+
PREEND
|
14
|
+
|
15
|
+
This will produce the files @foo.c@ and @foo.so@ (on Linux). @foo.c@ is the
|
16
|
+
generated C extension source code and @foo.so@ is the compiled C extension.
|
17
|
+
|
18
|
+
If @foo.rb@ is a library, you can just rename, move or delete @foo.rb@ (only
|
19
|
+
if you have a backup, of course) and your Ruby program will just use @foo.so@
|
20
|
+
instead.
|
21
|
+
|
22
|
+
If @foo.rb@ is a script, then it isn't possible to just run @foo.so@, because
|
23
|
+
Ruby does not support running C extensions directly, but you can do this:
|
24
|
+
|
25
|
+
PRE
|
26
|
+
ruby -r foo.so -e ""
|
27
|
+
PREEND
|
28
|
+
|
29
|
+
which should produce the same output as
|
30
|
+
|
31
|
+
PRE
|
32
|
+
ruby -r foo.rb -e ""
|
33
|
+
PREEND
|
34
|
+
|
35
|
+
|
36
|
+
h2. Why?
|
37
|
+
|
38
|
+
Well, like everybody else I wanted a faster Ruby and I also wanted to learn
|
39
|
+
about Ruby's internals, so I thought translating Ruby to C might be worth a
|
40
|
+
try...
|
41
|
+
|
42
|
+
The initial results were not as good as I had hoped, but they weren't bad
|
43
|
+
either: without optimizations the generated C extension is practically never
|
44
|
+
slower than the Ruby code and I found cases where it is more than twice as
|
45
|
+
fast, usually it is somewhere in between. But, starting from version 0.2.0,
|
46
|
+
Ruby2CExtension can use "optimizations":optimizations.html to *significantly
|
47
|
+
speedup* execution in many cases (*sometimes more than five times faster* than
|
48
|
+
normal Ruby).
|
49
|
+
|
50
|
+
Of course Ruby2CExtension can also be used as an obfuscator for Ruby code,
|
51
|
+
though this was not my main motivation.
|
52
|
+
|
53
|
+
|
54
|
+
h2. Requirements
|
55
|
+
|
56
|
+
Ruby2CExtension is developed for the Ruby 1.8 versions (only 1.8.4 and later).
|
57
|
+
It is currently tested with *Ruby 1.8.4, 1.8.5 and 1.8.6*. Only those versions
|
58
|
+
should be used, because Ruby2CExtension depends on Ruby internals that can
|
59
|
+
change between Ruby versions. If an untested Ruby version is used, then there
|
60
|
+
will be a warning. It might work for later 1.8 versions, but it definitely
|
61
|
+
won't work with Ruby 1.9.
|
62
|
+
|
63
|
+
Ruby2CExtension requires RubyNode to access Ruby's node trees (the AST).
|
64
|
+
RubyNode is available at
|
65
|
+
"http://rubynode.rubyforge.org/":http://rubynode.rubyforge.org/.
|
66
|
+
|
67
|
+
Ruby2CExtension is pure Ruby code, so it should work on all platforms that
|
68
|
+
Ruby supports, but it is currently only tested on Linux. There might be
|
69
|
+
problems with the automatic compilation of the generated C code on some
|
70
|
+
platforms (in particular on Windows).
|
71
|
+
|
72
|
+
|
73
|
+
h2. Download
|
74
|
+
|
75
|
+
* "Project page":http://rubyforge.org/projects/ruby2cext/
|
76
|
+
* "Download":http://rubyforge.org/frs/?group_id=1799
|
77
|
+
|
78
|
+
|
79
|
+
h2. Installation
|
80
|
+
|
81
|
+
Just run (as root):
|
82
|
+
|
83
|
+
PRE
|
84
|
+
gem install ruby2cext
|
85
|
+
PREEND
|
86
|
+
|
87
|
+
Or if you do not use the gem:
|
88
|
+
|
89
|
+
PRE
|
90
|
+
ruby setup.rb
|
91
|
+
PREEND
|
92
|
+
|
93
|
+
This will install Ruby2CExtension to the default locations. Optionally you
|
94
|
+
can supply some options to @setup.rb@ to customize the installation (see
|
95
|
+
@"ruby setup.rb --help"@).
|
96
|
+
|
97
|
+
|
98
|
+
h2. Features
|
99
|
+
|
100
|
+
Ruby2CExtension supports a very large subset of Ruby's features:
|
101
|
+
|
102
|
+
* all the basics (classes, methods, ...)
|
103
|
+
* blocks, closures
|
104
|
+
* @instance_eval@, @define_method@, ... (only when the block is given directly)
|
105
|
+
* correct constant and class variable lookup
|
106
|
+
* @raise@, @rescue@, @retry@, @ensure@
|
107
|
+
* ...
|
108
|
+
|
109
|
+
Things that (currently) don't work:
|
110
|
+
|
111
|
+
* @break@ with a value from inside a block
|
112
|
+
* @return@ from inside a block
|
113
|
+
* @return@, @break@, @next@, @redo@ inside @ensure@
|
114
|
+
* @defined?@ is not implemented for all cases
|
115
|
+
* block pass (passing a proc as block to a method) works, but only through a
|
116
|
+
hack and it doesn't work (correctly) for things like @instance_eval@
|
117
|
+
|
118
|
+
Some of the above things might be fixed in future versions.
|
119
|
+
|
120
|
+
Things that don't work as expected and probably never will:
|
121
|
+
|
122
|
+
* methods like @local_variables@, that depend on a Ruby SCOPE
|
123
|
+
* interoperability with @eval(str)@ and similar methods that parse a string and
|
124
|
+
eval it; these methods work, but they might not behave as expected (i.e.
|
125
|
+
access to local variables and similar things won't work, see above)
|
126
|
+
* @callcc@ works but might behave strangely (in particular local variables
|
127
|
+
might behave wrong)
|
128
|
+
* some more things, please see "limitations":limitations.html
|
129
|
+
|
130
|
+
Ruby2CExtension will translate and compile Ruby files using one or more of the
|
131
|
+
above functionalities without a warning (for some cases warnings can be
|
132
|
+
enabled, see "rb2cx":rb2cx.html), so if your Ruby code uses such
|
133
|
+
functionality, please verify that the compiled C extension works as expected.
|
134
|
+
|
135
|
+
For more details please see "limitations":limitations.html.
|
136
|
+
|
137
|
+
|
138
|
+
h2. Usage
|
139
|
+
|
140
|
+
There are two "interfaces" to use Ruby2CExtension:
|
141
|
+
|
142
|
+
* "rb2cx":rb2cx.html: the command line compiler.
|
143
|
+
* "Eval2C":eval2c.html: a class that allows dynamic compilation of Ruby code
|
144
|
+
at runtime.
|
145
|
+
|
146
|
+
Please see their respective documentations.
|
147
|
+
|
148
|
+
|
149
|
+
h2. Feedback
|
150
|
+
|
151
|
+
If you find a bug, think that something doesn't work as it should or have
|
152
|
+
other suggestions, then please don't hesitate to "contact
|
153
|
+
me":mailto:dbatml@remove_nospam.gmx.de and tell me about it.
|
154
|
+
|
155
|
+
I am also interested to know if Ruby2CExtension works under Windows (or other
|
156
|
+
non Linux platforms).
|
157
|
+
|
158
|
+
|
159
|
+
h2. Thanks
|
160
|
+
|
161
|
+
I would like to thank Eric Mahurin for various good ideas for
|
162
|
+
"optimizations":optimizations.html and for inspiring "Eval2C":eval2c.html.
|
163
|
+
|
164
|
+
|
165
|
+
h2. License
|
166
|
+
|
167
|
+
Copyright 2006-2007 "Dominik Bathon":mailto:dbatml@remove_nospam.gmx.de.
|
168
|
+
|
169
|
+
Ruby2CExtension is licensed under the same terms as Ruby.
|