当前位置: 首页 > article >正文

Mininet-topo.py源码解析

在这里插入图片描述

整体构架概述

topo.py 是一个基于 Python 的网络拓扑构建模块,主要用于定义和管理网络节点(如交换机、主机)及其连接关系。其核心作用是为 Mininet 网络仿真框架提供灵活的拓扑结构支持,简化复杂网络的建模和测试过程。目的是通过模块化的设计,实现拓扑的快速生成、复用和扩展。整体架构分为三层:数据存储层MultiGraph 管理节点和链路数据)、逻辑控制层Topo 类封装核心操作方法)和预置模板层(子类定义标准拓扑结构)。


程序调用关系

子类重写
子类重写
存储
存储
Topo
addHost
addSwitch
addLink
addPort
端口映射管理
build方法
SingleSwitchTopo
LinearTopo
MultiGraph
节点数据
链路数据
生成单交换机拓扑
生成链式拓扑

说明

  • Topo 类:通过 addHostaddSwitch 添加节点,addLink 构建链路,后者调用 addPort 实现动态端口分配。
  • 预置子类:如 SingleSwitchTopoLinearTopo,通过重写 build 方法生成特定拓扑。
  • MultiGraph:作为底层数据结构,存储所有节点和链路信息。

功能模块剖析

1. MultiGraph 数据存储模块

功能:替代 networkx.MultiGraph,存储节点和链路数据。
实现细节

  • 节点存储node 字典以 {节点名称: 属性字典} 格式保存节点信息(如主机 IP、交换机 DPID)。
  • 链路存储edge 字典以 {源节点: {目标节点: {链路键: 属性}}} 格式记录链路元数据(如端口号)。
    流程图
添加节点/链路 → 更新 node 或 edge 字典 → 支持拓扑查询与遍历

2. Topo 核心控制模块

功能:管理网络拓扑的构建与端口分配。
关键方法

  • addHost(name, **opts):添加主机,继承默认配置 hopts
  • addSwitch(name, **opts):添加交换机并标记 isSwitch=True
  • addLink(node1, node2, **opts):添加双向链路,自动分配端口。

实现细节

  • 链路添加时调用 addPort 动态计算端口号。
  • 通过 ports 字典维护端口映射关系,确保双向一致性。

3. 预置拓扑子类模块

功能:快速生成标准拓扑结构。
示例

  • SingleSwitchTopo:单交换机连接 k 个主机。
  • LinearTopok 个交换机链式连接,每个连接 n 个主机。

实现流程图

子类重写 build() → 调用 addHost/addSwitch/addLink → 生成特定拓扑

数据结构剖析

1. MultiGraph.node

格式{节点名称: 属性字典}
示例

{
    "h1": {"ip": "10.0.0.1", "mac": "00:00:00:00:00:01"},
    "s1": {"isSwitch": True, "dpid": "0000000000000001"}
}

2. MultiGraph.edge

格式{源节点: {目标节点: {链路键: 链路属性}}
示例

{
    "s1": {
        "h1": {0: {"port1": 1, "port2": 0}},
        "s2": {0: {"port1": 2, "port2": 1}}
    }
}

3. Topo.ports

格式{节点: {端口号: (目标节点, 目标端口)}
示例

{
    "s1": {1: ("h1", 0), 2: ("s2", 1)},
    "h1": {0: ("s1", 1)},
    "s2": {1: ("s1", 2)}
}

关键代码剖析

1. 动态端口分配(addPort)

def addPort(self, src, dst, sport=None, dport=None):
    # 自动分配源端口
    if sport is None:
        src_base = 1 if self.isSwitch(src) else 0  # 交换机端口从1开始,主机从0开始
        sport = len(self.ports.get(src, {})) + src_base
    # 自动分配目标端口(逻辑同上)
    if dport is None:
        dst_base = 1 if self.isSwitch(dst) else 0
        dport = len(self.ports.get(dst, {})) + dst_base
    # 更新端口映射字典
    self.ports.setdefault(src, {})[sport] = (dst, dport)
    self.ports.setdefault(dst, {})[dport] = (src, sport)
    return sport, dport

注释

  • 根据节点类型(交换机或主机)决定端口起始值。
  • 双向更新 ports 字典,确保链路一致性。

2. 链路迭代器(iterLinks)

def iterLinks(self, withKeys=False, withInfo=False):
    for src, dst, key, info in self.g.edges_iter(keys=True, data=True):
        node1, node2 = info["node1"], info["node2"]
        if withKeys and withInfo:
            yield (node1, node2, key, info)  # 返回完整链路信息
        elif withKeys:
            yield (node1, node2, key)
        else:
            yield (node1, node2)

注释

  • 遍历所有链路,支持按需返回链路键和元数据。
  • 用于拓扑验证、可视化或日志输出。

3. 线性拓扑生成(LinearTopo.build)

def build(self, k=2, n=1):
    lastSwitch = None
    for i in irange(1, k):  # 生成k个交换机
        switch = self.addSwitch(f"s{i}")
        for j in irange(1, n):  # 每个交换机连接n个主机
            host = self.addHost(f"h{j}s{i}")
            self.addLink(host, switch)
        if lastSwitch:  # 连接当前交换机与上一个
            self.addLink(switch, lastSwitch)
        lastSwitch = switch

注释

  • 使用 lastSwitch 变量记录上一个交换机,形成链式结构。
  • 主机命名规则为 h<序号>s<交换机序号>,便于标识。

实际应用示例

from topo import LinearTopo
from mininet.net import Mininet
from mininet.cli import CLI

# 创建拓扑:3个交换机,每个连接1个主机
topo = LinearTopo(k=3, n=1)
net = Mininet(topo=topo)
net.start()

# 测试命令:pingall 验证全连通
CLI(net)  # 在交互界面输入 pingall
net.stop()

关键设计模式

1. 模板方法模式

  • 体现Topo 基类定义 build 方法框架,子类重写以实现具体拓扑逻辑。
  • 示例LinearTopo.build 实现链式拓扑生成。

2. 组合模式

  • 体现:通过 MultiGraph 组合节点和链路数据,统一管理复杂结构。
  • 示例Topo 类将节点、链路操作委托给 MultiGraph

3. 工厂方法模式

  • 体现addHostaddSwitch 封装对象创建细节。
  • 示例:根据参数动态生成主机或交换机节点。

项目前置技能

1. Python 面向对象编程

  • 关键技能:类与继承、方法重写、装饰器。
  • 示例:理解 class LinearTopo(Topo) 的继承关系。

2. 网络基础知识

  • 关键技能:交换机、主机、端口、链路的定义与作用。
  • 示例:知道交换机端口从 1 开始编号,主机端口从 0 开始。

3. Mininet 框架基础

  • 关键技能:使用 Mininet 类启动拓扑并执行测试。
  • 示例net = Mininet(topo=topo); net.start()

4. 图论基础

  • 关键技能:理解图结构中的节点、边、邻接表等概念。
  • 示例:通过 MultiGraph.edge 分析链路连接关系。

学习与训练建议

1. 从模板入手

  • 运行 SingleSwitchTopo 示例,观察生成的节点和链路。
  • 修改 k 参数生成不同规模拓扑,验证输出结果。

2. 调试关键逻辑

  • addPort 中添加 print 语句,观察端口分配过程。
  • 示例:打印 sportdport 的实时计算值。

3. 扩展自定义拓扑

  • 继承 Topo 创建树状拓扑(如每个交换机连接两个子交换机)。
  • 示例代码:
class TreeTopo(Topo):
    def build(self, depth=3):
        # 实现树状拓扑生成逻辑

4. 结合 Mininet 测试

  • 使用 pingall 验证连通性,iperf 测试带宽性能。
  • 示例:在 LinearTopo 中测量端到端延迟。

5. 深入源码分析

  • 阅读 TopoMultiGraph 的源码,理解数据存储与操作细节。
  • 重点分析 edges_iter 如何遍历链路数据。

总结

topo.py 是一个高效、灵活的网络拓扑构建工具,具有以下核心特点:

  1. 模块化设计:数据存储(MultiGraph)、逻辑控制(Topo)、预置模板(子类)分层清晰。
  2. 自动化管理:动态端口分配和双向链路维护减少手动配置错误。
  3. 高扩展性:用户可通过继承 Topo 快速定义自定义拓扑。

http://www.kler.cn/a/600997.html

相关文章:

  • linux中防火墙的配置
  • 【Docker系列八】使用 Docker run 命令部署 Nginx
  • Windows系统安装Node.js和npm教程【成功】
  • 使用 fn_dblog手动恢复误操作的 update(单列数值型数据恢复)
  • 基于SpringBoot + Vue 的汽车租赁管理系统
  • C++类与对象的的第三个简单的实战练习-3.25笔记
  • 【Qt 01】cmake搭建Qt VS2019开发环境
  • uniapp 微信小程序图片下载保存功能
  • 贪心算法 力扣hot100热门面试算法题 面试基础 核心思路 背题
  • Micropython RPI-PICO 随记-双PICO串口传数据
  • Excel多级联动下拉菜单的自动化设置(使用Python中的openpyxl模块)
  • Rust异步编程tokio--问题记录
  • 数智读书笔记系列024《主数据驱动的数据治理 —— 原理、技术与实践》
  • 基于SpringBoot的电影售票系统
  • 【网络】HTTP 和 HTTPS
  • [网鼎杯 2020 白虎组]PicDown1 [反弹shell] [敏感文件路径] [文件描述符]
  • 2、二分和贪心
  • S32K3 RAM ECC 的问题
  • 《似锦》:曹兴昱—残暴和孝顺并不冲突家庭成长环境分析以命抵命逻辑悖论
  • 代码随想录Day23