IgH EtherCAT Master  1.5.3
fsm_coe.c
Go to the documentation of this file.
1 /******************************************************************************
2  *
3  * $Id$
4  *
5  * Copyright (C) 2006-2008 Florian Pose, Ingenieurgemeinschaft IgH
6  *
7  * This file is part of the IgH EtherCAT Master.
8  *
9  * The IgH EtherCAT Master is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU General Public License version 2, as
11  * published by the Free Software Foundation.
12  *
13  * The IgH EtherCAT Master is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
16  * Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License along
19  * with the IgH EtherCAT Master; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
21  *
22  * ---
23  *
24  * The license mentioned above concerns the source code only. Using the
25  * EtherCAT technology and brand is only permitted in compliance with the
26  * industrial property and similar rights of Beckhoff Automation GmbH.
27  *
28  *****************************************************************************/
29 
34 /*****************************************************************************/
35 
36 #include "globals.h"
37 #include "master.h"
38 #include "mailbox.h"
39 #include "fsm_coe.h"
40 #include "slave_config.h"
41 
42 /*****************************************************************************/
43 
46 #define EC_FSM_COE_DICT_TIMEOUT 1000
47 
50 #define EC_COE_DOWN_REQ_HEADER_SIZE 10
51 
54 #define EC_COE_DOWN_SEG_REQ_HEADER_SIZE 3
55 
58 #define EC_COE_DOWN_SEG_MIN_DATA_SIZE 7
59 
62 #define DEBUG_RETRIES 0
63 
66 #define DEBUG_LONG 0
67 
68 /*****************************************************************************/
69 
80 
87 
95 
98 
99 /*****************************************************************************/
100 
108  {0x05030000, "Toggle bit not changed"},
109  {0x05040000, "SDO protocol timeout"},
110  {0x05040001, "Client/Server command specifier not valid or unknown"},
111  {0x05040005, "Out of memory"},
112  {0x06010000, "Unsupported access to an object"},
113  {0x06010001, "Attempt to read a write-only object"},
114  {0x06010002, "Attempt to write a read-only object"},
115  {0x06020000, "This object does not exist in the object directory"},
116  {0x06040041, "The object cannot be mapped into the PDO"},
117  {0x06040042, "The number and length of the objects to be mapped would"
118  " exceed the PDO length"},
119  {0x06040043, "General parameter incompatibility reason"},
120  {0x06040047, "Gerneral internal incompatibility in device"},
121  {0x06060000, "Access failure due to a hardware error"},
122  {0x06070010, "Data type does not match, length of service parameter does"
123  " not match"},
124  {0x06070012, "Data type does not match, length of service parameter too"
125  " high"},
126  {0x06070013, "Data type does not match, length of service parameter too"
127  " low"},
128  {0x06090011, "Subindex does not exist"},
129  {0x06090030, "Value range of parameter exceeded"},
130  {0x06090031, "Value of parameter written too high"},
131  {0x06090032, "Value of parameter written too low"},
132  {0x06090036, "Maximum value is less than minimum value"},
133  {0x08000000, "General error"},
134  {0x08000020, "Data cannot be transferred or stored to the application"},
135  {0x08000021, "Data cannot be transferred or stored to the application"
136  " because of local control"},
137  {0x08000022, "Data cannot be transferred or stored to the application"
138  " because of the present device state"},
139  {0x08000023, "Object dictionary dynamic generation fails or no object"
140  " dictionary is present"},
141  {}
142 };
143 
144 /*****************************************************************************/
145 
149  const ec_slave_t *slave,
150  uint32_t abort_code
151  )
152 {
153  const ec_code_msg_t *abort_msg;
154 
155  for (abort_msg = sdo_abort_messages; abort_msg->code; abort_msg++) {
156  if (abort_msg->code == abort_code) {
157  EC_SLAVE_ERR(slave, "SDO abort message 0x%08X: \"%s\".\n",
158  abort_msg->code, abort_msg->message);
159  return;
160  }
161  }
162 
163  EC_SLAVE_ERR(slave, "Unknown SDO abort code 0x%08X.\n", abort_code);
164 }
165 
166 /*****************************************************************************/
167 
171  ec_fsm_coe_t *fsm
172  )
173 {
174  fsm->state = NULL;
175  fsm->datagram = NULL;
176 }
177 
178 /*****************************************************************************/
179 
183  ec_fsm_coe_t *fsm
184  )
185 {
186 }
187 
188 /*****************************************************************************/
189 
193  ec_fsm_coe_t *fsm,
194  ec_slave_t *slave
195  )
196 {
197  fsm->slave = slave;
199 }
200 
201 /*****************************************************************************/
202 
206  ec_fsm_coe_t *fsm,
207  ec_slave_t *slave,
208  ec_sdo_request_t *request
209  )
210 {
211  fsm->slave = slave;
212  fsm->request = request;
213 
214  if (request->dir == EC_DIR_OUTPUT) {
216  }
217  else {
218  fsm->state = ec_fsm_coe_up_start;
219  }
220 }
221 
222 /*****************************************************************************/
223 
229  ec_fsm_coe_t *fsm,
230  ec_datagram_t *datagram
231  )
232 {
233  int datagram_used = 0;
234 
235  if (fsm->datagram &&
236  (fsm->datagram->state == EC_DATAGRAM_INIT ||
237  fsm->datagram->state == EC_DATAGRAM_QUEUED ||
238  fsm->datagram->state == EC_DATAGRAM_SENT)) {
239  // datagram not received yet
240  return datagram_used;
241  }
242 
243  fsm->state(fsm, datagram);
244 
245  datagram_used =
246  fsm->state != ec_fsm_coe_end && fsm->state != ec_fsm_coe_error;
247 
248  if (datagram_used) {
249  fsm->datagram = datagram;
250  } else {
251  fsm->datagram = NULL;
252  }
253 
254  return datagram_used;
255 }
256 
257 /*****************************************************************************/
258 
263  const ec_fsm_coe_t *fsm
264  )
265 {
266  return fsm->state == ec_fsm_coe_end;
267 }
268 
269 /*****************************************************************************/
270 
278  ec_fsm_coe_t *fsm,
279  const uint8_t *data,
280  size_t size
281  )
282 {
283  if (size < 2 || ((EC_READ_U16(data) >> 12) & 0x0F) != 0x01)
284  return 0;
285 
286  if (size < 10) {
287  EC_SLAVE_WARN(fsm->slave, "Received incomplete CoE Emergency"
288  " request:\n");
289  ec_print_data(data, size);
290  return 1;
291  }
292 
293  {
294  ec_slave_config_t *sc = fsm->slave->config;
295  if (sc) {
296  ec_coe_emerg_ring_push(&sc->emerg_ring, data + 2);
297  }
298  }
299 
300  EC_SLAVE_WARN(fsm->slave, "CoE Emergency Request received:\n"
301  "Error code 0x%04X, Error register 0x%02X, data:\n",
302  EC_READ_U16(data + 2), EC_READ_U8(data + 4));
303  ec_print_data(data + 5, 5);
304  return 1;
305 }
306 
307 /******************************************************************************
308  * CoE dictionary state machine
309  *****************************************************************************/
310 
316  ec_fsm_coe_t *fsm,
317  ec_datagram_t *datagram
318  )
319 {
320  ec_slave_t *slave = fsm->slave;
321  uint8_t *data = ec_slave_mbox_prepare_send(slave, datagram,
322  EC_MBOX_TYPE_COE, 8);
323  if (IS_ERR(data)) {
324  return PTR_ERR(data);
325  }
326 
327  EC_WRITE_U16(data, 0x8 << 12); // SDO information
328  EC_WRITE_U8 (data + 2, 0x01); // Get OD List Request
329  EC_WRITE_U8 (data + 3, 0x00);
330  EC_WRITE_U16(data + 4, 0x0000);
331  EC_WRITE_U16(data + 6, 0x0001); // deliver all SDOs!
332 
334  return 0;
335 }
336 
337 /*****************************************************************************/
338 
342  ec_fsm_coe_t *fsm,
343  ec_datagram_t *datagram
344  )
345 {
346  ec_slave_t *slave = fsm->slave;
347 
348  if (!(slave->sii.mailbox_protocols & EC_MBOX_COE)) {
349  EC_SLAVE_ERR(slave, "Slave does not support CoE!\n");
350  fsm->state = ec_fsm_coe_error;
351  return;
352  }
353 
354  if (slave->sii.has_general && !slave->sii.coe_details.enable_sdo_info) {
355  EC_SLAVE_ERR(slave, "Slave does not support"
356  " SDO information service!\n");
357  fsm->state = ec_fsm_coe_error;
358  return;
359  }
360 
361  fsm->retries = EC_FSM_RETRIES;
362 
363  if (ec_fsm_coe_prepare_dict(fsm, datagram)) {
364  fsm->state = ec_fsm_coe_error;
365  }
366 }
367 
368 /*****************************************************************************/
369 
374  ec_fsm_coe_t *fsm,
375  ec_datagram_t *datagram
376  )
377 {
378  ec_slave_t *slave = fsm->slave;
379 
380  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
381  if (ec_fsm_coe_prepare_dict(fsm, datagram)) {
382  fsm->state = ec_fsm_coe_error;
383  }
384  return;
385  }
386 
387  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
388  fsm->state = ec_fsm_coe_error;
389  EC_SLAVE_ERR(slave, "Failed to receive CoE dictionary"
390  " request datagram: ");
392  return;
393  }
394 
395  if (fsm->datagram->working_counter != 1) {
396  fsm->state = ec_fsm_coe_error;
397  EC_SLAVE_ERR(slave, "Reception of CoE dictionary request failed: ");
399  return;
400  }
401 
402  fsm->jiffies_start = fsm->datagram->jiffies_sent;
403 
404  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
405  fsm->retries = EC_FSM_RETRIES;
407 }
408 
409 /*****************************************************************************/
410 
414  ec_fsm_coe_t *fsm,
415  ec_datagram_t *datagram
416  )
417 {
418  ec_slave_t *slave = fsm->slave;
419 
420  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
421  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
422  return;
423  }
424 
425  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
426  fsm->state = ec_fsm_coe_error;
427  EC_SLAVE_ERR(slave, "Failed to receive CoE mailbox check datagram: ");
429  return;
430  }
431 
432  if (fsm->datagram->working_counter != 1) {
433  fsm->state = ec_fsm_coe_error;
434  EC_SLAVE_ERR(slave,"Reception of CoE mailbox check"
435  " datagram failed: ");
437  return;
438  }
439 
440  if (!ec_slave_mbox_check(fsm->datagram)) {
441  unsigned long diff_ms =
442  (fsm->datagram->jiffies_received - fsm->jiffies_start) *
443  1000 / HZ;
444  if (diff_ms >= EC_FSM_COE_DICT_TIMEOUT) {
445  fsm->state = ec_fsm_coe_error;
446  EC_SLAVE_ERR(slave, "Timeout while waiting for"
447  " SDO dictionary list response.\n");
448  return;
449  }
450 
451  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
452  fsm->retries = EC_FSM_RETRIES;
453  return;
454  }
455 
456  // Fetch response
457  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
458  fsm->retries = EC_FSM_RETRIES;
460 }
461 
462 /*****************************************************************************/
463 
469  ec_fsm_coe_t *fsm,
470  ec_datagram_t *datagram
471  )
472 {
473  ec_slave_t *slave = fsm->slave;
474  u8 *data = ec_slave_mbox_prepare_send(slave, datagram, EC_MBOX_TYPE_COE,
475  8);
476  if (IS_ERR(data)) {
477  return PTR_ERR(data);
478  }
479 
480  EC_WRITE_U16(data, 0x8 << 12); // SDO information
481  EC_WRITE_U8 (data + 2, 0x03); // Get object description request
482  EC_WRITE_U8 (data + 3, 0x00);
483  EC_WRITE_U16(data + 4, 0x0000);
484  EC_WRITE_U16(data + 6, fsm->sdo->index); // SDO index
485 
487  return 0;
488 }
489 
490 /*****************************************************************************/
491 
498  ec_fsm_coe_t *fsm,
499  ec_datagram_t *datagram
500  )
501 {
502  ec_slave_t *slave = fsm->slave;
503  uint8_t *data, mbox_prot;
504  size_t rec_size;
505  unsigned int sdo_count, i;
506  uint16_t sdo_index, fragments_left;
507  ec_sdo_t *sdo;
508  bool first_segment;
509  size_t index_list_offset;
510 
511  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
512  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
513  return;
514  }
515 
516  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
517  fsm->state = ec_fsm_coe_error;
518  EC_SLAVE_ERR(slave, "Failed to receive CoE dictionary"
519  " response datagram: ");
521  return;
522  }
523 
524  if (fsm->datagram->working_counter != 1) {
525  fsm->state = ec_fsm_coe_error;
526  EC_SLAVE_ERR(slave, "Reception of CoE dictionary response failed: ");
528  return;
529  }
530 
531  data = ec_slave_mbox_fetch(slave, fsm->datagram, &mbox_prot, &rec_size);
532  if (IS_ERR(data)) {
533  fsm->state = ec_fsm_coe_error;
534  return;
535  }
536 
537  if (mbox_prot != EC_MBOX_TYPE_COE) {
538  EC_SLAVE_ERR(slave, "Received mailbox protocol 0x%02X as response.\n",
539  mbox_prot);
540  fsm->state = ec_fsm_coe_error;
541  return;
542  }
543 
544  if (ec_fsm_coe_check_emergency(fsm, data, rec_size)) {
545  // check for CoE response again
546  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
547  fsm->retries = EC_FSM_RETRIES;
549  return;
550  }
551 
552  if (rec_size < 3) {
553  EC_SLAVE_ERR(slave, "Received corrupted SDO dictionary response"
554  " (size %zu).\n", rec_size);
555  fsm->state = ec_fsm_coe_error;
556  return;
557  }
558 
559  if (EC_READ_U16(data) >> 12 == 0x8 && // SDO information
560  (EC_READ_U8(data + 2) & 0x7F) == 0x07) { // error response
561  EC_SLAVE_ERR(slave, "SDO information error response!\n");
562  if (rec_size < 10) {
563  EC_SLAVE_ERR(slave, "Incomplete SDO information"
564  " error response:\n");
565  ec_print_data(data, rec_size);
566  } else {
567  ec_canopen_abort_msg(slave, EC_READ_U32(data + 6));
568  }
569  fsm->state = ec_fsm_coe_error;
570  return;
571  }
572 
573  if (EC_READ_U16(data) >> 12 != 0x8 || // SDO information
574  (EC_READ_U8 (data + 2) & 0x7F) != 0x02) { // Get OD List response
575  if (fsm->slave->master->debug_level) {
576  EC_SLAVE_DBG(slave, 1, "Invalid SDO list response!"
577  " Retrying...\n");
578  ec_print_data(data, rec_size);
579  }
580  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
581  fsm->retries = EC_FSM_RETRIES;
583  return;
584  }
585 
586  first_segment = list_empty(&slave->sdo_dictionary) ? true : false;
587  index_list_offset = first_segment ? 8 : 6;
588 
589  if (rec_size < index_list_offset || rec_size % 2) {
590  EC_SLAVE_ERR(slave, "Invalid data size %zu!\n", rec_size);
591  ec_print_data(data, rec_size);
592  fsm->state = ec_fsm_coe_error;
593  return;
594  }
595 
596  sdo_count = (rec_size - index_list_offset) / 2;
597 
598  for (i = 0; i < sdo_count; i++) {
599  sdo_index = EC_READ_U16(data + index_list_offset + i * 2);
600  if (!sdo_index) {
601  EC_SLAVE_DBG(slave, 1, "SDO dictionary contains index 0x0000.\n");
602  continue;
603  }
604 
605  if (!(sdo = (ec_sdo_t *) kmalloc(sizeof(ec_sdo_t), GFP_KERNEL))) {
606  EC_SLAVE_ERR(slave, "Failed to allocate memory for SDO!\n");
607  fsm->state = ec_fsm_coe_error;
608  return;
609  }
610 
611  ec_sdo_init(sdo, slave, sdo_index);
612  list_add_tail(&sdo->list, &slave->sdo_dictionary);
613  }
614 
615  fragments_left = EC_READ_U16(data + 4);
616  if (fragments_left) {
617  EC_SLAVE_DBG(slave, 1, "SDO list fragments left: %u\n",
618  fragments_left);
619  }
620 
621  if (EC_READ_U8(data + 2) & 0x80 || fragments_left) {
622  // more messages waiting. check again.
623  fsm->jiffies_start = fsm->datagram->jiffies_sent;
624  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
625  fsm->retries = EC_FSM_RETRIES;
627  return;
628  }
629 
630  if (list_empty(&slave->sdo_dictionary)) {
631  // no SDOs in dictionary. finished.
632  fsm->state = ec_fsm_coe_end; // success
633  return;
634  }
635 
636  // fetch SDO descriptions
637  fsm->sdo = list_entry(slave->sdo_dictionary.next, ec_sdo_t, list);
638 
639  fsm->retries = EC_FSM_RETRIES;
640  if (ec_fsm_coe_dict_prepare_desc(fsm, datagram)) {
641  fsm->state = ec_fsm_coe_error;
642  }
643 }
644 
645 /*****************************************************************************/
646 
653  ec_fsm_coe_t *fsm,
654  ec_datagram_t *datagram
655  )
656 {
657  ec_slave_t *slave = fsm->slave;
658 
659  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
660  if (ec_fsm_coe_dict_prepare_desc(fsm, datagram)) {
661  fsm->state = ec_fsm_coe_error;
662  }
663  return;
664  }
665 
666  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
667  fsm->state = ec_fsm_coe_error;
668  EC_SLAVE_ERR(slave, "Failed to receive CoE SDO"
669  " description request datagram: ");
671  return;
672  }
673 
674  if (fsm->datagram->working_counter != 1) {
675  fsm->state = ec_fsm_coe_error;
676  EC_SLAVE_ERR(slave, "Reception of CoE SDO description"
677  " request failed: ");
679  return;
680  }
681 
682  fsm->jiffies_start = fsm->datagram->jiffies_sent;
683 
684  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
685  fsm->retries = EC_FSM_RETRIES;
687 }
688 
689 /*****************************************************************************/
690 
696  ec_fsm_coe_t *fsm,
697  ec_datagram_t *datagram
698  )
699 {
700  ec_slave_t *slave = fsm->slave;
701 
702  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
703  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
704  return;
705  }
706 
707  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
708  fsm->state = ec_fsm_coe_error;
709  EC_SLAVE_ERR(slave, "Failed to receive CoE mailbox check datagram: ");
711  return;
712  }
713 
714  if (fsm->datagram->working_counter != 1) {
715  fsm->state = ec_fsm_coe_error;
716  EC_SLAVE_ERR(slave, "Reception of CoE mailbox check"
717  " datagram failed: ");
719  return;
720  }
721 
722  if (!ec_slave_mbox_check(fsm->datagram)) {
723  unsigned long diff_ms =
724  (fsm->datagram->jiffies_received - fsm->jiffies_start) *
725  1000 / HZ;
726  if (diff_ms >= EC_FSM_COE_DICT_TIMEOUT) {
727  fsm->state = ec_fsm_coe_error;
728  EC_SLAVE_ERR(slave, "Timeout while waiting for"
729  " SDO 0x%04x object description response.\n",
730  fsm->sdo->index);
731  return;
732  }
733 
734  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
735  fsm->retries = EC_FSM_RETRIES;
736  return;
737  }
738 
739  // Fetch response
740  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
741  fsm->retries = EC_FSM_RETRIES;
743 }
744 
745 /*****************************************************************************/
746 
752  ec_fsm_coe_t *fsm,
753  ec_datagram_t *datagram
754  )
755 {
756  ec_slave_t *slave = fsm->slave;
757  u8 *data = ec_slave_mbox_prepare_send(slave, datagram, EC_MBOX_TYPE_COE,
758  10);
759  if (IS_ERR(data)) {
760  return PTR_ERR(data);
761  }
762 
763  EC_WRITE_U16(data, 0x8 << 12); // SDO information
764  EC_WRITE_U8 (data + 2, 0x05); // Get entry description request
765  EC_WRITE_U8 (data + 3, 0x00);
766  EC_WRITE_U16(data + 4, 0x0000);
767  EC_WRITE_U16(data + 6, fsm->sdo->index); // SDO index
768  EC_WRITE_U8 (data + 8, fsm->subindex); // SDO subindex
769  EC_WRITE_U8 (data + 9, 0x01); // value info (access rights only)
770 
772  return 0;
773 }
774 
775 /*****************************************************************************/
776 
783  ec_fsm_coe_t *fsm,
784  ec_datagram_t *datagram
785  )
786 {
787  ec_slave_t *slave = fsm->slave;
788  ec_sdo_t *sdo = fsm->sdo;
789  uint8_t *data, mbox_prot;
790  size_t rec_size, name_size;
791 
792  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
793  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
794  return;
795  }
796 
797  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
798  fsm->state = ec_fsm_coe_error;
799  EC_SLAVE_ERR(slave, "Failed to receive CoE SDO description"
800  " response datagram: ");
802  return;
803  }
804 
805  if (fsm->datagram->working_counter != 1) {
806  fsm->state = ec_fsm_coe_error;
807  EC_SLAVE_ERR(slave, "Reception of CoE SDO description"
808  " response failed: ");
810  return;
811  }
812 
813  data = ec_slave_mbox_fetch(slave, fsm->datagram, &mbox_prot, &rec_size);
814  if (IS_ERR(data)) {
815  fsm->state = ec_fsm_coe_error;
816  return;
817  }
818 
819  if (mbox_prot != EC_MBOX_TYPE_COE) {
820  EC_SLAVE_ERR(slave, "Received mailbox protocol 0x%02X as response.\n",
821  mbox_prot);
822  fsm->state = ec_fsm_coe_error;
823  return;
824  }
825 
826  if (ec_fsm_coe_check_emergency(fsm, data, rec_size)) {
827  // check for CoE response again
828  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
829  fsm->retries = EC_FSM_RETRIES;
831  return;
832  }
833 
834  if (rec_size < 3) {
835  EC_SLAVE_ERR(slave, "Received corrupted SDO description response"
836  " (size %zu).\n", rec_size);
837  fsm->state = ec_fsm_coe_error;
838  return;
839  }
840 
841  if (EC_READ_U16(data) >> 12 == 0x8 && // SDO information
842  (EC_READ_U8 (data + 2) & 0x7F) == 0x07) { // error response
843  EC_SLAVE_ERR(slave, "SDO information error response while"
844  " fetching SDO 0x%04X!\n", sdo->index);
845  ec_canopen_abort_msg(slave, EC_READ_U32(data + 6));
846  fsm->state = ec_fsm_coe_error;
847  return;
848  }
849 
850  if (rec_size < 8) {
851  EC_SLAVE_ERR(slave, "Received corrupted SDO"
852  " description response (size %zu).\n", rec_size);
853  fsm->state = ec_fsm_coe_error;
854  return;
855  }
856 
857  if (EC_READ_U16(data) >> 12 != 0x8 || // SDO information
858  (EC_READ_U8 (data + 2) & 0x7F) != 0x04 || // Object desc. response
859  EC_READ_U16(data + 6) != sdo->index) { // SDO index
860  if (fsm->slave->master->debug_level) {
861  EC_SLAVE_DBG(slave, 1, "Invalid object description response while"
862  " fetching SDO 0x%04X!\n", sdo->index);
863  ec_print_data(data, rec_size);
864  }
865  // check for CoE response again
866  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
867  fsm->retries = EC_FSM_RETRIES;
869  return;
870  }
871 
872  if (rec_size < 12) {
873  EC_SLAVE_ERR(slave, "Invalid data size!\n");
874  ec_print_data(data, rec_size);
875  fsm->state = ec_fsm_coe_error;
876  return;
877  }
878 
879  sdo->max_subindex = EC_READ_U8(data + 10);
880  sdo->object_code = EC_READ_U8(data + 11);
881 
882  name_size = rec_size - 12;
883  if (name_size) {
884  if (!(sdo->name = kmalloc(name_size + 1, GFP_KERNEL))) {
885  EC_SLAVE_ERR(slave, "Failed to allocate SDO name!\n");
886  fsm->state = ec_fsm_coe_error;
887  return;
888  }
889 
890  memcpy(sdo->name, data + 12, name_size);
891  sdo->name[name_size] = 0;
892  }
893 
894  if (EC_READ_U8(data + 2) & 0x80) {
895  EC_SLAVE_ERR(slave, "Fragment follows (not implemented)!\n");
896  fsm->state = ec_fsm_coe_error;
897  return;
898  }
899 
900  // start fetching entries
901 
902  fsm->subindex = 0;
903  fsm->retries = EC_FSM_RETRIES;
904 
905  if (ec_fsm_coe_dict_prepare_entry(fsm, datagram)) {
906  fsm->state = ec_fsm_coe_error;
907  }
908 }
909 
910 /*****************************************************************************/
911 
918  ec_fsm_coe_t *fsm,
919  ec_datagram_t *datagram
920  )
921 {
922  ec_slave_t *slave = fsm->slave;
923 
924  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
925  if (ec_fsm_coe_dict_prepare_entry(fsm, datagram)) {
926  fsm->state = ec_fsm_coe_error;
927  }
928  return;
929  }
930 
931  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
932  fsm->state = ec_fsm_coe_error;
933  EC_SLAVE_ERR(slave, "Failed to receive CoE SDO entry"
934  " request datagram: ");
936  return;
937  }
938 
939  if (fsm->datagram->working_counter != 1) {
940  fsm->state = ec_fsm_coe_error;
941  EC_SLAVE_ERR(slave, "Reception of CoE SDO entry request failed: ");
943  return;
944  }
945 
946  fsm->jiffies_start = fsm->datagram->jiffies_sent;
947 
948  ec_slave_mbox_prepare_check(slave, datagram); // can not fail
949  fsm->retries = EC_FSM_RETRIES;
951 }
952 
953 /*****************************************************************************/
954 
960  ec_fsm_coe_t *fsm,
961  ec_datagram_t *datagram
962  )
963 {
964  ec_slave_t *slave = fsm->slave;
965 
966  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
967  ec_slave_mbox_prepare_check(slave, datagram); // can not fail
968  return;
969  }
970 
971  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
972  fsm->state = ec_fsm_coe_error;
973  EC_SLAVE_ERR(slave, "Failed to receive CoE mailbox check datagram: ");
975  return;
976  }
977 
978  if (fsm->datagram->working_counter != 1) {
979  fsm->state = ec_fsm_coe_error;
980  EC_SLAVE_ERR(slave, "Reception of CoE mailbox check"
981  " datagram failed: ");
983  return;
984  }
985 
986  if (!ec_slave_mbox_check(fsm->datagram)) {
987  unsigned long diff_ms =
988  (fsm->datagram->jiffies_received - fsm->jiffies_start) *
989  1000 / HZ;
990  if (diff_ms >= EC_FSM_COE_DICT_TIMEOUT) {
991  fsm->state = ec_fsm_coe_error;
992  EC_SLAVE_ERR(slave, "Timeout while waiting for"
993  " SDO entry 0x%04x:%x description response.\n",
994  fsm->sdo->index, fsm->subindex);
995  return;
996  }
997 
998  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
999  fsm->retries = EC_FSM_RETRIES;
1000  return;
1001  }
1002 
1003  // Fetch response
1004  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
1005  fsm->retries = EC_FSM_RETRIES;
1007 }
1008 
1009 /*****************************************************************************/
1010 
1017  ec_fsm_coe_t *fsm,
1018  ec_datagram_t *datagram
1019  )
1020 {
1021  ec_slave_t *slave = fsm->slave;
1022  ec_sdo_t *sdo = fsm->sdo;
1023  uint8_t *data, mbox_prot;
1024  size_t rec_size, data_size;
1025  ec_sdo_entry_t *entry;
1026  u16 word;
1027 
1028  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
1029  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
1030  return;
1031  }
1032 
1033  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
1034  fsm->state = ec_fsm_coe_error;
1035  EC_SLAVE_ERR(slave, "Failed to receive CoE SDO"
1036  " description response datagram: ");
1038  return;
1039  }
1040 
1041  if (fsm->datagram->working_counter != 1) {
1042  fsm->state = ec_fsm_coe_error;
1043  EC_SLAVE_ERR(slave, "Reception of CoE SDO description"
1044  " response failed: ");
1046  return;
1047  }
1048 
1049  data = ec_slave_mbox_fetch(slave, fsm->datagram, &mbox_prot, &rec_size);
1050  if (IS_ERR(data)) {
1051  fsm->state = ec_fsm_coe_error;
1052  return;
1053  }
1054 
1055  if (mbox_prot != EC_MBOX_TYPE_COE) {
1056  EC_SLAVE_ERR(slave, "Received mailbox protocol"
1057  " 0x%02X as response.\n", mbox_prot);
1058  fsm->state = ec_fsm_coe_error;
1059  return;
1060  }
1061 
1062  if (ec_fsm_coe_check_emergency(fsm, data, rec_size)) {
1063  // check for CoE response again
1064  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1065  fsm->retries = EC_FSM_RETRIES;
1067  return;
1068  }
1069 
1070  if (rec_size < 3) {
1071  EC_SLAVE_ERR(slave, "Received corrupted SDO entry"
1072  " description response (size %zu).\n", rec_size);
1073  fsm->state = ec_fsm_coe_error;
1074  return;
1075  }
1076 
1077  if (EC_READ_U16(data) >> 12 == 0x8 && // SDO information
1078  (EC_READ_U8 (data + 2) & 0x7F) == 0x07) { // error response
1079  EC_SLAVE_WARN(slave, "SDO information error response while"
1080  " fetching SDO entry 0x%04X:%02X!\n",
1081  sdo->index, fsm->subindex);
1082  ec_canopen_abort_msg(slave, EC_READ_U32(data + 6));
1083 
1084  /* There may be gaps in the subindices, so try to continue with next
1085  * subindex. */
1086 
1087  } else {
1088 
1089  if (rec_size < 9) {
1090  EC_SLAVE_ERR(slave, "Received corrupted SDO entry"
1091  " description response (size %zu).\n", rec_size);
1092  fsm->state = ec_fsm_coe_error;
1093  return;
1094  }
1095 
1096  if (EC_READ_U16(data) >> 12 != 0x8 || // SDO information
1097  (EC_READ_U8(data + 2) & 0x7F) != 0x06 || // Entry desc. response
1098  EC_READ_U16(data + 6) != sdo->index || // SDO index
1099  EC_READ_U8(data + 8) != fsm->subindex) { // SDO subindex
1100  if (fsm->slave->master->debug_level) {
1101  EC_SLAVE_DBG(slave, 1, "Invalid entry description response"
1102  " while fetching SDO entry 0x%04X:%02X!\n",
1103  sdo->index, fsm->subindex);
1104  ec_print_data(data, rec_size);
1105  }
1106  // check for CoE response again
1107  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1108  fsm->retries = EC_FSM_RETRIES;
1110  return;
1111  }
1112 
1113  if (rec_size < 16) {
1114  EC_SLAVE_ERR(slave, "Invalid data size %zu!\n", rec_size);
1115  ec_print_data(data, rec_size);
1116  fsm->state = ec_fsm_coe_error;
1117  return;
1118  }
1119 
1120  data_size = rec_size - 16;
1121 
1122  if (!(entry = (ec_sdo_entry_t *)
1123  kmalloc(sizeof(ec_sdo_entry_t), GFP_KERNEL))) {
1124  EC_SLAVE_ERR(slave, "Failed to allocate entry!\n");
1125  fsm->state = ec_fsm_coe_error;
1126  return;
1127  }
1128 
1129  ec_sdo_entry_init(entry, sdo, fsm->subindex);
1130  entry->data_type = EC_READ_U16(data + 10);
1131  entry->bit_length = EC_READ_U16(data + 12);
1132 
1133  // read access rights
1134  word = EC_READ_U16(data + 14);
1135  entry->read_access[EC_SDO_ENTRY_ACCESS_PREOP] = word & 0x0001;
1137  (word >> 1) & 0x0001;
1138  entry->read_access[EC_SDO_ENTRY_ACCESS_OP] = (word >> 2) & 0x0001;
1139  entry->write_access[EC_SDO_ENTRY_ACCESS_PREOP] = (word >> 3) & 0x0001;
1141  (word >> 4) & 0x0001;
1142  entry->write_access[EC_SDO_ENTRY_ACCESS_OP] = (word >> 5) & 0x0001;
1143 
1144  if (data_size) {
1145  uint8_t *desc;
1146  if (!(desc = kmalloc(data_size + 1, GFP_KERNEL))) {
1147  EC_SLAVE_ERR(slave, "Failed to allocate SDO entry name!\n");
1148  fsm->state = ec_fsm_coe_error;
1149  return;
1150  }
1151  memcpy(desc, data + 16, data_size);
1152  desc[data_size] = 0;
1153  entry->description = desc;
1154  }
1155 
1156  list_add_tail(&entry->list, &sdo->entries);
1157  }
1158 
1159  if (fsm->subindex < sdo->max_subindex) {
1160 
1161  fsm->subindex++;
1162  fsm->retries = EC_FSM_RETRIES;
1163 
1164  if (ec_fsm_coe_dict_prepare_entry(fsm, datagram)) {
1165  fsm->state = ec_fsm_coe_error;
1166  }
1167 
1168  return;
1169  }
1170 
1171  // another SDO description to fetch?
1172  if (fsm->sdo->list.next != &slave->sdo_dictionary) {
1173 
1174  fsm->sdo = list_entry(fsm->sdo->list.next, ec_sdo_t, list);
1175  fsm->retries = EC_FSM_RETRIES;
1176 
1177  if (ec_fsm_coe_dict_prepare_desc(fsm, datagram)) {
1178  fsm->state = ec_fsm_coe_error;
1179  }
1180 
1181  return;
1182  }
1183 
1184  fsm->state = ec_fsm_coe_end;
1185 }
1186 
1187 /******************************************************************************
1188  * CoE state machine
1189  *****************************************************************************/
1190 
1196  ec_fsm_coe_t *fsm,
1197  ec_datagram_t *datagram
1198  )
1199 {
1200  u8 *data;
1201  ec_slave_t *slave = fsm->slave;
1202  ec_sdo_request_t *request = fsm->request;
1203  uint8_t data_set_size;
1204 
1205  if (request->data_size > 0 && request->data_size <= 4) {
1206  // use expedited transfer mode for lengths between 1 and 4 bytes
1207  data = ec_slave_mbox_prepare_send(slave, datagram, EC_MBOX_TYPE_COE,
1209  if (IS_ERR(data)) {
1210  request->errno = PTR_ERR(data);
1211  return PTR_ERR(data);
1212  }
1213 
1214  fsm->remaining = 0;
1215 
1216  data_set_size = 4 - request->data_size;
1217 
1218  EC_WRITE_U16(data, 0x2 << 12); // SDO request
1219  EC_WRITE_U8 (data + 2, (0x3 // size specified, expedited
1220  | data_set_size << 2
1221  | ((request->complete_access ? 1 : 0) << 4)
1222  | 0x1 << 5)); // Download request
1223  EC_WRITE_U16(data + 3, request->index);
1224  EC_WRITE_U8 (data + 5,
1225  request->complete_access ? 0x00 : request->subindex);
1226  memcpy(data + 6, request->data, request->data_size);
1227  memset(data + 6 + request->data_size, 0x00, 4 - request->data_size);
1228 
1229  if (slave->master->debug_level) {
1230  EC_SLAVE_DBG(slave, 1, "Expedited download request:\n");
1232  }
1233  }
1234  else { // data_size < 1 or data_size > 4, use normal transfer type
1235  size_t data_size,
1236  max_data_size =
1238  required_data_size =
1240 
1241  if (max_data_size < required_data_size) {
1242  // segmenting needed
1243  data_size = max_data_size;
1244  } else {
1245  data_size = required_data_size;
1246  }
1247 
1248  data = ec_slave_mbox_prepare_send(slave, datagram, EC_MBOX_TYPE_COE,
1249  data_size);
1250  if (IS_ERR(data)) {
1251  request->errno = PTR_ERR(data);
1252  return PTR_ERR(data);
1253  }
1254 
1255  fsm->offset = 0;
1256  fsm->remaining = request->data_size;
1257 
1258  EC_WRITE_U16(data, 0x2 << 12); // SDO request
1259  EC_WRITE_U8(data + 2,
1260  0x1 // size indicator, normal
1261  | ((request->complete_access ? 1 : 0) << 4)
1262  | 0x1 << 5); // Download request
1263  EC_WRITE_U16(data + 3, request->index);
1264  EC_WRITE_U8 (data + 5,
1265  request->complete_access ? 0x00 : request->subindex);
1266  EC_WRITE_U32(data + 6, request->data_size);
1267 
1268  if (data_size > EC_COE_DOWN_REQ_HEADER_SIZE) {
1269  size_t segment_size = data_size - EC_COE_DOWN_REQ_HEADER_SIZE;
1270  memcpy(data + EC_COE_DOWN_REQ_HEADER_SIZE,
1271  request->data, segment_size);
1272  fsm->offset += segment_size;
1273  fsm->remaining -= segment_size;
1274  }
1275 
1276  if (slave->master->debug_level) {
1277  EC_SLAVE_DBG(slave, 1, "Normal download request:\n");
1278  ec_print_data(data, data_size);
1279  }
1280  }
1281 
1283  return 0;
1284 }
1285 
1286 /****************************************************************************/
1287 
1291  ec_fsm_coe_t *fsm,
1292  ec_datagram_t *datagram
1293  )
1294 {
1295  ec_slave_t *slave = fsm->slave;
1296  ec_sdo_request_t *request = fsm->request;
1297 
1298  if (fsm->slave->master->debug_level) {
1299  char subidxstr[10];
1300  if (request->complete_access) {
1301  subidxstr[0] = 0x00;
1302  } else {
1303  sprintf(subidxstr, ":%02X", request->subindex);
1304  }
1305  EC_SLAVE_DBG(slave, 1, "Downloading SDO 0x%04X%s.\n",
1306  request->index, subidxstr);
1307  ec_print_data(request->data, request->data_size);
1308  }
1309 
1310  if (!(slave->sii.mailbox_protocols & EC_MBOX_COE)) {
1311  EC_SLAVE_ERR(slave, "Slave does not support CoE!\n");
1312  request->errno = EPROTONOSUPPORT;
1313  fsm->state = ec_fsm_coe_error;
1314  return;
1315  }
1316 
1317  if (slave->configured_rx_mailbox_size <
1319  EC_SLAVE_ERR(slave, "Mailbox too small!\n");
1320  request->errno = EOVERFLOW;
1321  fsm->state = ec_fsm_coe_error;
1322  return;
1323  }
1324 
1325 
1326  fsm->request->jiffies_sent = jiffies;
1327  fsm->retries = EC_FSM_RETRIES;
1328 
1329  if (ec_fsm_coe_prepare_down_start(fsm, datagram)) {
1330  fsm->state = ec_fsm_coe_error;
1331  }
1332 }
1333 
1334 /*****************************************************************************/
1335 
1342  ec_fsm_coe_t *fsm,
1343  ec_datagram_t *datagram
1344  )
1345 {
1346  ec_slave_t *slave = fsm->slave;
1347  unsigned long diff_ms;
1348 
1349  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
1350  if (ec_fsm_coe_prepare_down_start(fsm, datagram)) {
1351  fsm->state = ec_fsm_coe_error;
1352  }
1353  return;
1354  }
1355 
1356  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
1357  fsm->request->errno = EIO;
1358  fsm->state = ec_fsm_coe_error;
1359  EC_SLAVE_ERR(slave, "Failed to receive CoE download"
1360  " request datagram: ");
1362  return;
1363  }
1364 
1365  diff_ms = (jiffies - fsm->request->jiffies_sent) * 1000 / HZ;
1366 
1367  if (fsm->datagram->working_counter != 1) {
1368  if (!fsm->datagram->working_counter) {
1369  if (diff_ms < fsm->request->response_timeout) {
1370 #if DEBUG_RETRIES
1371  EC_SLAVE_DBG(slave, 1, "Slave did not respond to SDO"
1372  " download request. Retrying after %lu ms...\n",
1373  diff_ms);
1374 #endif
1375  // no response; send request datagram again
1376  if (ec_fsm_coe_prepare_down_start(fsm, datagram)) {
1377  fsm->state = ec_fsm_coe_error;
1378  }
1379  return;
1380  }
1381  }
1382  fsm->request->errno = EIO;
1383  fsm->state = ec_fsm_coe_error;
1384  EC_SLAVE_ERR(slave, "Reception of CoE download request"
1385  " for SDO 0x%04x:%x failed with timeout after %lu ms: ",
1386  fsm->request->index, fsm->request->subindex, diff_ms);
1388  return;
1389  }
1390 
1391 #if DEBUG_LONG
1392  if (diff_ms > 200) {
1393  EC_SLAVE_WARN(slave, "SDO 0x%04x:%x download took %lu ms.\n",
1394  fsm->request->index, fsm->request->subindex, diff_ms);
1395  }
1396 #endif
1397 
1398  fsm->jiffies_start = fsm->datagram->jiffies_sent;
1399 
1400  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1401  fsm->retries = EC_FSM_RETRIES;
1403 }
1404 
1405 /*****************************************************************************/
1406 
1410  ec_fsm_coe_t *fsm,
1411  ec_datagram_t *datagram
1412  )
1413 {
1414  ec_slave_t *slave = fsm->slave;
1415 
1416  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
1417  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1418  return;
1419  }
1420 
1421  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
1422  fsm->request->errno = EIO;
1423  fsm->state = ec_fsm_coe_error;
1424  EC_SLAVE_ERR(slave, "Failed to receive CoE mailbox check"
1425  " datagram: ");
1427  return;
1428  }
1429 
1430  if (fsm->datagram->working_counter != 1) {
1431  fsm->request->errno = EIO;
1432  fsm->state = ec_fsm_coe_error;
1433  EC_SLAVE_ERR(slave, "Reception of CoE mailbox check"
1434  " datagram failed: ");
1436  return;
1437  }
1438 
1439  if (!ec_slave_mbox_check(fsm->datagram)) {
1440  unsigned long diff_ms =
1441  (fsm->datagram->jiffies_received - fsm->jiffies_start) *
1442  1000 / HZ;
1443  if (diff_ms >= fsm->request->response_timeout) {
1444  fsm->request->errno = EIO;
1445  fsm->state = ec_fsm_coe_error;
1446  EC_SLAVE_ERR(slave, "Timeout after %lu ms while waiting"
1447  " for SDO 0x%04x:%x download response.\n", diff_ms,
1448  fsm->request->index, fsm->request->subindex);
1449  return;
1450  }
1451 
1452  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1453  fsm->retries = EC_FSM_RETRIES;
1454  return;
1455  }
1456 
1457  // Fetch response
1458  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
1459  fsm->retries = EC_FSM_RETRIES;
1461 }
1462 
1463 /*****************************************************************************/
1464 
1468  ec_fsm_coe_t *fsm,
1469  ec_datagram_t *datagram
1470  )
1471 {
1472  ec_slave_t *slave = fsm->slave;
1473  ec_sdo_request_t *request = fsm->request;
1474  size_t max_segment_size =
1478  size_t data_size;
1479  uint8_t last_segment, seg_data_size, *data;
1480 
1481  if (fsm->remaining > max_segment_size) {
1482  fsm->segment_size = max_segment_size;
1483  last_segment = 0;
1484  } else {
1485  fsm->segment_size = fsm->remaining;
1486  last_segment = 1;
1487  }
1488 
1490  seg_data_size = 0x00;
1491  data_size = EC_COE_DOWN_SEG_REQ_HEADER_SIZE + fsm->segment_size;
1492  } else {
1493  seg_data_size = EC_COE_DOWN_SEG_MIN_DATA_SIZE - fsm->segment_size;
1496  }
1497 
1498  data = ec_slave_mbox_prepare_send(slave, datagram, EC_MBOX_TYPE_COE,
1499  data_size);
1500  if (IS_ERR(data)) {
1501  request->errno = PTR_ERR(data);
1502  fsm->state = ec_fsm_coe_error;
1503  return;
1504  }
1505 
1506  EC_WRITE_U16(data, 0x2 << 12); // SDO request
1507  EC_WRITE_U8(data + 2, (last_segment ? 1 : 0)
1508  | (seg_data_size << 1)
1509  | (fsm->toggle << 4)
1510  | (0x00 << 5)); // Download segment request
1511  memcpy(data + EC_COE_DOWN_SEG_REQ_HEADER_SIZE,
1512  request->data + fsm->offset, fsm->segment_size);
1514  memset(data + EC_COE_DOWN_SEG_REQ_HEADER_SIZE + fsm->segment_size,
1516  }
1517 
1518  if (slave->master->debug_level) {
1519  EC_SLAVE_DBG(slave, 1, "Download segment request:\n");
1520  ec_print_data(data, data_size);
1521  }
1522 
1524 }
1525 
1526 /*****************************************************************************/
1527 
1534  ec_fsm_coe_t *fsm,
1535  ec_datagram_t *datagram
1536  )
1537 {
1538  ec_slave_t *slave = fsm->slave;
1539  uint8_t *data, mbox_prot;
1540  size_t rec_size;
1541  ec_sdo_request_t *request = fsm->request;
1542 
1543  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
1544  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
1545  return;
1546  }
1547 
1548  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
1549  request->errno = EIO;
1550  fsm->state = ec_fsm_coe_error;
1551  EC_SLAVE_ERR(slave, "Failed to receive CoE download"
1552  " response datagram: ");
1554  return;
1555  }
1556 
1557  if (fsm->datagram->working_counter != 1) {
1558  request->errno = EIO;
1559  fsm->state = ec_fsm_coe_error;
1560  EC_SLAVE_ERR(slave, "Reception of CoE download response failed: ");
1562  return;
1563  }
1564 
1565  data = ec_slave_mbox_fetch(slave, fsm->datagram, &mbox_prot, &rec_size);
1566  if (IS_ERR(data)) {
1567  request->errno = PTR_ERR(data);
1568  fsm->state = ec_fsm_coe_error;
1569  return;
1570  }
1571 
1572  if (mbox_prot != EC_MBOX_TYPE_COE) {
1573  request->errno = EIO;
1574  fsm->state = ec_fsm_coe_error;
1575  EC_SLAVE_ERR(slave, "Received mailbox protocol 0x%02X as response.\n",
1576  mbox_prot);
1577  return;
1578  }
1579 
1580  if (ec_fsm_coe_check_emergency(fsm, data, rec_size)) {
1581  // check for CoE response again
1582  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1583  fsm->retries = EC_FSM_RETRIES;
1585  return;
1586  }
1587 
1588  if (slave->master->debug_level) {
1589  EC_SLAVE_DBG(slave, 1, "Download response:\n");
1590  ec_print_data(data, rec_size);
1591  }
1592 
1593  if (rec_size < 6) {
1594  request->errno = EIO;
1595  fsm->state = ec_fsm_coe_error;
1596  EC_SLAVE_ERR(slave, "Received data are too small (%zu bytes):\n",
1597  rec_size);
1598  ec_print_data(data, rec_size);
1599  return;
1600  }
1601 
1602  if (EC_READ_U16(data) >> 12 == 0x2 && // SDO request
1603  EC_READ_U8 (data + 2) >> 5 == 0x4) { // abort SDO transfer request
1604  char subidxstr[10];
1605  request->errno = EIO;
1606  fsm->state = ec_fsm_coe_error;
1607  if (request->complete_access) {
1608  subidxstr[0] = 0x00;
1609  } else {
1610  sprintf(subidxstr, ":%02X", request->subindex);
1611  }
1612  EC_SLAVE_ERR(slave, "SDO download 0x%04X%s (%zu bytes) aborted.\n",
1613  request->index, subidxstr, request->data_size);
1614  if (rec_size < 10) {
1615  EC_SLAVE_ERR(slave, "Incomplete abort command:\n");
1616  ec_print_data(data, rec_size);
1617  } else {
1618  fsm->request->abort_code = EC_READ_U32(data + 6);
1619  ec_canopen_abort_msg(slave, fsm->request->abort_code);
1620  }
1621  return;
1622  }
1623 
1624  if (EC_READ_U16(data) >> 12 != 0x3 || // SDO response
1625  EC_READ_U8 (data + 2) >> 5 != 0x3 || // Download response
1626  EC_READ_U16(data + 3) != request->index || // index
1627  EC_READ_U8 (data + 5) != request->subindex) { // subindex
1628  if (slave->master->debug_level) {
1629  EC_SLAVE_DBG(slave, 1, "Invalid SDO download response!"
1630  " Retrying...\n");
1631  ec_print_data(data, rec_size);
1632  }
1633  // check for CoE response again
1634  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1635  fsm->retries = EC_FSM_RETRIES;
1637  return;
1638  }
1639 
1640  if (fsm->remaining) { // more segments to download
1641  fsm->toggle = 0;
1643  } else {
1644  fsm->state = ec_fsm_coe_end; // success
1645  }
1646 }
1647 
1648 /*****************************************************************************/
1649 
1655  ec_fsm_coe_t *fsm,
1656  ec_datagram_t *datagram
1657  )
1658 {
1659  ec_slave_t *slave = fsm->slave;
1660 
1661  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--)
1662  return;
1663 
1664  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
1665  fsm->request->errno = EIO;
1666  fsm->state = ec_fsm_coe_error;
1667  EC_SLAVE_ERR(slave, "Failed to receive CoE mailbox check datagram: ");
1669  return;
1670  }
1671 
1672  if (fsm->datagram->working_counter != 1) {
1673  fsm->request->errno = EIO;
1674  fsm->state = ec_fsm_coe_error;
1675  EC_SLAVE_ERR(slave, "Reception of CoE mailbox segment check"
1676  " datagram failed: ");
1678  return;
1679  }
1680 
1681  if (!ec_slave_mbox_check(fsm->datagram)) {
1682  unsigned long diff_ms =
1683  (fsm->datagram->jiffies_received - fsm->jiffies_start) *
1684  1000 / HZ;
1685  if (diff_ms >= fsm->request->response_timeout) {
1686  fsm->request->errno = EIO;
1687  fsm->state = ec_fsm_coe_error;
1688  EC_SLAVE_ERR(slave, "Timeout while waiting for SDO download"
1689  " segment response.\n");
1690  return;
1691  }
1692 
1693  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1694  fsm->retries = EC_FSM_RETRIES;
1695  return;
1696  }
1697 
1698  // Fetch response
1699  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
1700  fsm->retries = EC_FSM_RETRIES;
1702 }
1703 
1704 /*****************************************************************************/
1705 
1712  ec_fsm_coe_t *fsm,
1713  ec_datagram_t *datagram
1714  )
1715 {
1716  ec_slave_t *slave = fsm->slave;
1717  uint8_t *data, mbox_prot;
1718  size_t rec_size;
1719  ec_sdo_request_t *request = fsm->request;
1720 
1721  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
1722  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
1723  return;
1724  }
1725 
1726  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
1727  request->errno = EIO;
1728  fsm->state = ec_fsm_coe_error;
1729  EC_SLAVE_ERR(slave, "Failed to receive CoE download response"
1730  " datagram: ");
1732  return;
1733  }
1734 
1735  if (fsm->datagram->working_counter != 1) {
1736  request->errno = EIO;
1737  fsm->state = ec_fsm_coe_error;
1738  EC_SLAVE_ERR(slave, "Reception of CoE download response failed: ");
1740  return;
1741  }
1742 
1743  data = ec_slave_mbox_fetch(slave, fsm->datagram, &mbox_prot, &rec_size);
1744  if (IS_ERR(data)) {
1745  request->errno = PTR_ERR(data);
1746  fsm->state = ec_fsm_coe_error;
1747  return;
1748  }
1749 
1750  if (mbox_prot != EC_MBOX_TYPE_COE) {
1751  request->errno = EIO;
1752  fsm->state = ec_fsm_coe_error;
1753  EC_SLAVE_ERR(slave, "Received mailbox protocol 0x%02X as response.\n",
1754  mbox_prot);
1755  return;
1756  }
1757 
1758  if (ec_fsm_coe_check_emergency(fsm, data, rec_size)) {
1759  // check for CoE response again
1760  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1761  fsm->retries = EC_FSM_RETRIES;
1763  return;
1764  }
1765 
1766  if (slave->master->debug_level) {
1767  EC_SLAVE_DBG(slave, 1, "Download response:\n");
1768  ec_print_data(data, rec_size);
1769  }
1770 
1771  if (rec_size < 6) {
1772  request->errno = EIO;
1773  fsm->state = ec_fsm_coe_error;
1774  EC_SLAVE_ERR(slave, "Received data are too small (%zu bytes):\n",
1775  rec_size);
1776  ec_print_data(data, rec_size);
1777  return;
1778  }
1779 
1780  if (EC_READ_U16(data) >> 12 == 0x2 && // SDO request
1781  EC_READ_U8 (data + 2) >> 5 == 0x4) { // abort SDO transfer request
1782  char subidxstr[10];
1783  request->errno = EIO;
1784  fsm->state = ec_fsm_coe_error;
1785  if (request->complete_access) {
1786  subidxstr[0] = 0x00;
1787  } else {
1788  sprintf(subidxstr, ":%02X", request->subindex);
1789  }
1790  EC_SLAVE_ERR(slave, "SDO download 0x%04X%s (%zu bytes) aborted.\n",
1791  request->index, subidxstr, request->data_size);
1792  if (rec_size < 10) {
1793  EC_SLAVE_ERR(slave, "Incomplete abort command:\n");
1794  ec_print_data(data, rec_size);
1795  } else {
1796  fsm->request->abort_code = EC_READ_U32(data + 6);
1797  ec_canopen_abort_msg(slave, fsm->request->abort_code);
1798  }
1799  return;
1800  }
1801 
1802  if (EC_READ_U16(data) >> 12 != 0x3 ||
1803  ((EC_READ_U8(data + 2) >> 5) != 0x01)) { // segment response
1804  if (slave->master->debug_level) {
1805  EC_SLAVE_DBG(slave, 1, "Invalid SDO download response!"
1806  " Retrying...\n");
1807  ec_print_data(data, rec_size);
1808  }
1809  // check for CoE response again
1810  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1811  fsm->retries = EC_FSM_RETRIES;
1813  return;
1814  }
1815 
1816  if (((EC_READ_U8(data + 2) >> 4) & 0x01) != fsm->toggle) {
1817  EC_SLAVE_ERR(slave, "Invalid toggle received during"
1818  " segmented download:\n");
1819  ec_print_data(data, rec_size);
1820  request->errno = EIO;
1821  fsm->state = ec_fsm_coe_error;
1822  return;
1823  }
1824 
1825  fsm->offset += fsm->segment_size;
1826  fsm->remaining -= fsm->segment_size;
1827 
1828  if (fsm->remaining) { // more segments to download
1829  fsm->toggle = !fsm->toggle;
1831  } else {
1832  fsm->state = ec_fsm_coe_end; // success
1833  }
1834 }
1835 
1836 /*****************************************************************************/
1837 
1843  ec_fsm_coe_t *fsm,
1844  ec_datagram_t *datagram
1845  )
1846 {
1847  ec_slave_t *slave = fsm->slave;
1848  ec_sdo_request_t *request = fsm->request;
1849  ec_master_t *master = slave->master;
1850 
1851  u8 *data = ec_slave_mbox_prepare_send(slave, datagram, EC_MBOX_TYPE_COE,
1852  10);
1853  if (IS_ERR(data)) {
1854  request->errno = PTR_ERR(data);
1855  return PTR_ERR(data);
1856  }
1857 
1858  EC_WRITE_U16(data, 0x2 << 12); // SDO request
1859  EC_WRITE_U8 (data + 2, 0x2 << 5); // initiate upload request
1860  EC_WRITE_U16(data + 3, request->index);
1861  EC_WRITE_U8 (data + 5, request->subindex);
1862  memset(data + 6, 0x00, 4);
1863 
1864  if (master->debug_level) {
1865  EC_SLAVE_DBG(slave, 1, "Upload request:\n");
1866  ec_print_data(data, 10);
1867  }
1868 
1870  return 0;
1871 }
1872 
1873 /*****************************************************************************/
1874 
1880  ec_fsm_coe_t *fsm,
1881  ec_datagram_t *datagram
1882  )
1883 {
1884  ec_slave_t *slave = fsm->slave;
1885  ec_sdo_request_t *request = fsm->request;
1886 
1887  EC_SLAVE_DBG(slave, 1, "Uploading SDO 0x%04X:%02X.\n",
1888  request->index, request->subindex);
1889 
1890  if (!(slave->sii.mailbox_protocols & EC_MBOX_COE)) {
1891  EC_SLAVE_ERR(slave, "Slave does not support CoE!\n");
1892  request->errno = EPROTONOSUPPORT;
1893  fsm->state = ec_fsm_coe_error;
1894  return;
1895  }
1896 
1897  fsm->retries = EC_FSM_RETRIES;
1898  fsm->request->jiffies_sent = jiffies;
1899 
1900  if (ec_fsm_coe_prepare_up(fsm, datagram)) {
1901  fsm->state = ec_fsm_coe_error;
1902  }
1903 }
1904 
1905 /*****************************************************************************/
1912  ec_fsm_coe_t *fsm,
1913  ec_datagram_t *datagram
1914  )
1915 {
1916  ec_slave_t *slave = fsm->slave;
1917  unsigned long diff_ms;
1918 
1919  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
1920  if (ec_fsm_coe_prepare_up(fsm, datagram)) {
1921  fsm->state = ec_fsm_coe_error;
1922  }
1923  return;
1924  }
1925 
1926  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
1927  fsm->request->errno = EIO;
1928  fsm->state = ec_fsm_coe_error;
1929  EC_SLAVE_ERR(slave, "Failed to receive CoE upload request: ");
1931  return;
1932  }
1933 
1934  diff_ms = (jiffies - fsm->request->jiffies_sent) * 1000 / HZ;
1935 
1936  if (fsm->datagram->working_counter != 1) {
1937  if (!fsm->datagram->working_counter) {
1938  if (diff_ms < fsm->request->response_timeout) {
1939 #if DEBUG_RETRIES
1940  EC_SLAVE_DBG(slave, 1, "Slave did not respond to"
1941  " SDO upload request. Retrying after %lu ms...\n",
1942  diff_ms);
1943 #endif
1944  // no response; send request datagram again
1945  if (ec_fsm_coe_prepare_up(fsm, datagram)) {
1946  fsm->state = ec_fsm_coe_error;
1947  }
1948  return;
1949  }
1950  }
1951  fsm->request->errno = EIO;
1952  fsm->state = ec_fsm_coe_error;
1953  EC_SLAVE_ERR(slave, "Reception of CoE upload request for"
1954  " SDO 0x%04x:%x failed with timeout after %lu ms: ",
1955  fsm->request->index, fsm->request->subindex, diff_ms);
1957  return;
1958  }
1959 
1960 #if DEBUG_LONG
1961  if (diff_ms > 200) {
1962  EC_SLAVE_WARN(slave, "SDO 0x%04x:%x upload took %lu ms.\n",
1963  fsm->request->index, fsm->request->subindex, diff_ms);
1964  }
1965 #endif
1966 
1967  fsm->jiffies_start = fsm->datagram->jiffies_sent;
1968 
1969  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1970  fsm->retries = EC_FSM_RETRIES;
1971  fsm->state = ec_fsm_coe_up_check;
1972 }
1973 
1974 /*****************************************************************************/
1975 
1981  ec_fsm_coe_t *fsm,
1982  ec_datagram_t *datagram
1983  )
1984 {
1985  ec_slave_t *slave = fsm->slave;
1986 
1987  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
1988  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
1989  return;
1990  }
1991 
1992  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
1993  fsm->request->errno = EIO;
1994  fsm->state = ec_fsm_coe_error;
1995  EC_SLAVE_ERR(slave, "Failed to receive CoE mailbox check datagram: ");
1997  return;
1998  }
1999 
2000  if (fsm->datagram->working_counter != 1) {
2001  fsm->request->errno = EIO;
2002  fsm->state = ec_fsm_coe_error;
2003  EC_SLAVE_ERR(slave, "Reception of CoE mailbox check"
2004  " datagram failed: ");
2006  return;
2007  }
2008 
2009  if (!ec_slave_mbox_check(fsm->datagram)) {
2010  unsigned long diff_ms =
2011  (fsm->datagram->jiffies_received - fsm->jiffies_start) *
2012  1000 / HZ;
2013  if (diff_ms >= fsm->request->response_timeout) {
2014  fsm->request->errno = EIO;
2015  fsm->state = ec_fsm_coe_error;
2016  EC_SLAVE_ERR(slave, "Timeout after %lu ms while waiting for"
2017  " SDO 0x%04x:%x upload response.\n", diff_ms,
2018  fsm->request->index, fsm->request->subindex);
2019  return;
2020  }
2021 
2022  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
2023  fsm->retries = EC_FSM_RETRIES;
2024  return;
2025  }
2026 
2027  // Fetch response
2028  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
2029  fsm->retries = EC_FSM_RETRIES;
2031 }
2032 
2033 /*****************************************************************************/
2034 
2038  ec_fsm_coe_t *fsm,
2039  ec_datagram_t *datagram
2040  )
2041 {
2042  uint8_t *data =
2043  ec_slave_mbox_prepare_send(fsm->slave, datagram, EC_MBOX_TYPE_COE,
2044  10);
2045  if (IS_ERR(data)) {
2046  fsm->request->errno = PTR_ERR(data);
2047  fsm->state = ec_fsm_coe_error;
2048  return;
2049  }
2050 
2051  EC_WRITE_U16(data, 0x2 << 12); // SDO request
2052  EC_WRITE_U8 (data + 2, (fsm->toggle << 4 // toggle
2053  | 0x3 << 5)); // upload segment request
2054  memset(data + 3, 0x00, 7);
2055 
2056  if (fsm->slave->master->debug_level) {
2057  EC_SLAVE_DBG(fsm->slave, 1, "Upload segment request:\n");
2058  ec_print_data(data, 10);
2059  }
2060 }
2061 
2062 /*****************************************************************************/
2063 
2070  ec_fsm_coe_t *fsm,
2071  ec_datagram_t *datagram
2072  )
2073 {
2074  ec_slave_t *slave = fsm->slave;
2075  ec_master_t *master = slave->master;
2076  uint16_t rec_index;
2077  uint8_t *data, mbox_prot, rec_subindex;
2078  size_t rec_size, data_size;
2079  ec_sdo_request_t *request = fsm->request;
2080  unsigned int expedited, size_specified;
2081  int ret;
2082 
2083  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
2084  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
2085  return;
2086  }
2087 
2088  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
2089  request->errno = EIO;
2090  fsm->state = ec_fsm_coe_error;
2091  EC_SLAVE_ERR(slave, "Failed to receive CoE upload response"
2092  " datagram: ");
2094  return;
2095  }
2096 
2097  if (fsm->datagram->working_counter != 1) {
2098  request->errno = EIO;
2099  fsm->state = ec_fsm_coe_error;
2100  EC_SLAVE_ERR(slave, "Reception of CoE upload response failed: ");
2102  return;
2103  }
2104 
2105  data = ec_slave_mbox_fetch(slave, fsm->datagram, &mbox_prot, &rec_size);
2106  if (IS_ERR(data)) {
2107  request->errno = PTR_ERR(data);
2108  fsm->state = ec_fsm_coe_error;
2109  return;
2110  }
2111 
2112  if (master->debug_level) {
2113  EC_SLAVE_DBG(slave, 1, "Upload response:\n");
2114  ec_print_data(data, rec_size);
2115  }
2116 
2117  if (mbox_prot != EC_MBOX_TYPE_COE) {
2118  request->errno = EIO;
2119  fsm->state = ec_fsm_coe_error;
2120  EC_SLAVE_WARN(slave, "Received mailbox protocol 0x%02X"
2121  " as response.\n", mbox_prot);
2122  return;
2123  }
2124 
2125  if (ec_fsm_coe_check_emergency(fsm, data, rec_size)) {
2126  // check for CoE response again
2127  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
2128  fsm->retries = EC_FSM_RETRIES;
2129  fsm->state = ec_fsm_coe_up_check;
2130  return;
2131  }
2132 
2133  if (rec_size < 6) {
2134  request->errno = EIO;
2135  fsm->state = ec_fsm_coe_error;
2136  EC_SLAVE_ERR(slave, "Received currupted SDO upload response"
2137  " (%zu bytes)!\n", rec_size);
2138  ec_print_data(data, rec_size);
2139  return;
2140  }
2141 
2142  if (EC_READ_U16(data) >> 12 == 0x2 && // SDO request
2143  EC_READ_U8(data + 2) >> 5 == 0x4) { // abort SDO transfer request
2144  EC_SLAVE_ERR(slave, "SDO upload 0x%04X:%02X aborted.\n",
2145  request->index, request->subindex);
2146  if (rec_size >= 10) {
2147  request->abort_code = EC_READ_U32(data + 6);
2148  ec_canopen_abort_msg(slave, request->abort_code);
2149  } else {
2150  EC_SLAVE_ERR(slave, "No abort message.\n");
2151  }
2152  request->errno = EIO;
2153  fsm->state = ec_fsm_coe_error;
2154  return;
2155  }
2156 
2157  if (EC_READ_U16(data) >> 12 != 0x3 || // SDO response
2158  EC_READ_U8(data + 2) >> 5 != 0x2) { // upload response
2159  EC_SLAVE_ERR(slave, "Received unknown response while"
2160  " uploading SDO 0x%04X:%02X.\n",
2161  request->index, request->subindex);
2162  ec_print_data(data, rec_size);
2163  request->errno = EIO;
2164  fsm->state = ec_fsm_coe_error;
2165  return;
2166  }
2167 
2168  rec_index = EC_READ_U16(data + 3);
2169  rec_subindex = EC_READ_U8(data + 5);
2170 
2171  if (rec_index != request->index || rec_subindex != request->subindex) {
2172  EC_SLAVE_ERR(slave, "Received upload response for wrong SDO"
2173  " (0x%04X:%02X, requested: 0x%04X:%02X).\n",
2174  rec_index, rec_subindex, request->index, request->subindex);
2175  ec_print_data(data, rec_size);
2176 
2177  // check for CoE response again
2178  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
2179  fsm->retries = EC_FSM_RETRIES;
2180  fsm->state = ec_fsm_coe_up_check;
2181  return;
2182  }
2183 
2184  // normal or expedited?
2185  expedited = EC_READ_U8(data + 2) & 0x02;
2186 
2187  if (expedited) {
2188  size_specified = EC_READ_U8(data + 2) & 0x01;
2189  if (size_specified) {
2190  fsm->complete_size = 4 - ((EC_READ_U8(data + 2) & 0x0C) >> 2);
2191  } else {
2192  fsm->complete_size = 4;
2193  }
2194 
2195  if (rec_size < 6 + fsm->complete_size) {
2196  request->errno = EIO;
2197  fsm->state = ec_fsm_coe_error;
2198  EC_SLAVE_ERR(slave, "Received corrupted SDO expedited upload"
2199  " response (only %zu bytes)!\n", rec_size);
2200  ec_print_data(data, rec_size);
2201  return;
2202  }
2203 
2204  ret = ec_sdo_request_copy_data(request, data + 6, fsm->complete_size);
2205  if (ret) {
2206  request->errno = -ret;
2207  fsm->state = ec_fsm_coe_error;
2208  return;
2209  }
2210  } else { // normal
2211  if (rec_size < 10) {
2212  request->errno = EIO;
2213  fsm->state = ec_fsm_coe_error;
2214  EC_SLAVE_ERR(slave, "Received currupted SDO normal upload"
2215  " response (only %zu bytes)!\n", rec_size);
2216  ec_print_data(data, rec_size);
2217  return;
2218  }
2219 
2220  data_size = rec_size - 10;
2221  fsm->complete_size = EC_READ_U32(data + 6);
2222 
2223  ret = ec_sdo_request_alloc(request, fsm->complete_size);
2224  if (ret) {
2225  request->errno = -ret;
2226  fsm->state = ec_fsm_coe_error;
2227  return;
2228  }
2229 
2230  ret = ec_sdo_request_copy_data(request, data + 10, data_size);
2231  if (ret) {
2232  request->errno = -ret;
2233  fsm->state = ec_fsm_coe_error;
2234  return;
2235  }
2236 
2237  fsm->toggle = 0;
2238 
2239  if (data_size < fsm->complete_size) {
2240  EC_SLAVE_DBG(slave, 1, "SDO data incomplete (%zu / %u)."
2241  " Segmenting...\n", data_size, fsm->complete_size);
2243  fsm->retries = EC_FSM_RETRIES;
2245  return;
2246  }
2247  }
2248 
2249  if (master->debug_level) {
2250  EC_SLAVE_DBG(slave, 1, "Uploaded data:\n");
2251  ec_print_data(request->data, request->data_size);
2252  }
2253 
2254  fsm->state = ec_fsm_coe_end; // success
2255 }
2256 
2257 /*****************************************************************************/
2258 
2265  ec_fsm_coe_t *fsm,
2266  ec_datagram_t *datagram
2267  )
2268 {
2269  ec_slave_t *slave = fsm->slave;
2270 
2271  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
2273  return;
2274  }
2275 
2276  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
2277  fsm->request->errno = EIO;
2278  fsm->state = ec_fsm_coe_error;
2279  EC_SLAVE_ERR(slave, "Failed to receive CoE upload segment"
2280  " request datagram: ");
2282  return;
2283  }
2284 
2285  if (fsm->datagram->working_counter != 1) {
2286  fsm->request->errno = EIO;
2287  fsm->state = ec_fsm_coe_error;
2288  EC_SLAVE_ERR(slave, "Reception of CoE upload segment"
2289  " request failed: ");
2291  return;
2292  }
2293 
2294  fsm->jiffies_start = fsm->datagram->jiffies_sent;
2295 
2296  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
2297  fsm->retries = EC_FSM_RETRIES;
2299 }
2300 
2301 /*****************************************************************************/
2302 
2308  ec_fsm_coe_t *fsm,
2309  ec_datagram_t *datagram
2310  )
2311 {
2312  ec_slave_t *slave = fsm->slave;
2313 
2314  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
2315  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
2316  return;
2317  }
2318 
2319  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
2320  fsm->request->errno = EIO;
2321  fsm->state = ec_fsm_coe_error;
2322  EC_SLAVE_ERR(slave, "Failed to receive CoE mailbox check"
2323  " datagram: ");
2325  return;
2326  }
2327 
2328  if (fsm->datagram->working_counter != 1) {
2329  fsm->request->errno = EIO;
2330  fsm->state = ec_fsm_coe_error;
2331  EC_SLAVE_ERR(slave, "Reception of CoE mailbox check datagram"
2332  " failed: ");
2334  return;
2335  }
2336 
2337  if (!ec_slave_mbox_check(fsm->datagram)) {
2338  unsigned long diff_ms =
2339  (fsm->datagram->jiffies_received - fsm->jiffies_start) *
2340  1000 / HZ;
2341  if (diff_ms >= fsm->request->response_timeout) {
2342  fsm->request->errno = EIO;
2343  fsm->state = ec_fsm_coe_error;
2344  EC_SLAVE_ERR(slave, "Timeout while waiting for SDO upload"
2345  " segment response.\n");
2346  return;
2347  }
2348 
2349  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
2350  fsm->retries = EC_FSM_RETRIES;
2351  return;
2352  }
2353 
2354  // Fetch response
2355  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
2356  fsm->retries = EC_FSM_RETRIES;
2358 }
2359 
2360 /*****************************************************************************/
2361 
2368  ec_fsm_coe_t *fsm,
2369  ec_datagram_t *datagram
2370  )
2371 {
2372  ec_slave_t *slave = fsm->slave;
2373  ec_master_t *master = slave->master;
2374  uint8_t *data, mbox_prot;
2375  size_t rec_size, data_size;
2376  ec_sdo_request_t *request = fsm->request;
2377  unsigned int last_segment;
2378 
2379  if (fsm->datagram->state == EC_DATAGRAM_TIMED_OUT && fsm->retries--) {
2380  ec_slave_mbox_prepare_fetch(slave, datagram); // can not fail.
2381  return;
2382  }
2383 
2384  if (fsm->datagram->state != EC_DATAGRAM_RECEIVED) {
2385  request->errno = EIO;
2386  fsm->state = ec_fsm_coe_error;
2387  EC_SLAVE_ERR(slave, "Failed to receive CoE upload segment"
2388  " response datagram: ");
2390  return;
2391  }
2392 
2393  if (fsm->datagram->working_counter != 1) {
2394  request->errno = EIO;
2395  fsm->state = ec_fsm_coe_error;
2396  EC_SLAVE_ERR(slave, "Reception of CoE upload segment"
2397  " response failed: ");
2399  return;
2400  }
2401 
2402  data = ec_slave_mbox_fetch(slave, fsm->datagram, &mbox_prot, &rec_size);
2403  if (IS_ERR(data)) {
2404  request->errno = PTR_ERR(data);
2405  fsm->state = ec_fsm_coe_error;
2406  return;
2407  }
2408 
2409  if (master->debug_level) {
2410  EC_SLAVE_DBG(slave, 1, "Upload segment response:\n");
2411  ec_print_data(data, rec_size);
2412  }
2413 
2414  if (mbox_prot != EC_MBOX_TYPE_COE) {
2415  EC_SLAVE_ERR(slave, "Received mailbox protocol 0x%02X as response.\n",
2416  mbox_prot);
2417  request->errno = EIO;
2418  fsm->state = ec_fsm_coe_error;
2419  return;
2420  }
2421 
2422  if (ec_fsm_coe_check_emergency(fsm, data, rec_size)) {
2423  // check for CoE response again
2424  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
2425  fsm->retries = EC_FSM_RETRIES;
2427  return;
2428  }
2429 
2430  if (rec_size < 10) {
2431  EC_SLAVE_ERR(slave, "Received currupted SDO upload"
2432  " segment response!\n");
2433  ec_print_data(data, rec_size);
2434  request->errno = EIO;
2435  fsm->state = ec_fsm_coe_error;
2436  return;
2437  }
2438 
2439  if (EC_READ_U16(data) >> 12 == 0x2 && // SDO request
2440  EC_READ_U8 (data + 2) >> 5 == 0x4) { // abort SDO transfer request
2441  EC_SLAVE_ERR(slave, "SDO upload 0x%04X:%02X aborted.\n",
2442  request->index, request->subindex);
2443  request->abort_code = EC_READ_U32(data + 6);
2444  ec_canopen_abort_msg(slave, request->abort_code);
2445  request->errno = EIO;
2446  fsm->state = ec_fsm_coe_error;
2447  return;
2448  }
2449 
2450  if (EC_READ_U16(data) >> 12 != 0x3 || // SDO response
2451  EC_READ_U8 (data + 2) >> 5 != 0x0) { // upload segment response
2452  if (fsm->slave->master->debug_level) {
2453  EC_SLAVE_DBG(slave, 1, "Invalid SDO upload segment response!\n");
2454  ec_print_data(data, rec_size);
2455  }
2456  // check for CoE response again
2457  ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
2458  fsm->retries = EC_FSM_RETRIES;
2460  return;
2461  }
2462 
2463  data_size = rec_size - 3; /* Header of segment upload is smaller than
2464  normal upload */
2465  if (rec_size == 10) {
2466  uint8_t seg_size = (EC_READ_U8(data + 2) & 0xE) >> 1;
2467  data_size -= seg_size;
2468  }
2469 
2470  if (request->data_size + data_size > fsm->complete_size) {
2471  EC_SLAVE_ERR(slave, "SDO upload 0x%04X:%02X failed: Fragment"
2472  " exceeding complete size!\n",
2473  request->index, request->subindex);
2474  request->errno = EOVERFLOW;
2475  fsm->state = ec_fsm_coe_error;
2476  return;
2477  }
2478 
2479  memcpy(request->data + request->data_size, data + 3, data_size);
2480  request->data_size += data_size;
2481 
2482  last_segment = EC_READ_U8(data + 2) & 0x01;
2483  if (!last_segment) {
2484  fsm->toggle = !fsm->toggle;
2486  fsm->retries = EC_FSM_RETRIES;
2488  return;
2489  }
2490 
2491  if (request->data_size != fsm->complete_size) {
2492  EC_SLAVE_WARN(slave, "SDO upload 0x%04X:%02X: Assembled data"
2493  " size (%zu) does not match complete size (%u)!\n",
2494  request->index, request->subindex,
2495  request->data_size, fsm->complete_size);
2496  }
2497 
2498  if (master->debug_level) {
2499  EC_SLAVE_DBG(slave, 1, "Uploaded data:\n");
2500  ec_print_data(request->data, request->data_size);
2501  }
2502 
2503  fsm->state = ec_fsm_coe_end; // success
2504 }
2505 
2506 /*****************************************************************************/
2507 
2513  ec_fsm_coe_t *fsm,
2514  ec_datagram_t *datagram
2515  )
2516 {
2517 }
2518 
2519 /*****************************************************************************/
2520 
2526  ec_fsm_coe_t *fsm,
2527  ec_datagram_t *datagram
2528  )
2529 {
2530 }
2531 
2532 /*****************************************************************************/
int ec_fsm_coe_prepare_down_start(ec_fsm_coe_t *fsm, ec_datagram_t *datagram)
Prepare a donwnload request.
Definition: fsm_coe.c:1195
#define EC_FSM_RETRIES
Number of state machine retries on datagram timeout.
Definition: globals.h:47
void ec_fsm_coe_up_seg_response(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: UP RESPONSE.
Definition: fsm_coe.c:2367
uint8_t * ec_slave_mbox_prepare_send(const ec_slave_t *slave, ec_datagram_t *datagram, uint8_t type, size_t size)
Prepares a mailbox-send datagram.
Definition: mailbox.c:51
unsigned long jiffies_sent
Jiffies, when the datagram was sent.
Definition: datagram.h:104
ec_sii_t sii
Extracted SII data.
Definition: slave.h:223
uint8_t * ec_slave_mbox_fetch(const ec_slave_t *slave, const ec_datagram_t *datagram, uint8_t *type, size_t *size)
Processes received mailbox data.
Definition: mailbox.c:165
int ec_fsm_coe_prepare_up(ec_fsm_coe_t *fsm, ec_datagram_t *datagram)
Prepare an upload request.
Definition: fsm_coe.c:1842
void ec_fsm_coe_up_start(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: UP START.
Definition: fsm_coe.c:1879
uint32_t offset
Data offset during segmented download.
Definition: fsm_coe.h:64
#define EC_SLAVE_DBG(slave, level, fmt, args...)
Convenience macro for printing slave-specific debug messages to syslog.
Definition: slave.h:106
CANopen SDO entry.
Definition: sdo_entry.h:54
void ec_fsm_coe_end(ec_fsm_coe_t *, ec_datagram_t *)
State: END.
Definition: fsm_coe.c:2525
size_t segment_size
Current segment size.
Definition: fsm_coe.h:66
void ec_fsm_coe_dict_response(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DICT RESPONSE.
Definition: fsm_coe.c:497
CANopen SDO request.
Definition: sdo_request.h:46
void ec_fsm_coe_error(ec_fsm_coe_t *, ec_datagram_t *)
State: ERROR.
Definition: fsm_coe.c:2512
void ec_fsm_coe_dict_entry_check(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DICT ENTRY CHECK.
Definition: fsm_coe.c:959
uint16_t bit_length
Data size in bit.
Definition: sdo_entry.h:59
uint32_t response_timeout
Maximum time in ms, the transfer is retried, if the slave does not respond.
Definition: sdo_request.h:56
int ec_slave_mbox_prepare_fetch(const ec_slave_t *slave, ec_datagram_t *datagram)
Prepares a datagram to fetch mailbox data.
Definition: mailbox.c:127
uint32_t code
Code.
Definition: globals.h:267
#define EC_SLAVE_WARN(slave, fmt, args...)
Convenience macro for printing slave-specific warnings to syslog.
Definition: slave.h:90
void ec_fsm_coe_dict_entry_response(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DICT ENTRY RESPONSE.
Definition: fsm_coe.c:1016
EtherCAT datagram.
Definition: datagram.h:87
ec_sii_coe_details_t coe_details
CoE detail flags.
Definition: slave.h:160
uint16_t index
SDO index.
Definition: sdo_request.h:48
void ec_fsm_coe_down_check(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DOWN CHECK.
Definition: fsm_coe.c:1409
#define EC_WRITE_U8(DATA, VAL)
Write an 8-bit unsigned value to EtherCAT data.
Definition: ecrt.h:2401
uint32_t abort_code
SDO request abort code.
Definition: sdo_request.h:66
void(* state)(ec_fsm_coe_t *, ec_datagram_t *)
CoE state function.
Definition: fsm_coe.h:56
void ec_fsm_coe_down_prepare_segment_request(ec_fsm_coe_t *fsm, ec_datagram_t *datagram)
Prepare a download segment request.
Definition: fsm_coe.c:1467
void ec_fsm_coe_up_seg_request(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: UP REQUEST.
Definition: fsm_coe.c:2264
uint16_t working_counter
Working counter.
Definition: datagram.h:99
struct list_head list
List item.
Definition: sdo.h:50
void ec_fsm_coe_down_seg_check(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DOWN SEG CHECK.
Definition: fsm_coe.c:1654
#define EC_COE_DOWN_SEG_MIN_DATA_SIZE
Minimum size of download segment.
Definition: fsm_coe.c:58
CANopen SDO.
Definition: sdo.h:49
uint16_t index
SDO index.
Definition: sdo.h:52
void ec_fsm_coe_up_seg_check(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: UP CHECK.
Definition: fsm_coe.c:2307
uint8_t * data
Pointer to SDO data.
Definition: sdo_request.h:50
int ec_fsm_coe_success(const ec_fsm_coe_t *fsm)
Returns, if the state machine terminated with success.
Definition: fsm_coe.c:262
#define EC_FSM_COE_DICT_TIMEOUT
Maximum time in ms to wait for responses when reading out the dictionary.
Definition: fsm_coe.c:46
Access rights in SAFEOP.
Definition: globals.h:182
Sent (still in the queue).
Definition: datagram.h:77
#define EC_COE_DOWN_SEG_REQ_HEADER_SIZE
CoE download segment request header size.
Definition: fsm_coe.c:54
int ec_fsm_coe_check_emergency(ec_fsm_coe_t *fsm, const uint8_t *data, size_t size)
Check if the received data are a CoE emergency request.
Definition: fsm_coe.c:277
struct list_head list
List item.
Definition: sdo_entry.h:55
void ec_fsm_coe_dict_entry_request(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DICT ENTRY REQUEST.
Definition: fsm_coe.c:917
const char * message
Message belonging to code.
Definition: globals.h:268
Access rights in PREOP.
Definition: globals.h:181
struct list_head sdo_dictionary
SDO dictionary list.
Definition: slave.h:225
Global definitions and macros.
void ec_fsm_coe_up_request(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: UP REQUEST.
Definition: fsm_coe.c:1911
ec_direction_t dir
Direction.
Definition: sdo_request.h:58
EtherCAT master structure.
uint8_t object_code
Object code.
Definition: sdo.h:53
ec_sdo_t * sdo
current SDO
Definition: fsm_coe.h:59
Initial state of a new datagram.
Definition: datagram.h:75
EtherCAT CoE state machines.
EtherCAT slave.
Definition: slave.h:176
int ec_sdo_request_copy_data(ec_sdo_request_t *req, const uint8_t *source, size_t size)
Copies SDO data from an external source.
Definition: sdo_request.c:156
char * description
Description.
Definition: sdo_entry.h:62
Code/Message pair.
Definition: globals.h:266
ec_datagram_state_t state
State.
Definition: datagram.h:100
void ec_fsm_coe_dict_desc_request(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DICT DESC REQUEST.
Definition: fsm_coe.c:652
ec_slave_config_t * config
Current configuration.
Definition: slave.h:190
#define EC_WRITE_U32(DATA, VAL)
Write a 32-bit unsigned value to EtherCAT data.
Definition: ecrt.h:2435
void ec_fsm_coe_up_prepare_segment_request(ec_fsm_coe_t *fsm, ec_datagram_t *datagram)
Prepare an SDO upload segment request.
Definition: fsm_coe.c:2037
uint8_t enable_sdo_info
SDO information service available.
Definition: globals.h:147
uint16_t mailbox_protocols
Supported mailbox protocols.
Definition: slave.h:147
ec_sdo_request_t * request
SDO request.
Definition: fsm_coe.h:61
int ec_fsm_coe_dict_prepare_desc(ec_fsm_coe_t *fsm, ec_datagram_t *datagram)
Prepare an object description request.
Definition: fsm_coe.c:468
unsigned int debug_level
Master debug level.
Definition: master.h:285
void ec_fsm_coe_dict_desc_response(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DICT DESC RESPONSE.
Definition: fsm_coe.c:782
#define EC_SLAVE_ERR(slave, fmt, args...)
Convenience macro for printing slave-specific errors to syslog.
Definition: slave.h:76
void ec_datagram_print_wc_error(const ec_datagram_t *datagram)
Evaluates the working counter of a single-cast datagram.
Definition: datagram.c:602
void ec_fsm_coe_up_response(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: UP RESPONSE.
Definition: fsm_coe.c:2069
unsigned long jiffies_sent
Jiffies, when the upload/download request was sent.
Definition: sdo_request.h:63
uint8_t subindex
current subindex
Definition: fsm_coe.h:60
char * name
SDO name.
Definition: sdo.h:54
void ec_fsm_coe_clear(ec_fsm_coe_t *fsm)
Destructor.
Definition: fsm_coe.c:182
#define EC_WRITE_U16(DATA, VAL)
Write a 16-bit unsigned value to EtherCAT data.
Definition: ecrt.h:2418
ec_datagram_t * datagram
Datagram used in last step.
Definition: fsm_coe.h:57
uint32_t remaining
Remaining bytes during segmented download.
Definition: fsm_coe.h:65
#define EC_READ_U32(DATA)
Read a 32-bit unsigned value from EtherCAT data.
Definition: ecrt.h:2329
uint32_t complete_size
Used when segmenting.
Definition: fsm_coe.h:62
int ec_fsm_coe_dict_prepare_entry(ec_fsm_coe_t *fsm, ec_datagram_t *datagram)
Prepare an entry description request.
Definition: fsm_coe.c:751
ec_master_t * master
Master owning the slave.
Definition: slave.h:178
int errno
Error number.
Definition: sdo_request.h:65
unsigned long jiffies_start
CoE timestamp.
Definition: fsm_coe.h:58
void ec_fsm_coe_dict_desc_check(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DICT DESC CHECK.
Definition: fsm_coe.c:695
CANopen over EtherCAT.
Definition: globals.h:137
void ec_fsm_coe_dictionary(ec_fsm_coe_t *fsm, ec_slave_t *slave)
Starts reading a slaves&#39; SDO dictionary.
Definition: fsm_coe.c:192
void ec_fsm_coe_dict_start(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DICT START.
Definition: fsm_coe.c:341
void ec_fsm_coe_down_request(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DOWN REQUEST.
Definition: fsm_coe.c:1341
void ec_canopen_abort_msg(const ec_slave_t *slave, uint32_t abort_code)
Outputs an SDO abort message.
Definition: fsm_coe.c:148
uint16_t data_type
Data type.
Definition: sdo_entry.h:58
Access rights in OP.
Definition: globals.h:183
void ec_fsm_coe_dict_check(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DICT CHECK.
Definition: fsm_coe.c:413
#define EC_MBOX_HEADER_SIZE
Mailbox header size.
Definition: globals.h:83
void ec_sdo_init(ec_sdo_t *sdo, ec_slave_t *slave, uint16_t index)
Constructor.
Definition: sdo.c:47
int ec_fsm_coe_prepare_dict(ec_fsm_coe_t *fsm, ec_datagram_t *datagram)
Prepare a dictionary request.
Definition: fsm_coe.c:315
void ec_fsm_coe_init(ec_fsm_coe_t *fsm)
Constructor.
Definition: fsm_coe.c:170
void ec_print_data(const uint8_t *, size_t)
Outputs frame contents for debugging purposes.
Definition: module.c:348
uint8_t read_access[EC_SDO_ENTRY_ACCESS_COUNT]
Read access.
Definition: sdo_entry.h:60
uint8_t subindex
SDO subindex.
Definition: sdo_request.h:49
struct list_head entries
List of entries.
Definition: sdo.h:56
size_t data_size
Size of SDO data.
Definition: sdo_request.h:52
int ec_slave_mbox_prepare_check(const ec_slave_t *slave, ec_datagram_t *datagram)
Prepares a datagram for checking the mailbox state.
Definition: mailbox.c:96
#define EC_READ_U16(DATA)
Read a 16-bit unsigned value from EtherCAT data.
Definition: ecrt.h:2313
ec_coe_emerg_ring_t emerg_ring
CoE emergency ring buffer.
Definition: slave_config.h:150
void ec_datagram_print_state(const ec_datagram_t *datagram)
Prints the state of a datagram.
Definition: datagram.c:565
Mailbox functionality.
void ec_coe_emerg_ring_push(ec_coe_emerg_ring_t *ring, const u8 *msg)
Add a new emergency message.
int ec_fsm_coe_exec(ec_fsm_coe_t *fsm, ec_datagram_t *datagram)
Executes the current state of the state machine.
Definition: fsm_coe.c:228
void ec_fsm_coe_dict_request(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DICT REQUEST.
Definition: fsm_coe.c:373
Queued for sending.
Definition: datagram.h:76
void ec_fsm_coe_down_start(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DOWN START.
Definition: fsm_coe.c:1290
Timed out (dequeued).
Definition: datagram.h:79
uint8_t max_subindex
Maximum subindex.
Definition: sdo.h:55
void ec_fsm_coe_down_seg_response(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DOWN SEG RESPONSE.
Definition: fsm_coe.c:1711
uint16_t configured_rx_mailbox_size
Configured receive mailbox size.
Definition: slave.h:197
uint8_t toggle
toggle bit for segment commands
Definition: fsm_coe.h:63
void ec_sdo_entry_init(ec_sdo_entry_t *entry, ec_sdo_t *sdo, uint8_t subindex)
Constructor.
Definition: sdo_entry.c:45
#define EC_READ_U8(DATA)
Read an 8-bit unsigned value from EtherCAT data.
Definition: ecrt.h:2297
EtherCAT slave configuration.
Definition: slave_config.h:117
void ec_fsm_coe_down_response(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: DOWN RESPONSE.
Definition: fsm_coe.c:1533
#define EC_COE_DOWN_REQ_HEADER_SIZE
CoE download request header size.
Definition: fsm_coe.c:50
unsigned int retries
retries upon datagram timeout
Definition: fsm_coe.h:54
EtherCAT slave configuration structure.
uint8_t write_access[EC_SDO_ENTRY_ACCESS_COUNT]
Write access.
Definition: sdo_entry.h:61
void ec_fsm_coe_transfer(ec_fsm_coe_t *fsm, ec_slave_t *slave, ec_sdo_request_t *request)
Starts to transfer an SDO to/from a slave.
Definition: fsm_coe.c:205
int ec_sdo_request_alloc(ec_sdo_request_t *req, size_t size)
Pre-allocates the data memory.
Definition: sdo_request.c:127
Values written by the master.
Definition: ecrt.h:448
Received (dequeued).
Definition: datagram.h:78
EtherCAT master.
Definition: master.h:194
unsigned long jiffies_received
Jiffies, when the datagram was received.
Definition: datagram.h:108
ec_slave_t * slave
slave the FSM runs on
Definition: fsm_coe.h:53
int ec_slave_mbox_check(const ec_datagram_t *datagram)
Processes a mailbox state checking datagram.
Definition: mailbox.c:115
const ec_code_msg_t sdo_abort_messages[]
SDO abort messages.
Definition: fsm_coe.c:107
uint8_t complete_access
SDO shall be transferred completely.
Definition: sdo_request.h:53
void ec_fsm_coe_up_check(ec_fsm_coe_t *, ec_datagram_t *)
CoE state: UP CHECK.
Definition: fsm_coe.c:1980
unsigned int has_general
General category present.
Definition: slave.h:154
Finite state machines for the CANopen over EtherCAT protocol.
Definition: fsm_coe.h:52