Posts | Archive

A Peek Inside the GTalkService Connection

This posts aims to peek inside the Android GTalkService connection and observe its protocol.  In particular, we're interested in the INSTALL_ASSET message and whether or not it is protected by any additional cryptographic signatures beyond the intended guarantees provided by the SSL transport.

A Brief Introduction to the GTalkService

If you haven't read the previous post on the GTalkService and INSTALL_ASSET/REMOVE_ASSET, do so first.

In short, the GTalkService is a persistent connection maintained from your Android phone to Google's servers at all time.  It allows Google to push down messages to your phone in order to perform particular actions.  For example, when you click to install an app through the Android Market, Google pushes down an INSTALL_ASSET to your phone which causes it to fetch and install that application.  When Google wants to remote kill an application from your phone, it pushes down a REMOVE_ASSET message to your phone which causes it to remove the particular application.

The GTalkService is a SSL connection which is intended to provide confidentiality and integrity of the messages exchanged between your phone and Google's servers.  However, as we've seen in the past, SSL does not always hold up those guarantees.

So the question we're trying to answer in this post is: If an attacker is able to compromise the integrity of the GTalkService SSL connection in any way, will they be able to forge INSTALL_ASSET messages to install arbitrary applications on the target device?  Or, is there any additional layer of integrity (eg. INSTALL_ASSET messages being signed by Google) to prevent it?

Experimental Setup

To snoop on the GTalkService connection, we need to man-in-the-middle the SSL connection.  There's three steps to doing this:

  1. Obtain an Android emulator image with market capabilities.
  2. Add your own CA certificate to /system/etc/security/cacerts.bks using keytools.
  3. MITM the connection using a tool such as Moxie's sslsniff with your CA cert.

Now, when we fire up the emulator and the GTalkService attempts to connect, it will be successfully MITM'ed since it trusts the CA certificate we created.

The GTalkService Protocol

We can now snoop on the GTalkService connection.  Here's a brief dump of several of the message types used when your phone communicates with Google's servers over the GTalkService.

Login Messages

The initial login exchange passes your Jabber ID (JID) to Google's servers along with (I believe) the authentication token associated with your Google account after obtaining it from Google's ClientLogin service.

Client -> Server
00000000  03                                                |.|
00000001

Server -> Client
00000000  03                                                |.|
00000001

Client -> Server
00000000  02 c1 02 0a 07 41 32 49  36 44 2d 30 12 09 67 6d  |.....A2I6D-0..gm|
00000010  61 69 6c 2e 63 6f 6d 1a  11 6a 6f 6e 6f 61 6e 64  |ail.com..jonoand|
00000020  72 6f 69 64 6d 61 72 6b  65 74 22 13 61 6e 64 72  |roidmarket".andr|
00000030  6f 69 64 77 43 78 77 58  70 68 59 6a 33 4a 4d 2a  |oidwCxwXphYj3JM*|
00000040  e0 01 44 51 41 41 41 4a  30 41 41 41 44 39 4f 4c  |..DQAAAJ0AAAD9OL|
00000050  6a 43 6a 48 71 34 49 62  36 7a 77 6d 6d 44 32 33  |jCjHq4Ib6zwmmD23|
00000060  39 52 56 78 5f 73 77 5f  56 63 77 43 6e 45 70 4c  |9RVx_sw_VcwCnEpL|
00000070  38 70 56 56 6f 79 4f 70  36 6b 49 4a 63 31 38 70  |8pVVoyOp6kIJc18p|
00000080  72 52 66 71 77 34 76 59  34 50 74 78 70 43 5a 67  |rRfqw4vY4PtxpCZg|
00000090  4e 54 30 35 50 77 5a 59  65 72 59 32 43 4e 58 45  |NT05PwZYerY2CNXE|
000000a0  54 49 37 73 62 72 63 4c  70 6a 4b 30 7a 50 4c 45  |TI7sbrcLpjK0zPLE|
000000b0  51 65 6f 38 50 4b 66 67  38 51 4e 41 34 66 34 69  |Qeo8PKfg8QNA4f4i|
000000c0  31 7a 43 48 5a 73 43 62  68 41 32 50 39 59 6c 59  |1zCHZsCbhA2P9YlY|
000000d0  58 6f 55 65 65 68 79 4d  77 70 66 6a 51 39 35 68  |XoUeehyMwpfjQ95h|
000000e0  31 30 46 4c 45 79 79 6b  67 78 4c 30 6a 76 42 4e  |10FLEyykgxL0jvBN|
000000f0  68 4a 42 4c 6d 5a 6a 4d  50 46 33 2d 71 33 41 48  |hJBLmZjMPF3-q3AH|
00000100  63 70 74 4d 78 5a 35 59  56 4f 30 6b 32 73 58 56  |cptMxZ5YVO0k2sXV|
00000110  30 2d 44 4b 63 66 66 7a  31 34 51 49 31 7a 33 33  |0-DKcffz14QI1z33|
00000120  57 38 32 17 61 6e 64 72  6f 69 64 2d 66 32 66 31  |W82.android-f2f1|
00000130  35 63 63 64 31 37 66 62  33 30 35 38 d6 e1 d9 c4  |5ccd17fb3058....|
00000140  c5 c1 a2 02                                       |....|
00000144

Server -> Client
00000000  03 3a 0a 07 41 32 49 36  44 2d 30 12 2f 6a 6f 6e  |.:..A2I6D-0./jon|
00000010  6f 61 6e 64 72 6f 69 64  6d 61 72 6b 65 74 40 67  |oandroidmarket@g|
00000020  6d 61 69 6c 2e 63 6f 6d  2f 61 6e 64 72 6f 69 64  |mail.com/android|
00000030  77 43 78 77 58 70 68 59  6a 33 4a 4d              |wCxwXphYj3JM|
0000003c

Heartbeat Messages

Heartbeats are initiated by the Android client simply to ping Google's servers and ensure connectivity is active.

Client -> Server
00000000  00 00                                             |..|
00000002

Server -> Client
00000000  01 00                                             |..|
00000002

INSTALL_ASSET Messages

The INSTALL_ASSET message is what we're most interested in.  During my testing, I installed a random application from the Android Market on my emulator in order to capture an INSTALL_ASSET payload.  As you can see below, the message specifies a number of parameters:

  • tickle_id: 1277687266074
  • assetid: -155863831473120556
  • asset_name: Replica Island
  • asset_type: GAME
  • asset_package: com.replica.replicaisland
  • asset_blob_url: http://android.clients.google.com/market/download/Download?assetId=-155863831473120556&userId=986032118775&deviceId=1094117203906638597
  • asset_signature: Ayn2bWDqckQkKsBY4JurvCFpYN0
  • asset_size: 5144485
Server -> Client
00000000  08 d5 03 08 8a c2 89 fd  cb c1 a2 02 1a 0a 67 6f  |..............go|
00000010  6f 67 6c 65 2e 63 6f 6d  22 2f 6a 6f 6e 6f 61 6e  |ogle.com"/jonoan|
00000020  64 72 6f 69 64 6d 61 72  6b 65 74 40 67 6d 61 69  |droidmarket@gmai|
00000030  6c 2e 63 6f 6d 2f 61 6e  64 72 6f 69 64 77 43 78  |l.com/androidwCx|
00000040  77 58 70 68 59 6a 33 4a  4d 2a 0d 49 4e 53 54 41  |wXphYj3JM*.INSTA|
00000050  4c 4c 5f 41 53 53 45 54  3a 1a 0a 09 74 69 63 6b  |LL_ASSET:...tick|
00000060  6c 65 5f 69 64 12 0d 31  32 37 37 36 38 37 32 36  |le_id..127768726|
00000070  36 30 37 34 3a 1e 0a 07  61 73 73 65 74 69 64 12  |6074:...assetid.|
00000080  13 2d 31 35 35 38 36 33  38 33 31 34 37 33 31 32  |.-15586383147312|
00000090  30 35 35 36 3a 1c 0a 0a  61 73 73 65 74 5f 6e 61  |0556:...asset_na|
000000a0  6d 65 12 0e 52 65 70 6c  69 63 61 20 49 73 6c 61  |me..Replica Isla|
000000b0  6e 64 3a 12 0a 0a 61 73  73 65 74 5f 74 79 70 65  |nd:...asset_type|
000000c0  12 04 47 41 4d 45 3a 2a  0a 0d 61 73 73 65 74 5f  |..GAME:*..asset_|
000000d0  70 61 63 6b 61 67 65 12  19 63 6f 6d 2e 72 65 70  |package..com.rep|
000000e0  6c 69 63 61 2e 72 65 70  6c 69 63 61 69 73 6c 61  |lica.replicaisla|
000000f0  6e 64 3a 9a 01 0a 0e 61  73 73 65 74 5f 62 6c 6f  |nd:....asset_blo|
00000100  62 5f 75 72 6c 12 87 01  68 74 74 70 3a 2f 2f 61  |b_url...http://a|
00000110  6e 64 72 6f 69 64 2e 63  6c 69 65 6e 74 73 2e 67  |ndroid.clients.g|
00000120  6f 6f 67 6c 65 2e 63 6f  6d 2f 6d 61 72 6b 65 74  |oogle.com/market|
00000130  2f 64 6f 77 6e 6c 6f 61  64 2f 44 6f 77 6e 6c 6f  |/download/Downlo|
00000140  61 64 3f 61 73 73 65 74  49 64 3d 2d 31 35 35 38  |ad?assetId=-1558|
00000150  36 33 38 33 31 34 37 33  31 32 30 35 35 36 26 75  |63831473120556&u|
00000160  73 65 72 49 64 3d 39 38  36 30 33 32 31 31 38 37  |serId=9860321187|
00000170  37 35 26 64 65 76 69 63  65 49 64 3d 31 30 39 34  |75&deviceId=1094|
00000180  31 31 37 32 30 33 39 30  36 36 33 38 35 39 37 3a  |117203906638597:|
00000190  2e 0a 0f 61 73 73 65 74  5f 73 69 67 6e 61 74 75  |...asset_signatu|
000001a0  72 65 12 1b 41 79 6e 32  62 57 44 71 63 6b 51 6b  |re..Ayn2bWDqckQk|
000001b0  4b 73 42 59 34 4a 75 72  76 43 46 70 59 4e 30 3a  |KsBY4JurvCFpYN0:|
000001c0  15 0a 0a 61 73 73 65 74  5f 73 69 7a 65 12 07 35  |...asset_size..5|
000001d0  31 34 34 34 38 35 40 01                           |144485@.|
000001d8

The INSTALL_ASSET Signature

Uh-oh, there's an opaque asset_signature attribute in that INSTALL_ASSET message.  Is it possible Google is cryptographically signing each message in order to thwart an attacker trying to forge malicious INSTALL_ASSET messages?  Let's take a deeper look at the signature and where it is used in the Android system.

The asset_signature attribute is processed in the getDownloadInfo function of the InstallAssetReceiver class in the Vending.apk package.  Later, we see that the signature is actually a base64-encoded SHA-1 which is compared to the hash of the fetched APK file specified in the asset_blob_url attribute:

verifyapk

To verify our assumptions that this is a SHA-1 of the APK and not a digital signature over the INSTALL_ASSET message, let's take a peek at the vending package's sqlite database:

# sqlite3 /data/data/com.android.vending/databases/assets.db
sqlite> select * from assets10;
...|com.replica.replicaisland|false|Ayn2bWDqckQkKsBY4JurvCFpYN0#5144485|...

Let's try to verify the signature present in the assets.db against the SHA-1 hash of the application's APK:

>>> print binascii.hexlify(base64.b64decode('Ayn2bWDqckQkKsBY4JurvCFpYN0='))
0329f66d60ea7244242ac058e09babbc216960dd

jono@dionysus ~ $ openssl sha1 com.replica.replicaisland.apk
SHA1(com.replica.replicaisland.apk)= 0329f66d60ea7244242ac058e09babbc216960dd

Indeed, these signatures are identical, indicating that the asset_signature contained in the INSTALL_ASSET message is simply a hash of the target APK, and _not_ a digital signature authenticating the source of the message.

Conclusion

After peeking in to the GTalkService and observing the plaintext INSTALL_ASSET payloads, it is clear that there are no digital signatures attached to the INSTALL_ASSET messages.  Therefore, an attacker who is able to intercept the SSL connection used by the GTalkService will be able to push down arbitrary INSTALL_ASSET messages to the victim's phone.  Since the phone will install the APK specified in the INSTALL_ASSET message automatically without user intervention, the attacker could remotely install a malicious application requesting arbitrary permissions and containing a malicious payload.

The larger lesson here is that SSL is not an end-all solution for delivering software payloads.  A loss in network integrity should not directly lead to a loss of host integrity.  Just as used in many desktop application auto-updating components, the update manifest and/or payload should be digitally signed by the distributor in addition to using SSL as a transport.  Google should be cryptographically signing the INSTALL_ASSET messages used in the GTalkService to protect against this threat model.

Copyright © 2015 - Jon Oberheide <jon at oberheide dot org>.