[Linux] 檢查 OpenSSL 是否掛載了 FIPS 模組

[Linux] 檢查 OpenSSL 是否掛載了 FIPS 模組

最近專案被要求支援 FIPS (Federal Information Processing Standards) 140-2

什麼是 FIPS 140-2呢?

基本上就是美國政府公認過、安全可用的演算法的集合,

所以有許多有規模的公司,也會要求採買的產品是符合這個規範的。

 

平常加解密常用的 OpenSSL,可以在加上一個 FIPS 模組之後,

限制那些不在 FIPS 允許清單內的功能,

像是 MD5 就會被禁止使用,

一呼叫到 MD5 相關的函式,就會吐出錯誤訊息之後 abort()…

而 MD5 還只是不被允許使用的眾多演算法之一…

 

麻煩的是,MD5 除了直接計算某個檔案內容的雜湊值外,

還可能用在其他地方,連帶使這些東西都不能用。

例如我們本來會支援 HTTP Proxy 中的 Basic、Digest 和 NTLM 等不同的驗證方式,

但因為 Digest/NTLM 這兩種驗證方式裡面都會用到 MD5,

所以它們就變成不能使用了!

 

不能用就算了,curl 在經由 Digest/NTLM proxy 時還會因此當掉,

這才是最糟糕的地方…

總不能跟客戶說,因為 FIPS 不允許 MD5,

所以我們的程式在這種情況下會當機 Orz…

 

現在找到的一個解法,是設定 CURLOPT_HTTPAUTH 這個選項,

把平常常用的 CURLAUTH_ANY 換成 CURLAUTH_BASIC,

這樣 curl 就不會去支援 Digest/NTLM,自然就不會去用到 OpenSSL MD5 函式而當機了~

proxy_auth = pycurl.HTTPAUTH_ANY

# When FIPS mode is enabled, http proxy only allow basic authentication
if is_fips_mode_enabled():
    proxy_auth = pycurl.HTTPAUTH_BASIC

# FIPS mode is disabled, NTLM can be used
elif is_ntlm:
    proxy_auth = pycurl.HTTPAUTH_NTLM

self._curl.setopt(pycurl.PROXYAUTH, proxy_auth)

 

至於要怎麼檢查現在是 FIPS 模式呢?

網路上有些作法是檢查系統設定:

cat /proc/sys/crypto/fips_enabled
sysctl crypto.fips_enabled

 

但以上的作法看起來是在 Linux Kernel 開啟 FIPS 模式才會有效,

像我們只是套用了 OpenSSL 的 FIPS 模組的話,

上面的設定都是 0,檢查不出 FIPS 有開啟…

 

後來發現最簡單的方式, 就是直接去執行 MD5 相關的東西,

會掛掉就是 FIPS 模式了~

像是執行這段指令來試著產生 hashlib.md5() 物件,

但如果 OpenSSL FIPS 模組有掛上的話,就會跑出 exception:

python -c 'import hashlib; hashlib.md5()'

 

只要檢查 python 最後的 exit code 是否為 0,

0 的話表示現在不是 FIPS 模式,

非 0 值表示程式當掉,也就是 FIPS 有開囉~

 

另外一種方式是比較正規的,

就是去查詢 libcrypto 提供的 FIPS_mode() 函式,

回傳值如果是 1 就是有開 FIPS 模式囉:

import ctypes
libcrypto = ctypes.CDLL("libcrypto.so")

get_fips_mode = libcrypto.FIPS_mode
get_fips_mode.argtypes = []
get_fips_mode.restype = ctypes.c_int

fips_mode = get_fips_mode()

 

參考資料:

curl: Disable accepting MD5 certificates

stackoverflow: How to check FIPS 140-2 support in OpenSSL?

 

(本頁面已被瀏覽過 11 次)

發表迴響

你的電子郵件位址並不會被公開。

This site uses Akismet to reduce spam. Learn how your comment data is processed.