0c85ab7329fa0e6e74cd2292f54f8aaecae8a963
[charm.git] / examples / pose / Ring / Worker.C
1 #include <math.h>
2
3 int GCD(int a, int b) {
4   if (b > a) 
5     return GCD(b,a);
6   else if(b == 0) 
7     return a;
8   else
9     return GCD(b, a%b);
10 }
11
12
13 worker::worker(WorkerData *m)
14 {
15   int i;
16   numObjs = m->numObjs;
17   numMsgs = m->numMsgs;
18   msgSize = m->msgSize;
19   grainSize = m->grainSize;
20   granularity = m->granularity;
21   density = m->density;
22   for (i=0; i<100; i++) data[i] = 0;
23   sent = 0;
24   totalObjs = numObjs * CkNumPes();
25   localDensity = ((double)density)/((double)totalObjs);
26   delete m;
27   CkPrintf("Worker %d created on PE %d.\n", myHandle, CkMyPe());
28
29   SmallWorkMsg *sm = new SmallWorkMsg;
30   memset(sm->data, 0, SM_MSG_SZ*sizeof(int));
31   sm->fromPE = -1;
32   CkPrintf("Worker %d created on PE %d.\n", myHandle, CkMyPe());
33   //if (myHandle%numObjs == 0) { //local ring; multiple global rings
34   //if (myHandle%(numObjs/2) == 0) { //multiple offset global rings
35   //if (myHandle == 0) { 
36   CkPrintf("Worker %d starting ring, sending to self.\n", myHandle);
37   POSE_invoke(workSmall(sm), worker, parent->thisIndex, 0);
38   //}
39 }
40
41 worker::worker()
42 {
43 }
44
45 worker& worker::operator=(const worker& obj)
46 {
47   int i;
48   rep::operator=(obj);
49   numObjs = obj.numObjs;
50   numMsgs = obj.numMsgs;
51   msgSize = obj.msgSize;
52   grainSize = obj.grainSize;
53   granularity = obj.granularity;
54   density = obj.density;
55   sent = obj.sent;
56   totalObjs = obj.totalObjs;
57   for (i=0; i<100; i++) data[i] = obj.data[i];
58   return *this;
59 }
60
61 void worker::terminus()
62 {
63   if (sent != numMsgs)
64     CkPrintf("%d sent %d messages!\n", myHandle, sent);
65 }
66
67 void worker::workSmall(SmallWorkMsg *m)
68 {
69   CkPrintf("%d receiving small work at %d from obj %d\n", parent->thisIndex, ovt, m->fromPE);
70   doWork();
71 }
72
73 void worker::workSmall_anti(SmallWorkMsg *m)
74 {
75   restore(this);
76 }
77
78 void worker::workSmall_commit(SmallWorkMsg *m)
79 {
80 }
81
82 void worker::workMedium(MediumWorkMsg *m)
83 {
84   //CkPrintf("%d receiving medium work at %d\n", parent->thisIndex, ovt);
85   doWork();
86 }
87
88 void worker::workMedium_anti(MediumWorkMsg *m)
89 {
90   restore(this);
91 }
92
93 void worker::workMedium_commit(MediumWorkMsg *m)
94 {
95 }
96
97 void worker::workLarge(LargeWorkMsg *m)
98 {
99   //CkPrintf("%d receiving large work at %d\n", parent->thisIndex, ovt);
100   doWork();
101 }
102
103 void worker::workLarge_anti(LargeWorkMsg *m)
104 {
105   restore(this);
106 }
107
108 void worker::workLarge_commit(LargeWorkMsg *m)
109 {
110 }
111
112 void worker::doWork()
113 {
114   SmallWorkMsg *sm;
115   MediumWorkMsg *mm;
116   LargeWorkMsg *lm;
117   int nbr;
118
119   if (sent == numMsgs) return;
120   sent++;
121
122   // generate an event
123   int actualMsgSize = msgSize;
124   if (msgSize == MIX_MS) actualMsgSize = (actualMsgSize + 1) % 3;
125   if (actualMsgSize == SMALL) {
126     sm = new SmallWorkMsg;
127     memset(sm->data, 0, SM_MSG_SZ*sizeof(int));
128     sm->fromPE = myHandle;
129     // local ring
130     POSE_invoke(workSmall(sm), worker, ((myHandle%numObjs)+1)%numObjs + (numObjs*CkMyPe()), 0);
131     //POSE_invoke(workSmall(sm), worker, (myHandle+1)%totalObjs, 0);
132     CkPrintf("%d sending small work to %d at %d. Sent=%d\n",myHandle,((myHandle%numObjs)+1)%numObjs + (numObjs*CkMyPe()),ovt,sent);
133   }
134   else if (actualMsgSize == MEDIUM) {
135     mm = new MediumWorkMsg;
136     memset(mm->data, 0, MD_MSG_SZ*sizeof(int));
137     POSE_invoke(workMedium(mm), worker, (myHandle+1)%totalObjs, 0);
138     //CkPrintf("%d sending medium work to %d at %d\n",myHandle,nbr,ovt);
139   }
140   else if (actualMsgSize == LARGE) {
141     lm = new LargeWorkMsg;
142     memset(lm->data, 0, LG_MSG_SZ*sizeof(int));
143     POSE_invoke(workLarge(lm), worker, (myHandle+1)%totalObjs, 0);
144     //CkPrintf("%d sending large work to %d at %d\n",myHandle,nbr,ovt);
145   }
146   int elapseCheck = sent * (1.0/localDensity);
147   if (OVT() < elapseCheck) elapse(elapseCheck-OVT());
148   CkPrintf("%d sent %d messages out of %d!\n", myHandle, sent, numMsgs);
149 }
150