网络协议-VLAN&VXLAN


文章目录

  • 网络协议-VLAN&VXLAN
  • 一、VLAN
  • 二、实验
  • 1、实验环境
  • 2、实验脚本
  • 3、实验结果


一、VLAN

VLAN (Virtual Local Area Network)意为虚拟局域网,是在交换机实现过程中涉及到的概念,由802.1Q标准所定义。由于交换机是工作在链路层的网络设备,连接在同一台交换机的终端处于同一个三层网中,同时也处于同一个广播域。当交换机接入较多的终端时,任意一台终端发送广播报文时(例如:ARP请求),报文都会传遍整个网络。对于规模较大的组网场景,广播报文的泛滥对于网络通信将会造成较大的影响。VLAN技术为这一问题提供了解决方案,VLAN将同一网络划分为多个逻辑上的虚拟子网,并规定当收到广播报文时,仅仅在其所在VLAN中进行广播从而防止广播报文泛滥。VLAN技术在链路层的层次中实现了广播域的隔离。

vlan报文格式如下:

vlan头报文格式 vlan 报文_vlan头报文格式

字段

长度

含义

Destination address

6字节

目的MAC地址。

Source address

6字节

源MAC地址。

Type

2字节

长度为2字节,表示帧类型。取值为0x8100时表示802.1Q Tag帧。如果不支持802.1Q的设备收到这样的帧,会将其丢弃。

PRI

3比特

Priority,长度为3比特,表示帧的优先级,取值范围为0~7,值越大优先级越高。用于当阻塞时,优先发送优先级高的数据包。如果设置用户优先级,但是没有VLANID,则VLANID必须设置为0x000。

CFI

1比特

CFI (Canonical Format Indicator),长度为1比特,表示MAC地址是否是经典格式。CFI为0说明是标准格式,CFI为1表示为非标准格式。用于区分以太网帧、FDDI(Fiber Distributed Digital Interface)帧和令牌环网帧。在以太网中,CFI的值为0。

VID

12比特

LAN ID,长度为12比特,表示该帧所属的VLAN。在VRP中,可配置的VLAN ID取值范围为1~4094。0和4095协议中规定为保留的VLAN ID。三种类型:Untagged帧:VID 不计Priority-tagged帧:VID为 0x000VLAN-tagged帧:VID范围0~4095三个特殊的VID:0x000:设置优先级但无VID0x001:缺省VID0xFFF:预留VID

Length/Type

2字节

指后续数据的字节长度,但不包括CRC检验码。

Data

42~1500字节

负载(可能包含填充位)。

CRC

4字节

用于帧内后续字节差错的循环冗余检验(也称为FCS或帧检验序列)。

二、实验

1、实验环境

本系列文章后续都采用minitnet环境进行实验,如果没有这个环境的,可以先参考官方文档进行搭建。

  • 安装mininethttp://mininet.org/download/ 里面是四种方法进行搭建。
  • Option 1: Mininet VM Installation (easy, recommended)
  • Option 2: Native Installation from Source
  • Option 3: Installation from Packages
  • Option 4. Upgrading an existing Mininet Installation
  • 安装wireshark
    sudo apt-get install wireshark
  • 安装controller
    sudo apt-get install openvswitch-testcontroller
    sudo ln /usr/bin/ovs-testcontroller /usr/bin/controller

2、实验脚本

#!/usr/bin/env python
"""
vlanhost.py: 
$ sudo apt-get install vlan
$ sudo python vlanhost.py 1000
"""

from mininet.node import Host
from mininet.topo import Topo
from mininet.util import quietRun
from mininet.log import error

class VLANHost( Host ):
    "Host connected to VLAN interface"

    def config( self, vlan=100, **params ):
        """Configure VLANHost according to (optional) parameters:
           vlan: VLAN ID for default interface"""

        r = super( VLANHost, self ).config( **params )

        intf = self.defaultIntf()
        # remove IP from default, "physical" interface
        self.cmd( 'ifconfig %s inet 0' % intf )
        # create VLAN interface
        self.cmd( 'vconfig add %s %d' % ( intf, vlan ) )
        # assign the host's IP to the VLAN interface
        self.cmd( 'ifconfig %s.%d inet %s' % ( intf, vlan, params['ip'] ) )
        # update the intf name and host's intf map
        newName = '%s.%d' % ( intf, vlan )
        # update the (Mininet) interface to refer to VLAN interface name
        intf.name = newName
        # add VLAN interface to host's name to intf map
        self.nameToIntf[ newName ] = intf

        return r

hosts = { 'vlan': VLANHost }


def exampleAllHosts( vlan ):
    """Simple example of how VLANHost can be used in a script"""
    # This is where the magic happens...
    host = partial( VLANHost, vlan=vlan )
    # vlan (type: int): VLAN ID to be used by all hosts

    # Start a basic network using our VLANHost
    topo = SingleSwitchTopo( k=2 )
    net = Mininet( host=host, topo=topo )
    net.start()
    CLI( net )
    net.stop()

# pylint: disable=arguments-differ

class VLANStarTopo( Topo ):
    """Example topology that uses host in multiple VLANs
       The topology has a single switch. There are k VLANs with
       n hosts in each, all connected to the single switch. There
       are also n hosts that are not in any VLAN, also connected to
       the switch."""

    def build( self, k=2, n=2, vlanBase=100 ):
        s1 = self.addSwitch( 's1' )
        for i in range( k ):
            vlan = vlanBase + i
            for j in range(n):
                name = 'h%d-%d' % ( j+1, vlan )
                h = self.addHost( name, cls=VLANHost, vlan=vlan )
                self.addLink( h, s1 )
        for j in range( n ):
            h = self.addHost( 'h%d' % (j+1) )
            self.addLink( h, s1 )


def exampleCustomTags():
    """Simple example that exercises VLANStarTopo"""

    net = Mininet( topo=VLANStarTopo() )
    net.start()
    CLI( net )
    net.stop()

if __name__ == '__main__':
    import sys
    from functools import partial

    from mininet.net import Mininet
    from mininet.cli import CLI
    from mininet.topo import SingleSwitchTopo
    from mininet.log import setLogLevel

    setLogLevel( 'info' )

    if not quietRun( 'which vconfig' ):
        error( "Cannot find command 'vconfig'\nThe package",
               "'vlan' is required in Ubuntu or Debian,",
               "or 'vconfig' in Fedora\n" )
        exit()

    if len( sys.argv ) >= 2:
        exampleAllHosts( vlan=int( sys.argv[ 1 ] ) )
    else:
        exampleCustomTags()

3、实验结果

在mininet 命令行执行h1 ping h2 ,然后启动wireshark抓包, 可以查看到结果

mininet> net
h1 h1-eth0.1000:s1-eth1
h2 h2-eth0.1000:s1-eth2
s1 lo:  s1-eth1:h1-eth0.1000 s1-eth2:h2-eth0.1000
c0
mininet> h1 ping h2
PING 10.0.0.2 (10.0.0.2) 56(84) bytes of data.
64 bytes from 10.0.0.2: icmp_seq=1 ttl=64 time=4.35 ms
64 bytes from 10.0.0.2: icmp_seq=2 ttl=64 time=0.958 ms
^C
--- 10.0.0.2 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1001ms
rtt min/avg/max/mdev = 0.958/2.654/4.350/1.696 ms

注包结果:

vlan头报文格式 vlan 报文_优先级_02