1 // Copyright (C) 2007-2020 CEA/DEN, EDF R&D, OPEN CASCADE
3 // Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License, or (at your option) any later version.
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 // Lesser General Public License for more details.
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
23 // File : Superv_Component_i.hxx
24 // Author : André RIBES (EDF), Eric Fayolle (EDF)
27 #ifndef _SUPERV_COMPONENT_I_HXX_
28 #define _SUPERV_COMPONENT_I_HXX_
31 #include "base_port.hxx"
32 #include "uses_port.hxx"
33 #include "provides_port.hxx"
34 #include "port_factory.hxx"
36 #include "DSC_Exception.hxx"
41 /*! \class Superv_Component_i
42 * \brief This class implements DSC_User component.
44 * This class allows a higher programming level than DSC_Basic. It enables
45 * a programming level for service's developers who want to use DSC ports.
47 * This class has two level for using and declare ports. The higher level proposes
48 * operations to add ports that are provided by default by SALOME like Calcium ports.
49 * It provides too some methods to add their own DSC_User ports.
51 * \note This class doesn't implement the init_service CORBA operation.
53 class Superv_Component_i :
55 virtual public POA_Engines::Superv_Component
58 Superv_Component_i(CORBA::ORB_ptr orb,
59 PortableServer::POA_ptr poa,
60 PortableServer::ObjectId * contId,
61 const char *instanceName,
62 const char *interfaceName,
64 Superv_Component_i(CORBA::ORB_ptr orb,
65 PortableServer::POA_ptr poa,
66 Engines::Container_ptr container,
67 const char *instanceName,
68 const char *interfaceName,
71 virtual ~Superv_Component_i();
73 // Exceptions declarations.
74 // There are defined on the Superv_Component_i.cxx to avoid problems
76 DSC_EXCEPTION(BadFabType);
77 DSC_EXCEPTION(BadType);
78 DSC_EXCEPTION(BadCast);
79 DSC_EXCEPTION(UnexpectedState);
80 DSC_EXCEPTION(PortAlreadyDefined);
81 DSC_EXCEPTION(PortNotDefined);
82 DSC_EXCEPTION(PortNotConnected);
83 DSC_EXCEPTION(NilPort);
84 DSC_EXCEPTION(BadProperty);
87 * \warning currently disabled.
89 virtual provides_port * create_provides_control_port()
93 * \warning currently disabled.
95 virtual provides_port * create_provides_data_and_control_port(const char* port_type)
99 * \warning currently disabled.
101 virtual uses_port * create_uses_control_port()
105 * \warning currently disabled.
107 virtual uses_port * create_uses_data_and_control_port(const char* port_type)
111 * This method permits to create a provides port provided by the platform.
112 * (See documentation of DSC for knoing these ports).
115 * \param port_fab_type type provides port.
116 * \return the provides port.
118 * \note It's user repsonsability to destroy the provides port.
120 virtual provides_port * create_provides_data_port(const std::string& port_fab_type)
125 * This method permits to create a uses port provided by the platform.
126 * (See documentation of DSC for knoing these ports).
129 * \param port_fab_type type uses port.
130 * \return the uses port.
132 * \note It's user repsonsability to destroy the uses port.
134 virtual uses_port * create_uses_data_port(const std::string& port_fab_type)
138 * Adds a port to the component. With this method only Salomé's provided DSC ports
141 * \param port_fab_type type of the port.
142 * \param port_type uses or provides.
143 * \param port_name the name of the port in the component.
145 virtual void add_port(const char * port_fab_type,
146 const char * port_type,
147 const char * port_name)
148 throw (PortAlreadyDefined, BadFabType, BadType, BadProperty);
151 * Adds a port to the component. With this method only Salomé's provided DSC ports
154 * \param port_fab_type type of the port.
155 * \param port_type uses or provides.
156 * \param port_name the name of the port in the component.
157 * \return the created port.
159 template < typename SpecificPortType >
160 SpecificPortType * add_port(const char * port_fab_type,
161 const char * port_type,
162 const char * port_name)
163 throw (PortAlreadyDefined, BadFabType, BadType, BadCast, BadProperty);
166 * Adds a created provides port to the component.
168 * \param port the provides port.
169 * \param provides_port_name the name of the port in the component.
171 virtual void add_port(provides_port * port,
172 const char* provides_port_name)
173 throw (PortAlreadyDefined, NilPort, BadProperty);
176 * Adds a created uses port to the component.
178 * \param port the uses port.
179 * \param uses_port_name the name of the port in the component.
181 virtual void add_port(uses_port * port,
182 const char* uses_port_name)
183 throw (PortAlreadyDefined, NilPort, BadProperty);
186 * Gets the provides port already added in the component.
188 * \param port the provides port pointer.
189 * \param provides_port_name the name of the port.
191 virtual void get_port(provides_port *& port,
192 const char* provides_port_name)
193 throw (PortNotDefined, PortNotConnected);
196 * Gets the uses port already added in the component.
198 * \param port the uses port pointer.
199 * \param uses_port_name the name of the port.
201 virtual void get_port(uses_port *& port,
202 const char* uses_port_name)
203 throw (PortNotDefined, PortNotConnected);
206 * Gets the list of the ports of a service.
207 * If servicename is not set, all the ports of the component are
210 * \param port_names the ports's list.
211 * \param servicename service's name.
213 virtual void get_uses_port_names(std::vector<std::string> & port_names,
214 const std::string servicename="") const;
217 * Gets a port already added in the component.
219 * \param port_name the name of the port.
220 * \return a port's pointer.
222 template <typename SpecificPortType >
223 SpecificPortType * get_port( const char * port_name)
224 throw (PortNotDefined, PortNotConnected, BadCast, UnexpectedState);
227 * \see DSC_Callbacks::provides_port_changed
229 virtual void provides_port_changed(const char* provides_port_name,
231 const Engines::DSC::Message message);
234 * \see DSC_Callbacks::uses_port_changed
236 virtual void uses_port_changed(const char* uses_port_name,
237 Engines::DSC::uses_port * new_uses_port,
238 const Engines::DSC::Message message);
242 * Add a factory the component. If the factory_name is already
243 * used, the new library is not added.
245 * \param factory_name name of the factory (used by Superv_Component_i::create_provides_data_port
246 * and Superv_Component_i::create_uses_data_port)
247 * \param factory_ptr factory pointer (destroyed by the component)
249 static void register_factory(const std::string & factory_name,
250 port_factory * factory_ptr);
253 * Get a factory from the component.
255 * \param factory_name name of the factory.
256 * \return factory pointer, NULL if the factory doesn't exist.
258 virtual port_factory * get_factory(const std::string & factory_name);
262 static long dscTimeOut;
263 static void setTimeOut();
264 void beginService(const char *serviceName);
267 // This method is implemented by default since it is a very specific usage.
268 // It also permits to not break compatibility with older components.
269 virtual CORBA::Boolean init_service_with_multiple(const char* service_name,
270 const Engines::Superv_Component::seq_multiple_param & params)
277 typedef std::map<std::string, port_factory*> factory_map_t;
278 static factory_map_t _factory_map;
280 /*-------------------------------------------------*/
281 // A Superv_Component port.
282 struct superv_port_t {
283 superv_port_t():u_ref(NULL),p_ref(NULL){};
286 if(u_ref)delete u_ref;
289 // do not delete CORBA servant : deactivate it and then call _remove_ref or delete
290 PortableServer::ServantBase* servant=dynamic_cast<PortableServer::ServantBase*>(p_ref);
293 PortableServer::POA_var poa =servant->_default_POA();
294 PortableServer::ObjectId_var oid = poa->servant_to_id(servant);
295 poa->deactivate_object(oid);
296 servant->_remove_ref();
302 // For provides ports.
303 provides_port * p_ref;
306 typedef std::map<std::string, superv_port_t *> superv_ports;
308 /*-------------------------------------------------*/
309 /*-------------------------------------------------*/
311 superv_ports my_superv_ports;
312 superv_ports::iterator my_superv_ports_it;
317 template < typename SpecificPortType > SpecificPortType *
318 Superv_Component_i::add_port(const char * port_fab_type,
319 const char * port_type,
320 const char * port_name)
321 throw (PortAlreadyDefined, BadFabType, BadType, BadCast, BadProperty)
323 assert(port_fab_type);
326 SpecificPortType * retPort;
329 std::cout << "---- Superv_Component_i::add_port : Mark 0 ---- " << port_name << "----" << std::endl;
332 std::string s_port_type(port_type);
333 if (s_port_type == "provides") {
334 provides_port * port = create_provides_data_port(port_fab_type);
335 add_port(port, port_name);
336 retPort = dynamic_cast<SpecificPortType *>(port);
337 if ( retPort == NULL ) { delete port;
338 throw BadCast( LOC("Can't cast to asked port type " ));
341 else if (s_port_type == "uses") {
342 uses_port * port = create_uses_data_port(port_fab_type);
343 add_port(port, port_name);
345 std::cout << "---- Superv_Component_i::add_port : Mark 1 ---- " << port << "----" << std::endl;
346 std::cout << "---- Superv_Component_i::add_port : Mark 1 ---- get_repository_id()" << port->get_repository_id() << std::endl;
348 retPort = dynamic_cast<SpecificPortType *>(port);
350 std::cout << "---- Superv_Component_i::add_port : Mark 2 ---- " << retPort << "----" << std::endl;
352 if ( retPort == NULL ) { delete port;
353 throw BadCast( LOC("Can't cast to asked port type " ));
357 throw BadType(LOC(OSS()<< "port_type must be either 'provides' either 'uses' not "
364 template <typename SpecificPortType > SpecificPortType *
365 Superv_Component_i::get_port( const char * port_name)
366 throw (PortNotDefined, PortNotConnected, BadCast, UnexpectedState)
370 SpecificPortType * retPort;
373 my_superv_ports_it = my_superv_ports.find(port_name);
374 if (my_superv_ports_it == my_superv_ports.end())
376 throw PortNotDefined( LOC(OSS()<< "Port " << port_name <<" does not exist"));
379 superv_port_t * superv_port = my_superv_ports[port_name];
381 if ( superv_port->p_ref != NULL ) {
382 port = superv_port->p_ref;
383 Ports::Port_var portref=Engines_DSC_interface::get_provides_port(port_name, false);
385 else if ( superv_port->u_ref != NULL ) {
386 port = superv_port->u_ref;
387 Engines::DSC::uses_port * portseq=Engines_DSC_i::get_uses_port(port_name);
390 throw UnexpectedState( LOC(OSS()<< "Internal Error superv_port struct is inconsistent "));
393 } catch (const Engines::DSC::PortNotDefined&) {
394 throw PortNotDefined( LOC(OSS()<< "port "
395 << port_name <<" does not exist."));
396 } catch (const Engines::DSC::PortNotConnected&) {
397 throw PortNotConnected( LOC(OSS()<< "port " << port_name
398 << " is not connected."));
401 retPort = dynamic_cast<SpecificPortType *>(port);
402 if ( retPort == NULL ) {
403 throw BadCast( LOC("Can't cast to required port type " ));