aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--.github/ISSUE_TEMPLATE/bug_report.md19
-rw-r--r--.github/ISSUE_TEMPLATE/feature_request.md20
-rw-r--r--docs/src/content/howto-install-system-trusted-ca-android.md86
-rw-r--r--mitmproxy/platform/pf.py17
-rw-r--r--mitmproxy/utils/human.py4
-rw-r--r--test/mitmproxy/data/pf016
-rw-r--r--test/mitmproxy/platform/test_pf.py5
-rw-r--r--test/mitmproxy/utils/test_human.py1
8 files changed, 155 insertions, 3 deletions
diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md
new file mode 100644
index 00000000..01b6fb85
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/bug_report.md
@@ -0,0 +1,19 @@
+---
+name: Bug report
+about: Create a report to help us improve
+title: ''
+labels: kind/triage
+assignees: ''
+
+---
+
+#### Problem Description
+A clear and concise description of what the bug is.
+
+#### Steps to reproduce the behavior:
+1.
+2.
+3.
+
+#### System Information
+Paste the output of "mitmproxy --version" here.
diff --git a/.github/ISSUE_TEMPLATE/feature_request.md b/.github/ISSUE_TEMPLATE/feature_request.md
new file mode 100644
index 00000000..8e8080db
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/feature_request.md
@@ -0,0 +1,20 @@
+---
+name: Feature request
+about: Suggest an idea for this project
+title: ''
+labels: kind/feature
+assignees: ''
+
+---
+
+**Is your feature request related to a problem? Please describe.**
+A clear and concise description of what the problem is. Ex. I'm always frustrated when [...]
+
+#### Describe the solution you'd like
+A clear and concise description of what you want to happen.
+
+#### Describe alternatives you've considered
+A clear and concise description of any alternative solutions or features you've considered.
+
+#### Additional context
+Add any other context or screenshots about the feature request here.
diff --git a/docs/src/content/howto-install-system-trusted-ca-android.md b/docs/src/content/howto-install-system-trusted-ca-android.md
new file mode 100644
index 00000000..2ef67f30
--- /dev/null
+++ b/docs/src/content/howto-install-system-trusted-ca-android.md
@@ -0,0 +1,86 @@
+---
+title: "Install System CA on Android"
+menu:
+ howto:
+ weight: 4
+---
+
+# Install System CA Certificate on Android Emulator
+
+[Since Android 7, apps ignore user certificates](https://android-developers.googleblog.com/2016/07/changes-to-trusted-certificate.html), unless they are configured to use them.
+As most applications do not explicitly opt in to use user certificates, we need to place our mitmproxy CA certificate in the system certificate store,
+in order to avid having to patch each application, which we want to monitor.
+
+Please note, that apps can decide to ignore the system certificate store and maintain their own CA certificates. In this case you have to patch the application.
+
+## 1. Prerequisites
+
+ - Emulator from Android SDK with proxy settings pointing to mitmproxy
+
+ - Mitmproxy CA certificate
+ - Usually located in `~/.mitmproxy/mitmproxy-ca-cert.cer`
+ - If the folder is empty or does not exist, run `mitmproxy` in order to generate the certificates
+
+## 2. Rename certificate
+Enter your certificate folder
+{{< highlight bash >}}
+cd ~/.mitmproxy/
+{{< / highlight >}}
+
+ - CA Certificates in Android are stored by the name of their hash, with a '0' as extension
+ - Now generate the hash of your certificate
+
+{{< highlight bash >}}
+openssl x509 -inform PEM -subject_hash_old -in mitmproxy-ca-cert.cer | head -1
+{{< / highlight >}}
+Lets assume, the output is `c8450d0d`
+
+We can now copy `mitmproxy-ca-cert.cer` to `c8450d0d.0` and our system certificate is ready to use
+{{< highlight bash >}}
+cp mitmproxy-ca-cert.cer c8450d0d.0
+{{< / highlight >}}
+
+## 3. Insert certificate into system certificate store
+
+Note, that Android 9 (API LEVEL 28) was used to test the following steps and that the `emulator` executable is located in the Android SDK
+
+ - Start your android emulator.
+ - Get a list of your AVDs with `emulator -list-avds`
+ - Make sure to use the `-writable-system` option. Otherwise it will not be possible to write to `/system`
+ - Keep in mind, that the **emulator will load a clean system image when starting without `-writable-system` option**.
+ - This means you always have to start the emulator with `-writable-system` option in order to use your certificate
+
+{{< highlight bash >}}
+emulator -avd <avd_name_here> -writable-system
+{{< / highlight >}}
+
+ - Restart adb as root
+
+{{< highlight bash >}}
+adb root
+{{< / highlight >}}
+
+ - Get write access to `/system` on the device
+ - In earlier versions (API LEVEL < 28) of Android you have to use `adb shell "mount -o rw,remount /system"`
+
+{{< highlight bash >}}
+adb shell "mount -o rw,remount /"
+{{< / highlight >}}
+
+ - Push your certificate to the system certificate store and set file permissions
+
+{{< highlight bash >}}
+adb push c8450d0d.0 /system/etc/security/cacerts
+adb shell "chmod 664 /system/etc/security/cacerts/c8450d0d.0"
+{{< / highlight >}}
+
+## 4. Reboot device and enjoy decrypted TLS traffic
+
+ - Reboot your device.
+ - You CA certificate should now be system trusted
+
+{{< highlight bash >}}
+adb reboot
+{{< / highlight >}}
+
+**Remember**: You **always** have to start the emulator using the `-writable-system` option in order to use your certificate \ No newline at end of file
diff --git a/mitmproxy/platform/pf.py b/mitmproxy/platform/pf.py
index 5e22ec31..74e077a4 100644
--- a/mitmproxy/platform/pf.py
+++ b/mitmproxy/platform/pf.py
@@ -13,9 +13,15 @@ def lookup(address, port, s):
# Those still appear as "127.0.0.1" in the table, so we need to strip the prefix.
address = re.sub(r"^::ffff:(?=\d+.\d+.\d+.\d+$)", "", address)
s = s.decode()
- spec = "%s:%s" % (address, port)
+
+ # ALL tcp 192.168.1.13:57474 -> 23.205.82.58:443 ESTABLISHED:ESTABLISHED
+ specv4 = "%s:%s" % (address, port)
+
+ # ALL tcp 2a01:e35:8bae:50f0:9d9b:ef0d:2de3:b733[58505] -> 2606:4700:30::681f:4ad0[443] ESTABLISHED:ESTABLISHED
+ specv6 = "%s[%s]" % (address, port)
+
for i in s.split("\n"):
- if "ESTABLISHED:ESTABLISHED" in i and spec in i:
+ if "ESTABLISHED:ESTABLISHED" in i and specv4 in i:
s = i.split()
if len(s) > 4:
if sys.platform.startswith("freebsd"):
@@ -26,4 +32,11 @@ def lookup(address, port, s):
if len(s) == 2:
return s[0], int(s[1])
+ elif "ESTABLISHED:ESTABLISHED" in i and specv6 in i:
+ s = i.split()
+ if len(s) > 4:
+ s = s[4].split("[")
+ port = s[1].split("]")
+ port = port[0]
+ return s[0], int(port)
raise RuntimeError("Could not resolve original destination.")
diff --git a/mitmproxy/utils/human.py b/mitmproxy/utils/human.py
index 5c02b072..3158a294 100644
--- a/mitmproxy/utils/human.py
+++ b/mitmproxy/utils/human.py
@@ -48,12 +48,14 @@ def parse_size(s: typing.Optional[str]) -> typing.Optional[int]:
raise ValueError("Invalid size specification.")
-def pretty_duration(secs):
+def pretty_duration(secs: typing.Optional[float]) -> str:
formatters = [
(100, "{:.0f}s"),
(10, "{:2.1f}s"),
(1, "{:1.2f}s"),
]
+ if secs is None:
+ return ""
for limit, formatter in formatters:
if secs >= limit:
diff --git a/test/mitmproxy/data/pf01 b/test/mitmproxy/data/pf01
index 3139a289..019a6b76 100644
--- a/test/mitmproxy/data/pf01
+++ b/test/mitmproxy/data/pf01
@@ -1,4 +1,10 @@
No ALTQ support in kernel
ALTQ related functions disabled
+ALL tcp 192.168.1.111:40001 -> 5.5.5.6:80 FIN_WAIT_2:FIN_WAIT_2
ALL tcp 127.0.0.1:8080 <- 5.5.5.6:80 <- 192.168.1.111:40001 FIN_WAIT_2:FIN_WAIT_2
+ALL tcp 192.168.1.111:40000 -> 5.5.5.5:80 ESTABLISHED:ESTABLISHED
ALL tcp 127.0.0.1:8080 <- 5.5.5.5:80 <- 192.168.1.111:40000 ESTABLISHED:ESTABLISHED
+ALL tcp 2a01:e35:8bae:50f0:396f:e6c7:f4f1:f3db[40002] -> 2a03:2880:f21f:c5:face:b00c::167[443] ESTABLISHED:ESTABLISHED
+ALL tcp ::1[8080] <- 2a03:2880:f21f:c5:face:b00c::167[443] <- 2a01:e35:8bae:50f0:396f:e6c7:f4f1:f3db[40002] ESTABLISHED:ESTABLISHED
+ALL tcp 2a01:e35:8bae:50f0:396f:e6c7:f4f1:f3db[40003] -> 2a03:2880:f21f:c5:face:b00c::167[443] FIN_WAIT_2:FIN_WAIT_2
+ALL tcp ::1[6970] <- 2a03:2880:f21f:c5:face:b00c::167[443] <- 2a01:e35:8bae:50f0:396f:e6c7:f4f1:f3db[40003] FIN_WAIT_2:FIN_WAIT_2 \ No newline at end of file
diff --git a/test/mitmproxy/platform/test_pf.py b/test/mitmproxy/platform/test_pf.py
index 9795a2db..4a7dfe75 100644
--- a/test/mitmproxy/platform/test_pf.py
+++ b/test/mitmproxy/platform/test_pf.py
@@ -19,3 +19,8 @@ class TestLookup:
pf.lookup("192.168.1.112", 40000, d)
with pytest.raises(Exception, match="Could not resolve original destination"):
pf.lookup("192.168.1.111", 40001, d)
+ assert pf.lookup("2a01:e35:8bae:50f0:396f:e6c7:f4f1:f3db", 40002, d) == ("2a03:2880:f21f:c5:face:b00c::167", 443)
+ with pytest.raises(Exception, match="Could not resolve original destination"):
+ pf.lookup("2a01:e35:8bae:50f0:396f:e6c7:f4f1:f3db", 40003, d)
+ with pytest.raises(Exception, match="Could not resolve original destination"):
+ pf.lookup("2a01:e35:face:face:face:face:face:face", 40003, d)
diff --git a/test/mitmproxy/utils/test_human.py b/test/mitmproxy/utils/test_human.py
index faf35f72..6f8bf732 100644
--- a/test/mitmproxy/utils/test_human.py
+++ b/test/mitmproxy/utils/test_human.py
@@ -47,6 +47,7 @@ def test_pretty_duration():
assert human.pretty_duration(10000) == "10000s"
assert human.pretty_duration(1.123) == "1.12s"
assert human.pretty_duration(0.123) == "123ms"
+ assert human.pretty_duration(None) == ""
def test_format_address():