Skip to content

Commit

Permalink
DS402: Simplify setup procedure. (#259)
Browse files Browse the repository at this point in the history
* p402: Do not switch any states during setup_402_state_machine().

Reading the PDO configuration is possible in OPERATIONAL or
PRE-OPERATIONAL states, so switching that is unnecessary.  The
application should be responsible to handle such transitions, and the
library function should be usable without disturbing the application
logic.

Changing the DS402 state machine to SWITCH ON DISABLED is also not
necessary.  The drive may be in whatever state from a previous usage,
and then the change to SWITCH ON DISABLED may even trigger an
exception because there is no way to reach it directly.  So this
transition should also be the application's responsibility.

* p402: Check NMT state before reading PDO configuration.

SDOs are allowed in all but the STOPPED state.  That would lead to a
timeout and an SdoCommunicationError exception.  Checking the NMT
state here raises an exception without a timeout involved.

* p402: Make reading the PDO configuration optional during setup.

If the application already configured the PDOs and called .save() on
the pdo.Maps object, there is no sense in reading everything back
again in the setup_pdos() method.  Provide an optional argument to
disable that behavior.

A call to subscribe to the PDOs from the network is added because that
side-effect of pdo.read() is necessary for the TPDO callback to work.

* p402: Allow skipping PDO upload from setup_402_state_machine().

Add an optional argument which is simply passed down to setup_pdos()
to choose whether reading the PDO configuration is necessary.

* Fix DS402 documentation to match the implementation.

Besides the changes regarding setup_402_state_machine(), there were
numerous errors where the documentation talks about nonexistent or
differently named attributes.

Also fix the description regaring what the method actually does.  It
won't configure the TPDO1 to contain the Statusword, but only check
the PDO configuration for Statusword and Controlword presence.

Co-authored-by: André Filipe Silva <[email protected]>
  • Loading branch information
acolomb and af-silva authored Aug 16, 2021
1 parent e5355f4 commit 7c5e4ce
Show file tree
Hide file tree
Showing 2 changed files with 33 additions and 22 deletions.
25 changes: 17 additions & 8 deletions canopen/profiles/p402.py
Original file line number Diff line number Diff line change
Expand Up @@ -212,22 +212,31 @@ def __init__(self, node_id, object_dictionary):
self.tpdo_pointers = {} # { index: pdo.Map instance }
self.rpdo_pointers = {} # { index: pdo.Map instance }

def setup_402_state_machine(self):
def setup_402_state_machine(self, read_pdos=True):
"""Configure the state machine by searching for a TPDO that has the StatusWord mapped.
:param bool read_pdos: Upload current PDO configuration from node.
:raises ValueError:
If the the node can't find a Statusword configured in any of the TPDOs.
"""
self.nmt.state = 'PRE-OPERATIONAL' # Why is this necessary?
self.setup_pdos()
self.setup_pdos(read_pdos)
self._check_controlword_configured()
self._check_statusword_configured()
self._check_op_mode_configured()
self.nmt.state = 'OPERATIONAL'
self.state = 'SWITCH ON DISABLED' # Why change state?

def setup_pdos(self):
self.pdo.read() # TPDO and RPDO configurations
def setup_pdos(self, upload=True):
"""Find the relevant PDO configuration to handle the state machine.
:param bool upload:
Retrieve up-to-date configuration via SDO. If False, the node's mappings must
already be configured in the object, matching the drive's settings.
:raises AssertionError:
When the node's NMT state disallows SDOs for reading the PDO configuration.
"""
if upload:
assert self.nmt.state in 'PRE-OPERATIONAL', 'OPERATIONAL'
self.pdo.read() # TPDO and RPDO configurations
else:
self.pdo.subscribe() # Get notified on reception, usually a side-effect of read()
self._init_tpdo_values()
self._init_rpdo_pointers()

Expand Down
30 changes: 16 additions & 14 deletions doc/profiles.rst
Original file line number Diff line number Diff line change
Expand Up @@ -34,10 +34,13 @@ The current status can be read from the device by reading the register
0x6041, which is called the "Statusword".
Changes in state can only be done in the 'OPERATIONAL' state of the NmtMaster

TPDO1 needs to be set up correctly. For this, run the the
`BaseNode402.setup_402_state_machine()` method. Note that this setup
routine will change only TPDO1 and automatically go to the 'OPERATIONAL' state
of the NmtMaster::
PDOs with the Controlword and Statusword mapped need to be set up correctly,
which is the default configuration of most DS402-compatible drives. To make
them accessible to the state machine implementation, run the the
`BaseNode402.setup_402_state_machine()` method. Note that this setup routine
will read the current PDO configuration by default, causing some SDO traffic.
That works only in the 'OPERATIONAL' or 'PRE-OPERATIONAL' states of the
:class:`NmtMaster`::

# run the setup routine for TPDO1 and it's callback
some_node.setup_402_state_machine()
Expand All @@ -50,21 +53,20 @@ Write Controlword and read Statusword::
# Read the state of the Statusword
some_node.sdo[0x6041].raw

During operation the state can change to states which cannot be commanded
by the Controlword, for example a 'FAULT' state.
Therefore the :class:`PowerStateMachine` class (in similarity to the :class:`NmtMaster`
class) automatically monitors state changes of the Statusword which is sent
by TPDO1. The available callback on thet TPDO1 will then extract the
information and mirror the state change in the :attr:`BaseNode402.powerstate_402`
attribute.
During operation the state can change to states which cannot be commanded by the
Controlword, for example a 'FAULT' state. Therefore the :class:`BaseNode402`
class (in similarity to :class:`NmtMaster`) automatically monitors state changes
of the Statusword which is sent by TPDO. The available callback on that TPDO
will then extract the information and mirror the state change in the
:attr:`BaseNode402.state` attribute.

Similar to the :class:`NmtMaster` class, the states of the :class:`BaseNode402`
class :attr:`._state` attribute can be read and set (command) by a string::
class :attr:`.state` attribute can be read and set (command) by a string::

# command a state (an SDO message will be called)
some_node.powerstate_402.state = 'SWITCHED ON'
some_node.state = 'SWITCHED ON'
# read the current state
some_node.powerstate_402.state = 'SWITCHED ON'
some_node.state = 'SWITCHED ON'

Available states:

Expand Down

0 comments on commit 7c5e4ce

Please sign in to comment.