PostgreSQL中的数据位对齐——MAXALIGN

in 编程
关注公众号【好便宜】( ID:haopianyi222 ),领红包啦~
阿里云,国内最大的云服务商,注册就送数千元优惠券:https://t.cn/AiQe5A0g
腾讯云,良心云,价格优惠: https://t.cn/AieHwwKl
搬瓦工,CN2 GIA 优质线路,搭梯子、海外建站推荐: https://t.cn/AieHwfX9

最近在看PG的xlog的源代码时,发现了一个这样的宏定义

#define SizeOfXLogLongPHD   MAXALIGN(sizeof(XLogLongPageHeaderData))

其实理解起来很简单,就是取得XLogLongPageHeaderData结构体的size,但是对于MAXALIGN这个宏还是通过源代码了解了一下,下面对齐进行简单的分析。

这个宏定义,在c.h头文件中

/* Define as the maximum alignment requirement of any C data type. */
#define MAXALIGN(LEN)           TYPEALIGN(MAXIMUM_ALIGNOF  , (LEN))

MAXIMUM_ALIGNOF这个在pg_config.h中定义,熟悉PG源码的都清楚,pg_config.h实在configure执行时自动生成,这个头文件里面的定义基本都和编译环境和configure时设置的参数相关,这个MAXIMUM_ALIGNOF也不例外,这个是获得当前编译器中占最大.位的基本类型,比如long long类型。我的机器是ubuntu16.04 的64位版,编译器是gcc5.4,取得的long long类型的大小为8BYTE,所以在这个宏定义当中,MAXIMUM_ALIGNOF=8

下面分析一下TYPEALIGN这个宏定义

 /* NOTE: TYPEALIGN[_DOWN] will not work if ALIGNVAL is not a power of 2.
  * That case seems extremely unlikely to be needed in practice, however.
  */
#define TYPEALIGN(ALIGNVAL,LEN) (((uintptr_t) (LEN) + ((ALIGNVAL) - 1)) & ~((uintptr_t) ((ALIGNVAL) - 1)))

一步一步的进行理解:(ALIGNVAL在我的机器上为8,那么我们就按照8来进行解析)

提前计算:8的二进制1000;8-1(即(ALIGNVAL) - 1))=7的二进制为0111;最开始的sizeof(XLogLongPageHeaderData)的结构体大小是20.(可自行查看PG的源代码)

(1)了解"与非"运算符(&~),这可以看成两步运算,~的优先级大于&,所以先进行~运算,在进行&运算。

(2)由于(ALIGNVAL) - 1的值为7,所以后面的部分~((uintptr_t) ((ALIGNVAL) - 1))的值为1000。

(3)前面的部分(((uintptr_t) (LEN) + ((ALIGNVAL) - 1))就是20+7 =27 ,转化为二进制为 0001 1011。

(4)与第(3)步的计算值进行&运算,得到0001 1000,转换为十进制为24。所以最初的宏SizeOfXLogLongPHD的大小为24。

 

总结:

通过上面几步,我明白了一下的几点:

(1)为什么需要对ALIGNVAL进行减1操作?

答:通过C语言的定义我们知道,其实ALIGNVAL必定是2的n次幂,因为它代表基本数据类型的size,比如sizeof(char)=2^0;sizeof(int)=2^2。这样转换为二进制必定是1后面接n个0。比如说8=2^3,转换为二进制就是1000,1后面接3个0;16=2^4,转换为二进制就是10000,1后面接4个0。

(2)TYPEALIGN宏定义的意义?

答:通过上面的运算我们能得到,将ALIGNVAL-1进行'非'操作,就是将最后的n位转为0,然后与前面的结构体的size进行与操作,最终的目的就是将sizeof(struct)的大小成为8的倍数。那我们的那个举例:sizeof(XLogLongPageHeaderData)的大小为20,在此基础上加上7就等于27,二进制为11011,然后与1000进行与操作,变为11000,十进制就是24=3*8

其实看到这里我们也就明白了MAXALIGN的作用其实就是为了使sizeof(struct)向上对齐,成为8的倍数的大小。

 

关注公众号【好便宜】( ID:haopianyi222 ),领红包啦~
阿里云,国内最大的云服务商,注册就送数千元优惠券:https://t.cn/AiQe5A0g
腾讯云,良心云,价格优惠: https://t.cn/AieHwwKl
搬瓦工,CN2 GIA 优质线路,搭梯子、海外建站推荐: https://t.cn/AieHwfX9
扫一扫关注公众号添加购物返利助手,领红包
Comments are closed.

推荐使用阿里云服务器

超多优惠券

服务器最低一折,一年不到100!

朕已阅去看看