forked from enlightenment/efl
cxx: remove compilation warnings in C++ code, from both gcc and clang
Summary: Remove almost all the compilation warnings from C++ code. Only explicit warnings using the `#warning` preprocessor directive remain. Some warnings had to be suppressed with `#pragma` directives because the behavior they were warning about is intended in some specific places. Code comments were added in such situations. Added a generator that creates `#pragma` directives in order to suppress warnings in all generated C++ headers. Currently `-Wignored-qualifiers` is the only warning category being suppressed. The innocuous const qualifiers that it points are inoffensive and have no effect in compilation at all. They are also hard to track in generation since they can emerge from different types in many places. To ease the generation of the warning suppressors an utility constructor was added to `efl::eolian::grammar::attributes::unused_type`. Add constructors to `eolian_mono::class_context` to default initialize its internal string and avoid field initialization warnings. Test Plan: `meson test` Reviewers: lauromoura, felipealmeida, zmike, segfaultxavi Reviewed By: zmike Subscribers: cedric, #reviewers, #committers Tags: #efl_language_bindings Differential Revision: https://phab.enlightenment.org/D9275
This commit is contained in:
parent
c001a8146b
commit
b1e44484a5
|
@ -1,5 +1,5 @@
|
|||
#ifndef EOLIAN_MONO_EVENTS_HH
|
||||
#define EOLINA_MONO_EVENTS_HH
|
||||
#define EOLIAN_MONO_EVENTS_HH
|
||||
|
||||
#include <iterator>
|
||||
|
||||
|
|
|
@ -21,6 +21,16 @@ struct class_context
|
|||
};
|
||||
wrapper_kind current_wrapper_kind;
|
||||
std::string name;
|
||||
|
||||
class_context(wrapper_kind current_wrapper_kind)
|
||||
: current_wrapper_kind(current_wrapper_kind)
|
||||
, name()
|
||||
{}
|
||||
|
||||
class_context(wrapper_kind current_wrapper_kind, std::string const& name)
|
||||
: current_wrapper_kind(current_wrapper_kind)
|
||||
, name(name)
|
||||
{}
|
||||
};
|
||||
|
||||
struct indentation_context
|
||||
|
|
|
@ -183,6 +183,7 @@ struct marshall_type_visitor_generate
|
|||
, is_out
|
||||
, is_return
|
||||
, is_ptr
|
||||
, false
|
||||
, is_special_subtype
|
||||
}(r);
|
||||
}
|
||||
|
@ -195,6 +196,7 @@ struct marshall_type_visitor_generate
|
|||
, is_out
|
||||
, is_return
|
||||
, is_ptr
|
||||
, false
|
||||
, is_special_subtype
|
||||
}(regular);
|
||||
}
|
||||
|
@ -208,6 +210,7 @@ struct marshall_type_visitor_generate
|
|||
, is_out
|
||||
, is_return
|
||||
, is_ptr
|
||||
, false
|
||||
, is_special_subtype
|
||||
}(klass_name);
|
||||
}
|
||||
|
@ -253,7 +256,7 @@ struct marshall_type_visitor_generate
|
|||
auto default_match = [&] (attributes::complex_type_def const& complex)
|
||||
{
|
||||
regular_type_def no_pointer_regular = complex.outer;
|
||||
return visitor_type{sink, context, c_type, false}(no_pointer_regular)
|
||||
return visitor_type{sink, context, c_type, false, false, false, false}(no_pointer_regular)
|
||||
&& as_generator("<" << (type(false, false, true) % ", ") << ">").generate(sink, complex.subtypes, *context);
|
||||
};
|
||||
|
||||
|
@ -286,6 +289,7 @@ struct marshall_type_visitor_generate
|
|||
, is_out
|
||||
, is_return
|
||||
, is_ptr
|
||||
, false
|
||||
, is_special_subtype
|
||||
}(complex);
|
||||
}
|
||||
|
|
|
@ -412,7 +412,7 @@ struct visitor_generate
|
|||
// pointers.swap(no_pointer_regular.pointers);
|
||||
// if(is_out)
|
||||
// pointers.push_back({{attributes::qualifier_info::is_none, {}}, true});
|
||||
return visitor_type{sink, context, c_type, false}(no_pointer_regular)
|
||||
return visitor_type{sink, context, c_type, false, false, false, false, false}(no_pointer_regular)
|
||||
&& as_generator("<" << (type(false, false, true) % ", ") << ">").generate(sink, complex.subtypes, *context)
|
||||
;
|
||||
// && detail::generate_pointers(sink, pointers, *context, false);
|
||||
|
|
|
@ -387,7 +387,15 @@ private:
|
|||
void _construct(U&& object)
|
||||
{
|
||||
assert(!is_engaged());
|
||||
// NOTE: the buffer memory is intended to be in an
|
||||
// uninitialized state here.
|
||||
// So this warning can be disabled.
|
||||
#pragma GCC diagnostic push
|
||||
#ifndef __clang__
|
||||
#pragma GCC diagnostic ignored "-Wmaybe-uninitialized"
|
||||
#endif
|
||||
new (&buffer) T(std::forward<U>(object));
|
||||
#pragma GCC diagnostic pop
|
||||
engaged = true;
|
||||
}
|
||||
|
||||
|
|
|
@ -293,11 +293,23 @@ void _create_methods_specification_impl(Method const& method, Eldbus_Method2& el
|
|||
|
||||
eldbus::_fill_methods(*out_params, method.outs);
|
||||
|
||||
// NOTE: C pointer magic performed under the hood requires this conversion
|
||||
// between incompatible function pointer types.
|
||||
// C++ always raises a warning for such conversions, so this warning
|
||||
// can be disabled just here.
|
||||
#pragma GCC diagnostic push
|
||||
#ifndef __clang__
|
||||
#pragma GCC diagnostic ignored "-Wcast-function-type"
|
||||
#endif
|
||||
Eldbus_Method_Cb method_cb =
|
||||
reinterpret_cast<Eldbus_Method_Cb>
|
||||
(static_cast<Eldbus_Method_Data_Cb>
|
||||
(&_method_callback<typename Method::function_type
|
||||
, typename Method::ins_type, typename Method::outs_type>));
|
||||
#pragma GCC diagnostic pop
|
||||
|
||||
eldbus_method = {{method.name, &(*in_params)[0], &(*out_params)[0]
|
||||
, reinterpret_cast<Eldbus_Method_Cb>
|
||||
(static_cast<Eldbus_Method_Data_Cb>
|
||||
(&_method_callback<typename Method::function_type
|
||||
, typename Method::ins_type, typename Method::outs_type>))
|
||||
, method_cb
|
||||
, ELDBUS_METHOD_FLAG_HAS_DATA}
|
||||
, new std::tuple<typename Method::function_type
|
||||
, typename Method::ins_type, typename Method::outs_type
|
||||
|
|
|
@ -9,7 +9,10 @@ namespace efl { namespace eolian { namespace grammar {
|
|||
|
||||
namespace attributes {
|
||||
|
||||
struct unused_type {};
|
||||
struct unused_type {
|
||||
unused_type() = default;
|
||||
unused_type(std::nullptr_t) {}
|
||||
};
|
||||
unused_type const unused = {};
|
||||
|
||||
template <int N, typename Tuple, typename Enable = void>
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
#include "grammar/type_impl.hpp"
|
||||
#include "grammar/attribute_reorder.hpp"
|
||||
#include "grammar/part_implementation.hpp"
|
||||
#include "grammar/ignore_warning.hpp"
|
||||
|
||||
namespace efl { namespace eolian { namespace grammar {
|
||||
|
||||
|
@ -42,6 +43,9 @@ struct class_implementation_generator
|
|||
.generate(sink, std::make_tuple(cls.namespaces, cls.cxx_name), add_lower_case_context(ctx)))
|
||||
return false;
|
||||
|
||||
if(!as_generator(ignore_warning_begin).generate(sink, nullptr, ctx))
|
||||
return false;
|
||||
|
||||
#ifndef USE_EOCXX_INHERIT_ONLY
|
||||
if(!as_generator(
|
||||
(namespaces
|
||||
|
@ -71,6 +75,9 @@ struct class_implementation_generator
|
|||
)).generate(sink, std::make_tuple(cls.namespaces, cls.functions, cpp_namespaces, cls.cxx_name, cls.parts), ctx))
|
||||
return false;
|
||||
|
||||
if(!as_generator(ignore_warning_end).generate(sink, nullptr, ctx))
|
||||
return false;
|
||||
|
||||
if(!as_generator("#endif\n").generate(sink, std::make_tuple(), ctx))
|
||||
return false;
|
||||
|
||||
|
|
|
@ -46,7 +46,7 @@ struct is_eager_generator<T volatile const&> : is_eager_generator<T> {};
|
|||
// struct is_generator<T> : is_eager_generator<T> {};
|
||||
|
||||
template <typename G, typename Enable = typename std::enable_if<is_eager_generator<G>::value>::type>
|
||||
G as_generator(G&& g) { return g; }
|
||||
G as_generator(G g) { return g; }
|
||||
|
||||
|
||||
} } }
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
#include "class_definition.hpp"
|
||||
#include "class_declaration.hpp"
|
||||
#include "implementation_include_directive.hpp"
|
||||
#include "ignore_warning.hpp"
|
||||
|
||||
namespace efl { namespace eolian { namespace grammar {
|
||||
|
||||
|
@ -27,11 +28,13 @@ auto class_header =
|
|||
<< *class_declaration // sequence<class> | class
|
||||
<< *class_forward_declaration // sequence<class> | class
|
||||
<< string // extra header <string>
|
||||
<< ignore_warning_begin
|
||||
<< "\nnamespace eo_cxx {\n"
|
||||
<< *base_class_definition // sequence<class> | class
|
||||
<< "}\n"
|
||||
<< *class_definition // sequence<class> | class
|
||||
// << *implementation_include_directive
|
||||
<< ignore_warning_end
|
||||
]
|
||||
;
|
||||
|
||||
|
|
|
@ -0,0 +1,48 @@
|
|||
#ifndef EOLIAN_CXX_IGNORE_WARNING_HH
|
||||
#define EOLIAN_CXX_IGNORE_WARNING_HH
|
||||
|
||||
#include "grammar/generator.hpp"
|
||||
|
||||
namespace efl { namespace eolian { namespace grammar {
|
||||
|
||||
struct ignore_warning_begin_generator
|
||||
{
|
||||
template <typename OutputIterator, typename Context>
|
||||
bool generate(OutputIterator sink, attributes::unused_type, Context const& context) const
|
||||
{
|
||||
return as_generator(
|
||||
"\n"
|
||||
"#pragma GCC diagnostic push\n"
|
||||
"#pragma GCC diagnostic ignored \"-Wignored-qualifiers\"\n"
|
||||
"\n"
|
||||
).generate(sink, nullptr, context);
|
||||
}
|
||||
};
|
||||
|
||||
struct ignore_warning_end_generator
|
||||
{
|
||||
template <typename OutputIterator, typename Context>
|
||||
bool generate(OutputIterator sink, attributes::unused_type, Context const& context) const
|
||||
{
|
||||
return as_generator(
|
||||
"\n#pragma GCC diagnostic pop\n\n"
|
||||
).generate(sink, nullptr, context);
|
||||
}
|
||||
};
|
||||
|
||||
template <>
|
||||
struct is_eager_generator<ignore_warning_begin_generator> : std::true_type {};
|
||||
template <>
|
||||
struct is_generator<ignore_warning_begin_generator> : std::true_type {};
|
||||
|
||||
template <>
|
||||
struct is_eager_generator<ignore_warning_end_generator> : std::true_type {};
|
||||
template <>
|
||||
struct is_generator<ignore_warning_end_generator> : std::true_type {};
|
||||
|
||||
ignore_warning_begin_generator constexpr ignore_warning_begin = {};
|
||||
ignore_warning_end_generator constexpr ignore_warning_end = {};
|
||||
|
||||
} } }
|
||||
|
||||
#endif
|
|
@ -348,7 +348,7 @@ struct visitor_generate
|
|||
// pointers.swap(no_pointer_regular.pointers);
|
||||
// if(is_out)
|
||||
// pointers.push_back({{attributes::qualifier_info::is_none, {}}, true});
|
||||
return visitor_type{sink, context, c_type, false}(no_pointer_regular)
|
||||
return visitor_type{sink, context, c_type, false, false}(no_pointer_regular)
|
||||
&& as_generator("<" << (type % ", ") << ">").generate(sink, complex.subtypes, *context)
|
||||
;
|
||||
// && detail::generate_pointers(sink, pointers, *context, false);
|
||||
|
|
|
@ -126,7 +126,6 @@ ephysics_quaternion_euler_set(EPhysics_Quaternion *quat, double yaw, double pitc
|
|||
return;
|
||||
}
|
||||
|
||||
bt_quat = btQuaternion();
|
||||
bt_quat.setEuler(yaw / RAD_TO_DEG, pitch / RAD_TO_DEG, roll / RAD_TO_DEG);
|
||||
_ephysics_quaternion_update(quat, &bt_quat);
|
||||
}
|
||||
|
|
|
@ -14,7 +14,7 @@ void call_async(efl::eina::mutex& mutex, efl::eina::condition_variable& cond, in
|
|||
{
|
||||
efl::ecore::main_loop_thread_safe_call_async
|
||||
(
|
||||
[&mutex,&cond,&done]
|
||||
[&mutex,&done]
|
||||
{
|
||||
std::cout << "yeah" << std::endl;
|
||||
efl::eina::unique_lock<efl::eina::mutex> l(mutex);
|
||||
|
|
|
@ -102,7 +102,14 @@ EFL_START_TEST(eina_cxx_optional_assignment)
|
|||
|
||||
assert(!a); assert(b); assert(c); assert(d);
|
||||
|
||||
// NOTE: resistance to self assignment is exactly what is being tested here,
|
||||
// so this compilation warning can be suppressed.
|
||||
#pragma GCC diagnostic push
|
||||
#ifdef __clang__
|
||||
#pragma GCC diagnostic ignored "-Wself-assign-overloaded"
|
||||
#endif
|
||||
a = a;
|
||||
#pragma GCC diagnostic pop
|
||||
ck_assert(a == a);
|
||||
ck_assert(!a);
|
||||
|
||||
|
|
|
@ -385,7 +385,7 @@ EFL_START_TEST(eina_cxx_ptrlist_constructors)
|
|||
efl::eina::list<wrapper> list2(10, w1);
|
||||
ck_assert(list2.size() == 10);
|
||||
ck_assert(std::find_if(list2.begin(), list2.end()
|
||||
, [&list2, w2] (wrapper i)
|
||||
, [w2] (wrapper i)
|
||||
{
|
||||
return i == w2;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue