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

Private GIT Repository
moved clocks list to graph
[blast.git] / Parameters.cpp
index c991e5ff86fd033d5470157f7303d67576c0a6be..d7621d232a1afa54f59d2a4078eeba3bac0f521b 100644 (file)
@@ -9,6 +9,7 @@
 #include "GroupScene.h"\r
 #include "GroupItem.h"\r
 #include "BoxItem.h"\r
+#include "StimuliItem.h"\r
 #include "InterfaceItem.h"\r
 #include "ConnectionItem.h"\r
 \r
 #include "Exception.h"\r
 #include "BlocksToConfigureWidget.h"\r
 \r
+#include "BlockParameterGeneric.h"\r
+\r
+#include "DelayInputModifier.h"\r
+\r
 Parameters::Parameters() {\r
   categoryTree = NULL;\r
   arrowWidth = 5;\r
@@ -41,8 +46,14 @@ Parameters::Parameters() {
 \r
   unsaveModif = false;\r
   isRstClkShown = false;\r
+  \r
+  validityExtension = "_enb";\r
 \r
-  projectPath = QDir::currentPath();\r
+  projectPath = "";\r
+  projectName = "";\r
+  projectFile = "";\r
+\r
+  graph = new Graph();\r
 }\r
 \r
 Parameters::~Parameters() {\r
@@ -60,8 +71,8 @@ void Parameters::clear() {
   refPathes.clear();\r
 }\r
 \r
-Graph* Parameters::createGraph() {\r
-  graph = new Graph();\r
+Graph* Parameters::initGraph(bool createTopGroupIfaces) {\r
+  graph->createTopGroup(createTopGroupIfaces);\r
   return graph;\r
 }\r
 \r
@@ -69,40 +80,133 @@ void Parameters::destroyGraph() {
   delete graph;\r
 }\r
 \r
-GroupBlock* Parameters::addGroupBlock() {\r
-  GroupBlock* parent = AB_TO_GRP(currentScene->getGroupItem()->getRefBlock());\r
-  GroupBlock* newOne = graph->createChildBlock(parent);\r
-  return newOne;\r
-}\r
-\r
-FunctionalBlock* Parameters::addFunctionalBlock(int idCategory, int idBlock) {\r
+ReferenceBlock* Parameters::getReferenceBlock(int idCategory, int idBlock) {\r
 \r
   BlockCategory* blockCat = categoryTree->searchCategory(idCategory);\r
 \r
   if (blockCat == NULL) return NULL;\r
-  GroupBlock* group = AB_TO_GRP(currentScene->getGroupItem()->getRefBlock());\r
-  ReferenceBlock* ref = blockCat->getBlock(idBlock);\r
-  if (ref == NULL) return NULL;\r
+  ReferenceBlock* ref = blockCat->getBlockById(idBlock);\r
+  return ref;\r
+}\r
 \r
-  FunctionalBlock* newOne = graph->addFunctionalBlock(group, ref);\r
-  unsaveModif = true;\r
+ReferenceBlock* Parameters::getHiddenReferenceBlock(QString blockName) {\r
 \r
-  return newOne;\r
+  BlockCategory* blockCat = categoryTree->searchCategory(100);\r
+  if (blockCat == NULL) return NULL;\r
+  ReferenceBlock* ref = blockCat->getBlockByName(blockName);\r
+  return ref;\r
 }\r
 \r
-FunctionalBlock* Parameters::duplicateFunctionalBlock(FunctionalBlock *block) {\r
+double Parameters::getFeedingClockFrequency(AbstractInterface *iface) {\r
+\r
+  int idClock = 0;\r
+\r
+  if (iface->isReferenceInterface()) return 0.0;\r
+\r
+  if (iface->getClockIfaceType() == AbstractInterface::ParameterName) {\r
+    BlockParameter* param = iface->getOwner()->getParameterFromName(iface->getClockIfaceString());\r
+    if (!param->isUserParameter()) return 0.0;\r
+    bool ok;\r
+    double freq = param->getDoubleValue(&ok);\r
+    if (!ok) {\r
+      cerr << "Abnormal case: cannot retrieve clock id from parameter  " << qPrintable(param->getName()) << endl;\r
+    }\r
+    return freq;\r
+  }\r
+  else if ( (iface->getClockIfaceType() == AbstractInterface::ClockName) || ((iface->getDirection() == AbstractInterface::Input) && (iface->getPurpose() == AbstractInterface::Clock))) {\r
 \r
-  ReferenceBlock* ref = block->getReference();\r
-  GroupBlock* group = AB_TO_GRP(block->getParent());\r
+    // if iface is not clock, retrieve the clock related to it\r
+    if (iface->getClockIfaceType() == AbstractInterface::ClockName) {\r
+      iface = iface->getClockIface();\r
+    }\r
+    // if iface is a group interface, then iface name is ext_clk_X, thus extract the X\r
+    if (iface->isGroupInterface()) {\r
+      QString name = iface->getName();\r
+      name.remove(0,8);\r
+      bool ok;\r
+      idClock = name.toInt(&ok);\r
+      if (!ok) {\r
+        cerr << "Abnormal case: cannot retrieve clock id from iface name " << qPrintable(iface->getName()) << endl;\r
+        return 0.0;\r
+      }\r
+    }\r
+    // if iface is a functional interface, it is connected to clkrstgen_X (in top group) or to ext_clk_X (in subgroup)\r
+    else if (iface->isFunctionalInterface()) {\r
+      FunctionalInterface* funIface = AI_TO_FUN(iface);\r
+      ConnectedInterface* connFrom = funIface->getConnectedFrom();\r
+      if (connFrom == NULL) {\r
+        cerr << "Abnormal case: input clock " << qPrintable(iface->getName()) << " is not connected" << endl;\r
+        return 0.0;\r
+      }\r
+      if (iface->getOwner()->isTopGroupBlock()) {\r
+        QString name = connFrom->getOwner()->getName();\r
+        name.remove(0,10);\r
+        bool ok;\r
+        idClock = name.toInt(&ok);\r
+        if (!ok) {\r
+          cerr << "Abnormal case: cannot retrieve clock id for " << qPrintable(iface->getName()) << endl;\r
+          return 0.0;\r
+        }\r
+      }\r
+      else {\r
+        QString name = connFrom->getName();\r
+        name.remove(0,8);\r
+        bool ok;\r
+        idClock = name.toInt(&ok);\r
+        if (!ok) {\r
+          cerr << "Abnormal case: cannot retrieve clock id for " << qPrintable(iface->getName()) << endl;\r
+          return 0.0;\r
+        }\r
+      }\r
+    }\r
+  }\r
+  return graph->getClock(idClock);\r
+}\r
 \r
-  // adding to the group\r
-  FunctionalBlock* newBlock = new FunctionalBlock(group,ref);\r
-  newBlock->populate();\r
-  group->addBlock(newBlock);\r
+void Parameters::createDelayBlock() {\r
+  delayRef = new ReferenceBlock("no.xml");\r
+  delayRef->addCategory(100);\r
+  delayRef->setName("delay");\r
+\r
+  BlockCategory* cat = categoryTree->searchCategory(100);\r
+  cat->blocks.append(delayRef);\r
+\r
+  AbstractInterface* interIn = new ReferenceInterface(delayRef,"data_in",AbstractInterface::Input, AbstractInterface::Data, "expression","$in_width");\r
+  delayRef->addInterface(interIn);\r
+  AbstractInterface* interInCtl = new ReferenceInterface(delayRef,"data_in_enb",AbstractInterface::Input, AbstractInterface::Control, "boolean","1");\r
+  delayRef->addInterface(interInCtl);\r
+  interInCtl->setAssociatedIface(interIn);\r
+  AbstractInterface* interOut = new ReferenceInterface(delayRef,"data_out",AbstractInterface::Output, AbstractInterface::Data, "expression","$in_width");\r
+  delayRef->addInterface(interOut);\r
+  AbstractInterface* interOutCtl = new ReferenceInterface(delayRef,"data_out_enb",AbstractInterface::Output, AbstractInterface::Control, "boolean","1");\r
+  delayRef->addInterface(interOutCtl);\r
+  interOutCtl->setAssociatedIface(interOut);\r
+  BlockParameter* param1 = new BlockParameterGeneric(delayRef,"in_width","natural","8");\r
+  BlockParameter* param2 = new BlockParameterGeneric(delayRef,"dly_length","natural","1");\r
+  delayRef->addParameter(param1);\r
+  delayRef->addParameter(param2);\r
+  delayImpl = new BlockImplementation("no.xml");\r
+  delayImpl->setDelta("1");\r
+  QHash<QString,QString> consPattern;\r
+  consPattern.insert("data_in_enb","1");\r
+  delayImpl->setConsumptionPattern(consPattern);\r
+  QHash<QString,QString> prodPattern;\r
+  prodPattern.insert("data_out_enb","O{$dly_length}1");\r
+  delayImpl->setProductionPattern(prodPattern);\r
+  delayImpl->setProductionCounter("1");\r
+  delayRef->addImplementation(delayImpl);\r
+  delayImpl->setReference(delayRef);\r
+  if (! delayImpl->checkPatterns()) {\r
+    cout << "Delay block creation: failure" << endl;\r
+  }\r
+  else {\r
+    cout << "Delay block creation: success" << endl;\r
+  }\r
 \r
-  return newBlock;\r
 }\r
 \r
+\r
+\r
 void Parameters::validateXmlFile(const QString& xmlFileName, const QString& xsdFileName, XmlFileType fileType) throw(Exception) {\r
   // opening configFile\r
   QFile xmlFile(xmlFileName);\r
@@ -203,115 +307,80 @@ QDomElement Parameters::openProjectFile(const QString& projectFileName) throw(Ex
   return root;\r
 }\r
 \r
-void Parameters::loadProject(QDomElement root) {\r
-\r
-#ifdef DEBUG_INCLFUN\r
+GroupWidget *Parameters::loadProject(QDomElement root) throw(Exception) {\r
 \r
   bool ok = false;\r
   GroupWidget* groupWidget = NULL;\r
   GroupItem *groupItem = NULL;\r
   GroupBlock *groupBlock = NULL;\r
 \r
+  GroupWidget* topGroup = NULL;\r
+\r
+  QString path = root.attribute("project_path","none");\r
+  if (path != "none") {\r
+    QDir dir(path);\r
+    if (dir.exists()) {\r
+      projectPath = path;\r
+\r
+    }\r
+    cout << "project path set to " << qPrintable(projectPath) << endl;\r
+  }\r
   /**********************************************************\r
    1 : getting scene and creating associated group widgets\r
   ***********************************************************/\r
   QDomNodeList scenesNodes = root.elementsByTagName("scene");\r
 \r
+  int maxIdScene = -1;\r
   for(int i=0; i<scenesNodes.length(); i++) {\r
     QDomElement currentSceneNode = scenesNodes.at(i).toElement();\r
     int idScene = currentSceneNode.attribute("id","none").toInt(&ok);\r
     if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
+    if (idScene > maxIdScene) maxIdScene = idScene;\r
     int idUpperScene = currentSceneNode.attribute("upper_scene","none").toInt(&ok);\r
     if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
 \r
     if (idUpperScene == -1) {\r
-      dispatcher->createTopScene();\r
+      topGroup = dispatcher->createTopScene(Dispatcher::Load);\r
       topScene->setId(idScene);\r
-      groupItem = topScene->getGroupItem();\r
-      groupBlock = AB_TO_GRP(groupItem->getRefBlock());\r
+      groupItem = topScene->getGroupItem();      \r
       cout << "top group added to scene n°" << idScene << endl;\r
     }\r
     else {\r
-      GroupScene* scene = searchSceneById(idUpperScene, topScene);\r
-      GroupWidget* parent = scene->getGroupWindow();\r
-      groupWidget = dispatcher->createChildScene(parent);\r
-      groupItem = groupWidget->getScene()->getGroupItem();\r
-      groupBlock = AB_TO_GRP(groupItem->getRefBlock());\r
+      cout << "trying to create scene n°" << idScene << " with upper scene n°" <<idUpperScene << endl;\r
+      GroupScene* upperScene = searchSceneById(idUpperScene, topScene);\r
+      /* IMPORTANT: calling addNewEmptyGroup() leads to create a new GroupWidget\r
+       *            AND a BoxItem in upperScene that represents the GroupItem in the\r
+       *            newly created child scene. Thus, it has not to be created when\r
+       *            reading bi_group tags in the following but just searched\r
+       */\r
+      groupWidget = dispatcher->addNewEmptyGroup(Dispatcher::Load, upperScene,false);\r
+      groupWidget->getScene()->setId(idScene);\r
+      groupItem = groupWidget->getScene()->getGroupItem();      \r
     }\r
+    groupBlock = AB_TO_GRP(groupItem->getRefBlock());\r
     /**********************************************************\r
-     1.1 : getting the group item\r
+     1.1 : getting the group item of each scene\r
     ***********************************************************/\r
     QDomElement groupItemNode = currentSceneNode.firstChildElement("group_item");\r
-\r
-    int id = groupItemNode.attribute("id","none").toInt(&ok);\r
-    if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-    QString name = groupItemNode.attribute("name","none");\r
-    if(name == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-    QStringList positionStr = groupItemNode.attribute("position","none").split(",");\r
-    if(positionStr.length() != 2) throw(Exception(PROJECTFILE_CORRUPTED));\r
-    int posX = positionStr.at(0).toInt(&ok);\r
-    if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-    int posY = positionStr.at(1).toInt(&ok);\r
-    if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-    QStringList dimensionStr = groupItemNode.attribute("dimension","none").split(",");\r
-    if(dimensionStr.length() != 2) throw(Exception(PROJECTFILE_CORRUPTED));\r
-    int dimX = dimensionStr.at(0).toInt(&ok);\r
-    if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-    int dimY = dimensionStr.at(1).toInt(&ok);\r
-    if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-    groupItem->setId(id);\r
-    groupItem->setPos(posX,posY);\r
-    groupItem->setDimension(dimX,dimY);\r
-    groupBlock->setName(name);\r
+    try {\r
+      groupItem->load(groupItemNode);\r
+    }\r
+    catch(Exception err) {\r
+      throw(err);\r
+    }\r
 \r
     if (idUpperScene != -1) {\r
       groupWidget->setWindowTitle(groupBlock->getName());\r
       groupWidget->show();\r
-    }\r
-    cout << "group info : \n-id : " << id << "\n-pos : " << posX << ", " << posY << "\n-dim : " << dimX << ", " << dimY << "\n-name : " << name.toStdString() << endl;\r
-\r
-    QDomNodeList interfaces = groupItemNode.elementsByTagName("group_iface");\r
-    for(int j=0; j<interfaces.length(); j++){\r
-      QDomElement currentInterfaceNode = interfaces.at(j).toElement();\r
-\r
-      int id = currentInterfaceNode.attribute("id","none").toInt(&ok);\r
-      if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      QString name = currentInterfaceNode.attribute("name","none");\r
-      if(name == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      QString levelStr = currentInterfaceNode.attribute("level","none");\r
-      int level = AbstractInterface::getIntLevel(levelStr);\r
-      if(level == -1) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      QString directionStr = currentInterfaceNode.attribute("direction","none");\r
-      int direction = AbstractInterface::getIntDirection(directionStr);\r
-      if(direction == -1) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      QString orientationStr = currentInterfaceNode.attribute("orientation","none");\r
-      int orientation = InterfaceItem::getIntOrientation(orientationStr);\r
-      if(orientation == -1) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      double position = currentInterfaceNode.attribute("position","none").toDouble(&ok);\r
-      if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      GroupInterface *groupInterface = new GroupInterface(groupBlock,name,direction,level);\r
-\r
-      InterfaceItem *interfaceItem = new InterfaceItem(position,orientation,groupInterface,groupItem,this);\r
-      interfaceItem->setId(id);\r
-\r
-      groupBlock->addInterface(groupInterface);\r
-      groupItem->addInterface(interfaceItem);\r
-      cout << "interface add to " << groupBlock->getName().toStdString() << endl;\r
-    }\r
+      cout << qPrintable(groupItem->getRefBlock()->getName()) << " has upper box item in " << qPrintable(groupItem->getParentItem()->getScene()->getGroupItem()->getRefBlock()->getName()) << endl;\r
+    }    \r
   }\r
-\r
+  dispatcher->setSceneCounter(Dispatcher::Load, maxIdScene+1);\r
   cout << "groupItems loaded and windows created succefully!" << endl;\r
 \r
+  /**********************************************************\r
+   2 : getting the functional blocks of each scene\r
+  ***********************************************************/\r
 \r
   for(int i=0; i<scenesNodes.length(); i++){\r
     QDomElement currentSceneNode = scenesNodes.at(i).toElement();\r
@@ -321,137 +390,49 @@ void Parameters::loadProject(QDomElement root) {
     GroupScene *currentScene = searchSceneById(idScene,topScene);\r
 \r
     if(currentScene == NULL) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
+    /**********************************************************\r
+     2.1 : getting sources if it is top scene\r
+    ***********************************************************/\r
+    if (currentScene->isTopScene()) {\r
+      QDomNodeList sourceNodes = currentSceneNode.elementsByTagName("source_item");\r
+      cout << "top scene has " << sourceNodes.length() << " sources" << endl;\r
+      for(int j=0; j<sourceNodes.length(); j++) {\r
+        QDomElement currentSBNode = sourceNodes.at(j).toElement();      \r
+        StimuliItem* sourceItem = new StimuliItem(dispatcher,this);\r
+        try {\r
+          sourceItem->load(currentSBNode);\r
+        }\r
+        catch(Exception err) {\r
+          throw(err);\r
+        }\r
+        cout << "source item has been read, add it to the scene" << endl;\r
+        // add the block to the GroupScene\r
+        currentScene->addStimuliItem(sourceItem);\r
+      } \r
+    }\r
+    /**********************************************************\r
+     2.2 : getting functional blocks\r
+    ***********************************************************/\r
     QDomNodeList functionalBlockNodes = currentSceneNode.elementsByTagName("bi_functional");\r
 \r
-    for(int j=0; j<functionalBlockNodes.length(); j++){\r
-      QDomElement currentFBNode = functionalBlockNodes.at(j).toElement();\r
-\r
-      int id = currentFBNode.attribute("id","none").toInt(&ok);\r
-      if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      QString refXml = currentFBNode.attribute("ref_xml","none");\r
-      if(refXml == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      QString refMd5 = currentFBNode.attribute("ref_md5","none");\r
-      if(refMd5 == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      cout << "ref md5 : " << refMd5.toStdString() << "\nref xml : " << refXml.toStdString() << endl;\r
-\r
-      QString name = currentFBNode.attribute("name","none");\r
-      if(name == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      QStringList positionStr = currentFBNode.attribute("position","none").split(",");\r
-      if(positionStr.length() != 2) throw(Exception(PROJECTFILE_CORRUPTED));\r
-      int posX = positionStr.at(0).toInt(&ok);\r
-      if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-      int posY = positionStr.at(1).toInt(&ok);\r
-      if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      QStringList dimensionStr = currentFBNode.attribute("dimension","none").split(",");\r
-      if(dimensionStr.length() != 2) throw(Exception(PROJECTFILE_CORRUPTED));\r
-      int dimX = dimensionStr.at(0).toInt(&ok);\r
-      if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-      int dimY = dimensionStr.at(1).toInt(&ok);\r
-      if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-      AbstractBlock *reference;\r
-      /*if(refMd5 != "none"){\r
-        cout << "md5" << endl;\r
-        reference = searchBlockByMd5(refMd5);\r
-      }\r
-      else */if(refXml != "none"){\r
-        cout << "xml" << endl;\r
-        reference = searchBlockByXml(refXml);\r
-      }\r
-      else {\r
-        throw(Exception(PROJECTFILE_CORRUPTED));\r
-      }\r
-\r
-      FunctionalBlock *functionalBlock = new FunctionalBlock(currentScene->getGroupItem()->getRefBlock(),reference);\r
-      functionalBlock->setName(name);\r
-\r
-      ((GroupBlock*)currentScene->getGroupItem()->getRefBlock())->addBlock(functionalBlock);\r
-\r
-\r
-      BlockItem *blockItem = new BlockItem(currentScene->getGroupItem(),functionalBlock,dispatcher,this);\r
-      blockItem->setPos(posX,posY);\r
-      blockItem->setDimension(dimX,dimY);\r
-      blockItem->setId(id);\r
-      ((GroupItem*)currentScene->getGroupItem())->addBlockItem(blockItem);\r
-      currentScene->addItem(blockItem);\r
-      currentScene->addBlockItem(blockItem);\r
-\r
-      QDomNodeList blockParamNodes = currentFBNode.elementsByTagName("bif_parameter");\r
-\r
-      for(int i=0; i<blockParamNodes.length(); i++){\r
-        QDomElement currentBlockParamNode = blockParamNodes.at(i).toElement();\r
-\r
-        QString name = currentBlockParamNode.attribute("name","none");\r
-        if(name == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-        QString value = currentBlockParamNode.attribute("value","none");\r
-        if(value == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-        QString context = currentBlockParamNode.attribute("context","none");\r
-        if(context == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-        QString type = currentBlockParamNode.attribute("type","none");\r
-        if(type == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-\r
-        BlockParameter *blockParam = new BlockParameter;\r
-        blockParam->setName(name);\r
-        blockParam->setValue(value);\r
-        blockParam->setType(type);\r
-        if(context == "constant") blockParam->setContext(BlockParameter::Constant);\r
-        if(context == "user") blockParam->setContext(BlockParameter::User);\r
-        if(context == "generic") blockParam->setContext(BlockParameter::Generic);\r
-        if(context == "wb") blockParam->setContext(BlockParameter::Wishbone);\r
-        if(context == "port") blockParam->setContext(BlockParameter::Port);\r
-\r
-        functionalBlock->addParameter(blockParam);\r
+    for(int j=0; j<functionalBlockNodes.length(); j++) {\r
+      QDomElement currentFBNode = functionalBlockNodes.at(j).toElement();      \r
+      BoxItem* funcItem = new BoxItem(dispatcher,this, currentScene->getGroupItem());\r
+      try {\r
+        funcItem->loadFunctional(currentFBNode);\r
       }\r
-\r
-\r
-      QDomNodeList interfaceNodes = currentFBNode.elementsByTagName("bif_iface");\r
-\r
-      for(int i=0; i<interfaceNodes.length(); i++){\r
-\r
-        QDomElement currentInterfaceNode = interfaceNodes.at(i).toElement();\r
-\r
-        int id = currentInterfaceNode.attribute("id","none").toInt(&ok);\r
-        if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-        QString name = currentInterfaceNode.attribute("name","none");\r
-        if(name == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-        QString refName = currentInterfaceNode.attribute("ref_name","none");\r
-        if(refName == "none") throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-        QString orientationStr = currentInterfaceNode.attribute("orientation","none");\r
-        int orientation = InterfaceItem::getIntOrientation(orientationStr);\r
-        if(orientation == -1) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-        double position = currentInterfaceNode.attribute("position","none").toDouble(&ok);\r
-        if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-        ReferenceInterface *refInter = (ReferenceInterface*)reference->getIfaceFromName(refName);\r
-        FunctionalInterface *functionalInterface = new FunctionalInterface(functionalBlock,refInter);\r
-        functionalBlock->addInterface(functionalInterface);\r
-        functionalInterface->setName(refName);\r
-\r
-        InterfaceItem *interfaceItem = new InterfaceItem(position,orientation,functionalInterface,blockItem,this);\r
-        interfaceItem->setId(id);\r
-        interfaceItem->setName(name);\r
-\r
-        blockItem->addInterface(interfaceItem);\r
-\r
+      catch(Exception err) {\r
+        throw(err);\r
       }\r
+      // add the block to the GroupScene\r
+      currentScene->addBoxItem(funcItem);\r
     }\r
   }\r
-  cout << "functionalBlocks loaded and created succefully!" << endl;\r
+  cout << "functional blocks loaded and created succefully!" << endl;\r
 \r
+  /**********************************************************\r
+   3 : set the BoxItem that represents a GroupItem in a child scene\r
+  ***********************************************************/\r
 \r
   for(int i=0; i<scenesNodes.length(); i++){\r
     QDomElement currentSceneNode = scenesNodes.at(i).toElement();\r
@@ -485,19 +466,27 @@ void Parameters::loadProject(QDomElement root) {
       int dimY = dimensionStr.at(1).toInt(&ok);\r
       if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
 \r
-\r
+      // get the GroupItem already created and set at phase 1\r
       GroupItem *insideGroup = searchGroupItemById(idGroup, topScene);\r
-      if(insideGroup == NULL) cout << "group null" << endl;\r
-      BlockItem *blockItem = new BlockItem(insideGroup->getRefBlock(), dispatcher, this);\r
-      blockItem->setChildGroupItem(insideGroup);\r
-      blockItem->setId(id);\r
-      blockItem->setPos(posX,posY);\r
-      blockItem->setDimension(dimX,dimY);\r
+      BoxItem* upperItem = NULL;\r
+      if(insideGroup == NULL) cout << "group null" << endl;      \r
+      // now search within the scene which BoxItem has a childItem that is = to insideGroup\r
+      QList<BoxItem *> lst = currentScene->getBoxItems();\r
+      foreach(BoxItem* item, lst) {\r
+        if (item->getChildGroupItem() == insideGroup) {\r
+          upperItem = item;\r
+          break;\r
+        }\r
+      }\r
+      if (upperItem == NULL) {\r
+        throw(Exception(PROJECTFILE_CORRUPTED));\r
+      }\r
 \r
-      ((GroupItem*)currentScene->getGroupItem())->addBlockItem(blockItem);\r
-      currentScene->addItem(blockItem);\r
-      currentScene->addBlockItem(blockItem);\r
+      upperItem->setId(id);\r
+      upperItem->setPos(posX,posY);\r
+      upperItem->setDimension(dimX,dimY);\r
 \r
+      // set interfaces of this BoxItem\r
       QDomNodeList interfaceNodes = currentBiGroup.elementsByTagName("big_iface");\r
 \r
       for(int k=0; k<interfaceNodes.length(); k++){\r
@@ -516,34 +505,15 @@ void Parameters::loadProject(QDomElement root) {
         double position = currentInterfaceNode.attribute("position","none").toDouble(&ok);\r
         if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
 \r
-        GroupInterface *refInter = (GroupInterface*)insideGroup->searchInterfaceByName(refName)->refInter;\r
-        InterfaceItem *ifaceItem = new InterfaceItem(position, orientation, refInter, blockItem, this);\r
+        ConnectedInterface *refInter = insideGroup->searchInterfaceItemByName(refName)->refInter;\r
+        InterfaceItem *ifaceItem = new InterfaceItem(position, orientation, refInter, upperItem, this);\r
         ifaceItem->setId(id);\r
-        blockItem->addInterface(ifaceItem);\r
+        upperItem->addInterfaceItem(ifaceItem);\r
       }\r
     }\r
   }\r
   cout << "blockItems \"group\" loaded and created succefully!" << endl;\r
 \r
-\r
-  for(int i=0; i<scenesNodes.length(); i++){\r
-    QDomElement currentSceneNode = scenesNodes.at(i).toElement();\r
-\r
-    QDomElement groupItemNode = currentSceneNode.firstChildElement("group_item");\r
-\r
-    int id = groupItemNode.attribute("id","none").toInt(&ok);\r
-    if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-    int idUpperItem = groupItemNode.attribute("upper_item","none").toInt(&ok);\r
-    if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
-\r
-    BlockItem *currentItem = searchBlockItemById(id,topScene);\r
-    GroupItem *upperItem = searchGroupItemById(idUpperItem, topScene);\r
-\r
-    if(currentItem != NULL && upperItem != NULL){\r
-      currentItem->setUpperItem(upperItem);\r
-    }\r
-  }\r
-\r
   QDomNodeList connectionNodes = root.elementsByTagName("connection");\r
 \r
   for(int i=0; i<connectionNodes.length(); i++){\r
@@ -560,13 +530,48 @@ void Parameters::loadProject(QDomElement root) {
     InterfaceItem *iface2 = searchInterfaceItemById(to,topScene);\r
 \r
     if(iface1 != NULL && iface2 != NULL){\r
-      dispatcher->connect(iface1,iface2);\r
+      dispatcher->createConnection(Dispatcher::Load, iface1,iface2);\r
     } else {\r
       cout << "interfaces not found, connect canceled!" << endl;\r
     }\r
   }\r
+  cout << "connections loaded and created succefully!" << endl;\r
 \r
-#endif\r
+  QDomNodeList modifierNodes = root.elementsByTagName("modifier");\r
+\r
+  for(int i=0; i<modifierNodes.length(); i++){\r
+    QDomElement currentModifierNode = modifierNodes.at(i).toElement();\r
+\r
+    int id = currentModifierNode.attribute("id","none").toInt(&ok);\r
+    if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
+\r
+    QString typeStr = currentModifierNode.attribute("type","none");\r
+    if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
+    QString paramsStr = currentModifierNode.attribute("params","none");\r
+    if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
+\r
+    /* NB: just adding delays for now. To be cont'd */\r
+    InterfaceItem *iface = searchInterfaceItemById(id,topScene);\r
+\r
+    if ((iface == NULL ) || (iface->refInter == NULL) || (iface->refInter->getAssociatedIface() == NULL)) {\r
+      cout << "modified interface not found, modifiers setup canceled!" << endl;\r
+    }\r
+    else {\r
+      ConnectedInterface* connIface = AI_TO_CON(iface->refInter->getAssociatedIface());\r
+\r
+      AbstractInputModifier* mod = NULL;\r
+      if (typeStr == "delay") {\r
+        int delay = paramsStr.toInt(&ok);\r
+        if(!ok) throw(Exception(PROJECTFILE_CORRUPTED));\r
+        mod = new DelayInputModifier(connIface, delay);\r
+        connIface->setInputModifier(mod);\r
+      }\r
+    }\r
+  }\r
+\r
+  cout << "modifiers loaded and created succefully!" << endl;\r
+\r
+  return topGroup;\r
 }\r
 \r
 void Parameters::loadBlastConfiguration(QString confFile) throw(Exception) {\r
@@ -642,10 +647,27 @@ void Parameters::loadBlastConfiguration(QString confFile) throw(Exception) {
     implPathes.append(path);\r
     cout << "impl path : " << qPrintable(path) << endl << endl;\r
   }\r
+\r
+  QDomElement eltSource = eltImpl.nextSiblingElement("sources");\r
+  nbPathesStr = eltSource.attribute("nb","none");\r
+  nbPathes = nbPathesStr.toInt(&ok);\r
+  QDomNodeList listSourceDir = eltSource.elementsByTagName("source_lib");\r
+  if ((!ok) || (nbPathes != listSourceDir.size())) throw(Exception(CONFIGFILE_CORRUPTED));\r
+\r
+  for(int i=0;i<listSourceDir.size();i++) {\r
+    QDomNode nodeSourceDir = listSourceDir.at(i);\r
+    QDomElement eltSourceDir = nodeSourceDir.toElement();\r
+    if (eltSourceDir.isNull()) throw(Exception(CONFIGFILE_CORRUPTED));\r
+    QString path = eltSourceDir.attribute("path","none");\r
+    if (path == "none") throw(Exception(CONFIGFILE_CORRUPTED));\r
+    sourcePathes.append(path);\r
+    cout << "core path : " << qPrintable(path) << endl << endl;\r
+  }\r
+\r
   // getting elt = the element <defaults>\r
   // for each child element, initialize the associated attributes of Parameters\r
 \r
-  QDomElement eltDefaults = eltImpl.nextSiblingElement("defaults");\r
+  QDomElement eltDefaults = eltSource.nextSiblingElement("defaults");\r
 \r
   QDomElement eltBlocks = eltDefaults.firstChildElement("blocks");\r
   QString attributeStr = eltBlocks.attribute("width", "none");\r
@@ -707,14 +729,14 @@ void Parameters::loadReferencesFromXml() throw(Exception) {
       QString line = in.readLine();\r
       line = in.readLine();\r
 \r
-      if (!line.contains("<block>")) {\r
+      if (!line.contains("<block")) {\r
         blockXML.close();\r
         continue;\r
       }\r
 \r
       blockXML.close();\r
       try {\r
-        validateXmlFile(fileName,"block.xsd",Reference);\r
+        validateXmlFile(fileName,"reference.xsd",Reference);\r
       }\r
       catch(Exception err) {\r
         throw(err);\r
@@ -850,14 +872,14 @@ void Parameters::loadImplementationsFromXml() throw(Exception) {
       implXML.close();\r
       cout << "OK" << endl;\r
       cout << "reading " << qPrintable(fileName) << " content ...";\r
-      /*\r
+\r
       try {\r
-        validateXmlFile(fileName,"block.xsd",Implementation);\r
+        validateXmlFile(fileName,"implementation.xsd",Implementation);\r
       }\r
       catch(Exception e) {\r
         throw(e);\r
       }\r
-      */\r
+\r
       // reading in into QDomDocument\r
       QDomDocument document ("FileXML");\r
       if (!implXML.open(QIODevice::ReadOnly)) {\r
@@ -875,6 +897,28 @@ void Parameters::loadImplementationsFromXml() throw(Exception) {
       QString refXml = implRoot.attribute("ref_name","none");\r
       QString refMd5 = implRoot.attribute("ref_md5","none");\r
       BlockImplementation* impl = new BlockImplementation(fileName,refXml,refMd5);\r
+\r
+      QDomNodeList archNode = implRoot.elementsByTagName("architecture");\r
+\r
+      if (archNode.isEmpty()) {\r
+        cout << "impl has no architecture" << endl;\r
+        return;\r
+      }\r
+      QDomElement archElt = archNode.at(0).toElement();\r
+      QString compList = archElt.attribute("comp_list","none");\r
+      if (compList != "none") {\r
+        QStringList compos = compList.split(",");\r
+        foreach(QString s, compos) {\r
+          impl->addResource(s);\r
+        }\r
+      }\r
+\r
+      try {\r
+        impl->loadPatterns(implRoot);\r
+      }\r
+      catch(int err) {\r
+        throw(err);\r
+      }\r
       availableImplementations.append(impl);\r
 \r
       ReferenceBlock* ref = NULL;\r
@@ -886,9 +930,12 @@ void Parameters::loadImplementationsFromXml() throw(Exception) {
       }\r
       if (ref == NULL) {\r
         cout << "Cannot find a reference block for impl :" << qPrintable(fileName) << endl;\r
-      }\r
-      ref->addImplementation(impl);\r
-      impl->setReference(ref);\r
+      }      \r
+      else {          \r
+        ref->addImplementation(impl);\r
+        impl->setReference(ref);\r
+        if (! impl->checkPatterns()) throw(Exception(IMPLFILE_CORRUPTED));\r
+      }      \r
       cout << "OK" << endl;\r
     }\r
   }\r
@@ -933,8 +980,11 @@ void Parameters::loadImplementationsFromLib() throw(Exception) {
     if (ref == NULL) {\r
       cout << "Cannot find a reference block for impl :" << qPrintable(impl->getXmlFile()) << endl;\r
     }\r
-    ref->addImplementation(impl);\r
-    impl->setReference(ref);\r
+    else {          \r
+      ref->addImplementation(impl);\r
+      impl->setReference(ref);\r
+      if (! impl->checkPatterns()) throw(Exception(IMPLFILE_CORRUPTED));\r
+    }\r
   }\r
   libFile.close();\r
 }\r
@@ -964,6 +1014,74 @@ void Parameters::saveImplementationsToLib() throw(Exception) {
   libFile.close();\r
 \r
 }\r
+\r
+\r
+void Parameters::loadSources() throw(Exception) {\r
+\r
+  for(int i=0;i<sourcePathes.size();i++) {\r
+    cout << "analyzing " << qPrintable(sourcePathes.at(i)) << endl;\r
+    QDir dir(sourcePathes.at(i));\r
+    QStringList filter;\r
+    filter << "*.vhd" << "*.ngc";\r
+    dir.setNameFilters(filter);\r
+    QStringList list = dir.entryList();\r
+    for(int j=0;j<list.size();j++) {\r
+      QString fileName = dir.absolutePath();\r
+      fileName.append("/"+list.at(j));\r
+\r
+      if (list.at(j).endsWith(".ngc")) {\r
+        QString netName = list.at(j);\r
+        netName.truncate(list.at(j).size() -4);\r
+        cout << "found netlist " << qPrintable(netName) << endl;\r
+        availableResources.append(new ExternalResource(netName,fileName,ExternalResource::Netlist));\r
+      }\r
+      else {\r
+        cout << "parsing " << qPrintable(fileName) << " ... ";\r
+        QFile srcXML(fileName);\r
+        if (!srcXML.open(QIODevice::ReadOnly)) {\r
+          throw(Exception(IMPLFILE_NOACCESS));\r
+        }\r
+        QTextStream in(&srcXML);\r
+\r
+        QString line = in.readLine();\r
+        while (!line.isNull()) {\r
+          if (line.contains("package", Qt::CaseInsensitive)) {\r
+            QRegularExpression rxPack("^package (.+) is$",QRegularExpression::CaseInsensitiveOption);\r
+            QRegularExpressionMatch matchPack = rxPack.match(line);\r
+            if (matchPack.hasMatch()) {\r
+              QString packName = matchPack.captured(1);\r
+              cout << "found package " << qPrintable(packName) << endl;\r
+              availableResources.append(new ExternalResource(packName,fileName,ExternalResource::Package));\r
+            }\r
+          }\r
+          else if (line.contains("entity", Qt::CaseInsensitive)) {\r
+            QRegularExpression rxEnt("^entity (.+) is$",QRegularExpression::CaseInsensitiveOption);\r
+            QRegularExpressionMatch matchEnt = rxEnt.match(line);\r
+            if (matchEnt.hasMatch()) {\r
+              QString entityName = matchEnt.captured(1);\r
+              cout << "found entity " << qPrintable(entityName) << endl;\r
+              availableResources.append(new ExternalResource(entityName,fileName,ExternalResource::Code));\r
+            }\r
+          }\r
+          line = in.readLine();\r
+        }\r
+        srcXML.close();\r
+        cout << "OK" << endl;\r
+      }\r
+    }\r
+  }\r
+}\r
+\r
+QList<ExternalResource *> Parameters::searchResourceByName(const QString& name) {\r
+  QList<ExternalResource*> listRes;\r
+  foreach(ExternalResource* s, availableResources) {\r
+    if (s->getName() == name) {\r
+      listRes.append(s);\r
+    }\r
+  }\r
+  return listRes;\r
+}\r
+\r
 void Parameters::addAvailableBlock(ReferenceBlock *block) {\r
   availableBlocks.append(block);\r
   foreach (int id,block->getCategories()) {\r
@@ -1029,14 +1147,14 @@ QList<AbstractBlock *> Parameters::getBlocksToConfigure() {
 \r
 \r
 void Parameters::updateToolbar() {\r
-  int nb = currentScene->getBlockItems().length();\r
+  int nb = currentScene->getBoxItems().length();\r
   for(int i = 0; i<nb; i++){\r
-    if(currentScene->getBlockItems().at(i)->isSelected()){\r
-      currentScene->getGroupWindow()->enableGroupButton(true);\r
+    if(currentScene->getBoxItems().at(i)->isSelected()){\r
+      currentScene->getGroupWidget()->enableGroupButton(true);\r
       return;\r
     }\r
   }\r
-  currentScene->getGroupWindow()->enableGroupButton(false);\r
+  currentScene->getGroupWidget()->enableGroupButton(false);\r
 }\r
 \r
 \r
@@ -1098,9 +1216,6 @@ void Parameters::save(QString confFile) {
     // cross the scene level by level using a FIFO\r
     QList<GroupScene*> fifoScene;\r
     fifoScene.append(topScene);\r
-    foreach(ConnectionItem* item, topScene->getConnectionItems()) {\r
-      allConnections.append(item);\r
-    }\r
 \r
     GroupScene *scene;\r
     while (!fifoScene.isEmpty()) {\r
@@ -1109,11 +1224,12 @@ void Parameters::save(QString confFile) {
       foreach(GroupScene* s, scene->getChildrenScene()) {\r
         fifoScene.append(s);\r
       }\r
-      foreach(ConnectionItem* item, topScene->getConnectionItems()) {\r
+\r
+      foreach(ConnectionItem* item, scene->getConnectionItems()) {\r
         allConnections.append(item);\r
       }\r
     }\r
-\r
+    writer.writeEndElement();    //</scenes>\r
 \r
     writer.writeStartElement("connections");\r
     foreach(ConnectionItem* item, allConnections) {\r
@@ -1127,6 +1243,35 @@ void Parameters::save(QString confFile) {
     }\r
 \r
     writer.writeEndElement();    //</connections>\r
+\r
+    QList<InterfaceItem *> lstIfaceItem;\r
+    // search for modifiers\r
+    foreach(ConnectionItem* item, allConnections) {\r
+      InterfaceItem* fromIfaceItem = item->getFromInterfaceItem();\r
+      AbstractInputModifier* mod = fromIfaceItem->refInter->getInputModifier();\r
+      if (mod != NULL) {\r
+        if (!lstIfaceItem.contains(fromIfaceItem)) lstIfaceItem.append(fromIfaceItem);\r
+      }\r
+      InterfaceItem* toIfaceItem = item->getToInterfaceItem();\r
+      mod = toIfaceItem->refInter->getInputModifier();\r
+      if (mod != NULL) {\r
+        if (!lstIfaceItem.contains(toIfaceItem)) lstIfaceItem.append(toIfaceItem);\r
+      }\r
+    }\r
+    // write input modifiers\r
+    writer.writeStartElement("modifiers");\r
+    foreach(InterfaceItem* item, lstIfaceItem) {\r
+      AbstractInputModifier* mod = item->refInter->getInputModifier();\r
+      if (mod != NULL) {\r
+        writer.writeStartElement("modifier");\r
+        writer.writeAttribute("id", QString::number(item->getId()));\r
+        writer.writeAttribute("type",mod->getTypeStr());\r
+        writer.writeAttribute("params", mod->getParametersStr());\r
+        writer.writeEndElement();\r
+      }\r
+    }\r
+\r
+    writer.writeEndElement();    //</modifiers>\r
     writer.writeEndElement();      //</blast_project\r
 \r
     writer.writeEndDocument();\r
@@ -1143,8 +1288,13 @@ void Parameters::setArrowPathes() {
   _inArrow.lineTo(arrowLineLength+arrowWidth,-arrowHeight/2);\r
   _inArrow.lineTo(arrowLineLength+arrowWidth,arrowHeight/2);\r
   _inArrow.lineTo(arrowLineLength,0);\r
-  _inArrow.closeSubpath();\r
-  inArrow = _inArrow;\r
+  //_inArrow.closeSubpath();\r
+  dataArrowIn = _inArrow;\r
+\r
+  QPainterPath _inArrowC;\r
+  _inArrowC.lineTo(arrowLineLength,0);\r
+  _inArrowC.addEllipse(arrowLineLength,-arrowHeight/2,arrowHeight-1,arrowHeight-1);\r
+  clkrstArrow = _inArrowC;\r
 \r
   QPainterPath _outArrow;\r
   _outArrow.lineTo(arrowLineLength,0);\r
@@ -1152,8 +1302,8 @@ void Parameters::setArrowPathes() {
   _outArrow.lineTo(arrowLineLength+arrowWidth,0);\r
   _outArrow.lineTo(arrowLineLength,arrowHeight/2);\r
   _outArrow.lineTo(arrowLineLength,0);\r
-  _outArrow.closeSubpath();\r
-  outArrow = _outArrow;\r
+  //_outArrow.closeSubpath();\r
+  dataArrowOut = _outArrow;\r
 \r
 }\r
 \r
@@ -1183,7 +1333,7 @@ GroupItem* Parameters::searchGroupItemById(int id, GroupScene *scene) {
 \r
 BoxItem* Parameters::searchBlockItemById(int id, GroupScene *scene) {\r
 \r
-  foreach(BoxItem *item, scene->getBlockItems()){\r
+  foreach(BoxItem *item, scene->getBoxItems()){\r
     if(item->getId() == id){\r
       return item;\r
     }\r
@@ -1197,6 +1347,27 @@ BoxItem* Parameters::searchBlockItemById(int id, GroupScene *scene) {
   return NULL;\r
 }\r
 \r
+BoxItem* Parameters::searchFunctionalBlock(AbstractBlock* block) {\r
+\r
+  return searchFunctionalBlockRecur(block,topScene);\r
+}\r
+\r
+BoxItem* Parameters::searchFunctionalBlockRecur(AbstractBlock* block, GroupScene* scene) {\r
+\r
+  foreach(BoxItem *item, scene->getBoxItems()){\r
+    if(item->getRefBlock() == block) {\r
+      return item;\r
+    }\r
+  }\r
+\r
+  BoxItem* item = NULL;\r
+  foreach(GroupScene *s, scene->getChildrenScene()) {\r
+    item = searchFunctionalBlockRecur(block,s);\r
+    if (item != NULL) return item;\r
+  }\r
+  return NULL;\r
+}\r
+\r
 InterfaceItem* Parameters::searchInterfaceItemById(int id, GroupScene* scene) {\r
 \r
   foreach(InterfaceItem *item, scene->getGroupItem()->getInterfaces()){\r
@@ -1204,7 +1375,16 @@ InterfaceItem* Parameters::searchInterfaceItemById(int id, GroupScene* scene) {
       return item;\r
     }\r
   }\r
-  foreach(BoxItem *block, scene->getBlockItems()){\r
+  if (scene->isTopScene()) {\r
+    foreach(StimuliItem *block, scene->getSourceItems()){\r
+      foreach(InterfaceItem *item, block->getInterfaces()){\r
+        if(item->getId() == id){\r
+          return item;\r
+        }\r
+      }\r
+    } \r
+  }\r
+  foreach(BoxItem *block, scene->getBoxItems()){\r
     foreach(InterfaceItem *item, block->getInterfaces()){\r
       if(item->getId() == id){\r
         return item;\r
@@ -1218,3 +1398,10 @@ InterfaceItem* Parameters::searchInterfaceItemById(int id, GroupScene* scene) {
   }\r
   return NULL;\r
 }\r
+\r
+QString Parameters::normalizeName(const QString &name) {\r
+  QString s = name;\r
+  s.replace(QRegularExpression("[^a-zA-Z0-9_]"),"_");\r
+  s.replace(QRegularExpression("[_]+"),"_");\r
+  return s;\r
+}\r