Chinaunix首页 | 论坛 | 博客
  • 博客访问: 2149447
  • 博文数量: 438
  • 博客积分: 3871
  • 博客等级: 中校
  • 技术积分: 6075
  • 用 户 组: 普通用户
  • 注册时间: 2011-09-10 00:11
个人简介

邮箱: wangcong02345@163.com

文章分类

全部博文(438)

文章存档

2017年(15)

2016年(119)

2015年(91)

2014年(62)

2013年(56)

2012年(79)

2011年(16)

分类: LINUX

2012-07-03 15:40:20

  首先声明下面这个va_list的实现,只适用于32位的机器,像单片机这样int 是2Byte的不适合,但是原理是一样的。

点击(此处)折叠或打开

  1. typedef char * va_list;
  2. #define _INTSIZEOF(n) ((sizeof(n)+sizeof(int)-1)&~(sizeof(int) - 1) )
  3. #define va_start(ap,v) ( ap = (va_list)&v + _INTSIZEOF(v) )
  4. #define va_arg(ap,t) ( *(t *)((ap += _INTSIZEOF(t)) - _INTSIZEOF(t)) )
  5. #define va_end(ap) ( ap = (va_list)0 )

  6. void test_vparameter(int i,...)
  7. {
  8.     int mm;
  9.     va_list argv;
  10.     va_start(argv,i);
  11.     while(i--)
  12.     {
  13.         mm=va_arg(argv,int);
  14.         putc(mm);
  15.     }
  16.     va_end(argv);
  17. }
1. va_list
   在调用va_start之前参数都己压入栈中,因为其它的都是可变参数,只有fmt是确定的,fmt是最后压入栈中的,并且每个参数在栈中占用的空间是一样的,所以可以由第一个参数fmt依次推算出其它参数的地址。
2. va_start
   a. (va_list)&t 取第一个参数fmt的地址
   b. (va_list)&t+_INT_SIZEOF(t) 第一个参数的地址加上参数的长度,此时ap指向了第二个参数即ap指向了第一个可变的参数。

3. va_arg
   a. ap+=__INT_SIZEOF(t)
ap移动指向第二个可变参数
   b. (ap+=__INT_SIZEOF(t))-__INT_SIZEOF(t)
用指针运算,确定第一个可变参数的地址
   c. (t*)((ap+=__INT_SIZEOF(t))-__INT_SIZEOF(t))
进行强制类型转化
   d. (*(t*)((ap+=__INT_SIZEOF(t))-__INT_SIZEOF(t)))
取出第一个可变参数地址中的值
阅读(3274) | 评论(0) | 转发(1) |
给主人留下些什么吧!~~