[webkit-dev] Memory profiler

Raul raulh.wk at gmail.com
Tue Feb 3 13:07:09 PST 2009


I would like to start working on bug 10930 "WebKit could benefit from
a JavaScript live object profiler" (if no one else is already working
on it)

This is what I understand on how memory is allocated now (please
correct me if I'm wrong or missed something):

JavaScript objects are stored in the Collector object that is composed
of CollectorBlocks that contain CollectorCells.
The base object stored in this collector is JSCell. It overrides the
default "new" operator and returns memory from a collector cell
These cells have a hard limit in terms of size, meaning that no other
properties can be added to the base class, because all the JSObjects
will become bigger then a cell size.
In order to hold bigger objects, JSObject has an internal pointer to
the actual structure that holds the data. The constructor and
destructor maintain this structure.
For example, JSString has a pointer to an internal structure that
holds the actual data. This means that overriding the "new" operator
and extracting allocation size will not going to be enough.
WebCore has many IDL files that are used to automatically generate
glue code for C++ classes. Every C++ class exposed to javascript will
have a single JSObject wrapper created.

This how I plan to implement this:

All JSObjects have a ClassInfo which stores the object type name as a
string. This class can also store the size of the objects.
In WebCore the glue code is generated using python script from an IDL
file. The script can be changed to create ClassInfo structures that
also contain the sizeof().
A special virtual size() function can be added on each JSCell that
will return the size of the JSCell/JSString/JSObject + the size from
the classinfo + the value returned by the size() function of the
implementation object (we can implement this method for the most
used/most memory consuming objects).
Special cases that use large amount of memory like String, HashTables,
Arrays, Functions, Images, Canvas, CSS, DOM Elements can be added a
size() function. This function will be declared in the IDL file and
the python script will generate a special function in the JSObject
glue code.

When a new JSCell is created its CallStack can be recorded in a
hashtable for later use. The CallStack can be  stored in a per thread
global variable as (WebKit is using a collector for each page, so the
"new" operator also have an ExecState argument that can be used to get
the callstack). When it is destroyed, the hashtable should be updated
accordingly. Each JSObject should have an unique id per session.

Another issue in javascript is that objects defined by the user code
do not hold a ClassName. Their ClassInfo is simply "Object". Another
virtual function can be added on JSCell to return the actual type. In
this case the type can be the Function name that generated the object
(javascript constructor) or the FileName.js at LineNumber in case of
anonymous functions.

Finally, memory snapshots can be generated by iterating the collector.
Then, the snapshots can be compared to extract relevant information
and displayed.

Any comments/suggestions are welcome.


More information about the webkit-dev mailing list