linux 中typeof的一些记录

linux 中typeof的一些记录

问题的由来

在代码的编写过程中经常会写

if (a > b)
 z = a;
else 
 z = b

这样逻辑简单的判断,这时我们会很自然的想到用 三目运算符( ?: ),再结合宏定义。

#define max(a,b) ((a) > (b) ? (a) : (b))

这里对于一些简单的判断代码能保证正常运行,但对于类似这样的判断,则会出错

max(a++,--b);

等多次调用会改变结果的,则会出错。

这里我们对max进行改进

#define maxint(a,b) \
  ({int _a = (a), _b = (b); _a > _b ? _a : _b; })

但是并不是所有的a,b 都是int类型,如果想找一种通用的方法该如何处理。

GNU c 中的typeof

c++ 中可以使用模板

template <typename T> 
const T &max(const T &a, const T &b)
{
	....
}

GNU c 中 使用typeof 重新定义类型

#define max(a,b) \
  ({ typeof (a) _a = (a); \
      typeof (b) _b = (b); \
    _a > _b ? _a : _b; })

所以我们在读linux 内核代码时会发现很多的地方使用了typeof

例如

#define __put_unaligned_t(type, val, ptr) do {					\
	struct { type x; } __packed *__pptr = (typeof(__pptr))(ptr);		\
	__pptr->x = (val);							\
} while (0)

#define put_unaligned(val, ptr) __put_unaligned_t(typeof(*(ptr)), (val), (ptr))

static inline void put_unaligned_le16(u16 val, void *p)
{
	__put_unaligned_t(__le16, cpu_to_le16(val), p);
}
static inline void put_unaligned_le32(u32 val, void *p)
{
	__put_unaligned_t(__le32, cpu_to_le32(val), p);
}

上述代码宏替换后如下

put_unaligned_be16((u16)val, &buf[offset]);  ->
	__put_unaligned_t(__le16, cpu_to_le16(val), &buf[offset]);
	
		#define __put_unaligned_t(type, val, ptr) do {					\
			struct { type x; } __packed *__pptr = (typeof(__pptr))(ptr);		\
			__pptr->x = (val);							\
		} while (0)

这里常见的处理方法是定义 一个struct { type x; } 然后通过赋值的方式把val 值放到对应的8字节数组中。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值