00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 template<class T>
00022 INLINE ThreadSafePointerToBase<T>::
00023 ThreadSafePointerToBase(To *ptr) {
00024 reassign(ptr);
00025 }
00026
00027
00028
00029
00030
00031
00032 template<class T>
00033 INLINE ThreadSafePointerToBase<T>::
00034 ThreadSafePointerToBase(const ThreadSafePointerToBase<T> ©) {
00035 reassign(copy);
00036 }
00037
00038
00039
00040
00041
00042
00043 template<class T>
00044 INLINE ThreadSafePointerToBase<T>::
00045 ~ThreadSafePointerToBase() {
00046 reassign((To *)NULL);
00047 }
00048
00049
00050
00051
00052
00053
00054
00055
00056 template<class T>
00057 INLINE void ThreadSafePointerToBase<T>::
00058 reassign(To *ptr) {
00059 To *old_ptr = (To *)AtomicAdjust::get_ptr(_void_ptr);
00060 if (ptr == old_ptr) {
00061 return;
00062 }
00063
00064 #ifdef HAVE_THREADS
00065 void *orig_ptr = AtomicAdjust::compare_and_exchange_ptr(_void_ptr, old_ptr, ptr);
00066 while (orig_ptr != old_ptr) {
00067
00068 old_ptr = (To *)AtomicAdjust::get_ptr(_void_ptr);
00069 if (ptr == old_ptr) {
00070 return;
00071 }
00072
00073 orig_ptr = AtomicAdjust::compare_and_exchange_ptr(_void_ptr, old_ptr, ptr);
00074 }
00075 #else // HAVE_THREADS
00076 _void_ptr = ptr;
00077 #endif // HAVE_THREADS
00078
00079 if (ptr != (To *)NULL) {
00080 ptr->ref();
00081 #ifdef DO_MEMORY_USAGE
00082 if (MemoryUsage::get_track_memory_usage()) {
00083 update_type(ptr);
00084 }
00085 #endif
00086 }
00087
00088
00089 if (old_ptr != (To *)NULL) {
00090 unref_delete(old_ptr);
00091 }
00092 }
00093
00094
00095
00096
00097
00098
00099 template<class T>
00100 INLINE void ThreadSafePointerToBase<T>::
00101 reassign(const ThreadSafePointerToBase<To> ©) {
00102 reassign((To *)copy._void_ptr);
00103 }
00104
00105 #ifdef DO_MEMORY_USAGE
00106
00107
00108
00109
00110
00111
00112
00113 template<class T>
00114 void ThreadSafePointerToBase<T>::
00115 update_type(To *ptr) {
00116 TypeHandle type = get_type_handle(To);
00117 if (type == TypeHandle::none()) {
00118 do_init_type(To);
00119 type = get_type_handle(To);
00120 }
00121 if (type != TypeHandle::none()) {
00122 MemoryUsage::update_type(ptr, type);
00123 }
00124 }
00125 #endif // DO_MEMORY_USAGE
00126
00127
00128
00129
00130
00131
00132
00133
00134 template<class T>
00135 INLINE void ThreadSafePointerToBase<T>::
00136 clear() {
00137 reassign((To *)NULL);
00138 }
00139
00140
00141
00142
00143
00144
00145
00146 template<class T>
00147 INLINE void ThreadSafePointerToBase<T>::
00148 output(ostream &out) const {
00149 out << _void_ptr;
00150 if (_void_ptr != (void *)NULL) {
00151 out << ":" << ((To *)_void_ptr)->get_ref_count();
00152 }
00153 }