Skip to content

Commit ecfa7c2

Browse files
committed
slot, signal: Avoid compiler warnings from function pointer conversions
gcc8 -Wextra prints a warning when reinterpret_cast is used for conversion between different types of function pointers. Avoid that by adding sigc::internal::bitwise_equivalent_cast<>() with a union with members of the two types of function pointers. Fixes libsigcplusplus#1
1 parent 1aabb89 commit ecfa7c2

File tree

2 files changed

+24
-5
lines changed

2 files changed

+24
-5
lines changed

sigc++/functors/slot.h

Lines changed: 21 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,25 @@ namespace sigc
3333
namespace internal
3434
{
3535

36+
// Conversion between different types of function pointers with
37+
// reinterpret_cast can make gcc8 print a warning.
38+
// https://github.com/libsigcplusplus/libsigcplusplus/issues/1
39+
/** Returns the supplied bit pattern, interpreted as another type.
40+
*
41+
* When reinterpret_cast causes a compiler warning or error, this function
42+
* may work. Intended mainly for conversion between different types of pointers.
43+
*/
44+
template <typename out_type, typename in_type>
45+
inline out_type bitwise_equivalent_cast(in_type in)
46+
{
47+
union {
48+
in_type in;
49+
out_type out;
50+
} u;
51+
u.in = in;
52+
return u.out;
53+
}
54+
3655
/** A typed slot_rep.
3756
* A typed slot_rep holds a functor that can be invoked from
3857
* slot::operator()(). visit_each() is used to visit the functor's
@@ -134,7 +153,7 @@ struct slot_call
134153
/** Forms a function pointer from call_it().
135154
* @return A function pointer formed from call_it().
136155
*/
137-
static hook address() { return reinterpret_cast<hook>(&call_it); }
156+
static hook address() { return bitwise_equivalent_cast<hook>(&call_it); }
138157
};
139158

140159
} /* namespace internal */
@@ -192,7 +211,7 @@ class slot<T_return(T_arg...)> : public slot_base
192211
inline T_return operator()(type_trait_take_t<T_arg>... a) const
193212
{
194213
if (!empty() && !blocked()) {
195-
return std::invoke(reinterpret_cast<call_type>(slot_base::rep_->call_), slot_base::rep_, a...);
214+
return std::invoke(internal::bitwise_equivalent_cast<call_type>(slot_base::rep_->call_), slot_base::rep_, a...);
196215
}
197216

198217
return T_return();

sigc++/signal.h

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -322,12 +322,12 @@ struct signal_emit<T_return, void, T_arg...>
322322
return T_return();
323323
}
324324

325-
r_ = (reinterpret_cast<call_type>(it->rep_->call_))(it->rep_, a...);
325+
r_ = (bitwise_equivalent_cast<call_type>(it->rep_->call_))(it->rep_, a...);
326326
for (++it; it != slots.end(); ++it)
327327
{
328328
if (it->empty() || it->blocked())
329329
continue;
330-
r_ = (reinterpret_cast<call_type>(it->rep_->call_))(it->rep_, a...);
330+
r_ = (bitwise_equivalent_cast<call_type>(it->rep_->call_))(it->rep_, a...);
331331
}
332332
}
333333

@@ -365,7 +365,7 @@ struct signal_emit<void, void, T_arg...>
365365
if (slot.empty() || slot.blocked())
366366
continue;
367367

368-
(reinterpret_cast<call_type>(slot.rep_->call_))(slot.rep_, a...);
368+
(bitwise_equivalent_cast<call_type>(slot.rep_->call_))(slot.rep_, a...);
369369
}
370370
}
371371
};

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy