change to use (1) virtual inheritance and (2) dynamic_pointer_cast