C++ delete operator undefined behavior

David Holmes david.holmes at oracle.com
Sat Feb 9 12:36:12 UTC 2019


Hi Ioi,

On 9/02/2019 6:42 pm, Ioi Lam wrote:
> I am getting a "ud2" instruction on the Mac for a 'delete' expression. 
> According to this page, it's clang flagging an undefined behavior:
> 
> https://stackoverflow.com/questions/21529308/why-does-clang-generate-ud2-opcode-on-osx 
> 
> 
> My code looks like this:
> 
> class MetaspaceClosure {
>    class Ref : public ResourceObj {
>    ...
>    };
> 
> 
>    void push_impl(Ref* ref) {
>      if (_nest_level < MAX_NEST_LEVEL) {
>        do_push(ref);
>        delete ref;
>      } else {
>        ref->set_next(_pending_refs);
>        _pending_refs = ref;
>      }
>    }
> };
> 
> and clang generates this code
> 
> libjvm.dylib`MetaspaceClosure::push_impl:
>      0x10316db9c <+0>:  pushq  %rbp
>      0x10316db9d <+1>:  movq   %rsp, %rbp
>      0x10316dba0 <+4>:  pushq  %rbx
>      0x10316dba1 <+5>:  pushq  %rax
>      0x10316dba2 <+6>:  movq   %rsi, %rbx
>      0x10316dba5 <+9>:  cmpl   $0x4, 0x10(%rdi)
>      0x10316dba9 <+13>: jg     0x10316dbba
>      0x10316dbab <+15>: movq   %rbx, %rsi
>      0x10316dbae <+18>: callq  0x10316dbce  ; do_push()
>      0x10316dbb3 <+23>: testq  %rbx, %rbx
>      0x10316dbb6 <+26>: je     0x10316dbc6
> ->  0x10316dbb8 <+28>: ud2 <<<<<<<<<<<<<<<<<<<<<<< HERE
>      0x10316dbba <+30>: movq   0x8(%rdi), %rax
>      0x10316dbbe <+34>: movq   %rax, 0x20(%rbx)
>      0x10316dbc2 <+38>: movq   %rbx, 0x8(%rdi)
>      0x10316dbc6 <+42>: addq   $0x8, %rsp
>      0x10316dbca <+46>: popq   %rbx
>      0x10316dbcb <+47>: popq   %rbp
>      0x10316dbcc <+48>: retq
>      0x10316dbcd <+49>: nop
> 
> Shouldn't the 'delete' expression be translated to ResourceObj::operator 
> delete()?

Are Ref's allocated on the C_heap? That's the only kind of resourceObj 
you can delete:

void ResourceObj::operator delete(void* p) {
   assert(((ResourceObj *)p)->allocated_on_C_heap(),
          "delete only allowed for C_HEAP objects");
   DEBUG_ONLY(((ResourceObj *)p)->_allocation_t[0] = 
(uintptr_t)badHeapOopVal;)
   FreeHeap(p);
}

David
-----

> And I couldn't find any warning messages given by clang ....
> 
> I rewrote the Ref class to inherit from CHeapObj<mtInternal> instead, 
> and it magically worked.
> 
> However, but there's other use of 'delete' on ResourceObj (such as 
> ResourceHashtable) that seems to work just fine. Am I missing something?
> 
> Thanks
> 
> - Ioi
> 
> 
> 


More information about the hotspot-dev mailing list