https://gcc.gnu.org/bugzilla/show_bug.cgi?id=92928
--- Comment #1 from Jakub Jelinek <jakub at gcc dot gnu.org> ---
Even more reduced (without headers):
struct Base
{
virtual ~Base() = default;
virtual bool foo() noexcept = 0;
};
struct Derived : public Base
{
Derived() noexcept {};
bool foo() noexcept override { return true; };
};
int main()
{
int diff = reinterpret_cast<__PTRDIFF_TYPE__>(static_cast<Derived
*>(reinterpret_cast<Base *>(1 << 20))) - (1 << 20);
__builtin_printf ("%d\n", diff);
}
I'd say this is just invalid, there is no object of type Base or Derived at the
address 1 << 20 and -fsanitize=vptr attempts to verify that the object has the
right virtual table pointer, but as nothing is mapped at 1 << 20, that access
obviously fails.
You get exactly the same behavior with clang++ -fsanitize=address,undefined.
Both will work with -fsanitize=address,undefined -fno-sanitize=vptr.