1

Possible Duplicate:
When does invoking a member function on a null instance result in undefined behavior?

The person in this question failed to create a pointer to an object using 'new', an then used this wild pointer to call a member function on the object.

The program fails when a member-variable is accessed (at myPoint[i].x = xData;).

Why does it fail at that location and not earlier?

Community
  • 1
  • 1
slashmais
  • 7,069
  • 9
  • 54
  • 80
  • 4
    Please understand that C++ makes **no statement whatsoever** about the behavior of such a program. You are asking, instead, about a particular implementation of C++, that is, "why does a specific compiler running on a specific OS do that?" – Robᵩ Oct 26 '12 at 17:11

3 Answers3

3

The line in question is the first position where this is referenced.

Dabbler
  • 9,733
  • 5
  • 41
  • 64
  • Why does it get to `setPoint` at all? In `main` .. `mclass->setPoint();` – slashmais Oct 26 '12 at 17:12
  • 1
    When you call a C++ method, the `this` pointer is passed as an argument behind the scenes. Apart from that it's pretty much a regular function call. In his case the `this` pointer is uninitialized (or NULL in the "best" case), and when the function dereferences the pointer, an access violation occurs. – Dabbler Oct 26 '12 at 17:18
1

And why not? Standard say that this program has undefined behavior, but in C++ we have 3 kind of functions in a class:

// 1) static functions
class test {
public:
    static void foo( int n );
};

In this example foo is like a global function with same signature, but C++ have a different rule for access check and name of it.

// 2) normal member functions
class test {
public:
    void foo( int n );
};

In almost all compilers this function is same as a a free function with signature void foo(foo* this, int n) and this is not an error to call this function with an invalid this unless you access this in the function that in that case function possibly generate segmentation fault or even worse, change some unexpected point of your memory.

// 3) virtual functions
class test {
public:
    virtual void foo( int n );
};

In this case class test contain an extra invisible member that usually called vtable and contain one pointer to implementation of each virtual function of the class and using this technique C++ can have late binding at runtime, so in this case when you call foo compiler write something like

this->vtable[foo_index]( this, n );

so in this case invalid this immediately show itself and possibly generate errors like segmentation fault or invalid instruction, since you access this at point of call. So as you see in almost all implementation you can have a member function that called through an invalid this pointer and never generate any error(if you never access this in the function), but it can't be virtual.

But remember what explained above completely depend on your compiler, but almost all compilers implement it like above.

BigBoss
  • 6,904
  • 2
  • 23
  • 38
1

You should read more about Undefined Behavior and to build on the example:

struct A { A(int i): _i(i) {} void print() const { printf("%d", _i); } int _i; };

void function(A* a) {
    if (a == 0) { printf("%s", "A is null!"); }
    a->print();
}

What do you expect for function(0); ?

Well, you seem to expect that A is null! will get printed, and then the program will crash, right ? Maybe... maybe not.

The compiler might actually proceed like so:

  • a->print();: a cannot be null here, otherwise this statement is meaningless
  • a == 0 is therefore always false
  • the function can be rewritten as void function(A* a) { a->print(); }

And then, on a common Linux platform, you will get your crash (SEGFAULT), but no message... at all!

That's what undefined behavior does with optimizations: your program runs a lot faster, but dies in unfathomable ways at the slightest mistakes.

Matthieu M.
  • 287,565
  • 48
  • 449
  • 722
  • The compiler would have to be pretty sure that `printf` doesn't modify the value of `a` though (not even through any indirect means), if it performs reasoning like that. – Dabbler Oct 26 '12 at 21:25
  • @Dabbler: `printf` is one of those functions who come in the Standard Library implementation delivered alongside the compiler, so the compiler knows everything there is to know about it. For example, most compilers will warn *at compile-time* if your format string is off with regard to the parameters passed :) – Matthieu M. Oct 27 '12 at 12:45