Bu belgede, Android'in kriptografik olanaklarının doğru şekilde nasıl kullanılacağı açıklanmakta ve bu olanakların kullanımına ilişkin bazı örnekler verilmektedir. Uygulamanız daha fazla anahtar güvenliği gerektiriyorsa Android anahtar deposu sistemini kullanın.
Yalnızca Android anahtar deposu sistemiyle sağlayıcı belirtme
Android anahtar deposu sistemini kullanıyorsanız bir sağlayıcı belirtmeniz gerekir.
Ancak diğer durumlarda Android, belirli bir algoritma için belirli bir sağlayıcıyı garanti etmez. Android Keystore sistemini kullanmadan sağlayıcı belirtmek, gelecekteki sürümlerde uyumluluk sorunlarına neden olabilir.
Önerilen bir algoritma seçme
Hangi algoritmayı kullanacağınızı seçme özgürlüğünüz olduğunda (ör. üçüncü taraf bir sistemle uyumluluk gerekmediğinde) aşağıdaki algoritmaları kullanmanızı öneririz:
Sınıf | Öneri |
---|---|
Cipher | 256 bit anahtarlarla CBC veya GCM modunda AES (ör. AES/GCM/NoPadding ) |
MessageDigest | SHA-2 ailesi (ör. SHA-256 ) |
Mac | SHA-2 ailesi HMAC'si (ör. HMACSHA256 ) |
İmza | ECDSA ile SHA-2 ailesi (ör. SHA256withECDSA ) |
Yaygın kriptografik işlemleri gerçekleştirme
Aşağıdaki bölümlerde, uygulamanızda yaygın kriptografik işlemleri nasıl tamamlayabileceğinizi gösteren kod snippet'leri yer almaktadır.
İletileri şifreleme
Kotlin
val plaintext: ByteArray = ... val keygen = KeyGenerator.getInstance("AES") keygen.init(256) val key: SecretKey = keygen.generateKey() val cipher = Cipher.getInstance("AES/CBC/PKCS5PADDING") cipher.init(Cipher.ENCRYPT_MODE, key) val ciphertext: ByteArray = cipher.doFinal(plaintext) val iv: ByteArray = cipher.iv
Java
byte[] plaintext = ...; KeyGenerator keygen = KeyGenerator.getInstance("AES"); keygen.init(256); SecretKey key = keygen.generateKey(); Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5PADDING"); cipher.init(Cipher.ENCRYPT_MODE, key); byte[] ciphertext = cipher.doFinal(plaintext); byte[] iv = cipher.getIV();
Mesaj özeti oluşturma
Kotlin
val message: ByteArray = ... val md = MessageDigest.getInstance("SHA-256") val digest: ByteArray = md.digest(message)
Java
byte[] message = ...; MessageDigest md = MessageDigest.getInstance("SHA-256"); byte[] digest = md.digest(message);
Dijital imza oluşturma
İmzalama anahtarını içeren bir PrivateKey
nesneniz olmalıdır. Bu nesneyi çalışma zamanında oluşturabilir, uygulamanızla birlikte paketlenmiş bir dosyadan okuyabilir veya ihtiyaçlarınıza bağlı olarak başka bir kaynaktan alabilirsiniz.
Kotlin
val message: ByteArray = ... val key: PrivateKey = ... val s = Signature.getInstance("SHA256withECDSA") .apply { initSign(key) update(message) } val signature: ByteArray = s.sign()
Java
byte[] message = ...; PrivateKey key = ...; Signature s = Signature.getInstance("SHA256withECDSA"); s.initSign(key); s.update(message); byte[] signature = s.sign();
Dijital imzayı doğrulama
İmzalayanın ortak anahtarını içeren bir PublicKey
nesneniz olmalıdır. Bu nesneyi uygulamanızla birlikte paketlenmiş bir dosyadan okuyabilir, sertifikadan çıkarabilir veya ihtiyaçlarınıza bağlı olarak başka bir kaynaktan alabilirsiniz.
Kotlin
val message: ByteArray = ... val signature: ByteArray = ... val key: PublicKey = ... val s = Signature.getInstance("SHA256withECDSA") .apply { initVerify(key) update(message) } val valid: Boolean = s.verify(signature)
Java
byte[] message = ...; byte[] signature = ...; PublicKey key = ...; Signature s = Signature.getInstance("SHA256withECDSA"); s.initVerify(key); s.update(message); boolean valid = s.verify(signature);
Uygulama karmaşıklıkları
Android kriptografi uygulamasında, alışılmadık gibi görünen ancak uyumluluk sorunları nedeniyle mevcut olan bazı ayrıntılar vardır. Bu bölümde, en sık karşılaşacağınız sorunlar ele alınmaktadır.
OAEP MGF1 mesaj özeti
RSA OAEP şifreleri, iki farklı ileti özetiyle parametrelendirilir: "ana" özet ve MGF1 özeti. Cipher
karma adları içeren tanımlayıcılar vardır. Örneğin, Cipher.getInstance("RSA/ECB/OAEPwithSHA-256andMGF1Padding")
, ana karmayı belirtir ve MGF1 karmasını belirtilmemiş olarak bırakır. Android
Keystore için MGF1 özetinde SHA-1 kullanılırken diğer Android
şifreleme sağlayıcılarında iki özet aynıdır.
Uygulamanızın kullandığı özetler üzerinde daha fazla kontrol sahibi olmak için Cipher.getInstance("RSA/ECB/OAEPPadding")
örneğindeki gibi OAEPPadding ile bir şifre isteyin ve her iki özeti de açıkça seçmek için init()
'ye OAEPParameterSpec
sağlayın.
Bu durum, aşağıdaki kodda gösterilmektedir:
Kotlin
val key: Key = ... val cipher = Cipher.getInstance("RSA/ECB/OAEPPadding") .apply { // To use SHA-256 the main digest and SHA-1 as the MGF1 digest init(Cipher.ENCRYPT_MODE, key, OAEPParameterSpec("SHA-256", "MGF1", MGF1ParameterSpec.SHA1, PSource.PSpecified.DEFAULT)) // To use SHA-256 for both digests init(Cipher.ENCRYPT_MODE, key, OAEPParameterSpec("SHA-256", "MGF1", MGF1ParameterSpec.SHA256, PSource.PSpecified.DEFAULT)) }
Java
Key key = ...; Cipher cipher = Cipher.getInstance("RSA/ECB/OAEPPadding"); // To use SHA-256 the main digest and SHA-1 as the MGF1 digest cipher.init(Cipher.ENCRYPT_MODE, key, new OAEPParameterSpec("SHA-256", "MGF1", MGF1ParameterSpec.SHA1, PSource.PSpecified.DEFAULT)); // To use SHA-256 for both digests cipher.init(Cipher.ENCRYPT_MODE, key, new OAEPParameterSpec("SHA-256", "MGF1", MGF1ParameterSpec.SHA256, PSource.PSpecified.DEFAULT));
Kullanımdan kaldırılan işlevler
Aşağıdaki bölümlerde desteği sonlandırılan işlevler açıklanmaktadır. Uygulamanızda kullanmayın.
Bouncy Castle algoritmaları
Birçok algoritmanın Bouncy Castle uygulamaları kullanımdan kaldırılmıştır. Bu durum yalnızca aşağıdaki örnekte gösterildiği gibi Bouncy Castle sağlayıcısını açıkça istediğiniz durumları etkiler:
Kotlin
Cipher.getInstance("AES/CBC/PKCS7PADDING", "BC") // OR Cipher.getInstance("AES/CBC/PKCS7PADDING", Security.getProvider("BC"))
Java
Cipher.getInstance("AES/CBC/PKCS7PADDING", "BC"); // OR Cipher.getInstance("AES/CBC/PKCS7PADDING", Security.getProvider("BC"));
Yalnızca Android anahtar deposu sistemiyle sağlayıcı belirtme hakkındaki bölümde belirtildiği gibi, belirli bir sağlayıcıyı istemeniz önerilmez. Bu yönergeye uyarsanız bu kullanımdan kaldırma işleminden etkilenmezsiniz.
Başlatma vektörü olmayan şifre tabanlı şifreleme şifreleri
Başlatma vektörü (IV) gerektiren parola tabanlı şifreleme (PBE) şifreleri, uygun şekilde oluşturulmuşsa anahtardan veya açıkça iletilen bir IV'den başlatma vektörü alabilir. IV içermeyen bir PBE anahtarı iletirseniz ve açık bir IV iletmezseniz Android'deki PBE şifreleri şu anda sıfır IV'yi varsayar.
PBE şifreleri kullanırken her zaman aşağıdaki kod snippet'inde gösterildiği gibi açık bir IV iletin:
Kotlin
val key: SecretKey = ... val cipher = Cipher.getInstance("PBEWITHSHA256AND256BITAES-CBC-BC") val iv = ByteArray(16) SecureRandom().nextBytes(iv) cipher.init(Cipher.ENCRYPT_MODE, key, IvParameterSpec(iv))
Java
SecretKey key = ...; Cipher cipher = Cipher.getInstance("PBEWITHSHA256AND256BITAES-CBC-BC"); byte[] iv = new byte[16]; new SecureRandom().nextBytes(iv); cipher.init(Cipher.ENCRYPT_MODE, key, new IvParameterSpec(iv));
Kripto para sağlayıcı
Android 9'dan (API düzeyi 28) itibaren Crypto Java Cryptography Architecture (JCA) sağlayıcısı kaldırıldı. Uygulamanız aşağıdaki yöntemi çağırarak Crypto sağlayıcısının bir örneğini isterse NoSuchProviderException
oluşur.
Kotlin
SecureRandom.getInstance("SHA1PRNG", "Crypto")
Java
SecureRandom.getInstance("SHA1PRNG", "Crypto");
Jetpack security-crypto kitaplığı
security-crypto
Jetpack kitaplığındaki tüm API'lerin desteği, sürüm 1.1.0
'ün kararlı sürümünde sonlandırıldı.
Bu kitaplığın sonraki sürümleri yayınlanmayacak.
Uygulama modülünüzün build.gradle
dosyasında aşağıdaki bağımlılıklardan herhangi biri varsa kullanımdan kaldırma ek açıklamaları görünür:
Groovy
dependencies { implementation "androidx.security:security-crypto:1.1.0" // or implementation "androidx.security:security-crypto-ktx:1.1.0" }
Kotlin
dependencies { implementation("androidx.security:security-crypto:1.1.0") // or implementation("androidx.security:security-crypto-ktx:1.1.0") }
Desteklenen algoritmalar
Android'de desteklenen JCA algoritma tanımlayıcıları şunlardır:
AlgorithmParameterGenerator
AlgorithmParameters
CertPathBuilder
CertPathValidator
CertStore
CertificateFactory
Cipher
KeyAgreement
KeyFactory
KeyGenerator
KeyManagerFactory
KeyPairGenerator
KeyStore
Mac
MessageDigest
SSLContext
SSLEngine.Supported
SSLSocket.Supported
SecretKeyFactory
SecureRandom
Signature
TrustManagerFactory