rice 1.2.0 → 1.3.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (65) hide show
  1. data/Doxyfile +1 -1
  2. data/Makefile.in +130 -52
  3. data/README +45 -79
  4. data/Rakefile +1 -36
  5. data/aclocal.m4 +133 -61
  6. data/config.guess +43 -8
  7. data/config.sub +41 -13
  8. data/configure +1370 -1898
  9. data/configure.ac +2 -2
  10. data/doxygen.ac +1 -1
  11. data/extconf.rb +3 -1
  12. data/rice/Arg_impl.hpp +2 -2
  13. data/rice/Data_Type.cpp +34 -1
  14. data/rice/Data_Type.ipp +14 -5
  15. data/rice/Data_Type_defn.hpp +28 -1
  16. data/rice/Director.cpp +0 -6
  17. data/rice/Director.hpp +0 -8
  18. data/rice/Hash.hpp +1 -1
  19. data/rice/Makefile.am +2 -12
  20. data/rice/Makefile.in +111 -88
  21. data/rice/Object.cpp +8 -1
  22. data/rice/Object.ipp +1 -1
  23. data/rice/Object_defn.hpp +8 -0
  24. data/rice/config.hpp +3 -0
  25. data/rice/config.hpp.in +3 -0
  26. data/rice/detail/Auto_Function_Wrapper.ipp +1025 -512
  27. data/rice/detail/Auto_Member_Function_Wrapper.ipp +545 -272
  28. data/rice/detail/cfp.hpp +24 -0
  29. data/rice/detail/cfp.ipp +51 -0
  30. data/rice/detail/method_data.cpp +107 -336
  31. data/rice/detail/node.hpp +13 -13
  32. data/rice/detail/ruby.hpp +4 -0
  33. data/rice/detail/rubysig.hpp +19 -19
  34. data/rice/detail/traits.hpp +43 -0
  35. data/rice/generate_code.rb +37 -16
  36. data/rice/protect.hpp +1 -1
  37. data/rice/protect.ipp +448 -192
  38. data/rice/to_from_ruby.ipp +4 -12
  39. data/rice/to_from_ruby_defn.hpp +2 -2
  40. data/ruby/Makefile.in +99 -32
  41. data/ruby/lib/Makefile.in +61 -21
  42. data/ruby/lib/mkmf-rice.rb.in +9 -2
  43. data/ruby/lib/version.rb +1 -1
  44. data/sample/Makefile.in +33 -10
  45. data/test/Makefile.am +27 -0
  46. data/test/Makefile.in +270 -59
  47. data/test/ext/Makefile.am +43 -0
  48. data/test/ext/Makefile.in +399 -0
  49. data/test/ext/t1/Foo.hpp +10 -0
  50. data/test/ext/t1/extconf.rb +2 -0
  51. data/test/ext/t1/t1.cpp +15 -0
  52. data/test/ext/t2/extconf.rb +2 -0
  53. data/test/ext/t2/t2.cpp +11 -0
  54. data/test/test_Allocation_Strategies.cpp +1 -1
  55. data/test/test_Class.cpp +79 -0
  56. data/test/test_Data_Type.cpp +2 -2
  57. data/test/test_Director.cpp +114 -38
  58. data/test/test_Module.cpp +27 -2
  59. data/test/test_To_From_Ruby.cpp +4 -4
  60. data/test/test_rice.rb +9 -1
  61. metadata +23 -8
  62. data/rice/detail/method_data.cpp.rpp +0 -301
  63. data/rice/detail/mininode.cpp.rpp +0 -62
  64. data/rice/detail/mininode.hpp.rpp +0 -119
  65. data/rice/detail/remove_const.hpp +0 -21
@@ -0,0 +1,2 @@
1
+ require 'mkmf-rice'
2
+ create_makefile('t1')
@@ -0,0 +1,15 @@
1
+ #include "Foo.hpp"
2
+
3
+ #include "rice/Data_Type.hpp"
4
+ #include "rice/Constructor.hpp"
5
+
6
+ using namespace Rice;
7
+
8
+ extern "C"
9
+ void Init_t1()
10
+ {
11
+ define_class<Foo>("Foo")
12
+ .define_constructor(Constructor<Foo>())
13
+ .define_method("foo", &Foo::foo);
14
+ }
15
+
@@ -0,0 +1,2 @@
1
+ require 'mkmf-rice'
2
+ create_makefile('t2')
@@ -0,0 +1,11 @@
1
+ #include "../t1/Foo.hpp"
2
+ #include "rice/Data_Type.hpp"
3
+
4
+ using namespace Rice;
5
+
6
+ extern "C"
7
+ void Init_t2()
8
+ {
9
+ volatile Data_Type<Foo> foo;
10
+ }
11
+
@@ -67,7 +67,7 @@ TESTCASE(xmalloc_allocation_strategy_allocate)
67
67
 
68
68
  TESTCASE(xmalloc_allocation_strategy_free)
69
69
  {
70
- Foo * t = new Foo;
70
+ Foo * t = Xmalloc_Allocation_Strategy<Foo>::allocate();
71
71
  ASSERT(constructor_called);
72
72
  ASSERT(!destructor_called);
73
73
  Xmalloc_Allocation_Strategy<Foo>::free(t);
@@ -396,3 +396,82 @@ TESTCASE(subclassing)
396
396
  m.instance_eval("class NewClass < Testing::BaseClass; end;");
397
397
  m.instance_eval("n = NewClass.new");
398
398
  }
399
+
400
+ namespace
401
+ {
402
+ int defaults_method_one_arg1;
403
+ int defaults_method_one_arg2;
404
+ bool defaults_method_one_arg3 = false;
405
+
406
+ class DefaultArgs
407
+ {
408
+ public:
409
+ void defaults_method_one(int arg1, int arg2 = 3, bool arg3 = true)
410
+ {
411
+ defaults_method_one_arg1 = arg1;
412
+ defaults_method_one_arg2 = arg2;
413
+ defaults_method_one_arg3 = arg3;
414
+ }
415
+ };
416
+ }
417
+
418
+ TESTCASE(define_method_default_arguments)
419
+ {
420
+ Class c = define_class<DefaultArgs>("DefaultArgs")
421
+ .define_constructor(Constructor<DefaultArgs>())
422
+ .define_method("with_defaults",
423
+ &DefaultArgs::defaults_method_one,
424
+ (Arg("arg1"), Arg("arg2") = 3, Arg("arg3") = true));
425
+
426
+ Object o = c.call("new");
427
+ o.call("with_defaults", 2);
428
+
429
+ ASSERT_EQUAL(2, defaults_method_one_arg1);
430
+ ASSERT_EQUAL(3, defaults_method_one_arg2);
431
+ ASSERT(defaults_method_one_arg3);
432
+
433
+ o.call("with_defaults", 11, 10);
434
+
435
+ ASSERT_EQUAL(11, defaults_method_one_arg1);
436
+ ASSERT_EQUAL(10, defaults_method_one_arg2);
437
+ ASSERT(defaults_method_one_arg3);
438
+
439
+ o.call("with_defaults", 22, 33, false);
440
+
441
+ ASSERT_EQUAL(22, defaults_method_one_arg1);
442
+ ASSERT_EQUAL(33, defaults_method_one_arg2);
443
+ ASSERT(!defaults_method_one_arg3);
444
+ }
445
+
446
+ /*
447
+ namespace {
448
+ float with_reference_defaults_x;
449
+ std::string with_reference_defaults_str;
450
+
451
+ class DefaultArgsRefs
452
+ {
453
+ public:
454
+ void with_reference_defaults(float x, std::string const& str = std::string("testing"))
455
+ {
456
+ with_reference_defaults_x = x;
457
+ with_reference_defaults_str = str;
458
+ }
459
+ };
460
+
461
+ }
462
+
463
+ TESTCASE(define_method_works_with_reference_const_default_values)
464
+ {
465
+ Class c = define_class<DefaultArgsRefs>("DefaultArgsRefs")
466
+ .define_constructor(Constructor<DefaultArgsRefs>())
467
+ .define_method("bar",
468
+ &DefaultArgsRefs::with_reference_defaults,
469
+ (Arg("x"), Arg("str") = std::string("testing")));
470
+
471
+ Object o = c.call("new");
472
+ o.call("bar", 3);
473
+
474
+ ASSERT_EQUAL(3, with_reference_defaults_x);
475
+ ASSERT_EQUAL("testing", with_reference_defaults_str);
476
+ }
477
+ */
@@ -44,7 +44,7 @@ namespace {
44
44
  }
45
45
 
46
46
  int process() {
47
- vector<Listener*>::iterator i = mListeners.begin();
47
+ std::vector<Listener*>::iterator i = mListeners.begin();
48
48
  int accum = 0;
49
49
  for(; i != mListeners.end(); i++) {
50
50
  accum += (*i)->getValue();
@@ -56,7 +56,7 @@ namespace {
56
56
  int listenerCount() { return mListeners.size(); }
57
57
 
58
58
  private:
59
- vector<Listener*> mListeners;
59
+ std::vector<Listener*> mListeners;
60
60
  };
61
61
  }
62
62
 
@@ -65,20 +65,20 @@ namespace {
65
65
  public:
66
66
  WorkerDirector(Object self) : Director(self) { }
67
67
 
68
- int process(int num) {
69
- if(callIsFromRuby("process")) {
70
- raisePureVirtual();
71
- } else {
72
- return from_ruby<int>( getSelf().call("process", num) );
73
- }
68
+ virtual int process(int num) {
69
+ return from_ruby<int>( getSelf().call("process", num) );
74
70
  }
75
71
 
76
- int doSomething(int num) {
77
- if(callIsFromRuby("do_something")) {
78
- return this->Worker::doSomething(num);
79
- } else {
80
- return from_ruby<int>( getSelf().call("do_something", num) );
81
- }
72
+ int default_process(int num) {
73
+ raisePureVirtual();
74
+ }
75
+
76
+ virtual int doSomething(int num) {
77
+ return from_ruby<int>( getSelf().call("do_something", num) );
78
+ }
79
+
80
+ int default_doSomething(int num) {
81
+ return Worker::doSomething(num);
82
82
  }
83
83
  };
84
84
  };
@@ -86,15 +86,12 @@ namespace {
86
86
  SETUP(Director)
87
87
  {
88
88
  ruby_init();
89
-
90
- // Always need to tell Rice about the base class so that
91
- // casting works correctly
92
- define_class<Worker>("__Worker__");
93
89
  }
94
90
 
95
91
  TESTCASE(exposes_worker_as_instantiatable_class)
96
92
  {
97
- define_class<WorkerDirector, Worker>("Worker")
93
+ define_class<Worker>("Worker")
94
+ .define_director<WorkerDirector>()
98
95
  .define_constructor(Constructor<WorkerDirector, Object>())
99
96
  .define_method("get_number", &Worker::getNumber);
100
97
 
@@ -106,10 +103,11 @@ TESTCASE(exposes_worker_as_instantiatable_class)
106
103
 
107
104
  TESTCASE(can_call_virtual_methods_on_base_class)
108
105
  {
109
- define_class<WorkerDirector, Worker>("Worker")
106
+ define_class<Worker>("Worker")
107
+ .define_director<WorkerDirector>()
110
108
  .define_constructor(Constructor<WorkerDirector, Object>())
111
109
  .define_method("get_number", &Worker::getNumber)
112
- .define_method("do_something", &WorkerDirector::doSomething);
110
+ .define_method("do_something", &WorkerDirector::default_doSomething);
113
111
 
114
112
  Module m = define_module("Testing");
115
113
 
@@ -120,9 +118,10 @@ TESTCASE(can_call_virtual_methods_on_base_class)
120
118
 
121
119
  TESTCASE(super_calls_pass_execution_up_the_inheritance_chain)
122
120
  {
123
- define_class<WorkerDirector, Worker>("Worker")
121
+ define_class<Worker>("Worker")
122
+ .define_director<WorkerDirector>()
124
123
  .define_constructor(Constructor<WorkerDirector, Object>())
125
- .define_method("do_something", &WorkerDirector::doSomething);
124
+ .define_method("do_something", &WorkerDirector::default_doSomething);
126
125
 
127
126
  Module m = define_module("Testing");
128
127
  m.instance_eval("class RubyWorker < Worker; def do_something(num); super * num; end; end");
@@ -134,9 +133,10 @@ TESTCASE(super_calls_pass_execution_up_the_inheritance_chain)
134
133
 
135
134
  TESTCASE(super_calls_on_pure_virtual_raise_error)
136
135
  {
137
- define_class<WorkerDirector, Worker>("Worker")
136
+ define_class<Worker>("Worker")
137
+ .define_director<WorkerDirector>()
138
138
  .define_constructor(Constructor<WorkerDirector, Object>())
139
- .define_method("process", &WorkerDirector::process);
139
+ .define_method("process", &WorkerDirector::default_process);
140
140
 
141
141
  Module m = define_module("Testing");
142
142
  m.instance_eval("class RubyWorker < Worker; def process(num); super; end; end");
@@ -158,21 +158,22 @@ TESTCASE(polymorphic_calls_head_down_the_call_chain)
158
158
  .define_method("add_worker", &Handler::addWorker)
159
159
  .define_method("process_workers", &Handler::processWorkers);
160
160
 
161
- define_class<WorkerDirector, Worker>("Worker")
161
+ define_class<Worker>("Worker")
162
+ .define_director<WorkerDirector>()
162
163
  .define_constructor(Constructor<WorkerDirector, Object>())
163
- .define_method("process", &WorkerDirector::process);
164
+ .define_method("process", &WorkerDirector::default_process);
164
165
 
165
166
  Module m = define_module("Testing");
166
167
 
167
168
  m.instance_eval(
168
169
  "class EchoWorker < Worker; def process(num); num + 2; end; end;"
169
170
  "class DoubleWorker < Worker; def process(num); num * 2; end; end;"
170
- "handler = Handler.new;"
171
- "handler.add_worker(EchoWorker.new);"
172
- "handler.add_worker(DoubleWorker.new);"
171
+ "$handler = Handler.new;"
172
+ "$handler.add_worker(EchoWorker.new);"
173
+ "$handler.add_worker(DoubleWorker.new);"
173
174
  );
174
175
 
175
- Object result = m.instance_eval("handler.process_workers(5)");
176
+ Object result = m.instance_eval("$handler.process_workers(5)");
176
177
 
177
178
  // Hit's EchoWorker, so 5 + 2, then passes that to DoubleWorker, so 7 * 2 = 14
178
179
  ASSERT_EQUAL(14, from_ruby<int>(result.value()));
@@ -195,23 +196,42 @@ namespace {
195
196
  CallsSelfDirector(Object self) : Director(self) { }
196
197
 
197
198
  virtual int doItImpl(int in) {
198
- if(!callIsFromRuby("do_it_impl")) {
199
- return 0;
200
- } else {
201
- return from_ruby<int>( getSelf().call("do_it_impl", in) );
202
- }
199
+ return from_ruby<int>( getSelf().call("do_it_impl", in) );
200
+ }
201
+
202
+ int default_doItImpl(int in) {
203
+ raisePureVirtual();
203
204
  }
204
205
  };
205
206
 
207
+ struct MyCallsSelf : CallsSelf {
208
+ MyCallsSelf() { }
209
+
210
+ int doItImpl(int in) { return in * 12; }
211
+ };
212
+
213
+ // Abstract type return types handled properly
214
+ CallsSelf* getCallsSelf() {
215
+ return new MyCallsSelf();
216
+ }
217
+
218
+ // Abstract type Argument types handled properly
219
+ int doItOnPointer(CallsSelf* obj, int in) {
220
+ return obj->doIt(in);
221
+ }
222
+
223
+ int doItOnReference(CallsSelf& obj, int in) {
224
+ return obj.doIt(in);
225
+ }
226
+
206
227
  }
207
228
 
208
229
  TESTCASE(mix_of_polymorphic_calls_and_inheritance_dont_cause_infinite_loops)
209
230
  {
210
- define_class<CallsSelf>("__CallsSelf__");
211
-
212
- define_class<CallsSelfDirector, CallsSelf>("CallsSelf")
231
+ define_class<CallsSelf>("CallsSelf")
232
+ .define_director<CallsSelfDirector>()
213
233
  .define_constructor(Constructor<CallsSelfDirector, Rice::Object>())
214
- .define_method("do_it_impl", &CallsSelfDirector::doItImpl)
234
+ .define_method("do_it_impl", &CallsSelfDirector::default_doItImpl)
215
235
  .define_method("do_it", &CallsSelf::doIt);
216
236
 
217
237
  Module m = define_module("Testing");
@@ -223,3 +243,59 @@ TESTCASE(mix_of_polymorphic_calls_and_inheritance_dont_cause_infinite_loops)
223
243
 
224
244
  ASSERT_EQUAL(100, from_ruby<int>(result.value()));
225
245
  }
246
+
247
+ TESTCASE(director_class_super_classes_get_type_bound)
248
+ {
249
+ Module m = define_module("Testing");
250
+ m.define_module_function("get_calls_self", &getCallsSelf);
251
+
252
+ define_class<CallsSelf>("CallsSelf")
253
+ .define_director<CallsSelfDirector>()
254
+ .define_constructor(Constructor<CallsSelfDirector, Rice::Object>())
255
+ .define_method("do_it_impl", &CallsSelfDirector::default_doItImpl)
256
+ .define_method("do_it", &CallsSelf::doIt);
257
+
258
+ Object result = m.instance_eval("cs = Testing::get_calls_self; cs.do_it(3);");
259
+ ASSERT_EQUAL(36, from_ruby<int>(result.value()));
260
+ }
261
+
262
+ TESTCASE(director_allows_abstract_types_used_as_parameters_pointers)
263
+ {
264
+ Module m = define_module("Testing");
265
+ m.define_module_function("do_it_on_pointer", &doItOnPointer);
266
+
267
+ define_class<CallsSelf>("CallsSelf")
268
+ .define_director<CallsSelfDirector>()
269
+ .define_constructor(Constructor<CallsSelfDirector, Rice::Object>())
270
+ .define_method("do_it_impl", &CallsSelfDirector::default_doItImpl)
271
+ .define_method("do_it", &CallsSelf::doIt);
272
+
273
+ Object result = m.instance_eval(
274
+ "class MySelf < CallsSelf; def do_it_impl(num); num * 10; end; end;"
275
+ "c = MySelf.new;"
276
+ "Testing::do_it_on_pointer(c, 5)"
277
+ );
278
+
279
+ ASSERT_EQUAL(50, from_ruby<int>(result.value()));
280
+ }
281
+ /*
282
+ TESTCASE(director_allows_abstract_types_used_as_parameters_reference)
283
+ {
284
+ Module m = define_module("Testing");
285
+ m.define_module_function("do_it_on_ref", &doItOnReference);
286
+
287
+ define_class<CallsSelf>("CallsSelf")
288
+ .define_director<CallsSelfDirector>()
289
+ .define_constructor(Constructor<CallsSelfDirector, Rice::Object>())
290
+ .define_method("do_it_impl", &CallsSelfDirector::default_doItImpl)
291
+ .define_method("do_it", &CallsSelf::doIt);
292
+
293
+ Object result = m.instance_eval(
294
+ "class MySelf < CallsSelf; def do_it_impl(num); num * 10; end; end;"
295
+ "c = MySelf.new;"
296
+ "Testing::do_it_on_ref(c, 3)"
297
+ );
298
+
299
+ ASSERT_EQUAL(30, from_ruby<int>(result.value()));
300
+ }
301
+ */
@@ -179,12 +179,12 @@ Foo * from_ruby<Foo *>(Object x)
179
179
  TESTCASE(define_singleton_method_int_foo)
180
180
  {
181
181
  Module m(anonymous_module());
182
- m.define_singleton_method("foo", define_method_int_foo_helper);
182
+ m.define_singleton_method("int_and_foo", define_method_int_foo_helper);
183
183
  define_method_int_result = 0;
184
184
  Foo * foo = new Foo;
185
185
  foo->x = 1024;
186
186
  VALUE f = Data_Wrap_Struct(rb_cObject, 0, Default_Allocation_Strategy<Foo>::free, foo);
187
- m.call("foo", 42, Object(f));
187
+ m.call("int_and_foo", 42, Object(f));
188
188
  ASSERT_EQUAL(42, define_method_int_foo_result_i);
189
189
  ASSERT_EQUAL(foo, define_method_int_foo_result_x);
190
190
  }
@@ -426,3 +426,28 @@ TESTCASE(define_method_works_with_reference_arguments)
426
426
  ASSERT_EQUAL("test", with_defaults_and_references_x);
427
427
  ASSERT(!with_defaults_and_references_doIt);
428
428
  }
429
+
430
+ /*
431
+ namespace {
432
+ float with_reference_defaults_x;
433
+ std::string with_reference_defaults_str;
434
+
435
+ void with_reference_defaults(float x, std::string const& str = std::string("testing"))
436
+ {
437
+ with_reference_defaults_x = x;
438
+ with_reference_defaults_str = str;
439
+ }
440
+ }
441
+
442
+ TESTCASE(define_method_works_with_reference_const_default_values)
443
+ {
444
+ Module m(anonymous_module());
445
+ m.define_module_function("bar", &with_reference_defaults,
446
+ (Arg("x"), Arg("str") = std::string("testing")));
447
+
448
+ m.call("bar", 3);
449
+
450
+ ASSERT_EQUAL(3, with_reference_defaults_x);
451
+ ASSERT_EQUAL("testing", with_reference_defaults_str);
452
+ }
453
+ */
@@ -188,9 +188,9 @@ TESTCASE(float_from_ruby)
188
188
  std::numeric_limits<float>::max(),
189
189
  from_ruby<float>(rb_float_new(std::numeric_limits<float>::max())));
190
190
  ASSERT(
191
- isnan(from_ruby<float>(rb_float_new(std::numeric_limits<float>::quiet_NaN()))));
191
+ std::isnan(from_ruby<float>(rb_float_new(std::numeric_limits<float>::quiet_NaN()))));
192
192
  ASSERT(
193
- isnan(from_ruby<float>(rb_float_new(std::numeric_limits<float>::signaling_NaN()))));
193
+ std::isnan(from_ruby<float>(rb_float_new(std::numeric_limits<float>::signaling_NaN()))));
194
194
  ASSERT_EQUAL(
195
195
  std::numeric_limits<float>::epsilon(),
196
196
  from_ruby<float>(rb_float_new(std::numeric_limits<float>::epsilon())));
@@ -229,9 +229,9 @@ TESTCASE(double_from_ruby)
229
229
  std::numeric_limits<double>::max(),
230
230
  from_ruby<double>(rb_float_new(std::numeric_limits<double>::max())));
231
231
  ASSERT(
232
- isnan(from_ruby<double>(rb_float_new(std::numeric_limits<double>::quiet_NaN()))));
232
+ std::isnan(from_ruby<double>(rb_float_new(std::numeric_limits<double>::quiet_NaN()))));
233
233
  ASSERT(
234
- isnan(from_ruby<double>(rb_float_new(std::numeric_limits<double>::signaling_NaN()))));
234
+ std::isnan(from_ruby<double>(rb_float_new(std::numeric_limits<double>::signaling_NaN()))));
235
235
  ASSERT_EQUAL(
236
236
  std::numeric_limits<double>::epsilon(),
237
237
  from_ruby<double>(rb_float_new(std::numeric_limits<double>::epsilon())));
@@ -16,10 +16,18 @@ class RiceTest < Test::Unit::TestCase
16
16
  run_external_test("./vm_unittest#{EXEEXT}")
17
17
  end
18
18
 
19
- def test_vm_unittest
19
+ def test_multiple_extensions
20
20
  run_external_test("#{RUBY} test_multiple_extensions.rb")
21
21
  end
22
22
 
23
+ def test_multiple_extensions_with_inheritance
24
+ run_external_test("#{RUBY} test_multiple_extensions_with_inheritance.rb")
25
+ end
26
+
27
+ def test_multiple_extensions_same_class
28
+ run_external_test("#{RUBY} test_multiple_extensions_same_class.rb")
29
+ end
30
+
23
31
  def run_external_test(executable)
24
32
  if VERBOSE then
25
33
  system(executable)