搜索
查看
编辑修改
首页
UNITY
NODEJS
PYTHON
AI
GIT
PHP
GO
CEF3
JAVA
HTML
CSS
搜索
酷酷是懒虫
这个屌丝很懒,什么也没留下!
关注作者
热门标签
jquery
HTML
CSS
PHP
ASP
PYTHON
GO
AI
C
C++
C#
PHOTOSHOP
UNITY
iOS
android
vue
xml
爬虫
SEO
LINUX
WINDOWS
JAVA
MFC
CEF3
CAD
NODEJS
GIT
Pyppeteer
article
热门文章
1
大数据技术原理笔记-考点版_行键查询的缺点
2
React--》UI组件库ant-design的介绍与使用_ant组件库
3
使用 Python 和 Matplotlib 绘制科学图表:实例演示_马吕斯定律曲线图
4
CRC校验码计算,以常用CRC-8为例_crc8算法
5
NLP的这一年2017:深度学习或成主角_2017nlp
6
win10+AMD显卡在安装Stable-diffusion-webui-directml报错RuntimeError: Couldn‘t checkout commit xxx for yyy._runtimeerror: couldn't checkout commit for stable
7
python interpolate_Python:插值interpolate模块
8
顺丰科技2019秋招测试工程师,Java开发工程师客观题合集_影响web前端页面性能一般不包括下面哪个
9
PyTorch 1-深度学习
10
万字长文:读懂微服务编排利器Zeebe_微服务编排引擎对比
当前位置:
article
> 正文
Linux内核中的IPSEC实现(1)_ipsec linux内核实现
作者:酷酷是懒虫 | 2024-07-12 15:12:39
赞
踩
ipsec linux内核实现
Java代码
1
. 前言
在Linux2.
6
内核中自带了IPSEC的实现,这样就不用象
2.4
那样打补丁来实现了。该实现包括以下几个部分: PF_KEY类型套接口, 用来提供和用户层空间进行PF_KEY通信,代码在net/key目录下,前面已经介绍过;安全联盟SA和安全策略SP管理,是使用xfrm库来实现的,代码在net/xfrm/目录下定义;ESP,AH等协议实现,在net/ipv4(
6
)下定义;加密认证算法库,在crypto目录下定义,这些算法都是标准代码了。本系列文章主要描述XFRM库的实现以及在IPV4下相关协议的处理部分, IPV6的忽略。
本文Linux内核代码版本为
2.6
.
19.2
。xfrm是内核中变化比较大的部分,每个版本中都有不小的差异, 同时也说明了该模块的不成熟性。
在net/xfrm目录下的各文件大致功能说明如下:
xfrm_state.c: xfrm状态管理
xfrm_policy.c: xfrm策略管理
xfrm_algo.c: 算法管理
xfrm_hash.c: HASH计算函数
xfrm_input.c: 安全路径(sec_path)处理,用于进入的ipsec包
xfrm_user.c: netlink接口的SA和SP管理
在net/ipv4目录下的和ipsec相关各文件大致功能说明如下:
ah4.c: IPV4的AH协议处理
esp4.c: IPV4的ESP协议处理
ipcomp.c: IP压缩协议处理
xfrm4_input: 接收的IPV4的IPSEC包处理
xfrm4_output: 发出的IPV4的IPSEC包处理
xfrm4_state: IPV4的SA处理
xfrm4_policy: IPV4的策略处理
xfrm4_tunnel: IPV4的通道处理
xfrm4_mode_transport: 传输模式
xfrm4_mode_tunnel: 通道模式
xfrm4_mode_beet: BEET模式
2
. 数据结构
内核SA的定义用xfrm_state结构定义,SP用xfrm_policy结构定义,在include/net/xfrm.h中定义。
2.1
状态(SA)
xfrm_state状态结构用来描述SA在内核中的具体实现:
struct xfrm_state
{
/* Note: bydst is re-used during gc */
// 每个状态结构挂接到三个HASH链表中
struct hlist_node bydst;
// 按目的地址HASH
struct hlist_node bysrc;
// 按源地址HASH
struct hlist_node byspi;
// 按SPI值HASH
atomic_t refcnt;
// 所有使用计数
spinlock_t lock;
// 状态锁
struct xfrm_id id;
// ID结构, 即目的地址,SPI,协议三元组
struct xfrm_selector sel;
// 状态选择子
u32 genid;
// 状态的标志值, 防止发生碰撞
/* Key manger bits */
struct {
u8 state;
u8 dying;
u32 seq;
} km;
// KEY回调管理处理结构参数
/* Parameters of this state. */
struct {
u32 reqid;
// 请求ID
u8 mode;
// 模式: 传输/通道
u8 replay_window;
// 回放窗口
u8 aalgo, ealgo, calgo;
// 认证,加密,压缩算法ID值
u8 flags;
// 一些标准
u16 family;
// 协议族
xfrm_address_t saddr;
// 源地址
int
header_len;
// 添加的协议头长度
int
trailer_len;
//
} props;
// SA相关参数结构
struct xfrm_lifetime_cfg lft;
// 生存时间配置
/* Data for transformer */
struct xfrm_algo *aalg;
// hash算法
struct xfrm_algo *ealg;
// 加密算法
struct xfrm_algo *calg;
// 压缩算法
/* Data for encapsulator */
struct xfrm_encap_tmpl *encap;
// NAT-T封装信息
/* Data for care-of address */
xfrm_address_t *coaddr;
/* IPComp needs an IPIP tunnel for handling uncompressed packets */
struct xfrm_state *tunnel;
// 通道, 实际是另一个SA
/* If a tunnel, number of users + 1 */
atomic_t tunnel_users;
// 通道的使用数
/* State for replay detection */
struct xfrm_replay_state replay;
// 回放检测结构,包含各种序列号掩码等信息
/* Replay detection state at the time we sent the last notification */
struct xfrm_replay_state preplay;
// 上次的回放记录值
/* internal flag that only holds state for delayed aevent at the
* moment
*/
u32 xflags;
// 标志
/* Replay detection notification settings */
u32 replay_maxage;
// 回放最大时间间隔
u32 replay_maxdiff;
// 回放最大差值
/* Replay detection notification timer */
struct timer_list rtimer;
// 回放检测定时器
/* Statistics */
struct xfrm_stats stats;
// 统计值
struct xfrm_lifetime_cur curlft;
// 当前时间计数器
struct timer_list timer;
// SA定时器
/* Last used time */
u64 lastused;
// 上次使用时间
/* Reference to data common to all the instances of this
* transformer. */
struct xfrm_type *type;
// 协议, ESP/AH/IPCOMP
struct xfrm_mode *mode;
// 模式, 通道或传输
/* Security context */
struct xfrm_sec_ctx *security;
// 安全上下文, 加密时使用
/* Private data of this transformer, format is opaque,
* interpreted by xfrm_type methods. */
void
*data;
// 内部数据
};
2.2
安全策略(SP)
xfrm_policy结构用于描述SP在内核内部的具体实现:
struct xfrm_policy
{
struct xfrm_policy *next;
// 下一个策略
struct hlist_node bydst;
// 按目的地址HASH的链表
struct hlist_node byidx;
// 按索引号HASH的链表
/* This lock only affects elements except for entry. */
rwlock_t lock;
// 策略结构锁
atomic_t refcnt;
// 引用次数
struct timer_list timer;
// 策略定时器
u8 type;
// 类型
u32 priority;
// 策略优先级
u32 index;
// 策略索引号
struct xfrm_selector selector;
// 选择子
struct xfrm_lifetime_cfg lft;
// 策略生命期
struct xfrm_lifetime_cur curlft;
// 当前的生命期数据
struct dst_entry *bundles;
// 路由链表
__u16 family;
// 协议族
__u8 action;
// 策略动作, 接受/加密/阻塞...
__u8 flags;
// 标志
__u8 dead;
// 策略死亡标志
__u8 xfrm_nr;
// 使用的xfrm_vec的数量
struct xfrm_sec_ctx *security;
// 安全上下文
struct xfrm_tmpl xfrm_vec[XFRM_MAX_DEPTH];
// 状态模板
};
xfrm模板结构, 用于状态和策略的查询:
struct xfrm_tmpl
{
/* id in template is interpreted as:
* daddr - destination of tunnel, may be zero for transport mode.
* spi - zero to acquire spi. Not zero if spi is static, then
* daddr must be fixed too.
* proto - AH/ESP/IPCOMP
*/
// SA三元组, 目的地址, 协议, SOI
struct xfrm_id id;
/* Source address of tunnel. Ignored, if it is not a tunnel. */
// 源地址
xfrm_address_t saddr;
// 请求ID
__u32 reqid;
/* Mode: transport, tunnel etc. */
__u8 mode;
/* Sharing mode: unique, this session only, this user only etc. */
__u8 share;
/* May skip this transfomration if no SA is found */
__u8 optional;
/* Bit mask of algos allowed for acquisition */
__u32 aalgos;
__u32 ealgos;
__u32 calgos;
};
2.3
协议结构
对ESP, AH, IPCOMP等协议的描述是通过xfrm_type结构来描述的, 多个协议的封装就是靠多个协议结构形成的链表来实现:
struct xfrm_type
{
char
*description;
// 描述字符串
struct module *owner;
// 协议模块
__u8 proto;
// 协议值
__u8 flags;
// 标志
#define XFRM_TYPE_NON_FRAGMENT
1
// 初始化状态
int
(*init_state)(struct xfrm_state *x);
// 析构函数
void
(*destructor)(struct xfrm_state *);
// 数据输入函数
int
(*input)(struct xfrm_state *, struct sk_buff *skb);
// 数据输出函数
int
(*output)(struct xfrm_state *, struct sk_buff *pskb);
// 拒绝函数
int
(*reject)(struct xfrm_state *, struct sk_buff *, struct flowi *);
// 头部偏移
int
(*hdr_offset)(struct xfrm_state *, struct sk_buff *, u8 **);
// 本地地址
xfrm_address_t *(*local_addr)(struct xfrm_state *, xfrm_address_t *);
// 远程地址
xfrm_address_t *(*remote_addr)(struct xfrm_state *, xfrm_address_t *);
/* Estimate maximal size of result of transformation of a dgram */
// 最大数据报长度
u32 (*get_max_size)(struct xfrm_state *,
int
size);
};
具体的协议结构定义如下, 通常只定义初始化,析构,输入和输出四个成员函数:
AH协议定义
/* net/ipv4/ah4.c */
static
struct xfrm_type ah_type =
{
.description =
"AH4"
,
.owner = THIS_MODULE,
.proto = IPPROTO_AH,
.init_state = ah_init_state,
.destructor = ah_destroy,
.input = ah_input,
.output = ah_output
};
ESP协议定义:
/* net/ipv4/esp4.c */
static
struct xfrm_type esp_type =
{
.description =
"ESP4"
,
.owner = THIS_MODULE,
.proto = IPPROTO_ESP,
.init_state = esp_init_state,
.destructor = esp_destroy,
.get_max_size = esp4_get_max_size,
.input = esp_input,
.output = esp_output
};
IP压缩协议定义:
/* net/ipv4/ipcomp.c */
static
struct xfrm_type ipcomp_type = {
.description =
"IPCOMP4"
,
.owner = THIS_MODULE,
.proto = IPPROTO_COMP,
.init_state = ipcomp_init_state,
.destructor = ipcomp_destroy,
.input = ipcomp_input,
.output = ipcomp_output
};
IPIP协议定义:
/* net/ipv4/xfrm4_tunnel.c */
static
struct xfrm_type ipip_type = {
.description =
"IPIP"
,
.owner = THIS_MODULE,
.proto = IPPROTO_IPIP,
.init_state = ipip_init_state,
.destructor = ipip_destroy,
.input = ipip_xfrm_rcv,
.output = ipip_output
};
2.4
模式结构
模式结构用于描述IPSEC连接描述, 可为通道模式或传输模式两种:
struct xfrm_mode {
// 数据输入函数
int
(*input)(struct xfrm_state *x, struct sk_buff *skb);
// 数据输出函数
int
(*output)(struct xfrm_state *x,struct sk_buff *skb);
// 模块指针
struct module *owner;
// 封装
unsigned
int
encap;
};
通道模式结构定义:
/* net/ipv4/xfrm4_mode_tunnel.c */
static
struct xfrm_mode xfrm4_tunnel_mode = {
.input = xfrm4_tunnel_input,
.output = xfrm4_tunnel_output,
.owner = THIS_MODULE,
.encap = XFRM_MODE_TUNNEL,
};
传输模式结构定义:
/* net/ipv4/xfrm4_mode_transport.c */
static
struct xfrm_mode xfrm4_transport_mode = {
.input = xfrm4_transport_input,
.output = xfrm4_transport_output,
.owner = THIS_MODULE,
.encap = XFRM_MODE_TRANSPORT,
};
beet模式, 不知道在哪用
/* net/ipv4/xfrm4_mode_beet.c */
static
struct xfrm_mode xfrm4_beet_mode = {
.input = xfrm4_beet_input,
.output = xfrm4_beet_output,
.owner = THIS_MODULE,
.encap = XFRM_MODE_BEET,
};
2.5
策略的相关协议处理结构
以下结构用于描述具体协议族下的的策略处理:
struct xfrm_policy_afinfo {
// 协议族
unsigned
short
family;
// 协议类型
struct xfrm_type *type_map[IPPROTO_MAX];
// 模式
struct xfrm_mode *mode_map[XFRM_MODE_MAX];
// 目的操作结构
struct dst_ops *dst_ops;
// 垃圾搜集
void
(*garbage_collect)(
void
);
// 路由选择
int
(*dst_lookup)(struct xfrm_dst **dst, struct flowi *fl);
// 获取源地址
int
(*get_saddr)(xfrm_address_t *saddr, xfrm_address_t *daddr);
// 查找路由项
struct dst_entry *(*find_bundle)(struct flowi *fl, struct xfrm_policy *policy);
// 创建新路由项
int
(*bundle_create)(struct xfrm_policy *policy,
struct xfrm_state **xfrm,
int
nx,
struct flowi *fl,
struct dst_entry **dst_p);
// 解码会话
void
(*decode_session)(struct sk_buff *skb,
struct flowi *fl);
};
IPV4的策略协议相关处理结构定义如下:
/* net/ipv4/xfrm4_policy.c */
static
struct xfrm_policy_afinfo xfrm4_policy_afinfo = {
.family = AF_INET,
.dst_ops = &xfrm4_dst_ops,
.dst_lookup = xfrm4_dst_lookup,
.get_saddr = xfrm4_get_saddr,
.find_bundle = __xfrm4_find_bundle,
.bundle_create = __xfrm4_bundle_create,
.decode_session = _decode_session4,
2.5
状态的相关协议处理结构
以下结构用于描述具体协议族下的的状态处理:
struct xfrm_state_afinfo {
// 协议族
unsigned
short
family;
// 初始化标志
int
(*init_flags)(struct xfrm_state *x);
// 初始化模板选择
void
(*init_tempsel)(struct xfrm_state *x, struct flowi *fl,
struct xfrm_tmpl *tmpl,
xfrm_address_t *daddr, xfrm_address_t *saddr);
// 模板排序
int
(*tmpl_sort)(struct xfrm_tmpl **dst, struct xfrm_tmpl **src,
int
n);
// 状态排序
int
(*state_sort)(struct xfrm_state **dst, struct xfrm_state **src,
int
n);
};
IPV4的状态相关协议处理结构
/* net/ipv4/xfrm4_state.c */
static
struct xfrm_state_afinfo xfrm4_state_afinfo = {
.family = AF_INET,
.init_flags = xfrm4_init_flags,
.init_tempsel = __xfrm4_init_tempsel,
};
2.6
回调通知信息结构
struct xfrm_mgr
{
struct list_head list;
char
*id;
// 状态通知
int
(*notify)(struct xfrm_state *x, struct km_event *c);
// 获取, 如获取SA
int
(*acquire)(struct xfrm_state *x, struct xfrm_tmpl *, struct xfrm_policy *xp,
int
dir);
// 编译策略
struct xfrm_policy *(*compile_policy)(struct sock *sk,
int
opt, u8 *data,
int
len,
int
*dir);
// 映射
int
(*new_mapping)(struct xfrm_state *x, xfrm_address_t *ipaddr, u16 sport);
// 策略通知
int
(*notify_policy)(struct xfrm_policy *x,
int
dir, struct km_event *c);
// 报告
int
(*report)(u8 proto, struct xfrm_selector *sel, xfrm_address_t *addr);
};
在net/key/pf_key.c中定义了pkeyv2_mgr结构:
static
struct xfrm_mgr pfkeyv2_mgr =
{
.id =
"pfkeyv2"
,
.notify = pfkey_send_notify,
.acquire = pfkey_send_acquire,
.compile_policy = pfkey_compile_policy,
.new_mapping = pfkey_send_new_mapping,
.notify_policy = pfkey_send_policy_notify,
};
3
. 初始化
/* net/xfrm/xfrm_policy.c */
// xfrm初始化函数包括状态, 策略和输入处理的三初始化函数
// xfrm是不支持模块方式的
void
__init xfrm_init(
void
)
{
xfrm_state_init();
xfrm_policy_init();
xfrm_input_init();
}
3.1
xfrm状态初始化
/* net/xfrm/xfrm_state.c */
void
__init xfrm_state_init(
void
)
{
unsigned
int
sz;
// 初始HASH表不大, 每个HASH中初始化为8个链表, 但随着状态数量的增加
// 会动态增加HASH表数量
sz = sizeof(struct hlist_head) *
8
;
// 建立3组HASH, 分别按SA的源地址, 目的地址和SPI值
xfrm_state_bydst = xfrm_hash_alloc(sz);
xfrm_state_bysrc = xfrm_hash_alloc(sz);
xfrm_state_byspi = xfrm_hash_alloc(sz);
if
(!xfrm_state_bydst || !xfrm_state_bysrc || !xfrm_state_byspi)
panic(
"XFRM: Cannot allocate bydst/bysrc/byspi hashes."
);
// xfrm_state_hmask初始值为=7, 计算出的HASH值与该值与来得到链表号
xfrm_state_hmask = ((sz / sizeof(struct hlist_head)) -
1
);
// 初始化工作队列work_queue, 完成对状态垃圾的搜集和释放
INIT_WORK(&xfrm_state_gc_work, xfrm_state_gc_task, NULL);
}
3.2
策略初始化
static
void
__init xfrm_policy_init(
void
)
{
unsigned
int
hmask, sz;
int
dir;
// 建立一个内核cache, 用于分配xfrm_dst结构()
xfrm_dst_cache = kmem_cache_create(
"xfrm_dst_cache"
,
sizeof(struct xfrm_dst),
0
, SLAB_HWCACHE_ALIGN|SLAB_PANIC,
NULL, NULL);
// 分配状态HASH表, 初始是8个HASH链表,以后随着策略数量的增加
// 会动态增加HASH表的数量
hmask =
8
-
1
;
sz = (hmask+
1
) * sizeof(struct hlist_head);
// 该HASH表是按策略的index参数进行索引的
xfrm_policy_byidx = xfrm_hash_alloc(sz);
xfrm_idx_hmask = hmask;
if
(!xfrm_policy_byidx)
panic(
"XFRM: failed to allocate byidx hash\n"
);
// 输入, 输出, 转发三个处理点, 双向
for
(dir =
0
; dir < XFRM_POLICY_MAX *
2
; dir++) {
struct xfrm_policy_hash *htab;
// 初始化inexact链表头, inexact处理选择子相关长度不是标准值的一些特别策略
INIT_HLIST_HEAD(&xfrm_policy_inexact[dir]);
// 分配按地址HASH的HASH表
htab = &xfrm_policy_bydst[dir];
htab->table = xfrm_hash_alloc(sz);
htab->hmask = hmask;
if
(!htab->table)
panic(
"XFRM: failed to allocate bydst hash\n"
);
}
// 初始化策略垃圾搜集的工作队列, 完成对策略垃圾的搜集和释放
INIT_WORK(&xfrm_policy_gc_work, xfrm_policy_gc_task, NULL);
// 登记网卡通知
register_netdevice_notifier(&xfrm_dev_notifier);
}
xfrm的网卡通知回调结构
static
struct notifier_block xfrm_dev_notifier = {
xfrm_dev_event,
NULL,
0
};
// 网卡通知回调函数
static
int
xfrm_dev_event(struct notifier_block *
this
, unsigned
long
event,
void
*ptr)
{
switch
(event) {
// 如果网卡down掉的话, 清除相关的所有的xfrm路由项
case
NETDEV_DOWN:
xfrm_flush_bundles();
}
return
NOTIFY_DONE;
}
// 清除相关的所有的xfrm路由项
static
int
xfrm_flush_bundles(
void
)
{
// 将不用的路由项删除
xfrm_prune_bundles(stale_bundle);
return
0
;
}
3.3
输入初始化
/* net/xfrm/xfrm_input.c */
void
__init xfrm_input_init(
void
)
{
// 建立一个内核cache, 用于分配sec_path结构(安全路径)
secpath_cachep = kmem_cache_create(
"secpath_cache"
,
sizeof(struct sec_path),
0
, SLAB_HWCACHE_ALIGN|SLAB_PANIC,
NULL, NULL);
}
struct sec_path结构是对输入的加密包进行层层解包的处理, 在sk_buff中有该结构的指针sp, 如果sp非空表示这是个IPSEC解密后的包。
...... 待续 ......
发表于:
2007
-
06
-
03
,修改于:
2007
-
06
-
03
00
:
27
,已浏览
6239
次,有评论
23
条 推荐 投诉
网友: 本站网友 时间:
2007
-
10
-
12
15
:
19
:
10
IP地址:
222.64
.
17
.★
强烈的顶顶顶!!!
15G空间=
5
个网站=
500
元/年 可免费试用
www.abcnic.com QQ:
1012727
5GB 独立WEB空间、5GB 企业邮箱空间、5GB MSSQL数据库
IIS连接数据
500
个、500GB/月流量、共享日志文件空间
数据库功能
支持5GB MSSQL数据库空间,
5
个用户数据库、Access
主机功能支持
采用安全稳定的Win2003 .net2.
0
架构
支持ASP、PHP、ASP.NET、PERL等脚本、支持自定义CGI
全面支持.net2.
0
版本,独立的Application应用池,
支持SSI(Shtml),支持FrontPage扩展
可免费自行绑定
5
个域名、
500
个解析、
500
个子域名
企业邮箱功能
赠送5GB 超大企业邮箱,
500
个Email企业邮箱用户
自动回复、自动转发、POP3、SMTP收发信、SMTP发信认证
邮件过滤、邮件拒收、邮件夹管理、邮件域管理、定制邮件数
网友: zetalog 时间:
2007
-
11
-
19
10
:
57
:
41
IP地址:
218.81
.
225
.★
为什么bundle是路由?!!
根据RFC2401,对于外出处理SPD entry直接指向SA Bundle,是这SA束吧!
看看注释也知道了:
dst -. xfrm .-> xfrm_state #
1
|---. child .-> dst -. xfrm .-> xfrm_state #
2
|---. child .-> dst -. xfrm .-> xfrm_state #
3
|---. child .-> NULL
dst_entry和xfrm_dst都是包含xfrm_state的,而且通过.child连接为SA束。
网友: yfydz 时间:
2007
-
11
-
19
12
:
36
:
03
IP地址:
218.247
.
216
.★
那你觉得这SA束又是什么东西?
网友: yfydz 时间:
2007
-
11
-
19
12
:
36
:
56
IP地址:
218.247
.
216
.★
或者说dst_entry/xfrm_dst又是什么东西?
网友: zetalog 时间:
2007
-
11
-
20
11
:
27
:
13
IP地址:
218.81
.
225
.★
安全关联束(Security Association Bundle)是一个SA序列,传输必须通过它处理以满足一个安全策略。组成束的SA可以终止于不同端点。
网友: Zetalog 时间:
2007
-
11
-
20
11
:
29
:
39
IP地址:
218.81
.
225
.★
我再来提个小意见。
struct xfrm_policy
{
struct xfrm_policy *next;
// 下一个策略
next是不要的,我保证你去掉它可以编译通过,策略存储是通过byidx和bydst还有inexact哈希表完成的。这些哈希表都是动态哈希表,会根据节点数量的多少自动增加。
next留在那里一定是改造不彻底,我打算发个patch去。
网友: Zetalog 时间:
2007
-
11
-
20
11
:
33
:
17
IP地址:
218.81
.
225
.★
我再来补充一下SA bundle。
RFC2401定义了组成SA bundle的几种方式:
传输邻接(transport adjacency),只能是AH应用于ESP输出,其他方式没有意义。
迭代隧道(iterated tunneling):允许多重迭代,仅road warrior和VPN两种情况需要支持。
隧道模式和传输模式两种方式也可以被任意组合。
网友: Zetalog 时间:
2007
-
11
-
20
11
:
44
:
44
IP地址:
218.81
.
225
.★
根据RFC2401定义,策略必须有一个参数用来表示报文的流向。
为什么xfrm_policy里面没有呢?其实index的第三位就是方向。
网友: yfydz 时间:
2007
-
11
-
20
12
:
34
:
14
IP地址:
218.247
.
216
.★
你说的没错,但RFC只定义了SA bundle的形式,却没限制这个bundle是如何实现的. xfrm的实现就是扩展了路由dst_entry为xfrm_dst,这个xfrm_dst的in/output函数就是IPSEC的解封/加封操作,通过dst链表实现bundle的处理.不要一提路由就立即为就是发送数据包,我在该系列后面文章也详细分析了这个路由链的处理,这里直接称其为路由是透过现象说本质的说法,当然如果是其他方式的实现,当然就不会称其为路由
网友: Zetalog 时间:
2007
-
11
-
20
12
:
41
:
17
IP地址:
218.81
.
225
.★
这么说可以理解了,呵呵。
网友: yfydz 时间:
2007
-
11
-
20
13
:
23
:
22
IP地址:
218.247
.
216
.★
由此就可以把xfrm和klips归为一类,都是靠路由来实现安全策略的,如果从FW+VPN角度说,FW的访问控制策略和VPN连接就需要分开定义的,VPN只处理点到点。而以前用过checkpoint的FW,可以在访问控制策略的动作中定义加密,也就是IPSEC封装,这说明其SA bundle应该和路由没关系,所以强调这点也是在区分不同的IPSEC的实现流派.
网友: Zetalog 时间:
2007
-
11
-
20
16
:
25
:
57
IP地址:
218.81
.
225
.★
我这样理解不知道是否可以:
在报文进行路由处理的时候,xfrm_lookup会被调用。在xfrm_lookup处理中,如果对当前的传输流有对应的policy(可能是sk_policy也可能是一般的policy),则查找dst_entry中是否缓存过IPsec处理的表项。如果没有,则根据policy的xfrm_tmpl解析出一个SA bundle,并且将它创建为dst_entry并缓存在bundle成员中,这个新创建或者查找到的dst_entry挂载在插入点中(xfrm_lookup)传入的dst_p。这样当报文发送的时候外出处理的回调就会被调用到。不知道是不是这样的?好像您在该系列的第三篇里面有描述,不过跟我现在看的git_kernel的代码有些不同。
网友: Zetalog 时间:
2007
-
11
-
20
16
:
34
:
40
IP地址:
218.81
.
225
.★
如果我的理解正确,bundle里面只是缓存了跟IPsec处理相关的处理项,其它路由项还是在__xfrm_lookup函数的传入参数的dst_p所关联的另一个链表中中。所以xfrm_policy的成员bundle就是RFC2401描述的那个SPD表项必然实现的SA bundle缓存。
网友: Zetalog 时间:
2007
-
11
-
20
16
:
46
:
19
IP地址:
218.81
.
225
.★
我是对着RFC2401在看xfrm_policy。RFC描述SPD表项必须要有以下参数:
流向:linux的dir应该在index里面了
动作:linux应该就是action
有序:linux应该是priority
由选择符索引:linux中应该是family和selector,因为xfrm_address_t没有协议族,所以xfrm里面到处都要family
有一个外出处理SA bundle缓存:linux就是bundle
有一个管理接口(xfrm_mgr)
主机端允许、用户对单独的流修改策略(sk_policy)
允许SA选择继承SPD表项还是传输流的选择子,好像linux实现在试验这个功能,在XFRM_SUB_POLICY有效时能看到相关代码。
。。。。。。
网友: Zetalog 时间:
2007
-
11
-
20
17
:
04
:
46
IP地址:
218.81
.
225
.★
呵呵,我有点追求名字了。
本质上说Linux就是路由型的IPsec处理。
网友: yfydz 时间:
2007
-
11
-
21
12
:
40
:
58
IP地址:
218.247
.
216
.★
基本就是这样吧
网友: zetalog 时间:
2007
-
11
-
21
20
:
53
:
31
IP地址:
58.33
.
88
.★
楼主,你好。
我这两天一直在分析xfrm代码,今天的总体感觉xfrm里面dst_entry好像还是用来实现PMTUD对应的功能。
在xfrm_state里面有一个genid参数,当新的SA加入时候会调用__xfrm_state_bump_genids把所有目标源地址相同的SA(他们的路由也应该一样)的genid改成一样。xfrm_dst里面也有genid。看到注释中说好像也和PMTUD相关的。不过实在没看明白是干吗的。不知道楼主对genid了解吗?
网友: yfydz 时间:
2007
-
11
-
23
11
:
06
:
37
IP地址:
218.247
.
216
.★
xfrm_dst里的genid和xfrm_state的没关系,前者只是flow的ID,因为是路由,xfrm_dst也是flow的一种
网友: 本站网友 时间:
2008
-
03
-
22
12
:
07
:
41
IP地址:
202.198
.
16
.★
斑竹你好,想把red算法的平均队列,瞬时队列,以及时间作为日志输出到一文件中,却不知怎么下手,请指点....
网友: _Lightsky_ 时间:
2008
-
04
-
01
10
:
27
:
31
IP地址:
222.88
.
1
.★
这些天一直在阅读XFRM里的源代码,却发现里面全是.h和.C,找不到调用的源头在那里?指点一下!谢谢了!
网友: _Lightsky_ 时间:
2008
-
04
-
01
10
:
30
:
52
IP地址:
222.88
.
1
.★
XFRM里面有一个USER,好像是调用的接口,但不知道编程的时候该怎么调用,不知道楼主有没有相关的文档?
网友: _Lightsky_ 时间:
2008
-
04
-
01
11
:
05
:
18
IP地址:
222.88
.
1
.★
我的邮箱是yangzhongxiqq
@163
.com,谢谢帮助啊!你的邮箱呢?
网友: yfydz 时间:
2008
-
04
-
02
13
:
11
:
39
IP地址:
218.247
.
216
.★
看最新的iproute2代码,就是用户层接口
声明:
本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:
https://www.wpsshop.cn/w/酷酷是懒虫/article/detail/814553
推荐阅读
article
自建
speed
test测速
服务器
教程,
Linux
/
Windows
/群晖_
搭建
speed
测速
服务器
...
可以在VPS上
搭建
speed
test测速网站来测试VPS的带宽,也可以在局域网内
搭建
speed
test来测试内网带宽。本...
赞
踩
article
linux
vim
底部
快捷键
,
Linux
vim
三种模式的
快捷键
...
1.移动光标1 h,j,k,l 上,下,左,右2 ctrl-e 移动页面3 ctrl-f 上翻一页4 ctrl-b 下翻...
赞
踩
article
Linux
Ubuntu
20.04
LTS 解决无法
输入
中文
输入
法
问题_ubuntu
20.04
输...
前言简单概述一下,
Linux
输入
法
可选的有ibus和fcitx等目前绝大部分
Linux
输入
法
都基于fcitx包括谷歌
中文
...
赞
踩
article
Linux
下
的
init
0
,
1
,
2
,
3
,
4
,
5
,
6
知识
介绍...
对于这个
知识
点
,
自己以前一直不了解
,
今天特意总结
下
,
作为自己
的
一个学习记录一.
init
是
Linux
系统操作中不可缺少
的
...
赞
踩
article
linux
vim
常用快捷键_
linux
vim
快捷键...
linux
vim
常用快捷键_
linux
vim
快捷键
linux
vim
快捷键 ...
赞
踩
article
Linux
文件
探秘:
检查
Linux
系统
的
文件
大小
的四种神器_
linux
检测
文件
大小
...
在
Linux
操作
系统
中,掌握如何高效
检查
文件
大小
是每位开发者和
系统
管理员的必备技能。本文详细介绍了四种
检查
Linux
文件
...
赞
踩
article
Linux
文件
探秘:
检查
文件
大小
的
四种
神器_查看
linux
文件
大小
...
作为技术博主,我们经常需要在
Linux
系统中
检查
文件
的大小。本文将介绍
四种
在
Linux
系统中
检查
文件
大小
的神器,涵盖了常...
赞
踩
article
linux
查看
文件夹
大小
及文件
大小
_
linux
文件夹
大小
...
1、最简单的查看方法可以使用ls -ll、ls-lh命令进行查看,当使用ls -ll,会显示成字节
大小
,而ls- lh会...
赞
踩
article
Linux
du命令:
查看
文件
夹
和
文件
的
磁盘
占用
情况_
查看
文件
夹
文件
占用
磁盘
情况...
du 命令,全称是 disk usage,用来展示
磁盘
使用量的统计信息。du 和 df 算是一对同门师兄弟,du 侧重在...
赞
踩
article
Linux
如何
查看
当前目录
的总大小/总
磁盘空间
_
linux
查看
硬盘容量
...
3 查找出/目录下占用空间最大的前10个文件或者文件夹:sudo du -a / | sort -n -r | head...
赞
踩
article
【
Linux
】
磁盘
空间
占用
:查看某个
文件
或目录
占用
磁盘
空间
的
大小
_使用du、df查
空间
占用
_linu...
du-ah--max-depth=1 这个是我想要的结果 a表示显示目录下所有的
文件
和
文件
夹(不含子目录),h表示以人类...
赞
踩
article
【
Linux
】
查看
某个
目录
的
大小
_
linux
查看
一个
目录
大小
...
【
Linux
】
查看
某个
目录
的
大小
1.1
查看
当前
目录
总
大小
1.2
查看
指定
目录
总
大小
2.1
查看
当前
目录
大小
明细2.2 ...
赞
踩
article
#
Linux
#
Linux
系统下如何
查看
磁盘空间
占据
情况
_
显示
var
子目录
磁盘空间
占用
情况
...
Linux
查看
磁盘空间
占据
情况
_
显示
var
子目录
磁盘空间
占用
情况
显示
var
子目录
磁盘空间
占用
情况
...
赞
踩
article
Linux
查看
文件夹
占用
内存
_
linux
查看
某一个
文件夹
先用的
内存
...
Linux
查看
文件夹
占用
内存
查看
当前目录下所有
文件夹
以及子目录的
内存
du -sh ./*
_
linux
查看
某一个
文件夹
先...
赞
踩
article
linux
查看
文件夹
占用大小 du
sort
_
查看
linux
文件夹
占用
内存大小
排序...
前面指令是
查看
文件夹
的占用大小,后面的
sort
是用于排序前一步的结果,就是让结果排序显示。_
查看
linux
文件夹
占...
赞
踩
article
linux
查看
磁盘
使用
情况_
linux
查询
磁盘
使用
率...
查询
linux
的
磁盘
占用情况_
linux
查询
磁盘
使用
率
linux
查询
磁盘
使用
率 ...
赞
踩
article
linux
查看
某个
目录
的
磁盘
空间
占用_
linux
查看
当前
目录
空间
占用情况...
这里写自定义
目录
标题
查看
空间
使用
查看
各个
目录
使用情况
查看
当前
目录
磁盘
空间
使用情况往下二级级
目录
使用情况对
当前
目录
的子
目录
...
赞
踩
article
linux
查看
磁盘
使用率_
linux
查看
磁盘
使用率...
df -h 按照默认设置,该工具把分区大小显示为1KB的块,已用的和可用的
磁盘
空间以KB 为单位显示。要查看以 MB 和...
赞
踩
article
Linux
查看
磁盘空间
_
查看
磁盘空间
占用情况
linux
...
Linux
查看
磁盘空间
可以使用 df 和 du 命令。_
查看
磁盘空间
占用情况
linux
查看
磁盘空间
占用情况
linux
...
赞
踩
article
构建
机
部署之
Azure
DevOps
添加
代理
机
(
Linux
)...
1)
代理
池所有者可以生成一个PAT,共享使用。2.创建PAT,组织必须选择“所有可访问的组织”级别的权限,范围选择“读取...
赞
踩
相关标签
linux
SpeedTest
linux vim底部快捷键
ubuntu
运维
ssh
init
操作系统
猫头虎
猫头虎技术团队
vim
编辑器
服务器
kubernetes
运维开发
nginx