Thursday 9 August 2018

Xgody D24 and the nasty background app

As my previous blog posting mentioned, I decided to get a cheap (less than £100) android phone from ebay, it's a chinese import and it's the Xgody D24 Pro. It's a really nice phone and I'm liking it, it's fast enough, designed well and other than poor battery life has been great.

That is until around 2 weeks of ownership and then it seems to cause problems. It gets really hot at the back top (I'm assuming where the CPU is), battery life starts to suffer and then it starts switching wifi OFF.
This was the biggest pain for me, as switching to my limited 4G data service wasn't ideal, so why was it switching wifi OFF. Annoyingly searching Android and permissions it seems the ability to turn wifi on and off is not a system/secured function and so pretty much any app can do this. I wanted to see if I could spot the app doing it so started to use adb to debug and view the logs from the phone. This is trival on most Android devices. Get into debug mode by going to about the phone and clicking 7 times on BUILD NUMBER, and you get the developer options. Enable USB debugging and you can then start using adb shell, logcat and others. This is good as we can now see debug output from the phone and get a shell.
Unfortunately root doesn't seem an option at the moment as none of the traditional Mediatek methods of rooting work so far, so I'm still hunting for this.

Anyway, back to debugging and nothing showed the wifi getting switched off, other than the android system messages showing the wifi trigger to switch off had occurred. So this didn't give me anything useful unfortunately. So I then wondered what the phone was doing, why did it want to switch wifi off, and why did it hate my wifi so much! It's not my WIFI as loads of other devices in the house were happy, so to me the phone was deciding to switch it off and move to 4G.
I therefore started to capture what traffic the phone was doing, and in doing so got quite alarmed. I did this firstly by just capturing what DNS queries were being made, I run my own caching dns at home as I then filter out known dodgy websites, adverts, etc, so this was my biggest thought. Some app on my phone didn't like that I was stopping their ad revenue and circumventing my block! So looking at the DNS queries should help, here is a small extract:

08-Aug-2018 18:17:36.176 client -redacted-#37694 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:17:36.245 client -redacted-#46380 ( view internal-view: query: IN A +T -redacted-
08-Aug-2018 18:17:54.151 client -redacted-#61674 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:17:54.198 client -redacted-#41326 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:18:05.719 client -redacted-#41059 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:18:06.490 client -redacted-#47730 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:18:07.553 client -redacted-#62811 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:18:58.558 client -redacted-#37185 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:18:58.660 client -redacted-#39907 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:18:58.963 client -redacted-#40249 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:18:59.497 client -redacted-#44690 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:20:01.643 client -redacted-#53189 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:20:02.847 client -redacted-#42812 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:20:03.019 client -redacted-#34487 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:20:03.198 client -redacted-#55749 ( view internal-view: query: IN A + -redacted-

So these weren't great, but I can see how they were working, tracking on various software, phone-home stuff, click trackers. Not things I like seeing, but I can kind of see why, there are some googleapis in there, some facebook stuff, so unsurprising.
But then the ones that worried me came along:
08-Aug-2018 18:20:53.374 client -redacted-#11447 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:20:53.599 client -redacted-#4099 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:20:53.829 client -redacted-#21446 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:20:54.132 client -redacted-#23448 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:20:54.517 client -redacted-#26753 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:20:54.789 client -redacted-#27880 ( view internal-view: query: IN A + -redacted-
08-Aug-2018 18:20:55.167 client -redacted-#18179 ( view internal-view: query: IN A + -redacted-

The last one was the one I was concerned about. What was coinhive? Cryptomining was the answer that google provided, and it was a method of embedding mining into websites, apps, in fact almost anywhere you could hide one. This was starting to sound a bit suspicious, why would my phone be mining? Well it's obvious when you stop and think.
Cheap phone, potentially cheaper than cost of manufacture, how do you subsidise the cost? Get it to click on banner ads, and mine cryptocurrencies when the user isn't using it! At least that's my guess. So now I have an idea what's going on, the phone is doing this in the background and of course needs to phone home to upload it's progress, completion, etc. Well my DNS at home is blocking this (sending it to loopback) so it can't do that, so next option? Try to switch to 4G and go that way.

This would also account for the hot CPU, as cryptomining uses CPU cycles to do the work, so that is also contributing to the battery running down so fast and as mentioned the heat generated. So now finding it should be straight forward, just wait for the thing to get hot and look at what process is using the CPU. It didn't take long to find it:

User 95%, System 3%, IOW 0%, IRQ 0%
User 796 + Nice 0 + Sys 29 + Idle 12 + IOW 0 + IRQ 0 + SIRQ 0 = 837

  PID USER     PR  NI CPU% S  #THR     VSS     RSS PCY Name
 5515 system   16  -4  91% S    93 1300280K 190604K  bg com.mediatek.factorymode
  834 system   20   0   3% S   114 1253876K 118232K  fg system_server
 6170 shell    20   0   1% R     1  12588K   1596K  fg top

Here you can see the CPU is at 95% use (the phone was sat with screen off, idling here) and the process at the top was a strange background process "bg com.mediatek.factorymode". Which is again odd as the phone wasn't in "factory mode" or anything like that, it was in normal operation. So that was the suspect. Occasionally when I unlock the phone that process went away (I'm guessing it lowered its cpu use accordingly) and then when idle again popped straight back up. So this one I think is the problem.

It's stored into the heart of the factory ROM, as I did a factory reset and this didn't remove it. The APK is stored at /system/vendor/framework/mediatek-res/mediatek-res.apk (SEE NOTE BELOW, I REALISE THIS IS WRONG!)
However without root, I'm struggling to stop it from running. Ideally with root you'd stop the apk from being called at boot time and that would stop it in it's tracks, but without root this gets tricky.

Luckily I've found what is currently (as I type) working, and so far the app hasn't restarted itself. I'm unsure if it will and how it is called, so only time will tell.
I've used the Android developer tools themselves to help here.
Go into Settings and Developer options. Down to "Running services" and click "Show cached processes" to see as much as you can. I then went down the list and found:
"FactoryTest" showing 1 process and 1 service.
Clicking it shows a service called "Vmaezz" which is a bit unknown so I hit STOP on it.
I then had to also find "FactoryMode" when showing cached services and you can hit STOP on that too. When I did that, the process went away.

So what you look for is:

system    10762 345   1146172 155852 futex_wait 00000000 S com.mediatek.factorymode

And once I stopped those processes that went away. Whilst that app isn't running, the wifi didn't switch off and the cpu idled away at pretty low values.

The problem? What causes the app to run, there is probably another app somewhere that calls it, or schedules it to run, so no doubt it'll be back, so I really need to get onto the bigger challenge and find out how to root and kill this app.

In the meantime, I'm going to extract and try to reverse engineer mediatek-res.apk to discover what I can about it and see if I can spot the triggers, etc.

Wherever you saw me referring to mediatek-res.apk please note this is WRONG information! Don't break mediatek-res.apk as you'll get a bootloop which is evil on these no-name chinese phones!

I did further discovery and found the key apk:

So that was the one to focus on.

I went ahead and used an online analyser of the APK to see what it said:

Two interesting things appeared here in the services section. The first is that it had a wifistatelistener, so that makes me think it could check wifi. Second is the Vmaezz class which was the one I killed in android developers, so that does indicate that's the main process/class that's running this. Curiously this didn't report the app as malicious, but it depends on what this scanner was looking for.

As of now, I killed the app around 20 minutes ago and it's not come back yet, and wifi has remained on, so hopefully this is the "solution" for now until I can dig further into it and extract the code from the apk.

To try and get into the code, I've found that the .apk is a compile-at-boot type, so that produces an .odex file. In combination with the devices own "boot.oat" I then extracted the DEX and from that the majority of sourcecode. Viewing it with jadx-gui shows something interesting:

What looks like the factory (Mediatek factorymode) code is at the top with the normal attribute names and definitions.
There is then an unusual one added below, so almost like a second program hiding within the first. This second program:
I'd guess is what we want to investigate, so opening some of the source up reveals:

Sure enough, there is our vmaezz code that we keep killing off.

I now started looking through the code for what looked to be interesting code. I found quite a few things, udplistener events, trigger and http download events, and this one which watches the network changes taking place:

So this lets the app recognise when a wifi state change happens, so this looks potential as if it watches for this change perhaps it also influences it.
Couple that with the handler:

I think we can see that it likes to watch and take action on changes to this state.

I've also discovered from adb I can stop the application "automatically" by calling
adb shell am force-stop com.mediatek.factorymode
So as a short-term solution I've written a small shell script:

while [ /system/bin/true ]; do
/system/bin/am force-stop com.mediatek.factorymode
sleep 1

Uploaded it to /data/local/tmp and set executable. Then ran it with & to background it. It appears to stay running and does kill the process before it finishes starting. It's not very elegant but it'll work for now.

Slowly, I'll figure out how to kill this thing off!

--UPDATE-- 13/08/2018
I've found that the script above is working great, killing the process off the moment it tries to start (It works in my favour that it takes a few seconds to start up fully as it has to de-odex itself). So my shell killer is working. However battery life has reduced, I'm guessing because my shell script isn't letting the phone go to sleep.
I'd also installed Blokada which is an interesting blocking method for non-rooted phones. It creates a local VPN (to itself) and then blocks known ad networks, etc. It seems to be working REALLY well, and added to the previous fixes seems good. I'm not sure if this is also eating my battery, but it seems worth it.

I've just improved on my shell script killer:

while [ /system/bin/true ]; do
if /system/bin/pgrep "com.mediatek.factorymode" >/dev/null
/system/bin/am force-stop com.mediatek.factorymode
echo "Not running"
sleep 10
I'm not sure how long I can push the sleep timer to, so might experiment further on this.

I've had Xgody reply to my queries, I'd opened discussion on them over the process using 100% CPU and if there was an updated ROM/firmware. They've flatly said there is no ability to update the ROM at all, but have now offered a partial refund of the cost of the phone which is an odd offer. I'm probably not going to take them up on this though.


  1. hola,pasa lo mismo en un oukitel c8 4g en un leeago kiipower y en un doogee x6 .todos chinos con mtk .mi solucion fue app cortafuegos sin root y negar acceso a ajustes llavero miravision etz,afecta solo a posicion gps,pero ya no se calientan y dura la bateria,gracias por investigar ,un saludo

  2. I have the same phone and am getting the same issue with the WiFi settings turning off, who do I contact to obtain a refund ? Or is there a solution? TIA

  3. Very useful post. This is my first time i visit here. I found so many interesting stuff in your blog especially its discussion. Really its great article. Keep it up. oil tank removal NJ

  4. I love the way you write and share your niche! Very interesting and different! Keep it coming! app development agency

  5. Anyway, back to debugging andkhalid Hassan nothing showed the wifi getting switched off, other than the android system messages showing the wifi trigger to switch off had occurred. So this didn't give me anything useful unfortunately


Note: only a member of this blog may post a comment.