00001
00002
00003 #ifndef ACE_FUTURE_CPP
00004 #define ACE_FUTURE_CPP
00005
00006 #include "ace/Future.h"
00007
00008 #if !defined (ACE_LACKS_PRAGMA_ONCE)
00009 # pragma once
00010 #endif
00011
00012 ACE_RCSID (ace, Future, "$Id: Future.cpp,v 1.1.1.4 2003/02/21 18:36:32 chad Exp $")
00013
00014 #if defined (ACE_HAS_THREADS)
00015
00016 template <class T>
00017 ACE_Future_Holder<T>::ACE_Future_Holder (void)
00018 {
00019 }
00020
00021 template <class T>
00022 ACE_Future_Holder<T>::ACE_Future_Holder (const ACE_Future<T> &item)
00023 : item_ (item)
00024 {
00025 }
00026
00027 template <class T>
00028 ACE_Future_Holder<T>::~ACE_Future_Holder (void)
00029 {
00030 }
00031
00032 template <class T>
00033 ACE_Future_Observer<T>::ACE_Future_Observer (void)
00034 {
00035 }
00036
00037 template <class T>
00038 ACE_Future_Observer<T>::~ACE_Future_Observer (void)
00039 {
00040 }
00041
00042
00043
00044 template <class T> void
00045 ACE_Future_Rep<T>::dump (void) const
00046 {
00047 ACE_DEBUG ((LM_DEBUG, ACE_BEGIN_DUMP, this));
00048 ACE_DEBUG ((LM_DEBUG,
00049 "ref_count_ = %d\n",
00050 (int) this->ref_count_));
00051 ACE_DEBUG ((LM_INFO,"value_: \n"));
00052 if (this->value_)
00053 ACE_DEBUG ((LM_DEBUG, ACE_LIB_TEXT (" (NON-NULL)\n")));
00054 else
00055 ACE_DEBUG ((LM_DEBUG, ACE_LIB_TEXT (" (NULL)\n")));
00056
00057 ACE_DEBUG ((LM_INFO,"value_ready_: \n"));
00058 this->value_ready_.dump ();
00059 ACE_DEBUG ((LM_INFO,"value_ready_mutex_: \n"));
00060 this->value_ready_mutex_.dump ();
00061 ACE_DEBUG ((LM_DEBUG, ACE_END_DUMP));
00062 }
00063
00064 template <class T> ACE_Future_Rep<T> *
00065 ACE_Future_Rep<T>::internal_create (void)
00066 {
00067 ACE_Future_Rep<T> *temp = 0;
00068 ACE_NEW_RETURN (temp,
00069 ACE_Future_Rep<T> (),
00070 0);
00071 return temp;
00072 }
00073
00074 template <class T> ACE_Future_Rep<T> *
00075 ACE_Future_Rep<T>::create (void)
00076 {
00077
00078 ACE_Future_Rep<T> *temp = internal_create ();
00079 #if defined (ACE_NEW_THROWS_EXCEPTIONS)
00080 if (temp == 0)
00081 ACE_throw_bad_alloc;
00082 #else
00083 ACE_ASSERT (temp != 0);
00084 #endif
00085 return temp;
00086 }
00087
00088
00089 template <class T> ACE_Future_Rep<T> *
00090 ACE_Future_Rep<T>::attach (ACE_Future_Rep<T>*& rep)
00091 {
00092 ACE_ASSERT (rep != 0);
00093
00094 ACE_MT (ACE_Guard<ACE_Thread_Mutex> r_mon (rep->value_ready_mutex_));
00095 ++rep->ref_count_;
00096 return rep;
00097 }
00098
00099 template <class T> void
00100 ACE_Future_Rep<T>::detach (ACE_Future_Rep<T>*& rep)
00101 {
00102 ACE_ASSERT (rep != 0);
00103
00104 ACE_MT (ACE_GUARD (ACE_Thread_Mutex, r_mon, rep->value_ready_mutex_));
00105
00106 if (rep->ref_count_-- == 0)
00107 {
00108 ACE_MT (r_mon.release ());
00109
00110
00111
00112 delete rep;
00113 }
00114 }
00115
00116 template <class T> void
00117 ACE_Future_Rep<T>::assign (ACE_Future_Rep<T>*& rep, ACE_Future_Rep<T>* new_rep)
00118 {
00119 ACE_ASSERT (rep != 0);
00120 ACE_ASSERT (new_rep != 0);
00121
00122 ACE_MT (ACE_GUARD (ACE_Thread_Mutex, r_mon, rep->value_ready_mutex_));
00123
00124 ACE_Future_Rep<T>* old = rep;
00125 rep = new_rep;
00126
00127
00128 if (old->ref_count_-- == 0)
00129 {
00130 ACE_MT (r_mon.release ());
00131
00132
00133
00134 delete old;
00135 }
00136 }
00137
00138 template <class T>
00139 ACE_Future_Rep<T>::ACE_Future_Rep (void)
00140 : value_ (0),
00141 ref_count_ (0),
00142 value_ready_ (this->value_ready_mutex_)
00143 {
00144 }
00145
00146 template <class T>
00147 ACE_Future_Rep<T>::~ACE_Future_Rep (void)
00148 {
00149 delete this->value_;
00150 }
00151
00152 template <class T> int
00153 ACE_Future_Rep<T>::ready (void) const
00154 {
00155 return this->value_ != 0;
00156 }
00157
00158 template <class T> int
00159 ACE_Future_Rep<T>::set (const T &r,
00160 ACE_Future<T> &caller)
00161 {
00162
00163 if (this->value_ == 0)
00164 {
00165 ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex,
00166 ace_mon,
00167 this->value_ready_mutex_,
00168 -1));
00169
00170
00171
00172 if (this->value_ == 0)
00173 {
00174 ACE_NEW_RETURN (this->value_,
00175 T (r),
00176 -1);
00177
00178
00179 ACE_TYPENAME OBSERVER_COLLECTION::iterator iterator =
00180 this->observer_collection_.begin ();
00181
00182 ACE_TYPENAME OBSERVER_COLLECTION::iterator end =
00183 this->observer_collection_.end ();
00184
00185 while (iterator != end)
00186 {
00187 OBSERVER *observer = *iterator++;
00188 observer->update (caller);
00189 }
00190
00191
00192 return this->value_ready_.broadcast ();
00193 }
00194
00195 }
00196 return 0;
00197 }
00198
00199 template <class T> int
00200 ACE_Future_Rep<T>::get (T &value,
00201 ACE_Time_Value *tv) const
00202 {
00203
00204 if (this->value_ == 0)
00205 {
00206 ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon,
00207 ACE_const_cast (ACE_Thread_Mutex &, this->value_ready_mutex_),
00208 -1));
00209
00210
00211
00212 while (this->value_ == 0)
00213
00214 if ((ACE_const_cast (ACE_Condition_Thread_Mutex &, this->value_ready_)).wait (tv) == -1)
00215 return -1;
00216
00217
00218 }
00219
00220 value = *this->value_;
00221 return 0;
00222 }
00223
00224 template <class T> int
00225 ACE_Future_Rep<T>::attach (ACE_Future_Observer<T> *observer,
00226 ACE_Future<T> &caller)
00227 {
00228 ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, this->value_ready_mutex_, -1));
00229
00230
00231
00232
00233 int result = 1;
00234
00235
00236 if (this->value_ == 0)
00237 result = this->observer_collection_.insert (observer);
00238 else
00239 observer->update (caller);
00240
00241 return result;
00242 }
00243
00244 template <class T> int
00245 ACE_Future_Rep<T>::detach (ACE_Future_Observer<T> *observer)
00246 {
00247 ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, this->value_ready_mutex_, -1));
00248
00249
00250
00251 return this->observer_collection_.remove (observer);
00252 }
00253
00254 template <class T>
00255 ACE_Future_Rep<T>::operator T ()
00256 {
00257
00258 if (this->value_ == 0)
00259 {
00260
00261 ACE_MT (ACE_GUARD_RETURN (ACE_Thread_Mutex, ace_mon, this->value_ready_mutex_, 0));
00262
00263
00264
00265
00266
00267
00268 while (this->value_ == 0)
00269 if (this->value_ready_.wait () == -1)
00270
00271
00272
00273 return 0;
00274
00275
00276 }
00277
00278 return *this->value_;
00279 }
00280
00281 template <class T>
00282 ACE_Future<T>::ACE_Future (void)
00283 : future_rep_ (FUTURE_REP::create ())
00284 {
00285 }
00286
00287 template <class T>
00288 ACE_Future<T>::ACE_Future (const ACE_Future<T> &r)
00289 : future_rep_ (FUTURE_REP::attach (((ACE_Future<T> &) r).future_rep_))
00290 {
00291 }
00292
00293 template <class T>
00294 ACE_Future<T>::ACE_Future (const T &r)
00295 : future_rep_ (FUTURE_REP::create ())
00296 {
00297 ACE_DEBUG ((LM_DEBUG,
00298 ACE_LIB_TEXT (" (%t) funny constructor\n")));
00299 this->future_rep_->set (r,
00300 *this);
00301 }
00302
00303 template <class T>
00304 ACE_Future<T>::~ACE_Future (void)
00305 {
00306 FUTURE_REP::detach (future_rep_);
00307 }
00308
00309 template <class T> int
00310 ACE_Future<T>::operator== (const ACE_Future<T> &r) const
00311 {
00312 return r.future_rep_ == this->future_rep_;
00313 }
00314
00315 template <class T> int
00316 ACE_Future<T>::operator!= (const ACE_Future<T> &r) const
00317 {
00318 return r.future_rep_ != this->future_rep_;
00319 }
00320
00321 template <class T> int
00322 ACE_Future<T>::cancel (const T &r)
00323 {
00324 this->cancel ();
00325 return this->future_rep_->set (r,
00326 *this);
00327 }
00328
00329 template <class T> int
00330 ACE_Future<T>::cancel (void)
00331 {
00332
00333
00334 FUTURE_REP::assign (this->future_rep_,
00335 FUTURE_REP::create ());
00336 return 0;
00337 }
00338
00339 template <class T> int
00340 ACE_Future<T>::set (const T &r)
00341 {
00342
00343 return this->future_rep_->set (r,
00344 *this);
00345 }
00346
00347 template <class T> int
00348 ACE_Future<T>::ready (void) const
00349 {
00350
00351 return this->future_rep_->ready ();
00352 }
00353
00354 template <class T> int
00355 ACE_Future<T>::get (T &value,
00356 ACE_Time_Value *tv) const
00357 {
00358
00359 return this->future_rep_->get (value, tv);
00360 }
00361
00362 template <class T> int
00363 ACE_Future<T>::attach (ACE_Future_Observer<T> *observer)
00364 {
00365 return this->future_rep_->attach (observer, *this);
00366 }
00367
00368 template <class T> int
00369 ACE_Future<T>::detach (ACE_Future_Observer<T> *observer)
00370 {
00371 return this->future_rep_->detach (observer);
00372 }
00373
00374 template <class T>
00375 ACE_Future<T>::operator T ()
00376 {
00377
00378
00379
00380
00381
00382
00383
00384
00385
00386
00387
00388
00389 return *future_rep_;
00390 }
00391
00392 template <class T> void
00393 ACE_Future<T>::operator = (const ACE_Future<T> &rhs)
00394 {
00395
00396
00397
00398
00399
00400 ACE_Future<T> &r = (ACE_Future<T> &) rhs;
00401 FUTURE_REP::assign (this->future_rep_,
00402 FUTURE_REP::attach (r.future_rep_));
00403 }
00404
00405 template <class T> void
00406 ACE_Future<T>::dump (void) const
00407 {
00408 ACE_DEBUG ((LM_DEBUG,
00409 ACE_BEGIN_DUMP, this));
00410
00411 if (this->future_rep_)
00412 this->future_rep_->dump ();
00413
00414 ACE_DEBUG ((LM_DEBUG,
00415 ACE_END_DUMP));
00416 }
00417
00418 template <class T> ACE_Future_Rep<T> *
00419 ACE_Future<T>::get_rep ()
00420 {
00421 return this->future_rep_;
00422 }
00423
00424 template <class T> void *
00425 ACE_Future<T>::operator new (size_t)
00426 {
00427 ACE_throw_bad_alloc;
00428 #if defined (__HP_aCC)
00429 return 0;
00430 #endif
00431 }
00432
00433 template <class T> void
00434 ACE_Future<T>::operator delete (void *)
00435 {
00436 }
00437
00438 template <class T> void
00439 ACE_Future<T>::operator & ()
00440 {
00441 }
00442
00443 #endif
00444 #endif