为以太网功能启用 MACsec

本页面介绍了如何为以太网功能启用 MACsec。

您可以使用 MACsec 针对不同的 ECU 单元为车载信息娱乐系统 (IVI) 使用的以太网通信进行身份验证和加密,从而保护数据免遭篡改、重放或信息泄露。通过为以太网启用 MACsec IEEE 802.11AE 可实现这一目的。

概览

为了启用 MACsec,系统会将 wpa_supplicant 用作守护程序来处理 MACsec 密钥协议 (MKA) 握手。我们定义了一个 MACsec HAL,用于安全存储 MACsec 预共享密钥(称为连接关联密钥 (CAK))。MACsec HAL 仅支持 CAK。该供应商专用 MACsec HAL 将 CAK 安全地存储在防篡改的存储空间中。配置该密钥取决于供应商实现。

MACsec 流程

图 1 展示了车机上的 MACsec 流程。

图 1:MACsec 流程。

启用 MACsec

为了支持 MACsec CAK 密钥的功能,必须使用供应商专用 MACsec HAL 明确启用以太网 MACsec。

如需启用此功能,请将 wpa_supplicant_macsec 和供应商专用 macsec-service 设置为 PRODUCT_PACKAGES,并将 wpa_supplicant_macsecinit rc 脚本的配置文件设置为 PRODUCT_COPY_FILES

例如,以下 [device-product].mk 文件:

# MACSEC HAL

# This is a mock MACsec HAL implementation with keys embedded in it. Replace with vendor specific HAL
PRODUCT_PACKAGES += android.hardware.automotive.macsec-service

# wpa_supplicant build with MACsec support

PRODUCT_PACKAGES += wpa_supplicant_macsec

# configuration file for wpa_supplicant with MACsec

PRODUCT_COPY_FILES += \
    $(LOCAL_PATH)/wpa_supplicant_macsec.conf:$(TARGET_COPY_OUT_VENDOR)/etc/wpa_supplicant_macsec.conf \
    $(LOCAL_PATH)/wpa_supplicant_macsec.rc:$(TARGET_COPY_OUT_VENDOR)/etc/init/wpa_supplicant_macsec.rc

例如,wpa_supplicant_macsec.conf

# wpa_supplicant_macsec.conf
eapol_version=3
ap_scan=0
fast_reauth=1
# Example configuration for MACsec with preshared key
# mka_cak is not actual key but index for MACsec HAL to specify which key to use
# and make_cak must be either 16 digits or 32 digits depends the actually CAK key length.
network={
        key_mgmt=NONE
        eapol_flags=0
        macsec_policy=1
        macsec_replay_protect=1
        macsec_replay_window=0
        mka_cak=00000000000000000000000000000001
        mka_ckn=31323334
        mka_priority=128
}

eth0 上的示例 wpa_supplicant_macsec.conf。当多个网络接口需要受 MACsec 保护时,您可以启动多项服务。

# wpa_supplicant_macsec.rc
service wpa_supplicant_macsec /vendor/bin/hw/wpa_supplicant_macsec \
        -dd -i eth0 -Dmacsec_linux -c /vendor/etc/wpa_supplicant_macsec.conf
        oneshot

以太网接口准备就绪后,启动 wpa_supplicant_macsec。如果系统以太网尚未准备就绪,wpa_supplicant 会立即返回错误。 为避免出现竞态条件,/sys//class/net/${eth_interface} 可能需要等待(默认超时时间为五 (5) 秒)。

# init.target.rc
on late-fs
    …
    wait /sys/class/net/eth0
    start wpa_supplicant_macsec
    …

为 MACsec 接口配置 IP 地址

Zygote 启动后,MACsec 接口 IP 地址的配置可由系统连接管理器完成。下面是一个用于连接的叠加层 XML 文件示例。如果 MACsec 接口的 IP 地址需要在 zygote 启动之前准备就绪,则供应商专用守护程序需要监听 macsec0 接口并对其进行配置,因为系统连接管理器仅在 zygote 启动后启动。

# Example of com.google.android.connectivity.resources overlay config
<?xml version="1.0" encoding="utf-8"?>
<!-- Resources to configure the connectivity module based on each OEM's preference. -->
<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
    <!-- Whether the internal vehicle network should remain active even when no
         apps requested it. -->
    <bool name="config_vehicleInternalNetworkAlwaysRequested">true</bool>
    <string-array translatable="false" name="config_ethernet_interfaces">
        <!-- Not metered, trusted, not vpn, vehicle, not vcn managed, restricted -->
        <item>macsec0;11,14,15,27,28;ip=10.10.10.2/24 gateway=10.10.10.1 dns=4.4.4.4,8.8.8.8</item>
    </string-array>
    <string translatable="false" name="config_ethernet_iface_regex">macsec\\d</string>
</resources>

MACsec HAL

MACsec 供应商专用 HAL 必须实现以下函数来保护 CAK 密钥。使用密钥的所有加密和解密操作都直接完成,而不会向 wpa_supplicant 公开密钥。

/**
 * MACSEC pre-shared key plugin for wpa_applicant
 *
 * The goal of this service is to provide function for using the MACSEC CAK
 *
 */
@VintfStability
interface IMacsecPSKPlugin {
    /**
     * For xTS test only, not called in production
     *
     * @param keyId is key id to add
     * @param CAK, CAK key to set
     * @param CKN, CKN to set
     *
     * @return ICV.
     */
    void addTestKey(in byte[] keyId, in byte[] CAK, in byte[] CKN);

/** * Use ICV key do AES CMAC same as ieee802_1x_icv_aes_cmac in wpa_supplicant * * @param keyId is key id to be used for AES CMAC * @param data * * @return ICV. */ byte[] calcICV(in byte[] keyId, in byte[] data);
/** * KDF with CAK key to generate SAK key same as ieee802_1x_sak_aes_cmac in wpa_supplicant * * @param keyId is key id to be used for KDF * @param seed is key seed (random number) * @param sakLength generated SAK length (16 or 32) * * @return SAK key. */ byte[] generateSAK(in byte[] keyId, in byte[] data, in int sakLength);
/** * Encrypt using KEK key, this is same as aes_wrap with kek.key in wpa_supplicant * which used to wrap a SAK key * * @param keyId is key id to be used for encryption * @param sak is SAK key (16 or 32 bytes) to be wrapped. * * @return wrapped data using KEK key. */ byte[] wrapSAK(in byte[] keyId, in byte[] sak);
/** * Decrypt using KEK key, this is same as aes_unwrap with kek.key in wpa_supplicant * which used to unwrap a SAK key * * @param keyId is key id to be used for decryption * @param sak is wrapped SAK key. * * @return unwrapped data using KEK key. */ byte[] unwrapSAK(in byte[] keyId, in byte[] sak); }

参考实现

hardware/interfaces/macsec/aidl/default 中提供了参考实现,它提供了 HAL 的软件实现(其中嵌入了密钥)。此实现仅提供对 HAL 的功能引用,因为密钥不受防篡改存储空间的支持。

测试 MACsec HAL

hardware/interfaces/automotive/macsec/aidl/vts/functional 中提供了 MACsec HAL 测试。

如需运行测试,请执行以下操作:

$ atest VtsHalMacsecPskPluginV1Test

这会调用 addTestKey--,以将测试密钥插入 HAL,并根据 calcIcvgenerateSakwrapSakunwrapSak 的预期值进行验证。

如需确认 MACsec 是否正常工作,对于集成测试,请在 MACsec 接口中的两台机器之间执行 ping 操作:

# ping -I macsec0 10.10.10.1

如需使用主机测试 Cuttlefish,需要主机中的 echo 8 > /sys/devices/virtual/net/cvd-ebr/bridge/group_fwd_mask 才能允许透传 MACsec 所需的 LLDP 帧。