Kamailio的学习

目录

一.概述

二.配置文件

1.全局参数部分

2.模块设置部分

3.路由区块部分

4.伪变量

三.架构

1.总述

2.核心

3.模块

4.SIP消息处理

四.底层实现

1.多进程模型

(1)进程表数据结构模型

(2)进程创建流程

(3)进程间通信IPC机制

2.Epoll多路复用机制

(1)io_wait_h数据结构

(2)初始化函数

(3)资源清理

3.共享内存

(1)底层机制

4.锁定系统

(1)多平台锁定支持

(2)高级锁定功能

一.概述

Kamailio是一款SIP服务器。它可以在高并发环境中,做SIP呼叫的均衡负载处理,是多进程模式(使用fork)。Kamailio支持异步的TCP、UDP、SCTP、TLS、WebSocket,支持WebRTC,支持IPv4和IPv6,支持异步操作,支持负载均衡、主备用路由(Fail-Over),支持AAA(记账、鉴权和授权),支持很多SQL和noSQL数据库后端如MySQL、PostgreSQL、Oracle、Redis、MongoDB等,支持消息队列如RabbitMQ、Kafka等,支持JSON-RPC和XML-RPC控制协议以及SNMP监控等诸多特性。

二.配置文件

kamailio.cfg的结构可以分为三个部分,分别是全局参数、模块设置、路由区块。

1. 全局参数部分

name=value

名称对应官方文档(https://www.kamailio.org/w/documentation/)中的核心参数,如果名称与核心参数不匹配的话,Kamailio无法启动。

值通常是整数、bool或字符串

Go 复制代码
log_facility=LOG_LOCAL0

children=4

disable_tcp=yes

alias="sip.mydomain.com"

listen=udp:10.0.0.10:5060

比如在上面的例子中,如果 Kamailio日志登录到syslog,你可以控制该设施进行日志记录。当你想把所有 Kamailio日志转到另一个日志时,这非常有用。LOG_LOCAL0是rsyslogd中的概念,就是日志流的分类,会根据这些分类导出到不同文件。默认值是LOG_DAEMON。

children=4 UDP接口的子接口数量(每个接口一组- ip:port)。缺省值为8。例如,如果你配置代理监听3个UDP端口,它将创建3xchildren processes子进程来处理传入的UDP消息。

disable_tcp=yes 用来调整TCP的行为,全局参数用于禁用SIP服务器中的TCP支持,默认值是no

alias="sip.mydomain.com" 别名就是域名,用于设置服务器的别名主机名,它可以设置多次,每个值都被添加到一个列表中,以便在选中"myself"时匹配主机名。有必要在别名定义中包含端口("port="或"listen="定义中使用的端口值,alias:5060=other.domain.com),否则loose_route()函数将无法按预期的方式工作。

listen=udp:10.0.0.10:5060 设置SIP服务器应该监听的网络地址。它可以是IP地址、主机名或网络接口id或协议、地址、端口的组合。该参数可以在同一个配置文件中多次设置,服务器监听指定的所有地址。如果省略了这个指令,SIP服务器就会监听所有指令接口

2.模块设置部分

包含加载模块和设置模块参数的指令。它包含指令loadmodule和modparam。在默认配置文件中,以设置模块路径的行开头(对mpath core参数的赋值)

loadmodule "debugger.so"

...

modparam("debugger", "cfgtrace", 1)

loadmodule "debugger.so" 启用kamailio的交互调试功能,实时跟踪SIP消息处理流程

modparam("debugger", "cfgtrace", 1) 启用配置跟踪,参数含义分别是模块名称、配置跟踪参数、启用跟踪。如果为0就是禁用跟踪

3.路由区块部分

包含了Kamailio处理的SIP流量的路由逻辑的路由块。唯一的强制路由块是request_route,它包含决定SIP请求路由的操作。

request_route {

per request initial checks

route(REQINIT);

...

}

branch_route[MANAGE_BRANCH] {

xdbg("new branch [T_branch_idx\] to ru\n");

route(NATMANAGE);

}

onreply_route[MANAGE_REPLY] {

if (has_totag()) {

route(IN_DIALOG_REPLY);

}

route(HANDLE_NAT_REPLY);

}

主请求路由(request_route):调用子路由REQINIT

分支路由(branch_route):调用子路由NATMANAGE

主响应路由(onreply_route)

"伪变量"一词用于指可以被赋予的特殊符号作不同脚本函数的参数,这些参数将被替换在函数执行之前的值,开头用字符"$"标记

$T_branch_idx 执行branch_route[]的分支的索引(第一个分支从1开始)。如果在branch_route[]块之外使用,则值为'0'。

$ru SIP请求的URI的引用,它是R/W变量(可以直接在配置文件中赋值给它)

4.伪变量

是Kamailio核心系统提供的变量,用于访问SIP消息、系统状态等信息。当Kamailio收到SIP消息时,会自动解析并填充这些变量,它覆盖SIP消息、网络、系统等各方面。

$ru = "sip:1001@192.168.1.100:5060" # 指定新的请求行

$rm = "INVITE" # 从 SIP 请求方法提取

$si = "192.168.1.50" # 从网络包提取源IP

第一个变量是可读可写的,请求URI,可以修改来改变SIP消息目的地

第二个和第三个都是只读变量,分别是请求方法和源IP地址,修改会导致错误

三.架构

1.总述

Kamailio采用模块化架构,从整体看主要分为核心和模块两大类。

图中为Kamailio 1.x架构

Kamailio v3.0.x(或更新版本)的架构进行了重构,把原本核心的数据库API、管理接口API移出,重构为内部库

假设有一个INVITE请求到达:

①接收:SIP TRANSPORT LAYER(SIP传输层)从INTERNET接收到UDP数据包(也可以是UDP/TCP/TLS/WSS)

②解析:SIP PARSER(SIP解析器)将其转换为内部结构sip_msg

③执行路由脚本:CONFIG INTERPRETER开始执行kamailio.cfg对应的路由逻辑(比如route{...})

④调用功能模块:在脚本执行中,遇到类似lookup("location")或ds_select_dst()的命令,就会通过MODULE INTERFACE调用对应的LOCATION MODULES或ROUTING MODULES

⑤访问数据:模块在需要查询用户或路由规则时,通过DB API调用DB DRIVER MODULES,从DB SERVER获取数据

⑥管理与监控:这时管理员通过WEB GUI发送一个"查看当前呼叫数"的命令,该命令通过MI TRANSPORT MODULES和MI API传递给核心,核心返回数据并在界面上展示。

⑦发送响应:最终,处理后的INVITE消息再通过SIP TRANSPORT LAYER​发送到网络。

演示:./register_test.sh 1 10.0.2.15:5060发起一个注册请求,查看日志进行分析:

①接收:SIP TRANSPORT LAYER接收数据包

Received SIP message,这是TCP传输层接收到的REGISTER请求。

②解析:SIP PARSER转换为内部结构

解析器逐行解析SIP消息,识别方法为REGISTER,URI等信息。

③执行路由脚本:CONFIG INTERPRETER

<script>标签表明正在执行kamailio.cfg中的路由脚本,这是配置解释器在执行。

④调用功能模块:MODULE INTERFACE

正在解析目标地址,是通过路由模块实现的。

⑤发送响应:SIP TRANSPORT LAYER

请求转发:

响应返回:

通过TCP传输层发送完整的SIP消息。

2.核心

核心包括内存管理器、SIP消息解析器、锁定系统、DNS和传输层管理、配置文件解析器和解释器、计时器API;内部库包括一些来自旧Kamailio核心的组件,数据库抽象层(DB API),管理接口(MI API),统计引擎等

3.模块

目前仓库中有超过150个模块,通过加载模块,可以获得以下功能:注册商和用户位置管理;计费、授权与认证;有状态处理-SIP事务管理;异步SIP请求处理

4.SIP消息处理

Kamailio配置文件的执行在收到来自网络SIP请求和SIP回复的处理流程不同。

(1)SIP请求处理

①所有请求都从传输层进入,执行主路由

②路由脚本决定三分之一:

立即回复并结束(认证失败、错误请求等)

简单无状态转发(高性能代理)

完整有状态处理(支持分支路由、失败处理等)

③最终都通过传输层发送响应或转发请求

(2)SIP回复处理

四.底层实现

1.多进程模型

(1)进程表数据结构模型

(2)进程创建流程

(3)进程间通信IPC机制

Unix域socket通信

文件描述符传递

子进程的sockfd[1]和父进程的sockfd[0]通信

通过"/opt/kamailio/sbin/kamcmd ps"查看kamailio的多进程

5375:主管理进程,启动和监控所有子进程

定时器进程组:有三个独立的定时器进程,分别处理不同精度的定时任务

5377:慢定时器

5378:主定时器,SIP事务超时处理、对话状态维护

5379:次级定时器,与主定时器配合,处理不同时间粒度的任务

5380:控制处理程序,处理kamcmd命令

5385:TCP主进程,监听TCP端口,接收TCP连接,将连接分配给工作进程

5381-5384:4个工作进程,从TCP连接读取SIP消息、解析SIP消息、执行路由脚本

(children参数可以在cfg文件中tcp_children进行配置)

2.Epoll多路复用机制

(1)io_wait_h数据结构

通用字段

epoll专用字段

(2)初始化函数

初始化调用时机

模式选择逻辑

内核版本>=2.5.66 默认使用水平触发

(3)资源清理

销毁函数

epoll销毁

3.共享内存

(1)底层机制

有两种共享内存的方式

第一种MMAP(内存映射)

MAP_ANON:创建匿名内存区域,不与任何文件关联;/dev/zero:特殊设备文件,提供全零的内存页

第二种System V SHM

shmget():创建或获取共享内存段

shmat():将共享内存附加到进程地址空间

IPC_PRIVATE:每次创建新的共享内存段

4.锁定系统

(1)多平台锁定支持

Futex,用户态快速路径,避免系统调用

FAST_LOCK,快速自旋锁,自选等待,低延迟。适用于高并发短临界区

Pthread互斥锁

POSIX信号量,需要跨进程锁定时,用于进程间同步

编译时根据目标平台自动选择最快的锁实现

(2)高级锁定功能

递归锁,同一进程可多次获取锁,记录持有者防止死锁

相关推荐
龘龍龙2 小时前
Python基础学习(二)
开发语言·python·学习
xiaoxiaoxiaolll2 小时前
机器学习材料性能预测与材料基因工程
深度学习·学习
Rousson2 小时前
硬件学习笔记--92 关于UWB的介绍
笔记·学习
玩具猴_wjh2 小时前
12.12 学习笔记
笔记·学习
炽烈小老头2 小时前
【每天学习一点算法 2025/12/10】反转链表
学习·算法·链表
QiZhang | UESTC2 小时前
学习日记day47
学习
●VON2 小时前
AI辅助学习如何避免依赖陷阱?
人工智能·学习
点云SLAM2 小时前
Incisive英文单词学习
人工智能·学习·英文单词学习·雅思备考·incisive·犀利的、有洞察力的·直击核心、犀利有力、分析深刻
LiYingL2 小时前
OctoThinker 通过改进 Llama 来支持强化学习,展示了中间学习的威力
人工智能·学习·llama