]> SALOME platform Git repositories - modules/kernel.git/commitdiff
Salome HOME
Adding DSC's basic layer.
authorribes <ribes>
Tue, 27 Feb 2007 10:05:51 +0000 (10:05 +0000)
committerribes <ribes>
Tue, 27 Feb 2007 10:05:51 +0000 (10:05 +0000)
Needs to fix CORBA headers declarations and
fix debug infos.

14 files changed:
configure.ac
src/DSC/DSC_Basic/ConnectionManager_i.cxx [new file with mode: 0644]
src/DSC/DSC_Basic/ConnectionManager_i.hxx [new file with mode: 0644]
src/DSC/DSC_Basic/DSC_Callbacks.hxx [new file with mode: 0644]
src/DSC/DSC_Basic/DSC_i.cxx [new file with mode: 0644]
src/DSC/DSC_Basic/DSC_i.hxx [new file with mode: 0644]
src/DSC/DSC_Basic/DSC_interface.cxx [new file with mode: 0644]
src/DSC/DSC_Basic/DSC_interface.hxx [new file with mode: 0644]
src/DSC/DSC_Basic/Makefile.am [new file with mode: 0644]
src/DSC/DSC_Basic/PortProperties_i.cxx [new file with mode: 0644]
src/DSC/DSC_Basic/PortProperties_i.hxx [new file with mode: 0644]
src/DSC/DSC_Basic/SALOME_ConnectionManagerServer.cxx [new file with mode: 0644]
src/DSC/Makefile.am
src/Makefile.am

index 1a623565e8fc6d4b91eaf2105d1640c8460649e2..39f26951624368634debcc71026bdebc19026c02 100644 (file)
@@ -518,6 +518,8 @@ AC_OUTPUT([ \
        ./src/Communication/Makefile \
        ./src/Communication_SWIG/Makefile \
        ./src/Container/Makefile \
+       ./src/DSC/Makefile \
+       ./src/DSC/DSC_Basic/Makefile \
        ./src/GenericObj/Makefile \
        ./src/HDFPersist/Makefile \
        ./src/KERNEL_PY/Makefile \
diff --git a/src/DSC/DSC_Basic/ConnectionManager_i.cxx b/src/DSC/DSC_Basic/ConnectionManager_i.cxx
new file mode 100644 (file)
index 0000000..66dd032
--- /dev/null
@@ -0,0 +1,77 @@
+// André Ribes EDF R&D - 2006
+// 
+#include "ConnectionManager_i.hxx"
+#include "SALOME_NamingService.hxx"
+
+ConnectionManager_i::ConnectionManager_i(CORBA::ORB_ptr orb) {
+  SALOME_NamingService * ns = new SALOME_NamingService(orb);
+  const char * ConnectionManagerNameInNS = "/ConnectionManager";
+  ns->Register(_this(), ConnectionManagerNameInNS);
+
+  current_id = 0;
+  pthread_mutex_init(&mutex, NULL);
+}
+
+ConnectionManager_i::~ConnectionManager_i() {}
+
+/* Cette méthode connecte deux ports ensembles.
+ * Elle permet de rendre plus simple l'utilisation du modèle de programmation
+ * à base de ports.
+ */
+Engines::ConnectionManager::connectionId
+ConnectionManager_i::connect(Engines::DSC_ptr uses_component, 
+                            const char* uses_port_name, 
+                            Engines::DSC_ptr provides_component, 
+                            const char* provides_port_name) 
+throw (Engines::DSC::PortNotDefined,
+       Engines::DSC::BadPortType,
+       Engines::DSC::NilPort) 
+{
+
+  Ports::Port_ptr p_port = provides_component->get_provides_port(provides_port_name, false);
+  uses_component->connect_uses_port(uses_port_name, p_port);
+  provides_component->connect_provides_port(provides_port_name);
+
+  // Ajout de l'id dans la map comme tout s'est bien passé
+  // 
+  // Protection du current_id pour récupérer un id unique
+  pthread_mutex_lock(&mutex);
+  Engines::ConnectionManager::connectionId rtn_id = current_id;
+  current_id += 1;
+  pthread_mutex_unlock(&mutex);
+
+  // Creation de la structure et ajout dans la map
+  connection_infos * infos = new connection_infos();
+  infos->uses_component = Engines::DSC::_duplicate(uses_component);
+  infos->uses_port_name = uses_port_name;
+  infos->provides_component = Engines::DSC::_duplicate(provides_component);
+  infos->provides_port_name = provides_port_name;
+  infos->provides_port = Ports::Port::_duplicate(p_port);
+
+  // Ajout dans la map
+  ids[rtn_id] = infos;
+
+  return rtn_id;
+}
+
+void
+ConnectionManager_i::disconnect(const Engines::ConnectionManager::connectionId id,
+                               Engines::DSC::Message message)
+throw (Engines::ConnectionManager::BadId)
+{
+  // Verification que l'id existe
+  ids_it = ids.find(id);
+  if (ids_it == ids.end())
+    throw Engines::ConnectionManager::BadId();
+
+  // Recuperation des infos
+  connection_infos * infos = ids[id];
+  infos->provides_component->disconnect_provides_port(infos->provides_port_name.c_str(),
+                                                     message);
+  infos->uses_component->disconnect_uses_port(infos->uses_port_name.c_str(),
+                                             Ports::Port::_duplicate(infos->provides_port),
+                                             message);
+  // Nettoyage
+  delete infos;
+  ids.erase(id);
+}
diff --git a/src/DSC/DSC_Basic/ConnectionManager_i.hxx b/src/DSC/DSC_Basic/ConnectionManager_i.hxx
new file mode 100644 (file)
index 0000000..f872d87
--- /dev/null
@@ -0,0 +1,61 @@
+// André Ribes EDF R&D - 2006
+// 
+#ifndef _CONNECTION_MANAGER_I_HXX_
+#define _CONNECTION_MANAGER_I_HXX_
+
+#include <iostream>
+#include <map>
+#include "DSC_Engines.hh"
+#include <pthread.h>
+
+/*! \class ConnectionManager_i
+ *  \brief This class implements the interface Engines::ConnectionManager.
+ */
+class ConnectionManager_i :
+  public virtual POA_Engines::ConnectionManager
+{
+  public :
+    ConnectionManager_i(CORBA::ORB_ptr orb);
+    ~ConnectionManager_i();
+
+    /*!
+     * \see Engines::ConnectionManager::connect
+     */
+    Engines::ConnectionManager::connectionId connect(Engines::DSC_ptr uses_component, 
+                                                    const char* uses_port_name, 
+                                                    Engines::DSC_ptr provides_component, 
+                                                    const char* provides_port_name)
+      throw (Engines::DSC::PortNotDefined,
+            Engines::DSC::BadPortType,
+            Engines::DSC::NilPort);
+
+    /*!
+     * \see Engines::ConnectionManager::disconnect
+     */
+    void disconnect(const Engines::ConnectionManager::connectionId id,
+                   Engines::DSC::Message message)
+      throw (Engines::ConnectionManager::BadId);
+
+  private :
+
+    struct connection_infos {
+      Engines::DSC_ptr uses_component; 
+      std::string uses_port_name;
+      Engines::DSC_ptr provides_component;
+      std::string provides_port_name;
+      Ports::Port_ptr provides_port;
+    };
+
+    typedef std::map<Engines::ConnectionManager::connectionId, 
+           connection_infos *> ids_type;
+    typedef std::map<Engines::ConnectionManager::connectionId, 
+           connection_infos *>::iterator ids_it_type;
+
+    ids_type ids;
+    ids_it_type ids_it;
+
+    int current_id;
+    pthread_mutex_t mutex;
+};
+
+#endif
diff --git a/src/DSC/DSC_Basic/DSC_Callbacks.hxx b/src/DSC/DSC_Basic/DSC_Callbacks.hxx
new file mode 100644 (file)
index 0000000..b501981
--- /dev/null
@@ -0,0 +1,47 @@
+// André Ribes EDF R&D - 2006
+//
+#ifndef _DSC_CALLBACKS_HXX_
+#define _DSC_CALLBACKS_HXX_
+
+#include "DSC_Engines.hh"
+
+/*! \class DSC_Callbacks
+ *  \brief this is an abstract that defines the methods that the component
+ *  uses to prevent the component user code that the state of the component has changed.
+ *  Currently only port's connection modifications are signaled.
+ */
+class DSC_Callbacks
+{
+  public:
+    virtual ~DSC_Callbacks() {}
+
+    /*!
+     * \brief This method is used by the component when the number of connection
+     * on a provides port changes. This information helps the user code to detect
+     * operation on his ports.
+     * 
+     *
+     * \param provides_port_name the name of the provides name that has changed.
+     * \param connection_nbr the new number of connection on the provides port.
+     * \param message contains informations about the modification of the port.
+     */
+    virtual void provides_port_changed(const char* provides_port_name,
+                                      int connection_nbr,
+                                      const Engines::DSC::Message message) = 0;
+
+    /*!
+     * \brief This method is used by the component when the number of connection
+     * on a uses port changes. This information helps the user code to detect
+     * operation on his ports.
+     * 
+     *
+     * \param uses_port_name the name of the uses name that has changed.
+     * \param connection_nbr the new sequence representing the uses port.
+     * \param message contains informations about the modification of the port.
+     */
+    virtual void uses_port_changed(const char* uses_port_name,
+                                  Engines::DSC::uses_port * new_uses_port,
+                                  const Engines::DSC::Message message) = 0;
+};
+
+#endif
diff --git a/src/DSC/DSC_Basic/DSC_i.cxx b/src/DSC/DSC_Basic/DSC_i.cxx
new file mode 100644 (file)
index 0000000..b84a496
--- /dev/null
@@ -0,0 +1,19 @@
+// André Ribes EDF R&D - 2006
+// 
+
+#include "DSC_i.hxx"
+
+Engines_DSC_i::
+Engines_DSC_i(CORBA::ORB_ptr orb,
+                       PortableServer::POA_ptr poa,
+                       PortableServer::ObjectId * contId,
+                       const char *instanceName,
+                       const char *interfaceName,
+                       bool notif) : Engines_Component_i(orb, 
+                                                         poa, 
+                                                         contId, 
+                                                         instanceName, 
+                                                         interfaceName) {}
+
+Engines_DSC_i::~Engines_DSC_i() {}
+
diff --git a/src/DSC/DSC_Basic/DSC_i.hxx b/src/DSC/DSC_Basic/DSC_i.hxx
new file mode 100644 (file)
index 0000000..a97b9d7
--- /dev/null
@@ -0,0 +1,141 @@
+// André Ribes EDF R&D - 2006
+// 
+#ifndef _DSC_I_HXX_
+#define _DSC_I_HXX_
+
+#include <iostream>
+#include <map>
+#include <string.h>
+#include <assert.h>
+
+#include "SALOME_Component_i.hxx"
+#include "DSC_interface.hxx"
+
+/*! \class Engines_DSC_i
+ *  \brief This class implements the interface Engines::DSC
+ */
+class Engines_DSC_i: 
+  public Engines_Component_i, // On ne met pas virtual afin que ce soit cette classe 
+                             // qui appelle le bon constructeur de Engines_Component_i.
+                             // Si on mettait virtual ce serait a la classe dérivée
+                             // de Engines_DSC_i qui devrait appeler le bon constructeur
+                             // de Engines_Component_i.
+  public virtual POA_Engines::DSC,
+  public Engines_DSC_interface
+{
+public:
+  Engines_DSC_i(CORBA::ORB_ptr orb,
+                         PortableServer::POA_ptr poa,
+                         PortableServer::ObjectId * contId,
+                         const char *instanceName,
+                         const char *interfaceName,
+                         bool notif = false);
+
+  virtual ~Engines_DSC_i();
+
+  /*!
+   * \see Engines::DSC::add_provides_port
+   */
+  virtual void add_provides_port(Ports::Port_ptr ref, 
+                                const char* provides_port_name,
+                                Ports::PortProperties_ptr port_prop) 
+    throw (Engines::DSC::PortAlreadyDefined,
+          Engines::DSC::NilPort,
+          Engines::DSC::BadProperty) {
+      Engines_DSC_interface::add_provides_port(ref, 
+                                              provides_port_name,
+                                              port_prop);
+    }
+
+  /*!
+   * \see Engines::DSC::add_uses_port
+   */
+  virtual void add_uses_port(const char* repository_id, 
+                            const char* uses_port_name,
+                            Ports::PortProperties_ptr port_prop)
+    throw (Engines::DSC::PortAlreadyDefined,
+          Engines::DSC::BadProperty) {
+      Engines_DSC_interface::add_uses_port(repository_id, 
+                                          uses_port_name,
+                                          port_prop);
+    }
+
+  /*!
+   * \see Engines::DSC::get_provides_port
+   */
+  virtual Ports::Port_ptr get_provides_port(const char* provides_port_name,
+                                           const CORBA::Boolean connection_error) 
+    throw (Engines::DSC::PortNotDefined,
+          Engines::DSC::PortNotConnected) {
+      return Engines_DSC_interface::get_provides_port(provides_port_name,
+                                                     connection_error);
+    }
+
+  /*!
+   * \see Engines::DSC::get_uses_port
+   */
+  virtual Engines::DSC::uses_port * get_uses_port(const char* uses_port_name)
+    throw (Engines::DSC::PortNotDefined,
+          Engines::DSC::PortNotConnected) {
+      return Engines_DSC_interface::get_uses_port(uses_port_name);
+    }
+
+  /*!
+   * \see Engines::DSC::connect_provides_port
+   */
+  virtual void connect_provides_port(const char* provides_port_name)
+    throw (Engines::DSC::PortNotDefined) {
+      Engines_DSC_interface::connect_provides_port(provides_port_name);
+    }
+
+  /*!
+   * \see Engines::DSC::connect_uses_port
+   */
+  virtual void connect_uses_port(const char* uses_port_name,
+                                Ports::Port_ptr provides_port_ref) 
+  throw (Engines::DSC::PortNotDefined,
+        Engines::DSC::BadPortType,
+        Engines::DSC::NilPort) {
+    Engines_DSC_interface::connect_uses_port(uses_port_name,
+                                            provides_port_ref);
+  }
+
+  /*!
+   * \see Engines::DSC::is_connected
+   */
+  virtual CORBA::Boolean is_connected(const char* port_name)
+    throw (Engines::DSC::PortNotDefined) {
+      return Engines_DSC_interface::is_connected(port_name);
+    }
+
+   /*!
+   * \see Engines::DSC::disconnect_provides_port
+   */
+  virtual void disconnect_provides_port(const char* provides_port_name,
+                                       const Engines::DSC::Message message)
+    throw (Engines::DSC::PortNotDefined,
+          Engines::DSC::PortNotConnected) {
+      Engines_DSC_interface::disconnect_provides_port(provides_port_name,
+                                                     message);
+    }
+
+   /*!
+   * \see Engines::DSC::disconnect_uses_port
+   */
+  virtual void disconnect_uses_port(const char* uses_port_name,
+                                   Ports::Port_ptr provides_port_ref,
+                                   const Engines::DSC::Message message)
+    throw (Engines::DSC::PortNotDefined,
+          Engines::DSC::PortNotConnected,
+          Engines::DSC::BadPortReference) {
+      Engines_DSC_interface::disconnect_uses_port(uses_port_name,
+                                                 provides_port_ref,
+                                                 message);
+    }
+  virtual Ports::PortProperties_ptr get_port_properties(const char* port_name)
+    throw (Engines::DSC::PortNotDefined) {
+      return Engines_DSC_interface::get_port_properties(port_name);
+    }
+};
+
+#endif
diff --git a/src/DSC/DSC_Basic/DSC_interface.cxx b/src/DSC/DSC_Basic/DSC_interface.cxx
new file mode 100644 (file)
index 0000000..69b7f30
--- /dev/null
@@ -0,0 +1,389 @@
+
+// André Ribes EDF R&D - 2006
+// 
+
+#include "DSC_interface.hxx"
+
+Engines_DSC_interface::Engines_DSC_interface() {}
+
+Engines_DSC_interface::~Engines_DSC_interface() {}
+
+/* Ajoute le provides port "name" avec sa reference "ref".
+ * Lève PortAlreadyDefined si le port est déjà défini.
+ * Lève NilPort si la reference du port est nil.
+ */
+void
+Engines_DSC_interface::add_provides_port(Ports::Port_ptr ref, 
+                                const char* provides_port_name,
+                                Ports::PortProperties_ptr port_prop) 
+throw (Engines::DSC::PortAlreadyDefined,
+       Engines::DSC::NilPort,
+       Engines::DSC::BadProperty) 
+{
+  // Test des arguments de la méthode
+  assert(provides_port_name);
+  if (CORBA::is_nil(ref))
+    throw Engines::DSC::NilPort();
+  if (CORBA::is_nil(port_prop))
+    throw Engines::DSC::BadProperty();
+
+  my_ports_it = my_ports.find(provides_port_name);
+  if (my_ports_it ==  my_ports.end()) {
+    // Creation d'un nouveau port de type provides.
+    port_t * new_port = new port_t();
+    new_port->type = provides;
+    new_port->connection_nbr = 0;
+    new_port->provides_port_ref = Ports::Port::_duplicate(ref);
+    new_port->port_prop = Ports::PortProperties::_duplicate(port_prop);
+
+    // Enregistrement du port dans la map.
+    my_ports[provides_port_name] = new_port;
+  }
+  else
+    throw Engines::DSC::PortAlreadyDefined();
+}
+
+/* Ajoute le uses port "name" avec son repository_id Corba.
+ * Lève PortAlreadyDefined si le port est déjà défini.
+ */
+void
+Engines_DSC_interface::add_uses_port(const char* repository_id, 
+                            const char* uses_port_name,
+                            Ports::PortProperties_ptr port_prop) 
+throw (Engines::DSC::PortAlreadyDefined,
+       Engines::DSC::BadProperty) 
+{
+  // Test des arguments de la méthode
+  // Note : Il est difficile de tester si la chaîne du 
+  // repository_id est valide ...
+  assert(repository_id);
+  assert(uses_port_name);
+  if (CORBA::is_nil(port_prop))
+    throw Engines::DSC::BadProperty();
+
+  my_ports_it = my_ports.find(uses_port_name);
+  if (my_ports_it ==  my_ports.end()) {
+    // Creation d'un nouveau port de type uses.
+    port_t * new_port = new port_t();
+    new_port->type = uses;
+    new_port->connection_nbr = 0;
+    new_port->uses_port_refs.length(0);
+    new_port->repository_id = repository_id;
+    new_port->port_prop = Ports::PortProperties::_duplicate(port_prop);
+
+    // Enregistrement du port dans la map.
+    my_ports[uses_port_name] = new_port;
+  }
+  else
+    throw Engines::DSC::PortAlreadyDefined();
+}
+
+/* Fournit le port provides qui a le nom "provides_port_name" dans les my_ports.
+ * Lève l'exception Engines::DSC::PortNotDefined s'il ne trouve
+ * pas le port.
+ * Le booleen permet de savoir s'il faut donner ou non le port s'il est connecté
+ * ou non.
+ */ 
+Ports::Port_ptr
+Engines_DSC_interface::get_provides_port(const char* provides_port_name,
+                                const CORBA::Boolean connection_error) 
+  throw (Engines::DSC::PortNotDefined,
+        Engines::DSC::PortNotConnected, 
+        Engines::DSC::BadPortType) 
+{
+  // Test des arguments de la méthode
+  assert(provides_port_name);
+
+  Ports::Port_ptr rtn_port = Ports::Port::_nil();
+//   std::cout << "---- DSC_Interface : MARK 1 ---- Recherche de : " << provides_port_name << "----" << std::endl;
+//   ports::iterator it;
+//   std::cout << "----> ";
+//   for(it=my_ports.begin();it!=my_ports.end();++it) 
+//     std::cout << "|"<<(*it).first<<"|, ";
+//   std::cout << std::endl;
+  
+  my_ports_it = my_ports.find(provides_port_name);
+  if (my_ports_it ==  my_ports.end())
+    throw Engines::DSC::PortNotDefined();
+  if (my_ports[provides_port_name]->type != provides) {
+    Engines::DSC::BadPortType BPT;
+    BPT.expected = CORBA::string_dup("Expected a provides port");
+    BPT.received = CORBA::string_dup((std::string("Received a uses/none port : ")+provides_port_name).c_str());
+    throw BPT;
+  }
+
+  if (my_ports[provides_port_name]->connection_nbr == 0 && connection_error)
+    throw Engines::DSC::PortNotConnected();
+
+  rtn_port = Ports::Port::_duplicate(my_ports[provides_port_name]->provides_port_ref);
+  return rtn_port;
+}
+
+/* Fournit le port uses qui a le nom "uses_port_name" s'il existe et s'il est 
+ * connecté.
+ * Dans le cas contraire lève les exceptions :
+ * PortNotDefined, PortNotConnected.
+ */
+Engines::DSC::uses_port * 
+Engines_DSC_interface::get_uses_port(const char* uses_port_name) 
+  throw (Engines::DSC::PortNotDefined,
+        Engines::DSC::PortNotConnected,
+        Engines::DSC::BadPortType) 
+{
+  // Test des arguments de la méthode
+  assert(uses_port_name);
+
+  Engines::DSC::uses_port * rtn_port = NULL;  
+  // On commence par tester si le port existe
+  my_ports_it = my_ports.find(uses_port_name);
+  if (my_ports_it == my_ports.end())
+    throw Engines::DSC::PortNotDefined();
+  if (my_ports[uses_port_name]->type != uses){
+    Engines::DSC::BadPortType BPT;
+    BPT.expected = CORBA::string_dup("Expected a uses port");
+    BPT.received = CORBA::string_dup((std::string("Received a provides/none port : ")+uses_port_name).c_str());
+    throw BPT;
+  }
+
+  // On regarde maintenant si le port est connecté
+  if (my_ports[uses_port_name]->connection_nbr > 0) {
+    rtn_port = new Engines::DSC::uses_port(my_ports[uses_port_name]->uses_port_refs);
+  }
+  else
+    throw Engines::DSC::PortNotConnected();
+  
+  return rtn_port;
+}
+
+
+/* 
+ * Cette méthode prévient par le biais de l'attribut connection_nbr
+ * que le port provides est connecté à un uses port de plus.
+ * Notons que pour le moment le provides_port n'a pas de référence sur le composant
+ * qui détient le uses port. Le modèle actuel considère que c'est au 
+ * "framework" ou a l'application de gérer les connexions et les déconnexions.
+ * Il n'y a donc pas de callback entre deux ports connectés.
+ *
+ */
+void
+Engines_DSC_interface::connect_provides_port(const char* provides_port_name)
+    throw (Engines::DSC::PortNotDefined)
+{
+  assert(provides_port_name);
+
+  // Le port uses existe t'il ?
+  my_ports_it = my_ports.find(provides_port_name);
+  if (my_ports_it ==  my_ports.end())
+    throw Engines::DSC::PortNotDefined();
+  if (my_ports[provides_port_name]->type != provides)
+    throw Engines::DSC::PortNotDefined();
+
+
+  // Augmentation du nombre de connexions
+  my_ports[provides_port_name]->connection_nbr += 1;
+  // On prévient le code utilisateur
+  provides_port_changed(provides_port_name, 
+                       my_ports[provides_port_name]->connection_nbr,
+                       Engines::DSC::AddingConnection
+                      );
+}
+
+/* Cette méthode permet d'ajouter une connexion à un port uses.
+ * Elle appelle ensuite une méthode abstraite que le composant doit 
+ * implémenter afin d'être averti lorsque les connexions changent.
+ * En effet, l'utilisateur doit ensuite prendre le nouveau uses_port
+ * fournit dans le callback.
+ *
+ */
+void
+Engines_DSC_interface::connect_uses_port(const char* uses_port_name,
+                                        Ports::Port_ptr provides_port_ref) 
+  throw (Engines::DSC::PortNotDefined,
+        Engines::DSC::BadPortType,
+        Engines::DSC::NilPort)
+{
+  assert(uses_port_name);
+
+  // Le port uses existe t'il ?
+  my_ports_it = my_ports.find(uses_port_name);
+  if (my_ports_it ==  my_ports.end())
+    throw Engines::DSC::PortNotDefined();
+  if (my_ports[uses_port_name]->type != uses) {
+    Engines::DSC::BadPortType BPT;
+    BPT.expected = CORBA::string_dup("Expected a uses port");
+    BPT.received = CORBA::string_dup((std::string("Received a provides/none port : ")+uses_port_name).c_str());
+    throw BPT;
+  }
+
+  // La reference est-elle nulle ?
+  if (CORBA::is_nil(provides_port_ref))
+    throw Engines::DSC::NilPort();
+
+  // Le type est-il correct ?
+  const char * repository_id = my_ports[uses_port_name]->repository_id.c_str();
+  if (provides_port_ref->_is_a(repository_id)) 
+  {
+    // Ajout dans la sequence
+    CORBA::ULong lgth = my_ports[uses_port_name]->uses_port_refs.length();
+    my_ports[uses_port_name]->
+      uses_port_refs.length(lgth + 1);
+    my_ports[uses_port_name]->uses_port_refs[lgth] = 
+      Ports::Port::_duplicate(provides_port_ref);
+
+    // Augmentation du nombre de connexions
+    my_ports[uses_port_name]->connection_nbr += 1;
+    
+    // Appel du callback pour prévenir le uses port a été modifié
+    uses_port_changed(uses_port_name,
+                     new Engines::DSC::uses_port(my_ports[uses_port_name]->uses_port_refs),
+                     Engines::DSC::AddingConnection);
+  }
+  else {
+    Engines::DSC::BadPortType BPT;
+    BPT.expected = CORBA::string_dup("Expected ...");
+    BPT.received = CORBA::string_dup((std::string("Received an incorrect repository id type ")+
+                                     repository_id).c_str());
+    throw BPT;
+  }
+
+}
+
+/* Cette méthode teste si le uses port "name" est connecté.
+ * Léve PortNotDefined si le port n'existe pas.
+ */
+CORBA::Boolean
+Engines_DSC_interface::is_connected(const char* port_name) 
+  throw (Engines::DSC::PortNotDefined) 
+{
+  assert(port_name);
+
+  CORBA::Boolean rtn = false;
+
+  // Le port existe t-il ?
+  my_ports_it = my_ports.find(port_name);
+  if (my_ports_it ==  my_ports.end())
+    throw Engines::DSC::PortNotDefined();
+
+  // Le port est-il connecté ?
+  if (my_ports[port_name]->connection_nbr > 0)
+    rtn = true;
+
+  return rtn;
+}
+
+void
+Engines_DSC_interface::disconnect_provides_port(const char* provides_port_name,
+                                       const Engines::DSC::Message message)
+throw (Engines::DSC::PortNotDefined,
+       Engines::DSC::PortNotConnected)
+{
+  assert(provides_port_name);
+
+  // Le port existe t-il ?
+  my_ports_it = my_ports.find(provides_port_name);
+  if (my_ports_it ==  my_ports.end())
+    throw Engines::DSC::PortNotDefined();
+  if (my_ports[provides_port_name]->type != provides)
+    throw Engines::DSC::PortNotDefined();
+
+  // Le port est-il connecté ?
+  if (my_ports[provides_port_name]->connection_nbr > 0) 
+  {
+    my_ports[provides_port_name]->connection_nbr -= 1;
+    provides_port_changed(provides_port_name,
+                         my_ports[provides_port_name]->connection_nbr,
+                         message);
+  }
+  else
+    throw Engines::DSC::PortNotConnected();
+}
+
+void
+Engines_DSC_interface::disconnect_uses_port(const char* uses_port_name,
+                                   Ports::Port_ptr provides_port_ref,
+                                   const Engines::DSC::Message message)
+throw (Engines::DSC::PortNotDefined,
+       Engines::DSC::PortNotConnected,
+       Engines::DSC::BadPortReference) 
+{
+  assert(uses_port_name);
+
+  // Le port existe t-il ?
+  my_ports_it = my_ports.find(uses_port_name);
+  if (my_ports_it ==  my_ports.end())
+    throw Engines::DSC::PortNotDefined();
+  if (my_ports[uses_port_name]->type != uses)
+    throw Engines::DSC::PortNotDefined();
+
+  // Le port est-il connecté ?
+  if (my_ports[uses_port_name]->connection_nbr > 0) {
+    // On cherche le port dans la sequence representant le
+    // uses port.
+    if (CORBA::is_nil(provides_port_ref))
+      throw Engines::DSC::BadPortReference();
+
+    CORBA::Long port_index = -1;
+    CORBA::ULong seq_length = my_ports[uses_port_name]->uses_port_refs.length(); 
+    for(int i = 0; i < seq_length; i++)
+    {
+      if (my_ports[uses_port_name]->uses_port_refs[i]->_is_equivalent(provides_port_ref))
+      {
+       port_index = i;
+       break;
+      }
+    }
+
+    if (port_index == -1)
+      throw Engines::DSC::BadPortReference();
+
+    my_ports[uses_port_name]->connection_nbr -= 1;
+    Engines::DSC::uses_port * new_uses_port = 
+      new Engines::DSC::uses_port();
+    new_uses_port->length(seq_length - 1);
+
+    int index_ancien = 0;
+    int index_nouveau = 0;
+    for(;index_ancien < seq_length;) {
+      if (index_ancien == port_index) 
+      {
+       // Rien a faire !
+       // On ne change pas le index du nouveau tableau
+       index_ancien += 1;
+      }
+      else 
+      {
+       (*new_uses_port)[index_nouveau] = my_ports[uses_port_name]->uses_port_refs[index_ancien];
+       index_ancien += 1;
+       index_nouveau += 1;
+      }
+    }
+
+    // On remplace la sequence ...
+    my_ports[uses_port_name]->uses_port_refs = *new_uses_port;
+
+    // Rq c'est à l'utilisateur de détruire 
+    // la sequence s'il n'en veut pas !!!
+    uses_port_changed(uses_port_name,
+                     new_uses_port,
+                     message);
+  }
+  else
+    throw Engines::DSC::PortNotConnected();
+}
+
+Ports::PortProperties_ptr
+Engines_DSC_interface::get_port_properties(const char* port_name) 
+  throw (Engines::DSC::PortNotDefined) 
+{
+  assert(port_name);
+
+  Ports::PortProperties_ptr rtn_properties = Ports::PortProperties::_nil();
+
+  // Le port existe t-il ?
+  my_ports_it = my_ports.find(port_name);
+  if (my_ports_it ==  my_ports.end())
+    throw Engines::DSC::PortNotDefined();
+
+  rtn_properties = Ports::PortProperties::_duplicate(my_ports[port_name]->port_prop);
+  return rtn_properties;
+}
diff --git a/src/DSC/DSC_Basic/DSC_interface.hxx b/src/DSC/DSC_Basic/DSC_interface.hxx
new file mode 100644 (file)
index 0000000..2bcda63
--- /dev/null
@@ -0,0 +1,132 @@
+
+// André Ribes EDF R&D - 2006
+// 
+#ifndef _DSC_INTERFACE_HXX_
+#define _DSC_INTERFACE_HXX_
+
+#include <iostream>
+#include <map>
+#include <string.h>
+#include <assert.h>
+
+#include "DSC_Callbacks.hxx"
+
+/*! \class Engines_DSC_interface
+ *  \brief This class implements the interface Engines::DSC
+ */
+class Engines_DSC_interface: 
+  public DSC_Callbacks
+{
+public:
+  Engines_DSC_interface();
+  virtual ~Engines_DSC_interface();
+
+  /*!
+   * \see Engines::DSC::add_provides_port
+   */
+  virtual void add_provides_port(Ports::Port_ptr ref, 
+                                const char* provides_port_name,
+                                Ports::PortProperties_ptr port_prop) 
+    throw (Engines::DSC::PortAlreadyDefined,
+          Engines::DSC::NilPort,
+          Engines::DSC::BadProperty);
+
+  /*!
+   * \see Engines::DSC::add_uses_port
+   */
+  virtual void add_uses_port(const char* repository_id, 
+                            const char* uses_port_name,
+                            Ports::PortProperties_ptr port_prop)
+    throw (Engines::DSC::PortAlreadyDefined,
+          Engines::DSC::BadProperty);
+
+  /*!
+   * \see Engines::DSC::get_provides_port
+   */
+  virtual Ports::Port_ptr get_provides_port(const char* provides_port_name,
+                                           const CORBA::Boolean connection_error) 
+    throw (Engines::DSC::PortNotDefined,
+          Engines::DSC::PortNotConnected,
+          Engines::DSC::BadPortType);
+
+  /*!
+   * \see Engines::DSC::get_uses_port
+   */
+  virtual Engines::DSC::uses_port * get_uses_port(const char* uses_port_name)
+    throw (Engines::DSC::PortNotDefined,
+          Engines::DSC::PortNotConnected,
+          Engines::DSC::BadPortType);
+
+  /*!
+   * \see Engines::DSC::connect_provides_port
+   */
+  virtual void connect_provides_port(const char* provides_port_name)
+    throw (Engines::DSC::PortNotDefined);
+
+  /*!
+   * \see Engines::DSC::connect_uses_port
+   */
+  virtual void connect_uses_port(const char* uses_port_name,
+                                Ports::Port_ptr provides_port_ref) 
+  throw (Engines::DSC::PortNotDefined,
+        Engines::DSC::BadPortType,
+        Engines::DSC::NilPort);
+
+  /*!
+   * \see Engines::DSC::is_connected
+   */
+  virtual CORBA::Boolean is_connected(const char* port_name)
+    throw (Engines::DSC::PortNotDefined);
+
+   /*!
+   * \see Engines::DSC::disconnect_provides_port
+   */
+  virtual void disconnect_provides_port(const char* provides_port_name,
+                                       const Engines::DSC::Message message)
+    throw (Engines::DSC::PortNotDefined,
+          Engines::DSC::PortNotConnected);
+
+   /*!
+   * \see Engines::DSC::disconnect_uses_port
+   */
+  virtual void disconnect_uses_port(const char* uses_port_name,
+                                   Ports::Port_ptr provides_port_ref,
+                                   const Engines::DSC::Message message)
+    throw (Engines::DSC::PortNotDefined,
+          Engines::DSC::PortNotConnected,
+          Engines::DSC::BadPortReference);
+
+  virtual Ports::PortProperties_ptr get_port_properties(const char* port_name)
+    throw (Engines::DSC::PortNotDefined);
+
+protected:
+
+  /*-------------------------------------------------*/
+  /* Definition des types pour le stockage des ports */
+  
+  enum port_type {uses, provides, none};
+
+  struct port_t {
+    port_type type;
+    int connection_nbr;
+    
+    // Specifique aux uses port
+    Engines::DSC::uses_port uses_port_refs;
+    std::string repository_id;
+
+    // Specifique aux provides port;
+    Ports::Port_ptr provides_port_ref;
+
+    Ports::PortProperties_ptr port_prop;
+  };
+
+  typedef std::map<std::string, port_t *> ports;
+
+  /*-------------------------------------------------*/
+  /*-------------------------------------------------*/
+  ports my_ports;
+  ports::iterator my_ports_it;
+};
+
+#endif
diff --git a/src/DSC/DSC_Basic/Makefile.am b/src/DSC/DSC_Basic/Makefile.am
new file mode 100644 (file)
index 0000000..d0dc85c
--- /dev/null
@@ -0,0 +1,89 @@
+#  Copyright (C) 2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+#  CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS 
+# 
+#  This library is free software; you can redistribute it and/or 
+#  modify it under the terms of the GNU Lesser General Public 
+#  License as published by the Free Software Foundation; either 
+#  version 2.1 of the License. 
+# 
+#  This library is distributed in the hope that it will be useful, 
+#  but WITHOUT ANY WARRANTY; without even the implied warranty of 
+#  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU 
+#  Lesser General Public License for more details. 
+# 
+#  You should have received a copy of the GNU Lesser General Public 
+#  License along with this library; if not, write to the Free Software 
+#  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA 
+# 
+# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+#
+#
+#
+#  File   : Makefile.am
+#  Author : André RIBES (EDF)
+#  Module : KERNEL
+
+include $(top_srcdir)/salome_adm/unix/make_common_starter.am
+
+#
+# ===============================================================
+# Header to be installed
+# ===============================================================
+#
+# header files  
+salomeinclude_HEADERS = ConnectionManager_i.hxx \
+                       DSC_Callbacks.hxx \
+                       DSC_i.hxx \
+                       DSC_interface.hxx \
+                       PortProperties_i.hxx
+#
+# ===============================================================
+# Local definitions
+# ===============================================================
+#
+
+# This local variable defines the list of CPPFLAGS common to all target in this package.
+COMMON_CPPFLAGS= -I$(top_srcdir)/src/Container \
+                -I$(top_srcdir)/src/Notification \
+                -I$(top_srcdir)/src/SALOMELocalTrace \
+                -I$(top_srcdir)/src/Basics \
+                -I$(top_srcdir)/src/NamingService \
+                -I$(top_srcdir)/src/Utils \
+                -I$(top_builddir)/salome_adm/unix \
+                -I$(top_builddir)/idl \
+                @CORBA_CXXFLAGS@ @CORBA_INCLUDES@
+
+# This local variable defines the list of dependant libraries common to all target in this package.
+COMMON_LIBS = $(top_builddir)/src/Container/libSalomeContainer.la \
+             @CORBA_LIBS@
+
+#
+# ===============================================================
+# Libraries targets
+# ===============================================================
+#
+lib_LTLIBRARIES = libSalomeDSCContainer.la 
+
+libSalomeDSCContainer_la_SOURCES  = DSC_i.cxx \
+                                   ConnectionManager_i.cxx \
+                                   DSC_interface.cxx \
+                                   PortProperties_i.cxx
+
+libSalomeDSCContainer_la_CXXFLAGS = -no-undefined -version-info=0:0:0 \
+                                   $(COMMON_CPPFLAGS)
+
+libSalomeDSCContainer_la_LIBADD   = $(COMMON_LIBS)
+
+#
+# ===============================================================
+# Executables targets
+# ===============================================================
+#
+bin_PROGRAMS = SALOME_ConnectionManagerServer
+
+SALOME_ConnectionManagerServer_SOURCES  = SALOME_ConnectionManagerServer.cxx
+
+SALOME_ConnectionManagerServer_CXXFLAGS = $(COMMON_CPPFLAGS)
+
+SALOME_ConnectionManagerServer_LDADD    = libSalomeDSCContainer.la \
+                                         $(COMMON_LIBS)
diff --git a/src/DSC/DSC_Basic/PortProperties_i.cxx b/src/DSC/DSC_Basic/PortProperties_i.cxx
new file mode 100644 (file)
index 0000000..b70d0c8
--- /dev/null
@@ -0,0 +1,25 @@
+// André Ribes EDF R&D - 2006
+// 
+
+#include "PortProperties_i.hxx"
+
+PortProperties_i::PortProperties_i() {}
+
+PortProperties_i::~PortProperties_i() {}
+
+void
+PortProperties_i::set_property(const char * name, const CORBA::Any& value)
+  throw (Ports::NotDefined, Ports::BadType)
+{
+  // Default ...
+  throw Ports::NotDefined();
+}
+
+CORBA::Any* 
+PortProperties_i::get_property(const char* name)
+  throw (Ports::NotDefined)
+{
+  // Default ...
+  throw Ports::NotDefined();
+}
+
diff --git a/src/DSC/DSC_Basic/PortProperties_i.hxx b/src/DSC/DSC_Basic/PortProperties_i.hxx
new file mode 100644 (file)
index 0000000..71bffef
--- /dev/null
@@ -0,0 +1,23 @@
+// André Ribes EDF R&D - 2007
+// 
+#ifndef _PORTPROPERTIES_I_HXX_
+#define _PORTPROPERTIES_I_HXX_
+
+#include "SALOME_Ports.hh"
+
+class PortProperties_i:
+  public virtual POA_Ports::PortProperties
+{
+  public:
+    PortProperties_i();
+    virtual ~PortProperties_i();
+
+    virtual void set_property(const char * name, const CORBA::Any& value)
+      throw (Ports::NotDefined, Ports::BadType);
+    virtual CORBA::Any* get_property(const char* name)
+      throw (Ports::NotDefined);
+};
+
+#endif
+
+
diff --git a/src/DSC/DSC_Basic/SALOME_ConnectionManagerServer.cxx b/src/DSC/DSC_Basic/SALOME_ConnectionManagerServer.cxx
new file mode 100644 (file)
index 0000000..df894db
--- /dev/null
@@ -0,0 +1,37 @@
+#include "ConnectionManager_i.hxx"
+#include "utilities.h"
+#include <iostream>
+
+using namespace std;
+
+int main(int argc, char* argv[])
+{
+  PortableServer::POA_var root_poa;
+  PortableServer::POAManager_var pman;
+  CORBA::Object_var obj;
+  CORBA::ORB_var orb = CORBA::ORB_init( argc , argv ) ;
+  try{
+    obj = orb->resolve_initial_references("RootPOA");
+    if(!CORBA::is_nil(obj))
+      root_poa = PortableServer::POA::_narrow(obj);
+    if(!CORBA::is_nil(root_poa))
+      pman = root_poa->the_POAManager();
+    ConnectionManager_i * serv = new ConnectionManager_i(orb);
+    pman->activate();
+    orb->run();
+  }catch(CORBA::SystemException&){
+    MESSAGE("Caught CORBA::SystemException.");
+  }catch(PortableServer::POA::WrongPolicy&){
+    MESSAGE("Caught CORBA::WrongPolicyException.");
+  }catch(PortableServer::POA::ServantAlreadyActive&){
+    MESSAGE("Caught CORBA::ServantAlreadyActiveException");
+  }catch(CORBA::Exception&){
+    MESSAGE("Caught CORBA::Exception.");
+  }catch(std::exception& exc){
+    MESSAGE("Caught std::exception - "<<exc.what()); 
+  }catch(...){
+    MESSAGE("Caught unknown exception.");
+  }
+  END_OF(argv[0]);
+}
+
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..28473541b88c930f10cdf42fb4745f7818563775 100644 (file)
@@ -0,0 +1,26 @@
+#  Copyright (C) 2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+#  CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS 
+# 
+#  This library is free software; you can redistribute it and/or 
+#  modify it under the terms of the GNU Lesser General Public 
+#  License as published by the Free Software Foundation; either 
+#  version 2.1 of the License. 
+# 
+#  This library is distributed in the hope that it will be useful, 
+#  but WITHOUT ANY WARRANTY; without even the implied warranty of 
+#  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU 
+#  Lesser General Public License for more details. 
+# 
+#  You should have received a copy of the GNU Lesser General Public 
+#  License along with this library; if not, write to the Free Software 
+#  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA 
+# 
+# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+#
+#
+#
+#  File   : Makefile.am
+#  Author : André RIBES (EDF)
+#  Module : KERNEL
+
+SUBDIRS = DSC_Basic
index 8d6b7fa897608bcd585b2e04a8b2995deeabd5ce..2b3828839831145ff7cc8fc70da7cfde1736c7e8 100644 (file)
@@ -52,7 +52,8 @@ SUBDIR_CORBA = \
   KERNEL_PY \
   ModuleGenerator \
   Communication \
-  Communication_SWIG
+  Communication_SWIG \
+  DSC
 
 SUBDIR_CPPUNIT_BASE= \
   Basics/Test \