一种利用编解码输出信息的方法

文档序号:6446188阅读:120来源:国知局
专利名称:一种利用编解码输出信息的方法
技术领域
本发明涉及计算机和通信领域中的编解码技术,尤其涉及利用编解码输出信息的方法。
背景技术
在软件代码中,为了调试、跟踪、测试、了解系统运行状态和故障定位等目的,常常需要输出一些软件运行信息,例如打印信息、调试信息、日志信息、跟踪信息和告警信息等。而为了阅读方便,开发者往往采用文本方式输出这些信息。在对软件性能要求不高,或者软件规模不大的情况下,采用文本方式是一种简单有效的方法,对软件性能的冲击不是很明显。但是在嵌入式实时环境,或者其它商业环境中,其对软件性能往往有较高的要求,而且软件规模也较大,常常达到百万,甚至千万行以上的源代码。这种情况下,采用文本方式输出信息会对软件性能产生较大的影响,严重时甚至会导致软件处理能力下降或者宕机等。
现有技术采用文本输出方式输出信息的实现方式一般为trace(“The msg is from module%d,length%d.\n”,ModID,len);假设ModID=5,len=100,那么经过函数trace的处理(一般调用printf之类的库函数),最终会生成一个字符串“The msg is from module5,length100.\n”,并输出该字符串,如下图1所示。
现有技术最大的问题在于对软件资源占用较多,降低了软件系统的性能。例如使用了更多的CPU资源、内存、消息包、通讯带宽和硬盘等资源,从而导致系统性能下降。在电信产品软件中,如果采用这种方式输出日志和打印等信息,往往一天就要输出几百兆,甚至几千兆字节的信息,不仅会占用大量的各种关键资源,严重时甚至会影响到软件功能的正常实现。

发明内容
本发明提供利用编解码输出信息的方法,以解决现有技术在实现输出程序的运行信息时存在占用系统资源大和影响程序性能的问题。
为解决上述问题,本发明提供的方法包括如下步骤A、对程序运行时需要输出的、在程序运行过程中恒定不变的静态信息进行编码,并建立各编码与静态信息之间的对应关系,所述编码具有唯一性;B、执行所述程序并接收输出信息;C、利用所述输出信息中的编码查询所述对应关系得到对应的静态信息,将该静态信息替换所述输出信息中的编码并最终输出信息。
所述步骤A进一步包括如下步骤根据匹配规则在源程序中搜索需要输出静态信息的语句;对搜索到的语句,根据编码规则生成具有唯一性的编码插入该语句的相应位置以代替静态信息,并生成编码与静态信息的对应关系;将所有编码与对应的静态信息加入所述源程序中,或者生成一个头文件合入所述源程序中。
步骤C中,根据输出信息的编程接口所定义的编码位置从接收的输出信息中获取静态信息编码。
所述编程接口为可变参数的编程接口或固定参数的编程接口。
本发明主要有以下有益效果1、在信息含量不变的情况下,减少了信息表达的数据量和对系统资源的占用,降低了对软件系统性能的影响和冲击。
2、减小了软件编译后的目标代码、可执行代码大小,能够加快代码执行速度。
3、由于无需将其它形式的数据处理成字符形式,因而减少了对动态信息的格式化处理。
4、有助于开发人员书写更加详细、清晰、明了的输出信息内容5、减少对Printf之类的系统函数的调用,这类函数的实现往往很复杂,对系统性能、稳定性影响较大。


图1为现有技术中软件系统运行时输出信息的示意图;图2为本发明流程图;图3为现有技术与本发明输出信息的比较示意图。
具体实施例方式
本实施例以软件系统输出的静态信息为文本信息为例对本发明进行说明。
本发明中的静态信息是指在软件运行中恒定不变的信息,该信息在软件编译阶段即可确定,如前述例子中的字符串“The msg is from module%d,length%d.\n”。
动态信息是指在软件运行时动态可变的信息,如变量值等,例如前述例子中的变量ModID和len的取值。
为了保证文本信息含量不变的情况下减少信息表达所需的数据量,从而减少对软件资源的占用和降低对系统性能的影响,本发明对程序中的静态信息进行编码,输出编码后的信息,然后显示时再对静态信息解码,将经过编码的信息还原成文本方式,以提供良好的可读性。
参阅图2所示,本发明的主要流程如下1、对程序运行时需要输出的静态信息进行编码,并使该编码具有唯一性。
2、建立各编码与静态信息之间的对应关系。该对应关系可以存放在一个表中,也可以是一个配置文件。
3、执行所述程序并接收输出信息。
4、利用所述输出信息中的编码查询所述对应关系得到对应的静态信息,利用该静态信息替换所述输出信息中的编码,最终端显示或/和打印该信息。
保证编码唯一性的方法有多种,如以下两种(1)按照一定的规则划分编码取值空间进行编码,包括软件模块划分、功能划分和软件行为类型划分等。例如1-1000属于功能A,功能A由3个模块组成,那么1-300属于功能A的子模块1;301-500属于功能A的子模块2;501-1000属于功能A的子模块3。这种编码方案的优点是编码取值固定,编码携带信息量大(可以包含功能、模块、行为等多种信息),可利用编码进行很强的过滤、流控等处理。
(2)使用“文件ID+行号”的方式编码。每个源程序文件有一个唯一的ID,然后加上行号,如果有必要还可以加上其他信息,如输出级别信息等。这种编码方案的优点是编码处理过程简单,代码维护简单,无需人工分配编码取值;缺点是由于程序源代码经常变动,编码取值不固定,且编码携带信息量较少,利用编码进行过滤、流控等处理的能力较弱。
编码可以人工完成,即开发人员按照一定的编程规范进行开发,即可保证编码取值的唯一性。例如在C语言中使用枚举方式定义编码,保证每个编码的枚举值唯一。
编码也可以通过工具自动完成,其处理过程如下(1)根据匹配规则在源程序中找到一处需要编码的地方,匹配规则可以是某个特定的函数调用,如trace(…);(2)在函数调用中添加一个编码枚举值,按照一定的规则生成枚举的名字,保证名字的唯一性;(3)同时生成一个枚举值列表,添加上述的枚举名到列表中;(4)对源程序中所有需要编码的地方,都按照步骤1-3处理;(5)最后将枚举值列表加入、或者生成为一个头文件,合入源代码中。
下面以实例对上述的编码和解码进行说明,例如输出信息语句形式为trace(“The msg is from module%d,length%d.\n”,ModID,len);对于这个例子,不论该trace语句被调用、执行多少次,其静态信息是永远不变的,变化的只是动态信息。因此,将该trace语句的静态信息用一个唯一的编号代替,例如1,并且该编号在整个软件源代码中唯一,即其它静态信息的编号都不能为1。将所有需要输出的文本信息中的静态信息部分进行唯一的编码,生成一个形如下表的编码对应表

在输出信息时,例如上面提到的trace调用,就不再是输出一个字符串“Themsg is from module5,length100.\n”,而是输出3个数值“1,5,100”(输出接口定义为(编码,动态信息,动态信息,……),当采用固定参数个数输出时,后面的动态信息个数是固定的,例如2个;当采用可变参数个数输出时,后面的动态信息个数是不定的,可以为0~N个),它们分别代表“静态信息编号,变量ModID的值,变量len的值”。对于动态信息直接以数据方式输出,而不再格式化成字符形式输出。格式化是指将变量ModID的数值5变成字符“5”(即二进制的0x5变成ASCII码0x35)。可见,采用编码技术后,不仅无需输送一长串的静态信息字符串,还无需对动态信息进行格式化(一般都是采用类似于Printf这样的库函数进行格式化处理),进一步节省了软件处理性能。
比较两种输出方式所占用的字节个数,文本方式需要占用40个字节,而编码方式只需要输出12个字节(假设这3个数值都是用4字节的整型数表示的)。相当于压缩掉了(40-12)*100/40=70%的数据量。
如果程序中“静态信息占用字节数”与“动态信息占用字节数”之比越大,那么采用编码方式所获得的性能收益就越明显。一般来说,经过编码之后的信息其数据量只有原来文本方式数据量的1%~30%。当然,如果源代码中,静态信息较少,或者动态信息非常多,那么采用编码方法所能带来的性能提升就比较有限了。然而,在大多数产品软件(尤其是电信领域)中,静态信息都远远多于动态信息,因此,达到80%甚至更高的压缩率都是很可能的。
采用上述编码方式之后,源代码中的所有静态信息在编译时都可以不生成目标代码,因为其编码就完全替代了静态信息,所以软件编译之后的目标代码中,将不再含有静态信息内容,可以大大减小目标代码、可执行代码的大小,加快软件运行速度。在动态信息在软件处理过程中,无需进行格式化处理(其它形式转换成字符形式),减少CPU处理。由于静态信息不再编译到目标代码中,而是存储在编码对应表中,因此其长度不会影响软件的运行效率。所以可以书写任意长度的静态信息,来更加清晰、完整的描述信息的内容,使读者更加清楚、明白。例如可以详细解释输出的每一个动态信息的含义。而在原有技术方案(技术一)中,开发人员为了减少输出信息的长度,提高软件效率,往往牺牲信息的可读性,书写较简短的静态信息,导致其描述有时甚至不足以让人明白该信息,而需要去读源代码。
在运行程序过程中,收到一条编码后的输出信息,如上面提到的“1,5,100”;查询“静态信息-编码对应表”,获得相应的静态信息,如“The msg isfrom module%d,length%d.\n”。利用静态信息作为打印语句的格式化字符串,将变量值5,100打印出来,生成字符串“The msg is from module5,length100.\n”。由此,可以看到此输出结果和技术一中得到的输出文本信息是一摸一样的。这一步工作相当于把原本应该在输出信息时进行的处理挪到输出后、显示前来进行了,相当于减少了输出信息的软件系统的工作量。
编码后的信息输出主要有两种方式固定参数个数,或者可变参数个数方式输出编码后的信息。
固定参数个数的输出,例如一条文本信息中只包含2个动态信息参数;可变参数个数的输出,例如使用类似于printf的函数,一次输出0到多个动态信息参数相应的,本发明也提供2种编程接口供参考,分别处理固定参数个数和可变参数个数的信息输出。
支持可变参数的编程接口输出简单变量的函数接口函数宏TLIB_TRACE_VP(string,(code,num,可变参数列表));输出消息、数组等复杂结构的函数接口函数宏TLIB_TRACE(code,string,len,pData)。
函数宏TLIB_TRACE_VP的说明(1)string表示静态信息,是与编码code一一对应的;(2)该接口不支持字符串变量类型,如果要输出字符串,可以使用TLIB_TRACE函数接口;(3)string中的字符串包含的格式控制符应该和后面带的可变参数的个数相等;(4)num变量表示所有可变参数一共需要占用多少个函数堆栈单元,除double类型和I64整型每个占用2个外,其它类型都是每个占用1个堆栈单元(4字节或2字节,根据CPU和编译软件类型而定);(5)可变参数列表除了不支持字符串类型以外,对printf函数支持的打印类型都支持,包括浮点数float、double,指针地址%p等等;具体来说,以微软MSDN(2001年4月版本)介绍的printf支持的打印类型来说,本接口支持如下类型cCdiouxXeEfgGp,不支持的类型为nsS。
上述调用采用宏替换为对函数tlib_trace_vp(code,num,……)的调用,tlib_trace_vp实现时,需要做如下判断以支持各种CPU、编译软件的实现(1)从code和num的地址是递增还是递减判断函数堆栈地址是递增还是递减;(2)从code和num地址之差判断每个参数的堆栈单元大小(一般是4字节);(3)从“变量num的地址”和“堆栈单元大小”获得第一个可变参数的内存地址;(4)然后再调用tlib_trace处理并发送信息。
函数TLIB_TRACE的说明该函数宏替换为tlib_trace(code,len,pData),支持输出最大为64KB的数据块,用于输出消息、内存、数组等。
代码实例//实现信息输出的函数,第一个为真正的输出函数,第二个为可变参数处理函数void_tlib_trace(int_code,int len,char*pData);void_tlib_trace_vp(int code,int num,…);//a表示字符串,b为一个列表(编码,可变参数的个数,可变参数列表)//注意参数b书写时是有一对″()″的//将编码接口转化为对具体函数的调用#define TLIB_TRACE_VP(a,b)tlib_trace_vp b;#define TLIB_TRACE(a,b,c,d)tlib_trace(a,c,d);void main(void){int a,b,c;a=b=c=1;//可变参数编程接口调用方法示例分别是0、1、2、3个动态参数TLIB_TRACE_VP(″%Hi,Nice to meet you!\n″,(100,0))TLIB_TRACE_VP(″%d\n″,(101,1,a))TLIB_TRACE_VP(″%d\t%d\n″,(102,2,a,b))TLIB_TRACE_VP(″%d\t%d\t%d\n″,(103,3,a,b,c))//输出指定长度动态信息的编程接口调用方法示例TLIB_TRACE(104,″%d\n″,sizeof(a),&a)}void tlib_trace_vp(int code,int num,…){//计算可变参数的个数,长度,开始定制,然后调用真正的输出函数进行输出tlib_trace(code,num*sizeof(int),(char*)&num+sizeof(char*));}void tlib_trace(int code,int len,char*pData)
{//负责完成将指定长度的信息输出}支持可变参数的编程接口虽然用起来方便,但是也有其缺点(1)实现复杂,可移植性较差(需要考虑不同CPU、编译器的处理情况)(2)对字符串变量的支持较差(3)对double、64位整型数支持较差,因为要将一个当作2个堆栈单元来算。
在实际产品应用中,其实很少有必要使用可变参数,采用固定参数方式的接口就足够了。下面介绍一种固定参数个数的接口函数接口TLIB_TRACE(code,string,paral,para2,flag,len,pData)说明para1,para2为定长动态参数,如每个参数4字节大小flag为类型标志,标明pData数据的格式,其取值可以参考下表

对于double、I64整型数、字符串,都可以在len参数中记录其长度,并由指针pData指向这些参数的实参地址编程接口调用方法举例TLIB_TRACE(100,“msgtype%d,msglen%d,msg content is”,1,sizeof(msg),0,sizeof(msg),msg)其中paral等于1,表示消息类型;para2等于sizeof(msg)表示消息长度,后面的flag等于0表示后面的信息是二进制数据;最后两个参数,给出二进制数据的长度以及开始地址。
固定参数个数的接口有如下优点1、支持字符串变量的输出,且实现简单;2、支持多个字符串变量的输出,只要把这些字符串放到一个字符串中即可;3、支持double、I64整型数等类型的输出。
本发明与现有技术的差别如图3所示,从上图可以看出,经过编码后,软件系统需要输出的信息量大大减少,因此对系统性能的影响也大大减少。而在显示时,只要采用解码技术,就能将信息完全还原成文本格式,得到与原技术同样的输出信息。
虽然以上以静态信息为文本信息进行说明,但不限于,上述方法同样适用于图形信息和二进制比特流信息等。
显然,本领域的技术人员可以对本发明进行各种改动和变型而不脱离本发明的精神和范围。这样,倘若本发明的这些修改和变型属于本发明权利要求及其等同技术的范围之内,则本发明也意图包含这些改动和变型在内。
权利要求
1.一种利用编解码输出信息的方法,其特征在于包括如下步骤A、对程序运行时需要输出的、在程序运行过程中恒定不变的静态信息进行编码,并建立各编码与静态信息之间的对应关系,所述编码具有唯一性;B、执行所述程序并接收输出信息;C、利用所述输出信息中的编码查询所述对应关系得到对应的静态信息,将该静态信息替换所述输出信息中的编码并最终输出信息。
2.如权利要求1所述的方法,其特征在于,步骤A包括如下步骤根据匹配规则在源程序中搜索需要输出静态信息的语句;对搜索到的语句,根据编码规则生成具有唯一性的编码插入该语句的相应位置以代替静态信息,并生成编码与静态信息的对应关系;将所有编码与对应的静态信息加入所述源程序中,或者生成一个头文件合入所述源程序中。
3.如权利要求1所述的方法,其特征在于,步骤C中,根据输出信息的编程接口所定义的编码位置从接收的输出信息中获取静态信息编码。
4.如权利要求3所述的方法,其特征在于,所述编程接口为可变参数的编程接口或固定参数的编程接口。
5.如权利要求1至4任一项所述的方法,其特征在于,对于数值类型的动态信息,直接以数据方式输出。
6.如权利要求5所述的方法,其特征在于,所述静态信息包括但不限于文本信息、图形信息和二进制比特流信息。
7.如权利要求5所述的方法,其特征在于,所述最终输出信息是指打印和/或显示信息。
全文摘要
本发明公开了一种利用编解码输出信息的方法,该方法为对程序运行时需要输出的、在程序运行过程中恒定不变的静态信息进行编码,并使该编码具有唯一性;建立各编码与静态信息之间的对应关系;执行所述程序并接收输出信息;利用所述输出信息中的编码查询所述对应关系得到对应的静态信息,利用该静态信息替换所述输出信息中的编码并最终输出信息。
文档编号G06F11/36GK1797365SQ20041010253
公开日2006年7月5日 申请日期2004年12月24日 优先权日2004年12月24日
发明者龙纲 申请人:华为技术有限公司
网友询问留言 已有0条留言
  • 还没有人留言评论。精彩留言会获得点赞!
1