00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #ifndef __peoSyncIslandMig_h
00025 #define __peoSyncIslandMig_h
00026
00027
00028 #include <queue>
00029 #include <cassert>
00030
00031 #include <eoPeriodicContinue.h>
00032
00033 #include <utils/eoUpdater.h>
00034
00035 #include <eoContinue.h>
00036 #include <eoSelect.h>
00037 #include <eoReplacement.h>
00038 #include <eoPop.h>
00039
00040 #include "core/topology.h"
00041 #include "core/thread.h"
00042 #include "core/eoPop_comm.h"
00043 #include "core/peo_debug.h"
00044
00045
00047
00129 template< class EOT > class peoSyncIslandMig : public Cooperative, public eoUpdater {
00130
00131 public:
00132
00142 peoSyncIslandMig(
00143 unsigned __frequency,
00144 eoSelect< EOT >& __select,
00145 eoReplacement< EOT >& __replace,
00146 Topology& __topology,
00147 eoPop< EOT >& __source,
00148 eoPop< EOT >& __destination
00149 );
00150
00155 void operator()();
00156
00158 void pack();
00160 void unpack();
00161
00163 void notifySending();
00164
00165
00166 private:
00167
00168 void emigrate();
00169 void immigrate();
00170
00171
00172 private:
00173
00174 eoPeriodicContinue< EOT > cont;
00175 eoSelect< EOT >& select;
00176 eoReplacement< EOT >& replace;
00177 Topology& topology;
00178
00179
00180 eoPop< EOT >& source;
00181 eoPop< EOT >& destination;
00182
00183
00184 std :: queue< eoPop< EOT > > imm;
00185 std :: queue< eoPop< EOT > > em;
00186
00187 std :: queue< Cooperative* > coop_em;
00188
00189 sem_t sync;
00190 };
00191
00192
00193 template< class EOT > peoSyncIslandMig< EOT > :: peoSyncIslandMig(
00194
00195 unsigned __frequency,
00196 eoSelect< EOT >& __select,
00197 eoReplacement< EOT >& __replace,
00198 Topology& __topology,
00199 eoPop< EOT >& __source,
00200 eoPop< EOT >& __destination
00201
00202 ) : cont( __frequency ), select( __select ), replace( __replace ), topology( __topology ), source( __source ), destination( __destination )
00203 {
00204
00205 __topology.add( *this );
00206 sem_init( &sync, 0, 0 );
00207 }
00208
00209
00210 template< class EOT > void peoSyncIslandMig< EOT > :: pack() {
00211
00212 lock(); {
00213
00214 :: pack( coop_em.front()->getKey() );
00215 :: pack( em.front() );
00216 coop_em.pop();
00217 em.pop();
00218 }
00219 unlock();
00220 }
00221
00222
00223 template< class EOT > void peoSyncIslandMig< EOT > :: unpack() {
00224
00225 lock(); {
00226
00227 eoPop< EOT > mig;
00228 :: unpack( mig );
00229 imm.push( mig );
00230 }
00231 unlock();
00232
00233 sem_post( &sync );
00234 }
00235
00236
00237 template< class EOT > void peoSyncIslandMig< EOT > :: emigrate() {
00238
00239 std :: vector< Cooperative* > in, out;
00240 topology.setNeighbors( this, in, out );
00241
00242 for ( unsigned i = 0; i < out.size(); i ++ ) {
00243
00244 eoPop< EOT > mig;
00245 select( source, mig );
00246 em.push( mig );
00247 coop_em.push( out[ i ] );
00248 send( out[ i ] );
00249 printDebugMessage( "sending some emigrants." );
00250 }
00251 }
00252
00253
00254 template< class EOT > void peoSyncIslandMig< EOT > :: immigrate() {
00255
00256 lock(); {
00257
00258 assert( imm.size() );
00259 replace( destination, imm.front() ) ;
00260 imm.pop();
00261 printDebugMessage( "receiving some immigrants." );
00262 }
00263 unlock();
00264 }
00265
00266
00267 template< class EOT > void peoSyncIslandMig< EOT > :: operator()() {
00268
00269 if ( !cont( source ) ) {
00270
00271
00272 emigrate();
00273 stop();
00274
00275
00276 sem_wait( &sync );
00277 getOwner()->setActive();
00278
00279
00280 immigrate();
00281 }
00282 }
00283
00284
00285 template< class EOT > void peoSyncIslandMig< EOT > :: notifySending() {
00286
00287 lock(); {
00288
00289 if ( imm.empty() ) {
00290
00291 printDebugMessage( "entering pasive mode\n" );
00292 getOwner()->setPassive();
00293 }
00294 }
00295 unlock();
00296
00297 resume();
00298 }
00299
00300
00301 #endif