Take the 2-minute tour ×
Stack Overflow is a question and answer site for professional and enthusiast programmers. It's 100% free, no registration required.

I realized from this FAQ entry that one cannot convert a pointer to member function to/from void*. The reason being pointers to members are not memory addresses exactly like pointers to data! Why so? Please help me get clarified. And this isn't necessarily with member functions but any normal C functions as well, isn't?

share|improve this question
    
IMHO - Pointers to functions in C++ is a bad idea since there are better alternatives. (virtual functions and inheritance) –  Ed Heal 12 hours ago
3  
Check the next FAQ entry Can I convert a pointer-to-function to a void*? –  jsantander 12 hours ago
1  
Also IMHO using void * is also a bad idea in both C and C++ –  Ed Heal 12 hours ago
    
@EdHeal, In C it can be the only way to achieve certain kind of polymorphism. –  Jefffrey 12 hours ago
    
@Jefffrey - I agree but it is best avoided –  Ed Heal 12 hours ago
show 5 more comments

2 Answers

up vote 10 down vote accepted

pointers to members are not memory addresses exactly like pointers to data! Why so?

Pointers to member functions need to indicate whether the function is virtual, and allow virtual dispatch (perhaps by specifying the index into the vtable, rather than the address of a specific function) if so. This makes them more complicated than just an address.

And this isn't necessarily with member functions but any normal C functions as well, isn't?

Pointers to "normal" (non-member) functions may be converted to object pointers, but not portably. Quoting the standard:

C++11 5.2.10/8 Converting a function pointer to an object pointer type or vice versa is conditionally-supported. The meaning of such a conversion is implementation-defined, [...]

On many platforms, a (non-member) function pointer is simply a memory address, and the conversion is well-defined. Some platforms have more exotic memory architectures - for example, separate memory spaces for instructions and data - and the conversion may not be allowed on those platforms.

share|improve this answer
    
Separate spaces for functions and data makes sense. But still, all entities should resolve into one address, isn't? Why prohibit conversions into address where functions are located? –  Prabhu 12 hours ago
    
@Prabhu: because you assume that a pointer to member-function points into the function space, but it is not necessarily so. To implement support for virtual pointers and virtual inheritance they might carry data. –  Matthieu M. 12 hours ago
    
@Prabhu: "all entities should resolve into one address" - not if there are separate address spaces for instructions and data. An address in instruction space is not usable as an address in data space, so should not be convertible to one. –  Mike Seymour 12 hours ago
    
Your question appears to be about pointers to member functions rather than just members - that is not clear from the title. –  Clifford 11 hours ago
1  
@Prabhu, most microcontrollers follow the Harvard model of having separate program and data address spaces. The program address space is usually linear but the data address space is often implemented using bank switching. Therefore a pointer into the data space has a completely different representation than a pointer into the address space with the former being complex objects and not simply numbers. –  Hristo Iliev 8 hours ago
add comment

In the C++ standard

As the next FAQ says:

The language does not require functions and data to be in the same address space, so, by way of example and not limitation, on architectures that have them in different address spaces, the two different pointer types will not be comparable.

In §5.2.10/8 (of N3936 specifically) the standard specifies that this is indeed implementation defined:

Converting a function pointer to an object pointer type or vice versa is conditionally-supported. The meaning of such a conversion is implementation-defined, except that if an implementation supports conversions in both directions, converting a prvalue of one type to the other type and back, possibly with different cv- qualification, shall yield the original pointer value.

Here the behavior is well specified.

In the C standard

The C standard doesn't appear to contemplate the conversion from a function pointer to an object pointer. In fact it barely draws a line between them.

It just states, at §6.3.2.3/8, that:

A pointer to a function of one type may be converted to a pointer to a function of another type and back again; the result shall compare equal to the original pointer. If a converted pointer is used to call a function whose type is not compatible with the referenced type, the behavior is undefined.

At this point the behavior almost seems to be unspecified.

And then later in §6.5.9/6:

Two pointers compare equal if and only if both are null pointers, both are pointers to the same object (including a pointer to an object and a subobject at its beginning) or function, both are pointers to one past the last element of the same array object, or one is a pointer to one past the end of one array object and the other is a pointer to the start of a different array object that happens to immediately follow the first array object in the address space.

Here we can see the only trace of an actual difference in:

Two pointers compare equal if and only if both are [..] pointers to the same object (..) or function [..].

The why

As for the "why", it appears to be dependent on the fact that some architectures simply have functions and objects in two address space.

share|improve this answer
1  
In some x86-16 memory models, data and function pointers could even be different sizes. –  dan04 6 hours ago
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.