Категория OWASP: MASVS-STORAGE: Хранилище
Обзор
В этом документе рассматривается несколько проблем, связанных с включением файлов, которые имеют схожие меры по снижению риска. Эти проблемы связаны с уязвимостями, возникающими при доступе к файлам в WebViews, и варьируются от опасных WebSettings
разрешающих доступ к файлам или включающих JavaScript, до метода WebKit, который создает запрос на выбор файла. Этот документ будет полезен, если вы ищете рекомендации по устранению проблем в WebView, возникающих из-за использования схемы file://
, неограниченного доступа к локальным файлам и межсайтовых сценариев.
Более конкретно, этот документ охватывает следующие темы:
-
WebSettings
— это класс, содержащий методы, которые управляют состояниями настроек для WebViews. Эти методы могут открыть WebViews для различных атак, которые будут описаны позже. В этом документе мы рассмотрим методы, относящиеся к доступу к файлам, и настройку, позволяющую выполнять JavaScript: - Методы
setAllowFileAccess
,setAllowFileAccessFromFileURLs
иsetAllowUniversalAccessFromFileURLs
можно использовать для предоставления доступа к локальным файлам с использованием URL-адреса файловой схемы (file://
). Однако они могут быть использованы вредоносными сценариями для доступа к произвольным локальным файлам, к которым у приложения есть доступ, например к их собственной папке/data/
. По этой причине эти методы были помечены как небезопасные и объявлены устаревшими в API 30 в пользу более безопасных альтернатив, таких какWebViewAssetLoader
. - Метод
setJavascriptEnabled
можно использовать для включения выполнения JavaScript в WebViews. Это делает приложения уязвимыми для файлового XSS. Пользователи и их данные подвергаются риску, особенно если они настроены на разрешение загрузки локальных файлов или ненадежного веб-контента, который может содержать исполняемый код, настроен на разрешение доступа к файлам, которые могут быть созданы или изменены внешними источниками, или позволяют веб-представлениям выполнять JavaScript. . -
WebChromeClient.onShowFileChooser
— это метод, принадлежащий пакетуandroid.webkit
, который предоставляет инструменты просмотра веб-страниц. Этот метод можно использовать, чтобы позволить пользователям выбирать файлы в WebView. Однако этой функцией можно злоупотреблять, поскольку WebViews не налагает ограничений на выбор файла.
Влияние
Влияние включения файла может зависеть от того, какие параметры WebSettings настроены в WebView. Чрезмерно широкие права доступа к файлам могут позволить злоумышленникам получить доступ к локальным файлам и украсть конфиденциальные данные, PII (персональную информацию) или данные частных приложений. Включение выполнения JavaScript может позволить злоумышленникам запускать JavaScript внутри WebView или на устройстве пользователя. Файлы, выбранные с помощью метода onShowFileChooser
могут поставить под угрозу безопасность пользователя, поскольку метод или WebView не могут гарантировать, что источник файла является надежным.
Риск: рискованный доступ к файлам через file://
Включение setAllowFileAccess
, setAllowFileAccessFromFileURLs
и setAllowUniversalAccessFromFileURLs
может разрешить злонамеренным намерениям и запросам WebView с контекстом file://
доступ к произвольным локальным файлам, включая файлы cookie WebView и личные данные приложения. Кроме того, использование метода onShowFileChooser
может позволить пользователям выбирать и загружать файлы из ненадежных источников.
Все эти методы могут привести к утечке личных данных, учетных данных для входа или других конфиденциальных данных, в зависимости от конфигурации приложения.
Смягчения
Проверка URL-адресов файлов
Если вашему приложению требуется доступ к файлам через URL-адреса file://
, важно внести в белый список только определенные URL-адреса, которые заведомо являются законными, чтобы избежать распространенных ошибок .
Используйте WebViewAssetLoader.
Используйте WebViewAssetLoader
вместо упомянутых методов. Этот метод использует схему http(s)//:
вместо схемы file://
для доступа к ресурсам локальной файловой системы и не уязвим для описанной атаки.
Котлин
val assetLoader: WebViewAssetLoader = Builder()
.addPathHandler("/assets/", AssetsPathHandler(this))
.build()
webView.setWebViewClient(object : WebViewClientCompat() {
@RequiresApi(21)
override fun shouldInterceptRequest(view: WebView?, request: WebResourceRequest): WebResourceResponse {
return assetLoader.shouldInterceptRequest(request.url)
}
@Suppress("deprecation") // for API < 21
override fun shouldInterceptRequest(view: WebView?, url: String?): WebResourceResponse {
return assetLoader.shouldInterceptRequest(Uri.parse(url))
}
})
val webViewSettings: WebSettings = webView.getSettings()
// Setting this off for security. Off by default for SDK versions >= 16.
webViewSettings.allowFileAccessFromFileURLs = false
// Off by default, deprecated for SDK versions >= 30.
webViewSettings.allowUniversalAccessFromFileURLs = false
// Keeping these off is less critical but still a good idea, especially if your app is not
// using file:// or content:// URLs.
webViewSettings.allowFileAccess = false
webViewSettings.allowContentAccess = false
// Assets are hosted under http(s)://appassets.androidplatform.net/assets/... .
// If the application's assets are in the "main/assets" folder this will read the file
// from "main/assets/www/index.html" and load it as if it were hosted on:
// https://appassets.androidplatform.net/assets/www/index.html
webView.loadUrl("https://appassets.androidplatform.net/assets/www/index.html")
Ява
final WebViewAssetLoader assetLoader = new WebViewAssetLoader.Builder()
.addPathHandler("/assets/", new AssetsPathHandler(this))
.build();
webView.setWebViewClient(new WebViewClientCompat() {
@Override
@RequiresApi(21)
public WebResourceResponse shouldInterceptRequest(WebView view, WebResourceRequest request) {
return assetLoader.shouldInterceptRequest(request.getUrl());
}
@Override
@SuppressWarnings("deprecation") // for API < 21
public WebResourceResponse shouldInterceptRequest(WebView view, String url) {
return assetLoader.shouldInterceptRequest(Uri.parse(url));
}
});
WebSettings webViewSettings = webView.getSettings();
// Setting this off for security. Off by default for SDK versions >= 16.
webViewSettings.setAllowFileAccessFromFileURLs(false);
// Off by default, deprecated for SDK versions >= 30.
webViewSettings.setAllowUniversalAccessFromFileURLs(false);
// Keeping these off is less critical but still a good idea, especially if your app is not
// using file:// or content:// URLs.
webViewSettings.setAllowFileAccess(false);
webViewSettings.setAllowContentAccess(false);
// Assets are hosted under http(s)://appassets.androidplatform.net/assets/... .
// If the application's assets are in the "main/assets" folder this will read the file
// from "main/assets/www/index.html" and load it as if it were hosted on:
// https://appassets.androidplatform.net/assets/www/index.html
webview.loadUrl("https://appassets.androidplatform.net/assets/www/index.html");
Отключить опасные методы WebSettings
Значения методов setAllowFileAccess()
, setAllowFileAccessFromFileURLs()
и setAllowUniversalAccessFromFileURLs()
по умолчанию установлены в TRUE
на уровне API 29 и ниже и FALSE
на уровне API 30 и выше.
Если есть необходимость настроить другие WebSettings
, лучше всего явно отключить эти методы, особенно для приложений, ориентированных на уровни API, меньшие или равные 29.
Риск: файловый XSS
Установка для метода setJavacriptEnabled
значения TRUE
позволяет выполнять JavaScript внутри WebView, а в сочетании с включенным доступом к файлам, как описано ранее, XSS на основе файлов возможен посредством выполнения кода в произвольных файлах или вредоносных веб-сайтов, открытых в WebView.
Смягчения
Запретить WebViews загружать локальные файлы
Как и в случае с предыдущим риском, файлового XSS можно избежать, если setAllowFileAccess()
, setAllowFileAccessFromFileURLs()
и setAllowUniversalAccessFromFileURLs()
установлено значение FALSE
.
Запретить WebViews выполнять JavaScript
Установите для метода setJavascriptEnabled
значение FALSE
, чтобы JavaScript не мог выполняться в WebViews.
Убедитесь, что WebViews не загружают ненадежный контент
Иногда включение этих настроек необходимо в WebViews. В этом случае важно обеспечить загрузку только доверенного контента. Ограничение выполнения JavaScript только тем, что вы контролируете, и запрет произвольного JavaScript — один из хороших способов обеспечить надежность контента. В противном случае предотвращение загрузки трафика открытого текста гарантирует, что WebViews с опасными настройками, по крайней мере, не смогут загружать URL-адреса HTTP. Это можно сделать либо через манифест, установив android:usesCleartextTraffic
значение False
, либо установив Network Security Config
, которая запрещает HTTP-трафик.
Ресурсы
- Справочная страница API setAllowUniversalAccessFromFileURLs
- Справочная страница API setAllowFileAccessFromFileURLs
- Справочная страница API WebViewAssetLoader
- Документация CodeQL
- Защищенный блог
- Справочная страница onShowFileChooser