免费国产精品自在自线-91精品国产色综合久久久浪潮-99热久久免费频精品-国产精品国模在线观看-久久亚洲国产精品成人?V秋霞-久久国产一级A片免费播放-亚洲国产欧洲综合97久久-久久国产白嫩美女呻吟高潮

ARTICLE DETAIL

資訊詳情

深耕商務建站與企業(yè)官網(wǎng)運營的一線實戰(zhàn)洞察。

Java手寫DHCP服務器:報文解析與租約管理的完整實踐

Java手寫DHCP服務器:報文解析與租約管理的完整實踐 簡介面向DHCP協(xié)議與Java網(wǎng)絡編程開發(fā)者提供一套可直接運行的DHCP服務器與客戶端源代碼適合用于課程設計、畢業(yè)設計以及企業(yè)內(nèi)網(wǎng)管理工具的二次開發(fā)參考。壓縮包共84個文件大小僅186KB其中包含16個Java源文件作為核心實現(xiàn)代碼64個HTML格式的Javadoc頁面用于查閱類與接口說明另含CSS樣式、properties配置和GIF圖片等輔助文件整體結(jié)構清晰便于按需取用。代碼完整實現(xiàn)了DHCP發(fā)現(xiàn)、提供、請求、確認四個階段讀者可學習到基于UDP廣播的報文交互、BOOTP協(xié)議的編解碼方式以及服務器端多線程并發(fā)處理和IP地址池的動態(tài)分配策略。通過閱讀源碼和文檔既能掌握DatagramSocket、NIO等網(wǎng)絡編程技巧也能理解真實協(xié)議落地時的異常處理、配置存儲等工程問題為深入網(wǎng)絡協(xié)議開發(fā)打下基礎。截至當前已有632人學習使用是一份實用且輕量的協(xié)議源碼學習資料。1. 當你的設備拿不到 IPJava 手寫 DHCP 到底在做什么排查網(wǎng)絡時最讓人血壓飆升的場景之一就是終端瘋狂廣播 DHCP Discover 卻始終收不到 Offer。抓包一看服務器根本沒回應或者回應了但報文格式錯得離譜。這時候你如果能有一份 Java 實現(xiàn)的 DHCP 源代碼在手可以直接在 JVM 里跑起來調(diào)試比反復翻 RFC 2131 和路由器日志要直觀得多。DHCP 協(xié)議本身不復雜復雜的是 UDP 廣播、報文選項解析、租約狀態(tài)機這些細節(jié)在 Java 里怎么落地。這個方向的價值在于它不是讓你去替代現(xiàn)成的 dhcpd 或路由器內(nèi)置服務而是幫你理解協(xié)議交互的每一幀報文、每一個狀態(tài)轉(zhuǎn)換。無論是做網(wǎng)絡設備模擬器、接入認證系統(tǒng)、還是在測試環(huán)境里模擬 DHCP 攻擊與防護場景一份能跑的 Java 源碼都是最直接的學習和調(diào)試工具。適合的人群是網(wǎng)絡協(xié)議棧開發(fā)者、物聯(lián)網(wǎng)設備接入層的工程師以及那些在面試里被問到「DHCP 報文是怎么組裝和解析的」之后想弄個明白的 Java 后端。2. 實現(xiàn)前必須吃透的 DHCP 報文結(jié)構從 BOOTP 到選項域的字節(jié)級拆解2.1 為什么 DHCP 報文要用字節(jié)數(shù)組硬拼而不是 JSON 或?qū)ο罅骱芏嗳藙偵鲜謺r第一反應是我需要一個 DHCP 報文類把 op、htype、xid 這些字段用 Java 對象表示然后序列化。這個方向沒錯但注意 DHCP 報文在網(wǎng)絡上傳輸時就是純字節(jié)流而且它沒有現(xiàn)成的 Java 序列化協(xié)議必須按 RFC 2131 規(guī)定的固定偏移量逐字節(jié)塞進去。報文頭固定部分只有 236 字節(jié)從 op 字段到 sname 的 64 字節(jié)加上 file 的 128 字節(jié)后面接著的是 64 字節(jié)的 options 區(qū)。這里的第一個坑是你用的 ByteBuffer 是 Big-Endian 字節(jié)序而 DHCP 報文里絕大多數(shù)多字節(jié)字段比如 yiaddr、ciaddr都是網(wǎng)絡字節(jié)序也就是 Big-Endian。這意味著直接調(diào)用ByteBuffer.wrap()然后putInt()是安全的但如果你為了取某個字段用getInt()時忘記考慮緩沖區(qū)位置就會讀到錯位的數(shù)據(jù)。常見的實現(xiàn)方式是寫一個專門的 DHCPPacket 類內(nèi)部持有byte[] packet對外提供getOp()、setOp()之類的訪問方法。這樣在解碼時不需要反復 copy 字節(jié)直接對底層數(shù)組按偏移量操作。我一般還會內(nèi)置一個parseOptions()方法把 options 區(qū)從 240 字節(jié)偏移開始循環(huán)讀取先讀 option code1 字節(jié)如果是 0 是 padding如果是 255 是 end否則讀長度再讀值。這個循環(huán)邏輯是整個解析器最容易出錯的地方原因在于你必須在讀 code 前判斷剩余長度是否至少為 2code len否則直接拋異常。2.2 報文類型選項53 號選項和事務 ID區(qū)分 Discover / Offer / Request 的分水嶺如果你只是在網(wǎng)絡上抓包看源端口 68 和 67 就能猜出大概。但代碼要處理的是具體邏輯分支Discover類型 1、Offer類型 2、Request類型 3、Ack類型 5、Nak類型 6這些行為全靠 options 區(qū)里的第 53 號選項區(qū)分。byte類型取值有符號的問題在這里就暴露了。Java 里的byte是 -128 到 127而 DHCP 報文里某個 code 可能是 0x80 甚至 0xFF。如果你寫int code buffer[index]你會得到一個負數(shù)比如 0xFF 變成 -1。正確做法是int code buffer[index] 0xFF。這一點不著重說明后面的報文解析一定會翻車。事務 ID 是 xid 字段4 字節(jié)由客戶端隨機生成。服務器在回復時原樣帶回 xid客戶端用它匹配請求和響應。在 Java 里你用SecureRandom.nextLong()然后截取低 32 位就可以。注意不要用Math.random()去生成因為它在高并發(fā)或多次快速重啟時可能重復導致客戶端把舊 Offer 當成新 Offer。2.3 租約時間、子網(wǎng)掩碼、網(wǎng)關和 DNS選項的讀寫順序決定兼容性拿到選項值之后你要按標準順序把它們編碼回去。常見的順序是53報文類型、 server identifier54、 lease time51、 subnet mask1、 router3、 dns6。有些舊客戶端對選項順序敏感比如 Windows 老版本 DHCP 客戶端必須把 53 號選項放在最前面否則直接丟棄報文。選項值里額外要留意的是 IP 地址數(shù)組的對齊router 選項3和 DNS 選項6都是可以包含多個 IP 的列表以 4 字節(jié)為間隔。讀取時要循環(huán)讀滿length才算完不能只讀第一個。寫入時同樣按 4 字節(jié)一組。租約時間51 號是 4 字節(jié)整數(shù)單位是秒不能錯成毫秒否則客戶端會在幾小時內(nèi)以為租約到期瘋狂續(xù)租。提示寫一個獨立的DhcpOption類字段包括 code、length、byte[] data。解析時先把 options 全部拆成若干 DhcpOption 對象再按 code 去查而不是在讀循環(huán)里當場做分支處理。這樣的設計避免后續(xù)新增選項時改一大段解析代碼。3. 從零寫最小 DHCP 服務器UDP 廣播收發(fā)與租約管理的完整 Java 代碼3.1 綁定 67 端口監(jiān)聽廣播Socket 選項和網(wǎng)絡接口選擇DHCP 服務器監(jiān)聽 UDP 67 端口客戶端從 68 端口發(fā)送。在 Java 里這不是普通的DatagramSocket因為你希望收到發(fā)往 255.255.255.255 的廣播包。先看最精簡的監(jiān)聽代碼import java.net.DatagramPacket; import java.net.DatagramSocket; import java.net.InetAddress; import java.net.SocketException; public class DhcpServerSocket { private DatagramSocket socket; private InetAddress broadcastAddress; public DhcpServerSocket(int port, String broadcastIp) throws SocketException { // 廣播地址由網(wǎng)卡配置決定通常取 255.255.255.255 或子網(wǎng)定向廣播 this.broadcastAddress InetAddress.getByName(broadcastIp); // 第一個參數(shù)為端口第二個參數(shù)為綁定的本地地址null 表示所有地址 this.socket new DatagramSocket(port, null); // 允許廣播這步不做會收不到 255.255.255.255 的報文 socket.setBroadcast(true); // 加大接收緩沖區(qū)防止瞬間大量 Discover 導致丟包 socket.setReceiveBufferSize(64 * 1024); } public DatagramPacket receive() throws Exception { byte[] buf new byte[1500]; DatagramPacket packet new DatagramPacket(buf, buf.length); socket.receive(packet); return packet; } public void send(byte[] data, int length, InetAddress destIp, int destPort) throws Exception { DatagramPacket reply new DatagramPacket(data, length, destIp, destPort); // 目標端口固定為 68客戶端監(jiān)聽端口 socket.send(reply); } }參數(shù)說明new DatagramSocket(port, null)中的 null 代表綁定到所有網(wǎng)卡。如果你的機器有多塊網(wǎng)卡只希望在特定網(wǎng)卡上服務這里可以傳InetAddress.getByName(192.168.1.100)。setBroadcast(true)是為了能夠向廣播地址發(fā)送回復包不設置就只能單播。監(jiān)聽端口時如果提示Address already in use在 Linux 上可以用setsockopt的 SO_REUSEADDR 解決但 Java 里沒有直接暴露這個選項最簡單的辦法是確認沒有其他 DHCP 服務占著 67 端口。3.2 解析 Discover 報文并組裝 Offer一個完整的請求處理鏈路收到 Discover 后你要做的是讀取客戶端 MACchaddr 字段從偏移 28 開始16 字節(jié)根據(jù) MAC 查租約表分配一個空閑地址然后組裝 Offer 報文。下面這段代碼集中展示了核心處理流程public class DhcpRequestHandler { // 租約表MAC - IP 和過期時間 private final MapString, Lease leaseMap new ConcurrentHashMap(); // 可用 IP 池用隊列模擬分配 private final QueueString addressPool; public DhcpRequestHandler(ListString poolAddresses) { addressPool new LinkedList(poolAddresses); // 啟動一個定時線程定期清理過期租約 Executors.newSingleThreadScheduledExecutor() .scheduleAtFixedRate(this::cleanupExpiredLeases, 60, 60, TimeUnit.SECONDS); } public byte[] handleDiscover(byte[] requestPacket) { // 1. 解析客戶端 MAC包偏移 28 處長度 6但 chaddr 字段是 16 字節(jié) byte[] chaddr Arrays.copyOfRange(requestPacket, 28, 44); String macKey toMacString(chaddr); String offeredIp leaseMap.containsKey(macKey) ? leaseMap.get(macKey).ipAddress : allocateIp(macKey); if (offeredIp null) { return null; // 地址池耗盡 } // 2. 構造 Offer 報文的基礎字段 byte[] response new byte[240]; // 只占固定頭選項在后面追加 response[0] (byte) 0x02; // op: BOOTREPLY response[1] (byte) 0x01; // htype: Ethernet response[2] (byte) 0x06; // hlen: MAC 地址長度 // 復制 xid客戶端用這個字段匹配 Offer System.arraycopy(requestPacket, 4, response, 4, 4); // yiaddr 字段從偏移 16 開始填入分配的 IP byte[] ipBytes ipToBytes(offeredIp); System.arraycopy(ipBytes, 0, response, 16, 4); // 復制客戶端 MAC 到 chaddr System.arraycopy(chaddr, 0, response, 28, 6); // 3. 追加 options53 號報文類型 Offer、54server id、1掩碼、51租約 ByteBuffer options ByteBuffer.allocate(256); options.put((byte) 53).put((byte) 1).put((byte) 2); // Offer 類型 options.put((byte) 54).put((byte) 4) .put(ipToBytes(192.168.1.1)); // 服務器自身 IP options.put((byte) 1).put((byte) 4) .put(ipToBytes(255.255.255.0)); options.put((byte) 51).put((byte) 4) .putInt(7200); // 租約 2 小時 options.put((byte) 255); // End 選項 byte[] responseWithOptions new byte[240 options.position()]; System.arraycopy(response, 0, responseWithOptions, 0, 240); System.arraycopy(options.array(), 0, responseWithOptions, 240, options.position()); return responseWithOptions; } private String allocateIp(String mac) { // 簡化實現(xiàn)從隊列取地址不考慮釋放問題 String ip addressPool.poll(); if (ip ! null) { leaseMap.put(mac, new Lease(ip, System.currentTimeMillis() 7200_000L)); } return ip; } }邏輯說明handleDiscover的輸入是整個 UDP 報文的有效載荷字節(jié)數(shù)組。第一步解析 chaddr 時注意只取前 6 字節(jié)做 MAC因為 Ethernet 的 hlen 是 6但報文里該字段長度是 16 字節(jié)剩余部分為零填充。response[0] 0x02表示這是 BOOTREPLY而請求包對應值是 0x01BOOTREQUEST。xid 必須從請求包偏移 4 的位置復制 4 字節(jié)否則響應對不上客戶端。Options 的組裝用了ByteBuffer且每個 option 的格式是 code length value。長度字段必須是實際字節(jié)數(shù)比如 51 號 option 的租約時間是 4所以先put((byte) 4)再putInt(7200)。positon()返回當前寫入位置作為 options 區(qū)總長度。這種寫法比逐字節(jié)往一個byte[]里塞要清晰調(diào)試時也方便中途打印。3.3 收到 Request 后回 Ack狀態(tài)機里的最后一步Offer 發(fā)出后客戶端會廣播一個 Request類型為 3。這時候服務器要做的是確認該 Request 中的 requested IP50 號選項確實是本服務器分配的然后回復 Ack。下面代碼展示如何處理 Requestpublic byte[] handleRequest(byte[] requestPacket) { // 1. 從 options 里找到 50 號選項取請求的 IP ByteBuffer options ByteBuffer.wrap(requestPacket, 240, requestPacket.length - 240); String requestedIp null; String serverIdentifier null; while (options.remaining() 0) { int code options.get() 0xFF; if (code 0) { continue; // padding } if (code 255) { break; } int len options.get() 0xFF; byte[] val new byte[len]; options.get(val); if (code 50) { requestedIp bytesToIp(val); // 客戶端請求的地址 } else if (code 54) { serverIdentifier bytesToIp(val); // 客戶端期望的服務器地址 } } // 2. 判斷是否應該由本服務器響應客戶端指定了其他 server id 則忽略 if (serverIdentifier ! null !serverIdentifier.equals(localServerIp)) { return null; } // 3. 校驗地址池里確實有這個地址且未分配給別人 if (!addressPool.contains(requestedIp) !isLeasedToClient(requestedIp)) { return null; } // 4. 組裝 Ack報文類型 5返回分配結(jié)果 byte[] ack buildReply(requestPacket, (byte) 5, requestedIp); return ack; }邏輯說明handleRequest里的循環(huán)解析 options特別要注意options.get()返回的是有符號字節(jié)這里用 0xFF規(guī)避負數(shù)問題。當客戶端拿到 Offer 后會發(fā) Request并把 50 號選項設成自己想要的 IP。如果網(wǎng)絡里有多個 DHCP 服務器同時收到了 Request客戶端會用 54 號選項指定它認可的服務器其他服務器看到 54 號不是自己就直接忽略。這一步邏輯不寫就會出現(xiàn)兩臺服務器同時回 Ack 的沖突場景。3.4 定時清理租約ConcurrentHashMap 怎么和地址池配合實際運行中客戶端釋放地址時的 Release 報文是單播發(fā)給服務器的所以handleRequest方法里還需要處理報文類型 7Release。Release 報文里含客戶端 IPciaddr 字段服務器拿到后把地址放回池子、從租約表刪除。但客戶端可能異常斷電永遠不發(fā) Release所以必須依賴租約過期機制。private void cleanupExpiredLeases() { long now System.currentTimeMillis(); for (Map.EntryString, Lease entry : leaseMap.entrySet()) { if (entry.getValue().expireTime now) { // 地址回收放回隊列尾部允許被重新分配 addressPool.offer(entry.getValue().ipAddress); leaseMap.remove(entry.getKey()); } } }這里的隱患是地址池用ConcurrentHashMap和LinkedList組合本身就不是線程安全的。cleanupExpiredLeases在獨立線程里跑而handleDiscover在主接收線程里也會操作addressPool。解決方式是給地址池操作加鎖或者直接用BlockingQueue并用ConcurrentHashMap記錄租約和到期時間。我在實際項目里會用ConcurrentHashMap存mac - ip的映射再用ConcurrentHashMapString, Long存ip - expireTime清理時同時刪兩個 map分配時用AtomicInteger做輪詢游標而不是直接 poll 隊列因為釋放和過期回收都會動態(tài)往隊列里放地址。private final AtomicInteger cursor new AtomicInteger(0); private final ListString allIps; // 固定列表初始化時排序好 private String allocateIp(String mac) { for (int i 0; i allIps.size(); i) { int idx Math.abs(cursor.getAndIncrement() % allIps.size()); String candidate allIps.get(idx); if (!leaseMap.containsKey(mac) !leasedIpSet.contains(candidate)) { leaseMap.put(mac, new Lease(candidate, System.currentTimeMillis() 7200_000L)); leasedIpSet.add(candidate); return candidate; } } return null; }參數(shù)說明allIps在初始化時從配置的網(wǎng)段展開比如192.168.1.100到192.168.1.200生成 101 個地址。cursor每次分配時累加再取模實現(xiàn)輪詢分配避免每次都從列表頭部開始找導致早期地址快被用光、后續(xù)地址閑置。leasedIpSet是一個SetString用來快速判斷地址是否已被占用否則每次都要遍歷租約表。4. 客戶端實現(xiàn)與抓包驗證三步確認你的 DHCP 協(xié)議棧沒寫歪4.1 構造 Discover 報文的細節(jié)68 端口和全零地址客戶端代碼比服務器少很多核心是構造 Discover 并發(fā)送到 255.255.255.255:67。關鍵約束是源端口必須是 68源 IP 可以是 0.0.0.0因為客戶端此時還沒有 IP。public class DhcpClient { private DatagramSocket socket; public void startDiscovery() throws Exception { socket new DatagramSocket(68, InetAddress.getByName(0.0.0.0)); socket.setBroadcast(true); socket.setSoTimeout(5000); // 5 秒收不到就超時 byte[] discover buildDiscoverPacket(); DatagramPacket pkt new DatagramPacket(discover, discover.length, InetAddress.getByName(255.255.255.255), 67); socket.send(pkt); // 等待 Offer,讀到報文后校驗 xid 與自己的匹配 byte[] buf new byte[1500]; DatagramPacket response new DatagramPacket(buf, buf.length); socket.receive(response); parseOffer(buf); } private byte[] buildDiscoverPacket() { byte[] packet new byte[240 4]; packet[0] (byte) 0x01; // BOOTREQUEST packet[1] (byte) 0x01; packet[2] (byte) 0x06; // xid: 4 字節(jié)隨機數(shù) int xid new SecureRandom().nextInt(); packet[4] (byte) (xid 24); packet[5] (byte) (xid 16); packet[6] (byte) (xid 8); packet[7] (byte) xid; // 自己的 MAC假設網(wǎng)卡 MAC 是 01:02:03:04:05:06 byte[] mac new byte[]{(byte) 0x01, (byte) 0x02, (byte) 0x03, (byte) 0x04, (byte) 0x05, (byte) 0x06}; System.arraycopy(mac, 0, packet, 28, 6); // options53 號選項 Discover1 packet[240] (byte) 53; packet[241] (byte) 1; packet[242] (byte) 1; packet[243] (byte) 255; // End return packet; } }邏輯說明new DatagramSocket(68, 0.0.0.0)綁定到 68 端口這樣收到的 Offer 會被操作系統(tǒng)路由到該 socket。xid 的生成用SecureRandom.nextInt()而不是Math.random()是為了避免在多線程場景下的重復性。注意把 xid 拆成 4 個字節(jié)的順序——Java 的 byte 是有符號的xid 24的結(jié)果 0~255賦值給 byte 時 0xFF 會變成 -1但在傳輸中字節(jié)序列是正確的因為二進制表達沒變。實際解析時用 0xFF再拼回 int 即可。4.2 收到 Offer 后如何提取租約信息ip 和 options 的解析順序在parseOffer中要依次做檢查 op 字段是否為 2、xid 是否匹配、拿到 yiaddr偏移 16 起的 4 字節(jié)、掃描 options 找 51 號租約時間和 54 號服務器標識。解析順序別看反了很多人先處理 options 后取 IP就會發(fā)現(xiàn) options 區(qū)的偏移計算有誤。private void parseOffer(byte[] response) { if (response[0] ! (byte) 0x02) { throw new IllegalStateException(不是 BOOTREPLY); } // 檢查 xid 是否匹配這里略去與發(fā)送時保存的 xid 比較 byte[] yiaddr Arrays.copyOfRange(response, 16, 20); String assignedIp InetAddress.getByAddress(yiaddr).getHostAddress(); // 掃描 options int offset 240; while (offset response.length) { int code response[offset] 0xFF; if (code 0) { offset; continue; } if (code 255) break; int len response[offset 1] 0xFF; byte[] value Arrays.copyOfRange(response, offset 2, offset 2 len); if (code 1) { // 子網(wǎng)掩碼 String mask bytesToIp(value); // 后續(xù)計算可用地址范圍會用到 } else if (code 3) { // 網(wǎng)關列表一個選項可能包含多個 IP for (int i 0; i value.length; i 4) { String gateway bytesToIp(Arrays.copyOfRange(value, i, i 4)); } } else if (code 51) { long leaseTimeSec ((long) (value[0] 0xFF) 24) | ((value[1] 0xFF) 16) | ((value[2] 0xFF) 8) | (value[3] 0xFF); // leaseTimeSec 單位是秒 } offset 2 len; } }參數(shù)說明租約時間如果直接用ByteBuffer.wrap(value).getInt()也可以但要注意getInt()會得到有符號 int最長租約 0xFFFFFFFF 會變成 -1。這里我演示了手工拼接的方式結(jié)果用 long 承接。網(wǎng)關選項按 4 字節(jié)一組遍歷時要小心 len 不是 4 的倍數(shù)這種畸形包用value.length / 4作為循環(huán)次數(shù)更穩(wěn)妥。4.3 用 Wireshark 對照驗證你寫的源碼和標準報文差在哪代碼寫完后別急著部署先在本地起服務器再起客戶端用 Wireshark 抓bootp或dhcp過濾。如果要驗證 Java 客戶端發(fā)的 Discover 是否規(guī)范抓包后看這幾個點檢查項正確值/行為常見錯誤源端口68錯寫成 67 或隨機端口目標端口67錯寫成 68op 字段1請求/ 2響應兩個方向搞反xid 一致性請求與響應相同響應時復制偏移搞成 8 或 12options 的 End 標記必須有 255 結(jié)尾漏掉后服務端解析會越界chaddr 填充前 6 字節(jié) MAC后 10 字節(jié)補 0直接 copy 16 字節(jié)導致把雜數(shù)據(jù)帶進去我習慣在寫代碼時加一段 debug 日志每次收到 / 發(fā)出的報文用 HexFormat 或DatatypeConverter.printHexBinary()把前 40 字節(jié)打出來。這樣不依賴 Wireshark 也能在控制臺里對著報文字段偏移人工校驗。提示如果你在 Windows 上跑 Java 服務端收到的廣播包源地址可能是 0.0.0.0而目標地址是 255.255.255.255。如果綁定 67 端口時報SocketException: Permission denied是因為非管理員進程無權綁定 1024 以下端口。開發(fā)時用 6767 端口調(diào)試需要聯(lián)調(diào)時再以管理員權限啟動。5. Java 實現(xiàn) DHCP 的 5 個高頻踩坑點與對應排查手段5.1 報文里大于 127 的字節(jié)變成負數(shù)解析全盤錯亂現(xiàn)象客戶端發(fā)來的 Discover 包服務器讀到選項 code 是負數(shù)比如 -128實際是 0x80然后直接數(shù)組越界或走錯分支。原因Java byte 是有符號類型0x80 到 0xFF 會被解釋為 -128 到 -1。你在int code buffer[offset]時沒做掩碼處理。解決所有從報文里讀單字節(jié)并轉(zhuǎn)成「無符號整數(shù)」的地方統(tǒng)一寫成buffer[offset] 0xFF。不要覺得這行代碼多余特別是在 options 循環(huán)、長度字段和 IP 地址首字節(jié)處。另外在把 int 寫成 byte 時比如packet[240] (byte) 53如果 int 值超過 127必須強轉(zhuǎn)否則編譯不通過。寫一個toUnsignedByte(int)工具方法可以減少重復出錯。5.2 廣播包收不到setBroadcast(true) 漏了或者網(wǎng)卡綁定錯了現(xiàn)象服務器啟動后沒有任何日志客戶端一直顯示發(fā)送成功但等不到 Offer。用 Wireshark 看服務器所在機器發(fā)現(xiàn)根本沒有收到包。原因有兩類。第一類是 Java 的DatagramSocket默認不接收廣播地址的包必須顯式socket.setBroadcast(true)。第二類是服務器綁定的 IP 和客戶端廣播到達的網(wǎng)卡不是同一個。如果機器有 eth0 和 eth1客戶端廣播從 eth1 進來但你綁定的是 eth0 的 IP內(nèi)核同樣會丟包。排查方法先臨時寫一段代碼打印本機所有網(wǎng)卡地址然后把new DatagramSocket(port, null)改成new DatagramSocket(port, InetAddress.getByName(0.0.0.0))保證綁定到所有接口。如果還不行用tcpdump -i any port 67在 Linux 上確認報文是否到達內(nèi)核。5.3 Options 解析越界漏了 padding 和 End 選項的處理現(xiàn)象服務器解析某些客戶端比如老舊設備發(fā)來的請求時代碼直接拋ArrayIndexOutOfBoundsException或讀到一個巨大的 len 值。原因DHCP 報文 options 區(qū)不是每次都恰好填滿 64 字節(jié)。RFC 2131 規(guī)定 options 區(qū)末尾以 255 結(jié)束但在它之前可能有一串值為 0 的 padding 選項。你的循環(huán)如果只看了 255 沒看 0或者認為 len 字段一定是合理的遇到 0 時把 padding 當普通選項的 code 和 len 去讀就會讀到錯亂的字節(jié)。解決循環(huán)里的處理順序必須是讀 code如果 code 0跳過當前字節(jié)繼續(xù)下一個如果 code 255立即結(jié)束否則再讀 len 并跳過 len 字節(jié)。注意不能把 padding 當 code 為 0 的選項因為 padding 沒有 len 字段。另外解析時要用offset 2 len packet.length做邊界保護一旦條件不滿足直接丟棄該包并記日志。5.4 客戶端對 Ack 不買賬Server Identifier 選項寫錯地址現(xiàn)象服務器日志顯示已發(fā)出 AckWireshark 也看到了但客戶端就是報錯或者客戶端狀態(tài)停在 Request 階段不進入 Bound。原因Ack 里必須包含 54 號選項Server Identifier且該值必須是服務器自身的 IP 地址。如果寫成 255.255.255.255 或者 0.0.0.0客戶端按 RFC 就認為這個 Ack 不合法。還有一種情況是服務器有多個 IP寫成了其中某個不是客戶端網(wǎng)關所在網(wǎng)段的地址客戶端可能無法路由這個單播 Ack。解決在組裝 Ack 時用DatagramPacket的getLocalAddress()或提前從網(wǎng)卡讀到的地址確保54號選項的值與收包時客戶端發(fā)來的目標地址段匹配。實在無法確定時用收到 Discover 報文的源地址所在子網(wǎng)推斷服務器該用哪個地址回復。5.5 租約過期后地址沒釋放cleanup 線程跑飛或者占用檢查漏了現(xiàn)象地址池明明只有 50 個地址跑了幾天后全部被占用新設備拿不到 IP。但檢查 DHCP 租約表很多租約早已過期。原因cleanupExpiredLeases方法里刪除 map 條目時沒有同步更新地址池。比如你把leaseMap.remove(entry.getKey())寫了卻忘了把 IP 放回addressPool。還有可能是在移除租約時遍歷的是 entrySet但后面又有新請求往同一個 key 寫入導致 remove 和 put 競爭。解決清理邏輯要和分配邏輯用同一個鎖。我習慣做法是把租約表和地址池封裝成一個LeaseManager類所有方法加synchronized或者直接用ReentrantLock。清理時先標記 IP 釋放再刪租約順序不能反否則中間態(tài)有分配線程可能拿到這個 IP 又被后續(xù)刪除動作誤傷。提示這些坑里前三個是 Java 獨有的后兩個是 DHCP 協(xié)議實現(xiàn)共有的。如果你在做自己的項目建議每解決一個坑就補一條單測比如構造一個含 padding 的畸形報文驗證解析器是否崩潰覆蓋這些場景后改代碼會安心很多。6. 讓實現(xiàn)可以上生產(chǎn)報文一致性校驗與性能壓測的小工具我的習慣是給 DHCP 服務器代碼加一個獨立的「報文自檢」入口用真實的客戶端抓包文件回放而不是每次手動敲命令。流程是先用 Wireshark 把真實環(huán)境的 Discover 和 Request 報文導出為二進制文件然后用 Java 程序讀取每個包并調(diào)用你自己的解析邏輯最后把輸出的 Offer/Ack 再與 Wireshark 里抓到的真實響應逐字節(jié)對比。核心校驗代碼可以寫成一個獨立方法public boolean validatePacket(byte[] packet, int maxLength) { if (packet.length 240 || packet.length maxLength) { return false; } // op 只能是 1 或 2 if ((packet[0] 0xFF) ! 1 (packet[0] 0xFF) ! 2) { return false; } // htype 為 1 時 hlen 必須是 6 if (packet[1] 1 (packet[2] 0xFF) ! 6) { return false; } // 掃描 options驗證每個 option 都不越界 int offset 240; while (offset packet.length) { int code packet[offset] 0xFF; if (code 0) { offset; continue; } if (code 255) break; if (offset 1 packet.length) return false; int len packet[offset 1] 0xFF; if (offset 2 len packet.length) return false; offset 2 len; } return true; }運行單測時我把抓到的包分兩類合法報文和畸形報文。合法報文必須通過校驗畸形報文必須被拒絕。這個校驗器本質(zhì)上就是你的防御性編程的集中體現(xiàn)值很值得維護。有了能跑通的核心邏輯和校驗器下一步建議做一次壓力測試。用循環(huán)線程模擬 500 個客戶端同時啟動ExecutorService pool Executors.newFixedThreadPool(50); CountDownLatch startSignal new CountDownLatch(1); for (int i 0; i 500; i) { final int clientId i; pool.submit(() - { try { startSignal.await(); DhcpClient client new DhcpClient(); client.setMac(randomMac(clientId)); client.startDiscovery(); } catch (Exception e) { System.err.println(client clientId failed: e.getMessage()); } }); } startSignal.countDown(); pool.shutdown();注意這里每個線程都創(chuàng)建獨立DatagramSocket綁定 68 端口這本身就會遇到端口沖突——多個進程不能同時綁同一個端口。所以在壓測時要讓客戶端隨機使用 68 到 70 范圍內(nèi)的端口或者用同一個 socket 串行發(fā)。更實際的做法是直接用服務端日志里的xid去重統(tǒng)計單位時間收到多少個不同 xid 的 Discover再用單線程代碼往服務器灌大量手工構造的 Discover 報文來測試吞吐。最后一個技巧把核心的報文組裝和解析邏輯與網(wǎng)絡收發(fā)解耦。網(wǎng)絡層可以換 Netty 的 DatagramChannel 或者 OIO 實現(xiàn)但解析和組裝是純函數(shù)式的輸入 byte[] 輸出 byte[]。這樣將來想把服務跑在 Vert.x 上或者遷移到 GraalVM 原生鏡像都不需要動協(xié)議代碼。我的個人習慣是任何時候都會以 Wireshark 抓包為最終真理寫完代碼先抓包對比 20 個請求再談可靠性。DHCP 看起來簡單但報文里的每個字節(jié)都有自己的脾氣希望這套實現(xiàn)思路能幫你少走幾個彎路。本文還有配套的精品資源點擊獲取
返回列表
PREV
查看更多資訊
NEXT
返回資訊列表
久青操| 99热只有| 欧美大道不卡| 欧美性生交xXxX久久久| 色综合色色| 婷婷伊人久久综合| 成人色五月天| 99久久99热| 亚洲视频久久| 久青草大香蕉| 国成人网| 99热最新国内| 色婷婷香蕉在线| 深爱五月婷婷| 天天干夜夜想| 五月天综合婷婷| yazhochengrenavwang| 好激情在线综合网| 狠狠五月激情婷婷直播片| 亚洲不卡欧洲| 91色逼| 丁香九月色| 青草五月天| 激情五月天婷婷五月天| 久久99热这里只有精品| 亚洲综合五月| 综合网啪| 久久总和99| 中文在线视频久1| 丁香伊人综合| 99这里只有精彩视频| 丁香花五月天| 9久热这里只有精品| 都市激情蜜桃婷婷五月天 | 五月天激情网图片| 婷婷性福五月天| 99re26视频| 开心五月天私房婷婷| 婷婷欧美激情综合| 亚洲成人免费电影| 精品国产人人爱人人| www.99色| 亚洲狠狠婷婷综合久久久| 亚洲视99| 五月花婷婷最新| 色婷婷黄色网络| 日本精品99| 九九色大香蕉| 五月激情五月丁香| 丁香五月激情视频在线| 噜噜噜噜综合在线| 中文字幕在线播放视频| 做爰丰满少妇1313| 色婷婷丁香社综合| 99热色无码| 大香蕉人妻| 丁香五月婷婷狠狠色| 九热视频| 99热精品一| 久久久人妻门| 久久婷婷五月丁香网| 亚洲精品国产setv| 亚洲成av人影院| 激情内射人妻1区2区3区| 亚洲人妻av伦理| 国产美女无遮挡裸体毛片A片| 五月天激情小说| WWW.国产| 中文字幕成人影视| 极品 少妇 内射| 色小说五月婷婷| 天天爽综合| 激情五月婷婷综合色播小说| 久久久91| 久久久久9久无码视频| 亚洲第二AV| 99狠狠色| 婷婷五月天综合色| 99亚州综合精品成人网| 日日夜夜亚洲一区| 久久er免费视频| 99色在线观看| www.五月丁香| 97香蕉人人在线观看| 婷婷色网站| 狠狠色丁香婷婷综合久久97AV| 丁香六月色婷婷| 色婷婷AAA| 亚洲精品字幕在线观看| 《久久综合九色综合97婷婷| 婷婷激情综合色五月久久,色婷婷丁香花,丁香婷婷五月情天,久久婷婷五月综合色 | 久久这里只| 久久Xx| 99操| 久久99久久99精品免视看婷| 天天日夜夜拍| 亚洲亚洲人成综合网络| 色色色欧美| 激情婷婷啪啪| 亚洲亚洲人成综合网络| 色色免费网站| 婷婷五月六| 三级三久久线久久99久目本WW| 9久热精品在线视频| 久婷婷婷| 婷婷久久五月天| 五月婷婷丁香六月| 亚洲色色五月天| 九九这里有精品视频| 99精品视频网| 97se视频在线| 天天影院色| 国产一二区爆乳_1国产日韩一区二区三-成人AV | 天天操天天操天天操天天操天天操天天操天天操天天操天天操 | 婷婷五月天视频亚洲| 色综合九九| 97超碰色| 丁香六月婷婷色XXXXX| 久久九九国产精品怡红院| 五月天婷婷久草丁香| 五月天自拍视频| 久综合网| 97人人干| 五月天成人在线视频网站| 超碰99热在线观看| 人妻久久久久久久久久久| 九九热最新| 97天堂| 九九视频这里只有精品| 国产亚洲av片| 五月天播播| 韩日另类| www.丁香五月| 五月天久草| 天天久久综合| 男女激情久久| 五月婷婷真爱激情网| 操笔无码| 另类激情综合| 99色综合网| www.爱婷婷.com| 欧亚色色| 欧美内射AAAAAAXXXXX| 一逼色综合| 综合色色色| 91九色超碰| 天天上天天爽| 五月激情四射网站| 五月天停停成人网| 亚州操操| 午夜九九电影| 99热网精品| 99久久丝| 被强行糟蹋的女人A片| a在线观看| 在线视频99| 色欲影香| 色婷五月| 五月天激情子轮| 99超碰欧美| 99视频热| 狠狠综合久久| 国产乱妇乱子在线播视频播放网站| 亚洲婷婷视频| 色五月情| 亚洲日韩欧美综合VA| 国产精品成人网站| 色色婷婷丁香| 天天碰天天插天天操| 丁香五月之久操视频| 国产,欧美,日韩,性爱| 久久天堂女人| 操99| 五月丁香淫淫婷婷婷| 综合色婷婷| 亚洲视频操| 亚洲情色一区| 99婷婷狠狠成为人免费视频| 激情久久久久久久久久久| 五月天天综合| 色5月婷婷| 99视频| 丁香六月成人网| 婷婷丁香五月天色色| 婷婷亚洲欧美丁香五月| 五月丁香六月综合情在线观看| 激情婷婷五月天| 五月丁香婷中文| 婷婷激情五月天桃花网| 婷婷五月天av| 5五月综合网亚洲| 激情视频网址| 五月婷婷六月丁香首页| 少妇高潮呻吟A片免费看软件| 激情99在线视频| 五月婷婷与六月丁香图片激情| 五月丁香综合啪啪| 99狠狠色| 五月六月丁香激情| 激情综合网,婷婷五月天| 亚洲婷婷综合视频| 日本啪啪视频HD| 九九热视频在线观看| 婷婷五月天av网| www.色情五月天.com| 九九在线精点品| 99亚州综合精品成人网| 99人人操人人摸| YJLZZJLZZ亚洲乱熟无码| 免费观看18视频网站| 婷婷色五月丁香六月欧美啪| 激情 婷婷 插| 情欲综合网| 国产一级婬片毛片| 丁香花色色网| 成人网址在线观看| 婷婷五月无码| 婷婷综合色播网| 色婷五月婷婷| 五月天狠狠网站| 婷婷色色丁香| 五月婷丁香久久综合| 婷婷五月天福利| 色五月激情网| 一区二区成人电影免费播放| 深爱五月婷婷| 国产亚洲在线观看| 丁香五月性| 激情网婷婷五月天| 精品无吗va视频免费观看| 日本在线视频手机播放五月婷| 日韩高清久久| 久婷婷色| 人人综合久| 日韩三级视频一区二区| 九九久99免费视频| 伊人热婷婷| 亚洲AV成人无码精品| 狠狠干综合| 一级黄色影片| 日韩九区| 思思久久99热只有频精品66| 爆乳熟妇一区二区三区四区| 五月天久久小说| 亚洲日韩成人三级av| 国产成人+综合亚洲+天堂| 激情综合无码| 婷婷五月天丁香| 色婷婷电影网| 偷偷与邻居做爰完整视频| 26uuu在线观看| 激情小说五月天| www色五月| 五月天久久丁香| 婷婷中文字幕版| 午夜丁香六月婷| 婷婷五月天激情偷拍| 五月丁色AV| 99热九九这里只有精品| 丁香婷婷人妻综合网| 婷婷五月天国产手机在线视频观看| 99色在线观看免费| 久久久区区一久久久久久| 五月天综合区| 五月丁香色综合| 色综合九九色综合88| 丁香激情网| 99精在线| 国产操B| 婷婷情色五月| 久久色五月| 中文精品在| 啪啪91| 国产日批视频免费播放| 丁香六月伊人| 狠狠色成人影片| 热久久这里只有精品| 免看黄大片AA | 666555。COm毛片| 婷婷五月丁香99| 啪啪夜久久| 欧美99热| 深情五月天| 日韩欧美成人片| 亚洲午夜av| 激情五月丁香五月| 激情综合婷婷久久| 天天综合久久| 五月丁香五月综合欧美| 夜精品无码A片一区二区蜜桃| 久777| 182TV大香蕉| 激情综合亚洲| 五月综合婷婷五月| 欧美成人一区二区三区在线视频| 久久激情五月婷婷| 国产资源91在线| 久青操| 五月婷婷色| Av在线不卡一区| 色综合九九色综合88| wwW天天干| 激情五月天色婷婷| 久久久五月天| 日韩成人电影av| 亚洲综合网区| 激情综合在线观看| 激情av网| 婷婷五月开心中文字幕在线| 九九热这里只有精品6| 五月婷婷黄网站大全| 成人版视频在线观看| 777丁香六月青青草婷婷综合久月 五月丁香综合伦理片 | 超碰免费观看| 日本色婷婷久久99精品91| 丁香五月六月综合欧美| 五月激香蕉网| 色五月亚洲五月天| 99热一区| 中文精品在| 五月亚洲| jiujiuxiangjiaowang| 五月丁香六月婷婷啪啪综合| 色综合色| 99re视频在线播放| 狼人婷婷综合| 草榴视频网| 26UUU精品一区二区c〇m| 久久综合爱| 伊人超碰在线| 欧美色色网| 风流少妇A片一区二区蜜桃| 综合久久影院| 激情综合婷婷| 无码激情| 99色在线| 大香蕉九九| 色婷婷五月天成人网| 天天肏视奸| 色婷婷4| 青草激情综合| 成人看片网站| 婷婷久久五月| 婷婷五月天777| 丁香五月婷久久| 综合另类视频| 色五月网址| 91丨九色丨熟女丰满| 狠狠草狠狠草| 99热丁香五月| 大香蕉网站,大香蕉综合| 超碰在线网站| 99热国产精品| 六月婷婷无码| 乱乱av| 另类综合激情| 久久九九99视频| 能看的av片| 被男人添B超爽视频| 蜜乳.comcom| 婷婷综合在线| 日韩小视频在线99| 岛国资源站| 五月天激情无码| 欧美婷婷精品激| 99视频精品全部观看10| 超碰91在线| 综合网色| 天天爽日日爽夜夜爽| 色99久草在线| 免费播放片大片| 婷婷五月综合网| 久久曰曰| 五月婷婷熟女| 色婷婷色| 天天干天天操天天拍| 亚洲丁香五月综合| 91啦丨九色丨刺激中文| 五月婷婷中文字幕| 婷婷永久在线| 五月激情综合性爱| 日日干天天| 久久奄也去色色网站| 九月性爱网| 婷婷五月天亚洲综合| 色噜噜狠狠色综合无码久久欧美| 最新无码专区| 色停停香蕉视频| 色之综合网| 久久ri精品| 天天干天天做| 丁香婷婷五月六月天| 精品成人在线| 中文字幕av久久爽一区| 天天操夜夜玩!| 97成人在线视频| 成人短视频在线免费观看| 丁香五月性爱| 激情五月天婷婷色色色色色色色色色色色 | 超碰操网| 五月婷婷久草| 婷婷五月激情丁香| 六月综合在线| 色五月天成人在线| 97色在线| 久热伊人9| 人妻精品一区二区三区| 日本天天色| 草操AV在线| www.爱婷婷.com| 婷婷五月丁香六月| 五月丁香五月婷婷| 99热这里只是精品| 欧美五月丁香啪啪响视频| 日逼影音先锋AV男人资源站| 噜噜噜久久| 天天爽天天| 婷婷综合五月天激情| 久久婷婷东京热大香樵| 无码激情AAAAA片-区区| www.色五月| 日本色色网站| 五月天天天色| 婷婷激情丁五月| 九九热这里只有精品23| 激情五月天综合网| 婷五月天| 丁香婷婷激情四射五月| 激情婷婷狠狠干综合| 丁香五月天电影| 超碰爱爱爱| 天天爽天天做| 五月婷婷开心亚州在线| 五月婷婷精品视频| 能看的av片| 色婷婷五月天av在线| 五月天激情图片网| 色9999综合久久| 国精产品一区一区三区免费视频| 五月天婷婷小说| 中文色婷婷| 色播播五月| 五月天色网站| 婷婷十月丁香| 这里只有精品2| 婷婷五月天深爱| www。狠狠干。com| 伊人青草成人| 桃色激情婷婷伊人网| 久久丁香五月综合六月激情红杏视频 | 色色色网站| 久久综合婷婷| 婷婷狠狠操| www色色com| 色一情一乱一乱一区91| 丁香五月天堂| 亚洲婷婷五月天| 婷婷性爱| 男女啪啪做爰高潮无遮挡| 亚洲色色色| 伊人综合网站| 亚洲mm免费| 国内熟女黄色系列| 综合网狠狠| 大香蕉久久婷婷精品综合| 97热久久五月婷婷| 9l视频自拍9l九色成人| 开心婷婷五| 狠狠婷婷爱| 日韩五月天婷婷| 婷婷六月插屄激情| 五月丁香六月激情在线| 噜噜五月天综合| 网站免费一站二站| 九九婷| 国产亚洲99久久精品熟女| 亚洲4区国产欧美| 欧美人久久| 国产成人综合网| 五月天色导航婷婷资源婷婷| 99久久天堂婷婷| www.com亚洲网站在线免费| www.AV在线| 婷婷五月色色| 天天爽成人综合网站| 丁香五月天欧美| 99成人精品视频| 婷婷五月天天天| 成人亚洲精品| 亚洲五月六月婷婷| 91久久综合亚洲噜噜成人在线| 亚洲综合视频网| 丁香五月自拍| 少妇激情五月天| 狠狠丁香| 婷婷丁香大香蕉| 色色色区| 亚洲99视频| 97色色视频| 这里只有精品久久| 色五月婷婷影视| ww亚洲ww在线观看| 99热最新| 五月婷婷综合网| 色色色色色日韩午夜激情 | 99re热精品在线视频| 丁香五月宝贝激情网| 色欲一区二区三区精品A片| 狠狠操狠狠爱| Av免费网站在线| 久思思热视频在线观看| 人人操AV| 伊人喵咪a V| 久久色天堂| 欧美色色色| 99热国产精品| 色99免费视频中文| 天天日日天天| 婷婷五月天AV| 久久99精品久久久久久青青AR| 影音先锋色色色资源色资源色| 99操逼| 操人无码| 婷婷伊人綜合中文字幕| 五月天啪啪啪| 黄色av网站在线免费播放| 丁香五月影院| 欧洲不卡视频| 欧美丁香五月| 五月丁香六月婷婷综合网站| 激情五月丁香五月色| 婷婷午夜| 婷婷色网站| 亚洲国产网址| 五月婷婷之美女图片| 开心婷婷五月| 国产亚洲在线| 久综合色| 婷婷五月丁香花综合| 亚美欧色影院| 五月色亭丁香| 五月开心深深爱激情综合| 99热伊人| 丁香五月网络网络| 色五月六月| 色色色地址| 99热这里只有精品3| 日本不卡高字幕在线2019| 久青青久| 婷婷午夜| 色国产五月| 久9视频| 91狠狠色丁香婷婷综合久久精品| 国产67194| 91久久综合亚洲噜噜成人在线| 亚洲色婷婷五月| 色噜噜丁香| 五月综合亚洲婷婷| 超碰婷婷五月| 五月丁香婷婷三级| bukadeavzaixian| 99在线精品免费视频| 在线中文字幕免费视频| 久久精品视频在这里有| 69色婷婷| 91精品婷婷国产综合久久| 丁香五月区| 99久久久免费| 国产夫妻操逼内射视频| 青草青草视频2免费观看| 深爱激情五月天色婷婷| 久草免费福利视频| 丁香在线视频| 91丨九色丨43老版熟女| 被强行糟蹋的女人A片| 丁香五月天综合| 99九九精品| 吾爱AV导航| 天天插天天爱| 久热中文字幕| 另类视频在线| 五月天激情啪啪| 玖玖爱导航| 丁香五月区| 狠狠搞五月天| 久久您您综合网| 色婷婷成人| 婷婷五月天激情小说| 高清无码网址| 婷婷丁香色五月久久88| 久久嘟嘟丁香| 日韩一级片| 五月婷婷丁香av| 大香久久伊人网| 欧美97色| 色99综合视频| 91尤物九色在线| 在线99热| 深爱激情五月网| 综合久久99| 牛牛热这里只有jingpin| 狠狠狠夜夜夜| 五月丁香手机在线| 热婷婷av| 丁香五月影院| 99热这里只有精品免费| 天天日夜夜B久久| 热久91| 99日本黄站| 婷婷六月久久| 色婷视频| 99久免费视频| 色综合天天| 九九热只有精品| 天天搞夜夜叫| 婷婷欧美激情| 天堂婷婷综合| 五月天成人综合| 色在线视频网2025| 五月婷婷和六月| 久久久久8888| 影音先锋一区二区资源站| 五月天社区| 五月天精品视频| WWW色五月天| 色五月欧美| 色色色激情网| 精品无码久久久久久久久| 九九这里精品| 色五月大| ZpRSw| 另类图片五月天| 久热69| 俺去也在线www色官网| 五月婷婷欧美| 国产超碰人人| 日本人妻操| 免费看欧美成人A片无码| 中文字幕在线日亚州9| 79精品视频在线观看,| 夜夜骑日日夜夜| 99色在线观看免费| 丁香九月激情久久| 激情五月丁香五月| 操操国产| 综合网啪| 99九九视频| 亚洲免费99| 日本美女天天日天天爽| 看婷婷五月天网| 狼友超碰| 久婷婷五月综合欧美| 禁片二区| 五月婷婷激情综合在线| 啪啪夜久久| 99热草草| 丁香8月手机综合| 丁香五月综合| 99热这里| 天天碰夜夜操| 六月婷婷色色网| 日韩国产在线精品| 日产精品一线二线三线芒果| 国产精产国品一二三在观看| 91919191919久久成人视频| 国精产品一区一区三区免费视频 | 丁香六月啪| 亚洲中文字幕AV| 91色五月| 久久九九热视频| 五月天婷婷综合网| 久久久GOGO无码啪啪艺术| 婷婷色婷婷| 国产精品18久久久| 97日韩无套内| 99在线小视频| 亚洲色激情| 久久久91| 天天开心婷婷丁香五月| 色月视频| 狠狠色综合精品视频在线| 五月天综合视频网| 色五月天堂| 丁香五月欧美| av网址在线播放| 啪啪操网| 另类激情综合| 人人人人人人人人人草| 99热这里只有精品最新地址获取| 五月丁香六月激情在线| 67194国产| 农村熟妇高潮精品A片| 色在线免费观看| 人人插9| av九九| 六月丁香综合网| 深爱五月婷| 性视频久久| 九九热超碰| 久久综合55| www99在线观看视频| 五月综合视频在线| 天天操狠狠操| 久久久久9999| 久久电影五月天丁香电影| 日韩超碰在线| 亚洲视频丁香网va| 五月天偷拍| www.久久爱| 在线播放成人| 丁香婷婷五月天网站| 99热这里只有精品 搜| www.精品99| 欧美成人猛片AAAAAAA| 五月天激情网址| 欧美激情xxxXX| 色偷偷五月天| 日韩色色色色| 操碰91| 99免费视频网| 99热最新网址| 超碰无码318604| 九九一综合精品| 日韩在线9| 热99色| 99色色爰| 色五月婷婷九月| 99热色精品| 国产精品日日躁夜夜躁| 五月丁香花激情综合网| 噜噜噜久久| 丁香六月婷| av性爱在线| 97碰在线视频| 日韩精品999| 欧美日本va| 久久小说| 婷婷久久欧美| 欧美在线干| 伊人9草在线观看| 五月丁香人人婷婷在线观看| 日韩一级片| 人人摸人人操人人爽| 国产玖玖资源| 丁香,开心成人,久久| 国产人妻操逼| 超碰人人超碰| 免费97碰碰| 婷婷激情五月综合| 伊人久久丁香五月91| 六月色色综合| 这里只有精品视频| 五月花综合网| 色婷婷小说网| 久久久人妻人伦| 久久六月天| 久久婷婷五月综合啪| www.99视频| 熟女国产在线一区二区三区四区| 中文字幕色色色| 婷婷在线中文字幕| 99热精品综合| 狠狠干五月| 婷婷激情五月综合在线视频| 久草热8精品视频在线观看 | 99综合视频在线| 色啪影院| 国产韩日亚洲美州欧亚综合在线| 四色永久成人网站| 久久婷婷伊人| 欧美婷婷综合| 色久在| 伊人综合网站| 久99久热只有精品国产99| 国产美女无遮挡裸体毛片A片| 精品国产人人爱人人| 能看的AV| 色五月成人网| 日本高清不卡免费一区二区三区| 天天搞天天爽| 色99自拍| 五月天综合| 五月婷高清视频| 一级黄在线| 激情五月四色| 丁香六月婷婷色播| 日本久热| 99丁香五月婷| 国产精品第一国产精品| 日本五月天一页| 婷婷五月天久久综合88| 亚洲高清在线| 亚洲熟妇AV综合网五月丁香伊人 | 超级碰碰碰97免费| 婷婷伊人綜合中文字幕小说| 久久99最新| 婷婷影视久久| 精品无吗va视频免费观看| 亚洲成人超碰| 九九碰九九爱97| 人人操人av| 久色88| 伊人啪啪网| 久热最新视频| 夜夜久久综合网| 日韩无码专区| 五月成人天| 婷婷综合激情| 操操综合网婷婷| 激情综合网五月| 99久久a线观| 爆乳熟女-区二区三区| 天天操加勒比| 久色五月婷婷综合| 色五月婷婷操逼| 激情综合五月婷婷| 色色性爱视频| 丁香婷婷精品视频| 99久高清视频| 久99| 婷婷五月色激情欧美激情| 婷婷免费精品视频| 色婷综合| 99超级碰免费视频| 丁婷婷五月天在线播放| 密黄站| 亚洲AV无码成人精品电影| 色屌丝中文字幕| 婷婷五月丁香综合激情| 综合激情网五月激情| 国产婷婷久久| 99国产精品久久久久久久久久久 | 99操逼视频| 天天操天天爱天天玩| 色欲av伊人久久大香线蕉影院| 97超碰,人人舔,人人操,人人摸 | 亚洲视频色色| 婷婷 伊人 久久| 少妇被下春药玩弄A片| 9九色首页| 很很干五月天| 黄色大片又大粗又爽| 99久免费视频| 国产黄色在线| 99久久婷婷国产综合精品草原| 五月花免费视频| www.五月天性.com| 亚洲精品亚洲人成人网| 超碰色天堂| 91呦呦呦| 大战熟女丰满人妻AV| 超碰九色| 五月丁香影院| 色婷婷色五月天| 襙比视频| 九九热九九| 激情久久久久| 色女人久久| 久久五月天丁香| 香蕉久操| 国产真人做爰视频免费| 激情丁香五月| 99热在线精品观看| 婷婷五月丁香啪啪| 开心网五月色婷婷| 亚洲五月天婷婷在线| 狠狠操天天操综合| 秋霞学生妹一二级| 五月婷婷在线短视频| 日韩不卡DvD| 伊人9在线| 激情久久网| 综合久久8| 91操女| 亚洲中文AV| 97色婷婷| 色色色五月天婷婷| 丁香五月婷婷天激情| 色一色综合| 91夫妻网站九色| 琪琪布丁香社区激情五月天| 黄桃AV无码免费一区二区三区| 久久精品99国产精品日本| 久久精彩免费视频| 嫩草AV久久伊人妇女超级A| 丁香五月手机在线| 五月丁香六月婷| 97操碰| 无码人妻少妇色欲AV一区二区| 丁香六月婷| 性无码专区无码| 国产亚洲成AV人片在线观黄桃| EEUSS鲁片一区二区三区| 天天爽夜夜操| 五月天婷久久| av超碰在线| 99热69| 欧美在线操| av大香蕉| 天天日日天天| 五月激情五月婷婷五月天在线| 天天搞天天色综合| 五月丁香影院| 成人看片网站| 国产欧美精品AAAAAA片| 久热A片| 色色色色色综合| 熟女激情网| 婷婷欧美色| WWW.桔色成人.COM| 五月丁香六月婷婷操操操| 久久超视频| 久久五月丁香| 婷婷五月丁香亚洲| 99内射视频| 九九国产视频| 色五月婷婷激情五月| 色五月影视| 亚洲欧美婷婷五月色综合| 一级黄色影片| 九97免费视频| 欧美色99| 九九综合五月欧美| 免费碰碰视频久| 亚洲色图81p| 婷婷综合另类小说| 天天综合天综合| 91婷婷丁香| 亚洲综合网在线| 一操久久| 日日操,日日爽| 播播网色播播| 五月丁香影视| 99热久久日本| 4399在线观看免费高清电视剧| 国产精品蜜臀99| 久久伦乱| 激情五月黄色| 色五月婷婷综合| 99秘 在线| 久久在这里99| 欧美一级a | 91av色色乱视频| www.久久| 日本五月婷婷| 桃色五月天| 色婷婷影| 婷婷色五月色妇| 97中文在线| 久久精99| 五月丁香婷婷在线综合蜜桃| 狠狠干夜夜干| 搡BBBB搡BBB搡18| 五月丁香久久呀| 五月婷婷六月激情网| 黄色三级日本| 激情综合五月| 激情久久伊人| 超碰免费99| 婷婷激情五月天小说| 超碰av在线| 色婷婷精| 婷婷成人综合免费视频| 人妻久热| 婷婷婷五月香蕉| 婷婷色无码| 亚洲激情在线| 视频1区2区| 婷婷丁香综合成人| www.色婷婷.com| 激情另类综合| 狠狠干狠狠干| 1024在线视频| 婷婷丁香五月欧美人| 五月婷婷六月激情| 色婷婷综合视频| 青青日韩| 日日爽日日爽| 久久婷婷老| 激情五月丁香色婷婷| 综合网亚洲| 亚洲无线视频| 九九精品亚洲| 色开心五月丁香| 丁香六月激情综合啪啪| 爱99干99| 午夜精品777| 五月激情综合网| 婷激情五月天视频导航| 日日夜夜天天综合| 日韩综合天堂| 丁香六月激情| 色婷婷五月色| 婷婷五月电影| 婷婷五月综合社区| 婷婷丁香五月网| 免费人人操| 99热这里只有精品8| 亚洲第一影院高清无码网站| 五月婷精品| 日本天堂久久| 夜夜撸日日操| www久久艹| 五月天伊人综合| 综合激情在线| 大香蕉五月天| 97色在线| 中文字幕永久在线| 伊人六月丁香婷婷| 99热 精品在线| 五月丁香婷婷啪啪综合网| 五月天久久婷| 天天日夜夜帕| 玖玖色资源| 武则天精品久久| 大香蕉综合网| 狠狠狠狠狠狠| 99精品久久久久久久婷婷久久| 久久婷婷六月综合国际| 久久亚洲激情五码| 天堂综合久久| 99热18| 精品视频这里只有精品| 午夜69成人做爰视频| 婷婷色五月久久| 超碰无码老师| 区美毛片子| 噜综合| 激情五月综合网丁| 五月的色婷婷高潮| 色五月激情| 九九人人操| 丁香五月六月激情| 激情涩涩网| 久久成人综合五月天| 丰满人妻妇伦又伦精品国产 | 丁香五月天激情四射网| 噜噜狠狠色| 狠狠色婷婷777| 日本天天色| 天天射色五月天| 婷婷色五月大香蕉在线观看| 99热手机在线精品| 26uu| 久久九九囯产| 99久久婷婷国产综合精品草原| 狠狠色激情在线| 婷婷色色丁香| 婷婷色婷婷| 亚洲人妻一区二区| 人妻aV在线| 亚洲无AV在线中文字幕| 色婷婷亚洲五月天| 婷色人人狠| 九九色黄色| 日本片日本片祼观看网站在线看中文版网页在线看 | 丁香五月激情六月综合| 日本理论久久| 9色在线| 久久激情五月婷婷| 天天做天天视天天谢| 色都都狠狠色都都色综合色| 色五月婷婷丁香五月| 欧美狠狠地| 大香网伊人久久综合| 伊人大香蕉爱聚| 色香蕉影院| 99热这里只有精品在线播放| 大香蕉综合网| 久久婷婷六月综合综合| 色九九综合| 日亚二欧美| 春色激情第四色| 操逼六区| 五月婷婷综合成人| 午夜丁香| 中文成人在线| 亚洲VA在线| 丁香五月婷婷深爱综合激情| 99欧美三级视频| 国产美女无遮挡裸体毛片A片 | 丁香五月婷婷久久久| 色色五月天激情| 久久综合首页| 色五婷婷| 日韩狠狠色婷婷| 天天久综合网永久入口17v| 欧美97超碰| 99国产精品久久久久久久久久久 | 国产亚洲网站在线| 亚洲欧洲美女在线观| www.狠狠| 婷婷在线视频| 一级二级色大片| 五月天综合图片| caopeng97日韩| 五月婷婷六月丁香免费| 久久色五月| 91xxxx九色| 精品热九九| 欧美69久成人做爰视频| 涩涩五月天| 色欲色香综合网| 婷丁香五月天| 99热在线这里| 日日夜夜小色哥| 激情亚洲五月| 色必久悠悠影院| 五月丁香激情片| 99久久精彩视频。| 9色在线| 日本久热| 久久99网址| 国产亚洲99久久| 九九人人看| 99热国产婷婷| 婷婷五月丁香香蕉| 丁香六月色| 中文网婷婷字幕婷| 久久艹网| 九九中文字幕九| 九九色天堂| 五月婷婷色白丝| 伊人久久大香线蕉AV最新午夜| 碰人人97| www99xxxx五月丁| 99久久高清视频| 2021日韩无码| 激情 婷婷| 婷婷情色五月天| 粉嫩av蜜桃av蜜臀av| 殴美日比视频| 色噜噜综合网| 天天做天天爱天天搞| 国产99热在线看| 五月丁香婷婷在线综合蜜桃| 婷婷色五月天第7色| 啪啪五月天啪啪| 久久这里只有精品22| 色色色色色色色色综合网| 色久丁香五| 久久女人天堂| 五月激情六月丁香| 国产99久久久国产精品免费看| 青青久在线视频免费观看| 免费黄网不卡AV| 婷婷97C| 1024操逼视频| 久久久com| 欧美日韓成人亚洲精品另类| 五月丁香啪啪啪啪| 激情综合色五月丁香六月亚洲| 久久少妇视频| 色综合中文| 五月婷婷深深爱| 九久久婷婷| 伊人婷婷91| 天天爱天天做天天日| 九九视频热| 日日噜狠狠色综合久| 激情五月天色色| 超碰成人黄色网| 99超碰人人| eeuss人妻| 五月天婷婷丁香六月| 狠狠爱婷婷爱| 亚洲人妻av伦理| 久久综合9| 97色在线视频| 人人天堂操| 大婷婷色呦呦噜噜色呦呦噜噜| 激情丁香婷婷| 97爱艹婷婷开心丁香激情综合| 99五月婷| 丁香五月天人体| 婷婷五月天视频亚洲| 岛国av网站| 色99欧洲色19| 五月色在线| www天天爽| 狠狠干在线| 色五月激情问网站| 亚洲午夜AV| 精品国产va久久久| 久久久激情| 久久免费干| 亚洲一个色| AAAA网站| AA丁香综合激情| 91在线操| 99热这里有精品24| 亚洲操逼片| 婷婷丁香大香蕉| 色婷婷五月天亚洲 | 婷婷丁香先锋资源网站| 狠狠操之狠狠操| 26uuu欧美| 1024在线一区| 日韩成人综合网| 五月丁香中文字幕| 99精品成人无码A片观看金桔| 九九综合网色全集 | 久久免费操| 99热这里只有精品最新| 夜夜操天天干| www.97干视频| 天天情色五月天| 91色色色| 91视频一起草| 色婷婷丁香香香蕉视频| 日韩一级片| 久综合| 久久99精品久久只有精品| 99爱免费视频| 色狠狠999综合| 91色呦哟| 丁香六月婷婷综合激情欧美 | 久久久久er热| 99热第一页| 婷婷无码视频| 亚洲精品一区无码A片| 综合久| 99热都是精品| 综合久久五| 第四色婷婷最爱| 99超级碰免费视频| 九九操操| 99啪啪网| 日韩啪图| 婷婷五月天成人综合网| 青草青草视频2免费观看| 激情婷婷| 六月丁香久久| 激情婷婷在线中文字幕| 婷婷五月天视频| 国产在线视频1234| 丁香婷婷五月基地| 大香蕉在线99热| 伊人丁香花综合影院| 少妇人妻丰满做爰XXX| 九九热这里有精品23| 狠狠操狠狠操| 久久综合九九| 欧美99| 婷婷丁香人妻天久久| www.狠狠| 婷婷五月天最新综合你懂的 | 久久性刺激| 九九热精品视频在线观看| 久久图色4| 色五月五月天色婷婷色五月| 九月激情综合婷婷| 久久色五月天| 成人版视频在线观看| 国产熟女一区二区三区五月婷| 99热主页日本| 在线播放成人网站| 九九久久精品| 天天日综合| 久久这里在精品视频| 国产乱妇无乱码大黄AA片| caopeng97日韩| 天堂美国久久| 六月丁香VA| www.maotanji.com| 思思久久精品|