Mobile BI 移動(dòng)商務(wù)智能的數(shù)字證書

這篇文章主要介紹了Mobile BI(移動(dòng)商務(wù)智能)在安全網(wǎng)絡(luò)通信中涉及的數(shù)字證書認(rèn)證的背景知識(shí)以及相應(yīng)實(shí)現(xiàn)的認(rèn)證功能。

文章的具體內(nèi)容包括:網(wǎng)絡(luò)的基礎(chǔ)知識(shí)(OSI模型、TLS),證書的信息(數(shù)字證書、證書的類別、證書文件擴(kuò)展名、系統(tǒng)支持、相關(guān)概念),證書的認(rèn)證(Server Certificate、Client Certificate - Download/Embedding/CSR、Certificate Pinning),iOS CodingOpenSSL引用

網(wǎng)絡(luò)基礎(chǔ)知識(shí)

OSI 模型

OSI Model 即 Open Systems Interconnection Model 開放式系統(tǒng)互聯(lián)通信參考模型

數(shù)據(jù)單元 協(xié)議 設(shè)備 功能
主機(jī)層 Host Layer Data 數(shù)據(jù) 應(yīng)用層 Application Layer HTTP、HTTPS、 FTP 為特定類型的網(wǎng)絡(luò)應(yīng)用提供了訪問OSI環(huán)境的手段
Data 數(shù)據(jù) 表示層 Presentation layer SSL、TLS、MIME 負(fù)責(zé)流經(jīng)節(jié)點(diǎn)的數(shù)據(jù)編碼的表示方式問題,保證信息可以被讀出;數(shù)據(jù)格式交換、數(shù)據(jù)加密和解密、數(shù)據(jù)壓縮
Data 數(shù)據(jù) 會(huì)話層 Session Layer Socket 管理不同主機(jī)上各種進(jìn)程之間的通信,建立、管理和終止應(yīng)用程序之間的會(huì)話
Segments 數(shù)據(jù)段 傳輸層 Session Layer TCP(Segment)、UDP(Datagram) 在網(wǎng)絡(luò)的各個(gè)節(jié)點(diǎn)之間可靠地分發(fā)數(shù)據(jù)包,端對(duì)端的數(shù)據(jù)傳輸服務(wù)機(jī)制;全雙工,半雙工,流控制,錯(cuò)誤恢復(fù)服務(wù)
媒介層 Media Layer Packet 數(shù)據(jù)包 網(wǎng)絡(luò)層 Network Layer IP 路由器、交換機(jī) 在網(wǎng)絡(luò)的各個(gè)節(jié)點(diǎn)之間進(jìn)行地址分配、路由和分發(fā)報(bào)文;通過尋址來建立兩個(gè)節(jié)點(diǎn)之間的鏈接;路徑選擇算法,將數(shù)據(jù)包送到目的地;擁塞控制,對(duì)流入的數(shù)據(jù)包數(shù)量進(jìn)行控制
Frame 數(shù)據(jù)幀 數(shù)據(jù)鏈路層 Data Link Layer WiFi、ATM、GPRS 網(wǎng)卡、網(wǎng)橋、交換機(jī) 一個(gè)可靠地點(diǎn)對(duì)點(diǎn)數(shù)據(jù)直連,解決兩個(gè)相鄰節(jié)點(diǎn)之間的通信問題;將數(shù)據(jù)分幀,在一條有可能出差錯(cuò)的物理連接上,進(jìn)行幾乎無差錯(cuò)的數(shù)據(jù)傳輸;物理地址MAC
Bit 比特 物理層 Physical Layer 集線器、中繼器、調(diào)制解調(diào)器、網(wǎng)線 一個(gè)不一定可靠的點(diǎn)對(duì)點(diǎn)數(shù)據(jù)直連,利用物理傳輸介質(zhì)為數(shù)據(jù)層提供物理連接

TLS

傳輸層安全協(xié)議 TLS Transport Layer Security 及其前身安全套接字層 SSL Secure Socket Layer 是一種安全協(xié)議,目的是為互聯(lián)網(wǎng)通信提供安全及數(shù)據(jù)完整性保障,即保證“信息加密”、“數(shù)據(jù)完整”以及“身份認(rèn)證”三方面的風(fēng)險(xiǎn)。

SSL 3.0 Google在2014年發(fā)布了3.0的設(shè)計(jì)缺陷,建議禁用此協(xié)議。在兼容SSL3.0的情況下,攻擊者可以向TLS發(fā)送虛假錯(cuò)誤提示,然后將安全連接降級(jí)到SSL3.0,然后利用此設(shè)計(jì)漏洞竊取敏感信息。

TLS 1.0 從技術(shù)上來看,與SSL 3.0類似,并包含可降級(jí)到SSL 3.0的實(shí)現(xiàn)。

TLS 1.1 于2006年發(fā)表,增加了對(duì)CBC攻擊的保護(hù)(隱式IV被替換成顯式IV,更改分組密碼模式中的填充錯(cuò)誤)等。

TLS 1.2 于2008年發(fā)表,基于TLS 1.1規(guī)范:

  • 偽隨機(jī)數(shù)可使用SHA-256替換MD5-SHA-1
  • 密鑰交換和協(xié)商 RSA
  • 加密算法 AES
  • 數(shù)據(jù)完整性 HMAC

TLS 1.3 仍是草案,持續(xù)加強(qiáng)安全等方面的標(biāo)準(zhǔn)。

與應(yīng)用層無關(guān),SSL/TLS是一個(gè)介于HTTP協(xié)議與TCP之間的一個(gè)可選層:


SSL協(xié)議可分為兩層:SSL記錄協(xié)議 SSL Record Protocol 建立在可靠的傳輸協(xié)議(如TCP)之上,為高層協(xié)議提供數(shù)據(jù)封裝、壓縮、加密等基本功能的支持;SSL握手協(xié)議 SSL Handshake Protocol 建立在SSL記錄協(xié)議之上,用于在實(shí)際的數(shù)據(jù)傳輸開始前,通訊雙方進(jìn)行身份認(rèn)證、協(xié)商加密算法、交換加密密鑰等

TLS協(xié)議類似,由TLS記錄協(xié)議 TLS Record 和 TLS 握手協(xié)議 TLS Handshake 組成,TLS記錄協(xié)議位于某個(gè)可靠的傳輸協(xié)議(如TCP)之上。

握手協(xié)議
雖然非對(duì)稱加密RSA可以確保網(wǎng)絡(luò)上信息交換的安全性,但是由于RSA加密的速度較慢,所以并不適合直接加密傳輸數(shù)據(jù),而一般只用于交換密鑰,另外再使用對(duì)稱加密AES高效的傳輸數(shù)據(jù)。

握手協(xié)議用來驗(yàn)證通信雙方的身份并協(xié)商通信密鑰:

客戶端發(fā)出請(qǐng)求 Client Hello:

  • 客戶端發(fā)出信息包含:所支持的協(xié)議版本、加密算法、壓縮方法,以及生產(chǎn)的一個(gè)隨機(jī)數(shù)(用于生成對(duì)話密鑰)

服務(wù)器回應(yīng) Server Hello:

  • 服務(wù)器回應(yīng)信息包括:確認(rèn)支持的協(xié)議版本、加密算法,服務(wù)器生成的隨機(jī)數(shù)(用于生成對(duì)話密鑰),服務(wù)器證書
  • 對(duì)服務(wù)器的一種認(rèn)證:服務(wù)器證書,由數(shù)字證書認(rèn)證機(jī)構(gòu)CA審核后頒發(fā)的電子證書,包含一個(gè)私鑰和公鑰,公鑰附在證書的信息中,另外證書還包含電子簽名來確保證書的完整性和真實(shí)性,以及有效期。
  • 對(duì)客戶端認(rèn)證:同樣的對(duì)客戶端也可以進(jìn)行證書認(rèn)證
  • 隨機(jī)數(shù):客戶端和服務(wù)端都需要使用這兩個(gè)隨機(jī)數(shù)來產(chǎn)生對(duì)話密鑰 Master Secret

客戶端回應(yīng) Certificate Verify:

  • Client Key Exchange:如果需要對(duì)客戶端進(jìn)行驗(yàn)證,首先需要發(fā)送客戶端證書以便服務(wù)器端來驗(yàn)證
  • Certificate Verify,客戶端驗(yàn)證通過后會(huì)獲得服務(wù)器的公鑰后,發(fā)送下列信息:第三個(gè)隨機(jī)數(shù)(使用服務(wù)器公鑰加密)、編碼改變通知(后繼信息使用協(xié)商的加密方法和密鑰發(fā)送)、客戶端握手結(jié)束通知(一般為發(fā)送內(nèi)容的hash值,用來服務(wù)器校驗(yàn))
  • ChangeCipherSpec協(xié)議在數(shù)據(jù)包中就是一個(gè)字節(jié)的數(shù)據(jù),用于告知服務(wù)端,客戶端已經(jīng)準(zhǔn)備好。

服務(wù)器的最后回應(yīng) Server Finish:

  • 服務(wù)器得到加密數(shù)據(jù)后使用私鑰進(jìn)行解密,并對(duì)數(shù)據(jù)進(jìn)行驗(yàn)證,會(huì)使用跟客戶端同樣的方式生成 會(huì)話密鑰 Session Secret
  • ChangeCipherSpec 完成后同樣發(fā)送,表示服務(wù)器也準(zhǔn)備好
  • 服務(wù)器端同樣使用會(huì)話密鑰加密一段Finish消息發(fā)送給客戶端,以驗(yàn)證之前通過握手建立起來的安全通道是否成功。

幾個(gè)密鑰 Secret

  • PreMaster Secret:是在客戶端使用RSA等加密算法生成的。用來跟服務(wù)端和客戶端在Hello階段產(chǎn)生的隨機(jī)數(shù)結(jié)合在一起生成Master Secret;在客戶端使用服務(wù)器端的公鑰對(duì)PreMaster Secret進(jìn)行加密之后傳送給服務(wù)器端,而服務(wù)器端使用私鑰進(jìn)行解密得到PreMaster Secret,這樣兩方都有一份相同的PreMaster Secret和隨機(jī)數(shù)。
  • Master Secret:根據(jù)上面提到的信息,客戶端和服務(wù)器端都可以計(jì)算出相同的Master Secret,而這個(gè)將作為最終Session Key的Key Material(包含MAC,Encryption Key,IV等)的一部分信息。

證書的信息

數(shù)字證書

數(shù)字證書 Digital Certificate 即 Public Key Certificate/Identity Certificate 是用來證明公鑰歸屬的一個(gè)電子證書:

A digital certificate certifies the ownership of a public key by the named subject of the certificate, and indicates certain expected usages of that key.

This allows others (relying parties) to rely upon signatures or on assertions made by the private key that corresponds to the certified public key.

X.509 定義了數(shù)字證書的格式標(biāo)準(zhǔn),它的結(jié)構(gòu)如下:

Certificate
  - Version Number
  - Serial Number
  - Signature Algorithm ID
  - Issuer Name
  - Validity period
    - Not Before
    - Not After
  - Subject name
  - Subject Public Key Info
    - Public Key Algorithm
    - Subject Public Key
  - Issuer Unique Identifier (optional)
  - Subject Unique Identifier (optional)
  - Extensions (optional)
    - ...
Certificate Signature Algorithm
Certificate Signature

證書的類別

TLS/SSL Server Certificate:用來驗(yàn)證服務(wù)器身份,包括是否符合"hostname"以及是否是可信任的"CA"頒發(fā)

TLS/SSL Client Certificate:用來驗(yàn)證客戶端身份

Root Certificate:用來簽發(fā)其他證書的自簽名證書

Intermediate Certificate:用來簽發(fā)其他證書的非自簽名證書,它必須被其他中間證書或者根證書簽發(fā)

Self-signed Certificate:這種證書擁有可以與它的發(fā)布者匹配的主題,以及可以通過它自己的公鑰驗(yàn)證的簽名

證書文件擴(kuò)展名

證書一般有兩種編碼格式:

  • DER Distinguished Encoding Rules:二進(jìn)制格式
  • PEM Privacy Enhanced Electronic Mail:Base64編碼

證書會(huì)以不同的后綴文件出現(xiàn):

  • .pem 即Base64編碼的DER證書
  • .der, .cer, .crt 即二進(jìn)制DER格式,不絕對(duì),也可能使用PEM編碼
  • .p7b, .p7c 即PKCS#7結(jié)構(gòu),僅包含Certificate/CRL
  • .p12 即 PKCS#12 "Public Key Cryptography Standards 12" 包含證書和私鑰,私鑰被密碼保護(hù)
  • .pfx 即PFX為PKCS#12的前身

系統(tǒng)支持

Mac和Windows都有專門的處理證書的地方,我們可以從中了解它們所支持的不同的格式和所包含的信息:

Mac: From Keychain Access, Save Certificate
- Certificate (.cer)
- Privacy Enhanced Mail (.pem)
- Certificate Bundle (.p7b)
- Personal Information Exchange (.p12)

Windows: From IE
- DER encoded binary X.509 (.CER)
- Base-64 encoded X.509 (.CER)
- Cryptographic Message Syntax Standard - PKCS #7 Certificates (.P7B)
  - Include all certificates in the certification path if possible
- Personal Information Exchange - PKCS #12 (.PFX)
  - Include all certificates in the certification path if possible
  - Delete the private key if the export is successful
  - Export all extended properties
- Microsoft Serialized Certificate Store (.SST)

相關(guān)概念

CA Certificate Authority/Certification Authority 是用來簽發(fā)數(shù)字證書的可信任的第三方

Certificate Chain 是指一個(gè)證書列表鏈,通常第一個(gè)是CA證書,而最后一個(gè)是Self-signed Certificate

CSR Certificate Signing Request 證書簽名請(qǐng)求,包含一個(gè)公鑰

CRL Certificate Revocation List 證書吊銷列表

KEY: 用來存放一個(gè)公鑰或者私鑰,非證書

JKS: Java Key Storage Java的專利

PKI: Public Key Infrastructure 公鑰基礎(chǔ)設(shè)施,支持公開密鑰管理并能支持認(rèn)證、加密、完整性和可追究性服務(wù)的基礎(chǔ)設(shè)施

證書的認(rèn)證

從上面的介紹我們已經(jīng)可以了解網(wǎng)絡(luò)通信安全的核心在于SSL安全協(xié)議,而SSL的核心在于證書的驗(yàn)證。所以這里就介紹一下在Mobile BI安全網(wǎng)絡(luò)實(shí)施過程中涉及的關(guān)于證書認(rèn)證的功能。

Server Certificate

這是最常見的服務(wù)器身份驗(yàn)證,交換密鑰,確保數(shù)據(jù)加密安全傳輸。使用CSR保留私鑰,使用公鑰申請(qǐng),CA認(rèn)證。

iOS中會(huì)收到NSURLAuthenticationMethodServerTrust的Challenge,而一般而言,我們不需要在應(yīng)用中處理,而直接通過在設(shè)備上安裝根證書來自動(dòng)驗(yàn)證服務(wù)器證書。

Issue: Server Certificate doesn’t work in iOS8.1
這是因?yàn)槲覀兡J(rèn)的證書不是一個(gè)完整的證書鏈,而僅僅是一個(gè)單獨(dú)的證書,在iOS8.1中需要使用完整的證書鏈來認(rèn)證:

iOS8 is less permissive as iOS7

  • Add the intermediate certificates in the server certificate and got it working
  • in iOS8, add intermediate certificates in the server certificate and keep only the root in the device

Client Certificate - Download

相應(yīng)的對(duì)客戶端的認(rèn)證,需要客戶端提供一個(gè)證書,在與服務(wù)器進(jìn)行握手協(xié)議時(shí)發(fā)送給服務(wù)器認(rèn)證。

這個(gè)功能是從應(yīng)用中向證書服務(wù)器請(qǐng)求獲取一個(gè)證書,而證書服務(wù)器會(huì)生成一個(gè)PKCS#12文件發(fā)送給應(yīng)用,客戶端下載證書后會(huì)保存在Keychain中。這種方式的缺點(diǎn)也顯而易見:私鑰需要通過網(wǎng)絡(luò)傳遞給客戶端,并且客戶端就這么無驗(yàn)證的接受一個(gè)證書也可能存在風(fēng)險(xiǎn),比如中間人攻擊這種。

Issue:Handshake in Apache
這個(gè)問題的表現(xiàn)是在一個(gè)WebView中無法處理Client Certificate Challenge,一般情況下,當(dāng)我們回答一次后就完成了,但是這個(gè)問題卻表現(xiàn)為持續(xù)收到來自 Apache Server的Challenge,同樣的問題在 Tomcat Server中卻不存在。

這是因?yàn)?Apache Server采用了更加嚴(yán)格的握手協(xié)議,對(duì)于客戶端證書,它的默認(rèn)配置即為每次連接都會(huì)要求驗(yàn)證。對(duì)于這個(gè)問題,我們需要修改httpd.conf的配置 SSLSessionCache dbm:/var/cache/apache2/sslcache

Client Certificate - Embedding

這是使用客戶端證書的另一種方法,即默認(rèn)客戶端證書嵌入安裝包,使用Plist配置密碼,或者運(yùn)行時(shí)輸入密碼來提取證書,而不需要從證書服務(wù)器上下載。這種方式的缺點(diǎn)也很明顯:不同的設(shè)備會(huì)使用同一個(gè)證書。

Issue:Certificate Chain

使用Client Certificate Chain認(rèn)證,在Tomcat 6/7 中正常,但在 Tomcat 5.5 中會(huì)失敗,5.5需要使用單獨(dú)的證書。

Client Certificate - CSR

我們可以看到上面提到的 Download/Embedding 方式在安全性上都有問題,所以相應(yīng)的,CSR方式:設(shè)備自己生成CSR,保留私鑰,而將公鑰證書發(fā)送到證書服務(wù)器獲取簽名認(rèn)證后使用。這種方式既保證了私鑰不會(huì)通過網(wǎng)絡(luò)傳送,并且不同的設(shè)備將擁有不同的客戶端證書。

Certificate Pinning

在我們驗(yàn)證服務(wù)器證書時(shí),即使它可以被可信任CA認(rèn)證,也可能存在某種風(fēng)險(xiǎn),比如CA認(rèn)證的疏漏,或者遭遇到的中間人攻擊。所以更安全的方式是我們限定認(rèn)證某個(gè)范圍內(nèi)的證書:這可以是某個(gè)特定的證書或者更小范圍的根證書。

一般而言,當(dāng)應(yīng)用獲取到服務(wù)器證書后,客戶端需要使用可信任的驗(yàn)證數(shù)據(jù) "trusted validation data" 來驗(yàn)證,這種數(shù)據(jù)可以為下面兩種形式之一:

a trusted copy of that certificate
a trusted hash or fingerprint of that certificate or the certificate's public key

在Mobile BI中,Pinning的過程分為三步:TLS verification, Domain Evaluation, Pinning Verification。需要注意的是:

For each certificate we extract the SPKI and hash it with SHA-256 (hash is aka Fingerprint)

這里的SPKI 即 Subject Public Key Info,包含了 "public key"以及 "public key algorithm"。你可能注意到,這里沒有直接使用證書,而是使用了證書里面的SPKI,這是因?yàn)椋篊A證書經(jīng)常會(huì)被重新簽發(fā)不夠穩(wěn)定;多個(gè)證書可能具有相同的公鑰和主題名等,但是有效期卻不同,但事實(shí)上它們還是可被認(rèn)證的同一個(gè)證書。所以我們使用了不變的且可代表證書特性的SPKI。

我們需要從證書中提取SPKI:

Extracting public key

  • SecTrustCopyPublicKey(trust) provided by iOS
  • X509_get0_pubkey_bitstr(certificateX509) provided by OpenSSL

Extracting public key algorithm

  • We can use X509_get_pubkey(certificateX509) to get an EVP_PKEY object first
  • Then use its ->type variable (should be an integer) to decide the type of algorithm.
  • For example, if the type is 6, the algorithm should be RSA Encryption

Pinning大熱是由Google前兩年一次更新導(dǎo)致:Google列出了可被信任的白名單 Verisign, Google Internet Authority, Equifax and GeoTrust,對(duì)于其他CA簽發(fā)的證書不再認(rèn)可。

iOS Coding

關(guān)于id的引用SecIdentityRef

@abstract CFType representing an identity, which contains a SecKeyRef and an associated SecCertificateRef
typedef struct CF_BRIDGED_TYPE(id) SECTYPE(SecIdentity) *SecIdentityRef;

代表X.509證書的引用SecCertificateRef

@abstract CFType representing a X.509 certificate.
typedef struct CF_BRIDGED_TYPE(id) SECTYPE(SecCertificate) *SecCertificateRef;

獲得證書鏈中的證書數(shù)目的方法SecTrustGetCertificateCount

@abstract Returns the number of certificates in an evaluated certificate chain.
CFIndex SecTrustGetCertificateCount(SecTrustRef trust)

從證書鏈中獲取證書的方法SecTrustGetCertificateAtIndex,得到SecCertificateRef的證書引用:

@abstract Returns a certificate from the trust chain.
SecCertificateRef SecTrustGetCertificateAtIndex(SecTrustRef trust, CFIndex ix)

keychain中取得證書引用SecItemCopyMatching,可轉(zhuǎn)換成SecIdentityRef引用:

@abstract Returns one or more items which match a search query.
OSStatus SecItemCopyMatching(CFDictionaryRef query, CFTypeRef * __nullable result)

SecIdentityRef引用獲取證書引用的方法SecIdentityCopyCertificate

@abstract Returns a reference to a certificate for the given identity reference.
OSStatus SecIdentityCopyCertificate(
            SecIdentityRef identityRef,
            SecCertificateRef * __nonnull CF_RETURNS_RETAINED certificateRef)

導(dǎo)入證書文件的方法SecPKCS12Import

@abstract Imports the contents of a PKCS12 formatted blob.
OSStatus SecPKCS12Import(CFDataRef pkcs12_data, CFDictionaryRef options, CFArrayRef * __nonnull items)

獲取DER格式的X.509證書的方法SecCertificateCopyData

@abstract Return the DER representation of an X.509 certificate.
CFDataRef SecCertificateCopyData(SecCertificateRef certificate)

生成哈希值的方法CC_SHA256

extern unsigned char *CC_SHA256(const void *data, CC_LONG len, unsigned char *md)

證書的驗(yàn)證SecTrustEvaluate

@abstract Evaluates a trust reference synchronously.
OSStatus SecTrustEvaluate(SecTrustRef trust, SecTrustResultType * __nullable result)

OpenSSL

SSL是一種規(guī)范,而OpenSSL是SSL的一個(gè)實(shí)現(xiàn),順便還提供了相應(yīng)的工具軟件。之前曾出現(xiàn)過“心臟出血漏洞”,需要使用最新的版本來避免。

OpenSSL支持多種不同的加密算法

加密:AES, Blowfish, Camellia, SEED, CAST-128, DES, IDEA, RC2, RC4, RC5, Triple DES, GOST 28147-89[3]

散列函數(shù):MD5, MD2, SHA-1, SHA-2, RIPEMD-160, MDC-2, GOST R 34.11-94

公開密鑰加密:RSA, DSA, Diffie–Hellman key exchange, Elliptic curve, GOST R 34.10-2001

我們開發(fā)中涉及的OpenSSL的API:從二進(jìn)制數(shù)據(jù)中獲取一個(gè)DER格式的X509證書d2i_X509,并提取public key以及algorithm

X509 *d2i_X509_AUX(X509 **a, const unsigned char **pp, long length);
ASN1_BIT_STRING *X509_get0_pubkey_bitstr(const X509 *x);
EVP_PKEY *X509_get_pubkey(X509 *x);

引用

Wikipedia OSI Model

Wikipedia TLS

SSL/TLS原理詳解

Wikipedia Certificate

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

推薦閱讀更多精彩內(nèi)容