Panda3D
|
00001 // Filename: pipelineCyclerTrueImpl.I 00002 // Created by: drose (31Jan06) 00003 // 00004 //////////////////////////////////////////////////////////////////// 00005 // 00006 // PANDA 3D SOFTWARE 00007 // Copyright (c) Carnegie Mellon University. All rights reserved. 00008 // 00009 // All use of this software is subject to the terms of the revised BSD 00010 // license. You should have received a copy of this license along 00011 // with this source code in a file named "LICENSE." 00012 // 00013 //////////////////////////////////////////////////////////////////// 00014 00015 00016 //////////////////////////////////////////////////////////////////// 00017 // Function: PipelineCyclerTrueImpl::acquire 00018 // Access: Public 00019 // Description: Grabs an overall lock on the cycler. Release it with 00020 // a call to release(). This lock should be held while 00021 // walking the list of stages. 00022 //////////////////////////////////////////////////////////////////// 00023 INLINE void PipelineCyclerTrueImpl:: 00024 acquire() { 00025 TAU_PROFILE("void PipelineCyclerTrueImpl::acquire()", " ", TAU_USER); 00026 _lock.acquire(); 00027 } 00028 00029 //////////////////////////////////////////////////////////////////// 00030 // Function: PipelineCyclerTrueImpl::acquire 00031 // Access: Public 00032 // Description: Grabs an overall lock on the cycler. Release it with 00033 // a call to release(). This lock should be held while 00034 // walking the list of stages. 00035 //////////////////////////////////////////////////////////////////// 00036 INLINE void PipelineCyclerTrueImpl:: 00037 acquire(Thread *current_thread) { 00038 TAU_PROFILE("void PipelineCyclerTrueImpl::acquire(Thread *)", " ", TAU_USER); 00039 _lock.acquire(current_thread); 00040 } 00041 00042 //////////////////////////////////////////////////////////////////// 00043 // Function: PipelineCyclerTrueImpl::release 00044 // Access: Public 00045 // Description: Release the overall lock on the cycler that was 00046 // grabbed via acquire(). 00047 //////////////////////////////////////////////////////////////////// 00048 INLINE void PipelineCyclerTrueImpl:: 00049 release() { 00050 TAU_PROFILE("void PipelineCyclerTrueImpl::release()", " ", TAU_USER); 00051 _lock.release(); 00052 } 00053 00054 //////////////////////////////////////////////////////////////////// 00055 // Function: PipelineCyclerTrueImpl::read_unlocked 00056 // Access: Public 00057 // Description: Returns a const CycleData pointer, filled with the 00058 // data for the current stage of the pipeline as seen by 00059 // this thread. No lock is made on the contents; there 00060 // is no guarantee that some other thread won't modify 00061 // this object's data while you are working on it. 00062 // (However, the data within the returned CycleData 00063 // object itself is safe from modification; if another 00064 // thread modifies the data, it will perform a 00065 // copy-on-write, and thereby change the pointer stored 00066 // within the object.) 00067 //////////////////////////////////////////////////////////////////// 00068 INLINE const CycleData *PipelineCyclerTrueImpl:: 00069 read_unlocked(Thread *current_thread) const { 00070 TAU_PROFILE("const CycleData *PipelineCyclerTrueImpl::read_unlocked(Thread *)", " ", TAU_USER); 00071 int pipeline_stage = current_thread->get_pipeline_stage(); 00072 #ifdef _DEBUG 00073 nassertr(pipeline_stage >= 0 && pipeline_stage < _num_stages, NULL); 00074 #endif 00075 return _data[pipeline_stage]._cdata; 00076 } 00077 00078 //////////////////////////////////////////////////////////////////// 00079 // Function: PipelineCyclerTrueImpl::read 00080 // Access: Public 00081 // Description: Returns a const CycleData pointer, filled with the 00082 // data for the current stage of the pipeline as seen by 00083 // this thread. This pointer should eventually be 00084 // released by calling release_read(). 00085 // 00086 // There should be no outstanding write pointers on the 00087 // data when this function is called. 00088 //////////////////////////////////////////////////////////////////// 00089 INLINE const CycleData *PipelineCyclerTrueImpl:: 00090 read(Thread *current_thread) const { 00091 TAU_PROFILE("const CycleData *PipelineCyclerTrueImpl::read(Thread *)", " ", TAU_USER); 00092 int pipeline_stage = current_thread->get_pipeline_stage(); 00093 #ifdef _DEBUG 00094 nassertr(pipeline_stage >= 0 && pipeline_stage < _num_stages, NULL); 00095 #endif 00096 _lock.acquire(current_thread); 00097 return _data[pipeline_stage]._cdata; 00098 } 00099 00100 //////////////////////////////////////////////////////////////////// 00101 // Function: PipelineCyclerTrueImpl::increment_read 00102 // Access: Public 00103 // Description: Increments the count on a pointer previously 00104 // retrieved by read(); now the pointer will need to be 00105 // released twice. 00106 //////////////////////////////////////////////////////////////////// 00107 INLINE void PipelineCyclerTrueImpl:: 00108 increment_read(const CycleData *pointer) const { 00109 TAU_PROFILE("void PipelineCyclerTrueImpl::increment_read(const CycleData *)", " ", TAU_USER); 00110 #ifdef _DEBUG 00111 int pipeline_stage = Thread::get_current_pipeline_stage(); 00112 nassertv(pipeline_stage >= 0 && pipeline_stage < _num_stages); 00113 nassertv(_data[pipeline_stage]._cdata == pointer); 00114 #endif 00115 _lock.elevate_lock(); 00116 } 00117 00118 //////////////////////////////////////////////////////////////////// 00119 // Function: PipelineCyclerTrueImpl::release_read 00120 // Access: Public 00121 // Description: Releases a pointer previously obtained via a call to 00122 // read(). 00123 //////////////////////////////////////////////////////////////////// 00124 INLINE void PipelineCyclerTrueImpl:: 00125 release_read(const CycleData *pointer) const { 00126 TAU_PROFILE("void PipelineCyclerTrueImpl::release_read(const CycleData *)", " ", TAU_USER); 00127 #ifdef _DEBUG 00128 int pipeline_stage = Thread::get_current_pipeline_stage(); 00129 nassertv(pipeline_stage >= 0 && pipeline_stage < _num_stages); 00130 nassertv(_data[pipeline_stage]._cdata == pointer); 00131 #endif 00132 _lock.release(); 00133 } 00134 00135 //////////////////////////////////////////////////////////////////// 00136 // Function: PipelineCyclerTrueImpl::write 00137 // Access: Public 00138 // Description: Returns a non-const CycleData pointer, filled with a 00139 // unique copy of the data for the current stage of the 00140 // pipeline as seen by this thread. This pointer may 00141 // now be used to write to the data, and that copy of 00142 // the data will be propagated to all later stages of the 00143 // pipeline. This pointer should eventually be released 00144 // by calling release_write(). 00145 // 00146 // There may only be one outstanding write pointer on a 00147 // given stage at a time, and if there is a write 00148 // pointer there may be no read pointers on the same 00149 // stage (but see elevate_read). 00150 //////////////////////////////////////////////////////////////////// 00151 INLINE CycleData *PipelineCyclerTrueImpl:: 00152 write(Thread *current_thread) { 00153 TAU_PROFILE("CycleData *PipelineCyclerTrueImpl::write(Thread *)", " ", TAU_USER); 00154 return write_stage(current_thread->get_pipeline_stage(), current_thread); 00155 } 00156 00157 //////////////////////////////////////////////////////////////////// 00158 // Function: PipelineCyclerTrueImpl::write_upstream 00159 // Access: Public 00160 // Description: This special variant on write() will automatically 00161 // propagate changes back to upstream pipeline stages. 00162 // If force_to_0 is false, then it propagates back only 00163 // as long as the CycleData pointers are equivalent, 00164 // guaranteeing that it does not modify upstream data 00165 // (other than the modification that will be performed 00166 // by the code that returns this pointer). This is 00167 // particularly appropriate for minor updates, where it 00168 // doesn't matter much if the update is lost, such as 00169 // storing a cached value. 00170 // 00171 // If force_to_0 is true, then the CycleData pointer for 00172 // the current pipeline stage is propagated all the way 00173 // back up to stage 0; after this call, there will be 00174 // only one CycleData pointer that is duplicated in all 00175 // stages between stage 0 and the current stage. This 00176 // may undo some recent changes that were made 00177 // independently at pipeline stage 0 (or any other 00178 // upstream stage). However, it guarantees that the 00179 // change that is to be applied at this pipeline stage 00180 // will stick. This is slightly dangerous because of 00181 // the risk of losing upstream changes; generally, this 00182 // should only be done when you are confident that there 00183 // are no upstream changes to be lost (for instance, for 00184 // an object that has been recently created). 00185 //////////////////////////////////////////////////////////////////// 00186 INLINE CycleData *PipelineCyclerTrueImpl:: 00187 write_upstream(bool force_to_0, Thread *current_thread) { 00188 TAU_PROFILE("CycleData *PipelineCyclerTrueImpl::write_upstream(bool, Thread *)", " ", TAU_USER); 00189 return write_stage_upstream(current_thread->get_pipeline_stage(), force_to_0, 00190 current_thread); 00191 } 00192 00193 //////////////////////////////////////////////////////////////////// 00194 // Function: PipelineCyclerTrueImpl::elevate_read 00195 // Access: Public 00196 // Description: Elevates a currently-held read pointer into a write 00197 // pointer. This may or may not change the value of the 00198 // pointer. It is only valid to do this if this is the 00199 // only currently-outstanding read pointer on the 00200 // current stage. 00201 //////////////////////////////////////////////////////////////////// 00202 INLINE CycleData *PipelineCyclerTrueImpl:: 00203 elevate_read(const CycleData *pointer, Thread *current_thread) { 00204 TAU_PROFILE("CycleData *PipelineCyclerTrueImpl::elevate_read(const CycleData *)", " ", TAU_USER); 00205 #ifdef _DEBUG 00206 int pipeline_stage = current_thread->get_pipeline_stage(); 00207 nassertr(pipeline_stage >= 0 && pipeline_stage < _num_stages, NULL); 00208 nassertr(_data[pipeline_stage]._cdata == pointer, NULL); 00209 #endif 00210 CycleData *new_pointer = write(current_thread); 00211 _lock.release(); 00212 return new_pointer; 00213 } 00214 00215 //////////////////////////////////////////////////////////////////// 00216 // Function: PipelineCyclerTrueImpl::elevate_read_upstream 00217 // Access: Public 00218 // Description: Elevates a currently-held read pointer into a write 00219 // pointer, like elevate_read(), but also propagates the 00220 // pointer back to upstream stages, like 00221 // write_upstream(). 00222 //////////////////////////////////////////////////////////////////// 00223 INLINE CycleData *PipelineCyclerTrueImpl:: 00224 elevate_read_upstream(const CycleData *pointer, bool force_to_0, Thread *current_thread) { 00225 TAU_PROFILE("CycleData *PipelineCyclerTrueImpl::elevate_read_upstream(const CycleData *, bool)", " ", TAU_USER); 00226 #ifdef _DEBUG 00227 int pipeline_stage = current_thread->get_pipeline_stage(); 00228 nassertr(pipeline_stage >= 0 && pipeline_stage < _num_stages, NULL); 00229 nassertr(_data[pipeline_stage]._cdata == pointer, NULL); 00230 #endif 00231 CycleData *new_pointer = write_upstream(force_to_0, current_thread); 00232 _lock.release(); 00233 return new_pointer; 00234 } 00235 00236 //////////////////////////////////////////////////////////////////// 00237 // Function: PipelineCyclerTrueImpl::increment_write 00238 // Access: Public 00239 // Description: Increments the count on a pointer previously 00240 // retrieved by write(); now the pointer will need to be 00241 // released twice. 00242 //////////////////////////////////////////////////////////////////// 00243 INLINE void PipelineCyclerTrueImpl:: 00244 increment_write(CycleData *pointer) const { 00245 TAU_PROFILE("void PipelineCyclerTrueImpl::increment_write(CycleData *)", " ", TAU_USER); 00246 int pipeline_stage = Thread::get_current_pipeline_stage(); 00247 #ifdef _DEBUG 00248 nassertv(pipeline_stage >= 0 && pipeline_stage < _num_stages); 00249 nassertv(_data[pipeline_stage]._cdata == pointer); 00250 #endif 00251 ++(_data[pipeline_stage]._writes_outstanding); 00252 _lock.elevate_lock(); 00253 } 00254 00255 //////////////////////////////////////////////////////////////////// 00256 // Function: PipelineCyclerTrueImpl::release_write 00257 // Access: Public 00258 // Description: Releases a pointer previously obtained via a call to 00259 // write(). 00260 //////////////////////////////////////////////////////////////////// 00261 INLINE void PipelineCyclerTrueImpl:: 00262 release_write(CycleData *pointer) { 00263 TAU_PROFILE("void PipelineCyclerTrueImpl::release_write(CycleData *)", " ", TAU_USER); 00264 int pipeline_stage = Thread::get_current_pipeline_stage(); 00265 return release_write_stage(pipeline_stage, pointer); 00266 } 00267 00268 //////////////////////////////////////////////////////////////////// 00269 // Function: PipelineCyclerTrueImpl::get_num_stages 00270 // Access: Public 00271 // Description: Returns the number of stages in the pipeline. 00272 //////////////////////////////////////////////////////////////////// 00273 INLINE int PipelineCyclerTrueImpl:: 00274 get_num_stages() { 00275 return _num_stages; 00276 } 00277 00278 //////////////////////////////////////////////////////////////////// 00279 // Function: PipelineCyclerTrueImpl::read_stage_unlocked 00280 // Access: Public 00281 // Description: Returns a const CycleData pointer, filled with the 00282 // data for the indicated stage of the pipeline. As in 00283 // read_unlocked(), no lock is held on the returned 00284 // pointer. 00285 //////////////////////////////////////////////////////////////////// 00286 INLINE const CycleData *PipelineCyclerTrueImpl:: 00287 read_stage_unlocked(int pipeline_stage) const { 00288 TAU_PROFILE("const CycleData *PipelineCyclerTrueImpl::read_stage_unlocked(int)", " ", TAU_USER); 00289 #ifdef _DEBUG 00290 nassertr(pipeline_stage >= 0 && pipeline_stage < _num_stages, NULL); 00291 #endif 00292 return _data[pipeline_stage]._cdata; 00293 } 00294 00295 //////////////////////////////////////////////////////////////////// 00296 // Function: PipelineCyclerTrueImpl::read_stage 00297 // Access: Public 00298 // Description: Returns a const CycleData pointer, filled with the 00299 // data for the indicated stage of the pipeline. This 00300 // pointer should eventually be released by calling 00301 // release_read_stage(). 00302 // 00303 // There should be no outstanding write pointers on the 00304 // data when this function is called. 00305 //////////////////////////////////////////////////////////////////// 00306 INLINE const CycleData *PipelineCyclerTrueImpl:: 00307 read_stage(int pipeline_stage, Thread *current_thread) const { 00308 TAU_PROFILE("const CycleData *PipelineCyclerTrueImpl::read_stage(int, Thread *)", " ", TAU_USER); 00309 #ifdef _DEBUG 00310 nassertr(pipeline_stage >= 0 && pipeline_stage < _num_stages, NULL); 00311 #endif 00312 _lock.acquire(current_thread); 00313 return _data[pipeline_stage]._cdata; 00314 } 00315 00316 //////////////////////////////////////////////////////////////////// 00317 // Function: PipelineCyclerTrueImpl::release_read_stage 00318 // Access: Public 00319 // Description: Releases a pointer previously obtained via a call to 00320 // read_stage(). 00321 //////////////////////////////////////////////////////////////////// 00322 INLINE void PipelineCyclerTrueImpl:: 00323 release_read_stage(int pipeline_stage, const CycleData *pointer) const { 00324 TAU_PROFILE("void PipelineCyclerTrueImpl::release_read_stage(int, const CycleData *)", " ", TAU_USER); 00325 #ifdef _DEBUG 00326 nassertv(pipeline_stage >= 0 && pipeline_stage < _num_stages); 00327 nassertv(_data[pipeline_stage]._cdata == pointer); 00328 #endif 00329 _lock.release(); 00330 } 00331 00332 //////////////////////////////////////////////////////////////////// 00333 // Function: PipelineCyclerTrueImpl::elevate_read_stage 00334 // Access: Public 00335 // Description: Elevates a currently-held read pointer into a write 00336 // pointer. This may or may not change the value of the 00337 // pointer. It is only valid to do this if this is the 00338 // only currently-outstanding read pointer on the 00339 // indicated stage. 00340 //////////////////////////////////////////////////////////////////// 00341 INLINE CycleData *PipelineCyclerTrueImpl:: 00342 elevate_read_stage(int pipeline_stage, const CycleData *pointer, 00343 Thread *current_thread) { 00344 TAU_PROFILE("CycleData *PipelineCyclerTrueImpl::elevate_read_stage(int, const CycleData *)", " ", TAU_USER); 00345 #ifdef _DEBUG 00346 nassertr(pipeline_stage >= 0 && pipeline_stage < _num_stages, NULL); 00347 nassertr(_data[pipeline_stage]._cdata == pointer, NULL); 00348 #endif 00349 CycleData *new_pointer = write_stage(pipeline_stage, current_thread); 00350 _lock.release(); 00351 return new_pointer; 00352 } 00353 00354 //////////////////////////////////////////////////////////////////// 00355 // Function: PipelineCyclerTrueImpl::elevate_read_stage_upstream 00356 // Access: Public 00357 // Description: Elevates a currently-held read pointer into a write 00358 // pointer. This may or may not change the value of the 00359 // pointer. It is only valid to do this if this is the 00360 // only currently-outstanding read pointer on the 00361 // indicated stage. 00362 //////////////////////////////////////////////////////////////////// 00363 INLINE CycleData *PipelineCyclerTrueImpl:: 00364 elevate_read_stage_upstream(int pipeline_stage, const CycleData *pointer, 00365 bool force_to_0, Thread *current_thread) { 00366 TAU_PROFILE("CycleData *PipelineCyclerTrueImpl::elevate_read_stage(int, const CycleData *)", " ", TAU_USER); 00367 #ifdef _DEBUG 00368 nassertr(pipeline_stage >= 0 && pipeline_stage < _num_stages, NULL); 00369 nassertr(_data[pipeline_stage]._cdata == pointer, NULL); 00370 #endif 00371 CycleData *new_pointer = 00372 write_stage_upstream(pipeline_stage, force_to_0, current_thread); 00373 _lock.release(); 00374 return new_pointer; 00375 } 00376 00377 //////////////////////////////////////////////////////////////////// 00378 // Function: PipelineCyclerTrueImpl::release_write_stage 00379 // Access: Public 00380 // Description: Releases a pointer previously obtained via a call to 00381 // write_stage(). 00382 //////////////////////////////////////////////////////////////////// 00383 INLINE void PipelineCyclerTrueImpl:: 00384 release_write_stage(int pipeline_stage, CycleData *pointer) { 00385 TAU_PROFILE("void PipelineCyclerTrueImpl::release_write_stage(int, const CycleData *)", " ", TAU_USER); 00386 #ifdef _DEBUG 00387 nassertv(pipeline_stage >= 0 && pipeline_stage < _num_stages); 00388 nassertv(_data[pipeline_stage]._cdata == pointer); 00389 nassertv(_data[pipeline_stage]._writes_outstanding > 0); 00390 #endif 00391 --(_data[pipeline_stage]._writes_outstanding); 00392 _lock.release(); 00393 } 00394 00395 //////////////////////////////////////////////////////////////////// 00396 // Function: PipelineCyclerTrueImpl::get_parent_type 00397 // Access: Public 00398 // Description: Returns the type of object that owns this cycler, as 00399 // reported by CycleData::get_parent_type(). 00400 //////////////////////////////////////////////////////////////////// 00401 INLINE TypeHandle PipelineCyclerTrueImpl:: 00402 get_parent_type() const { 00403 return _data[0]._cdata->get_parent_type(); 00404 } 00405 00406 //////////////////////////////////////////////////////////////////// 00407 // Function: PipelineCyclerTrueImpl::cheat 00408 // Access: Public 00409 // Description: Returns a pointer without counting it. This is only 00410 // intended for use as the return value for certain 00411 // nassertr() functions, so the application can recover 00412 // after a failure to manage the read and write pointers 00413 // correctly. You should never call this function 00414 // directly. 00415 //////////////////////////////////////////////////////////////////// 00416 INLINE CycleData *PipelineCyclerTrueImpl:: 00417 cheat() const { 00418 TAU_PROFILE("CycleData *PipelineCyclerTrueImpl::cheat()", " ", TAU_USER); 00419 int pipeline_stage = Thread::get_current_pipeline_stage(); 00420 nassertr(pipeline_stage >= 0 && pipeline_stage < _num_stages, NULL); 00421 return _data[pipeline_stage]._cdata; 00422 } 00423 00424 //////////////////////////////////////////////////////////////////// 00425 // Function: PipelineCyclerTrueImpl::get_read_count 00426 // Access: Public 00427 // Description: Returns the number of handles currently outstanding 00428 // to read the current stage of the data. This should 00429 // only be used for debugging purposes. 00430 //////////////////////////////////////////////////////////////////// 00431 INLINE int PipelineCyclerTrueImpl:: 00432 get_read_count() const { 00433 return 0; 00434 } 00435 00436 //////////////////////////////////////////////////////////////////// 00437 // Function: PipelineCyclerTrueImpl::get_write_count 00438 // Access: Public 00439 // Description: Returns the number of handles currently outstanding 00440 // to read the current stage of the data. This will 00441 // normally only be either 0 or 1. This should only be 00442 // used for debugging purposes. 00443 //////////////////////////////////////////////////////////////////// 00444 INLINE int PipelineCyclerTrueImpl:: 00445 get_write_count() const { 00446 return 0; 00447 } 00448 00449 //////////////////////////////////////////////////////////////////// 00450 // Function: PipelineCyclerTrueImpl::cycle_2 00451 // Access: Private 00452 // Description: This is a special implementation of cycle() for the 00453 // special case of just two stages to the pipeline. It 00454 // does the same thing as cycle(), but is a little bit 00455 // faster because it knows there are exactly two stages. 00456 //////////////////////////////////////////////////////////////////// 00457 INLINE PT(CycleData) PipelineCyclerTrueImpl:: 00458 cycle_2() { 00459 TAU_PROFILE("PT(CycleData) PipelineCyclerTrueImpl::cycle_2()", " ", TAU_USER); 00460 PT(CycleData) last_val = _data[1]._cdata.p(); 00461 nassertr(_lock.debug_is_locked(), last_val); 00462 nassertr(_dirty, last_val); 00463 nassertr(_num_stages == 2, last_val); 00464 00465 nassertr(_data[1]._writes_outstanding == 0, last_val); 00466 _data[1]._cdata = _data[0]._cdata; 00467 00468 // No longer dirty. 00469 _dirty = false; 00470 return last_val; 00471 } 00472 00473 //////////////////////////////////////////////////////////////////// 00474 // Function: PipelineCyclerTrueImpl::cycle_3 00475 // Access: Private 00476 // Description: This is a special implementation of cycle() for the 00477 // special case of exactly three stages to the pipeline. 00478 // It does the same thing as cycle(), but is a little 00479 // bit faster because it knows there are exactly three 00480 // stages. 00481 //////////////////////////////////////////////////////////////////// 00482 INLINE PT(CycleData) PipelineCyclerTrueImpl:: 00483 cycle_3() { 00484 TAU_PROFILE("PT(CycleData) PipelineCyclerTrueImpl::cycle_3()", " ", TAU_USER); 00485 PT(CycleData) last_val = _data[2]._cdata.p(); 00486 nassertr(_lock.debug_is_locked(), last_val); 00487 nassertr(_dirty, last_val); 00488 nassertr(_num_stages == 3, last_val); 00489 00490 nassertr(_data[2]._writes_outstanding == 0, last_val); 00491 nassertr(_data[1]._writes_outstanding == 0, last_val); 00492 _data[2]._cdata = _data[1]._cdata; 00493 _data[1]._cdata = _data[0]._cdata; 00494 00495 if (_data[2]._cdata == _data[1]._cdata) { 00496 // No longer dirty. 00497 _dirty = false; 00498 } 00499 00500 return last_val; 00501 } 00502 00503 //////////////////////////////////////////////////////////////////// 00504 // Function: PipelineCyclerTrueImpl::CyclerMutex::Constructor 00505 // Access: Public 00506 // Description: 00507 //////////////////////////////////////////////////////////////////// 00508 INLINE PipelineCyclerTrueImpl::CyclerMutex:: 00509 CyclerMutex(PipelineCyclerTrueImpl *cycler) { 00510 #ifdef DEBUG_THREADS 00511 _cycler = cycler; 00512 #endif 00513 } 00514 00515 //////////////////////////////////////////////////////////////////// 00516 // Function: PipelineCyclerTrueImpl::CyclerMutex::Constructor 00517 // Access: Public 00518 // Description: 00519 //////////////////////////////////////////////////////////////////// 00520 INLINE PipelineCyclerTrueImpl::CycleDataNode:: 00521 CycleDataNode() : 00522 _writes_outstanding(0) 00523 { 00524 } 00525 00526 //////////////////////////////////////////////////////////////////// 00527 // Function: PipelineCyclerTrueImpl::CyclerMutex::Copy Constructor 00528 // Access: Public 00529 // Description: 00530 //////////////////////////////////////////////////////////////////// 00531 INLINE PipelineCyclerTrueImpl::CycleDataNode:: 00532 CycleDataNode(const PipelineCyclerTrueImpl::CycleDataNode ©) : 00533 _cdata(copy._cdata), 00534 _writes_outstanding(0) 00535 { 00536 } 00537 00538 //////////////////////////////////////////////////////////////////// 00539 // Function: PipelineCyclerTrueImpl::CyclerMutex::Destructor 00540 // Access: Public 00541 // Description: 00542 //////////////////////////////////////////////////////////////////// 00543 INLINE PipelineCyclerTrueImpl::CycleDataNode:: 00544 ~CycleDataNode() { 00545 nassertv(_writes_outstanding == 0); 00546 } 00547 00548 //////////////////////////////////////////////////////////////////// 00549 // Function: PipelineCyclerTrueImpl::CyclerMutex::Copy Assignment 00550 // Access: Public 00551 // Description: 00552 //////////////////////////////////////////////////////////////////// 00553 INLINE void PipelineCyclerTrueImpl::CycleDataNode:: 00554 operator = (const PipelineCyclerTrueImpl::CycleDataNode ©) { 00555 _cdata = copy._cdata; 00556 }