1

I just starting learning Android app development and I'm doing an app for embedded devices. My app needs to keep running for long hours but it fails to do so. I cleaned up my code of possible memory leaks but still the issue occurs.

So I tried running an app that is doing nothing, overnight, and here are my findings.

First, a snippet of the source code:

@RequiresApi(api = Build.VERSION_CODES.N)
public MainActivity()
{
    super();
    Log.d("TEST","NEW INSTANCE CREATED " + Calendar.getInstance().getTime()+"=================================================");
}

@RequiresApi(api = Build.VERSION_CODES.N)
@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
    setSupportActionBar(toolbar);

    FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
    fab.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            Snackbar.make(view, "Replace with your own action", Snackbar.LENGTH_LONG)
                    .setAction("Action", null).show();
        }
    });

    DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
    ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
            this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
    drawer.setDrawerListener(toggle);
    toggle.syncState();

    NavigationView navigationView = (NavigationView) findViewById(R.id.nav_view);
    navigationView.setNavigationItemSelectedListener(this);

    ((TextView)findViewById(R.id.textHere)).setText(Calendar.getInstance().getTime()+"");
}

Then the overnight log:

    $ adb shell am start -n "domain.removed.myapplication/domain.removed.myapplication.MainActivity" -a android.intent.action.MAIN -c android.intent.category.LAUNCHER
    Client not ready yet..Waiting for process to come online
    Connected to process 1324 on device freescale-ivg_mx6dq-1126a9d4e315e294
    I/art: Late-enabling -Xcheck:jni
    I/art: Debugger is no longer active
    W/System: ClassLoader referenced unknown path: /data/app/domain.removed.myapplication-2/lib/arm
    I/InstantRun: Instant Run Runtime started. Android package is domain.removed.myapplication, real application class is null.
    W/System: ClassLoader referenced unknown path: /data/app/domain.removed.myapplication-2/lib/arm
    D/TEST: NEW INSTANCE CREATED Tue Jan 25 19:00:45 GMT+08:00 2011=================================================
    W/art: Before Android 4.1, method android.graphics.PorterDuffColorFilter android.support.graphics.drawable.VectorDrawableCompat.updateTintFilter(android.graphics.PorterDuffColorFilter, android.content.res.ColorStateList, android.graphics.PorterDuff$Mode) would have incorrectly overridden the package-private method in android.graphics.drawable.Drawable
    D/OpenGLRenderer: Use EGL_SWAP_BEHAVIOR_PRESERVED: true
    I/imx6.gralloc: open gpu gralloc module!
    I/OpenGLRenderer: Initialized EGL, version 1.4
    D/TEST: NEW INSTANCE CREATED Wed Jan 26 04:08:19 GMT+08:00 2011=================================================
    D/TEST: NEW INSTANCE CREATED Wed Jan 26 05:10:15 GMT+08:00 2011=================================================
    D/TEST: NEW INSTANCE CREATED Wed Jan 26 06:13:26 GMT+08:00 2011=================================================
    D/TEST: NEW INSTANCE CREATED Wed Jan 26 07:15:13 GMT+08:00 2011=================================================
    W/art: Suspending all threads took: 32.077ms
    W/art: Suspending all threads took: 28.910ms
    W/art: Suspending all threads took: 29.957ms
    W/PathParser: Points are too far apart 4.000000596046461

Based on the logs, the app re-instantiates FIVE times.

My questions:

  1. Why Android is behaving this way?
  2. What is the best practice to handle this, and achieve my desired behavior? (app that can run for long hours without re-instantiating)
  3. If this is also common knowledge for Android devs, can you suggest/recommend key words, or search terms to find issues related to this?

Thanks guys in advance! :)

Joey

Lori
  • 1,392
  • 1
  • 21
  • 29
Joey
  • 11
  • 3

4 Answers4

0

You can not keep your application running all the time. It's not good for the battery. If your application in background can kill it to free resources for another app. Or for any other reasons like energy saving or whatever.

If you need do something in the background. You need to use service

With AlarmManager you can schedule when you service will start and do some work.

But in Android 6 google added a doze mode. When device goes to deep sleep after some time and only applications are optimized for doze mode can wake up.

thealeksandr
  • 1,686
  • 12
  • 17
  • Hi @thealeksandr , thanks for your fast response, the device is not powered by battery, and the app will not run all the time, just for long hours. (until hardware of the device is verified). But still thanks for those info I will keep that in mind. Also thanks for suggesting service, that might work with my app. – Joey Feb 10 '17 at 04:45
0

Heavy app initialization can happen when your code overrides the Application object. App initialization often occurs because of garbage collection being many in number, but however since you've told that you've checked for memory leaks already, that may/may not be the main issue. You can use the Method Tracing or Inline tracing as mentioned here.

You can avoid repeated app-initialization by making the UI simpler, avoiding complex initialization of sub systems within the activity.

Follow the content on the link - reply to this comment if you learn something new apart from what I've told. It will be a good learning for me as well :)

Cheers!

0

Joey, To start off this is not really an "Issue" because as you know almost all the android devices are battery powered and saving power is one of the main objectives of the android runtime (ART or Delvik). To answer your questions,

  1. Why Android is behaving this way?

If your activity isn't doing any effective "work" then the android system will suspend your app/apps and hibernate/sleep/go to power saver mode etc.

W/art: Suspending all threads took: 32.077ms
W/art: Suspending all threads took: 28.910ms
W/art: Suspending all threads took: 29.957ms

These lines indicate what i just said.That it how android works, don't get panicked.

  1. What is the best practice to handle this, and achieve my desired behavior? (app that can run for long hours without re-instantiating

well, if your app is actually doing something then the app won't go into hibernation, From what i see in your MainActivity, Your activity does NOTHING. its a simple UI which just sits there.. So the android runtime thinks that this app isn't doing anything => Suspend/kill the app.

  1. If this is also common knowledge for Android devs, can you suggest/recommend key words, or search terms to find issues related to this?

Check thealeksandr's answer for running long processes as a background service. Hope this helps..Cheers..!!

Infamous
  • 744
  • 11
  • 25
0

Sorry it took a while for me to update this, your answers to my question number 1 lead me to finding the perfect solution to my app requirements.

I added my app to the white list of battery optimization, check the following link for more info. Battery optimization

Joey
  • 11
  • 3