Fix warnings and errors in ampi_noimpl.C
[charm.git] / src / xlat-i / xi-Message.C
blob55d8f15d5b8c8a7c5e4220caec69c446c2386f9f
1 #include "xi-Message.h"
3 #include <vector>
5 namespace xi {
7 static const char* CIMsgClassAnsi =
8     "{\n"
9     "  public:\n"
10     "    static int __idx;\n"
11     "    void* operator new(size_t, void*p) { return p; }\n"
12     "    void* operator new(size_t);\n"
13     "    void* operator new(size_t, int*, const int);\n"
14     "    void* operator new(size_t, int*, const int, const GroupDepNum);\n"
15     "    void* operator new(size_t, int*);\n"
16     "#if CMK_MULTIPLE_DELETE\n"
17     "    void operator delete(void*p, void*){dealloc(p);}\n"
18     "    void operator delete(void*p){dealloc(p);}\n"
19     "    void operator delete(void*p, int*, const int){dealloc(p);}\n"
20     "    void operator delete(void*p, int*, const int, const GroupDepNum){dealloc(p);}\n"
21     "    void operator delete(void*p, int*){dealloc(p);}\n"
22     "#endif\n"
23     "    void operator delete(void*p, size_t){dealloc(p);}\n"
24     "    static void* alloc(int,size_t, int*, int, GroupDepNum);\n"
25     "    static void dealloc(void *p);\n";
27 Message::Message(int l, NamedType* t, MsgVarList* mv) : type(t), mvlist(mv) {
28   line = l;
29   setTemplate(0);
32 const char* Message::proxyPrefix(void) { return Prefix::Message; }
34 void Message::genAllocDecl(XStr& str) {
35   int i, num;
36   XStr mtype;
37   mtype << type;
38   if (templat) templat->genVars(mtype);
39   str << CIMsgClassAnsi;
40   str << "    CMessage_" << mtype << "();\n";
41   str << "    static void *pack(" << mtype << " *p);\n";
42   str << "    static " << mtype << "* unpack(void* p);\n";
43   num = numArrays();
44   if (num > 0) {
45     str << "    void *operator new(size_t";
46     for (i = 0; i < num; i++) str << ", int";
47     str << ");\n";
48   }
49   str << "    void *operator new(size_t, ";
50   for (i = 0; i < num; i++) str << "int, ";
51   str << "const int);\n";
52   str << "    void *operator new(size_t, ";
53   for(i=0;i<num;i++)
54     str << "int, ";
55   str << "const int, const GroupDepNum);\n";
56   str << "#if CMK_MULTIPLE_DELETE\n";
57   if (num > 0) {
58     str << "    void operator delete(void *p";
59     for (i = 0; i < num; i++) str << ", int";
60     str << "){dealloc(p);}\n";
61   }
62   str << "    void operator delete(void *p, ";
63   for (i = 0; i < num; i++) str << "int, ";
64   str << "const int){dealloc(p);}\n";
65   str << "    void operator delete(void *p, ";
66   for (i = 0; i < num; i++) str << "int, ";
67   str << "const int, const GroupDepNum){dealloc(p);}\n";
68   str << "#endif\n";
71 const char GroupDepNumStruct[] =
72 "#ifndef GROUPDEPNUM_DECLARED\n"
73 "# define GROUPDEPNUM_DECLARED\n"
74 "struct GroupDepNum\n"
75 "{\n"
76 "  int groupDepNum;\n"
77 "  explicit GroupDepNum(int g = 0) : groupDepNum{g} { }\n"
78 "  operator int() const { return groupDepNum; }\n"
79 "};\n"
80 "#endif\n";
82 void Message::genDecls(XStr& str) {
83   XStr ptype;
84   ptype << proxyPrefix() << type;
85   if (type->isTemplated()) return;
86   str << GroupDepNumStruct;
87   str << "/* DECLS: ";
88   print(str);
89   str << " */\n";
90   if (templat) templat->genSpec(str);
91   str << "class ";
92   type->print(str);
93   str << ";\n";
94   if (templat) templat->genSpec(str);
95   str << "class " << ptype;
96   if (external || type->isTemplated()) {
97     str << ";\n";
98     return;
99   }
100   str << ":public CkMessage";
102   genAllocDecl(str);
104   if (!(external || type->isTemplated())) {
105     // generate register function
106     str << "    static void __register(const char *s, size_t size, CkPackFnPtr pack, "
107            "CkUnpackFnPtr unpack) {\n";
108     str << "      __idx = CkRegisterMsg(s, pack, unpack, dealloc, size);\n";
109     str << "    }\n";
110   }
111   str << "};\n";
113   if (strncmp(type->getBaseName(), "MarshallMsg_", 12) == 0) {
114     MsgVarList* ml;
115     MsgVar* mv;
116     int i;
117     str << "class " << type << " : public " << ptype << " {\n";
118     str << "  public:\n";
119     int num = numVars();
120     for (i = 0, ml = mvlist; i < num; i++, ml = ml->next) {
121       mv = ml->msg_var;
122       if (mv->isConditional() || mv->isArray()) {
123         str << "    /* ";
124         mv->print(str);
125         str << " */\n";
126         str << "    " << mv->type << " *" << mv->name << ";\n";
127       }
128     }
129     str << "};\n";
130   }
133 void Message::genDefs(XStr& str) {
134   int i, count, num = numVars();
135   int numArray = numArrays();
136   MsgVarList* ml;
137   MsgVar* mv;
138   XStr ptype, mtype, tspec;
139   ptype << proxyPrefix() << type;
140   if (templat) templat->genVars(ptype);
141   mtype << type;
142   if (templat) templat->genVars(mtype);
143   if (templat) {
144     templat->genSpec(tspec);
145     tspec << " ";
146   }
148   str << "/* DEFS: ";
149   print(str);
150   str << " */\n";
152   templateGuardBegin(templat, str);
153   if (!(external || type->isTemplated())) {
154     // new (size_t)
155     str << tspec << "void *" << ptype << "::operator new(size_t s){\n";
156     str << "  return " << mtype << "::alloc(__idx, s, 0, 0, GroupDepNum{});\n}\n";
157     // new (size_t, int*)
158     str << tspec << "void *" << ptype << "::operator new(size_t s, int* sz){\n";
159     str << "  return " << mtype << "::alloc(__idx, s, sz, 0, GroupDepNum{});\n}\n";
160     // new (size_t, int*, priobits)
161     str << tspec << "void *" << ptype << "::operator new(size_t s, int* sz,";
162     str << "const int pb){\n";
163     str << "  return " << mtype << "::alloc(__idx, s, sz, pb, GroupDepNum{});\n}\n";
164     // new (size_t, int *, priobits, groupDepNum)
165     str << tspec << "void *" << ptype << "::operator new(size_t s, int* sz,";
166     str << "const int pb, const GroupDepNum groupDepNum){\n";
167     str << "  return " << mtype << "::alloc(__idx, s, sz, pb, groupDepNum);\n}\n";
168     // new (size_t, int, int, ..., int)
169     if (numArray > 0) {
170       str << tspec << "void *" << ptype << "::operator new(size_t s";
171       for (i = 0; i < numArray; i++) str << ", int sz" << i;
172       str << ") {\n";
173       str << "  int sizes[" << numArray << "];\n";
174       for (i = 0; i < numArray; i++) str << "  sizes[" << i << "] = sz" << i << ";\n";
175       str << "  return " << mtype << "::alloc(__idx, s, sizes, 0, GroupDepNum{});\n";
176       str << "}\n";
177     }
178     // new (size_t, int, int, ..., int, priobits)
179     // degenerates to  new(size_t, priobits)  if no varsize
180     std::vector<MsgVar*> arrayVars;
181     str << tspec << "void *" << ptype << "::operator new(size_t s, ";
182     for (i = 0; i < numArray; i++) str << "int sz" << i << ", ";
183     str << "const int p) {\n";
184     if (numArray > 0) {
185       str << "  int sizes[" << numArray << "];\n";
186       for (i = 0, count = 0, ml = mvlist; i < num; i++, ml = ml->next) {
187         mv = ml->msg_var;
188         if (mv->isArray()) {
189           str << "  sizes[" << count << "] = sz" << count << ";\n";
190           count++;
191           arrayVars.push_back(mv);
192         }
193       }
194     }
195     str << "  return " << mtype << "::alloc(__idx, s, " << (numArray > 0 ? "sizes" : "0")
196         << ", p, GroupDepNum{});\n";
197     str << "}\n";
198     // new (size_t, int, int, ..., int, priobits, groupDepNum)
199     // degenerates to  new(size_t, priobits, groupDepNum)  if no varsize
200     arrayVars.clear();
201     str << tspec << "void *"<< ptype << "::operator new(size_t s, ";
202     for(i=0;i<numArray;i++)
203       str << "int sz" << i << ", ";
204     str << "const int p, const GroupDepNum groupDepNum) {\n";
205     if (numArray>0) {
206       str << "  int sizes[" << numArray << "];\n";
207       for(i=0, count=0, ml=mvlist ;i<num; i++, ml=ml->next) {
208         mv = ml->msg_var;
209         if (mv->isArray()) {
210           str << "  sizes[" << count << "] = sz" << count << ";\n";
211           count ++;
212           arrayVars.push_back(mv);
213         }
214       }
215     }
216     str << "  return " << mtype << "::alloc(__idx, s, " << (numArray>0?"sizes":"0") << ", p, groupDepNum);\n";
217     str << "}\n";
219     // alloc(int, size_t, int*, priobits, groupDepNum)
220     str << tspec << "void* " << ptype;
221     str << "::alloc(int msgnum, size_t sz, int *sizes, int pb, GroupDepNum groupDepNum) {\n";
222     str << "  CkpvAccess(_offsets)[0] = ALIGN_DEFAULT(sz);\n";
223     for (count = 0; count < numArray; count++) {
224       mv = arrayVars[count];
225       str << "  if(sizes==0)\n";
226       str << "    CkpvAccess(_offsets)[" << count + 1 << "] = CkpvAccess(_offsets)[0];\n";
227       str << "  else\n";
228       str << "    CkpvAccess(_offsets)[" << count + 1 << "] = CkpvAccess(_offsets)["
229           << count << "] + ";
230       str << "ALIGN_DEFAULT(sizeof(" << mv->type << ")*sizes[" << count << "]);\n";
231     }
232     str << "  return CkAllocMsg(msgnum, CkpvAccess(_offsets)[" << numArray << "], pb, groupDepNum);\n";
233     str << "}\n";
235     str << tspec << ptype << "::" << proxyPrefix() << type << "() {\n";
236     str << mtype << " *newmsg = (" << mtype << " *)this;\n";
237     for (i = 0, count = 0, ml = mvlist; i < num; i++, ml = ml->next) {
238       mv = ml->msg_var;
239       if (mv->isArray()) {
240         str << "  newmsg->" << mv->name << " = (" << mv->type << " *) ";
241         str << "((char *)newmsg + CkpvAccess(_offsets)[" << count << "]);\n";
242         count++;
243       }
244     }
245     str << "}\n";
247     int numCond = numConditional();
248     str << tspec << "void " << ptype << "::dealloc(void *p) {\n";
249     if (numCond > 0) {
250       str << "  " << mtype << " *msg = (" << mtype << "*) p;\n";
251       for (i = 0, count = 0, ml = mvlist; i < num; i++, ml = ml->next) {
252         mv = ml->msg_var;
253         if (mv->isConditional()) {
254           if (mv->type->isPointer())
255             XLAT_ERROR_NOCOL("conditional variable cannot be a pointer", line);
256           str << "  CkConditional *cond_" << mv->name
257               << " = static_cast<CkConditional*>(msg->" << mv->name << ");\n";
258           str << "  if (cond_" << mv->name << "!=NULL) cond_" << mv->name
259               << "->deallocate();\n";
260         }
261       }
262     }
263     str << "  CkFreeMsg(p);\n";
264     str << "}\n";
265     // pack
266     str << tspec << "void* " << ptype << "::pack(" << mtype << " *msg) {\n";
267     for (i = 0, ml = mvlist; i < num; i++, ml = ml->next) {
268       mv = ml->msg_var;
269       if (mv->isArray()) {
270         str << "  msg->" << mv->name << " = (" << mv->type << " *) ";
271         str << "((char *)msg->" << mv->name << " - (char *)msg);\n";
272       }
273     }
274     if (numCond > 0) {
275       str << "  int impl_off[" << numCond + 1 << "];\n";
276       str << "  impl_off[0] = UsrToEnv(msg)->getUsersize();\n";
277       for (i = 0, count = 0, ml = mvlist; i < num; i++, ml = ml->next) {
278         mv = ml->msg_var;
279         if (mv->isConditional()) {
280           str << "  if (msg->" << mv->name << "!=NULL) { /* conditional packing of ";
281           mv->type->print(str);
282           str << " " << mv->name << " */\n";
283           str << "    PUP::sizer implP;\n";
284           str << "    implP|*msg->" << mv->name << ";\n";
285           str << "    impl_off[" << count + 1 << "] = impl_off[" << count
286               << "] + implP.size();\n";
287           str << "  } else {\n";
288           str << "    impl_off[" << count + 1 << "] = impl_off[" << count << "];\n";
289           str << "  }\n";
290           count++;
291         }
292       }
293       str << "  " << mtype << " *newmsg = (" << mtype << "*) CkAllocMsg(__idx, impl_off["
294           << numCond << "], UsrToEnv(msg)->getPriobits());\n";
295       str << "  envelope *newenv = UsrToEnv(newmsg);\n";
296       str << "  UInt newSize = newenv->getTotalsize();\n";
297       str << "  CmiMemcpy(newenv, UsrToEnv(msg), impl_off[0]+sizeof(envelope));\n";
298       str << "  newenv->setTotalsize(newSize);\n";
299       str << "  if (UsrToEnv(msg)->getPriobits() > 0) CmiMemcpy(newenv->getPrioPtr(), "
300              "UsrToEnv(msg)->getPrioPtr(), newenv->getPrioBytes());\n";
301       for (i = 0, count = 0, ml = mvlist; i < num; i++, ml = ml->next) {
302         mv = ml->msg_var;
303         if (mv->isConditional()) {
304           str << "  if (msg->" << mv->name << "!=NULL) { /* conditional packing of ";
305           mv->type->print(str);
306           str << " " << mv->name << " */\n";
307           str << "    newmsg->" << mv->name << " = (";
308           mv->type->print(str);
309           str << "*)(((char*)newmsg)+impl_off[" << count << "]);\n";
310           str << "    PUP::toMem implP((void *)newmsg->" << mv->name << ");\n";
311           str << "    implP|*msg->" << mv->name << ";\n";
312           str << "    newmsg->" << mv->name << " = (" << mv->type
313               << "*) ((char *)newmsg->" << mv->name << " - (char *)newmsg);\n";
314           str << "  }\n";
315           count++;
316         }
317       }
318       str << "  CkFreeMsg(msg);\n";
319       str << "  msg = newmsg;\n";
320     }
321     str << "  return (void *) msg;\n}\n";
322     // unpack
323     str << tspec << mtype << "* " << ptype << "::unpack(void* buf) {\n";
324     str << "  " << mtype << " *msg = (" << mtype << " *) buf;\n";
325     for (i = 0, ml = mvlist; i < num; i++, ml = ml->next) {
326       mv = ml->msg_var;
327       if (mv->isArray()) {
328         str << "  msg->" << mv->name << " = (" << mv->type << " *) ";
329         str << "((size_t)msg->" << mv->name << " + (char *)msg);\n";
330       }
331     }
332     if (numCond > 0) {
333       for (i = 0, count = 0, ml = mvlist; i < num; i++, ml = ml->next) {
334         mv = ml->msg_var;
335         if (mv->isConditional()) {
336           str << "  if (msg->" << mv->name << "!=NULL) { /* conditional packing of ";
337           mv->type->print(str);
338           str << " " << mv->name << " */\n";
339           str << "    PUP::fromMem implP((char*)msg + (size_t)msg->" << mv->name
340               << ");\n";
341           str << "    msg->" << mv->name << " = new " << mv->type << ";\n";
342           str << "    implP|*msg->" << mv->name << ";\n";
343           str << "  }\n";
344           count++;
345         }
346       }
347     }
348     str << "  return msg;\n}\n";
349   }
350   if (!templat) {
351     if (!external && !type->isTemplated()) {
352       str << "int " << ptype << "::__idx=0;\n";
353     }
354   } else {
355     str << tspec << "int " << ptype << "::__idx=0;\n";
356   }
357   templateGuardEnd(str);
360 void Message::genReg(XStr& str) {
361   str << "/* REG: ";
362   print(str);
363   str << "*/\n";
364   if (!templat && !external) {
365     XStr ptype, mtype, tspec;
366     ptype << proxyPrefix() << type;
367     str << ptype << "::__register(\"" << type << "\", sizeof(" << type << "),";
368     str << "(CkPackFnPtr) " << type << "::pack,";
369     str << "(CkUnpackFnPtr) " << type << "::unpack);\n";
370   }
373 void Message::print(XStr& str) {
374   if (external) str << "extern ";
375   if (templat) templat->genSpec(str);
376   str << "message ";
377   type->print(str);
378   printVars(str);
379   str << ";\n";
382 void Message::printVars(XStr& str) {
383   if (mvlist != 0) {
384     str << "{\n";
385     mvlist->print(str);
386     str << "}\n";
387   }
390 int Message::numArrays(void) {
391   if (mvlist == 0) return 0;
392   int count = 0;
393   MsgVarList* mv = mvlist;
394   for (int i = 0; i < mvlist->len(); ++i, mv = mv->next)
395     if (mv->msg_var->isArray()) count++;
396   return count;
399 int Message::numConditional(void) {
400   if (mvlist == 0) return 0;
401   int count = 0;
402   MsgVarList* mv = mvlist;
403   for (int i = 0; i < mvlist->len(); ++i, mv = mv->next)
404     if (mv->msg_var->isConditional()) count++;
405   return count;
408 int Message::numVars(void) { return ((mvlist == 0) ? 0 : mvlist->len()); }
410 MsgVar::MsgVar(Type* t, const char* n, int c, int a)
411     : type(t), name(n), cond(c), array(a) {}
413 Type* MsgVar::getType() { return type; }
415 const char* MsgVar::getName() { return name; }
417 int MsgVar::isConditional() { return cond; }
419 int MsgVar::isArray() { return array; }
421 void MsgVar::print(XStr& str) {
422   str << (isConditional() ? "conditional " : "");
423   type->print(str);
424   str << " " << name << (isArray() ? "[]" : "") << ";";
427 MsgVarList::MsgVarList(MsgVar* mv, MsgVarList* n) : msg_var(mv), next(n) {}
429 void MsgVarList::print(XStr& str) {
430   msg_var->print(str);
431   str << "\n";
432   if (next) next->print(str);
435 int MsgVarList::len(void) { return (next == 0) ? 1 : (next->len() + 1); }
437 }  // namespace xi