Skip to content

Commit 5d0ce92

Browse files
Implement Cppyy::GetActualClass
1 parent 5025eda commit 5d0ce92

File tree

2 files changed

+22
-65
lines changed

2 files changed

+22
-65
lines changed

clingwrapper/src/clingwrapper.cxx

Lines changed: 21 additions & 64 deletions
Original file line numberDiff line numberDiff line change
@@ -645,70 +645,27 @@ bool Cppyy::IsTypedefed(TCppScope_t handle)
645645
return Cpp::IsTypedefed(handle);
646646
}
647647

648-
// namespace {
649-
// class AutoCastRTTI {
650-
// public:
651-
// virtual ~AutoCastRTTI() {}
652-
// };
653-
// }
654-
//
655-
// Cppyy::TCppType_t Cppyy::GetActualClass(TCppType_t klass, TCppObject_t obj)
656-
// {
657-
// TClassRef& cr = type_from_handle(klass);
658-
// if (!cr.GetClass() || !obj) return klass;
659-
//
660-
// if (!(cr->ClassProperty() & kClassHasVirtual))
661-
// return klass; // not polymorphic: no RTTI info available
662-
//
663-
// #ifdef _WIN64
664-
// // Cling does not provide a consistent ImageBase address for calculating relative addresses
665-
// // as used in Windows 64b RTTI. So, check for our own RTTI extension instead. If that fails,
666-
// // see whether the unmangled raw_name is available (e.g. if this is an MSVC compiled rather
667-
// // than JITed class) and pass on if it is.
668-
// volatile const char* raw = nullptr; // to prevent too aggressive reordering
669-
// try {
670-
// // this will filter those objects that do not have RTTI to begin with (throws)
671-
// AutoCastRTTI* pcst = (AutoCastRTTI*)obj;
672-
// raw = typeid(*pcst).raw_name();
673-
//
674-
// // check the signature id (0 == absolute, 1 == relative, 2 == ours)
675-
// void* vfptr = *(void**)((intptr_t)obj);
676-
// void* meta = (void*)((intptr_t)*((void**)((intptr_t)vfptr-sizeof(void*))));
677-
// if (*(intptr_t*)meta == 2) {
678-
// // access the extra data item which is an absolute pointer to the RTTI
679-
// void* ptdescr = (void*)((intptr_t)meta + 4*sizeof(unsigned long)+sizeof(void*));
680-
// if (ptdescr && *(void**)ptdescr) {
681-
// auto rtti = *(std::type_info**)ptdescr;
682-
// raw = rtti->raw_name();
683-
// if (raw && raw[0] != '\0') // likely unnecessary
684-
// return (TCppType_t)GetScope(rtti->name());
685-
// }
686-
//
687-
// return klass; // do not fall through if no RTTI info available
688-
// }
689-
//
690-
// // if the raw name is the empty string (no guarantees that this is so as truly, the
691-
// // address is corrupt, but it is common to be empty), then there is no accessible RTTI
692-
// // and getting the unmangled name will crash ...
693-
//
694-
// // a common case are the i/o stream objects b/c these are pulled in from libCling
695-
// if (!raw || (strstr(cr->GetName(), "std::basic_") && strstr(cr->GetName(), "stream")) || raw[0] == '\0')
696-
// return klass;
697-
// } catch (std::bad_typeid) {
698-
// return klass; // can't risk passing to ROOT/meta as it may do RTTI
699-
// }
700-
// #endif
701-
//
702-
// TClass* clActual = cr->GetActualClass((void*)obj);
703-
// if (clActual && clActual != cr.GetClass()) {
704-
// auto itt = g_name2classrefidx.find(clActual->GetName());
705-
// if (itt != g_name2classrefidx.end())
706-
// return (TCppType_t)itt->second;
707-
// return (TCppType_t)GetScope(clActual->GetName());
708-
// }
709-
//
710-
// return klass;
711-
// }
648+
namespace {
649+
class AutoCastRTTI {
650+
public:
651+
virtual ~AutoCastRTTI() {}
652+
};
653+
} // namespace
654+
655+
Cppyy::TCppScope_t Cppyy::GetActualClass(TCppScope_t klass, TCppObject_t obj) {
656+
if (!Cpp::IsClassPolymorphic(klass))
657+
return klass;
658+
659+
const std::type_info *typ = &typeid(*(AutoCastRTTI *)obj);
660+
661+
std::string mangled_name = typ->name();
662+
std::string demangled_name = Cpp::Demangle(mangled_name);
663+
664+
if (TCppScope_t scope = Cppyy::GetScope(demangled_name))
665+
return scope;
666+
667+
return klass;
668+
}
712669

713670
size_t Cppyy::SizeOf(TCppScope_t klass)
714671
{

clingwrapper/src/cpp_cppyy.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -111,7 +111,7 @@ namespace Cppyy {
111111
RPY_EXPORTED
112112
TCppScope_t GetGlobalScope();
113113
RPY_EXPORTED
114-
TCppType_t GetActualClass(TCppType_t klass, TCppObject_t obj) { assert(0 && "GetActualClass"); return 0; }
114+
TCppScope_t GetActualClass(TCppScope_t klass, TCppObject_t obj);
115115
RPY_EXPORTED
116116
size_t SizeOf(TCppScope_t klass);
117117
RPY_EXPORTED

0 commit comments

Comments
 (0)