master/fsm_coe.c
branchredundancy
changeset 2312 2212bb83c981
parent 2311 dc8e5a35bc05
child 2438 9c3e629a220c
equal deleted inserted replaced
2311:dc8e5a35bc05 2312:2212bb83c981
   955         return;
   955         return;
   956     }
   956     }
   957 
   957 
   958     if (EC_READ_U16(data) >> 12 == 0x8 && // SDO information
   958     if (EC_READ_U16(data) >> 12 == 0x8 && // SDO information
   959         (EC_READ_U8 (data + 2) & 0x7F) == 0x07) { // error response
   959         (EC_READ_U8 (data + 2) & 0x7F) == 0x07) { // error response
   960         EC_SLAVE_ERR(slave, "SDO information error response while"
   960         EC_SLAVE_WARN(slave, "SDO information error response while"
   961                " fetching SDO entry 0x%04X:%02X!\n",
   961                " fetching SDO entry 0x%04X:%02X!\n",
   962                sdo->index, fsm->subindex);
   962                sdo->index, fsm->subindex);
   963         ec_canopen_abort_msg(slave, EC_READ_U32(data + 6));
   963         ec_canopen_abort_msg(slave, EC_READ_U32(data + 6));
   964         fsm->state = ec_fsm_coe_error;
   964 
   965         return;
   965         /* There may be gaps in the subindices, so try to continue with next
   966     }
   966          * subindex. */
   967 
   967 
   968     if (rec_size < 9) {
   968     } else {
   969         EC_SLAVE_ERR(slave, "Received corrupted SDO entry"
   969 
   970                 " description response (size %zu).\n", rec_size);
   970         if (rec_size < 9) {
   971         fsm->state = ec_fsm_coe_error;
   971             EC_SLAVE_ERR(slave, "Received corrupted SDO entry"
   972         return;
   972                     " description response (size %zu).\n", rec_size);
   973     }
   973             fsm->state = ec_fsm_coe_error;
   974 
   974             return;
   975     if (EC_READ_U16(data) >> 12 != 0x8 || // SDO information
   975         }
   976         (EC_READ_U8(data + 2) & 0x7F) != 0x06 || // Entry desc. response
   976 
   977         EC_READ_U16(data + 6) != sdo->index || // SDO index
   977         if (EC_READ_U16(data) >> 12 != 0x8 || // SDO information
   978         EC_READ_U8(data + 8) != fsm->subindex) { // SDO subindex
   978             (EC_READ_U8(data + 2) & 0x7F) != 0x06 || // Entry desc. response
   979         if (fsm->slave->master->debug_level) {
   979             EC_READ_U16(data + 6) != sdo->index || // SDO index
   980             EC_SLAVE_DBG(slave, 1, "Invalid entry description response while"
   980             EC_READ_U8(data + 8) != fsm->subindex) { // SDO subindex
   981                     " fetching SDO entry 0x%04X:%02X!\n",
   981             if (fsm->slave->master->debug_level) {
   982                     sdo->index, fsm->subindex);
   982                 EC_SLAVE_DBG(slave, 1, "Invalid entry description response"
       
   983                         " while fetching SDO entry 0x%04X:%02X!\n",
       
   984                         sdo->index, fsm->subindex);
       
   985                 ec_print_data(data, rec_size);
       
   986             }
       
   987             // check for CoE response again
       
   988             ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
       
   989             fsm->retries = EC_FSM_RETRIES;
       
   990             fsm->state = ec_fsm_coe_dict_entry_check;
       
   991             return;
       
   992         }
       
   993 
       
   994         if (rec_size < 16) {
       
   995             EC_SLAVE_ERR(slave, "Invalid data size %zu!\n", rec_size);
   983             ec_print_data(data, rec_size);
   996             ec_print_data(data, rec_size);
   984         }
       
   985         // check for CoE response again
       
   986         ec_slave_mbox_prepare_check(slave, datagram); // can not fail.
       
   987         fsm->retries = EC_FSM_RETRIES;
       
   988         fsm->state = ec_fsm_coe_dict_entry_check;
       
   989         return;
       
   990     }
       
   991 
       
   992     if (rec_size < 16) {
       
   993         EC_SLAVE_ERR(slave, "Invalid data size %zu!\n", rec_size);
       
   994         ec_print_data(data, rec_size);
       
   995         fsm->state = ec_fsm_coe_error;
       
   996         return;
       
   997     }
       
   998 
       
   999     data_size = rec_size - 16;
       
  1000 
       
  1001     if (!(entry = (ec_sdo_entry_t *)
       
  1002           kmalloc(sizeof(ec_sdo_entry_t), GFP_KERNEL))) {
       
  1003         EC_SLAVE_ERR(slave, "Failed to allocate entry!\n");
       
  1004         fsm->state = ec_fsm_coe_error;
       
  1005         return;
       
  1006     }
       
  1007 
       
  1008     ec_sdo_entry_init(entry, sdo, fsm->subindex);
       
  1009     entry->data_type = EC_READ_U16(data + 10);
       
  1010     entry->bit_length = EC_READ_U16(data + 12);
       
  1011 
       
  1012     // read access rights
       
  1013     word = EC_READ_U16(data + 14);
       
  1014     entry->read_access[EC_SDO_ENTRY_ACCESS_PREOP] = word & 0x0001;
       
  1015     entry->read_access[EC_SDO_ENTRY_ACCESS_SAFEOP] = (word >> 1)  & 0x0001;
       
  1016     entry->read_access[EC_SDO_ENTRY_ACCESS_OP] = (word >> 2)  & 0x0001;
       
  1017     entry->write_access[EC_SDO_ENTRY_ACCESS_PREOP] = (word >> 3) & 0x0001;
       
  1018     entry->write_access[EC_SDO_ENTRY_ACCESS_SAFEOP] = (word >> 4)  & 0x0001;
       
  1019     entry->write_access[EC_SDO_ENTRY_ACCESS_OP] = (word >> 5)  & 0x0001;
       
  1020 
       
  1021     if (data_size) {
       
  1022         uint8_t *desc;
       
  1023         if (!(desc = kmalloc(data_size + 1, GFP_KERNEL))) {
       
  1024             EC_SLAVE_ERR(slave, "Failed to allocate SDO entry name!\n");
       
  1025             fsm->state = ec_fsm_coe_error;
   997             fsm->state = ec_fsm_coe_error;
  1026             return;
   998             return;
  1027         }
   999         }
  1028         memcpy(desc, data + 16, data_size);
  1000 
  1029         desc[data_size] = 0;
  1001         data_size = rec_size - 16;
  1030         entry->description = desc;
  1002 
  1031     }
  1003         if (!(entry = (ec_sdo_entry_t *)
  1032 
  1004               kmalloc(sizeof(ec_sdo_entry_t), GFP_KERNEL))) {
  1033     list_add_tail(&entry->list, &sdo->entries);
  1005             EC_SLAVE_ERR(slave, "Failed to allocate entry!\n");
       
  1006             fsm->state = ec_fsm_coe_error;
       
  1007             return;
       
  1008         }
       
  1009 
       
  1010         ec_sdo_entry_init(entry, sdo, fsm->subindex);
       
  1011         entry->data_type = EC_READ_U16(data + 10);
       
  1012         entry->bit_length = EC_READ_U16(data + 12);
       
  1013 
       
  1014         // read access rights
       
  1015         word = EC_READ_U16(data + 14);
       
  1016         entry->read_access[EC_SDO_ENTRY_ACCESS_PREOP] = word & 0x0001;
       
  1017         entry->read_access[EC_SDO_ENTRY_ACCESS_SAFEOP] =
       
  1018             (word >> 1)  & 0x0001;
       
  1019         entry->read_access[EC_SDO_ENTRY_ACCESS_OP] = (word >> 2)  & 0x0001;
       
  1020         entry->write_access[EC_SDO_ENTRY_ACCESS_PREOP] = (word >> 3) & 0x0001;
       
  1021         entry->write_access[EC_SDO_ENTRY_ACCESS_SAFEOP] =
       
  1022             (word >> 4)  & 0x0001;
       
  1023         entry->write_access[EC_SDO_ENTRY_ACCESS_OP] = (word >> 5)  & 0x0001;
       
  1024 
       
  1025         if (data_size) {
       
  1026             uint8_t *desc;
       
  1027             if (!(desc = kmalloc(data_size + 1, GFP_KERNEL))) {
       
  1028                 EC_SLAVE_ERR(slave, "Failed to allocate SDO entry name!\n");
       
  1029                 fsm->state = ec_fsm_coe_error;
       
  1030                 return;
       
  1031             }
       
  1032             memcpy(desc, data + 16, data_size);
       
  1033             desc[data_size] = 0;
       
  1034             entry->description = desc;
       
  1035         }
       
  1036 
       
  1037         list_add_tail(&entry->list, &sdo->entries);
       
  1038     }
  1034 
  1039 
  1035     if (fsm->subindex < sdo->max_subindex) {
  1040     if (fsm->subindex < sdo->max_subindex) {
  1036         fsm->subindex++;
  1041         fsm->subindex++;
  1037 
  1042 
  1038         data = ec_slave_mbox_prepare_send(slave, datagram, 0x03, 10);
  1043         data = ec_slave_mbox_prepare_send(slave, datagram, 0x03, 10);