Bug #11962
closedRuby 2.3.0 causing compile failure on extensions using a C++ compiler
Description
Hello,
I'm a contributor with the SciRuby foundation, and we have a gem called nmatrix, which is a ruby gem for linear algebra processing in Ruby.
For representing different types of data, nmatrix makes heavy use of C++ templates, which requires compilation with g++. Currently we wrap the code that defines ruby functions at C level in an extern "C" {} block in a .cpp file and use g++ to compile the file as a whole.
Upgrading to ruby 2.3.0 has caused a problem because of this change implemented in the internals of the ruby C API.
As specified in the GCC docs (https://gcc.gnu.org/onlinedocs/gcc/Other-Builtins.html) the function "__builtin_choose_expr" (that has been introduced in the latest Ruby C API) is available only for C. Thus the change is rendering our C++ extensions useless.
You can see the compile error being caused in nmatrix here: https://github.com/SciRuby/nmatrix/issues/429
I have come up with a temporary fix for this, but its only patch work and will need to be done by every single extension employing a C++ compiler.
Looking forward to a positive response from you.
Updated by hsbt (Hiroshi SHIBATA) almost 10 years ago
- Assignee set to nobu (Nobuyoshi Nakada)
Updated by mrkn (Kenta Murata) almost 10 years ago
Can I fix it by the following change?
diff --git a/include/ruby/ruby.h b/include/ruby/ruby.h
index 7aabf5b..72523c6 100644
--- a/include/ruby/ruby.h
+++ b/include/ruby/ruby.h
@@ -874,7 +874,7 @@ struct RBasic {
VALUE rb_obj_hide(VALUE obj);
VALUE rb_obj_reveal(VALUE obj, VALUE klass); /* do not use this API to change klass information */
-#if defined(HAVE_BUILTIN___BUILTIN_CHOOSE_EXPR_CONSTANT_P)
+#if defined(HAVE_BUILTIN___BUILTIN_CHOOSE_EXPR_CONSTANT_P) && !defined(__cplusplus)
# define RB_OBJ_WB_UNPROTECT_FOR(type, obj) \
__extension__( \
__builtin_choose_expr( \
Updated by mrkn (Kenta Murata) almost 10 years ago
I found the other place to be fixed.
The following patch is the complete version.
diff --git a/include/ruby/ruby.h b/include/ruby/ruby.h
index 7aabf5b..a2f42c8 100644
--- a/include/ruby/ruby.h
+++ b/include/ruby/ruby.h
@@ -620,7 +620,7 @@ int ruby_safe_level_2_warning(void) __attribute__((warning("$SAFE=2 to 4 are obs
# ifdef RUBY_EXPORT
# define ruby_safe_level_2_warning() ruby_safe_level_2_error()
# endif
-#if defined(HAVE_BUILTIN___BUILTIN_CHOOSE_EXPR_CONSTANT_P)
+#if defined(HAVE_BUILTIN___BUILTIN_CHOOSE_EXPR_CONSTANT_P) && !defined(__cplusplus)
# define RUBY_SAFE_LEVEL_INVALID_P(level) \
__extension__(\
__builtin_choose_expr(\
@@ -874,7 +874,7 @@ struct RBasic {
VALUE rb_obj_hide(VALUE obj);
VALUE rb_obj_reveal(VALUE obj, VALUE klass); /* do not use this API to change klass information */
-#if defined(HAVE_BUILTIN___BUILTIN_CHOOSE_EXPR_CONSTANT_P)
+#if defined(HAVE_BUILTIN___BUILTIN_CHOOSE_EXPR_CONSTANT_P) && !defined(__cplusplus)
# define RB_OBJ_WB_UNPROTECT_FOR(type, obj) \
__extension__( \
__builtin_choose_expr( \
@@ -1376,7 +1376,7 @@ rb_data_object_wrap_warning(VALUE klass, void *ptr, RUBY_DATA_FUNC mark, RUBY_DA
return rb_data_object_wrap(klass, ptr, mark, free);
}
-#if defined(HAVE_BUILTIN___BUILTIN_CHOOSE_EXPR_CONSTANT_P)
+#if defined(HAVE_BUILTIN___BUILTIN_CHOOSE_EXPR_CONSTANT_P) && !defined(__cplusplus)
#define rb_data_object_wrap_warning(klass, ptr, mark, free) \
__extension__( \
__builtin_choose_expr( \
diff --git a/include/ruby/st.h b/include/ruby/st.h
index 190bad2..97c08b1 100644
--- a/include/ruby/st.h
+++ b/include/ruby/st.h
@@ -59,7 +59,7 @@ struct st_hash_type {
#define ST_INDEX_BITS (sizeof(st_index_t) * CHAR_BIT)
-#if defined(HAVE_BUILTIN___BUILTIN_CHOOSE_EXPR) && defined(HAVE_BUILTIN___BUILTIN_TYPES_COMPATIBLE_P)
+#if defined(HAVE_BUILTIN___BUILTIN_CHOOSE_EXPR) && defined(HAVE_BUILTIN___BUILTIN_TYPES_COMPATIBLE_P) && !defined(__cplusplus)
# define ST_DATA_COMPATIBLE_P(type) \
__builtin_choose_expr(__builtin_types_compatible_p(type, st_data_t), 1, 0)
#else
Updated by mrkn (Kenta Murata) almost 10 years ago
- Status changed from Open to Closed
Applied in changeset r53455.
- ruby.h: undef HAVE_BUILTIN___BUILTIN_CHOOSE_EXPR_CONSTANT_P
and HAVE_BUILTIN___BUILTIN_TYPES_COMPATIBLE_P on C++.
[ruby-core:72736] [Bug #11962]
Updated by vo.x (Vit Ondruch) almost 10 years ago
- Backport changed from 2.0.0: UNKNOWN, 2.1: UNKNOWN, 2.2: UNKNOWN, 2.3: UNKNOWN to 2.0.0: UNKNOWN, 2.1: UNKNOWN, 2.2: UNKNOWN, 2.3: REQUIRED
Updated by vo.x (Vit Ondruch) almost 10 years ago
BTW this causes issues compiling SWIG:
Updated by terceiro (Antonio Terceiro) almost 10 years ago
We are trying to transition Debian unstable to ruby2.3, it would be very helpful to have this applied to the 2.3 branch.
Updated by usa (Usaku NAKAMURA) almost 10 years ago
- Backport changed from 2.0.0: UNKNOWN, 2.1: UNKNOWN, 2.2: UNKNOWN, 2.3: REQUIRED to 2.1: DONTNEED, 2.2: REQUIRED, 2.3: REQUIRED
Updated by nagachika (Tomoyuki Chikanaga) over 9 years ago
- Backport changed from 2.1: DONTNEED, 2.2: REQUIRED, 2.3: REQUIRED to 2.1: DONTNEED, 2.2: DONE, 2.3: REQUIRED
Backported into ruby_2_2 branch at r54315.
Updated by naruse (Yui NARUSE) over 9 years ago
- Backport changed from 2.1: DONTNEED, 2.2: DONE, 2.3: REQUIRED to 2.1: DONTNEED, 2.2: DONE, 2.3: DONE
ruby_2_3 r54364 merged revision(s) 53455.