master/fsm_master.c
changeset 907 570ae1c64465
parent 906 f95e3e33c0cf
child 908 386b908033be
equal deleted inserted replaced
906:f95e3e33c0cf 907:570ae1c64465
    29  *  standard) as the (only) precondition to have the right to use EtherCAT
    29  *  standard) as the (only) precondition to have the right to use EtherCAT
    30  *  Technology, IP and trade marks.
    30  *  Technology, IP and trade marks.
    31  *
    31  *
    32  *****************************************************************************/
    32  *****************************************************************************/
    33 
    33 
    34 /**
    34 /** \file
    35    \file
    35  * EtherCAT master state machine.
    36    EtherCAT finite state machines.
    36  */
    37 */
       
    38 
    37 
    39 /*****************************************************************************/
    38 /*****************************************************************************/
    40 
    39 
    41 #include "globals.h"
    40 #include "globals.h"
    42 #include "master.h"
    41 #include "master.h"
    50 
    49 
    51 /*****************************************************************************/
    50 /*****************************************************************************/
    52 
    51 
    53 void ec_fsm_master_state_start(ec_fsm_master_t *);
    52 void ec_fsm_master_state_start(ec_fsm_master_t *);
    54 void ec_fsm_master_state_broadcast(ec_fsm_master_t *);
    53 void ec_fsm_master_state_broadcast(ec_fsm_master_t *);
    55 void ec_fsm_master_state_read_states(ec_fsm_master_t *);
    54 void ec_fsm_master_state_read_state(ec_fsm_master_t *);
    56 void ec_fsm_master_state_acknowledge(ec_fsm_master_t *);
    55 void ec_fsm_master_state_acknowledge(ec_fsm_master_t *);
    57 void ec_fsm_master_state_configure_slave(ec_fsm_master_t *);
    56 void ec_fsm_master_state_configure_slave(ec_fsm_master_t *);
    58 void ec_fsm_master_state_clear_addresses(ec_fsm_master_t *);
    57 void ec_fsm_master_state_clear_addresses(ec_fsm_master_t *);
    59 void ec_fsm_master_state_scan_slaves(ec_fsm_master_t *);
    58 void ec_fsm_master_state_scan_slave(ec_fsm_master_t *);
    60 void ec_fsm_master_state_write_sii(ec_fsm_master_t *);
    59 void ec_fsm_master_state_write_sii(ec_fsm_master_t *);
    61 void ec_fsm_master_state_sdo_dictionary(ec_fsm_master_t *);
    60 void ec_fsm_master_state_sdo_dictionary(ec_fsm_master_t *);
    62 void ec_fsm_master_state_sdo_request(ec_fsm_master_t *);
    61 void ec_fsm_master_state_sdo_request(ec_fsm_master_t *);
    63 void ec_fsm_master_state_end(ec_fsm_master_t *);
    62 void ec_fsm_master_state_end(ec_fsm_master_t *);
    64 void ec_fsm_master_state_error(ec_fsm_master_t *);
    63 void ec_fsm_master_state_error(ec_fsm_master_t *);
    65 
    64 
    66 /*****************************************************************************/
    65 /*****************************************************************************/
    67 
    66 
    68 /**
    67 /** Constructor.
    69    Constructor.
    68  */
    70 */
    69 void ec_fsm_master_init(
    71 
    70         ec_fsm_master_t *fsm, /**< Master state machine. */
    72 void ec_fsm_master_init(ec_fsm_master_t *fsm, /**< master state machine */
    71         ec_master_t *master, /**< EtherCAT master. */
    73         ec_master_t *master, /**< EtherCAT master */
    72         ec_datagram_t *datagram /**< Datagram object to use. */
    74         ec_datagram_t *datagram /**< datagram object to use */
       
    75         )
    73         )
    76 {
    74 {
    77     fsm->master = master;
    75     fsm->master = master;
    78     fsm->datagram = datagram;
    76     fsm->datagram = datagram;
    79     fsm->state = ec_fsm_master_state_start;
    77     fsm->state = ec_fsm_master_state_start;
    92     ec_fsm_coe_map_init(&fsm->fsm_coe_map, &fsm->fsm_coe);
    90     ec_fsm_coe_map_init(&fsm->fsm_coe_map, &fsm->fsm_coe);
    93 }
    91 }
    94 
    92 
    95 /*****************************************************************************/
    93 /*****************************************************************************/
    96 
    94 
    97 /**
    95 /** Destructor.
    98    Destructor.
    96  */
    99 */
    97 void ec_fsm_master_clear(
   100 
    98         ec_fsm_master_t *fsm /**< Master state machine. */
   101 void ec_fsm_master_clear(ec_fsm_master_t *fsm /**< master state machine */)
    99         )
   102 {
   100 {
   103     // clear sub-state machines
   101     // clear sub-state machines
   104     ec_fsm_slave_config_clear(&fsm->fsm_slave_config);
   102     ec_fsm_slave_config_clear(&fsm->fsm_slave_config);
   105     ec_fsm_slave_scan_clear(&fsm->fsm_slave_scan);
   103     ec_fsm_slave_scan_clear(&fsm->fsm_slave_scan);
   106     ec_fsm_sii_clear(&fsm->fsm_sii);
   104     ec_fsm_sii_clear(&fsm->fsm_sii);
   109     ec_fsm_coe_map_clear(&fsm->fsm_coe_map);
   107     ec_fsm_coe_map_clear(&fsm->fsm_coe_map);
   110 }
   108 }
   111 
   109 
   112 /*****************************************************************************/
   110 /*****************************************************************************/
   113 
   111 
   114 /**
   112 /** Executes the current state of the state machine.
   115    Executes the current state of the state machine.
   113  *
   116    If the state machine's datagram is not sent or received yet, the execution
   114  * If the state machine's datagram is not sent or received yet, the execution
   117    of the state machine is delayed to the next cycle.
   115  * of the state machine is delayed to the next cycle.
   118    \return false, if state machine has terminated
   116  *
   119 */
   117  * \return false, if state machine has terminated
   120 
   118  */
   121 int ec_fsm_master_exec(ec_fsm_master_t *fsm /**< master state machine */)
   119 int ec_fsm_master_exec(
       
   120         ec_fsm_master_t *fsm /**< Master state machine. */
       
   121         )
   122 {
   122 {
   123     if (fsm->datagram->state == EC_DATAGRAM_SENT
   123     if (fsm->datagram->state == EC_DATAGRAM_SENT
   124         || fsm->datagram->state == EC_DATAGRAM_QUEUED) {
   124         || fsm->datagram->state == EC_DATAGRAM_QUEUED) {
   125         // datagram was not sent or received yet.
   125         // datagram was not sent or received yet.
   126         return ec_fsm_master_running(fsm);
   126         return ec_fsm_master_running(fsm);
   133 /*****************************************************************************/
   133 /*****************************************************************************/
   134 
   134 
   135 /**
   135 /**
   136  * \return false, if state machine has terminated
   136  * \return false, if state machine has terminated
   137  */
   137  */
   138 
       
   139 int ec_fsm_master_running(
   138 int ec_fsm_master_running(
   140         const ec_fsm_master_t *fsm /**< master state machine */
   139         const ec_fsm_master_t *fsm /**< Master state machine. */
   141         )
   140         )
   142 {
   141 {
   143     return fsm->state != ec_fsm_master_state_end
   142     return fsm->state != ec_fsm_master_state_end
   144         && fsm->state != ec_fsm_master_state_error;
   143         && fsm->state != ec_fsm_master_state_error;
   145 }
   144 }
   147 /*****************************************************************************/
   146 /*****************************************************************************/
   148 
   147 
   149 /**
   148 /**
   150  * \return true, if the state machine is in an idle phase
   149  * \return true, if the state machine is in an idle phase
   151  */
   150  */
   152 
       
   153 int ec_fsm_master_idle(
   151 int ec_fsm_master_idle(
   154         const ec_fsm_master_t *fsm /**< master state machine */
   152         const ec_fsm_master_t *fsm /**< Master state machine. */
   155         )
   153         )
   156 {
   154 {
   157     return fsm->idle;
   155     return fsm->idle;
   158 }
   156 }
   159 
   157 
   160 /******************************************************************************
   158 /******************************************************************************
   161  *  master state machine
   159  * Master state machine
   162  *****************************************************************************/
   160  *****************************************************************************/
   163 
   161 
   164 /**
   162 /** Master state: START.
   165    Master state: START.
   163  *
   166    Starts with getting slave count and slave states.
   164  * Starts with getting slave count and slave states.
   167 */
   165  */
   168 
   166 void ec_fsm_master_state_start(
   169 void ec_fsm_master_state_start(ec_fsm_master_t *fsm)
   167         ec_fsm_master_t *fsm /**< Master state machine. */
       
   168         )
   170 {
   169 {
   171     fsm->idle = 1;
   170     fsm->idle = 1;
   172     ec_datagram_brd(fsm->datagram, 0x0130, 2);
   171     ec_datagram_brd(fsm->datagram, 0x0130, 2);
   173     fsm->state = ec_fsm_master_state_broadcast;
   172     fsm->state = ec_fsm_master_state_broadcast;
   174 }
   173 }
   175 
   174 
   176 /*****************************************************************************/
   175 /*****************************************************************************/
   177 
   176 
   178 /**
   177 /** Master state: BROADCAST.
   179    Master state: BROADCAST.
   178  *
   180    Processes the broadcast read slave count and slaves states.
   179  * Processes the broadcast read slave count and slaves states.
   181 */
   180  */
   182 
   181 void ec_fsm_master_state_broadcast(
   183 void ec_fsm_master_state_broadcast(ec_fsm_master_t *fsm /**< master state machine */)
   182         ec_fsm_master_t *fsm /**< Master state machine. */
       
   183         )
   184 {
   184 {
   185     ec_datagram_t *datagram = fsm->datagram;
   185     ec_datagram_t *datagram = fsm->datagram;
   186     unsigned int i;
   186     unsigned int i;
   187     ec_slave_t *slave;
   187     ec_slave_t *slave;
   188     ec_master_t *master = fsm->master;
   188     ec_master_t *master = fsm->master;
   274     }
   274     }
   275 
   275 
   276     if (list_empty(&master->slaves)) {
   276     if (list_empty(&master->slaves)) {
   277         fsm->state = ec_fsm_master_state_end;
   277         fsm->state = ec_fsm_master_state_end;
   278     } else {
   278     } else {
   279         // fetch state from each slave
   279         // fetch state from first slave
   280         fsm->slave = list_entry(master->slaves.next, ec_slave_t, list);
   280         fsm->slave = list_entry(master->slaves.next, ec_slave_t, list);
   281         ec_datagram_fprd(fsm->datagram, fsm->slave->station_address, 0x0130, 2);
   281         ec_datagram_fprd(fsm->datagram, fsm->slave->station_address,
       
   282                 0x0130, 2);
   282         fsm->retries = EC_FSM_RETRIES;
   283         fsm->retries = EC_FSM_RETRIES;
   283         fsm->state = ec_fsm_master_state_read_states;
   284         fsm->state = ec_fsm_master_state_read_state;
   284     }
   285     }
   285 }
   286 }
   286 
   287 
   287 /*****************************************************************************/
   288 /*****************************************************************************/
   288 
   289 
   289 /**
   290 /** Check for pending SII write requests and process one.
   290  * Check for pending SII write requests and process one.
   291  * 
   291  * \return non-zero, if an SII write request is processed.
   292  * \return non-zero, if an SII write request is processed.
   292  */
   293  */
   293 
       
   294 int ec_fsm_master_action_process_sii(
   294 int ec_fsm_master_action_process_sii(
   295         ec_fsm_master_t *fsm /**< master state machine */
   295         ec_fsm_master_t *fsm /**< Master state machine. */
   296         )
   296         )
   297 {
   297 {
   298     ec_master_t *master = fsm->master;
   298     ec_master_t *master = fsm->master;
   299     ec_sii_write_request_t *request;
   299     ec_sii_write_request_t *request;
   300 
   300 
   328     return 0;
   328     return 0;
   329 }
   329 }
   330 
   330 
   331 /*****************************************************************************/
   331 /*****************************************************************************/
   332 
   332 
   333 /**
   333 /** Check for pending Sdo requests and process one.
   334  * Check for pending Sdo requests and process one.
   334  * 
   335  * \return non-zero, if an Sdo request is processed.
   335  * \return non-zero, if an Sdo request is processed.
   336  */
   336  */
   337 
       
   338 int ec_fsm_master_action_process_sdo(
   337 int ec_fsm_master_action_process_sdo(
   339         ec_fsm_master_t *fsm /**< master state machine */
   338         ec_fsm_master_t *fsm /**< Master state machine. */
   340         )
   339         )
   341 {
   340 {
   342     ec_master_t *master = fsm->master;
   341     ec_master_t *master = fsm->master;
   343     ec_master_sdo_request_t *request;
   342     ec_master_sdo_request_t *request;
   344     ec_sdo_request_t *req;
   343     ec_sdo_request_t *req;
   423     return 0;
   422     return 0;
   424 }
   423 }
   425 
   424 
   426 /*****************************************************************************/
   425 /*****************************************************************************/
   427 
   426 
   428 /**
   427 /** Master action: IDLE.
   429  * Check for slaves that are not configured and configure them.
   428  *
   430  */
   429  * Does secondary work.
   431 
   430  */
   432 int ec_fsm_master_action_configure(
   431 void ec_fsm_master_action_idle(
   433         ec_fsm_master_t *fsm /**< master state machine */
   432         ec_fsm_master_t *fsm /**< Master state machine. */
   434         )
   433         )
   435 {
   434 {
       
   435     ec_master_t *master = fsm->master;
   436     ec_slave_t *slave;
   436     ec_slave_t *slave;
   437     ec_master_t *master = fsm->master;
       
   438     char old_state[EC_STATE_STRING_SIZE], new_state[EC_STATE_STRING_SIZE];
       
   439 
       
   440     // check if any slaves are not in the state, they're supposed to be
       
   441     // FIXME do not check all slaves in every cycle...
       
   442     list_for_each_entry(slave, &master->slaves, list) {
       
   443         if (slave->error_flag
       
   444                 || slave->requested_state == EC_SLAVE_STATE_UNKNOWN
       
   445                 || (slave->current_state == slave->requested_state
       
   446                     && slave->self_configured)) continue;
       
   447 
       
   448         if (master->debug_level) {
       
   449             ec_state_string(slave->current_state, old_state);
       
   450             if (slave->current_state != slave->requested_state) {
       
   451                 ec_state_string(slave->requested_state, new_state);
       
   452                 EC_DBG("Changing state of slave %i (%s -> %s).\n",
       
   453                         slave->ring_position, old_state, new_state);
       
   454             }
       
   455             else if (!slave->self_configured) {
       
   456                 EC_DBG("Reconfiguring slave %i (%s).\n",
       
   457                         slave->ring_position, old_state);
       
   458             }
       
   459         }
       
   460 
       
   461         fsm->idle = 0;
       
   462         fsm->slave = slave;
       
   463         fsm->state = ec_fsm_master_state_configure_slave;
       
   464         ec_fsm_slave_config_start(&fsm->fsm_slave_config, slave);
       
   465         ec_fsm_slave_config_exec(&fsm->fsm_slave_config); // execute immediately
       
   466         return 1;
       
   467     }
       
   468 
       
   469     master->config_busy = 0;
       
   470     wake_up_interruptible(&master->config_queue);
       
   471     return 0;
       
   472 }
       
   473 
       
   474 /*****************************************************************************/
       
   475 
       
   476 /**
       
   477    Master action: PROC_STATES.
       
   478    Processes the slave states.
       
   479 */
       
   480 
       
   481 void ec_fsm_master_action_process_states(ec_fsm_master_t *fsm
       
   482                                          /**< master state machine */
       
   483                                          )
       
   484 {
       
   485     ec_master_t *master = fsm->master;
       
   486     ec_slave_t *slave;
       
   487 
       
   488     // Start slave configuration, if it is allowed.
       
   489     down(&master->config_sem);
       
   490     if (!master->allow_config) {
       
   491         up(&master->config_sem);
       
   492     } else {
       
   493         master->config_busy = 1;
       
   494         up(&master->config_sem);
       
   495 
       
   496         // check for pending slave configurations
       
   497         if (ec_fsm_master_action_configure(fsm))
       
   498             return;
       
   499     }
       
   500 
   437 
   501     // Check for pending Sdo requests
   438     // Check for pending Sdo requests
   502     if (ec_fsm_master_action_process_sdo(fsm))
   439     if (ec_fsm_master_action_process_sdo(fsm))
   503         return;
   440         return;
   504 
   441 
   536     fsm->state = ec_fsm_master_state_end;
   473     fsm->state = ec_fsm_master_state_end;
   537 }
   474 }
   538 
   475 
   539 /*****************************************************************************/
   476 /*****************************************************************************/
   540 
   477 
   541 /**
   478 /** Master action: Get state of next slave.
   542    Master action: Get state of next slave.
   479  */
   543 */
   480 void ec_fsm_master_action_next_slave_state(
   544 
   481         ec_fsm_master_t *fsm /**< Master state machine. */
   545 void ec_fsm_master_action_next_slave_state(ec_fsm_master_t *fsm
   482         )
   546                                            /**< master state machine */)
       
   547 {
   483 {
   548     ec_master_t *master = fsm->master;
   484     ec_master_t *master = fsm->master;
   549     ec_slave_t *slave = fsm->slave;
   485     ec_slave_t *slave = fsm->slave;
   550 
   486 
   551     // is there another slave to query?
   487     // is there another slave to query?
   552     if (slave->list.next != &master->slaves) {
   488     if (slave->list.next != &master->slaves) {
   553         // process next slave
   489         // fetch state from next slave
   554         fsm->idle = 1;
   490         fsm->idle = 1;
   555         fsm->slave = list_entry(slave->list.next, ec_slave_t, list);
   491         fsm->slave = list_entry(slave->list.next, ec_slave_t, list);
   556         ec_datagram_fprd(fsm->datagram, fsm->slave->station_address,
   492         ec_datagram_fprd(fsm->datagram, fsm->slave->station_address,
   557                          0x0130, 2);
   493                          0x0130, 2);
   558         fsm->retries = EC_FSM_RETRIES;
   494         fsm->retries = EC_FSM_RETRIES;
   559         fsm->state = ec_fsm_master_state_read_states;
   495         fsm->state = ec_fsm_master_state_read_state;
   560         return;
   496         return;
   561     }
   497     }
   562 
   498 
   563     // all slave states read
   499     // all slaves processed
   564     ec_fsm_master_action_process_states(fsm);
   500     ec_fsm_master_action_idle(fsm);
   565 }
   501 }
   566 
   502 
   567 /*****************************************************************************/
   503 /*****************************************************************************/
   568 
   504 
   569 /**
   505 /** Master action: Configure.
   570    Master state: READ STATES.
   506  */
   571    Fetches the AL- and online state of a slave.
   507 void ec_fsm_master_action_configure(
   572 */
   508         ec_fsm_master_t *fsm /**< Master state machine. */
   573 
   509         )
   574 void ec_fsm_master_state_read_states(ec_fsm_master_t *fsm /**< master state machine */)
   510 {
       
   511     ec_master_t *master = fsm->master;
       
   512     ec_slave_t *slave = fsm->slave;
       
   513 
       
   514     // Does the slave have to be configured?
       
   515     if (!slave->error_flag
       
   516             && (slave->current_state != slave->requested_state
       
   517                 || !slave->self_configured)) {
       
   518         // Start slave configuration, if it is allowed.
       
   519         down(&master->config_sem);
       
   520         if (!master->allow_config) {
       
   521             up(&master->config_sem);
       
   522         } else {
       
   523             master->config_busy = 1;
       
   524             up(&master->config_sem);
       
   525 
       
   526             if (master->debug_level) {
       
   527                 char old_state[EC_STATE_STRING_SIZE];
       
   528                 ec_state_string(slave->current_state, old_state);
       
   529                 if (slave->current_state != slave->requested_state) {
       
   530                     char new_state[EC_STATE_STRING_SIZE];
       
   531                     ec_state_string(slave->requested_state, new_state);
       
   532                     EC_DBG("Changing state of slave %u (%s -> %s).\n",
       
   533                             slave->ring_position, old_state, new_state);
       
   534                 } else if (!slave->self_configured) {
       
   535                     EC_DBG("Reconfiguring slave %u (%s).\n",
       
   536                             slave->ring_position, old_state);
       
   537                 }
       
   538             }
       
   539 
       
   540             fsm->idle = 0;
       
   541             fsm->state = ec_fsm_master_state_configure_slave;
       
   542             ec_fsm_slave_config_start(&fsm->fsm_slave_config, slave);
       
   543             fsm->state(fsm); // execute immediately
       
   544             return;
       
   545         }
       
   546     }
       
   547 
       
   548     // slave has error flag set; process next one
       
   549     ec_fsm_master_action_next_slave_state(fsm);
       
   550 }
       
   551 
       
   552 /*****************************************************************************/
       
   553 
       
   554 /** Master action: Acknowledge.
       
   555  */
       
   556 void ec_fsm_master_action_acknowledge(
       
   557         ec_fsm_master_t *fsm /**< Master state machine. */
       
   558         )
       
   559 {
       
   560     ec_slave_t *slave = fsm->slave;
       
   561 
       
   562     if (!slave->error_flag) {
       
   563         // Check, if new slave state has to be acknowledged
       
   564         if (slave->current_state & EC_SLAVE_STATE_ACK_ERR) {
       
   565             fsm->idle = 0;
       
   566             fsm->state = ec_fsm_master_state_acknowledge;
       
   567             ec_fsm_change_ack(&fsm->fsm_change, slave);
       
   568             fsm->state(fsm); // execute immediately
       
   569             return;
       
   570         }
       
   571 
       
   572         // No acknowlegde necessary; check for configuration
       
   573         ec_fsm_master_action_configure(fsm);
       
   574         return;
       
   575     }
       
   576 
       
   577     // slave has error flag set; process next one
       
   578     ec_fsm_master_action_next_slave_state(fsm);
       
   579 }
       
   580 
       
   581 /*****************************************************************************/
       
   582 
       
   583 /** Master state: READ STATE.
       
   584  *
       
   585  * Fetches the AL state of a slave.
       
   586  */
       
   587 void ec_fsm_master_state_read_state(
       
   588         ec_fsm_master_t *fsm /**< Master state machine. */
       
   589         )
   575 {
   590 {
   576     ec_slave_t *slave = fsm->slave;
   591     ec_slave_t *slave = fsm->slave;
   577     ec_datagram_t *datagram = fsm->datagram;
   592     ec_datagram_t *datagram = fsm->datagram;
   578 
   593 
   579     if (datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--)
   594     if (datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--)
   580         return;
   595         return;
   581 
   596 
   582     if (datagram->state != EC_DATAGRAM_RECEIVED) {
   597     if (datagram->state != EC_DATAGRAM_RECEIVED) {
   583         EC_ERR("Failed to receive AL state datagram for slave %i"
   598         EC_ERR("Failed to receive AL state datagram for slave %u"
   584                 " (datagram state %i)\n",
   599                 " (datagram state %i)\n",
   585                 slave->ring_position, datagram->state);
   600                 slave->ring_position, datagram->state);
   586         fsm->state = ec_fsm_master_state_error;
   601         fsm->state = ec_fsm_master_state_error;
   587         return;
   602         return;
   588     }
   603     }
   598         fsm->topology_change_pending = 1;
   613         fsm->topology_change_pending = 1;
   599         fsm->state = ec_fsm_master_state_error;
   614         fsm->state = ec_fsm_master_state_error;
   600         return;
   615         return;
   601     }
   616     }
   602 
   617 
   603     // a single slave responded
   618     // A single slave responded
   604     ec_slave_set_state(slave, EC_READ_U8(datagram->data)); // set app state first
   619     ec_slave_set_state(slave, EC_READ_U8(datagram->data));
   605 
   620     ec_fsm_master_action_acknowledge(fsm);
   606     // check, if new slave state has to be acknowledged
   621 }
   607     if (slave->current_state & EC_SLAVE_STATE_ACK_ERR && !slave->error_flag) {
   622 
   608         fsm->idle = 0;
   623 /*****************************************************************************/
   609         fsm->state = ec_fsm_master_state_acknowledge;
   624 
   610         ec_fsm_change_ack(&fsm->fsm_change, slave);
   625 /** Master state: ACKNOWLEDGE.
   611         ec_fsm_change_exec(&fsm->fsm_change);
   626  */
   612         return;
   627 void ec_fsm_master_state_acknowledge(
   613     }
   628         ec_fsm_master_t *fsm /**< Master state machine. */
   614 
   629         )
   615     ec_fsm_master_action_next_slave_state(fsm);
       
   616 }
       
   617 
       
   618 /*****************************************************************************/
       
   619 
       
   620 /**
       
   621    Master state: ACKNOWLEDGE
       
   622 */
       
   623 
       
   624 void ec_fsm_master_state_acknowledge(ec_fsm_master_t *fsm /**< master state machine */)
       
   625 {
   630 {
   626     ec_slave_t *slave = fsm->slave;
   631     ec_slave_t *slave = fsm->slave;
   627 
   632 
   628     if (ec_fsm_change_exec(&fsm->fsm_change)) return;
   633     if (ec_fsm_change_exec(&fsm->fsm_change))
       
   634         return;
   629 
   635 
   630     if (!ec_fsm_change_success(&fsm->fsm_change)) {
   636     if (!ec_fsm_change_success(&fsm->fsm_change)) {
   631         fsm->slave->error_flag = 1;
   637         fsm->slave->error_flag = 1;
   632         EC_ERR("Failed to acknowledge state change on slave %i.\n",
   638         EC_ERR("Failed to acknowledge state change on slave %u.\n",
   633                slave->ring_position);
   639                slave->ring_position);
   634         fsm->state = ec_fsm_master_state_error;
   640     }
   635         return;
   641 
   636     }
   642     ec_fsm_master_action_configure(fsm);
   637 
   643 }
   638     ec_fsm_master_action_next_slave_state(fsm);
   644 
   639 }
   645 /*****************************************************************************/
   640 
   646 
   641 /*****************************************************************************/
   647 /** Master state: CLEAR ADDRESSES.
   642 
   648  */
   643 /**
       
   644  * Master state: CLEAR ADDRESSES.
       
   645  */
       
   646 
       
   647 void ec_fsm_master_state_clear_addresses(
   649 void ec_fsm_master_state_clear_addresses(
   648         ec_fsm_master_t *fsm /**< master state machine */
   650         ec_fsm_master_t *fsm /**< Master state machine. */
   649         )
   651         )
   650 {
   652 {
   651     ec_master_t *master = fsm->master;
   653     ec_master_t *master = fsm->master;
   652     ec_datagram_t *datagram = fsm->datagram;
   654     ec_datagram_t *datagram = fsm->datagram;
   653 
   655 
   670 
   672 
   671     EC_INFO("Scanning bus.\n");
   673     EC_INFO("Scanning bus.\n");
   672 
   674 
   673     // begin scanning of slaves
   675     // begin scanning of slaves
   674     fsm->slave = list_entry(master->slaves.next, ec_slave_t, list);
   676     fsm->slave = list_entry(master->slaves.next, ec_slave_t, list);
   675     fsm->state = ec_fsm_master_state_scan_slaves;
   677     fsm->state = ec_fsm_master_state_scan_slave;
   676     ec_fsm_slave_scan_start(&fsm->fsm_slave_scan, fsm->slave);
   678     ec_fsm_slave_scan_start(&fsm->fsm_slave_scan, fsm->slave);
   677     ec_fsm_slave_scan_exec(&fsm->fsm_slave_scan); // execute immediately
   679     ec_fsm_slave_scan_exec(&fsm->fsm_slave_scan); // execute immediately
   678 }
   680 }
   679 
   681 
   680 /*****************************************************************************/
   682 /*****************************************************************************/
   681 
   683 
   682 /**
   684 /** Master state: SCAN SLAVE.
   683  * Master state: SCAN SLAVES.
   685  *
   684  * Executes the sub-statemachine for the scanning of a slave.
   686  * Executes the sub-statemachine for the scanning of a slave.
   685  */
   687  */
   686 
   688 void ec_fsm_master_state_scan_slave(
   687 void ec_fsm_master_state_scan_slaves(
   689         ec_fsm_master_t *fsm /**< Master state machine. */
   688         ec_fsm_master_t *fsm /**< master state machine */
       
   689         )
   690         )
   690 {
   691 {
   691     ec_master_t *master = fsm->master;
   692     ec_master_t *master = fsm->master;
   692     ec_slave_t *slave = fsm->slave;
   693     ec_slave_t *slave = fsm->slave;
   693 
   694 
   694     if (ec_fsm_slave_scan_exec(&fsm->fsm_slave_scan)) // execute slave state machine
   695     if (ec_fsm_slave_scan_exec(&fsm->fsm_slave_scan))
   695         return;
   696         return;
   696 
   697 
   697 #ifdef EC_EOE
   698 #ifdef EC_EOE
   698     if (slave->sii.mailbox_protocols & EC_MBOX_EOE) {
   699     if (slave->sii.mailbox_protocols & EC_MBOX_EOE) {
   699         // create EoE handler for this slave
   700         // create EoE handler for this slave
   736     fsm->state = ec_fsm_master_state_end;
   737     fsm->state = ec_fsm_master_state_end;
   737 }
   738 }
   738 
   739 
   739 /*****************************************************************************/
   740 /*****************************************************************************/
   740 
   741 
   741 /**
   742 /** Master state: CONFIGURE SLAVE.
   742    Master state: CONFIGURE SLAVES.
   743  *
   743    Starts configuring a slave.
   744  * Starts configuring a slave.
   744 */
   745  */
   745 
   746 void ec_fsm_master_state_configure_slave(
   746 void ec_fsm_master_state_configure_slave(ec_fsm_master_t *fsm
   747         ec_fsm_master_t *fsm /**< Master state machine. */
   747                                    /**< master state machine */
   748         )
   748                                    )
   749 {
   749 {
   750     ec_master_t *master = fsm->master;
   750     if (ec_fsm_slave_config_exec(&fsm->fsm_slave_config)) // execute slave's state machine
   751 
   751         return;
   752     if (ec_fsm_slave_config_exec(&fsm->fsm_slave_config))
       
   753         return;
       
   754 
       
   755     // configuration finished
       
   756     master->config_busy = 0;
       
   757     wake_up_interruptible(&master->config_queue);
   752 
   758 
   753     if (!ec_fsm_slave_config_success(&fsm->fsm_slave_config)) {
   759     if (!ec_fsm_slave_config_success(&fsm->fsm_slave_config)) {
   754         // TODO: mark slave_config as failed.
   760         // TODO: mark slave_config as failed.
   755     }
   761     }
   756 
   762 
   757     // configure next slave, if necessary
   763     fsm->idle = 1;
   758     if (ec_fsm_master_action_configure(fsm))
   764     ec_fsm_master_action_next_slave_state(fsm);
   759         return;
   765 }
   760 
   766 
   761     fsm->state = ec_fsm_master_state_end;
   767 /*****************************************************************************/
   762 }
   768 
   763 
   769 /** Master state: WRITE SII.
   764 /*****************************************************************************/
   770  */
   765 
       
   766 /**
       
   767    Master state: WRITE SII.
       
   768 */
       
   769 
       
   770 void ec_fsm_master_state_write_sii(
   771 void ec_fsm_master_state_write_sii(
   771         ec_fsm_master_t *fsm /**< master state machine */)
   772         ec_fsm_master_t *fsm /**< Master state machine. */
       
   773         )
   772 {
   774 {
   773     ec_master_t *master = fsm->master;
   775     ec_master_t *master = fsm->master;
   774     ec_sii_write_request_t *request = fsm->sii_request;
   776     ec_sii_write_request_t *request = fsm->sii_request;
   775     ec_slave_t *slave = request->slave;
   777     ec_slave_t *slave = request->slave;
   776 
   778 
   812     fsm->state = ec_fsm_master_state_end;
   814     fsm->state = ec_fsm_master_state_end;
   813 }
   815 }
   814 
   816 
   815 /*****************************************************************************/
   817 /*****************************************************************************/
   816 
   818 
   817 /**
   819 /** Master state: SDO DICTIONARY.
   818    Master state: SdoDICT.
   820  */
   819 */
       
   820 
       
   821 void ec_fsm_master_state_sdo_dictionary(
   821 void ec_fsm_master_state_sdo_dictionary(
   822         ec_fsm_master_t *fsm /**< master state machine */
   822         ec_fsm_master_t *fsm /**< Master state machine. */
   823         )
   823         )
   824 {
   824 {
   825     ec_slave_t *slave = fsm->slave;
   825     ec_slave_t *slave = fsm->slave;
   826     ec_master_t *master = fsm->master;
   826     ec_master_t *master = fsm->master;
   827 
   827 
   844     fsm->state = ec_fsm_master_state_end;
   844     fsm->state = ec_fsm_master_state_end;
   845 }
   845 }
   846 
   846 
   847 /*****************************************************************************/
   847 /*****************************************************************************/
   848 
   848 
   849 /**
   849 /** Master state: SDO REQUEST.
   850    Master state: SDO REQUEST.
   850  */
   851 */
   851 void ec_fsm_master_state_sdo_request(
   852 
   852         ec_fsm_master_t *fsm /**< Master state machine. */
   853 void ec_fsm_master_state_sdo_request(ec_fsm_master_t *fsm /**< master state machine */)
   853         )
   854 {
   854 {
   855     ec_master_t *master = fsm->master;
   855     ec_master_t *master = fsm->master;
   856     ec_sdo_request_t *request = fsm->sdo_request;
   856     ec_sdo_request_t *request = fsm->sdo_request;
   857 
   857 
   858     if (ec_fsm_coe_exec(&fsm->fsm_coe)) return;
   858     if (ec_fsm_coe_exec(&fsm->fsm_coe)) return;
   881     fsm->state = ec_fsm_master_state_end;
   881     fsm->state = ec_fsm_master_state_end;
   882 }
   882 }
   883 
   883 
   884 /*****************************************************************************/
   884 /*****************************************************************************/
   885 
   885 
   886 /**
   886 /** State: ERROR.
   887    State: ERROR.
   887  */
   888 */
       
   889 
       
   890 void ec_fsm_master_state_error(
   888 void ec_fsm_master_state_error(
   891         ec_fsm_master_t *fsm /**< master state machine */
   889         ec_fsm_master_t *fsm /**< Master state machine. */
   892         )
   890         )
   893 {
   891 {
   894     fsm->state = ec_fsm_master_state_start;
   892     fsm->state = ec_fsm_master_state_start;
   895 }
   893 }
   896 
   894 
   897 /*****************************************************************************/
   895 /*****************************************************************************/
   898 
   896 
   899 /**
   897 /** State: END.
   900    State: END.
   898  */
   901 */
   899 void ec_fsm_master_state_end(
   902 
   900         ec_fsm_master_t *fsm /**< Master state machine. */
   903 void ec_fsm_master_state_end(ec_fsm_master_t *fsm /**< master state machine */)
   901         )
   904 {
   902 {
   905     fsm->state = ec_fsm_master_state_start;
   903     fsm->state = ec_fsm_master_state_start;
   906 }
   904 }
   907 
   905 
   908 /*****************************************************************************/
   906 /*****************************************************************************/
   909