How much cpu usage is too much - android

I'm almost done with an app and I noticed that it runs at about 6-12% cpu when its in the background. Is this too much? What's a good amount our does it mostly depend on the app?

It does depend on the application. 6-12% CPU would be too much for a software like text editor. But it would not be too much for a web crawler and indexer crawling and indexing the web through 30 threads.
Whether it is too much or not also depends on the nature of other processes running on the system. While 6-12% CPU usage may not be threatening to other processes running on the system, but in case you are running a CPU intensive task say, sorting gigabytes of data that you need very urgently or indexing the web, you would want the CPU usage to go as high as 80% or even more and as a result you wouldn't want to run any other CPU intensive process on the server.

If you are concerned that you may be doing some wasteful operation without realizing it, you may want to use the profiler to see if you are spending too much time in code that you shouldn't. It may also be the case that your app requires 6-12% CPU for what it does, which shouldn't a problem if it's actually putting it to good use.

Related

Heavy CPU analysis while running foreground service

So, I've a Service that is important for applications logic and thus needs to be alive all the time.
First thing is first, I created it as a foreground service.
Whenever user starts to run, Service starts to do a lot of heavy things. It uses FusedLocationAPI different type of sensors and do a lot of different calculations. At this point phone starts to heat up (CPU usage is high). When running stops, heating stops and CPU drops lower.
This makes me think that the main problem is whenever these sensors are used and calculations are made, but there's a lot of possibilities that could cause this and I wanted to understand, how can I deeply analyze batter usage in this case? I read that Battery Historian should be way to go, but the information there is complicated and do not give me much information. How can I use this data to understand which class/runnable/code part is held responsible for the CPU usage? Maybe there's better ways to solve this? Thanks in advance.
Detailed analysis on what's happening using CPU profiler (after suggestion).
Image. Application is opened and few different screens are switch to and from. Nothing special. Phone does not heat up and from CPU analysis everything also looks pretty okay.
2.User starts to run and enter heavy state. The yellow (light green) rectangle shows previously mentioned "important service" that bring important role to application. Called functions does not use too much time of CPU considering the % of whole running trip - which makes me think, I've to look somewhere else..
What I saw is that CPU increases heavily whenever I lock the phone (while service is running. From CPU Bottom Up analysis I cannot understand what is causing the problem (orange rectangle) - looks like a bunch of Android stuff is happening, but it does not give me any clue.
From CPU profiler I do understand that I have a serious problem considering CPU usage, but right now I do not understand what is causing it (which piece of code/class/function). I know for the fact that whenever my important service is created (on app start) I use PARTIAL_WAKE_LOCK to not allow CPU go to sleep and also make service to be alive at all times. As I understand I need to find different solution for this, because CPU drains too much of battery.
How could I found this using only profiler? I now this fact only for code and profiler stack does not tell me much about this (maybe Im not looking at the right place?)
I found out the root cause of high CPU usage.
I did detailed investigation on threads and found out that DefaultDispatcher threads are using A LOT of CPU.
Turns out the has been a bug in Kotlin-Coroutines library and latest version provides fixes. When I did tests I used version 1.3.1, but changing version number to 1.3.3 provided me with big improvements: from 40% usage to 10% CPU usage.

Context switching is too expensive

I am writing a video processing app and have come across the following performance issue:
Most of the methods in my app have great differences between cpu time and real time.
I have investigated using the DDMS TraceView and have discovered that the main culprit for these discrepancies is context switching in some base methods, such as MediaCodec.start() or MediaCodec.dequeueOutputBuffer()
MediaCodec.start() for example has 0.7ms Cpu time and 24.2ms Real time. 97% of this real time is used up by the context switch.
This would not be a real problem, but the method is called quite often, and it is not the only one that presents this kind of symptom.
I also need to mention that all of the processing happens in a single AsyncTask, therefore on a single non-UI thread.
Is context switching a result of poor implementation, or an inescapable reality of threading?
I would very much appreciate any advice in this matter.
First, I doubt the time is actually spent context-switching. MediaCodec.start() is going to spend some amount of time waiting for the mediaserver process to talk to the video driver, and that's probably what you're seeing. (Unless you're using a software codec, your process doesn't do any of the actual work -- it sends IPC requests to mediaserver, which talks to the hardware codec.) It's possible traceview is just reporting its best guess at where the time went.
Second, AsyncTask threads are executed at a lower priority. Since MediaCodec should be doing all of the heavy lifting in the hardware codec, this won't affect throughput, but it's possible that it's having some effect on latency because other threads will be prioritized by the scheduler. If you're worried about performance, stop using AsyncTask. Either do the thread management yourself, or use the handy helpers in java.util.concurrent.
Third, if you really want to know what's happening when multiple threads and processes are involved, you should be using systrace, not traceview. An example of using systrace with custom trace markers (to watch CPU cores spin up) can be found here.

High Performance Audio Cracking / Prevent a CPU core from downclocking

This may be very specific, still trying to ask:
I'm founder of Heat Synthesizer, a software music synthesizer for Android. (https://play.google.com/store/apps/details?id=com.nilsschneider.heat.demo)
This app generates audio signals in realtime and needs to do heavy math calculations to do so.
Having seen the talk on Google I/O 2013 about "High Performance Audio on Android" (http://www.youtube.com/watch?v=d3kfEeMZ65c), I was excited to implement it as they suggested, but I keep having problems with crackling.
I have a CPU usage of a single core of about 50% on a Nexus 7 (2012), everything seems to be okay so far. Locking has been reduced to a minimum and most of the code is done lock-free.
Using an app that is called Usemon, I can see that the core I use for processing is used only 50% and is even being downclocked by the kernel because my CPU usage is not high enough.
However, this core speed changes result in crackling of the audio, because the next audio block is not calculated fast enough because my core is underclocked.
Is there any way to prevent a core from changing it's clock frequency?
FWIW, I recommend the use of systrace (docs, explanation, example) for this sort of analysis. On a rooted device you can enable the "freq" tags, which show the clock frequencies of various components. Works best on Android 4.3 and later.
The hackish battery-unfriendly way to deal with this is to start up a second thread that does nothing but spin while your computations are in progress. In theory this shouldn't work (since you're spinning on a different core), but in practice it usually gets the job done. Make sure you verify that the device has multiple cores (Runtime.getRuntime().availableProcessors() or NDK equivalent), as doing this on a single-core device would be bad.
Assuming your computations are performed asynchronously in a separate thread, you can do a bit better by changing the worker thread from a "compute, then wait for work" to a "compute, then poll for work" model. Again, far less efficient battery-wise, but if you never sleep then the kernel will assume you're working hard and needs to keep the core at full speed. Make sure you drop out of polling mode if there isn't any actual work to do (i.e. you hit the end of input).

Optimal thread pool size in android

I got an app that got a lot of remote resource loading actions, scheduled runnables and other OS events handling.
I'm using a single executor service with cached threads.
I have no idea how many threads should I use for optimal performance and battery usage.
Is there a way to know?
Usually, you do not need to worry about number of threads affecting battery usage. Because if the amount of work is the same (lets say in terms of CPU instructions) there should be not much difference in battery drain if you do it on one thread or in parallel using 2 threads. You will have your result faster, but CPU will still execute almost same number of instructions.
As for performance gains, if thread consuming cpu 100% of a time, then having more threads, than amount of Cores wont make any performance difference, actually you will get a little bit less performance because of scheduling overhead.
You should define a metric to evaluate performance, and define what is "optimal" for you. It is really hard to say not knowing what software is doing exactly. And if there is no performance/battery issue right now, then there is probably no need to worry about it.
Your question cant have definitive answer because it is very broad.

typical android cpu split between app and kernel

What is the typical split between kernel CPU time and UserMode CPU time on an Android while executing a typical cpu-bound application ?
A typical dual core ARM android phone, while executing a common app, and not waiting for i.o from user or network
Even more helpful, if there is any data on the cpu time split between the usermode portion of system libraries, and time spent inside app actual code
(I realize this is a very subjective question, complicated by the jvm/jit and other functions but any pointers (ha!;) would be helpful.)
Well, it really depends on the application. In an application that is I/O bound, the time will be spent in syscalls like read and write. In an application that is compute bound, the CPU time will be almost all userland. In an application that's RAM bound (doing a lot of manipulation of data in RAM) that CPU will spend most of it's time waiting for RAM because of cache misses (I don't think ARM processors have very large caches).
On the other hand, if your app does a lot of UI stuff, while all of the graphics processing is done in userland, there is still a lot of I/O bound operations waiting for the frame-buffer and input devices.

Categories

Resources