憑證透明度 Certificate Transparency 機制

Certificate Transparency - CT Logs, SCT Verification and Monitoring

憑證透明度(Certificate Transparency,CT)是一個開放的框架,用於監控和審計 SSL/TLS 憑證的簽發過程。它由 Google 於 2013 年提出,旨在解決憑證生態系統中的信任問題,特別是防止惡意或錯誤簽發的憑證被濫用。

CT 簡介與目的

什麼是 Certificate Transparency?

Certificate Transparency 是一套公開、可審計的憑證日誌系統。所有由公開信任的憑證授權中心(CA)簽發的 SSL/TLS 憑證都應該被記錄到 CT 日誌中,讓網域擁有者和安全研究人員能夠監控和驗證憑證的簽發情況。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
傳統憑證簽發流程:
+--------+     +-----+     +----------+
| 申請者 | --> | CA  | --> | 憑證     |
+--------+     +-----+     +----------+
                              |
                              v
                         直接使用(無公開記錄)

CT 機制下的憑證簽發流程:
+--------+     +-----+     +----------+     +----------+
| 申請者 | --> | CA  | --> | CT 日誌  | --> | 憑證+SCT |
+--------+     +-----+     +----------+     +----------+
                              |
                              v
                         公開可查詢

CT 的目的

CT 機制主要解決以下問題:

  • 偵測惡意簽發:當 CA 被入侵或內部人員惡意操作時,能夠被及時發現
  • 發現錯誤簽發:CA 在驗證流程中的失誤導致的錯誤簽發能被追蹤
  • 提高透明度:所有憑證簽發都有公開記錄,增強整體生態系統的信任
  • 快速應對:網域擁有者能夠即時發現未授權的憑證簽發並採取行動

CT 的歷史背景

CT 的誕生源自多起重大的憑證安全事件:

年份事件影響
2011DigiNotar 被入侵為 google.com 等網域簽發了假憑證
2011Comodo 附屬 RA 被入侵多個主要網域的假憑證被簽發
2013TURKTRUST 事件錯誤簽發了中繼 CA 憑證
2015CNNIC/MCS Holdings簽發了未授權的 Google 網域憑證

這些事件顯示,即使是知名的 CA 也可能出現安全問題,因此需要一個公開透明的監控機制。

CT 運作機制

基本架構

CT 系統由以下主要元件組成:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
+------------------+
|   憑證授權中心    |
|      (CA)        |
+--------+---------+
         |
         | 1. 提交憑證
         v
+------------------+
|    CT 日誌       |
|  (CT Log Server) |
+--------+---------+
         |
         | 2. 返回 SCT
         v
+------------------+
|    SCT          |
| (Signed         |
|  Certificate    |
|  Timestamp)     |
+------------------+
         |
         | 3. 附加到憑證
         v
+------------------+     +------------------+
|   網頁伺服器     | --> |    瀏覽器        |
+------------------+     +--------+---------+
                                  |
                                  | 4. 驗證 SCT
                                  v
                         +------------------+
                         |   CT 日誌        |
                         +------------------+

運作流程詳解

1. 預先簽發記錄(Pre-certificate Logging)

CA 在正式簽發憑證前,先將「預憑證」(Pre-certificate)提交到 CT 日誌:

1
2
3
4
5
6
預憑證結構:
+------------------------------------------+
| 與正式憑證幾乎相同                         |
| 但包含特殊的 poison 擴充欄位               |
| OID: 1.3.6.1.4.1.11129.2.4.3             |
+------------------------------------------+

2. SCT 簽發

CT 日誌伺服器接收到預憑證後,會返回一個 SCT(Signed Certificate Timestamp):

1
2
3
4
5
6
7
8
SCT 結構:
+------------------------------------------+
| 版本 (Version)                            |
| 日誌 ID (Log ID)                          |
| 時間戳記 (Timestamp)                       |
| 擴充欄位 (Extensions)                      |
| 數位簽章 (Signature)                       |
+------------------------------------------+

3. 憑證簽發

CA 將收到的 SCT 嵌入最終憑證中,完成簽發流程。

SCT 傳遞方式

SCT 可以透過三種方式傳遞給用戶端:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
方式一:嵌入憑證(X.509 Extension)
+------------------+
|    憑證          |
|  +------------+  |
|  |   SCT      |  |
|  | Extension  |  |
|  +------------+  |
+------------------+

方式二:TLS 擴充(TLS Extension)
+------------------+     +------------------+
|   TLS Handshake  | --> | signed_          |
|                  |     | certificate_     |
|                  |     | timestamp        |
+------------------+     +------------------+

方式三:OCSP Stapling
+------------------+     +------------------+
|   OCSP Response  | --> |   SCT            |
+------------------+     +------------------+

CT 日誌

CT 日誌的結構

CT 日誌使用 Merkle Tree(梅克爾樹)資料結構來儲存憑證:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
                    +------------------+
                    |    Root Hash     |
                    +--------+---------+
                             |
              +--------------+--------------+
              |                             |
     +--------v---------+         +--------v---------+
     |    Hash(A+B)     |         |    Hash(C+D)     |
     +--------+---------+         +--------+---------+
              |                             |
       +------+------+               +------+------+
       |             |               |             |
  +----v----+   +----v----+     +----v----+   +----v----+
  | Hash(A) |   | Hash(B) |     | Hash(C) |   | Hash(D) |
  +---------+   +---------+     +---------+   +---------+
       |             |               |             |
  +----v----+   +----v----+     +----v----+   +----v----+
  | Cert A  |   | Cert B  |     | Cert C  |   | Cert D  |
  +---------+   +---------+     +---------+   +---------+

Merkle Tree 的優點:

  • 高效驗證:可以快速證明某憑證是否存在於日誌中
  • 防篡改:任何修改都會改變根雜湊值
  • 一致性證明:可以驗證日誌的完整性和一致性

主要的 CT 日誌服務

目前有多個組織營運 CT 日誌服務:

營運者日誌名稱狀態
GoogleArgon, Xenon, Icarus運作中
CloudflareNimbus運作中
DigiCertYeti, Nessie運作中
SectigoSabre, Mammoth運作中
Let’s EncryptOak運作中

日誌的要求

根據 Chrome CT 政策,受信任的 CT 日誌必須滿足:

  • 可用性:99% 以上的運行時間
  • 最大合併延遲(MMD):24 小時內將憑證加入日誌
  • 遵循規範:符合 RFC 6962 規範
  • 審計能力:支援一致性和包含性證明

SCT 驗證

驗證流程

瀏覽器驗證 SCT 的流程:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
+------------------+
|  收到憑證和 SCT   |
+--------+---------+
         |
         v
+------------------+
| 驗證 SCT 簽章     |
| (使用日誌公鑰)    |
+--------+---------+
         |
    簽章有效?
    /        \
   是         否
   |           |
   v           v
+----------+ +----------+
| 檢查時間戳 | | 驗證失敗 |
+----+-----+ +----------+
     |
     v
+------------------+
| 確認 SCT 數量     |
| 符合政策要求      |
+--------+---------+
         |
         v
+------------------+
|    驗證通過       |
+------------------+

Chrome 的 CT 要求

Chrome 對 SCT 的數量有特定要求:

1
2
3
4
5
6
7
8
9
憑證有效期 < 180 天:需要 2 個來自不同日誌的 SCT
憑證有效期 >= 180 天:
  - 有效期 < 15 個月:需要 2 個 SCT
  - 有效期 >= 15 個月 且 < 27 個月:需要 3 個 SCT
  - 有效期 >= 27 個月 且 < 39 個月:需要 4 個 SCT
  - 有效期 >= 39 個月:需要 5 個 SCT

註:自 2018 年起,Chrome 要求所有新簽發的公開信任憑證
    必須具有有效的 SCT

使用 OpenSSL 驗證 SCT

1
2
3
4
5
6
7
8
9
# 連接伺服器並顯示 SCT 資訊
openssl s_client -connect example.com:443 -ct

# 檢視憑證中嵌入的 SCT
openssl x509 -in certificate.crt -text -noout | grep -A 20 "CT Precertificate SCTs"

# 使用 openssl 顯示 SCT 詳細資訊
openssl s_client -connect example.com:443 2>/dev/null | \
    openssl x509 -text -noout | grep -A 50 "Precertificate"

手動解析 SCT

SCT 的二進位結構:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
+------------------------------------------+
| Version (1 byte)        | 0x00 (v1)      |
| Log ID (32 bytes)       | SHA-256 hash   |
| Timestamp (8 bytes)     | Unix 毫秒      |
| Extensions Length       | 變長           |
| Extensions              | 變長           |
| Hash Algorithm (1 byte) | 簽章雜湊演算法 |
| Signature Algorithm     | 簽章演算法     |
| Signature Length        | 簽章長度       |
| Signature               | 數位簽章       |
+------------------------------------------+

監控與查詢

CT 監控的重要性

網域擁有者應該監控 CT 日誌以:

  • 偵測未授權簽發:發現未經授權的憑證簽發
  • 追蹤憑證庫存:了解自己網域的所有有效憑證
  • 安全事件應對:及時發現並應對安全威脅

常用的 CT 查詢工具

1. crt.sh

crt.sh 是由 Sectigo 營運的免費 CT 日誌搜尋服務:

1
2
3
4
5
6
7
8
# 使用 curl 查詢特定網域的憑證
curl -s "https://crt.sh/?q=example.com&output=json" | jq '.'

# 查詢特定組織的憑證
curl -s "https://crt.sh/?q=organization&output=json" | jq '.'

# 查詢包含萬用字元的憑證
curl -s "https://crt.sh/?q=%.example.com&output=json" | jq '.'

2. Google Certificate Transparency Search

1
2
3
4
5
網址:https://transparencyreport.google.com/https/certificates
功能:
- 搜尋特定網域的憑證
- 檢視憑證詳細資訊
- 追蹤憑證時間線

3. Censys

1
2
3
4
# 使用 Censys 搜尋特定網域的憑證
# 需要 API 金鑰
curl -s "https://search.censys.io/api/v2/certificates/search?q=names:example.com" \
    -H "Authorization: Basic <API_KEY>"

自建 CT 監控系統

使用 certspotter 進行監控:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
# 安裝 certspotter
go install software.sslmate.com/src/certspotter/cmd/certspotter@latest

# 設定監控網域
mkdir -p ~/.certspotter/watchlist
echo "example.com" >> ~/.certspotter/watchlist

# 執行監控
certspotter

# 設定 cron job 定期執行
# 在 crontab 中加入:
# 0 * * * * /path/to/certspotter 2>&1 | logger -t certspotter

使用 Python 查詢 CT 日誌

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
import requests
import json
from datetime import datetime

def search_ct_logs(domain):
    """搜尋特定網域的 CT 日誌記錄"""
    url = f"https://crt.sh/?q={domain}&output=json"

    try:
        response = requests.get(url, timeout=30)
        response.raise_for_status()
        certificates = response.json()

        for cert in certificates:
            print(f"ID: {cert['id']}")
            print(f"Issuer: {cert['issuer_name']}")
            print(f"Common Name: {cert['common_name']}")
            print(f"Not Before: {cert['not_before']}")
            print(f"Not After: {cert['not_after']}")
            print("-" * 50)

        return certificates
    except Exception as e:
        print(f"Error: {e}")
        return []

# 使用範例
certificates = search_ct_logs("example.com")
print(f"找到 {len(certificates)} 個憑證")

監控最佳實踐

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
建議的監控策略:

1. 定期掃描
   +------------------+
   | 每小時查詢       |
   | CT 日誌          |
   +------------------+
           |
           v
2. 比對已知憑證
   +------------------+
   | 與內部憑證       |
   | 清單比對         |
   +------------------+
           |
           v
3. 異常警報
   +------------------+
   | 發現未知憑證     |
   | 時發送通知       |
   +------------------+
           |
           v
4. 事件應對
   +------------------+
   | 調查來源         |
   | 必要時撤銷       |
   +------------------+

警報設定範例

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
#!/bin/bash
# CT 監控腳本

DOMAIN="example.com"
KNOWN_CERTS="/path/to/known_certs.txt"
ALERT_EMAIL="security@example.com"

# 查詢 CT 日誌
NEW_CERTS=$(curl -s "https://crt.sh/?q=${DOMAIN}&output=json" | \
    jq -r '.[].id' | sort -u)

# 比對已知憑證
for cert_id in $NEW_CERTS; do
    if ! grep -q "$cert_id" "$KNOWN_CERTS"; then
        echo "發現新憑證: $cert_id"
        # 發送警報
        echo "發現新的 CT 日誌記錄: $cert_id" | \
            mail -s "CT Alert: ${DOMAIN}" "$ALERT_EMAIL"
        # 記錄到已知清單
        echo "$cert_id" >> "$KNOWN_CERTS"
    fi
done

總結

Certificate Transparency 是現代 PKI 生態系統中不可或缺的一環。透過公開、可審計的日誌系統,CT 機制大幅提高了憑證簽發的透明度,讓惡意或錯誤簽發的憑證能夠被及時發現。

重點回顧:

  • CT 目的:提高憑證簽發透明度,防止惡意簽發
  • 運作機制:CA 將憑證提交到 CT 日誌,獲得 SCT 作為證明
  • CT 日誌:使用 Merkle Tree 結構,確保資料完整性
  • SCT 驗證:瀏覽器驗證 SCT 的簽章和數量
  • 監控查詢:網域擁有者應定期監控 CT 日誌

參考資料

comments powered by Disqus
Built with Hugo
Theme Stack designed by Jimmy