About a year ago I was looking at our Mac OS X XPCOM local file implementation in Gecko and I noticed that it is pretty inefficient in terms of the number of system calls it makes for some common operations. I put optimizing that on my to-do list and I’ve now committed most of the big optimizations. Here are the results.
I tested a Firefox 3.6 nightly build (6/24/2009) against Firefox 3.5rc2 by recording all of the filesystem-related system calls each build made during the course of a full standalone talos Ts run. This talos test essentially launches and quits the browser over and over again (about 23 times). I recorded the filesystem-related system calls using the following command:
sudo fs_usage -e -f filesys | grep firefox-bin > ~/Desktop/call_log.txt
The high-level result is that there were 13% fewer filesystem-related system calls made by the Firefox 3.6 nightly build (184,609 vs. 212,253). Most of my optimizations involved moving to a single “stat” system call to get information instead of using Carbon and Cocoa APIs, which often make multiple system calls, particularly if they involve using Carbon FSRefs. Given my intent, it was unsurprising that the Firefox 3.6 nightly build made 32,344 calls to “stat” vs. 15,134 calls for Firefox 3.5rc2. That is a price worth paying for having the Firefox 3.6 nightly build make only 38,250 calls to “getattrlist” vs. 98,965 calls for Firefox 3.5rc2. In case you’re unfamiliar with “getattrlist,” its man page says “you can think of getattrlist() as a seriously enhanced version of stat(2).”
Here are some other results which are interesting because they give you a good idea of how often Firefox makes certain calls. I omitted some less interesting system calls that were made fewer than 3,000 times apiece.
15,134 stat, Firefox 3.5rc2
32,344 stat, Firefox 3.6 nightly
98,965 getattrlist, Firefox 3.5rc2
38,250 getattrlist, Firefox 3.6 nightly
14,290 open, Firefox 3.5rc2
14,196 open, Firefox 3.6 nightly
9,027 write, Firefox 3.5rc2
8,649 write, Firefox 3.6 nightly
20,643 read, Firefox 3.5rc2
20,245 read, Firefox 3.6 nightly
1,325 pread, Firefox 3.5rc2
1,052 pread, Firefox 3.6 nightly
12,230 lseek, Firefox 3.5rc2
11,787 lseek, Firefox 3.6 nightly
7,692 fcntl, Firefox 3.5rc2
7,214 fcntl, Firefox 3.6 nightly
2,096 mmap, Firefox 3.5rc2
1,950 mmap, Firefox 3.6 nightly