constant-time-analysis

constant-time-analysis

熱門

偵測加密程式碼中的時間旁路漏洞。在實作或審查加密程式碼、遇到對機密值進行除法、依賴機密的分支,或有關常數時間程式設計的問題時使用,支援 C、C++、Go、Rust、Swift、Java、Kotlin、C#、PHP、JavaScript、TypeScript、Python 或 Ruby。

6317星標
544分支
更新於 2026/7/28
SKILL.md
readonlyread-only
name
constant-time-analysis
description

偵測加密程式碼中的時間旁路漏洞。在實作或審查加密程式碼、遇到對機密值進行除法、依賴機密的分支,或有關常數時間程式設計的問題時使用,支援 C、C++、Go、Rust、Swift、Java、Kotlin、C#、PHP、JavaScript、TypeScript、Python 或 Ruby。

常數時間分析

分析加密程式碼,偵測哪些操作會因執行時間變化而洩漏機密資料。

使用時機

使用者在寫加密程式碼? ──是──> 使用此技能
         │
         否
         │
         v
使用者在問時間攻擊? ──是──> 使用此技能
         │
         否
         │
         v
程式碼處理金鑰/令牌? ──是──> 使用此技能
         │
         否
         │
         v
跳過此技能

具體觸發條件:

  • 使用者實作簽章、加密或金鑰推導
  • 程式碼中對機密衍生的值使用 /% 運算子
  • 使用者提到「常數時間」、「時間攻擊」、「旁路」、「KyberSlash」
  • 審查名為 signverifyencryptdecryptderive_key 的函式

何時不該使用

  • 非加密程式碼(商業邏輯、UI 等)
  • 公開資料處理,時間洩漏不影響安全
  • 不處理機密、金鑰或驗證令牌的程式碼
  • 高階 API 使用,時間處理已由函式庫負責

語言選擇

根據副檔名或語言上下文,參考對應指南:

語言 副檔名 指南
C, C++ .c, .h, .cpp, .cc, .hpp references/compiled.md
Go .go references/compiled.md
Rust .rs references/compiled.md
Swift .swift references/swift.md
Java .java references/vm-compiled.md
Kotlin .kt, .kts references/kotlin.md
C# .cs references/vm-compiled.md
PHP .php references/php.md
JavaScript .js, .mjs, .cjs references/javascript.md
TypeScript .ts, .tsx references/javascript.md
Python .py references/python.md
Ruby .rb references/ruby.md

快速開始

# 分析任何支援的檔案類型
uv run {baseDir}/ct_analyzer/analyzer.py <source_file>

# 包含條件分支警告
uv run {baseDir}/ct_analyzer/analyzer.py --warnings <source_file>

# 過濾特定函式
uv run {baseDir}/ct_analyzer/analyzer.py --func 'sign|verify' <source_file>

# JSON 輸出,適合 CI
uv run {baseDir}/ct_analyzer/analyzer.py --json <source_file>

僅限原生編譯語言(C, C++, Go, Rust)

# 跨架構測試(建議)
uv run {baseDir}/ct_analyzer/analyzer.py --arch x86_64 crypto.c
uv run {baseDir}/ct_analyzer/analyzer.py --arch arm64 crypto.c

# 多種最佳化層級
uv run {baseDir}/ct_analyzer/analyzer.py --opt-level O0 crypto.c
uv run {baseDir}/ct_analyzer/analyzer.py --opt-level O3 crypto.c

VM 編譯語言(Java, Kotlin, C#)

# 分析 Java 位元組碼
uv run {baseDir}/ct_analyzer/analyzer.py CryptoUtils.java

# 分析 Kotlin 位元組碼(Android/JVM)
uv run {baseDir}/ct_analyzer/analyzer.py CryptoUtils.kt

# 分析 C# IL
uv run {baseDir}/ct_analyzer/analyzer.py CryptoUtils.cs

注意:Java、Kotlin 和 C# 編譯為位元組碼(JVM/CIL),在具有 JIT 編譯的虛擬機器上執行。分析器直接檢查位元組碼,而非 JIT 編譯後的原生碼。--arch--opt-level 旗標不適用於這些語言。

Swift(iOS/macOS)

# 分析 Swift 原生架構
uv run {baseDir}/ct_analyzer/analyzer.py crypto.swift

# 分析特定架構(iOS 裝置)
uv run {baseDir}/ct_analyzer/analyzer.py --arch arm64 crypto.swift

# 使用不同最佳化層級分析
uv run {baseDir}/ct_analyzer/analyzer.py --opt-level O0 crypto.swift

注意:Swift 像 C/C++/Go/Rust 一樣編譯為原生碼,因此使用組合語言層級分析,並支援 --arch--opt-level 旗標。

前置需求

語言 需求
C, C++, Go, Rust PATH 中有對應編譯器(gcc/clanggorustc
Swift Xcode 或 Swift 工具鏈(PATH 中有 swiftc
Java JDK,PATH 中有 javacjavap
Kotlin Kotlin 編譯器(kotlinc)+ JDK(PATH 中有 javap
C# .NET SDK + ilspycmddotnet tool install -g ilspycmd
PHP 安裝 VLD 擴充或 OPcache 的 PHP
JavaScript/TypeScript PATH 中有 Node.js
Python PATH 中有 Python 3.x
Ruby 支援 --dump=insns 的 Ruby

macOS 使用者:Homebrew 將 Java 和 .NET 安裝為「keg-only」。您必須將它們加入 PATH:

# 針對 Java(加入 ~/.zshrc)
export PATH="/opt/homebrew/opt/openjdk@21/bin:$PATH"

# 針對 .NET 工具(加入 ~/.zshrc)
export PATH="$HOME/.dotnet/tools:$PATH"

詳細設定說明與疑難排解請參閱 references/vm-compiled.md

快速參考

問題 偵測方式 修正方式
對機密值進行除法 DIV, IDIV, SDIV, UDIV Barrett 約減或乘以倒數
依賴機密的分支 JE, JNE, BEQ, BNE 常數時間選擇(cmov、位元遮罩)
機密比較 提前退出的 memcmp 使用 crypto/subtle 或常數時間比較
弱隨機數產生器 rand(), mt_rand, Math.random 使用加密安全隨機數產生器
以機密為索引的查表 陣列下標使用機密索引 位元切片查表

解讀結果

PASSED - 未偵測到可變時間操作。

FAILED - 發現危險指令。範例:

[ERROR] SDIV
  Function: decompose_vulnerable
  Reason: SDIV 有提前終止最佳化;執行時間取決於運算元值

驗證結果(避免誤判)

重要:並非每個被標記的操作都是漏洞。此工具沒有資料流分析——它會標記所有潛在危險的操作,無論它們是否涉及機密。

對於每個被標記的違規,請詢問:此操作的輸入是否依賴於機密資料?

  1. 識別函式的機密輸入(私鑰、明文、簽章、令牌)

  2. 追蹤資料流,從被標記的指令回溯到輸入

  3. 常見的誤判模式

    // 誤判:除法使用公開常數,非機密
    int num_blocks = data_len / 16;  // data_len 是長度,不是內容
    
    // 真陽性:除法涉及機密衍生的值
    int32_t q = secret_coef / GAMMA2;  // secret_coef 來自私鑰
    
  4. 記錄您的分析,針對每個被標記的項目

快速分類問題

問題 若是 若否
運算元是編譯期常數? 可能是誤判 繼續
運算元是公開參數(長度、計數)? 可能是誤判 繼續
運算元衍生自金鑰/明文/機密? 真陽性 可能是誤判
攻擊者能否影響運算元值? 真陽性 可能是誤判

限制

  1. 僅靜態分析:分析組合語言/位元組碼,而非執行時期行為。無法偵測快取時間或微架構旁路。

  2. 無資料流分析:標記所有危險操作,無論是否處理機密。需要人工審查。

  3. 編譯器/執行時期差異:不同的編譯器、最佳化層級和執行時期版本可能產生不同的輸出。

實際影響

  • KyberSlash(2023):後量子 ML-KEM 實作中的除法指令導致金鑰恢復
  • Lucky Thirteen(2013):CBC 填充驗證中的時間差異導致明文恢復
  • RSA 時間攻擊:早期實作透過除法時間洩漏私鑰位元

參考資料