Android from the foundation · Start here

The one idea behind everything

Your app doesn't control its own life. Another process decides, and tells your app by sending messages to its main thread.

The problem

Why does one slow line of code freeze the whole UI? Why can't your app keep a screen alive when the system wants it gone? These look like separate rules to memorise. They aren't. They follow from one idea about who is in charge, and this course builds it up one puzzle at a time.

First, four words

  • A process is a running program with its own private memory. Your app is one process; other apps are others.
  • Memory here means the program's data while it runs. A process can only touch its own.
  • The kernel is the core of the operating system. It's the only code that can reach into every process.
  • A thread is one worker inside a process that runs code, one instruction after another.

And one Android word: a screen in your app is an Activity. onCreate()Your override of this method is what the main thread calls when system_server says "create". 1864 protected void onCreate(@Nullable Bundle savedInstanceState) {Activity.java, line 1864 · AOSP frameworks/base ↗ is the method that sets one up.

See it

The town hall (system_server) writes a letter; the post office (Binder, in the kernel) carries it into your app's house; the clerk (main thread) takes it from the in-tray and runs onCreate() your app (a process) onCreate() { … } main thread system_server Binder start X runs!
  1. Your app is a house with one clerk inside: the main thread. Your code waits on the desk. Notice what's missing: nothing in the house decides when your screen starts.

    Step 1 of 5
  2. That decision is made in another process, system_server: the town hall. It writes the order "start screen X". Predict: can the town hall just walk into your house?

    Step 2 of 5
  3. No: processes can't touch each other's memory. The letter goes through Binder, a driver in the kernel: the post office, the only one allowed into every house.

    Step 3 of 5
  4. The letter lands in the clerk's in-tray. The clerk handles letters one at a time, in order. (A small helper actually carries it in; you'll meet it in puzzle 6.) Predict: what happens next?

    Step 4 of 5
  5. The clerk runs your code: onCreate()Your override of this method is what the main thread calls when system_server says "create". 1864 protected void onCreate(@Nullable Bundle savedInstanceState) {Activity.java, line 1864 · AOSP frameworks/base ↗. You didn't call it. You were called. Every puzzle in this course is one piece of this chain.

    Step 5 of 5

The four characters

Every puzzle uses these four. Learn the picture once and you can reason about the rest.

  • Your app's process: your house. It runs your code, but it doesn't decide when things happen.
  • system_server: the town hall. One long-running Android process that keeps the register of every app and screen.
  • The kernel's Binder driver: the post office. The only way to carry a message between houses.
  • The main thread: the one clerk at your desk, handling one letter at a time.

Check yourself

Answer all three to unlock the next puzzle.

Who decides that your Activity should be created?

Not quite. That's the picture this puzzle replaces: you write onCreate()Your override of this method is what the main thread calls when system_server says "create". 1864 protected void onCreate(@Nullable Bundle savedInstanceState) {Activity.java, line 1864 · AOSP frameworks/base ↗, but you never call it. Watch who writes the order.

Right. system_server decides. Binder only carries the message, and your app is told.

Not quite. Binder carries the letter, it doesn't write it. The post office delivers; the town hall decides.

Can system_server call a method on your Activity object directly?

Not quite. Being powerful doesn't let a process into another's memory. Only the kernel can reach into every process, which is why the letter needs the post office.

Right. system_server lives in a different process and can't touch your app's memory, so the request travels through Binder.

Which worker runs your onCreate()Your override of this method is what the main thread calls when system_server says "create". 1864 protected void onCreate(@Nullable Bundle savedInstanceState) {Activity.java, line 1864 · AOSP frameworks/base ↗?

Not quite. Not any thread: screen code always runs on the one clerk, the main thread, in order.

Not quite. system_server only sends the order. The code of your screen runs in your house, by your clerk.

Right. The letter lands in your main thread's tray, and the main thread runs your code when it gets there.

Sources

What you now know

system_server decides → Binder carries the letter → your main thread receives it → your code runs. You don't call onCreate(); you get called.