亭亭五月天在线观看,亭亭五月天在线观看,国产最新av一区二区,国产 高清 中文字幕,99re热久久亚洲综合精品成人,熟妇 一区二区三区,一级做a爰片性色毛片武则天,美女的骚穴视频播放,国产美女午夜免费视频

首頁>國內(nèi) > 正文

圖解 Kafka 源碼之 NetworkClient 網(wǎng)絡(luò)通信組件架構(gòu)設(shè)計(jì)

2023-03-15 09:18:18來源:華仔聊技術(shù)

大家好,我是華仔, 又跟大家見面了。

上篇主要帶大家深度剖析了「發(fā)送網(wǎng)絡(luò) I/O 的 Sender 線程的架構(gòu)設(shè)計(jì)」,消息先被暫存然后調(diào)用網(wǎng)絡(luò)I/O組件進(jìn)行發(fā)送,今天主要聊聊「真正進(jìn)行網(wǎng)絡(luò) I/O 的 NetworkClient 的架構(gòu)設(shè)計(jì)」深度剖析下消息是如何被發(fā)送出去的。

認(rèn)真讀完這篇文章,我相信你會(huì)對 Kafka NetworkClient 的源碼有更加深刻的理解。


(相關(guān)資料圖)

這篇文章干貨很多,希望你可以耐心讀完。一、總的概述

繼續(xù)通過「場景驅(qū)動(dòng)」的方式,來看看消息是如何在客戶端被累加和待發(fā)送的。

在上篇中,我們知道了消息被 Sender 子線程先暫存到 KafkaChannel 的 Send 字段中,然后調(diào)用 NetworkClient#client.poll() 進(jìn)行真正發(fā)送出去,如下圖所示「6-11步」。

NetworkClient 為「生產(chǎn)者」、「消費(fèi)者」、「服務(wù)端」等上層業(yè)務(wù)提供了網(wǎng)絡(luò)I/O的能力。在 NetworkClient 內(nèi)部使用了前面介紹的 Kafka 對 NIO 的封裝組件,同時(shí)做了一定的封裝,最終實(shí)現(xiàn)了網(wǎng)絡(luò)I/O能力。NetworkClient 不僅僅用于客戶端與服務(wù)端的通信,也用于服務(wù)端之間的通信。

接下來我們就來看看,「NetworkClient 網(wǎng)絡(luò)I/O組件的架構(gòu)實(shí)現(xiàn)以及發(fā)送處理流程」,為了方便大家理解,所有的源碼只保留骨干。

二、NetworkClient 架構(gòu)設(shè)計(jì)

NetworkClient 類是 KafkaClient 接口的實(shí)現(xiàn)類,它內(nèi)部的重要字段有「Selectable」、「InflightRequest」以及內(nèi)部類 「MetadataUpdate」。

github 源碼地址如下:

https://github.com/apache/kafka/blob/2.7.0/clients/src/main/java/org/apache/kafka/clients/NetworkClient.java

https://github.com/apache/kafka/blob/2.7.0/clients/src/main/java/org/apache/kafka/clients/InFlightRequests.java

https://github.com/apache/kafka/blob/2.7.0/clients/src/main/java/org/apache/kafka/clients/ClusterConnectionStates.java

https://github.com/apache/kafka/blob/2.7.0/clients/src/main/java/org/apache/kafka/clients/ClientRequest.java

https://github.com/apache/kafka/blob/2.7.0/clients/src/main/java/org/apache/kafka/clients/ClientResponse.java

1、關(guān)鍵字段
public class NetworkClient implements KafkaClient {    // 狀態(tài)枚舉值    private enum State {        ACTIVE,        CLOSING,        CLOSED    }    /* the selector used to perform network i/o */    // 用于執(zhí)行網(wǎng)絡(luò) I/O 的選擇器    private final Selectable selector;    // Metadata元信息的更新器, 它可以嘗試更新元信息    private final MetadataUpdater metadataUpdater;    /* the state of each node"s connection */    // 管理集群所有節(jié)點(diǎn)連接的狀態(tài)    private final ClusterConnectionStates connectionStates;    /* the set of requests currently being sent or awaiting a response */    // 當(dāng)前正在發(fā)送或等待響應(yīng)的請求集合    private final InFlightRequests inFlightRequests;    /* the socket send buffer size in bytes */    // 套接字發(fā)送數(shù)據(jù)的緩沖區(qū)的大?。ㄒ宰止?jié)為單位)    private final int socketSendBuffer;    /* the socket receive size buffer in bytes */    // 套接字接收數(shù)據(jù)的緩沖區(qū)的大小(以字節(jié)為單位)    private final int socketReceiveBuffer;    /* the client id used to identify this client in requests to the server */    // 表示客戶端id,標(biāo)識(shí)客戶端身份    private final String clientId;    /* the current correlation id to use when sending requests to servers */    // 向服務(wù)器發(fā)送請求時(shí)使用的當(dāng)前關(guān)聯(lián) ID    private int correlation;    /* default timeout for individual requests to await acknowledgement from servers */    // 單個(gè)請求等待服務(wù)器確認(rèn)的默認(rèn)超時(shí)    private final int defaultRequestTimeoutMs;    /* time in ms to wait before retrying to create connection to a server */    // 重連的退避時(shí)間    private final long reconnectBackoffMs;    /**     * True if we should send an ApiVersionRequest when first connecting to a broker.     * 是否需要與 Broker 端的版本協(xié)調(diào),默認(rèn)為 true     * 如果為 true 當(dāng)?shù)谝淮芜B接到一個(gè) broker 時(shí),應(yīng)當(dāng)發(fā)送一個(gè) version 的請求,用來得知 broker 的版本, 如果為 false 則不需要發(fā)送 version 的請求。     */    private final boolean discoverBrokerVersions;    // broker 端版本    private final ApiVersions apiVersions;    // 存儲(chǔ)著要發(fā)送的版本請求,key 為 nodeId,value 為構(gòu)建請求的 Builder    private final Map nodesNeedingApiVersionsFetch = new HashMap<>();    // 取消的請求集合    private final List abortedSends = new LinkedList<>();

從該類屬性字段來看比較多,這里說幾個(gè)關(guān)鍵字段:

selector:Kafka 自己封裝的 Selector,該選擇器負(fù)責(zé)監(jiān)聽「網(wǎng)絡(luò)I/O事件」、「網(wǎng)絡(luò)連接」、「讀寫操作」。metadataUpdater:NetworkClient 的內(nèi)部類,主要用來實(shí)現(xiàn)Metadata元信息的更新器, 它可以嘗試更新元信息。connectionStates:管理集群所有節(jié)點(diǎn)連接的狀態(tài),底層使用 Map實(shí)現(xiàn),NodeConnectionState 枚舉值表示連接狀態(tài),并且記錄了最后一次連接的時(shí)間戳。inFlightRequests:用來保存當(dāng)前正在發(fā)送或等待響應(yīng)的請求集合。socketSenderBuffer:表示套接字發(fā)送數(shù)據(jù)的緩沖區(qū)的大小。socketReceiveBuffer:表示套接字接收數(shù)據(jù)的緩沖區(qū)的大小。clientId:表示客戶端id,標(biāo)識(shí)客戶端身份。reconnectBackoffMs:表示重連的退避事件,為了防止短時(shí)間內(nèi)大量重連造成的網(wǎng)絡(luò)壓力,設(shè)計(jì)了這么一個(gè)時(shí)間段,在此時(shí)間段內(nèi)不得重連。
2、關(guān)鍵方法

NetworkClient 類的方法也不少,這里針對關(guān)鍵方法逐一講解下。

(1)ready()
/** * Begin connecting to the given node, return true if we are already connected and ready to send to that node. * * @param node The node to check * @param now The current timestamp * @return True if we are ready to send to the given node */ @Override public boolean ready(Node node, long now) {     // 空節(jié)點(diǎn)     if (node.isEmpty())        throw new IllegalArgumentException("Cannot connect to empty node " + node);     // 1、判斷節(jié)點(diǎn)是否準(zhǔn)備好發(fā)送請求     if (isReady(node, now))        return true;     // 2、判斷節(jié)點(diǎn)連接狀態(tài)     if (connectionStates.canConnect(node.idString(), now))        // if we are interested in sending to a node and we don"t have a connection to it, initiate one        // 3、初始化連接,但此時(shí)不一定連接成功了        initiateConnect(node, now);     return false;}/** * Check if the node with the given id is ready to send more requests. * @param node The node * @param now The current time in ms * @return true if the node is ready*/@Overridepublic boolean isReady(Node node, long now) {    // if we need to update our metadata now declare all requests unready to make metadata requests first priority    // 當(dāng)發(fā)現(xiàn)正在更新元數(shù)據(jù)時(shí),會(huì)禁止發(fā)送請求 && 當(dāng)連接沒有創(chuàng)建完畢或者當(dāng)前發(fā)送的請求過多時(shí),也會(huì)禁止發(fā)送請求    return !metadataUpdater.isUpdateDue(now) && canSendRequest(node.idString(), now);}/** * Are we connected and ready and able to send more requests to the given connection? * 檢測連接狀態(tài)、發(fā)送請求是否過多 * @param node The node * @param now the current timestamp */ private boolean canSendRequest(String node, long now) {    // 三個(gè)條件必須都滿足    return connectionStates.isReady(node, now) && selector.isChannelReady(node) &&            inFlightRequests.canSendMore(node);}

該方法表示某個(gè)節(jié)點(diǎn)是否準(zhǔn)備好并可以發(fā)送請求,主要做了三件事:

先判斷節(jié)點(diǎn)是否已經(jīng)準(zhǔn)備好連接并接收請求了,需要滿足以下四個(gè)條件:!metadataUpdater.isUpdateDue(now):不能是正在更新元數(shù)據(jù)的狀態(tài),且元數(shù)據(jù)不能過期。canSendRequest(node.idString(), now):此處有3個(gè)條件。(1)、客戶端和 node 連接是否處于 ready 狀態(tài);(2)、客戶端和 node 的 channel 是否建立好;(3)、inFlightRequests 中對應(yīng)的節(jié)點(diǎn)是否可以接收更多的請求。如果連接好返回 true 表示準(zhǔn)備好,如果沒有準(zhǔn)備好接收請求,則會(huì)嘗試與對應(yīng)的 Node 連接,此處也需要滿足兩個(gè)條件:

首先連接必須是 isDisconnected,不能是 connecteding 狀態(tài),即客戶端與服務(wù)端的連接狀態(tài)是沒有連接上。

兩次重試之間時(shí)間差要大于重試退避時(shí)間,目的就是為了避免網(wǎng)絡(luò)擁塞,防止重連過于頻繁造成網(wǎng)絡(luò)壓力過大

最后初始化連接。

(2)initiateConnect()
/**  * 創(chuàng)建連接   * Initiate a connection to the given node  * @param node the node to connect to  * @param now current time in epoch milliseconds  */ private void initiateConnect(Node node, long now) {    String nodeConnectionId = node.idString();    try {        // 1、更新連接狀態(tài)為正在連接        connectionStates.connecting(nodeConnectionId, now, node.host(), clientDnsLookup);        // 獲取連接地址        InetAddress address = connectionStates.currentAddress(nodeConnectionId);        log.debug("Initiating connection to node {} using address {}", node, address);        // 2、調(diào)用 selector 嘗試異步進(jìn)行連接,后續(xù)通過selector.poll進(jìn)行監(jiān)聽事件就緒         selector.connect(nodeConnectionId,                    new InetSocketAddress(address, node.port()),                    this.socketSendBuffer,                    this.socketReceiveBuffer);    } catch (IOException e) {        log.warn("Error connecting to node {}", node, e);        // Attempt failed, we"ll try again after the backoff        connectionStates.disconnected(nodeConnectionId, now);        // Notify metadata updater of the connection failure        metadataUpdater.handleServerDisconnect(now, nodeConnectionId, Optional.empty());    }}

該方法主要是進(jìn)行初始化連接,做了兩件事:

調(diào)用 connectionStates.connecting() 更新連接狀態(tài)為正在連接。調(diào)用 selector.connect() 異步發(fā)起連接,此時(shí)不一定連接上了,后續(xù) Selector.poll() 會(huì)監(jiān)聽連接是否準(zhǔn)備好并完成連接,如果連接成功,則會(huì)將 ConnectionState 設(shè)置為 CONNECTED。

當(dāng)連接準(zhǔn)備好后,接下來我們來看下發(fā)送相關(guān)的方法。

(3)send()、doSend()
/** * ClientRequest 是客戶端的請求,封裝了 requestBuilder  */public final class ClientRequest {    // 節(jié)點(diǎn)地址    private final String destination;    // ClientRequest 中通過 requestBuilder 給不同類型的請求設(shè)置不同的請求內(nèi)容    private final AbstractRequest.Builder requestBuilder;    // 請求頭的 correlationId    private final int correlationId;    // 請求頭的 clientid    private final String clientId;    // 創(chuàng)建時(shí)間    private final long createdTimeMs;    // 是否需要進(jìn)行響應(yīng)    private final boolean expectResponse;    // 請求的超時(shí)時(shí)間    private final int requestTimeoutMs;    // 回調(diào)函數(shù) 用來處理響應(yīng)    private final RequestCompletionHandler callback;    ......}/** * Queue up the given request for sending. Requests can only be sent out to ready nodes. * @param request The request * @param now The current timestamp * 發(fā)送請求,這個(gè)方法 生產(chǎn)者和消費(fèi)者都會(huì)調(diào)用,其中 ClientRequest 表示客戶端的請求。 */ @Override public void send(ClientRequest request, long now) {     doSend(request, false, now); }  // 檢測請求版本是否支持,如果支持則發(fā)送請求 private void doSend(ClientRequest clientRequest, boolean isInternalRequest, long now) {        // 確認(rèn)是否活躍        ensureActive();        // 目標(biāo)節(jié)點(diǎn)id        String nodeId = clientRequest.destination();        // 是否是 NetworkClient 內(nèi)部請求 這里為 false        if (!isInternalRequest) {             // 檢測是否可以向指定 Node 發(fā)送請求,如果還不能發(fā)送請求則拋異常             if (!canSendRequest(nodeId, now))                throw new IllegalStateException("Attempt to send a request to node " + nodeId + " which is not ready.");        }        AbstractRequest.Builder builder = clientRequest.requestBuilder();        try {            // 檢測版本            NodeApiVersions versionInfo = apiVersions.get(nodeId);            // ... 忽略            // builder.build()是 ProduceRequest.Builder,結(jié)果是ProduceRequest            // 調(diào)用 doSend 方法            doSend(clientRequest, isInternalRequest, now, builder.build(version));        } catch (UnsupportedVersionException unsupportedVersionException) {            log.debug("Version mismatch when attempting to send {} with correlation id {} to {}", builder, clientRequest.correlationId(), clientRequest.destination(), unsupportedVersionException);           // 請求的版本不協(xié)調(diào),那么生成 clientResponse           ClientResponse clientResponse = new ClientResponse(clientRequest.makeHeader(builder.latestAllowedVersion()),                    clientRequest.callback(), clientRequest.destination(), now, now,                    false, unsupportedVersionException, null, null);            // 添加到 abortedSends 集合里            abortedSends.add(clientResponse);        }  }  /**   * isInternalRequest 表示發(fā)送前是否需要驗(yàn)證連接狀態(tài),如果為 true 則表示客戶端已經(jīng)確定連接是好的   * request表示請求體   */  private void doSend(ClientRequest clientRequest, boolean isInternalRequest, long now, AbstractRequest request) {        // 目標(biāo)節(jié)點(diǎn)地址        String destination = clientRequest.destination();        // 生成請求頭        RequestHeader header = clientRequest.makeHeader(request.version());        if (log.isDebugEnabled()) {            log.debug("Sending {} request with header {} and timeout {} to node {}: {}",                clientRequest.apiKey(), header, clientRequest.requestTimeoutMs(), destination, request);        }        // 1、構(gòu)建 NetworkSend 對象 結(jié)合請求頭和請求體,序列化數(shù)據(jù),保存到 NetworkSend         Send send = request.toSend(destination, header);        // 2、構(gòu)建 inFlightRequest 對象 保存了發(fā)送前的所有信息        InFlightRequest inFlightRequest = new InFlightRequest(                clientRequest,                header,                isInternalRequest,                request,                send,                now);        // 3、把 inFlightRequest 加入 inFlightRequests 集合里        this.inFlightRequests.add(inFlightRequest);        // 4、調(diào)用 Selector 異步發(fā)送數(shù)據(jù),并將 send 和對應(yīng) kafkaChannel 綁定起來,并開啟該 kafkaChannel 底層 socket 的寫事件,等待下一步真正的網(wǎng)絡(luò)發(fā)送        selector.send(send);}@Overridepublic boolean active() {    // 判斷狀態(tài)是否是活躍的    return state.get() == State.ACTIVE;}// 確認(rèn)是否活躍private void ensureActive() {   if (!active())      throw new DisconnectException("NetworkClient is no longer active, state is " + state);}

從上面源碼可以看出此處發(fā)送并不是真正的網(wǎng)絡(luò)發(fā)送,而是先將數(shù)據(jù)發(fā)送到緩存中。

首先最外層是 send() ,里面調(diào)用 doSend() 。這里的 doSend() 主要的作用是判斷 inFlightRequests 集合上對應(yīng)的節(jié)點(diǎn)是不是能發(fā)送請求,需要滿足三個(gè)條件:客戶端和 node 連接是否處于 ready 狀態(tài)。客戶端和 node 的 channel 是否建立好。inFlightRequests 集合中對應(yīng)的節(jié)點(diǎn)是否可以接收更多的請求。最后再次調(diào)用另一個(gè) doSend(),用來最終的請求發(fā)送到緩存中。步驟如下:構(gòu)建 NetworkSend 對象 結(jié)合請求頭和請求體,序列化數(shù)據(jù),保存到 NetworkSend。構(gòu)建 inFlightRequest 對象。把 inFlightRequest 加入 inFlightRequests 集合里等待響應(yīng)。調(diào)用Selector異步發(fā)送數(shù)據(jù),并將 send 和對應(yīng) kafkaChannel 綁定起來,并開啟該 kafkaChannel 底層 socket 的寫事件,等待下一步真正的網(wǎng)絡(luò)發(fā)送。

綜上可以得出這里的發(fā)送過程其實(shí)是把要發(fā)送的請求先封裝成 inFlightRequest,然后放到 inFlightRequests 集合里,然后放到對應(yīng) channel 的字段 NetworkSend 里緩存起來。總之,這里的發(fā)送過程就是為了下一步真正的網(wǎng)絡(luò)I/O發(fā)送而服務(wù)的

接下來看下真正網(wǎng)絡(luò)發(fā)送的方法。

(4)poll()

該方法執(zhí)行網(wǎng)絡(luò)發(fā)送并把響應(yīng)結(jié)果「pollSelectionKeys 的各種讀寫」做各種狀態(tài)處理,此處是通過調(diào)用 handleXXX() 方法進(jìn)行處理的,代碼如下:

/** * Do actual reads and writes to sockets. * @param timeout The maximum amount of time to wait (in ms) for responses if there are none immediately, * must be non-negative. The actual timeout will be the minimum of timeout, request timeout and * metadata timeout * @param now The current time in milliseconds * @return The list of responses received*/@Overridepublic List poll(long timeout, long now) {   // 確認(rèn)是否活躍   ensureActive();   // 取消發(fā)送是否為空   if (!abortedSends.isEmpty()) {      // If there are aborted sends because of unsupported version exceptions or disconnects,      // handle them immediately without waiting for Selector#poll.      List responses = new ArrayList<>();      handleAbortedSends(responses);      completeResponses(responses);      return responses;   }   // 1、嘗試更新元數(shù)據(jù)   long metadataTimeout = metadataUpdater.maybeUpdate(now);   try {      // 2、執(zhí)行網(wǎng)絡(luò) I/O 操作,真正讀寫發(fā)送的地方,如果客戶端的請求被完整的處理過了,會(huì)加入到completeSends 或 complteReceives 集合中      this.selector.poll(Utils.min(timeout, metadataTimeout, defaultRequestTimeoutMs));   } catch (IOException e) {      log.error("Unexpected error during I/O", e);   }   // process completed actions   long updatedNow = this.time.milliseconds();   // 響應(yīng)結(jié)果集合:真正的讀寫操作, 會(huì)生成responses   List responses = new ArrayList<>();   // 3、完成發(fā)送的handler,處理 completedSends 集合   handleCompletedSends(responses, updatedNow);   // 4、完成接收的handler,處理 completedReceives 隊(duì)列   handleCompletedReceives(responses, updatedNow);   // 5、斷開連接的handler,處理 disconnected 列表   handleDisconnections(responses, updatedNow);   // 6、處理連接的handler,處理 connected 列表   handleConnections();   // 7、處理版本協(xié)調(diào)請求(獲取api版本號(hào)) handler   handleInitiateApiVersionRequests(updatedNow);   // 8、超時(shí)連接的handler,處理超時(shí)連接集合   handleTimedOutConnections(responses, updatedNow);   // 9、超時(shí)請求的handler,處理超時(shí)請求集合   handleTimedOutRequests(responses, updatedNow);   // 10、完成響應(yīng)回調(diào)   completeResponses(responses);   return responses;}

這里的步驟比較多,我們按照先后順序講解下。

嘗試更新元數(shù)據(jù)。調(diào)用 Selector.poll() 執(zhí)行真正網(wǎng)絡(luò) I/O 操作,可以點(diǎn)擊查看 圖解 Kafka 源碼網(wǎng)絡(luò)層實(shí)現(xiàn)機(jī)制之 Selector 多路復(fù)用器 主要操作以下3個(gè)集合。connected集合:已經(jīng)完成連接的 Node 節(jié)點(diǎn)集合。completedReceives集合:接收完成的集合,即 KafkaChannel 上的 NetworkReceive 寫滿后會(huì)放入這個(gè)集合里。completedSends集合:發(fā)送完成的集合,即 channel 上的 NetworkSend 讀完后會(huì)放入這個(gè)集合里。調(diào)用 handleCompletedSends() 處理 completedSends 集合。調(diào)用 handleCompletedReceives() 處理 completedReceives 隊(duì)列。調(diào)用 handleDisconnections() 處理與 Node 斷開連接的請求。調(diào)用 handleConnections() 處理 connected 列表。調(diào)用 handleInitiateApiVersionRequests() 處理版本號(hào)請求。調(diào)用 handleTimedOutConnections() 處理連接超時(shí)的 Node 集合。調(diào)用 handleTimedOutRequests() 處理 inFlightRequests 集合中的超時(shí)請求,并修改其狀態(tài)。調(diào)用 completeResponses() 完成每個(gè)消息自定義的響應(yīng)回調(diào)。

接下來看下第 3~9 步驟的方法實(shí)現(xiàn)。

(5)handleCompletedSends()

當(dāng) NetworkClient 發(fā)送完請求后,就會(huì)調(diào)用handleCompletedSends方法,表示請求已經(jīng)發(fā)送到 Broker 端了。

/** * Handle any completed request send. In particular if no response is expected consider the request complete. * @param responses The list of responses to update * @param now The current time*/private void handleCompletedSends(List responses, long now) {   // if no response is expected then when the send is completed, return it   // 1、遍歷 completedSends 發(fā)送完成的請求集合,通過調(diào)用 Selector 獲取從上一次 poll 開始的請求   for (Send send : this.selector.completedSends()) {       // 2、從 inFlightRequests 集合獲取該 Send 關(guān)聯(lián)對應(yīng) Node 的隊(duì)列取出最新的請求,但并沒有從隊(duì)列中刪除,取出后判斷這個(gè)請求是否期望得到響應(yīng)       InFlightRequest request = this.inFlightRequests.lastSent(send.destination());       // 3、是否需要響應(yīng), 如果不需要響應(yīng),當(dāng)Send請求完成時(shí),就直接返回.還是有request.completed生成的ClientResponse對象       if (!request.expectResponse) {           // 4、如果不需要響應(yīng)就取出 inFlightRequests 中該 Sender 關(guān)聯(lián)對應(yīng) Node 的 inFlightRequest,即提取最新的請求           this.inFlightRequests.completeLastSent(send.destination());           // 5、調(diào)用 completed() 生成 ClientResponse,第一個(gè)參數(shù)為null,表示沒有響應(yīng)內(nèi)容,把請求添加到 Responses 集合           responses.add(request.completed(null, now));       }   }}

該方法主要用來在客戶端發(fā)送請求后,對響應(yīng)結(jié)果進(jìn)行處理,做了五件事:

遍歷 seletor 中的 completedSends 集合,逐個(gè)處理完成的 Send 對象。從 inFlightRequests 集合獲取該 Send 關(guān)聯(lián)對應(yīng) Node 的隊(duì)列中第一個(gè)元素,但并沒有從隊(duì)列中刪除,取出后判斷這個(gè)請求是否期望得到響應(yīng)。判斷是否需要響應(yīng)。如果不需要響應(yīng)就刪除 inFlightRequests 中該 Sender 關(guān)聯(lián)對應(yīng) Node 的 inFlightRequest,對于 Kafka 來說,有些請求是不需要響應(yīng)的,對于發(fā)送完不用考慮是否發(fā)送成功的話,就構(gòu)建 callback 為 null 的 Response 對象。通過 InFlightRequest.completed(),生成 ClientResponse,第一個(gè)參數(shù)為 null 表示沒有響應(yīng)內(nèi)容,最后把 ClientResponse 添加到 Responses 集合。

從上面源碼可以看出,「completedSends」集合與「InflightRequests」集合協(xié)作的關(guān)系。

但是這里有個(gè)問題:如何保證從 Selector 返回的請求,就是對應(yīng)到 InflightRequests 集合隊(duì)列的最新的請求呢?

completedSends集合保存的是最近一次調(diào)用 poll() 方法中發(fā)送成功的請求「發(fā)送成功但還沒有收到響應(yīng)的請求集合」。而InflightRequests集合存儲(chǔ)的是已經(jīng)發(fā)送但還沒收到響應(yīng)的請求。每個(gè)請求發(fā)送都需要等待前面的請求發(fā)送完成,這樣就能保證同一時(shí)間只有一個(gè)請求正在發(fā)送,因?yàn)?Selector 返回的請求是從上一次 poll 開始的,這樣就對上了。

「completedSends」的元素對應(yīng)著「InflightRequests」集合里對應(yīng)隊(duì)列的最后一個(gè)元素, 如下圖所示:

(6)handleCompletedReceives()

當(dāng) NetworkClient 收到響應(yīng)時(shí),就會(huì)調(diào)用handleCompletedReceives方法。

/** * Handle any completed receives and update the response list with the responses received. * @param responses The list of responses to update * @param now The current time * 處理 CompletedReceives 隊(duì)列,根據(jù)返回的響應(yīng)信息實(shí)例化 ClientResponse ,并加到響應(yīng)集合里*/private void handleCompletedReceives(List responses, long now) {   // 1、遍歷 CompletedReceives 響應(yīng)集合,通過 Selector 返回未處理的響應(yīng)   for (NetworkReceive receive : this.selector.completedReceives()) {       // 2、獲取發(fā)送請求的 Node id       String source = receive.source();       // 3、從 inFlightRequests 集合隊(duì)列獲取已發(fā)送請求「最老的請求」并刪除(從 inFlightRequests 刪除,因?yàn)閕nFlightRequests 存儲(chǔ)的是未收到請求響應(yīng)的 ClientRequest,現(xiàn)在請求已經(jīng)有響應(yīng)了,就不需要保存了)       InFlightRequest req = inFlightRequests.completeNext(source);       // 4、解析響應(yīng),并且驗(yàn)證響應(yīng)頭,生成 responseStruct 實(shí)例       Struct responseStruct = parseStructMaybeUpdateThrottleTimeMetrics(receive.payload(), req.header,throttleTimeSensor, now);       // 生成響應(yīng)體       AbstractResponse response = AbstractResponse.parseResponse(req.header.apiKey(), responseStruct, req.header.apiVersion());             ....      // If the received response includes a throttle delay, throttle the connection.      // 流控處理      maybeThrottle(response, req.header.apiVersion(), req.destination, now);      // 5、判斷返回類型      if (req.isInternalRequest && response instanceof MetadataResponse)          // 處理元數(shù)據(jù)請求響應(yīng)          metadataUpdater.handleSuccessfulResponse(req.header, now, (MetadataResponse) response);      else if (req.isInternalRequest && response instanceof ApiVersionsResponse)          // 處理版本協(xié)調(diào)響應(yīng)          handleApiVersionsResponse(responses, req, now, (ApiVersionsResponse) response);      else          // 普通發(fā)送消息的響應(yīng),通過 InFlightRequest.completed(),生成 ClientResponse,將響應(yīng)添加到 responses 集合中          responses.add(req.completed(response, now));    }}// 解析響應(yīng),并且驗(yàn)證響應(yīng)頭,生成 responseStruct 實(shí)例private static Struct parseStructMaybeUpdateThrottleTimeMetrics(ByteBuffer responseBuffer, RequestHeader requestHeader, Sensor throttleTimeSensor, long now) {    // 解析響應(yīng)頭    ResponseHeader responseHeader = ResponseHeader.parse(responseBuffer,            requestHeader.apiKey().responseHeaderVersion(requestHeader.apiVersion()));    // 解析響應(yīng)體    Struct responseBody = requestHeader.apiKey().parseResponse(requestHeader.apiVersion(), responseBuffer);    // 驗(yàn)證請求頭與響應(yīng)頭的 correlation id 必須相等    correlate(requestHeader, responseHeader);    if (throttleTimeSensor != null && responseBody.hasField(CommonFields.THROTTLE_TIME_MS))            throttleTimeSensor.record(responseBody.get(CommonFields.THROTTLE_TIME_MS), now);    return responseBody;}

該方法主要用來處理接收完畢的網(wǎng)絡(luò)請求集合,做了五件事:

遍歷 selector 中的 completedReceives 集合,逐個(gè)處理完成的 Receive 對象。獲取發(fā)送請求的 Node id。從 inFlightRequests 集合隊(duì)列獲取已發(fā)送請求「最老的請求」并刪除(從 inFlightRequests 刪除,因?yàn)閕nFlightRequests 存儲(chǔ)的是未收到請求響應(yīng)的 ClientRequest,現(xiàn)在請求已經(jīng)有響應(yīng)了,就不需要保存了)。解析響應(yīng),并且驗(yàn)證響應(yīng)頭,生成 responseStruct 實(shí)例,生成響應(yīng)體。處理響應(yīng)結(jié)果,此處分為三種情況:處理元數(shù)據(jù)請求響應(yīng),則調(diào)用 metadataUpdater.handleSuccessfulResponse()。處理版本協(xié)調(diào)響應(yīng),則調(diào)用 handleApiVersionsResponse()。普通發(fā)送消息的響應(yīng),通過 InFlightRequest.completed(),生成 ClientResponse,將響應(yīng)添加到 responses 集合中。

從上面源碼可以看出,「completedReceives」集合與「InflightRequests」集合也有協(xié)作的關(guān)系,completedReceives集合指的是接收到的響應(yīng)集合,如果請求已經(jīng)收到響應(yīng)了,就可以從InflightRequests刪除了,這樣InflightRequests就起到了可以防止請求堆積的作用。

與 「completedSends」正好相反,「completedReceives」集合對應(yīng) 「InflightRequests」集合里對應(yīng)隊(duì)列的第一個(gè)元素,如下圖所示:

(7)leastLoadedNode()
/** * Choose the node with the fewest outstanding requests which is at least eligible for connection. This method will * prefer a node with an existing connection, but will potentially choose a node for which we don"t yet have a * connection if all existing connections are in use. If no connection exists, this method will prefer a node * with least recent connection attempts. This method will never choose a node for which there is no * existing connection and from which we have disconnected within the reconnect backoff period, or an active * connection which is being throttled. * * @return The node with the fewest in-flight requests. */ @Override public Node leastLoadedNode(long now) {        // 從元數(shù)據(jù)中獲取所有的節(jié)點(diǎn)        List nodes = this.metadataUpdater.fetchNodes();        if (nodes.isEmpty())            throw new IllegalStateException("There are no nodes in the Kafka cluster");        int inflight = Integer.MAX_VALUE;        Node foundConnecting = null;        Node foundCanConnect = null;        Node foundReady = null;        int offset = this.randOffset.nextInt(nodes.size());        for (int i = 0; i < nodes.size(); i++) {            int idx = (offset + i) % nodes.size();            Node node = nodes.get(idx);            // 節(jié)點(diǎn)是否可以發(fā)送請求            if (canSendRequest(node.idString(), now)) {                // 獲取節(jié)點(diǎn)的隊(duì)列大小                int currInflight = this.inFlightRequests.count(node.idString());                // 如果為 0 則返回該節(jié)點(diǎn),負(fù)載最小                 if (currInflight == 0) {                    // if we find an established connection with no in-flight requests we can stop right away                    log.trace("Found least loaded node {} connected with no in-flight requests", node);                    return node;                } else if (currInflight < inflight) { // 如果隊(duì)列大小小于最大值                    // otherwise if this is the best we have found so far, record that                    inflight = currInflight;                    foundReady = node;                }            } else if (connectionStates.isPreparingConnection(node.idString())) {                foundConnecting = node;            } else if (canConnect(node, now)) {                if (foundCanConnect == null ||                        this.connectionStates.lastConnectAttemptMs(foundCanConnect.idString()) >                                this.connectionStates.lastConnectAttemptMs(node.idString())) {                    foundCanConnect = node;                }            } else {                log.trace("Removing node {} from least loaded node selection since it is neither ready " +                        "for sending or connecting", node);            }        }        // We prefer established connections if possible. Otherwise, we will wait for connections        // which are being established before connecting to new nodes.        if (foundReady != null) {            log.trace("Found least loaded node {} with {} inflight requests", foundReady, inflight);            return foundReady;        } else if (foundConnecting != null) {            log.trace("Found least loaded connecting node {}", foundConnecting);            return foundConnecting;        } else if (foundCanConnect != null) {            log.trace("Found least loaded node {} with no active connection", foundCanConnect);            return foundCanConnect;        } else {            log.trace("Least loaded node selection failed to find an available node");            return null;        } }

該方法主要是選出一個(gè)負(fù)載最小的節(jié)點(diǎn),如下圖所示:

三、InflightRequests 集合設(shè)計(jì)

通過上面的代碼分析,我們知道「InflightRequests」集合的作用就是緩存已經(jīng)發(fā)送出去但還沒有收到響應(yīng)的 ClientRequest 請求集合。底層是通過ReqMap>實(shí)現(xiàn),其中 key 是 NodeId,value 是發(fā)送到對應(yīng) Node 的 ClientRequest 請求隊(duì)列,默認(rèn)為5個(gè),參數(shù):max.in.flight.requests.per.connection配置請求隊(duì)列大小。它為每個(gè)連接生成一個(gè)雙端隊(duì)列,因此它能控制請求發(fā)送的速度。

其作用有以下2個(gè):

節(jié)點(diǎn)是否正常:收集從「開始發(fā)送」到「接收響應(yīng)」這段時(shí)間的請求,來判斷要發(fā)送的 Broker 節(jié)點(diǎn)是否正常,請求和連接是否超時(shí)等等,也就是說用來監(jiān)控發(fā)送到哥哥節(jié)點(diǎn)請求是否正常。節(jié)點(diǎn)的負(fù)載情況:Deque 隊(duì)列到一定長度后就認(rèn)為某個(gè) Broker 節(jié)點(diǎn)負(fù)載過高了。
/** * The set of requests which have been sent or are being sent but haven"t yet received a response * 用來緩存已經(jīng)發(fā)送出去或者正在發(fā)送但均還沒有收到響應(yīng)的  ClientRequest 請求集合 */final class InFlightRequests {    // 每個(gè)連接最大執(zhí)行中的請求數(shù)    private final int maxInFlightRequestsPerConnection;    // 節(jié)點(diǎn) Node 至客戶端請求雙端隊(duì)列 Deque 的映射集合,key為 NodeId, value 是請求隊(duì)列    private final Map> requests = new HashMap<>();    /** Thread safe total number of in flight requests. */    // 線程安全的 inFlightRequestCount     private final AtomicInteger inFlightRequestCount = new AtomicInteger(0);    // 設(shè)置每個(gè)連接最大執(zhí)行中的請求數(shù)    public InFlightRequests(int maxInFlightRequestsPerConnection) {        this.maxInFlightRequestsPerConnection = maxInFlightRequestsPerConnection;}

這里通過「場景驅(qū)動(dòng)」的方式來講解關(guān)鍵方法,當(dāng)有新請求需要發(fā)送處理時(shí),會(huì)在隊(duì)首入隊(duì)。而實(shí)際被處理的請求,則是從隊(duì)尾出隊(duì),保證入隊(duì)早的請求先得到處理。

1、canSendMore()

先來看下發(fā)送條件限制, NetworkClient 調(diào)用這個(gè)方法用來判斷是否還可以向指定 Node 發(fā)送請求。

/** * Can we send more requests to this node? * @param node Node in question * @return true iff we have no requests still being sent to the given node * 判斷該連接是否還能發(fā)送請求*/public boolean canSendMore(String node) {        // 獲取節(jié)點(diǎn)對應(yīng)的雙端隊(duì)列        Deque queue = requests.get(node);        // 判斷條件 隊(duì)列為空 || (隊(duì)首已經(jīng)發(fā)送完成 && 隊(duì)列中沒有堆積更多的請求)        return queue == null || queue.isEmpty() ||               (queue.peekFirst().send.completed() && queue.size() < this.maxInFlightRequestsPerConnection);}

從上面代碼可以看出限制條件,隊(duì)列雖然可以存儲(chǔ)多個(gè)請求,但是新的請求要是加進(jìn)來?xiàng)l件是上一個(gè)請求必須發(fā)送成功。

條件判斷如下:

queue == null || queue.isEmpty(),隊(duì)列為空就能發(fā)送。判斷 queue.peekFirst().send.completed() 隊(duì)首是否發(fā)送完成。如果隊(duì)首的請求遲遲發(fā)送不出去,可能就是網(wǎng)絡(luò)的原因,因此不能繼續(xù)向此 Node 發(fā)送請求。隊(duì)首的請求與對應(yīng)的 KafkaChannel.send 字段指向的是同一個(gè)請求,為了避免未發(fā)送的消息被覆蓋掉,也不能讓 KafkaChannel.send 字段指向新請求。queue.size() < this.maxInFlightRequestsPerConnection,該條件就是為了判斷隊(duì)列中是否堆積過多請求,如果 Node 已經(jīng)堆積了很多未響應(yīng)的請求,說明這個(gè)節(jié)點(diǎn)出現(xiàn)了網(wǎng)絡(luò)擁塞,繼續(xù)再發(fā)送請求,則可能會(huì)超時(shí)。
2、add() 入隊(duì)
/** * Add the given request to the queue for the connection it was directed to * 將請求添加到隊(duì)列首部*/public void add(NetworkClient.InFlightRequest request) {        // 這個(gè)請求要發(fā)送到哪個(gè) Broker 節(jié)點(diǎn)上        String destination = request.destination;        // 從 requests 集合中根據(jù)給定請求的目標(biāo) Node 節(jié)點(diǎn)獲取對應(yīng) Deque 雙端隊(duì)列 reqs        Deque reqs = this.requests.get(destination);        // 如果雙端隊(duì)列reqs為null        if (reqs == null) {            // 構(gòu)造一個(gè)雙端隊(duì)列 ArrayDeque 類型的 reqs            reqs = new ArrayDeque<>();            // 將請求目標(biāo) Node 節(jié)點(diǎn)至 reqs 的映射關(guān)系添加到 requests 集合            this.requests.put(destination, reqs);        }        // 將請求 request 添加到 reqs 隊(duì)首        reqs.addFirst(request);        // 增加計(jì)數(shù)        inFlightRequestCount.incrementAndGet();}
3、completeNext() 出隊(duì)最老請求
/** * Get the oldest request (the one that will be completed next) for the given node * 取出該連接對應(yīng)的隊(duì)列中最老的請求 */ public NetworkClient.InFlightRequest completeNext(String node) {     // 根據(jù)給定 Node 節(jié)點(diǎn)獲取客戶端請求雙端隊(duì)列 reqs,并從隊(duì)尾出隊(duì)     NetworkClient.InFlightRequest inFlightRequest = requestQueue(node).pollLast();     // 遞減計(jì)數(shù)器     inFlightRequestCount.decrementAndGet();     return inFlightRequest; }

對比下入隊(duì)和出隊(duì)這2個(gè)方法,「入隊(duì) add()」時(shí)是通過 addFirst() 方法添加到隊(duì)首的,所以隊(duì)尾的請求是時(shí)間最久的,也是應(yīng)該先處理的,所以「出隊(duì) completeNext()」是通過 pollLast(),將隊(duì)列中時(shí)間最久的請求袁術(shù)移出進(jìn)行處理。

4、lastSent() 獲取最新請求?
/** * Get the last request we sent to the given node (but don"t remove it from the queue) * @param node The node id */ public NetworkClient.InFlightRequest lastSent(String node) {     return requestQueue(node).peekFirst(); }
5、completeLastSent() 出隊(duì)最新請求
/**  * Complete the last request that was sent to a particular node.  * @param node The node the request was sent to  * @return The request  * 取出該連接對應(yīng)的隊(duì)列中最新的請求  */ public NetworkClient.InFlightRequest completeLastSent(String node) {        // 根據(jù)給定 Node 節(jié)點(diǎn)獲取客戶端請求雙端隊(duì)列 reqs,并從隊(duì)首出隊(duì)        NetworkClient.InFlightRequest inFlightRequest = requestQueue(node).pollFirst();        // 遞減計(jì)數(shù)器        inFlightRequestCount.decrementAndGet();        return inFlightRequest; }

最后我們來看看「InflightRequests」,表示正在發(fā)送的請求,存儲(chǔ)著請求發(fā)送前的所有信息。

另外它支持生成響應(yīng) ClientResponse,當(dāng)正常收到響應(yīng)時(shí),completed()會(huì)根據(jù)響應(yīng)內(nèi)容生成對應(yīng)的 ClientResponse,當(dāng)連接突然斷開后,disconnected() 會(huì)生成 ClientResponse 對象,代碼如下:

static class InFlightRequest {     //  請求頭     final RequestHeader header;     // 這個(gè)請求要發(fā)送到哪個(gè) Broker 節(jié)點(diǎn)上     final String destination;     // 回調(diào)函數(shù)     final RequestCompletionHandler callback;     // 是否需要進(jìn)行響應(yīng)     final boolean expectResponse;     // 請求體     final AbstractRequest request;     // 發(fā)送前是否需要驗(yàn)證連接狀態(tài)     final boolean isInternalRequest; // used to flag requests which are initiated internally by NetworkClient     // 請求的序列化數(shù)據(jù)     final Send send;     // 發(fā)送時(shí)間     final long sendTimeMs;     // 請求的創(chuàng)建時(shí)間,即 ClientRequest 的創(chuàng)建時(shí)間     final long createdTimeMs;     // 請求超時(shí)時(shí)間     final long requestTimeoutMs;     .....    /**     * 收到響應(yīng),回調(diào)的時(shí)候據(jù)響應(yīng)內(nèi)容生成 ClientResponse     */    public ClientResponse completed(AbstractResponse response, long timeMs) {        return new ClientResponse(header, callback, destination, createdTimeMs, timeMs,                    false, null, null, response);    }        /**     * 當(dāng)連接突然斷開,也會(huì)生成 ClientResponse。     */    public ClientResponse disconnected(long timeMs, AuthenticationException authenticationException) {       return new ClientResponse(header, callback, destination, createdTimeMs, timeMs,                    true, null, authenticationException, null);    }}

中間的部分代碼請移步到星球查看。

五、完整請求流程串聯(lián)

一條完整的請求主要分為以下幾個(gè)階段:

調(diào)用 NetworkClient 的 ready(),連接服務(wù)端。調(diào)用 NetworkClient 的 poll(),處理連接。調(diào)用 NetworkClient 的 newClientRequest(),創(chuàng)建請求 ClientRequest。然后調(diào)用 NetworkClient 的 send(),發(fā)送請求。最后調(diào)用 NetworkClient 的 poll(),處理響應(yīng)。
1、創(chuàng)建連接過程

NetworkClient 發(fā)送請求之前,都需要先和 Broker 端創(chuàng)建連接。NetworkClient 負(fù)責(zé)管理與集群的所有連接。

2、生成請求過程3、發(fā)送請求過程4、處理響應(yīng)過程(1)請求發(fā)送完成(2)請求收到響應(yīng)(3)執(zhí)行處理響應(yīng)六、總結(jié)

這里,我們一起來總結(jié)一下這篇文章的重點(diǎn)。

1、開篇總述消息消息被 Sender 子線程先將消息暫存到 KafkaChannel 的 send 中,等調(diào)用「poll方法」執(zhí)行真正的網(wǎng)絡(luò)I/O 操作,從而引出了為客戶端提供網(wǎng)絡(luò) I/O 能力的 「NetworkClient 組件」。

2、帶你深度剖析了「NetworkClient 組件」 、「InflightRequests」、「ClusterConnectionState」的實(shí)現(xiàn)細(xì)節(jié)。

3、最后帶你串聯(lián)了整個(gè)消息發(fā)送請求和處理響應(yīng)的流程,讓你有個(gè)更好的整體認(rèn)知。

關(guān)鍵詞:

相關(guān)新聞

Copyright 2015-2020   三好網(wǎng)  版權(quán)所有 聯(lián)系郵箱:435 22 640@qq.com  備案號(hào): 京ICP備2022022245號(hào)-21
亚洲 自拍 激情 另类| 首页欧美日韩中文字幕| 日韩av水蜜桃一区二区三区| 中文字幕福利视频第四页| 91人妻人人做人人爽高清| 黑人黄色免费一级av| 熟女国内精品一区二区三区 | 91精品视频在线观看视频| 西野翔人妻中文字幕中字在| 大陆中文字幕视频在线| 亚洲国产综合久久精品| 国产漂亮白嫩美女在线图片| 九九六视频,这里只有精品| 国产成人av在线你懂得| 国产夫妻视频在线观看免费| 91九色91在线视频| 色屁屁一区二区三区在线观看| 韩国在线播放一区二区三区| yellow在线亚洲精品一区| 老鸭窝在线毛片观看免费播放 | 色噜噜噜噜色噜噜色合久一| 91亚洲国产成人久久精品| 午夜精品久久久久久久精品乱码| 每日更新日韩欧美在线| 凹凸视频一区二区在线观看| 豆豆专区操逼性视频在线| 天天想要天天操天天干| 激情九月天在线视频| 中文字幕 首页 人妻| 亚洲精品国产99999| 男女真人做带声音视频图片| 91人妻人人做人人爽高清| 一级毛片特级毛片免费的| 自拍偷拍色图亚洲天堂| 182tv精品免费在线观看| 国语对白性爱三级片免费看| 全球高清中文字幕av| 久久精品国产亚洲av热软件| 亚洲天堂色综合久久| 亚洲国产精品一区二区第二页| 亚洲黑人欧美二区三区| 亚洲天堂色综合久久| 少妇熟女天堂网av| 黄在线看片免费人成视频| 欧美成人一二三在线网| 亚洲综合首页综合在线观看| 国产不卡免费在线观看| 亚洲成人中文无码在线| 2026天天操天天干| 亚洲人精品午夜射精日韩| 午夜精品久久久久久久精品乱码 | 亚洲三级综合在线观看| 大片a免费观看在线视频观看| 男女啪啪啪网站在线观看免费| 亚洲国产日韩欧美一区二区三区,| 国产精品网站亚洲发布| 在线视频国产精品欧美| 精品国产污污污污免费观看| 国产精品国产三级在线高清观看| 欧美成人屋影院在线视频观看| 天天色 天天操 天天好逼| 欧美肥妇久久久久久| 又粗又长又硬又黄又爽| 日韩一区二区在线播放观看| 欧美成人屋影院在线视频观看| 色狠狠色综合久久久绯色| 人妻熟女 亚洲 一页二页| lutu玩弄人妻短视频| 无码人妻丰满熟妇区五路| 免费在线观看亚洲福利| 亚洲一区二区偷拍女厕所| 99精品久久一区二区| 成人精品影视一区二区| 一区二区三区午夜福利在线| 69av精品国产探花| 人妻少妇视频系列视频在线| 东北老女人熟女啪啪视频| ass亚洲熟女ass| 国产精品蝌蚪自拍视频| 天天操,天天射,天天爽| 99免费观看在线视频| 欧洲成熟女人色惰片| 一区二区三区四区视频精品免费| 在线能看视频你懂的| 久久久亚洲熟女一区二区| 青青青在线视频观看97| 大乳丰满人妻中文字幕韩国hd| 亚洲精品综合欧美精品综合| 日本香港韩国三级黄色 | 69av精品国产探花| 国产欧美福利在线观看| 亚洲午夜熟女在线观看| 一区二区三区四区 在线播放| 亚洲无码专区中文字幕专区| 91超碰国产在线观看| 欧美久久蜜臀蜜桃资源吧| 亚洲全国精品女人久久久| 黄在线看片免费人成视频| 日韩久久九九精品视频| 亚洲 综合 欧美 一区| 国产精品免费看一区二区三区| 欧美日韩久久丝袜在线| 18禁男女啪啪啪无遮挡| 最近日韩免费在线观看| 国产做A爱免费视频在线观看| 天天插天天干天天狠| 日韩美精品成人一区二区三区四区| 亚洲在线免费观看18| 国产原创一区二区三区在线播放| 99福利一区二区视频| 亚洲av中文免费在线| 中文字幕熟女人妻丝袜丝在线| 国产女人18毛片水真多精选| 97人妻人人揉人人躁人人夜夜爽| 亚洲一区二区偷拍女厕所| 熟妇高潮久久久久久久 | 2020国产成人精品视频| 熟女人妻aⅴ一区二区三| 97香蕉久久国产超碰| 免费的啪啪视频软件| 亚洲国产精品自拍偷拍视频在线| 日本老熟妇av老熟妇| 91精品资源在线观看| 美女激情久久久久久久| 久久99嫩草99久久精品| 91人妻人人做人人爽高清| 在线能看视频你懂的| 在线 激情 亚洲 视频| 91色老久久精品偷偷蜜臀| 公侵犯人妻中文字幕巨| 亚洲色大WWW永久网站| 亚洲男人的天堂最新网址| 91精品国产欧美在线| 天天在线播放日韩av| 女人扒开逼让男人操| 国产高清在线观看av| 啪啪啪网站免费在线看| 日本成人福利电影网| 夫亡人妻被强干中文字幕| 欧美大胆a级视频秒播| 人妻色综合aaaaaa网| 婷婷综合缴情亚洲五月伊人| 97精品人妻免费视频| 黄色网络中文字幕日本| 蜜桃臀av在线一区二区| 户外露出视频在线观看| 久久久西西gogo日本美女人体| 九十九步都是爱最后一步是尊严| 99热这里只有精品免费播放| 精品日本少妇久久久| 国产一区二区三区四区精| 午夜久久久久久av五月| 天天弄天天草天天日天天| 天天日夜夜操人人爽| 人人妻人人澡人人爽97| 欧美一区二区三区视频看| 欧美老熟妇xxoo老妇| 美女妩媚午夜诱惑网站| 99精品久久99久久久久一| 久久99嫩草99久久精品| 伊人网在线欧美日韩在线| av丝袜免费在线观看| 久99久视频免费观看中文字幕| 欧美巨大另类极品video| 亚洲午夜熟女在线观看| 黄片操操操操操操c| 亚洲中文字幕最新地址| 天天色天天射天天日天天干| 亚洲综合成人精品成人精品| 午夜福利国产精品久久久久| 波多野结衣在线一区别| 欧美黑人性猛交小矮人| 中文字幕熟女人妻丝袜丝在线| 男人和女人的逼视频| 91在线九色porny| 亚洲色视频在线播放网站| 国产激情免费在线视频 | 日本高清有码在线视频| 国产女主播在线观看一区| 午夜精品视频免费观看| 91九色pony蝌蚪| 国产精品视频网站污污污| 韩国在线播放一区二区三区| 国际日韩日韩日韩日韩日韩| 日韩人妻精品久久久久| 东京热日韩av影片| 一区二区三区观看在线| 东京热日本一区二区三区| 午夜精品小视频在线播放| 夜夜骚av一二三区| 亚洲色大WWW永久网站| 色欲天天媓色媓香视频综合网| yellow在线亚洲精品一区| 欧美黄色性视频网站| 亚洲成人 国产精品| 亚洲综合另类欧美久久| 岳母的诱惑电影在线观看| 360偷拍蜜桃臀69式| 污网址在线观看视频| 天天日天天玩天天摸| 51vv精品视频在线观看| 18福利视频在线观看| 99精品久久99久久久久一| 69国产精品成人aaaaa片| 宅男噜噜噜66国产在线观看| 九一精品人妻一区二区三区| 欧美成人短视频在线播放| 亚洲成a人片777777张柏芝| 日本不卡 中文字幕| 亚洲欧洲无码一区2区无码| 国产自拍偷拍在线精品| 91超碰国产在线观看| 黑人爆操女人免费视频| www,日韩av,com| 全彩漫画口工18禁| 欧美一级aaaaaaa片| 久久久久久久精品乱码| 不用付费特黄特色亚洲特级黄色片| 婷婷色综合五月天视频| 亚洲欧美日韩中文在线观看| 欧美日本在线免费视频| 每日更新日韩欧美在线| 鸡巴在里面福利视频在线观看| 精品国模一区二区三区欧美| 日本高清有码在线视频| 色老头一区二区三区四区五区| 色丁香久久激情综合网| 精品av天堂毛片久久久| av在线中文字幕在线| 国际日韩日韩日韩日韩日韩| 午夜精品久久秘?18免费观看| 快进来插我的逼嗯啊视频| 亚洲人妻系列在线视频| 快进来插我的逼嗯啊视频| 在线观看视频免费一区二区三区| 最近最新最好看的中文字幕| 九九热视频1这里只有精品| 天天弄天天草天天日天天| 天天操天天搞天天操| 操人妻人妻天天爽天天偷| 超碰在线免费观看视频97| 男人和女人的逼视频| 国产一区二区三区四区精| 午夜8050免费小说| 后入日韩翘臀蜜桃臀美女| 成人午夜高清福利视频| 亚洲av在线免费播放| 青青操久久综合激情| 黄色片免费网站在线| 天天早上头和脸出汗是怎么办| 欧美视频免费观看777| 自拍偷拍视频亚洲一区| 看女人大BB群伦交| 天天干天天日天天弄| 91超碰九色porny| 最新日韩中文字幕啪啪啪| 亚洲a区在线免费观看| 亚洲熟女乱色一区二区三区视频| 美女把逼扒开让男人桶| 2020年亚洲男人天堂网| 精品不卡一区二区三区| 小妹妹爱大棒棒免费观看视频| 天天碰天天摸天天搞| 亚洲乱熟女一区二区三区影片| www国产亚洲精品久久久| 99久久国产精品免费热| 熟女一区二区三区综合| 情趣视频在线观看91| 色哟哟亚洲乱码国产乱码精品精| 精品一区二区三区喷水内射高潮| av在线观看视频免费| 国语精品视频自产自拍| 美女网站视频久久精品| 操人妻人妻天天爽天天偷| 99re这里是国产精品首页 | 亚洲色视频在线播放网站| 女人高潮潮呻吟喷水网站| alisontyler和黑人| 亚洲人人爽人人澡起碰av| 51vv精品视频在线观看| 久久人妻人人草人人爽| 少妇熟女天堂网av| 欧美猛少妇色ⅹⅹⅹⅹⅹ猛叫| 大屁股熟女一区二区视频| 2019年中文字幕在线播放视频| 一二区二区不卡视频| 精品一区二区三区免费毛片W| 国产午夜在线播放视频| 韩国在线播放一区二区三区| 视频在线+欧美十亚洲曰本| 国产av嗯嗯啊啊av| 午夜宅男电影av网站| 日韩加勒比精品在线看| 性感美女极品18禁网站在线| 美女网站福利在线观看| 成人精品影视一区二区| 日韩少妇免费在线播放| 成人免费视频现网站99在线观看| 在线能看视频你懂的| 亚洲国产精品久久久久久无码| 亚洲av中文无码网站| av福利免费体验观看| 日本成人福利电影网| 东北老女人熟女啪啪视频| —区二区三区女厕偷拍| 国产主播诱惑毛片av| 丰满少妇人妻一区二区三区蜜桃| 久久久西西gogo日本美女人体| 人妻中文字幕亚洲在线| 久久久人妻免费视频| 不用付费特黄特色亚洲特级黄色片| 亚洲午夜熟女在线观看| 国产熟妇色xxⅹ交白浆视频| 大片a免费观看在线视频观看| 深夜福利免费观看在线看| 嗯~嗯~啊啊啊~高潮了软件| 欧美vr专区日韩vr专区| 999精品视频免费在线观看| 亚洲另类激情视频在线看| 国产成人综合久久婷婷| 成年人黄色日本视频| 欧美日韩高清片在线观看| 熟女人妻精品视频一区| 色就色综合偷拍区欧美在线| 久久内射天天玩天天懂色| 欧美一级特黄大片在线| 熟女国内精品一区二区三区| 三级欧美日韩一区二区三区| 久久久久久免费观看av| 超peng视频在线免费播放97| 99热99这里免费的精品| 天天干天天操天天要| 欧美精品激情在线不卡| 天天在线播放日韩av| 亚洲乱熟女一区二区三区山| 岛国av成人午夜高清| 亚洲美女露隐私av一区二区精品| 亚洲美女a级黄色在线播放| 夜夜操天天干夜夜操| 国产激情免费在线视频| 黑人3p日本女优中出| 99热99这里免费的精品| 天天干天天操天天要| 亚洲一区二区偷拍女厕所| 亚洲av毛片一区二区三区网| 亚洲美女a级黄色在线播放| 开心激情五月天作爱片| 中文人妻av一区二区三区| 麻豆国产精品777777在| 91国产精品乱码久久久久久| 天天早上头和脸出汗是怎么办| 核xp工厂精品久久亚洲| 黑人侵犯人妻森泽佳奈| 最近在线中文字幕免费| 蜜臀久久精品久久久久久av| 精品国产人伦一区二区三区| 午夜久久久久欠久久久久| 成人黄色录像在线观看| 不卡一二三区别视频| 在线视频自拍第三页| 2018中文字字幕人妻| 亚洲av毛片在在线播放| 中文字幕日本一二三区| 92在线播放观看视频| 亚洲男人天堂最新网址大全| 国产精品内射婷婷一级| 亚洲经典av中文字幕| 中文在线字幕免费观看日韩视频| 国内精品一区二区2021在线| 鸡巴在里面福利视频在线观看| 亚洲av综合av一去二区三区| 4438x亚洲最大的成人| 成熟了的熟妇毛茸茸| 神马不卡视频在线视频| 69国产在线视频网站| 黑人巨大精品一区二区在线| 92在线播放观看视频| 亚洲熟妇在线视频观看| 午夜在线成人免费电影| 亚洲一区二区偷拍女厕所| 蜜桃tv一区二区三区| 午夜野花视频在线观看| 亚洲精品乱码久久久久app| 精品美女洗澡一区二区| 人妻被强av系列一区二区| 久久久久高潮白浆久久| 大奶熟妇激情操逼逼| 91色哟哟视频在线观看| 成人午夜麻豆大胆视频| 日本福利视频网站导航| 四虎国产精品国产精品国产精品| —区二区三区女厕偷拍| 蜜桃tv一区二区三区| 91精品资源在线观看| 欧美不卡一二三区精品| 久久久精品人妻无码专区不卡 | 97精品人妻免费视频| 日韩三级黄色大片在线观看| 亚洲欧洲一区二区三区在线| 奇米网首页神马久久| 精品国产污污污污免费观看| 国产精品 亚洲欧美 自拍偷拍| 天天操天天舔天天射天天日天天干| 五月婷婷伊人久久中文字幕| 国语精品视频自产自拍| 日本福利视频网站导航| 日韩黄色在线观看网站上| 欧美久久蜜臀蜜桃资源吧| 99久久精品视频16| 三区美女视频在线观看| 欧美激情视频第一页| 免费成人av麻豆| 人妻色综合aaaaaa网| 欧美精品乱码99久久蜜桃免费| 亚洲熟妇在线视频观看| 在线观看视频免费一区二区三区| 日韩A级毛片免费视频| 久久99精品热在线观看| 日本一道中文字幕99| 日本久久久久久黄色| 大成色亚洲一二三区| 中文字幕观看中文字幕免费 | 亚洲欧美精品海量播放| 99免费观看在线视频| v天堂国产精品久久| 精品视频一区二区三区◇| 亚洲综合天堂av网站在线观看| 国产精品视频网站污污污| 制服丝袜中文字幕熟女人妻| 久久久视频在线播放| 五月天天堂视频在线| 国产黑色丝袜 在线日韩欧美| 亚洲图片另类综合小说| 99热这里只有精品免费播放| 日本黄色一级电影网址| 精产国品一二三产品区别97 | 96在线观看免费播放| 老司机伊人99久久精品| 欧美色视频网址大全| 国产人妻熟女ⅹxx丝袜| 日本老熟妇av老熟妇| 亚洲激情视频在线观看免费| 成人超碰一区二区三区| 最近最新最好看的中文字幕| 日本免费人爱做视频在线观看不卡| 亚洲国产精品一区二区第二页| 国产高清视频www夜色资源| 欧美大鸡吧男操女啊啊啊视频| 青青在线免费手机播放视频| 中文字幕亚洲乱码精品无限| 欧美啪啪一区二区三区| 在线观看中文字幕精品av| 人妻女侠被擒受辱记| 亚洲欧洲无码一区2区无码| 最近日韩免费在线观看| 天天爱天天日天天爽| 老色鬼精品视频在线观看播放| 亚洲在线免费观看18| 欧美成人区一区二区三| 91亚洲国产成人久久精品| 日本人妻熟妇丰满成熟HD系列 | 亚洲欧美另类校园春色| 顶级欧美色妇4khd| 婷婷一区二区三区五月丁| 夜夜爽夜夜操夜夜爱| 亚洲国产电影的一区| 91人妻人人做人人爽高清| av在线播放观看h| av在线免费在线观看| 在线中文字幕人妻av| 亚洲av三级电影在线观看| 欧美国产精品久久久免费| 大成色亚洲一二三区| 在线能看视频你懂的| 久操资源在线免费播放| 亚洲欧美精品日韩偷拍| 国内精品一区二区2021在线 | 丰满放荡熟妇在线播放| 夫亡人妻被强干中文字幕| 亚洲美女露隐私av一区二区精品 | 亚洲欧美精品海量播放 | 亚洲熟女乱色一区二区三区视频| 天天操天天干加勒比久久| 秋霞成人午夜鲁丝一区二区三区| 男生用大肌巴操美女骚穴| 天天干天天操天天日天天日| 国产av嗯嗯啊啊av| 亚洲天堂av最新在线| 美女欧美视频在线观看免费| 免费观看在线中文字幕视频| 蜜桃臀av在线一区二区| 午夜精品老牛av一区二区三区| 天天日天天亲天天操| 无码人妻丰满熟妇区五路| 日本丰满熟妇浓密多毛| 亚洲av中文无码网站| 国产农村乱子伦精精品视频| 日本一区二区高清av中文| 天天操天天干加勒比久久| 日韩免费黄色片在线观看| 日本香港韩国三级黄色| 99热99这里免费的精品| 北野中文字幕一区二区| 伊人网国产在线播放| 国产大桥未久一区二区| 蜜臀久久精品久久久久久av| 顶级欧美色妇4khd| 亚洲一区亚洲二区成人福利| 久久久西西gogo日本美女人体| 99久9在线视频播放| 久久久精品人妻无码专区不卡| av激情四射五月婷婷| 5d蜜桃臀女无痕裸感| 亚洲女人自熨在线视频| 亚洲成人,国产精品| 99精品视频在线在线观看| 国产一区二区手机在线观看| 大香蕉尹人在线最新| 69精品人妻久久久久久久久久久 | 国产最新av在线免费观看| 欧美日本国产一区二区| 中文字幕人妻精品精品| 精品国产无乱码一区二区三区| 国产一区二区三区四区精| 亚洲午夜熟女在线观看| 麻豆白洁少妇在线播放| 69精品人妻久久久久久久久久久| 极品风骚人妻3p视频| 免费在线小视频你懂的| 亚洲欧美小说中文字幕| 911美女片黄在线观看| 国内销魂老女人老泬| 精品高潮呻吟久久av| 九九热视频1这里只有精品| 女人扒开逼让男人操| 一区二区三区四区 在线播放| 亚洲综合一区二区三区四区| 福利视频导航在线观看| 强乱人妻中文字幕日本| 大香蕉尹人在线最新| 九九九九九久久久国产| 亚洲国内精品久久久久久久| 核xp工厂精品久久亚洲| 蜜桃tv一区二区三区| 91精品91久久久久| 国产91免费在线观看| 午夜美女福利视频在线| 日韩欧美一区二区三区免费看 | 天海翼亚洲一区在线观看| 国产精品亚洲精品亚洲| 亚洲美女午夜激情视频在线观看 | 亚洲第一区av中文字幕| 欧美极品少妇高潮喷水| 色就色综合偷拍区欧美在线| 性感人妻 中文字幕| 免费中文三级在线观看| 亚洲国产精品 久久久| 丝袜美女诱惑佐佐三上| 欧美 日韩 精品 中文| 日韩久久九九精品视频| 国产精品视频网站污污污| 亚洲自拍偷拍一区二区中文字幕 | 精品人妻在线激情视频| 亚洲美女露隐私av一区二区精品| 亚洲欧美一级特黄大片 | 99色在线观看免费观看| 亚洲国产精品久久久久久无码| 凹凸视频一区二区在线观看| 丰满少妇人妻一区二区三区蜜桃| 成人午夜麻豆大胆视频| 一区二区在线观看视频观看| 精品国产污污污免费入口| 日韩黄色在线观看网站上| 午夜精品视频免费观看| 亚洲欧美韩国日本一区二区| 超碰在线免费观看视频97| 91精品麻豆91夜夜骚| 老熟女 露脸 嗷嗷叫| 久久久久高潮白浆久久| 国产午夜在线播放视频| 最新日韩av电影在线播放| www国产亚洲精品久久久| 欧美在线观看视频欧美| 一区二区三区av免费天天看| 日本久久久久久黄色| 天天透天天舔天天操| 亚洲男人天堂最新网址大全| 国产美女高潮精品视频| 亚洲自拍偷拍一区二区中文字幕| 亚洲欧美不卡专业视频| 亚洲韩精品一区二区三区| 999久久久人妻精品一区| 男女啪啪啪网站在线观看免费| 69av精品国产探花| 68福利精品在线视频| 亚洲综合一区二区三区四区| 亚洲精品中文字幕手机在线免费看| 日韩国产欧美久久一区| 国产白丝一区二区三区av| 91精品麻豆91夜夜骚| 2018中文字字幕人妻| 加勒比东京热绿帽人妻多人操| 最新激情中文字幕视频| 女同大尺度视频网站在线观看| 91污污在线观看视频| 欧美巨大另类极品video| 亚洲熟女一区二区六区| av 一区二区三区 熟女| 日本丰满熟妇浓密多毛| 久久久人妻免费视频| 国产资源网站在线播放| 欧美日韩精品aaa| 老司机免费视频福利0| 午夜92福利1000| 日本东京热视频欧美视频| 夜色17s精品人妻熟女av| 天天插天天透天天爽| xxxx69在线观看视频| 亚洲熟女乱一区二区精品成人| 欧美日韩在线观看免费播放| 欧美啪啪一区二区三区| 久久久久久a女人处女| aa福利影视在线观看| 国产福利三级在线观看| 亚洲欧美精品海量播放| 91超碰九色porny| 亚洲在线观看中文字幕av| 无码精品黑人一区二区老人| 日本五六十路熟女视频| 老鸭窝在线毛片观看免费播放| 久久国产精品久精国产爱| 色欲AV亚洲AV无码精品| 91偷拍被偷拍在线播放| 鸡巴在里面福利视频在线观看| 国产av剧变态维修工虐杀美女| 国产美女主播av在线| 亚洲av网站一区二区三区| 人妻少妇视频系列视频在线| 亚洲人成小说网站色| tushy一区二区三区视频| 日韩人妻中文字幕二区| 亚洲av毛片一区二区三区网| 精品国产污污污免费入口| av在线观看视频免费| 无码精品黑人一区二区老人| 亚洲欧美另类丝袜另类自拍| 亚洲精品中文字幕手机在线免费看 | 日本少妇人妻中文在线| 超级黄肉动漫在线观看| 国产精品成人免费电影| 少妇精品视频一区二区免费看| 国产视频成人一区二区| 亚洲成人五月婷婷久久综合| 日本清纯中文字幕版| 东京热日韩av影片| 亚洲自拍偷拍一区二区中文字幕 | 男生用大肌巴操美女骚穴| 漂亮人妻口爆久久精品| 女生裸体视频免费网站| 夜夜骚av一二三区| 天天早上头和脸出汗是怎么办| 欧美日韩国产在线中文字幕| 97精品国产91久久久| 韩国在线播放一区二区三区| 妈妈的朋友2中文字幕在线| 久久人妻诱惑我视频| 老司国产精品视频免费观看| 中文字幕免费啪啪啪| 在线免费观看a视频免费| 核xp工厂精品久久亚洲 | 亚洲经典av中文字幕| 国产av剧变态维修工虐杀美女| 欧美日韩久久丝袜在线| 国内销魂老女人老泬| xxxx69在线观看视频| 最近最新欧美日韩精品| av日韩视频在线观看| 91中文字幕视频网站| 久久精品久久久久观看99水蜜桃| 色视频免费观看网址| 加勒比不卡在线视频| 啪啪啪网站免费看视频| 国际日韩日韩日韩日韩日韩 | 在线视频国产精品欧美| 99 re国产精品| 女人扒开逼让男人操| 户外露出视频在线观看| 亚洲国产精品久久久久久无码| av资源中文字幕在线观看| 老色鬼精品视频在线观看播放| 亚洲欧美激情久久久| 日韩一级欧美一级片| 日本福利片在线播放| 在线免费观看欧美小视频| 国产福利小视频在线观看网站| 国产男女无套?免费网站下载| 中文字幕 一区二区在线观看| 亚洲第一成年偷拍视频| 欧美视频免费观看777| 熟女一区二区三区综合| 91精品夜夜夜一区二区蜜桃| 2020精品视频在线| 国产中文亚洲熟女日韩| 夏目彩春av在线看| 亚州av嫩草av极品在线观看| 日本欧美亚洲国产啊啊啊| 午夜精品老牛av一区二区三区| 最新日韩中文字幕啪啪啪| 免费成人av麻豆| 天天干天天操天天要| 天天早上头和脸出汗是怎么办 | 国产做A爱免费视频在线观看| 国产av在线免费视频| 午夜3p福利视频合集| 97精品国产91久久久| 日本成人福利电影网| 美利坚合众国av天堂| 男女爱爱好爽视频免费看| 欧美精品激情在线不卡| 9999久久久久老熟妇二区| 日本高清有码在线视频| 中文字幕亚洲无线乱码| 日韩男女视频网站在线观看| 亚洲国产美女主播在线观看| 精品国产人伦一区二区三区| 亚洲一区二区精品在线播放| 精品国产人伦一区二区三区| 亚洲成人偷拍自拍在线| 亚洲一区二区在线激情| 高清欧美色欧美综合网站| 亚洲中文字幕在线视频观看二区| 日韩一区二区在线播放观看| 成人资源中文在线观看| 综合久久伊人久久88| 日本在线免费观看国产精品| 人人妻人人狠人人爽| 中文字幕中文字幕在线中…一区| 熟妇高潮久久久久久久| 91大神福利视频网| 亚洲中文字幕在线av| 国产av啊啊啊啊啊啊啊| 伊人情人成综合视频| 色丁香久久激情综合网| 91在线九色porny| 天天操天天日天天插天天舔| 中文字幕在线免费观看成人| 午夜福利在线不卡视频| 99精品久久99久久久久一| 男人和女人的逼视频| 成熟了的熟妇毛茸茸| 69xx精品久久久久| 亚洲欧美国产一本综合首页| 91国产精品乱码久久久久久| 99国产精品国产精品毛片19| 91佛爷视频在线观看| 欧美日韩成人高清中文网| 五月在线视频免费播放91| 日韩一级欧美一级片| 天天弄天天草天天日天天| 欧美在线观看一区二区不卡| 偷拍熟女大胆免费视频| 五月的婷婷综合视频| av里面的动作是真进去吗| 老熟女 露脸 嗷嗷叫| 亚洲av手机免费在线| 最新久久这里只有精品| 福利小视频免费在线| 精品欧美黑人一区二区三区| 亚洲女人自熨在线视频| 日韩成人免费观看电影| 丰满少妇高潮喷水视频| 黑人和日本人av一区二区| 亚洲国产电影的一区| 亚洲 偷拍 自拍 欧美| 亚洲午夜高清在线观看| 婷婷一区二区三区五月丁| 一区二区三区av免费天天看| 欧美成人性生活视频播放| av资源中文字幕在线观看 | 国产成人综合久久婷婷| 国产主播诱惑毛片av| 亚洲欧美激情国产综合久久久| 视频自拍偷拍视频自拍 | 亚洲乱码国产乱码精品精视频| 成人大片男人的天堂| 九色91操最新在线观看网址| 大香蕉在线欧美在线视频| ysl蜜桃色7425| 后入日韩翘臀蜜桃臀美女| 妈妈的朋友2中文字幕在线| 日韩激情文学在线视频 | 欧美极品少妇高潮喷水| 青青操久久综合激情| 亚洲图片另类综合小说| 91在线九色porny| 户外露出视频在线观看| 69国产在线视频网站| 国产一级一国产一级毛片| 国产经典精品欧美日韩| 加勒比不卡在线视频| 亚洲熟妇在线视频观看| 欧美日韩黄片免费在线观看| 亚洲精品激情视频在线观看| 日本高清激情乱一区二区三区 | 亚洲av中文免费在线| 黑人黄色免费一级av| 大屁股熟女一区二区视频| 中文字幕av人妻一区二区三区| 亭亭五月天在线观看| 老司国产精品视频免费观看| 伊人精品久久一区二区| 亚洲中文字幕无线乱码人妻精品| 亚洲另类欧美综合久久| 亚洲制服丝袜美腿在线| 天天弄天天草天天日天天| 四虎国产精品国产精品国产精品| 欧美不卡一二三区精品| 国产原创一区二区三区在线播放| 日本少妇丰满大bbb的小乳沟| 亚洲欧美国产一本综合首页| 亚洲国产电影的一区| 91超碰九色porny| 超碰在线观看97资源| 杜达雄啪啪毛片视频| 38av一区二区三区| 亚洲熟女少妇中文字幕系列| 亚洲av在线免费播放| 午夜五十路久久福利| 97精品人妻免费视频| 182tv精品免费在线观看| 亚欧洲乱码视频一二三区| 久久久人妻免费视频| 中文字幕一区二区人妻视频| 日韩三级精品电影久久久久 | 午夜亚洲国产精品中字| 9999久久久久老熟妇二区| 神马午夜久久电影网| 国产伦理二区三区在干嘛呢| 午夜精品秘一区二区三区| 国产剧情av在线免费观看| 熟女人妻aⅴ一区二区三| 亚洲妹妹我爱你在线观看| 美女扒开逼逼给你看| 中文字幕福利视频第四页| 顶级欧美色妇xxxx| 欧美成人久久久桃色aa| 91精品资源在线观看| 免费在线观看视频啪啪| 天天操天天干加勒比久久| 亚洲少妇色小说综合| 先锋人妻啪啪中文字幕| av在线播放观看h| 欧美一级特黄大片做受99| 天天干天天色综合久久| 奇米网首页神马久久| 国产一区二区手机在线观看| 女人扒开逼让男人操| 国产视频成人一区二区| 69xx精品久久久久| 欧洲成熟女人色惰片| 青青青在线视频观看97| 不卡在线一区二区三区| 国产美女高潮精品视频| 天天干夜夜撸天天操| 女同大尺度视频网站在线观看| 成人人妻h在线观看| 黄色片黄色片黄色片黄色片黄色| 亚洲制服丝袜美腿在线| 中文字幕日韩首页欧美在线激情| 五月在线视频免费播放91| 新亚洲天堂男子av| 一区二区九日韩美女| 国产肥胖熟女又色又爽免费视频| 精产国品一二三产品区别91| 国际精品熟女一区二区| 亚洲精品国品乱码久久久久| 亚洲午夜精品视频节目| 亚洲一区二区精品在线播放| 狂操鸡巴小骚逼视频免费观看| 中文字幕 人妻 熟女| 亚洲男人天堂最新网址大全 | 欧美一级特黄大片做受99| 可以免费观看日韩av| 日本人妻熟妇丰满成熟HD系列| 老司国产精品视频免费观看| 欧美日韩久久丝袜在线| 亚洲欧美另类丝袜另类自拍| 亚洲欧美另类丝袜另类自拍| 亚洲宅男噜噜噜66在线观看 | 河北全程露脸对白自拍| 伊人久久综合国产精品| 亚洲av综合av一去二区三区| 欧美精品熟妇免费在线| 欧美成人久久久桃色aa| 黄色片免费网站在线| 成人免费电影二区三区| 亚洲精品综合欧美精品综合| 亚洲色视频在线播放网站| 国产人妻777人伦精品hd超碰| 大乳丰满人妻中文字幕韩国hd| 免费绝清毛片a在线播放| v天堂国产精品久久| 亚洲字幕一区二区夜色av| 最新激情中文字幕视频| 亚洲第一成年偷拍视频| 最新福利二区三区视频| 亚洲人成小说网站色| 久久无码高清免费视频| av在线中文字幕在线| 亚洲精品激情视频在线观看| 人人妻人人爽人人爽欧美一区| 69视频在线精品国自产拍| 欧美亚洲另类精品第一页| 精品欧美黑人一区二区三区| 日本东京热视频欧美视频| 91福利高清在线播放| 午夜92福利1000| 国产做A爱免费视频在线观看| 日韩A级毛片免费视频| avjpm亚洲伊人久久| 特级aaaaa黄色片| 中文人妻av一区二区三区| 日韩A级毛片免费视频| 核xp工厂精品久久亚洲| 夜夜操夜夜爱夜夜摸| 天天干夜夜爽狠狠操| 亚洲成人激情在线综合| 天天日 天天舔 天天射| 天天日天天玩天天摸| 熟女阿高潮合集一区二区| 天天搞天天操天天干| 日本欧美亚洲国产啊啊啊| 久草视频在线看免费| 五十岁熟妇高潮喷水| 五十岁熟女高潮喷水| 青青操天堂在线观看视频| 漂亮人妻口爆久久精品| 国产igao激情在线视频入口| 精久久久久久久久久久久| 91精品夜夜夜一区二区| 青青国产95免看视频| 在线看日韩av不卡| 女人的天堂av在线网| 中文字幕中文字幕在线中…一区| 夜夜躁av麻豆男| 男女69视频在线观看免费| 亚洲天堂av最新在线| 在线免费视频999| 成熟了的熟妇毛茸茸| 日本小视频一区二区| 乱子伦国产一区二区三区| 午夜精品久久秘?18免费观看| 福利视频导航在线观看| 大成色亚洲一二三区| 亚洲第一页欧美第一页| 久久99精品热在线观看| 国产自拍偷拍在线精品| 亚洲一区二区三区四区入口| jiee日本美女视频网站| 美女激情久久久久久久| 91porny九色视频偷拍| 免费看一级高潮喷水片| 欧美成人短视频在线播放| lutu玩弄人妻短视频| 大陆中文字幕视频在线| 手机看片福利一区二区三区四区| 亚洲色大WWW永久网站| 中文字幕欧美人妻在线.| 人人妻人人爽人人摸| 成人做爰av在线观看网站| 精久久久久久久久久久久 | 1区3区4区产品乱入视频| 91青青青国产免费高清| 国产精品 亚洲欧美 自拍偷拍| 精品一区二区三区喷水内射高潮| 97超碰人人爽人人做| 欧洲精品在线免费观看| 欧美精品激情在线不卡| 中文字幕日韩首页欧美在线激情| 大乳人妻一区二区三区| 港台美女明星av天堂| 福利美女视频在线观看| 亚洲欧美综合另类最新| 91精品夜夜夜一区二区| 黑川堇人妻88av| 五月天天堂视频在线| 熟女阿高潮合集一区二区| 欧美成人区一区二区三| 亚洲美女露隐私av一区二区精品| 男女插鸡巴视频软件| caopeng97在线观看视频| 青青青在线观看国产| 日韩少妇免费在线播放| 人人妻人人爽人人爽欧美一区 | 亚洲一区视频中文字幕在线播放 | 天天操天天搞天天操| 91超精品碰国产在线观看| 亚洲自拍偷拍av在线| 青青青在线视频免费播放| 最近在线中文字幕免费| 九九热视频1这里只有精品| 欧美一级aaaaaaa片| 97精品人妻免费视频| 亚洲成人av在线一区二区| 精久久久久久久久久久久| 裸日本资源在线午夜| 国产精品视频网站污污污| 日本一本午夜在线播放| 亚洲人妻系列在线视频| 九色91操最新在线观看网址| 午夜精品久久久久久久久久蜜桃| 区一区二区三免费观看视频| 日本少妇人妻凌辱在线| 91青青青国产免费高清| 国产自拍偷拍视频在线免费观看 | 中文字幕一区二区三区久久久| 国产激情在线观看一区二区三区| 国产精美视频精品视频精品 | 国产视频1区2区3区| 成人做爰av在线观看网站| 蜜桃臀av在线一区二区| 成人人妻h在线观看| 日本一区二区三区区别| 全国熟妇精品一区二区免费视频 | 18在线观看免费观看| 北野中文字幕一区二区| 天堂网成人av电影| 在线看的免费网站黄| 美女激情久久久久久久| 天天日 天天舔 天天射| 手机看片福利一区二区三区四区 | 全彩漫画口工18禁| 嗯~嗯~啊啊啊~高潮了软件| 新香蕉视频香蕉视频2| caopeng97在线观看视频| 日本福利片在线播放| 亚欧洲乱码视频一二三区| 亚洲国产精品自产拍在线观看| 欧美久久蜜臀蜜桃资源吧| 久久久久九九九九九12| 河北全程露脸对白自拍| 中文字幕 一区二区在线观看| 少妇精品视频一区二区免费看| 99久久国产精品免费消防器材| 国产天堂av不卡网| 91超碰九色porny| 北野中文字幕一区二区| 欧美一区日韩二区三区四区| 超peng视频在线免费播放97| 日韩三级精品电影久久久久| 精品日本少妇久久久| 国产91免费在线观看| 女人扒开逼让男人操| 亚洲精品国产99999| 亚州av嫩草av极品在线观看| 中文字幕熟女乱一区二区| 欧美猛少妇色ⅹⅹⅹⅹⅹ猛叫| 亚洲资源在线免费观看| 亚洲av中文免费在线| 天天插天天透天天爽| 快色视频在线观看免费| 亚洲国产精品自拍偷拍视频在线 | 九九热在线精品播放| 日韩欧美中文字幕老司机三分钟| 国产精品 亚洲欧美 自拍偷拍| 亚洲欧美国产人成在线| 成人免费视频现网站99在线观看| 午夜国产成人精品视频观看| 综合久久伊人久久88| 天堂一区二区三区在线等| alisontyler和黑人| 亚洲综合第一区二区| 男插女视频大全免费| 55夜色66夜色亚洲精品| 天天操天天舔天天做| 成人午夜高清福利视频| 最近在线中文字幕免费| 2020国产成人精品视频| 女同性恋av在线播放| 日韩三级黄色大片在线观看| 欧美日韩高清片在线观看| 国产成人av在线你懂得| 最新日韩中文字幕啪啪啪| 大香蕉在线欧美在线视频| 成年人免费福利在线| 熟妇人妻丰满久久久久久久| 在线视频国产精品欧美| 韩国一级片最火爆中文字幕| 9662av在线视频| 亚洲va999天堂va| tushy一区二区三区视频| 久久无码高清免费视频| 久操资源在线免费播放| 视频在线+欧美十亚洲曰本 | 中文字幕一区二区人妻视频| 日韩美精品成人一区二区三区四区| 国长拍拍视频免费孕妇| 欧美三区四区在线视频| 91进入蜜桃臀在线播放| 爱搞视频在线观看视频91| 久久99精品热在线观看| 2020国产成人精品视频| 全球高清中文字幕av| 日韩欧美国产一区二区在线观看| 制服丝袜 中文字幕 日韩| 国长拍拍视频免费孕妇| 午夜福利午夜福利影院| 一区二区三区四区影片| 国产高清在线观看av| 亚洲国产精品一区二区第二页| 青青草成人免费自拍视频| 欧美日韩不卡视频合集| 强乱人妻中文字幕日本| 亚洲成a人片777777张柏芝| 人妻人妻在线视频网站| 欧美一级特黄大片做受99| 午夜五十路久久福利| 亚洲男人天堂最新网址大全| 国产激情视频在线观看的| 天堂在线中文字幕av| 欧美日韩福利视频网| 插鸡视频免费网站在线播放| 欧美老熟妇xxoo老妇| 99久久久久久久久久久久久| 天天曰天天摸天天爽| 西野翔人妻中文字幕中字在| 人妻熟女 亚洲 一页二页| 男女69视频在线观看免费| 亚洲国产精品久久久久久无码| 国产福利三级在线观看| 久久久久夜色国产精品电影| 91人妻人人做人人爽高清 | 成人资源中文在线观看| 久久国产半精品99精品国产| 午夜精品久久久久久久精品乱码| 欧美啪啪一区二区三区| 久久久久久久岛国免费观看| 激情九月天在线视频| 青娱乐免费最新视频| 亚洲18片综合国产av| 五月天男人的天堂中文字幕| 天天插天天操天天射天天干| 男女69视频在线观看免费| 又爽又粗又猛又色又黄视频| 免费中文三级在线观看| 久久久久性感美女偷拍视频| 丝袜美腿日韩av一区| jiee日本美女视频网站| 豆豆专区操逼性视频在线| 亚洲精品久久久人妻| 欧美日韩精品aaa| 日本男女免费福利视频| av 一区二区三区 熟女| 久久热在线免费观看| 一二三四区国产在线观看| 四虎精品久久免费最新| 青青草成人免费自拍视频| 在线视频自拍第三页| 老熟妇一区二区三区v∧88| 自拍丝袜国产欧美日韩| 国产av啊啊啊啊啊啊啊| 一区二区欧美 国产日韩| 成人午夜av电影网| 新亚洲天堂男子av| 黑人大吊大战亚洲女人。| 中文字幕麻绳捆绑的人妻| 日韩少妇免费在线播放| 亚洲精品9999蜜桃| 男人电影天堂在线观看| 每日更新日韩欧美在线| 99久久国产精品免费热| 亚洲 综合 欧美 一区| 亚洲乱熟女一区二区三区山| 99女福利女女视频在线播放| 神马午夜久久电影网| 日韩在线 中文字幕| 日韩三级精品电影久久久久| 亚洲成人中文无码在线| tobu8日本高清| avtt中文字幕手机版| 青青青在线视频免费播放| 成人超碰一区二区三区| 中文字幕人妻一区色偷偷久久| 自拍偷自拍亚洲精品10p| 人妻中文字幕亚洲在线| 男女爱爱好爽视频免费看| 亚洲乱熟女一区二区三区山| 涩涩黄片在线免费观看| 天天想要天天操天天干| 偷拍熟女大胆免费视频| 亚洲午夜国产末满十八岁勿进网站| 国内精品一区二区2021在线 | 国产精品网站亚洲发布| 欧美日韩一区二区三区成人影院| 日本高清在线观看不卡视频| 精久久久久久久久久久久| 户外露出视频在线观看| 国产三级自拍视频在线观看网站| 日韩激情文学在线视频| 蜜臀一区二区日韩美女少妇视频| 夫亡人妻被强干中文字幕| 欧美强奸视频在线观看| 男女啪啪啪网站在线观看免费| 中文字幕人妻精品精品| 天天日天天玩天天摸| 自拍丝袜国产欧美日韩| 亚洲字幕一区二区夜色av| 5566熟女人妻人妻| 美利坚合众国av天堂| 男人的天堂av中文字幕| 快使劲弄我视频在线播放| 亚洲激情视频在线观看免费| 91九色人妻在线播放| 夜夜爽夜夜操夜夜爱| 人妻女侠被擒受辱记| 欧美猛少妇色ⅹⅹⅹⅹⅹ猛叫| 亚洲熟女人妻自拍在线视频| 亚洲日本欧美韩国另类综合| 抽插小穴啊啊啊视频| 亚洲经典av中文字幕| 国产精品视频网站污污污| 亚洲女人自熨在线视频| 麻豆午夜激情在线观看| 55夜色66夜色亚洲精品| 性感美女人妻久久久| 免费中文三级在线观看| 中文字字幕在线精品乱码| 黄片视频免费观看视频| 亚洲 自拍 激情 另类| 18在线观看免费观看| 成熟了的熟妇毛茸茸| 久久午夜免费鲁丝片| 日韩无码国产一区二区| 国产 亚洲 欧美 自拍| av里面的动作是真进去吗 | 亚洲av毛片一区二区三区网| 一区二区三区婷婷中文字幕| 抽插小穴啊啊啊视频| 婷婷一区二区三区五月丁| 狂操鸡巴小骚逼视频免费观看| a级黄片免费观看| 好看的日本中文字幕在线观看二区| 欧美久久一区二区伊人| 视频在线+欧美十亚洲曰本 | 911精产国品一二三产区区| 日本少妇三级交换做爰做| 东京热男人的天堂视频| 亚洲自拍偷拍av在线| 精品高潮呻吟久久av| 美国男的操女孩的小嫩逼| 中文字幕欧美人妻在线.| 中文字字幕在线精品乱码| 日本四十路人妻熟女| 大香蕉尹人在线最新| 97视频538在线观看| 免费成人av麻豆| 亚洲熟女在线免费观看| 成人做爰av在线观看网站| 性高潮视频在线观看日韩| 午夜久久人妻一级内射av网址 | 亚洲一区二区偷拍女厕所| 午夜美女福利视频在线| 欧美成人性生活视频播放| 91九色国产在线视频| 亚洲精品色图1234| 无码人妻丰满熟妇区五路| 宅男噜噜噜66国产在线观看| 日本一本午夜在线播放| 成人十欧美亚洲综合在线| 国产精品午夜无码AV体验区| 秋霞成人午夜鲁丝一区二区三区| 男人的天堂av中文字幕| 中文字幕日韩人妻在线三区 | 久久久久九九九九九12| 亚洲熟女一区二区六区| 三级欧美日韩一区二区三区| 国产精美视频精品视频精品| 91人妻人人做人人爽高清| 亚洲熟女乱一区二区精品成人| 一区二区三区高清视频3| 亚洲精品色图1234| 欧美精品激情在线不卡| 午夜精品久久久久久久久久蜜桃| av在线播放观看h| 一区二区三区观看在线| 亚洲人人爽人人澡起碰av| 亚洲国产美女主播在线观看| 91精品91久久久久| 69视频在线精品国自产拍| av大尺度一区二区三区| aaaa级少妇高潮在线观看 | 欧美成人屋影院在线视频观看 | 97人妻在线视频自拍| 综合激情网,激情五月| 亚洲情色777中文字幕| 天天天天天天天天日日日| 九九热在线精品播放| 人人妻人人爽人人爽欧美一区| 日韩成人在线电影首页| 色视频在线播放免费观看| 夜夜躁av麻豆男| 久草视频在线视频在线视频| 男人资源站中文字幕| 亚洲一区二区中文字幕久久| 超级黄肉动漫在线观看| 国产剧情av在线免费观看| 操人妻人妻天天爽天天偷| 亚洲码av一区二区三区| 伊人网在线观看 视频一区| 久久久久久免费观看av| 日本老女人日比视频| 国产av精品一区二区三区久久| 欧美日韩成人高清中文网| 可以直接看av网站| 国产毛片特级Av片| 国产视频成人自拍蝌蚪视频| 青青青免费手机视频在线观看| 久久久久国产精品二区| 天天插天天操天天射天天干| 亚洲综合首页综合在线观看| 大奶熟妇激情操逼逼| 狠狠操狠狠操狠狠插| 瑟瑟干视频在线观看| 最新日韩中文字幕啪啪啪| 在线观看黄页网站视频网站| 成人午夜麻豆大胆视频| 天天操天天干加勒比久久| 亚洲乱码国产乱码精品精视频| 九热精品视频在线观看| 中文字幕观看中文字幕免费 | 九一精品人妻一区二区三区| 91在线九色porny| 亚洲免费在线不卡视频| 天天干天天弄天天日| 中文字幕免费啪啪啪| lutu玩弄人妻短视频| 夫亡人妻被强干中文字幕| 亚洲成年人精品国产| 青青青青午夜手机国产视频| 日韩少妇免费在线播放| 91 精品视频在线看| 亚洲成人中文无码在线| 中文字幕免费啪啪啪| 五十岁熟女高潮喷水| 2021国产在线视频| 中出小骚货在线观看| 天天操,天天射,天天爽| 国产女人18毛片水真多精选| 日本特级黄片免费观看| 五月天色婷婷狠狠爱| 午夜在线成人免费电影| 久久久久夜色国产精品电影| 精产国品一二三77777| 欧美日本国产一区二区| 亚洲黄色成人一级片| 欧美日韩亚洲tv不卡久久| 欧美插插插插插插| 国产精品成人免费电影| 夜夜操夜夜爱夜夜摸| 最新日韩中文字幕啪啪啪| 亚洲成人五月婷婷久久综合| 五月的婷婷综合视频| 天天干夜夜操夜夜骑| 女人扒开逼让男人操| 亚洲欧美激情久久久| 99久久久久久久久久久久久| 亚洲av日韩久久网站| 国产av嗯嗯啊啊av| 欧美日韩亚洲国产视频二区| 欧洲精品在线免费观看| 国产成人在线观看hd| 夜夜爽夜夜操夜夜爱| 91精品资源在线观看| 午夜国产一区二区三区| 日本成年视频在线免费观看| 国产激情免费在线视频| 九色porny91国产| 午夜亚洲国产精品中字 | 不卡在线一区二区三区| 极品风骚人妻3p视频| 久久视频 在线播放| 男插女视频大全免费| 人人妻人人爽人人爽欧美一区| 天天干天天弄天天日| 国产精品性感美女视频| 亚洲综合熟女乱中文| 五十岁熟女高潮喷水| av网页免费在线观看| 男人电影天堂在线观看| 午夜宅男电影av网站| 欧美强奸视频在线观看| 午夜精品老牛av一区二区三区 | 熟女人妻少妇一区二区| yy4080黄色片| 亚洲第一中文字幕成人| 夏目彩春av在线看| 日韩少妇免费在线播放| 日韩av电影中文在线免费观看| 欧美日韩综合精品无人区| 色网站在线观看免费| 911精产国品一二三产区区| 福利一二三在线视频观看| 在线视频国产精品欧美| 国内自拍第一区二区三区| 精品人妻在线激情视频| 加勒比东京热绿帽人妻多人操| 国产av在线免费视频| 制服丝袜 中文字幕 日韩 | 蜜桃臀少妇白色紧身裤细高跟| 天天弄天天草天天日天天| 青青免费观看视频| 99精品视频在线在线观看| 福利小视频免费在线| 国产农村乱子伦精精品视频| 青青青青午夜手机国产视频| 亚洲精品一区二区gif| 欧美日韩一区二区三区成人影院| 青青青在线观看国产| 婷婷色综合五月天视频| 中文乱码字幕人妻熟女人妻| 久久sm人妻中出精品一区二区| 久久精品久久久久观看99水蜜桃| 天天日天天亲天天操| 麻豆白洁少妇在线播放| 黄色av网址在线播放| 一区二区在线观看视频观看| 午夜在线观看一级毛| 操死你美女在线视频| 久久99精品热在线观看| 五月的婷婷综合视频| 日韩欧美一区二区三区免费看 | 99国产精品国产精品毛片19| 五月天色婷婷狠狠爱| 亚洲黄色免费在线观看网站| 国产一区二区手机在线观看| 亚洲黄色成人一级片| 在线视频国产精品欧美| 黑人黄色免费一级av| 午夜五十路久久福利| 国产在线小视频一区二区| 豆豆专区操逼性视频在线| 亚洲美女黄色福利视频网站大全| 亚av一二三在线观看| 女生裸体视频免费网站 | 天天操天天日天天碰| 午夜久久久久久av五月| 亚洲最强的25个城市| 蜜桃臀av在线一区二区| 人妻少妇的va视频| 9420高清视频在线观看国语版| 四季av人妻一区二区三区| 欧美视频免费观看777| 人妻色综合aaaaaa网| 91人妻人人爽色啊啊啊| 911精产国品一二三产区区| 丰满少妇_区二区三区| 亚成区一区二区人妻熟女| 91人妻人人爽色啊啊啊| 亚洲综合一区二区三区四区| 国产成人情侣av在线| 中文字幕欧美一区二区视频| 欧美一区二区播放视频| 大香蕉尹人在线最新| xxxx69在线观看视频| 中文字幕福利视频第四页| 亚洲第一页欧美第一页| 欧美性感美女热舞视频| 国产成人91色精品免费看片| 国产精品午夜无码AV体验区| 五月天天堂视频在线| 欧美熟女xx00视频| 亚洲熟妇丰满多毛xxxx网站| 4日日夜夜精品视频免费| 中文字幕熟女人妻丝袜丝在线| 青青国产95免看视频| 国产精品久久久久久成人久| 污网址在线观看视频| 丝袜美女诱惑佐佐三上| av丝袜免费在线观看| 欧美区日本区国产区| 日本高清激情乱一区二区三区|