The destructor does not have a name as such. For class C ~C C syntax is used to denote a single, nameless destructor.
In your case, ~B therefore simply means "destructor." Since virtual dynamic dispatch occurs at runtime with the D destructor, it is called.
If you did this instead:
b->B::~B();
it will disable dynamic sending (like any other qualified call), and you only call the destructor B
source share