diff --git a/SUMMARY.md b/SUMMARY.md index 316a3a986..b62751ef8 100644 --- a/SUMMARY.md +++ b/SUMMARY.md @@ -123,6 +123,7 @@ * [APK decompilers](mobile-apps-pentesting/android-app-pentesting/apk-decompilers.md) * [AVD - Android Virtual Device](mobile-apps-pentesting/android-app-pentesting/avd-android-virtual-device.md) * [Burp Suite Configuration for Android](mobile-apps-pentesting/android-app-pentesting/android-burp-suite-settings.md) + * [content:// protocol](mobile-apps-pentesting/android-app-pentesting/content-protocol.md) * [Drozer Tutorial](mobile-apps-pentesting/android-app-pentesting/drozer-tutorial/README.md) * [Exploiting Content Providers](mobile-apps-pentesting/android-app-pentesting/drozer-tutorial/exploiting-content-providers.md) * [Exploiting a debuggeable applciation](mobile-apps-pentesting/android-app-pentesting/exploiting-a-debuggeable-applciation.md) diff --git a/mobile-apps-pentesting/android-app-pentesting/README.md b/mobile-apps-pentesting/android-app-pentesting/README.md index 8f31d0313..5b397d41b 100644 --- a/mobile-apps-pentesting/android-app-pentesting/README.md +++ b/mobile-apps-pentesting/android-app-pentesting/README.md @@ -152,7 +152,9 @@ Read the following page to learn how to easily access javascript code of React a * **Native functions** declared as `native`: `public native, System.loadLibrary, System.load` * [Read this to learn **how to reverse native functions**](reversing-native-libraries.md)\*\*\*\* - +### **Other tricks** + +{% page-ref page="content-protocol.md" %} ## Dynamic Analysis diff --git a/mobile-apps-pentesting/android-app-pentesting/content-protocol.md b/mobile-apps-pentesting/android-app-pentesting/content-protocol.md new file mode 100644 index 000000000..cb1b4dc6d --- /dev/null +++ b/mobile-apps-pentesting/android-app-pentesting/content-protocol.md @@ -0,0 +1,101 @@ +# content:// protocol + +To experiment with content providers, one can use the `content` command on Android devices. Root access is not necessarily required. For example, to see the list of files managed by the Media Store, one can execute the following command: + +```bash +$ content query --uri content://media/external/file +``` + +To make the output more human friendly, one can limit the displayed columns to the identifier and path of each indexed file. + +```bash +$ content query --uri content://media/external/file --projection _id,_data +``` + +Media providers exist in their own private namespace. As illustrated in the example above, to access a content provider the corresponding `content://` URI should be specified. Generally, information on the paths, via which a provider can be accessed, can be recovered by looking at application manifests \(in case the content provider is exported by an application\) or the source code of the Android framework. + +Interestingly, on Android devices Chrome supports accessing content providers via the `content://` scheme. This feature allows the browser to access resources \(e.g. photos, documents etc.\) exported by third party applications. To verify this, one can insert a custom entry in the Media Store and then access it using the browser: + +```bash +$ cd /sdcard +$ echo "Hello, world!" > test.txt +$ content insert --uri content://media/external/file \ + --bind _data:s:/storage/emulated/0/test.txt \ + --bind mime_type:s:text/plain +``` + +To discover the identifier of the newly inserted file: + +```bash +$ content query --uri content://media/external/file \ + --projection _id,_data | grep test.txt +Row: 283 _id=747, _data=/storage/emulated/0/test.txt +``` + +And to actually view the file in Chrome, one can use a URL like the one shown in the following picture. Notice the file identifier 747 \(discovered above\) which is used as a suffix in the URL. + +![Chrome "Hello, world!"](https://census-labs.com/media/whatsapp-screenshot-hello-world.png) + +For example, you could list all the files related to WhatsApp with: + +```bash +$ content query --uri content://media/external/file --projection _id,_data | grep -i whatsapp +... + +Row: 82 _id=58, _data=/storage/emulated/0/Android/data/com.whatsapp/cache/SSLSessionCache +Row: 83 _id=705, _data=/storage/emulated/0/Android/data/com.whatsapp/cache/SSLSessionCache/157.240.9.53.443 +Row: 84 _id=239, _data=/storage/emulated/0/Android/data/com.whatsapp/cache/SSLSessionCache/crashlogs.whatsapp.net.443 +Row: 85 _id=240, _data=/storage/emulated/0/Android/data/com.whatsapp/cache/SSLSessionCache/pps.whatsapp.net.443 +Row: 86 _id=90, _data=/storage/emulated/0/Android/data/com.whatsapp/cache/SSLSessionCache/static.whatsapp.net.443 +Row: 87 _id=706, _data=/storage/emulated/0/Android/data/com.whatsapp/cache/SSLSessionCache/v.whatsapp.net.443 +Row: 88 _id=89, _data=/storage/emulated/0/Android/data/com.whatsapp/cache/SSLSessionCache/www.whatsapp.com.443 +... +``` + +### The Chrome CVE-2020-6516 Same-Origin-Policy bypass + +The _Same Origin Policy_ \(SOP\) \[[12](https://developer.mozilla.org/en-US/docs/Web/Security/Same-origin_policy)\] in browsers dictates that Javascript content of URL A will only be able to access content at URL B if the following URL attributes remain the same for A and B: + +* The protocol e.g. `https` vs. `http` +* The domain e.g. `www.example1.com` vs. `www.example2.com` +* The port e.g. `www.example1.com:8080` vs. `www.example1.com:8443` + +Of course, there are exceptions to the above rules, but in general, a resource from `https://www.example1.com` \(e.g. a piece of Javascript code\) cannot access the DOM of a resource on `https://www.example2.com`, as this would introduce serious information leaks. **Unless a Cross-Origin-Resource-Sharing \(CORS\) policy explicitly allows so, it shouldn't be possible for a web resource to bypass the SOP rules.** + +It's essential to note that Chrome considers `content://` to be a _local scheme_, just like `file://`. In this case SOP rules are even more strict, as each local scheme URL is considered a separate origin. For example, Javascript code in **file:///tmp/test.html** should not be able to access the contents of **file:///tmp/test2.html**, or any other file on the filesystem for that matter. **Consequently, according to SOP rules, a resource loaded via `content://` should not be able access any other `content://` resource.** Well, vulnerability CVE-2020-6516 of Chrome created an "exception" to this rule. + +CVE-2020-6516 \[[03](https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2020-6516)\] is a SOP bypass on resources loaded via a `content://` URL. **For example, Javascript code, running from within the context of an HTML document loaded from `content://com.example.provider/test.html`, can load and access any other resource loaded via a `content://` URL.** This is a serious vulnerability, especially on devices running Android 9 or previous versions of Android. On these devices scoped storage \[[13](https://developer.android.com/about/versions/10/privacy/changes#scoped-storage)\] is not implemented and, consequently, application-specific data under **/sdcard**, and more interestingly under **/sdcard/Android**, can be accessed via the system's Media Store content provider. + +A proof-of-concept is pretty straightforward. An HTML document that uses `XMLHttpRequest` to access arbitrary `content://` URLs is uploaded under **/sdcard**. It is then added in the Media Store and rendered in Chrome, in a fashion similar to the example shown earlier. For demonstration purposes, one can attempt to load `content://media/external/file/747` which is, in fact, the Media Store URL of the "Hello, world!" example. Surprisingly, the Javascript code, running within the origin of the HTML document, will fetch and display the contents of **test.txt**. + +```markup + + + PoC + + + + +``` + +**Information taken from this writeup:** [**https://census-labs.com/news/2021/04/14/whatsapp-mitd-remote-exploitation-CVE-2021-24027/**](https://census-labs.com/news/2021/04/14/whatsapp-mitd-remote-exploitation-CVE-2021-24027/)\*\*\*\* + diff --git a/pentesting/pentesting-kubernetes/README.md b/pentesting/pentesting-kubernetes/README.md index a64b72dcf..5bb3107a6 100644 --- a/pentesting/pentesting-kubernetes/README.md +++ b/pentesting/pentesting-kubernetes/README.md @@ -558,99 +558,6 @@ kubectl get secrets --all-namespaces -o json | kubectl replace -f - * [https://kubernetes.io/docs/concepts/configuration/secret/\#risks](https://kubernetes.io/docs/concepts/configuration/secret/#risks) * [https://docs.cyberark.com/Product-Doc/OnlineHelp/AAM-DAP/11.2/en/Content/Integrations/Kubernetes\_deployApplicationsConjur-k8s-Secrets.htm](https://docs.cyberark.com/Product-Doc/OnlineHelp/AAM-DAP/11.2/en/Content/Integrations/Kubernetes_deployApplicationsConjur-k8s-Secrets.htm) -### Vulnerabilities - OS - -Is mandatory to keep in mind to define privilege and access control for container / pod: - -* userID’s and groupID’s. -* Privileged or unprivileged escalation runs. -* Linux. - -More info at: [https://kubernetes.io/docs/tasks/configure-pod-container/security-context/](https://kubernetes.io/docs/tasks/configure-pod-container/security-context/) - -#### userID and groupID - -```bash -kubectl run pod --image=busybox --command -oyaml --dry-run=client > -- sh -c 'sleep 1h' -vi .yaml -``` - -Add the uncomment lines: - -```yaml -#apiVersion: v1 -#kind: Pod -#metadata: -# name: security-context-demo -spec: - securityContext: - runAsUser: 1000 - runAsGroup: 3000 - fsGroup: 2000 -# volumes: -# - name: sec-ctx-vol -# emptyDir: {} -# containers: -# - name: sec-ctx-demo -# image: busybox -# command: [ "sh", "-c", "sleep 1h" ] - securityContext: - runAsNonRoot: true -# volumeMounts: -# - name: sec-ctx-vol -# mountPath: /data/demo -# securityContext: -# allowPrivilegeEscalation: true -``` - -Save and: - -```bash -kubectl -f .yaml delete --force -kubectl -f .yaml create -``` - -Check permissions: - -```bash -kubectl exec -it -- sh -``` - -#### How to disable privilege escalation: - -```bash -vi .yaml -``` - -Set this line to false - -```yaml - allowPrivilegeEscalation: false -``` - -Save and: - -```bash -kubectl -f .yaml delete --force -kubectl -f .yaml create -``` - -#### Modify PodSecurityPolicy - -Pod security policies control the security policies about how a pod has to run. More info at: [https://kubernetes.io/docs/concepts/policy/pod-security-policy/](https://kubernetes.io/docs/concepts/policy/pod-security-policy/) - -Edit the kube-apiserver.yaml file: - -```bash -vi /etc/kubernetes/manifests/kube-apiserver.yaml -``` - -Inside you add in - -```text -- --enable-admission-plugins=NodeRestriction,PodSecurityPolicy -``` - ## RBAC Hardening Kubernetes has an **authorization module named Role-Based Access Control** \([**RBAC**](https://kubernetes.io/docs/reference/access-authn-authz/rbac/)\) that helps to set utilization permissions to the API server. @@ -799,6 +706,39 @@ User or K8s ServiceAccount –> Authentication –> Authorization –> * Avoid unauthorized access RBAC. * ApiServer port with firewall and IP whitelisting. +## SecurityContext Hardening + +By default root user will be used when a Pod is started if no other user is specified. You can run your application inside a more secure context using a template similar to the following one: + +```yaml +apiVersion: v1 +kind: Pod +metadata: + name: security-context-demo +spec: + securityContext: + runAsUser: 1000 + runAsGroup: 3000 + fsGroup: 2000 + volumes: + - name: sec-ctx-vol + emptyDir: {} + containers: + - name: sec-ctx-demo + image: busybox + command: [ "sh", "-c", "sleep 1h" ] + securityContext: + runAsNonRoot: true + volumeMounts: + - name: sec-ctx-vol + mountPath: /data/demo + securityContext: + allowPrivilegeEscalation: true +``` + +* [https://kubernetes.io/docs/tasks/configure-pod-container/security-context/](https://kubernetes.io/docs/tasks/configure-pod-container/security-context/) +* [https://kubernetes.io/docs/concepts/policy/pod-security-policy/](https://kubernetes.io/docs/concepts/policy/pod-security-policy/) + ## General Hardening You should update your Kubernetes environment as frequently as necessary to have: