OWASP kategorisi: MASVS-STORAGE: Depolama
Genel Bakış
Android 10 (API 29) veya önceki sürümleri hedefleyen uygulamalar kapsamlı depolamayı zorunlu kılmaz. Bu durumda, harici depolama alanında saklanan tüm verilere READ_EXTERNAL_STORAGE izni olan diğer uygulamalar erişebilir.
Etki
Android 10'u (API 29) veya daha eski bir sürümü hedefleyen uygulamalarda hassas veriler harici depolama alanında depolanıyorsa cihazdaki READ_EXTERNAL_STORAGE iznine sahip tüm uygulamalar bu verilere erişebilir. Bu durum, kötü amaçlı uygulamaların harici depolama alanında kalıcı veya geçici olarak depolanan hassas dosyalara sessizce erişmesine olanak tanır. Ayrıca, harici depolama alanındaki içeriğe sistemdeki herhangi bir uygulama tarafından erişilebildiğinden, WRITE_EXTERNAL_STORAGE iznini de bildiren kötü amaçlı uygulamalar, harici depolama alanında depolanan dosyaları (ör. kötü amaçlı veriler eklemek için) değiştirebilir. Uygulamaya yüklenen bu kötü amaçlı veriler, kullanıcıları yanıltmak veya kod yürütmek için tasarlanmış olabilir.
Çözümler
Kapsamlı depolama (Android 10 ve sonraki sürümler)
Android 10
Android 10'u hedefleyen uygulamalarda geliştiriciler, kapsamlı depolamayı açıkça etkinleştirebilir. Bu, AndroidManifest.xml dosyasında requestLegacyExternalStorage işaretini false olarak ayarlayarak yapılabilir. Kapsamlı depolama ile uygulamalar, harici depolama alanında yalnızca kendilerinin oluşturduğu dosyalara veya MediaStore API kullanılarak depolanan dosya türlerine (ör. ses ve video) erişebilir. Bu, kullanıcı gizliliğini ve güvenliğini korumaya yardımcı olur.
Android 11 ve sonraki sürümler
Android 11 veya sonraki sürümleri hedefleyen uygulamalarda işletim sistemi kapsamlı depolama kullanımını zorunlu kılar. Yani requestLegacyExternalStorage işaretini yok sayar ve uygulamaların harici depolama alanını istenmeyen erişime karşı otomatik olarak korur.
Hassas Veriler İçin Dahili Depolama Alanını Kullanma
Hedeflenen Android sürümünden bağımsız olarak, bir uygulamanın hassas verileri her zaman dahili depolamada saklanmalıdır. Android sanal alanı sayesinde dahili depolama alanına erişim, otomatik olarak sahip olan uygulamayla sınırlandırılır. Bu nedenle, cihazda root işlemi yapılmadığı sürece güvenli olduğu kabul edilebilir.
Hassas verileri şifreleme
Uygulamanın kullanım alanları, hassas verilerin harici depolama alanında saklanmasını gerektiriyorsa veriler şifrelenmelidir. Anahtarı güvenli bir şekilde depolamak için Android KeyStore'un kullanıldığı güçlü bir şifreleme algoritması önerilir.
Genel olarak, hassas verilerin depolandığı yer fark etmeksizin tüm hassas verilerin şifrelenmesi önerilen bir güvenlik uygulamasıdır.
Tam disk şifrelemenin (veya Android 10'dan itibaren dosya tabanlı şifrelemenin) verileri fiziksel erişime ve diğer saldırı vektörlerine karşı korumayı amaçlayan bir önlem olduğunu unutmamak önemlidir. Bu nedenle, aynı güvenlik önlemini sağlamak için harici depolama alanında tutulan hassas veriler uygulama tarafından da şifrelenmelidir.
Bütünlük kontrolleri gerçekleştirme
Verilerin veya kodun harici depolama alanından uygulamaya yüklenmesi gerektiği durumlarda, başka bir uygulamanın bu verilerle veya kodla oynamadığını doğrulamak için bütünlük kontrolleri yapılması önerilir. Dosyaların karma değerleri güvenli bir şekilde, tercihen şifrelenmiş olarak ve dahili depolama alanında saklanmalıdır.
Kotlin
package com.example.myapplication
import java.io.BufferedInputStream
import java.io.FileInputStream
import java.io.IOException
import java.security.MessageDigest
import java.security.NoSuchAlgorithmException
object FileIntegrityChecker {
@Throws(IOException::class, NoSuchAlgorithmException::class)
fun getIntegrityHash(filePath: String?): String {
val md = MessageDigest.getInstance("SHA-256") // You can choose other algorithms as needed
val buffer = ByteArray(8192)
var bytesRead: Int
BufferedInputStream(FileInputStream(filePath)).use { fis ->
while (fis.read(buffer).also { bytesRead = it } != -1) {
md.update(buffer, 0, bytesRead)
}
}
private fun bytesToHex(bytes: ByteArray): String {
val sb = StringBuilder()
for (b in bytes) {
sb.append(String.format("%02x", b))
}
return sb.toString()
}
@Throws(IOException::class, NoSuchAlgorithmException::class)
fun verifyIntegrity(filePath: String?, expectedHash: String): Boolean {
val actualHash = getIntegrityHash(filePath)
return actualHash == expectedHash
}
@Throws(Exception::class)
@JvmStatic
fun main(args: Array<String>) {
val filePath = "/path/to/your/file"
val expectedHash = "your_expected_hash_value"
if (verifyIntegrity(filePath, expectedHash)) {
println("File integrity is valid!")
} else {
println("File integrity is compromised!")
}
}
}
Java
package com.example.myapplication;
import java.io.BufferedInputStream;
import java.io.FileInputStream;
import java.io.IOException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
public class FileIntegrityChecker {
public static String getIntegrityHash(String filePath) throws IOException, NoSuchAlgorithmException {
MessageDigest md = MessageDigest.getInstance("SHA-256"); // You can choose other algorithms as needed
byte[] buffer = new byte[8192];
int bytesRead;
try (BufferedInputStream fis = new BufferedInputStream(new FileInputStream(filePath))) {
while ((bytesRead = fis.read(buffer)) != -1) {
md.update(buffer, 0, bytesRead);
}
}
byte[] digest = md.digest();
return bytesToHex(digest);
}
private static String bytesToHex(byte[] bytes) {
StringBuilder sb = new StringBuilder();
for (byte b : bytes) {
sb.append(String.format("%02x", b));
}
return sb.toString();
}
public static boolean verifyIntegrity(String filePath, String expectedHash) throws IOException, NoSuchAlgorithmException {
String actualHash = getIntegrityHash(filePath);
return actualHash.equals(expectedHash);
}
public static void main(String[] args) throws Exception {
String filePath = "/path/to/your/file";
String expectedHash = "your_expected_hash_value";
if (verifyIntegrity(filePath, expectedHash)) {
System.out.println("File integrity is valid!");
} else {
System.out.println("File integrity is compromised!");
}
}
}
Kaynaklar
- Kapsamlı depolama alanı
- READ_EXTERNAL_STORAGE
- WRITE_EXTERNAL_STORAGE
- requestLegacyExternalStorage
- Veri ve dosya depolamaya genel bakış
- Veri Depolama (Uygulamaya Özel)
- Kriptografi
- Anahtar deposu
- Dosya tabanlı şifreleme
- Tam disk şifreleme