Linux中ext4文件系統(tǒng)的工作原理和優(yōu)化策略
ext4(Fourth Extended Filesystem)是 Linux 系統(tǒng)中最廣泛使用的日志型文件系統(tǒng)之一,自 2008 年正式合并入 Linux 內(nèi)核主線以來,它已成為大多數(shù)主流發(fā)行版的默認(rèn)文件系統(tǒng)。其設(shè)計目標(biāo)是在保持與 ext3 兼容的基礎(chǔ)上,提供更高的性能、更大的容量支持以及更強(qiáng)的數(shù)據(jù)完整性保障。對于 Java 開發(fā)者而言,理解 ext4 的工作原理和優(yōu)化策略,不僅能提升應(yīng)用程序在 Linux 環(huán)境下的 IO 性能,還能幫助我們寫出更高效、更穩(wěn)定的磁盤操作代碼。
ext4 的核心特性概覽
ext4 是 ext3 的直接繼承者,在保留原有穩(wěn)定性和兼容性的基礎(chǔ)上,引入了多項革命性改進(jìn):
向后兼容性
ext4 完全兼容 ext3 和 ext2。這意味著你可以將 ext3 分區(qū)“原地升級”為 ext4,而無需重新格式化或遷移數(shù)據(jù)。這種無縫過渡對生產(chǎn)環(huán)境至關(guān)重要。
# 將 ext3 升級為 ext4(需先卸載分區(qū)) sudo tune2fs -O extents,uninit_bg,dir_index /dev/sdXN sudo e2fsck -f /dev/sdXN
注意:雖然可以掛載 ext4 為 ext3 使用,但會喪失 ext4 的新特性。
支持超大文件與分區(qū)
ext4 最大支持 1EB(Exabyte) 的文件系統(tǒng)容量和 16TB 的單個文件大小(取決于塊大?。?。相比之下,ext3 最大僅支持 16TB 文件系統(tǒng)和 2TB 單文件。
| 文件系統(tǒng) | 最大卷大小 | 最大文件大小 |
|---|---|---|
| ext3 | 16TB | 2TB |
| ext4 | 1EB (理論值) | 16TB |
這使得 ext4 能輕松應(yīng)對現(xiàn)代大數(shù)據(jù)、視頻處理、數(shù)據(jù)庫等應(yīng)用場景。
Extents 取代間接塊映射
這是 ext4 最重要的革新之一。傳統(tǒng) ext2/ext3 使用“間接塊指針”來記錄文件數(shù)據(jù)塊位置,對于大文件,需要多層指針跳轉(zhuǎn),效率低下。
ext4 引入 Extent(區(qū)段) 概念 —— 一個 extent 是一組連續(xù)的物理塊。例如,一個 100MB 的文件如果存儲在連續(xù)的磁盤區(qū)域,只需要一條 extent 記錄即可,而不是成百上千個塊指針。

這種方式極大減少了元數(shù)據(jù)開銷,提升了大文件讀寫性能。
延遲分配(Delayed Allocation)
ext4 默認(rèn)啟用延遲分配機(jī)制:當(dāng)應(yīng)用程序?qū)懭霐?shù)據(jù)時,文件系統(tǒng)不會立即分配磁盤塊,而是等到數(shù)據(jù)真正刷盤(如調(diào)用 sync 或緩存滿)時才分配。
優(yōu)點:
- 減少碎片(有機(jī)會合并相鄰寫入)
- 提高寫入吞吐量
- 降低元數(shù)據(jù)更新頻率
缺點:
- 在突然斷電時可能丟失更多數(shù)據(jù)(可通過
data=ordered或journal緩解)
目錄索引(HTree)
ext4 使用 Hash Tree(htree) 結(jié)構(gòu)加速目錄查找。在包含數(shù)萬甚至數(shù)十萬文件的大目錄中,查找速度從 O(n) 降至接近 O(log n)。
# 查看目錄是否啟用 dir_index sudo dumpe2fs /dev/sdXN | grep dir_index
預(yù)分配(Preallocation)
通過 fallocate() 系統(tǒng)調(diào)用,應(yīng)用程序可預(yù)先分配磁盤空間,避免運行時因空間不足失敗,同時減少碎片。
Java 中可通過 FileChannel 的 truncate() 或第三方庫實現(xiàn)類似效果(后文詳述)。
時間戳增強(qiáng)
ext4 支持納秒級時間戳,并擴(kuò)展了時間范圍(至 2514 年),解決了“2038 年問題”。
ext4 掛載選項深度解析
掛載選項直接影響 ext4 的行為和性能。以下是最常用且值得深入理解的幾個:
data={journal|ordered|writeback}
控制數(shù)據(jù)與日志的同步方式:
data=journal:最安全,所有數(shù)據(jù)先寫日志再寫主文件系統(tǒng)。性能最低。data=ordered(默認(rèn)):數(shù)據(jù)寫入主文件系統(tǒng)前,先提交元數(shù)據(jù)到日志。平衡安全與性能。data=writeback:僅日志記錄元數(shù)據(jù),數(shù)據(jù)異步寫入。性能最高,崩潰時可能數(shù)據(jù)不一致。
# /etc/fstab 示例 /dev/sda1 / ext4 defaults,data=ordered 0 1
noatime / relatime
每次讀取文件時,系統(tǒng)默認(rèn)更新訪問時間(atime),造成額外寫入。
noatime:完全禁用 atime 更新relatime(默認(rèn)):僅當(dāng) atime < mtime 或 ctime 時才更新,兼顧 POSIX 兼容性與性能
# 推薦用于數(shù)據(jù)庫/日志服務(wù)器 /dev/sdb1 /data ext4 defaults,noatime,nodiratime 0 2
barrier / nobarrier
寫屏障(barrier)確保日志提交順序,防止斷電導(dǎo)致元數(shù)據(jù)損壞。但在帶電池緩存的 RAID 控制器上可關(guān)閉以提升性能。
生產(chǎn)環(huán)境除非你明確知道自己在做什么,否則不要使用 nobarrier。
journal_async_commit
允許異步提交日志,提高并發(fā)寫入性能,輕微降低數(shù)據(jù)一致性保障。
Java 應(yīng)用中的 ext4 優(yōu)化實踐
作為 Java 開發(fā)者,我們雖不直接管理文件系統(tǒng),但可以通過合理的 API 使用和配置,最大化利用 ext4 特性。
1. 使用 NIO.2 進(jìn)行高效文件操作
Java 7 引入的 java.nio.file 包提供了更貼近底層的操作能力。
import java.nio.file.*;
import java.nio.ByteBuffer;
import java.io.IOException;
public class Ext4OptimizedWriter {
public static void writeWithAllocation(Path filePath, long fileSize) throws IOException {
// 使用 fallocate 類似功能預(yù)分配空間
try (FileChannel channel = FileChannel.open(filePath,
StandardOpenOption.WRITE,
StandardOpenOption.CREATE)) {
// 預(yù)分配空間,減少后續(xù)碎片
channel.truncate(fileSize);
// 寫入數(shù)據(jù)
ByteBuffer buffer = ByteBuffer.allocate(8192);
for (int i = 0; i < fileSize / buffer.capacity(); i++) {
buffer.clear();
// 填充數(shù)據(jù)...
buffer.put(("Chunk " + i + "\n").getBytes());
buffer.flip();
channel.write(buffer);
}
}
}
public static void main(String[] args) {
Path path = Paths.get("/mnt/ext4_data/largefile.dat");
try {
writeWithAllocation(path, 1024 * 1024 * 100); // 100MB
System.out.println("? 文件寫入完成,已預(yù)分配空間");
} catch (IOException e) {
System.err.println("? 寫入失敗: " + e.getMessage());
}
}
}2. 利用 Direct I/O 繞過頁緩存(謹(jǐn)慎使用)
對于數(shù)據(jù)庫類應(yīng)用,有時希望繞過操作系統(tǒng)緩存,直接控制磁盤 IO。可通過 FileChannel.map() 或 JNI 實現(xiàn),但 Java 標(biāo)準(zhǔn)庫不直接支持 O_DIRECT。
替代方案:增大 JVM 堆外內(nèi)存 + 使用 DirectByteBuffer
import java.nio.MappedByteBuffer;
import java.nio.channels.FileChannel;
import java.nio.file.StandardOpenOption;
public class DirectMappedExample {
public static void useMemoryMapping(Path file) throws Exception {
try (FileChannel channel = FileChannel.open(file,
StandardOpenOption.READ,
StandardOpenOption.WRITE)) {
// 內(nèi)存映射文件 —— OS 自動管理緩存
MappedByteBuffer buffer = channel.map(
FileChannel.MapMode.READ_WRITE, 0, 1024 * 1024);
buffer.put("Hello from memory-mapped world!".getBytes());
buffer.force(); // 強(qiáng)制刷盤
System.out.println("?? 數(shù)據(jù)已通過內(nèi)存映射寫入");
}
}
}3. 批量寫入與緩沖策略
ext4 的延遲分配機(jī)制鼓勵“批量寫入”。頻繁的小寫入會導(dǎo)致多次分配和日志提交。
import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
public class BatchWriteOptimizer {
// ? 低效:每次寫一行都 flush
public static void badPractice(Path file) throws IOException {
try (FileWriter fw = new FileWriter(file.toString())) {
for (int i = 0; i < 10000; i++) {
fw.write("Line " + i + "\n");
fw.flush(); // 強(qiáng)制刷盤,破壞延遲分配
}
}
}
// ? 高效:批量寫入 + 大緩沖區(qū)
public static void goodPractice(Path file) throws IOException {
// 使用 128KB 緩沖區(qū)
try (BufferedWriter bw = Files.newBufferedWriter(file,
java.nio.charset.StandardCharsets.UTF_8,
java.util.EnumSet.of(StandardOpenOption.CREATE, StandardOpenOption.WRITE))) {
for (int i = 0; i < 10000; i++) {
bw.write("Line " + i + "\n");
}
// 自動 flush on close,觸發(fā)一次延遲分配
}
System.out.println("?? 批量寫入完成,充分利用 ext4 延遲分配");
}
}4. 文件預(yù)熱與順序訪問優(yōu)化
如果你的應(yīng)用需要順序讀取大文件(如日志分析),可提示內(nèi)核進(jìn)行預(yù)讀:
import java.io.RandomAccessFile;
import java.nio.channels.FileChannel;
public class FilePrefetcher {
public static void prefetchFile(Path filePath) throws Exception {
try (RandomAccessFile raf = new RandomAccessFile(filePath.toFile(), "r");
FileChannel channel = raf.getChannel()) {
// 建議內(nèi)核預(yù)讀 4MB
channel.position(0);
long fileSize = channel.size();
int readAheadSize = Math.min((int) fileSize, 4 * 1024 * 1024);
ByteBuffer buffer = ByteBuffer.allocateDirect(readAheadSize);
channel.read(buffer);
buffer.flip();
// 實際處理邏輯...
System.out.println("?? 文件預(yù)熱完成,提升后續(xù)順序讀取性能");
}
}
}ext4 性能監(jiān)控與調(diào)優(yōu)工具
使用 iostat 監(jiān)控磁盤 IO
# 每2秒刷新一次,關(guān)注 %util 和 await iostat -x 2
關(guān)鍵指標(biāo):
%util> 90% 表示磁盤飽和await高表示 IO 延遲大svctm服務(wù)時間,應(yīng)盡量低
使用 blktrace + blkparse 分析 IO 模式
# 跟蹤 sda 設(shè)備的 IO sudo blktrace -d /dev/sda -o trace sudo blkparse trace -o trace.txt
可看到每個 IO 請求的起始扇區(qū)、大小、延遲等,用于分析是否產(chǎn)生大量隨機(jī)小 IO。
使用 fio 進(jìn)行基準(zhǔn)測試
安裝 fio:
sudo apt install fio # Ubuntu/Debian sudo yum install fio # CentOS/RHEL
測試順序?qū)懶阅埽?/p>
# seq-write.fio [global] bs=128k ioengine=libaio direct=1 size=1g numjobs=1 [seq-write] rw=write filename=/mnt/ext4_test/testfile
運行:
fio seq-write.fio
ext4 vs 其他現(xiàn)代文件系統(tǒng)對比
雖然 ext4 成熟穩(wěn)定,但面對新型硬件(如 NVMe SSD)和新型負(fù)載(容器、云原生),其他文件系統(tǒng)也展現(xiàn)出優(yōu)勢:
渲染錯誤: Mermaid 渲染失敗: Parsing failed: Lexer error on line 3, column 5: unexpected character: ->“<- at offset: 35, skipped 4 characters. Lexer error on line 3, column 11: unexpected character: ->—<- at offset: 41, skipped 1 characters. Lexer error on line 3, column 13: unexpected character: ->通<- at offset: 43, skipped 6 characters. Lexer error on line 3, column 20: unexpected character: ->:<- at offset: 50, skipped 1 characters. Lexer error on line 4, column 5: unexpected character: ->“<- at offset: 59, skipped 4 characters. Lexer error on line 4, column 10: unexpected character: ->—<- at offset: 64, skipped 1 characters. Lexer error on line 4, column 12: unexpected character: ->大<- at offset: 66, skipped 8 characters. Lexer error on line 4, column 21: unexpected character: ->:<- at offset: 75, skipped 1 characters. Lexer error on line 5, column 5: unexpected character: ->“<- at offset: 84, skipped 6 characters. Lexer error on line 5, column 12: unexpected character: ->—<- at offset: 91, skipped 1 characters. Lexer error on line 5, column 14: unexpected character: ->快<- at offset: 93, skipped 10 characters. Lexer error on line 5, column 25: unexpected character: ->:<- at offset: 104, skipped 1 characters. Lexer error on line 6, column 5: unexpected character: ->“<- at offset: 113, skipped 4 characters. Lexer error on line 6, column 10: unexpected character: ->—<- at offset: 118, skipped 1 characters. Lexer error on line 6, column 12: unexpected character: ->企<- at offset: 120, skipped 9 characters. Lexer error on line 6, column 22: unexpected character: ->:<- at offset: 130, skipped 1 characters. Parse error on line 3, column 9: Expecting token of type 'EOF' but found `4`. Parse error on line 4, column 23: Expecting token of type 'EOF' but found `30`. Parse error on line 5, column 27: Expecting token of type 'EOF' but found `15`. Parse error on line 6, column 24: Expecting token of type 'EOF' but found `10`.
ext4 vs XFS
XFS 在處理超大文件和高并發(fā)寫入時表現(xiàn)更優(yōu),常用于媒體服務(wù)器和數(shù)據(jù)庫。但 ext4 啟動恢復(fù)更快,更適合根文件系統(tǒng)。
ext4 vs Btrfs
Btrfs 支持透明壓縮、快照、RAID 等高級功能,但穩(wěn)定性仍受質(zhì)疑。ext4 仍是生產(chǎn)環(huán)境首選。
高級調(diào)優(yōu):tune2fs 與 e2fsck
調(diào)整預(yù)留塊百分比
默認(rèn) ext4 為 root 用戶保留 5% 空間,防止用戶占滿導(dǎo)致系統(tǒng)崩潰。對于專用數(shù)據(jù)盤,可降低此值:
# 設(shè)置預(yù)留空間為 1% sudo tune2fs -m 1 /dev/sdb1
啟用額外特性
# 啟用 project quota(項目配額) sudo tune2fs -O project /dev/sdb1 # 啟用大目錄索引 sudo tune2fs -O large_file,dir_index /dev/sdb1
定期檢查與修復(fù)
即使 ext4 很穩(wěn)定,也建議定期運行 e2fsck:
# 強(qiáng)制檢查(需卸載分區(qū)) sudo umount /dev/sdb1 sudo e2fsck -f /dev/sdb1 sudo mount /dev/sdb1 /mnt/data
ext4 在容器與云環(huán)境中的表現(xiàn)
隨著 Docker 和 Kubernetes 的普及,ext4 仍是大多數(shù)容器鏡像和持久卷的底層文件系統(tǒng)。
Docker Overlay2 與 ext4
Docker 默認(rèn)使用 overlay2 存儲驅(qū)動,其底層依賴 ext4 的 d_type 支持(目錄項類型)。
確認(rèn)支持:
# 應(yīng)返回 "ftype=1" sudo xfs_info /var/lib/docker | grep ftype # 對于 ext4,需確保掛載時未禁用 dir_index mount | grep ext4
Kubernetes PersistentVolume 優(yōu)化
在 PV 的 StorageClass 中,可指定掛載選項:
apiVersion: storage.k8s.io/v1 kind: StorageClass metadata: name: ext4-optimized provisioner: kubernetes.io/aws-ebs parameters: type: gp3 mountOptions: - noatime - nodiratime - data=ordered
常見陷阱與解決方案
1. 磁盤空間“神秘消失”
現(xiàn)象:df 顯示空間已滿,但 du 顯示文件總和遠(yuǎn)小于容量。
原因:被刪除但仍被進(jìn)程打開的文件占用空間。
解決:
# 查找被刪除但仍占用空間的文件 lsof +L1 # 重啟相關(guān)進(jìn)程或 kill -HUP 釋放
2. 大量小文件性能下降
ext4 雖有 htree,但百萬級小文件仍可能變慢。
優(yōu)化方案:
- 使用
noatime - 增大 inode 數(shù)量(格式化時指定
-N) - 考慮使用專門的小文件系統(tǒng)(如 F2FS)
# 格式化時指定更多 inode sudo mkfs.ext4 -N 10000000 /dev/sdc1 # 一千萬 inode
3. 日志磁盤滿導(dǎo)致系統(tǒng)卡頓
ext4 日志默認(rèn)大小 128MB,高負(fù)載下可能成為瓶頸。
調(diào)整日志大?。?/p>
# 格式化時指定更大日志(最大 1024 塊組,通常 4GB) sudo mkfs.ext4 -J size=4096 /dev/sdd1
未來展望:ext4 仍在演進(jìn)
盡管 Btrfs、ZFS、F2FS 等新興文件系統(tǒng)不斷涌現(xiàn),ext4 因其穩(wěn)定性、兼容性和持續(xù)優(yōu)化,仍將在未來多年主導(dǎo) Linux 生態(tài)。
近期內(nèi)核版本中,ext4 新增了:
- 在線碎片整理支持(e4defrag)
- 項目配額(Project Quota)
- 加密支持(fscrypt)
- 大分配塊(bigalloc)
# 查看當(dāng)前內(nèi)核支持的 ext4 特性 cat /proc/filesystems | grep ext4 modinfo ext4
給 Java 開發(fā)者的終極建議
- 了解你的存儲層 —— 不要假設(shè)“文件系統(tǒng)是透明的”。不同掛載選項對性能影響巨大。
- 批量操作優(yōu)于頻繁小操作 —— 利用 ext4 延遲分配和 extent 特性。
- 預(yù)分配空間 —— 對于已知大小的文件,提前分配可減少碎片。
- 合理使用緩存 —— Buffered vs Direct,根據(jù)場景選擇。
- 監(jiān)控真實 IO 行為 —— 使用 iostat、blktrace 驗證你的優(yōu)化是否生效。
附:完整性能對比測試代碼
以下是一個綜合測試程序,比較不同寫入策略在 ext4 上的表現(xiàn):
import java.io.*;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
import java.nio.file.*;
import java.util.concurrent.TimeUnit;
public class Ext4PerformanceBenchmark {
private static final int FILE_SIZE = 100 * 1024 * 1024; // 100MB
private static final int CHUNK_SIZE = 8192;
public static void testBufferedWrite(Path file) throws IOException {
long start = System.nanoTime();
try (BufferedWriter writer = Files.newBufferedWriter(file)) {
byte[] chunk = new byte[CHUNK_SIZE];
for (int i = 0; i < FILE_SIZE / CHUNK_SIZE; i++) {
writer.write(new String(chunk));
}
}
long end = System.nanoTime();
System.out.printf("?? Buffered Write: %.2f ms%n",
TimeUnit.NANOSECONDS.toMillis(end - start));
}
public static void testChannelWrite(Path file) throws IOException {
long start = System.nanoTime();
try (FileChannel channel = FileChannel.open(file,
StandardOpenOption.WRITE,
StandardOpenOption.CREATE,
StandardOpenOption.TRUNCATE_EXISTING)) {
ByteBuffer buffer = ByteBuffer.allocate(CHUNK_SIZE);
for (int i = 0; i < FILE_SIZE / CHUNK_SIZE; i++) {
buffer.clear();
buffer.put(("Chunk" + i + "\n").getBytes());
buffer.flip();
while (buffer.hasRemaining()) {
channel.write(buffer);
}
}
}
long end = System.nanoTime();
System.out.printf("? Channel Write: %.2f ms%n",
TimeUnit.NANOSECONDS.toMillis(end - start));
}
public static void testPreallocatedWrite(Path file) throws IOException {
long start = System.nanoTime();
try (FileChannel channel = FileChannel.open(file,
StandardOpenOption.WRITE,
StandardOpenOption.CREATE)) {
// 預(yù)分配
channel.truncate(FILE_SIZE);
ByteBuffer buffer = ByteBuffer.allocate(CHUNK_SIZE);
for (int i = 0; i < FILE_SIZE / CHUNK_SIZE; i++) {
buffer.clear();
buffer.put(("Chunk" + i + "\n").getBytes());
buffer.flip();
while (buffer.hasRemaining()) {
channel.write(buffer);
}
}
}
long end = System.nanoTime();
System.out.printf("?? Preallocated Write: %.2f ms%n",
TimeUnit.NANOSECONDS.toMillis(end - start));
}
public static void main(String[] args) {
Path basePath = Paths.get("/tmp/ext4_bench");
try {
Files.createDirectories(basePath);
} catch (IOException ignored) {}
Path file1 = basePath.resolve("buffered.dat");
Path file2 = basePath.resolve("channel.dat");
Path file3 = basePath.resolve("prealloc.dat");
System.out.println("?? 開始 ext4 寫入性能測試...");
try {
testBufferedWrite(file1);
testChannelWrite(file2);
testPreallocatedWrite(file3);
} catch (IOException e) {
System.err.println("測試失敗: " + e.getMessage());
}
System.out.println("? 測試完成。請結(jié)合 iostat 分析實際磁盤行為。");
}
}運行此程序前,請確保 /tmp 掛載在 ext4 分區(qū)上:
mount | grep /tmp # 若不是,可創(chuàng)建專用測試目錄: sudo mkdir /mnt/ext4_test sudo mount -o remount,noatime /dev/sdXN /mnt/ext4_test
結(jié)語
ext4 不僅僅是一個“老而彌堅”的文件系統(tǒng) —— 它持續(xù)進(jìn)化,適應(yīng)現(xiàn)代硬件與負(fù)載。作為 Java 開發(fā)者,我們不應(yīng)忽視存儲層的影響。通過理解 ext4 的核心機(jī)制(如 extents、延遲分配、目錄索引),并結(jié)合 Java NIO 的最佳實踐,我們可以構(gòu)建出在 Linux 環(huán)境下飛馳的高性能應(yīng)用。
記?。鹤羁斓拇a,是懂得與操作系統(tǒng)協(xié)作的代碼。
以上就是Linux中ext4文件系統(tǒng)的工作原理和優(yōu)化策略的詳細(xì)內(nèi)容,更多關(guān)于Linux ext4文件系統(tǒng)特性與優(yōu)化的資料請關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
Linux服務(wù)器NFS文件共享的實現(xiàn)方式
項目上用到文件服務(wù),文件存儲使用的是服務(wù)器本地磁盤,需要在多個服務(wù)器上部署文件服務(wù)以及在其他服務(wù)上面,也需要像讀取本地文件一樣讀取上傳上來的文件,所以本文給大家介紹了Linux服務(wù)器NFS文件共享的實現(xiàn)方式,需要的朋友可以參考下2025-10-10
Linux環(huán)境下快速搭建ftp服務(wù)器方法介紹
這篇文章主要介紹了Linux環(huán)境下快速搭建ftp服務(wù)器方法介紹,分享了相關(guān)代碼示例,小編覺得還是挺不錯的,具有一定借鑒價值,需要的朋友可以參考下2018-01-01
Linux下Oracle設(shè)置定時任務(wù)備份數(shù)據(jù)庫的教程
這篇文章主要介紹了Linux下Oracle設(shè)置定時任務(wù)備份數(shù)據(jù)庫的方法,本文給大家介紹的非常詳細(xì),具有一定的參考借鑒價值,需要的朋友可以參考下2019-11-11
Centos系統(tǒng)服務(wù)器查看端口是否開放的方法
本文介紹了在Centos系統(tǒng)服務(wù)器上如何查看端口是否開放的方法,通過telnet命令可以輕松實現(xiàn)。這對于服務(wù)器管理員來說非常重要,可以幫助他們及時發(fā)現(xiàn)端口問題并進(jìn)行修復(fù)。2023-03-03

