master/slave.c
changeset 121 1cd6f7a47b72
parent 119 b2de89096010
child 122 132c3ffc8dea
equal deleted inserted replaced
120:e713e7420c4d 121:1cd6f7a47b72
     1 /******************************************************************************
     1 /******************************************************************************
     2  *
     2  *
     3  *  s l a v e . c
     3  *  s l a v e . c
     4  *
     4  *
     5  *  Methoden für einen EtherCAT-Slave.
     5  *  Methoden fŽür einen EtherCAT-Slave.
     6  *
     6  *
     7  *  $Id$
     7  *  $Id$
     8  *
     8  *
     9  *****************************************************************************/
     9  *****************************************************************************/
    10 
    10 
    51     slave->sii_serial_number = 0;
    51     slave->sii_serial_number = 0;
    52     slave->type = NULL;
    52     slave->type = NULL;
    53     slave->registered = 0;
    53     slave->registered = 0;
    54     slave->fmmu_count = 0;
    54     slave->fmmu_count = 0;
    55 
    55 
    56     INIT_LIST_HEAD(&slave->cat_strings);
    56     INIT_LIST_HEAD(&slave->eeprom_strings);
       
    57     slave->eeprom_name = NULL;
       
    58     slave->eeprom_group = NULL;
       
    59     slave->eeprom_desc = NULL;
    57 }
    60 }
    58 
    61 
    59 /*****************************************************************************/
    62 /*****************************************************************************/
    60 
    63 
    61 /**
    64 /**
    65 void ec_slave_clear(ec_slave_t *slave /**< EtherCAT-Slave */)
    68 void ec_slave_clear(ec_slave_t *slave /**< EtherCAT-Slave */)
    66 {
    69 {
    67     ec_slave_string_t *string, *next;
    70     ec_slave_string_t *string, *next;
    68 
    71 
    69     // Alle Strings freigeben
    72     // Alle Strings freigeben
    70     list_for_each_entry_safe(string, next, &slave->cat_strings, list) {
    73     list_for_each_entry_safe(string, next, &slave->eeprom_strings, list) {
    71         list_del(&string->list);
    74         list_del(&string->list);
    72         kfree(string);
    75         kfree(string);
    73     }
    76     }
    74 }
    77 
    75 
    78     if (slave->eeprom_name) kfree(slave->eeprom_name);
    76 /*****************************************************************************/
    79     if (slave->eeprom_group) kfree(slave->eeprom_group);
    77 
    80     if (slave->eeprom_desc) kfree(slave->eeprom_desc);
    78 /**
    81 }
    79    Liest alle benötigten Informationen aus einem Slave.
    82 
       
    83 /*****************************************************************************/
       
    84 
       
    85 /**
       
    86    Liest alle benŽötigten Informationen aus einem Slave.
    80 
    87 
    81    \return 0 wenn alles ok, < 0 bei Fehler.
    88    \return 0 wenn alles ok, < 0 bei Fehler.
    82 */
    89 */
    83 
    90 
    84 int ec_slave_fetch(ec_slave_t *slave /**< EtherCAT-Slave */)
    91 int ec_slave_fetch(ec_slave_t *slave /**< EtherCAT-Slave */)
   152 int ec_slave_sii_read(ec_slave_t *slave,
   159 int ec_slave_sii_read(ec_slave_t *slave,
   153                       /**< EtherCAT-Slave */
   160                       /**< EtherCAT-Slave */
   154                       uint16_t offset,
   161                       uint16_t offset,
   155                       /**< Adresse des zu lesenden SII-Registers */
   162                       /**< Adresse des zu lesenden SII-Registers */
   156                       uint32_t *target
   163                       uint32_t *target
   157                       /**< Zeiger auf einen 4 Byte großen Speicher zum Ablegen
   164                       /**< Zeiger auf einen 4 Byte groŽßen Speicher zum Ablegen
   158                          der Daten */
   165                          der Daten */
   159                       )
   166                       )
   160 {
   167 {
   161     ec_command_t command;
   168     ec_command_t command;
   162     uint8_t data[10];
   169     uint8_t data[10];
   173         EC_ERR("SII-read failed on slave %i!\n", slave->ring_position);
   180         EC_ERR("SII-read failed on slave %i!\n", slave->ring_position);
   174         return -1;
   181         return -1;
   175     }
   182     }
   176 
   183 
   177     // Der Slave legt die Informationen des Slave-Information-Interface
   184     // Der Slave legt die Informationen des Slave-Information-Interface
   178     // in das Datenregister und löscht daraufhin ein Busy-Bit. Solange
   185     // in das Datenregister und lŽöscht daraufhin ein Busy-Bit. Solange
   179     // den Status auslesen, bis das Bit weg ist.
   186     // den Status auslesen, bis das Bit weg ist.
   180 
   187 
   181     start = get_cycles();
   188     start = get_cycles();
   182     timeout = (cycles_t) 100 * cpu_khz; // 100ms
   189     timeout = (cycles_t) 100 * cpu_khz; // 100ms
   183 
   190 
   242         EC_ERR("SII-write failed on slave %i!\n", slave->ring_position);
   249         EC_ERR("SII-write failed on slave %i!\n", slave->ring_position);
   243         return -1;
   250         return -1;
   244     }
   251     }
   245 
   252 
   246     // Der Slave legt die Informationen des Slave-Information-Interface
   253     // Der Slave legt die Informationen des Slave-Information-Interface
   247     // in das Datenregister und löscht daraufhin ein Busy-Bit. Solange
   254     // in das Datenregister und lŽöscht daraufhin ein Busy-Bit. Solange
   248     // den Status auslesen, bis das Bit weg ist.
   255     // den Status auslesen, bis das Bit weg ist.
   249 
   256 
   250     start = get_cycles();
   257     start = get_cycles();
   251     timeout = (cycles_t) 100 * cpu_khz; // 100ms
   258     timeout = (cycles_t) 100 * cpu_khz; // 100ms
   252 
   259 
   397 
   404 
   398     string_count = data[0];
   405     string_count = data[0];
   399     offset = 1;
   406     offset = 1;
   400     for (i = 0; i < string_count; i++) {
   407     for (i = 0; i < string_count; i++) {
   401         size = data[offset];
   408         size = data[offset];
   402         // Speicher für String-Objekt und Daten in einem Rutsch allozieren
   409         // Speicher fŽür String-Objekt und Daten in einem Rutsch allozieren
   403         if (!(string = (ec_slave_string_t *) kmalloc(sizeof(ec_slave_string_t)
   410         if (!(string = (ec_slave_string_t *) kmalloc(sizeof(ec_slave_string_t)
   404                                                      + size + 1,
   411                                                      + size + 1,
   405                                                      GFP_KERNEL))) {
   412                                                      GFP_KERNEL))) {
   406             EC_ERR("Failed to allocate string memory.\n");
   413             EC_ERR("Failed to allocate string memory.\n");
   407             return -1;
   414             return -1;
   408         }
   415         }
   409         string->data = (char *) (string + sizeof(ec_slave_string_t));
   416         string->size = size;
       
   417         string->data = (char *) string + sizeof(ec_slave_string_t);
   410         memcpy(string->data, data + offset + 1, size);
   418         memcpy(string->data, data + offset + 1, size);
   411         string->data[size] = 0x00;
   419         string->data[size] = 0x00;
   412         list_add_tail(&string->list, &slave->cat_strings);
   420         list_add_tail(&string->list, &slave->eeprom_strings);
   413         offset += 1 + size;
   421         offset += 1 + size;
   414     }
   422     }
   415 
   423 
   416     return 0;
   424     return 0;
   417 }
   425 }
   477 }
   485 }
   478 
   486 
   479 /*****************************************************************************/
   487 /*****************************************************************************/
   480 
   488 
   481 /**
   489 /**
   482    Bestätigt einen Fehler beim Zustandswechsel.
   490    BestŽätigt einen Fehler beim Zustandswechsel.
   483 
   491 
   484    \todo Funktioniert noch nicht...
   492    \todo Funktioniert noch nicht...
   485 */
   493 */
   486 
   494 
   487 void ec_slave_state_ack(ec_slave_t *slave,
   495 void ec_slave_state_ack(ec_slave_t *slave,
   488                         /**< Slave, dessen Zustand geändert werden soll */
   496                         /**< Slave, dessen Zustand geŽändert werden soll */
   489                         uint8_t state
   497                         uint8_t state
   490                         /**< Alter Zustand */
   498                         /**< Alter Zustand */
   491                         )
   499                         )
   492 {
   500 {
   493     ec_command_t command;
   501     ec_command_t command;
   541 }
   549 }
   542 
   550 
   543 /*****************************************************************************/
   551 /*****************************************************************************/
   544 
   552 
   545 /**
   553 /**
   546    Ändert den Zustand eines Slaves.
   554    ŽÄndert den Zustand eines Slaves.
   547 
   555 
   548    \return 0 bei Erfolg, sonst < 0
   556    \return 0 bei Erfolg, sonst < 0
   549 */
   557 */
   550 
   558 
   551 int ec_slave_state_change(ec_slave_t *slave,
   559 int ec_slave_state_change(ec_slave_t *slave,
   552                           /**< Slave, dessen Zustand geändert werden soll */
   560                           /**< Slave, dessen Zustand geŽändert werden soll */
   553                           uint8_t state
   561                           uint8_t state
   554                           /**< Neuer Zustand */
   562                           /**< Neuer Zustand */
   555                           )
   563                           )
   556 {
   564 {
   557     ec_command_t command;
   565     ec_command_t command;
   608 
   616 
   609 /**
   617 /**
   610    Merkt eine FMMU-Konfiguration vor.
   618    Merkt eine FMMU-Konfiguration vor.
   611 
   619 
   612    Die FMMU wird so konfiguriert, dass sie den gesamten Datenbereich des
   620    Die FMMU wird so konfiguriert, dass sie den gesamten Datenbereich des
   613    entsprechenden Sync-Managers abdeckt. Für jede Domäne werden separate
   621    entsprechenden Sync-Managers abdeckt. FŽür jede DomŽäne werden separate
   614    FMMUs konfiguriert.
   622    FMMUs konfiguriert.
   615 
   623 
   616    Wenn die entsprechende FMMU bereits konfiguriert ist, wird dies als
   624    Wenn die entsprechende FMMU bereits konfiguriert ist, wird dies als
   617    Erfolg zurückgegeben.
   625    Erfolg zurŽückgegeben.
   618 
   626 
   619    \return 0 bei Erfolg, sonst < 0
   627    \return 0 bei Erfolg, sonst < 0
   620 */
   628 */
   621 
   629 
   622 int ec_slave_set_fmmu(ec_slave_t *slave, /**< EtherCAT-Slave */
   630 int ec_slave_set_fmmu(ec_slave_t *slave, /**< EtherCAT-Slave */
   623                       const ec_domain_t *domain, /**< Domäne */
   631                       const ec_domain_t *domain, /**< DomŽäne */
   624                       const ec_sync_t *sync  /**< Sync-Manager */
   632                       const ec_sync_t *sync  /**< Sync-Manager */
   625                       )
   633                       )
   626 {
   634 {
   627     unsigned int i;
   635     unsigned int i;
   628 
   636 
   648 }
   656 }
   649 
   657 
   650 /*****************************************************************************/
   658 /*****************************************************************************/
   651 
   659 
   652 /**
   660 /**
   653    Gibt alle Informationen über einen EtherCAT-Slave aus.
   661    Gibt alle Informationen Žüber einen EtherCAT-Slave aus.
   654 */
   662 */
   655 
   663 
   656 void ec_slave_print(const ec_slave_t *slave /**< EtherCAT-Slave */)
   664 void ec_slave_print(const ec_slave_t *slave /**< EtherCAT-Slave */)
   657 {
   665 {
   658     ec_slave_string_t *string;
       
   659 
       
   660     EC_INFO("--- EtherCAT slave information ---\n");
   666     EC_INFO("--- EtherCAT slave information ---\n");
   661 
   667 
   662     if (slave->type) {
   668     if (slave->type) {
   663         EC_INFO("  Vendor \"%s\", Product \"%s\": %s\n",
   669         EC_INFO("  Vendor \"%s\", Product \"%s\": %s\n",
   664                 slave->type->vendor_name, slave->type->product_name,
   670                 slave->type->vendor_name, slave->type->product_name,
   675     EC_INFO("    Type %u, Revision %i, Build %i\n",
   681     EC_INFO("    Type %u, Revision %i, Build %i\n",
   676             slave->base_type, slave->base_revision, slave->base_build);
   682             slave->base_type, slave->base_revision, slave->base_build);
   677     EC_INFO("    Supported FMMUs: %i, Sync managers: %i\n",
   683     EC_INFO("    Supported FMMUs: %i, Sync managers: %i\n",
   678             slave->base_fmmu_count, slave->base_sync_count);
   684             slave->base_fmmu_count, slave->base_sync_count);
   679 
   685 
   680     EC_INFO("  Slave information interface:\n");
   686     EC_INFO("  EEPROM data:\n");
   681     EC_INFO("    Configured station alias: 0x%04X (%i)\n", slave->sii_alias,
   687     EC_INFO("    Configured station alias: 0x%04X (%i)\n", slave->sii_alias,
   682             slave->sii_alias);
   688             slave->sii_alias);
   683     EC_INFO("    Vendor-ID: 0x%08X, Product code: 0x%08X\n",
   689     EC_INFO("    Vendor-ID: 0x%08X, Product code: 0x%08X\n",
   684             slave->sii_vendor_id, slave->sii_product_code);
   690             slave->sii_vendor_id, slave->sii_product_code);
   685     EC_INFO("    Revision number: 0x%08X, Serial number: 0x%08X\n",
   691     EC_INFO("    Revision number: 0x%08X, Serial number: 0x%08X\n",
   686             slave->sii_revision_number, slave->sii_serial_number);
   692             slave->sii_revision_number, slave->sii_serial_number);
   687 
   693     if (slave->eeprom_name)
   688     EC_INFO("    EEPROM strings:\n");
   694         EC_INFO("    Name: %s\n", slave->eeprom_name);
   689     list_for_each_entry(string, &slave->cat_strings, list) {
   695     if (slave->eeprom_group)
   690         EC_INFO("      * \"%s\"\n", string->data);
   696         EC_INFO("    Group: %s\n", slave->eeprom_group);
   691     }
   697     if (slave->eeprom_desc)
   692 }
   698         EC_INFO("    Description: %s\n", slave->eeprom_desc);
   693 
   699 }
   694 /*****************************************************************************/
   700 
   695 
   701 /*****************************************************************************/
   696 /**
   702 
   697    Gibt die Zählerstände der CRC-Fault-Counter aus und setzt diese zurück.
   703 /**
       
   704    Gibt die ZŽählerstŽände der CRC-Fault-Counter aus und setzt diese zurŽück.
   698 
   705 
   699    \return 0 bei Erfolg, sonst < 0
   706    \return 0 bei Erfolg, sonst < 0
   700 */
   707 */
   701 
   708 
   702 int ec_slave_check_crc(ec_slave_t *slave /**< EtherCAT-Slave */)
   709 int ec_slave_check_crc(ec_slave_t *slave /**< EtherCAT-Slave */)