Tanda tangani, verifikasi, mengenkripsi dan mendekripsi menggunakan kantong aman di iOS dan macOS.
Mendukung Kode FaceID, TouchID, Device Pass dan Kata Sandi Aplikasi.
Menggunakan kerangka keamanan bisa sedikit membingungkan. Itulah mengapa saya membuat ini. Anda dapat menggunakannya sebagai contoh kode dan panduan atau Anda dapat menggunakannya sebagai kerangka mikro.
Saya merasa sulit untuk mengetahui cara menggunakan SecKeyRawVerify , SecKeyGeneratePair dan SecItemCopyMatching C API di Swift 3, tetapi implementasinya cukup lurus ke depan berkat fitur Swift yang luar biasa.
Cukup seret Sources/EllipticCurveKeyPair.swift Sources/SHA256.swift
pod EllipticCurveKeyPair github "agens-no/EllipticCurveKeyPair" Ada banyak kemungkinan hebat dengan kantong aman. Berikut adalah beberapa contoh
Hanya tersedia di iOS 10 ke atas
Kasing penggunaan bisa
Untuk lebih banyak contoh, lihat aplikasi demo.
struct KeyPair {
static let manager : EllipticCurveKeyPair . Manager = {
let publicAccessControl = EllipticCurveKeyPair . AccessControl ( protection : kSecAttrAccessibleAlwaysThisDeviceOnly , flags : [ ] )
let privateAccessControl = EllipticCurveKeyPair . AccessControl ( protection : kSecAttrAccessibleAfterFirstUnlockThisDeviceOnly , flags : [ . userPresence , . privateKeyUsage ] )
let config = EllipticCurveKeyPair . Config (
publicLabel : " payment.sign.public " ,
privateLabel : " payment.sign.private " ,
operationPrompt : " Confirm payment " ,
publicKeyAccessControl : publicAccessControl ,
privateKeyAccessControl : privateAccessControl ,
token : . secureEnclave )
return EllipticCurveKeyPair . Manager ( config : config )
} ( )
}Anda juga dapat dengan anggun untuk menggunakan gantungan kunci jika Enclave aman tidak tersedia dengan menggunakan berbagai bendera kontrol akses:
let privateAccessControl = EllipticCurveKeyPair . AccessControl ( protection : kSecAttrAccessibleAfterFirstUnlockThisDeviceOnly , flags : {
return EllipticCurveKeyPair . Device . hasSecureEnclave ? [ . userPresence , . privateKeyUsage ] : [ . userPresence ]
} ( ) ) Dalam hal ini Anda perlu ingat untuk mengatur variabel token di objek Config ke .secureEnclaveIfAvailable .
do {
let key = try KeyPair . manager . publicKey ( ) . data ( ) . DER // Data
} catch {
// handle error
}Lihat Aplikasi Demo untuk Contoh Bekerja
do {
let key = try KeyPair . manager . publicKey ( ) . data ( ) . PEM // String
} catch {
// handle error
} do {
let digest = " some text to sign " . data ( using : . utf8 ) !
let signature = try KeyPair . manager . sign ( digest , hash : . sha256 )
} catch {
// handle error
}Anda juga dapat melewati objek lacontext saat menandatangani
do {
let digest = " some text to encrypt " . data ( using : . utf8 ) !
let encrypted = try KeyPair . manager . encrypt ( digest , hash : . sha256 )
} catch {
// handle error
}Anda juga dapat mengenkripsi pada perangkat/OS/platform yang berbeda menggunakan kunci publik. Jika Anda ingin mengetahui semua detail tentang cara mengenkripsi dalam format Enclave yang aman dipahami, maka Anda harus perlu membaca tulisan yang hebat ini oleh @dschuetz!
https://darthnull.org/security/2018/05/31/secure-enclave-ecies/
do {
let encrypted = ...
let decrypted = try KeyPair . manager . decrypt ( encrypted , hash : . sha256 )
let decryptedString = String ( data : decrypted , encoding : . utf8 )
} catch {
// handle error
}Anda juga dapat melewati objek lacontext saat mendekripsi
Hal yang paling umum adalah menangkap kesalahan yang terkait dengan
Dengan do/catch :
do {
let decrypted = try KeyPair . manager . decrypt ( encrypted )
} catch EllipticCurveKeyPair . Error . underlying ( _ , let underlying ) where underlying . code == errSecUnimplemented {
print ( " Unsupported device " )
} catch EllipticCurveKeyPair . Error . authentication ( let authenticationError ) where authenticationError . code == . userCancel {
print ( " User cancelled/dismissed authentication dialog " )
} catch {
print ( " Some other error occurred. Error ( error ) " )
} Dengan if let :
if case let EllipticCurveKeyPair . Error . underlying ( _ , underlying ) = error , underlying . code == errSecUnimplemented {
print ( " Unsupported device " )
} else if case let EllipticCurveKeyPair . Error . authentication ( authenticationError ) , authenticationError . code == . userCancel {
print ( " User cancelled/dismissed authentication dialog " )
} else {
print ( " Some other error occurred. Error ( error ) " )
} Untuk memeriksa kueri yang bolak -balik ke gantungan kunci, Anda dapat mencetak untuk menghibur setiap mutasi yang dilakukan perpustakaan ini pada gantungan kunci seperti ini
EllipticCurveKeyPair . logger = { print ( $0 ) } Di aplikasi demo Anda akan melihat bahwa setiap kali Anda membuat tanda tangan beberapa informasi berguna dicatat ke konsol.
Output contoh
#! /bin/sh
echo 414243 | xxd -r -p > dataToSign.dat
echo 3046022100842512baa16a3ec9b977d4456923319442342e3fdae54f2456af0b7b8a09786b022100a1b8d762b6cb3d85b16f6b07d06d2815cb0663e067e0b2f9a9c9293bde8953bb | xxd -r -p > signature.dat
cat > key.pem << EOF
-----BEGIN PUBLIC KEY-----
MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEdDONNkwaP8OhqFTmjLxVcByyPa19
ifY2IVDinFei3SvCBv8fgY8AU+Fm5oODksseV0sd4Zy/biSf6AMr0HqHcw==
-----END PUBLIC KEY-----
EOF
/usr/local/opt/openssl/bin/openssl dgst -sha256 -verify key.pem -signature signature.dat dataToSign.datUntuk menjalankan skrip ini, Anda bisa
verify.shchmod u+x verify.sh./verify.shMaka Anda harus melihat
Verified OKPS: Skrip ini akan membuat 4 file di direktori Anda saat ini.
Kerangka Kerja Keamanan, Swift 3, Swift 4, Swift, SeckeyRawverify, SeckeyGeneratePair, SecitemCopyMatching, SecP256R1, Elliptic Curve Cryptography, ECDSA, ECDH, Asn.1, Apple, iOS, Mac OS, KSECATtrKeyTypeecSsprimerandom, KSYPECECEDETYPEECSCRIMERDOM ksecattrtokenIdsecureEnclave, lacontext, localAuthentication, faceId, face ID, touchid, sentuh id, kata sandi aplikasi, pin perangkat, devicepin
Trailofbits menerbitkan beberapa kode objektif-C beberapa waktu lalu yang sangat membantu! Terima kasih telah berbagi Tidas dan SecureEnclavecrypto. Mereka juga mendapatkan beberapa proyek paling menarik lainnya. Lihatlah!
Dia berbagi som wawasan yang sangat berharga sehubungan dengan mengekspor kunci publik dalam format Der X.509 yang tepat.
Kelas SHA256 (awalnya SHA2.swift ) ditemukan di Perpustakaan Cryptoswift yang tak ternilai oleh Marcin Krzyżanowski. Kelas telah banyak diubah untuk menghapusnya ke minimum untuk apa yang kami butuhkan dalam proyek ini.
Mengapa saya tidak diminta dengan pin Touch ID / perangkat pada simulator?
Simulator tidak memiliki kantong yang aman dan karenanya mencoba mengaksesnya hanya akan menyebabkan kesalahan. Jika Anda menetapkan
fallbackToKeychainIfSecureEnclaveIsNotAvailablemenjaditruemaka kunci pribadi akan disimpan di gantungan kunci pada simulator sehingga mudah untuk menguji aplikasi Anda pada simulator juga.
Di mana saya bisa belajar lebih banyak?
Lihat video ini di WWDC 2015 tentang keamanan secara umum atau klik di sini untuk melewatkan ke bagian tentang Enclave Aman.
Mengapa dibungkus dengan enum?
Saya mencoba menyeimbangkan drag-dan-lepas file yang Anda butuhkan ke Xcode dan mendukung manajer ketergantungan seperti Carthage dan Cocoapods secara bersamaan. Jika Anda memiliki ide yang lebih baik atau tidak setuju dengan keputusan ini, saya senang membahas alternatif :)
Kami akan melakukannya? untuk mendengar pendapat Anda tentang perpustakaan ini. Apakah Anda suka atau tidak. Harap ajukan masalah jika ada sesuatu yang ingin Anda lihat ditingkatkan. Anda dapat menghubungi saya sebagai @hfossli di Twitter dan di tempat lain. ?