Apply PIE to nghttpx
[platform/upstream/nghttp2.git] / third-party / mruby / doc / limitations.md
1 # Limitations and Differences
2
3 The philosophy of mruby is to be a lightweight implementation of
4 the Ruby ISO standard. These two objectives are partially contradicting.
5 Ruby is an expressive language with complex implementation details which
6 are difficult to implement in a lightweight manner. To cope with this,
7 limitations to the "Ruby Compatibility" are defined.
8
9 This document is collecting these limitations.
10
11 ## Integrity
12
13 This document does not contain a complete list of limitations.
14 Please help to improve it by submitting your findings.
15
16
17 ## ```1/2``` gives ```0.5```
18
19 Since mruby does not have ```Bignum```, bigger integers are represented
20 by ```Float``` numbers. To enhance interoperability between ```Fixnum```
21 and ```Float```, mruby provides ```Float#upto``` and other iterating
22 methods for the ```Float``` class.  As a side effect, ```1/2``` gives ```0.5```
23 not ```0```.
24
25 ## ```Array``` passed to ```puts```
26
27 Passing an Array to ```puts``` results in different output.
28
29 ```ruby
30 puts [1,2,3]
31 ```
32
33 #### Ruby [ruby 2.0.0p645 (2015-04-13 revision 50299)]
34
35 ```
36 1
37 2
38 3
39 ```
40
41 #### mruby [2.0.1 (2019-4-4)]
42
43 ```
44 [1, 2, 3]
45 ```
46
47 ## ```Kernel.raise``` in rescue clause
48
49 ```Kernel.raise``` without arguments does not raise the current exception within
50 a rescue clause.
51
52 ```ruby
53 begin
54   1 / 0
55 rescue
56   raise
57 end
58 ```
59
60 #### Ruby [ruby 2.0.0p645 (2015-04-13 revision 50299)]
61
62 ```ZeroDivisionError``` is raised.
63
64 #### mruby [2.0.1 (2019-4-4)]
65
66 No exception is raised.
67
68 ## Fiber execution can't cross C function boundary
69
70 mruby's ```Fiber``` is implemented in a similar way to Lua's co-routine. This
71 results in the consequence that you can't switch context within C functions.
72 Only exception is ```mrb_fiber_yield``` at return.
73
74 ## ```Array``` does not support instance variables
75
76 To reduce memory consumption ```Array``` does not support instance variables.
77
78 ```ruby
79 class Liste < Array
80   def initialize(str = nil)
81     @feld = str
82   end
83 end
84
85 p Liste.new "foobar"
86 ```
87
88 #### Ruby [ruby 2.0.0p645 (2015-04-13 revision 50299)]
89
90 ``` [] ```
91
92 #### mruby [2.0.1 (2019-4-4)]
93
94 ```ArgumentError``` is raised.
95
96 ## Method visibility
97
98 For simplicity reasons no method visibility (public/private/protected) is
99 supported.
100
101 ```ruby
102 class VisibleTest
103
104   def public_method; end
105
106   private
107   def private_method; end
108
109 end
110
111 p VisibleTest.new.respond_to?(:private_method, false)
112 p VisibleTest.new.respond_to?(:private_method, true)
113 ```
114
115 #### Ruby [ruby 2.0.0p645 (2015-04-13 revision 50299)]
116
117 ```
118 false
119 true
120 ```
121
122 #### mruby [2.0.1 (2019-4-4)]
123
124 ```
125 true
126 true
127 ```
128
129 ## defined?
130
131 The ```defined?``` keyword is considered too complex to be fully
132 implemented. It is recommended to use ```const_defined?``` and
133 other reflection methods instead.
134
135 ```ruby
136 defined?(Foo)
137 ```
138
139 #### Ruby [ruby 2.0.0p645 (2015-04-13 revision 50299)]
140
141 ```
142 nil
143 ```
144
145 #### mruby [2.0.1 (2019-4-4)]
146
147 ```NameError``` is raised.
148
149 ## ```alias``` on global variables
150
151 Aliasing a global variable works in CRuby but is not part
152 of the ISO standard.
153
154 ```ruby
155 alias $a $__a__
156 ```
157
158 #### Ruby [ruby 2.0.0p645 (2015-04-13 revision 50299)]
159
160 ``` nil ```
161
162 #### mruby [2.0.1 (2019-4-4)]
163
164 Syntax error
165
166 ## Operator modification
167
168 An operator can't be overwritten by the user.
169
170 ```ruby
171 class String
172   def +
173   end
174 end
175
176 'a' + 'b'
177 ```
178
179 #### Ruby [ruby 2.0.0p645 (2015-04-13 revision 50299)]
180
181 ```ArgumentError``` is raised.
182 The re-defined ```+``` operator does not accept any arguments.
183
184 #### mruby [2.0.1 (2019-4-4)]
185
186 ``` 'ab' ```
187 Behavior of the operator wasn't changed.
188
189 ## Kernel#binding is not supported
190
191 `Kernel#binding` method is not supported.
192
193 #### Ruby [ruby 2.5.1p57 (2018-03-29 revision 63029)]
194
195 ```
196 $ ruby -e 'puts Proc.new {}.binding'
197 #<Binding:0x00000e9deabb9950>
198 ```
199
200 #### mruby [2.0.1 (2019-4-4)]
201
202 ```
203 $ ./bin/mruby -e 'puts Proc.new {}.binding'
204 trace (most recent call last):
205         [0] -e:1
206 -e:1: undefined method 'binding' (NoMethodError)
207 ```
208
209 ## Keyword arguments
210
211 mruby keyword arguments behave slightly different from CRuby 2.5
212 to make the behavior simpler and less confusing. Maybe in the
213 future, the simpler behavior will be adopted to CRuby as well.
214
215 #### Ruby [ruby 2.5.1p57 (2018-03-29 revision 63029)]
216
217 ```
218 $ ruby -e 'def m(*r,**k) p [r,k] end; m("a"=>1,:b=>2)'
219 [[{"a"=>1}], {:b=>2}]
220 ```
221
222 #### mruby [mruby 2.0.1]
223
224 ```
225 $ ./bin/mruby -e 'def m(*r,**k) p [r,k] end; m("a"=>1,:b=>2)'
226 trace (most recent call last):
227         [0] -e:1
228 -e:1: keyword argument hash with non symbol keys (ArgumentError)
229 ```
230
231 ## Argument Destructuring
232
233 ```ruby
234 def m(a,(b,c),d); p [a,b,c,d]; end
235 m(1,[2,3],4)  # => [1,2,3,4]
236 ```
237 Destructured arguments (`b` and `c` in above example) cannot be accessed
238 from the default expression of optional arguments and keyword arguments,
239 since actual assignment is done after the evaluation of those default
240 expressions. Thus:
241     
242 ```ruby
243 def f(a,(b,c),d=b)
244   p [a,b,c,d]
245 end
246 f(1,[2,3])
247 ```
248
249 CRuby gives `[1,2,3,nil]`. mruby raises `NoMethodError` for `b`.