Android Question How does secure inter-app communication work?

Sandman

Expert
Licensed User
Longtime User
Hi all,

This question isn't about something specific like problematic code. It's about understanding the concept of secure inter-app communication.

I've read up on how apps communicate, and it seems to be mainly using intents, sockets and running a local webserver on the phone. (Did I miss a method?) If we ignore the complexity factor of the methods for the time being, is one method more secure than the other? And I mean this mainly from a "don't allow sniffing or manipulating the communication" perspective. (It's my understanding that it's somewhat simple to intercept and log intents, for instance.)

Like, for instance, in Sweden, there is a standard method of identifying yourself using your mobile: BankID (https://play.google.com/store/apps/details?id=com.bankid.bus). And pretty much all banks have their own apps also, like Swedbank for example (https://play.google.com/store/apps/details?id=se.swedbank.mobil), which rely on BankID for authenticating its users. (BankID is such a dominating standard that it's also used for pretty much all government communcation, including doing your taxes once per year.)

When I want to look at my bank accounts, these are the steps:
  1. Launch the bank app, enter my social security number and press Next
  2. BankID launches automatically and I identify myself in it using a very secret code and press Next
  3. I automatically return to my bank app and can do whatever I wanted to do

The BankID app obviously communicates with an online webservice somewhere, but let's ignore those parts for now. I'm simply trying to understand how the two apps communicate in a secure way. Especially considering that if one uses a rooted device, everything can be transparent and recordable. Is the way around that to ensure the BankID app simply doesn't run if the device is rooted? (My phone isn't rooted, so I've never encountered the situation.)

Thanks
 

Erel

B4X founder
Staff member
Licensed User
Longtime User
Many bad things can happen if you assume that the OS itself is insecure. For example it can record all the keystrokes or record the screen.
You cannot implement a secure solution on a non-secure OS. If the OS wants to steal all the device data then it will be capable of doing it.

If you create a socket connection between two apps then other apps cannot monitor the connection. You do need to somehow identify the two apps and make sure that you are not connected to a malicious app.

Another approach is to avoid sending sensitive information. For example when you log in to this forum your password is never sent to the server. Only a hash of the password is sent.
 
Upvote 0

Sandman

Expert
Licensed User
Longtime User
You cannot implement a secure solution on a non-secure OS.

Yep, agreed. Thus all the discussions out there on the net on how important it is with open source firmware and bios and the like.


If you create a socket connection between two apps then other apps cannot monitor the connection.

We're assuming a non-rooted device here, right? In that case, ok, that does make sense.


You do need to somehow identify the two apps and make sure that you are not connected to a malicious app.

We're going off into real implementation details here, but I'm wondering if this solution would make sense or if it's just stupid:

Assumptions:
We have two apps, a client app (like the bank app) and an ID app (like the BankID app). There only exists a small, limited amount of client apps, and that they are all known by the BankID organization. The BankID app contains the package names for all the client apps. (Or it looks them up online, not really important for this discussion.)
  • The client makes an explicit intent to the ID app together with its request and its own package name.
  • The ID app verifies that the client package name is in list of approved, known clients.
  • The ID app then sends the response as another explicit intent to the specified package name, together with extra data.
Would this be enough to create secure IAC?


Another approach is to avoid sending sensitive information. For example when you log in to this forum your password is never sent to the server. Only a hash of the password is sent.

I'm not entirely sure I understand this. I mean, if someone would get hold of my cookie with the password, they'd be able to access to forum as me. Right? The hash is the sensitive information in itself. It doesn't provide any extra security above the fact that they don't actually know my password. (And this is why many sites require you to re-enter your password if you are about to do something extra dangerous, like terminate your account etc, just to make sure it's not a copied cookie/hash.)
 
Upvote 0

Erel

B4X founder
Staff member
Licensed User
Longtime User
We're assuming a non-rooted device here, right?
Probably yes.

There is no simple way to verify the identity of the app that sent the intent. Also remember that a hacker can create an app with the same package name and send the intent.

I mean, if someone would get hold of my cookie with the password, they'd be able to access to forum as me
You can use password noncing to prevent replay attack: https://stackoverflow.com/questions/8174131/what-is-the-difference-between-hash-salting-and-noncing
 
Upvote 0

Sandman

Expert
Licensed User
Longtime User
There is no simple way to verify the identity of the app that sent the intent.

Yeah, I think I've read that in the forum. That's why in my example the client added an extra field with its own package name so that the ID app knew where to send its response.


Also remember that a hacker can create an app with the same package name and send the intent.

You don't mean via the app store, right? In there they all need to be unique, I think. But assuming I haven't installed the official Facebook app, I would be able to whip up an app in B4A using the package name com.facebook.katana (same as Facebook app) and then be eligable for responses from the ID app. That's what you mean, right?

So perhaps intents aren't a good fit for secure communication. And using sockets wouldn't really improve anything at all, right? Just same complexity, but different communication method?

I'm starting to think that the bank app and the BankID app don't have any sensitive exchange at all. Perhaps it's more like this:
  • Bank app connects to its backend and informs its waiting for confirmation of my identity
  • Bank backend communicates with BankID backend, informing "Bank App For MegaBank" is requesting my identity
  • Bank app launches BankID app
  • BankID checks with its backend to see if there's a waiting request for identification
  • BankID finds waiting request, asks me to enter password and sends that somehow to its backend
  • BankID backend verifies my identity and sends an OK to bank backend, which in turn gives thumbs-up to bank app
  • Bank app is logged in and ready to be used
Using this flow it's a super simple IAC between the apps, it's basically just an explicit intent to launch the BankID and then BankID returns once there's a success or fail of some sort. It's up to either app to solve the security between itself and its backend.

Makes sense, doesn't it? Would you say it's probably done something like this?


You can use password noncing to prevent replay attack

But that would only be completely secure if you updated the nonce for every request, isn't that correct? If you "just" limit it to a time window, it's the same as having a vanilla hash, you just have a tighter window of potential (mis-)use. Taking a quick look at the cookies here, it seems posting my nonce would give people a five hour window to use my identity? (assuming I don't do anything before somebody else, thus invalidating the posted value)
 
Upvote 0

Erel

B4X founder
Staff member
Licensed User
Longtime User
You don't mean via the app store, right?
No. Package names in the app store are unique.

I would be able to whip up an app in B4A using the package name com.facebook.katana (same as Facebook app) and then be eligable for responses from the ID app. That's what you mean, right?
Yes.

Makes sense, doesn't it? Would you say it's probably done something like this?
It makes sense. Hard to say how they implemented it.

But that would only be completely secure if you updated the nonce for every request, isn't that correct?
You need to implement it as part of the handshake process. It would be unique for each session.
 
Upvote 0
Top