精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

C++多進程并發框架FFLIB之Tutorial

開發 后端
FFLIB框架是為簡化分布式/多進程并發而生的。它起始于本人嘗試解決工作中經常遇到的問題如消息定義、異步、多線程、單元測試、性能優化等。

 基本介紹可以看這里:

      http://www.cnblogs.com/zhiranok/archive/2012/07/30/fflib_framework.html

  其中之所以特意采用了Broker模式,是吸收了MPI和Erlang的思想。

 關于MPI:http://www.mcs.anl.gov/research/projects/mpi/

 關于Erlang:http://www.erlang.org/

  FFLIB 目前處于alpha階段,一些有用的功能還需繼續添加。但是FFLIB一開始就是為了解決實際問題而生。Broker 即可以以獨立進程運行,也可以集成到某個特定的進程中啟動。除了這些,FFLIB中使用epoll實現的網絡層也***參考價值。網上有一些關于epoll ET 和 LT的討論,關于哪種方式更簡單,本人的答案是ET。ET模式下epoll 就是一個完全狀態機。開發者只需實現FD的read、write、error 三種狀態即可。

  我進一步挖掘FFLIB的功能。寫一篇FFLIB的Tutorial。創建更多的FFLIB使用示例,以此來深入探討FFLIB的意義。在游戲開發中,或者一些分布式的環境中,有許多大家熟悉的模式。,本文挑選了如下作為FFLIB示例:

Request/Reply

點對點通訊

阻塞通訊

多播通訊

Map/Reduce

Request/Reply

異步的Request/Reply

  在FFLIB中所有的消息都是Request和Reply一一對應的,默認情況下工作在異步模式。假設如下場景,Flash連入GatewayServer并發送Login消息包,GatewaServer 解析用戶名密碼,調用LoginServer 驗證。

首先定義msg:

  1. struct user_login_t 
  2.     struct in_t: public msg_i 
  3.     { 
  4.         in_t(): 
  5.             msg_i("user_login_t::in_t"
  6.         {} 
  7.         string encode() 
  8.         { 
  9.             return (init_encoder() << uid << value).get_buff(); 
  10.         } 
  11.         void decode(const string& src_buff_) 
  12.         { 
  13.             init_decoder(src_buff_) >> uid >> value; 
  14.         } 
  15.         long   uid; 
  16.         string value; 
  17.     }; 
  18.     struct out_t: public msg_i 
  19.     { 
  20.         out_t(): 
  21.             msg_i("user_login_t::out_t"
  22.         {} 
  23.         string encode() 
  24.         { 
  25.             return (init_encoder() << value).get_buff(); 
  26.         } 
  27.         void decode(const string& src_buff_) 
  28.         { 
  29.             init_decoder(src_buff_) >> value; 
  30.         } 
  31.         bool value; 
  32.     }; 
  33. }; 

LoginServer中如此定義接口:

  1. class login_server_t 
  2. public
  3.     void verify(user_login_t::in_t& in_msg_, rpc_callcack_t<user_login_t::out_t>& cb_) 
  4.     { 
  5.         user_login_t::out_t out; 
  6.         out.value = true
  7.         cb_(out); 
  8.     } 
  9. }; 
  10. login_server_t login_server; 
  11. singleton_t<msg_bus_t>::instance().create_service("login_server", 1) 
  12.             .bind_service(&login_server) 
  13.             .reg(&login_server_t::verify); 

在GatewayServer中調用上面接口:

  1. struct lambda_t 
  2.     { 
  3.         static void callback(user_login_t::out_t& msg_, socket_ptr_t socket_) 
  4.         { 
  5.             if (true == msg_.value) 
  6.             { 
  7.                 //! socket_->send_msg("login ok"); 
  8.             } 
  9.             else 
  10.             { 
  11.                 //! socket_->send_msg("login failed"); 
  12.             } 
  13.         } 
  14.     }; 
  15.     user_login_t::in_t in; 
  16.     in.uid  = 520; 
  17.     in.value = "ILoveYou"
  18.     socket_ptr_t flash_socket = NULL;//! TODO 
  19.     singleton_t<msg_bus_t>::instance() 
  20.          .get_service_group("login_server_t"
  21.         ->get_service(1) 
  22.        ->async_call(in, binder_t::callback(&lambda_t::callback, flash_socket)); 

如上所示, async_call 可以通過binder_t模板函數為回調函綁定參數。

同步的Request/Reply

  大部分時候我們期望Reply被異步處理,但有時Reply 必須被首先處理后才能觸發后續操作,一般這種情況發生在程序初始化之時。假設如下場景,SceneServer啟動時必須從SuperServer中獲取配置,然后才能執行加載場景數據等后續初始化操作。

  首先定義通信的msg:

  1. struct config_t 
  2.     struct in_t: public msg_i 
  3.     { 
  4.         in_t(): 
  5.             msg_i("config_t::in_t"
  6.         {} 
  7.         string encode() 
  8.         { 
  9.             return (init_encoder() << server_type << server_id).get_buff(); 
  10.         } 
  11.         void decode(const string& src_buff_) 
  12.         { 
  13.             init_decoder(src_buff_) >> server_type >> server_id; 
  14.         } 
  15.         int server_type; 
  16.         int server_id; 
  17.     }; 
  18.     struct out_t: public msg_i 
  19.     { 
  20.         out_t(): 
  21.             msg_i("config_t::out_t"
  22.         {} 
  23.         string encode() 
  24.         { 
  25.             return (init_encoder() << value).get_buff(); 
  26.         } 
  27.         void decode(const string& src_buff_) 
  28.         { 
  29.             init_decoder(src_buff_) >> value; 
  30.         } 
  31.         map<string, string> value; 
  32.     }; 
  33. }; 

如上所示, msg 序列化自動支持map。

  SuperServer 中定義返回配置的接口:

  1. super_server_t super_server; 
  2. singleton_t<msg_bus_t>::instance().create_service("super_server", 1) 
  3.     .bind_service(&super_server) 
  4.     .reg(&super_server_t::get_config); 
  5. SceneServer 可以如此實現同步Request/Reply: 
  6. rpc_future_t<config_t::out_t> rpc_future; 
  7. config_t::in_t in; 
  8. in.server_type = 1; 
  9. in.server_id   = 1; 
  10. const config_t::out_t& out = rpc_future.call(  singleton_t<msg_bus_t>::instance().get_service_group("super_server"
  11.         ->get_service(1), in); 
  12. cout << out.value.size() <<"\n"
  13. //std::foreach(out.value.begin(), out.value.end(), fuctor_xx); 

點對點通訊

  異步Request/Reply 已經能夠解決大部分問題了,但是有時處理Push模式時稍顯吃了。我們知道消息推算有Push 和Poll兩種方式。了解二者:

      http://blog.sina.com.cn/s/blog_6617106b0100hrm1.html

  上面提到的Request/Reply 非常適合poll模式,以上一個獲取配置為例,SuperServer由于定義接口的時候只需知道callback,并不知道SceneServer的具體連接。,所以SuperServer不能向SceneServer Push消息。在FFLIB中并沒有限定某個節點必須是Client或只能是Service,實際上可以兼有二者的角色。SceneServer 也可以提供接口供SuperServer調用,這就符合了Push的語義。假設如下場景,GatewayServer需要在用戶登入時調用通知SessionServer,而某一時刻SessionServer也可能呢通知GatewayServer 強制某用戶下線。二者互為client和service。大家必須知道,在FFLIB中實現兩個節點的通信只需知道對方的服務名稱即可,Broker 在此時實現解耦的作用非常明顯,若要增加對其他節點的通信,只需通過服務名稱async_call即可。

  定義通信的msg:

  1. struct user_online_t 
  2.     struct in_t: public msg_i 
  3.     { 
  4.         in_t(): 
  5.             msg_i("user_online_t::in_t"
  6.         {} 
  7.         string encode() 
  8.         { 
  9.             return (init_encoder() << uid).get_buff(); 
  10.         } 
  11.         void decode(const string& src_buff_) 
  12.         { 
  13.             init_decoder(src_buff_) >> uid; 
  14.         } 
  15.         long uid; 
  16.     }; 
  17.     struct out_t: public msg_i 
  18.     { 
  19.         out_t(): 
  20.             msg_i("user_online_t::out_t"
  21.         {} 
  22.         string encode() 
  23.         { 
  24.             return (init_encoder() << value).get_buff(); 
  25.         } 
  26.         void decode(const string& src_buff_) 
  27.         { 
  28.             init_decoder(src_buff_) >> value; 
  29.         } 
  30.         bool value; 
  31.     }; 
  32. }; 
  33. struct force_user_offline_t 
  34.     struct in_t: public msg_i 
  35.     { 
  36.         in_t(): 
  37.             msg_i("force_user_offline_t::in_t"
  38.         {} 
  39.         string encode() 
  40.         { 
  41.             return (init_encoder() << uid).get_buff(); 
  42.         } 
  43.         void decode(const string& src_buff_) 
  44.         { 
  45.             init_decoder(src_buff_) >> uid; 
  46.         } 
  47.        long uid; 
  48.     }; 
  49.     struct out_t: public msg_i 
  50.     { 
  51.         out_t(): 
  52.             msg_i("force_user_offline_t::out_t"
  53.         {} 
  54.        string encode() 
  55.         { 
  56.             return (init_encoder() << value).get_buff(); 
  57.         } 
  58.         void decode(const string& src_buff_) 
  59.         { 
  60.             init_decoder(src_buff_) >> value; 
  61.         } 
  62.         bool value; 
  63.     }; 
  64. }; 

GatewayServer 通知SessionServer 用戶上線,并提供強制用戶下線的接口:

  1. class gateway_server_t 
  2. public
  3.     void force_user_offline(force_user_offline_t::in_t& in_msg_, rpc_callcack_t<force_user_offline_t::out_t>& cb_) 
  4.     { 
  5.         //! close user socket 
  6.         force_user_offline_t::out_t out; 
  7.         out.value = true
  8.         cb_(out); 
  9.     } 
  10. }; 
  11. gateway_server_t gateway_server; 
  12. singleton_t<msg_bus_t>::instance().create_service("gateway_server", 1) 
  13.             .bind_service(&gateway_server) 
  14.             .reg(&gateway_server_t::force_user_offline); 
  15. user_online_t::in_t in; 
  16. in.uid = 520; 
  17. singleton_t<msg_bus_t>::instance() 
  18.     .get_service_group("session_server"
  19.     ->get_service(1) 
  20.     ->async_call(in, callback_TODO); 

SessionServer 提供用戶上線接口,可能會調用GatewayServer 的接口強制用戶下線。

  1. class session_server_t 
  2. public
  3.     void user_login(user_online_t::in_t& in_msg_, rpc_callcack_t<user_online_t::out_t>& cb_) 
  4.     { 
  5.         //! close user socket 
  6.         user_online_t::out_t out; 
  7.         out.value = true
  8.         cb_(out); 
  9.     } 
  10. }; 
  11. session_server_t session_server; 
  12. singleton_t<msg_bus_t>::instance().create_service("session_server", 1) 
  13.             .bind_service(&session_server) 
  14.             .reg(&session_server_t::user_login); 
  15. force_user_offline_t::in_t in; 
  16. in.uid = 520; 
  17. singleton_t<msg_bus_t>::instance() 
  18.     .get_service_group("gateway_server"
  19.     ->get_service(1) 
  20.     ->async_call(in, callback_TODO); 

多播通信

  和點對點通信一樣,要實現多播,只需要知道目標的服務名稱。特別提一點的是,FFLIB中有服務組的概念。比如啟動了多個場景服務器SceneServer,除了數據不同,二者接口完全相同,有可能只是相同進程的不同實例。在FFLIB框架中把這些服務歸為一個服務組,然后再為每個實例分配索引id。

  假設如下場景,SuperServer 中要實現一個GM接口,通知所有SceneServer 重新加載配置。

  定義通信的msg:

  1. struct reload_config_t 
  2.  
  3.    struct in_t: public msg_i 
  4.    { 
  5.        in_t(): 
  6.            msg_i("reload_config_t::in_t"
  7.        {} 
  8.        string encode() 
  9.        { 
  10.            return (init_encoder()).get_buff(); 
  11.        } 
  12.        void decode(const string& src_buff_) 
  13.        { 
  14.            init_decoder(src_buff_); 
  15.        } 
  16.   }; 
  17.    struct out_t: public msg_i 
  18.    { 
  19.       out_t(): 
  20.            msg_i("reload_config_t::out_t"
  21.        {} 
  22.         string encode() 
  23.        { 
  24.            return (init_encoder() << value).get_buff(); 
  25.        } 
  26.        void decode(const string& src_buff_) 
  27.        { 
  28.            init_decoder(src_buff_) >> value; 
  29.        } 
  30.        bool value; 
  31.    }; 

SceneServer 提供重新載入配置接口:

  1. class scene_server_t 
  2. public
  3.     void reload_config(reload_config_t::in_t& in_msg_, rpc_callcack_t<reload_config_t::out_t>& cb_) 
  4.     { 
  5.         //! close user socket 
  6.         reload_config_t::out_t out; 
  7.         out.value = true
  8.         cb_(out); 
  9.     } 
  10. }; 
  11. scene_server_t scene_server; 
  12. singleton_t<msg_bus_t>::instance().create_service("scene_server", 1) 
  13.             .bind_service(&scene_server) 
  14.             .reg(&scene_server_t::reload_config);  

在SuperServer 中如此實現多播(跟準確是廣播,大同小異):

  1. struct lambda_t 
  2.   static void reload_config(rpc_service_t* rs_) 
  3.   { 
  4.           reload_config_t::in_t in; 
  5.           rs_->async_call(in, callback_TODO); 
  6.   } 
  7. }; 
  8. singleton_t<msg_bus_t>::instance() 
  9.     .get_service_group("scene_server"
  10.     ->foreach(&lambda_t::reload_config); 

Map/Reduce

  在游戲中使用Map/reduce 的情形并不多見,本人找到網上最常見的Map/reduce 實例 WordCount。情形如下:有一些文本字符串,統計每個字符出現的次數。

Map操作,將文本分為多個子文本,分發給多個Worker 進程進行統計

Reduce 操作,將多組worker 進程計算的結果匯總

Worker:為文本統計各個字符出現的次數

定義通信消息: 

  1. struct word_count_t 
  2.     struct in_t: public msg_i 
  3.     { 
  4.         in_t(): 
  5.             msg_i("word_count_t::in_t"
  6.         {} 
  7.         string encode() 
  8.         { 
  9.             return (init_encoder() << str).get_buff(); 
  10.         } 
  11.         void decode(const string& src_buff_) 
  12.         { 
  13.             init_decoder(src_buff_) >> str; 
  14.         } 
  15.         string str; 
  16.     }; 
  17.     struct out_t: public msg_i 
  18.     { 
  19.         out_t(): 
  20.             msg_i("word_count_t::out_t"
  21.         {} 
  22.         string encode() 
  23.         { 
  24.             return (init_encoder() << value).get_buff(); 
  25.         } 
  26.         void decode(const string& src_buff_) 
  27.         { 
  28.             init_decoder(src_buff_) >> value; 
  29.         } 
  30.        map<charint> value; 
  31.     }; 
  32.  
  33. }; 

定義woker的接口:

  1. class worker_t 
  2. public
  3.     void word_count(word_count_t::in_t& in_msg_, rpc_callcack_t<word_count_t::out_t>& cb_) 
  4.     { 
  5.         //! close user socket 
  6.         word_count_t::out_t out; 
  7.         for (size_t i = 0; i < in_msg_.str.size(); ++i) 
  8.         { 
  9.             map<intint>::iterator it = out.value.find(in_msg_.str[i]); 
  10.             if (it != out.value.end()) 
  11.             { 
  12.                 it->second += 1; 
  13.             } 
  14.             else 
  15.             { 
  16.                 out.value[in_msg_.str[i]] = 1; 
  17.             } 
  18.         } 
  19.         cb_(out); 
  20.     } 
  21. }; 
  22. worker_t worker; 
  23.    for (int i = 0; i < 5; ++i) 
  24.     { 
  25.        singleton_t<msg_bus_t>::instance().create_service("worker", 1) 
  26.             .bind_service(&worker) 
  27.             .reg(&worker_t::word_count); 
  28.     } 

模擬Map/reduce 操作:

  1. struct lambda_t 
  2.     static void reduce(word_count_t::out_t& msg_, map<intint>* result_, size_t* size_) 
  3.     { 
  4.         for (map<intint>::iterator it = msg_.value.begin(); it != msg_.value.end(); ++it) 
  5.         { 
  6.             map<intint>::iterator it2 = result_->find(it->first); 
  7.             if (it2 != result_->end()) 
  8.             { 
  9.                 it2->second += it->second; 
  10.             } 
  11.             else 
  12.             { 
  13.                 (*result_)[it->first] = it->second; 
  14.             } 
  15.         } 
  16.         if (-- size_ == 0) 
  17.         { 
  18.             //reduce end!!!!!!!!!!!!!!!! 
  19.             delete result_; 
  20.             delete size_; 
  21.         } 
  22.     } 
  23.     static void do_map(const char** p, size_t size_) 
  24.     { 
  25.         map<intint>* result  = new map<intint>(); 
  26.        size_t*    dest_size   = new size_t(); 
  27.         *dest_size = size_; 
  28.         for (size_t i = 0; i < size_; ++i) 
  29.         { 
  30.             word_count_t::in_t in; 
  31.             in.str = p[i]; 
  32.             singleton_t<msg_bus_t>::instance() 
  33.                 .get_service_group("worker"
  34.                 ->get_service(1 + i % singleton_t<msg_bus_t>::instance().get_service_group("worker")->size()) 
  35.                ->async_call(in, binder_t::callback(&lambda_t::reduce, result, dest_size)); 
  36.         } 
  37.     } 
  38. }; 
  39. const char* str_vec[] = {"oh nice""oh fuck""oh no""oh dear""oh wonderful""oh bingo"}; 
  40. lambda_t::do_map(str_vec, 6); 

總結:

FFLIB 使進程間通信更容易

source code:  https://ffown.googlecode.com/svn/trunk

原文鏈接:http://www.cnblogs.com/zhiranok/archive/2012/08/08/fflib_tutorial.html

 

【編輯推薦】

 

責任編輯:彭凡 來源: 博客園
相關推薦

2012-08-08 09:32:26

C++多進程并發框架

2025-07-02 01:00:00

2011-07-15 00:47:13

C++多態

2011-07-14 17:45:06

CC++

2017-06-30 10:12:46

Python多進程

2011-07-13 18:24:18

C++

2011-07-10 15:26:54

C++

2022-04-01 13:10:20

C++服務器代碼

2015-04-21 13:37:44

Google開源CC++版

2023-11-22 12:25:05

C++RTTI

2020-07-30 12:40:35

CC++編程語言

2010-07-15 12:51:17

Perl多進程

2024-12-27 08:11:44

Python編程模式IO

2010-02-01 10:54:37

C++框架

2023-12-13 10:51:49

C++函數模板編程

2023-11-28 11:51:01

C++函數

2024-02-01 00:10:21

C++PIMPL編程

2024-09-29 10:39:14

并發Python多線程

2024-01-03 10:03:26

PythonTCP服務器

2024-03-29 06:44:55

Python多進程模塊工具
點贊
收藏

51CTO技術棧公眾號

www.欧美| 色影院视频在线| 国产日韩亚洲欧美精品| 亚洲美女精品久久| 五月花丁香婷婷| 在线黄色网页| 久久先锋资源网| 成人精品一区二区三区| 日韩精品一区二区在线播放| 成人一二三区| 精品国产123| 999精品视频在线| 亚洲区欧洲区| 欧美激情资源网| 国产精品日韩一区二区| www.五月婷婷.com| 在线日韩电影| 久久精品99国产精品酒店日本| 先锋影音网一区| 亚洲国产欧美另类| 开心九九激情九九欧美日韩精美视频电影 | 91精品蜜臀在线一区尤物| 精品视频在线观看一区| 午夜视频在线| 久久综合一区二区| 国产99视频精品免费视频36| 中国黄色一级视频| 亚洲看片免费| 九九九热精品免费视频观看网站| 在线观看日本一区二区| 日产福利视频在线观看| 亚洲欧美日韩小说| 午夜一区二区三区| 天天舔天天干天天操| 国产精品一区二区91| 国产精品午夜国产小视频| 亚洲免费在线视频观看| 亚洲色图网站| 精品国产一区二区三区久久狼5月| 一本一道久久a久久综合蜜桃| 中文字幕在线观看日本| 91在线观看免费视频| 亚洲一区久久久| 91国偷自产中文字幕久久| 日韩高清欧美激情| 日韩av电影手机在线观看| www.国产成人| 一区免费在线| 91精品成人久久| 国产五月天婷婷| 亚洲第一伊人| 色综合91久久精品中文字幕| 日本一级特级毛片视频| 日韩国产一区二区| www日韩欧美| 综合五月激情网| 在线精品小视频| 久热精品视频在线| 亚洲一级生活片| 亚洲澳门在线| 久久精品亚洲一区| 少妇被躁爽到高潮无码文| 亚洲色图网站| 欧美激情中文网| 日产精品久久久| 久久久久国产一区二区| 国产成人精品久久| 一区二区视频在线免费观看| 久久电影网站中文字幕| 91精品国产99久久久久久红楼 | 色噜噜偷拍精品综合在线| 久久久久久久午夜| 成人天堂yy6080亚洲高清| 日本韩国视频一区二区| 日本肉体xxxx裸体xxx免费| 亚洲精品一区av| 欧美成人猛片aaaaaaa| 青青草视频网站| 免费成人av| 中文字幕综合一区| 日韩a级片在线观看 | 亚洲毛片在线观看| 精品少妇人妻一区二区黑料社区 | 91精品国产美女浴室洗澡无遮挡| 欧美一区二区三区爽大粗免费| 香蕉视频免费在线播放| 亚洲视频网在线直播| 免费高清一区二区三区| 欧美电影网站| 欧美一区二区三区在线观看视频 | 亚洲毛茸茸少妇高潮呻吟| 韩国女同性做爰三级| 99精品美女| 91禁国产网站| 国产美女明星三级做爰| 99久久精品国产毛片| 亚洲国产一区二区三区在线播| 性感美女视频一二三| 国产欧美一区二区精品性色| 无码人妻精品一区二区三区99v| 成人性爱视频在线观看| 亚洲精品欧美在线| 玩弄japan白嫩少妇hd| 日韩精品一级| 尤物yw午夜国产精品视频明星| 亚洲第一成人网站| 91精品国产自产拍在线观看蜜| 色狠狠久久aa北条麻妃| 亚洲国产精一区二区三区性色| 国产精品大片| 国产精品偷伦视频免费观看国产| 国产精品xxxxxx| 国产91精品一区二区麻豆亚洲| 亚洲自拍偷拍一区| 国产永久免费高清在线观看视频| 久久久夜色精品亚洲| 精品一区二区三区毛片| 色豆豆成人网| 日韩av在线一区二区| 尤物在线免费视频| 日本va欧美va欧美va精品| 国产精品美女xx| 国产美女在线观看| 精品视频一区三区九区| 精品无码人妻一区| 亚洲国产高清一区| 99视频免费观看| 午夜小视频在线| 欧美偷拍一区二区| 中文幕无线码中文字蜜桃| 尤物精品在线| 99九九视频| 国产三区视频在线观看| 欧美日韩国产区一| 手机看片国产日韩| 美日韩一区二区| 三区精品视频| 日韩一级二级| 一区二区三区美女xx视频| 一区二区三区在线观看av| av动漫一区二区| 国产精品久久..4399| 超碰97久久国产精品牛牛| 九九久久综合网站| 国产夫妻自拍av| 亚洲精品日日夜夜| 国产精久久久久| 亚洲欧美一级二级三级| 91一区二区三区| 精精国产xxxx视频在线中文版| 一本大道久久a久久综合婷婷| 中文字幕av专区| 日韩一区二区在线| 国产精品久久久久久久久久 | 精品91久久久| 不卡一卡二卡三乱码免费网站| 日本精品一区| 中文另类视频| 日韩中文在线中文网三级| 中文 欧美 日韩| 国产精品美女www爽爽爽| 另类小说第一页| 99精品综合| 91久久极品少妇xxxxⅹ软件| 蜜臀av国内免费精品久久久夜夜| 精品视频1区2区| 中日韩一级黄色片| 国产乱淫av一区二区三区| 人人妻人人澡人人爽欧美一区| 日韩欧美精品一区二区三区| 亚洲精品乱码久久久久久金桔影视| 免费中文字幕日韩| 国产福利91精品一区二区三区| 色一情一乱一伦一区二区三区| 国产高清自产拍av在线| 日韩电影免费观看在线观看| 精品免费囯产一区二区三区| 国产欧美日韩激情| 国产成人强伦免费视频网站| 亚洲毛片av| 日本一区免费看| 国产一区二区三区免费在线| 66m—66摸成人免费视频| 免费国产在线观看| 制服丝袜亚洲色图| 国产成人在线免费视频| 国产精品伦一区| 亚洲精品久久一区二区三区777| 一区二区在线| 国产综合第一页| 国产精品亚洲成在人线| 欧美另类99xxxxx| 男人的天堂在线| 日韩欧美中文字幕公布| 高清乱码免费看污| 一区二区三区在线看| 一本加勒比北条麻妃| 国产一区二区三区蝌蚪| 国产免费一区二区三区视频| 国产精品毛片久久| 另类小说综合网| 国产一区二区av在线| 欧美最猛性xxxxx(亚洲精品)| 日韩欧美在线番号| 欧美一区二区三区四区在线观看 | 亚洲一本大道在线| 97超碰在线免费观看| 国内精品在线播放| 免费裸体美女网站| 激情成人综合| 中文一区一区三区免费| 婷婷综合成人| 亚洲影视中文字幕| 日韩中文视频| 欧美在线性爱视频| 精品精品导航| 欧美成人亚洲成人| 1024免费在线视频| 亚洲精品一区二区在线| 黄色av网址在线| 3751色影院一区二区三区| 探花国产精品一区二区| 欧美日韩裸体免费视频| 国产亚洲精品码| 亚洲免费观看视频| 免费精品在线视频| 国产日韩欧美制服另类| 中文字幕在线观看网址| 成人av网站在线观看免费| www.色.com| 精品一区二区在线看| 国产高清视频网站| 日韩av高清在线观看| 国产91对白刺激露脸在线观看| 日韩国产一区二区三区| 欧洲精品国产| 欧美禁忌电影网| 欧美日韩国产精品一卡| 免费成人三级| 精品免费二区三区三区高中清不卡 | 亚州av日韩av| 国产美女精品久久久| 一区二区在线视频观看| 成人激情春色网| 日日狠狠久久| 91免费在线视频网站| 国产精品一区二区美女视频免费看 | 亚洲国产99精品国自产| 后进极品白嫩翘臀在线视频| 日韩欧美电影一区| 亚洲AV无码乱码国产精品牛牛| 91久久久免费一区二区| 天天射天天干天天| 欧美日韩综合一区| 一区二区视频网站| 91精品黄色片免费大全| 国产99久久九九精品无码免费| 色综合久久综合| 91video| 欧美日韩一区在线| 国产色片在线观看| 欧美成人免费网站| 青青草娱乐在线| 在线观看欧美日韩| 成人日日夜夜| 97精品在线观看| 亚洲综合电影| 国产精品一区二区三区免费视频| av中文资源在线资源免费观看| 在线性视频日韩欧美| 日韩黄色影院| 欧美日韩国产999| 狼人综合视频| 国产精品国产亚洲伊人久久| 亚洲伦理久久| 含羞草久久爱69一区| 国产精品三级| 成人在线观看毛片| 久久精品五月| 天天影视色综合| 99久久精品国产精品久久| 蜜桃无码一区二区三区| 亚洲欧美一区二区视频| 日韩欧美三级在线观看| 日本黄色一区二区| 99国产精品久久久久99打野战| 欧亚洲嫩模精品一区三区| 国产精品嫩草影院桃色| 精品国产99国产精品| 成年人在线视频免费观看| 欧美精品一区二区免费| 中文字幕色婷婷在线视频| 成人a免费视频| 群体交乱之放荡娇妻一区二区| 国产乱码精品一区二区三区日韩精品 | 婷婷色综合网| 97国产在线播放| 九九视频精品免费| 中文在线永久免费观看| 国产精品二三区| 可以在线观看av的网站| 8x8x8国产精品| 国产日本在线视频| 久久久人成影片一区二区三区观看 | 国产h视频在线播放| 精品在线免费视频| 蜜桃精品成人影片| 悠悠色在线精品| 中文字幕丰满人伦在线| 日韩成人中文字幕| 久久国产精品一区| 国产91在线播放| 农村少妇一区二区三区四区五区 | 午夜黄色小视频| 日韩视频免费中文字幕| 日韩在线免费| 国产一区视频观看| 一区二区影视| 中文字幕一区久久| 国产欧美一区二区精品性| 久久艹免费视频| 欧美一区二区三区白人| yiren22综合网成人| 日本高清视频精品| 国产精品自在| 久久av高潮av| 国产在线精品一区二区夜色| 国产黄色录像视频| 一本大道av一区二区在线播放| 欧美高清69hd| 亚洲区中文字幕| 欲香欲色天天天综合和网| 国产精品裸体一区二区三区| 国产精品videossex久久发布| 国产精品无码人妻一区二区在线| 香蕉久久久久久久av网站| 久久久久久久久久影视| 亚洲蜜臀av乱码久久精品| a片在线免费观看| 一区二区三区精品99久久| 成人mm视频在线观看| 日韩久久不卡| 爽好多水快深点欧美视频| 亚欧精品视频一区二区三区| 欧美图区在线视频| 婷婷成人激情| 91麻豆国产精品| 午夜精品影院| 亚洲欧美日韩色| 亚洲成a人v欧美综合天堂| 黄色a在线观看| 欧美一级大胆视频| 欧美理论视频| 777一区二区| 亚洲欧美日韩国产中文在线| japanese国产| 欧美极品美女电影一区| 激情小说亚洲图片| 男女高潮又爽又黄又无遮挡| 久久久精品黄色| 中文字幕一区二区在线视频| 久久精品夜夜夜夜夜久久| 涩涩屋成人免费视频软件 | 欧美在线资源| 免费啪视频在线观看| 黄色成人av网| 国产youjizz在线| 成人字幕网zmw| 黑人一区二区三区四区五区| 完美搭档在线观看| 91黄色免费观看| 久久精品视频免费看| 国产精品夜夜夜一区二区三区尤| 久久裸体网站| 日本少妇一区二区三区| 亚洲高清在线视频| 成年人视频免费在线观看| 91精品综合久久久久久五月天| 不卡日本视频| 国产成人精品综合久久久久99 | 97精品久久久久中文字幕| 老熟妇仑乱一区二区av| 日韩在线视频导航| 另类视频一区二区三区| 免费在线观看亚洲视频| 国产精品成人一区二区三区夜夜夜| 久久精品久久久久久久| 久久久国产影院| 日韩激情啪啪| 欧美激情第3页| 姬川优奈aav一区二区| av免费在线一区二区三区| 成人羞羞视频免费| 青草av.久久免费一区| 久久综合综合久久| 一区二区三欧美| 噜噜噜狠狠夜夜躁精品仙踪林| 日韩 欧美 视频| 中文字幕欧美国产| 涩涩视频免费看|