Chinaunix首页 | 论坛 | 博客
  • 博客访问: 563000
  • 博文数量: 61
  • 博客积分: 2438
  • 博客等级: 大尉
  • 技术积分: 871
  • 用 户 组: 普通用户
  • 注册时间: 2010-07-28 08:04
文章分类
文章存档

2013年(1)

2012年(8)

2011年(15)

2010年(37)

分类: LINUX

2012-06-20 17:08:45

这里所说的是假设在ISO C99标准上的,如果是在比C99旧的标准上,那么就无法使用这里说提到的一些特性。可以在命令行上用-std来指定GCC所使用的标准。
GCC对C进行了扩展主要分为两方面:功能性扩展和优化扩展。(在这里就一并给出了)
1、类型发现:
typeof(x); 得到x的数据类型。
2、范围扩展:
switch-case语句中:case 2 ... 7: statement;
3、范围初始化:
对数组的初始化:spinlock_t atomic_locks[] = {[0 ... LOCK_COUNT - 1] = SPIN_LOCK_UNLOCKED};
int widths[] = {[1 ... 9] = 1, [10 ... 19] = 2, [20] = 3};
4、零长数组:
struct store {
int a;
int data[0];
};
这样一个结构体变量的大小是4。这允许结构中的元素引用结构实例后面紧接着的内存。
5、常量检测:
__builtin_constant_p函数用来检测常量。原型:int __builtin_constant_p(exp);
6、优化扩展:
分支预测提示:在linux中常用的优化技术之一是__builtin_expect。在开发人员使用条件代码时,常常知道最可能执行哪个分支,而最少使用哪个分支。如果编译器知道这种预测的话,就可以围绕最可能执行的分支生成最优的代码。__builtin_expect的使用方法基于两个宏:likely和unlikely:
#define likely(x) __builtin_expect(!!(x), 1);
#define unlikely(x) __builtin_expect(!!(x), 0);
7、预抓取:
一种改进性能的方法是把必须的数据缓存在接近处理器的地方。缓存可以显著的减少访问数据花费的时间。大多数现代处理器都有三类内存:
a、一级缓存通常支持单周期访问
b、二级缓存支持两周期访问
c、系统内存支持更长的访问时间
GCC通过内置函数__builtin_prefetch支持数据的手工抓取。在数据需要之前,使用这个函数把数据放到缓存中。该函数接收3个参数:
void __bulitin_prefetch(const void *addr, int rw, int locality);
addr为数据的地址;rw参数指明抓取数据是为了执行读操作还是写操作;locality指定在使用数据之后应该保留在缓存中,还是应该清除。
8、变量属性:
__attribute__(); 用逗号分割的列表定义多个属性。
9、函数属性:
# define __inline__   __inline__   __attribute__((always_inline)) 
# define __deprecated      __attribute__((deprecated)) 
# define __attribute_used__   __attribute__((__used__)) 
# define __attribute_const__   __attribute__((__const__)) 
# define __must_check      __attribute__((warn_unused_result)) 
always_inline让gcc以内联的方式处理指定的函数,无论是否启用了优化。
depracated指出函数已经被废弃,不应该再使用。
__used__告诉编译器无论gcc是否发现这个函数的调用实例,都要使用这个函数。
__const__告诉编译器某个函数是无状态的。
warn_unused_result让编译器检查所有调用者是否都检查函数的结果。
对于这些特性在内核源码中都可以找到对应的程序段。
阅读(3338) | 评论(0) | 转发(1) |
给主人留下些什么吧!~~