rice 4.5.0 → 4.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (166) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +23 -0
  3. data/CMakeLists.txt +31 -0
  4. data/CMakePresets.json +75 -0
  5. data/COPYING +3 -2
  6. data/FindRuby.cmake +437 -0
  7. data/Rakefile +5 -4
  8. data/include/rice/rice.hpp +5436 -3201
  9. data/include/rice/stl.hpp +2355 -1269
  10. data/lib/make_rice_headers.rb +79 -0
  11. data/lib/mkmf-rice.rb +4 -0
  12. data/lib/rice/version.rb +3 -0
  13. data/lib/rice.rb +1 -0
  14. data/lib/rubygems/builder.rb +11 -0
  15. data/lib/rubygems/cmake_builder.rb +113 -0
  16. data/lib/rubygems_plugin.rb +9 -0
  17. data/rice/Arg.hpp +7 -1
  18. data/rice/Arg.ipp +11 -2
  19. data/rice/Buffer.hpp +123 -0
  20. data/rice/Buffer.ipp +599 -0
  21. data/rice/Constructor.ipp +3 -3
  22. data/rice/Data_Object.hpp +2 -3
  23. data/rice/Data_Object.ipp +188 -188
  24. data/rice/Data_Type.hpp +4 -5
  25. data/rice/Data_Type.ipp +42 -26
  26. data/rice/Enum.hpp +0 -1
  27. data/rice/Enum.ipp +26 -23
  28. data/rice/Init.hpp +8 -0
  29. data/rice/Init.ipp +8 -0
  30. data/rice/MemoryView.ipp +1 -41
  31. data/rice/Return.hpp +1 -1
  32. data/rice/Return.ipp +6 -0
  33. data/rice/cpp_api/Array.hpp +209 -0
  34. data/rice/cpp_api/Array.ipp +304 -0
  35. data/rice/cpp_api/Builtin_Object.hpp +31 -0
  36. data/rice/cpp_api/Builtin_Object.ipp +37 -0
  37. data/rice/cpp_api/Class.hpp +70 -0
  38. data/rice/cpp_api/Class.ipp +97 -0
  39. data/rice/cpp_api/Encoding.hpp +32 -0
  40. data/rice/cpp_api/Encoding.ipp +59 -0
  41. data/rice/cpp_api/Hash.hpp +194 -0
  42. data/rice/cpp_api/Hash.ipp +257 -0
  43. data/rice/cpp_api/Identifier.hpp +46 -0
  44. data/rice/cpp_api/Identifier.ipp +31 -0
  45. data/rice/cpp_api/Module.hpp +72 -0
  46. data/rice/cpp_api/Module.ipp +101 -0
  47. data/rice/cpp_api/Object.hpp +272 -0
  48. data/rice/cpp_api/Object.ipp +235 -0
  49. data/rice/cpp_api/String.hpp +74 -0
  50. data/rice/cpp_api/String.ipp +120 -0
  51. data/rice/cpp_api/Struct.hpp +113 -0
  52. data/rice/cpp_api/Struct.ipp +92 -0
  53. data/rice/cpp_api/Symbol.hpp +46 -0
  54. data/rice/cpp_api/Symbol.ipp +93 -0
  55. data/rice/cpp_api/shared_methods.hpp +134 -0
  56. data/rice/detail/MethodInfo.hpp +1 -9
  57. data/rice/detail/MethodInfo.ipp +5 -72
  58. data/rice/detail/Native.hpp +3 -2
  59. data/rice/detail/Native.ipp +32 -4
  60. data/rice/detail/NativeAttributeGet.hpp +3 -2
  61. data/rice/detail/NativeAttributeGet.ipp +8 -2
  62. data/rice/detail/NativeAttributeSet.hpp +3 -2
  63. data/rice/detail/NativeAttributeSet.ipp +8 -2
  64. data/rice/detail/NativeCallbackFFI.ipp +1 -1
  65. data/rice/detail/NativeFunction.hpp +17 -6
  66. data/rice/detail/NativeFunction.ipp +168 -64
  67. data/rice/detail/NativeIterator.hpp +3 -2
  68. data/rice/detail/NativeIterator.ipp +8 -2
  69. data/rice/detail/RubyType.hpp +2 -5
  70. data/rice/detail/RubyType.ipp +50 -5
  71. data/rice/detail/Type.hpp +3 -1
  72. data/rice/detail/Type.ipp +61 -31
  73. data/rice/detail/Wrapper.hpp +68 -33
  74. data/rice/detail/Wrapper.ipp +103 -113
  75. data/rice/detail/from_ruby.hpp +5 -4
  76. data/rice/detail/from_ruby.ipp +737 -365
  77. data/rice/detail/to_ruby.ipp +1092 -186
  78. data/rice/global_function.ipp +1 -1
  79. data/rice/libc/file.hpp +11 -0
  80. data/rice/libc/file.ipp +32 -0
  81. data/rice/rice.hpp +23 -16
  82. data/rice/stl/complex.hpp +6 -0
  83. data/rice/stl/complex.ipp +93 -0
  84. data/rice/stl/exception.hpp +11 -0
  85. data/rice/stl/exception.ipp +29 -0
  86. data/rice/stl/exception_ptr.hpp +6 -0
  87. data/rice/stl/exception_ptr.ipp +27 -0
  88. data/rice/stl/map.hpp +12 -0
  89. data/rice/stl/map.ipp +469 -0
  90. data/rice/stl/monostate.hpp +6 -0
  91. data/rice/stl/monostate.ipp +80 -0
  92. data/rice/stl/multimap.hpp +14 -0
  93. data/rice/stl/multimap.ipp +448 -0
  94. data/rice/stl/optional.hpp +6 -0
  95. data/rice/stl/optional.ipp +118 -0
  96. data/rice/stl/pair.hpp +13 -0
  97. data/rice/stl/pair.ipp +155 -0
  98. data/rice/stl/reference_wrapper.hpp +6 -0
  99. data/rice/stl/reference_wrapper.ipp +41 -0
  100. data/rice/stl/set.hpp +12 -0
  101. data/rice/stl/set.ipp +495 -0
  102. data/rice/stl/shared_ptr.hpp +28 -0
  103. data/rice/stl/shared_ptr.ipp +224 -0
  104. data/rice/stl/string.hpp +6 -0
  105. data/rice/stl/string.ipp +158 -0
  106. data/rice/stl/string_view.hpp +6 -0
  107. data/rice/stl/string_view.ipp +65 -0
  108. data/rice/stl/tuple.hpp +6 -0
  109. data/rice/stl/tuple.ipp +128 -0
  110. data/rice/stl/type_index.hpp +6 -0
  111. data/rice/stl/type_index.ipp +30 -0
  112. data/rice/stl/type_info.hpp +6 -0
  113. data/rice/stl/type_info.ipp +29 -0
  114. data/rice/stl/unique_ptr.hpp +22 -0
  115. data/rice/stl/unique_ptr.ipp +139 -0
  116. data/rice/stl/unordered_map.hpp +12 -0
  117. data/rice/stl/unordered_map.ipp +469 -0
  118. data/rice/stl/variant.hpp +6 -0
  119. data/rice/stl/variant.ipp +242 -0
  120. data/rice/stl/vector.hpp +12 -0
  121. data/rice/stl/vector.ipp +590 -0
  122. data/rice/stl.hpp +7 -3
  123. data/rice/traits/attribute_traits.hpp +26 -0
  124. data/rice/traits/function_traits.hpp +95 -0
  125. data/rice/traits/method_traits.hpp +47 -0
  126. data/rice/traits/rice_traits.hpp +160 -0
  127. data/rice.gemspec +85 -0
  128. data/test/embed_ruby.cpp +3 -0
  129. data/test/ruby/test_multiple_extensions_same_class.rb +14 -14
  130. data/test/test_Array.cpp +6 -3
  131. data/test/test_Attribute.cpp +34 -1
  132. data/test/test_Buffer.cpp +285 -0
  133. data/test/test_Callback.cpp +2 -3
  134. data/test/test_Data_Object.cpp +88 -34
  135. data/test/test_Data_Type.cpp +106 -65
  136. data/test/test_Director.cpp +7 -3
  137. data/test/test_Enum.cpp +5 -2
  138. data/test/test_File.cpp +1 -1
  139. data/test/test_From_Ruby.cpp +181 -114
  140. data/test/test_Iterator.cpp +1 -1
  141. data/test/{test_JumpException.cpp → test_Jump_Exception.cpp} +1 -0
  142. data/test/test_Keep_Alive.cpp +7 -18
  143. data/test/test_Keep_Alive_No_Wrapper.cpp +0 -1
  144. data/test/test_Module.cpp +13 -6
  145. data/test/test_Native_Registry.cpp +0 -1
  146. data/test/test_Overloads.cpp +180 -5
  147. data/test/test_Ownership.cpp +100 -57
  148. data/test/test_Proc.cpp +0 -1
  149. data/test/test_Self.cpp +4 -4
  150. data/test/test_Stl_Map.cpp +37 -39
  151. data/test/test_Stl_Multimap.cpp +693 -0
  152. data/test/test_Stl_Pair.cpp +8 -8
  153. data/test/test_Stl_Reference_Wrapper.cpp +4 -2
  154. data/test/test_Stl_Set.cpp +790 -0
  155. data/test/{test_Stl_SmartPointer.cpp → test_Stl_SharedPtr.cpp} +97 -127
  156. data/test/test_Stl_Tuple.cpp +116 -0
  157. data/test/test_Stl_Type.cpp +1 -1
  158. data/test/test_Stl_UniquePtr.cpp +202 -0
  159. data/test/test_Stl_Unordered_Map.cpp +28 -34
  160. data/test/test_Stl_Variant.cpp +217 -89
  161. data/test/test_Stl_Vector.cpp +209 -83
  162. data/test/test_To_Ruby.cpp +373 -1
  163. data/test/test_Type.cpp +85 -14
  164. data/test/test_global_functions.cpp +17 -4
  165. metadata +94 -10
  166. data/rice/detail/TupleIterator.hpp +0 -14
@@ -0,0 +1,285 @@
1
+ #include "unittest.hpp"
2
+ #include "embed_ruby.hpp"
3
+ #include <rice/rice.hpp>
4
+
5
+ #include <limits>
6
+ #include <cmath>
7
+
8
+ using namespace Rice;
9
+
10
+ TESTSUITE(Buffer);
11
+
12
+ SETUP(Buffer)
13
+ {
14
+ embed_ruby();
15
+ }
16
+
17
+ TEARDOWN(Buffer)
18
+ {
19
+ rb_gc_start();
20
+ }
21
+
22
+ TESTCASE(Char)
23
+ {
24
+ define_buffer<char>();
25
+
26
+ Module m = define_module("BufferTesting");
27
+
28
+ std::string code = R"(Rice::Buffer≺char≻.new("my string"))";
29
+ Object result = m.instance_eval(code);
30
+
31
+ ASSERT_EQUAL("Rice::Buffer≺char≻", result.class_name().c_str());
32
+ ASSERT_EQUAL("my string", String(result.call("bytes")).c_str());
33
+
34
+ Array array = result.call("to_ary");
35
+ ASSERT_EQUAL("109, 121, 32, 115, 116, 114, 105, 110, 103", array.join(", ").c_str());
36
+
37
+ Object size = result.call("size");
38
+ ASSERT_EQUAL(9, detail::From_Ruby<int>().convert(size));
39
+
40
+ Data_Object<Buffer<char>> dataObject(result);
41
+ Buffer<char> buffer = std::move(*dataObject);
42
+ ASSERT_EQUAL("my string", buffer.ptr());
43
+ ASSERT_EQUAL(9, (int)buffer.size());
44
+ }
45
+
46
+ TESTCASE(CharArray)
47
+ {
48
+ define_buffer<char>();
49
+
50
+ Module m = define_module("BufferTesting");
51
+
52
+ std::string code = R"(Rice::Buffer≺char≻.new([0, 127, 128, 255, 256, -128, -129, -255]))";
53
+ Data_Object<Buffer<char>> result = m.instance_eval(code);
54
+ Buffer<char> buffer = std::move(*result);
55
+ char* data = buffer.ptr();
56
+
57
+ ASSERT_EQUAL(data[0], 0);
58
+ ASSERT_EQUAL(data[1], 127);
59
+ ASSERT_EQUAL(data[2], -128);
60
+ ASSERT_EQUAL(data[3], -1);
61
+ ASSERT_EQUAL(data[4], 0);
62
+ ASSERT_EQUAL(data[5], -128);
63
+ ASSERT_EQUAL(data[6], 127);
64
+ ASSERT_EQUAL(data[7], 1);
65
+ }
66
+
67
+ TESTCASE(signed_char_pointer)
68
+ {
69
+ define_buffer<signed char>();
70
+ Module m = define_module("Testing");
71
+
72
+ std::string code = R"(Rice::Buffer≺signed char≻.new("my string"))";
73
+ Data_Object<Buffer<signed char>> result = m.instance_eval(code);
74
+ Buffer<signed char> buffer = std::move(*result);
75
+ signed char* data = buffer.ptr();
76
+
77
+ signed char* expected = (signed char*)"my string";
78
+ ASSERT_EQUAL(*expected, *data);
79
+
80
+ code = R"(Rice::Buffer≺signed char≻.new([0, 127, 128, 255, 256, -128, -129, -255]))";
81
+ result = m.instance_eval(code);
82
+ buffer = std::move(*result);
83
+ data = buffer.ptr();
84
+
85
+ ASSERT_EQUAL(data[0], 0);
86
+ ASSERT_EQUAL(data[1], 127);
87
+ ASSERT_EQUAL(data[2], -128);
88
+ ASSERT_EQUAL(data[3], -1);
89
+ ASSERT_EQUAL(data[4], 0);
90
+ ASSERT_EQUAL(data[5], -128);
91
+ ASSERT_EQUAL(data[6], 127);
92
+ ASSERT_EQUAL(data[7], 1);
93
+ }
94
+
95
+ TESTCASE(char_pointer_const)
96
+ {
97
+ define_buffer<char>();
98
+ Module m = define_module("Testing");
99
+
100
+ std::string code = R"(Rice::Buffer≺char≻.new("my string"))";
101
+
102
+ Data_Object<Buffer<char>> result = m.instance_eval(code);
103
+ Buffer<char> buffer = std::move(*result);
104
+ char* data = buffer.ptr();
105
+
106
+ const char* expected = "my string";
107
+ ASSERT_EQUAL(expected, data);
108
+
109
+ code = R"(Rice::Buffer≺char≻.new(""))";
110
+ result = m.instance_eval(code);
111
+ buffer = std::move(*result);
112
+ data = buffer.ptr();
113
+
114
+ expected = "";
115
+ ASSERT_EQUAL(expected, data);
116
+ }
117
+
118
+ TESTCASE(unsigned_char_pointer)
119
+ {
120
+ define_buffer<unsigned char>();
121
+ Module m = define_module("Testing");
122
+
123
+ std::string code = R"(Rice::Buffer≺unsigned char≻.new([0, 127, 128, 255, 256, -128, -129, -255]))";
124
+ Data_Object<Buffer<unsigned char>> result = m.instance_eval(code);
125
+ Buffer<unsigned char> buffer = std::move(*result);
126
+ unsigned char* data = buffer.ptr();
127
+
128
+ ASSERT_EQUAL(data[0], 0x0);
129
+ ASSERT_EQUAL(data[1], 0x7F);
130
+ ASSERT_EQUAL(data[2], 0x80);
131
+ ASSERT_EQUAL(data[3], 0xFF);
132
+ ASSERT_EQUAL(data[4], 0x00);
133
+ ASSERT_EQUAL(data[5], 0x80);
134
+ ASSERT_EQUAL(data[6], 0x7F);
135
+ ASSERT_EQUAL(data[7], 0x01);
136
+
137
+ code = R"(array = [0, 127, 128, 255, 256, -128, -129, -255]
138
+ packed = array.pack("C*")
139
+ Rice::Buffer≺unsigned char≻.new(packed))";
140
+ result = m.instance_eval(code);
141
+ buffer = std::move(*result);
142
+ data = buffer.ptr();
143
+
144
+ ASSERT_EQUAL(data[0], 0x0);
145
+ ASSERT_EQUAL(data[1], 0x7F);
146
+ ASSERT_EQUAL(data[2], 0x80);
147
+ ASSERT_EQUAL(data[3], 0xFF);
148
+ ASSERT_EQUAL(data[4], 0x00);
149
+ ASSERT_EQUAL(data[5], 0x80);
150
+ ASSERT_EQUAL(data[6], 0x7F);
151
+ ASSERT_EQUAL(data[7], 0x01);
152
+ }
153
+
154
+ TESTCASE(float_array_array)
155
+ {
156
+ define_buffer<float*>();
157
+ Module m = define_module("Testing");
158
+
159
+ std::string code = R"(Rice::Buffer≺float∗≻.new([[1.1, 2.2], [3.3, 4.4], [5.5, 6.6]]))";
160
+ Data_Object<Buffer<float*>> result = m.instance_eval(code);
161
+ Buffer<float*> buffer = std::move(*result);
162
+
163
+ ASSERT_EQUAL(3, (int)buffer.size());
164
+
165
+ const Buffer<float>& bufferInner1 = buffer[0];
166
+ ASSERT_EQUAL(2, (int)bufferInner1.size());
167
+
168
+ const Buffer<float>& bufferInner2 = buffer[1];
169
+ ASSERT_EQUAL(2, (int)bufferInner2.size());
170
+
171
+ const Buffer<float>& bufferInner3 = buffer[2];
172
+ ASSERT_EQUAL(2, (int)bufferInner3.size());
173
+ }
174
+
175
+ TESTCASE(wrong_type)
176
+ {
177
+ define_buffer<float*>();
178
+ Module m = define_module("Testing");
179
+
180
+ std::string code = R"(Rice::Buffer≺float∗≻.new([[4, "bad"], [2, 1]]))";
181
+
182
+ ASSERT_EXCEPTION_CHECK(
183
+ Exception,
184
+ m.module_eval(code),
185
+ ASSERT_EQUAL("can't convert String into Float", ex.what())
186
+ );
187
+ }
188
+
189
+ namespace
190
+ {
191
+ void updateRef(int& ref)
192
+ {
193
+ ref = 4;
194
+ }
195
+
196
+ void updatePtr(int* ptr)
197
+ {
198
+ *ptr = 5;
199
+ }
200
+ }
201
+
202
+ TESTCASE(update_reference)
203
+ {
204
+ define_buffer<int>();
205
+ Module m = define_module("Testing");
206
+ m.define_module_function("update_reference", &updateRef);
207
+
208
+ std::string code = R"(buffer = Rice::Buffer≺int≻.new(0)
209
+ update_reference(buffer)
210
+ buffer.to_ary(1).first)";
211
+
212
+ Object result = m.module_eval(code);
213
+ ASSERT_EQUAL(4, detail::From_Ruby<int>().convert(result));
214
+
215
+ code = R"(buffer = Rice::Buffer≺int≻.new(0)
216
+ update_reference(buffer)
217
+ buffer[0])";
218
+
219
+ result = m.module_eval(code);
220
+ ASSERT_EQUAL(4, detail::From_Ruby<int>().convert(result));
221
+
222
+ code = R"(buffer = Rice::Buffer≺int≻.new(0)
223
+ update_reference(buffer)
224
+ buffer[1])";
225
+
226
+ ASSERT_EXCEPTION_CHECK(
227
+ Exception,
228
+ m.module_eval(code),
229
+ ASSERT_EQUAL("index 1 outside of bounds: 0..1", ex.what())
230
+ );
231
+ }
232
+
233
+ TESTCASE(update_ptr)
234
+ {
235
+ define_buffer<int>();
236
+ Module m = define_module("Testing");
237
+ m.define_module_function("update_pointer", &updatePtr);
238
+
239
+ std::string code = R"(buffer = Rice::Buffer≺int≻.new(0)
240
+ update_pointer(buffer)
241
+ buffer.to_ary(1).first)";
242
+
243
+ Object result = m.module_eval(code);
244
+ ASSERT_EQUAL(5, detail::From_Ruby<int>().convert(result));
245
+
246
+ code = R"(buffer = Rice::Buffer≺int≻.new(0)
247
+ update_pointer(buffer)
248
+ buffer[0])";
249
+
250
+ result = m.module_eval(code);
251
+ ASSERT_EQUAL(5, detail::From_Ruby<int>().convert(result));
252
+
253
+ code = R"(buffer = Rice::Buffer≺int≻.new(0)
254
+ update_pointer(buffer)
255
+ buffer[1])";
256
+
257
+ ASSERT_EXCEPTION_CHECK(
258
+ Exception,
259
+ m.module_eval(code),
260
+ ASSERT_EQUAL("index 1 outside of bounds: 0..1", ex.what())
261
+ );
262
+ }
263
+
264
+ TESTCASE(update_buffer)
265
+ {
266
+ define_buffer<int>();
267
+ Module m = define_module("Testing");
268
+
269
+ std::string code = R"(buffer = Rice::Buffer≺int≻.new(0)
270
+ buffer[0] = 8
271
+ buffer[0])";
272
+
273
+ Object result = m.module_eval(code);
274
+ ASSERT_EQUAL(8, detail::From_Ruby<int>().convert(result));
275
+
276
+ code = R"(buffer = Rice::Buffer≺int≻.new(0)
277
+ buffer[1] = 9
278
+ buffer[1])";
279
+
280
+ ASSERT_EXCEPTION_CHECK(
281
+ Exception,
282
+ m.module_eval(code),
283
+ ASSERT_EQUAL("index 1 outside of bounds: 0..1", ex.what())
284
+ );
285
+ }
@@ -3,7 +3,6 @@
3
3
  #include "unittest.hpp"
4
4
  #include "embed_ruby.hpp"
5
5
  #include <rice/rice.hpp>
6
- #include <rice/stl.hpp>
7
6
 
8
7
  using namespace Rice;
9
8
 
@@ -140,7 +139,7 @@ namespace
140
139
  using Callback_T2 = char*(*)();
141
140
  std::vector<Callback_T2> callbacks;
142
141
 
143
- void registerCallback(Callback_T2 callback1, Callback_T2 callback2)
142
+ void registerTwoCallbacks(Callback_T2 callback1, Callback_T2 callback2)
144
143
  {
145
144
  callbacks.push_back(callback1);
146
145
  callbacks.push_back(callback2);
@@ -157,7 +156,7 @@ namespace
157
156
  TESTCASE(MultipleCallbacks)
158
157
  {
159
158
  Module m = define_module("TestingMultipleCallbacks");
160
- m.define_module_function<void(*)(Callback_T2, Callback_T2)>("register_callback", registerCallback).
159
+ m.define_module_function<void(*)(Callback_T2, Callback_T2)>("register_callback", registerTwoCallbacks).
161
160
  define_module_function<char*(*)(int)>("trigger_callback", triggerCallback);
162
161
 
163
162
  std::string code = R"(proc1 = Proc.new do
@@ -1,5 +1,3 @@
1
- #include <ruby/version.h>
2
-
3
1
  #include "unittest.hpp"
4
2
  #include "embed_ruby.hpp"
5
3
  #include <rice/rice.hpp>
@@ -15,7 +13,7 @@ namespace
15
13
 
16
14
  struct MyDataType
17
15
  {
18
- MyDataType() : x(42)
16
+ MyDataType(int value) : x(value)
19
17
  {
20
18
  }
21
19
 
@@ -27,6 +25,17 @@ namespace
27
25
  int x;
28
26
  };
29
27
 
28
+ static MyDataType myDataTypes[] = { 1,2,3 };
29
+ MyDataType* dataTypes()
30
+ {
31
+ return myDataTypes;
32
+ }
33
+
34
+ int dataTypesCount()
35
+ {
36
+ return sizeof(myDataTypes)/sizeof(MyDataType);
37
+ }
38
+
30
39
  struct Bar
31
40
  {
32
41
  };
@@ -63,18 +72,18 @@ TEARDOWN(Data_Object)
63
72
  rb_gc_start();
64
73
  }
65
74
 
66
- TESTCASE(construct_from_pointer)
75
+ TESTCASE(data_object_construct_from_pointer)
67
76
  {
68
- MyDataType* myDataType = new MyDataType;
77
+ MyDataType* myDataType = new MyDataType(42);
69
78
  Data_Object<MyDataType> wrapped_foo(myDataType);
70
79
  ASSERT_EQUAL(myDataType, wrapped_foo.get());
71
80
  ASSERT_EQUAL(Data_Type<MyDataType>::klass(), wrapped_foo.class_of());
72
81
  ASSERT_EQUAL(myDataType, detail::unwrap<MyDataType>(wrapped_foo, Data_Type<MyDataType>::ruby_data_type(), false));
73
82
  }
74
83
 
75
- TESTCASE(construct_from_ruby_object)
84
+ TESTCASE(data_object_construct_from_ruby_object)
76
85
  {
77
- MyDataType * myDataType = new MyDataType;
86
+ MyDataType * myDataType = new MyDataType(42);
78
87
  VALUE wrapped_foo = detail::wrap(Data_Type<MyDataType>::klass(), Data_Type<MyDataType>::ruby_data_type(), myDataType, true);
79
88
 
80
89
  Data_Object<MyDataType> data_object_foo(wrapped_foo);
@@ -84,9 +93,9 @@ TESTCASE(construct_from_ruby_object)
84
93
  ASSERT_EQUAL(myDataType, detail::unwrap<MyDataType>(wrapped_foo, Data_Type<MyDataType>::ruby_data_type(), false));
85
94
  }
86
95
 
87
- TESTCASE(construct_from_ruby_object_and_wrong_class)
96
+ TESTCASE(data_object_construct_from_ruby_object_and_wrong_class)
88
97
  {
89
- MyDataType * myDataType = new MyDataType;
98
+ MyDataType * myDataType = new MyDataType(42);
90
99
  VALUE wrapped_foo = detail::wrap(Data_Type<MyDataType>::klass(), Data_Type<MyDataType>::ruby_data_type(), myDataType, true);
91
100
 
92
101
  ASSERT_EXCEPTION_CHECK(
@@ -100,9 +109,9 @@ TESTCASE(construct_from_ruby_object_and_wrong_class)
100
109
  ASSERT_EQUAL("Wrong argument type. Expected: Bar. Received: MyDataType.", ex.what()));
101
110
  }
102
111
 
103
- TESTCASE(copy_construct)
112
+ TESTCASE(data_object_copy_construct)
104
113
  {
105
- MyDataType * myDataType = new MyDataType;
114
+ MyDataType * myDataType = new MyDataType(42);
106
115
  VALUE wrapped_foo = detail::wrap(Data_Type<MyDataType>::klass(), Data_Type<MyDataType>::ruby_data_type(), myDataType, true);
107
116
  Data_Object<MyDataType> orig_data_object_foo(wrapped_foo);
108
117
  Data_Object<MyDataType> data_object_foo(orig_data_object_foo);
@@ -113,9 +122,9 @@ TESTCASE(copy_construct)
113
122
  ASSERT_EQUAL(myDataType, detail::unwrap<MyDataType>(wrapped_foo, Data_Type<MyDataType>::ruby_data_type(), false));
114
123
  }
115
124
 
116
- TESTCASE(move_construct)
125
+ TESTCASE(data_object_move_construct)
117
126
  {
118
- MyDataType* myDataType = new MyDataType;
127
+ MyDataType* myDataType = new MyDataType(42);
119
128
 
120
129
  Data_Object<MyDataType> wrapper1(myDataType);
121
130
  Data_Object<MyDataType> wrapper2(std::move(wrapper1));
@@ -124,12 +133,12 @@ TESTCASE(move_construct)
124
133
  ASSERT((wrapper1.get() == nullptr));
125
134
  }
126
135
 
127
- TESTCASE(move_assign)
136
+ TESTCASE(data_object_move_assign)
128
137
  {
129
- MyDataType* foo1 = new MyDataType;
138
+ MyDataType* foo1 = new MyDataType(42);
130
139
  Data_Object<MyDataType> wrapper1(foo1);
131
140
 
132
- MyDataType* foo2 = new MyDataType;
141
+ MyDataType* foo2 = new MyDataType(42);
133
142
  Data_Object<MyDataType> wrapper2(foo2);
134
143
 
135
144
  wrapper2 = std::move(wrapper1);
@@ -138,74 +147,119 @@ TESTCASE(move_assign)
138
147
  ASSERT((wrapper1.get() == nullptr));
139
148
  }
140
149
 
141
- TESTCASE(dereference)
150
+ TESTCASE(data_object_dereference)
142
151
  {
143
152
  Data_Type<MyDataType> rb_cFoo;
144
- MyDataType * myDataType = new MyDataType;
153
+ MyDataType * myDataType = new MyDataType(42);
145
154
  Data_Object<MyDataType> wrapped_foo(myDataType);
146
155
  ASSERT_EQUAL(myDataType, &*wrapped_foo);
147
156
  }
148
157
 
149
- TESTCASE(arrow)
158
+ TESTCASE(data_object_arrow)
150
159
  {
151
160
  Data_Type<MyDataType> rb_cFoo;
152
- MyDataType * myDataType = new MyDataType;
161
+ MyDataType * myDataType = new MyDataType(42);
153
162
  Data_Object<MyDataType> wrapped_foo(myDataType);
154
163
  ASSERT_EQUAL(42, myDataType->x);
155
164
  }
156
165
 
157
- TESTCASE(get)
166
+ TESTCASE(data_object_get)
158
167
  {
159
168
  Data_Type<MyDataType> rb_cFoo;
160
- MyDataType * myDataType = new MyDataType;
169
+ MyDataType * myDataType = new MyDataType(42);
161
170
  Data_Object<MyDataType> wrapped_foo(myDataType);
162
171
  ASSERT_EQUAL(myDataType, wrapped_foo.get());
163
172
  }
164
173
 
165
- TESTCASE(to_ruby)
174
+ TESTCASE(data_object_to_ruby)
166
175
  {
167
176
  Data_Type<MyDataType> rb_cFoo;
168
- MyDataType * myDataType = new MyDataType;
177
+ MyDataType * myDataType = new MyDataType(42);
169
178
  Data_Object<MyDataType> wrapped_foo(myDataType);
170
179
  ASSERT_EQUAL(String("MyDataType"), wrapped_foo.class_name());
171
180
  }
172
181
 
173
- TESTCASE(from_ruby)
182
+ TESTCASE(data_object_from_ruby)
174
183
  {
175
184
  Data_Type<MyDataType> rb_cFoo;
176
- MyDataType* myDataType = new MyDataType();
185
+ MyDataType* myDataType = new MyDataType(42);
177
186
  Data_Object<MyDataType> wrapped_foo(myDataType);
178
187
  ASSERT_EQUAL(myDataType, wrapped_foo.get());
179
188
  }
180
189
 
181
- TESTCASE(from_ruby_const_ref)
190
+ TESTCASE(data_object_from_ruby_const_ref)
182
191
  {
183
192
  Data_Type<MyDataType> rb_cFoo;
184
- MyDataType * myDataType = new MyDataType;
193
+ MyDataType * myDataType = new MyDataType(42);
185
194
  Data_Object<MyDataType> wrapped_foo(myDataType);
186
195
  ASSERT_EQUAL(myDataType->x, detail::From_Ruby<MyDataType const &>().convert(wrapped_foo).x);
187
196
  }
188
197
 
189
- TESTCASE(from_ruby_copy)
198
+ TESTCASE(data_object_from_ruby_copy)
190
199
  {
191
200
  Data_Type<MyDataType> rb_cFoo;
192
- MyDataType * myDataType = new MyDataType;
201
+ MyDataType * myDataType = new MyDataType(42);
193
202
  Data_Object<MyDataType> wrapped_foo(myDataType);
194
203
  ASSERT_EQUAL(myDataType->x, detail::From_Ruby<MyDataType>().convert(wrapped_foo).x);
195
204
  }
196
205
 
197
- TESTCASE(ruby_custom_mark)
206
+ TESTCASE(data_object_return_array)
207
+ {
208
+ define_buffer<MyDataType>();
209
+
210
+ Module m = define_module("DataObjectTest").
211
+ define_module_function("data_types", &dataTypes, Return().setArray()).
212
+ define_module_function("data_types_count", &dataTypesCount);
213
+
214
+ std::string code = R"(buffer = data_types
215
+ count = data_types_count
216
+ buffer.to_ary(count))";
217
+
218
+ Array dataTypes = m.module_eval(code);
219
+ ASSERT_EQUAL(3, dataTypes.size());
220
+
221
+ std::vector<MyDataType> vector = dataTypes.to_vector<MyDataType>();
222
+ ASSERT_EQUAL(1, vector[0].x);
223
+ ASSERT_EQUAL(2, vector[1].x);
224
+ ASSERT_EQUAL(3, vector[2].x);
225
+ }
226
+
227
+ TESTCASE(data_object_update_buffer)
228
+ {
229
+ define_buffer<MyDataType>();
230
+
231
+ Class c = define_class<MyDataType>("MyDataType")
232
+ .define_constructor(Constructor<MyDataType, int>());
233
+
234
+ Module m = define_module("DataObjectTest").
235
+ define_module_function("data_types", &dataTypes, Return().setArray()).
236
+ define_module_function("data_types_count", &dataTypesCount);
237
+
238
+ std::string code = R"(buffer = data_types
239
+ my_data_type = MyDataType.new(100)
240
+ buffer.size = 3
241
+ buffer[2] = my_data_type
242
+ buffer)";
243
+
244
+ Object result = m.module_eval(code);
245
+ Data_Object<Buffer<MyDataType>> dataObject(result);
246
+ Buffer<MyDataType>* buffer = dataObject.get();
247
+ MyDataType myDataType = buffer->get(2);
248
+ ASSERT_EQUAL(100, myDataType.x);
249
+ }
250
+
251
+ TESTCASE(data_object_ruby_custom_mark)
198
252
  {
199
253
  test_ruby_mark_called = false;
200
254
 
201
- MyDataType* myDataType = new MyDataType;
255
+ MyDataType* myDataType = new MyDataType(42);
202
256
  Data_Object<MyDataType> wrapped_foo(myDataType);
203
257
  rb_gc_start();
204
258
 
205
259
  ASSERT_EQUAL(true, test_ruby_mark_called);
206
260
  }
207
261
 
208
- TESTCASE(ruby_custom_free)
262
+ TESTCASE(data_object_ruby_custom_free)
209
263
  {
210
264
  test_ruby_mark_called = false;
211
265
  test_destructor_called = false;
@@ -213,7 +267,7 @@ TESTCASE(ruby_custom_free)
213
267
  {
214
268
  // Put this code in a block so wrapped_foo is destroyed at the end of it.
215
269
  // That will set its value field to Qnil allowing myDataType to be freed
216
- MyDataType* myDataType = new MyDataType;
270
+ MyDataType* myDataType = new MyDataType(42);
217
271
  Data_Object<MyDataType> wrapped_foo(myDataType, true);
218
272
 
219
273
  // Force a mark