SDNLAB技术分享(五):浅谈Open vSwitch移植

前一段时间自己私下一直学习Open vSwitch。起初学习Open vSwitch的目的,只是为了更好的学习OpenFlow协议,然而当我看到Open vSwitch处理OpenFlow协议的入口函数时(即handle_OpenFlow__),突然感觉这代码的写的太NB啦。为什么这么说呢?因为Open vSwitch最新版本,号称支持of1.0,of1.1,of1.2,of1.3,of1.4,of1.5。然而它只用一个switch-case解决了协议版本差异性,它是怎么做到呢?带着这种疑问,开始了我学习Open vSwitch源码之旅。

随着学习一步一步的深入,发现了很多闻所未闻的新名词,比如说:DPDK,NetLink,NUMA等。这些新的名词(只是我没有听说过,其实业界早已不新鲜)令我产生了浓厚的兴趣,这样我就一点一点搜索相关资料,慢慢了解。以上就是我学习Open vSwitch背景,或者缘由吧。

今天我不打算进行源码分析,今天主要是想说一下如何移植Open vSwitch

很多人可能觉得移植Open vSwitch太难了,不知道应该如何移植?的确Open vSwitch这套代码太过于庞大,而且耦合度也比较大,要移植的确不容易。下面我把这两年工作中积累的一点经验和大家分享一下,如有不好之处,希望各位批评指出。

移植的时候我们需要考虑以下两个大方向:

1、是简单移植?还是将软件做为公司产品的一个组件,即二次开发移植?

2、平台。首先我们需要确定要移植到平台,Window、x86、arm、mips、ios等。

I、简单移植

如果只是简单的移植,那就非常方便了,只需要将代码下载后放到对应平台下,进行编译即可。如果是移植到arm、mips平台下,可能需要进行交叉编译。公司一般都有交叉环境,我们只需要在configure过程中指定对应的平台即可,例如:

./configure --build=i386-linux,--host=arm-linux,然后就可以执行make进行交叉编译了。这些步骤对于大家应该不陌生,这里不在多说了。

II、二次开发移植

相信很多公司都是基于开源软件进行二次开发,并且将开源软件作为公司产品的一个组件或一个服务而存在。那么接下来的问题就是如何移植到自己产品中呢?移植后的软件工作是否正常?

下面我们针对这两个问题并结合Open vSwitch进行简单剖析。接下来的一些分享内容,都是我提前准备好的,比如说编译环境、截图等。说句实在话,搞IT的,有些时候我们必须自己走一遍才可以,所以我私下移植了一下。

一、Open vSwitch框架

我们在移植一个软件的时候,第一要务就是了解软件架构,不必十分了解,最起码能够知道这个软件由哪些组件组成。针对Open vSwitch架构图,如下所示:

此图是之前一位网友在群里发出来,我觉得比较经典便保存起来。通过上图可知,Open vSwitch分为三层:

1)管理层即:ovs-dpctl、ovs-vsctl、ovs-ofctl、ovsdb-tool。

2)业务逻辑层即:vswitchd、ovsdb。

3)底层服务层即:datapath。

前两个都是用户态应用程序,最后一个是内核态应用程序。

我们移植一个软件的时候有些时候只需要移植一部分,有些时候需要全部移植过去。通过图1可知,Open vSwitch整个框架耦合度较大,若想单独移植某一个模块,难度较大。好在大多数基于Open vSwitch进行二次开发都是全部移植。这里呢,我只介绍一下如何移植vswitchd,起到抛砖引玉的效果。

二、正常编译

大家都知道linux下面编译一个软件是,configure、make、make install。不同之处往往就是configure配置过程。还有一点,像Open vSwitch这样一个非常成熟的一个软件,网上有很多教程如何编译它,因此我们不必花费心思去读文档说明。对于一个新的软件,网上可能没有具体教程,那么我们只能看官方提供的README文件了。

我只做过x86平台上的移植,所以下面介绍均是以x86平台进行解说

1、查看INSTALL.RHEL.md

每一个开源软件都会有有一个README.md文件,因此我们来看一下README.md文件。在这个文件里面有下面这样一句话,即Open vSwitch所支持的平台以及对应平台安装说明。我的linux是Centos6.7即RedHad系列。

通过读INSTALL.RHEL.md文件,有三点需要说明:

1)Open vSwitch安装方式默认是rpm包方式,对于我们移植来说显然是不可取的。

2)安装Open vSwitch必备条件,所以我们必须安装这些软件,才能保证编译顺利

3)通过阅读说明文件,能够大致知道编译顺序,但是在第三步make dist需要修改成make。因为make dist命令编译并打包即生成rpm。

2、查看configure配置说明

通过查看说明文件,我们能够清楚的知道编译方式,但是为了能够顺利移植我们还需要查看一下configure配置。

通过configure --help,可能会打印出很多内容,但是我们关心只有两项Optional Features、Optional Packages。具体内容如下图示:

上面内容都是一些特性选项,各个公司可能要求不一样,可以根据公司要求打开某些选项,在这里不进行详细介绍。这里想说一下dpdk。如果我们想让Open vSwitch支持dpdk,我们必须指定—with-dpdk即configure –with-dpdk=/usr/ pathxx/dpdk,这样生成的makefile将会支持dpdk编译。

3、执行编译步骤(在编译过程中可能会出现各种错误,也可能不会有错,取决于你自己机器中是否安装Open vSwitch所依赖的库)

本想把一些错误记录下来,拿出来和大家分享一下,可是在我编译过程中比较走运,没有任何错误!!

我们按照上面说的进行编译,下面编译过程都是我自己私下编译过程的:

首先下载源码:

默认下载代码,git分支是master分支,master分支是主线分支,不是很稳定,因此我们进行分支切换,切换到

branch-2.5是发布分支,是稳定分支。 一般公司都是基于发布分支进行开发。

此处为了加速编译,我指定了多线程编译:make –j32

我这里编译的非常顺利,没有任何错误,这样对于移植一个软件来说,无疑是件好事。下面为了方便移植,我们需要重新编译一次而且把编译过程重定向到一个文件中。如下命令行:

4、查看编译过程build.out.txt

查看编译过程主要是为了确定,可执行程序链接哪些库文件,这样在移植到我们自己产品中也需要链接对应的库。如下图所示:

通过链接过程可以清楚知道,某个程序需要哪些文件,我们只需要把这些文件移植到我们产品中就行了。

三、移植vswitchd模块

今天介绍一下我是如何进行vswtichd移植的。通过上面链接过程,vswitchd在链接过程会链接下面这些库以及.o文件:

下面是临时文件.o:

下面是Open vSwitch自带的静态库文件:

下面是系统库:

以上文件就是vswitchd所需要的文件,然而上面那些静态库文件我们是不知道由哪些源文件组成?那好我们可以再看一下编译过程,查找一下这些静态库由哪些文件组成。

如下图所示:

以上所有文件,就是我们需要的源文件,将这些源文件移植到自己平台中即可。当然只单纯的移植源文件是无法编译通过,还需要移植对应的头文件,这些工作都是体力活,没有什么技巧。

如果有人需要移植ovsdb-server也可以参考上面过程,过程相似。

四、编译参数

假设我们移植完所有源文件和头文件,接下来就需要编写makefile。如果不熟悉makefile语法的同学,若想移植一个软件估计是十分痛苦的。好在的是,公司有相应的编译框架,我们完全可以依靠现有资源。这里不想说makefile,而是说一下如何设置编译参数。编译参数对于编译出来的可执行程序,起着至关重要的作用,甚至影响移植后软件功能的准确性。那么我们如何做到编译参数正确性?其实很简单,还是查看编译过程。下面我截取一下编译过程:

五、如何保证移植后的软件功能的正确性?

其实我起这个话题是不好回答的,因为我不知道有哪些技巧能够保证软件的正确性。我这里只是总结一下吧:

1、按照上面流程,如果能够顺利移植并且编译出相应的可执行程序,那么可以保证80%的准确性。

2、如果可执行程序能够顺利运行起来,比如说vswitchd能够运行起来并且能够和控制器正常通信,基本上能够保证软件可靠性为95%。

3、进行日常测试,靠测试进行保证。

好了今天分享就到这里,感谢大家给面!!希望大家移植顺利。

Q&A

Q1:移植过程中好像没有修改OVS源代码,那源码中有没有跟特定平台相关的代码呢?(应该有与linux内核交互的部分吧)

A1:我在学习ovs时候,看到只有windows、linux平台。而linux平台下面只有一个dpdk是intel特定平台相关的,其他并没有

Q2:目前是否有已知的需要修改源代码的地方呢

A2:这个需要与公司特定产品才能进行改造。像我之前修改OpenFlow协议

Q3:假设 我要移植到2.6.x内核 怎么办? 2.6.31之前的一个版本不支持dpdk

A3:那就没有办法 dpdk也是有最低要求,如果这些不能满足是无法使用dpdk功能的

Q4:切换分支时候使用的是 git checkout -b 命令,-b 是否应该不用呢?因为这好像是会新建分支的

A4:git checkout -b 分支名 表示创建分支并且切换到新分支名

Q5:我看到你移植了vswitchd模块,但是OVS偶尔性很高,其会牵扯到和ovsdb-sever之间的交互等多模块,只是移植vswitchd这部分,可以完成ovs一个完整的功能吗?耦合性

A5:不可以的 vswtichd只是用户态核心程序,内核态核心程序是dataplane。在分享过程中也说了,虽然ovs耦合性很高,但好在很多公司都是全部移植

Q6:文中需要找的源文件比如 ofproto/.libs/ libofproto.a完整路径是/ ofproto/.libs/ libofproto.a吗?

A6

Q7:目前基于ovs做开发的很多,一般只是打印输出,但是效率很低,能否介绍一下开发过程中调试的一些经验和工具。

A7:1、能用gdb调试就用gdb。 在我之前博客中有一篇介绍main函数,里面会涉及到gdb调试,你可以参考一下。但是gdb调试多线程的时候 需要特别注意

2、日志。 对于多线程、多进程的ovs,日志特别重要。日志需要把ovs的日志开关打开,里面会有详细日志,其他方面我也不是很清楚。

Q8:请教下,编译时指定dpdk选项后是否意味着ovs与dpdk协同工作,不再需要改动其他地方?另外指定dpdk后比原来效率提高明显嘛?

A8:开启了dpdk选项,就必须与dpdk结合,因为源码中有些函数是条件编译。dpdk官方号称 使用dpdk性能会有所提升。但是通过我查看相关资料,dpdk配置还是比较麻烦,如果设置不好,反而性能会下降。编译选项这个地方有预编译

Q9:如果想调试比较靠后过程中的一段代码(可能已经不是main函数所在的文件代码),比如说是匹配过程代码等,是否gdb可以直接调试操作?

A9:一样可以的,我调试过的,你按照函数名进行断点调试

Q10:gdb调试文档在哪里?

A10:gdb是很高深的内容,你可以先查看一下gdb简单介绍,比如说:如何设置断点、如何查看堆栈等,建议百度。

Q11:这个是我参照你那篇main调试的,不知道为什么总是出现这个问题

A11:

把ovs-vswitchd 去掉,r参数。

原文发布于微信公众号 - SDNLAB(SDNLAB)

原文发表时间:2016-03-08

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏做全栈攻城狮

零基础开发高大上精美网站,一步步带你建设全能网站

不管你水平如何,请你仔细看下去。因为这份技能你值得拥有。网站建设完毕之后,下一系列讲解如何建设公众号。一起带你飞。

2381
来自专栏程序员互动联盟

【专业领域】jvm虚拟机android移植-接口篇

上一篇我们讲了如何下载phoneme虚拟机开源代码,如何配置编译脚本,编译测试验证基本功能。但是要让她在android上显示运行java小游戏我们还得费点劲。好...

3627
来自专栏Debian社区

Go 1.9 的新特性介绍

Go 1.9 beta版已发布, 正式版预期在8月初发布,让我们先来看看你Go 1.9带来了那些新特性。

834
来自专栏大前端开发

从编程小白到全栈开发:服务端的一些概念

幕后英雄总是容易被大家所忽略。在这看脸的世界,大家都以为脸就是全部了,你总是相信你所看到的就是事物的全部,可是你往往看到的只是冰山的一角而已。

1162
来自专栏phodal

编辑-发布-开发分离:git作为NoSQL数据库

动态网页是下一个要解决的难题。我们从数据库中读取数据,再用动态去渲染出一个静态页面,并且缓存服务器来缓存这个页面。既然我们都可以用Varnish、Squid这样...

21010
来自专栏大前端开发

从编程小白到全栈开发:寻找代码中的问题

很少有人能一下子就写出完全没有问题的代码。工作良好的程序,都是经过一遍遍的反复测试运行、发现问题、剔除问题(也就是我们所说的找Bug和修Bug)过后的产物,经过...

1003
来自专栏大史住在大前端

一统江湖的大前端(6)commander.js + inquirer.js——懒,才是第一生产力

你没有看错,懒绝壁是第一生产力,技术的进步,很多时候都是因为一些非常聪明的人难以忍受一些(在他们眼里)枯燥重复且低效的东西,从而发明出的东西,无论这些新发明在经...

2416
来自专栏24K纯开源

macOS平台下虚拟摄像头的研发总结

一、背景介绍     虚拟摄像头,顾名思义,就是利用软件技术虚拟出一个摄像头硬件设备供用户使用。当我们需要对视频图像进行处理再输出时,虚拟摄像头就具备非常大的价...

3779
来自专栏漫话前端

浏览器已原生支持 ES 模块,这对前端开发来说意味着什么?

还记得当初入门前端开发的时候写过的 Hello World 么?一开始我们先创建了一个 HTML 文件,在 <body> 标签里写上网页内容;后来需要学习页面交...

3757
来自专栏腾讯社交用户体验设计

高效编写微信小程序-你还在手动创建新项目吗?

2863

扫码关注云+社区

领取腾讯云代金券