4.4 Fast Ethernet Controller (FEC)
4.4.1 Introduction
Fast Ethernet Controller (FEC) 드라이버는 전체 IEEE 802.3/Ethernet CSMA/CD 미디어 액세스 컨트롤과 채널 인터페이스 기능을 수행한다.
FEC는 Ethernet 미디어에 대한 인터페이스를 완료하기 위해 외부 인터페이스 어댑터와 트랜시버 기능이 필요하다. 10Mbps, 100Mbps, 1000Mbps와 관련된 Ethernet 네트워크에서 반이중이나 전이중 작동을 지원한다.
FEC 드라이버는 아래 기능을 지원한다:
- 전이중/반이중 작동
- 링크 상태 변화 감지
- Auto-negotiation (자동 협상: 네트워크 속도와 전이중이나 반이중 작동을 결정)
- 충돌시 자동 재전송, CRC 생성과 같은 전송 기능
- 디바이스에서 전송 충돌과 같은 통계 얻기
네트워크 어댑터는 인터페이스 이름 ethx와 함께 ifconfig 커맨드를 사용하여 액세스할 수 있다. 드라이버는 외부 어댑터(PHY 디바이스)를 자동으로 검색(probe)한다.
4.4.2 Hardware Operation
FEC는 시스템을 LAN 네트워크에 인터페이스하는 Ethernet 컨트롤러이다.
FEC는 외부 Ethernet 트랜시버에 연결하기 위한 다양한 표준 MAC-PHY(물리적인) 인터페이스를 지원한다. FEC는 MII(10/100 Mbps), RMII(10/100 Mbps), 그리고 RGMII(10/100/1000 Mbps)를 지원한다. 또한, 125MHz에서 작동하는 4비트 reduced GMII를 사용하는, 1000 Mbps RGMII를 FEC는 지원한다.
디바이스 기능에 대한 간략한 개요는 여기에 제공된다. 자세한 내용은 Applications Processor Reference Manual의 FEC 장을 참조한다.
MII 모드에는, IEEE 802.3 표준에서 정의되고 EMAC에서 지원되는 18개의 신호가 있다. MII, RMII, RGMII 모드는 18개의 신호의 서브셋을 사용한다. 이러한 신호는 아래 테이블에 나열되어 있다.
Table 40. Pin Usage in MII, RMII and RGMII Modes
Direction | EMAC Pin Name |
RMII Usage | RGMII Usage (not supported by i.MX 6UltraLite) |
---|---|---|---|
In/Out | FEC_MDIO | Management Data Input/output |
Management Data Input/Output |
Out | FEC_MDC | General output | Management Data Clock |
Out | FEC_TXD[0] | Data out, bit 0 | Data out, bit 0 |
Out | FEC_TXD[1] | Data out, bit 1 | Data out, bit 1 |
Out | FEC_TXD[2] | Not Used | Data out, bit 2 |
Out | FEC_TXD[3] | Not Used | Data out, bit 3 |
Out | FEC_TX_EN | Transmit Enable | Transmit Enable |
Out | FEC_TX_ER | Not Used | Not Used |
In | FEC_CRS | Not Used | Not Used |
In | FEC_COL | Not Used | Not Used |
In | FEC_TX_CLK | Not Used | Synchronous clock reference (REF_CLK, can connect from PHY) |
In | FEC_RX_ER | Receive Error | Not Used |
In | FEC_RX_CLK | Not Used | Synchronous clock reference (REF_CLK, can connect from PHY) |
In | FEC_RX_DV | Receive Data Valid and generate CRS |
RXDV XOR RXERR on the falling edge of FEC_RX_CLK |
In | FEC_RXD[0] | Data in, bit 0 | Data in, bit 0 |
In | FEC_RXD[1] | Data in, bit 1 | Data in, bit 1 |
In | FEC_RXD[2] | Not Used | Data in, bit 2 |
In | FEC_RXD[3] | Not Used | Data in, bit 3 |
MII 관리 인터페이스는 FEC_MDIO와 FEC_MDC의 두 핀으로 구성된다. FEC 하드웨어 작업은 아래 나열된 부분으로 나뉠 수 있다. 자세한 내용은 Applications Processor Reference Manuals을 참조한다.
- Transmission(송신) - Ethernet 트랜스미터는 소프트웨어의 개입이 거의 없이 작동하도록 디자인되어 있다. ECR[ETHER_EN]이 어설션되고 전송 FIFO에 데이터가 나타나면, Ethernet MAC은 네트워크로 전송할 수 있다. 전송 FIFO에 워터 마크(TFWR에 의해 정의된)까지 채워지면, MAC 전송 로직은 FEC_TX_EN을 어설션하고 프리앰블(PA: preamble) 시퀀스, 시작 프레임 구분자(SFD: start frame delimiter), 그리고 FIFO의 프레임 정보를 전송하기 시작한다. 그러나 컨트롤러는 네트워크가 busy인 경우 전송을 연기한다(FEC_CRS 어설션).
- 전송하기 전에, 컨트롤러는 반송파(carrier) 감지가 비활성화될 때까지 기다린 다음, 반송파 감지가 60비트 시간 동안 비활성 상태를 유지하는지 확인한다. 추가로 36비트 시간(반송파 감지가 원래 비활성화된 후 96비트 시간)을 기다린 후 전송이 시작되면, EMIR의 설정에 따라 버퍼(TXB)와 프레임(TXF) 인터럽트가 모두 생성될 수 있다.
- Reception(수신) - FEC 리시버는 호스트의 개입이 거의 없이 작동하도록 디자인되었으며, 주소 인식, CRC 확인, 짧은 프레임 확인과 최대 프레임 길이 확인을 수행할 수 있다. 드라이버에서 ECR[ETHER_EN]을 어설션하여 FEC 리시버를 활성화하면, 즉시 프레임 수신 처리를 시작한다. FEC_RX_DV가 어설션되면, 리시버는 유효한 PA/SFD 헤더를 확인한다. PA/SFD가 유효하면, 스트립(PA/SFD가 제거)되고 프레임은 리시버에서 처리된다. 유효한 PA/SFD가 없으면, 프레임이 무시된다. MII 모드에서 리시버는 SFD와 일치하는 적어도 하나의 바이트를 확인한다. 0개 이상의 PA 바이트가 발생할 수 있지만, SFD 바이트 이전에 00 비트 시퀀스가 감지되면 프레임은 무시된다.
- 프레임의 처음 6바이트가 수신된 후, FEC는 프레임에서 주소 인식을 수행한다. 수신하는 동안, Ethernet 컨트롤러는 다양한 오류 조건을 확인하고 전체 프레임이 FIFO에 저장되면, 32비트 프레임 상태 워드(status word)를 FIFO에 저장한다. 이 상태 워드에는 M, BC, MC, LG, NO, CR, OV, 그리고 TR 상태 비트와 프레임 길이를 포함되어 있다. EIMR 레지스터에 의해 활성화된 경우, Receive Buffer(RXB)와 Frame Interrupts(RXF)가 생성될 수 있다. 수신 프레임이 완료되면, FEC는 RxBD의 L 비트를 설정하고, 다른 프레임 상태 비트를 RxBD에 저장하고, E 비트를 제거(clear)한다. 다음으로 Ethernet 컨트롤러는 마스크 가능한 인터럽트(EIR의 RXF 비트, EIMR의 RXF 비트로 마스크 가능)를 생성하여, 프레임이 수신되어 메모리에 있다는 것을 나타낸다. 그런 다음 Ethernet 컨트롤러는 새로운 프레임을 기다린다.
- Interrupt management(인터럽트 관리) - EIR에 비트를 설정하는 이벤트가 발생할 때, EIMR(interrupt mask register)의 해당 비트도 설정되어 있으면, 인터럽트가 발생한다. 해당 비트 위치에 1을 저장(0을 저장하는 것은 효과가 없다)하면, EIR의 비트가 제거(clear)된다. 이 레지스터는 하드웨어 리셋 시 지워진다. 이러한 인터럽트는 작동 인터럽트, 트랜시버/네트워크 오류 인터럽트, 그리고 내부 오류 인터럽트로 나눌 수 있다. 정상적인 동작에서 발생할 수 있는 인터럽트는 GRA, TXF, TXB, RXF, RXB이다. 네트워크나 트랜시버에서 감지된 오류/문제로 인해 발생하는 인터럽트는 HBERR, BABR, BABT, LC, RL이다. 내부 오류로 인한 인터럽트는 HBERR, UN이다. 오류 인터럽트 중 일부는 MIB 블록 카운터에서 독립적으로 계산된다. 이러한 오류는 MIB 카운터로 네트워크 관리에 표시되므로, 소프트웨어는 이러한 인터럽트를 마스킹하도록 선택할 수 있다.
- PHY management(PHY 관리) - phylib는 PHY 검색(discovery), 링크 상태와 상태 머신과 같은 모든 FEC PHY 관련 작업을 관리하는 데 사용된다. MDIO 버스는 FEC 드라이버에서 생성되어 시스템에 등록된다. 자세한 내용은 Linux OS 소스 디렉토리 아래에서 Documentation/networking/phy.txt를 참조한다.
4.4.3 Software Operation
FEC 드라이버는 아래 기능을 지원한다:
- Module initialization(모듈 초기화) - 디바이스별 구조체로 모듈 초기화
- Rx/Tx 전송
- 인터럽트 서비스 루틴
- PHY 관리
- init/start/stop와 같은 FEC 관리
- 리틀 엔디안 형식을 사용하는 i.MX 6 FEC 모듈
4.4.4 Source Code Structure
아래 테이블은 소스 파일을 보여준다.
이 파일은 drivers/net/ethernet/freescale 디렉토리에서 사용할 수 있다.
Table 41. FEC Driver Files
File | Description |
---|---|
drivers/net/ethernet/freescale/fec.h | 레지스터를 정의하는 헤더 파일 |
drivers/net/ethernet/freescale/fec_main.c | Ethernet LAN 컨트롤러를 위한 Linux 드라이버 |
drivers/net/ethernet/freescale/fec_fixup.c | SoC와 PHY 특수 구현을 위한 Linux 드라이버 |
4.4.5 Menu Configuration Options
이 모듈을 제공하도록 커널을 구성한다:
- CONFIG_FEC는 이 모듈을 위해 제공되고 있다. 이 옵션은 아래에서 사용할 수 있다:
- Device Drivers > Network device support > Ethernet (10, 100 or 1000 Mbit) > FEC Ethernet controller
- FEC로 NFC-rootfs를 마운트하려면, 필요한 경우 menuconfig에서 다른 네트워크 구성을 비활성화한다.
4.4.6 Programming Interface
디바이스별 정의는 헤더 파일(fec.h)에 추가되고, 공통적인 보드 구성 옵션을 제공한다.
fec.h는 레지스터 액세스를 위한 구조체와 버퍼 디스크립터를 위한 구조체를 정의한다. 예를 들어,
/*
* Define the buffer descriptor structure.
*/
struct bufdesc {
unsigned short cbd_datlen; /* Data length */
unsigned short cbd_sc; /* Control and status info */
unsigned long cbd_bufaddr; /* Buffer address */
};
struct bufdesc_ex {
struct bufdesc desc;
unsigned long cbd_esc;
unsigned long cbd_prot;
unsigned long cbd_bdu;
unsigned long ts;
unsigned short res0[4];
};
/*
* Define the register access structure.
*/
#define FEC_IEVENT 0x004 /* Interrupt event reg */
#define FEC_IMASK 0x008 /* Interrupt mask reg */
#define FEC_R_DES_ACTIVE 0x010 /* Receive descriptor reg */
#define FEC_X_DES_ACTIVE 0x014 /* Transmit descriptor reg */
#define FEC_ECNTRL 0x024 /* Ethernet control reg */
#define FEC_MII_DATA 0x040 /* MII manage frame reg */
#define FEC_MII_SPEED 0x044 /* MII speed control reg */
#define FEC_MIB_CTRLSTAT 0x064 /* MIB control/status reg */
#define FEC_R_CNTRL 0x084 /* Receive control reg */
#define FEC_X_CNTRL 0x0c4 /* Transmit Control reg */
#define FEC_ADDR_LOW 0x0e4 /* Low 32bits MAC address */
#define FEC_ADDR_HIGH 0x0e8 /* High 16bits MAC address */
#define FEC_OPD 0x0ec /* Opcode + Pause duration */
#define FEC_HASH_TABLE_HIGH 0x118 /* High 32bits hash table */
#define FEC_HASH_TABLE_LOW 0x11c /* Low 32bits hash table */
#define FEC_GRP_HASH_TABLE_HIGH 0x120 /* High 32bits hash table */
#define FEC_GRP_HASH_TABLE_LOW 0x124 /* Low 32bits hash table */
#define FEC_X_WMRK 0x144 /* FIFO transmit water mark */
#define FEC_R_BOUND 0x14c /* FIFO receive bound reg */
#define FEC_R_FSTART 0x150 /* FIFO receive start reg */
#define FEC_R_DES_START 0x180 /* Receive descriptor ring */
#define FEC_X_DES_START 0x184 /* Transmit descriptor ring */
#define FEC_R_BUFF_SIZE 0x188 /* Maximum receive buff size */
#define FEC_MIIGSK_CFGR 0x300 /* MIIGSK config register */
#define FEC_MIIGSK_ENR 0x308 /* MIIGSK enable register */
4.4.6.1 Getting a MAC Address
MAC 주소는 커널 커맨드 라인, 커널 디바이스 트리 DTS 파일, OCOTP나 U-Boot와 같은 부트로더에 의해 설정된 MAC 레지스터로 설정할 수 있다. FEC 드라이버는 이를 사용하여 네트워크 디바이스의 MAC 주소를 구성한다. 일반적으로, "fec.macaddr=0x00,0x04,0x9f,0x01,0x30,0xe0" 형식의 커널 커맨드 라인을 사용하여 MAC 주소를 설정한다. 특정 핀의 충돌로 인해(FEC RMII 모드는 GPIO_16이나 RGMII_TX_CTL 핀을 레퍼런스 클럭 입력/출력 채널로 사용해야 함), 분기 라인이 클럭에 심각한 영향을 미치기 때문에 다른 모듈에서 사용하기 위해, 두 핀 중 하나는 분기 라인에 연결할 수 없다.