Microchip® Advanced Software Framework

 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
Ethernet Media Access Controller

See Quickstart guide for EMAC driver..

Driver for the EMAC (Ethernet Media Access Controller). This file contains basic functions for the EMAC, with support for all modes, settings and clock speeds.

Dependencies

This driver does not depend on other modules.

Modules

 
 Quick Start Guide(s)
 In this section you can find a list of all Quick Start guides related to the Ethernet Media Access Controller.
 

Data Structures

struct  emac_dev_mem
 EMAC device memory management struct. More...
 

Macros

#define CIRC_CLEAR(head, tail)   (head = tail = 0)
 Clear circular buffer. More...
 
#define CIRC_CNT(head, tail, size)   (((head) - (tail)) % (size))
 Return count in buffer. More...
 
#define CIRC_EMPTY(head, tail)   (head == tail)
 Circular buffer is empty ? More...
 
#define CIRC_SPACE(head, tail, size)   CIRC_CNT((tail),((head)+1),(size))
 

Typedefs

typedef struct emac_dev_mem emac_dev_mem_t
 EMAC device memory management struct. More...
 

Functions

static void circ_inc (uint16_t *headortail, uint32_t size)
 Increment head or tail. More...
 
uint32_t emac_dev_get_tx_load (emac_device_t *p_emac_dev)
 Get current load of transmit. More...
 
void emac_dev_init (Emac *p_emac, emac_device_t *p_emac_dev, emac_options_t *p_opt)
 Initialize the EMAC driver. More...
 
uint32_t emac_dev_read (emac_device_t *p_emac_dev, uint8_t *p_frame, uint32_t ul_frame_size, uint32_t *p_rcv_size)
 Frames can be read from the EMAC in multiple sections. More...
 
void emac_dev_reset (emac_device_t *p_emac_dev)
 Reset TX & RX queue & statistics. More...
 
void emac_dev_set_rx_callback (emac_device_t *p_emac_dev, emac_dev_tx_cb_t func_rx_cb)
 Register/Clear RX callback. More...
 
uint8_t emac_dev_set_tx_wakeup_callback (emac_device_t *p_emac_dev, emac_dev_wakeup_cb_t func_wakeup_cb, uint8_t uc_threshold)
 Register/Clear TX wakeup callback. More...
 
uint32_t emac_dev_write (emac_device_t *p_emac_dev, void *p_buffer, uint32_t ul_size, emac_dev_tx_cb_t func_tx_cb)
 Send ulLength bytes from pcFrom. More...
 
void emac_handler (emac_device_t *p_emac_dev)
 EMAC Interrupt handler. More...
 
static uint8_t emac_init_mem (Emac *p_emac, emac_device_t *p_emac_dev, emac_dev_mem_t *p_dev_mm, emac_dev_tx_cb_t *p_tx_cb)
 Initialize the allocated buffer lists for EMAC driver to transfer data. More...
 
uint8_t emac_phy_read (Emac *p_emac, uint8_t uc_phy_address, uint8_t uc_address, uint32_t *p_value)
 Read the PHY register. More...
 
uint8_t emac_phy_write (Emac *p_emac, uint8_t uc_phy_address, uint8_t uc_address, uint32_t ul_value)
 Write the PHY register. More...
 
static void emac_reset_rx_mem (emac_device_t *p_dev)
 Disable receiver, reset registers and descriptor list. More...
 
static void emac_reset_tx_mem (emac_device_t *p_dev)
 Disable transfer, reset registers and descriptor lists. More...
 
static uint8_t emac_wait_phy (Emac *p_emac, const uint32_t ul_retry)
 Wait PHY operation to be completed. More...
 

Variables

static emac_rx_descriptor_t gs_rx_desc [EMAC_RX_BUFFERS]
 RX descriptors lists. More...
 
static emac_dev_tx_cb_t gs_tx_callback [EMAC_TX_BUFFERS]
 TX callback lists. More...
 
static emac_tx_descriptor_t gs_tx_desc [EMAC_TX_BUFFERS]
 TX descriptor lists. More...
 
static uint8_t gs_uc_rx_buffer [EMAC_RX_BUFFERS *EMAC_RX_UNITSIZE]
 Receive Buffer. More...
 
static uint8_t gs_uc_tx_buffer [EMAC_TX_BUFFERS *EMAC_TX_UNITSIZE]
 Send Buffer. More...
 

#define CIRC_CLEAR (   head,
  tail 
)    (head = tail = 0)

Clear circular buffer.

Referenced by emac_reset_tx_mem().

#define CIRC_CNT (   head,
  tail,
  size 
)    (((head) - (tail)) % (size))

Return count in buffer.

Referenced by emac_dev_get_tx_load(), and emac_handler().

#define CIRC_EMPTY (   head,
  tail 
)    (head == tail)

Circular buffer is empty ?

Referenced by emac_handler().

#define CIRC_SPACE (   head,
  tail,
  size 
)    CIRC_CNT((tail),((head)+1),(size))

Referenced by emac_dev_write(), and emac_handler().

typedef struct emac_dev_mem emac_dev_mem_t

EMAC device memory management struct.

static void circ_inc ( uint16_t *  headortail,
uint32_t  size 
)
static

Increment head or tail.

Referenced by emac_dev_read(), emac_dev_write(), and emac_handler().

uint32_t emac_dev_get_tx_load ( emac_device_t p_emac_dev)

Get current load of transmit.

Parameters
p_emac_devPointer to the EMAC device instance.
Returns
Current load of transmit.

References CIRC_CNT, emac_device::us_tx_head, emac_device::us_tx_list_size, and emac_device::us_tx_tail.

uint32_t emac_dev_read ( emac_device_t p_emac_dev,
uint8_t *  p_frame,
uint32_t  ul_frame_size,
uint32_t *  p_rcv_size 
)

Frames can be read from the EMAC in multiple sections.

Read ul_frame_size bytes from the EMAC receive buffers to pcTo. p_rcv_size is the size of the entire frame. Generally emac_read will be repeatedly called until the sum of all the ul_frame_size equals the value of p_rcv_size.

Parameters
p_emac_devPointer to the EMAC device instance.
p_frameAddress of the frame buffer.
ul_frame_sizeLength of the frame.
p_rcv_sizeReceived frame size.
Returns
EMAC_OK if receiving frame successfully, otherwise failed.

References emac_rx_descriptor::addr, circ_inc(), EMAC_OK, EMAC_PARAM, EMAC_RX_NULL, EMAC_RX_UNITSIZE, EMAC_RXD_ADDR_MASK, EMAC_RXD_EOF, EMAC_RXD_LEN_MASK, EMAC_RXD_OWNERSHIP, EMAC_RXD_SOF, EMAC_SIZE_TOO_SMALL, NULL, emac_device::p_rx_dscr, emac_rx_descriptor::status, emac_device::us_rx_idx, emac_device::us_rx_list_size, emac_rx_descriptor::emac_rx_addr::val, and emac_rx_descriptor::emac_rx_status::val.

Referenced by low_level_input(), main(), and run_emac_read_write_test().

void emac_dev_reset ( emac_device_t p_emac_dev)

Reset TX & RX queue & statistics.

Parameters
p_emac_devPointer to EMAC device instance.

References emac_network_control(), emac_reset_rx_mem(), emac_reset_tx_mem(), and emac_device::p_hw.

void emac_dev_set_rx_callback ( emac_device_t p_emac_dev,
emac_dev_tx_cb_t  func_rx_cb 
)

Register/Clear RX callback.

Callback will be invoked after the next received frame.

When emac_dev_read() returns EMAC_RX_NULL, the application task calls emac_dev_set_rx_callback() to register func_rx_cb() callback and enters suspend state. The callback is in charge to resume the task once a new frame has been received. The next time emac_dev_read() is called, it will be successful.

This function is usually invoked from the RX callback itself with NULL callback, to unregister. Once the callback has resumed the application task, there is no need to invoke the callback again.

Parameters
p_emac_devPointer to the EMAC device instance.
func_tx_cbReceive callback function.

References emac_disable_interrupt(), emac_enable_interrupt(), emac_device::func_rx_cb, NULL, and emac_device::p_hw.

uint8_t emac_dev_set_tx_wakeup_callback ( emac_device_t p_emac_dev,
emac_dev_wakeup_cb_t  func_wakeup_cb,
uint8_t  uc_threshold 
)

Register/Clear TX wakeup callback.

When emac_dev_write() returns EMAC_TX_BUSY (all transmit descriptor busy), the application task calls emac_dev_set_tx_wakeup_callback() to register func_wakeup() callback and enters suspend state. The callback is in charge to resume the task once several transmit descriptors have been released. The next time emac_dev_write() will be called, it shall be successful.

This function is usually invoked with NULL callback from the TX wakeup callback itself, to unregister. Once the callback has resumed the application task, there is no need to invoke the callback again.

Parameters
p_emac_devPointer to EMAC device instance.
func_wakeupPointer to wakeup callback function.
uc_thresholdNumber of free transmit descriptor before wakeup callback invoked.
Returns
EMAC_OK, EMAC_PARAM on parameter error.

References EMAC_OK, EMAC_PARAM, emac_device::func_wakeup_cb, NULL, and emac_device::uc_wakeup_threshold.

uint32_t emac_dev_write ( emac_device_t p_emac_dev,
void *  p_buffer,
uint32_t  ul_size,
emac_dev_tx_cb_t  func_tx_cb 
)

Send ulLength bytes from pcFrom.

This copies the buffer to one of the EMAC Tx buffers, and then indicates to the EMAC that the buffer is ready. If lEndOfFrame is true then the data being copied is the end of the frame and the frame can be transmitted.

Parameters
p_emac_devPointer to the EMAC device instance.
p_bufferPointer to the data buffer.
ul_sizeLength of the frame.
func_tx_cbTransmit callback function.
Returns
Length sent.

References emac_tx_descriptor::addr, circ_inc(), CIRC_SPACE, EMAC_OK, EMAC_PARAM, emac_start_transmission(), EMAC_TX_BUSY, EMAC_TX_UNITSIZE, EMAC_TXD_LAST, EMAC_TXD_LEN_MASK, EMAC_TXD_WRAP, emac_device::func_tx_cb_list, emac_device::p_hw, emac_device::p_tx_dscr, emac_tx_descriptor::status, emac_device::us_tx_head, emac_device::us_tx_list_size, emac_device::us_tx_tail, and emac_tx_descriptor::emac_tx_status::val.

Referenced by emac_process_arp_packet(), emac_process_ip_packet(), low_level_output(), and run_emac_read_write_test().

static uint8_t emac_init_mem ( Emac *  p_emac,
emac_device_t p_emac_dev,
emac_dev_mem_t p_dev_mm,
emac_dev_tx_cb_t p_tx_cb 
)
static

Initialize the allocated buffer lists for EMAC driver to transfer data.

Must be invoked after emac_dev_init() but before RX/TX starts.

Note
If input address is not 8-byte aligned, the address is automatically adjusted and the list size is reduced by one.
Parameters
p_emacPointer to EMAC instance.
p_emac_devPointer to EMAC device instance.
p_dev_mmPointer to the EMAC memory management control block.
p_tx_cbPointer to allocated TX callback list.
Returns
EMAC_OK or EMAC_PARAM.

References emac_enable_interrupt(), emac_enable_receive(), emac_enable_statistics_write(), emac_enable_transmit(), EMAC_OK, EMAC_PARAM, emac_reset_rx_mem(), emac_reset_tx_mem(), emac_device::func_tx_cb_list, NULL, emac_dev_mem::p_rx_buffer, emac_device::p_rx_buffer, emac_dev_mem::p_rx_dscr, emac_device::p_rx_dscr, emac_dev_mem::p_tx_buffer, emac_device::p_tx_buffer, emac_dev_mem::p_tx_dscr, emac_device::p_tx_dscr, emac_device::us_rx_list_size, emac_dev_mem::us_rx_size, emac_device::us_tx_list_size, and emac_dev_mem::us_tx_size.

Referenced by emac_dev_init().

uint8_t emac_phy_read ( Emac *  p_emac,
uint8_t  uc_phy_address,
uint8_t  uc_address,
uint32_t *  p_value 
)

Read the PHY register.

Parameters
p_emacPointer to the EMAC instance.
uc_phy_addressPHY address.
uc_addressRegister address.
p_valuePointer to a 32-bit location to store read data.

EMAC_OK if successfully, EMAC_TIMEOUT if timeout.

References emac_get_phy_data(), emac_maintain_phy(), EMAC_OK, EMAC_TIMEOUT, and emac_wait_phy().

Referenced by ethernet_phy_auto_negotiate(), ethernet_phy_find_valid(), ethernet_phy_reset(), and ethernet_phy_set_link().

uint8_t emac_phy_write ( Emac *  p_emac,
uint8_t  uc_phy_address,
uint8_t  uc_address,
uint32_t  ul_value 
)

Write the PHY register.

Parameters
p_emacPointer to the EMAC instance.
uc_phy_addressPHY Address.
uc_addressRegister Address.
ul_valueData to write, actually 16-bit data.

EMAC_OK if successfully, EMAC_TIMEOUT if timeout.

References emac_maintain_phy(), EMAC_OK, EMAC_TIMEOUT, and emac_wait_phy().

Referenced by ethernet_phy_auto_negotiate(), and ethernet_phy_reset().

static uint8_t emac_wait_phy ( Emac *  p_emac,
const uint32_t  ul_retry 
)
static

Wait PHY operation to be completed.

Parameters
p_emacHW controller address.
ul_retryThe retry times, 0 to wait forever until completeness.

Return EMAC_OK if the operation is completed successfully.

References emac_is_phy_idle(), EMAC_OK, and EMAC_TIMEOUT.

Referenced by emac_phy_read(), and emac_phy_write().

emac_rx_descriptor_t gs_rx_desc[EMAC_RX_BUFFERS]
static

RX descriptors lists.

Referenced by emac_dev_init().

emac_dev_tx_cb_t gs_tx_callback[EMAC_TX_BUFFERS]
static

TX callback lists.

Referenced by emac_dev_init().

emac_tx_descriptor_t gs_tx_desc[EMAC_TX_BUFFERS]
static

TX descriptor lists.

Referenced by emac_dev_init().

uint8_t gs_uc_rx_buffer[EMAC_RX_BUFFERS *EMAC_RX_UNITSIZE]
static

Receive Buffer.

Referenced by emac_dev_init().

uint8_t gs_uc_tx_buffer[EMAC_TX_BUFFERS *EMAC_TX_UNITSIZE]
static

Send Buffer.

Section 3.6 of AMBA 2.0 spec states that burst should not cross the 1K Boundaries. Receive buffer manager write operations are burst of 2 words => 3 lsb bits of the address shall be set to 0.

Referenced by emac_dev_init().