Linux 內核信號量參數控制 System V 信號量 (IPC) 的資源上限,直接影響 Oracle、PostgreSQL、WebLogic、MQ 等企業級中間件的啟動與運行。本文詳細解析 /proc/sys/kernel/sem 四個參數含義、調優依據、臨時/永久修改方法、以及典型應用場景推薦值。
文件 /proc/sys/kernel/sem 包含四個數值 (空格分隔):
cat /proc/sys/kernel/sem
# 輸出示例:250 32000 32 128
| 位置 | 參數名 | 含義 | 默認值 (典型) | 調優影響 |
|---|---|---|---|---|
| 1 | SEMMSL | **單個信號量集最大信號量數** (semaphores per set) | 250 | 限制 semget(key, nsems, ...) 中 nsems 最大值。Oracle SGA 大頁/進程數多時需調大。 |
| 2 | SEMMNS | **系統全局最大信號量總數** (system-wide max semaphores) | 32000 | 所有信號量集的信號量數之和上限。理論上 SEMMNS >= SEMMSL * SEMMNI。 |
| 3 | SEMOPM | **單次 semop() 系統調用最大操作數** (max ops per semop call) | 32 | 限制一次 semop() 能執行的原子操作個數。複雜同步邏輯需調大。 |
| 4 | SEMMNI | **系統全局最大信號量集數量** (max number of semaphore sets/arrays) | 128 | 限制 semget() 能創建的集合總數。高併發應用創建大量集合時需調大。 |
| 場景 | SEMMSL | SEMMNS | SEMOPM | SEMMNI | 備註 |
|---|---|---|---|---|---|
| Oracle Database (單實例, 中小型) | 250-500 | 256000 | 100-256 | 1024-4096 | 參考 Oracle 安裝前檢查腳本 (CVU) 建議值 |
| Oracle RAC / 大型實例 | 500-1000 | 1024000 | 256-512 | 4096-8192 | 進程數、實例數多,信號量集多 |
| PostgreSQL (高併發) | 256 | 512000 | 64 | 2048 | 配合 max_connections, max_locks_per_transaction |
| WebLogic / JBoss / Tomcat (大量 JVM) | 250 | 320000 | 100 | 4096 | 每 JVM 可能創建多個信號量集 |
| IBM MQ / Kafka / RabbitMQ | 512 | 1024000 | 1024 | 8192 | 消息隊列大量同步原語 |
| 通用高併發服務器 (保守增大) | 500 | 512000 | 256 | 4096 | 無特定應用時的安全基線 |
# 1. 直接寫入 /proc (推薦簡單)
echo "500 512000 256 4096" > /proc/sys/kernel/sem
# 2. 或使用 sysctl
sysctl -w kernel.sem="500 512000 256 4096"
# 3. 驗證
cat /proc/sys/kernel/sem
sysctl kernel.sem
# 1. 寫入 /etc/sysctl.conf (或 /etc/sysctl.d/99-semaphore.conf 推薦模塊化)
echo "kernel.sem = 500 512000 256 4096" >> /etc/sysctl.conf
# 2. 立即生效
sysctl -p
# 或
sysctl --system
# 3. 驗證重啟後
# 重啟機器後執行 cat /proc/sys/kernel/sem 確認
注意:sysctl -w和/proc寫入**順序固定為 SEMMSL SEMMNS SEMOPM SEMMNI**,四個值缺一不可,空格分隔。
# 1. 查看當前使用情況
ipcs -s
# 輸出關鍵欄位:
# SEMS: 該集合信號量數 (≤ SEMMSL)
# NSEMS: 系統當前總信號量數 (≤ SEMMNS)
# 總集合數 (≤ SEMMNI)
# 2. 監控腳本 (Nagios/Zabbix/Prometheus node_exporter)
# 關鍵指標:使用率 = 當前值 / 限制值
# 告警閾值:> 80% 預警,> 95% 嚴重
# 3. 內核日志關注
dmesg -T | grep -i semaphore
# 出現 "semget: No space left on device" 或 "semop: Resource temporarily unavailable" 表明參數不足
| 報錯信息 | 原因參數 | 調整方向 |
|---|---|---|
semget: No space left on device (ENOSPC) | SEMMNI (集合數達上限) 或 SEMMNS (總信號量數達上限) | 增大 SEMMNI、SEMMNS |
semget: Invalid argument (EINVAL) nsems > SEMMSL | SEMMSL (單集信號量數不足) | 增大 SEMMSL |
semop: Argument list too long (E2BIG) nops > SEMOPM | SEMOPM (單次操作數不足) | 增大 SEMOPM |
semop: Resource temporarily unavailable (EAGAIN) 非阻塞模式下資源忙 | 綜合資源不足 | 綜合增大四參數 |
semvmx = 32767:信號量最大值 (單次操作增量上限)。semume = SEMOPM:撤銷結構體最大操作數,通常等於 SEMOPM。semusz = 20:每個撤銷結構體條目數。semvmx (極罕見),內核啟動參數:semvmx=65535。ipcs -s 觀察當前使用量/限制比。SEMMSL ≥ max(nsems),SEMMNS ≥ SEMMSL * SEMMNI,SEMOPM ≥ max(nops),SEMMNI ≥ 總集合數峰值 * 1.5。/etc/sysctl.d/99-semaphore.conf,執行 sysctl --system。科學調優信號量參數,是保障企業級中間件穩定運行、避免「No space left on device」假象性磁盤錯誤的關鍵基礎設施工作。