rice 4.3.0 → 4.3.1

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.
@@ -1,102 +1,102 @@
1
- #include <iterator>
2
- #include <functional>
3
- #include <type_traits>
4
-
5
- #include "cpp_protect.hpp"
6
- #include "NativeRegistry.hpp"
7
-
8
- namespace Rice::detail
9
- {
10
- template <typename T, typename Iterator_Func_T>
11
- inline void NativeIterator<T, Iterator_Func_T>::define(VALUE klass, std::string method_name, Iterator_Func_T begin, Iterator_Func_T end)
12
- {
13
- // Tell Ruby to invoke the static method call on this class
14
- detail::protect(rb_define_method, klass, method_name.c_str(), (RUBY_METHOD_FUNC)&NativeIterator_T::call, 0);
15
-
16
- // Now create a NativeIterator instance and save it to the natives registry keyed on
17
- // Ruby klass and method id. There may be multiple NativeIterator instances
18
- // because the same C++ method could be mapped to multiple Ruby methods.
19
- NativeIterator_T* native = new NativeIterator_T(klass, method_name, begin, end);
20
- detail::Registries::instance.natives.add(klass, Identifier(method_name).id(), native);
21
- }
22
-
23
- template<typename T, typename Iterator_Func_T>
24
- inline VALUE NativeIterator<T, Iterator_Func_T>::call(VALUE self)
25
- {
26
- // Look up the native function based on the Ruby klass and method id
27
- NativeIterator_T* nativeIterator = detail::Registries::instance.natives.lookup<NativeIterator_T*>();
28
-
29
- return cpp_protect([&]
30
- {
31
- return nativeIterator->operator()(self);
32
- });
33
- }
34
-
35
- template <typename T, typename Iterator_Func_T>
36
- inline NativeIterator<T, Iterator_Func_T>::NativeIterator(VALUE klass, std::string method_name, Iterator_Func_T begin, Iterator_Func_T end) :
37
- klass_(klass), method_name_(method_name), begin_(begin), end_(end)
38
- {
39
- }
40
-
41
- template<typename T, typename Iterator_Func_T>
42
- inline VALUE NativeIterator<T, Iterator_Func_T>::createRubyEnumerator(VALUE self)
43
- {
44
- auto rb_size_function = [](VALUE recv, VALUE argv, VALUE eobj) -> VALUE
45
- {
46
- // Since we can't capture VALUE self from above (because then we can't send
47
- // this lambda to rb_enumeratorize_with_size), extract it from recv
48
- return cpp_protect([&]
49
- {
50
- // Get the iterator instance
51
- using Iter_T = NativeIterator<T, Iterator_Func_T>;
52
- // Class is easy
53
- VALUE klass = protect(rb_class_of, recv);
54
- // Read the method_id from an attribute we added to the enumerator instance
55
- ID method_id = protect(rb_ivar_get, eobj, rb_intern("rice_method"));
56
- Iter_T* iterator = detail::Registries::instance.natives.lookup<Iter_T*>(klass, method_id);
57
-
58
- // Get the wrapped C++ instance
59
- T* receiver = detail::From_Ruby<T*>().convert(recv);
60
-
61
- // Get the distance
62
- Iterator_T begin = std::invoke(iterator->begin_, *receiver);
63
- Iterator_T end = std::invoke(iterator->end_, *receiver);
64
- Difference_T distance = std::distance(begin, end);
65
-
66
- return detail::To_Ruby<Difference_T>().convert(distance);
67
- });
68
- };
69
-
70
- VALUE method_sym = Identifier(this->method_name_).to_sym();
71
- VALUE enumerator = protect(rb_enumeratorize_with_size, self, method_sym, 0, nullptr, rb_size_function);
72
-
73
- // Hack the enumerator object by storing name_ on the enumerator object so
74
- // the rb_size_function above has access to it
75
- ID method_id = Identifier(this->method_name_).id();
76
- protect(rb_ivar_set, enumerator, rb_intern("rice_method"), method_id);
77
-
78
- return enumerator;
79
- }
80
-
81
- template<typename T, typename Iterator_Func_T>
82
- inline VALUE NativeIterator<T, Iterator_Func_T>::operator()(VALUE self)
83
- {
84
- if (!protect(rb_block_given_p))
85
- {
86
- return createRubyEnumerator(self);
87
- }
88
- else
89
- {
90
- T* receiver = detail::From_Ruby<T*>().convert(self);
91
- Iterator_T it = std::invoke(this->begin_, *receiver);
92
- Iterator_T end = std::invoke(this->end_, *receiver);
93
-
94
- for (; it != end; ++it)
95
- {
96
- protect(rb_yield, detail::To_Ruby<Value_T&>().convert(*it));
97
- }
98
-
99
- return self;
100
- }
101
- }
1
+ #include <iterator>
2
+ #include <functional>
3
+ #include <type_traits>
4
+
5
+ #include "cpp_protect.hpp"
6
+ #include "NativeRegistry.hpp"
7
+
8
+ namespace Rice::detail
9
+ {
10
+ template <typename T, typename Iterator_Func_T>
11
+ inline void NativeIterator<T, Iterator_Func_T>::define(VALUE klass, std::string method_name, Iterator_Func_T begin, Iterator_Func_T end)
12
+ {
13
+ // Tell Ruby to invoke the static method call on this class
14
+ detail::protect(rb_define_method, klass, method_name.c_str(), (RUBY_METHOD_FUNC)&NativeIterator_T::call, 0);
15
+
16
+ // Now create a NativeIterator instance and save it to the natives registry keyed on
17
+ // Ruby klass and method id. There may be multiple NativeIterator instances
18
+ // because the same C++ method could be mapped to multiple Ruby methods.
19
+ NativeIterator_T* native = new NativeIterator_T(klass, method_name, begin, end);
20
+ detail::Registries::instance.natives.add(klass, Identifier(method_name).id(), native);
21
+ }
22
+
23
+ template<typename T, typename Iterator_Func_T>
24
+ inline VALUE NativeIterator<T, Iterator_Func_T>::call(VALUE self)
25
+ {
26
+ // Look up the native function based on the Ruby klass and method id
27
+ NativeIterator_T* nativeIterator = detail::Registries::instance.natives.lookup<NativeIterator_T*>();
28
+
29
+ return cpp_protect([&]
30
+ {
31
+ return nativeIterator->operator()(self);
32
+ });
33
+ }
34
+
35
+ template <typename T, typename Iterator_Func_T>
36
+ inline NativeIterator<T, Iterator_Func_T>::NativeIterator(VALUE klass, std::string method_name, Iterator_Func_T begin, Iterator_Func_T end) :
37
+ klass_(klass), method_name_(method_name), begin_(begin), end_(end)
38
+ {
39
+ }
40
+
41
+ template<typename T, typename Iterator_Func_T>
42
+ inline VALUE NativeIterator<T, Iterator_Func_T>::createRubyEnumerator(VALUE self)
43
+ {
44
+ auto rb_size_function = [](VALUE recv, VALUE argv, VALUE eobj) -> VALUE
45
+ {
46
+ // Since we can't capture VALUE self from above (because then we can't send
47
+ // this lambda to rb_enumeratorize_with_size), extract it from recv
48
+ return cpp_protect([&]
49
+ {
50
+ // Get the iterator instance
51
+ using Iter_T = NativeIterator<T, Iterator_Func_T>;
52
+ // Class is easy
53
+ VALUE klass = protect(rb_class_of, recv);
54
+ // Read the method_id from an attribute we added to the enumerator instance
55
+ ID method_id = protect(rb_ivar_get, eobj, rb_intern("rice_method"));
56
+ Iter_T* iterator = detail::Registries::instance.natives.lookup<Iter_T*>(klass, method_id);
57
+
58
+ // Get the wrapped C++ instance
59
+ T* receiver = detail::From_Ruby<T*>().convert(recv);
60
+
61
+ // Get the distance
62
+ Iterator_T begin = std::invoke(iterator->begin_, *receiver);
63
+ Iterator_T end = std::invoke(iterator->end_, *receiver);
64
+ Difference_T distance = std::distance(begin, end);
65
+
66
+ return detail::To_Ruby<Difference_T>().convert(distance);
67
+ });
68
+ };
69
+
70
+ VALUE method_sym = Identifier(this->method_name_).to_sym();
71
+ VALUE enumerator = protect(rb_enumeratorize_with_size, self, method_sym, 0, nullptr, rb_size_function);
72
+
73
+ // Hack the enumerator object by storing name_ on the enumerator object so
74
+ // the rb_size_function above has access to it
75
+ ID method_id = Identifier(this->method_name_).id();
76
+ protect(rb_ivar_set, enumerator, rb_intern("rice_method"), method_id);
77
+
78
+ return enumerator;
79
+ }
80
+
81
+ template<typename T, typename Iterator_Func_T>
82
+ inline VALUE NativeIterator<T, Iterator_Func_T>::operator()(VALUE self)
83
+ {
84
+ if (!protect(rb_block_given_p))
85
+ {
86
+ return createRubyEnumerator(self);
87
+ }
88
+ else
89
+ {
90
+ T* receiver = detail::From_Ruby<T*>().convert(self);
91
+ Iterator_T it = std::invoke(this->begin_, *receiver);
92
+ Iterator_T end = std::invoke(this->end_, *receiver);
93
+
94
+ for (; it != end; ++it)
95
+ {
96
+ protect(rb_yield, detail::To_Ruby<Value_T&>().convert(*it));
97
+ }
98
+
99
+ return self;
100
+ }
101
+ }
102
102
  }