109 char name[EC_DATAGRAM_NAME_SIZE]; |
109 char name[EC_DATAGRAM_NAME_SIZE]; |
110 |
110 |
111 eoe->slave = slave; |
111 eoe->slave = slave; |
112 |
112 |
113 ec_datagram_init(&eoe->datagram); |
113 ec_datagram_init(&eoe->datagram); |
|
114 ec_mbox_init(&eoe->mbox,&eoe->datagram); |
114 eoe->queue_datagram = 0; |
115 eoe->queue_datagram = 0; |
115 eoe->state = ec_eoe_state_rx_start; |
116 eoe->state = ec_eoe_state_rx_start; |
116 eoe->opened = 0; |
117 eoe->opened = 0; |
117 eoe->rx_skb = NULL; |
118 eoe->rx_skb = NULL; |
118 eoe->rx_expected_fragment = 0; |
119 eoe->rx_expected_fragment = 0; |
120 eoe->tx_frame = NULL; |
121 eoe->tx_frame = NULL; |
121 eoe->tx_queue_active = 0; |
122 eoe->tx_queue_active = 0; |
122 eoe->tx_queue_size = EC_EOE_TX_QUEUE_SIZE; |
123 eoe->tx_queue_size = EC_EOE_TX_QUEUE_SIZE; |
123 eoe->tx_queued_frames = 0; |
124 eoe->tx_queued_frames = 0; |
124 |
125 |
125 sema_init(&eoe->tx_queue_sem, 1); |
126 ec_mutex_init(&eoe->tx_queue_mutex); |
126 eoe->tx_frame_number = 0xFF; |
127 eoe->tx_frame_number = 0xFF; |
127 memset(&eoe->stats, 0, sizeof(struct net_device_stats)); |
128 memset(&eoe->stats, 0, sizeof(struct net_device_stats)); |
128 |
129 |
129 eoe->rx_counter = 0; |
130 eoe->rx_counter = 0; |
130 eoe->tx_counter = 0; |
131 eoe->tx_counter = 0; |
229 */ |
231 */ |
230 void ec_eoe_flush(ec_eoe_t *eoe /**< EoE handler */) |
232 void ec_eoe_flush(ec_eoe_t *eoe /**< EoE handler */) |
231 { |
233 { |
232 ec_eoe_frame_t *frame, *next; |
234 ec_eoe_frame_t *frame, *next; |
233 |
235 |
234 down(&eoe->tx_queue_sem); |
236 ec_mutex_lock(&eoe->tx_queue_mutex); |
235 |
237 |
236 list_for_each_entry_safe(frame, next, &eoe->tx_queue, queue) { |
238 list_for_each_entry_safe(frame, next, &eoe->tx_queue, queue) { |
237 list_del(&frame->queue); |
239 list_del(&frame->queue); |
238 dev_kfree_skb(frame->skb); |
240 dev_kfree_skb(frame->skb); |
239 kfree(frame); |
241 kfree(frame); |
240 } |
242 } |
241 eoe->tx_queued_frames = 0; |
243 eoe->tx_queued_frames = 0; |
242 |
244 |
243 up(&eoe->tx_queue_sem); |
245 ec_mutex_unlock(&eoe->tx_queue_mutex); |
244 } |
246 } |
245 |
247 |
246 /*****************************************************************************/ |
248 /*****************************************************************************/ |
247 |
249 |
248 /** Sends a frame or the next fragment. |
250 /** Sends a frame or the next fragment. |
292 } |
294 } |
293 } |
295 } |
294 printk("\n"); |
296 printk("\n"); |
295 #endif |
297 #endif |
296 |
298 |
297 data = ec_slave_mbox_prepare_send(eoe->slave, &eoe->datagram, |
299 data = ec_slave_mbox_prepare_send(eoe->slave, &eoe->mbox, |
298 0x02, current_size + 4); |
300 0x02, current_size + 4); |
299 if (IS_ERR(data)) |
301 if (IS_ERR(data)) |
300 return PTR_ERR(data); |
302 return PTR_ERR(data); |
301 |
303 |
302 EC_WRITE_U8 (data, 0x00); // eoe fragment req. |
304 EC_WRITE_U8 (data, 0x00); // eoe fragment req. |
321 { |
323 { |
322 if (!eoe->opened) |
324 if (!eoe->opened) |
323 return; |
325 return; |
324 |
326 |
325 // if the datagram was not sent, or is not yet received, skip this cycle |
327 // if the datagram was not sent, or is not yet received, skip this cycle |
326 if (eoe->queue_datagram || eoe->datagram.state == EC_DATAGRAM_SENT) |
328 if (eoe->queue_datagram || |
|
329 ec_mbox_is_datagram_state(&eoe->mbox,EC_DATAGRAM_QUEUED) || |
|
330 ec_mbox_is_datagram_state(&eoe->mbox,EC_DATAGRAM_SENT)) |
327 return; |
331 return; |
328 |
332 |
329 // call state function |
333 // call state function |
330 eoe->state(eoe); |
334 eoe->state(eoe); |
331 |
335 |
346 /** Queues the datagram, if necessary. |
350 /** Queues the datagram, if necessary. |
347 */ |
351 */ |
348 void ec_eoe_queue(ec_eoe_t *eoe /**< EoE handler */) |
352 void ec_eoe_queue(ec_eoe_t *eoe /**< EoE handler */) |
349 { |
353 { |
350 if (eoe->queue_datagram) { |
354 if (eoe->queue_datagram) { |
351 ec_master_queue_datagram_ext(eoe->slave->master, &eoe->datagram); |
355 ec_master_mbox_queue_datagrams(eoe->slave->master, &eoe->mbox); |
352 eoe->queue_datagram = 0; |
356 eoe->queue_datagram = 0; |
353 } |
357 } |
354 } |
358 } |
355 |
359 |
356 /*****************************************************************************/ |
360 /*****************************************************************************/ |
406 * Processes the checking datagram sent in RX_START and issues a receive |
410 * Processes the checking datagram sent in RX_START and issues a receive |
407 * datagram, if new data is available. |
411 * datagram, if new data is available. |
408 */ |
412 */ |
409 void ec_eoe_state_rx_check(ec_eoe_t *eoe /**< EoE handler */) |
413 void ec_eoe_state_rx_check(ec_eoe_t *eoe /**< EoE handler */) |
410 { |
414 { |
411 if (eoe->datagram.state != EC_DATAGRAM_RECEIVED) { |
415 if (!ec_mbox_is_datagram_state(&eoe->mbox,EC_DATAGRAM_RECEIVED)) { |
412 eoe->stats.rx_errors++; |
416 eoe->stats.rx_errors++; |
413 #if EOE_DEBUG_LEVEL >= 1 |
417 #if EOE_DEBUG_LEVEL >= 1 |
414 EC_SLAVE_WARN(eoe->slave, "Failed to receive mbox" |
418 EC_SLAVE_WARN(eoe->slave, "Failed to receive mbox" |
415 " check datagram for %s.\n", eoe->dev->name); |
419 " check datagram for %s.\n", eoe->dev->name); |
416 #endif |
420 #endif |
417 eoe->state = ec_eoe_state_tx_start; |
421 eoe->state = ec_eoe_state_tx_start; |
418 return; |
422 return; |
419 } |
423 } |
420 |
424 |
421 if (!ec_slave_mbox_check(&eoe->datagram)) { |
425 if (!ec_slave_mbox_check(&eoe->mbox)) { |
422 eoe->rx_idle = 1; |
426 eoe->rx_idle = 1; |
423 eoe->state = ec_eoe_state_tx_start; |
427 eoe->state = ec_eoe_state_tx_start; |
424 return; |
428 return; |
425 } |
429 } |
426 |
430 |
427 eoe->rx_idle = 0; |
431 eoe->rx_idle = 0; |
428 ec_slave_mbox_prepare_fetch(eoe->slave, &eoe->datagram); |
432 ec_slave_mbox_prepare_fetch(eoe->slave, &eoe->mbox); |
429 eoe->queue_datagram = 1; |
433 eoe->queue_datagram = 1; |
430 eoe->state = ec_eoe_state_rx_fetch; |
434 eoe->state = ec_eoe_state_rx_fetch; |
431 } |
435 } |
432 |
436 |
433 /*****************************************************************************/ |
437 /*****************************************************************************/ |
445 off_t offset; |
449 off_t offset; |
446 #if EOE_DEBUG_LEVEL >= 3 |
450 #if EOE_DEBUG_LEVEL >= 3 |
447 unsigned int i; |
451 unsigned int i; |
448 #endif |
452 #endif |
449 |
453 |
450 if (eoe->datagram.state != EC_DATAGRAM_RECEIVED) { |
454 if (!ec_mbox_is_datagram_state(&eoe->mbox,EC_DATAGRAM_RECEIVED)) { |
451 eoe->stats.rx_errors++; |
455 eoe->stats.rx_errors++; |
452 #if EOE_DEBUG_LEVEL >= 1 |
456 #if EOE_DEBUG_LEVEL >= 1 |
453 EC_SLAVE_WARN(eoe->slave, "Failed to receive mbox" |
457 EC_SLAVE_WARN(eoe->slave, "Failed to receive mbox" |
454 " fetch datagram for %s.\n", eoe->dev->name); |
458 " fetch datagram for %s.\n", eoe->dev->name); |
455 #endif |
459 #endif |
456 eoe->state = ec_eoe_state_tx_start; |
460 eoe->state = ec_eoe_state_tx_start; |
457 return; |
461 return; |
458 } |
462 } |
459 |
463 |
460 data = ec_slave_mbox_fetch(eoe->slave, &eoe->datagram, |
464 data = ec_slave_mbox_fetch(eoe->slave, &eoe->mbox, |
461 &mbox_prot, &rec_size); |
465 &mbox_prot, &rec_size); |
462 if (IS_ERR(data)) { |
466 if (IS_ERR(data)) { |
463 eoe->stats.rx_errors++; |
467 eoe->stats.rx_errors++; |
464 #if EOE_DEBUG_LEVEL >= 1 |
468 #if EOE_DEBUG_LEVEL >= 1 |
465 EC_SLAVE_WARN(eoe->slave, "Invalid mailbox response for %s.\n", |
469 EC_SLAVE_WARN(eoe->slave, "Invalid mailbox response for %s.\n", |
618 eoe->rx_idle = 1; |
622 eoe->rx_idle = 1; |
619 eoe->tx_idle = 1; |
623 eoe->tx_idle = 1; |
620 return; |
624 return; |
621 } |
625 } |
622 |
626 |
623 down(&eoe->tx_queue_sem); |
627 ec_mutex_lock(&eoe->tx_queue_mutex); |
624 |
628 |
625 if (!eoe->tx_queued_frames || list_empty(&eoe->tx_queue)) { |
629 if (!eoe->tx_queued_frames || list_empty(&eoe->tx_queue)) { |
626 up(&eoe->tx_queue_sem); |
630 ec_mutex_unlock(&eoe->tx_queue_mutex); |
627 eoe->tx_idle = 1; |
631 eoe->tx_idle = 1; |
628 // no data available. |
632 // no data available. |
629 // start a new receive immediately. |
633 // start a new receive immediately. |
630 ec_eoe_state_rx_start(eoe); |
634 ec_eoe_state_rx_start(eoe); |
631 return; |
635 return; |
682 * Checks is the previous transmit datagram succeded and sends the next |
686 * Checks is the previous transmit datagram succeded and sends the next |
683 * fragment, if necessary. |
687 * fragment, if necessary. |
684 */ |
688 */ |
685 void ec_eoe_state_tx_sent(ec_eoe_t *eoe /**< EoE handler */) |
689 void ec_eoe_state_tx_sent(ec_eoe_t *eoe /**< EoE handler */) |
686 { |
690 { |
687 if (eoe->datagram.state != EC_DATAGRAM_RECEIVED) { |
691 if (!ec_mbox_is_datagram_state(&eoe->mbox,EC_DATAGRAM_RECEIVED)) { |
688 if (eoe->tries) { |
692 if (eoe->tries) { |
689 eoe->tries--; // try again |
693 eoe->tries--; // try again |
690 eoe->queue_datagram = 1; |
694 eoe->queue_datagram = 1; |
691 } else { |
695 } else { |
692 eoe->stats.tx_errors++; |
696 eoe->stats.tx_errors++; |
698 eoe->state = ec_eoe_state_rx_start; |
702 eoe->state = ec_eoe_state_rx_start; |
699 } |
703 } |
700 return; |
704 return; |
701 } |
705 } |
702 |
706 |
703 if (eoe->datagram.working_counter != 1) { |
707 if (!ec_mbox_is_datagram_wc(&eoe->mbox,1)) { |
704 if (eoe->tries) { |
708 if (eoe->tries) { |
705 eoe->tries--; // try again |
709 eoe->tries--; // try again |
706 eoe->queue_datagram = 1; |
710 eoe->queue_datagram = 1; |
707 } else { |
711 } else { |
708 eoe->stats.tx_errors++; |
712 eoe->stats.tx_errors++; |
810 return 1; |
814 return 1; |
811 } |
815 } |
812 |
816 |
813 frame->skb = skb; |
817 frame->skb = skb; |
814 |
818 |
815 down(&eoe->tx_queue_sem); |
819 ec_mutex_lock(&eoe->tx_queue_mutex); |
816 list_add_tail(&frame->queue, &eoe->tx_queue); |
820 list_add_tail(&frame->queue, &eoe->tx_queue); |
817 eoe->tx_queued_frames++; |
821 eoe->tx_queued_frames++; |
818 if (eoe->tx_queued_frames == eoe->tx_queue_size) { |
822 if (eoe->tx_queued_frames == eoe->tx_queue_size) { |
819 netif_stop_queue(dev); |
823 netif_stop_queue(dev); |
820 eoe->tx_queue_active = 0; |
824 eoe->tx_queue_active = 0; |
821 } |
825 } |
822 up(&eoe->tx_queue_sem); |
826 ec_mutex_unlock(&eoe->tx_queue_mutex); |
823 |
827 |
824 #if EOE_DEBUG_LEVEL >= 2 |
828 #if EOE_DEBUG_LEVEL >= 2 |
825 EC_SLAVE_DBG(eoe->slave, 0, "EoE %s TX queued frame" |
829 EC_SLAVE_DBG(eoe->slave, 0, "EoE %s TX queued frame" |
826 " with %u octets (%u frames queued).\n", |
830 " with %u octets (%u frames queued).\n", |
827 eoe->dev->name, skb->len, eoe->tx_queued_frames); |
831 eoe->dev->name, skb->len, eoe->tx_queued_frames); |