Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why is "operator delete" invoked when I call "delete" on a null pointer?

While reading answers to this question I noticed that answers (this for example) imply that operator delete can be called even when delete statement is executed on a null pointer.

So I wrote a small snippet:

class Test {
public:
    void* operator new( size_t ) { /*doesn't matter*/ return 0; }
    void operator delete( void* ptr ) {
        ptr; //to suppress warning and have a line to put breakpoint on
    }
};

int main()
{
    Test* ptr = 0;
    delete ptr;
}

and - surprisingly for me - Test::operator delete() is invoked with ptr holding a null pointer.

As I understand it operator new allocates memory and operator delete returns memory to the allocator. If I call delete statement on a null pointer it means there was no object behind the pointer and there's no memory to return to the allocator.

delete statement includes invoking a destructor. When I pass a null pointer the destructor is surely not invoked - C++ takes care of that. Then why is operator delete invoked in this case?

like image 739
sharptooth Avatar asked Sep 29 '10 13:09

sharptooth


People also ask

What happens if you call delete on a null pointer?

What happens when delete is used for a NULL pointer? Explanation: Deleting a null pointer has no effect, so it is not necessary to check for a null pointer before calling delete.

Why delete operator is used in a pointer?

Using delete on a pointer to an object not allocated with new gives unpredictable results. You can, however, use delete on a pointer with the value 0. This provision means that, when new returns 0 on failure, deleting the result of a failed new operation is harmless.

Does delete destroy the pointer?

Yes, it destroys the object by calling its destructor. It also deallocates the memory that new allocated to store the object. Or does it only destory the pointer? It does nothing to the pointer.

What happens when delete is called?

Two things happen when delete[] is called: If the array is of a type that has a nontrivial destructor, the destructor is called for each of the elements in the array, in reverse order. The memory occupied by the array is released.


1 Answers

The language in the upcoming C++0x standard (section 5.3.5 [expr.delete]) is as follows:

If the value of the operand of the delete-expression is not a null pointer value, the delete-expression will call a deallocation function (3.7.4.2). Otherwise, it is unspecified whether the deallocation function will be called. [ Note: The deallocation function is called regardless of whether the destructor for the object or some element of the array throws an exception. — end note ]

So it is unspecified behavior, some compilers may call operator delete when a NULL pointer is deleted and others may not.

EDIT: The term deallocation function used by the standard seems to be causing some confusion. It comes with a reference. Some key language from 3.7.4.2 [basic.stc.dynamic.deallocation] which may help clarify:

If a class T has a member deallocation function named operator delete with exactly one parameter, then that function is a usual (non-placement) deallocation function.

The standard is also very clear that user-defined operator delete needs to accept a parameter which is a null pointer value:

The value of the first argument supplied to a deallocation function may be a null pointer value; if so, and if the deallocation function is one supplied in the standard library, the call has no effect.

But because of the unspecified behavior 5.3.5, you shouldn't rely on your operator delete being called when the pointer is null.

like image 126
Ben Voigt Avatar answered Nov 01 '22 23:11

Ben Voigt