CNI插件源码示例,对于github.com/rajatchopra/ocicni库的分析
CNI插件初始化
// ocicni.go
1、func InitCNI(pluginDir string) (CNIPlugin, error)
(1)、先调用plugin := probeNetworkingPluginsWithVendorCNIDirPrefix(pluginDir, "")
先初步创建一个默认的cniNetworkPlugin的结构,并调用plugin.nsenterPath, err = exec.LookPath("nsenter")
(2)、调用err = getDefaultCNINetwork(plugin.pluginDir, plugin.vendorCNIDirPrefix),检查默认的network
是否存在,若不存在,则停止CNI插件的搜索,直接返回一个&cniNoOp{}结构
(3)、生成一个goroutine,调用plugin.SyncNetworConfig()周期性地和pluginDir进行同步,从而检查网络状态的更新
(4)、最后,return plugin, nil
cniNetworkPlugin结构如下所示:
type cniNetworkPlugin struct {
loNetwork *cniNetwork
sync.RWMutex
defaultNetwork *cniNetwork
nsenterPath string
pluginDir string
vendorCNIDirPrefix string
}
cniNetwork结构如下所示:
type cniNetwork struct {
name string
NetworkConfig *libcni.NetworkConfig
CNIConfig libcni.CNI
}
// ocicni.go
2、func probeNetworkPluginsWithVendorCNIDirPrefix(pluginDir, vendorCNIDirPrefix string) (*cniNetworkPlugin)
(1)、创建plugin := &cniNetworkPlugin{
defaultNetwork: nil,
loNetwork: getLoNetwork(vendorCNIDirPrefix),
pluginDir: pluginDir,
vendorCNIDirPrefix: vendorCNIDirPrefix,
}
(2)、调用plugin.syncNetworkConfig() ---> sync NetworkConfig in best effort during probing
(3)、最后,return plugin
// ocicni.go
3、func getLoNetwork(vendorDirPrefix string) *cniNetwork
(1)、调用loConfig,err := libcni.ConfFromBytes([]byte(`{"cniVersion": "0.1.0", "name": "cni-loopback", "type": "loopback"}`))
(2)、调用cninet := &libcni.CNIConfig{Path: []string{vendorCNIDir(vendorDirPrefix, loConfig.Network.Type), DefaultCNIDir}},其中vendorCNIDir返回的就是这样一个目录:$vendorDirPrefix/opt/$type/bin
(3)、创建loNetwork := cniNetwork{
name: "lo"
NetworkConfig: loConfig,
CNIConfig: cninet
}
再return loNetwork
// ocicni.go
4、func (plugin *cniNetworkPlugin) syncNetworkConfig()
该函数仅仅调用network, err := getDefaultCNINetwork(plugin.pluginDir, plugin.vendorCNIDirPrefix)
再调用plugin.setDefaultNetwork(network)
// ocicni.go
5、func getDefaultCNINetwork(pluginDir, vendorCNIDirPrefix string) (*cniNetwork, error)
(1)、当pluginDir为""时,设置pluginDir = DefaultNetDir
(2)、调用files, err := libcni.ConfFiles(pluginDir),从pluginDir中加载文件,若err不为nil,或者len(files) == 0,则报错
(3)、遍历files,调用conf, err := libcni.ConfFromFile(confFile),加载CNI config file
再设置cninet := &libcni.CNIConfig{Path: []string{DefaultCNIDir, vendorDir},}
最后设置network := &cniNetwork{name: conf.Network.Name, NetworkConfig: conf, CNIConfig: cninet}
// ocicni.go
6、func setDefaultNetwork(n *cniNetwork)
该函数仅仅设置plugin.defaultNetwork = n而已
CNI插件创建POD
// cri-o端的调用为: podNamespace := "" s.netPlugin.SetUpPod(netNsPath, podNamespace, id, containerName)
// ocicni.go
1、func (plugin *cniNetworkPlugin) SetUpPod(netnsPath string, namespace string, name string, id string) error
(1)、首先调用plugin.checkInitialized(),该函数确定plugin.defaultNetwork是否为nil,若为nil则报错
(2)、调用plugin.loNetwork.addToNetwork(name, namespace, id, netnsPath)
(3)、调用plugin.getDefaultNetwork().addToNetwork(name, namespace, id, netnsPath)
// ocicni.go
2、func (network *cniNetwork) addToNetwork(podName string, podNamespace string, podInfraContainerID string, podNetnsPath string) (*cnitypes.Result, error)
(1)、调用rt, err := buildCNIRuntimeConf(podName, podNamespace, podInfraContainerID, podNetnsPath)
(2)、调用netconf, cninet := network.NetworkConfig, network.CNIConfig
(3)、调用res, err := cninet.AddNetwork(netconf, rt)
(4)、最后return res, nil
// ocicni.go
3、func buildCNIRuntimeConf(podName string, podNs string, podInfraContainerID string, podNetnsPath string) (*libcni.RuntimeConf, error)
该函数仅仅创建rt := &libcni.RuntimeConf{
ContainerID: podInfraContainerID,
NetNS: podNetnsPath,
IfName: DefaultInterfaceName,
Args: [][2]string{
{"IgnoreUnknown", "1"},
{"K8S_POD_NAMESPACE", podNs},
{"K8S_POD_NAME", podName},
{"K8S_POD_INFRA_CONTAINER_ID", podInfraContainerID},
}
}
最后,return rt, nil
获取pod的网络状态
1、func (plugin *cniNetworkPlugin) GetContainerNetworkStatus(netnsPath string, namespace string, name string, id string) (string, error)
该函数先调用ip, err := getContainerIP(plugin.nsenterPath, netnsPath, DefaultInterfaceName, "-4")
最后return ip.String(), nil
CNI插件源码示例,对于github.com/rajatchopra/ocicni库的分析的更多相关文章
- [C] c99int(让VC等编译器自动兼容C99的整数类型)V1.02。源码托管到github、添加CMake编译配置文件、使用doxygen规范注释
新版本—— http://www.cnblogs.com/zyl910/p/zlstdint_v100.html[C] zlstdint(让VC.TC等编译器自动兼容C99的整数类型)V1.0.支持T ...
- 如何查看google chrome 插件源码
常用浏览器google chrome 有很多优秀的插件,寂寞的时候想看看人家是怎么实现的,说是快那就动手吧 插件代码位置 本人mac笔记本,chrome 插件位置如下 $ cd /Users/vin ...
- Ocelot简易教程(七)之配置文件数据库存储插件源码解析
作者:依乐祝 原文地址:https://www.cnblogs.com/yilezhu/p/9852711.html 上篇文章给大家分享了如何集成我写的一个Ocelot扩展插件把Ocelot的配置存储 ...
- 手机端页面自适应解决方案—rem布局(进阶版,附源码示例)
转自:https://segmentfault.com/a/1190000007350680 一年前笔者写了一篇 <手机端页面自适应解决方案—rem布局>,意外受到很多朋友的关注和喜欢.但 ...
- tinymce原装插件源码分析(四)-fullscreen
fullscreen 作为一款文本编辑器,全屏功能是非常有必要的.在插件中主要是修改一些css style和触发resize事件. style问题(反例): 见github源码:https://git ...
- tinymce原装插件源码分析(一)-hr
tinymce简介 tinymce是一款能方便无限扩展的网页富文本编辑器. tinymce原装插件已经十分丰富,对于文本编辑(blog等文章)是绰绰有余,但是应对一些复杂的应用,比如在上面开发html ...
- [C] tcharall(让所有平台支持TCHAR)v1.1。源码托管到github、添加CMake编译配置文件、使用doxygen规范注释
作者:zyl910 v1.1版的改动如下—— 将源码上传到github. 调整目录结构. 添加CMake编译配置文件. 使用doxygen规范注释. 文件清单—— docs\ docs\images\ ...
- 安卓图表引擎AChartEngine(四) - 源码示例 嵌入Acitivity中的折线图
前面几篇博客中都是调用ChartFactory.get***Intent()方法,本节讲的内容调用ChartFactory.get***View()方法,这个方法调用的结果可以嵌入到任何一个Activ ...
- 基于tomcat插件的maven多模块工程热部署(附插件源码)
内容属原创,转载请注明出处 写在前面的话 最近一直比较纠结,归根结底在于工程的模块化拆分.以前也干过这事,但是一直对以前的结果不满意,这会重操旧业,希望搞出个自己满意的结果. 之前有什么不满意的呢? ...
随机推荐
- Entity Framework 6 开发系列 目录
2014 年开始接触 Entity Framework 6 也快两年,用它已经沉淀了一个成熟架构,也用来开发了不少大大小小的产品和项目,直到这段时间,才真正有时间来回顾,重新学习它,为让大家更加了解E ...
- super.getClass()方法调用
下面程序的输出结果是多少?import java.util.Date;public class Test extends Date{public static void main(String[] a ...
- 深入理解和应用display属性(二)
四.inline-block 此类元素是inline + block的合体 1) margin和padding都有效:width和height都有效: .inline{ display: inline ...
- Dog_Hybird的诞生
起因 开玩笑说“iOS搞不动了”,另外一方面iOS组的哥哥们给力,少一个我也妥妥的.又听闻web前端组来了一个不得了的人物,“老司机,带带我”这种机会不能错过,1个多月前就申请转web前端了.开始是苦 ...
- CSS3中flexbox如何实现水平垂直居中和三列等高布局
最近这些天都在弥补css以及css3的基础知识,在打开网页的时候,发现了火狐默认首页上有这样一个东西.
- [转载]Javascript异步编程的4种方法
NodeJs的最大特性就是"异步" 目前在NodeJs里实现异步的方法中,使用“回调”是最常见的. 其实还有其他4种实现异步的方法: 在此以做记录 --- http://www.r ...
- arcgis for flex展示GIS基本功能
1.地图框选搜索: 这是空间查询,在地图上框选一定的范围,然后搜索出在这个范围之内的所有信息,搜索到的详细信息在列表框显示出来 2.属性查询: 3.数据库展示: 4.绘制图形: 地图上绘制各种不同形状 ...
- docker中建立私有git服务器[gitlab]
现在使用git的很普遍,在开发内部如何建立个git服务器,本文以gitlab为例,让你分分钟就可以搭好一个环境[docker的威力非同一般] 首先在docker.com找到gitlab的下载源和信息, ...
- Android—Socket中关闭IO流后导致Socket关闭不能再收发数据的解决办法
以Socket发送数据为例: 发送数据时候要声明:DataOutputStream os = new DataOutputStream(socket.getOutputStream()); 最近开发遇 ...
- iOS开发-UI 从入门到精通(一)
一.UI概述 (1)UI(User Interface)用户界面,用户能看到的各种各样的页面元素: (2)iOS App = 各种各样的UI控件+业务逻辑和算法: (3)想要开发出一款精美的应用程序, ...