Feature #94
openProvide a standard "genom_set_port()" service to set an input port value
Description
Currently, the "connect_port()" service allows to connect an input port to an output port. This is sufficient when there exist such a compatible output port.
However, one may wish to set an input port directly from a client (matlab, prs, tcl) either for debugging or because the client is able to provide useful data for this port. Consider for instance the (real) use case where a simulink block wishes to feed a genom controller.
There are several possibilities for implementing this:
1. manually define an ad-hoc service (function) for this, in the relevant components. No change in genom required.
2. let all the clients (matlab, prs, tcl as well as the future ones) implement this, by adding a possibility to create (output) ports in the clients and then invoke "connect_port()" to connect the relevant components to those ports. Requires changes in the C client interface, as well as patching all existing clients.
3. implement a standard "genom_set_port()" function in the genom interface. All clients are already able to handle this properly, as the new function would appear as a standard genom service. This merely requires augmenting the stardard genom interface. One issue is that this cannot be written in in a standard .gen file, as this typically requires knowing the port(s) dataype(s) so that one can define e.g "function genom_set_port_foo(in ::foo::type data);" to set port "foo" to the data of type "foo::type". So this interface would have to be generated/parsed as dynamic string in the template parser. This is doable, although less "clean" than just having the current genom.gen file.
If we want to implement this feature, I prefer the 3rd approach, as this is the less invasive change (no client protocol update, transparent to existing clients). While here, we could also provide more self-descriptive port connection services, e.g. "genom_connect_port_foo(in string remote)" instead of "genom_connect_port(in string local, in string remote)".
If we consider this change is not useful, then the 1st approach is better.
What do you think?
Updated by Arnaud Degroote almost 9 years ago
- File signature.asc added
On 07/Dec - 17:16, Anthony Mallet wrote:
Issue #94 has been reported by Anthony Mallet.
----------------------------------------
Feature #94: Provide a standard "genom_set_port()" service to set an input port value
https://git.openrobots.org/issues/94
- Author: Anthony Mallet
- Status: New
- Priority: Normal
- Assignee: Anthony Mallet
- Category:
- Target version:
----------------------------------------
Currently, the "connect_port()" service allows to connect an input
port to an output port. This is sufficient when there exist such a
compatible output port.However, one may wish to set an input port directly from a client
(matlab, prs, tcl) either for debugging or because the client is able
to provide useful data for this port. Consider for instance the (real)
use case where a simulink block wishes to feed a genom controller.There are several possibilities for implementing this:
1. manually define an ad-hoc service (function) for this, in the
relevant components. No change in genom required.2. let all the clients (matlab, prs, tcl as well as the future ones)
implement this, by adding a possibility to create (output) ports in
the clients and then invoke "connect_port()" to connect the relevant
components to those ports. Requires changes in the C client interface,
as well as patching all existing clients.3. implement a standard "genom_set_port()" function in the genom
interface. All clients are already able to handle this properly, as
the new function would appear as a standard genom service. This merely
requires augmenting the stardard genom interface. One issue is that
this cannot be written in in a standard .gen file, as this typically
requires knowing the port(s) dataype(s) so that one can define e.g
"function genom_set_port_foo(in ::foo::type data);" to set port "foo"
to the data of type "foo::type". So this interface would have to be
generated/parsed as dynamic string in the template parser. This is
doable, although less "clean" than just having the current genom.gen
file.If we want to implement this feature, I prefer the 3rd approach, as
this is the less invasive change (no client protocol update,
transparent to existing clients). While here, we could also provide
more self-descriptive port connection services, e.g.
"genom_connect_port_foo(in string remote)" instead of
"genom_connect_port(in string local, in string remote)".If we consider this change is not useful, then the 1st approach is better.
It is definitively useful. I did a lot of implementation of 2 for
genom2, for unit-testing, simulation or to provide a dataflow from the
supervisor to some components. So, it is definitively a nice feature.
Option 2 looks "better" in my opinion (for simulation, unit-testing,
replay ...) as it is closer of the "real-implementation", and should be
a bit more efficient. Through, option 3 is a lot more rationale from a
point of view of the implementation (i.e. as you should have less
client-type than server one). One thing I like in Orocos is that, there
is no real-difference between client and server, client is just an
interactive (but standard anyway) component, so it is easy to create
port and connect to a "standard component".
Updated by Anthony Mallet almost 9 years ago
On Tuesday 8 Dec 2015, at 09:58, Arnaud Degroote wrote: | Option 2 looks "better" in my opinion (for simulation, unit-testing, | replay ...) as it is closer of the "real-implementation", and should | be a bit more efficient. Through, option 3 is a lot more rationale | from a point of view of the implementation (i.e. as you should have | less client-type than server one). One thing I like in Orocos is | that, there is no real-difference between client and server, client | is just an interactive (but standard anyway) component, so it is | easy to create port and connect to a "standard component".
Actually, both 2. and 3. could also be done simultaneously.
One question is: what cannot be done with either of the options?
For instance, what do have in mind with option 2 and "replay"?
Maybe we can also try to fill this table further:
--- Pros ----------------------------------------------------------
Option 2
- Closer to real implementation for debug/testing
Option 3
- Almost no new code required
- Usable in all clients directly
- Simple to use in client code, e.g.
foo::set_port_bar 42
--- Cons ----------------------------------------------------------
Options 2
- C client interface changed
- A lot more new code to handle port creation at the client level
- All clients to be updated
- Complex to use in client code, e.g.
foo::create_port_bar test
foo::connect_port_bar test
foo::test write 42
Option 3
- "genom" interface (in share/genom/templates/common/genom.gen) not
static anymore (e.g. set_port_bar() depends on the port name/type).
- requires component control task to update port value (actually its
the difference between a service and a port...).