ortp打印日志
//向字符串中打印数据
static char* ms_strdup_vprintf(const char *fmt, va_list ap)
{
int n, size = ;
char *p,*np;
#ifndef WIN32
va_list cap; /*copy of our argument list: a va_list cannot be re-used (SIGSEGV on linux 64 bits)*/
#endif
if ((p = (char *) ortp_malloc (size+)) == NULL)
return NULL;
while ()
{
#ifndef WIN32
va_copy(cap,ap);
n = vsnprintf (p, size, fmt, cap);
va_end(cap);
#else
n = vsnprintf (p, size, fmt, ap);
#endif
if (n > - && n < size)
return p;
if (n > -) // glibc 2.1 //
size = n + ; //precisely what is needed //
else // glibc 2.0//
size *= ; /// twice the old size //
if ((np = (char *) ortp_realloc (p, size)) == NULL){
free(p);
return NULL;
}else{
p = np;
}
}
}
void ms_logv_out(OrtpLogLevel lev, const char* fmt, va_list args)
{
char *msg;
msg = ms_strdup_vprintf(fmt, args);
ortp_free(msg);
} static inline void CHECK_FORMAT_ARGS(,) test_ms_message(const char *fmt,...)
{
va_list args;
va_start (args, fmt);
ms_logv_out(ORTP_MESSAGE, fmt, args);
va_end (args);
}
#define test_message test_ms_message
关于vs_start、vs_end的说明详见http://www.cnblogs.com/hanyonglu/archive/2011/05/07/2039916.html
以下介绍va_start和va_end的使用及原理。
介绍这两个宏之前先看一下C中传递函数的参数时的用法和原理:
1.在C中,当我们无法列出传递函数的所有实参的类型和数目时,可以用省略号指定参数表
void foo(...);
void foo(parm_list,...);
2.函数参数的传递原理
函数参数是以数据结构:栈的形式存取,从右至左入栈。
void func(int x, float y, char z);
那么,调用函数的时候,实参 char z 先进栈,然后是 float y,最后是 int x,因此在内存中变量的存放次序是
x->y->z,因此,从理论上说,我们只要探测到任意一个变量的地址,并且知道其他变量的类型,通过指针移位运算,则总可以顺藤摸瓜找到其
他的输入变量。
typedef char* va_list;
void va_start ( va_list ap, prev_param ); /* ANSI version */
type va_arg ( va_list ap, type );
void va_end ( va_list ap );
va_list 是一个字符指针,可以理解为指向当前参数的一个指针,取参必须通过这个指针进行。
- <Step 1> 在调用参数表之前,定义一个 va_list 类型的变量,(假设va_list 类型变量被定义为ap);
- <Step 2> 然后应该对ap 进行初始化,让它指向可变参数表里面的第一个参数,这是通过 va_start 来实现的,第一个参数是 ap 本身,第二个参数是在变参表前面紧挨着的一个变量,即“...”之前的那个参数;
- <Step 3> 然后是获取参数,调用va_arg,它的第一个参数是ap,第二个参数是要获取的参数的指定类型,然后返回这个指定类型的值,并且把 ap 的位置指向变参表的下一个变量位置;
- <Step 4> 获取所有的参数之后,我们有必要将这个 ap 指针关掉,以免发生危险,方法是调用 va_end,他是输入的参数 ap 置为 NULL,应该养成获取完参数表之后关闭指针的习惯。说白了,就是让我们的程序具有健壮性。通常va_start和va_end是成对出现。
#include <iostream.h>
void fun(int a, ...)
{
int *temp = &a;
temp++; for (int i = ; i < a; ++i)
{
cout << *temp << endl;
temp++;
}
}
int main()
{
int a = ;
int b = ;
int c = ;
int d = ;
fun(, a, b, c, d);
system("pause");
return ;
} Output:: :获取省略号指定的参数
在函数体中声明一个va_list,然后用va_start函数来获取参数列表中的参数,使用完毕后调用va_end()结束。像这段代码:
void TestFun(char* pszDest, int DestLen, const char* pszFormat, ...)
{
va_list args;
va_start(args, pszFormat); //一定要“...”之前的那个参数
_vsnprintf(pszDest, DestLen, pszFormat, args);
va_end(args);
}
#include 〈stdio.h〉
#include 〈string.h〉
#include 〈stdarg.h〉 /*函数原型声明,至少需要一个确定的参数,注意括号内的省略号*/
int demo( char, ... );
void main( void )
{
demo("DEMO", "This", "is", "a", "demo!", "");
} /*ANSI标准形式的声明方式,括号内的省略号表示可选参数*/
int demo( char msg, ... )
{
/*定义保存函数参数的结构*/
va_list argp;
int argno = ;
char para;
/*argp指向传入的第一个可选参数,msg是最后一个确定的参数*/
va_start( argp, msg );
while ()
{
para = va_arg( argp, char);
if ( strcmp( para, "") == )
break;
printf("Parameter #%d is: %s\n", argno, para);
argno++;
}
va_end( argp );
/*将argp置为NULL*/
return ;
}
以上是对va_start和va_end的介绍。
ortp打印日志的更多相关文章
- Xcode8中处理打印日志的配置
Xcode8中处理打印日志的配置
- Mybatis框架基于映射文件和配置文件的方式,实现增删改查,可以打印日志信息
首先在lib下导入: 与打印日志信息有关的架包 log4j-1.2.16.jar mybatis架包:mybatis-3.1.1.jar 连接数据库的架包:mysql-connector-java-5 ...
- Log打印日志遇到的问题
Log日志打印出现空指针问题 AndroidRuntime(372): Caused by: java.lang.NullPointerException: println needs a messa ...
- 重写NSLog,Debug模式下打印日志和当前行数
在pch文件中加入以下命令,NSLog在真机测试中就不会打印了 //重写NSLog,Debug模式下打印日志和当前行数 #if DEBUG #define NSLog(FORMAT, ...) fpr ...
- android112 c代码打印日志,c反编译调用java
activity: package com.itheima.ccalljava; import android.os.Bundle; import android.app.Activity; impo ...
- ruby脚本打印日志到rspec的报告文件中
在通过ruby+webdriver+rspec做自动化测试的时候,为了便于观察用例执行情况,我基本上都会用 rspec XX.rb --format doc -o result.log 如果遇到失败的 ...
- Log4j配置的经典总结,打印日志文件,日志存库
一.介绍 Log4j是Apache的一个开放源代码项目,通过使用Log4j,我们可以控制 日志信息输送的目的地是控制台.文件.GUI组件.甚至是套接口服务 器.NT的事件记录器.UNIX Sy ...
- rsyslog 不打印日志到/var/log/messages
*.info;mail.none;authpriv.none;cron.none;local3.none /var/log/messages 表示 所有来源的info级别都记录到/var/log/me ...
- 以打印日志为荣之logging模块详细使用
啄木鸟社区里的Pythonic八荣八耻有一条: 以打印日志为荣 , 以单步跟踪为耻; 很多程序都有记录日志的需求,并且日志中包含的信息既有正常的程序访问日志,还可能有错误.警告等信息输出,python ...
随机推荐
- centos中java安装跟配置
安装配置java环境 [root@JxateiLinux src]# Wget http://download.oracle.com/otn-pub/java/jdk/8u161-b12/2f38c ...
- RabbitMQ + topic发送消息+python
接口使用两个queue监听信息,且有两个测试环境,所以需要向mq中发送测试数据: python使用pika包:Pika is a RabbitMQ (AMQP-0-9-1) client librar ...
- android中OpenMax的实现【3】OMX中主要成员
原文 http://blog.csdn.net/tx3344/article/details/8117908 通过上文知道了,每个AwesomePlayer 只有一个OMX服务的入口,但是Awesom ...
- 时间、时间戳相关小结 - iOS
项目中难免会与时间打交道,故此次围绕时间展开做了一些日常使用的小结;如下 code 中也是围绕一些日常开发中较为常用的点展开小的方法封装. 具体方法的使用如下: // 2019-02-21 17:30 ...
- android软件开发基础
1.android特性:开放性:开源的一个基础, 方便性: 平等性: 2.Android四大基本组件分别是Activity,Service服务,Content Provider内容提供者,Broadc ...
- SQL注入点的类型
1.数字型注入点 形如“http://****?ID=55”,这类注入的参数是“数字”,因此称为“数字型注入点”. 此类注入点提交的SQL语句,其原形大致为:Select * from 表名 wher ...
- chromium之observer_list
典型用法如下 /////////////////////////////////////////////////////////////////////////////// // // OVERVIE ...
- Zabbix——设置模板
前提条件: Zabbix版本为4.0 可以正常使用Server 1. 添加H3C网络交换机的CPU和内存模板,并配置自动发现. 注意,需要添加完成后,重新进行搜索后再此进入才有下列选项. 添加CPU的 ...
- css:url链接去下划线+点击前黑色+点击时灰色+点击后黑色
一般的文章列表 加了样式之后的效果 附上css代码 /*点击前*/ a:link{ color: black; } /*点击后*/ a:visited{ color: black; } /*点击时*/ ...
- HTML a的连接
QQ电脑端 <a target="_blank" href="http://wpa.qq.com/msgrd?v=3&uin=XXXXXX&site ...