在学习SIP之前,我们首先要了解什么是SIP?
SIP是一个应用层的控制协议,可以用来建立、修改、和终止多媒体会话(或者会议)例如Internet电话。SIP在建立和维持终止多媒体会话协议上,支持5个方面:
了解完SIP之后我们应该来认识一下SIP协议的格式:
SIP消息体结构与HTTP协议结构相似,均由三部分组成:
请求行:
状态行:
下面简单列出一些常见的状态码:
消息头:
INVITE sip:10087@dev.xswitch.cn SIP/2.0
Record-Route: <sip:192.168.31.188:15060;lr=on;nat=yes>
Via: SIP/2.0/UDP 192.168.31.188:15060;branch=z9hG4bK986d.1c537238ae43750e62a423ddf7fe078c.0
Via: SIP/2.0/UDP 172.18.0.1:61789;received=172.18.0.1;rport=61789;branch=z9hG4bKPjTu0TroBVkc2BuxTbvQ4ODaYdk83-ljf9
Max-Forwards: 69
From: "10086USER" <sip:10086@dev.xswitch.cn>;tag=xav30sssdGzvtGLUJV7uwjtvKVZra6nl
To: sip:10087@dev.xswitch.cn
Contact: <sip:10086@172.18.0.1:61789;ob;alias=172.18.0.1~61789~1>
Call-ID: 01YPOzp4pT.DDQs5VapOAu9EEy7kss3I
CSeq: 10584 INVITE
Allow: PRACK, INVITE, ACK, BYE, CANCEL, UPDATE, INFO, SUBSCRIBE, NOTIFY, REFER, MESSAGE, OPTIONS
Supported: replaces, 100rel, norefersub
User-Agent: Telephone 1.5.2
Content-Type: application/sdp
Content-Length: 471
各消息头简介:
消息体:
消息编码协议头:
v=0
o=- 3874185567 3874185567 IN IP4 172.18.0.1
s=pjmedia
b=AS:117
t=0 0
a=X-nat:0
m=audio 4000 RTP/AVP 96 9 8 0 101 102
c=IN IP4 172.18.0.1
b=TIAS:96000
a=rtpmap:96 opus/48000/2
a=fmtp:96 useinbandfec=1
a=rtpmap:9 G722/8000
a=rtpmap:8 PCMA/8000
a=rtpmap:0 PCMU/8000
a=rtpmap:101 telephone-event/48000
a=fmtp:101 0-16
a=rtpmap:102 telephone-event/8000
a=fmtp:102 0-16
a=rtcp:4001 IN IP4 172.18.0.1
a=ssrc:2122978608 cname:0d505733158cdc19
完整流程Demo:
环境说明:
INVITE消息呼叫源 192.168.31.188 分机号 10086 发送一个会话请求,呼叫10087的分机,注意此时的call-id:01YPOzp4pT.DDQs5VapOAu9EEy7kss3I,留着后面做对比。
INVITE sip:10087@dev.xswitch.cn SIP/2.0
Record-Route: <sip:192.168.31.188:15060;lr=on;nat=yes>
Via: SIP/2.0/UDP 192.168.31.188:15060;branch=z9hG4bK986d.1c537238ae43750e62a423ddf7fe078c.0
Via: SIP/2.0/UDP 172.18.0.1:61789;received=172.18.0.1;rport=61789;branch=z9hG4bKPjTu0TroBVkc2BuxTbvQ4ODaYdk83-ljf9
Max-Forwards: 69
From: "10086USER" <sip:10086@dev.xswitch.cn>;tag=xav30sssdGzvtGLUJV7uwjtvKVZra6nl
To: sip:10087@dev.xswitch.cn
Contact: <sip:10086@172.18.0.1:61789;ob;alias=172.18.0.1~61789~1>
Call-ID: 01YPOzp4pT.DDQs5VapOAu9EEy7kss3I
CSeq: 10584 INVITE
Allow: PRACK, INVITE, ACK, BYE, CANCEL, UPDATE, INFO, SUBSCRIBE, NOTIFY, REFER, MESSAGE, OPTIONS
Supported: replaces, 100rel, norefersub
User-Agent: Telephone 1.5.2
Content-Type: application/sdp
Content-Length: 471
P-SRC-IP: 172.18.0.1
100 Trying 消息:
freeswitch告诉客户端,已收到请求,正准备呼叫目标10087
注意,这里的via头域的172.18.0.188,是kam的ip地址,因为此处是kam负责dispatch代理分发的。
至此,10086和fs的通话已经建立。对于fs这种b2bua的模式来说已经生成了一个channel。接下来,freeswitch将通过sip协议生成另一个channel。
SIP/2.0 100 Trying
Via: SIP/2.0/UDP 192.168.31.188:15060;branch=z9hG4bK986d.1c537238ae43750e62a423ddf7fe078c.0;received=172.18.0.188
From: "10086USER" <sip:10086@dev.xswitch.cn>;tag=xav30sssdGzvtGLUJV7uwjtvKVZra6nl
To: sip:10087@dev.xswitch.cn
Call-ID: 01YPOzp4pT.DDQs5VapOAu9EEy7kss3I
CSeq: 10584 INVITE
User-Agent: FreeSWITCH-mod_sofia/1.10.8-dev+git~20211222T004816Z~c7280c7e93~64bit
Content-Length: 0
生成另一个channel:
再次出现了一个invite消息头,但是call-id变了,变成了6e0d4d6e-1d00-4326-b82d-f2eb3bac236e。Via头域里的ip地址也变成了freeswtich容器的地址172.18.0.14,表明fs开始着手呼叫目标号码。
INVITE sip:10087@dev.xswitch.cn;dest=extension SIP/2.0
Via: SIP/2.0/UDP 172.18.0.14:17060;rport;branch=z9hG4bK9FNpKQ6v9aSea
Route: <sip:172.18.0.188:15060>
Max-Forwards: 68
From: "10086USER" <sip:10086@172.18.0.14>;tag=6vSBy8BgceeDQ
To: <sip:10087@dev.xswitch.cn;dest=extension>
Call-ID: 6e0d4d6e-1d00-4326-b82d-f2eb3bac236e
CSeq: 58044591 INVITE
Contact: <sip:mod_sofia@172.18.0.14:17060>
User-Agent: FreeSWITCH-mod_sofia/1.10.8-dev+git~20211222T004816Z~c7280c7e93~64bit
Allow: INVITE, ACK, BYE, CANCEL, OPTIONS, MESSAGE, INFO, UPDATE, REGISTER, REFER, NOTIFY
Supported: timer, path, replaces
Allow-Events: talk, hold, conference, refer
Content-Type: application/sdp
Content-Disposition: session
Content-Length: 248
P-SRC-IP: 172.18.0.1
X-FS-Session: c540ce3b-ef41-4cd8-b1ef-4081f678baa0
X-User-Fallback-Proxy: sip:192.168.7.8:5080;transport=tcp
X-FS-Support: update_display,send_info
Remote-Party-ID: "10086USER" <sip:10086@172.18.0.14>;party=calling;screen=yes;privacy=off
再次出现100 trying:
回复10087目标号码已经准备好了。注意,此时的回复是目标端10087回复给freeswitch的。
SIP/2.0 100 trying -- your call is important to us
Via: SIP/2.0/UDP 172.18.0.14:17060;rport=17060;branch=z9hG4bK9FNpKQ6v9aSea;received=172.18.0.14
From: "10086USER" <sip:10086@172.18.0.14>;tag=6vSBy8BgceeDQ
To: <sip:10087@dev.xswitch.cn;dest=extension>
Call-ID: 6e0d4d6e-1d00-4326-b82d-f2eb3bac236e
CSeq: 58044591 INVITE
Server: kamailio (5.5.2 (x86_64/linux))
Content-Length: 0
183 progres消息:
这个是freeswiitch回复给10086客户端的,此时10087振铃,10086播放回铃音。
SIP/2.0 183 Session Progress
Via: SIP/2.0/UDP 192.168.31.188:15060;branch=z9hG4bK986d.1c537238ae43750e62a423ddf7fe078c.0;received=172.18.0.188
Via: SIP/2.0/UDP 172.18.0.1:61789;received=172.18.0.1;rport=61789;branch=z9hG4bKPjTu0TroBVkc2BuxTbvQ4ODaYdk83-ljf9
Record-Route: <sip:192.168.31.188:15060;lr=on;nat=yes>
From: "10086USER" <sip:10086@dev.xswitch.cn>;tag=xav30sssdGzvtGLUJV7uwjtvKVZra6nl
To: <sip:10087@dev.xswitch.cn>;tag=5K0jvDUcF5QtB
Call-ID: 01YPOzp4pT.DDQs5VapOAu9EEy7kss3I
CSeq: 10584 INVITE
Contact: <sip:10087@172.18.0.14:17060;transport=udp>
User-Agent: FreeSWITCH-mod_sofia/1.10.8-dev+git~20211222T004816Z~c7280c7e93~64bit
Accept: application/sdp
Allow: INVITE, ACK, BYE, CANCEL, OPTIONS, MESSAGE, INFO, UPDATE, REGISTER, REFER, NOTIFY
Supported: timer, path, replaces
Allow-Events: talk, hold, conference, refer
Content-Type: application/sdp
Content-Disposition: session
Content-Length: 260
Remote-Party-ID: "10087" <sip:10087@dev.xswitch.cn>;party=calling;privacy=off;screen=no
200 OK消息:
当10087拿起电话接听后,回复200给freeswitch。
IP/2.0 200 OK
Via: SIP/2.0/UDP 172.18.0.14:17060;rport=17060;received=172.18.0.14;branch=z9hG4bK9FNpKQ6v9aSea
Record-Route: <sip:192.168.31.188:15060;transport=tcp;lr;r2=on;nat=yes>
Record-Route: <sip:192.168.31.188:15060;lr;r2=on;nat=yes>
Call-ID: 6e0d4d6e-1d00-4326-b82d-f2eb3bac236e
From: "10086USER" <sip:10086@172.18.0.14>;tag=6vSBy8BgceeDQ
To: <sip:10087@dev.xswitch.cn;dest=extension>;tag=B5e4EsqcqeTGk30gdo1X0way6hjX8t04
CSeq: 58044591 INVITE
Allow: PRACK, INVITE, ACK, BYE, CANCEL, UPDATE, INFO, SUBSCRIBE, NOTIFY, REFER, MESSAGE, OPTIONS
Contact: <sip:10087@172.18.0.1:57950;transport=TCP;ob;alias=172.18.0.1~57950~2>
Supported: replaces, 100rel, norefersub
Content-Type: application/sdp
Content-Length: 311
ACK消息:
freeswitch收到200之后,回复10087一个ack,表明已经收到,然后会给10086回200。
ACK sip:10087@172.18.0.1:57950;transport=TCP;ob;alias=172.18.0.1~57950~2 SIP/2.0
Via: SIP/2.0/UDP 172.18.0.14:17060;rport;branch=z9hG4bKaSeFNjQ06KF1N
Route: <sip:192.168.31.188:15060;lr;r2=on;nat=yes>
Route: <sip:192.168.31.188:15060;transport=tcp;lr;r2=on;nat=yes>
Max-Forwards: 70
From: "10086USER" <sip:10086@172.18.0.14>;tag=6vSBy8BgceeDQ
To: <sip:10087@dev.xswitch.cn;dest=extension>;tag=B5e4EsqcqeTGk30gdo1X0way6hjX8t04
Call-ID: 6e0d4d6e-1d00-4326-b82d-f2eb3bac236e
CSeq: 58044591 ACK
Contact: <sip:mod_sofia@172.18.0.14:17060>
Content-Length: 0
回送给客户端的200 ok消息:
SIP/2.0 200 OK
Via: SIP/2.0/UDP 192.168.31.188:15060;branch=z9hG4bK986d.1c537238ae43750e62a423ddf7fe078c.0;received=172.18.0.188
Via: SIP/2.0/UDP 172.18.0.1:61789;received=172.18.0.1;rport=61789;branch=z9hG4bKPjTu0TroBVkc2BuxTbvQ4ODaYdk83-ljf9
Record-Route: <sip:192.168.31.188:15060;lr=on;nat=yes>
From: "10086USER" <sip:10086@dev.xswitch.cn>;tag=xav30sssdGzvtGLUJV7uwjtvKVZra6nl
To: <sip:10087@dev.xswitch.cn>;tag=5K0jvDUcF5QtB
Call-ID: 01YPOzp4pT.DDQs5VapOAu9EEy7kss3I
CSeq: 10584 INVITE
Contact: <sip:10087@172.18.0.14:17060;transport=udp>
User-Agent: FreeSWITCH-mod_sofia/1.10.8-dev+git~20211222T004816Z~c7280c7e93~64bit
Allow: INVITE, ACK, BYE, CANCEL, OPTIONS, MESSAGE, INFO, UPDATE, REGISTER, REFER, NOTIFY
Supported: timer, path, replaces
Allow-Events: talk, hold, conference, refer
Session-Expires: 120;refresher=uas
Content-Type: application/sdp
Content-Disposition: session
Content-Length: 260
Remote-Party-ID: "Outbound Call" <sip:10087@dev.xswitch.cn>;party=calling;privacy=off;screen=no
客户端再回一个ack消息给freeswitch:
ACK sip:10087@172.18.0.14:17060;transport=udp SIP/2.0
Via: SIP/2.0/UDP 192.168.31.188:15060;branch=z9hG4bK986d.10b2bc120531367a8df6e82cbba0ef11.0
Via: SIP/2.0/UDP 172.18.0.1:61789;received=172.18.0.1;rport=61789;branch=z9hG4bKPjqRtG0BNHXz3lieovgGbagVMf1bgveYpB
Max-Forwards: 69
From: "10086USER" <sip:10086@dev.xswitch.cn>;tag=xav30sssdGzvtGLUJV7uwjtvKVZra6nl
To: sip:10087@dev.xswitch.cn;tag=5K0jvDUcF5QtB
Call-ID: 01YPOzp4pT.DDQs5VapOAu9EEy7kss3I
CSeq: 10584 ACK
Content-Length: 0
BYE消息:
此时的from是10087,可见是10087这个被叫主动发出的挂机请求给freeswitch。
BYE sip:mod_sofia@172.18.0.14:17060 SIP/2.0
Via: SIP/2.0/UDP 192.168.31.188:15060;branch=z9hG4bK71b.ab931f7decc319df14337c8822b5278b.0;i=3
Via: SIP/2.0/TCP 172.18.0.1:57950;received=172.18.0.1;rport=57950;branch=z9hG4bKPje2pt4x0eBwbYGx1ki8iKkZiCUhRD8oCD;alias
Max-Forwards: 69
From: <sip:10087@dev.xswitch.cn;dest=extension>;tag=B5e4EsqcqeTGk30gdo1X0way6hjX8t04
To: "10086USER" <sip:10086@172.18.0.14>;tag=6vSBy8BgceeDQ
Call-ID: 6e0d4d6e-1d00-4326-b82d-f2eb3bac236e
CSeq: 16442 BYE
User-Agent: Telephone 1.5.2
Content-Length: 0
freeswitch收到bye消息之后,回复200,删除被叫这个channel。
SIP/2.0 200 OK
Via: SIP/2.0/UDP 192.168.31.188:15060;branch=z9hG4bK71b.ab931f7decc319df14337c8822b5278b.0;i=3;received=172.18.0.188
Via: SIP/2.0/TCP 172.18.0.1:57950;received=172.18.0.1;rport=57950;branch=z9hG4bKPje2pt4x0eBwbYGx1ki8iKkZiCUhRD8oCD;alias
From: <sip:10087@dev.xswitch.cn;dest=extension>;tag=B5e4EsqcqeTGk30gdo1X0way6hjX8t04
To: "10086USER" <sip:10086@172.18.0.14>;tag=6vSBy8BgceeDQ
Call-ID: 6e0d4d6e-1d00-4326-b82d-f2eb3bac236e
CSeq: 16442 BYE
User-Agent: FreeSWITCH-mod_sofia/1.10.8-dev+git~20211222T004816Z~c7280c7e93~64bit
Allow: INVITE, ACK, BYE, CANCEL, OPTIONS, MESSAGE, INFO, UPDATE, REGISTER, REFER, NOTIFY
Supported: timer, path, replaces
Content-Length: 0
同时,freeswitch也会给原叫回bye,同时会携带挂机原因Reason:Q.850;cause=16;text="NORMAL_CLEARING"
BYE sip:10086@172.18.0.1:61789;ob;alias=172.18.0.1~61789~1 SIP/2.0
Via: SIP/2.0/UDP 172.18.0.14:17060;rport;branch=z9hG4bKB277pD833v5KH
Route: <sip:192.168.31.188:15060;lr=on;nat=yes>
Max-Forwards: 70
From: <sip:10087@dev.xswitch.cn>;tag=5K0jvDUcF5QtB
To: "10086USER" <sip:10086@dev.xswitch.cn>;tag=xav30sssdGzvtGLUJV7uwjtvKVZra6nl
Call-ID: 01YPOzp4pT.DDQs5VapOAu9EEy7kss3I
CSeq: 58044593 BYE
User-Agent: FreeSWITCH-mod_sofia/1.10.8-dev+git~20211222T004816Z~c7280c7e93~64bit
Allow: INVITE, ACK, BYE, CANCEL, OPTIONS, MESSAGE, INFO, UPDATE, REGISTER, REFER, NOTIFY
Supported: timer, path, replaces
Reason: Q.850;cause=16;text="NORMAL_CLEARING"
Content-Length: 0
客户端收到bye之后回复200给freeswitch,freeswitch挂断原叫这个channel。
至此,整个SIP协议流程完毕。
下面,通过一个简单的图整理一下整个流程:
本文分享自 FreeSWITCH中文社区 微信公众号,前往查看
如有侵权,请联系 cloudcommunity@tencent.com 删除。
本文参与 腾讯云自媒体同步曝光计划 ,欢迎热爱写作的你一起参与!