CAN FD와 Ethernet을 비교할 때 가장 먼저 눈에 들어오는 숫자는 64바이트와 1500바이트 입니다. CAN FD 한 프레임의 데이터 필드는 최대 64바이트이고, 일반적인 Ethernet의 MAC 데이터 영역은 최대 1500바이트입니다.

그러나 이 숫자를 곧바로 “내 프로그램이 한 번에 보낼 수 있는 데이터”로 읽으면 혼동이 생깁니다. Ethernet 위에 IP와 UDP 또는 TCP를 사용하면 그 헤더가 1500바이트 안에 들어갑니다. CAN FD도 자체 메시지 헤더나 분할 전송 프로토콜을 사용하면 64바이트 전부를 애플리케이션 데이터로 쓰지 못할 수 있습니다.

이 글은 일반적인 MTU 1500의 Ethernet II, 단일 링크, 비태그 프레임을 기본으로 설명합니다. 별도로 표시한 경우를 제외하면 IP 옵션, IPv6 확장 헤더, 터널, 암호화, 애플리케이션 헤더는 없다고 가정합니다. 수치 예제는 설계 계산이며 실측 결과가 아닙니다.

1. 무엇의 페이로드를 비교하는가

페이로드는 해당 계층이 전달하는 데이터입니다. 상위 계층의 헤더는 하위 계층에서는 페이로드의 일부가 될 수 있습니다.

Ethernet MAC 데이터 영역: 최대 1500B
└─ IPv4 패킷
   ├─ IPv4 헤더: 최소 20B
   └─ UDP 데이터그램
      ├─ UDP 헤더: 8B
      └─ 애플리케이션 데이터: 최대 1472B

CAN FD에서 링크 계층의 데이터 필드는 다음처럼 사용할 수 있습니다.

CAN FD 데이터 필드: 최대 64B
├─ 자체 프로토콜 헤더: 예를 들어 4B
└─ 애플리케이션 데이터: 이 경우 최대 60B

여기서 4바이트는 설명을 위한 가상 설계입니다. CAN FD가 모든 데이터 필드에 공통으로 요구하는 애플리케이션 헤더가 아닙니다.

CAN FD의 64바이트와 Ethernet의 1500바이트 데이터 영역을 계층별로 나눈 개념도

비교 대상 CAN FD Ethernet II
링크 계층 데이터 영역의 최대 크기 64B 일반적인 구성에서 1500B
상위 프로토콜 헤더 사용한 프로토콜에 따라 다름 IP·UDP·TCP 등을 사용하면 MAC 데이터 영역 안에 포함
애플리케이션 데이터 자체 헤더 등을 뺀 나머지 IP·전송 계층·애플리케이션 헤더 등을 뺀 나머지
더 큰 메시지 여러 프레임으로 분할하는 상위 프로토콜 필요 TCP 세그먼트화, UDP 메시지 분할 등 선택한 계층에 따라 처리

CAN FD의 최대 64바이트는 Bosch CAN FD 설명을, 기본 Ethernet 프레임 구조는 Microchip Ethernet Controller 문서를 참고했습니다.

2. CAN FD는 0~64바이트를 모두 자유롭게 선택하지 않는다

CAN FD의 DLC(Data Length Code)는 4비트 코드입니다. 0~8바이트 구간은 코드와 길이가 같지만, 그 이후에는 지정된 길이만 표현합니다.

DLC 데이터 필드 길이
0~8 0~8B
9 12B
10 16B
11 20B
12 24B
13 32B
14 48B
15 64B

이 매핑은 Microchip DLC Encoding 문서에서 확인할 수 있습니다.

예를 들어 필요한 데이터가 9바이트라면 데이터 필드 길이를 12바이트로 선택하고 나머지 3바이트를 처리해야 합니다. 필요한 데이터가 33바이트라면 48바이트 길이를 선택해야 합니다.

유효 데이터 33B → DLC 14 → 실제 데이터 필드 48B
남는 영역: 15B
데이터 필드 내부의 유효 데이터 비율: 33 / 48 = 68.75%

수신 측이 유효 길이를 어떻게 아는지도 정해야 합니다. 메시지 ID별 고정 구조를 정의하거나, 데이터 필드 안에 길이 정보를 넣을 수 있습니다. 패딩 값과 초기화는 드라이버·컨트롤러·사용한 프로토콜의 동작을 확인해야 하며, 남은 메모리가 자동으로 안전하게 채워진다고 가정하면 안 됩니다.

이 68.75%는 데이터 필드 내부 비율입니다. 중재, 제어, CRC, ACK, 비트 스터핑 등까지 포함한 전체 버스 효율은 아닙니다.

3. Ethernet의 1500, 1518, 1538은 서로 다른 숫자다

기본적인 비태그 Ethernet II 프레임을 다음처럼 나눌 수 있습니다.

구성 요소 크기 또는 시간에 해당하는 바이트 수
Destination MAC 6B
Source MAC 6B
EtherType 2B
MAC 데이터와 필요한 패딩 46~1500B
FCS 4B
Preamble + SFD 8B
최소 Interframe Gap(IFG) 96비트 시간, 12B 시간에 해당

EtherType까지의 헤더는 14바이트입니다. 최대 MAC 프레임 길이는 14 + 1500 + 4 = 1518B이며, 여기에는 Preamble과 SFD가 포함되지 않습니다.

연속 전송의 링크 사용 시간을 계산할 때 Preamble/SFD와 IFG까지 반영하면 다음과 같습니다.

최대 MAC 프레임: 1518B
Preamble + SFD:      8B
IFG 시간 등가:      12B
합계:            1538B에 해당하는 비트 시간

IFG는 프레임에 붙여 전송하는 12바이트 데이터가 아니라 프레임 사이의 시간 간격입니다. 따라서 1538바이트를 MAC 프레임 크기라고 부르면 안 됩니다. IFG를 포함한 값은 연속 프레임 전송의 처리율 계산에 적합합니다.

프레임의 최소·최대 길이는 Microchip Ethernet Controller 문서, 프리앰블과 최소 96비트 시간 간격은 Microchip Transmit Block 문서를 참고했습니다.

4. UDP와 TCP에서는 실제 데이터가 얼마나 남을까

IP MTU 1500을 기준으로 계산하면 다음과 같습니다.

Ethernet 위의 구성 IP 헤더 전송 계층 헤더 한 패킷/세그먼트의 데이터 상한
IPv4 + UDP 20B 8B 1472B
IPv4 + TCP, 옵션 없음 20B 20B 1460B
IPv6 + UDP, 확장 헤더 없음 40B 8B 1452B
IPv6 + TCP, 옵션·확장 헤더 없음 40B 20B 1440B
IPv4 + UDP: 1500 - 20 - 8 = 1472B
IPv4 + TCP: 1500 - 20 - 20 = 1460B
IPv6 + UDP: 1500 - 40 - 8 = 1452B
IPv6 + TCP: 1500 - 40 - 20 = 1440B

헤더 정의는 RFC 8200, RFC 768, RFC 9293을 참고했습니다. 실제 TCP에서는 옵션, 상대가 광고한 MSS, 경로 MTU 등의 조건 때문에 한 세그먼트의 데이터가 더 작아질 수 있습니다.

UDP 예제에서 애플리케이션 자체 헤더를 12바이트 추가한다면 실질적인 데이터 상한은 1472 - 12 = 1460B가 됩니다. 이는 TCP의 1460바이트와 숫자만 같을 뿐 의미는 다릅니다.

TCP의 1460바이트는 한 번의 send() 호출 제한이 아닙니다. TCP는 바이트 스트림이므로 큰 데이터를 여러 세그먼트로 나눌 수 있고, 수신 측의 recv()가 송신 측 호출과 동일한 경계로 반환된다는 보장도 없습니다. 메시지 길이 등의 프레이밍을 애플리케이션에서 정의해야 합니다.

UDP도 더 큰 데이터그램을 만들 수 있는 경우가 있지만, 경로 MTU를 넘으면 IP 단편화나 전송 실패 등 별도 조건이 생깁니다. 1472바이트는 이 가정에서 IPv4 단편화 없이 한 MTU 1500 패킷에 담는 UDP 데이터의 상한이지 UDP 자체의 절대 최대 크기가 아닙니다.

5. 같은 64바이트 데이터를 보낼 때

애플리케이션 데이터가 64바이트이고 자체 헤더가 없다고 가정합니다.

CAN FD

64바이트가 한 프레임의 데이터 필드에 들어갑니다. 여기에 링크 계층의 다른 비트가 추가됩니다. 프레임 전체가 64바이트라는 뜻은 아닙니다.

Ethernet + IPv4 + UDP

애플리케이션 데이터:     64B
UDP 헤더:                8B
IPv4 헤더:              20B
MAC 데이터 영역 사용:   92B
Ethernet 헤더 + FCS:    18B
MAC 프레임:            110B
Preamble/SFD + IFG:     20B 시간 등가
링크 사용량:           130B 시간 등가

100Mbit/s Ethernet에서 IFG까지 포함한 이 프레임의 연속 전송 주기는 다음과 같습니다.

130 × 8 / 100,000,000 = 10.4μs
유효 데이터 비율 = 64 / 130 ≈ 49.23%

비율이 절반 정도라고 해도 절대 전송 시간이 길다는 의미는 아닙니다. 전송 효율과 링크 속도는 별개의 변수입니다. 여기의 10.4μs는 소켓 호출부터 상대 프로그램의 수신까지 걸리는 시간도 아닙니다.

6. 작은 데이터를 보낼수록 헤더와 패딩의 비중이 커진다

IPv4 + UDP로 8바이트 데이터를 보내면 IP 패킷 크기는 20 + 8 + 8 = 36B입니다. 비태그 Ethernet MAC 데이터 영역의 최소 46바이트를 채우기 위해 10바이트 패딩이 필요합니다.

MAC 데이터와 패딩:       46B
Ethernet 헤더 + FCS:     18B
MAC 프레임:              64B
Preamble/SFD + IFG:      20B 시간 등가
합계:                    84B 시간 등가

다음 표의 효율은 애플리케이션 데이터 / IFG를 포함한 링크 시간 등가 바이트 수입니다.

UDP 애플리케이션 데이터 MAC 데이터, 패딩 전 패딩 링크 시간 등가 바이트 100Mbit/s 전송 주기 유효 데이터 비율
8B 36B 10B 84B 6.72μs 9.52%
64B 92B 0B 130B 10.40μs 49.23%
256B 284B 0B 322B 25.76μs 79.50%
1472B 1500B 0B 1538B 123.04μs 95.71%

여러 작은 데이터를 묶으면 헤더 비율을 낮출 수 있지만, 데이터를 모으기 위한 대기 시간이 늘어납니다.

예를 들어 센서 값을 1ms마다 생성하고 10건이 모이면 전송한다면, 첫 번째 값은 마지막 값이 생성될 때까지 약 9ms 기다립니다. 전송 효율과 데이터의 최신성 사이에서 요구사항에 맞는 선택이 필요합니다.

7. CAN FD의 데이터 비트레이트만으로 시간을 계산하지 않기

CAN FD에서 BRS(Bit Rate Switch)를 사용하면 정해진 구간을 데이터 페이즈의 비트레이트로 전송할 수 있습니다. 프레임 전체가 그 속도로 전송되는 것은 아닙니다.

개념적인 프레임 시간
  = 공칭 비트레이트 구간의 비트 수 / 공칭 비트레이트
  + 데이터 비트레이트 구간의 비트 수 / 데이터 비트레이트

정확한 계산에는 11비트/29비트 ID, ISO CAN FD 프레임 구조, CRC, 동적·고정 스터프 비트, BRS 유무, ACK 등을 반영해야 합니다. 송신 요청부터 걸리는 시간이라면 큐와 중재 대기, 오류 재전송도 별도로 고려합니다. Microchip CAN FD Operation을 참고하세요.

64바이트를 데이터 페이즈 2Mbit/s로 보낼 때, 원래의 데이터 512비트만 계산하면 다음과 같습니다.

64 × 8 / 2,000,000 = 256μs

256μs는 스터프 비트와 나머지 필드를 제외한 데이터 512비트의 시간입니다. 완전한 CAN FD 프레임 전송 시간이 아닙니다. Ethernet의 10.4μs와 동일한 조건의 프레임 시간으로 비교하면 안 됩니다.

8. 1024바이트 메시지는 몇 프레임이 필요한가

CAN FD에서 상위 헤더나 흐름 제어 없이 데이터를 채운다는 가정이라면 필요한 용량은 다음과 같습니다.

ceil(1024 / 64) = 16프레임

이는 데이터 용량만으로 구한 값입니다. 실제 설계에는 순서, 메시지 길이, 누락 검출과 재조립을 다루는 방법이 필요합니다.

각 프레임의 데이터 필드에 자체 헤더 4바이트를 넣는 예제에서는 유효 데이터가 최대 60바이트입니다.

ceil(1024 / 60) = 18개의 데이터 프레임

17프레임에 60바이트씩 넣으면 1020바이트이고, 마지막 프레임은 남은 데이터 4바이트와 헤더 4바이트로 8바이트가 됩니다. 이 가정에서는 마지막 데이터 필드를 64바이트로 만들 필요가 없습니다. 응답이나 흐름 제어 프레임이 있다면 따로 더해야 합니다. 이 예제는 ISO-TP 등 특정 표준 프로토콜의 계산이 아닙니다.

IPv4 + UDP에서는 1024바이트가 1472바이트 이하이므로, 이 조건에서 단편화 없이 하나의 IP 패킷에 들어갑니다.

1024 + 20 + 8 + 14 + 4 + 8 + 12 = 1090B 시간 등가
100Mbit/s에서 IFG를 포함한 주기 = 1090 × 8 / 100,000,000 = 87.2μs

프레임 수가 줄면 재조립 작업도 줄지만, 한 프레임을 잃었을 때 누락되는 데이터 양도 달라집니다. 재송신 단위와 필요한 신뢰성, 버퍼 크기를 함께 검토해야 합니다.

9. VLAN과 점보 프레임

단일 802.1Q VLAN 태그는 MAC 헤더 쪽에 4바이트를 추가합니다. 태그를 지원하는 구성에서는 IP MTU를 1500으로 유지하면서 MAC 프레임 최대 길이가 1522바이트가 될 수 있습니다. VLAN이 있다는 이유만으로 UDP 데이터 상한이 항상 1468바이트가 되는 것은 아닙니다. 인터페이스와 경로의 실제 MTU를 확인합니다.

태그 포함 1522바이트 프레임의 예시는 Microchip LAN950x 데이터시트에서 확인할 수 있습니다.

점보 프레임은 1500보다 큰 MTU를 사용하는 구성입니다. 9000 등의 값은 모든 Ethernet에서 공통으로 보장하는 값이 아니므로 송수신 장치, 스위치와 경로 설정을 확인해야 합니다. 장비가 표시한 값이 IP MTU인지 MAC 프레임 길이인지도 구별합니다.

Ethernet이라고 항상 IP와 UDP를 쓰는 것도 아닙니다. 별도 EtherType을 사용하는 Raw Ethernet에서는 상위 헤더 구성이 달라집니다.

10. 설계에서 실제로 비교할 항목

확인 사항 이유
데이터 크기와 생성 주기 작은 주기 데이터와 대용량 메시지를 구별
상위 헤더와 메시지 경계 실제 유효 데이터 용량 계산
최대 응답 시간과 지터 평균 처리량만으로 기한을 판단할 수 없음
CAN 버스 부하와 중재 전송을 시작하기까지의 대기 확인
Ethernet 큐와 스위치 경로 링크 직렬화 외의 지연 확인
재전송·누락 검출·순서 보장 링크 검사와 애플리케이션 신뢰성을 구별
MCU의 RAM·CPU와 드라이버 데이터를 보관하고 처리할 수 있는지 확인

CAN에 중재가 있다고 모든 메시지의 기한이 자동으로 보장되는 것은 아닙니다. Ethernet의 비트레이트가 높다고 애플리케이션 응답 시간도 항상 짧아지는 것은 아닙니다. 레이턴시와 지터의 차이에서 측정 구간과 타이밍 변동을 함께 살펴볼 수 있습니다.

11. Python으로 용량과 Ethernet 링크 사용 시간 계산하기

본문과 같은 비태그 Ethernet II·옵션 없는 IPv4·UDP 조건입니다. IFG까지 포함한 연속 전송 주기를 계산하며, 애플리케이션 간 응답 시간을 계산하는 코드는 아닙니다.

import math

CAN_FD_LENGTHS = list(range(9)) + [12, 16, 20, 24, 32, 48, 64]


def can_fd_data_field_size(required_bytes):
    if not isinstance(required_bytes, int) or not 0 <= required_bytes <= 64:
        raise ValueError("필요한 길이는 0~64의 정수여야 합니다.")
    return next(size for size in CAN_FD_LENGTHS if size >= required_bytes)


def ethernet_ipv4_udp(app_bytes, link_mbps=100):
    if not isinstance(app_bytes, int) or not 0 <= app_bytes <= 1472:
        raise ValueError("단일 MTU 1500 조건에서 데이터 길이는 0~1472입니다.")
    if not math.isfinite(link_mbps) or link_mbps <= 0:
        raise ValueError("링크 속도는 유한한 양수여야 합니다.")

    ip_packet = 20 + 8 + app_bytes
    padding = max(0, 46 - ip_packet)
    mac_frame = 14 + ip_packet + padding + 4
    byte_times = 8 + mac_frame + 12
    return {
        "padding_bytes": padding,
        "mac_frame_bytes": mac_frame,
        "link_byte_times_including_ifg": byte_times,
        "cycle_us_including_ifg": byte_times * 8 / link_mbps,
        "application_efficiency": app_bytes / byte_times,
    }


print("33B를 담는 CAN FD 데이터 필드:", can_fd_data_field_size(33))
for size in [8, 64, 256, 1024, 1472]:
    print(size, ethernet_ipv4_udp(size))

CAN FD 함수는 DLC가 표현할 수 있는 데이터 필드 크기만 계산합니다. 상위 헤더, 전체 프레임 전송 시간, 버스 대기를 계산하지 않습니다.

계층을 맞추고, 상위 헤더를 차감하고, 패딩과 분할을 반영한 다음 링크 속도와 대기를 각각 평가해야 합니다. 64와 1500의 크기 비교에서 시작하되, 실제 애플리케이션이 보내려는 데이터 단위로 계산해야 설계에 활용할 수 있습니다.

참고 자료