Перейти к содержанию

Возможность доступа к произвольному файлу через getParcelableExtra

Критичность: ВЫСОКИЙ
Способ обнаружения: IAST

Описание

Дефект возникает, когда компонент приложения (как правило, экспортируемая Activity или Service) извлекает из входящего Intent объект Uri через getParcelableExtra() и использует его для чтения или копирования файла без валидации. Поскольку Intent приходит от внешнего отправителя, злоумышленник может подсунуть file:// или content://-Uri, указывающий на приватные файлы атакуемого приложения, и спровоцировать их чтение, копирование во внешнее хранилище или отправку на сервер.

Это классический сценарий кражи файлов из песочницы (file theft) через подмену Uri в неявном/явном Intent (часто в обработчиках ACTION_SEND).

Пример уязвимого кода:

// Uri полностью контролируется отправителем Intent
Uri uri = getIntent().getParcelableExtra(Intent.EXTRA_STREAM);

// файл по контролируемому пути читается и, например, копируется в доступное место
InputStream in = getContentResolver().openInputStream(uri);
File out = new File(getExternalFilesDir(null), "uploaded.dat");
copy(in, new FileOutputStream(out));   // приватный файл вытек во внешнее хранилище

Злоумышленник отправляет:

Intent i = new Intent("com.example.IMPORT");
i.setClassName("com.example.victim", "com.example.victim.ImportActivity");
i.putExtra(Intent.EXTRA_STREAM,
        Uri.parse("file:///data/data/com.example.victim/databases/secret.db"));
startActivity(i);

Проблема

  1. Кража приватных данных — приложение само (с собственными правами) читает файл из своей песочницы (/data/data/<pkg>/...) и помещает его туда, откуда злоумышленник может его забрать (внешнее хранилище, экспортируемый ContentProvider, сеть).
  2. Path Traversal — отсутствие нормализации пути позволяет через ../ выйти за пределы ожидаемого каталога (CWE-22).
  3. Доступ к файлам других приложений / системы — при наличии у приложения соответствующих прав непроверенный Uri может указывать на чужие данные.
  4. Эксплуатация через content://Uri может ссылаться на чужой ContentProvider, что приводит к непреднамеренному раскрытию или перезаписи данных.

Рекомендации

  1. Не доверяйте Uri из внешнего Intent. Не используйте напрямую file://-пути, полученные от других приложений.

  2. Канонизируйте и проверяйте путь перед доступом, убеждаясь, что он находится внутри разрешённого каталога:

    File base = new File(getFilesDir(), "imports").getCanonicalFile();
    File target = new File(base, name).getCanonicalFile();
    if (!target.getPath().startsWith(base.getPath() + File.separator)) {
        throw new SecurityException("Path traversal attempt");
    }
    

  3. Запрещайте file://-схему для входящих Uri; принимайте только content:// и обрабатывайте их через ContentResolver с проверкой источника.

  4. Используйте FileProvider и временные права доступа (FLAG_GRANT_READ_URI_PERMISSION) для контролируемого обмена файлами вместо передачи произвольных путей.

  5. Ограничивайте экспорт компонентов: android:exported="false" либо защита permission уровня signature, если приём файлов не предназначен для сторонних приложений.

  6. Проверяйте вызывающую сторону (getCallingActivity() / проверка package) для чувствительных операций импорта.

Ссылки

  1. https://developer.android.com/privacy-and-security/risks/path-traversal
  2. https://developer.android.com/reference/androidx/core/content/FileProvider
  3. https://developer.android.com/training/secure-file-sharing
  4. https://mas.owasp.org/MASTG/0x05h-Testing-Platform-Interaction/
  5. https://cwe.mitre.org/data/definitions/22.html
  6. https://cwe.mitre.org/data/definitions/264.html
К началу