Browse Source

implement SIMPLE_STRUCT_POINTERS

David Rose 24 years ago
parent
commit
c82667c148

+ 7 - 1
panda/src/putil/pipelineCycler.h

@@ -48,9 +48,15 @@
 //               same interface but with minimal runtime overhead.
 //               (Actually, this isn't true yet, but it will be one
 //               day.)
+//
+//               We define this as a struct instead of a class to
+//               guarantee byte placement within the object, so that
+//               (particularly for the trivial implementation) the
+//               inherited struct's data is likely to be placed by the
+//               compiler at the "this" pointer.
 ////////////////////////////////////////////////////////////////////
 template<class CycleDataType>
-class PipelineCycler : public PipelineCyclerBase {
+struct PipelineCycler : public PipelineCyclerBase {
 public:
   INLINE PipelineCycler(Pipeline *pipeline = NULL);
   INLINE PipelineCycler(const PipelineCycler<CycleDataType> &copy);

+ 20 - 0
panda/src/putil/pipelineCyclerBase.I

@@ -299,7 +299,11 @@ PipelineCyclerBase(CycleData *initial_data, Pipeline *) {
   // If this turns out not to be true on a particular platform, we
   // will have to store the pointer in this class, for a little bit of
   // extra overhead.
+#ifdef SIMPLE_STRUCT_POINTERS
   nassertv(initial_data == (CycleData *)this);
+#else
+  _data = initial_data;
+#endif  // SIMPLE_STRUCT_POINTERS
 }
 
 ////////////////////////////////////////////////////////////////////
@@ -339,7 +343,11 @@ INLINE PipelineCyclerBase::
 ////////////////////////////////////////////////////////////////////
 INLINE const CycleData *PipelineCyclerBase::
 read() const {
+#ifdef SIMPLE_STRUCT_POINTERS
   return (const CycleData *)this;
+#else
+  return _data;
+#endif  // SIMPLE_STRUCT_POINTERS
 }
 
 ////////////////////////////////////////////////////////////////////
@@ -381,7 +389,11 @@ release_read(const CycleData *) const {
 ////////////////////////////////////////////////////////////////////
 INLINE CycleData *PipelineCyclerBase::
 write() {
+#ifdef SIMPLE_STRUCT_POINTERS
   return (CycleData *)this;
+#else
+  return _data;
+#endif  // SIMPLE_STRUCT_POINTERS
 }
 
 ////////////////////////////////////////////////////////////////////
@@ -395,7 +407,11 @@ write() {
 ////////////////////////////////////////////////////////////////////
 INLINE CycleData *PipelineCyclerBase::
 elevate_read(const CycleData *) {
+#ifdef SIMPLE_STRUCT_POINTERS
   return (CycleData *)this;
+#else
+  return _data;
+#endif  // SIMPLE_STRUCT_POINTERS
 }
 
 ////////////////////////////////////////////////////////////////////
@@ -467,7 +483,11 @@ release_write_stage(int, CycleData *) {
 ////////////////////////////////////////////////////////////////////
 INLINE CycleData *PipelineCyclerBase::
 cheat() const {
+#ifdef SIMPLE_STRUCT_POINTERS
   return (CycleData *)this;
+#else
+  return _data;
+#endif  // SIMPLE_STRUCT_POINTERS
 }
 
 ////////////////////////////////////////////////////////////////////

+ 17 - 1
panda/src/putil/pipelineCyclerBase.h

@@ -29,8 +29,14 @@
 //       Class : PipelineCyclerBase
 // Description : This is the non-template part of the implementation
 //               of PipelineCycler.  See PipelineCycler.
+//
+//               We define this as a struct instead of a class to
+//               guarantee byte placement within the object, so that
+//               (particularly for the trivial implementation) the
+//               inherited struct's data is likely to be placed by the
+//               compiler at the "this" pointer.
 ////////////////////////////////////////////////////////////////////
-class EXPCL_PANDA PipelineCyclerBase {
+struct EXPCL_PANDA PipelineCyclerBase {
 public:
   INLINE PipelineCyclerBase(CycleData *initial_data, Pipeline *pipeline = NULL);
   INLINE PipelineCyclerBase(const PipelineCyclerBase &copy);
@@ -63,6 +69,16 @@ private:
   PT(CycleData) _data;
   Pipeline *_pipeline;
   short _read_count, _write_count;
+
+#else  // !DO_PIPELINING
+  // In a trivial implementation, we only need to store the CycleData
+  // pointer.  Actually, we don't even need to do that, if we're lucky
+  // and the compiler doesn't do anything funny with the struct
+  // layout.
+  #ifndef SIMPLE_STRUCT_POINTERS
+  CycleData *_data;
+  #endif  // SIMPLE_STRUCT_POINTERS
+
 #endif  // DO_PIPELINING
 };