PxxxxR0
std::debug

New Proposal,

This version:
http://virjacode.com/papers/stddebug.htm
Author:
Thomas PK Healy <healy7tpk@vir7ja7code7.com> Remove all sevens from email address
Audience:
SG18
Project:
ISO/IEC 14882 Programming Languages — C++, ISO/IEC JTC1/SC22/WG21

Abstract

Standardise debugging across all C++ compilers with a new header called <debug>

1. Introduction

New additions to the standard library inside the namespace std::debug:

struct vtable {
    // The layout of the VTable is pretty much identical
    // for every compiler except for the Microsoft compiler
};

template<class T> requires is_polymorphic_v< remove_cvref_t<T> >
consteval size_t get_count_virtual_methods(void);

template<class T> requires is_polymorphic_v< remove_cvref_t<T> >
consteval size_t get_class_vptr_offset(void);

template<class T> requires is_polymorphic_v< remove_cvref_t<T> >
constexpr vtable *get_address_of_object_vptr(T&&);

template<class T> requires is_polymorphic_v< remove_cvref_t<T> >
consteval vtable &get_class_vtable(void);

template<class T> requires is_polymorphic_v< remove_cvref_t<T> >
consteval size_t get_class_vtable_size(void);

template<class T>
requires (         is_polymorphic_v< remove_cvref_t<T> >
      &&   has_virtual_destructor_v< remove_cvref_t<T> > )
consteval size_t get_offset_of_destructor_in_class_vtable(void);

template<class T, typename... Params>
consteval auto get_address_of_class_constructor(void) -> void (*)(void*);

template<class T>
consteval auto get_address_of_class_destructor(void) -> void (*)(void*);

template<class T>
constexpr auto get_address_of_object_destructor(T&&) -> void (*)(void*);

2. Usage

2.1. get_count_virtual_methods

The function get_count_virtual_methods returns the count of the class’s virtual methods (including virtual methods inherited from base classes).

#include <debug>

struct Base {
    int n;
};

struct Derived : Base {
    virtual ~Derived(void) = default;
};

int main(void)
{
    std::size_t n = std::debug::get_count_virtual_methods<Derived>();
}

2.2. get_class_vptr_offset

The function get_class_vptr_offset returns the offset at which the VTable pointer is to be found inside the polymorphic object.

#include <debug>

struct Base {
    int n;
};

struct Derived : Base {
    virtual ~Derived(void) = default;
};

int main(void)
{
    size_t offset = std::debug::get_class_vptr_offset<Derived>();
}

2.3. get_address_of_object_vptr

The function get_address_of_object_vptr returns the address at which the VTable pointer resides inside the polymorphic object.

#include <debug>

struct Base {
    int n;
};

struct Derived : Base {
    virtual ~Derived(void) = default;
};

int main(void)
{
    Derived obj;
    std::debug::vtable &v = *std::debug::get_address_of_object_vptr(obj);
}

2.4. get_class_vtable

The function get_class_vtable returns a reference to the class’s VTable.

#include <debug>

struct Base {
    int n;
};

struct Derived : Base {
    virtual ~Derived(void) = default;
};

int main(void)
{
    std::debug::vtable &v = std::debug::get_class_vtable<Derived>();
}

2.5. get_class_vtable_size

The function get_class_vtable_size returns the size (in bytes) of the class’s VTable.

#include <debug>

struct Base {
    int n;
};

struct Derived : Base {
    virtual ~Derived(void) = default;
};

int main(void)
{
    std::size_t n = std::debug::get_class_vtable_size<Derived>();
}

2.6. get_offset_of_destructor_in_class_vtable

The function get_offset_of_destructor_in_class_vtable returns the offset at which the entry point of the class’s destructor resides in the class’s VTable.

#include <debug>

struct Base {
    int n;
};

struct Derived : Base {
    virtual ~Derived(void) = default;
};

int main(void)
{
    size_t n = std::debug::get_offset_of_destructor_in_class_vtable<Derived>();
}

2.7. get_address_of_class_constructor

The function get_address_of_class_constructor returns the address of the class’s constructor which takes the specified parameters.

#include <debug>

struct Base {
    int n;
};

struct Derived : Base {
    virtual ~Derived(void) = default;
    Derived(int, double, float);
};

int main(void)
{
    void (*fp)(void*) = std::debug::get_address_of_class_constructor<Derived,int,double,float>();
}

2.8. get_address_of_class_destructor

The function get_address_of_class_destructor returns the address of the entry point of the class’s destructor.

#include <debug>

struct Base {
    int n;
};

struct Derived : Base {
    virtual ~Derived(void) = default;
};

int main(void)
{
    void (*fp)(void*) = std::debug::get_address_of_class_destructor<Derived>();
}

2.9. get_address_of_object_destructor

The function get_address_of_object_destructor returns the address of the entry point of the object’s destructor (which, in the case of a virtual destructor, will be gotten from the object’s VTable).

#include <debug>

struct Base {
    int n;
};

struct Derived : Base {
    virtual ~Derived(void) = default;
};

int main(void)
{
    Derived obj;
    void (*fp)(void*) = std::debug::get_address_of_obj_destructor(obj);
}