The C standard is written to assume that pointers to different object types, and especially pointers to function as opposed to object types, might have different representations. That's why, in general, you don't want to intermix pointers, or if you do a modern compiler will warn you, and if you want to silence the warnings you typically use an explicit cast.
dlsym
, on the other hand, by its very existence assumes that all pointers are pretty much the same, because it's supposed to be able to return you any pointer to any datatype -- object or function -- in your object file.
In other words, code that uses dlsym
is inherently nonportable, in the sense that it's not widely portable, in the sense that it's portable "only" to those machines where all pointers are safely interconvertible. (Which is of course virtually all of the popular machines today.)
So, yes, you'll need to cast the pointers to silence the warnings, and in doing so you may be making your code less portable to machines where all pointers aren't the same (and where the warnings, if unsilenced, would correctly inform you that your code won't work), but dlsym
is never going to work (or even exist in its current form) on those machines, anyway.
(And if gcc -pedantic
warns you about even an explicit cast from void *
to a function pointer type, there's not much you can do except switch to a different version of gcc
, or of course not use -pedantic
.)
Addendum: My answer made it sound like converting between pointers to different types of data might be an issue, but that's generally no problem. Type void *
is well defined to be the generic data pointer: it's what malloc
returns, and it's defined to be quietly convertible to any object pointer type -- that is, you're not supposed to even need a cast. So it's almost a fine choice for the return type of dlsym
, except for the wee problem of function pointers. malloc
never has this problem (you'd hardly ever try to malloc a pointer to a function), while dlsym
always has this problem (the symbols you're generally trying to access in dynamically-loaded object files are code at least as often as they're data). But function pointers are what void *
isn't guaranteed to convert to, so you're very likely to get warnings, which is why you need the casts, and you might get warnings under -pedantic
even with the casts.
dlsym()
a bit opaque in this regard but if someone can enlighten me on the manpage that would also help. – Hassockgcc
andclang
complain. – Hassockdlfsym
for that exact purpose (but that was not accepted). – Kuratypedef
signatures, like here – Kura