Skip to content

make operator new more standard compliant  #295

@ramosian-glider

Description

@ramosian-glider

Originally reported on Google Code with ID 295

Users sometimes complain that asan's operator new is not fully standard-compliant
when it comes to handling out of memory situation.

In particular: 

  - new-nothrow does not return 0 by default (it does with ASAN_OPTIONS=allocator_may_return_null=1)
  - new does not throw std::bad_alloc
  - either variant does not call new_handler 


Implementing these features appears to be surprisingly difficult.

The implementation of asan's operator new resides in asan/asan_new_delete.cc
http://llvm.org/viewvc/llvm-project/compiler-rt/trunk/lib/asan/asan_new_delete.cc?view=markup

asan's new/delete is essentially a user replacement of these operators. 
This has a side effect: a user can not replace new/delete with his own variants,
(this is undefined behavior: http://en.cppreference.com/w/cpp/memory/new/operator_new)

Throwing exceptions from asan/asan_new_delete.cc is currently not possible because
we build the entire run-time w/o exceptions. 
We can overcome this by having special flags for asan/asan_new_delete.cc.
Then there is a problem of linking with c++ lib.
asan run-time does not depend on c++ run-time and can be used with pure C w/o linking
c++.
We probably may overcome this my splitting asan_new_delete.cc into a separate library
asan-rt-cxx that will be linked in asan mode only for C++ programs. 

Calling new_handler from asan's operator new would be possible in c++11, where 
std::get_new_handler() is present, but we can't rely on this yet
(libstdc++ in gcc 4.8.2 does not have std::get_new_handler).
And again, the same problem with linking with c++ lib.

We can also simply remove our new/delete interceptors.
This will route new/delete to the standard c++ library and will solve the problem completely
(assuming new/delete call malloc/free),
but we will lose the ability to detect new/free and new[]/delete mismatch bugs. 

So, the possible plan is: 
- split asan run-time, moving asan/asan_new_delete.cc into a separate library and link
it only when libstdc++/libc++ is linked.
- make our operator new() throw bad_alloc
- declare std::get_new_handler() as weak and if it is present, handle the new_handler
case.

OMG, that sounds so hard, and for very little outcome.
I am tempted to leave it as is unless we find an easier route.
Better implementation ideas are welcome. 

Reported by konstantin.s.serebryany on 2014-04-15 12:00:10

Metadata

Metadata

Assignees

Type

No type
No fields configured for issues without a type.

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions