Browse Source

*** empty log message ***

David Rose 24 years ago
parent
commit
57b4db99c5
39 changed files with 889 additions and 404 deletions
  1. 7 1
      panda/src/express/Sources.pp
  2. 63 0
      panda/src/express/checksumHashGenerator.I
  3. 22 0
      panda/src/express/checksumHashGenerator.cxx
  4. 31 0
      panda/src/express/checksumHashGenerator.h
  5. 34 0
      panda/src/express/hashGeneratorBase.I
  6. 6 0
      panda/src/express/hashGeneratorBase.cxx
  7. 39 0
      panda/src/express/hashGeneratorBase.h
  8. 4 2
      panda/src/graph/Sources.pp
  9. 12 0
      panda/src/graph/allTransitionsWrapper.I
  10. 5 2
      panda/src/graph/allTransitionsWrapper.h
  11. 14 0
      panda/src/graph/bitMaskTransition.T
  12. 1 0
      panda/src/graph/bitMaskTransition.h
  13. 27 0
      panda/src/graph/graphHashGenerator.h
  14. 13 0
      panda/src/graph/matrixTransition.T
  15. 1 0
      panda/src/graph/matrixTransition.h
  16. 11 0
      panda/src/graph/nodeTransition.I
  17. 11 0
      panda/src/graph/nodeTransition.cxx
  18. 6 0
      panda/src/graph/nodeTransition.h
  19. 13 0
      panda/src/graph/nodeTransitionCache.cxx
  20. 4 0
      panda/src/graph/nodeTransitionCache.h
  21. 12 0
      panda/src/graph/nodeTransitionCacheEntry.I
  22. 4 0
      panda/src/graph/nodeTransitionCacheEntry.h
  23. 166 212
      panda/src/linmath/lmatrix3_src.I
  24. 75 21
      panda/src/linmath/lmatrix3_src.cxx
  25. 32 20
      panda/src/linmath/lmatrix3_src.h
  26. 27 81
      panda/src/linmath/lmatrix4_src.I
  27. 113 42
      panda/src/linmath/lmatrix4_src.cxx
  28. 28 18
      panda/src/linmath/lmatrix4_src.h
  29. 2 0
      panda/src/linmath/lvecBase2.h
  30. 21 0
      panda/src/linmath/lvecBase2_src.I
  31. 7 1
      panda/src/linmath/lvecBase2_src.h
  32. 2 0
      panda/src/linmath/lvecBase3.h
  33. 22 0
      panda/src/linmath/lvecBase3_src.I
  34. 6 1
      panda/src/linmath/lvecBase3_src.h
  35. 2 0
      panda/src/linmath/lvecBase4.h
  36. 23 0
      panda/src/linmath/lvecBase4_src.I
  37. 7 3
      panda/src/linmath/lvecBase4_src.h
  38. 11 0
      panda/src/putil/bitMask.I
  39. 5 0
      panda/src/putil/bitMask.h

+ 7 - 1
panda/src/express/Sources.pp

@@ -10,6 +10,8 @@
 
   #define SOURCES							\
     bigEndian.h buffer.I buffer.cxx buffer.h	\
+    checksumHashGenerator.I checksumHashGenerator.cxx \
+    checksumHashGenerator.h \
     circBuffer.I circBuffer.h clockObject.I clockObject.cxx		\
     clockObject.h config_express.cxx config_express.h datagram.I	\
     datagram.cxx datagram.h datagramGenerator.I datagramGenerator.cxx	\
@@ -19,6 +21,7 @@
     datagramOutputFile.I datagramOutputFile.h datagramOutputFile.cxx	\
     datagramSink.I datagramSink.cxx datagramSink.h			\
     get_config_path.cxx get_config_path.h				\
+    hashGeneratorBase.I hashGeneratorBase.cxx hashGeneratorBase.h \
     hashVal.I hashVal.cxx hashVal.h \
     indent.I indent.cxx indent.h \
     littleEndian.h memoryUsage.I memoryUsage.cxx	\
@@ -42,13 +45,16 @@
     patchfile.I patchfile.cxx patchfile.h
 
   #define INSTALL_HEADERS						\
-    bigEndian.h buffer.I buffer.h circBuffer.I		\
+    bigEndian.h buffer.I buffer.h \
+    checksumHashGenerator.I checksumHashGenerator.h \
+    circBuffer.I		\
     circBuffer.h clockObject.I clockObject.h config_express.h		\
     datagram.I datagram.h datagramInputFile.I datagramInputFile.h	\
     datagramIterator.I datagramIterator.h \
     datagramOutputFile.I datagramOutputFile.h	\
     datagramSink.I datagramSink.h datagramGenerator.I			\
     datagramGenerator.h get_config_path.h				\
+    hashGeneratorBase.I hashGeneratorBase.h \
     hashVal.I hashVal.h \
     indent.I indent.h littleEndian.h			\
     memoryUsage.I memoryUsage.h memoryUsagePointers.I			\

+ 63 - 0
panda/src/express/checksumHashGenerator.I

@@ -0,0 +1,63 @@
+// Filename: checksumHashGenerator.I
+// Created by:  drose (14May01)
+// 
+////////////////////////////////////////////////////////////////////
+
+
+////////////////////////////////////////////////////////////////////
+//     Function: ChecksumHashGenerator::add_int
+//       Access: Public
+//  Description: Adds another integer to the hash so far.  This
+//               function should be overridden in base classes; this
+//               is the principle implementation of the HashGenerator.
+////////////////////////////////////////////////////////////////////
+INLINE void ChecksumHashGenerator::
+add_int(int sum) {
+  _hash += (size_t)sum;
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: ChecksumHashGenerator::add_bool
+//       Access: Public
+//  Description: Adds a boolean flag.
+////////////////////////////////////////////////////////////////////
+INLINE void ChecksumHashGenerator::
+add_bool(bool flag) {
+  add_int(flag);
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: ChecksumHashGenerator::add_fp
+//       Access: Public
+//  Description: Adds a floating-point number, first converting it to
+//               fixed point by dividing it by the indicated
+//               threshold.
+////////////////////////////////////////////////////////////////////
+INLINE void ChecksumHashGenerator::
+add_fp(float number, float threshold) {
+  add_int((int)(number / threshold));
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: ChecksumHashGenerator::add_fp
+//       Access: Public
+//  Description: Adds a floating-point number, first converting it to
+//               fixed point by dividing it by the indicated
+//               threshold.
+////////////////////////////////////////////////////////////////////
+INLINE void ChecksumHashGenerator::
+add_fp(double number, double threshold) {
+  add_int((int)(number / threshold));
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: ChecksumHashGenerator::add_pointer
+//       Access: Public
+//  Description: Adds a pointer, derived simply by casting the pointer
+//               to an integer.  This should be good enough even on
+//               architectures for which this cast is lossy.
+////////////////////////////////////////////////////////////////////
+INLINE void ChecksumHashGenerator::
+add_pointer(void *ptr) {
+  add_int((int)ptr);
+}

+ 22 - 0
panda/src/express/checksumHashGenerator.cxx

@@ -0,0 +1,22 @@
+// Filename: checksumHashGenerator.cxx
+// Created by:  drose (14May01)
+// 
+////////////////////////////////////////////////////////////////////
+
+
+#include "checksumHashGenerator.h"
+
+////////////////////////////////////////////////////////////////////
+//     Function: ChecksumHashGenerator::add_string
+//       Access: Public
+//  Description: Adds a string to the hash, by breaking it down into a
+//               sequence of integers.
+////////////////////////////////////////////////////////////////////
+void ChecksumHashGenerator::
+add_string(const string &str) {
+  add_int(str.length());
+  string::const_iterator si;
+  for (si = str.begin(); si != str.end(); ++si) {
+    add_int(*si);
+  }
+}

+ 31 - 0
panda/src/express/checksumHashGenerator.h

@@ -0,0 +1,31 @@
+// Filename: checksumHashGenerator.h
+// Created by:  drose (14May01)
+// 
+////////////////////////////////////////////////////////////////////
+
+#ifndef CHECKSUMHASHGENERATOR_H
+#define CHECKSUMHASHGENERATOR_H
+
+#include <pandabase.h>
+
+#include "hashGeneratorBase.h"
+
+////////////////////////////////////////////////////////////////////
+// 	 Class : ChecksumHashGenerator
+// Description : This is a specific kind of HashGenerator that simply
+//               adds up all of the ints.  Nothing fancy, and pretty
+//               quick.
+////////////////////////////////////////////////////////////////////
+class EXPCL_PANDAEXPRESS ChecksumHashGenerator : public HashGeneratorBase {
+public:
+  INLINE void add_int(int num);
+  INLINE void add_bool(bool flag);
+  INLINE void add_fp(float num, float threshold);
+  INLINE void add_fp(double num, double threshold);
+  INLINE void add_pointer(void *ptr);
+  void add_string(const string &str);
+};
+
+#include "checksumHashGenerator.I"
+
+#endif

+ 34 - 0
panda/src/express/hashGeneratorBase.I

@@ -0,0 +1,34 @@
+// Filename: hashGeneratorBase.I
+// Created by:  drose (14May01)
+// 
+////////////////////////////////////////////////////////////////////
+
+
+////////////////////////////////////////////////////////////////////
+//     Function: HashGeneratorBase::Constructor
+//       Access: Public
+//  Description: 
+////////////////////////////////////////////////////////////////////
+INLINE HashGeneratorBase::
+HashGeneratorBase() {
+  _hash = 0;
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: HashGeneratorBase::Destructor
+//       Access: Public
+//  Description: 
+////////////////////////////////////////////////////////////////////
+INLINE HashGeneratorBase::
+~HashGeneratorBase() {
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: HashGeneratorBase::get_hash
+//       Access: Public
+//  Description: Returns the hash number generated.
+////////////////////////////////////////////////////////////////////
+INLINE size_t HashGeneratorBase::
+get_hash() const {
+  return _hash;
+}

+ 6 - 0
panda/src/express/hashGeneratorBase.cxx

@@ -0,0 +1,6 @@
+// Filename: hashGeneratorBase.cxx
+// Created by:  drose (14May01)
+// 
+////////////////////////////////////////////////////////////////////
+
+#include "hashGeneratorBase.h"

+ 39 - 0
panda/src/express/hashGeneratorBase.h

@@ -0,0 +1,39 @@
+// Filename: hashGeneratorBase.h
+// Created by:  drose (14May01)
+// 
+////////////////////////////////////////////////////////////////////
+
+#ifndef HASHGENERATORBASE_H
+#define HASHGENERATORBASE_H
+
+#include <pandabase.h>
+
+////////////////////////////////////////////////////////////////////
+// 	 Class : HashGeneratorBase
+// Description : This is the base class for a number of classes that
+//               generate arbitrary hash numbers for complex objects,
+//               based fundamentally on a sequence of integers.
+//
+//               There are no virtual functions here, for performance
+//               reasons; it is generally desirable to generate hash
+//               numbers as quickly as possible.  The derived classes
+//               must redefine all the basic functionality.
+//
+//               Thus, a compile-time decision must be made for the
+//               kind of HashGenerator that is appropriate for a
+//               particular class.
+////////////////////////////////////////////////////////////////////
+class EXPCL_PANDAEXPRESS HashGeneratorBase {
+public:
+  INLINE HashGeneratorBase();
+  INLINE ~HashGeneratorBase();
+
+  INLINE size_t get_hash() const;
+
+protected:
+  size_t _hash;
+};
+
+#include "hashGeneratorBase.I"
+
+#endif

+ 4 - 2
panda/src/graph/Sources.pp

@@ -15,7 +15,8 @@
     bitMask32Transition.h bitMaskAttribute.T bitMaskAttribute.h \
     bitMaskTransition.T bitMaskTransition.h boundedObject.I \
     boundedObject.N boundedObject.cxx boundedObject.h config_graph.cxx \
-    config_graph.h dftraverser.T dftraverser.h graphReducer.cxx \
+    config_graph.h dftraverser.T dftraverser.h \
+    graphHashGenerator.h graphReducer.cxx \
     graphReducer.h immediateAttribute.cxx immediateAttribute.h \
     immediateTransition.I immediateTransition.cxx \
     immediateTransition.h lmatrix4fTransition.cxx \
@@ -65,7 +66,8 @@
     arcChain.h bitMask32Transition.h bitMaskAttribute.T \
     bitMaskAttribute.h bitMaskTransition.T bitMaskTransition.h \
     boundedObject.I boundedObject.h config_graph.h dftraverser.T \
-    dftraverser.h graphReducer.h immediateAttribute.h \
+    dftraverser.h graphHashGenerator.h \
+    graphReducer.h immediateAttribute.h \
     immediateTransition.I immediateTransition.h lmatrix4fTransition.h \
     matrixAttribute.T matrixAttribute.h matrixTransition.T \
     matrixTransition.h multiAttribute.T multiAttribute.h \

+ 12 - 0
panda/src/graph/allTransitionsWrapper.I

@@ -225,6 +225,18 @@ compare_to(const AllTransitionsWrapper &other) const {
   return _cache->compare_to(*other._cache);
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: AllTransitionsWrapper::generate_hash
+//       Access: Public
+//  Description: Adds the transitions to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+INLINE_GRAPH void AllTransitionsWrapper::
+generate_hash(GraphHashGenerator &hash) const {
+  if (_cache != (NodeTransitionCache *)NULL) {
+    _cache->generate_hash(hash);
+  }
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: AllTransitionsWrapper::make_identity
 //       Access: Public

+ 5 - 2
panda/src/graph/allTransitionsWrapper.h

@@ -24,6 +24,7 @@
 #include "nodeTransition.h"
 #include "nodeTransitionCache.h"
 #include "config_graph.h"
+#include "graphHashGenerator.h"
 
 #include <pointerTo.h>
 
@@ -43,6 +44,7 @@ class EXPCL_PANDA AllTransitionsWrapper {
 public:
   typedef AllTransitionsWrapper TransitionWrapper;
   typedef AllAttributesWrapper AttributeWrapper;
+  typedef GraphHashGenerator HashGenerator;
 
   INLINE_GRAPH AllTransitionsWrapper();
   INLINE_GRAPH AllTransitionsWrapper(const AllTransitionsWrapper &copy);
@@ -66,6 +68,7 @@ public:
 
   INLINE_GRAPH bool is_identity() const;
   INLINE_GRAPH int compare_to(const AllTransitionsWrapper &other) const;
+  INLINE_GRAPH void generate_hash(GraphHashGenerator &hash) const;
 
   INLINE_GRAPH void make_identity();
   INLINE_GRAPH void extract_from(const NodeRelation *arc);
@@ -82,8 +85,8 @@ public:
   INLINE_GRAPH void set_computed_verified(UpdateSeq now);
 
   INLINE_GRAPH void cached_compose(const AllTransitionsWrapper &cache, 
-			     const AllTransitionsWrapper &value,
-			     UpdateSeq now);
+				   const AllTransitionsWrapper &value,
+				   UpdateSeq now);
 
 public:
   // STL-like definitions to allow read-only traversal of the

+ 14 - 0
panda/src/graph/bitMaskTransition.T

@@ -209,6 +209,20 @@ internal_compare_to(const NodeTransition *other) const {
   return result;
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: BitMaskTransition::internal_generate_hash
+//       Access: Protected, Virtual
+//  Description: Should be overridden by particular NodeTransitions to
+//               generate a hash value uniquifying this particular
+//               transition.
+////////////////////////////////////////////////////////////////////
+template<class MaskType>
+void BitMaskTransition<MaskType>::
+internal_generate_hash(GraphHashGenerator &hash) const {
+  _and.generate_hash(hash);
+  _or.generate_hash(hash);
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: BitMaskTransition::make_with_masks
 //       Access: Protected, Virtual

+ 1 - 0
panda/src/graph/bitMaskTransition.h

@@ -45,6 +45,7 @@ public:
 
 protected:
   virtual int internal_compare_to(const NodeTransition *other) const;
+  virtual void internal_generate_hash(GraphHashGenerator &hash) const;
 
 protected:
   virtual BitMaskTransition<MaskType> *

+ 27 - 0
panda/src/graph/graphHashGenerator.h

@@ -0,0 +1,27 @@
+// Filename: graphHashGenerator.h
+// Created by:  drose (14May01)
+// 
+////////////////////////////////////////////////////////////////////
+
+#ifndef GRAPHHASHGENERATOR_H
+#define GRAPHHASHGENERATOR_H
+
+////////////////////////////////////////////////////////////////////
+//
+// This file defines the typedef for GraphHashGenerator, which defines
+// the kind of HashGenerator used by all the NodeTransitions and
+// NodeAttributes.  By changing this typedef we can change the
+// fundamental hash generation mechanism for these things, if
+// necessary.
+//
+// These hash codes are used to uniquify NodeTransitions, particularly
+// in the cull traverser, but only if the hashtable based extensions
+// to STL are available (e.g. <hash_map> and <hash_set>).
+//
+////////////////////////////////////////////////////////////////////
+
+#include <checksumHashGenerator.h>
+
+typedef ChecksumHashGenerator GraphHashGenerator;
+
+#endif

+ 13 - 0
panda/src/graph/matrixTransition.T

@@ -191,6 +191,19 @@ internal_compare_to(const NodeTransition *other) const {
   //  return this - other;
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: MatrixTransition::internal_generate_hash
+//       Access: Protected, Virtual
+//  Description: Should be overridden by particular NodeTransitions to
+//               generate a hash value uniquifying this particular
+//               transition.
+////////////////////////////////////////////////////////////////////
+template<class Matrix>
+void MatrixTransition<Matrix>::
+internal_generate_hash(GraphHashGenerator &hash) const {
+  _matrix.generate_hash(hash, 0.00001);
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: MatrixTransition::make_with_matrix
 //       Access: Protected, Virtual

+ 1 - 0
panda/src/graph/matrixTransition.h

@@ -45,6 +45,7 @@ public:
 
 protected:
   virtual int internal_compare_to(const NodeTransition *other) const;
+  virtual void internal_generate_hash(GraphHashGenerator &hash) const;
 
 protected:
   virtual MatrixTransition<Matrix> *

+ 11 - 0
panda/src/graph/nodeTransition.I

@@ -129,6 +129,17 @@ compare_to(const NodeTransition &other) const {
   }
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: NodeTransition::generate_hash
+//       Access: Public
+//  Description: Adds the transition to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+INLINE_GRAPH void NodeTransition::
+generate_hash(GraphHashGenerator &hash) const {
+  hash.add_int(get_handle().get_index());
+  internal_generate_hash(hash);
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: NodeTransition::set_priority
 //       Access: Public

+ 11 - 0
panda/src/graph/nodeTransition.cxx

@@ -72,6 +72,17 @@ write(ostream &out, int indent_level) const {
   indent(out, indent_level) << *this << "\n";
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: NodeTransition::internal_generate_hash
+//       Access: Protected, Virtual
+//  Description: Should be overridden by particular NodeTransitions to
+//               generate a hash value uniquifying this particular
+//               transition.
+////////////////////////////////////////////////////////////////////
+void NodeTransition::
+internal_generate_hash(GraphHashGenerator &) const {
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: NodeTransition::state_changed
 //       Access: Protected

+ 6 - 0
panda/src/graph/nodeTransition.h

@@ -8,6 +8,8 @@
 
 #include <pandabase.h>
 
+#include "graphHashGenerator.h"
+
 #include <typedWritableReferenceCount.h>
 
 class Node;
@@ -41,6 +43,8 @@ protected:
   INLINE_GRAPH void operator = (const NodeTransition &copy);
 
 public:
+  typedef GraphHashGenerator HashGenerator;
+
   INLINE_GRAPH bool operator == (const NodeTransition &other) const;
   INLINE_GRAPH bool operator != (const NodeTransition &other) const;
   INLINE_GRAPH bool operator < (const NodeTransition &other) const;
@@ -49,6 +53,7 @@ public:
   INLINE_GRAPH bool operator >= (const NodeTransition &other) const;
 
   INLINE_GRAPH int compare_to(const NodeTransition &other) const;
+  INLINE_GRAPH void generate_hash(GraphHashGenerator &hash) const;
 
 PUBLISHED:
   INLINE_GRAPH void set_priority(int priority);
@@ -75,6 +80,7 @@ public:
 
 protected:
   virtual int internal_compare_to(const NodeTransition *other) const=0;
+  virtual void internal_generate_hash(GraphHashGenerator &hash) const;
 
   // And this is the internal function we'll call whenever our value
   // changes.

+ 13 - 0
panda/src/graph/nodeTransitionCache.cxx

@@ -84,6 +84,19 @@ compare_to(const NodeTransitionCache &other) const {
 			     other._cache.begin(), other._cache.end());
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: NodeTransitionCache::generate_hash
+//       Access: Public
+//  Description: Adds the transitions to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+void NodeTransitionCache::
+generate_hash(GraphHashGenerator &hash) const {
+  Cache::const_iterator ci;
+  for (ci = _cache.begin(); ci != _cache.end(); ++ci) {
+    (*ci).second.generate_hash(hash);
+  }
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: NodeTransitionCache::is_empty
 //       Access: Public

+ 4 - 0
panda/src/graph/nodeTransitionCache.h

@@ -9,6 +9,7 @@
 #include <pandabase.h>
 
 #include "nodeTransitionCacheEntry.h"
+#include "graphHashGenerator.h"
 
 #include <referenceCount.h>
 
@@ -22,12 +23,15 @@
 ////////////////////////////////////////////////////////////////////
 class EXPCL_PANDA NodeTransitionCache : public ReferenceCount {
 public:
+  typedef GraphHashGenerator HashGenerator;
+
   NodeTransitionCache();
   NodeTransitionCache(const NodeTransitions &nt);
   ~NodeTransitionCache();
 
   bool is_identity() const;
   int compare_to(const NodeTransitionCache &other) const;
+  void generate_hash(GraphHashGenerator &hash) const;
 
   bool is_empty() const;
   PT(NodeTransition) set_transition(TypeHandle handle, NodeTransition *trans);

+ 12 - 0
panda/src/graph/nodeTransitionCacheEntry.I

@@ -76,6 +76,18 @@ compare_to(const NodeTransitionCacheEntry &other) const {
   return _trans->compare_to(*other._trans);
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: NodeTransitionCacheEntry::generate_hash
+//       Access: Public
+//  Description: Adds the transition to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+INLINE_GRAPH void NodeTransitionCacheEntry::
+generate_hash(GraphHashGenerator &hash) const {
+  if (_trans != (NodeTransition *)NULL) {
+    _trans->generate_hash(hash);
+  }
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: NodeTransitionCacheEntry::clear
 //       Access: Public

+ 4 - 0
panda/src/graph/nodeTransitionCacheEntry.h

@@ -10,6 +10,7 @@
 
 #include "nodeTransition.h"
 #include "config_graph.h"
+#include "graphHashGenerator.h"
 
 #include <updateSeq.h>
 #include <pointerTo.h>
@@ -22,12 +23,15 @@
 ////////////////////////////////////////////////////////////////////
 class EXPCL_PANDA NodeTransitionCacheEntry {
 public:
+  typedef GraphHashGenerator HashGenerator;
+
   INLINE_GRAPH NodeTransitionCacheEntry(NodeTransition *trans = NULL);
   INLINE_GRAPH NodeTransitionCacheEntry(const NodeTransitionCacheEntry &copy);
   INLINE_GRAPH void operator = (const NodeTransitionCacheEntry &copy);
 
   INLINE_GRAPH bool is_identity() const;
   INLINE_GRAPH int compare_to(const NodeTransitionCacheEntry &other) const;
+  INLINE_GRAPH void generate_hash(GraphHashGenerator &hash) const;
 
   INLINE_GRAPH void clear();
 

+ 166 - 212
panda/src/linmath/lmatrix3_src.I

@@ -68,8 +68,8 @@ operator = (FLOATTYPE fill_value) {
 ////////////////////////////////////////////////////////////////////
 INLINE_LINMATH FLOATNAME(LMatrix3):: 
 FLOATNAME(LMatrix3)(FLOATTYPE e00, FLOATTYPE e01, FLOATTYPE e02,
-	 FLOATTYPE e10, FLOATTYPE e11, FLOATTYPE e12,
-	 FLOATTYPE e20, FLOATTYPE e21, FLOATTYPE e22) {
+		    FLOATTYPE e10, FLOATTYPE e11, FLOATTYPE e12,
+		    FLOATTYPE e20, FLOATTYPE e21, FLOATTYPE e22) {
   _m.m._00 = e00;
   _m.m._01 = e01;
   _m.m._02 = e02;
@@ -471,6 +471,143 @@ mult_cel(const FLOATNAME(LMatrix3) &other, int row, int col) const {
     return get_row(row).dot(other.get_col(col));
 }
 
+
+#define MATRIX3_PRODUCT(res, a, b)                   \
+res._m.m._00 = a._m.m._00*b._m.m._00 + a._m.m._01*b._m.m._10 + a._m.m._02*b._m.m._20;   \
+res._m.m._01 = a._m.m._00*b._m.m._01 + a._m.m._01*b._m.m._11 + a._m.m._02*b._m.m._21;   \
+res._m.m._02 = a._m.m._00*b._m.m._02 + a._m.m._01*b._m.m._12 + a._m.m._02*b._m.m._22;   \
+res._m.m._10 = a._m.m._10*b._m.m._00 + a._m.m._11*b._m.m._10 + a._m.m._12*b._m.m._20;   \
+res._m.m._11 = a._m.m._10*b._m.m._01 + a._m.m._11*b._m.m._11 + a._m.m._12*b._m.m._21;   \
+res._m.m._12 = a._m.m._10*b._m.m._02 + a._m.m._11*b._m.m._12 + a._m.m._12*b._m.m._22;   \
+res._m.m._20 = a._m.m._20*b._m.m._00 + a._m.m._21*b._m.m._10 + a._m.m._22*b._m.m._20;   \
+res._m.m._21 = a._m.m._20*b._m.m._01 + a._m.m._21*b._m.m._11 + a._m.m._22*b._m.m._21;   \
+res._m.m._22 = a._m.m._20*b._m.m._02 + a._m.m._21*b._m.m._12 + a._m.m._22*b._m.m._22;
+
+
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix3::matrix * matrix
+//       Access: Public
+//  Description: 
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH FLOATNAME(LMatrix3) FLOATNAME(LMatrix3)::
+operator * (const FLOATNAME(LMatrix3) &other) const {
+	FLOATNAME(LMatrix3) t;
+
+	MATRIX3_PRODUCT(t,(*this),other);
+/*
+typedef union {
+        struct {
+            FLOATTYPE     _m.m._11, _m.m._12, _m.m._13;
+            FLOATTYPE     _m.m._21, _m.m._22, _m.m._23;
+            FLOATTYPE     _m.m._31, _m.m._32, _m.m._33;
+        };
+
+		FLOATTYPE m[3][3];
+    } MYMATRIX3;
+
+	FLOATNAME(LMatrix3) t;
+
+	MYMATRIX3 *result_ptr=(MYMATRIX3 *)t.get_m.data();
+	MYMATRIX3 *mat1_ptr=(MYMATRIX3 *)this->get_m.data();
+	MYMATRIX3 *mat2_ptr=(MYMATRIX3 *)other.get_m.data();
+
+	MATRIX3_PRODUCT(result_ptr,mat1_ptr,mat2_ptr);
+*/
+/*
+  t(0, 0) = mult_cel(other, 0, 0);
+  t(0, 1) = mult_cel(other, 0, 1);
+  t(0, 2) = mult_cel(other, 0, 2);
+
+  t(1, 0) = mult_cel(other, 1, 0);
+  t(1, 1) = mult_cel(other, 1, 1);
+  t(1, 2) = mult_cel(other, 1, 2);
+
+  t(2, 0) = mult_cel(other, 2, 0);
+  t(2, 1) = mult_cel(other, 2, 1);
+  t(2, 2) = mult_cel(other, 2, 2);
+*/
+  return t;
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix3::matrix * scalar
+//       Access: Public
+//  Description: 
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH FLOATNAME(LMatrix3) FLOATNAME(LMatrix3)::
+operator * (FLOATTYPE scalar) const {
+  FLOATNAME(LMatrix3) t;
+
+  t._m.m._00 = _m.m._00 * scalar;
+  t._m.m._01 = _m.m._01 * scalar;
+  t._m.m._02 = _m.m._02 * scalar;
+
+  t._m.m._10 = _m.m._10 * scalar;
+  t._m.m._11 = _m.m._11 * scalar;
+  t._m.m._12 = _m.m._12 * scalar;
+
+  t._m.m._20 = _m.m._20 * scalar;
+  t._m.m._21 = _m.m._21 * scalar;
+  t._m.m._22 = _m.m._22 * scalar;
+
+  return t;
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix3::matrix / scalar
+//       Access: Public
+//  Description: 
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH FLOATNAME(LMatrix3) FLOATNAME(LMatrix3)::
+operator / (FLOATTYPE scalar) const {
+  FLOATTYPE recip_scalar = 1.0/scalar;
+  return (*this) * recip_scalar;
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix3::matrix += matrix
+//       Access: Public
+//  Description: Performs a memberwise addition between two matrices.
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH FLOATNAME(LMatrix3) &FLOATNAME(LMatrix3)::
+operator += (const FLOATNAME(LMatrix3) &other) {
+  _m.m._00 += other._m.m._00;
+  _m.m._01 += other._m.m._01;
+  _m.m._02 += other._m.m._02;
+
+  _m.m._10 += other._m.m._10;
+  _m.m._11 += other._m.m._11;
+  _m.m._12 += other._m.m._12;
+
+  _m.m._20 += other._m.m._20;
+  _m.m._21 += other._m.m._21;
+  _m.m._22 += other._m.m._22;
+
+  return *this;
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix3::matrix -= matrix
+//       Access: Public
+//  Description: Performs a memberwise subtraction between two matrices.
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH FLOATNAME(LMatrix3) &FLOATNAME(LMatrix3)::
+operator -= (const FLOATNAME(LMatrix3) &other) {
+  _m.m._00 -= other._m.m._00;
+  _m.m._01 -= other._m.m._01;
+  _m.m._02 -= other._m.m._02;
+
+  _m.m._10 -= other._m.m._10;
+  _m.m._11 -= other._m.m._11;
+  _m.m._12 -= other._m.m._12;
+
+  _m.m._20 -= other._m.m._20;
+  _m.m._21 -= other._m.m._21;
+  _m.m._22 -= other._m.m._22;
+
+  return *this;
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: LMatrix3::matrix *= matrix
 //       Access: Public
@@ -567,19 +704,6 @@ transpose_in_place() {
   #undef SWAP__
 }
 
-
-////////////////////////////////////////////////////////////////////
-//     Function: LMatrix3::transpose
-//  Description: Transposes the given matrix and returns it.
-////////////////////////////////////////////////////////////////////
-INLINE_LINMATH FLOATNAME(LMatrix3)
-transpose(const FLOATNAME(LMatrix3) &a) {
-
-  FLOATNAME(LMatrix3) result;
-  result.transpose_from(a);
-  return result;
-}
-
 // Matrix inversion code from Numerical Recipes in C.
 
 // dont trust compilers to inline these
@@ -676,18 +800,6 @@ invert_in_place() {
   return invert_from(temp);
 }
 
-////////////////////////////////////////////////////////////////////
-//     Function: LMatrix3::invert
-//  Description: Inverts the given matrix and returns it.
-////////////////////////////////////////////////////////////////////
-INLINE_LINMATH FLOATNAME(LMatrix3)
-invert(const FLOATNAME(LMatrix3) &a) {
-  FLOATNAME(LMatrix3) result;
-  bool nonsingular = result.invert_from(a);
-  nassertr(nonsingular, FLOATNAME(LMatrix3)::ident_mat());
-  return result;
-}
-
 ////////////////////////////////////////////////////////////////////
 //     Function: LMatrix::translate_mat
 //       Access: Public, Static
@@ -781,24 +893,15 @@ rotate_mat(FLOATTYPE angle, FLOATNAME(LVecBase3) axis,
   FLOATTYPE axis_2 = axis._v.v._2;
 
   // Normalize the axis.  
+  FLOATTYPE length_sq = axis_0 * axis_0 + axis_1 * axis_1 + axis_2 * axis_2;
+#ifdef _DEBUG
+  nassertr(length_sq != 0.0, ident_mat());
+#endif
+  FLOATTYPE recip_length = 1.0/csqrt(length_sq);
   
-/*
-  // hack check for prenormalization, only works for simple unit vecs, 
-  // which is what we usually pass in anyway. screws up if you happen to
-  // pass in something like (.5,.5,0).  need to add flag parameter so caller
-  // can request normalization if needed
-  if((cabs(axis_0)+cabs(axis_1)+cabs(axis_2)) != 1.0) {
-*/  
-	  FLOATTYPE length_sq = axis_0 * axis_0 + axis_1 * axis_1 + axis_2 * axis_2;
-	  #ifdef _DEBUG
-	      nassertr(length_sq != 0.0, ident_mat());
-   	  #endif
-	  FLOATTYPE recip_length = 1.0/csqrt(length_sq);
-
-	  axis_0 *= recip_length;
-	  axis_1 *= recip_length;
-	  axis_2 *= recip_length;  
-//  }
+  axis_0 *= recip_length;
+  axis_1 *= recip_length;
+  axis_2 *= recip_length;  
 
   FLOATTYPE angle_rad=deg_2_rad(angle);
   FLOATTYPE s,c;
@@ -949,184 +1052,35 @@ almost_equal(const FLOATNAME(LMatrix3) &other) const {
 }
 
 ////////////////////////////////////////////////////////////////////
-//     Function: LMatrix3::output
-//       Access: Public
-//  Description: 
-////////////////////////////////////////////////////////////////////
-INLINE_LINMATH void FLOATNAME(LMatrix3)::
-output(ostream &out) const {
-  out << "[ " 
-      << MAYBE_ZERO(_m.m._00) << " "
-      << MAYBE_ZERO(_m.m._01) << " " 
-      << MAYBE_ZERO(_m.m._02)
-      << " ] [ "
-      << MAYBE_ZERO(_m.m._10) << " "
-      << MAYBE_ZERO(_m.m._11) << " " 
-      << MAYBE_ZERO(_m.m._12)
-      << " ] [ "
-      << MAYBE_ZERO(_m.m._20) << " "
-      << MAYBE_ZERO(_m.m._21) << " " 
-      << MAYBE_ZERO(_m.m._22)
-      << " ]";
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: LMatrix3::write
+//     Function: LMatrix3::generate_hash
 //       Access: Public
-//  Description: 
+//  Description: Adds the vector to the indicated hash generator.
 ////////////////////////////////////////////////////////////////////
 INLINE_LINMATH void FLOATNAME(LMatrix3)::
-write(ostream &out, int indent_level) const {
-  indent(out, indent_level) 
-    << MAYBE_ZERO(_m.m._00) << " "
-    << MAYBE_ZERO(_m.m._01) << " " 
-    << MAYBE_ZERO(_m.m._02)
-    << "\n";
-  indent(out, indent_level)
-    << MAYBE_ZERO(_m.m._10) << " "
-    << MAYBE_ZERO(_m.m._11) << " " 
-    << MAYBE_ZERO(_m.m._12)
-    << "\n";
-  indent(out, indent_level)
-    << MAYBE_ZERO(_m.m._20) << " "
-    << MAYBE_ZERO(_m.m._21) << " " 
-    << MAYBE_ZERO(_m.m._22)
-    << "\n";
-}
-
-
-#define MATRIX3_PRODUCT(res, a, b)                   \
-res._m.m._00 = a._m.m._00*b._m.m._00 + a._m.m._01*b._m.m._10 + a._m.m._02*b._m.m._20;   \
-res._m.m._01 = a._m.m._00*b._m.m._01 + a._m.m._01*b._m.m._11 + a._m.m._02*b._m.m._21;   \
-res._m.m._02 = a._m.m._00*b._m.m._02 + a._m.m._01*b._m.m._12 + a._m.m._02*b._m.m._22;   \
-res._m.m._10 = a._m.m._10*b._m.m._00 + a._m.m._11*b._m.m._10 + a._m.m._12*b._m.m._20;   \
-res._m.m._11 = a._m.m._10*b._m.m._01 + a._m.m._11*b._m.m._11 + a._m.m._12*b._m.m._21;   \
-res._m.m._12 = a._m.m._10*b._m.m._02 + a._m.m._11*b._m.m._12 + a._m.m._12*b._m.m._22;   \
-res._m.m._20 = a._m.m._20*b._m.m._00 + a._m.m._21*b._m.m._10 + a._m.m._22*b._m.m._20;   \
-res._m.m._21 = a._m.m._20*b._m.m._01 + a._m.m._21*b._m.m._11 + a._m.m._22*b._m.m._21;   \
-res._m.m._22 = a._m.m._20*b._m.m._02 + a._m.m._21*b._m.m._12 + a._m.m._22*b._m.m._22;
-
-
-////////////////////////////////////////////////////////////////////
-//     Function: LMatrix3::matrix * matrix
-//       Access: Public
-//  Description: 
-////////////////////////////////////////////////////////////////////
-INLINE_LINMATH FLOATNAME(LMatrix3) FLOATNAME(LMatrix3)::
-operator * (const FLOATNAME(LMatrix3) &other) const {
-	FLOATNAME(LMatrix3) t;
-
-	MATRIX3_PRODUCT(t,(*this),other);
-/*
-typedef union {
-        struct {
-            FLOATTYPE     _m.m._11, _m.m._12, _m.m._13;
-            FLOATTYPE     _m.m._21, _m.m._22, _m.m._23;
-            FLOATTYPE     _m.m._31, _m.m._32, _m.m._33;
-        };
-
-		FLOATTYPE m[3][3];
-    } MYMATRIX3;
-
-	FLOATNAME(LMatrix3) t;
-
-	MYMATRIX3 *result_ptr=(MYMATRIX3 *)t.get_m.data();
-	MYMATRIX3 *mat1_ptr=(MYMATRIX3 *)this->get_m.data();
-	MYMATRIX3 *mat2_ptr=(MYMATRIX3 *)other.get_m.data();
-
-	MATRIX3_PRODUCT(result_ptr,mat1_ptr,mat2_ptr);
-*/
-/*
-  t(0, 0) = mult_cel(other, 0, 0);
-  t(0, 1) = mult_cel(other, 0, 1);
-  t(0, 2) = mult_cel(other, 0, 2);
-
-  t(1, 0) = mult_cel(other, 1, 0);
-  t(1, 1) = mult_cel(other, 1, 1);
-  t(1, 2) = mult_cel(other, 1, 2);
-
-  t(2, 0) = mult_cel(other, 2, 0);
-  t(2, 1) = mult_cel(other, 2, 1);
-  t(2, 2) = mult_cel(other, 2, 2);
-*/
-  return t;
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: LMatrix3::matrix * scalar
-//       Access: Public
-//  Description: 
-////////////////////////////////////////////////////////////////////
-INLINE_LINMATH FLOATNAME(LMatrix3) FLOATNAME(LMatrix3)::
-operator * (FLOATTYPE scalar) const {
-  FLOATNAME(LMatrix3) t;
-
-  t._m.m._00 = _m.m._00 * scalar;
-  t._m.m._01 = _m.m._01 * scalar;
-  t._m.m._02 = _m.m._02 * scalar;
-
-  t._m.m._10 = _m.m._10 * scalar;
-  t._m.m._11 = _m.m._11 * scalar;
-  t._m.m._12 = _m.m._12 * scalar;
-
-  t._m.m._20 = _m.m._20 * scalar;
-  t._m.m._21 = _m.m._21 * scalar;
-  t._m.m._22 = _m.m._22 * scalar;
-
-  return t;
+generate_hash(ChecksumHashGenerator &hash) const {
+  generate_hash(hash, NEARLY_ZERO(FLOATTYPE));
 }
 
-////////////////////////////////////////////////////////////////////
-//     Function: LMatrix3::matrix / scalar
-//       Access: Public
-//  Description: 
-////////////////////////////////////////////////////////////////////
-INLINE_LINMATH FLOATNAME(LMatrix3) FLOATNAME(LMatrix3)::
-operator / (FLOATTYPE scalar) const {
-  FLOATTYPE recip_scalar = 1.0/scalar;
-  return (*this) * recip_scalar;
-}
 
 ////////////////////////////////////////////////////////////////////
-//     Function: LMatrix3::matrix += matrix
-//       Access: Public
-//  Description: Performs a memberwise addition between two matrices.
+//     Function: transpose
+//  Description: Transposes the given matrix and returns it.
 ////////////////////////////////////////////////////////////////////
-INLINE_LINMATH FLOATNAME(LMatrix3) &FLOATNAME(LMatrix3)::
-operator += (const FLOATNAME(LMatrix3) &other) {
-  _m.m._00 += other._m.m._00;
-  _m.m._01 += other._m.m._01;
-  _m.m._02 += other._m.m._02;
-
-  _m.m._10 += other._m.m._10;
-  _m.m._11 += other._m.m._11;
-  _m.m._12 += other._m.m._12;
-
-  _m.m._20 += other._m.m._20;
-  _m.m._21 += other._m.m._21;
-  _m.m._22 += other._m.m._22;
-
-  return *this;
+INLINE_LINMATH FLOATNAME(LMatrix3)
+transpose(const FLOATNAME(LMatrix3) &a) {
+  FLOATNAME(LMatrix3) result;
+  result.transpose_from(a);
+  return result;
 }
 
 ////////////////////////////////////////////////////////////////////
-//     Function: LMatrix3::matrix -= matrix
-//       Access: Public
-//  Description: Performs a memberwise subtraction between two matrices.
+//     Function: invert
+//  Description: Inverts the given matrix and returns it.
 ////////////////////////////////////////////////////////////////////
-INLINE_LINMATH FLOATNAME(LMatrix3) &FLOATNAME(LMatrix3)::
-operator -= (const FLOATNAME(LMatrix3) &other) {
-  _m.m._00 -= other._m.m._00;
-  _m.m._01 -= other._m.m._01;
-  _m.m._02 -= other._m.m._02;
-
-  _m.m._10 -= other._m.m._10;
-  _m.m._11 -= other._m.m._11;
-  _m.m._12 -= other._m.m._12;
-
-  _m.m._20 -= other._m.m._20;
-  _m.m._21 -= other._m.m._21;
-  _m.m._22 -= other._m.m._22;
-
-  return *this;
+INLINE_LINMATH FLOATNAME(LMatrix3)
+invert(const FLOATNAME(LMatrix3) &a) {
+  FLOATNAME(LMatrix3) result;
+  bool nonsingular = result.invert_from(a);
+  nassertr(nonsingular, FLOATNAME(LMatrix3)::ident_mat());
+  return result;
 }

+ 75 - 21
panda/src/linmath/lmatrix3_src.cxx

@@ -62,33 +62,75 @@ almost_equal(const FLOATNAME(LMatrix3) &other, FLOATTYPE threshold) const {
 	  IS_THRESHOLD_EQUAL((*this)(2, 2), other(2, 2), threshold));
 }
 
+
 ////////////////////////////////////////////////////////////////////
-//     Function: LMatrix3::init_type
-//       Access: Public, Static
+//     Function: LMatrix3::output
+//       Access: Public
 //  Description: 
 ////////////////////////////////////////////////////////////////////
 void FLOATNAME(LMatrix3)::
-init_type() {
-  if (_type_handle == TypeHandle::none()) {
-    // Format a string to describe the type.
-    string name = "LMatrix3";
-    name += FLOATTOKEN; 
-    register_type(_type_handle, name);
-  }
+output(ostream &out) const {
+  out << "[ " 
+      << MAYBE_ZERO(_m.m._00) << " "
+      << MAYBE_ZERO(_m.m._01) << " " 
+      << MAYBE_ZERO(_m.m._02)
+      << " ] [ "
+      << MAYBE_ZERO(_m.m._10) << " "
+      << MAYBE_ZERO(_m.m._11) << " " 
+      << MAYBE_ZERO(_m.m._12)
+      << " ] [ "
+      << MAYBE_ZERO(_m.m._20) << " "
+      << MAYBE_ZERO(_m.m._21) << " " 
+      << MAYBE_ZERO(_m.m._22)
+      << " ]";
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix3::write
+//       Access: Public
+//  Description: 
+////////////////////////////////////////////////////////////////////
+void FLOATNAME(LMatrix3)::
+write(ostream &out, int indent_level) const {
+  indent(out, indent_level) 
+    << MAYBE_ZERO(_m.m._00) << " "
+    << MAYBE_ZERO(_m.m._01) << " " 
+    << MAYBE_ZERO(_m.m._02)
+    << "\n";
+  indent(out, indent_level)
+    << MAYBE_ZERO(_m.m._10) << " "
+    << MAYBE_ZERO(_m.m._11) << " " 
+    << MAYBE_ZERO(_m.m._12)
+    << "\n";
+  indent(out, indent_level)
+    << MAYBE_ZERO(_m.m._20) << " "
+    << MAYBE_ZERO(_m.m._21) << " " 
+    << MAYBE_ZERO(_m.m._22)
+    << "\n";
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix3::generate_hash
+//       Access: Public
+//  Description: Adds the vector to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+void FLOATNAME(LMatrix3)::
+generate_hash(ChecksumHashGenerator &hash, FLOATTYPE threshold) const {
+  for(int i = 0; i < 3; i++) {
+    for(int j = 0; j < 3; j++) {
+      hash.add_fp(get_cell(i,j), threshold);
+    }
+  }
+}
 
 ////////////////////////////////////////////////////////////////////
 //     Function: LMatrix3::write_datagram
 //  Description: Writes the matrix to the datagram
 ////////////////////////////////////////////////////////////////////
 void FLOATNAME(LMatrix3)::
-write_datagram(Datagram &destination) const
-{
-  for(int i = 0; i < 3; i++)
-  {
-    for(int j = 0; j < 3; j++)
-    {
+write_datagram(Datagram &destination) const {
+  for(int i = 0; i < 3; i++) {
+    for(int j = 0; j < 3; j++) {
       destination.add_float32(get_cell(i,j));
     }
   }
@@ -99,14 +141,26 @@ write_datagram(Datagram &destination) const
 //  Description: Reads itself out of the datagram
 ////////////////////////////////////////////////////////////////////
 void FLOATNAME(LMatrix3)::
-read_datagram(DatagramIterator &scan) 
-{
-  for(int i = 0; i < 3; i++)
-  {
-    for(int j = 0; j < 3; j++)
-    {
+read_datagram(DatagramIterator &scan) {
+  for(int i = 0; i < 3; i++) {
+    for(int j = 0; j < 3; j++) {
       set_cell(i, j, scan.get_float32());
     }
   }
 }
 
+
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix3::init_type
+//       Access: Public, Static
+//  Description: 
+////////////////////////////////////////////////////////////////////
+void FLOATNAME(LMatrix3)::
+init_type() {
+  if (_type_handle == TypeHandle::none()) {
+    // Format a string to describe the type.
+    string name = "LMatrix3";
+    name += FLOATTOKEN; 
+    register_type(_type_handle, name);
+  }
+}

+ 32 - 20
panda/src/linmath/lmatrix3_src.h

@@ -21,13 +21,13 @@ PUBLISHED:
   INLINE_LINMATH FLOATNAME(LMatrix3) &operator = (const FLOATNAME(LMatrix3) &other);
   INLINE_LINMATH FLOATNAME(LMatrix3) &operator = (FLOATTYPE fill_value);
   INLINE_LINMATH FLOATNAME(LMatrix3)(FLOATTYPE e00, FLOATTYPE e01, FLOATTYPE e02,
-			     FLOATTYPE e10, FLOATTYPE e11, FLOATTYPE e12,
-			     FLOATTYPE e20, FLOATTYPE e21, FLOATTYPE e22);
+				     FLOATTYPE e10, FLOATTYPE e11, FLOATTYPE e12,
+				     FLOATTYPE e20, FLOATTYPE e21, FLOATTYPE e22);
 
   void fill(FLOATTYPE fill_value);
   INLINE_LINMATH void set(FLOATTYPE e00, FLOATTYPE e01, FLOATTYPE e02,
-		  FLOATTYPE e10, FLOATTYPE e11, FLOATTYPE e12,
-		  FLOATTYPE e20, FLOATTYPE e21, FLOATTYPE e22);
+			  FLOATTYPE e10, FLOATTYPE e11, FLOATTYPE e12,
+			  FLOATTYPE e20, FLOATTYPE e21, FLOATTYPE e22);
 
   INLINE_LINMATH void set_row(int row, const FLOATNAME(LVecBase3) &v);
   INLINE_LINMATH void set_col(int col, const FLOATNAME(LVecBase3) &v);
@@ -108,23 +108,32 @@ PUBLISHED:
   // The following named constructors return 3x3 matrices suitable for
   // affine transforms in 2-d coordinate space.
 
-  static INLINE_LINMATH FLOATNAME(LMatrix3) translate_mat(const FLOATNAME(LVecBase2) &trans);
-  static INLINE_LINMATH FLOATNAME(LMatrix3) translate_mat(FLOATTYPE tx, FLOATTYPE ty);
-  static INLINE_LINMATH FLOATNAME(LMatrix3) rotate_mat(FLOATTYPE angle);
-  static INLINE_LINMATH FLOATNAME(LMatrix3) scale_mat(const FLOATNAME(LVecBase2) &scale);
-  static INLINE_LINMATH FLOATNAME(LMatrix3) scale_mat(FLOATTYPE sx, FLOATTYPE sy);
+  static INLINE_LINMATH FLOATNAME(LMatrix3)
+    translate_mat(const FLOATNAME(LVecBase2) &trans);
+  static INLINE_LINMATH FLOATNAME(LMatrix3)
+    translate_mat(FLOATTYPE tx, FLOATTYPE ty);
+  static INLINE_LINMATH FLOATNAME(LMatrix3)
+    rotate_mat(FLOATTYPE angle);
+  static INLINE_LINMATH FLOATNAME(LMatrix3)
+    scale_mat(const FLOATNAME(LVecBase2) &scale);
+  static INLINE_LINMATH FLOATNAME(LMatrix3) 
+    scale_mat(FLOATTYPE sx, FLOATTYPE sy);
 
   // The following named constructors return 3x3 matrices suitable for
   // scale/rotate transforms in 3-d coordinate space.
-  static INLINE_LINMATH FLOATNAME(LMatrix3) rotate_mat(FLOATTYPE angle,
-				      FLOATNAME(LVecBase3) axis,
-				      CoordinateSystem cs = CS_default);
-  static INLINE_LINMATH FLOATNAME(LMatrix3) rotate_mat_normaxis(FLOATTYPE angle,
-				      const FLOATNAME(LVecBase3) &axis,
-				      CoordinateSystem cs = CS_default);
-
-  static INLINE_LINMATH FLOATNAME(LMatrix3) scale_mat(const FLOATNAME(LVecBase3) &scale);
-  static INLINE_LINMATH FLOATNAME(LMatrix3) scale_mat(FLOATTYPE sx, FLOATTYPE sy, FLOATTYPE sz);
+  static INLINE_LINMATH FLOATNAME(LMatrix3) 
+    rotate_mat(FLOATTYPE angle,
+	       FLOATNAME(LVecBase3) axis,
+	       CoordinateSystem cs = CS_default);
+  static INLINE_LINMATH FLOATNAME(LMatrix3)
+    rotate_mat_normaxis(FLOATTYPE angle,
+			const FLOATNAME(LVecBase3) &axis,
+			CoordinateSystem cs = CS_default);
+  
+  static INLINE_LINMATH FLOATNAME(LMatrix3)
+    scale_mat(const FLOATNAME(LVecBase3) &scale);
+  static INLINE_LINMATH FLOATNAME(LMatrix3)
+    scale_mat(FLOATTYPE sx, FLOATTYPE sy, FLOATTYPE sz);
 
   // We don't have a scale_mat() that takes a single uniform scale
   // parameter, because it would be ambiguous whether we mean a 2-d or
@@ -135,11 +144,14 @@ PUBLISHED:
 
   INLINE_LINMATH bool almost_equal(const FLOATNAME(LMatrix3) &other) const;
   
-  INLINE_LINMATH void output(ostream &out) const;
-  INLINE_LINMATH void write(ostream &out, int indent_level = 0) const;
+  void output(ostream &out) const;
+  void write(ostream &out, int indent_level = 0) const;
 
 public:
+  INLINE_LINMATH void generate_hash(ChecksumHashGenerator &hash) const;
+  void generate_hash(ChecksumHashGenerator &hash, FLOATTYPE threshold) const;
 
+public:
   union {
         struct {
 	   FLOATTYPE  _00, _01, _02;

+ 27 - 81
panda/src/linmath/lmatrix4_src.I

@@ -939,17 +939,6 @@ transpose_in_place() {
   #undef SWAP__
 }
 
-////////////////////////////////////////////////////////////////////
-//     Function: LMatrix4::transpose
-//  Description: Transposes the given matrix and returns it.
-////////////////////////////////////////////////////////////////////
-INLINE_LINMATH FLOATNAME(LMatrix4)
-transpose(const FLOATNAME(LMatrix4) &a) {
-  FLOATNAME(LMatrix4) result;
-  result.transpose_from(a);
-  return result;
-}
-
 ////////////////////////////////////////////////////////////////////
 //     Function: LMatrix4::invert_from
 //       Access: Public
@@ -1071,18 +1060,6 @@ invert_in_place() {
   return invert_from(temp);
 }
 
-////////////////////////////////////////////////////////////////////
-//     Function: LMatrix4::invert
-//  Description: Inverts the given matrix and returns it.
-////////////////////////////////////////////////////////////////////
-INLINE_LINMATH FLOATNAME(LMatrix4)
-invert(const FLOATNAME(LMatrix4) &a) {
-  FLOATNAME(LMatrix4) result;
-  bool nonsingular = result.invert_from(a);
-  nassertr(nonsingular, FLOATNAME(LMatrix4)::ident_mat());
-  return result;
-}
-
 ////////////////////////////////////////////////////////////////////
 //     Function: LMatrix::translate_mat
 //       Access: Public, Static
@@ -1340,67 +1317,36 @@ almost_equal(const FLOATNAME(LMatrix4) &other) const {
 }
 
 ////////////////////////////////////////////////////////////////////
-//     Function: LMatrix4::output
-//       Access: Public
-//  Description: 
-////////////////////////////////////////////////////////////////////
-
-INLINE_LINMATH void FLOATNAME(LMatrix4)::
-output(ostream &out) const {
-  out << "[ " 
-      << MAYBE_ZERO(_m.m._00) << " "
-      << MAYBE_ZERO(_m.m._01) << " " 
-      << MAYBE_ZERO(_m.m._02) << " "
-      << MAYBE_ZERO(_m.m._03)
-      << " ] [ "
-      << MAYBE_ZERO(_m.m._10) << " "
-      << MAYBE_ZERO(_m.m._11) << " " 
-      << MAYBE_ZERO(_m.m._12) << " "
-      << MAYBE_ZERO(_m.m._13)
-      << " ] [ "
-      << MAYBE_ZERO(_m.m._20) << " "
-      << MAYBE_ZERO(_m.m._21) << " " 
-      << MAYBE_ZERO(_m.m._22) << " "
-      << MAYBE_ZERO(_m.m._23)
-      << " ] [ "
-      << MAYBE_ZERO(_m.m._30) << " "
-      << MAYBE_ZERO(_m.m._31) << " " 
-      << MAYBE_ZERO(_m.m._32) << " "
-      << MAYBE_ZERO(_m.m._33)
-      << " ]";
-}
-
-////////////////////////////////////////////////////////////////////
-//     Function: LMatrix4::write
+//     Function: LMatrix4::generate_hash
 //       Access: Public
-//  Description: 
+//  Description: Adds the vector to the indicated hash generator.
 ////////////////////////////////////////////////////////////////////
 INLINE_LINMATH void FLOATNAME(LMatrix4)::
-write(ostream &out, int indent_level) const {
-  indent(out, indent_level)
-    << MAYBE_ZERO(_m.m._00) << " "
-    << MAYBE_ZERO(_m.m._01) << " " 
-    << MAYBE_ZERO(_m.m._02) << " "
-    << MAYBE_ZERO(_m.m._03)
-    << "\n";
-  indent(out, indent_level)
-    << MAYBE_ZERO(_m.m._10) << " "
-    << MAYBE_ZERO(_m.m._11) << " " 
-    << MAYBE_ZERO(_m.m._12) << " "
-    << MAYBE_ZERO(_m.m._13)
-    << "\n";
-  indent(out, indent_level)
-    << MAYBE_ZERO(_m.m._20) << " "
-    << MAYBE_ZERO(_m.m._21) << " " 
-    << MAYBE_ZERO(_m.m._22) << " "
-    << MAYBE_ZERO(_m.m._23)
-    << "\n";
-  indent(out, indent_level)
-    << MAYBE_ZERO(_m.m._30) << " "
-    << MAYBE_ZERO(_m.m._31) << " " 
-    << MAYBE_ZERO(_m.m._32) << " "
-    << MAYBE_ZERO(_m.m._33)
-    << "\n";
+generate_hash(ChecksumHashGenerator &hash) const {
+  generate_hash(hash, NEARLY_ZERO(FLOATTYPE));
 }
 
 
+
+////////////////////////////////////////////////////////////////////
+//     Function: transpose
+//  Description: Transposes the given matrix and returns it.
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH FLOATNAME(LMatrix4)
+transpose(const FLOATNAME(LMatrix4) &a) {
+  FLOATNAME(LMatrix4) result;
+  result.transpose_from(a);
+  return result;
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: invert
+//  Description: Inverts the given matrix and returns it.
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH FLOATNAME(LMatrix4)
+invert(const FLOATNAME(LMatrix4) &a) {
+  FLOATNAME(LMatrix4) result;
+  bool nonsingular = result.invert_from(a);
+  nassertr(nonsingular, FLOATNAME(LMatrix4)::ident_mat());
+  return result;
+}

+ 113 - 42
panda/src/linmath/lmatrix4_src.cxx

@@ -87,6 +87,25 @@ convert_mat(CoordinateSystem from, CoordinateSystem to) {
   return ident_mat();
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix4::compare_to
+//       Access: Public
+//  Description: Sorts matrices lexicographically, componentwise.
+//               Returns a number less than 0 if this matrix sorts
+//               before the other one, greater than zero if it sorts
+//               after, 0 if they are equivalent (within the indicated
+//               tolerance).
+////////////////////////////////////////////////////////////////////
+int FLOATNAME(LMatrix4)::
+compare_to(const FLOATNAME(LMatrix4) &other, FLOATTYPE threshold) const {
+  for (int i = 0; i < 16; i++) {
+    if (!IS_THRESHOLD_EQUAL(_m.data[i], other._m.data[i], threshold)) {
+      return (_m.data[i] < other._m.data[i]) ? -1 : 1;
+    }
+  }
+  return 0;
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: LMatrix4::almost_equal
 //       Access: Public
@@ -114,6 +133,84 @@ almost_equal(const FLOATNAME(LMatrix4) &other, FLOATTYPE threshold) const {
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix4::output
+//       Access: Public
+//  Description: 
+////////////////////////////////////////////////////////////////////
+void FLOATNAME(LMatrix4)::
+output(ostream &out) const {
+  out << "[ " 
+      << MAYBE_ZERO(_m.m._00) << " "
+      << MAYBE_ZERO(_m.m._01) << " " 
+      << MAYBE_ZERO(_m.m._02) << " "
+      << MAYBE_ZERO(_m.m._03)
+      << " ] [ "
+      << MAYBE_ZERO(_m.m._10) << " "
+      << MAYBE_ZERO(_m.m._11) << " " 
+      << MAYBE_ZERO(_m.m._12) << " "
+      << MAYBE_ZERO(_m.m._13)
+      << " ] [ "
+      << MAYBE_ZERO(_m.m._20) << " "
+      << MAYBE_ZERO(_m.m._21) << " " 
+      << MAYBE_ZERO(_m.m._22) << " "
+      << MAYBE_ZERO(_m.m._23)
+      << " ] [ "
+      << MAYBE_ZERO(_m.m._30) << " "
+      << MAYBE_ZERO(_m.m._31) << " " 
+      << MAYBE_ZERO(_m.m._32) << " "
+      << MAYBE_ZERO(_m.m._33)
+      << " ]";
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix4::write
+//       Access: Public
+//  Description: 
+////////////////////////////////////////////////////////////////////
+void FLOATNAME(LMatrix4)::
+write(ostream &out, int indent_level) const {
+  indent(out, indent_level)
+    << MAYBE_ZERO(_m.m._00) << " "
+    << MAYBE_ZERO(_m.m._01) << " " 
+    << MAYBE_ZERO(_m.m._02) << " "
+    << MAYBE_ZERO(_m.m._03)
+    << "\n";
+  indent(out, indent_level)
+    << MAYBE_ZERO(_m.m._10) << " "
+    << MAYBE_ZERO(_m.m._11) << " " 
+    << MAYBE_ZERO(_m.m._12) << " "
+    << MAYBE_ZERO(_m.m._13)
+    << "\n";
+  indent(out, indent_level)
+    << MAYBE_ZERO(_m.m._20) << " "
+    << MAYBE_ZERO(_m.m._21) << " " 
+    << MAYBE_ZERO(_m.m._22) << " "
+    << MAYBE_ZERO(_m.m._23)
+    << "\n";
+  indent(out, indent_level)
+    << MAYBE_ZERO(_m.m._30) << " "
+    << MAYBE_ZERO(_m.m._31) << " " 
+    << MAYBE_ZERO(_m.m._32) << " "
+    << MAYBE_ZERO(_m.m._33)
+    << "\n";
+}
+
+
+////////////////////////////////////////////////////////////////////
+//     Function: LMatrix4::generate_hash
+//       Access: Public
+//  Description: Adds the vector to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+void FLOATNAME(LMatrix4)::
+generate_hash(ChecksumHashGenerator &hash, FLOATTYPE threshold) const {
+  for(int i = 0; i < 4; i++) {
+    for(int j = 0; j < 4; j++) {
+      hash.add_fp(get_cell(i,j), threshold);
+    }
+  }
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: LMatrix4::decompose_mat
 //       Access: Private
@@ -222,33 +319,14 @@ back_sub_mat(int index[4], FLOATNAME(LMatrix4) &inv, int row) const {
   return true;
 }
 
-////////////////////////////////////////////////////////////////////
-//     Function: LMatrix4::init_type
-//       Access: Public, Static
-//  Description: 
-////////////////////////////////////////////////////////////////////
-void FLOATNAME(LMatrix4)::
-init_type() {
-  if (_type_handle == TypeHandle::none()) {
-    // Format a string to describe the type.
-    string name = "LMatrix4";
-    name += FLOATTOKEN;
-    register_type(_type_handle, name);
-  }
-}
-
-
 ////////////////////////////////////////////////////////////////////
 //     Function: LMatrix4::write_datagram
 //  Description: Writes the matrix to the datagram
 ////////////////////////////////////////////////////////////////////
 void FLOATNAME(LMatrix4)::
-write_datagram(Datagram &destination) const
-{
-  for(int i = 0; i < 4; i++)
-  {
-    for(int j = 0; j < 4; j++)
-    {
+write_datagram(Datagram &destination) const {
+  for(int i = 0; i < 4; i++) {
+    for(int j = 0; j < 4; j++) {
       destination.add_float32(get_cell(i,j));
     }
   }
@@ -260,32 +338,25 @@ write_datagram(Datagram &destination) const
 //  Description: Reads itself out of the datagram
 ////////////////////////////////////////////////////////////////////
 void FLOATNAME(LMatrix4)::
-read_datagram(DatagramIterator &scan) 
-{
-  for(int i = 0; i < 4; i++)
-  {
-    for(int j = 0; j < 4; j++)
-    {
+read_datagram(DatagramIterator &scan) {
+  for(int i = 0; i < 4; i++) {
+    for(int j = 0; j < 4; j++) {
       set_cell(i, j, scan.get_float32());
     }
   }
 }
 
 ////////////////////////////////////////////////////////////////////
-//     Function: LMatrix4::compare_to
-//       Access: Public
-//  Description: Sorts matrices lexicographically, componentwise.
-//               Returns a number less than 0 if this matrix sorts
-//               before the other one, greater than zero if it sorts
-//               after, 0 if they are equivalent (within the indicated
-//               tolerance).
+//     Function: LMatrix4::init_type
+//       Access: Public, Static
+//  Description: 
 ////////////////////////////////////////////////////////////////////
-int FLOATNAME(LMatrix4)::
-compare_to(const FLOATNAME(LMatrix4) &other, FLOATTYPE threshold) const {
-  for (int i = 0; i < 16; i++) {
-    if (!IS_THRESHOLD_EQUAL(_m.data[i], other._m.data[i], threshold)) {
-      return (_m.data[i] < other._m.data[i]) ? -1 : 1;
-    }
+void FLOATNAME(LMatrix4)::
+init_type() {
+  if (_type_handle == TypeHandle::none()) {
+    // Format a string to describe the type.
+    string name = "LMatrix4";
+    name += FLOATTOKEN;
+    register_type(_type_handle, name);
   }
-  return 0;
 }

+ 28 - 18
panda/src/linmath/lmatrix4_src.h

@@ -19,10 +19,10 @@ PUBLISHED:
   INLINE_LINMATH FLOATNAME(LMatrix4) &operator = (FLOATTYPE fill_value);
 
   INLINE_LINMATH FLOATNAME(LMatrix4)(FLOATTYPE e00, FLOATTYPE e01, FLOATTYPE e02, FLOATTYPE e03,
-			     FLOATTYPE e10, FLOATTYPE e11, FLOATTYPE e12, FLOATTYPE e13,
-			     FLOATTYPE e20, FLOATTYPE e21, FLOATTYPE e22, FLOATTYPE e23,
-			     FLOATTYPE e30, FLOATTYPE e31, FLOATTYPE e32, FLOATTYPE e33);
-
+				     FLOATTYPE e10, FLOATTYPE e11, FLOATTYPE e12, FLOATTYPE e13,
+				     FLOATTYPE e20, FLOATTYPE e21, FLOATTYPE e22, FLOATTYPE e23,
+				     FLOATTYPE e30, FLOATTYPE e31, FLOATTYPE e32, FLOATTYPE e33);
+  
   // Construct a 4x4 matrix given a 3x3 rotation matrix and an optional
   // translation component.
   INLINE_LINMATH FLOATNAME(LMatrix4)(const FLOATNAME(LMatrix3) &upper3);
@@ -103,33 +103,43 @@ PUBLISHED:
   INLINE_LINMATH bool invert_in_place();
 
   INLINE_LINMATH static const FLOATNAME(LMatrix4) &ident_mat();
-  INLINE_LINMATH static FLOATNAME(LMatrix4) translate_mat(const FLOATNAME(LVecBase3) &trans);
-  INLINE_LINMATH static FLOATNAME(LMatrix4) translate_mat(FLOATTYPE tx, FLOATTYPE ty, FLOATTYPE tz);
-  INLINE_LINMATH static FLOATNAME(LMatrix4) rotate_mat(FLOATTYPE angle,
-				      FLOATNAME(LVecBase3) axis,
-				      CoordinateSystem cs = CS_default);
-  INLINE_LINMATH static FLOATNAME(LMatrix4) rotate_mat_normaxis(FLOATTYPE angle,
-				      const FLOATNAME(LVecBase3) &axis,
-				      CoordinateSystem cs = CS_default);
-  INLINE_LINMATH static FLOATNAME(LMatrix4) scale_mat(const FLOATNAME(LVecBase3) &scale);
-  INLINE_LINMATH static FLOATNAME(LMatrix4) scale_mat(FLOATTYPE sx, FLOATTYPE sy, FLOATTYPE sz);
-  INLINE_LINMATH static FLOATNAME(LMatrix4) scale_mat(FLOATTYPE scale);
+  INLINE_LINMATH static FLOATNAME(LMatrix4) 
+    translate_mat(const FLOATNAME(LVecBase3) &trans);
+  INLINE_LINMATH static FLOATNAME(LMatrix4)
+    translate_mat(FLOATTYPE tx, FLOATTYPE ty, FLOATTYPE tz);
+  INLINE_LINMATH static FLOATNAME(LMatrix4)
+    rotate_mat(FLOATTYPE angle,
+	       FLOATNAME(LVecBase3) axis,
+	       CoordinateSystem cs = CS_default);
+  INLINE_LINMATH static FLOATNAME(LMatrix4) 
+    rotate_mat_normaxis(FLOATTYPE angle,
+			const FLOATNAME(LVecBase3) &axis,
+			CoordinateSystem cs = CS_default);
+  INLINE_LINMATH static FLOATNAME(LMatrix4)
+    scale_mat(const FLOATNAME(LVecBase3) &scale);
+  INLINE_LINMATH static FLOATNAME(LMatrix4)
+    scale_mat(FLOATTYPE sx, FLOATTYPE sy, FLOATTYPE sz);
+  INLINE_LINMATH static FLOATNAME(LMatrix4)
+    scale_mat(FLOATTYPE scale);
 
   INLINE_LINMATH static const FLOATNAME(LMatrix4) &y_to_z_up_mat();
   INLINE_LINMATH static const FLOATNAME(LMatrix4) &z_to_y_up_mat();
 
   static FLOATNAME(LMatrix4) convert_mat(CoordinateSystem from,
-				       CoordinateSystem to);
+					 CoordinateSystem to);
 
   bool almost_equal(const FLOATNAME(LMatrix4) &other, 
 		    FLOATTYPE threshold) const;
   INLINE_LINMATH bool almost_equal(const FLOATNAME(LMatrix4) &other) const;
   
-  INLINE_LINMATH void output(ostream &out) const;
-  INLINE_LINMATH void write(ostream &out, int indent_level = 0) const;
+  void output(ostream &out) const;
+  void write(ostream &out, int indent_level = 0) const;
 
 public:
+  INLINE_LINMATH void generate_hash(ChecksumHashGenerator &hash) const;
+  void generate_hash(ChecksumHashGenerator &hash, FLOATTYPE scale) const;
 
+public:
   union {
         struct {
 	   FLOATTYPE  _00, _01, _02, _03;

+ 2 - 0
panda/src/linmath/lvecBase2.h

@@ -11,6 +11,8 @@
 #include <notify.h>
 #include <datagram.h>
 #include <datagramIterator.h>
+#include <checksumHashGenerator.h>
+
 #include "cmath.h"
 #include "nearly_zero.h"
 

+ 21 - 0
panda/src/linmath/lvecBase2_src.I

@@ -505,6 +505,27 @@ output(ostream &out) const {
       << MAYBE_ZERO(_v.v._1);
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: LVecBase2::generate_hash
+//       Access: Public
+//  Description: Adds the vector to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH void FLOATNAME(LVecBase2)::
+generate_hash(ChecksumHashGenerator &hash) const {
+  generate_hash(hash, NEARLY_ZERO(FLOATTYPE));
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: LVecBase2::generate_hash
+//       Access: Public
+//  Description: Adds the vector to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH void FLOATNAME(LVecBase2)::
+generate_hash(ChecksumHashGenerator &hash, FLOATTYPE threshold) const {
+  hash.add_fp(_v.v._0, threshold);
+  hash.add_fp(_v.v._1, threshold);
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: LVecBase2::write_datagram
 //       Access: Public

+ 7 - 1
panda/src/linmath/lvecBase2_src.h

@@ -63,7 +63,8 @@ PUBLISHED:
 
   INLINE_LINMATH int compare_to(const FLOATNAME(LVecBase2) &other) const;
   INLINE_LINMATH int compare_to(const FLOATNAME(LVecBase2) &other,
-		        FLOATTYPE threshold) const;
+				FLOATTYPE threshold) const;
+
 
   INLINE_LINMATH FLOATNAME(LVecBase2) operator - () const;
 
@@ -87,6 +88,11 @@ PUBLISHED:
 
   INLINE_LINMATH void output(ostream &out) const;
 
+public:
+  INLINE_LINMATH void generate_hash(ChecksumHashGenerator &hash) const;
+  INLINE_LINMATH void generate_hash(ChecksumHashGenerator &hash,
+				    FLOATTYPE threshold) const;
+
 public:
    union {
 	FLOATTYPE data[2];

+ 2 - 0
panda/src/linmath/lvecBase3.h

@@ -11,6 +11,8 @@
 #include <notify.h>
 #include <datagram.h>
 #include <datagramIterator.h>
+#include <checksumHashGenerator.h>
+
 #include "cmath.h"
 #include "nearly_zero.h"
 

+ 22 - 0
panda/src/linmath/lvecBase3_src.I

@@ -575,6 +575,28 @@ output(ostream &out) const {
 }
 
 
+////////////////////////////////////////////////////////////////////
+//     Function: LVecBase3::generate_hash
+//       Access: Public
+//  Description: Adds the vector to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH void FLOATNAME(LVecBase3)::
+generate_hash(ChecksumHashGenerator &hash) const {
+  generate_hash(hash, NEARLY_ZERO(FLOATTYPE));
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: LVecBase3::generate_hash
+//       Access: Public
+//  Description: Adds the vector to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH void FLOATNAME(LVecBase3)::
+generate_hash(ChecksumHashGenerator &hash, FLOATTYPE threshold) const {
+  hash.add_fp(_v.v._0, threshold);
+  hash.add_fp(_v.v._1, threshold);
+  hash.add_fp(_v.v._2, threshold);
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: LVecBase3::write_datagram
 //       Access: Public

+ 6 - 1
panda/src/linmath/lvecBase3_src.h

@@ -64,7 +64,7 @@ PUBLISHED:
 
   INLINE_LINMATH int compare_to(const FLOATNAME(LVecBase3) &other) const;
   INLINE_LINMATH int compare_to(const FLOATNAME(LVecBase3) &other,
-		        FLOATTYPE threshold) const;
+				FLOATTYPE threshold) const;
 
   INLINE_LINMATH FLOATNAME(LVecBase3) operator - () const;
 
@@ -90,6 +90,11 @@ PUBLISHED:
 
   INLINE_LINMATH void output(ostream &out) const;
 
+public:
+  INLINE_LINMATH void generate_hash(ChecksumHashGenerator &hash) const;
+  INLINE_LINMATH void generate_hash(ChecksumHashGenerator &hash,
+				    FLOATTYPE threshold) const;
+
 public:
   union {
 	FLOATTYPE data[3];

+ 2 - 0
panda/src/linmath/lvecBase4.h

@@ -11,6 +11,8 @@
 #include <notify.h>
 #include <datagram.h>
 #include <datagramIterator.h>
+#include <checksumHashGenerator.h>
+
 #include "cmath.h"
 #include "nearly_zero.h"
 

+ 23 - 0
panda/src/linmath/lvecBase4_src.I

@@ -605,6 +605,29 @@ output(ostream &out) const {
       << MAYBE_ZERO(_v.v._3);
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: LVecBase4::generate_hash
+//       Access: Public
+//  Description: Adds the vector to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH void FLOATNAME(LVecBase4)::
+generate_hash(ChecksumHashGenerator &hash) const {
+  generate_hash(hash, NEARLY_ZERO(FLOATTYPE));
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: LVecBase4::generate_hash
+//       Access: Public
+//  Description: Adds the vector to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+INLINE_LINMATH void FLOATNAME(LVecBase4)::
+generate_hash(ChecksumHashGenerator &hash, FLOATTYPE threshold) const {
+  hash.add_fp(_v.v._0, threshold);
+  hash.add_fp(_v.v._1, threshold);
+  hash.add_fp(_v.v._2, threshold);
+  hash.add_fp(_v.v._3, threshold);
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: LVecBase4::write_datagram
 //       Access: Public

+ 7 - 3
panda/src/linmath/lvecBase4_src.h

@@ -66,8 +66,8 @@ PUBLISHED:
 
   INLINE_LINMATH int compare_to(const FLOATNAME(LVecBase4) &other) const;
   INLINE_LINMATH int compare_to(const FLOATNAME(LVecBase4) &other,
-		        FLOATTYPE threshold) const;
-
+				FLOATTYPE threshold) const;
+  
   INLINE_LINMATH FLOATNAME(LVecBase4) operator - () const;
 
   INLINE_LINMATH FLOATNAME(LVecBase4)
@@ -91,7 +91,11 @@ PUBLISHED:
   INLINE_LINMATH void output(ostream &out) const;
 
 public:
-  
+  INLINE_LINMATH void generate_hash(ChecksumHashGenerator &hash) const;
+  INLINE_LINMATH void generate_hash(ChecksumHashGenerator &hash,
+				    FLOATTYPE threshold) const;
+
+public:
   union {
 	FLOATTYPE data[4];
 	struct {FLOATTYPE _0, _1, _2, _3;} v;

+ 11 - 0
panda/src/putil/bitMask.I

@@ -523,6 +523,17 @@ operator >>= (int shift) {
   _word >>= shift;
 }
 
+////////////////////////////////////////////////////////////////////
+//     Function: BitMask::generate_hash
+//       Access: Public
+//  Description: Adds the bitmask to the indicated hash generator.
+////////////////////////////////////////////////////////////////////
+template<class WordType, int num_bits>
+INLINE void BitMask<WordType, num_bits>::
+generate_hash(ChecksumHashGenerator &hash) const {
+  hash.add_int(_word);
+}
+
 ////////////////////////////////////////////////////////////////////
 //     Function: BitMask::init_type
 //       Access: Public

+ 5 - 0
panda/src/putil/bitMask.h

@@ -12,6 +12,8 @@
 #include "typedObject.h"
 #include "indent.h"
 
+#include <checksumHashGenerator.h>
+
 
 ////////////////////////////////////////////////////////////////////
 //       Class : BitMask
@@ -82,6 +84,9 @@ PUBLISHED:
   INLINE void operator <<= (int shift);
   INLINE void operator >>= (int shift);
 
+public:
+  INLINE void generate_hash(ChecksumHashGenerator &hash) const;
+
 private:
   WordType _word;