| 1 | // inline this structure to have a virtual dtor.
 | 
|---|
| 2 | // when using this, delete() is also virtual and will be called on the right address
 | 
|---|
| 3 | // using free() directly on polymorphic types may result in unaligned memory deallocation
 | 
|---|
| 4 | //     in multi-inheritance or in single inheritance if the inline isn't the first field
 | 
|---|
| 5 | 
 | 
|---|
| 6 | // This supports virtual dtors for both single and multiple inheritance,
 | 
|---|
| 7 | // however it does not support multiple inheritance of the virtual_dtor. e.g.:
 | 
|---|
| 8 | //     given struct A { inline virtual_dtor; } and struct B { inline virtual_dtor; }
 | 
|---|
| 9 | //     struct C { inline A; inline B; } will result in undefined behaviour
 | 
|---|
| 10 | 
 | 
|---|
| 11 | struct virtual_dtor {
 | 
|---|
| 12 |     void (*__virtual_dtor_ptr)(virtual_dtor &);
 | 
|---|
| 13 |     void * __virtual_obj_start;
 | 
|---|
| 14 | };
 | 
|---|
| 15 | 
 | 
|---|
| 16 | // the following routines are used by the compiler and should not be called directly
 | 
|---|
| 17 | static inline void __CFA_set_virt_dtor( virtual_dtor & this, void (*v_dtor)(virtual_dtor &)) {
 | 
|---|
| 18 |     this.__virtual_dtor_ptr = v_dtor;
 | 
|---|
| 19 | }
 | 
|---|
| 20 | static inline void __CFA_set_virt_start( virtual_dtor & this, void * start) {
 | 
|---|
| 21 |     this.__virtual_obj_start = start;
 | 
|---|
| 22 | }
 | 
|---|
| 23 | static inline void __CFA_setup_dtor( virtual_dtor & this ) with(this) {
 | 
|---|
| 24 |     __virtual_dtor_ptr = 0p;
 | 
|---|
| 25 |     __virtual_obj_start = &this;
 | 
|---|
| 26 | }
 | 
|---|
| 27 | static inline void __CFA_dtor_shutdown( virtual_dtor & this ) with(this) {
 | 
|---|
| 28 |     if ( __virtual_dtor_ptr ) {
 | 
|---|
| 29 |         void (*dtor_ptr)(virtual_dtor &) = __virtual_dtor_ptr;
 | 
|---|
| 30 |         __virtual_dtor_ptr = 0p;
 | 
|---|
| 31 |         dtor_ptr(*((virtual_dtor *)__virtual_obj_start)); // replace actor with base type
 | 
|---|
| 32 |         return;
 | 
|---|
| 33 |     }
 | 
|---|
| 34 | }
 | 
|---|
| 35 | static inline void __CFA_virt_free( virtual_dtor & this ) { free( this.__virtual_obj_start ); }
 | 
|---|
| 36 | static inline void * __CFA_get_virt_start( virtual_dtor & this ) { return this.__virtual_obj_start; }
 | 
|---|
| 37 | static inline void ?{}( virtual_dtor & this ) {}
 | 
|---|
| 38 | static inline void ^?{}( virtual_dtor & this ) {}
 | 
|---|