标签:cal mem 时间 local 自身 易用 print lan efault
本文系转载,出处不可考。
假设你对SIP/VoIP技术感兴趣,哪希望你不要错过:),假设你对写出堪称优美的Code感兴趣
,那么你也不可错过:)
这期间我想分析一下一个实际的协议栈的设计到实现的相关技术,算是自己的一个学习经
历记录.
最初选择这个库做分析的原因非常easy,文档齐全:),其他良好的特征则是慢慢发现的:)
www.pjsip.org
1. PJSIP简单介绍
PJSIP的实现是为了能在嵌入式设备上高效实现SIP/VOIP.其主要特征包含:
1).极具移植性.(Extremely portable)
当前可支持平台包含:
* Win32/x86 (Win95/98/ME, NT/2000/XP/2003, mingw).
* arm, WinCE and Windows Mobile.
* Linux/x86, (user mode and as kernel module(!)).
* Linux/alpha
* Solaris/ultra.
* MacOS X/powerpc
* RTEMS (x86 and powerpc).
正移植到:
* Symbian OS
2).很小的足印.(Very small footprint)
官方宣称编译后的库<150Kb,我在PC上编译后加上strip后大概173Kb,这对于嵌入
式设备,是个好消息:)
3).高性能.(High performance)
这点我们后面能够看看是否如作者宣称的:)
4).支持众多的特征.(Many features)
这点能够从http://www.pjsip.org/sip_media_features.htm#sip_features看出.
5).充足的SIP文档.(Extensive SIP documentation)
这是我最初选择该库的原因,当然不是终于的原因,终于的原因是它的code:)
2. PJSIP的组成.
事实上说是PJSIP不是特别贴切,这个库实际上是几个部分组成的.
1).PJSIP - Open Source SIP Stack[开源的SIP协议栈]
2).PJMEDIA - Open Source Media Stack[开源的媒体栈]
3).PJNATH - Open Source NAT Traversal Helper Library[开源的NAT-T辅助库]
4).PJLIB-UTIL - Auxiliary Library[辅助工具库]
5).PJLIB - Ultra Portable Base Framework Library[基础框架库]
而在最上层库的文件夹分为:(能够使用tree -d -L 1 查看)
$TOP/build [包括Makefile]
$TOP/build.symbian [针对symbian的Makefile]
$TOP/pjlib [參考上面]
$TOP/pjlib-util [參考上面]
$TOP/pjnath [參考上面]
$TOP/pjmedia [參考上面]
$TOP/pjsip [參考上面]
$TOP/pjsip-apps
$TOP/third_party
而在每一个子文件夹,能够看到分为:
bin [编译后产生的二进制文件]
build [Makefile]
build/output
build/wince-evc4
docs [doxygen的文档,用doxygen docs/doxygen.cfg产生]
include [头文件]
lib [编译后产生的库]
src [源码]
3. PJLIB简单介绍
要理解好PJSIP,就不得不先说说PJLIB,PJLIB算的上是这个库中最基础的库,正是这个
库的优美实现,才让PJSIP变得如此优越。
PJLIB提供了一系列特征。这是我们以下分析的重点。涉及到:
1).非动态内存分配[No Dynamic Memory Allocations]
实现了内存池,获取内存是从与分配的内存池中获取,高性能程序多会自己构造内存池
,后面我们会解释该内存池的使用以及主要的原理。依据作者的比較,是常规的 malloc(
)/free()函数的30倍。
2).OS抽象[Operating System Abstraction]
实现OS抽象的根本原因在与可移植性,毋庸置疑:).
涉及到:
a).线程[Threads.]
b).线程本地存储[Thread Local Storage.]
c).相互排斥[Mutexes.]
d).信号灯[Semaphores.]
e).原子变量[Atomic Variables.]
f).临届区[Critical sections.]
g).锁对象[Lock Objects.]
h).事件对象[Event Object.]
i).时间管理[Time Data Type and Manipulation.]
j).高解析的时间戳[High Resolution Timestamp.]
等等,这些我们后面分析代码时一一看来:)
3).低层的网络相关IO[Low-Level Network I/O]
这涉及到:
a).Socket抽象[Socket Abstraction.]
b).网络地址解析[Network Address Resolution.]
c).实现针对Socket的select API[Socket select() API.]
4).时间管理[Timer Management]
这主要涉及到两个部分。一个时定时器的管理,还有就是时间解析的精度(举例说来,就
是能精确到哪个时间等级,比方 POSIX sleep(),就仅仅能以秒为单位,而使用select()则可
以实现毫秒级别的计时)
5).各种数据结构[Various Data Structures]
主要有:
a).针对字符串的操作[String Operations]
b).数组辅助[Array helper]
c).Hash表[Hash Tabl]
d).链表[Linked List]
e).红黑平衡树[Red/Black Balanced Tree]
6).异常处理[Exception Construct]
使用的是TRY/CATCH,知道C++/JAVA之类面向对象语言的人看过会宛而一笑:)
7).LOG机制[Logging Facility]
非常显然,一个良好的程序,好的LOG机制不可少。
这能非常方便的让你去调试程序,对此我
是深有体会,不论什么时候。不要忘记“好的程序,是架构出来的;而能跑的程序,是调试出
来的:)”
8).随机数以及GUID的产生[Random and GUID Generation]
GUID指的是"globally unique identifier",仅仅是一个标识而已。比方说你的省份证,
算的上是一个GUID。当然。准确说来是“china unique identifier”:).
看了这么多的特征列举,是不是非常完备,的确。
总算是初步列举完了PJLIB的基本特征了。后面我们来说说它的使用与实现:
4. PJLIB的使用
有了上述介绍,是不是非常想知道这个库的使用,没关系,我们慢慢说来:)
首先是头文件和编译出来的库的位置,这就不必多说了,除非你没有使用过手动编译的库
,假设不太了解步骤,google一下。啊:)
1).为了使用这个库,须要使用:
#include
当然,也能够选择:
#include
#include
这样的分离的方式,只是。简单介绍其间,还是使用第一种吧:),毕竟,你不须要确认到你所
需的函数或者数据结构详细到哪个详细的头文件:)
2).确保在使用PJLIB之前调用 pj_init()来完毕PJLIB库使用前说必须的一些初始化.
这是一个不可缺少的步骤.
~~~~~~~~~~~~~~~~~~~~~~~
3).使用PJLIB的一些建议
作者对使用PJLIB的程序提出了一些建议,包含例如以下 :
a).不要使用ANSI C[Do NOT Use ANSI C]
观点非常明白。ANSI C并不会让程序具有最大的移植性,应该使用PJSIP库所提供的响
应机制来实现你所须要的功能.
b).使用pj_str_t代替C风格的字符串[Use pj_str_t instead of C Strings]
原因之中的一个是移植性,之二则是PJLIB内置的pj_str_t相关操作会更快(性能).
c).从内存池分配内存[Use Pool for Memory Allocations]
这非常明显,假设你知道为什么会使用内存池的话(提示一下,性能以及易用性:))
d).使用PJLIB的LOG机制做文字显示[Use Logging for Text Display]
非常明显:)
还有些关于移植的一些问题。不在我们的讨论范围。假设你须要移植到其他平台或者
环境,请參考http://www.pjsip.org/pjlib/docs/html/porting_pjlib_pg.htm
标签:cal mem 时间 local 自身 易用 print lan efault
原文地址:http://www.cnblogs.com/gavanwanggw/p/7235433.html