00001
00002
00003
00004
00005
00006
00007 #include <math.h>
00008 #include <string.h>
00009
00010 #include "LBAgent.h"
00011
00012 #define PREF_RET_SIZE 5
00013
00014 TopologyAgent::TopologyAgent(CentralLB::LDStats* lbDB,int p): Agent(p), stats(lbDB){
00015 int i;
00016
00017 LBtopoFn topofn;
00018 topofn = LBTopoLookup(_lbtopo);
00019 if (topofn == NULL) {
00020 char str[1024];
00021 CmiPrintf("LBAgent> Fatal error: Unknown topology: %s. Choose from:\n", _lbtopo);
00022 printoutTopo();
00023 sprintf(str, "LBAgent> Fatal error: Unknown topology: %s", _lbtopo);
00024 CmiAbort(str);
00025 }
00026 topo = topofn(p);
00027
00028 stats->makeCommHash();
00029 preferred_list = new Elem[p];
00030 commObjs = new int*[stats->n_objs];
00031 for(i=0;i<stats->n_objs;i++){
00032 commObjs[i] = new int[stats->n_objs];
00033 for(int j=0;j<stats->n_objs;j++)
00034 commObjs[i][j] = 0;
00035 }
00036
00037 hopCount = new int*[npes];
00038 for(i=0;i<npes;i++){
00039 hopCount[i] = new int[npes];
00040 for(int j=0;j<npes;j++)
00041 hopCount[i][j] = 0;
00042 }
00043
00044
00045 for(i=0;i<stats->n_comm;i++){
00046
00047
00048 LDCommData &cdata = stats->commData[i];
00049 if(cdata.from_proc() || cdata.receiver.get_type() != LD_OBJ_MSG)
00050 continue;
00051 int senderID = stats->getHash(cdata.sender);
00052 CmiAssert(senderID < stats->n_objs);
00053 int recverID = stats->getHash(cdata.receiver.get_destObj());
00054 CmiAssert(recverID < stats->n_objs);
00055
00056
00057
00058
00059 commObjs[senderID][recverID] += cdata.bytes;
00060 commObjs[recverID][senderID] += cdata.bytes;
00061 }
00062 }
00063
00064 int TopologyAgent :: compare(const void *p,const void *q){
00065 return (int)(((Elem*)p)->Cost - ((Elem*)q)->Cost);
00066 }
00067
00068
00069 Agent::Elem* TopologyAgent :: my_preferred_procs(int *existing_map,int object,int *trialpes,int metric) {
00070
00071 int tp;
00072 int *procs_list;
00073
00074
00075
00076 for(int i=0;i<npes;i++){
00077 preferred_list[i].pe = -1;
00078 preferred_list[i].Cost = 0;
00079 }
00080
00081 int preflistSize=0;
00082
00083 if(metric==1){
00084
00085 if(trialpes == NULL) {
00086 procs_list = &tp;
00087 *procs_list = -1;
00088 }
00089 else
00090 procs_list = trialpes;
00091
00092
00093 int proc=0;
00094 int index=0;
00095 int cost=0;
00096
00097 if(procs_list[0]!=-1)
00098 proc = procs_list[index];
00099
00100 while(1){
00101 cost=0;
00102 if(!stats->procs[proc].available){
00103 if(procs_list[0]==-1){
00104 proc++;
00105 if(proc == npes)
00106 break;
00107 }
00108 else {
00109 index++;
00110 if(procs_list[index] == -1)
00111 break;
00112 proc = procs_list[index];
00113 }
00114 continue;
00115 }
00116
00117
00118 for(int i=0;i<stats->n_objs;i++){
00119 if(existing_map[i]!=-1 && commObjs[object][i]!=0){
00120
00121 if(hopCount[proc][existing_map[i]])
00122 cost += hopCount[proc][existing_map[i]]*commObjs[object][i];
00123 else{
00124 hopCount[proc][existing_map[i]]=topo->get_hop_count(proc,existing_map[i]);
00125 hopCount[existing_map[i]][proc]=hopCount[proc][existing_map[i]];
00126 cost += hopCount[proc][existing_map[i]]*commObjs[object][i];
00127 }
00128 }
00129 }
00130 preferred_list[preflistSize].pe = proc;
00131 preferred_list[preflistSize].Cost = cost;
00132 preflistSize++;
00133
00134 if(procs_list[0]==-1){
00135 proc++;
00136 if(proc == npes)
00137 break;
00138 }
00139 else {
00140 index++;
00141 if(procs_list[index] == -1)
00142 break;
00143 proc = procs_list[index];
00144 }
00145 }
00146 }
00147
00148 if(metric==2){
00149
00150 int i=0;
00151 int max_neighbors = topo->max_neighbors();
00152 int *comProcs = new int[npes];
00153 for(i=0;i<npes;i++)
00154 comProcs[i]=0;
00155 int max_comm=0;
00156 int max_proc=-1;
00157 int *neigh;
00158 for(i=0;i<stats->n_objs;i++){
00159 if(existing_map[i]!=-1 && commObjs[object][i]!=0){
00160 comProcs[existing_map[i]] += commObjs[object][i];
00161 if(comProcs[existing_map[i]] > max_comm){
00162 max_comm = comProcs[existing_map[i]];
00163 max_proc = existing_map[i];
00164 }
00165 }
00166 }
00167 int num_neigh=0;
00168 int done=0,j=0;
00169 if(max_proc!=-1){
00170 i=0;
00171 while(trialpes[i]!=-1){
00172 if(max_proc==trialpes[i]){
00173 preferred_list[0].pe = max_proc;
00174 preferred_list[0].Cost = max_comm;
00175 preflistSize++;
00176 done = 1;
00177 }
00178 }
00179 if(!done){
00180 neigh = new int[max_neighbors];
00181 topo->neighbors(max_proc,neigh,num_neigh);
00182 while(trialpes[i]!=-1){
00183 for(j=0;j<num_neigh;j++)
00184 if(trialpes[i]==neigh[j]){
00185 preferred_list[preflistSize].pe = neigh[j];
00186 preferred_list[preflistSize].Cost = comProcs[neigh[j]];
00187 preflistSize++;
00188 done=1;
00189 }
00190 }
00191 }
00192 if(!done){
00193 int *secondneigh = new int[max_neighbors];
00194 int k=0;
00195 i=0;
00196 int num=num_neigh;
00197 for(k=0;k<num;k++){
00198 topo->neighbors(neigh[k],secondneigh,num_neigh);
00199 while(trialpes[i]!=-1){
00200 for(j=0;j<num_neigh;j++)
00201 if(trialpes[i]==secondneigh[j]){
00202 preferred_list[preflistSize].pe = secondneigh[j];
00203 preferred_list[preflistSize].Cost = comProcs[secondneigh[j]];
00204 preflistSize++;
00205 done=1;
00206 }
00207 }
00208 }
00209 }
00210
00211 }
00212 }
00213
00214
00215
00216
00217
00218 Agent::Elem *prefreturnList = new Elem[PREF_RET_SIZE+1];
00219 int *taken_proc = new int[preflistSize];
00220 double min_cost=preferred_list[0].Cost;
00221 int min_cost_index=0;
00222
00223
00224
00225
00226 int s=0;
00227 int flag=0;
00228 int u=0;
00229
00230 for(s=0;s<preflistSize;s++)
00231 taken_proc[s]=0;
00232 for(s=0;s<PREF_RET_SIZE;s++){
00233 for(u=0;u<preflistSize;u++)
00234 if(!taken_proc[u]){
00235 min_cost=preferred_list[u].Cost;
00236 min_cost_index=u;
00237 break;
00238 }
00239 if(u==preflistSize)
00240 break;
00241 for(int t=u;t<preflistSize;t++){
00242 if(preferred_list[t].Cost <= min_cost && !taken_proc[t]){
00243 min_cost = preferred_list[t].Cost;
00244 min_cost_index=t;
00245 flag=1;
00246 }
00247 }
00248 if(flag){
00249 taken_proc[min_cost_index]=1;
00250 prefreturnList[s].pe=preferred_list[min_cost_index].pe;
00251 prefreturnList[s].Cost=preferred_list[min_cost_index].Cost;
00252 flag=0;
00253 }
00254 }
00255 prefreturnList[s].pe=-1;
00256 prefreturnList[s].Cost=-1;
00257
00258
00259
00260
00261 return prefreturnList;
00262
00263 }
00264
00265
00266
00267
00268
00269 MulticastAgent::MulticastAgent(BaseLB::LDStats* stats, int p): Agent(p)
00270 {
00271 stats->makeCommHash();
00272
00273 nobj = stats->n_objs;
00274 objmap = new CkVec<int> [nobj];
00275 for (int com = 0; com < stats->n_comm;com++) {
00276 LDCommData &commData = stats->commData[com];
00277 if (commData.recv_type()!=LD_OBJLIST_MSG) continue;
00278
00279 mcastList.push_back(MInfo(commData.bytes, commData.messages));
00280 int mID = mcastList.size()-1;
00281 MInfo &minfo = mcastList[mID];
00282 int sender = stats->getHash(commData.sender);
00283
00284 objmap[sender].push_back(mID);
00285
00286 minfo.objs.push_back(sender);
00287 int nobjs;
00288 const LDObjKey *objs = commData.receiver.get_destObjs(nobjs);
00289 for (int i=0; i<nobjs; i++) {
00290 int receiver = stats->getHash(objs[i]);
00291 if((sender == -1)||(receiver == -1)) {
00292 if (_lb_args.migObjOnly()) continue;
00293 else CkAbort("Error in search\n");
00294 }
00295 objmap[receiver].push_back(mID);
00296 minfo.objs.push_back(receiver);
00297 }
00298 }
00299 }
00300
00301 Agent::Elem* MulticastAgent::my_preferred_procs(int *existing_map,int object,int *trialpes,int metric){
00302 int i;
00303
00304 CmiAssert(object < nobj);
00305
00306 double * comcosts = new double [npes];
00307 memset(comcosts, 0, sizeof(double)*npes);
00308 double alpha = _lb_args.alpha();
00309 double beta = _lb_args.beta();
00310
00311
00312 CkVec<int> &mlist = objmap[object];
00313
00314
00315 for (i=0; i<mlist.size(); i++) {
00316 MInfo &minfo = mcastList[mlist[i]];
00317 for (int obj=0; obj<minfo.objs.size(); obj++) {
00318 int pe = existing_map[obj];
00319 if (pe == -1) continue;
00320 comcosts[pe] += minfo.messages * alpha + minfo.nbytes * beta;
00321 }
00322 }
00323
00324 int count = 0;
00325 for (i=0; i<npes; i++) {
00326 if (comcosts[i] != 0.0) count++;
00327 }
00328 Elem *prefered = new Elem[count+1];
00329 for (i=0; i<count; i++) {
00330
00331 Elem maxp;
00332 for (int j=0; j<npes; j++)
00333 if (comcosts[j] != 0.0 && comcosts[j] > maxp.Cost) {
00334 maxp.pe = j;
00335 maxp.Cost = comcosts[j];
00336 }
00337 CmiAssert(maxp.pe!=-1);
00338 prefered[i] = maxp;
00339 comcosts[maxp.pe] = 0.0;
00340 }
00341
00342 delete [] comcosts;
00343 return prefered;
00344 }
00345
00346
00347
00348