APISIX: التوافق مع معيار FIPS 140-2

Jinhua Luo

January 6, 2023

Products

ما هو FIPS 140-2؟

FIPS تعني معايير معالجة المعلومات الفيدرالية، وهي مجموعة من معايير أمن الكمبيوتر التي أنشأتها وزارة التجارة الأمريكية عبر المعهد الوطني للمعايير والتكنولوجيا (NIST).

هدف FIPS هو إنشاء مستوى موحد من الأمان لجميع الوكالات الفيدرالية لحماية المعلومات الحساسة ولكن غير المصنفة - وهي جزء كبير من البيانات الإلكترونية التي لا تعتبر سرية أو أعلى.

مستويات أمان FIPS 140-2

FIPS 140-2/3 هي معايير مستخدمة بشكل متكرر في سياق الأمن السيبراني. كلاهما يتعلق بالمتطلبات الأمنية القياسية لوحدات التشفير. FIPS 140-3 سيحل في النهاية محل FIPS 140-2، وهذه العملية الانتقالية جارية حاليًا.

  • المستوى 1 – أدنى مستوى أمان يفرض الحد الأدنى من المتطلبات ويتطلب أن تكون جميع المكونات "من درجة الإنتاج". FIPS 140-2 المستوى 1 يتعلق بشكل خاص بوحدات التشفير البرمجية ويحدد الشروط حول خوارزميات التشفير التي يمكن استخدامها والاختبارات الذاتية التي يجب إجراؤها للتحقق من سلامتها.
  • المستوى 2 – متطلبات إضافية لـ دليل العبث المادي بالإضافة إلى المصادقة القائمة على الأدوار.
  • المستوى 3 – التزام إضافي بـ تعزيز الأمان ضد المهاجمين، واستخدام المصادقة القائمة على الهوية، بالإضافة إلى الفصل المادي بين الواجهات.
  • المستوى 4 – المستوى الأكثر صرامة الذي يتطلب إجراءات أمنية مادية قوية ضد الهجمات البيئية.

على سبيل المثال، وحدة التشفير التي تم التحقق منها وفقًا لـ FIPS 140-2 المستوى 1 توفر ذلك المستوى الأساسي من الأمان عن طريق تشفير البيانات التي تمر عبرها إلى مستوى الحماية الذي يوفرها AES. ومع ذلك، وحدة التشفير التي تم التحقق منها وفقًا لـ FIPS 140-2 المستوى 2 لا توفر فقط تشفير AES الإلكتروني ولكن أيضًا الأمان المادي للجهاز نفسه.

هذا يعني أن وحدة التشفير التي تم التحقق منها وفقًا لـ FIPS 140-2 المستوى 2 لا يمكن العبث بها إلا إذا تم كسر الأختام على غلاف الحل، وفي هذه الحالة سيعلم ما يسمى بضابط التشفير على الفور أن أمان المعلومات قد تم اختراقه ويمكنها بعد ذلك اتخاذ إجراء فوري لمعالجة أي خرق للبيانات.

لماذا FIPS مهم؟

وحدات التشفير التي تم التحقق منها وفقًا لـ FIPS 140-2 مطلوبة بموجب القانون لجميع الوكالات الفيدرالية الأمريكية التي تتعامل مع معلومات حساسة ولكن غير مصنفة. كما أن قطاعات صناعية أخرى تجعل FIPS 140-2 المستوى 2 عنصرًا غير قابل للتفاوض لأمان النقل الخلفي الخاص بها، بما في ذلك التمويل، والرعاية الصحية، والخدمات القانونية، ومشغلي الهواتف المحمولة، وصناعات السلامة العامة.

APISIX متوافق مع FIPS 140-2

كيف تكون متوافقًا مع FIPS 140-2؟

عند استخدامه مع إصدار OpenSSL 3.0 الذي تم التحقق منه وفقًا لـ FIPS 140-2 ويعمل في وضع FIPS، فإن APISIX متوافق مع متطلبات FIPS 140-2 (المستوى 1) فيما يتعلق بفك تشفير وتشفير حركة مرور الشبكة المشفرة بـ SSL/TLS.

التأثيرات

وضع FIPS يعطل الشفرات التالية:

  • TLS_ECDH_anon_WITH_RC4_128_SHA
  • TLS_ECDHE_RSA_WITH_RC4_128_SHA
  • TLS_RSA_WITH_CAMELLIA_128_CBC_SHA
  • TLS_RSA_WITH_CAMELLIA_256_CBC_SHA
  • TLS_RSA_WITH_IDEA_CBC_SHA
  • TLS_RSA_WITH_RC4_128_MD5
  • TLS_RSA_WITH_RC4_128_SHA
  • TLS_RSA_WITH_SEED_CBC_SHA

كما أن FIPS لا يدعم مفاتيح RSA أصغر من 2048 بت.

بناء OpenSSL

بناء وتثبيت OpenSSL مع تمكين FIPS

apt install -y build-essential
git clone https://github.com/openssl/openssl
cd openssl
./Configure --prefix=/usr/local/openssl-3.0 enable-fips
make install
bash -c "echo /usr/local/openssl-3.0/lib64 > /etc/ld.so.conf.d/openssl3.conf"
ldconfig
/usr/local/openssl-3.0/bin/openssl fipsinstall -out /usr/local/openssl-3.0/ssl/fipsmodule.cnf \
-module /usr/local/openssl-3.0/lib64/ossl-modules/fips.so
sed_expr='s@# .include fipsmodule.cnf@.include /usr/local/openssl-3.0/ssl/fipsmodule.cnf@g;'
sed_expr+=' s/# \(fips = fips_sect\)/\1\nbase = base_sect\n\n[base_sect]\nactivate=1\n/g'
sed -i "$sed_expr" /usr/local/openssl-3.0/ssl/openssl.cnf

bash -c "echo /usr/local/openssl-3.0/lib64 > /etc/ld.so.conf.d/openssl3.conf"
ldconfig

التحقق من OpenSSL

تحقق من ملف التكوين (/usr/local/openssl-3.0/ssl/openssl.cnf).

تأكد من أنه يتطابق مع المقتطف التالي:

config_diagnostics = 1
openssl_conf = openssl_init

.include /usr/local/ssl/fipsmodule.cnf

[openssl_init]
providers = provider_sect

[provider_sect]
fips = fips_sect
base = base_sect

[base_sect]
activate = 1

تحديد ما إذا كان OpenSSL يمكنه تنفيذ تجزئات SHA1: هذا الاختبار يتحقق من التشغيل الصحيح لـ OpenSSL. خوارزمية التجزئة SHA1 مسموح بها في جميع الأوضاع، لذا فإن فشل هذا الأمر يشير إلى أن تنفيذ OpenSSL لا يعمل بشكل صحيح:

# openssl sha1 /dev/null
SHA1(/dev/null)= da39a3ee5e6b4b0d3255bfef95601890afd80709

تحديد ما إذا كان OpenSSL يمكنه تنفيذ تجزئات MD5: هذا الاختبار يتحقق من أن OpenSSL يعمل في وضع FIPS. MD5 ليست خوارزمية تجزئة مسموح بها في وضع FIPS، لذا فإن محاولة استخدامها تفشل:

# openssl md5 /dev/null
Error setting digest
80920FA8DA7F0000:error:0308010C:digital envelope routines:
inner_evp_generic_fetch:unsupported:crypto/evp/evp_fetch.c:341:
Global default library context, Algorithm (MD5 : 100), Properties ()

إذا كان OpenSSL لا يعمل في وضع FIPS، فإن وظيفة تجزئة MD5 تعمل بشكل طبيعي:

# /usr/bin/openssl md5 /dev/null
MD5(/dev/null)= d41d8cd98f00b204e9800998ecf8427e

بناء APISIX مع FIPS

# تثبيت تبعيات pcre و zlib
wget -O - https://openresty.org/package/pubkey.gpg | apt-key add -
echo "deb http://openresty.org/package/${arch_path}ubuntu $(lsb_release -sc) main" | \
tee /etc/apt/sources.list.d/openresty.list
apt-get update
apt-get install -y openresty-pcre-dev openresty-zlib-dev

# تحديد خيارات التجميع والربط
export zlib_prefix=/usr/local/openresty/zlib
export pcre_prefix=/usr/local/openresty/pcre
export cc_opt="-DNGX_LUA_ABORT_AT_PANIC -I${zlib_prefix}/include -I${pcre_prefix}/include"
cc_opt+="-I/usr/local/openssl-3.0/include"
export ld_opt="-L${zlib_prefix}/lib -L${pcre_prefix}/lib -L/usr/local/openssl-3.0/lib64"
ld_opt+="-Wl,-rpath,${zlib_prefix}/lib:${pcre_prefix}/lib:/usr/local/openssl-3.0/lib64"

# بناء وتثبيت apisix-base
wget https://raw.githubusercontent.com/api7/apisix-build-tools/master/build-apisix-base.sh
bash build-apisix-base.sh latest

تكوين مسار اختبار

curl http://127.0.0.1:9180/apisix/admin/routes/httpbin -H 'X-API-KEY: YOUR-KEY' -X PUT -i -d '
{
    "uri": "/anything",
    "hosts": ["*.httpbin.org"],
    "methods": ["GET"],
    "upstream": {
        "type": "roundrobin",
        "nodes": {
            "httpbin.org": 1
        }
    }
}'

اختبار التحقق من المفتاح الخاص

اختبار الحالة العادية، نتوقع أن تكون ناجحة.

إنشاء نص برمجي مساعد بلغة Python لتحميل الشهادة:

cfg_ssl.py

import sys
import requests

if len(sys.argv) <= 3:
    print("bad argument")
    sys.exit(1)

with open(sys.argv[1]) as f:
    cert = f.read()

with open(sys.argv[2]) as f:
    key = f.read()

sni = sys.argv[3]
api_key = "edd1c9f034335f136f87ad84b625c8f1"

resp = requests.put("http://127.0.0.1:9180/apisix/admin/ssls/1", json={
    "cert": cert,
    "key": key,
    "snis": [sni],
}, headers={
    "X-API-KEY": api_key,
})
print(resp.status_code)
print(resp.text)

إنشاء دالة bash لتسهيل إنشاء المفاتيح:

genkey() {
    keylen=${1:-4096}
    /usr/bin/openssl genrsa -out apisix.key $keylen
    /usr/bin/openssl req -key apisix.key -new -out apisix.csr -subj '/C=/ST=/L=/O=/OU=web/CN=*.httpbin.org'
    /usr/bin/openssl x509 -req -in apisix.csr -signkey apisix.key -out apisix.crt -days 3650 -sha256
}

اختبار:

cd $(mktemp -d)
genkey 2048
python3 ssl.py apisix.crt apisix.key '*.httpbin.org'
curl --resolve 'www.httpbin.org:9443:127.0.0.1' https://www.httpbin.org:9443/uuid -vvv -k

الإخراج:

...
* TLSv1.3 (OUT), TLS handshake, Finished (20):
* SSL connection using TLSv1.3 / TLS_AES_256_GCM_SHA384
* ALPN, server accepted to use h2
* Server certificate:
*  subject: OU=web; CN=*.httpbin.org
*  start date: Dec 22 05:52:58 2022 GMT
*  expire date: Dec 19 05:52:58 2032 GMT
*  issuer: OU=web; CN=*.httpbin.org
*  SSL certificate verify result: self signed certificate (18), continuing anyway.
* Using HTTP2, server supports multi-use
* Connection state changed (HTTP/2 confirmed)
* Copying HTTP/2 data in stream buffer to connection buffer after upgrade: len=0
* Using Stream ID: 1 (easy handle 0x55e125a24e30)
> GET /uuid HTTP/2
> Host: www.httpbin.org:9443
> user-agent: curl/7.68.0
> accept: */*
>
* TLSv1.3 (IN), TLS handshake, Newsession Ticket (4):
* TLSv1.3 (IN), TLS handshake, Newsession Ticket (4):
* old SSL session ID is stale, removing
* Connection state changed (MAX_CONCURRENT_STREAMS == 128)!
< HTTP/2 200
< content-type: application/json
< content-length: 53
< date: Thu, 22 Dec 2022 06:35:04 GMT
< access-control-allow-origin: *
< access-control-allow-credentials: true
< server: APISIX/3.0.0
<
{
  "uuid": "1827f239-376f-47ec-9b54-d5addaa8c7f9"
}

اختبار مفتاح أصغر من 2048 بت

FIPS لا يدعم مفاتيح RSA أصغر من 2048 بت. لذا، دعونا نختبر ما إذا كان سيفشل مع مفتاح صغير.

genkey 1024
python3 cfg_ssl.py apisix.crt apisix.key '*.httpbin.org'
curl --resolve 'www.httpbin.org:9443:127.0.0.1' https://www.httpbin.org:9443/uuid -vvv -k

الإخراج:

...
* TLSv1.3 (OUT), TLS handshake, Client hello (1):
* TLSv1.3 (IN), TLS alert, internal error (592):
* error:14094438:SSL routines:ssl3_read_bytes:tlsv1 alert internal error
* Closing connection 0
curl: (35) error:14094438:SSL routines:ssl3_read_bytes:tlsv1 alert internal error

الخلاصة

نظرًا للاختبارات الصارمة التي تتضمنها FIPS، فإنها تعتبر معيارًا أمنيًا موثوقًا. بالإضافة إلى ذلك، فهي خط أساس مفيد لأي كيانات تحتاج إلى تنفيذ معايير أمنية داخل بنيتها التحتية.

من السهل إضافة دعم FIPS في APISIX. يمكن استخدام APISIX لفك تشفير وتشفير حركة مرور الشبكة المشفرة بـ SSL/TLS في النشرات التي تتطلب الامتثال لـ FIPS 140-2 المستوى 1.

لمزيد من المعلومات حول بوابة API، يرجى زيارة مدوناتنا أو الاتصال بنا.

Tags: