日韩av黄I国产麻豆传媒I国产91av视频在线观看I日韩一区二区三区在线看I美女国产在线I麻豆视频国产在线观看I成人黄色短片

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > php >内容正文

php

详谈PHP垃圾回收机制

發(fā)布時間:2024/9/20 php 33 豆豆
生活随笔 收集整理的這篇文章主要介紹了 详谈PHP垃圾回收机制 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

引用計數基本知識 每個php變量存在一個叫"zval"的變量容器中。一個zval變量容器,除了包含變量的類型和值,還包括兩個字節(jié)的額外信息。第一個是"is_ref",是個bool值,用來標識這個變量是否是屬于引用集合(reference set)。通過這個字節(jié),php引擎才能把普通變量和引用變量區(qū)分開來,由于php允許用戶通過使用&來使用自定義引用,zval變量容器中還有一個內部引用計數機制,來優(yōu)化內存使用。第二個額外字節(jié)是"refcount",用以表示指向這個zval變量容器的變量(也稱符號即symbol)個數。所有的符號存在一個符號表中,其中每個符號都有作用域(scope),那些主腳本(比如:通過瀏覽器請求的的腳本)和每個函數或者方法也都有作用域。 當一個變量被賦常量值時,就會生成一個zval變量容器,如下例這樣: Example #1 生成一個新的zval容器 <?php $a?=?"new?string"; ?> 在上例中,新的變量a,是在當前作用域中生成的。并且生成了類型為string 和值為new string的變量容器。在額外的兩個字節(jié)信息中,"is_ref"被默認設置為FALSE,因為沒有任何自定義的引用生成。"refcount" 被設定為1,因為這里只有一個變量使用這個變量容器. 注意到當"refcount"的值是1時,"is_ref"的值總是FALSE. 如果你已經安裝了??Xdebug,你能通過調用函數xdebug_debug_zval()顯示"refcount"和"is_ref"的值。 Example #2 顯示zval信息 <?php xdebug_debug_zval('a'); ?> 以上例程會輸出: a: (refcount=1, is_ref=0)='new string' 把一個變量賦值給另一變量將增加引用次數(refcount). Example #3 增加一個zval的引用計數 <?php $a?=?"new?string"; $b?=?$a; xdebug_debug_zval(?'a'?); ?> 以上例程會輸出: a: (refcount=2, is_ref=0)='new string' 這時,引用次數是2,因為同一個變量容器被變量a 和變量b關聯.當沒必要時,php不會去復制已生成的變量容器。變量容器在”refcount“變成0時就被銷毀. 當任何關聯到某個變量容器的變量離開它的作用域(比如:函數執(zhí)行結束),或者對變量調用了函數unset()時,”refcount“就會減1,下面的例子就能說明: Example #4 減少引用計數 <?php $a?=?"new?string"; $c?=?$b?=?$a; xdebug_debug_zval(?'a'?); unset(?$b,?$c?); xdebug_debug_zval(?'a'?); ?> 以上例程會輸出: a: (refcount=3, is_ref=0)='new string'a: (refcount=1, is_ref=0)='new string' 如果我們現在執(zhí)行 unset($a);,包含類型和值的這個變量容器就會從內存中刪除。 復合類型(Compound Types) 當考慮像 arrayobject這樣的復合類型時,事情就稍微有點復雜. 與 標量(scalar)類型的值不同,arrayobject類型的變量把它們的成員或屬性存在自己的符號表中。這意味著下面的例子將生成三個zval變量容器。 Example #5 Creating aarray zval <?php $a?=?array(?'meaning'?=>?'life',?'number'?=>?42?); xdebug_debug_zval(?'a'?); ?> 以上例程的輸出類似于: a: (refcount=1, is_ref=0)=array ( 'meaning' => (refcount=1, is_ref=0)='life', 'number' => (refcount=1, is_ref=0)=42) 圖示: 上面的結果如果在PHP5中是沒有問題的,但是當我在PHP7中進行試驗驗證是發(fā)現輸出的結果和上面并不一致,如下: a: (refcount=1, is_ref=0)array(size=2) 'meaning'=> (refcount=2, is_ref=0)string'life' (length=4) 'number'=> (refcount=0, is_ref=0)int42
這三個zval變量容器是:ameaningnumber。增加和減少”refcount”的規(guī)則和上面提到的一樣. 下面, 我們在數組中再添加一個元素,并且把它的值設為數組中已存在元素的值: Example #6 添加一個已經存在的元素到數組中 <?php $a?=?array(?'meaning'?=>?'life',?'number'?=>?42?); $a['life']?=?$a['meaning']; xdebug_debug_zval(?'a'?); ?> 以上例程的輸出類似于: a: (refcount=1, is_ref=0)=array ( 'meaning' => (refcount=2, is_ref=0)='life', 'number' => (refcount=1, is_ref=0)=42, 'life' => (refcount=2, is_ref=0)='life') PHP7中的運行結果 a: (refcount=1, is_ref=0)array(size=3) 'meaning'=> (refcount=3, is_ref=0)string'life' (length=4) 'number'=> (refcount=0, is_ref=0)int42 'life' =>(refcount=3, is_ref=0)string 'life' (length=4) 圖示: 從以上的xdebug輸出信息,我們看到原有的數組元素和新添加的數組元素關聯到同一個"refcount"2的zval變量容器. 盡管 Xdebug的輸出顯示兩個值為'life'的 zval 變量容器,其實是同一個。 函數xdebug_debug_zval()不顯示這個信息,但是你能通過顯示內存指針信息來看到。 刪除數組中的一個元素,就是類似于從作用域中刪除一個變量. 刪除后,數組中的這個元素所在的容器的“refcount”值減少,同樣,當“refcount”為0時,這個變量容器就從內存中被刪除,下面又一個例子可以說明: Example #7 從數組中刪除一個元素 <?php $a?=?array(?'meaning'?=>?'life',?'number'?=>?42?); $a['life']?=?$a['meaning']; unset(?$a['meaning'],?$a['number']?); xdebug_debug_zval(?'a'?); ?> 以上例程的輸出類似于: a: (refcount=1, is_ref=0)=array ( 'life' => (refcount=1, is_ref=0)='life') PHP7中運行的結果 a: (refcount=1, is_ref=0)array(size=1) 'life'=> (refcount=2, is_ref=0)string'life' (length=4) 現在,當我們添加一個數組本身作為這個數組的元素時,事情就變得有趣,下個例子將說明這個。例中我們加入了引用操作符,否則php將生成一個復制。 Example #8 把數組作為一個元素添加到自己 <?php $a?=?array(?'one'?); $a[]?=&?$a; xdebug_debug_zval(?'a'?); ?> 以上例程的輸出類似于: a: (refcount=2, is_ref=1)=array ( 0 => (refcount=1, is_ref=0)='one', 1 => (refcount=2, is_ref=1)=...) PHP中運行的結果 a: (refcount=2, is_ref=1)array(size=2) 0=>(refcount=2, is_ref=0)string'one' (length=3) 1=> (refcount=2, is_ref=1)&array< 圖示: 能看到數組變量 (a) 同時也是這個數組的第二個元素(1) 指向的變量容器中“refcount”為2。上面的輸出結果中的"..."說明發(fā)生了遞歸操作, 顯然在這種情況下意味著"..."指向原始數組。 跟剛剛一樣,對一個變量調用unset,將刪除這個符號,且它指向的變量容器中的引用次數也減1。所以,如果我們在執(zhí)行完上面的代碼后,對變量$a調用unset, 那么變量$a 和數組元素 "1" 所指向的變量容器的引用次數減1, 從"2"變成"1". 下例可以說明: Example #9 Unsetting$a (refcount=1, is_ref=1)=array ( 0 => (refcount=1, is_ref=0)='one', 1 => (refcount=1, is_ref=1)=...) 圖示:
通過PHP5和PHP7環(huán)境中的運行結果對比可以看出,PHP7中的內存回收機制有了改變,那么為什么會有這種改變呢?我查閱了一些資料供大家參考。 PHP7 中的 zval 在 PHP7 中 zval 有了新的實現方式。最基礎的變化就是 zval 需要的內存不再是單獨從堆上分配,不再自己存儲引用計數。復雜數據類型(比如字符串、數組和對象)的引用計數由其自身來存儲。這種實現方式有以下好處: 簡單數據類型不需要單獨分配內存,也不需要計數; 不會再有兩次計數的情況。在對象中,只有對象自身存儲的計數是有效的; 由于現在計數由數值自身存儲,所以也就可以和非 zval 結構的數據共享,比如 zval 和 hashtable key 之間; 間接訪問需要的指針數減少了。 我們看看現在 zval 結構體的定義(現在在 zend_types.h 文件中): struct _zval_struct { ?zend_value? value;?? /* value */ ?union { ??struct { ???ZEND_ENDIAN_LOHI_4( ????zend_uchar type,?? /* active type */ ????zend_uchar type_flags, ????zend_uchar const_flags, ????zend_uchar reserved)? /* call info for EX(This) */ ??} v; ??uint32_t type_info; ?} u1; ?union { ??uint32_t? var_flags; ??uint32_t? next;???? /* hash collision chain */ ??uint32_t? cache_slot;?? /* literal cache slot */ ??uint32_t? lineno;??? /* line number (for ast nodes) */ ??uint32_t? num_args;??? /* arguments number for EX(This) */ ??uint32_t? fe_pos;??? /* foreach position */ ??uint32_t? fe_iter_idx;?? /* foreach iterator index */ ?} u2; }; 結構體的第一個元素沒太大變化,仍然是一個 value 聯合體。第二個成員是由一個表示類型信息的整型和一個包含四個字符變量的結構體組成的聯合體(可以忽略 ZEND_ENDIAN_LOHI_4 宏,它只是用來解決跨平臺大小端問題的)。這個子結構中比較重要的部分是 type(和以前類似)和 type_flags,這個接下來會解釋。 上面這個地方也有一點小問題:value 本來應該占 8 個字節(jié),但是由于內存對齊,哪怕只增加一個字節(jié),實際上也是占用 16 個字節(jié)(使用一個字節(jié)就意味著需要額外的 8 個字節(jié))。但是顯然我們并不需要 8 個字節(jié)來存儲一個 type 字段,所以我們在 u1 的后面增加了了一個名為 u2 的聯合體。默認情況下是用不到的,需要使用的時候可以用來存儲 4 個字節(jié)的數據。這個聯合體可以滿足不同場景下的需求。 PHP7 中 value 的結構定義如下: typedef union _zend_value { ?zend_long?? lval;??? /* long value */ ?double?? dval;??? /* double value */ ?zend_refcounted *counted; ?zend_string? *str; ?zend_array? *arr; ?zend_object? *obj; ?zend_resource *res; ?zend_reference *ref; ?zend_ast_ref? *ast; ?zval??? *zv; ?void??? *ptr; ?zend_class_entry *ce; ?zend_function *func; ?struct { ??uint32_t w1; ??uint32_t w2; ?} ww; } zend_value; 首先需要注意的是現在 value 聯合體需要的內存是 8 個字節(jié)而不是 16。它只會直接存儲整型(lval)或者浮點型(dval)數據,其他情況下都是指針(上面提到過,指針占用 8 個字節(jié),最下面的結構體由兩個 4 字節(jié)的無符號整型組成)。上面所有的指針類型(除了特殊標記的)都有一個同樣的頭(zend_refcounted)用來存儲引用計數: typedef struct _zend_refcounted_h { ?uint32_t?? refcount;?? /* reference counter 32-bit */ ?union { ??struct { ???ZEND_ENDIAN_LOHI_3( ????zend_uchar type, ????zend_uchar flags, /* used for strings & objects */ ????uint16_t? gc_info) /* keeps GC root number (or 0) and color */ ??} v; ??uint32_t type_info; ?} u; } zend_refcounted_h;
現在,這個結構體肯定會包含一個存儲引用計數的字段。除此之外還有 type、flags 和 gc_info。type 存儲的和 zval 中的 type 相同的內容,這樣 GC 在不存儲 zval 的情況下單獨使用引用計數。flags 在不同的數據類型中有不同的用途,這個放到下一部分講。 gc_info 和 PHP5 中的 buffered 作用相同,不過不再是位于根緩沖區(qū)的指針,而是一個索引數字。因為以前根緩沖區(qū)的大小是固定的(10000 個元素),所以使用一個 16 位(2 字節(jié))的數字代替 64 位(8 字節(jié))的指針足夠了。gc_info 中同樣包含一個『顏色』位用于回收時標記結點。 zval 內存管理 上文提到過 zval 需要的內存不再單獨從堆上分配。但是顯然總要有地方來存儲它,所以會存在哪里呢?實際上大多時候它還是位于堆中(所以前文中提到的地方重點不是堆,而是單獨分配),只不過是嵌入到其他的數據結構中的,比如 hashtable 和 bucket 現在就會直接有一個 zval 字段而不是指針。所以函數表編譯變量和對象屬性在存儲時會是一個 zval 數組并得到一整塊內存而不是散落在各處的 zval 指針。之前的 zval * 現在都變成了 zval。 之前當 zval 在一個新的地方使用時會復制一份 zval * 并增加一次引用計數。現在就直接復制 zval 的值(忽略 u2),某些情況下可能會增加其結構指針指向的引用計數(如果在進行計數)。 那么 PHP 怎么知道 zval 是否正在計數呢?不是所有的數據類型都能知道,因為有些類型(比如字符串或數組)并不是總需要進行引用計數。所以 type_info 字段就是用來記錄 zval 是否在進行計數的,這個字段的值有以下幾種情況: #define IS_TYPE_CONSTANT?? (1<<0) /* special */ #define IS_TYPE_IMMUTABLE?? (1<<1) /* special */ #define IS_TYPE_REFCOUNTED?? (1<<2) #define IS_TYPE_COLLECTABLE?? (1<<3) #define IS_TYPE_COPYABLE?? (1<<4) #define IS_TYPE_SYMBOLTABLE?? (1<<5) /* special */
注:在 7.0.0 的正式版本中,上面這一段宏定義的注釋這幾個宏是供 zval.u1.v.type_flags 使用的。這應該是注釋的錯誤,因為這個上述字段是 zend_uchar 類型。 type_info 的三個主要的屬性就是『可計數』(refcounted)、『可回收』(collectable)和『可復制』(copyable)。計數的問題上面已經提過了。『可回收』用于標記 zval 是否參與循環(huán),不如字符串通常是可計數的,但是你卻沒辦法給字符串制造一個循環(huán)引用的情況。 是否可復制用于表示在復制時是否需要在復制時制造(原文用的 "duplication" 來表述,用中文表達出來可能不是很好理解)一份一模一樣的實體。"duplication" 屬于深度復制,比如在復制數組時,不僅僅是簡單增加數組的引用計數,而是制造一份全新值一樣的數組。但是某些類型(比如對象和資源)即使 "duplication" 也只能是增加引用計數,這種就屬于不可復制的類型。這也和對象和資源現有的語義匹配(現有,PHP7 也是這樣,不單是 PHP5)。 下面的表格上標明了不同的類型會使用哪些標記(x 標記的都是有的特性)。『簡單類型』(simple types)指的是整型或布爾類型這些不使用指針指向一個結構體的類型。下表中也有『不可變』(immutable)的標記,它用來標記不可變數組的,這個在下一部分再詳述。 interned string(保留字符)在這之前沒有提過,其實就是函數名、變量名等無需計數、不可重復的字符串。 | refcounted | collectable | copyable | immutable ----------------+------------+-------------+----------+---------- simple types??? |??????????? |???????????? |????????? | string????????? |????? x???? |???????????? |???? x??? | interned string |??????????? |???????????? |????????? | array?????????? |????? x???? |????? x????? |???? x??? | immutable array |??????????? |???????????? |????????? |???? x object????????? |????? x???? |????? x????? |????????? | resource??????? |????? x???? |???????????? |????????? | reference?????? |????? x???? |???????????? |????????? | 要理解這一點,我們可以來看幾個例子,這樣可以更好的認識 zval 內存管理是怎么工作的。 下面是整數行為模式,在上文中 PHP5 的例子的基礎上進行了一些簡化 : <?php $a= 42; // $a = zval_1(type=IS_LONG, value=42) $b= $a; // $a = zval_1(type=IS_LONG, value=42) ???// $b = zval_2(type=IS_LONG, value=42) $a+= 1; // $a = zval_1(type=IS_LONG, value=43) ???// $b = zval_2(type=IS_LONG, value=42) unset($a); // $a = zval_1(type=IS_UNDEF) ???// $b = zval_2(type=IS_LONG, value=42) 這個過程其實挺簡單的。現在整數不再是共享的,變量直接就會分離成兩個單獨的 zval,由于現在 zval 是內嵌的所以也不需要單獨分配內存,所以這里的注釋中使用 = 來表示的而不是指針符號 ->,unset 時變量會被標記為 IS_UNDEF。下面看一下更復雜的情況: <?php $a= []; // $a = zval_1(type=IS_ARRAY) -> zend_array_1(refcount=1, value=[]) $b= $a; // $a = zval_1(type=IS_ARRAY) -> zend_array_1(refcount=2, value=[]) ???// $b = zval_2(type=IS_ARRAY) ---^ // zval 分離在這里進行 $a[] = 1 // $a = zval_1(type=IS_ARRAY) -> zend_array_2(refcount=1, value=[1]) ???// $b = zval_2(type=IS_ARRAY) -> zend_array_1(refcount=1, value=[]) unset($a); // $a = zval_1(type=IS_UNDEF), zend_array_2 被銷毀 ???// $b = zval_2(type=IS_ARRAY) -> zend_array_1(refcount=1, value=[]) 這種情況下每個變量變量有一個單獨的 zval,但是是指向同一個(有引用計數) zend_array 的結構體。修改其中一個數組的值時才會進行復制。這點和 PHP5 的情況類似。 類型(Types) 我們大概看一下 PHP7 支持哪些類型(zval 使用的類型標記): /* regular data types */ #define IS_UNDEF???? 0 #define IS_NULL?????1 #define IS_FALSE???? 2 #define IS_TRUE????? 3 #define IS_LONG?????4 #define IS_DOUBLE????5 #define IS_STRING????6 #define IS_ARRAY????7 #define IS_OBJECT????8 #define IS_RESOURCE????9 #define IS_REFERENCE??? 10 /* constant expressions */ #define IS_CONSTANT???? 11 #define IS_CONSTANT_AST??? 12 /* internal types */ #define IS_INDIRECT???? 15 #define IS_PTR????? 17 這個列表和 PHP5 使用的類似,不過增加了幾項: IS_UNDEF 用來標記之前為 NULL 的 zval 指針(和 IS_NULL 并不沖突)。比如在上面的例子中使用 unset 注銷變量; IS_BOOL 現在分割成了 IS_FALSE 和 IS_TRUE 兩項。現在布爾類型的標記是直接記錄到 type 中,這么做可以優(yōu)化類型檢查。不過這個變化對用戶是透明的,還是只有一個『布爾』類型的數據(PHP 腳本中)。 PHP 引用不再使用 is_ref 來標記,而是使用 IS_REFERENCE 類型。這個也要放到下一部分講; IS_INDIRECT? 和? IS_PTR 是特殊的內部標記。 實際上上面的列表中應該還存在兩個 fake types,這里忽略了。 IS_LONG 類型表示的是一個 zend_long 的值,而不是原生的 C 語言的 long 類型。原因是 Windows 的 64 位系統(tǒng)(LLP64)上的 long 類型只有 32 位的位深度。所以 PHP5 在 Windows 上只能使用 32 位的數字。PHP7 允許你在 64 位的操作系統(tǒng)上使用 64 位的數字,即使是在 Windows 上面也可以。 zend_refcounted 的內容會在下一部分講。下面看看 PHP 引用的實現。 引用 PHP7 使用了和 PHP5 中完全不同的方法來處理 PHP & 符號引用的問題(這個改動也是 PHP7 開發(fā)過程中大量 bug 的根源)。我們先從 PHP5 中 PHP 引用的實現方式說起。 通常情況下, 寫時復制原則意味著當你修改一個 zval 之前需要對其進行分離來保證始終修改的只是某一個 PHP 變量的值。這就是傳值調用的含義。 但是使用 PHP 引用時這條規(guī)則就不適用了。如果一個 PHP 變量是 PHP 引用,就意味著你想要在將多個 PHP 變量指向同一個值。PHP5 中的 is_ref 標記就是用來注明一個 PHP 變量是不是 PHP 引用,在修改時需不需要進行分離的。比如: <?php $a= []; // $a? -> zval_1(type=IS_ARRAY, refcount=1, is_ref=0) -> HashTable_1(value=[]) $b=& $a; // $a, $b -> zval_1(type=IS_ARRAY, refcount=2, is_ref=1) -> HashTable_1(value=[]) $b[] = 1; // $a = $b = zval_1(type=IS_ARRAY, refcount=2, is_ref=1) -> HashTable_1(value=[1]) ???// 因為 is_ref 的值是 1, 所以 PHP 不會對 zval 進行分離
但是這個設計的一個很大的問題在于它無法在一個 PHP 引用變量和 PHP 非引用變量之間共享同一個值。比如下面這種情況: <?php $a= []; // $a?? -> zval_1(type=IS_ARRAY, refcount=1, is_ref=0) -> HashTable_1(value=[]) $b= $a; // $a, $b? -> zval_1(type=IS_ARRAY, refcount=2, is_ref=0) -> HashTable_1(value=[]) $c= $b// $a, $b, $c -> zval_1(type=IS_ARRAY, refcount=3, is_ref=0) -> HashTable_1(value=[]) $d=& $c; // $a, $b -> zval_1(type=IS_ARRAY, refcount=2, is_ref=0) -> HashTable_1(value=[]) ???// $c, $d -> zval_1(type=IS_ARRAY, refcount=2, is_ref=1) -> HashTable_2(value=[]) ???// $d 是 $c 的引用, 但卻不是 $a 的 $b, 所以這里 zval 還是需要進行復制 ???// 這樣我們就有了兩個 zval, 一個 is_ref 的值是 0, 一個 is_ref 的值是 1. $d[] = 1; // $a, $b -> zval_1(type=IS_ARRAY, refcount=2, is_ref=0) -> HashTable_1(value=[]) ???// $c, $d -> zval_1(type=IS_ARRAY, refcount=2, is_ref=1) -> HashTable_2(value=[1]) ???// 因為有兩個分離了的 zval, $d[] = 1 的語句就不會修改 $a 和 $b 的值.
這種行為方式也導致在 PHP 中使用引用比普通的值要慢。比如下面這個例子: <?php $array= range(0, 1000000); $ref=& $array; var_dump(count($array)); // <-- 這里會進行分離
因為 count() 只接受傳值調用,但是 $array 是一個 PHP 引用,所以 count() 在執(zhí)行之前實際上會有一個對數組進行完整的復制的過程。如果 $array 不是引用,這種情況就不會發(fā)生了。 現在我們來看看 PHP7 中 PHP 引用的實現。因為 zval 不再單獨分配內存,也就沒辦法再使用和 PHP5 中相同的實現了。所以增加了一個 IS_REFERENCE 類型,并且專門使用 zend_reference 來存儲引用值: struct _zend_reference { ?zend_refcounted gc; ?zval??? val; }; 本質上 zend_reference 只是增加了引用計數的 zval。所有引用變量都會存儲一個 zval 指針并且被標記為 IS_REFERENCE。val 和其他的 zval 的行為一樣,尤其是它也可以在共享其所存儲的復雜變量的指針,比如數組可以在引用變量和值變量之間共享。 我們還是看例子,這次是 PHP7 中的語義。為了簡潔明了這里不再單獨寫出 zval,只展示它們指向的結構體: <?php $a= []; // $a????????? -> zend_array_1(refcount=1, value=[]) $b=& $a; // $a, $b -> zend_reference_1(refcount=2) -> zend_array_1(refcount=1, value=[]) $b[] = 1; // $a, $b -> zend_reference_1(refcount=2) -> zend_array_1(refcount=1, value=[1]) 上面的例子中進行引用傳遞時會創(chuàng)建一個 zend_reference,注意它的引用計數是 2(因為有兩個變量在使用這個 PHP 引用)。但是值本身的引用計數是 1(因為 zend_reference 只是有一個指針指向它)。下面看看引用和非引用混合的情況: <?php $a= []; // $a?? -> zend_array_1(refcount=1, value=[]) $b= $a; // $a, $b, -> zend_array_1(refcount=2, value=[]) $c= $b// $a, $b, $c -> zend_array_1(refcount=3, value=[]) $d=& $c; // $a, $b???????? -> zend_array_1(refcount=3, value=[]) ???// $c, $d -> zend_reference_1(refcount=2) ---^ ???// 注意所有變量共享同一個 zend_array, 即使有的是 PHP 引用有的不是 $d[] = 1; // $a, $b???????? -> zend_array_1(refcount=2, value=[]) ???// $c, $d -> zend_reference_1(refcount=2) -> zend_array_2(refcount=1, value=[1]) ???// 只有在這時進行賦值的時候才會對 zend_array 進行賦值
這里和 PHP5 最大的不同就是所有的變量都可以共享同一個數組,即使有的是 PHP 引用有的不是。只有當其中某一部分被修改的時候才會對數組進行分離。這也意味著使用 count() 時即使給其傳遞一個很大的引用數組也是安全的,不會再進行復制。不過引用仍然會比普通的數值慢,因為存在需要為 zend_reference 結構體分配內存(間接)并且引擎本身處理這一塊兒也不快的的原因。 結語 總結一下 PHP7 中最重要的改變就是 zval 不再單獨從堆上分配內存并且不自己存儲引用計數。需要使用 zval 指針的復雜類型(比如字符串、數組和對象)會自己存儲引用計數。這樣就可以有更少的內存分配操作、更少的間接指針使用以及更少的內存分配。
清理變量容器的問題(Cleanup Problems) 盡管不再有某個作用域中的任何符號指向這個結構(就是變量容器),由于數組元素“1”仍然指向數組本身,所以這個容器不能被清除 。因為沒有另外的符號指向它,用戶沒有辦法清除這個結構,結果就會導致內存泄漏。慶幸的是,php將在腳本執(zhí)行結束時清除這個數據結構,但是在php清除之前,將耗費不少內存。如果你要實現分析算法,或者要做其他像一個子元素指向它的父元素這樣的事情,這種情況就會經常發(fā)生。當然,同樣的情況也會發(fā)生在對象上,實際上對象更有可能出現這種情況,因為對象總是隱式的被引用。 如果上面的情況發(fā)生僅僅一兩次倒沒什么,但是如果出現幾千次,甚至幾十萬次的內存泄漏,這顯然是個大問題。這樣的問題往往發(fā)生在長時間運行的腳本中,比如請求基本上不會結束的守護進程(deamons)或者單元測試中的大的套件(sets)中。后者的例子:在給巨大的eZ(一個知名的PHP Library) 組件庫的模板組件做單元測試時,就可能會出現問題。有時測試可能需要耗用2GB的內存,而測試服務器很可能沒有這么大的內存。
回收周期(Collecting Cycles) 傳統(tǒng)上,像以前的 php 用到的引用計數內存機制,無法處理循環(huán)的引用內存泄漏。然而 5.3.0 PHP 使用文章??引用計數系統(tǒng)中的同步周期回收(Concurrent Cycle Collection in Reference Counted Systems)中的同步算法,來處理這個內存泄漏問題。 對算法的完全說明有點超出這部分內容的范圍,將只介紹其中基礎部分。首先,我們先要建立一些基本規(guī)則,如果一個引用計數增加,它將繼續(xù)被使用,當然就不再在垃圾中。如果引用計數減少到零,所在變量容器將被清除(free)。就是說,僅僅在引用計數減少到非零值時,才會產生垃圾周期(garbage cycle)。其次,在一個垃圾周期中,通過檢查引用計數是否減1,并且檢查哪些變量容器的引用次數是零,來發(fā)現哪部分是垃圾。 為避免不得不檢查所有引用計數可能減少的垃圾周期,這個算法把所有可能根(possible roots 都是zval變量容器),放在根緩沖區(qū)(root buffer)中(用紫色來標記,稱為疑似垃圾),這樣可以同時確保每個可能的垃圾根(possible garbage root)在緩沖區(qū)中只出現一次。僅僅在根緩沖區(qū)滿了時,才對緩沖區(qū)內部所有不同的變量容器執(zhí)行垃圾回收操作。看上圖的步驟 A。 在步驟 B 中,模擬刪除每個紫色變量。模擬刪除時可能將不是紫色的普通變量引用數減"1",如果某個普通變量引用計數變成0了,就對這個普通變量再做一次模擬刪除。每個變量只能被模擬刪除一次,模擬刪除后標記為灰(原文說確保不會對同一個變量容器減兩次"1",不對的吧)。 在步驟 C 中,模擬恢復每個紫色變量。恢復是有條件的,當變量的引用計數大于0時才對其做模擬恢復。同樣每個變量只能恢復一次,恢復后標記為黑,基本就是步驟 B 的逆運算。這樣剩下的一堆沒能恢復的就是該刪除的藍色節(jié)點了,在步驟 D 中遍歷出來真的刪除掉。 算法中都是模擬刪除、模擬恢復、真的刪除,都使用簡單的遍歷即可(最典型的深搜遍歷)。復雜度為執(zhí)行模擬操作的節(jié)點數正相關,不只是紫色的那些疑似垃圾變量。 現在,你已經對這個算法有了基本了解,我們回頭來看這個如何與PHP集成。默認的,PHP的垃圾回收機制是打開的,然后有個php.ini 設置允許你修改它:zend.enable_gc 。 當垃圾回收機制打開時,每當根緩存區(qū)存滿時,就會執(zhí)行上面描述的循環(huán)查找算法。根緩存區(qū)有固定的大小,可存10,000個可能根,當然你可以通過修改PHP源碼文件Zend/zend_gc.c中的常量GC_ROOT_BUFFER_MAX_ENTRIES,然后重新編譯PHP,來修改這個10,000值。當垃圾回收機制關閉時,循環(huán)查找算法永不執(zhí)行,然而,可能根將一直存在根緩沖區(qū)中,不管在配置中垃圾回收機制是否激活。 當垃圾回收機制關閉時,如果根緩沖區(qū)存滿了可能根,更多的可能根顯然不會被記錄。那些沒被記錄的可能根,將不會被這個算法來分析處理。如果他們是循環(huán)引用周期的一部分,將永不能被清除進而導致內存泄漏。 即使在垃圾回收機制不可用時,可能根也被記錄的原因是,相對于每次找到可能根后檢查垃圾回收機制是否打開而言,記錄可能根的操作更快。不過垃圾回收和分析機制本身要耗不少時間。 除了修改配置zend.enable_gc ,也能通過分別調用gc_enable()gc_disable()函數來打開和關閉垃圾回收機制。調用這些函數,與修改配置項來打開或關閉垃圾回收機制的效果是一樣的。即使在可能根緩沖區(qū)還沒滿時,也能強制執(zhí)行周期回收。你能調用gc_collect_cycles()函數達到這個目的。這個函數將返回使用這個算法回收的周期數。 允許打開和關閉垃圾回收機制并且允許自主的初始化的原因,是由于你的應用程序的某部分可能是高時效性的。在這種情況下,你可能不想使用垃圾回收機制。當然,對你的應用程序的某部分關閉垃圾回收機制,是在冒著可能內存泄漏的風險,因為一些可能根也許存不進有限的根緩沖區(qū)。因此,就在你調用gc_disable()函數釋放內存之前,先調用gc_collect_cycles()函數可能比較明智。因為這將清除已存放在根緩沖區(qū)中的所有可能根,然后在垃圾回收機制被關閉時,可留下空緩沖區(qū)以有更多空間存儲可能根。

來源:http://blog.csdn.net/wangshiqueque/article/details/78074363

總結

以上是生活随笔為你收集整理的详谈PHP垃圾回收机制的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

欧美日韩国产综合一区二区 | 中日韩欧美精彩视频 | 日韩在线高清免费视频 | 国产资源免费在线观看 | 麻豆精品国产传媒 | 天天干夜夜操视频 | 最近日本字幕mv免费观看在线 | 在线观看av大片 | 久久成熟| 国产精品久久久久久久av电影 | 国产无限资源在线观看 | 特级毛片在线观看 | 欧美日韩高清国产 | 中文字幕高清在线播放 | 高清日韩一区二区 | 韩日成人av| 91亚洲精品久久久蜜桃 | 91av网站在线观看 | 亚洲综合视频在线 | 最新成人av | 日韩国产精品一区 | 日韩资源在线 | 精品成人在线 | 91av在线视频播放 | 最近中文字幕大全中文字幕免费 | 中文字幕一区二区三区乱码在线 | 中文字幕在线观看第一区 | 精品国产乱码久久久久久浪潮 | 久久久www成人免费毛片麻豆 | 亚洲精品久久久久久中文传媒 | 国产精品中文字幕在线 | 韩国av电影在线观看 | 亚洲三级av | 精品国产精品久久一区免费式 | av色图天堂网 | 日三级在线 | 国产香蕉av | 国产精品露脸在线 | 婷婷 中文字幕 | 中文av字幕在线观看 | 精品久久中文 | 丁香婷婷激情啪啪 | 久插视频 | 亚洲视频www| 亚洲国产精品传媒在线观看 | 国产小视频国产精品 | 久久精品视频在线观看 | 99精品在线| 91桃色在线免费观看 | 色99久久 | 国产丝袜网站 | 国产精品v欧美精品v日韩 | 友田真希x88av | 国产一级精品绿帽视频 | 在线观看 国产 | 麻豆传媒视频在线播放 | 亚州天堂| 成人av在线网址 | 欧美a级一区二区 | 97国产大学生情侣酒店的特点 | 色www永久免费 | 国产在线va | 亚洲精品中文字幕在线 | 精品国产成人av | 欧美一区二区三区在线播放 | 最新中文字幕在线播放 | 欧美亚洲三级 | 视色网站| 国产色秀视频 | 色a综合| av千婊在线免费观看 | 国产精品国产毛片 | 久草视频看看 | 欧美性脚交 | 日韩com| 毛片久久久 | 国产精品一区二区久久久久 | 波多野结衣一区三区 | 欧美日韩99| 九九热在线免费观看 | 99国产一区二区三精品乱码 | 一区二区久久久久 | 国产在线探花 | zzijzzij日本成熟少妇 | 中文一区二区三区在线观看 | 日韩中文字幕国产精品 | 草莓视频在线观看免费观看 | 久草视频手机在线 | 欧美日韩二区三区 | 久久精品日本啪啪涩涩 | www色婷婷com| 九九热在线精品 | 97精品国产97久久久久久春色 | 999久久久欧美日韩黑人 | 成人免费视频在线观看 | 亚洲综合色站 | 四虎影视精品成人 | 国产视频在线观看一区 | 在线免费高清一区二区三区 | 成人一级片免费看 | 一区二区三区日韩在线 | 成人免费在线网 | 99精品国产一区二区三区不卡 | 首页中文字幕 | 五月婷婷影视 | 久久精品1区 | 欧美日韩视频 | 亚州精品国产 | 精品国产乱码久久久久久1区2匹 | 超碰激情在线 | 国产中文字幕在线免费观看 | 日韩av偷拍 | a天堂在线看 | 国产成人精品av久久 | 久久免费视频3 | 国产一区在线观看视频 | 中文字幕一区二区三区四区视频 | 91麻豆精品国产91久久久使用方法 | 欧美小视频在线观看 | 91香蕉视频黄色 | 日日干日日色 | 国产精品一区二区中文字幕 | 日韩精品第一区 | 日本精品一区二区三区在线观看 | 成人在线观看av | 国产美女视频免费观看的网站 | 精品福利在线观看 | 免费观看黄色12片一级视频 | 免费看污污视频的网站 | 久色免费视频 | 91色九色| 国产福利av在线 | 婷婷国产v亚洲v欧美久久 | 国产精品久久久久久久午夜 | 亚洲国产电影在线观看 | 一区二区三区精品在线视频 | 激情久久久 | 日韩大陆欧美高清视频区 | 天天天射 | 欧美91精品 | 国产黄色片久久久 | 三级大片网站 | 日韩成人免费在线观看 | 国产精品igao视频网入口 | 中文字幕在线观看视频一区二区三区 | 在线观看精品视频 | 色婷婷狠狠干 | 国产精品va在线播放 | 在线看不卡av | 美女久久 | 国产原创在线 | 久久精品中文字幕少妇 | 中文字幕亚洲精品在线观看 | 午夜99| 99热精品在线 | 国产日本亚洲高清 | 久久一区二 | 日韩免费播放 | 五月婷婷av | 欧美日韩亚洲第一 | 国产 亚洲 欧美 在线 | 国产黄在线观看 | 91精品国产福利在线观看 | 欧美在一区 | 久久久久久久久爱 | 999久久a精品合区久久久 | av动图| 99久久精品国产欧美主题曲 | 欧美日本高清视频 | 成年人在线 | 日本xxxxav | 91人人澡人人爽人人精品 | 九九综合久久 | 亚洲最新av网站 | 一区二区三区不卡在线 | 大胆欧美gogo免费视频一二区 | 成人免费视频视频在线观看 免费 | 国产18精品乱码免费看 | 久草在线中文视频 | 天天射天天干天天操 | 日韩高清在线一区二区 | 成人蜜桃网 | 不卡的av中文字幕 | 在线之家免费在线观看电影 | 一区二区三区四区不卡 | 久久精品视频观看 | 男女啪啪免费网站 | 久久人人97超碰国产公开结果 | 丁香婷五月 | 日本色小说视频 | 香蕉久草 | 综合伊人av | 色综合在 | 激情综合五月网 | 91精品天码美女少妇 | 性色va| 亚洲黄色在线观看 | 亚洲视频 一区 | 久久97超碰 | 国产一区免费看 | 天天视频色版 | 91九色在线视频观看 | 亚洲成人免费 | 91人人网 | 永久免费在线 | 日本免费久久高清视频 | 在线播放国产一区二区三区 | 中文字幕国产精品 | 欧美日韩国产精品一区 | 狠狠做深爱婷婷综合一区 | 天天操天天摸天天射 | 日韩在线国产精品 | 婷婷去俺也去六月色 | 有码一区二区三区 | av资源在线看 | 菠萝菠萝在线精品视频 | 91在线观看高清 | 久久精品一区二区三区视频 | 日韩专区 在线 | 久久超碰免费 | 国产在线观看91 | 日本久久久久久科技有限公司 | 九九热在线观看视频 | 欧美在线视频一区二区三区 | 午夜视频久久久 | www.黄色片网站 | 日韩精品一区二区免费视频 | 欧美日韩中文在线视频 | 亚洲成av人片一区二区梦乃 | 国产五月色婷婷六月丁香视频 | 成人高清在线 | 久久综合色8888 | 国产精品手机播放 | 日韩在线观看视频中文字幕 | 天天射成人| 成人av资源在线 | 亚洲精品视频第一页 | 天天操狠狠操 | 日韩一区二区三区高清在线观看 | 午夜精品一二区 | 狠狠干电影 | 久久精品中文字幕 | 9797在线看片亚洲精品 | 在线黄色免费av | 精品国产一区在线观看 | 亚洲一区二区视频在线播放 | 亚洲成人频道 | 精品日韩视频 | 久草综合在线 | 日韩在线免费观看视频 | 狠狠狠狠狠狠狠干 | 成人午夜电影免费在线观看 | av不卡在线看| 亚洲无吗视频在线 | 99久久99精品 | 天天综合婷婷 | 中文字幕一区二区三区四区在线视频 | 成人a在线 | 香蕉日日 | 国产人成看黄久久久久久久久 | 精品在线观看一区二区 | 亚洲高清视频在线播放 | 天天射天天 | 2024国产精品视频 | 欧洲一区二区在线观看 | 99久久精品无码一区二区毛片 | 成年人电影毛片 | 免费看在线看www777 | 丁香婷婷综合色啪 | 亚洲成人黄 | 精品国产免费人成在线观看 | 免费视频国产 | 最近免费中文字幕大全高清10 | 88av色 | 亚洲国产伊人 | 日日爽日日操 | 婷婷丁香av| 亚洲精品videossex少妇 | jizz18欧美18 | 精品a级片 | 狠狠干狠狠操 | 久久精品视频免费 | 成人天堂网| 国产视频在线免费 | www.av中文字幕.com| 久久精品在线视频 | 亚洲资源网| 国产高清在线永久 | 婷婷色av | 日韩羞羞 | 国产精品久久久久久久久久ktv | 亚洲三级国产 | 日韩精品一区二区在线观看视频 | 亚洲国产三级在线 | 国产高清在线 | 美女网站视频久久 | 婷婷丁香导航 | 热久久这里只有精品 | 日批网站免费观看 | 亚洲精品日韩一区二区电影 | 国产精品久久久久久久久久久杏吧 | 国产一二区视频 | 国产精品黑丝在线观看 | 国产免费三级在线观看 | av看片在线 | 亚洲一二三区精品 | 99精品国产兔费观看久久99 | 97精品国产 | 国产精品久久久久久久av电影 | 成人免费xxxxxx视频 | 国产色一区| 成人免费毛片aaaaaa片 | 久久久久久久国产精品 | 99精品在这里 | 亚洲精品毛片一级91精品 | 伊人伊成久久人综合网站 | 精品伦理一区二区三区 | 97色婷婷| www免费在线观看 | 狠狠干狠狠艹 | 97看片| 日韩欧美69 | 青青河边草免费 | 精品不卡av| 国产一区二区手机在线观看 | 香蕉网在线播放 | 国产一级片免费视频 | 特黄特色特刺激视频免费播放 | 亚洲a成人v | 国产夫妻自拍av | 日韩乱色精品一区二区 | 成片免费| 69绿帽绿奴3pvideos | 中国一区二区视频 | av免费在线免费观看 | 在线免费观看国产黄色 | 免费a级毛片在线看 | 毛片精品免费在线观看 | 日韩中文字幕在线观看 | 啪啪精品| 国产亚洲精品免费 | 亚洲福利精品 | 国产96av| 久久婷婷视频 | 五月综合激情 | 日韩在线| 国产永久免费 | 色婷婷天天干 | 青草视频在线 | 国产精品1区 | 国产精品一区二区免费视频 | 99久久夜色精品国产亚洲 | 中文字幕国产 | 婷婷天天色 | 狠狠操导航 | 奇米网网址 | 精品国产亚洲日本 | 精品视频不卡 | a电影免费看 | 91精品区 | 久久好看| 黄色软件视频大全免费下载 | 一区二区三区四区精品视频 | 国产精品一区二区无线 | 91精品在线免费观看 | 日本久久久精品视频 | 国产精久久| 亚洲涩涩网 | 91福利视频一区 | 日韩素人在线观看 | 日韩v在线 | 国产精品毛片一区视频 | 国产网站av | 精品亚洲视频在线观看 | 四川妇女搡bbbb搡bbbb搡 | wwwwwww黄| 91传媒视频在线观看 | 日韩电影在线一区二区 | 97精品超碰一区二区三区 | 免费观看黄| 国产第一页在线观看 | 精油按摩av| 91传媒免费观看 | 国产免费又爽又刺激在线观看 | 欧美怡红院视频 | 69av网| 久久电影网站中文字幕 | 国产精品一二 | 亚洲欧美视频在线播放 | a黄色片 | 天天久久夜夜 | 国产精品麻豆视频 | 不卡国产在线 | 国产精品美女视频 | 欧美三级在线播放 | 一级久久久 | 国产精品一区在线观看你懂的 | 日韩一级电影在线 | a级免费观看 | 久久五月网 | 国产香蕉视频 | 亚洲综合成人婷婷小说 | 国产精品久久久久久久久免费 | 天天操天天射天天插 | 久草资源在线观看 | 久久久久久蜜桃一区二区 | 黄色影院在线免费观看 | 91精品视频播放 | 精品视频成人 | 国产大片黄色 | 成人禁用看黄a在线 | 成年人在线观看视频免费 | 黄色三级免费观看 | 国产韩国日本高清视频 | 亚洲免费在线观看视频 | 色久网| 日本在线观看一区二区三区 | 在线小视频你懂的 | 国产小视频在线观看免费 | 国产精品99久久免费黑人 | 成人毛片在线视频 | 国产精品99久久免费黑人 | 97天天干 | 黄色三级在线 | 91av色| 久久天天躁夜夜躁狠狠躁2022 | 久久久久久久久影院 | 高清av网站| 久久观看最新视频 | 国产精品综合在线观看 | 国产在线观看免费 | 国产亚洲日 | 日韩免费视频线观看 | 超碰97在线资源 | 天天色棕合合合合合合 | 国产色小视频 | 免费国产在线精品 | 亚洲精品高清视频 | 99欧美| 亚洲综合成人在线 | 欧美一级日韩免费不卡 | 精品视频久久 | 午夜精品久久久久久久99 | 亚洲欧美日韩国产一区二区 | av大片网址 | 久久五月网 | 成人九九视频 | 91在线观看高清 | 操操操av | 嫩草av在线 | 亚洲高清在线 | 亚洲人xxx| 亚州人成在线播放 | 久久99久久99精品免观看粉嫩 | 婷婷免费在线视频 | 制服丝袜天堂 | 99视频在线免费观看 | 国产91影视| 国内久久视频 | 色橹橹欧美在线观看视频高清 | 国产精品大片在线观看 | 久青草视频 | 久久免费黄色大片 | 免费三级av | 中文字幕亚洲不卡 | 久久美女视频 | www.久久免费 | 成全在线视频免费观看 | 视频在线观看一区 | 天天天天综合 | 久久狠狠婷婷 | 在线v片| 黄色一级大片在线观看 | 人人干人人做 | 91亚洲国产 | 天天操天天操天天干 | 午夜视频色 | 亚洲乱码中文字幕综合 | 免费黄色a网站 | 在线中文日韩 | 日韩视频一区二区在线 | 国产精品乱码高清在线看 | 91av欧美 | 伊人热 | 青青网视频 | 麻豆国产网站 | 超碰在线1| 夜夜干夜夜| 久久草在线视频国产 | 精品国产91亚洲一区二区三区www | 一区二区中文字幕在线播放 | 久久99欧美 | 久久99在线视频 | 国产精品伦一区二区三区视频 | 国产色久| 国产精品免费久久久久久久久久中文 | 在线观看中文字幕视频 | 久久综合影音 | 91丨九色丨蝌蚪丨老版 | 日韩免费观看一区二区 | 91视频 - 88av | 久久人人精品 | 亚洲精品国产精品国 | 99视频网站 | 精品国产一区二 | 国产精品一区二区在线观看免费 | www激情com| 在线观看国产中文字幕 | 日日激情| 黄色免费av | 日韩在线观看 | 国产夫妻性生活自拍 | 国产福利电影网址 | 亚洲欧洲成人精品av97 | 五月婷婷在线视频观看 | 69av久久 | 国内精品免费久久影院 | 麻豆一精品传二传媒短视频 | 成人一级免费电影 | 久久国产手机看片 | 三级黄色欧美 | 97视频人人 | 人人澡av | 免费看的黄色小视频 | 久久国产二区 | 久久精品美女视频网站 | 日本午夜在线亚洲.国产 | 91福利试看 | 免费在线黄色av | 亚洲精品久久久久久久不卡四虎 | 超碰在线个人 | av福利在线导航 | 久久视频在线 | 国产一级二级在线 | 国产一区在线观看免费 | 精品福利在线 | 久久不见久久见免费影院 | 免费午夜av | 久热精品国产 | 人人爽久久久噜噜噜电影 | 国产综合在线视频 | 亚洲国产成人久久 | 免费国产黄线在线观看视频 | 在线免费观看欧美日韩 | 这里只有精品视频在线观看 | 日韩在线 | 激情av综合 | 国产不卡在线观看视频 | 日韩一区二区免费播放 | 99高清视频有精品视频 | 久久夜靖品 | 国产一区二区不卡视频 | 日本在线观看中文字幕 | 国产亚洲婷婷免费 | 最新一区二区三区 | 久久男人视频 | 国产精品入口66mio女同 | 国产精品久久久久aaaa九色 | 成人在线黄色 | 久久久久久久久久久免费 | 狠狠色丁香久久婷婷综合丁香 | 午夜免费电影院 | 日韩中文字幕视频在线观看 | 色综合久久久网 | 欧美性精品 | 婷婷色综| 亚洲精品视频在线观看免费 | 综合天天久久 | 国产精品视频免费看 | 五月婷婷毛片 | 久久91网 | 亚洲国产精品va在线看 | 草樱av| 久久av一区二区三区亚洲 | 国产精品久久久久久久久大全 | 欧美激情h | 久久开心激情 | 香蕉视频免费在线播放 | 国产高清av免费在线观看 | 亚洲国产大片 | 免费电影一区二区三区 | 国产精品原创视频 | 色欧美视频 | 欧美日韩在线精品一区二区 | 久久国产精品二国产精品中国洋人 | 91中文字幕网 | 黄色软件在线看 | 国产日产亚洲精华av | 国产久草在线观看 | 国产精品自产拍在线观看 | 亚洲国产欧美在线看片xxoo | 干干夜夜 | 波多野结衣电影一区 | 激情婷婷亚洲 | 色综合天天综合 | 色网站国产精品 | 一区二区三区日韩在线观看 | 九九爱免费视频 | 在线播放精品一区二区三区 | 国产一区欧美一区 | 国产一区二区三精品久久久无广告 | 国产精品久久一区二区三区, | 国产视频在线播放 | 久久99国产精品视频 | 国产粉嫩在线观看 | av高清免费| 久久久久电影网站 | 五月天亚洲综合小说网 | 国产一区二区三区免费观看视频 | 中文字幕九九 | 天天草天天干天天射 | 美女视频一区 | 久久成人麻豆午夜电影 | 婷婷色网| 成人a在线观看 | 久久国产精品免费一区 | 国产精品永久 | 激情综合六月 | 国产一级电影 | 三级av在线免费观看 | 日日草视频 | 婷婷伊人综合 | 国产亚洲精品无 | 91国内在线 | 精品久久久999| 久久五月天综合 | 国产探花视频在线播放 | 久久久久久久久久久黄色 | 成人理论在线观看 | 久久久电影 | 激情五月色播五月 | 久久国产午夜精品理论片最新版本 | 久久免费视频一区 | 精品欧美小视频在线观看 | 99热在| 欧美成人基地 | 蜜臀一区二区三区精品免费视频 | 人人插人人插 | 69国产成人综合久久精品欧美 | 日韩欧美一区二区在线播放 | 超碰在线人| 亚洲免费一级电影 | 成人久久免费 | 日韩精品网址 | 欧美不卡视频在线 | 日韩欧美在线一区 | 色综合久久66 | 992tv在线观看网站 | 99精品久久精品一区二区 | 亚洲最快最全在线视频 | 欧美色图狠狠干 | 免费福利视频导航 | 黄网站app在线观看免费视频 | 色欧美综合 | 婷婷久久精品 | 最新色站| 日韩欧美在线不卡 | 热久久免费视频精品 | 天天爱天天操天天射 | 天天操天天怕 | 亚洲成人av片在线观看 | 亚洲亚洲精品在线观看 | 99久视频| 国产香蕉视频 | 99久久精品国产毛片 | 亚洲成人av在线播放 | 成人手机在线视频 | 18做爰免费视频网站 | 日本中文字幕视频 | 国产中的精品av小宝探花 | 国产精品乱码一区二三区 | 久久99久久久久 | 色婷婷av在线 | 精品免费观看视频 | 91看片淫黄大片91 | 女人魂免费观看 | 亚洲黄色小说网址 | 精品国内自产拍在线观看视频 | 探花在线观看 | 毛片一区二区 | 成全免费观看视频 | 亚洲精品免费在线播放 | 91精品在线免费观看视频 | 日韩欧美第二页 | 在线观看的av网站 | 国产黄色一级片在线 | 国产69精品久久久久9999apgf | 玖玖在线播放 | 日韩啪啪小视频 | 国产最新福利 | 五月宗合网 | 99久久超碰中文字幕伊人 | 视频二区 | 欧美精品一区二区在线观看 | 天天色天天操综合 | 狠狠干狠狠艹 | 人人玩人人爽 | 久久97精品 | 色视频成人在线观看免 | 国产日产精品一区二区三区四区 | 婷婷5月激情5月 | 精品a级片| 久久成人在线视频 | www色,com | 在线观看国产 | 中文字幕在线观看一区二区三区 | 国产日韩欧美自拍 | 中文在线a在线 | 丝袜美女在线 | 99久久精品电影 | 日韩网站中文字幕 | 九九九电影免费看 | 狠狠干五月天 | 精品久久久亚洲 | 中国一级片免费看 | 国产免费黄视频在线观看 | www.久热 | 久久久免费精品 | 欧美一级特黄aaaaaa大片在线观看 | 美州a亚洲一视本频v色道 | 欧美午夜a | 久久夜色精品亚洲噜噜国4 午夜视频在线观看欧美 | 精品国精品自拍自在线 | 激情视频免费在线观看 | 99精品国产一区二区 | 一区二区三区 亚洲 | 91大神电影| 福利精品在线 | 精品久久99 | 国产网红在线 | 国产在线色视频 | 精品国产精品一区二区夜夜嗨 | 国产精品九九九 | 亚洲va在线va天堂va偷拍 | 国产一区二区播放 | 99re国产视频 | 久久超级碰 | 国外调教视频网站 | 国产黄在线播放 | 99久久久国产精品免费观看 | 超碰97国产精品人人cao | 免费精品视频在线 | 欧美在线视频一区二区三区 | 日韩在线中文字幕 | 看国产黄色片 | 国产一级一片免费播放放a 一区二区三区国产欧美 | 最近日本韩国中文字幕 | 九九99靖品 | 视频福利在线 | 亚洲午夜精品在线观看 | av福利电影 | 精品视频国产 | 亚洲一级电影视频 | 成人在线电影观看 | 最新中文字幕在线播放 | 久久国产精彩视频 | 亚洲视频在线免费观看 | 国产精品mv | 黄色亚洲免费 | 午夜电影久久 | 久久午夜色播影院免费高清 | 久久视频国产精品免费视频在线 | 国产精品久久久久久久婷婷 | 国产不卡免费 | 婷婷五天天在线视频 | 欧美成人a在线 | 不卡的av在线播放 | 国产毛片久久久 | 亚洲精品午夜久久久久久久 | 狠狠色狠狠色合久久伊人 | 欧美日韩18 | 日韩经典一区二区三区 | 美女av在线免费 | 狂野欧美激情性xxxx欧美 | 亚洲乱亚洲乱亚洲 | 在线观看免费版高清版 | 韩日三级av | 一级理论片在线观看 | 青青河边草免费观看完整版高清 | 99在线精品视频 | 一级片免费在线 | 天天操天天操天天爽 | 日韩一区二区三区免费电影 | 日韩精品极品视频 | 国产伦精品一区二区三区四区视频 | 色综合久久久久综合体 | 成年人电影免费看 | 国产最新91 | 一级大片在线观看 | 国产精品久久久久久久久久久杏吧 | 色久天| 黄色片免费看 | 国产精品爽爽爽 | 激情综合中文娱乐网 | 国产高清av免费在线观看 | 久久99久久99精品中文字幕 | 九色精品免费永久在线 | 欧洲成人av | 天天干天天操av | 麻豆视频在线免费看 | 久久不射电影院 | 国产99在线免费 | 激情文学综合丁香 | 亚洲干 | 免费特级黄毛片 | 在线观看亚洲国产精品 | 欧美色噜噜 | 欧美精品视 | 91日韩在线视频 | 国产成人黄色 | av在线h| 中文资源在线官网 | 国产精品久久久久久电影 | 五月天伊人 | 欧美综合在线视频 | 久操久| 午夜精品久久久久久久99婷婷 | 99久久婷婷国产一区二区三区 | 最近2019好看的中文字幕免费 | 深夜免费福利视频 | 97人人精品 | 免费高清无人区完整版 | 国产91av视频在线观看 | 黄色片视频在线观看 | 亚洲欧美日韩国产一区二区三区 | 亚州天堂 | 九九九九热精品免费视频点播观看 | 在线影院中文字幕 | 亚洲综合在线发布 | 美国av大片 | 国产小视频免费在线网址 | 69性欧美| 97成人精品视频在线播放 | 亚洲免费精品视频 | 中文日韩在线 | 亚洲精品mv在线观看 | 91九色蝌蚪国产 | 成人一级电影在线观看 | 一区二区三区四区五区在线视频 | 玖草影院 | 五月婷婷丁香在线观看 | av在线永久免费观看 | 97视频在线免费 | 日韩av黄 | 一区二区三区电影 | wwxxxx日本| 狠狠狠色丁香综合久久天下网 | 国产成人av电影 | 狠狠干美女 | 国内视频在线 | 亚洲 欧洲 国产 日本 综合 | 欧美一级片在线观看视频 | 9在线观看免费高清完整版在线观看明 | 中文字幕视频三区 | 综合网天天 | 午夜精品久久久久久久99婷婷 | 深爱婷婷 | av线上免费观看 | 久久久国产一区二区三区四区小说 | 四虎影视www | 亚洲国产成人av网 | 日本性xxx | 久久大视频 | 久久久国产精品免费 | 色综合 久久精品 | 97色噜噜 | 麻豆精品传媒视频 | 黄色亚洲免费 | 精品视频999 | 日本三级久久久 | 欧美日韩精品区 | 国产区免费 | 欧美精品久久久久久久久久丰满 | 97视频在线播放 | 久久精品视频免费播放 | 中文字幕视频在线播放 | 正在播放亚洲精品 | 免费亚洲黄色 | 24小时日本在线www免费的 | 久久伊人八月婷婷综合激情 | 97超碰在线免费观看 | av无限看| 最新中文字幕在线观看视频 | av解说在线观看 | 精品视频免费在线 | 丰满少妇高潮在线观看 | 免费观看www7722午夜电影 | 精品久久久久久久久中文字幕 | 中文字幕在线观看第一页 | 一区在线电影 | 日韩最新在线视频 | 免费色av| 久久大片 | 欧美老女人xx| 日韩欧美aaa| 亚洲欧美国产精品18p | 国产一级大片免费看 | 色吊丝在线永久观看最新版本 | 91综合视频在线观看 | 欧美乱码精品一区 | 91一区二区三区在线观看 | 人人爽人人av | 狠狠躁日日躁 | 国产五月天婷婷 | 国产日产精品久久久久快鸭 | 麻豆视频免费播放 | 亚洲精品一区二区三区四区高清 | 免费合欢视频成人app | 在线观看久久 | 成人h电影 | 久久久美女 | 久久精品永久免费 | 在线日韩亚洲 | 日日夜夜狠狠干 | 亚洲成成品网站 | 亚洲影院色 | 国产日韩欧美在线播放 | 夜夜躁天天躁很躁波 | 91资源在线免费观看 | 成人免费视频网站在线观看 | 亚洲精品乱码久久久久久 | 中文字幕在线观看第三页 | 亚洲精品18日本一区app | 精品在线视频播放 | 天天操欧美 | 99精品区 | 欧美日韩午夜爽爽 | 欧美日韩精| 国产在线 一区二区三区 | 亚洲男人天堂a | 国产一区二区不卡视频 | 亚洲精品国产精品国自产观看浪潮 | 97视频免费在线看 | 三上悠亚在线免费 | 久久撸在线视频 | 特级毛片网 | 久久精品国产亚洲a | 日本在线观看中文字幕无线观看 | 日韩丝袜在线观看 | 91av网址| 国产在线一区观看 | 国产亚洲精品久久久久久网站 | 99国内精品久久久久久久 | 少妇视频在线播放 | 欧美a在线免费观看 | 在线观看成人国产 | 日日爽天天 | 美女视频黄网站 | 精品国产乱码久久 | 天天色天天操天天爽 | 九九久久久| 国产一区二区在线免费播放 | 四虎影视www| 国产精品系列在线观看 | 日韩一级电影在线观看 | 欧美国产一区二区 | 国产精品成人自产拍在线观看 | 精品国产一二三 | 欧美日韩调教 | 六月天综合网 | 66av99精品福利视频在线 | 激情综合一区 | 日韩视频免费观看高清完整版在线 | 日韩视频专区 | 国产精品久久久久永久免费观看 | 又大又硬又黄又爽视频在线观看 | 中文字幕成人在线观看 | 96精品视频 | 国产又粗又长又硬免费视频 | 免费看污在线观看 | 天天综合中文 | 国精产品一二三线999 | 久久成人一区 | 国产精品一区二区久久精品 | 成人av电影免费在线观看 | 国产高清永久免费 | 日韩大片在线免费观看 | 亚洲综合五月 | 日韩欧美高清视频在线观看 | 欧亚日韩精品一区二区在线 | 91爱爱视频 | 亚洲成aⅴ人在线观看 | 婷婷丁香色综合狠狠色 | 精品999在线| 热re99久久精品国产66热 | 久久综合九色综合97婷婷女人 | 日日夜色 | 国产九九九九九 | 免费成人av在线看 | 国产手机在线观看 | av福利免费 | 欧美日韩中文在线视频 | 99久热精品| 亚洲欧美国产日韩在线观看 | 免费在线观看午夜视频 | 国产剧在线观看片 | 91在线你懂的 | 日韩毛片在线免费观看 |