Overtaking Firefox Profiles: Vulnerabilities in Firefox for Android

Abstract|We present newly-found vulnerabilities in the Firefox Android Application. Exploiting them allows a malicious application to successfully derandomize the Firefox prole directory name in a practical amount of time and exltrate sensitive data (such as cookies and cached information) which reside in that directory, breaking Android's sandbox.

Overtaking Firefox Profiles: Vulnerabilities in Firefox for Android

1.
1
OVERTAKING FIREFOX PROFILES
Vulnerabilities in Firefox for Android
Roee Hay
IBM Security Systems
roeeh@il.ibm.com
Abstract—We present newly-found vulnerabili-
ties in the Firefox Android Application. Exploiting
them allows a malicious application to successfully
derandomize the Firefox proﬁle directory name in
a practical amount of time and exﬁltrate sensitive
data (such as cookies and cached information)
which reside in that directory, breaking Android’s
sandbox.
Index Terms—CVE-2014-1484; CVE-2014-
1506; CVE-2014-1515; CVE-2014-1516.
I. Android basics
A. Threat model
Android applications are executed in a sandbox
environment to ensure that no application can access
sensitive information held by another without proper
privileges. For example, Android’s browser appli-
cation holds sensitive information such as cookies,
cache and history which cannot be accessed by third-
party apps. An android application may request spe-
ciﬁc privileges (permissions) during its installation;
if granted by the user, the capabilities are extended.
Permissions are deﬁned under the application’s man-
ifest ﬁle, namely AndroidManifest.xml.
B. Activities and Services
Android applications are composed of compo-
nents of diﬀerent types including activities and
services. An Activity, implemented by the an-
droid.content.Activity class [1], deﬁnes a single
UI, e.g. a browsing window or a preferences screen.
Services [2] are application components that are used
for background tasks.
C. Inter-Process Communication (IPC) and Intents
Android applications communicate with each other
through Intents. These are messaging objects that
contain several attributes such as an action, data,
category, target and extras. The data attribute is
a URI which identiﬁes the Intent (e.g. tel:0422123).
Each Intent can also contain extra data ﬁelds, namely
Intent extras, which reside inside a Bundle (imple-
mented by the android.os.Bundle class [3]). Intent
extras can be set by using the Intent.putExtra
API or by manipulating the extras Bundle directly.
It is important to emphasize that intents provide a
channel for a malicious application to inject malicious
data into a target, potentially vulnerable application.
Intents can have either explicit or implicit destina-
tion, depending whether targets are speciﬁed or not.
Intents can be broadcast, passed to the startActiv-
ity call (when an application starts another activ-
ity), or passed to the startService call (when an
application starts a service). Under the application’s
manifest ﬁle, an application component may claim
whether it can be invoked externally using an Intent,
and if so which set of permissions is required. We
deﬁne a public application component as one which
can be invoked externally by a (potentially malicious)
application without any permissions. All other com-
ponents are deﬁned as private, i.e. they can only be
invoked by other application components of the same
package, or externally with proper privileges.
II. Generation of the Profile Directory
Firefox stores the personal data under the proﬁle
directory, located at files/mozilla/X.default/
where X is a randomly chosen 8-byte word over
the alphanumeric alphabet [a-z0-9]. The gener-
ation of X.default is implemented at GeckoPro-
file.saltProfileName (Figure II.1).
Since the proﬁle directory name is random, Firefox
stores a mapping under the files/mozilla/pro-
files.ini ﬁle (Figure II.2)
If Firefox does not ﬁnd a valid proﬁle, for example
due to a missing profiles.ini, it creates a new one
by invoking GeckoProfile.createProfileDir.
III. Vulnerabilities
A. Proﬁle Directory Name Weak Randomization
The Math.random() static method returns a uni-
formly distributed pseudo-random number between

2.
2
1 private static String
2 saltProfileName ( String name)
3 {
4 String allowedChars =
5 ”abcdefghijklmnopqrstuvwxyz0123456789 ” ;
6
7 StringBuilder s a l t =
8 new StringBuilder ( 1 6 ) ;
9
10 for ( int i = 0; i < 8; i++) {
11 s a l t . append ( allowedChars . charAt (( int )
12 (Math . random () ∗
13 allowedChars . length ( ) ) ) ) ;
14 }
15 s a l t . append ( ’ . ’ ) ;
16 s a l t . append (name ) ;
17 return s a l t . toString ( ) ;
18 }
Figure II.1. GeckoProfile.saltProfileName(String name)
[Profile0]
Default=1
Name=default
IsRelative=1
Path=475jbgu6.default
[General]
StartWithLastProfile=1
Figure II.2. profiles.ini
0 and 1. In Android, the implementation is under
libcore1
:
1 public static synchronized double random ()
2 {
3 i f ( random == null )
4 {
5 random = new Random ( ) ;
6 }
7 return random . nextDouble ( ) ;
8 }
Figure III.1. Math.random()
We can see that this method relies on the
java.util.Random class which is seeded in its de-
fault constructor. In Android 4.4 and below, it is
implemented as follows2
:
1https://android.googlesource.com/platform/libcore/
2https://android.googlesource.com/platform/libcore/+/
android-4.4 r1.2/luni/src/main/java/java/util/Random.java
1 public Random()
2 {
3 setSeed ( System . currentTimeMillis ()
4 + System . identityHashCode ( this ) ) ;
5 }
Figure III.2. java.util.Random’s constructor
Therefore the seed depends on a couple of values:
1) The current time in milliseconds precision
(System.currentTimeMillis())
2) The identity hash code of the Random object
(System.identityHashCode(this))
System.identityHashCode is implemented by na-
tive code in the Dalvik VM implementation3
. The
identity hash code value is the object’s Virtual Ad-
dress (VA) which resides in the heap of the Dalvik
VM process.
GeckoProfile.saltProfileName uses
Math.random() which is cryptographically insecure.
We have seen that its seed relies on the inner-
Random object creation time (in ms precision) and
its VA. Both factors are not random. The creation
time can be leaked by an adversary (see IV-A1b)
and the VA lacks randomness due to ineﬀective
ASLR in the Dalvik VM process [4], [5]. Since the
Dalvik VM is forked from the Zygote process, the
VA of the Dalvik Heap is the same for all Android
Dalvik applications. To conclude, the seed is not
random, thus the proﬁle directory name entropy is
far from the ideal 41.36 random bits (log2 368
) and
can be predicted by the adversary as we will see
next.
B. Proﬁle Directory Name Leaks to Android System
Log
The random Proﬁle Directory Name is written to
the Android System Log (logcat) in various locations.
For instance, upon Firefox launch, the following data
is written:
D/GeckoProfile( 4766): Found profile dir:
/data/data/.../files/mozilla/24pd90uh.default
In Android 4.0 and below, the Android log can easily
be read by all applications including malicious ones
by acquiring the READ_LOGS permission. Android 4.1
has introduced a change to this behavior to prevent
such log leakage attacks: the READ_LOGS permission
is no longer required, however applications can only
listen to their own log. In section IV-B we show how
a malicious app can manipulate Firefox to leak its
own private log in order to overcome this obstacle.
3https://android.googlesource.com/platform/dalvik.git/+/
android-4.4 r1.2/vm/Sync.cpp

3.
3
C. Automatic File Download to SD Card
Any ﬁle which cannot be rendered by Fire-
fox is automatically downloaded to the SD card
(/mnt/sdcard/Download), a folder which can be
read by a malicious application by acquiring the
READ_EXTERNAL_STORAGE permission. Interestingly,
this permission was not even enforced before Android
4.44
. This allows a malicious application to extract
non-renderable data such as the cookies database,
once it has managed to derandomize the proﬁle
directory name.
D. Crash Reporter File Manipulation
The org.mozilla.gecko.CrashReporter class is
a public activity. Its purpose is to send crash dumps
to Mozilla when needed (Figure III.3). The CrashRe-
porter activity receives the dump ﬁle path as an
input (an Intent extra parameter). When the activity
is launched, its onCreate method (Figure III.4) is
executed and the following actions take place:
1) Using the moveFile (Figure III.5) method, the
given minidump ﬁle is moved to the pending
minidumps path, files/mozilla/Crash Re-
ports/pending.
2) A meta-data ﬁlename is deduced from the given
minidump ﬁle path, by replacing all ’.dmp’
occurrences with ’.extra’. i.e. <filename>.dmp
becomes <filename>.extra.
3) The meta-data ﬁle is moved to the pending
minidumps path using the moveFile method.
4) The meta-data ﬁle is parsed as a key/value ﬁle
format (Figure III.6). The target server URL
(i.e. the one that the crash information is sent
to) is speciﬁed here using the ServerURL key.
5) The crash dialog is presented to the user (Fig-
ure III.3).
If the user presses the Close or Restart buttons with
the Send report check-box enabled, the minidump
alongside with other sensitive information is sent
to the speciﬁed server by calling the sendReport
method. It should be noted that if the user has
also checked the Include the address check-box, then
Android logs are sent as well.
The CrashReporter activity consumes the
minidump path from the input intent (Figure III.4,
Line 4) although it should be considered untrusted
data since the activity is public as deﬁned in
the Android Manifest ﬁle. Therefore, a malicious
application can control the source path of the
moved minidump ﬁle and the deduced extra ﬁle
4http://developer.android.com/reference/android/
Manifest.permission.html#READ EXTERNAL STORAGE
Figure III.3. Crash Reporter dialog
(Figure III.4, Lines 8, 11). We will see in the next
section that this allows that attacker to control the
destination server for the crash report, hence the
response value used as a ﬁle path in Figure III.7,
Line 19 should be untrusted as well.
IV. Exploitation
The attacker (by the use of a malicious appli-
cation) can exploit a subset of the aforementioned
vulnerabilities in order to:
1) Derandomize the proﬁle directory path.
2) Exﬁltrate sensitive data (such as cookies and
cached information) from the proﬁle directory.
In this section we describe several attractive exploita-
tion suites.
A. Suite I: Exploiting Vulnerabilities III-A, III-C and
optionally III-D
1) Derandomizing the Proﬁle Path: Let Y be the
seed chosen by Firefox. The goal of the attacker is to
derandomize it by recording some value which shares
a strong relation with it. Both the VA and the time
parts of the seed cannot be entirely determined by
the attacker, however, most of their bits can be leaked
to the attacker using simple actions:
a) Derandomizing the VA Value: To obtain
parts of the VA, as per the ineﬀective ASLR, the
attacker can query its own process using the Sys-
tem.identitiyHashCode routine on some object.

4.
4
b) Derandomizing the Time Value: The ms
time value can be leaked in two diﬀerent ways.
First, if Firefox had been installed after the ma-
licious app, the latter can record the ﬁrst Firefox
run by simply monitoring the device’s process list.
Otherwise, the attacker app can exploit Vulnera-
bility III-D to move the profiles.ini ﬁle (which
has a deterministic path) to the diﬀerent direc-
tory. The exploitation is done by sending an Intent
to the Crash Reporter with minidumpPath Intent
extra set to /data/data/org.mozilla.firefox/-
files/mozilla/profiles.ini. Firefox will create a
new proﬁle on its next run, which can be forced by
crashing it (this can be done by exploiting Vulnera-
bility III-D, sending an Intent to the Crash Reporter
without a minidumpPath extra). Again the attacker
can record the Firefox launch time.
Let X be the attacker’s inaccurate sample where
X = V A + MeasuredTime. Let ε be the error,
i.e. ε = Y − X. In our brute-force attack we try
values in the order of their inferred probabilities
which can be computed oﬄine by the attacker (see
Section V). Let N be the number of attempts until
a success, then the expected number of attempts is
E(N) =
n
k=1 k·p(k) where {p(k)}n
k=1 are the ordered
inferred probabilities (p(1) ≥ p(2) ≥ · · · ≥ p(n)).
Please note that the expression for E(N) proves
that this is the optimal search algorithm (in terms
of the expectation). A simpler model is to assume
that ε is a (discrete) bell-curve with the center
estimated by ¯ε = ¯x-¯y. It can be shown that E(N) =
O(E|X − EX|) = O (σε) so a more narrow bell-
curve yields a shorter attack time (on average). By
using the inferred probabilities of ε and the sampled
seed, X, the attacker creates a list of proﬁle names
by mimicking the GeckoProfile.saltProfileName
implementation (this computation can be also done
oﬀ the device and downloaded from the attacker).
2) Data Exﬁltration: This phase is online. The
attacker creates a specially crafted world-readable
HTML ﬁle and commands Firefox to load it (by using
an Intent). This ﬁle includes the list of proﬁle names
ordered by their probabilities generated previously.
The JavaScript code in the HTML ﬁle goes over the
list, searching for the correct proﬁle. When there is
a match, it can download any ﬁle under the proﬁles
directory by creating an iframe targeting the ﬁle-
name. As per Vulnerability III-C, if Firefox cannot
render the ﬁle, it will automatically download the ﬁle
to the SD card (/mnt/sdcard/Download), a folder
which can be read by the attacker.
B. Suite II: Exploiting Vulnerabilities III-B, III-C
and optionally III-D
1) Derandomizing the Proﬁle Path : On Android
4.0 and below, the Android System Log can easily be
read by the malicious app. This allows the malicious
app to exploit Vulnerability III-B and deduce the
proﬁle directory path.
Android 4.1 prevents this attack as applications
can only listen to their own logs. Since Firefox sends
its own private log alongside the crash report (see
Section III-D) , Vulnerability III-D can be exploited
for sending the logs to the attacker:
• The malicious app creates two world
readable ﬁles under its data directory:
/data/data/<malicious app>/foo.dmp with
an arbitrary content (can be left empty) and
/data/data/<malicious app>/foo.extra
which contains the attacker’s server,
ServerURL=http://<attacker>/.
• The malicious app generates an Intent ob-
ject which targets the CrashReporter activity
with a minidumpPath parameter set to /data/-
data/<malicious app>/foo.dmp
After the above actions take place, according to the
operation of the CrashReporter activity (see Section
III-D), Firefox will move foo.dmp and foo.extra
from the malicious app data directory to the Fire-
fox crash reports pending path and then parse
foo.extra for key-value pairs. Since the extra ﬁle
now contains the attacker’s IP as the ServerURL, if
the user pressed one of the buttons on the CrashRe-
porter dialog, Firefox would send the crash report
to the attacker. If the user has also checked the
Include the address check-box, then Firefox would
also append the Android Log output, which contains
the Firefox private logs that include the random
proﬁle directory name. It should be noted that since
Firefox only sends a 200 lines window of the log, the
leaked path can be out of that window since it is
logged upon Firefox’s launch. In order to make sure
that the path is within the window, the attacker can
restart Firefox by crashing it. This can be easily done
by invoking the CrashReporter activity without a
minidumpPath parameter.
2) Data Exﬁltration: Once the attacker has learnt
the proﬁle path, he can leak ﬁles by exploiting Vul-
nerability III-C. The attacker simply invokes Firefox
using an Intent with a payload set to the target ﬁle
path.
C. Suite III: Exploiting Vulnerabilities III-B and
III-D
1) Derandomizing the Proﬁle Path Seed: This part
is exactly as described in Section IV-B1.

5.
5
2) Data Exﬁltration: Here we exploit
Vulnerability III-D. We indirectly inject the
ServerURL=http://<attacker> string to the target
ﬁle and trick Firefox to use this ﬁle as the minidump
extra. For instance, by using this method, the
attacker can leak the cache. First, he opens Firefox
(using an Intent) on an attacker’s controlled website,
which contains the above string in its HTML body
(Figure IV.1). After the cache has been prepared,
the attacker can leak it by generating another Intent
that targets the CrashReporter activity, with the
minidump path parameter set to the cache ﬁle. Since
the cache ﬁle path has no ’.dmp’ substring, the
computed extra ﬁle will be the same, and the target
server URL will be parsed out of the cache ﬁle.
1 <HTML>
2 <BODY>
3 ServerURL=http : //<ATTACKER>
4 </BODY>
5 </HTML>
Figure IV.1. Injected payload into Firefox’s cache
V. Evaluation
We tested our Suite I exploit on Firefox 25.0.1
running on Samsung GT-I9500 Galaxy S4 device
equipped with Android 4.2.2. In order to infer the
probabilities of ε we ran 404 independent runs of the
following test:
1) Call Math.Random() and retrieve its identi-
tyHashCode (Figure V.1)
2) Start monitoring the process list in a frequency
of 20 Hz for recording the Firefox launch time.
3) Remove the profiles.ini ﬁle from the Firefox
directory by exploiting Vulnerability III-D.
4) Record the created proﬁle directory.
5) Kill Firefox.
6) Restart Firefox.
7) Print the needed values.
1 Math . random ( ) ;
2 Field f = Math . class .
3 getDeclaredField ( ”random ” ) ;
4 f . s e t A c c e s s i b l e ( true ) ;
5 Random r = (Random) f . get ( null ) ;
6 Long addr = System . identityHashCode ( r ) ;
Figure V.1. Retrieving the identityHashCode of the Math
inner Random object
For example, for each run we received and recorded
the following data:
Sampled VA: 42dc6cd8
Sampled Time: 1385337348079
Sampled Seed: 142cf66ccc7
Created profile: xa1x453r.default
Later we calculated the real seed and ε by an oﬄine
brute-force. For example, for the data above, the real
seed is 1386459232784 and ε = 142665.
We witnessed three strong linear correlations be-
tween Y and X (Figure V.2). We believe that the
reason for the less dense lines rely on Dalvik Heap
internals which caused the oﬀset to ’jump’ with a
ﬁxed number for a few tests (i.e. the probability for
this to happen is low).
Ϭ
ϮϬϬϬϬϬϬ
ϰϬϬϬϬϬϬ
ϲϬϬϬϬϬϬ
ϴϬϬϬϬϬϬ
ϭϬϬϬϬϬϬϬ
ϭϮϬϬϬϬϬϬ
ϭϰϬϬϬϬϬϬ
ϭϲϬϬϬϬϬϬ
Ϭ ϮϬϬϬϬϬϬ ϰϬϬϬϬϬϬ ϲϬϬϬϬϬϬ ϴϬϬϬϬϬϬ ϭϬϬϬϬϬϬϬ ϭϮϬϬϬϬϬϬ ϭϰϬϬϬϬϬϬ
Figure V.2. Linear correlation between the real seed and the
sampled one
We created a histogram for inferring the distribu-
tion of ε (Figure V.3) and calculated the expected
number of attempts, E(N), which is 152779.65 and
is equivalent to 17.22 bits. Note that the Shannon
entropy is very close, 18.63 bits. We’ve got an entropy
which is much lower than the ideal 64 bits (the java
long primitive size) seed entropy, thus the attack is
feasible.
Ϭ
Ϭ͘ϬϮ
Ϭ͘Ϭϰ
Ϭ͘Ϭϲ
Ϭ͘Ϭϴ
Ϭ͘ϭ
Ϭ͘ϭϮ
Ϭ͘ϭϰ
ͲϭϬϬϬϬϬ ϮϬϬϬϬϬ ϱϬϬϬϬϬ ϴϬϬϬϬϬ ϭϭϬϬϬϬϬ ϭϰϬϬϬϬϬ ϭϳϬϬϬϬϬ
Figure V.3. ε Histogram
We then adhered to the steps of section IV-A,
taken the simpler approach where we assert a sym-
metric bell curve. Since we received three linear