起因
最近在看PHP7的源碼屈扎,想要看一下一個(gè)zval一個(gè)執(zhí)行流程,此時(shí)需要用到gdb調(diào)試,然后按照相關(guān)的步驟進(jìn)行
每一個(gè)zval的字節(jié)數(shù)是16芽淡,zval的結(jié)構(gòu)類(lèi)型
struct _zval_struct {
zend_value value; //8個(gè)字節(jié)
union u1; //4個(gè)字節(jié)
union u2; //4個(gè)字節(jié)
}
具體的,這個(gè)是php-7.4.19中的
struct _zval_struct {
zend_value value; /* value */ //8個(gè)字節(jié)
union { //4個(gè)字節(jié)
struct {
ZEND_ENDIAN_LOHI_3(
zend_uchar type, /* active type */ //通過(guò)type值來(lái)區(qū)分類(lèi)型
zend_uchar type_flags,
union {
uint16_t extra; /* not further specified */
} u)
} v;
uint32_t type_info;
} u1;
union {//4個(gè)字節(jié)
uint32_t next; /* hash collision chain */ //解決哈希沖突的
uint32_t cache_slot; /* cache slot (for RECV_INIT) */ //運(yùn)行時(shí)緩存
uint32_t opline_num; /* opline number (for FAST_CALL) */ //
uint32_t lineno; /* line number (for ast nodes) */ //php的哪一行
uint32_t num_args; /* arguments number for EX(This) */ //參數(shù)的個(gè)數(shù)
uint32_t fe_pos; /* foreach position */
uint32_t fe_iter_idx; /* foreach iterator index */ //游標(biāo)的索引位置
uint32_t access_flags; /* class constant access flags */ //prviate protected public
uint32_t property_guard; /* single property guard */ //防止類(lèi)中魔術(shù)方法的循環(huán)引用
uint32_t constant_flags; /* constant flags */
uint32_t extra; /* not further specified */
} u2;
};
gdb php
b ZEND_ECHO_SPEC_CV_HANDLER #設(shè)置斷點(diǎn)
r zval.php
n
n
p z
p *z
.
.
.
zval.php
<?php
$a = 2;
echo $a;
$b = 1.1;
echo $b;
$c = null;
echo $c;
$d = true;
echo $d;
$e = false;
echo $e;
$f = 'string';
echo $f;
$g = [1, 2, 3];
echo $g;
$h = new stdClass();
echo $h;// FATAL ERROR