]> AND Private Git Repository - blast.git/blob - Parameters.cpp
Logo AND Algorithmique Numérique Distribuée

Private GIT Repository
started to code clkconvert output gen
[blast.git] / Parameters.cpp
1 #include "Parameters.h"\r
2 \r
3 #include "Dispatcher.h"\r
4 #include "BlockLibraryTree.h"\r
5 \r
6 #include "BlockCategory.h"\r
7 \r
8 #include "GroupWidget.h"\r
9 #include "GroupScene.h"\r
10 #include "GroupItem.h"\r
11 #include "BoxItem.h"\r
12 #include "StimuliItem.h"\r
13 #include "InterfaceItem.h"\r
14 #include "ConnectionItem.h"\r
15 \r
16 #include "Graph.h"\r
17 #include "ReferenceBlock.h"\r
18 #include "GroupBlock.h"\r
19 #include "FunctionalBlock.h"\r
20 #include "ReferenceInterface.h"\r
21 #include "GroupInterface.h"\r
22 #include "FunctionalInterface.h"\r
23 \r
24 #include "Exception.h"\r
25 #include "BlocksToConfigureWidget.h"\r
26 \r
27 #include "BlockParameterGeneric.h"\r
28 \r
29 #include "DelayInputModifier.h"\r
30 \r
31 Parameters::Parameters() {\r
32   categoryTree = NULL;\r
33   arrowWidth = 5;\r
34   arrowHeight = 10;\r
35   arrowLineLength = 10;\r
36 \r
37   defaultBlockWidth = 100;\r
38   defaultBlockHeight = 100;\r
39   defaultBlockFont = QFont("Arial");\r
40   defaultBlockFontSize = 12;\r
41 \r
42   setArrowPathes();\r
43 \r
44   sceneMode = MODE_EDITION; // default mode\r
45   editState = Parameters::EditNoOperation;\r
46 \r
47   unsaveModif = false;\r
48   isRstClkShown = false;\r
49   \r
50   validityExtension = "_enb";\r
51 \r
52   projectPath = "";\r
53   projectName = "";\r
54   projectFile = "";\r
55 }\r
56 \r
57 Parameters::~Parameters() {\r
58   clear();\r
59 }\r
60 \r
61 void Parameters::clear() {\r
62   delete categoryTree;\r
63   QListIterator<ReferenceBlock *> iter(availableBlocks);\r
64   while(iter.hasNext()) {\r
65     ReferenceBlock* item = iter.next();\r
66     delete item;\r
67   }\r
68   availableBlocks.clear();\r
69   refPathes.clear();\r
70 }\r
71 \r
72 Graph* Parameters::createGraph(bool createTopGroupIfaces) {\r
73   graph = new Graph(createTopGroupIfaces);\r
74   return graph;\r
75 }\r
76 \r
77 void Parameters::destroyGraph() {\r
78   delete graph;\r
79 }\r
80 \r
81 ReferenceBlock* Parameters::getReferenceBlock(int idCategory, int idBlock) {\r
82 \r
83   BlockCategory* blockCat = categoryTree->searchCategory(idCategory);\r
84 \r
85   if (blockCat == NULL) return NULL;\r
86   ReferenceBlock* ref = blockCat->getBlockById(idBlock);\r
87   return ref;\r
88 }\r
89 \r
90 ReferenceBlock* Parameters::getHiddenReferenceBlock(QString blockName) {\r
91 \r
92   BlockCategory* blockCat = categoryTree->searchCategory(100);\r
93   if (blockCat == NULL) return NULL;\r
94   ReferenceBlock* ref = blockCat->getBlockByName(blockName);\r
95   return ref;\r
96 }\r
97 \r
98 double Parameters::getFeedingClockFrequency(AbstractInterface *iface) {\r
99 \r
100   int idClock = 0;\r
101 \r
102   if (iface->isReferenceInterface()) return 0.0;\r
103 \r
104   if (iface->getClockIfaceType() == AbstractInterface::ParameterName) {\r
105     BlockParameter* param = iface->getOwner()->getParameterFromName(iface->getClockIfaceString());\r
106     if (!param->isUserParameter()) return 0.0;\r
107     bool ok;\r
108     double freq = param->getDoubleValue(&ok);\r
109     if (!ok) {\r
110       cerr << "Abnormal case: cannot retrieve clock id from parameter  " << qPrintable(param->getName()) << endl;\r
111     }\r
112     return freq;\r
113   }\r
114   else if ( (iface->getClockIfaceType() == AbstractInterface::ClockName) || ((iface->getDirection() == AbstractInterface::Input) && (iface->getPurpose() == AbstractInterface::Clock))) {\r
115 \r
116     // if iface is not clock, retrieve the clock related to it\r
117     if (iface->getClockIfaceType() == AbstractInterface::ClockName) {\r
118       iface = iface->getClockIface();\r
119     }\r
120     // if iface is a group interface, then iface name is ext_clk_X, thus extract the X\r
121     if (iface->isGroupInterface()) {\r
122       QString name = iface->getName();\r
123       name.remove(0,8);\r
124       bool ok;\r
125       idClock = name.toInt(&ok);\r
126       if (!ok) {\r
127         cerr << "Abnormal case: cannot retrieve clock id from iface name " << qPrintable(iface->getName()) << endl;\r
128         return 0.0;\r
129       }\r
130     }\r
131     // if iface is a functional interface, it is connected to clkrstgen_X (in top group) or to ext_clk_X (in subgroup)\r
132     else if (iface->isFunctionalInterface()) {\r
133       FunctionalInterface* funIface = AI_TO_FUN(iface);\r
134       ConnectedInterface* connFrom = funIface->getConnectedFrom();\r
135       if (connFrom == NULL) {\r
136         cerr << "Abnormal case: input clock " << qPrintable(iface->getName()) << " is not connected" << endl;\r
137         return 0.0;\r
138       }\r
139       if (iface->getOwner()->isTopGroupBlock()) {\r
140         QString name = connFrom->getOwner()->getName();\r
141         name.remove(0,10);\r
142         bool ok;\r
143         idClock = name.toInt(&ok);\r
144         if (!ok) {\r
145           cerr << "Abnormal case: cannot retrieve clock id for " << qPrintable(iface->getName()) << endl;\r
146           return 0.0;\r
147         }\r
148       }\r
149       else {\r
150         QString name = connFrom->getName();\r
151         name.remove(0,8);\r
152         bool ok;\r
153         idClock = name.toInt(&ok);\r
154         if (!ok) {\r
155           cerr << "Abnormal case: cannot retrieve clock id for " << qPrintable(iface->getName()) << endl;\r
156           return 0.0;\r
157         }\r
158       }\r
159     }\r
160   }\r
161   return clocks.at(idClock);\r
162 }\r
163 \r
164 void Parameters::createDelayBlock() {\r
165   delayRef = new ReferenceBlock("no.xml");\r
166   delayRef->addCategory(100);\r
167   delayRef->setName("delay");\r
168 \r
169   BlockCategory* cat = categoryTree->searchCategory(100);\r
170   cat->blocks.append(delayRef);\r
171 \r
172   AbstractInterface* interIn = new ReferenceInterface(delayRef,"data_in",AbstractInterface::Input, AbstractInterface::Data, "expression","$in_width");\r
173   delayRef->addInterface(interIn);\r
174   AbstractInterface* interInCtl = new ReferenceInterface(delayRef,"data_in_enb",AbstractInterface::Input, AbstractInterface::Control, "boolean","1");\r
175   delayRef->addInterface(interInCtl);\r
176   interInCtl->setAssociatedIface(interIn);\r
177   AbstractInterface* interOut = new ReferenceInterface(delayRef,"data_out",AbstractInterface::Output, AbstractInterface::Data, "expression","$in_width");\r
178   delayRef->addInterface(interOut);\r
179   AbstractInterface* interOutCtl = new ReferenceInterface(delayRef,"data_out_enb",AbstractInterface::Output, AbstractInterface::Control, "boolean","1");\r
180   delayRef->addInterface(interOutCtl);\r
181   interOutCtl->setAssociatedIface(interOut);\r
182   BlockParameter* param1 = new BlockParameterGeneric(delayRef,"in_width","natural","8");\r
183   BlockParameter* param2 = new BlockParameterGeneric(delayRef,"dly_length","natural","1");\r
184   delayRef->addParameter(param1);\r
185   delayRef->addParameter(param2);\r
186   delayImpl = new BlockImplementation("no.xml");\r
187   delayImpl->setDelta("1");\r
188   QHash<QString,QString> consPattern;\r
189   consPattern.insert("data_in_enb","1");\r
190   delayImpl->setConsumptionPattern(consPattern);\r
191   QHash<QString,QString> prodPattern;\r
192   prodPattern.insert("data_out_enb","O{$dly_length}1");\r
193   delayImpl->setProductionPattern(prodPattern);\r
194   delayImpl->setProductionCounter("1");\r
195   delayRef->addImplementation(delayImpl);\r
196   delayImpl->setReference(delayRef);\r
197   if (! delayImpl->checkPatterns()) {\r
198     cout << "Delay block creation: failure" << endl;\r
199   }\r
200   else {\r
201     cout << "Delay block creation: success" << endl;\r
202   }\r
203 \r
204 }\r
205 \r
206 \r
207 \r
208 void Parameters::validateXmlFile(const QString& xmlFileName, const QString& xsdFileName, XmlFileType fileType) throw(Exception) {\r
209   // opening configFile\r
210   QFile xmlFile(xmlFileName);\r
211   if (!xmlFile.open(QIODevice::ReadOnly)) {\r
212     if (fileType == Configuration) {\r
213       throw(Exception(CONFIGFILE_NOACCESS));\r
214     }\r
215     else if (fileType == Reference) {\r
216       throw(Exception(BLOCKFILE_NOACCESS));\r
217     }\r
218     else if (fileType == Implementation) {\r
219       throw(Exception(IMPLFILE_NOACCESS));\r
220     }\r
221     else if (fileType == Project) {\r
222       throw(Exception(PROJECTFILE_NOACCESS));\r
223     }\r
224   }\r
225 \r
226   QFile xsdFile(xsdFileName);\r
227   if (!xsdFile.open(QIODevice::ReadOnly)) {\r
228     xsdFile.close();\r
229     if (fileType == Configuration) {\r
230       throw(Exception(CONFIGFILE_NOACCESS));\r
231     }\r
232     else if (fileType == Reference) {\r
233       throw(Exception(BLOCKFILE_NOACCESS));\r
234     }\r
235     else if (fileType == Implementation) {\r
236       throw(Exception(IMPLFILE_NOACCESS));\r
237     }\r
238     else if (fileType == Project) {\r
239       throw(Exception(PROJECTFILE_NOACCESS));\r
240     }\r
241   }\r
242 \r
243   if(validate(xmlFile,xsdFile) == false) {\r
244     xmlFile.close();\r
245     xsdFile.close();\r
246     if (fileType == Configuration) {\r
247       throw(Exception(CONFIGFILE_CORRUPTED));\r
248     }\r
249     else if (fileType == Reference) {\r
250       throw(Exception(BLOCKFILE_CORRUPTED));\r
251     }\r
252     else if (fileType == Implementation) {\r
253       throw(Exception(IMPLFILE_CORRUPTED));\r
254     }\r
255     else if (fileType == Project) {\r
256       throw(Exception(PROJECTFILE_CORRUPTED));\r
257     }\r
258   }\r
259   xmlFile.close();\r
260   xsdFile.close();\r
261 }\r
262 \r
263 bool Parameters::validate(QFile& fileXml, QFile& fileSchema) {\r
264 \r
265   // 2 files are supposed to be already opened\r
266   QXmlSchema schema;\r
267 \r
268   if(! schema.load(&fileSchema)){\r
269     cout << "invalid schema" << endl;\r
270     return false;\r
271   }\r
272 \r
273   QXmlSchemaValidator validator(schema);\r
274 \r
275   if(! validator.validate(&fileXml)){\r
276     cout << "invalid xml" << endl;\r
277     return false;\r
278   }\r
279   return true;\r
280 }\r
281 \r
282 QDomElement Parameters::openProjectFile(const QString& projectFileName) throw(Exception) {\r
283 \r
284   try {\r
285     validateXmlFile(projectFileName,"projectfile.xsd",Project);\r
286   }\r
287   catch(Exception err) {\r
288     throw(err);\r
289   }\r
290 \r
291   QFile projectFile(projectFileName);\r
292   QDomDocument doc("projectFile");\r
293 \r
294   if(!projectFile.open(QIODevice::ReadOnly)) {\r
295     throw(Exception(PROJECTFILE_NOACCESS));\r
296   }\r
297   if(!doc.setContent(&projectFile)) {\r
298     projectFile.close();\r
299     throw(Exception(PROJECTFILE_CORRUPTED));\r
300   }\r
301   projectFile.close();\r
302 \r
303   QDomElement root = doc.documentElement();\r
304 \r
305   return root;\r
306 }\r
307 \r
308 GroupWidget *Parameters::loadProject(QDomElement root) throw(Exception) {\r
309 \r
310   bool ok = false;\r
311   GroupWidget* groupWidget = NULL;\r
312   GroupItem *groupItem = NULL;\r
313   GroupBlock *groupBlock = NULL;\r
314 \r
315   GroupWidget* topGroup = NULL;\r
316 \r
317   QString path = root.attribute("project_path","none");\r
318   if (path != "none") {\r
319     QDir dir(path);\r
320     if (dir.exists()) {\r
321       projectPath = path;\r
322 \r
323     }\r
324     cout << "project path set to " << qPrintable(projectPath) << endl;\r
325   }\r
326   /**********************************************************\r
327    1 : getting scene and creating associated group widgets\r
328   ***********************************************************/\r
329   QDomNodeList scenesNodes = root.elementsByTagName("scene");\r
330 \r
331   int maxIdScene = -1;\r
332   for(int i=0; i<scenesNodes.length(); i++) {\r
333     QDomElement currentSceneNode = scenesNodes.at(i).toElement();\r
334     int idScene = currentSceneNode.attribute("id","none").toInt(&ok);\r
335     if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
336     if (idScene > maxIdScene) maxIdScene = idScene;\r
337     int idUpperScene = currentSceneNode.attribute("upper_scene","none").toInt(&ok);\r
338     if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
339 \r
340     if (idUpperScene == -1) {\r
341       topGroup = dispatcher->createTopScene(Dispatcher::Load);\r
342       topScene->setId(idScene);\r
343       groupItem = topScene->getGroupItem();      \r
344       cout << "top group added to scene n°" << idScene << endl;\r
345     }\r
346     else {\r
347       cout << "trying to create scene n°" << idScene << " with upper scene n°" <<idUpperScene << endl;\r
348       GroupScene* upperScene = searchSceneById(idUpperScene, topScene);\r
349       groupWidget = dispatcher->addNewEmptyGroup(Dispatcher::Load, upperScene,false);\r
350       groupWidget->getScene()->setId(idScene);\r
351       groupItem = groupWidget->getScene()->getGroupItem();      \r
352     }\r
353     groupBlock = AB_TO_GRP(groupItem->getRefBlock());\r
354     /**********************************************************\r
355      1.1 : getting the group item of each scene\r
356     ***********************************************************/\r
357     QDomElement groupItemNode = currentSceneNode.firstChildElement("group_item");\r
358     try {\r
359       groupItem->load(groupItemNode);\r
360     }\r
361     catch(Exception err) {\r
362       throw(err);\r
363     }\r
364 \r
365     if (idUpperScene != -1) {\r
366       groupWidget->setWindowTitle(groupBlock->getName());\r
367       groupWidget->show();\r
368       cout << qPrintable(groupItem->getRefBlock()->getName()) << " has upper box item in " << qPrintable(groupItem->getParentItem()->getScene()->getGroupItem()->getRefBlock()->getName()) << endl;\r
369     }    \r
370   }\r
371   dispatcher->setSceneCounter(Dispatcher::Load, maxIdScene+1);\r
372   cout << "groupItems loaded and windows created succefully!" << endl;\r
373 \r
374   /**********************************************************\r
375    2 : getting the functional blocks of each scene\r
376   ***********************************************************/\r
377 \r
378   for(int i=0; i<scenesNodes.length(); i++){\r
379     QDomElement currentSceneNode = scenesNodes.at(i).toElement();\r
380     int idScene = currentSceneNode.attribute("id","none").toInt(&ok);\r
381     if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
382     cout << "SCENE : " << idScene << endl;\r
383     GroupScene *currentScene = searchSceneById(idScene,topScene);\r
384 \r
385     if(currentScene == NULL) throw(Exception(PROJECTFILE_CORRUPTED));\r
386     /**********************************************************\r
387      2.1 : getting sources if it is top scene\r
388     ***********************************************************/\r
389     if (currentScene->isTopScene()) {\r
390       QDomNodeList sourceNodes = currentSceneNode.elementsByTagName("source_item");\r
391       cout << "top scene has " << sourceNodes.length() << " sources" << endl;\r
392       for(int j=0; j<sourceNodes.length(); j++) {\r
393         QDomElement currentSBNode = sourceNodes.at(j).toElement();      \r
394         StimuliItem* sourceItem = new StimuliItem(dispatcher,this);\r
395         try {\r
396           sourceItem->load(currentSBNode);\r
397         }\r
398         catch(Exception err) {\r
399           throw(err);\r
400         }\r
401         cout << "source item has been read, add it to the scene" << endl;\r
402         // add the block to the GroupScene\r
403         currentScene->addStimuliItem(sourceItem);\r
404       } \r
405     }\r
406     /**********************************************************\r
407      2.2 : getting functional blocks\r
408     ***********************************************************/\r
409     QDomNodeList functionalBlockNodes = currentSceneNode.elementsByTagName("bi_functional");\r
410 \r
411     for(int j=0; j<functionalBlockNodes.length(); j++) {\r
412       QDomElement currentFBNode = functionalBlockNodes.at(j).toElement();      \r
413       BoxItem* funcItem = new BoxItem(dispatcher,this, currentScene->getGroupItem());\r
414       try {\r
415         funcItem->loadFunctional(currentFBNode);\r
416       }\r
417       catch(Exception err) {\r
418         throw(err);\r
419       }\r
420       // add the block to the GroupScene\r
421       currentScene->addBoxItem(funcItem);\r
422     }\r
423   }\r
424   cout << "functional blocks loaded and created succefully!" << endl;\r
425 \r
426   /**********************************************************\r
427    3 : set the BoxItem that represents a GroupItem in a child scene\r
428   ***********************************************************/\r
429 \r
430   for(int i=0; i<scenesNodes.length(); i++){\r
431     QDomElement currentSceneNode = scenesNodes.at(i).toElement();\r
432     int idScene = currentSceneNode.attribute("id","none").toInt(&ok);\r
433     if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
434     GroupScene *currentScene = searchSceneById(idScene, topScene);\r
435     if(currentScene == NULL) throw(Exception(PROJECTFILE_CORRUPTED));\r
436 \r
437     QDomNodeList biGroupNodes = currentSceneNode.elementsByTagName("bi_group");\r
438 \r
439     for(int j=0; j<biGroupNodes.length(); j++){\r
440       QDomElement currentBiGroup = biGroupNodes.at(j).toElement();\r
441 \r
442       int id = currentBiGroup.attribute("id","none").toInt(&ok);\r
443       if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
444 \r
445       int idGroup = currentBiGroup.attribute("inside_group","none").toInt(&ok);\r
446       if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
447 \r
448       QStringList positionStr = currentBiGroup.attribute("position","none").split(",");\r
449       if(positionStr.length() != 2) throw(Exception(PROJECTFILE_CORRUPTED));\r
450       int posX = positionStr.at(0).toInt(&ok);\r
451       if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
452       int posY = positionStr.at(1).toInt(&ok);\r
453       if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
454 \r
455       QStringList dimensionStr = currentBiGroup.attribute("dimension","none").split(",");\r
456       if(dimensionStr.length() != 2) throw(Exception(PROJECTFILE_CORRUPTED));\r
457       int dimX = dimensionStr.at(0).toInt(&ok);\r
458       if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
459       int dimY = dimensionStr.at(1).toInt(&ok);\r
460       if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
461 \r
462       // get the GroupItem already created and set at phase 1\r
463       GroupItem *insideGroup = searchGroupItemById(idGroup, topScene);\r
464       BoxItem* upperItem = NULL;\r
465       if(insideGroup == NULL) cout << "group null" << endl;      \r
466       // now search within the scene which BoxItem has a childItem that is = to insideGroup\r
467       QList<BoxItem *> lst = currentScene->getBoxItems();\r
468       foreach(BoxItem* item, lst) {\r
469         if (item->getChildGroupItem() == insideGroup) {\r
470           upperItem = item;\r
471           break;\r
472         }\r
473       }\r
474       if (upperItem == NULL) {\r
475         throw(Exception(PROJECTFILE_CORRUPTED));\r
476       }\r
477 \r
478       upperItem->setId(id);\r
479       upperItem->setPos(posX,posY);\r
480       upperItem->setDimension(dimX,dimY);\r
481 \r
482       // set interfaces of this BoxItem\r
483       QDomNodeList interfaceNodes = currentBiGroup.elementsByTagName("big_iface");\r
484 \r
485       for(int k=0; k<interfaceNodes.length(); k++){\r
486         QDomElement currentInterfaceNode = interfaceNodes.at(k).toElement();\r
487 \r
488         int id = currentInterfaceNode.attribute("id","none").toInt(&ok);\r
489         if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
490 \r
491         QString refName = currentInterfaceNode.attribute("ref_name","none");\r
492         if(refName == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
493 \r
494         QString orientationStr = currentInterfaceNode.attribute("orientation","none");\r
495         int orientation = InterfaceItem::getIntOrientation(orientationStr);\r
496         if(orientation == -1) throw(Exception(PROJECTFILE_CORRUPTED));\r
497 \r
498         double position = currentInterfaceNode.attribute("position","none").toDouble(&ok);\r
499         if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
500 \r
501         ConnectedInterface *refInter = insideGroup->searchInterfaceItemByName(refName)->refInter;\r
502         InterfaceItem *ifaceItem = new InterfaceItem(position, orientation, refInter, upperItem, this);\r
503         ifaceItem->setId(id);\r
504         upperItem->addInterfaceItem(ifaceItem);\r
505       }\r
506     }\r
507   }\r
508   cout << "blockItems \"group\" loaded and created succefully!" << endl;\r
509 \r
510   QDomNodeList connectionNodes = root.elementsByTagName("connection");\r
511 \r
512   for(int i=0; i<connectionNodes.length(); i++){\r
513     QDomElement currentConnectionNode = connectionNodes.at(i).toElement();\r
514 \r
515     int from = currentConnectionNode.attribute("from","none").toInt(&ok);\r
516     if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
517 \r
518     int to = currentConnectionNode.attribute("to","none").toInt(&ok);\r
519     if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
520 \r
521 \r
522     InterfaceItem *iface1 = searchInterfaceItemById(from,topScene);\r
523     InterfaceItem *iface2 = searchInterfaceItemById(to,topScene);\r
524 \r
525     if(iface1 != NULL && iface2 != NULL){\r
526       dispatcher->createConnection(Dispatcher::Load, iface1,iface2);\r
527     } else {\r
528       cout << "interfaces not found, connect canceled!" << endl;\r
529     }\r
530   }\r
531   cout << "connections loaded and created succefully!" << endl;\r
532 \r
533   QDomNodeList modifierNodes = root.elementsByTagName("modifier");\r
534 \r
535   for(int i=0; i<modifierNodes.length(); i++){\r
536     QDomElement currentModifierNode = modifierNodes.at(i).toElement();\r
537 \r
538     int id = currentModifierNode.attribute("id","none").toInt(&ok);\r
539     if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
540 \r
541     QString typeStr = currentModifierNode.attribute("type","none");\r
542     if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
543     QString paramsStr = currentModifierNode.attribute("params","none");\r
544     if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
545 \r
546     /* NB: just adding delays for now. To be cont'd */\r
547     InterfaceItem *iface = searchInterfaceItemById(id,topScene);\r
548 \r
549     if ((iface == NULL ) || (iface->refInter == NULL) || (iface->refInter->getAssociatedIface() == NULL)) {\r
550       cout << "modified interface not found, modifiers setup canceled!" << endl;\r
551     }\r
552     else {\r
553       ConnectedInterface* connIface = AI_TO_CON(iface->refInter->getAssociatedIface());\r
554 \r
555       AbstractInputModifier* mod = NULL;\r
556       if (typeStr == "delay") {\r
557         int delay = paramsStr.toInt(&ok);\r
558         if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
559         mod = new DelayInputModifier(connIface, delay);\r
560         connIface->setInputModifier(mod);\r
561       }\r
562     }\r
563   }\r
564 \r
565   cout << "modifiers loaded and created succefully!" << endl;\r
566 \r
567   return topGroup;\r
568 }\r
569 \r
570 void Parameters::loadBlastConfiguration(QString confFile) throw(Exception) {\r
571 \r
572   try {\r
573     validateXmlFile("blastconfig.xml", "blastconfig.xsd",Configuration);\r
574   }\r
575   catch(Exception err) {\r
576     throw(err);\r
577   }\r
578 \r
579   bool ok;\r
580   // opening configFile\r
581   QFile configFile(confFile);\r
582   // reading in into QDomDocument\r
583   QDomDocument document("configFile");\r
584 \r
585   if (!configFile.open(QIODevice::ReadOnly)) {\r
586     throw(Exception(CONFIGFILE_NOACCESS));\r
587   }\r
588   if (!document.setContent(&configFile)) {\r
589     configFile.close();\r
590     throw(Exception(CONFIGFILE_NOACCESS));\r
591   }\r
592   configFile.close();\r
593 \r
594   //Get the root element\r
595   QDomElement config = document.documentElement();\r
596 \r
597   QDomElement eltCat = config.firstChildElement("categories");\r
598   try {\r
599     categoryTree = new BlockLibraryTree();\r
600     categoryTree->load(eltCat);\r
601   }\r
602   catch(Exception err) {\r
603     throw(err);\r
604   }\r
605 \r
606   QDomElement eltReferences = eltCat.nextSiblingElement("references");\r
607   refLib = eltReferences.attribute("lib_file","none");\r
608   cout << "references lib : " << qPrintable(refLib)  << endl;\r
609   int nbPathes;\r
610   QString nbPathesStr;\r
611   nbPathesStr = eltReferences.attribute("nb","none");\r
612   nbPathes = nbPathesStr.toInt(&ok);\r
613   QDomNodeList listBlockDir = eltReferences.elementsByTagName("reference_lib");\r
614   if ((!ok) || (nbPathes != listBlockDir.size())) throw(Exception(CONFIGFILE_CORRUPTED));\r
615 \r
616   for(int i=0;i<listBlockDir.size();i++) {\r
617     QDomNode nodeBlockDir = listBlockDir.at(i);\r
618     QDomElement eltBlockDir = nodeBlockDir.toElement();\r
619     if (eltBlockDir.isNull()) throw(Exception(CONFIGFILE_CORRUPTED));\r
620     QString path = eltBlockDir.attribute("path","none");\r
621     if (path == "none") throw(Exception(CONFIGFILE_CORRUPTED));\r
622     refPathes.append(path);\r
623     cout << "references path : " << qPrintable(path) << endl;\r
624   }\r
625 \r
626   QDomElement eltImpl = eltReferences.nextSiblingElement("implementations");\r
627   implLib = eltImpl.attribute("lib_file","none");\r
628   cout << "implementation lib : " << qPrintable(implLib)  << endl;\r
629   nbPathesStr = eltImpl.attribute("nb","none");\r
630   nbPathes = nbPathesStr.toInt(&ok);\r
631   QDomNodeList listImplDir = eltImpl.elementsByTagName("impl_lib");\r
632   if ((!ok) || (nbPathes != listImplDir.size())) throw(Exception(CONFIGFILE_CORRUPTED));\r
633 \r
634   for(int i=0;i<listImplDir.size();i++) {\r
635     QDomNode nodeImplDir = listImplDir.at(i);\r
636     QDomElement eltImplDir = nodeImplDir.toElement();\r
637     if (eltImplDir.isNull()) throw(Exception(CONFIGFILE_CORRUPTED));\r
638     QString path = eltImplDir.attribute("path","none");\r
639     if (path == "none") throw(Exception(CONFIGFILE_CORRUPTED));\r
640     implPathes.append(path);\r
641     cout << "impl path : " << qPrintable(path) << endl << endl;\r
642   }\r
643 \r
644   QDomElement eltSource = eltImpl.nextSiblingElement("sources");\r
645   nbPathesStr = eltSource.attribute("nb","none");\r
646   nbPathes = nbPathesStr.toInt(&ok);\r
647   QDomNodeList listSourceDir = eltSource.elementsByTagName("source_lib");\r
648   if ((!ok) || (nbPathes != listSourceDir.size())) throw(Exception(CONFIGFILE_CORRUPTED));\r
649 \r
650   for(int i=0;i<listSourceDir.size();i++) {\r
651     QDomNode nodeSourceDir = listSourceDir.at(i);\r
652     QDomElement eltSourceDir = nodeSourceDir.toElement();\r
653     if (eltSourceDir.isNull()) throw(Exception(CONFIGFILE_CORRUPTED));\r
654     QString path = eltSourceDir.attribute("path","none");\r
655     if (path == "none") throw(Exception(CONFIGFILE_CORRUPTED));\r
656     sourcePathes.append(path);\r
657     cout << "core path : " << qPrintable(path) << endl << endl;\r
658   }\r
659 \r
660   // getting elt = the element <defaults>\r
661   // for each child element, initialize the associated attributes of Parameters\r
662 \r
663   QDomElement eltDefaults = eltSource.nextSiblingElement("defaults");\r
664 \r
665   QDomElement eltBlocks = eltDefaults.firstChildElement("blocks");\r
666   QString attributeStr = eltBlocks.attribute("width", "none");\r
667   defaultBlockWidth = attributeStr.toInt(&ok);\r
668   if (!ok || defaultBlockWidth < 1) throw(Exception(CONFIGFILE_CORRUPTED));\r
669   attributeStr = eltBlocks.attribute("height", "none");\r
670   defaultBlockHeight = attributeStr.toInt(&ok);\r
671   if (!ok || defaultBlockHeight < 1) throw(Exception(CONFIGFILE_CORRUPTED));\r
672   attributeStr = eltBlocks.attribute("font_size", "none");\r
673   defaultBlockFontSize = attributeStr.toFloat(&ok);\r
674   if (!ok || defaultBlockFontSize < 1) throw(Exception(CONFIGFILE_CORRUPTED));\r
675   attributeStr = eltBlocks.attribute("font", "none");\r
676   if (attributeStr == "none") throw(Exception(CONFIGFILE_CORRUPTED));\r
677   defaultBlockFontName = attributeStr;\r
678   defaultBlockFont = QFont(defaultBlockFontName, defaultBlockFontSize);\r
679 \r
680   QDomElement eltInterfaces = eltBlocks.nextSiblingElement("interfaces");\r
681   attributeStr = eltInterfaces.attribute("width", "none");\r
682   arrowWidth = attributeStr.toInt(&ok);\r
683   if (!ok || arrowWidth < 1) throw(Exception(CONFIGFILE_CORRUPTED));\r
684   attributeStr = eltInterfaces.attribute("height", "none");\r
685   arrowHeight = attributeStr.toInt(&ok);\r
686   if (!ok || arrowHeight < 1) throw(Exception(CONFIGFILE_CORRUPTED));\r
687   attributeStr = eltInterfaces.attribute("linelength", "none");\r
688   arrowLineLength = attributeStr.toInt(&ok);\r
689   if (!ok || arrowLineLength < 1) throw(Exception(CONFIGFILE_CORRUPTED));\r
690   attributeStr = eltInterfaces.attribute("font_size", "none");\r
691   defaultIfaceFontSize = attributeStr.toFloat(&ok);\r
692   if (!ok || defaultIfaceFontSize < 1) throw(Exception(CONFIGFILE_CORRUPTED));\r
693   attributeStr = eltInterfaces.attribute("font", "none");\r
694   if (attributeStr == "none") throw(Exception(CONFIGFILE_CORRUPTED));\r
695   defaultIfaceFontName = attributeStr;\r
696   defaultIfaceFont = QFont(defaultIfaceFontName, defaultIfaceFontSize);\r
697 \r
698   QDomElement eltConnections = eltInterfaces.nextSiblingElement("connections");\r
699   attributeStr = eltConnections.attribute("gaplength", "none");\r
700   connGapLength = attributeStr.toInt(&ok);\r
701   if (!ok || connGapLength < 1) throw(Exception(CONFIGFILE_CORRUPTED));\r
702 }\r
703 \r
704 void Parameters::loadReferencesFromXml() throw(Exception) {\r
705   cout << "load references from xml" << endl;\r
706   for(int i=0;i<refPathes.size();i++) {\r
707     cout << "analyzing " << qPrintable(refPathes.at(i)) << endl;\r
708     QDir dir(refPathes.at(i));\r
709     QStringList filter;\r
710     filter << "*.xml";\r
711     dir.setNameFilters(filter);\r
712     QStringList list = dir.entryList();\r
713     for(int j=0;j<list.size();j++) {\r
714       QString fileName = dir.absolutePath();\r
715       fileName.append("/"+list.at(j));\r
716 \r
717       QFile blockXML(fileName);\r
718       if (!blockXML.open(QIODevice::ReadOnly)) {\r
719         throw(Exception(BLOCKFILE_NOACCESS));\r
720       }\r
721       QTextStream in(&blockXML);\r
722       QString line = in.readLine();\r
723       line = in.readLine();\r
724 \r
725       if (!line.contains("<block")) {\r
726         blockXML.close();\r
727         continue;\r
728       }\r
729 \r
730       blockXML.close();\r
731       try {\r
732         validateXmlFile(fileName,"reference.xsd",Reference);\r
733       }\r
734       catch(Exception err) {\r
735         throw(err);\r
736       }\r
737 \r
738       // reading in into QDomDocument\r
739       QDomDocument document ("FileXML");\r
740       if (!blockXML.open(QIODevice::ReadOnly)) {\r
741         throw(Exception(BLOCKFILE_NOACCESS));\r
742       }\r
743       if (!document.setContent(&blockXML)) {\r
744         blockXML.close();\r
745         throw(Exception(BLOCKFILE_NOACCESS));\r
746       }\r
747       blockXML.close();\r
748 \r
749       QDomElement blockRoot = document.documentElement();\r
750       QString name = blockRoot.tagName();\r
751       if (name == "block") {\r
752 \r
753         cout << "xml:" << fileName.toStdString() << endl;\r
754         ReferenceBlock* b = new ReferenceBlock(fileName);\r
755         try {\r
756           b->load(blockRoot);\r
757           b->setHashMd5();\r
758         }\r
759         catch(int err) {\r
760           throw(err);\r
761         }\r
762         cout << "xml:" << b->getXmlFile().toStdString() << endl;\r
763 \r
764         availableBlocks.append(b);\r
765         foreach (int id,b->getCategories()) {\r
766           cout << "ajout du bloc dans cat n° : " << id << endl;\r
767           BlockCategory* cat = categoryTree->searchCategory(id);\r
768           cat->blocks.append(b);\r
769         }\r
770       }\r
771     }\r
772   }\r
773 }\r
774 \r
775 void Parameters::loadReferencesFromLib() throw(Exception) {\r
776 \r
777   cout << "loading references from lib" << endl;\r
778 \r
779   // removing blocks from category tree if they exist\r
780   categoryTree->clearBlocks();\r
781   // deleting existings blocks\r
782   ReferenceBlock* b = NULL;\r
783   for(int i=0;i<availableBlocks.size();i++) {\r
784     b = availableBlocks.at(i);\r
785     delete b;\r
786   }\r
787   availableBlocks.clear();\r
788 \r
789   QFile libFile(refLib);\r
790   if (!libFile.open(QIODevice::ReadOnly)) {\r
791     throw(Exception(BLOCKFILE_NOACCESS));\r
792   }\r
793   QDataStream in(&libFile);\r
794   quint32 size;\r
795 \r
796   in >> size;\r
797 \r
798   int nbBlocks;\r
799   in >> nbBlocks;\r
800   for(int i=0;i<nbBlocks;i++) {\r
801     b = new ReferenceBlock("");\r
802     in >> *b;\r
803     availableBlocks.append(b);\r
804     foreach (int id,b->getCategories()) {\r
805       BlockCategory* cat = categoryTree->searchCategory(id);\r
806       cat->blocks.append(b);\r
807     }\r
808   }\r
809   libFile.close();\r
810 }\r
811 \r
812 void Parameters::saveReferencesToLib() throw(Exception) {\r
813 \r
814   cout << "saving blocks in " << qPrintable(refLib) << endl;\r
815   QFile libFile(refLib);\r
816   if (!libFile.open(QIODevice::WriteOnly)) {\r
817     throw(Exception(BLOCKFILE_NOACCESS));\r
818   }\r
819   QDataStream out(&libFile);\r
820 \r
821   out.setVersion(QDataStream::Qt_5_0);\r
822 \r
823   QByteArray blockData;\r
824   QDataStream toWrite(&blockData, QIODevice::WriteOnly);\r
825 \r
826   toWrite << availableBlocks.size();\r
827   for(int i=0;i<availableBlocks.size();i++) {\r
828     ReferenceBlock* b = availableBlocks.at(i);\r
829     toWrite << *b;\r
830   }\r
831 \r
832   out << blockData;\r
833 \r
834   libFile.close();\r
835 \r
836 }\r
837 \r
838 void Parameters::loadImplementationsFromXml() throw(Exception) {\r
839 \r
840   for(int i=0;i<implPathes.size();i++) {\r
841     cout << "analyzing " << qPrintable(implPathes.at(i)) << endl;\r
842     QDir dir(implPathes.at(i));\r
843     QStringList filter;\r
844     filter << "*.xml";\r
845     dir.setNameFilters(filter);\r
846     QStringList list = dir.entryList();\r
847     for(int j=0;j<list.size();j++) {\r
848       QString fileName = dir.absolutePath();\r
849       fileName.append("/"+list.at(j));\r
850 \r
851       cout << "checking " << qPrintable(fileName) << " is an implementation file ...";\r
852       QFile implXML(fileName);\r
853       if (!implXML.open(QIODevice::ReadOnly)) {\r
854         throw(Exception(IMPLFILE_NOACCESS));\r
855       }\r
856       QTextStream in(&implXML);\r
857       QString line = in.readLine();\r
858       line = in.readLine();\r
859 \r
860       if (!line.contains("<block_impl")) {\r
861         implXML.close();\r
862         continue;\r
863       }\r
864 \r
865       implXML.close();\r
866       cout << "OK" << endl;\r
867       cout << "reading " << qPrintable(fileName) << " content ...";\r
868 \r
869       try {\r
870         validateXmlFile(fileName,"implementation.xsd",Implementation);\r
871       }\r
872       catch(Exception e) {\r
873         throw(e);\r
874       }\r
875 \r
876       // reading in into QDomDocument\r
877       QDomDocument document ("FileXML");\r
878       if (!implXML.open(QIODevice::ReadOnly)) {\r
879         throw(Exception(IMPLFILE_NOACCESS));\r
880       }\r
881       cout << "OK" << endl;\r
882       cout << "convert " << qPrintable(fileName) << " content into document...";\r
883       if (!document.setContent(&implXML)) {\r
884         implXML.close();\r
885         throw(Exception(IMPLFILE_NOACCESS));\r
886       }\r
887       implXML.close();\r
888 \r
889       QDomElement implRoot = document.documentElement();\r
890       QString refXml = implRoot.attribute("ref_name","none");\r
891       QString refMd5 = implRoot.attribute("ref_md5","none");\r
892       BlockImplementation* impl = new BlockImplementation(fileName,refXml,refMd5);\r
893 \r
894       QDomNodeList archNode = implRoot.elementsByTagName("architecture");\r
895 \r
896       if (archNode.isEmpty()) {\r
897         cout << "impl has no architecture" << endl;\r
898         return;\r
899       }\r
900       QDomElement archElt = archNode.at(0).toElement();\r
901       QString compList = archElt.attribute("comp_list","none");\r
902       if (compList != "none") {\r
903         QStringList compos = compList.split(",");\r
904         foreach(QString s, compos) {\r
905           impl->addResource(s);\r
906         }\r
907       }\r
908 \r
909       try {\r
910         impl->loadPatterns(implRoot);\r
911       }\r
912       catch(int err) {\r
913         throw(err);\r
914       }\r
915       availableImplementations.append(impl);\r
916 \r
917       ReferenceBlock* ref = NULL;\r
918       if (! refMd5.isEmpty()) {\r
919         ref = searchBlockByMd5(refMd5);\r
920       }\r
921       if (ref == NULL) {\r
922         ref = searchBlockByXml(refXml);\r
923       }\r
924       if (ref == NULL) {\r
925         cout << "Cannot find a reference block for impl :" << qPrintable(fileName) << endl;\r
926       }      \r
927       else {          \r
928         ref->addImplementation(impl);\r
929         impl->setReference(ref);\r
930         if (! impl->checkPatterns()) throw(Exception(IMPLFILE_CORRUPTED));\r
931       }      \r
932       cout << "OK" << endl;\r
933     }\r
934   }\r
935 }\r
936 \r
937 void Parameters::loadImplementationsFromLib() throw(Exception) {\r
938 \r
939   cout << "loading implementations from lib" << endl;\r
940 \r
941   BlockImplementation* impl = NULL;\r
942   ReferenceBlock* ref = NULL;\r
943   for(int i=0;i<availableImplementations.size();i++) {\r
944     impl = availableImplementations.at(i);\r
945     delete impl;\r
946   }\r
947   availableImplementations.clear();\r
948 \r
949   QFile libFile(implLib);\r
950   if (!libFile.open(QIODevice::ReadOnly)) {\r
951     throw(Exception(IMPLFILE_NOACCESS));\r
952   }\r
953   QDataStream in(&libFile);\r
954   quint32 size;\r
955 \r
956   in >> size;\r
957 \r
958   int nbImpls;\r
959   in >> nbImpls;\r
960   for(int i=0;i<nbImpls;i++) {\r
961     impl = new BlockImplementation("");\r
962     in >> *impl;\r
963     availableImplementations.append(impl);\r
964     QString refMd5 = impl->getReferenceMd5();\r
965     QString refXml = impl->getReferenceXml();\r
966     ref = NULL;\r
967     if (! refMd5.isEmpty()) {\r
968       ref = searchBlockByMd5(refMd5);\r
969     }\r
970     if (ref == NULL) {\r
971       ref = searchBlockByXml(refXml);\r
972     }\r
973     if (ref == NULL) {\r
974       cout << "Cannot find a reference block for impl :" << qPrintable(impl->getXmlFile()) << endl;\r
975     }\r
976     else {          \r
977       ref->addImplementation(impl);\r
978       impl->setReference(ref);\r
979       if (! impl->checkPatterns()) throw(Exception(IMPLFILE_CORRUPTED));\r
980     }\r
981   }\r
982   libFile.close();\r
983 }\r
984 \r
985 void Parameters::saveImplementationsToLib() throw(Exception) {\r
986 \r
987   cout << "saving implementations in " << qPrintable(implLib) << endl;\r
988   QFile libFile(implLib);\r
989   if (!libFile.open(QIODevice::WriteOnly)) {\r
990     throw(Exception(IMPLFILE_NOACCESS));\r
991   }\r
992   QDataStream out(&libFile);\r
993 \r
994   out.setVersion(QDataStream::Qt_5_0);\r
995 \r
996   QByteArray blockData;\r
997   QDataStream toWrite(&blockData, QIODevice::WriteOnly);\r
998 \r
999   toWrite << availableImplementations.size();\r
1000   for(int i=0;i<availableImplementations.size();i++) {\r
1001     BlockImplementation* impl = availableImplementations.at(i);\r
1002     toWrite << *impl;\r
1003   }\r
1004 \r
1005   out << blockData;\r
1006 \r
1007   libFile.close();\r
1008 \r
1009 }\r
1010 \r
1011 \r
1012 void Parameters::loadSources() throw(Exception) {\r
1013 \r
1014   for(int i=0;i<sourcePathes.size();i++) {\r
1015     cout << "analyzing " << qPrintable(sourcePathes.at(i)) << endl;\r
1016     QDir dir(sourcePathes.at(i));\r
1017     QStringList filter;\r
1018     filter << "*.vhd" << "*.ngc";\r
1019     dir.setNameFilters(filter);\r
1020     QStringList list = dir.entryList();\r
1021     for(int j=0;j<list.size();j++) {\r
1022       QString fileName = dir.absolutePath();\r
1023       fileName.append("/"+list.at(j));\r
1024 \r
1025       if (list.at(j).endsWith(".ngc")) {\r
1026         QString netName = list.at(j);\r
1027         netName.truncate(list.at(j).size() -4);\r
1028         cout << "found netlist " << qPrintable(netName) << endl;\r
1029         availableResources.append(new ExternalResource(netName,fileName,ExternalResource::Netlist));\r
1030       }\r
1031       else {\r
1032         cout << "parsing " << qPrintable(fileName) << " ... ";\r
1033         QFile srcXML(fileName);\r
1034         if (!srcXML.open(QIODevice::ReadOnly)) {\r
1035           throw(Exception(IMPLFILE_NOACCESS));\r
1036         }\r
1037         QTextStream in(&srcXML);\r
1038 \r
1039         QString line = in.readLine();\r
1040         while (!line.isNull()) {\r
1041           if (line.contains("package", Qt::CaseInsensitive)) {\r
1042             QRegularExpression rxPack("^package (.+) is$",QRegularExpression::CaseInsensitiveOption);\r
1043             QRegularExpressionMatch matchPack = rxPack.match(line);\r
1044             if (matchPack.hasMatch()) {\r
1045               QString packName = matchPack.captured(1);\r
1046               cout << "found package " << qPrintable(packName) << endl;\r
1047               availableResources.append(new ExternalResource(packName,fileName,ExternalResource::Package));\r
1048             }\r
1049           }\r
1050           else if (line.contains("entity", Qt::CaseInsensitive)) {\r
1051             QRegularExpression rxEnt("^entity (.+) is$",QRegularExpression::CaseInsensitiveOption);\r
1052             QRegularExpressionMatch matchEnt = rxEnt.match(line);\r
1053             if (matchEnt.hasMatch()) {\r
1054               QString entityName = matchEnt.captured(1);\r
1055               cout << "found entity " << qPrintable(entityName) << endl;\r
1056               availableResources.append(new ExternalResource(entityName,fileName,ExternalResource::Code));\r
1057             }\r
1058           }\r
1059           line = in.readLine();\r
1060         }\r
1061         srcXML.close();\r
1062         cout << "OK" << endl;\r
1063       }\r
1064     }\r
1065   }\r
1066 }\r
1067 \r
1068 QList<ExternalResource *> Parameters::searchResourceByName(const QString& name) {\r
1069   QList<ExternalResource*> listRes;\r
1070   foreach(ExternalResource* s, availableResources) {\r
1071     if (s->getName() == name) {\r
1072       listRes.append(s);\r
1073     }\r
1074   }\r
1075   return listRes;\r
1076 }\r
1077 \r
1078 void Parameters::addAvailableBlock(ReferenceBlock *block) {\r
1079   availableBlocks.append(block);\r
1080   foreach (int id,block->getCategories()) {\r
1081     cout << "ajout du bloc dans cat n° : " << id << endl;\r
1082     BlockCategory* cat = categoryTree->searchCategory(id);\r
1083     cat->blocks.append(block);\r
1084   }\r
1085 }\r
1086 \r
1087 void Parameters::parametersValidation() {\r
1088   QList<AbstractBlock*> blocksToConfigure = getBlocksToConfigure();\r
1089 \r
1090   if(!blocksToConfigure.isEmpty()){\r
1091     BlocksToConfigureWidget *widget = new BlocksToConfigureWidget(blocksToConfigure, this, NULL);\r
1092     widget->show();\r
1093   }\r
1094 }\r
1095 \r
1096 void Parameters::connectionsValidation() {\r
1097 \r
1098 #ifdef DEBUG_INCLFUN\r
1099 \r
1100   QStack<AbstractInterface*> *interfaceToValidate = new QStack<AbstractInterface*>;\r
1101   QList<AbstractInterface*> *validatedInterface = new QList<AbstractInterface*>;\r
1102 \r
1103   foreach(AbstractInterface *inter, topWindow->getScene()->getGroupItem()->getRefBlock()->getInterfaces()){\r
1104     foreach(AbstractInterface *connectedInter, inter->getConnectedTo()){\r
1105 \r
1106       inter->setWidth(connectedInter->getWidth());\r
1107       interfaceToValidate->push(connectedInter);\r
1108     }\r
1109   }\r
1110 \r
1111 \r
1112   try{\r
1113     while(!interfaceToValidate->isEmpty()){\r
1114       interfaceToValidate->pop()->connectionsValidation(interfaceToValidate, validatedInterface);\r
1115     }\r
1116   }\r
1117   catch(Exception e){\r
1118     cerr << e.getMessage().toStdString() << endl;\r
1119   }\r
1120 #endif\r
1121 }\r
1122 \r
1123 QList<AbstractBlock *> Parameters::getBlocksToConfigure() {\r
1124 \r
1125 #ifdef DEBUG_INCLFUN\r
1126 \r
1127   QList<AbstractBlock*> *checkedBlocks = new QList<AbstractBlock*>;\r
1128   QList<AbstractBlock*> *blocksToConfigure = new QList<AbstractBlock*>;\r
1129 \r
1130   foreach(AbstractInterface *inter, topWindow->getScene()->getGroupItem()->getRefBlock()->getInterfaces()){\r
1131     foreach(AbstractInterface *connectedInter, inter->getConnectedTo()){\r
1132       if(!checkedBlocks->contains(connectedInter->getOwner())){\r
1133         connectedInter->getOwner()->parametersValidation(checkedBlocks, blocksToConfigure);\r
1134       }\r
1135     }\r
1136   }\r
1137   return *blocksToConfigure;\r
1138 #endif\r
1139 }\r
1140 \r
1141 \r
1142 void Parameters::updateToolbar() {\r
1143   int nb = currentScene->getBoxItems().length();\r
1144   for(int i = 0; i<nb; i++){\r
1145     if(currentScene->getBoxItems().at(i)->isSelected()){\r
1146       currentScene->getGroupWidget()->enableGroupButton(true);\r
1147       return;\r
1148     }\r
1149   }\r
1150   currentScene->getGroupWidget()->enableGroupButton(false);\r
1151 }\r
1152 \r
1153 \r
1154 void Parameters::updateIds() {\r
1155 \r
1156   /* a in-width cross of the graph must be done so that ids of GroupItem\r
1157      are in the correct ordre when saving/loading a project\r
1158    */\r
1159   int countItem = 1;\r
1160   int countIface = 1;\r
1161   QList<GroupScene *> fifo;\r
1162   fifo.append(topScene);\r
1163   while (!fifo.isEmpty()) {\r
1164     GroupScene* scene = fifo.takeFirst();\r
1165     countItem = scene->setItemsId(countItem);\r
1166     countIface = scene->setInterfacesId(countIface);\r
1167     foreach(GroupScene* s, scene->getChildrenScene()) {\r
1168       fifo.append(s);\r
1169     }\r
1170   }\r
1171 }\r
1172 \r
1173 \r
1174 ReferenceBlock *Parameters::searchBlockByXml(QString xmlName) {\r
1175   foreach(ReferenceBlock *block, availableBlocks){\r
1176     if(block->getXmlFile().contains(xmlName))\r
1177       return block;\r
1178   }\r
1179   return NULL;\r
1180 }\r
1181 \r
1182 ReferenceBlock *Parameters::searchBlockByMd5(QString sumMd5) {\r
1183   foreach(ReferenceBlock *block, availableBlocks){\r
1184     if(block->getHashMd5() == sumMd5)\r
1185       return block;\r
1186   }\r
1187   return NULL;\r
1188 }\r
1189 \r
1190 void Parameters::save(QString confFile) {\r
1191 \r
1192 //#ifdef DEBUG_INCLFUN\r
1193 \r
1194   updateIds();\r
1195   QList<ConnectionItem*> allConnections;\r
1196   QFile file(confFile);\r
1197   if(file.open(QIODevice::WriteOnly)){\r
1198 \r
1199     QXmlStreamWriter writer(&file);\r
1200 \r
1201     writer.setAutoFormatting(true);\r
1202     writer.writeStartDocument();\r
1203 \r
1204     writer.writeStartElement("blast_project");\r
1205     writer.writeStartElement("scenes");\r
1206 \r
1207     writer.writeAttribute("count",QString::number(dispatcher->getNumberOfScenes()));\r
1208 \r
1209     // cross the scene level by level using a FIFO\r
1210     QList<GroupScene*> fifoScene;\r
1211     fifoScene.append(topScene);\r
1212 \r
1213     GroupScene *scene;\r
1214     while (!fifoScene.isEmpty()) {\r
1215       scene = fifoScene.takeFirst();\r
1216       scene->save(writer);\r
1217       foreach(GroupScene* s, scene->getChildrenScene()) {\r
1218         fifoScene.append(s);\r
1219       }\r
1220 \r
1221       foreach(ConnectionItem* item, scene->getConnectionItems()) {\r
1222         allConnections.append(item);\r
1223       }\r
1224     }\r
1225     writer.writeEndElement();    //</scenes>\r
1226 \r
1227     writer.writeStartElement("connections");\r
1228     foreach(ConnectionItem* item, allConnections) {\r
1229 \r
1230       writer.writeStartElement("connection");\r
1231 \r
1232       writer.writeAttribute("from",QString::number(item->getFromInterfaceItem()->getId()));\r
1233       writer.writeAttribute("to", QString::number(item->getToInterfaceItem()->getId()));\r
1234 \r
1235       writer.writeEndElement();\r
1236     }\r
1237 \r
1238     writer.writeEndElement();    //</connections>\r
1239 \r
1240     QList<InterfaceItem *> lstIfaceItem;\r
1241     // search for modifiers\r
1242     foreach(ConnectionItem* item, allConnections) {\r
1243       InterfaceItem* fromIfaceItem = item->getFromInterfaceItem();\r
1244       AbstractInputModifier* mod = fromIfaceItem->refInter->getInputModifier();\r
1245       if (mod != NULL) {\r
1246         if (!lstIfaceItem.contains(fromIfaceItem)) lstIfaceItem.append(fromIfaceItem);\r
1247       }\r
1248       InterfaceItem* toIfaceItem = item->getToInterfaceItem();\r
1249       mod = toIfaceItem->refInter->getInputModifier();\r
1250       if (mod != NULL) {\r
1251         if (!lstIfaceItem.contains(toIfaceItem)) lstIfaceItem.append(toIfaceItem);\r
1252       }\r
1253     }\r
1254     // write input modifiers\r
1255     writer.writeStartElement("modifiers");\r
1256     foreach(InterfaceItem* item, lstIfaceItem) {\r
1257       AbstractInputModifier* mod = item->refInter->getInputModifier();\r
1258       if (mod != NULL) {\r
1259         writer.writeStartElement("modifier");\r
1260         writer.writeAttribute("id", QString::number(item->getId()));\r
1261         writer.writeAttribute("type",mod->getTypeStr());\r
1262         writer.writeAttribute("params", mod->getParametersStr());\r
1263         writer.writeEndElement();\r
1264       }\r
1265     }\r
1266 \r
1267     writer.writeEndElement();    //</modifiers>\r
1268     writer.writeEndElement();      //</blast_project\r
1269 \r
1270     writer.writeEndDocument();\r
1271 \r
1272     file.close();\r
1273     unsaveModif = false;\r
1274   }\r
1275 //#endif\r
1276 }\r
1277 \r
1278 void Parameters::setArrowPathes() {\r
1279   QPainterPath _inArrow;\r
1280   _inArrow.lineTo(arrowLineLength,0);\r
1281   _inArrow.lineTo(arrowLineLength+arrowWidth,-arrowHeight/2);\r
1282   _inArrow.lineTo(arrowLineLength+arrowWidth,arrowHeight/2);\r
1283   _inArrow.lineTo(arrowLineLength,0);\r
1284   //_inArrow.closeSubpath();\r
1285   dataArrowIn = _inArrow;\r
1286 \r
1287   QPainterPath _inArrowC;\r
1288   _inArrowC.lineTo(arrowLineLength,0);\r
1289   _inArrowC.addEllipse(arrowLineLength,-arrowHeight/2,arrowHeight-1,arrowHeight-1);\r
1290   clkrstArrow = _inArrowC;\r
1291 \r
1292   QPainterPath _outArrow;\r
1293   _outArrow.lineTo(arrowLineLength,0);\r
1294   _outArrow.lineTo(arrowLineLength,-arrowHeight/2);\r
1295   _outArrow.lineTo(arrowLineLength+arrowWidth,0);\r
1296   _outArrow.lineTo(arrowLineLength,arrowHeight/2);\r
1297   _outArrow.lineTo(arrowLineLength,0);\r
1298   //_outArrow.closeSubpath();\r
1299   dataArrowOut = _outArrow;\r
1300 \r
1301 }\r
1302 \r
1303 GroupScene* Parameters::searchSceneById(int id, GroupScene *scene) {\r
1304 \r
1305   if (scene->getId() == id) return scene;\r
1306   GroupScene* sc = NULL;\r
1307 \r
1308   foreach(GroupScene *s, scene->getChildrenScene()) {\r
1309     sc = searchSceneById(id,s);\r
1310     if (sc != NULL) return sc;\r
1311   }\r
1312   return NULL;\r
1313 }\r
1314 \r
1315 GroupItem* Parameters::searchGroupItemById(int id, GroupScene *scene) {\r
1316 \r
1317   if (scene->getGroupItem()->getId() == id) return scene->getGroupItem();\r
1318 \r
1319   GroupItem* item = NULL;\r
1320   foreach(GroupScene *s, scene->getChildrenScene()) {\r
1321     item = searchGroupItemById(id,s);\r
1322     if (item != NULL) return item;\r
1323   }\r
1324   return NULL;\r
1325 }\r
1326 \r
1327 BoxItem* Parameters::searchBlockItemById(int id, GroupScene *scene) {\r
1328 \r
1329   foreach(BoxItem *item, scene->getBoxItems()){\r
1330     if(item->getId() == id){\r
1331       return item;\r
1332     }\r
1333   }\r
1334 \r
1335   BoxItem* item = NULL;\r
1336   foreach(GroupScene *s, scene->getChildrenScene()) {\r
1337     item = searchBlockItemById(id,s);\r
1338     if (item != NULL) return item;\r
1339   }\r
1340   return NULL;\r
1341 }\r
1342 \r
1343 BoxItem* Parameters::searchFunctionalBlock(AbstractBlock* block) {\r
1344 \r
1345   return searchFunctionalBlockRecur(block,topScene);\r
1346 }\r
1347 \r
1348 BoxItem* Parameters::searchFunctionalBlockRecur(AbstractBlock* block, GroupScene* scene) {\r
1349 \r
1350   foreach(BoxItem *item, scene->getBoxItems()){\r
1351     if(item->getRefBlock() == block) {\r
1352       return item;\r
1353     }\r
1354   }\r
1355 \r
1356   BoxItem* item = NULL;\r
1357   foreach(GroupScene *s, scene->getChildrenScene()) {\r
1358     item = searchFunctionalBlockRecur(block,s);\r
1359     if (item != NULL) return item;\r
1360   }\r
1361   return NULL;\r
1362 }\r
1363 \r
1364 InterfaceItem* Parameters::searchInterfaceItemById(int id, GroupScene* scene) {\r
1365 \r
1366   foreach(InterfaceItem *item, scene->getGroupItem()->getInterfaces()){\r
1367     if(item->getId() == id){\r
1368       return item;\r
1369     }\r
1370   }\r
1371   if (scene->isTopScene()) {\r
1372     foreach(StimuliItem *block, scene->getSourceItems()){\r
1373       foreach(InterfaceItem *item, block->getInterfaces()){\r
1374         if(item->getId() == id){\r
1375           return item;\r
1376         }\r
1377       }\r
1378     } \r
1379   }\r
1380   foreach(BoxItem *block, scene->getBoxItems()){\r
1381     foreach(InterfaceItem *item, block->getInterfaces()){\r
1382       if(item->getId() == id){\r
1383         return item;\r
1384       }\r
1385     }\r
1386   }\r
1387   InterfaceItem* item = NULL;\r
1388   foreach(GroupScene *s, scene->getChildrenScene()) {\r
1389     item = searchInterfaceItemById(id,s);\r
1390     if (item != NULL) return item;\r
1391   }\r
1392   return NULL;\r
1393 }\r
1394 \r
1395 QString Parameters::normalizeName(const QString &name) {\r
1396   QString s = name;\r
1397   s.replace(QRegularExpression("[^a-zA-Z0-9_]"),"_");\r
1398   s.replace(QRegularExpression("[_]+"),"_");\r
1399   return s;\r
1400 }\r