PaCO++  0.05
ClientSide.cc
Go to the documentation of this file.
00001 /* Padico Advanced Examples
00002  * author: Christian Pérez
00003  */
00004 
00005 #include <stdio.h>
00006 
00007 #include "Schedule.h"
00008 #include "DistributionBloc.h"
00009 #include "Internal.h"
00010 
00011 //#define NO_COM
00012 
00013 #undef STANDALONE_FILE
00014 
00015 #undef DEBUG_INTERNAL
00016 #undef DEBUG_COMM
00017 
00018 #ifdef NO_COM
00019 inline char* mymalloc(unsigned sz) {
00020   static unsigned base=0x1000000;
00021   unsigned ret = base;
00022   base+=0x1000;
00023   return (char*) ret;
00024 }
00025 #endif
00026 
00027 #ifdef STANDALONE_FILE
00028 int pid;
00029 
00030 #include "../Generated/Concret.h"
00031 #include "../Generated/XServiceType.h"
00032 
00033 #endif
00034 
00038 
00039 void computeSendDataBlock1DClient(const GlobalData_t& gd, const LocalData_t &sd, 
00040               const Topology_t &stopo, const Topology_t &dtopo,
00041               vAbstrait& vdarray, vector<unsigned>& destid, void* comm)
00042 {
00043 
00044   cerr << "In computeSendDataBlock1DClient...\n";
00045 
00046   vector<LocalData_t> sched_send;
00047   vector<LocalData_t> sched_recv;
00048 
00049   sched_send.clear();
00050   sched_recv.clear();
00051 
00055   // Compute what to send
00057   cerr << "In computeSendDataBlock1DClient...computing what to send\n";
00058   computeSendBlock1D(gd, sd, stopo, dtopo, sched_send);
00059 
00063   // Compute what to receive
00065   cerr << "In computeSendDataBlock1DClient...computing what to receive\n";
00066 
00067   // compute how many dest local data this node has to handle
00068   unsigned int nvdarray  = dtopo.total/stopo.total;
00069   unsigned int remaining = (nvdarray*stopo.total + sd.rank < dtopo.total)?1:0;
00070   nvdarray += remaining;
00071 
00072   // Preparing also CORBA stuff
00073   vdarray.clear();
00074   vdarray.resize(nvdarray);
00075   destid.clear();
00076   destid.resize(nvdarray);
00077 
00078   // so, we simulate node from rank, rank+stopo.total ,... only if nvdarray>0
00079   unsigned dbsz = blockSize(gd.len, dtopo.total);
00080   //  cerr << "DBSZ: " << dbsz << endl;
00081   for (unsigned it=0; it<nvdarray; it++) {
00082 
00083     cerr << "computeSendDataBlock1DClient: it = " << it << endl;
00084 
00085     Abstrait* out = vdarray[it];
00086 
00087     out->topo().total   = dtopo.total;
00088     out->gd().len       = gd.len;
00089     out->gd().unit_size = gd.unit_size;
00090 
00091     // add for mode informations
00092     out->mode() = PaCO::ClientSide;
00093 
00094     out->dist().length(1);
00095     out->setSeqLength(1);
00096 
00097     PaCO::PacoLocalData_t& pld = out->dist()[0];
00098     LocalData_t dd;
00099     pld.rank  = dd.rank  = sd.rank + it * stopo.total;
00100     pld.start = dd.start = dd.rank * dbsz;
00101     pld.len   = dd.len   = localBlockLengthO(gd.len, dd.rank, dtopo.total, dbsz);
00102 
00103 #ifdef DEBUG_INTERNAL
00104     fprintf(stderr, "%d: -- r:%d gl:%d ll:%d start:%d bz:%d dt:%d\n", pid,
00105        dd.rank, gd.len, dd.len, dd.start, dbsz, dtopo.total);
00106 #endif
00107 
00108     destid[it] = dd.rank;
00109 
00112     // Allocating memory
00113 #ifdef NO_COM
00114     dd.base = (char*) mymalloc(pld.len * gd.unit_size);
00115     out->setDataLength(0, pld.len);
00116 #else
00117 #ifdef DEBUG_INTERNAL
00118     cerr << "Allocating a sequence of length " << pld.len << endl;
00119 #endif
00120     out->setDataLength(0, pld.len);
00121     if (pld.len > 0 )
00122       dd.base = out->getDataBuffer(0, false);
00123     else
00124       dd.base = (char*) 1;
00125 #endif
00126 
00127     if (dd.base==0) {
00128       cerr << "Cannot allocate memory for #elements" << pld.len  << endl;
00129     } else {
00130 #ifdef DEBUG_INTERNAL
00131       fprintf(stderr, "dd.base = %p\n", dd.base);
00132 #endif
00133     }
00134 
00135     computeReceiveBlock1D(gd, dd, stopo, dtopo, sched_recv);
00136   }
00137 
00141   // Doing local communication
00143   fprintf(stderr, "In computeSendDataBlock1DClient...Doing local communications with ctopo: %ld\n", dtopo.total);
00144   doSchedule(gd, sd, stopo, sched_send, sched_recv, comm); 
00145 
00146   cerr << "In computeSendDataBlock1DClient...ok\n";
00147 }
00148 
00152 
00153 // simply send data from source i to dest i % dtopo.total
00154 // if less sources than destination: dest j <  source j % stopo.total
00155 
00156 // Client Side function
00157 void computeSendDataBlock1DServer(const GlobalData_t& gd, const LocalData_t &sd, 
00158               const Topology_t &stopo, const Topology_t &dtopo,
00159               vAbstrait& vdarray, vector<unsigned>& destid)
00160 {
00161 
00162 
00163   // Easy: node i send data to node i%dtopo.total
00164   // It has to send an empty message to nodes i+stopo.total, i+2*stopo.total ... < dtopo.total
00165 
00166   // How messages to send ?
00167   unsigned int nvdarray  = dtopo.total/stopo.total;
00168   unsigned int remaining = (nvdarray*stopo.total + sd.rank < dtopo.total)?1:0;
00169   nvdarray += remaining;
00170 
00171   // alwaays something to send
00172   if ( nvdarray == 0 ) nvdarray=1;
00173 
00174   // Preparing  CORBA stuff
00175   vdarray.clear();
00176   vdarray.resize(nvdarray);
00177   destid.clear();
00178   destid.resize(nvdarray);
00179 
00180   for (unsigned it=0; it<nvdarray; it++) {
00181 
00182     Abstrait* out = vdarray[it];
00183 
00184     out->topo().total   = stopo.total;
00185     out->gd().len       = gd.len;
00186     out->gd().unit_size = gd.unit_size;
00187     
00188     // add for mode information
00189     out->mode() = PaCO::ServerSide;
00190 
00191     if ( it == 0 ) { // always data to send
00192       out->dist().length(1);
00193       out->setSeqLength(1);
00194 
00195       out->dist()[0].rank  = sd.rank;
00196       out->dist()[0].start = sd.start;
00197       out->dist()[0].len   = sd.len;
00198       out->DataReplace(0, sd.len, sd.base, false);
00199     } else { // always nothing to send
00200       out->dist().length(0);
00201       out->setSeqLength(0);
00202     }
00203     destid[it] = ( sd.rank + it * stopo.total ) % dtopo.total;
00204   }
00205 }
00206 
00209 
00210 void computeSendDataBlock1DComm() {
00211 }
00212 
00215 
00216 // vOut represents what localData/stopo have to send to nodes of dtopo (vOut[].rank is in dtopo space)
00217 void computeSendDataBlock1D(const GlobalData_t& gd, const LocalData_t &sd, 
00218              const Topology_t &stopo, const Topology_t &dtopo,
00219              vAbstrait& vdarray, vector<unsigned>& destid,
00220              const PaCO::distLoc_t& mode, void* comm) {
00221 
00222   switch(mode) {
00223   case PaCO::none: cerr << "INTERNAL ERROR: " << __FILE__ << " " << __FUNCTION__ << endl;
00224   case PaCO::ClientSide: computeSendDataBlock1DClient(gd, sd, stopo, dtopo, vdarray, destid, comm); break;
00225   case PaCO::ServerSide: computeSendDataBlock1DServer(gd, sd, stopo, dtopo, vdarray, destid); break;
00226   case PaCO::CommSide:   computeSendDataBlock1DComm  (); break;   
00227   }
00228   
00229 }
00230