diff --git a/dtool/src/interrogate/interrogateBuilder.cxx b/dtool/src/interrogate/interrogateBuilder.cxx index b2d7198f6b..3d0de4da0b 100644 --- a/dtool/src/interrogate/interrogateBuilder.cxx +++ b/dtool/src/interrogate/interrogateBuilder.cxx @@ -957,6 +957,46 @@ should_include(const string &filename) const { return true; } +//////////////////////////////////////////////////////////////////// +// Function: InterrogateBuilder::is_inherited_published +// Access: Private +// Description: Recursively looks for the first inherited version of +// this function in the derivation chain of this class. +// Returns true if this function is declared published, +// or false if it is not published, or if it can't be +// found. +//////////////////////////////////////////////////////////////////// +bool InterrogateBuilder:: +is_inherited_published(CPPInstance *function, CPPStructType *struct_type) { + nassertr(struct_type->_derivation.size() == 1, false); + CPPStructType *base = struct_type->_derivation[0]._base->as_struct_type(); + nassertr(base != (CPPStructType *)NULL, false); + + CPPScope *base_scope = base->get_scope(); + CPPDeclaration *symbol = base_scope->find_symbol(function->get_simple_name(), true); + if (symbol == (CPPDeclaration *)NULL) { + // Couldn't find the inherited function. + return false; + } + + CPPFunctionGroup *fgroup = symbol->as_function_group(); + if (fgroup == (CPPFunctionGroup *)NULL) { + // Weird, it wasn't a function. + return false; + } + + CPPFunctionGroup::Instances::iterator ii; + for (ii = fgroup->_instances.begin(); ii != fgroup->_instances.end(); ++ii) { + CPPInstance *inst = (*ii); + if (inst->_vis != V_published) { + // Some flavors of the method are not published. Take no chances. + return false; + } + } + // It appears that all flavors of the inherited method are published. + return true; +} + //////////////////////////////////////////////////////////////////// // Function: InterrogateBuilder::remap_indices // Access: Private @@ -2292,7 +2332,7 @@ define_method(CPPInstance *function, InterrogateType &itype, if ((ftype->_flags & CPPFunctionType::F_destructor) != 0) { // A destructor is a special case. If it's public, we export it // (even if it's not published), but if it's protected or private, - // we don't exported it, and we flag it so we don't try to + // we don't export it, and we flag it so we don't try to // synthesize one later. if (function->_vis > V_public) { itype._flags |= InterrogateType::F_private_destructor; @@ -2340,8 +2380,15 @@ define_method(CPPInstance *function, InterrogateType &itype, // inheritance. if ((ftype->_flags & CPPFunctionType::F_destructor) != 0) { itype._flags |= InterrogateType::F_inherited_destructor; + return; } - return; + + // Let's make sure the that first appearance of the function is + // actually declared published. + if (is_inherited_published(function, struct_type)) { + return; + } + // If it isn't, we should publish this method anyway. } diff --git a/dtool/src/interrogate/interrogateBuilder.h b/dtool/src/interrogate/interrogateBuilder.h index b400106fce..bc4e97bfaf 100644 --- a/dtool/src/interrogate/interrogateBuilder.h +++ b/dtool/src/interrogate/interrogateBuilder.h @@ -66,7 +66,6 @@ public: static string hash_string(const string &name, int shift_offset); TypeIndex get_type(CPPType *type, bool global); -private: public: typedef set Commands; typedef map CommandParams; @@ -84,6 +83,8 @@ public: bool in_noinclude(const string &name) const; bool should_include(const string &filename) const; + bool is_inherited_published(CPPInstance *function, CPPStructType *struct_type); + void remap_indices(vector &remaps); void scan_function(CPPFunctionGroup *fgroup); void scan_function(CPPInstance *function);