今日も秋田で IoT

旧 Trema 日記

Features Request でスイッチから情報を取得する (その4)

今回もTremaを少し離れて、OpenFlow 1.0 の仕様の話です。今回は Features Request/Reply で取得できるポートの情報について見ていきます。

ポート情報を格納するための構造体 struct ofp_phy_port は、以下のように定義されています。

struct ofp_phy_port {
    uint16_t port_no;
    uint8_t hw_addr[OFP_ETH_ALEN];
    char name[OFP_MAX_PORT_NAME_LEN]; /* Null-terminated */

    uint32_t config;        /* Bitmap of OFPPC_* flags. */
    uint32_t state;         /* Bitmap of OFPPS_* flags. */

    /* Bitmaps of OFPPF_* that describe features.  All bits zeroed if
     * unsupported or unavailable. */
    uint32_t curr;          /* Current features. */
    uint32_t advertised;    /* Features being advertised by the port. */
    uint32_t supported;     /* Features supported by the port. */
    uint32_t peer;          /* Features advertised by peer. */
};
OFP_ASSERT(sizeof(struct ofp_phy_port) == 48);
  • port_no : ポート番号
  • hw_addr : ハードウェアアドレス (MAC アドレス)
  • name : ポート名。OFP_MAX_PORT_NAME_LEN は 16 (Null-terminated なので、Null を除いて最大 15 文字まで)
  • config : ポートのコンフィグ (後述)
  • state : ポートの状態(後述)
  • curr, advertised, supported, peer : ポートのフィーチャー (後述)

ポートのコンフィグ

config には、ポートがどのようにコンフィグされているかに関する情報を示すビットマップが格納されています。各ビットの意味は、以下のように定義されています。

enum ofp_port_config {
    OFPPC_PORT_DOWN    = 1 << 0,  /* Port is administratively down. */

    OFPPC_NO_STP       = 1 << 1,  /* Disable 802.1D spanning tree on port. */
    OFPPC_NO_RECV      = 1 << 2,  /* Drop all packets except 802.1D spanning
                                     tree packets. */
    OFPPC_NO_RECV_STP  = 1 << 3,  /* Drop received 802.1D STP packets. */
    OFPPC_NO_FLOOD     = 1 << 4,  /* Do not include this port when flooding. */
    OFPPC_NO_FWD       = 1 << 5,  /* Drop packets forwarded to port. */
    OFPPC_NO_PACKET_IN = 1 << 6   /* Do not send packet-in msgs for port. */
};

OFPPC_PORT_DOWN はコンフィグによるダウンである Administratively down を意味します。

ポートの状態

state には、ポートの現在の状態が格納されます。各ビットは、以下のような意味を持ちます。

enum ofp_port_state {
    OFPPS_LINK_DOWN   = 1 << 0, /* No physical link present. */

    /* The OFPPS_STP_* bits have no effect on switch operation.  The
     * controller must adjust OFPPC_NO_RECV, OFPPC_NO_FWD, and
     * OFPPC_NO_PACKET_IN appropriately to fully implement an 802.1D spanning
     * tree. */
    OFPPS_STP_LISTEN  = 0 << 8, /* Not learning or relaying frames. */
    OFPPS_STP_LEARN   = 1 << 8, /* Learning but not relaying frames. */
    OFPPS_STP_FORWARD = 2 << 8, /* Learning and relaying frames. */
    OFPPS_STP_BLOCK   = 3 << 8, /* Not part of spanning tree. */
    OFPPS_STP_MASK    = 3 << 8  /* Bit mask for OFPPS_STP_* values. */
};

OFPPS_LINK_DOWN は、いわゆるケーブルが接続されていない等の理由でリンクアップしていない状態を表します。

ポートのフィーチャー

curr, advertised, supported, peer には、ポートのフィーチャーに関する情報が格納されます。各ビットの意味は、以下のとおりです。

enum ofp_port_features {
    OFPPF_10MB_HD    = 1 << 0,  /* 10 Mb half-duplex rate support. */
    OFPPF_10MB_FD    = 1 << 1,  /* 10 Mb full-duplex rate support. */
    OFPPF_100MB_HD   = 1 << 2,  /* 100 Mb half-duplex rate support. */
    OFPPF_100MB_FD   = 1 << 3,  /* 100 Mb full-duplex rate support. */
    OFPPF_1GB_HD     = 1 << 4,  /* 1 Gb half-duplex rate support. */
    OFPPF_1GB_FD     = 1 << 5,  /* 1 Gb full-duplex rate support. */
    OFPPF_10GB_FD    = 1 << 6,  /* 10 Gb full-duplex rate support. */
    OFPPF_COPPER     = 1 << 7,  /* Copper medium. */
    OFPPF_FIBER      = 1 << 8,  /* Fiber medium. */
    OFPPF_AUTONEG    = 1 << 9,  /* Auto-negotiation. */
    OFPPF_PAUSE      = 1 << 10, /* Pause. */
    OFPPF_PAUSE_ASYM = 1 << 11  /* Asymmetric pause. */
};

各フィールドの違いは以下のとおりです。

  • curr : 現在の状態
  • advertised : 広告したフィーチャー
  • supported : サポートしているフィーチャー
  • peer : 対向から広告されたフィーチャー

ちゃんと仕様通り実装されているのか確認しないと怖くて使えなさそうな感じです。どうしても必要ならば確認して使いましょう。とりあえず curr だけ抑えておけば大丈夫そうな気がします。