Merge inbound to m-c. a=merge
authorRyan VanderMeulen <ryanvm@gmail.com>
Wed, 03 Sep 2014 16:38:57 -0400
changeset 203417 acbdce59da2fda8c1dce44802cfae8dd4147aabf
parent 203256 bfef88becbba6972b2a5c1f92afac2ab4a9f0d4c (current diff)
parent 203416 a2bdb4249448077674cdc3bb022d43e9ed1f19d1 (diff)
child 203435 03665e187d8c43d405d6948a26dd48daa2faf9c3
child 203444 d76eb4c469dcf342c4ddbb39dd3842e9c16d995e
child 203465 0da762e6868a1601e6f78dfe26aa9ccdd1d94d2b
push id27425
push userryanvm@gmail.com
push dateWed, 03 Sep 2014 20:38:59 +0000
treeherdermozilla-central@acbdce59da2f [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmerge
milestone35.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Merge inbound to m-c. a=merge
b2g/installer/package-manifest.in
browser/base/content/test/general/browser.ini
build/mozconfig.vs2010-common
dom/webidl/moz.build
ipc/chromium/src/base/base_paths.cc
ipc/chromium/src/base/base_paths.h
ipc/chromium/src/base/base_paths_linux.cc
ipc/chromium/src/base/base_paths_linux.h
ipc/chromium/src/base/base_paths_mac.h
ipc/chromium/src/base/base_paths_mac.mm
ipc/chromium/src/base/base_paths_win.cc
ipc/chromium/src/base/base_paths_win.h
ipc/chromium/src/base/hmac.h
ipc/chromium/src/base/hmac_mac.cc
ipc/chromium/src/base/path_service.cc
ipc/chromium/src/base/path_service.h
ipc/chromium/src/base/stats_counters.h
ipc/chromium/src/base/stats_table.cc
ipc/chromium/src/base/stats_table.h
ipc/chromium/src/base/system_monitor.cc
ipc/chromium/src/base/system_monitor.h
ipc/chromium/src/base/system_monitor_posix.cc
ipc/chromium/src/base/system_monitor_win.cc
ipc/chromium/src/base/trace_event.cc
ipc/chromium/src/base/trace_event.h
ipc/chromium/src/base/worker_pool.h
ipc/chromium/src/base/worker_pool_linux.h
ipc/chromium/src/base/worker_pool_mac.mm
js/src/jit/IonSpewer.cpp
js/src/jit/IonSpewer.h
layout/reftests/w3c-css/submitted/flexbox/flexbox-abspos-child-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-abspos-child-1a.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-abspos-child-1b.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-content-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-content-horiz-1a.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-content-horiz-1b.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-content-vert-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-content-vert-1a.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-content-vert-1b.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-baseline-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-baseline-horiz-1a.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-baseline-horiz-1b.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-baseline-horiz-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-baseline-horiz-2.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-baseline-horiz-3-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-baseline-horiz-3.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-baseline-horiz-4-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-baseline-horiz-4.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-baseline-horiz-5-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-baseline-horiz-5.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-horiz-1-block.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-horiz-1-table.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-horiz-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-horiz-2.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-horiz-3-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-horiz-3.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-horiz-4-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-horiz-4.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-horiz-5-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-horiz-5.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-stretch-vert-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-stretch-vert-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-stretch-vert-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-stretch-vert-2.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-2.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-3-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-3.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-4-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-4.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-rtl-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-rtl-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-rtl-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-rtl-2.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-rtl-3-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-rtl-3.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-rtl-4-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-align-self-vert-rtl-4.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-anonymous-items-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-anonymous-items-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-align-self-baseline-horiz-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-align-self-baseline-horiz-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-align-self-baseline-vert-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-align-self-baseline-vert-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-empty-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-empty-1a.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-empty-1b.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-item-horiz-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-item-horiz-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-item-vert-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-item-vert-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-horiz-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-horiz-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-horiz-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-horiz-2.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-horiz-3-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-horiz-3.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-horiz-4-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-horiz-4.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-vert-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-vert-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-vert-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-multi-line-vert-2.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-single-item-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-single-item-1a.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-baseline-single-item-1b.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-block-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-block-horiz-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-block-vert-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-block-vert-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-canvas-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-canvas-horiz-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-canvas-vert-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-canvas-vert-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-fieldset-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-fieldset-horiz-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-fieldset-vert-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-fieldset-vert-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-iframe-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-iframe-horiz-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-iframe-vert-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-iframe-vert-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-img-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-img-horiz-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-img-vert-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-img-vert-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-textarea-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-textarea-horiz-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-textarea-vert-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-textarea-vert-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-video-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-video-horiz-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-video-vert-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-basic-video-vert-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-horiz-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-horiz-1a.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-horiz-1b.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-horiz-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-horiz-2a.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-horiz-2b.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-vert-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-vert-1a.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-vert-1b.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-vert-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-vert-2a.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-break-request-vert-2b.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-collapsed-item-baseline-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-collapsed-item-baseline-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-collapsed-item-horiz-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-collapsed-item-horiz-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-collapsed-item-horiz-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-collapsed-item-horiz-2.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-collapsed-item-horiz-3-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-collapsed-item-horiz-3.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-flow-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-flow-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-flow-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-flow-2.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-wrap-horiz-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-wrap-horiz-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-wrap-horiz-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-wrap-horiz-2.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-wrap-vert-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-wrap-vert-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-wrap-vert-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-flex-wrap-vert-2.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-items-as-stacking-contexts-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-items-as-stacking-contexts-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-items-as-stacking-contexts-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-items-as-stacking-contexts-2.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-items-as-stacking-contexts-3-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-items-as-stacking-contexts-3.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-horiz-1a.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-horiz-1b.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-horiz-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-horiz-2.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-horiz-3-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-horiz-3.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-horiz-4-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-horiz-4.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-horiz-5-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-horiz-5.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-vert-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-vert-1a.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-vert-1b.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-vert-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-vert-2.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-vert-3-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-vert-3.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-vert-4-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-vert-4.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-vert-5-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-justify-content-vert-5.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-margin-auto-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-margin-auto-horiz-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-margin-auto-horiz-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-margin-auto-horiz-2.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-1-reverse-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-1-reverse.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-1-rtl-reverse.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-1-rtl.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-2a.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-2b.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-3-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-3-reverse-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-3-reverse.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-3.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-4-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-mbp-horiz-4.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-horiz-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-horiz-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-horiz-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-horiz-2.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-horiz-3-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-horiz-3.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-horiz-4-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-horiz-4.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-horiz-5-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-horiz-5.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-vert-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-vert-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-vert-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-vert-2.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-vert-3-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-vert-3.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-vert-4-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-vert-4.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-vert-5-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-overflow-vert-5.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-paint-ordering-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-paint-ordering-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-paint-ordering-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-paint-ordering-2.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-root-node-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-root-node-1a.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-root-node-1b.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-sizing-horiz-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-sizing-horiz-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-sizing-horiz-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-sizing-horiz-2.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-sizing-vert-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-sizing-vert-1.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-sizing-vert-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-sizing-vert-2.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-table-fixup-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-table-fixup-1a.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-table-fixup-1b.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-whitespace-handling-1-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-whitespace-handling-1a.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-whitespace-handling-1b.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-whitespace-handling-2-ref.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-whitespace-handling-2.xhtml
layout/reftests/w3c-css/submitted/flexbox/flexbox-with-pseudo-elements-1-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-with-pseudo-elements-1.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-with-pseudo-elements-2-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-with-pseudo-elements-2.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-with-pseudo-elements-3-ref.html
layout/reftests/w3c-css/submitted/flexbox/flexbox-with-pseudo-elements-3.html
media/libvpx/vpx_rtcd.h
media/libvpx/vpx_rtcd_armv7-android-gcc.h
media/libvpx/vpx_rtcd_generic-gnu.h
media/libvpx/vpx_rtcd_x86-darwin9-gcc.h
media/libvpx/vpx_rtcd_x86-linux-gcc.h
media/libvpx/vpx_rtcd_x86-win32-vs8.h
media/libvpx/vpx_rtcd_x86_64-darwin9-gcc.h
media/libvpx/vpx_rtcd_x86_64-linux-gcc.h
media/libvpx/vpx_rtcd_x86_64-win64-vs8.h
--- a/.gdbinit
+++ b/.gdbinit
@@ -172,10 +172,10 @@ document ptarray
         ptarray a 1 2 - Prints elements in range [idx1..idx2] from tarray
 end
 
 def js
   call DumpJSStack()
 end
 
 def ft
-  call nsFrame::DumpFrameTree($arg0)
+  call $arg0->DumpFrameTree()
 end
--- a/accessible/xpcom/xpcAccessibleTable.h
+++ b/accessible/xpcom/xpcAccessibleTable.h
@@ -16,17 +16,20 @@ class nsIArray;
 namespace mozilla {
 namespace a11y {
 
 class TableAccessible;
 
 class xpcAccessibleTable
 {
 public:
-  explicit xpcAccessibleTable(mozilla::a11y::TableAccessible* aTable) : mTable(aTable) { }
+  explicit xpcAccessibleTable(TableAccessible* aTable) :
+    mTable(aTable)
+  {
+  }
 
   nsresult GetCaption(nsIAccessible** aCaption);
   nsresult GetSummary(nsAString& aSummary);
   nsresult GetColumnCount(int32_t* aColumnCount);
   nsresult GetRowCount(int32_t* aRowCount);
   nsresult GetCellAt(int32_t aRowIndex, int32_t aColumnIndex,
                      nsIAccessible** aCell);
   nsresult GetCellIndexAt(int32_t aRowIndex, int32_t aColumnIndex,
--- a/accessible/xpcom/xpcAccessibleTableCell.h
+++ b/accessible/xpcom/xpcAccessibleTableCell.h
@@ -20,18 +20,20 @@ class TableCellAccessible;
 
 /**
  * This class provides an implementation of the nsIAccessibleTableCell
  * interface's methods.
  */
 class xpcAccessibleTableCell
 {
 public:
-  explicit xpcAccessibleTableCell(mozilla::a11y::TableCellAccessible* aTableCell) :
-    mTableCell(aTableCell) { }
+  explicit xpcAccessibleTableCell(TableCellAccessible* aTableCell) :
+    mTableCell(aTableCell)
+  {
+  }
 
   nsresult GetTable(nsIAccessibleTable** aTable);
   nsresult GetColumnIndex(int32_t* aColIdx);
   nsresult GetRowIndex(int32_t* aRowIdx);
   nsresult GetColumnExtent(int32_t* aExtent);
   nsresult GetRowExtent(int32_t* aExtent);
   nsresult GetColumnHeaderCells(nsIArray** aHeaderCells);
   nsresult GetRowHeaderCells(nsIArray** aHeaderCells);
--- a/addon-sdk/test/browser.ini
+++ b/addon-sdk/test/browser.ini
@@ -2,14 +2,13 @@
 support-files =
   head.js
   Math.jsm
   math.js
   data.json
   invalid.json
 [browser_sdk_loader_sdk_modules.js]
 [browser_sdk_loader_sdk_gui_modules.js]
-skip-if = e10s # Bug ?????? - test times out.
 [browser_sdk_loader_jsm_modules.js]
 [browser_sdk_loader_js_modules.js]
 [browser_sdk_loader_json.js]
 [browser_sdk_loader_chrome.js]
 [browser_sdk_loader_chrome_in_sdk.js]
--- a/b2g/installer/package-manifest.in
+++ b/b2g/installer/package-manifest.in
@@ -288,16 +288,17 @@
 #ifdef MOZ_CAPTIVEDETECT
 @BINPATH@/components/captivedetect.xpt
 #endif
 @BINPATH@/components/shellservice.xpt
 @BINPATH@/components/shistory.xpt
 @BINPATH@/components/spellchecker.xpt
 @BINPATH@/components/storage.xpt
 @BINPATH@/components/telemetry.xpt
+@BINPATH@/components/toolkit_filewatcher.xpt
 @BINPATH@/components/toolkit_finalizationwitness.xpt
 @BINPATH@/components/toolkit_formautofill.xpt
 @BINPATH@/components/toolkit_osfile.xpt
 @BINPATH@/components/toolkit_xulstore.xpt
 @BINPATH@/components/toolkitprofile.xpt
 #ifdef MOZ_ENABLE_XREMOTE
 @BINPATH@/components/toolkitremote.xpt
 #endif
--- a/browser/base/content/test/chat/browser.ini
+++ b/browser/base/content/test/chat/browser.ini
@@ -1,9 +1,9 @@
 [DEFAULT]
-skip-if = buildapp == 'mulet'
+skip-if = buildapp == 'mulet' || e10s
 support-files =
   head.js
   chat.html
 
 [browser_chatwindow.js]
 [browser_focus.js]
 [browser_tearoff.js]
--- a/browser/base/content/test/general/browser.ini
+++ b/browser/base/content/test/general/browser.ini
@@ -97,37 +97,41 @@ support-files =
   content_aboutAccounts.js
 [browser_aboutSupport_newtab_security_state.js]
 [browser_aboutHealthReport.js]
 skip-if = os == "linux" # Bug 924307
 [browser_aboutHome.js]
 skip-if = e10s # Bug ?????? - no about:home support yet
 [browser_aboutSyncProgress.js]
 [browser_addKeywordSearch.js]
+skip-if = e10s
 [browser_alltabslistener.js]
 skip-if = os == "linux" || e10s # Linux: Intermittent failures, bug 951680; e10s: Bug ?????? - notifications don't work correctly.
 [browser_backButtonFitts.js]
 skip-if = os != "win" || e10s # The Fitts Law back button is only supported on Windows (bug 571454) / e10s - Bug ?????? test touches content (attempts to add an event listener directly to the contentWindow)
 [browser_blob-channelname.js]
 [browser_bookmark_titles.js]
 skip-if = buildapp == 'mulet' || toolkit == "windows" || e10s # Disabled on Windows due to frequent failures (bugs 825739, 841341) / e10s - Bug ?????? test checks event.target on load event, which our e10s utils don't support
 [browser_bug304198.js]
+skip-if = e10s
 [browser_bug321000.js]
 skip-if = true # browser_bug321000.js is disabled because newline handling is shaky (bug 592528)
 [browser_bug329212.js]
+skip-if = e10s
 [browser_bug331772_xul_tooltiptext_in_html.js]
+skip-if = e10s
 [browser_bug356571.js]
 [browser_bug380960.js]
 [browser_bug386835.js]
 skip-if = e10s # Bug 691614 - no e10s zoom support yet
 [browser_bug405137.js]
 [browser_bug406216.js]
 [browser_bug409481.js]
-skip-if = e10s # Bug 921952 - Content:Click event issues (test simulated middle-click on a link and checks the value pastes - it doesn't)
 [browser_bug409624.js]
+skip-if = e10s
 [browser_bug413915.js]
 [browser_bug416661.js]
 skip-if = e10s # Bug 691614 - no e10s zoom support yet
 [browser_bug417483.js]
 skip-if = e10s # Bug ?????? - no about:home support yet
 [browser_bug419612.js]
 skip-if = e10s # Bug 691614 - no e10s zoom support yet
 [browser_bug422590.js]
@@ -141,29 +145,31 @@ skip-if = e10s # Bug ?????? - "content w
 skip-if = e10s # Bug ?????? - test directly manipulates content (eg, var expertDiv = gBrowser.contentDocument.getElementById("expertContent");)
 [browser_bug432599.js]
 [browser_bug435035.js]
 [browser_bug435325.js]
 skip-if = buildapp == 'mulet' || e10s # Bug ?????? - test directly manipulates content
 [browser_bug441778.js]
 skip-if = buildapp == 'mulet' || e10s # Bug 691614 - no e10s zoom support yet
 [browser_bug455852.js]
+skip-if = e10s
 [browser_bug460146.js]
 skip-if = e10s # Bug 866413 - PageInfo doesn't work in e10s
 [browser_bug462289.js]
 skip-if = toolkit == "cocoa" || e10s # Bug ?????? - not sure why this is timing out and crashing!!
 [browser_bug462673.js]
 skip-if = e10s # Bug 924260 - "Window is closed"
 [browser_bug477014.js]
 skip-if = e10s # Bug 918634 - swapFrameLoaders not implemented for e10s
 [browser_bug479408.js]
 skip-if = buildapp == 'mulet' || e10s # Bug 918663 - DOMLinkAdded events don't make their way to chrome
 [browser_bug481560.js]
 skip-if = e10s # Bug ????? - This bug attached an event listener directly to the content
 [browser_bug484315.js]
+skip-if = e10s
 [browser_bug491431.js]
 skip-if = buildapp == 'mulet' || e10s # Bug 918634 - swapFrameLoaders (and thus replaceTabWithWindow) not implemented for e10s
 [browser_bug495058.js]
 skip-if = e10s # Bug 918634 - swapFrameLoaders (and thus replaceTabWithWindow) not implemented for e10s
 [browser_bug517902.js]
 skip-if = e10s # Bug 866413 - PageInfo doesn't work in e10s
 [browser_bug519216.js]
 skip-if = e10s # Bug ?????? - some weird timing issue with progress listeners that fails intermittently
@@ -183,40 +189,44 @@ skip-if = buildapp == 'mulet' || e10s # 
 skip-if = e10s # Bug 691614 - no e10s zoom support yet
 [browser_bug555767.js]
 skip-if = e10s # Bug 916974 - Session history doesn't work in e10s
 [browser_bug556061.js]
 skip-if = e10s # Bug 932651 - getClipboardData in specialpowersAPI.js not e10s friendly
 [browser_bug559991.js]
 skip-if = e10s # Bug 691614 - no e10s zoom support yet
 [browser_bug561623.js]
+skip-if = e10s
 [browser_bug561636.js]
 skip-if = e10s # Bug 691601 - no form submit observers
 [browser_bug562649.js]
 skip-if = e10s # Bug 940195 - XULBrowserWindow.isBusy is false as a remote tab starts loading
 [browser_bug563588.js]
 [browser_bug565575.js]
+skip-if = e10s
 [browser_bug565667.js]
 run-if = toolkit == "cocoa"
 [browser_bug567306.js]
+skip-if = e10s
 [browser_bug575561.js]
 [browser_bug575830.js]
 skip-if = e10s # Bug 691614 - no e10s zoom support yet
 [browser_bug577121.js]
 [browser_bug578534.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content
 [browser_bug579872.js]
 [browser_bug580638.js]
 [browser_bug580956.js]
 skip-if = e10s # Bug 516755 - SessionStore disabled for e10s
 [browser_bug581242.js]
 skip-if = e10s # Bug 930863 - pageshow issues ("TypeError: charset is undefined" in pageshow listener, as document is null)
 [browser_bug581253.js]
 skip-if = e10s # Bug 930863 - pageshow issues ("TypeError: charset is undefined" in pageshow listener, as document is null)
 [browser_bug581947.js]
+skip-if = e10s
 [browser_bug585558.js]
 [browser_bug585785.js]
 [browser_bug585830.js]
 [browser_bug590206.js]
 [browser_bug592338.js]
 skip-if = e10s # Bug 653065 - Make the lightweight theme web installer ready for e10s
 [browser_bug594131.js]
 [browser_bug595507.js]
@@ -230,78 +240,85 @@ skip-if = e10s # Bug ?????? - URLBar iss
 [browser_bug623893.js]
 skip-if = e10s # Bug 916974 - Session history doesn't work in e10s
 [browser_bug624734.js]
 [browser_bug633691.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content (eg, var expertDiv = gBrowser.contentDocument.getElementById("expertContent");)
 [browser_bug647886.js]
 skip-if = buildapp == 'mulet' || e10s # Bug 916974 - Session history doesn't work in e10s
 [browser_bug655584.js]
+skip-if = e10s
 [browser_bug664672.js]
 [browser_bug676619.js]
 skip-if = buildapp == 'mulet' || os == "mac" || e10s # mac: Intermittent failures, bug 925225; e10s: Bug ?????? - test directly manipulates content (event.target.location)
 [browser_bug678392.js]
 skip-if = e10s # Bug ?????? - Obscure non-windows failures ("Snapshot array has correct length of 1 after loading one page. - Got 0, expected 1" and more)
 [browser_bug710878.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content (doc.querySelector)
 [browser_bug719271.js]
 skip-if = e10s # Bug 691614 - no e10s zoom support yet
 [browser_bug724239.js]
 [browser_bug734076.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content
 [browser_bug735471.js]
 [browser_bug749738.js]
 skip-if = e10s # Bug 921935 - focusmanager issues with e10s
 [browser_bug763468_perwindowpb.js]
+skip-if = e10s
 [browser_bug767836_perwindowpb.js]
 skip-if = e10s # Bug ?????? - test reports a leaked nsGlobalWindow with e10s enabled.
 [browser_bug771331.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content
 [browser_bug783614.js]
 [browser_bug816527.js]
 skip-if = e10s # Bug 916974 - Session history doesn't work in e10s
 [browser_bug817947.js]
 skip-if = e10s # Bug 916974 - Session history doesn't work in e10s
 [browser_bug822367.js]
 [browser_bug832435.js]
 [browser_bug839103.js]
 [browser_bug880101.js]
 [browser_bug882977.js]
 [browser_bug902156.js]
+skip-if = e10s
 [browser_bug906190.js]
 skip-if = buildapp == "mulet" || e10s # Bug ?????? - test directly manipulates content (strange - gets an element from a child which it tries to treat as a string, but that fails)
 [browser_bug970746.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content (directly gets elements from the content)
 [browser_bug1015721.js]
 skip-if = os == 'win' || e10s # Bug 1056146 - FullZoomHelper uses promiseTabLoadEvent() which isn't e10s friendly
 [browser_canonizeURL.js]
 skip-if = e10s # Bug ?????? - [JavaScript Error: "Error in AboutHome.sendAboutHomeData TypeError: target.messageManager is undefined" {file: "resource:///modules/AboutHome.jsm" line: 208}]
 [browser_contentAreaClick.js]
+skip-if = e10s
 [browser_contextSearchTabPosition.js]
-skip-if = os == "mac" # bug 967013, bug 926729
+skip-if = os == "mac" || e10s # bug 967013, bug 926729
 [browser_ctrlTab.js]
 skip-if = e10s # Bug ????? - thumbnail captures need e10s love (tabPreviews_capture fails with Argument 1 of CanvasRenderingContext2D.drawWindow does not implement interface Window.)
 [browser_customize_popupNotification.js]
+skip-if = e10s
 [browser_datareporting_notification.js]
 run-if = datareporting
 [browser_devices_get_user_media.js]
 skip-if = buildapp == 'mulet' || (os == "linux" && debug) || e10s # linux: bug 976544; e10s: Bug 973001 - appears user media notifications only happen in the child and don't make their way to the parent?
 [browser_devices_get_user_media_about_urls.js]
 skip-if = e10s # Bug 973001 - appears user media notifications only happen in the child and don't make their way to the parent?
 [browser_discovery.js]
 skip-if = e10s # Bug 918663 - DOMLinkAdded events don't make their way to chrome
 [browser_duplicateIDs.js]
 [browser_drag.js]
 skip-if = true # browser_drag.js is disabled, as it needs to be updated for the new behavior from bug 320638.
 [browser_favicon_change.js]
+skip-if = e10s
 [browser_findbarClose.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content (tries to grab an iframe directly from content)
 [browser_fullscreen-window-open.js]
 skip-if = buildapp == 'mulet' || e10s || os == "linux" # Bug 933103 - mochitest's EventUtils.synthesizeMouse functions not e10s friendly. Linux: Intermittent failures - bug 941575.
 [browser_fxa_oauth.js]
+skip-if = e10s
 [browser_gestureSupport.js]
 skip-if = e10s # Bug 863514 - no gesture support.
 [browser_getshortcutoruri.js]
 [browser_hide_removing.js]
 [browser_homeDrop.js]
 skip-if = buildapp == 'mulet'
 [browser_identity_UI.js]
 skip-if = e10s # Bug ?????? - this test fails for obscure reasons on non-windows builds only.
@@ -311,16 +328,17 @@ skip-if = e10s # Bug ?????? - this test 
 skip-if = e10s # Bug 921957 - remote webprogress doesn't supply originalURI attribute on the request object
 [browser_keywordSearch_postData.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content (gBrowser.contentDocument.body.textContent)
 [browser_lastAccessedTab.js]
 skip-if = toolkit == "windows" # Disabled on Windows due to frequent failures (bug 969405)
 [browser_locationBarCommand.js]
 skip-if = os == "linux" || e10s # Linux: Intermittent failures, bug 917535; e10s: Bug ?????? - Focus issues (There should be no focused element - Got [object XULElement], expected null)
 [browser_locationBarExternalLoad.js]
+skip-if = e10s
 [browser_menuButtonFitts.js]
 skip-if = os != "win" || e10s # The Fitts Law menu button is only supported on Windows (bug 969376); # Bug ?????? - URL bar issues ("There should be no focused element - Got [object XULElement], expected null")
 [browser_middleMouse_noJSPaste.js]
 skip-if = e10s # Bug 921952 - Content:Click event issues
 [browser_minimize.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content (TypeError: gBrowser.docShell is null)
 [browser_mixedcontent_securityflags.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content ("cannot ipc non-cpow object")
@@ -330,16 +348,17 @@ skip-if = buildapp == 'mulet' || e10s # 
 skip-if = buildapp == 'mulet' || e10s # Bug ?????? - test directly manipulates content (gBrowser.selectedBrowser.contentWindow.applicationCache.oncached = function() {...})
 [browser_overflowScroll.js]
 [browser_pageInfo.js]
 skip-if = buildapp == 'mulet' || e10s # Bug 866413 - PageInfo doesn't work in e10s
 [browser_page_style_menu.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content
 
 [browser_parsable_css.js]
+skip-if = e10s
 [browser_parsable_script.js]
 skip-if = debug || asan # Times out on debug/asan, and we are less picky about our JS there
 
 [browser_pinnedTabs.js]
 [browser_plainTextLinks.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content (creates and fetches elements directly from content document)
 [browser_popupUI.js]
 skip-if = buildapp == 'mulet' || e10s # Bug ?????? - test directly manipulates content (tries to get a popup element directly from content)
@@ -347,16 +366,17 @@ skip-if = buildapp == 'mulet' || e10s # 
 skip-if = buildapp == 'mulet' || e10s # Bug ?????? - timeout after logging "Error: Channel closing: too late to send/recv, messages will be lost"
 [browser_private_browsing_window.js]
 skip-if = buildapp == 'mulet'
 [browser_private_no_prompt.js]
 skip-if = buildapp == 'mulet'
 [browser_relatedTabs.js]
 [browser_removeTabsToTheEnd.js]
 [browser_removeUnsafeProtocolsFromURLBarPaste.js]
+skip-if = e10s
 [browser_sanitize-download-history.js]
 skip-if = true # bug 432425
 [browser_sanitize-passwordDisabledHosts.js]
 [browser_sanitize-sitepermissions.js]
 [browser_sanitize-timespans.js]
 skip-if = buildapp == 'mulet'
 [browser_sanitizeDialog.js]
 skip-if = buildapp == 'mulet'
@@ -367,65 +387,72 @@ skip-if = true  # disabled until the tre
 [browser_save_link-perwindowpb.js]
 skip-if = buildapp == 'mulet' || e10s # Bug ?????? - test directly manipulates content (event.target)
 [browser_save_private_link_perwindowpb.js]
 skip-if = buildapp == 'mulet' || e10s # e10s: Bug 933103 - mochitest's EventUtils.synthesizeMouse functions not e10s friendly
 [browser_save_video.js]
 skip-if = buildapp == 'mulet' || e10s # Bug ?????? - test directly manipulates content (event.target)
 [browser_scope.js]
 [browser_searchSuggestionUI.js]
+skip-if = e10s
 support-files =
   searchSuggestionUI.html
   searchSuggestionUI.js
 [browser_selectTabAtIndex.js]
 skip-if = e10s # Bug ?????? - no idea! "Accel+9 selects expected tab - Got 0, expected 9"
 [browser_star_hsts.js]
 skip-if = e10s # Bug ?????? - timeout after logging "Error: Channel closing: too late to send/recv, messages will be lost"
 [browser_subframe_favicons_not_used.js]
 [browser_tabDrop.js]
-skip-if = buildapp == 'mulet'
+skip-if = buildapp == 'mulet' || e10s
 [browser_tabMatchesInAwesomebar_perwindowpb.js]
 skip-if = e10s # Bug 918634 - swapFrameLoaders not implemented for e10s (test uses gBrowser.swapBrowsersAndCloseOther)
 [browser_tab_drag_drop_perwindow.js]
 skip-if = buildapp == 'mulet'
 [browser_tab_dragdrop.js]
 skip-if = buildapp == 'mulet' || e10s # Bug 918634 - swapFrameLoaders not implemented for e10s (test uses gBrowser.swapBrowsersAndCloseOther)
 [browser_tab_dragdrop2.js]
-skip-if = buildapp == 'mulet'
+skip-if = buildapp == 'mulet' || e10s
 [browser_tabbar_big_widgets.js]
 skip-if = os == "linux" || os == "mac" # No tabs in titlebar on linux
                                        # Disabled on OS X because of bug 967917
 [browser_tabfocus.js]
 skip-if = e10s # Bug 921935 - focusmanager issues with e10s (test calls getFocusedElementForWindow with a content window)
 [browser_tabkeynavigation.js]
+skip-if = e10s
 [browser_tabopen_reflows.js]
 skip-if = e10s # Bug ?????? - test needs to be updated for e10s (captures a stack that isn't correct in e10s)
 [browser_tabs_isActive.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content (tries to get/set attributes directly on content docshell)
 [browser_tabs_owner.js]
 [browser_trackingUI.js]
+skip-if = e10s
 support-files =
   trackingPage.html
   benignPage.html
 [browser_typeAheadFind.js]
 skip-if = buildapp == 'mulet' || e10s # Bug 921935 - focusmanager issues with e10s (test calls waitForFocus)
 [browser_unloaddialogs.js]
 skip-if = e10s # Bug ?????? - test uses chrome windowMediator to try and see alert() from content
 [browser_urlHighlight.js]
+skip-if = e10s
 [browser_urlbarAutoFillTrimURLs.js]
+skip-if = e10s
 [browser_urlbarCopying.js]
 skip-if = e10s # Bug 932651 - getClipboardData in specialpowersAPI.js not e10s friendly
 [browser_urlbarEnter.js]
 skip-if = e10s # Bug ?????? - obscure non-windows child process crashes on try
 [browser_urlbarRevert.js]
 skip-if = e10s # Bug ?????? - ESC reverted the location bar value - Got foobar, expected example.com
 [browser_urlbarSearchSingleWordNotification.js]
+skip-if = e10s
 [browser_urlbarStop.js]
 skip-if = e10s # Bug ????? - test calls gBrowser.contentWindow.stop
 [browser_urlbarTrimURLs.js]
+skip-if = e10s
 [browser_urlbar_search_healthreport.js]
 skip-if = e10s # Bug ?????? - FHR tests failing (either with "no data for today" or "2 records for today")
 [browser_utilityOverlay.js]
 [browser_visibleFindSelection.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content
 [browser_visibleLabel.js]
 [browser_visibleTabs.js]
 [browser_visibleTabs_bookmarkAllPages.js]
@@ -441,13 +468,16 @@ skip-if = buildapp == 'mulet'
 skip-if = e10s # Bug ?????? - test directly manipulates content (content.document.getElementById)
 [browser_zbug569342.js]
 skip-if = e10s # Bug 516755 - SessionStore disabled for e10s
 [browser_registerProtocolHandler_notification.js]
 skip-if = e10s # Bug 940206 - nsIWebContentHandlerRegistrar::registerProtocolHandler doesn't work in e10s
 [browser_no_mcb_on_http_site.js]
 skip-if = e10s # Bug 516755 - SessionStore disabled for e10s
 [browser_bug1003461-switchtab-override.js]
+skip-if = e10s
 [browser_bug1024133-switchtab-override-keynav.js]
+skip-if = e10s
 [browser_bug1025195_switchToTabHavingURI_ignoreFragment.js]
 [browser_addCertException.js]
 skip-if = e10s # Bug ?????? - test directly manipulates content (content.document.getElementById)
 [browser_bug1045809.js]
+skip-if = e10s
--- a/browser/components/customizableui/test/browser.ini
+++ b/browser/components/customizableui/test/browser.ini
@@ -1,10 +1,10 @@
 [DEFAULT]
-skip-if = buildapp == "mulet"
+skip-if = buildapp == "mulet" || e10s
 support-files =
   head.js
   support/test_967000_charEncoding_page.html
   support/feeds_test_page.html
   support/test-feed.xml
 
 [browser_873501_handle_specials.js]
 [browser_876926_customize_mode_wrapping.js]
--- a/browser/components/downloads/test/browser/browser.ini
+++ b/browser/components/downloads/test/browser/browser.ini
@@ -1,9 +1,9 @@
 [DEFAULT]
 support-files = head.js
 
 [browser_basic_functionality.js]
-skip-if = buildapp == "mulet"
+skip-if = buildapp == "mulet" || e10s
 [browser_first_download_panel.js]
 skip-if = os == "linux" # Bug 949434
 [browser_overflow_anchor.js]
 skip-if = os == "linux" # Bug 952422
--- a/browser/components/loop/test/mochitest/browser.ini
+++ b/browser/components/loop/test/mochitest/browser.ini
@@ -1,17 +1,17 @@
 [DEFAULT]
 support-files =
     head.js
     loop_fxa.sjs
     ../../../../base/content/test/general/browser_fxa_oauth.html
 
 [browser_CardDavImporter.js]
 [browser_fxa_login.js]
-skip-if = !debug
+skip-if = !debug || e10s
 [browser_loop_fxa_server.js]
 [browser_LoopContacts.js]
 [browser_mozLoop_appVersionInfo.js]
 [browser_mozLoop_prefs.js]
 [browser_mozLoop_doNotDisturb.js]
 [browser_mozLoop_softStart.js]
 skip-if = buildapp == 'mulet'
 [browser_toolbarbutton.js]
--- a/browser/components/places/tests/browser/browser.ini
+++ b/browser/components/places/tests/browser/browser.ini
@@ -10,25 +10,27 @@ support-files =
   frameLeft.html
   frameRight.html
   sidebarpanels_click_test_page.html
 
 [browser_0_library_left_pane_migration.js]
 [browser_library_left_pane_fixnames.js]
 [browser_425884.js]
 [browser_475045.js]
+skip-if = e10s
 [browser_423515.js]
 [browser_410196_paste_into_tags.js]
 skip-if = e10s # Bug ?????? - clipboard operations don't seem to work in this test?
 [browser_sort_in_library.js]
 [browser_library_open_leak.js]
 [browser_library_panel_leak.js]
 [browser_library_search.js]
 [browser_history_sidebar_search.js]
 [browser_bookmarksProperties.js]
+skip-if = e10s
 
 [browser_forgetthissite_single.js]
 # disabled for very frequent oranges - bug 551540
 skip-if = true
 
 [browser_library_left_pane_commands.js]
 [browser_drag_bookmarks_on_toolbar.js]
 skip-if = e10s # Bug ?????? - test fails - "Number of dragged items should be the same. - Got 0, expected 1"
@@ -41,15 +43,18 @@ skip-if = e10s # Bug ?????? - test fails
 skip-if = true
 
 [browser_library_infoBox.js]
 [browser_markPageAsFollowedLink.js]
 skip-if = e10s # Bug 933103 - mochitest's EventUtils.synthesizeMouse functions not e10s friendly (test does EventUtils.sendMouseEvent...)
 [browser_toolbar_migration.js]
 [browser_library_batch_delete.js]
 [browser_555547.js]
+skip-if = e10s
 [browser_416459_cut.js]
 skip-if = e10s # Bug ?????? - clipboard operations don't seem to work in this test?
 [browser_library_downloads.js]
 [browser_library_left_pane_select_hierarchy.js]
 [browser_435851_copy_query.js]
+skip-if = e10s
 [browser_toolbarbutton_menu_context.js]
+skip-if = e10s
 [browser_library_openFlatContainer.js]
--- a/browser/components/preferences/in-content/advanced.js
+++ b/browser/components/preferences/in-content/advanced.js
@@ -57,29 +57,29 @@ var gAdvancedPane = {
     setEventListener("connectionSettings", "command",
                      gAdvancedPane.showConnections);
     setEventListener("clearCacheButton", "command",
                      gAdvancedPane.clearCache);
     setEventListener("clearOfflineAppCacheButton", "command",
                      gAdvancedPane.clearOfflineAppCache);
     setEventListener("offlineNotifyExceptions", "command",
                      gAdvancedPane.showOfflineExceptions);
-    setEventListener("offlineNotifyExceptions", "command", function (event) {
-      gAdvancedPane.offlineAppSelected(event); })
+    setEventListener("offlineAppsList", "select",
+                     gAdvancedPane.offlineAppSelected);
     let bundlePrefs = document.getElementById("bundlePreferences");
     document.getElementById("offlineAppsList")
             .style.height = bundlePrefs.getString("offlineAppsList.height");
     setEventListener("offlineAppsListRemove", "command",
                      gAdvancedPane.removeOfflineApp);
 #ifdef MOZ_UPDATER
     setEventListener("updateRadioGroup", "command",
                      gAdvancedPane.updateWritePrefs);
-#endif
     setEventListener("showUpdateHistory", "command",
                      gAdvancedPane.showUpdates);
+#endif
     setEventListener("viewCertificatesButton", "command",
                      gAdvancedPane.showCertificates);
     setEventListener("viewSecurityDevicesButton", "command",
                      gAdvancedPane.showSecurityDevices);
   },
 
   /**
    * Stores the identity of the current tab in preferences so that the selected
--- a/browser/components/preferences/tests/browser.ini
+++ b/browser/components/preferences/tests/browser.ini
@@ -1,10 +1,10 @@
 [DEFAULT]
-skip-if = buildapp == "mulet"
+skip-if = buildapp == "mulet" || e10s
 support-files =
   head.js
   privacypane_tests_perwindow.js
 
 [browser_advanced_update.js]
 [browser_bug410900.js]
 [browser_bug705422.js]
 skip-if = e10s # Bug 941459 - pushPrefEnv, popPrefEnv in specialPowersAPI.js not e10s friendly
@@ -12,10 +12,12 @@ skip-if = e10s # Bug 941459 - pushPrefEn
 [browser_connection_bug388287.js]
 [browser_cookies_exceptions.js]
 [browser_healthreport.js]
 skip-if = !healthreport || (os == 'linux' && debug)
 [browser_permissions.js]
 [browser_privacypane_1.js]
 [browser_privacypane_3.js]
 [browser_privacypane_4.js]
+skip-if = e10s # leaks windows
 [browser_privacypane_5.js]
+skip-if = e10s # leaks windows
 [browser_privacypane_8.js]
--- a/browser/components/privatebrowsing/test/browser/browser.ini
+++ b/browser/components/privatebrowsing/test/browser/browser.ini
@@ -1,10 +1,10 @@
 [DEFAULT]
-skip-if = buildapp == "mulet"
+skip-if = buildapp == "mulet" || e10s
 support-files =
   browser_privatebrowsing_concurrent_page.html
   browser_privatebrowsing_cookieacceptdialog.html
   browser_privatebrowsing_geoprompt_page.html
   browser_privatebrowsing_localStorage_before_after_page.html
   browser_privatebrowsing_localStorage_before_after_page2.html
   browser_privatebrowsing_localStorage_page1.html
   browser_privatebrowsing_localStorage_page2.html
@@ -12,29 +12,24 @@ support-files =
   browser_privatebrowsing_protocolhandler_page.html
   browser_privatebrowsing_windowtitle_page.html
   head.js
   popup.html
   title.sjs
 
 [browser_privatebrowsing_DownloadLastDirWithCPS.js]
 [browser_privatebrowsing_aboutHomeButtonAfterWindowClose.js]
-skip-if = e10s # Bug ?????? - test directly manipulates content (win.getComputedStyle(win.gBrowser.contentDocument.getElementById("restorePreviousSession")))
 [browser_privatebrowsing_aboutSessionRestore.js]
-skip-if = e10s # Bug ?????? -  "leaked until shutdown [nsGlobalWindow...]"
 [browser_privatebrowsing_cache.js]
 [browser_privatebrowsing_certexceptionsui.js]
 [browser_privatebrowsing_concurrent.js]
-skip-if = e10s # Bug ?????? - test directly manipulates content (private_tab.docShell.QueryInterface...)
 [browser_privatebrowsing_cookieacceptdialog.js]
 [browser_privatebrowsing_crh.js]
 [browser_privatebrowsing_downloadLastDir.js]
-skip-if = e10s # Bug ?????? MockFilePicker cleanup failing ( nsresult: "0x80040154 (NS_ERROR_FACTORY_NOT_REGISTERED)" location: "JS frame :: resource://specialpowers/MockFilePicker.jsm :: this.MockFilePicker.cleanup :: line 84")
 [browser_privatebrowsing_downloadLastDir_c.js]
-skip-if = e10s # Bug ?????? MockFilePicker cleanup failing ( nsresult: "0x80040154 (NS_ERROR_FACTORY_NOT_REGISTERED)" location: "JS frame :: resource://specialpowers/MockFilePicker.jsm :: this.MockFilePicker.cleanup :: line 84")
 [browser_privatebrowsing_downloadLastDir_toggle.js]
 [browser_privatebrowsing_geoprompt.js]
 [browser_privatebrowsing_lastpbcontextexited.js]
 [browser_privatebrowsing_localStorage.js]
 [browser_privatebrowsing_localStorage_before_after.js]
 [browser_privatebrowsing_noSessionRestoreMenuOption.js]
 [browser_privatebrowsing_nonbrowser.js]
 [browser_privatebrowsing_opendir.js]
@@ -42,13 +37,10 @@ skip-if = e10s # Bug ?????? MockFilePick
 [browser_privatebrowsing_placestitle.js]
 [browser_privatebrowsing_popupblocker.js]
 [browser_privatebrowsing_protocolhandler.js]
 [browser_privatebrowsing_sidebar.js]
 [browser_privatebrowsing_theming.js]
 [browser_privatebrowsing_ui.js]
 [browser_privatebrowsing_urlbarfocus.js]
 [browser_privatebrowsing_windowtitle.js]
-skip-if = e10s # Bug 918634 - swapFrameLoaders
 [browser_privatebrowsing_zoom.js]
-skip-if = e10s # Bug 691614 - e10s support for content zooming
 [browser_privatebrowsing_zoomrestore.js]
-skip-if = e10s # Bug 691614 - e10s support for content zooming
--- a/browser/components/safebrowsing/content/test/browser.ini
+++ b/browser/components/safebrowsing/content/test/browser.ini
@@ -1,10 +1,11 @@
 [DEFAULT]
 support-files = head.js
 
 [browser_bug400731.js]
+skip-if = e10s
 [browser_bug415846.js]
 skip-if = true
 # Disabled because it seems to now touch network resources
 # skip-if = os == "mac"
 # Disabled on Mac because of its bizarre special-and-unique
 # snowflake of a help menu.
--- a/browser/components/translation/test/browser.ini
+++ b/browser/components/translation/test/browser.ini
@@ -1,10 +1,11 @@
 [DEFAULT]
 support-files =
   bing.sjs
   fixtures/bug1022725-fr.html
   fixtures/result-da39a3ee5e.txt
 
 [browser_translation_bing.js]
 [browser_translation_fhr.js]
+skip-if = e10s
 [browser_translation_infobar.js]
 [browser_translation_exceptions.js]
--- a/browser/config/mozconfigs/win64/beta
+++ b/browser/config/mozconfigs/win64/beta
@@ -1,8 +1,9 @@
+. "$topsrcdir/build/mozconfig.win-common"
 . "$topsrcdir/browser/config/mozconfigs/win64/common-win64"
 . "$topsrcdir/browser/config/mozconfigs/win64/common-opt"
 
 mk_add_options MOZ_PGO=1
 
 ac_add_options --enable-official-branding
 . $topsrcdir/build/win64/mozconfig.vs2010
 
--- a/browser/config/mozconfigs/win64/release
+++ b/browser/config/mozconfigs/win64/release
@@ -1,10 +1,11 @@
 # This make file should be identical to the beta mozconfig, apart from the
 # safeguard below
+. "$topsrcdir/build/mozconfig.win-common"
 . "$topsrcdir/browser/config/mozconfigs/win64/common-win64"
 . "$topsrcdir/browser/config/mozconfigs/win64/common-opt"
 
 mk_add_options MOZ_PGO=1
 
 ac_add_options --enable-official-branding
 
 # safeguard against someone forgetting to re-set EARLY_BETA_OR_EARLIER in
--- a/browser/installer/package-manifest.in
+++ b/browser/installer/package-manifest.in
@@ -295,16 +295,17 @@
 @BINPATH@/components/services-crypto-component.xpt
 #ifdef MOZ_CAPTIVEDETECT
 @BINPATH@/components/captivedetect.xpt
 #endif
 @BINPATH@/browser/components/shellservice.xpt
 @BINPATH@/components/shistory.xpt
 @BINPATH@/components/spellchecker.xpt
 @BINPATH@/components/storage.xpt
+@BINPATH@/components/toolkit_filewatcher.xpt
 @BINPATH@/components/toolkit_finalizationwitness.xpt
 @BINPATH@/components/toolkit_formautofill.xpt
 @BINPATH@/components/toolkit_osfile.xpt
 @BINPATH@/components/toolkit_xulstore.xpt
 @BINPATH@/components/toolkitprofile.xpt
 #ifdef MOZ_ENABLE_XREMOTE
 @BINPATH@/components/toolkitremote.xpt
 #endif
--- a/browser/modules/test/browser.ini
+++ b/browser/modules/test/browser.ini
@@ -1,16 +1,17 @@
 [DEFAULT]
 support-files =
   head.js
   image.png
   uitour.*
 
 [browser_BrowserUITelemetry_buckets.js]
 [browser_ContentSearch.js]
+skip-if = e10s
 support-files =
   contentSearch.js
   contentSearchBadImage.xml
   contentSearchSuggestions.sjs
   contentSearchSuggestions.xml
 [browser_NetworkPrioritizer.js]
 skip-if = e10s # Bug 666804 - Support NetworkPrioritizer in e10s
 [browser_SignInToWebsite.js]
rename from build/mozconfig.vs2010-common
rename to build/mozconfig.vs-common
--- a/build/win32/mozconfig.vs2010
+++ b/build/win32/mozconfig.vs2010
@@ -1,13 +1,13 @@
 export INCLUDE=/d/msvs10/vc/include:/d/msvs10/vc/atlmfc/include:/d/sdks/v7.0/include:/d/sdks/v7.0/include/atl:/d/msvs8/VC/PlatformSDK/include:/d/sdks/dx10/include
 export LIBPATH=/d/msvs10/vc/lib:/d/msvs10/vc/atlmfc/lib:/c/WINDOWS/Microsoft.NET/Framework/v2.0.50727
 export LIB=/d/msvs10/vc/lib:/d/msvs10/vc/atlmfc/lib:/d/sdks/v7.0/lib:/d/msvs8/VC/PlatformSDK/lib:/d/msvs8/SDK/v2.0/lib:/d/mozilla-build/atlthunk_compat:/d/sdks/dx10/lib/x86
 export PATH="/d/msvs10/VSTSDB/Deploy:/d/msvs10/Common7/IDE/:/d/msvs10/VC/BIN:/d/msvs10/Common7/Tools:/d/msvs10/VC/VCPackages:${PATH}"
 export WIN32_REDIST_DIR=/d/msvs10/VC/redist/x86/Microsoft.VC100.CRT
 
-. $topsrcdir/build/mozconfig.vs2010-common
+. $topsrcdir/build/mozconfig.vs-common
 
 mk_export_correct_style LIB
 mk_export_correct_style LIBPATH
 mk_export_correct_style PATH
 mk_export_correct_style INCLUDE
 mk_export_correct_style WIN32_REDIST_DIR
--- a/build/win32/mozconfig.vs2010-win64
+++ b/build/win32/mozconfig.vs2010-win64
@@ -20,17 +20,17 @@ export LIBPATH=/c/Program\ Files\ \(x86\
 export LIB=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/Lib/win8/um/x86:${_VSPATH}/vc/lib:${_VSPATH}/vc/atlmfc/lib:/c/tools/sdks/dx10/lib
 
 ## paths: win8 sdk x86 (32-bit) tools, msvc 10 (32-bit) build toolchain, moz tools  ##
 export PATH="/c/Program Files (x86)/Windows Kits/8.0/bin/x86:${_VSPATH}/Common7/IDE:${_VSPATH}/VC/BIN:${_VSPATH}/Common7/Tools:${_VSPATH}/VC/VCPackages:/c/mozilla-build/moztools:${PATH}"
 
 ## WindowsSDKDir ##
 export WINDOWSSDKDIR="/c/Program Files (x86)/Windows Kits/8.0/"
 
-. $topsrcdir/build/mozconfig.vs2010-common
+. $topsrcdir/build/mozconfig.vs-common
 
 mk_export_correct_style LIB
 mk_export_correct_style LIBPATH
 mk_export_correct_style PATH
 mk_export_correct_style INCLUDE
 mk_export_correct_style WIN32_REDIST_DIR
 
 mk_add_options "export MOZ_TOOLS=$MOZ_TOOLS"
copy from build/win32/mozconfig.vs2010-win64
copy to build/win32/mozconfig.vs2013-win64
--- a/build/win32/mozconfig.vs2010-win64
+++ b/build/win32/mozconfig.vs2013-win64
@@ -1,36 +1,28 @@
-
-if [ -d "/c/PROGRA~2/MICROS~2.0" ]; then
-  # /c/Program Files (x86)/Microsoft Visual Studio 10.0
-  _VSPATH="/c/PROGRA~2/MICROS~2.0"
-else
-  _VSPATH="/c/tools/msvs10"
-fi
-
-## SDK redist ##
-export WIN32_REDIST_DIR=${_VSPATH}/VC/redist/x86/Microsoft.VC100.CRT
+_VSPATH="/c/tools/vs2013"
+export WIN32_REDIST_DIR=${_VSPATH}/VC/redist/x86/Microsoft.VC120.CRT
 
 ## moz tools location for 64-bit builders ##
 export MOZ_TOOLS=C:/mozilla-build/moztools
 
-## includes: win8 sdk includes, winrt headers for metro, msvc 10 std library, directx sdk for d3d9 ##
+## includes: win8 sdk includes, winrt headers for metro, msvc std library, directx sdk for d3d9 ##
 export INCLUDE=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/shared:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/um:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt/wrl:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt/wrl/wrappers:${_VSPATH}/vc/include:${_VSPATH}/vc/atlmfc/include:/c/tools/sdks/dx10/include
 
-## libs: win8 sdk x86 (32-bit) libs, msvc 10 (32-bit) std library, msvc 10 atl libs, directx sdk (32-bit) for d3d9  ##
+## libs: win8 sdk x86 (32-bit) libs, msvc (32-bit) std library, msvc atl libs, directx sdk (32-bit) for d3d9  ##
 export LIBPATH=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/Lib/win8/um/x86:${_VSPATH}/vc/lib:${_VSPATH}/vc/atlmfc/lib:/c/tools/sdks/dx10/lib
 export LIB=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/Lib/win8/um/x86:${_VSPATH}/vc/lib:${_VSPATH}/vc/atlmfc/lib:/c/tools/sdks/dx10/lib
 
-## paths: win8 sdk x86 (32-bit) tools, msvc 10 (32-bit) build toolchain, moz tools  ##
-export PATH="/c/Program Files (x86)/Windows Kits/8.0/bin/x86:${_VSPATH}/Common7/IDE:${_VSPATH}/VC/BIN:${_VSPATH}/Common7/Tools:${_VSPATH}/VC/VCPackages:/c/mozilla-build/moztools:${PATH}"
+## paths: win8 sdk x86 (32-bit) tools, msvc (64-bit compiling 32-bit) build toolchain, moz tools  ##
+export PATH="/c/Program Files (x86)/Windows Kits/8.0/bin/x86:${_VSPATH}/Common7/IDE:${_VSPATH}/VC/BIN/amd64_x86:${_VSPATH}/VC/BIN/amd64:${_VSPATH}/Common7/Tools:${_VSPATH}/VC/VCPackages:/c/mozilla-build/moztools:${PATH}"
 
 ## WindowsSDKDir ##
 export WINDOWSSDKDIR="/c/Program Files (x86)/Windows Kits/8.0/"
 
-. $topsrcdir/build/mozconfig.vs2010-common
+. $topsrcdir/build/mozconfig.vs-common
 
 mk_export_correct_style LIB
 mk_export_correct_style LIBPATH
 mk_export_correct_style PATH
 mk_export_correct_style INCLUDE
 mk_export_correct_style WIN32_REDIST_DIR
 
 mk_add_options "export MOZ_TOOLS=$MOZ_TOOLS"
--- a/build/win64/mozconfig.vs2010
+++ b/build/win64/mozconfig.vs2010
@@ -26,15 +26,15 @@ export WINDOWSSDKDIR="/c/Program Files (
 # https://connect.microsoft.com/VisualStudio/feedback/details/686117/
 if [ -f /c/PROGRA~2/MICROS~2.0/VC/BIN/x86_amd64/link.exe ]; then
   # /c/Program Files (x86)/Microsoft Visual Studio 10.0
   export LD=c:/PROGRA~2/MICROS~2.0/VC/BIN/x86_amd64/link.exe
 else
   export LD=c:/tools/msvs10/VC/BIN/x86_amd64/link.exe
 fi
 
-. $topsrcdir/build/mozconfig.vs2010-common
+. $topsrcdir/build/mozconfig.vs-common
 
 mk_export_correct_style LIB
 mk_export_correct_style LIBPATH
 mk_export_correct_style PATH
 mk_export_correct_style INCLUDE
 mk_export_correct_style WIN32_REDIST_DIR
copy from build/win64/mozconfig.vs2010
copy to build/win64/mozconfig.vs2013
--- a/build/win64/mozconfig.vs2010
+++ b/build/win64/mozconfig.vs2013
@@ -1,40 +1,23 @@
-
-if [ -d "/c/PROGRA~2/MICROS~2.0" ]; then
-  # /c/Program Files (x86)/Microsoft Visual Studio 10.0
-  _VSPATH="/c/PROGRA~2/MICROS~2.0"
-else
-  _VSPATH="/c/tools/msvs10"
-fi
-
-## SDK redist ##
-export WIN32_REDIST_DIR=${_VSPATH}/VC/redist/x64/Microsoft.VC100.CRT
+_VSPATH="/c/tools/vs2013"
+export WIN32_REDIST_DIR=${_VSPATH}/VC/redist/x64/Microsoft.VC120.CRT
 
 ## includes: win8 sdk includes, winrt headers for metro, msvc 10 std library, directx sdk for d3d9 ##
 export INCLUDE=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/shared:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/um:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt/wrl:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt/wrl/wrappers:${_VSPATH}/vc/include:${_VSPATH}/vc/atlmfc/include:/c/tools/sdks/dx10/include
 
 ## libs: win8 sdk x64 (64-bit) libs, msvc 10 (64-bit) std library, msvc 10 atl libs, directx sdk (64-bit) for d3d9  ##
 export LIBPATH=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/Lib/win8/um/x64:${_VSPATH}/vc/lib/amd64:${_VSPATH}/vc/atlmfc/lib/amd64:/c/tools/sdks/dx10/lib/x64
 export LIB=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/Lib/win8/um/x64:${_VSPATH}/vc/lib/amd64:${_VSPATH}/vc/atlmfc/lib/amd64:/c/tools/sdks/dx10/lib/x64
 
 ## paths: win8 sdk x64 (64-bit) tools, msvc 10 (64-bit) build toolchain, moz tools  ##
 export PATH="/c/Program Files (x86)/Windows Kits/8.0/bin/x64:${_VSPATH}/Common7/IDE:${_VSPATH}/VC/BIN/amd64:${_VSPATH}/VC/BIN/x86_amd64:${_VSPATH}/VC/BIN:${_VSPATH}/Common7/Tools:${_VSPATH}/VC/VCPackages:${PATH}"
 
 ## WindowsSDKDir ##
 export WINDOWSSDKDIR="/c/Program Files (x86)/Windows Kits/8.0/"
 
-# Use 32bit linker for PGO crash bug.
-# https://connect.microsoft.com/VisualStudio/feedback/details/686117/
-if [ -f /c/PROGRA~2/MICROS~2.0/VC/BIN/x86_amd64/link.exe ]; then
-  # /c/Program Files (x86)/Microsoft Visual Studio 10.0
-  export LD=c:/PROGRA~2/MICROS~2.0/VC/BIN/x86_amd64/link.exe
-else
-  export LD=c:/tools/msvs10/VC/BIN/x86_amd64/link.exe
-fi
-
-. $topsrcdir/build/mozconfig.vs2010-common
+. $topsrcdir/build/mozconfig.vs-common
 
 mk_export_correct_style LIB
 mk_export_correct_style LIBPATH
 mk_export_correct_style PATH
 mk_export_correct_style INCLUDE
 mk_export_correct_style WIN32_REDIST_DIR
--- a/caps/nsNullPrincipalURI.h
+++ b/caps/nsNullPrincipalURI.h
@@ -29,17 +29,17 @@ class nsNullPrincipalURI MOZ_FINAL : pub
 public:
   NS_DECL_THREADSAFE_ISUPPORTS
   NS_DECL_NSIURI
 
   // nsISizeOf
   virtual size_t SizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf) const;
   virtual size_t SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const;
 
-  nsNullPrincipalURI(const nsCString &aSpec);
+  explicit nsNullPrincipalURI(const nsCString &aSpec);
 
 private:
   ~nsNullPrincipalURI() {}
 
   nsCString mScheme;
   nsCString mPath;
 };
 
--- a/caps/nsPrincipal.h
+++ b/caps/nsPrincipal.h
@@ -118,17 +118,17 @@ protected:
    * Returns the app status of the principal based on mAppId and mInMozBrowser.
    */
   uint16_t GetAppStatus();
 };
 
 class nsExpandedPrincipal : public nsIExpandedPrincipal, public nsBasePrincipal
 {
 public:
-  nsExpandedPrincipal(nsTArray< nsCOMPtr<nsIPrincipal> > &aWhiteList);
+  explicit nsExpandedPrincipal(nsTArray< nsCOMPtr<nsIPrincipal> > &aWhiteList);
 
 protected:
   virtual ~nsExpandedPrincipal();
 
 public:
   NS_DECL_ISUPPORTS_INHERITED
   NS_DECL_NSIEXPANDEDPRINCIPAL
   NS_DECL_NSISERIALIZABLE
--- a/chrome/nsChromeRegistryChrome.h
+++ b/chrome/nsChromeRegistryChrome.h
@@ -122,17 +122,17 @@ class nsChromeRegistryChrome : public ns
   };
 
   class OverlayListEntry : public nsURIHashKey
   {
    public:
     typedef nsURIHashKey::KeyType        KeyType;
     typedef nsURIHashKey::KeyTypePointer KeyTypePointer;
 
-    OverlayListEntry(KeyTypePointer aKey) : nsURIHashKey(aKey) { }
+    explicit OverlayListEntry(KeyTypePointer aKey) : nsURIHashKey(aKey) { }
     OverlayListEntry(OverlayListEntry&& toMove) : nsURIHashKey(mozilla::Move(toMove)),
                                                   mArray(mozilla::Move(toMove.mArray)) { }
     ~OverlayListEntry() { }
 
     void AddURI(nsIURI* aURI);
 
     nsCOMArray<nsIURI> mArray;
   };
--- a/config/config.mk
+++ b/config/config.mk
@@ -354,29 +354,35 @@ MY_RULES	:= $(DEPTH)/config/myrules.mk
 #
 CCC = $(CXX)
 
 # Java macros
 JAVA_GEN_DIR  = _javagen
 JAVA_DIST_DIR = $(DEPTH)/$(JAVA_GEN_DIR)
 JAVA_IFACES_PKG_NAME = org/mozilla/interfaces
 
-OS_INCLUDES += $(MOZ_JPEG_CFLAGS) $(MOZ_PNG_CFLAGS) $(MOZ_ZLIB_CFLAGS) $(MOZ_PIXMAN_CFLAGS)
-
-# NSPR_CFLAGS and NSS_CFLAGS must appear ahead of OS_INCLUDES to avoid Linux
-# builds wrongly picking up system NSPR/NSS header files.
 INCLUDES = \
   -I$(srcdir) \
   -I. \
   $(LOCAL_INCLUDES) \
   -I$(DIST)/include \
+  $(NULL)
+
+ifndef IS_GYP_DIR
+# NSPR_CFLAGS and NSS_CFLAGS must appear ahead of the other flags to avoid Linux
+# builds wrongly picking up system NSPR/NSS header files.
+OS_INCLUDES := \
   $(if $(LIBXUL_SDK),-I$(LIBXUL_SDK)/include) \
   $(NSPR_CFLAGS) $(NSS_CFLAGS) \
-  $(OS_INCLUDES) \
+  $(MOZ_JPEG_CFLAGS) \
+  $(MOZ_PNG_CFLAGS) \
+  $(MOZ_ZLIB_CFLAGS) \
+  $(MOZ_PIXMAN_CFLAGS) \
   $(NULL)
+endif
 
 include $(topsrcdir)/config/static-checking-config.mk
 
 CFLAGS		= $(OS_CPPFLAGS) $(OS_CFLAGS)
 CXXFLAGS	= $(OS_CPPFLAGS) $(OS_CXXFLAGS)
 LDFLAGS		= $(OS_LDFLAGS) $(MOZBUILD_LDFLAGS) $(MOZ_FIX_LINK_PATHS)
 
 # Allow each module to override the *default* optimization settings
@@ -478,18 +484,18 @@ HOST_CMMFLAGS += -fobjc-exceptions
 OS_COMPILE_CMFLAGS += -fobjc-exceptions
 OS_COMPILE_CMMFLAGS += -fobjc-exceptions
 ifeq ($(MOZ_WIDGET_TOOLKIT),uikit)
 OS_COMPILE_CMFLAGS += -fobjc-abi-version=2 -fobjc-legacy-dispatch
 OS_COMPILE_CMMFLAGS += -fobjc-abi-version=2 -fobjc-legacy-dispatch
 endif
 endif
 
-COMPILE_CFLAGS	= $(VISIBILITY_FLAGS) $(DEFINES) $(INCLUDES) $(DSO_CFLAGS) $(DSO_PIC_CFLAGS) $(RTL_FLAGS) $(OS_CPPFLAGS) $(OS_COMPILE_CFLAGS) $(CFLAGS) $(MOZBUILD_CFLAGS) $(EXTRA_COMPILE_FLAGS)
-COMPILE_CXXFLAGS = $(if $(DISABLE_STL_WRAPPING),,$(STL_FLAGS)) $(VISIBILITY_FLAGS) $(DEFINES) $(INCLUDES) $(DSO_CFLAGS) $(DSO_PIC_CFLAGS) $(RTL_FLAGS) $(OS_CPPFLAGS) $(OS_COMPILE_CXXFLAGS) $(CXXFLAGS) $(MOZBUILD_CXXFLAGS) $(EXTRA_COMPILE_FLAGS)
+COMPILE_CFLAGS	= $(VISIBILITY_FLAGS) $(DEFINES) $(INCLUDES) $(OS_INCLUDES) $(DSO_CFLAGS) $(DSO_PIC_CFLAGS) $(RTL_FLAGS) $(OS_CPPFLAGS) $(OS_COMPILE_CFLAGS) $(CFLAGS) $(MOZBUILD_CFLAGS) $(EXTRA_COMPILE_FLAGS)
+COMPILE_CXXFLAGS = $(if $(DISABLE_STL_WRAPPING),,$(STL_FLAGS)) $(VISIBILITY_FLAGS) $(DEFINES) $(INCLUDES) $(OS_INCLUDES) $(DSO_CFLAGS) $(DSO_PIC_CFLAGS) $(RTL_FLAGS) $(OS_CPPFLAGS) $(OS_COMPILE_CXXFLAGS) $(CXXFLAGS) $(MOZBUILD_CXXFLAGS) $(EXTRA_COMPILE_FLAGS)
 COMPILE_CMFLAGS = $(OS_COMPILE_CMFLAGS) $(MOZBUILD_CMFLAGS) $(EXTRA_COMPILE_FLAGS)
 COMPILE_CMMFLAGS = $(OS_COMPILE_CMMFLAGS) $(MOZBUILD_CMMFLAGS) $(EXTRA_COMPILE_FLAGS)
 ASFLAGS += $(EXTRA_ASSEMBLER_FLAGS)
 
 ifndef CROSS_COMPILE
 HOST_CFLAGS += $(RTL_FLAGS)
 endif
 
@@ -745,27 +751,10 @@ PLY_INCLUDE = -I$(topsrcdir)/other-licen
 export CL_INCLUDES_PREFIX
 # Make sure that the build system can handle non-ASCII characters
 # in environment variables to prevent it from breking silently on
 # non-English systems.
 export NONASCII
 
 DEFINES += -DNO_NSPR_10_SUPPORT
 
-ifdef IS_GYP_DIR
-LOCAL_INCLUDES += \
-  -I$(topsrcdir)/ipc/chromium/src \
-  -I$(topsrcdir)/ipc/glue \
-  -I$(DEPTH)/ipc/ipdl/_ipdlheaders \
-  $(NULL)
-
-ifeq (WINNT,$(OS_TARGET))
-# These get set via VC project file settings for normal GYP builds.
-DEFINES += -DUNICODE -D_UNICODE
-endif
-
-DISABLE_STL_WRAPPING := 1
-# Skip most Mozilla-specific include locations.
-INCLUDES = -I. $(LOCAL_INCLUDES) -I$(DEPTH)/dist/include
-endif
-
 # Freeze the values specified by moz.build to catch them if they fail.
 $(foreach var,$(_MOZBUILD_EXTERNAL_VARIABLES) $(_DEPRECATED_VARIABLES),$(eval $(var)_FROZEN := '$($(var))'))
--- a/content/base/src/DOMRect.h
+++ b/content/base/src/DOMRect.h
@@ -137,16 +137,19 @@ public:
   }
   void SetHeight(double aHeight)
   {
     mHeight = aHeight;
   }
 
 protected:
   double mX, mY, mWidth, mHeight;
+
+private:
+  ~DOMRect() {};
 };
 
 class DOMRectList MOZ_FINAL : public nsIDOMClientRectList,
                               public nsWrapperCache
 {
   ~DOMRectList() {}
 
 public:
@@ -205,17 +208,11 @@ public:
 
 protected:
   nsTArray<nsRefPtr<DOMRect> > mArray;
   nsCOMPtr<nsISupports> mParent;
 };
 
 }
 
-template<>
-struct HasDangerousPublicDestructor<dom::DOMRect>
-{
-  static const bool value = true;
-};
-
 }
 
 #endif /*MOZILLA_DOMRECT_H_*/
--- a/content/base/src/nsDocument.cpp
+++ b/content/base/src/nsDocument.cpp
@@ -1596,16 +1596,22 @@ nsDocument::~nsDocument()
 #ifdef PR_LOGGING
   if (gDocumentLeakPRLog)
     PR_LOG(gDocumentLeakPRLog, PR_LOG_DEBUG,
            ("DOCUMENT %p destroyed", this));
 #endif
 
   NS_ASSERTION(!mIsShowing, "Destroying a currently-showing document");
 
+  // Note: This assert is only non-fatal because mochitest-bc triggers
+  // it... as well as the preceding assert about !mIsShowing.
+  NS_ASSERTION(!mObservingAppThemeChanged,
+               "Document leaked to shutdown, then the observer service dropped "
+               "its ref to us so we were able to go away.");
+
   if (IsTopLevelContentDocument()) {
     //don't report for about: pages
     nsCOMPtr<nsIPrincipal> principal = GetPrincipal();
     nsCOMPtr<nsIURI> uri;
     principal->GetURI(getter_AddRefs(uri));
     bool isAboutScheme = true;
     if (uri) {
       uri->SchemeIs("about", &isAboutScheme);
@@ -8868,17 +8874,20 @@ nsDocument::OnPageShow(bool aPersisted,
   // Dispatch observer notification to notify observers page is shown.
   nsCOMPtr<nsIObserverService> os = mozilla::services::GetObserverService();
   nsIPrincipal *principal = GetPrincipal();
   os->NotifyObservers(static_cast<nsIDocument*>(this),
                       nsContentUtils::IsSystemPrincipal(principal) ?
                         "chrome-page-shown" :
                         "content-page-shown",
                       nullptr);
-  os->AddObserver(this, "app-theme-changed", /* ownsWeak */ false);
+  if (!mObservingAppThemeChanged) {
+    os->AddObserver(this, "app-theme-changed", /* ownsWeak */ false);
+    mObservingAppThemeChanged = true;
+  }
 
   DispatchPageTransition(target, NS_LITERAL_STRING("pageshow"), aPersisted);
 }
 
 static bool
 NotifyPageHide(nsIDocument* aDocument, void* aData)
 {
   const bool* aPersistedPtr = static_cast<const bool*>(aData);
@@ -8944,16 +8953,17 @@ nsDocument::OnPageHide(bool aPersisted,
     nsIPrincipal* principal = GetPrincipal();
     os->NotifyObservers(static_cast<nsIDocument*>(this),
                         nsContentUtils::IsSystemPrincipal(principal) ?
                           "chrome-page-hidden" :
                           "content-page-hidden",
                         nullptr);
 
     os->RemoveObserver(this, "app-theme-changed");
+    mObservingAppThemeChanged = false;
   }
 
   DispatchPageTransition(target, NS_LITERAL_STRING("pagehide"), aPersisted);
 
   mVisible = false;
 
   UpdateVisibilityState();
 
--- a/content/base/src/nsDocument.h
+++ b/content/base/src/nsDocument.h
@@ -1593,16 +1593,22 @@ public:
   friend class nsPointerLockPermissionRequest;
   friend class nsCallRequestFullScreen;
   // When set, trying to lock the pointer doesn't require permission from the
   // user.
   bool mAllowRelocking:1;
 
   bool mAsyncFullscreenPending:1;
 
+  // Whether we're observing the "app-theme-changed" observer service
+  // notification.  We need to keep track of this because we might get multiple
+  // OnPageShow notifications in a row without an OnPageHide in between, if
+  // we're getting document.open()/close() called on us.
+  bool mObservingAppThemeChanged:1;
+
   // Keeps track of whether we have a pending
   // 'style-sheet-applicable-state-changed' notification.
   bool mSSApplicableStateNotificationPending:1;
 
   uint32_t mCancelledPointerLockRequests;
 
   uint8_t mXMLDeclarationBits;
 
--- a/content/base/src/nsFormData.h
+++ b/content/base/src/nsFormData.h
@@ -21,20 +21,20 @@ namespace mozilla {
 class ErrorResult;
 
 namespace dom {
 class HTMLFormElement;
 class GlobalObject;
 } // namespace dom
 } // namespace mozilla
 
-class nsFormData : public nsIDOMFormData,
-                   public nsIXHRSendable,
-                   public nsFormSubmission,
-                   public nsWrapperCache
+class nsFormData MOZ_FINAL : public nsIDOMFormData,
+                             public nsIXHRSendable,
+                             public nsFormSubmission,
+                             public nsWrapperCache
 {
   ~nsFormData() {}
 
 public:
   explicit nsFormData(nsISupports* aOwner = nullptr);
 
   NS_DECL_CYCLE_COLLECTING_ISUPPORTS
   NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS_AMBIGUOUS(nsFormData,
--- a/content/base/src/nsObjectLoadingContent.cpp
+++ b/content/base/src/nsObjectLoadingContent.cpp
@@ -1030,16 +1030,26 @@ nsObjectLoadingContent::BuildParametersA
   bool isJava = nsPluginHost::IsJavaMIMEType(mContentType.get());
 
   nsCString codebase;
   if (isJava) {
       mBaseURI->GetSpec(codebase);
   }
 
   nsAdoptingCString wmodeOverride = Preferences::GetCString("plugins.force.wmode");
+#if defined(XP_WIN) || defined(XP_LINUX)
+  // Bug 923745 (/Bug 1061995) - Until we support windowed mode plugins in
+  // content processes, force flash to use a windowless rendering mode. This
+  // hack should go away when bug 923746 lands. (OS X plugins always use some
+  // native widgets, so unfortunately this does not help there)
+  if (wmodeOverride.IsEmpty() &&
+      XRE_GetProcessType() == GeckoProcessType_Content) {
+    wmodeOverride.AssignLiteral("transparent");
+  }
+#endif
 
   for (uint32_t i = 0; i < mCachedAttributes.Length(); i++) {
     if (!wmodeOverride.IsEmpty() && mCachedAttributes[i].mName.EqualsIgnoreCase("wmode")) {
       CopyASCIItoUTF16(wmodeOverride, mCachedAttributes[i].mValue);
       wmodeOverride.Truncate();
     } else if (!codebase.IsEmpty() && mCachedAttributes[i].mName.EqualsIgnoreCase("codebase")) {
       CopyASCIItoUTF16(codebase, mCachedAttributes[i].mValue);
       codebase.Truncate();
--- a/content/base/src/nsScriptLoader.h
+++ b/content/base/src/nsScriptLoader.h
@@ -30,17 +30,17 @@ namespace dom {
 class AutoJSAPI;
 }
 }
 
 //////////////////////////////////////////////////////////////
 // Script loader implementation
 //////////////////////////////////////////////////////////////
 
-class nsScriptLoader : public nsIStreamLoaderObserver
+class nsScriptLoader MOZ_FINAL : public nsIStreamLoaderObserver
 {
   class MOZ_STACK_CLASS AutoCurrentScriptUpdater
   {
   public:
     AutoCurrentScriptUpdater(nsScriptLoader* aScriptLoader,
                              nsIScriptElement* aCurrentScript)
       : mOldScript(aScriptLoader->mCurrentScript)
       , mScriptLoader(aScriptLoader)
--- a/content/html/content/src/HTMLPropertiesCollection.h
+++ b/content/html/content/src/HTMLPropertiesCollection.h
@@ -43,19 +43,19 @@ public:
 protected:
   virtual ~PropertyStringList();
 
   virtual void EnsureFresh() MOZ_OVERRIDE;
 
   nsRefPtr<HTMLPropertiesCollection> mCollection;
 };
 
-class HTMLPropertiesCollection : public nsIHTMLCollection,
-                                 public nsStubMutationObserver,
-                                 public nsWrapperCache
+class HTMLPropertiesCollection MOZ_FINAL : public nsIHTMLCollection,
+                                           public nsStubMutationObserver,
+                                           public nsWrapperCache
 {
   friend class PropertyNodeList;
   friend class PropertyStringList;
 public:
   explicit HTMLPropertiesCollection(nsGenericHTMLElement* aRoot);
 
   // nsWrapperCache
   using nsWrapperCache::GetWrapperPreserveColor;
--- a/content/media/AbstractMediaDecoder.h
+++ b/content/media/AbstractMediaDecoder.h
@@ -60,21 +60,16 @@ public:
   // Called by the decode thread to keep track of the number of bytes read
   // from the resource.
   virtual void NotifyBytesConsumed(int64_t aBytes, int64_t aOffset) = 0;
 
   // Increments the parsed and decoded frame counters by the passed in counts.
   // Can be called on any thread.
   virtual void NotifyDecodedFrames(uint32_t aParsed, uint32_t aDecoded) = 0;
 
-  // Returns the end time of the last sample in the media. Note that a media
-  // can have a non-zero start time, so the end time may not necessarily be
-  // the same as the duration (i.e. duration is (end_time - start_time)).
-  virtual int64_t GetEndMediaTime() const = 0;
-
   // Return the duration of the media in microseconds.
   virtual int64_t GetMediaDuration() = 0;
 
   // Set the duration of the media in microseconds.
   virtual void SetMediaDuration(int64_t aDuration) = 0;
 
   // Sets the duration of the media in microseconds. The MediaDecoder
   // fires a durationchange event to its owner (e.g., an HTML audio
--- a/content/media/GraphDriver.cpp
+++ b/content/media/GraphDriver.cpp
@@ -12,16 +12,30 @@
 
 #ifdef PR_LOGGING
 extern PRLogModuleInfo* gMediaStreamGraphLog;
 #define STREAM_LOG(type, msg) PR_LOG(gMediaStreamGraphLog, type, msg)
 #else
 #define STREAM_LOG(type, msg)
 #endif
 
+// We don't use NSPR log here because we want this interleaved with adb logcat
+// on Android/B2G
+// #define ENABLE_LIFECYCLE_LOG
+#ifdef ENABLE_LIFECYCLE_LOG
+#ifdef ANDROID
+#include "android/log.h"
+#define LIFECYCLE_LOG(args...)  __android_log_print(ANDROID_LOG_INFO, "Gecko - MSG" , ## __VA_ARGS__); printf(__VA_ARGS__);printf("\n");
+#else
+#define LIFECYCLE_LOG(...) printf(__VA_ARGS__);printf("\n");
+#endif
+#else
+#define LIFECYCLE_LOG(...)
+#endif
+
 namespace mozilla {
 
 struct AutoProfilerUnregisterThread
 {
   // The empty ctor is used to silence a pre-4.8.0 GCC unused variable warning.
   AutoProfilerUnregisterThread()
   {
   }
@@ -63,20 +77,22 @@ void GraphDriver::SetGraphTime(GraphDriv
   STREAM_LOG(PR_LOG_DEBUG, ("Setting previous driver: %p (%s)", aPreviousDriver, aPreviousDriver->AsAudioCallbackDriver() ? "AudioCallbackDriver" : "SystemClockDriver"));
   MOZ_ASSERT(!mPreviousDriver);
   mPreviousDriver = aPreviousDriver;
 }
 
 void GraphDriver::SwitchAtNextIteration(GraphDriver* aNextDriver)
 {
 
-  STREAM_LOG(PR_LOG_DEBUG, ("Switching to new driver: %p (%s)", aNextDriver, aNextDriver->AsAudioCallbackDriver() ? "AudioCallbackDriver" : "SystemClockDriver"));
+  LIFECYCLE_LOG("Switching to new driver: %p (%s)",
+      aNextDriver, aNextDriver->AsAudioCallbackDriver() ?
+      "AudioCallbackDriver" : "SystemClockDriver");
   // Sometimes we switch twice to a new driver per iteration, this is probably a
   // bug.
-  MOZ_ASSERT(!mNextDriver || !mNextDriver->AsAudioCallbackDriver());
+  MOZ_ASSERT(!mNextDriver || mNextDriver->AsAudioCallbackDriver());
   mNextDriver = aNextDriver;
 }
 
 void GraphDriver::EnsureImmediateWakeUpLocked()
 {
   mGraphImpl->GetMonitor().AssertCurrentThreadOwns();
   mWaitState = WAITSTATE_WAKING_UP;
   mGraphImpl->GetMonitor().Notify();
@@ -110,65 +126,85 @@ void GraphDriver::EnsureNextIterationLoc
   }
 
   if (mNeedAnotherIteration) {
     return;
   }
   mNeedAnotherIteration = true;
 }
 
+class MediaStreamGraphShutdownThreadRunnable : public nsRunnable {
+public:
+  explicit MediaStreamGraphShutdownThreadRunnable(GraphDriver* aDriver)
+    : mDriver(aDriver)
+  {
+  }
+  NS_IMETHOD Run()
+  {
+    MOZ_ASSERT(NS_IsMainThread());
+
+    LIFECYCLE_LOG("MediaStreamGraphShutdownThreadRunnable for graph %p",
+        mDriver->GraphImpl());
+    // We can't release an audio driver on the main thread, because it can be
+    // blocking.
+    if (mDriver->AsAudioCallbackDriver()) {
+      LIFECYCLE_LOG("Releasing audio driver off main thread.");
+      nsRefPtr<AsyncCubebTask> releaseEvent =
+        new AsyncCubebTask(mDriver->AsAudioCallbackDriver(),
+                           AsyncCubebTask::SHUTDOWN);
+      mDriver = nullptr;
+      releaseEvent->Dispatch();
+    } else {
+      LIFECYCLE_LOG("Dropping driver reference for SystemClockDriver.");
+      mDriver = nullptr;
+    }
+    return NS_OK;
+  }
+private:
+  nsRefPtr<GraphDriver> mDriver;
+};
+
+void GraphDriver::Shutdown()
+{
+  if (AsAudioCallbackDriver()) {
+    LIFECYCLE_LOG("Releasing audio driver off main thread (GraphDriver::Shutdown).\n");
+    nsRefPtr<AsyncCubebTask> releaseEvent =
+      new AsyncCubebTask(AsAudioCallbackDriver(), AsyncCubebTask::SHUTDOWN);
+    releaseEvent->Dispatch();
+  }
+}
+
 ThreadedDriver::ThreadedDriver(MediaStreamGraphImpl* aGraphImpl)
   : GraphDriver(aGraphImpl)
 { }
 
 ThreadedDriver::~ThreadedDriver()
 {
   if (mThread) {
     mThread->Shutdown();
   }
 }
-
-class MediaStreamGraphShutdownThreadRunnable : public nsRunnable {
-public:
-  explicit MediaStreamGraphShutdownThreadRunnable(GraphDriver* aDriver)
-    : mDriver(aDriver)
-  {
-  }
-  NS_IMETHOD Run()
-  {
-    MOZ_ASSERT(NS_IsMainThread());
-    // We can't release an audio driver on the main thread, because it can be
-    // blocking.
-    if (mDriver->AsAudioCallbackDriver()) {
-      STREAM_LOG(PR_LOG_DEBUG, ("Releasing audio driver off main thread.\n"));
-      nsRefPtr<AsyncCubebTask> releaseEvent =
-        new AsyncCubebTask(mDriver->AsAudioCallbackDriver(), AsyncCubebTask::SHUTDOWN);
-      mDriver = nullptr;
-      releaseEvent->Dispatch();
-    } else {
-      mDriver = nullptr;
-    }
-    return NS_OK;
-  }
-private:
-  nsRefPtr<GraphDriver> mDriver;
-};
-
 class MediaStreamGraphInitThreadRunnable : public nsRunnable {
 public:
   explicit MediaStreamGraphInitThreadRunnable(ThreadedDriver* aDriver)
     : mDriver(aDriver)
   {
   }
   NS_IMETHOD Run()
   {
     char aLocal;
     STREAM_LOG(PR_LOG_DEBUG, ("Starting system thread"));
     profiler_register_thread("MediaStreamGraph", &aLocal);
+    LIFECYCLE_LOG("Starting a new system driver for graph %p\n",
+                  mDriver->mGraphImpl);
     if (mDriver->mPreviousDriver) {
+      LIFECYCLE_LOG("%p releasing an AudioCallbackDriver(%p), for graph %p\n",
+                    mDriver,
+                    mDriver->mPreviousDriver.get(),
+                    mDriver->GraphImpl());
       MOZ_ASSERT(!mDriver->AsAudioCallbackDriver());
       // Stop and release the previous driver off-main-thread.
       nsRefPtr<AsyncCubebTask> releaseEvent =
         new AsyncCubebTask(mDriver->mPreviousDriver->AsAudioCallbackDriver(), AsyncCubebTask::SHUTDOWN);
       mDriver->mPreviousDriver = nullptr;
       releaseEvent->Dispatch();
     } else {
       MonitorAutoLock mon(mDriver->mGraphImpl->GetMonitor());
@@ -180,16 +216,17 @@ public:
   }
 private:
   ThreadedDriver* mDriver;
 };
 
 void
 ThreadedDriver::Start()
 {
+  LIFECYCLE_LOG("Starting thread for a SystemClockDriver  %p\n", mGraphImpl);
   nsCOMPtr<nsIRunnable> event = new MediaStreamGraphInitThreadRunnable(this);
   NS_NewNamedThread("MediaStreamGrph", getter_AddRefs(mThread), event);
 }
 
 void
 ThreadedDriver::Resume()
 {
   Start();
@@ -408,16 +445,27 @@ OfflineClockDriver::WaitForNextIteration
 }
 
 void
 OfflineClockDriver::WakeUp()
 {
   MOZ_ASSERT(false, "An offline graph should not have to wake up.");
 }
 
+AsyncCubebTask::AsyncCubebTask(AudioCallbackDriver* aDriver, AsyncCubebOperation aOperation)
+  : mDriver(aDriver),
+    mOperation(aOperation),
+    mShutdownGrip(aDriver->GraphImpl())
+{
+  MOZ_ASSERT(mDriver->mAudioStream || aOperation == INIT, "No audio stream !");
+}
+
+AsyncCubebTask::~AsyncCubebTask()
+{
+}
 
 NS_IMETHODIMP
 AsyncCubebTask::Run()
 {
   MOZ_ASSERT(mThread);
   if (NS_IsMainThread()) {
     mThread->Shutdown(); // can't shutdown from the thread itself, darn
     // don't null out mThread!
@@ -427,24 +475,28 @@ AsyncCubebTask::Run()
     // assumes the caller does.
     return NS_OK;
   }
 
   MOZ_ASSERT(mDriver);
 
   switch(mOperation) {
     case AsyncCubebOperation::INIT:
+      LIFECYCLE_LOG("AsyncCubebOperation::INIT\n");
       mDriver->Init();
       break;
     case AsyncCubebOperation::SHUTDOWN:
+      LIFECYCLE_LOG("AsyncCubebOperation::SHUTDOWN\n");
       mDriver->Stop();
       mDriver = nullptr;
+      mShutdownGrip = nullptr;
       break;
     case AsyncCubebOperation::SLEEP: {
       {
+        LIFECYCLE_LOG("AsyncCubebOperation::SLEEP\n");
         MonitorAutoLock mon(mDriver->mGraphImpl->GetMonitor());
         // We might just have been awoken
         if (mDriver->mNeedAnotherIteration) {
           mDriver->mPauseRequested = false;
           mDriver->mWaitState = AudioCallbackDriver::WAITSTATE_RUNNING;
           break;
         }
         mDriver->Stop();
@@ -792,17 +844,17 @@ AudioCallbackDriver::DataCallback(AudioD
     mGraphImpl->SetCurrentDriver(mNextDriver);
     mNextDriver->Start();
     // Returning less than aFrames starts the draining and eventually stops the
     // audio thread. This function will never get called again.
     return aFrames - 1;
   }
 
   if (!stillProcessing) {
-    STREAM_LOG(PR_LOG_DEBUG, ("Stopping audio thread for MediaStreamGraph %p", this));
+    LIFECYCLE_LOG("Stopping audio thread for MediaStreamGraph %p", this);
     return aFrames - 1;
   }
   return aFrames;
 }
 
 void
 AudioCallbackDriver::StateCallback(cubeb_state aState)
 {
--- a/content/media/GraphDriver.h
+++ b/content/media/GraphDriver.h
@@ -91,16 +91,17 @@ public:
   /* Start the graph, init the driver, start the thread. */
   virtual void Start() = 0;
   /* Stop the graph, shutting down the thread. */
   virtual void Stop() = 0;
   /* Resume after a stop */
   virtual void Resume() = 0;
   /* Revive this driver, as more messages just arrived. */
   virtual void Revive() = 0;
+  void Shutdown();
   /* Rate at which the GraphDriver runs, in ms. This can either be user
    * controlled (because we are using a {System,Offline}ClockDriver, and decide
    * how often we want to wakeup/how much we want to process per iteration), or
    * it can be indirectly set by the latency of the audio backend, and the
    * number of buffers of this audio backend: say we have four buffers, and 40ms
    * latency, we will get a callback approximately every 10ms. */
   virtual uint32_t IterationDuration() = 0;
 
@@ -182,16 +183,20 @@ public:
    */
   void EnsureNextIteration();
 
   /**
    * Same thing, but not locked.
    */
   void EnsureNextIterationLocked();
 
+  MediaStreamGraphImpl* GraphImpl() {
+    return mGraphImpl;
+  }
+
 protected:
   // Time of the start of this graph iteration.
   GraphTime mIterationStart;
   // Time of the end of this graph iteration.
   GraphTime mIterationEnd;
   // Time, in the future, for which blocking has been computed.
   GraphTime mStateComputedTime;
   GraphTime mNextStateComputedTime;
@@ -455,39 +460,35 @@ class AsyncCubebTask : public nsRunnable
 public:
   enum AsyncCubebOperation {
     INIT,
     SHUTDOWN,
     SLEEP
   };
 
 
-  AsyncCubebTask(AudioCallbackDriver* aDriver, AsyncCubebOperation aOperation)
-    : mDriver(aDriver),
-      mOperation(aOperation)
-  {
-    MOZ_ASSERT(mDriver->mAudioStream || aOperation == INIT, "No audio stream !");
-  }
+  AsyncCubebTask(AudioCallbackDriver* aDriver, AsyncCubebOperation aOperation);
 
   nsresult Dispatch()
   {
     // Can't add 'this' as the event to run, since mThread may not be set yet
     nsresult rv = NS_NewNamedThread("CubebOperation", getter_AddRefs(mThread));
     if (NS_SUCCEEDED(rv)) {
       // Note: event must not null out mThread!
       rv = mThread->Dispatch(this, NS_DISPATCH_NORMAL);
     }
     return rv;
   }
 
 protected:
-  virtual ~AsyncCubebTask() {};
+  virtual ~AsyncCubebTask();
 
 private:
   NS_IMETHOD Run() MOZ_OVERRIDE MOZ_FINAL;
   nsCOMPtr<nsIThread> mThread;
   nsRefPtr<AudioCallbackDriver> mDriver;
   AsyncCubebOperation mOperation;
+  nsRefPtr<MediaStreamGraphImpl> mShutdownGrip;
 };
 
 }
 
 #endif // GRAPHDRIVER_H_
--- a/content/media/MediaDecoder.cpp
+++ b/content/media/MediaDecoder.cpp
@@ -125,57 +125,52 @@ NS_IMPL_ISUPPORTS(MediaMemoryTracker, ns
 
 NS_IMPL_ISUPPORTS(MediaDecoder, nsIObserver)
 
 void MediaDecoder::SetDormantIfNecessary(bool aDormant)
 {
   MOZ_ASSERT(NS_IsMainThread());
   ReentrantMonitorAutoEnter mon(GetReentrantMonitor());
 
-  if (!mDecoderStateMachine || !mDecoderStateMachine->IsDormantNeeded() || (mPlayState == PLAY_STATE_SHUTDOWN)) {
-    return;
-  }
-
-  if (mIsDormant == aDormant) {
-    // no change to dormant state
+  if (!mDecoderStateMachine ||
+      !mDecoderStateMachine->IsDormantNeeded() ||
+      mPlayState == PLAY_STATE_SHUTDOWN ||
+      mIsDormant == aDormant) {
     return;
   }
 
   if(aDormant) {
     // enter dormant state
     StopProgress();
     DestroyDecodedStream();
     mDecoderStateMachine->SetDormant(true);
 
     int64_t timeUsecs = 0;
     SecondsToUsecs(mCurrentTime, timeUsecs);
     mRequestedSeekTarget = SeekTarget(timeUsecs, SeekTarget::Accurate);
 
-    if (mPlayState == PLAY_STATE_PLAYING){
-      mNextState = PLAY_STATE_PLAYING;
-    } else {
-      mNextState = PLAY_STATE_PAUSED;
-    }
     mNextState = mPlayState;
     mIsDormant = true;
     mIsExitingDormant = false;
     ChangeState(PLAY_STATE_LOADING);
-  } else if ((aDormant != true) && (mPlayState == PLAY_STATE_LOADING)) {
+  } else if (!aDormant && mPlayState == PLAY_STATE_LOADING) {
     // exit dormant state
     // trigger to state machine.
     mDecoderStateMachine->SetDormant(false);
     mIsExitingDormant = true;
   }
 }
 
 void MediaDecoder::Pause()
 {
   MOZ_ASSERT(NS_IsMainThread());
   ReentrantMonitorAutoEnter mon(GetReentrantMonitor());
-  if ((mPlayState == PLAY_STATE_LOADING && mIsDormant)  || mPlayState == PLAY_STATE_SEEKING || mPlayState == PLAY_STATE_ENDED) {
+  if ((mPlayState == PLAY_STATE_LOADING && mIsDormant) ||
+      mPlayState == PLAY_STATE_SEEKING ||
+      mPlayState == PLAY_STATE_ENDED) {
     mNextState = PLAY_STATE_PAUSED;
     return;
   }
 
   ChangeState(PLAY_STATE_PAUSED);
 }
 
 void MediaDecoder::SetVolume(double aVolume)
@@ -864,18 +859,21 @@ bool MediaDecoder::IsEnded() const
   MOZ_ASSERT(NS_IsMainThread());
   return mPlayState == PLAY_STATE_ENDED || mPlayState == PLAY_STATE_SHUTDOWN;
 }
 
 void MediaDecoder::PlaybackEnded()
 {
   MOZ_ASSERT(NS_IsMainThread());
 
-  if (mShuttingDown || mPlayState == MediaDecoder::PLAY_STATE_SEEKING)
+  if (mShuttingDown ||
+      mPlayState == PLAY_STATE_SEEKING ||
+      (mPlayState == PLAY_STATE_LOADING && mIsDormant)) {
     return;
+  }
 
   {
     ReentrantMonitorAutoEnter mon(GetReentrantMonitor());
 
     for (int32_t i = mOutputStreams.Length() - 1; i >= 0; --i) {
       OutputStreamData& os = mOutputStreams[i];
       if (os.mStream->IsDestroyed()) {
         // Probably the DOM MediaStream was GCed. Clean up.
@@ -1549,21 +1547,16 @@ MediaDecoder::NotifyWaitingForResourcesS
   }
 }
 
 bool MediaDecoder::IsShutdown() const {
   NS_ENSURE_TRUE(GetStateMachine(), true);
   return GetStateMachine()->IsShutdown();
 }
 
-int64_t MediaDecoder::GetEndMediaTime() const {
-  NS_ENSURE_TRUE(GetStateMachine(), -1);
-  return GetStateMachine()->GetEndMediaTime();
-}
-
 // Drop reference to state machine.  Only called during shutdown dance.
 void MediaDecoder::BreakCycles() {
   mDecoderStateMachine = nullptr;
 }
 
 MediaDecoderOwner* MediaDecoder::GetMediaOwner() const
 {
   return mOwner;
--- a/content/media/MediaDecoder.h
+++ b/content/media/MediaDecoder.h
@@ -576,18 +576,16 @@ public:
   // changed. Called on main thread only.
   virtual void NotifyPrincipalChanged();
 
   // Called by the MediaResource to keep track of the number of bytes read
   // from the resource. Called on the main by an event runner dispatched
   // by the MediaResource read functions.
   void NotifyBytesConsumed(int64_t aBytes, int64_t aOffset) MOZ_FINAL MOZ_OVERRIDE;
 
-  int64_t GetEndMediaTime() const MOZ_FINAL MOZ_OVERRIDE;
-
   // Return true if we are currently seeking in the media resource.
   // Call on the main thread only.
   virtual bool IsSeeking() const;
 
   // Return true if the decoder has reached the end of playback.
   // Call on the main thread only.
   virtual bool IsEnded() const;
 
--- a/content/media/MediaDecoderStateMachine.cpp
+++ b/content/media/MediaDecoderStateMachine.cpp
@@ -1445,16 +1445,17 @@ void MediaDecoderStateMachine::Play()
   // Once we start playing, we don't want to minimize our prerolling, as we
   // assume the user is likely to want to keep playing in future.
   mMinimizePreroll = false;
   ScheduleStateMachine();
 }
 
 void MediaDecoderStateMachine::ResetPlayback()
 {
+  AssertCurrentThreadInMonitor();
   MOZ_ASSERT(mState == DECODER_STATE_SEEKING ||
              mState == DECODER_STATE_SHUTDOWN ||
              mState == DECODER_STATE_DORMANT);
   mVideoFrameEndTime = -1;
   mAudioStartTime = -1;
   mAudioEndTime = -1;
   mAudioCompleted = false;
   AudioQueue().Reset();
@@ -2480,17 +2481,17 @@ nsresult MediaDecoderStateMachine::RunSt
   return NS_OK;
 }
 
 void
 MediaDecoderStateMachine::FlushDecoding()
 {
   NS_ASSERTION(OnStateMachineThread() || OnDecodeThread(),
                "Should be on state machine or decode thread.");
-  mDecoder->GetReentrantMonitor().AssertNotCurrentThreadIn();
+  AssertCurrentThreadInMonitor();
 
   {
     // Put a task in the decode queue to abort any decoding operations.
     // The reader is not supposed to put any tasks to deliver samples into
     // the queue after this runs (unless we request another sample from it).
     RefPtr<nsIRunnable> task;
     task = NS_NewRunnableMethod(mReader, &MediaDecoderReader::ResetDecode);
 
--- a/content/media/MediaDecoderStateMachine.h
+++ b/content/media/MediaDecoderStateMachine.h
@@ -270,21 +270,16 @@ public:
     if (mReader) {
       return mReader->SizeOfAudioQueueInBytes();
     }
     return 0;
   }
 
   void NotifyDataArrived(const char* aBuffer, uint32_t aLength, int64_t aOffset);
 
-  int64_t GetEndMediaTime() const {
-    AssertCurrentThreadInMonitor();
-    return mEndTime;
-  }
-
   // Returns the shared state machine thread.
   nsIEventTarget* GetStateMachineThread() const;
 
   // Calls ScheduleStateMachine() after taking the decoder lock. Also
   // notifies the decoder thread in case it's waiting on the decoder lock.
   void ScheduleStateMachineWithLockAndWakeDecoder();
 
   // Schedules the shared state machine thread to run the state machine
--- a/content/media/MediaResource.cpp
+++ b/content/media/MediaResource.cpp
@@ -931,16 +931,17 @@ ChannelMediaResource::RecreateChannel()
   NS_ENSURE_TRUE(loadGroup, NS_ERROR_NULL_POINTER);
 
   nsresult rv = NS_NewChannel(getter_AddRefs(mChannel),
                               mURI,
                               nullptr,
                               loadGroup,
                               nullptr,
                               loadFlags);
+  NS_ENSURE_SUCCESS(rv, rv);
 
   // We have cached the Content-Type, which should not change. Give a hint to
   // the channel to avoid a sniffing failure, which would be expected because we
   // are probably seeking in the middle of the bitstream, and sniffing relies
   // on the presence of a magic number at the beginning of the stream.
   NS_ASSERTION(!GetContentType().IsEmpty(),
       "When recreating a channel, we should know the Content-Type.");
   mChannel->SetContentType(GetContentType());
@@ -1029,18 +1030,17 @@ ChannelMediaResource::CacheClientSeek(in
     if (mChannel) {
       mIgnoreClose = true;
       CloseChannel();
     }
     return NS_OK;
   }
 
   nsresult rv = RecreateChannel();
-  if (NS_FAILED(rv))
-    return rv;
+  NS_ENSURE_SUCCESS(rv, rv);
 
   return OpenChannel(nullptr);
 }
 
 void
 ChannelMediaResource::FlushCache()
 {
   NS_ASSERTION(NS_IsMainThread(), "Should be on main thread.");
--- a/content/media/MediaStreamGraph.cpp
+++ b/content/media/MediaStreamGraph.cpp
@@ -40,26 +40,42 @@ namespace mozilla {
 
 #ifdef PR_LOGGING
 PRLogModuleInfo* gMediaStreamGraphLog;
 #define STREAM_LOG(type, msg) PR_LOG(gMediaStreamGraphLog, type, msg)
 #else
 #define STREAM_LOG(type, msg)
 #endif
 
+// #define ENABLE_LIFECYCLE_LOG
+
+// We don't use NSPR log here because we want this interleaved with adb logcat
+// on Android/B2G
+#ifdef ENABLE_LIFECYCLE_LOG
+#  ifdef ANDROID
+#    include "android/log.h"
+#    define LIFECYCLE_LOG(...)  __android_log_print(ANDROID_LOG_INFO, "Gecko - MSG", ## __VA_ARGS__); printf(__VA_ARGS__);printf("\n");
+#  else
+#    define LIFECYCLE_LOG(...) printf(__VA_ARGS__);printf("\n");
+#  endif
+#else
+#  define LIFECYCLE_LOG(...)
+#endif
+
 /**
  * The singleton graph instance.
  */
 static MediaStreamGraphImpl* gGraph;
 
 MediaStreamGraphImpl::~MediaStreamGraphImpl()
 {
   NS_ASSERTION(IsEmpty(),
                "All streams should have been destroyed by messages from the main thread");
   STREAM_LOG(PR_LOG_DEBUG, ("MediaStreamGraph %p destroyed", this));
+  LIFECYCLE_LOG("MediaStreamGraphImpl::~MediaStreamGraphImpl\n");
 }
 
 
 StreamTime
 MediaStreamGraphImpl::GetDesiredBufferEnd(MediaStream* aStream)
 {
   StreamTime current = IterationEnd() - aStream->mBufferStartTime;
   // When waking up media decoders, we need a longer safety margin, as it can
@@ -521,18 +537,21 @@ MediaStreamGraphImpl::UpdateStreamOrder(
   if (!audioTrackPresent &&
       CurrentDriver()->AsAudioCallbackDriver()) {
     bool started;
     {
       MonitorAutoLock mon(mMonitor);
       started = CurrentDriver()->AsAudioCallbackDriver()->IsStarted();
     }
     if (started) {
-      SystemClockDriver* driver = new SystemClockDriver(this);
-      CurrentDriver()->SwitchAtNextIteration(driver);
+      MonitorAutoLock mon(mMonitor);
+      if (mLifecycleState == LIFECYCLE_RUNNING) {
+        SystemClockDriver* driver = new SystemClockDriver(this);
+        CurrentDriver()->SwitchAtNextIteration(driver);
+      }
     }
   }
 
   if (shouldAEC && !mFarendObserverRef && gFarendObserver) {
     mFarendObserverRef = gFarendObserver;
     mMixer.AddCallback(mFarendObserverRef);
   } else if (!shouldAEC && mFarendObserverRef){
     if (mMixer.FindCallback(mFarendObserverRef)) {
@@ -900,19 +919,22 @@ MediaStreamGraphImpl::CreateOrDestroyAud
           aStream->mAudioOutputStreams.AppendElement();
         audioOutputStream->mAudioPlaybackStartTime = aAudioOutputStartTime;
         audioOutputStream->mBlockedAudioTime = 0;
         audioOutputStream->mLastTickWritten = 0;
         audioOutputStream->mTrackID = tracks->GetID();
 
         if (!CurrentDriver()->AsAudioCallbackDriver() &&
             !CurrentDriver()->Switching()) {
-          AudioCallbackDriver* driver = new AudioCallbackDriver(this);
-          mMixer.AddCallback(driver);
-          CurrentDriver()->SwitchAtNextIteration(driver);
+          MonitorAutoLock mon(mMonitor);
+          if (mLifecycleState == LIFECYCLE_RUNNING) {
+            AudioCallbackDriver* driver = new AudioCallbackDriver(this);
+            mMixer.AddCallback(driver);
+            CurrentDriver()->SwitchAtNextIteration(driver);
+          }
         }
       }
     }
   }
 
   for (int32_t i = audioOutputStreamsFound.Length() - 1; i >= 0; --i) {
     if (!audioOutputStreamsFound[i]) {
       aStream->mAudioOutputStreams.RemoveElementAt(i);
@@ -1451,23 +1473,23 @@ public:
   explicit MediaStreamGraphShutDownRunnable(MediaStreamGraphImpl* aGraph)
     : mGraph(aGraph)
   {}
   NS_IMETHOD Run()
   {
     NS_ASSERTION(mGraph->mDetectedNotRunning,
                  "We should know the graph thread control loop isn't running!");
 
-    STREAM_LOG(PR_LOG_DEBUG, ("Shutting down graph %p", mGraph.get()));
+    LIFECYCLE_LOG("Shutting down graph %p", mGraph.get());
 
     if (mGraph->CurrentDriver()->AsAudioCallbackDriver()) {
       MOZ_ASSERT(!mGraph->CurrentDriver()->AsAudioCallbackDriver()->InCallback());
     }
 
-    mGraph->CurrentDriver()->Stop();
+    mGraph->CurrentDriver()->Shutdown();
 
     // mGraph's thread is not running so it's OK to do whatever here
     if (mGraph->IsEmpty()) {
       // mGraph is no longer needed, so delete it.
       mGraph->Destroy();
     } else {
       // The graph is not empty.  We must be in a forced shutdown, or a
       // non-realtime graph that has finished processing.  Some later
@@ -1554,40 +1576,59 @@ MediaStreamGraphImpl::RunInStableState(b
 
   {
     MonitorAutoLock lock(mMonitor);
     if (aSourceIsMSG) {
       MOZ_ASSERT(mPostedRunInStableStateEvent);
       mPostedRunInStableStateEvent = false;
     }
 
+#ifdef ENABLE_LIFECYCLE_LOG
+  // This should be kept in sync with the LifecycleState enum in
+  // MediaStreamGraphImpl.h
+  const char * LifecycleState_str[] = {
+    "LIFECYCLE_THREAD_NOT_STARTED",
+    "LIFECYCLE_RUNNING",
+    "LIFECYCLE_WAITING_FOR_MAIN_THREAD_CLEANUP",
+    "LIFECYCLE_WAITING_FOR_THREAD_SHUTDOWN",
+    "LIFECYCLE_WAITING_FOR_STREAM_DESTRUCTION"
+  };
+
+  if (mLifecycleState != LIFECYCLE_RUNNING) {
+    LIFECYCLE_LOG("Running %p in stable state. Current state: %s\n",
+        this, LifecycleState_str[mLifecycleState]);
+  }
+#endif
+
     runnables.SwapElements(mUpdateRunnables);
     for (uint32_t i = 0; i < mStreamUpdates.Length(); ++i) {
       StreamUpdate* update = &mStreamUpdates[i];
       if (update->mStream) {
         ApplyStreamUpdate(update);
       }
     }
     mStreamUpdates.Clear();
 
     if (mCurrentTaskMessageQueue.IsEmpty()) {
       if (mLifecycleState == LIFECYCLE_WAITING_FOR_MAIN_THREAD_CLEANUP && IsEmpty()) {
         // Complete shutdown. First, ensure that this graph is no longer used.
         // A new graph graph will be created if one is needed.
-        STREAM_LOG(PR_LOG_DEBUG, ("Disconnecting MediaStreamGraph %p", this));
+        // Asynchronously clean up old graph. We don't want to do this
+        // synchronously because it spins the event loop waiting for threads
+        // to shut down, and we don't want to do that in a stable state handler.
+        mLifecycleState = LIFECYCLE_WAITING_FOR_THREAD_SHUTDOWN;
+        LIFECYCLE_LOG("Sending MediaStreamGraphShutDownRunnable %p", this);
+        nsCOMPtr<nsIRunnable> event = new MediaStreamGraphShutDownRunnable(this );
+        NS_DispatchToMainThread(event);
+
+        LIFECYCLE_LOG("Disconnecting MediaStreamGraph %p", this);
         if (this == gGraph) {
           // null out gGraph if that's the graph being shut down
           gGraph = nullptr;
         }
-        // Asynchronously clean up old graph. We don't want to do this
-        // synchronously because it spins the event loop waiting for threads
-        // to shut down, and we don't want to do that in a stable state handler.
-        mLifecycleState = LIFECYCLE_WAITING_FOR_THREAD_SHUTDOWN;
-        nsCOMPtr<nsIRunnable> event = new MediaStreamGraphShutDownRunnable(this );
-        NS_DispatchToMainThread(event);
       }
     } else {
       if (mLifecycleState <= LIFECYCLE_WAITING_FOR_MAIN_THREAD_CLEANUP) {
         MessageBlock* block = mBackMessageQueue.AppendElement();
         block->mMessages.SwapElements(mCurrentTaskMessageQueue);
         block->mGraphUpdateIndex = mNextGraphUpdateIndex;
         ++mNextGraphUpdateIndex;
         CurrentDriver()->EnsureNextIterationLocked();
@@ -1600,16 +1641,19 @@ MediaStreamGraphImpl::RunInStableState(b
       if (mLifecycleState == LIFECYCLE_WAITING_FOR_MAIN_THREAD_CLEANUP &&
           mRealtime && !mForceShutDown) {
         mLifecycleState = LIFECYCLE_RUNNING;
         // Revive the MediaStreamGraph since we have more messages going to it.
         // Note that we need to put messages into its queue before reviving it,
         // or it might exit immediately.
         {
           MonitorAutoUnlock unlock(mMonitor);
+          LIFECYCLE_LOG("Reviving a graph (%p) ! %s\n",
+              this, CurrentDriver()->AsAudioCallbackDriver() ? "AudioDriver" :
+                                                               "SystemDriver");
           CurrentDriver()->Revive();
         }
       }
     }
 
     // Don't start the thread for a non-realtime graph until it has been
     // explicitly started by StartNonRealtimeProcessing.
     if (mLifecycleState == LIFECYCLE_THREAD_NOT_STARTED &&
@@ -1617,17 +1661,20 @@ MediaStreamGraphImpl::RunInStableState(b
       mLifecycleState = LIFECYCLE_RUNNING;
       // Start the thread now. We couldn't start it earlier because
       // the graph might exit immediately on finding it has no streams. The
       // first message for a new graph must create a stream.
       {
         // We should exit the monitor for now, because starting a stream might
         // take locks, and we don't want to deadlock.
         MonitorAutoUnlock unlock(mMonitor);
-        STREAM_LOG(PR_LOG_DEBUG, ("Starting a graph ! %s\n", CurrentDriver()->AsAudioCallbackDriver() ? "AudioDriver" : "SystemDriver"));
+        LIFECYCLE_LOG("Starting a graph (%p) ! %s\n",
+                      this,
+                      CurrentDriver()->AsAudioCallbackDriver() ? "AudioDriver" :
+                                                                 "SystemDriver");
         CurrentDriver()->Start();
       }
     }
 
     if ((mForceShutDown || !mRealtime) &&
         mLifecycleState == LIFECYCLE_WAITING_FOR_MAIN_THREAD_CLEANUP) {
       // Defer calls to RunDuringShutdown() to happen while mMonitor is not held.
       for (uint32_t i = 0; i < mBackMessageQueue.Length(); ++i) {
--- a/content/media/MediaStreamGraph.h
+++ b/content/media/MediaStreamGraph.h
@@ -683,17 +683,18 @@ protected:
 class SourceMediaStream : public MediaStream {
 public:
   explicit SourceMediaStream(DOMMediaStream* aWrapper) :
     MediaStream(aWrapper),
     mLastConsumptionState(MediaStreamListener::NOT_CONSUMED),
     mMutex("mozilla::media::SourceMediaStream"),
     mUpdateKnownTracksTime(0),
     mPullEnabled(false),
-    mUpdateFinished(false)
+    mUpdateFinished(false),
+    mNeedsMixing(false)
   {}
 
   virtual SourceMediaStream* AsSourceStream() { return this; }
 
   // Media graph thread only
   virtual void DestroyImpl();
 
   // Call these on any thread.
--- a/content/media/MediaStreamGraphImpl.h
+++ b/content/media/MediaStreamGraphImpl.h
@@ -515,16 +515,19 @@ public:
    * object.
    * 2) Forced shutdown at application shutdown, or completion of a
    * non-realtime graph. A flag is set, RunThread() detects the flag and
    * exits, the next RunInStableState() detects the flag, and dispatches the
    * async event to Shutdown() the graph's threads. However the graph object
    * is not deleted. New messages for the graph are processed synchronously on
    * the main thread if necessary. When the last stream is destroyed, the
    * graph object is deleted.
+   *
+   * This should be kept in sync with the LifecycleState_str array in
+   * MediaStreamGraph.cpp
    */
   enum LifecycleState {
     // The graph thread hasn't started yet.
     LIFECYCLE_THREAD_NOT_STARTED,
     // RunThread() is running normally.
     LIFECYCLE_RUNNING,
     // In the following states, the graph thread is not running so
     // all "graph thread only" state in this class can be used safely
--- a/content/media/fmp4/apple/AppleVTDecoder.cpp
+++ b/content/media/fmp4/apple/AppleVTDecoder.cpp
@@ -444,25 +444,29 @@ AppleVTDecoder::InitializeSession()
     return NS_ERROR_FAILURE;
   }
 
   // Contruct video decoder selection spec.
   AutoCFRelease<CFMutableDictionaryRef> spec =
     CFDictionaryCreateMutable(NULL, 0,
                               &kCFTypeDictionaryKeyCallBacks,
                               &kCFTypeDictionaryValueCallBacks);
+// FIXME: Enabling hardware acceleration causes crashes in
+// VTDecompressionSessionCreate() with multiple videos. Bug 1055694
+#if 0
   // This key is supported (or ignored) but not declared prior to OSX 10.9.
   AutoCFRelease<CFStringRef>
         kVTVideoDecoderSpecification_EnableHardwareAcceleratedVideoDecoder =
         CFStringCreateWithCString(NULL, "EnableHardwareAcceleratedVideoDecoder",
             kCFStringEncodingUTF8);
 
   CFDictionarySetValue(spec,
       kVTVideoDecoderSpecification_EnableHardwareAcceleratedVideoDecoder,
       kCFBooleanTrue);
+#endif
 
   VTDecompressionOutputCallbackRecord cb = { PlatformCallback, this };
   rv = VTDecompressionSessionCreate(NULL, // Allocator.
                                     mFormat,
                                     spec, // Video decoder selection.
                                     NULL, // Output video format.
                                     &cb,
                                     &mSession);
--- a/content/media/mediasource/MediaSourceReader.cpp
+++ b/content/media/mediasource/MediaSourceReader.cpp
@@ -36,16 +36,18 @@ extern PRLogModuleInfo* GetMediaSourceAP
 namespace mozilla {
 
 MediaSourceReader::MediaSourceReader(MediaSourceDecoder* aDecoder)
   : MediaDecoderReader(aDecoder)
   , mTimeThreshold(-1)
   , mDropAudioBeforeThreshold(false)
   , mDropVideoBeforeThreshold(false)
   , mEnded(false)
+  , mAudioIsSeeking(false)
+  , mVideoIsSeeking(false)
 {
 }
 
 bool
 MediaSourceReader::IsWaitingMediaResources()
 {
   return mDecoders.IsEmpty() && mPendingDecoders.IsEmpty();
 }
@@ -71,28 +73,36 @@ MediaSourceReader::OnAudioDecoded(AudioD
       MSE_DEBUG("MediaSourceReader(%p)::OnAudioDecoded mTime=%lld < mTimeThreshold=%lld",
                 this, aSample->mTime, mTimeThreshold);
       delete aSample;
       mAudioReader->RequestAudioData();
       return;
     }
     mDropAudioBeforeThreshold = false;
   }
+
+  // If we are seeking we need to make sure the first sample decoded after
+  // that seek has the mDiscontinuity field set to ensure the media decoder
+  // state machine picks up that the seek is complete.
+  if (mAudioIsSeeking) {
+    mAudioIsSeeking = false;
+    aSample->mDiscontinuity = true;
+  }
   GetCallback()->OnAudioDecoded(aSample);
 }
 
 void
 MediaSourceReader::OnAudioEOS()
 {
   MSE_DEBUG("MediaSourceReader(%p)::OnAudioEOS reader=%p (readers=%u)",
             this, mAudioReader.get(), mDecoders.Length());
   if (SwitchReaders(SWITCH_FORCED)) {
     // Success! Resume decoding with next audio decoder.
     RequestAudioData();
-  } else {
+  } else if (IsEnded()) {
     // End of stream.
     MSE_DEBUG("MediaSourceReader(%p)::OnAudioEOS reader=%p EOS (readers=%u)",
               this, mAudioReader.get(), mDecoders.Length());
     GetCallback()->OnAudioEOS();
   }
 }
 
 void
@@ -117,16 +127,25 @@ MediaSourceReader::OnVideoDecoded(VideoD
       MSE_DEBUG("MediaSourceReader(%p)::OnVideoDecoded mTime=%lld < mTimeThreshold=%lld",
                 this, aSample->mTime, mTimeThreshold);
       delete aSample;
       mVideoReader->RequestVideoData(false, mTimeThreshold);
       return;
     }
     mDropVideoBeforeThreshold = false;
   }
+
+  // If we are seeking we need to make sure the first sample decoded after
+  // that seek has the mDiscontinuity field set to ensure the media decoder
+  // state machine picks up that the seek is complete.
+  if (mVideoIsSeeking) {
+    mVideoIsSeeking = false;
+    aSample->mDiscontinuity = true;
+  }
+
   GetCallback()->OnVideoDecoded(aSample);
 }
 
 void
 MediaSourceReader::OnVideoEOS()
 {
   // End of stream. See if we can switch to another video decoder.
   MSE_DEBUG("MediaSourceReader(%p)::OnVideoEOS reader=%p (readers=%u)",
@@ -433,23 +452,25 @@ MediaSourceReader::Seek(int64_t aTime, i
   }
 
   if (IsShutdown()) {
     return NS_ERROR_FAILURE;
   }
 
   ResetDecode();
   if (mAudioReader) {
+    mAudioIsSeeking = true;
     nsresult rv = mAudioReader->Seek(aTime, aStartTime, aEndTime, aCurrentTime);
     MSE_DEBUG("MediaSourceReader(%p)::Seek audio reader=%p rv=%x", this, mAudioReader.get(), rv);
     if (NS_FAILED(rv)) {
       return rv;
     }
   }
   if (mVideoReader) {
+    mVideoIsSeeking = true;
     nsresult rv = mVideoReader->Seek(aTime, aStartTime, aEndTime, aCurrentTime);
     MSE_DEBUG("MediaSourceReader(%p)::Seek video reader=%p rv=%x", this, mVideoReader.get(), rv);
     if (NS_FAILED(rv)) {
       return rv;
     }
   }
   return NS_OK;
 }
--- a/content/media/mediasource/MediaSourceReader.h
+++ b/content/media/mediasource/MediaSourceReader.h
@@ -111,13 +111,21 @@ private:
 
   nsTArray<nsRefPtr<SourceBufferDecoder>> mPendingDecoders;
   nsTArray<nsRefPtr<SourceBufferDecoder>> mDecoders;
 
   nsRefPtr<MediaDecoderReader> mAudioReader;
   nsRefPtr<MediaDecoderReader> mVideoReader;
 
   bool mEnded;
+
+  // For a seek to complete we need to send a sample with
+  // the mDiscontinuity field set to true once we have the
+  // first decoded sample. These flags are set during seeking
+  // so we can detect when we have the first decoded sample
+  // after a seek.
+  bool mAudioIsSeeking;
+  bool mVideoIsSeeking;
 };
 
 } // namespace mozilla
 
 #endif /* MOZILLA_MEDIASOURCEREADER_H_ */
--- a/content/media/mediasource/SourceBuffer.cpp
+++ b/content/media/mediasource/SourceBuffer.cpp
@@ -56,16 +56,27 @@ public:
               this, aLength,
               aLength > 0 ? aData[0] : 0,
               aLength > 1 ? aData[1] : 0,
               aLength > 2 ? aData[2] : 0,
               aLength > 3 ? aData[3] : 0);
     return false;
   }
 
+  virtual bool IsMediaSegmentPresent(const uint8_t* aData, uint32_t aLength)
+  {
+    MSE_DEBUG("ContainerParser(%p)::IsMediaSegmentPresent aLength=%u [%x%x%x%x]",
+              this, aLength,
+              aLength > 0 ? aData[0] : 0,
+              aLength > 1 ? aData[1] : 0,
+              aLength > 2 ? aData[2] : 0,
+              aLength > 3 ? aData[3] : 0);
+    return false;
+  }
+
   virtual bool ParseStartAndEndTimestamps(const uint8_t* aData, uint32_t aLength,
                                           double& aStart, double& aEnd)
   {
     return false;
   }
 
   virtual const nsTArray<uint8_t>& InitData()
   {
@@ -77,17 +88,17 @@ public:
 
 protected:
   nsTArray<uint8_t> mInitData;
 };
 
 class WebMContainerParser : public ContainerParser {
 public:
   WebMContainerParser()
-    : mTimecodeScale(0)
+    : mParser(0), mOffset(0)
   {}
 
   bool IsInitSegmentPresent(const uint8_t* aData, uint32_t aLength)
   {
     ContainerParser::IsInitSegmentPresent(aData, aLength);
     // XXX: This is overly primitive, needs to collect data as it's appended
     // to the SB and handle, rather than assuming everything is present in a
     // single aData segment.
@@ -100,65 +111,102 @@ public:
     // 0x1654ae6b // -> One or more Tracks
     if (aLength >= 4 &&
         aData[0] == 0x1a && aData[1] == 0x45 && aData[2] == 0xdf && aData[3] == 0xa3) {
       return true;
     }
     return false;
   }
 
-  virtual bool ParseStartAndEndTimestamps(const uint8_t* aData, uint32_t aLength,
-                                          double& aStart, double& aEnd)
+  bool IsMediaSegmentPresent(const uint8_t* aData, uint32_t aLength)
   {
+    ContainerParser::IsMediaSegmentPresent(aData, aLength);
     // XXX: This is overly primitive, needs to collect data as it's appended
     // to the SB and handle, rather than assuming everything is present in a
     // single aData segment.
+    // 0x1a45dfa3 // EBML
+    // ...
+    // DocType == "webm"
+    // ...
+    // 0x18538067 // Segment (must be "unknown" size)
+    // 0x1549a966 // -> Segment Info
+    // 0x1654ae6b // -> One or more Tracks
+    if (aLength >= 4 &&
+        aData[0] == 0x1f && aData[1] == 0x43 && aData[2] == 0xb6 && aData[3] == 0x75) {
+      return true;
+    }
+    return false;
+  }
 
-    WebMBufferedParser parser(0);
-    if (mTimecodeScale != 0) {
-      parser.SetTimecodeScale(mTimecodeScale);
+  virtual bool ParseStartAndEndTimestamps(const uint8_t* aData, uint32_t aLength,
+                                          double& aStart, double& aEnd)
+  {
+    bool initSegment = IsInitSegmentPresent(aData, aLength);
+    if (initSegment) {
+      mOffset = 0;
+      mParser = WebMBufferedParser(0);
+      mOverlappedMapping.Clear();
     }
 
+    // XXX if it only adds new mappings, overlapped but not available
+    // (e.g. overlap < 0) frames are "lost" from the reported mappings here.
     nsTArray<WebMTimeDataOffset> mapping;
+    mapping.AppendElements(mOverlappedMapping);
+    mOverlappedMapping.Clear();
     ReentrantMonitor dummy("dummy");
-    parser.Append(aData, aLength, mapping, dummy);
-
-    mTimecodeScale = parser.GetTimecodeScale();
+    mParser.Append(aData, aLength, mapping, dummy);
 
     // XXX This is a bit of a hack.  Assume if there are no timecodes
     // present and it's an init segment that it's _just_ an init segment.
     // We should be more precise.
-    if (IsInitSegmentPresent(aData, aLength)) {
+    if (initSegment) {
       uint32_t length = aLength;
       if (!mapping.IsEmpty()) {
         length = mapping[0].mSyncOffset;
         MOZ_ASSERT(length <= aLength);
       }
       MSE_DEBUG("WebMContainerParser(%p)::ParseStartAndEndTimestamps: Stashed init of %u bytes.",
                 this, length);
 
       mInitData.ReplaceElementsAt(0, mInitData.Length(), aData, length);
     }
+    mOffset += aLength;
 
     if (mapping.IsEmpty()) {
       return false;
     }
 
+    // Exclude frames that we don't enough data to cover the end of.
+    uint32_t endIdx = mapping.Length() - 1;
+    while (mOffset < mapping[endIdx].mEndOffset && endIdx > 0) {
+      endIdx -= 1;
+    }
+
+    if (endIdx == 0) {
+      return false;
+    }
+
     static const double NS_PER_S = 1e9;
     aStart = mapping[0].mTimecode / NS_PER_S;
-    aEnd = mapping.LastElement().mTimecode / NS_PER_S;
+    aEnd = mapping[endIdx].mTimecode / NS_PER_S;
+    aEnd += (mapping[endIdx].mTimecode - mapping[endIdx - 1].mTimecode) / NS_PER_S;
 
-    MSE_DEBUG("WebMContainerParser(%p)::ParseStartAndEndTimestamps: [%f, %f] [fso=%lld, leo=%lld]",
-              this, aStart, aEnd, mapping[0].mSyncOffset, mapping.LastElement().mEndOffset);
+    MSE_DEBUG("WebMContainerParser(%p)::ParseStartAndEndTimestamps: [%f, %f] [fso=%lld, leo=%lld, l=%u endIdx=%u]",
+              this, aStart, aEnd, mapping[0].mSyncOffset, mapping[endIdx].mEndOffset, mapping.Length(), endIdx);
+
+    mapping.RemoveElementsAt(0, endIdx + 1);
+    mOverlappedMapping.AppendElements(mapping);
 
     return true;
   }
 
 private:
-  uint32_t mTimecodeScale;
+  WebMBufferedParser mParser;
+  nsTArray<WebMTimeDataOffset> mOverlappedMapping;
+  int64_t mOffset;
 };
 
 class MP4ContainerParser : public ContainerParser {
 public:
   MP4ContainerParser() : mTimescale(0) {}
 
   bool IsInitSegmentPresent(const uint8_t* aData, uint32_t aLength)
   {
@@ -580,17 +628,18 @@ SourceBuffer::AppendData(const uint8_t* 
     Optional<MediaSourceEndOfStreamError> decodeError(MediaSourceEndOfStreamError::Decode);
     ErrorResult dummy;
     mMediaSource->EndOfStream(decodeError, dummy);
     aRv.Throw(NS_ERROR_FAILURE);
     return;
   }
   double start, end;
   if (mParser->ParseStartAndEndTimestamps(aData, aLength, start, end)) {
-    if (start <= mLastParsedTimestamp || mLastParsedTimestamp - start > 0.1) {
+    if (mParser->IsMediaSegmentPresent(aData, aLength) &&
+        (start < mLastParsedTimestamp || start - mLastParsedTimestamp > 0.1)) {
       MSE_DEBUG("SourceBuffer(%p)::AppendData: Data (%f, %f) overlaps %f.",
                 this, start, end, mLastParsedTimestamp);
 
       // This data is earlier in the timeline than data we have already
       // processed, so we must create a new decoder to handle the decoding.
       DiscardDecoder();
 
       // If we've got a decoder here, it's not initialized, so we can use it
--- a/content/media/mediasource/SourceBufferDecoder.cpp
+++ b/content/media/mediasource/SourceBufferDecoder.cpp
@@ -59,22 +59,16 @@ SourceBufferDecoder::IsShutdown() const
 
 void
 SourceBufferDecoder::NotifyBytesConsumed(int64_t aBytes, int64_t aOffset)
 {
   MSE_DEBUG("SourceBufferDecoder(%p)::NotifyBytesConsumed UNIMPLEMENTED", this);
 }
 
 int64_t
-SourceBufferDecoder::GetEndMediaTime() const
-{
-  return mMediaDuration;
-}
-
-int64_t
 SourceBufferDecoder::GetMediaDuration()
 {
   return mMediaDuration;
 }
 
 VideoFrameContainer*
 SourceBufferDecoder::GetVideoFrameContainer()
 {
--- a/content/media/mediasource/SourceBufferDecoder.h
+++ b/content/media/mediasource/SourceBufferDecoder.h
@@ -32,17 +32,16 @@ public:
 
   NS_DECL_THREADSAFE_ISUPPORTS
 
   virtual bool IsMediaSeekable() MOZ_FINAL MOZ_OVERRIDE;
   virtual bool IsShutdown() const MOZ_FINAL MOZ_OVERRIDE;
   virtual bool IsTransportSeekable() MOZ_FINAL MOZ_OVERRIDE;
   virtual bool OnDecodeThread() const MOZ_FINAL MOZ_OVERRIDE;
   virtual bool OnStateMachineThread() const MOZ_FINAL MOZ_OVERRIDE;
-  virtual int64_t GetEndMediaTime() const MOZ_FINAL MOZ_OVERRIDE;
   virtual int64_t GetMediaDuration() MOZ_FINAL MOZ_OVERRIDE;
   virtual layers::ImageContainer* GetImageContainer() MOZ_FINAL MOZ_OVERRIDE;
   virtual MediaDecoderOwner* GetOwner() MOZ_FINAL MOZ_OVERRIDE;
   virtual SourceBufferResource* GetResource() const MOZ_FINAL MOZ_OVERRIDE;
   virtual ReentrantMonitor& GetReentrantMonitor() MOZ_FINAL MOZ_OVERRIDE;
   virtual VideoFrameContainer* GetVideoFrameContainer() MOZ_FINAL MOZ_OVERRIDE;
   virtual void MetadataLoaded(MediaInfo* aInfo, MetadataTags* aTags) MOZ_FINAL MOZ_OVERRIDE;
   virtual void NotifyBytesConsumed(int64_t aBytes, int64_t aOffset) MOZ_FINAL MOZ_OVERRIDE;
--- a/content/media/webaudio/BufferDecoder.cpp
+++ b/content/media/webaudio/BufferDecoder.cpp
@@ -84,23 +84,16 @@ BufferDecoder::NotifyBytesConsumed(int64
 
 void
 BufferDecoder::NotifyDecodedFrames(uint32_t aParsed, uint32_t aDecoded)
 {
   // ignore
 }
 
 int64_t
-BufferDecoder::GetEndMediaTime() const
-{
-  // unknown
-  return -1;
-}
-
-int64_t
 BufferDecoder::GetMediaDuration()
 {
   // unknown
   return -1;
 }
 
 void
 BufferDecoder::SetMediaDuration(int64_t aDuration)
--- a/content/media/webaudio/BufferDecoder.h
+++ b/content/media/webaudio/BufferDecoder.h
@@ -38,18 +38,16 @@ public:
   virtual bool OnDecodeThread() const MOZ_FINAL MOZ_OVERRIDE;
 
   virtual MediaResource* GetResource() const MOZ_FINAL MOZ_OVERRIDE;
 
   virtual void NotifyBytesConsumed(int64_t aBytes, int64_t aOffset) MOZ_FINAL MOZ_OVERRIDE;
 
   virtual void NotifyDecodedFrames(uint32_t aParsed, uint32_t aDecoded) MOZ_FINAL MOZ_OVERRIDE;
 
-  virtual int64_t GetEndMediaTime() const MOZ_FINAL MOZ_OVERRIDE;
-
   virtual int64_t GetMediaDuration() MOZ_FINAL MOZ_OVERRIDE;
 
   virtual void SetMediaDuration(int64_t aDuration) MOZ_FINAL MOZ_OVERRIDE;
 
   virtual void UpdateEstimatedMediaDuration(int64_t aDuration) MOZ_FINAL MOZ_OVERRIDE;
 
   virtual void SetMediaSeekable(bool aMediaSeekable) MOZ_FINAL MOZ_OVERRIDE;
 
--- a/content/media/webaudio/test/browser.ini
+++ b/content/media/webaudio/test/browser.ini
@@ -1,7 +1,8 @@
 [DEFAULT]
+skip-if = e10s
 support-files =
   browser_mozAudioChannel.html
   browser_mozAudioChannel_muted.html
 
 [browser_mozAudioChannel.js]
 [browser_mozAudioChannel_muted.js]
--- a/content/media/webm/WebMReader.cpp
+++ b/content/media/webm/WebMReader.cpp
@@ -152,16 +152,17 @@ WebMReader::WebMReader(AbstractMediaDeco
   mOpusDecoder(nullptr),
   mSkip(0),
   mSeekPreroll(0),
 #endif
   mVideoTrack(0),
   mAudioTrack(0),
   mAudioStartUsec(-1),
   mAudioFrames(0),
+  mLastVideoFrameTime(0),
   mAudioCodec(-1),
   mVideoCodec(-1),
   mHasVideo(false),
   mHasAudio(false)
 {
   MOZ_COUNT_CTOR(WebMReader);
 #ifdef PR_LOGGING
   if (!gNesteggLog) {
@@ -859,36 +860,33 @@ bool WebMReader::DecodeVideoFrame(bool &
     return false;
   }
 
   uint64_t tstamp = 0;
   r = nestegg_packet_tstamp(packet, &tstamp);
   if (r == -1) {
     return false;
   }
+  mLastVideoFrameTime = tstamp;
 
   // The end time of this frame is the start time of the next frame.  Fetch
   // the timestamp of the next packet for this track.  If we've reached the
   // end of the resource, use the file's duration as the end time of this
   // video frame.
   uint64_t next_tstamp = 0;
   nsAutoRef<NesteggPacketHolder> next_holder(NextPacket(VIDEO));
   if (next_holder) {
     r = nestegg_packet_tstamp(next_holder->mPacket, &next_tstamp);
     if (r == -1) {
       return false;
     }
     PushVideoPacket(next_holder.disown());
   } else {
-    ReentrantMonitorAutoEnter decoderMon(mDecoder->GetReentrantMonitor());
-    int64_t endTime = mDecoder->GetEndMediaTime();
-    if (endTime == -1) {
-      return false;
-    }
-    next_tstamp = endTime * NS_PER_USEC;
+    next_tstamp = tstamp;
+    next_tstamp += tstamp - mLastVideoFrameTime;
   }
 
   int64_t tstamp_usecs = tstamp / NS_PER_USEC;
   for (uint32_t i = 0; i < count; ++i) {
     unsigned char* data;
     size_t length;
     r = nestegg_packet_data(packet, i, &data, &length);
     if (r == -1) {
--- a/content/media/webm/WebMReader.h
+++ b/content/media/webm/WebMReader.h
@@ -219,16 +219,20 @@ private:
   int64_t mAudioStartUsec;
 
   // Number of audio frames we've decoded since decoding began at mAudioStartMs.
   uint64_t mAudioFrames;
 
   // Number of microseconds that must be discarded from the start of the Stream.
   uint64_t mCodecDelay;
 
+  // Calculate the frame duration from the last decodeable frame using the
+  // previous frame's timestamp.  In NS.
+  uint64_t mLastVideoFrameTime;
+
   // Parser state and computed offset-time mappings.  Shared by multiple
   // readers when decoder has been cloned.  Main thread only.
   nsRefPtr<WebMBufferedState> mBufferedState;
 
   // Size of the frame initially present in the stream. The picture region
   // is defined as a ratio relative to this.
   nsIntSize mInitialFrame;
 
--- a/content/media/webspeech/synth/nsSynthVoiceRegistry.h
+++ b/content/media/webspeech/synth/nsSynthVoiceRegistry.h
@@ -18,17 +18,17 @@ namespace mozilla {
 namespace dom {
 
 class RemoteVoice;
 class SpeechSynthesisUtterance;
 class SpeechSynthesisChild;
 class nsSpeechTask;
 class VoiceData;
 
-class nsSynthVoiceRegistry : public nsISynthVoiceRegistry
+class nsSynthVoiceRegistry MOZ_FINAL : public nsISynthVoiceRegistry
 {
 public:
   NS_DECL_ISUPPORTS
   NS_DECL_NSISYNTHVOICEREGISTRY
 
   nsSynthVoiceRegistry();
 
   already_AddRefed<nsSpeechTask> SpeakUtterance(SpeechSynthesisUtterance& aUtterance,
--- a/content/svg/content/src/SVGForeignObjectElement.cpp
+++ b/content/svg/content/src/SVGForeignObjectElement.cpp
@@ -70,32 +70,29 @@ SVGForeignObjectElement::Height()
 
 //----------------------------------------------------------------------
 // nsSVGElement methods
 
 /* virtual */ gfxMatrix
 SVGForeignObjectElement::PrependLocalTransformsTo(const gfxMatrix &aMatrix,
                                                   TransformTypes aWhich) const
 {
-  NS_ABORT_IF_FALSE(aWhich != eChildToUserSpace || aMatrix.IsIdentity(),
-                    "Skipping eUserSpaceToParent transforms makes no sense");
-
   // 'transform' attribute:
   gfxMatrix fromUserSpace =
     SVGGraphicsElement::PrependLocalTransformsTo(aMatrix, aWhich);
   if (aWhich == eUserSpaceToParent) {
     return fromUserSpace;
   }
   // our 'x' and 'y' attributes:
   float x, y;
   const_cast<SVGForeignObjectElement*>(this)->
     GetAnimatedLengthValues(&x, &y, nullptr);
   gfxMatrix toUserSpace = gfxMatrix().Translate(gfxPoint(x, y));
   if (aWhich == eChildToUserSpace) {
-    return toUserSpace;
+    return toUserSpace * aMatrix;
   }
   NS_ABORT_IF_FALSE(aWhich == eAllTransforms, "Unknown TransformTypes");
   return toUserSpace * fromUserSpace;
 }
 
 /* virtual */ bool
 SVGForeignObjectElement::HasValidDimensions() const
 {
--- a/content/svg/content/src/SVGIFrameElement.cpp
+++ b/content/svg/content/src/SVGIFrameElement.cpp
@@ -59,19 +59,16 @@ SVGIFrameElement::~SVGIFrameElement()
 
 //----------------------------------------------------------------------
 // nsSVGElement methods
 
 /* virtual */ gfxMatrix
 SVGIFrameElement::PrependLocalTransformsTo(const gfxMatrix &aMatrix,
                                            TransformTypes aWhich) const
 {
-  NS_ABORT_IF_FALSE(aWhich != eChildToUserSpace || aMatrix.IsIdentity(),
-                    "Skipping eUserSpaceToParent transforms makes no sense");
-
   // 'transform' attribute:
   gfxMatrix fromUserSpace =
     SVGGraphicsElement::PrependLocalTransformsTo(aMatrix, aWhich);
   if (aWhich == eUserSpaceToParent) {
     return fromUserSpace;
   }
   // our 'x' and 'y' attributes:
   float x, y;
--- a/content/svg/content/src/SVGSVGElement.cpp
+++ b/content/svg/content/src/SVGSVGElement.cpp
@@ -951,35 +951,32 @@ SVGSVGElement::GetLength(uint8_t aCtxTyp
 
 //----------------------------------------------------------------------
 // nsSVGElement methods
 
 /* virtual */ gfxMatrix
 SVGSVGElement::PrependLocalTransformsTo(const gfxMatrix &aMatrix,
                                         TransformTypes aWhich) const
 {
-  NS_ABORT_IF_FALSE(aWhich != eChildToUserSpace || aMatrix.IsIdentity(),
-                    "Skipping eUserSpaceToParent transforms makes no sense");
-
   // 'transform' attribute:
   gfxMatrix fromUserSpace =
     SVGSVGElementBase::PrependLocalTransformsTo(aMatrix, aWhich);
   if (aWhich == eUserSpaceToParent) {
     return fromUserSpace;
   }
 
   if (IsInner()) {
     float x, y;
     const_cast<SVGSVGElement*>(this)->GetAnimatedLengthValues(&x, &y, nullptr);
     if (aWhich == eAllTransforms) {
       // the common case
       return ThebesMatrix(GetViewBoxTransform()) * gfxMatrix().Translate(gfxPoint(x, y)) * fromUserSpace;
     }
     NS_ABORT_IF_FALSE(aWhich == eChildToUserSpace, "Unknown TransformTypes");
-    return ThebesMatrix(GetViewBoxTransform()) * gfxMatrix().Translate(gfxPoint(x, y));
+    return ThebesMatrix(GetViewBoxTransform()) * gfxMatrix().Translate(gfxPoint(x, y)) * aMatrix;
   }
 
   if (IsRoot()) {
     gfxMatrix zoomPanTM;
     zoomPanTM.Translate(gfxPoint(mCurrentTranslate.GetX(), mCurrentTranslate.GetY()));
     zoomPanTM.Scale(mCurrentScale, mCurrentScale);
     return ThebesMatrix(GetViewBoxTransform()) * zoomPanTM * fromUserSpace;
   }
--- a/content/svg/content/src/SVGTransformableElement.cpp
+++ b/content/svg/content/src/SVGTransformableElement.cpp
@@ -88,19 +88,16 @@ SVGTransformableElement::IsEventAttribut
 
 //----------------------------------------------------------------------
 // nsSVGElement overrides
 
 gfxMatrix
 SVGTransformableElement::PrependLocalTransformsTo(const gfxMatrix &aMatrix,
                                                   TransformTypes aWhich) const
 {
-  NS_ABORT_IF_FALSE(aWhich != eChildToUserSpace || aMatrix.IsIdentity(),
-                    "Skipping eUserSpaceToParent transforms makes no sense");
-
   gfxMatrix result(aMatrix);
 
   if (aWhich == eChildToUserSpace) {
     // We don't have anything to prepend.
     // eChildToUserSpace is not the common case, which is why we return
     // 'result' to benefit from NRVO rather than returning aMatrix before
     // creating 'result'.
     return result;
--- a/content/svg/content/src/SVGUseElement.cpp
+++ b/content/svg/content/src/SVGUseElement.cpp
@@ -420,31 +420,28 @@ SVGUseElement::UnlinkSource()
 
 //----------------------------------------------------------------------
 // nsSVGElement methods
 
 /* virtual */ gfxMatrix
 SVGUseElement::PrependLocalTransformsTo(const gfxMatrix &aMatrix,
                                         TransformTypes aWhich) const
 {
-  NS_ABORT_IF_FALSE(aWhich != eChildToUserSpace || aMatrix.IsIdentity(),
-                    "Skipping eUserSpaceToParent transforms makes no sense");
-
   // 'transform' attribute:
   gfxMatrix fromUserSpace =
     SVGUseElementBase::PrependLocalTransformsTo(aMatrix, aWhich);
   if (aWhich == eUserSpaceToParent) {
     return fromUserSpace;
   }
   // our 'x' and 'y' attributes:
   float x, y;
   const_cast<SVGUseElement*>(this)->GetAnimatedLengthValues(&x, &y, nullptr);
   gfxMatrix toUserSpace = gfxMatrix().Translate(gfxPoint(x, y));
   if (aWhich == eChildToUserSpace) {
-    return toUserSpace;
+    return toUserSpace * aMatrix;
   }
   NS_ABORT_IF_FALSE(aWhich == eAllTransforms, "Unknown TransformTypes");
   return toUserSpace * fromUserSpace;
 }
 
 /* virtual */ bool
 SVGUseElement::HasValidDimensions() const
 {
--- a/docshell/test/browser/browser.ini
+++ b/docshell/test/browser/browser.ini
@@ -87,11 +87,13 @@ skip-if = e10s # Bug ?????? - test touch
 skip-if = e10s # Bug ?????? - event handler checks event.target is the content document and test e10s-utils doesn't do that.
 [browser_bug92473.js]
 skip-if = e10s # Bug ?????? - BrowserSetForcedCharacterSet() in browser.js references docShell
 [browser_bug941562.js]
 skip-if = e10s # Bug ?????? - event handler checks event.target is the content document and test e10s-utils doesn't do that.
 [browser_uriFixupIntegration.js]
 skip-if = e10s
 [browser_loadDisallowInherit.js]
+skip-if = e10s
 [browser_loadURI.js]
 skip-if = e10s # Bug ?????? - event handler checks event.target is the content document and test e10s-utils doesn't do that.
 [browser_search_notification.js]
+skip-if = e10s
--- a/dom/base/nsFocusManager.cpp
+++ b/dom/base/nsFocusManager.cpp
@@ -114,33 +114,53 @@ struct nsDelayedBlurOrFocusEvent
      mTarget(aOther.mTarget) { }
 
   uint32_t mType;
   nsCOMPtr<nsIPresShell> mPresShell;
   nsCOMPtr<nsIDocument> mDocument;
   nsCOMPtr<EventTarget> mTarget;
 };
 
+inline void ImplCycleCollectionUnlink(nsDelayedBlurOrFocusEvent& aField)
+{
+  aField.mPresShell = nullptr;
+  aField.mDocument = nullptr;
+  aField.mTarget = nullptr;
+}
+
+inline void
+ImplCycleCollectionTraverse(nsCycleCollectionTraversalCallback& aCallback,
+                            nsDelayedBlurOrFocusEvent& aField,
+                            const char* aName,
+                            uint32_t aFlags = 0)
+{
+  CycleCollectionNoteChild(aCallback, aField.mPresShell.get(), aName, aFlags);
+  CycleCollectionNoteChild(aCallback, aField.mDocument.get(), aName, aFlags);
+  CycleCollectionNoteChild(aCallback, aField.mTarget.get(), aName, aFlags);
+}
+
 NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(nsFocusManager)
   NS_INTERFACE_MAP_ENTRY(nsIFocusManager)
   NS_INTERFACE_MAP_ENTRY(nsIObserver)
   NS_INTERFACE_MAP_ENTRY(nsISupportsWeakReference)
   NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIFocusManager)
 NS_INTERFACE_MAP_END
 
 NS_IMPL_CYCLE_COLLECTING_ADDREF(nsFocusManager)
 NS_IMPL_CYCLE_COLLECTING_RELEASE(nsFocusManager)
 
 NS_IMPL_CYCLE_COLLECTION(nsFocusManager,
                          mActiveWindow,
                          mFocusedWindow,
                          mFocusedContent,
                          mFirstBlurEvent,
                          mFirstFocusEvent,
-                         mWindowBeingLowered)
+                         mWindowBeingLowered,
+                         mDelayedBlurFocusEvents,
+                         mMouseButtonEventHandlingDocument)
 
 nsFocusManager* nsFocusManager::sInstance = nullptr;
 bool nsFocusManager::sMouseFocusesFormControl = false;
 bool nsFocusManager::sTestMode = false;
 
 static const char* kObservedPrefs[] = {
   "accessibility.browsewithcaret",
   "accessibility.tabfocus_applies_to_xul",
--- a/dom/base/nsJSEnvironment.cpp
+++ b/dom/base/nsJSEnvironment.cpp
@@ -1391,115 +1391,16 @@ static const JSFunctionSpec TraceMallocF
     JS_FS("TraceMallocCloseLogFD",      TraceMallocCloseLogFD,      1, 0),
     JS_FS("TraceMallocLogTimestamp",    TraceMallocLogTimestamp,    1, 0),
     JS_FS("TraceMallocDumpAllocations", TraceMallocDumpAllocations, 1, 0),
     JS_FS_END
 };
 
 #endif /* NS_TRACE_MALLOC */
 
-#ifdef MOZ_DMD
-
-#include <errno.h>
-
-namespace mozilla {
-namespace dmd {
-
-// See https://wiki.mozilla.org/Performance/MemShrink/DMD for instructions on
-// how to use DMD.
-
-static FILE *
-OpenDMDOutputFile(JSContext *cx, JS::CallArgs &args)
-{
-  JSString *str = JS::ToString(cx, args.get(0));
-  if (!str)
-    return nullptr;
-  JSAutoByteString pathname(cx, str);
-  if (!pathname)
-    return nullptr;
-
-  FILE* fp = fopen(pathname.ptr(), "w");
-  if (!fp) {
-    JS_ReportError(cx, "DMD can't open %s: %s",
-                   pathname.ptr(), strerror(errno));
-    return nullptr;
-  }
-  return fp;
-}
-
-static bool
-AnalyzeReports(JSContext *cx, unsigned argc, JS::Value *vp)
-{
-  if (!dmd::IsRunning()) {
-    JS_ReportError(cx, "DMD is not running");
-    return false;
-  }
-
-  JS::CallArgs args = JS::CallArgsFromVp(argc, vp);
-  FILE *fp = OpenDMDOutputFile(cx, args);
-  if (!fp) {
-    return false;
-  }
-
-  dmd::ClearReports();
-  dmd::RunReportersForThisProcess();
-  dmd::Writer writer(FpWrite, fp);
-  dmd::AnalyzeReports(writer);
-
-  fclose(fp);
-
-  args.rval().setUndefined();
-  return true;
-}
-
-// This will be removed eventually.
-static bool
-ReportAndDump(JSContext *cx, unsigned argc, JS::Value *vp)
-{
-  JS_ReportWarning(cx, "DMDReportAndDump() is deprecated; "
-                   "please use DMDAnalyzeReports() instead");
-
-  return AnalyzeReports(cx, argc, vp);
-}
-
-static bool
-AnalyzeHeap(JSContext *cx, unsigned argc, JS::Value *vp)
-{
-  if (!dmd::IsRunning()) {
-    JS_ReportError(cx, "DMD is not running");
-    return false;
-  }
-
-  JS::CallArgs args = JS::CallArgsFromVp(argc, vp);
-  FILE *fp = OpenDMDOutputFile(cx, args);
-  if (!fp) {
-    return false;
-  }
-
-  dmd::Writer writer(FpWrite, fp);
-  dmd::AnalyzeHeap(writer);
-
-  fclose(fp);
-
-  args.rval().setUndefined();
-  return true;
-}
-
-} // namespace dmd
-} // namespace mozilla
-
-static const JSFunctionSpec DMDFunctions[] = {
-    JS_FS("DMDReportAndDump",  dmd::ReportAndDump,  1, 0),
-    JS_FS("DMDAnalyzeReports", dmd::AnalyzeReports, 1, 0),
-    JS_FS("DMDAnalyzeHeap",    dmd::AnalyzeHeap,    1, 0),
-    JS_FS_END
-};
-
-#endif  // defined(MOZ_DMD)
-
 #ifdef MOZ_JPROF
 
 #include <signal.h>
 
 inline bool
 IsJProfAction(struct sigaction *action)
 {
     return (action->sa_sigaction &&
@@ -1613,23 +1514,16 @@ nsJSContext::InitClasses(JS::Handle<JSOb
 
 #ifdef NS_TRACE_MALLOC
   if (nsContentUtils::IsCallerChrome()) {
     // Attempt to initialize TraceMalloc functions
     ::JS_DefineFunctions(cx, aGlobalObj, TraceMallocFunctions);
   }
 #endif
 
-#ifdef MOZ_DMD
-  if (nsContentUtils::IsCallerChrome()) {
-    // Attempt to initialize DMD functions
-    ::JS_DefineFunctions(cx, aGlobalObj, DMDFunctions);
-  }
-#endif
-
 #ifdef MOZ_JPROF
   // Attempt to initialize JProf functions
   ::JS_DefineFunctions(cx, aGlobalObj, JProfFunctions);
 #endif
 
   return NS_OK;
 }
 
--- a/dom/bindings/BindingUtils.cpp
+++ b/dom/bindings/BindingUtils.cpp
@@ -1247,17 +1247,17 @@ XrayResolveProperty(JSContext* cx, JS::H
   return true;
 }
 
 static bool
 ResolvePrototypeOrConstructor(JSContext* cx, JS::Handle<JSObject*> wrapper,
                               JS::Handle<JSObject*> obj,
                               size_t protoAndIfaceCacheIndex, unsigned attrs,
                               JS::MutableHandle<JSPropertyDescriptor> desc,
-                              bool cacheOnHolder)
+                              bool& cacheOnHolder)
 {
   JS::Rooted<JSObject*> global(cx, js::GetGlobalForObjectCrossCompartment(obj));
   {
     JSAutoCompartment ac(cx, global);
     ProtoAndIfaceCache& protoAndIfaceCache = *GetProtoAndIfaceCache(global);
     JSObject* protoOrIface =
       protoAndIfaceCache.EntrySlotIfExists(protoAndIfaceCacheIndex);
     if (!protoOrIface) {
--- a/dom/browser-element/BrowserElementChildPreload.js
+++ b/dom/browser-element/BrowserElementChildPreload.js
@@ -191,16 +191,21 @@ BrowserElementChild.prototype = {
                      /* useCapture = */ true,
                      /* wantsUntrusted = */ false);
 
     addEventListener('DOMLinkAdded',
                      this._linkAddedHandler.bind(this),
                      /* useCapture = */ true,
                      /* wantsUntrusted = */ false);
 
+    addEventListener('MozScrolledAreaChanged',
+                     this._mozScrollAreaChanged.bind(this),
+                     /* useCapture = */ true,
+                     /* wantsUntrusted = */ false);
+
     addEventListener('DOMMetaAdded',
                      this._metaChangedHandler.bind(this),
                      /* useCapture = */ true,
                      /* wantsUntrusted = */ false);
 
     addEventListener('DOMMetaChanged',
                      this._metaChangedHandler.bind(this),
                      /* useCapture = */ true,
@@ -231,16 +236,17 @@ BrowserElementChild.prototype = {
       sendAsyncMsg('firstpaint');
     });
 
     let self = this;
 
     let mmCalls = {
       "purge-history": this._recvPurgeHistory,
       "get-screenshot": this._recvGetScreenshot,
+      "get-contentdimensions": this._recvGetContentDimensions,
       "set-visible": this._recvSetVisible,
       "get-visible": this._recvVisible,
       "send-mouse-event": this._recvSendMouseEvent,
       "send-touch-event": this._recvSendTouchEvent,
       "get-can-go-back": this._recvCanGoBack,
       "get-can-go-forward": this._recvCanGoForward,
       "go-back": this._recvGoBack,
       "go-forward": this._recvGoForward,
@@ -869,16 +875,39 @@ BrowserElementChild.prototype = {
 
     // Try to wait for the event loop to go idle before we take the screenshot,
     // but once we've waited maxDelayMS milliseconds, go ahead and take it
     // anyway.
     Cc['@mozilla.org/message-loop;1'].getService(Ci.nsIMessageLoop).postIdleTask(
       takeScreenshotClosure, maxDelayMS);
   },
 
+  _recvGetContentDimensions: function(data) {
+    debug("Received getContentDimensions message: (" + data.json.id + ")");
+    sendAsyncMsg('got-contentdimensions', {
+      id: data.json.id,
+      successRv: this._getContentDimensions()
+    });
+  },
+
+  _mozScrollAreaChanged: function(e) {
+    let dimensions = this._getContentDimensions();
+    sendAsyncMsg('scrollareachanged', {
+      width: dimensions.width,
+      height: dimensions.height
+    });
+  },
+
+  _getContentDimensions: function() {
+    return {
+      width: content.document.body.scrollWidth,
+      height: content.document.body.scrollHeight
+    }
+  },
+
   /**
    * Actually take a screenshot and foward the result up to our parent, given
    * the desired maxWidth and maxHeight (in CSS pixels), and given the
    * DOMRequest ID associated with the request from the parent.
    */
   _takeScreenshot: function(maxWidth, maxHeight, mimeType, domRequestID) {
     // You can think of the screenshotting algorithm as carrying out the
     // following steps:
--- a/dom/browser-element/BrowserElementParent.jsm
+++ b/dom/browser-element/BrowserElementParent.jsm
@@ -133,16 +133,17 @@ function BrowserElementParent(frameLoade
     defineNoReturnMethod('stop', this._stop);
     defineMethod('download', this._download);
     defineDOMRequestMethod('purgeHistory', 'purge-history');
     defineMethod('getScreenshot', this._getScreenshot);
     defineNoReturnMethod('zoom', this._zoom);
 
     defineDOMRequestMethod('getCanGoBack', 'get-can-go-back');
     defineDOMRequestMethod('getCanGoForward', 'get-can-go-forward');
+    defineDOMRequestMethod('getContentDimensions', 'get-contentdimensions');
   }
 
   defineMethod('addNextPaintListener', this._addNextPaintListener);
   defineMethod('removeNextPaintListener', this._removeNextPaintListener);
 
   let principal = this._frameElement.ownerDocument.nodePrincipal;
   let perm = Services.perms
              .testExactPermissionFromPrincipal(principal, "input-manage");
@@ -242,16 +243,17 @@ BrowserElementParent.prototype = {
       "close": this._fireEventFromMsg,
       "error": this._fireEventFromMsg,
       "firstpaint": this._fireProfiledEventFromMsg,
       "documentfirstpaint": this._fireProfiledEventFromMsg,
       "nextpaint": this._recvNextPaint,
       "keyevent": this._fireKeyEvent,
       "got-purge-history": this._gotDOMRequestResult,
       "got-screenshot": this._gotDOMRequestResult,
+      "got-contentdimensions": this._gotDOMRequestResult,
       "got-can-go-back": this._gotDOMRequestResult,
       "got-can-go-forward": this._gotDOMRequestResult,
       "fullscreen-origin-change": this._remoteFullscreenOriginChange,
       "rollback-fullscreen": this._remoteFrameFullscreenReverted,
       "exit-fullscreen": this._exitFullscreen,
       "got-visible": this._gotDOMRequestResult,
       "visibilitychange": this._childVisibilityChange,
       "got-set-input-method-active": this._gotDOMRequestResult,
@@ -259,16 +261,17 @@ BrowserElementParent.prototype = {
     };
 
     let mmSecuritySensitiveCalls = {
       "showmodalprompt": this._handleShowModalPrompt,
       "contextmenu": this._fireCtxMenuEvent,
       "securitychange": this._fireEventFromMsg,
       "locationchange": this._fireEventFromMsg,
       "iconchange": this._fireEventFromMsg,
+      "scrollareachanged": this._fireEventFromMsg,
       "titlechange": this._fireProfiledEventFromMsg,
       "opensearch": this._fireEventFromMsg,
       "manifestchange": this._fireEventFromMsg,
       "metachange": this._fireEventFromMsg,
       "resize": this._fireEventFromMsg,
       "activitydone": this._fireEventFromMsg,
       "scroll": this._fireEventFromMsg
     };
@@ -565,17 +568,18 @@ BrowserElementParent.prototype = {
    *
    */
   _gotDOMRequestResult: function(data) {
     let req = this._pendingDOMRequests[data.json.id];
     delete this._pendingDOMRequests[data.json.id];
 
     if ('successRv' in data.json) {
       debug("Successful gotDOMRequestResult.");
-      Services.DOMRequest.fireSuccess(req, data.json.successRv);
+      let clientObj = Cu.cloneInto(data.json.successRv, this._window);
+      Services.DOMRequest.fireSuccess(req, clientObj);
     }
     else {
       debug("Got error in gotDOMRequestResult.");
       Services.DOMRequest.fireErrorAsync(req, data.json.errorMsg);
     }
   },
 
   _setVisible: function(visible) {
new file mode 100644
--- /dev/null
+++ b/dom/browser-element/mochitest/browserElement_GetContentDimensions.js
@@ -0,0 +1,67 @@
+/* Any copyright is dedicated to the public domain.
+   http://creativecommons.org/publicdomain/zero/1.0/ */
+
+// Bug 757859 - Test the getContentDimensions functionality of mozbrowser
+
+"use strict";
+SimpleTest.waitForExplicitFinish();
+browserElementTestHelpers.setEnabledPref(true);
+browserElementTestHelpers.addPermission();
+
+var resizeContent = function() {
+  var innerBox = content.document.getElementById('abox');
+  innerBox.style.width = '800px';
+  innerBox.style.height = '800px';
+}
+
+function runTest() {
+
+  var iframe1 = document.createElement('iframe');
+  SpecialPowers.wrap(iframe1).mozbrowser = true;
+
+  var iframeWidth = 400;
+  var iframeHeight = 400;
+  var numIframeLoaded = 0;
+  var numResizeEvents = 0;
+  var mm;
+
+  iframe1.src = 'data:text/html,<html><body><div id=\'abox\' ' +
+    'style=\'background:blue;width:200px;height:200px\'>test</div></body></html>';
+  iframe1.style.width = iframeWidth + 'px';
+  iframe1.style.height = iframeHeight + 'px';
+  document.body.appendChild(iframe1);
+
+  function iframeScrollAreaChanged(e) {
+    numResizeEvents++;
+    if (numResizeEvents === 1) {
+      ok(true, 'Resize event when changing content size');
+      ok(e.detail.width > iframeWidth, 'Iframes content is larger than iframe');
+      ok(e.detail.height > iframeHeight, 'Iframes content is larger than iframe');
+      iframe1.src = 'data:text/html,<html><body><div id=\'abox\' ' +
+        'style=\'background:blue;width:200px;height:200px\'>test</div></body></html>';
+    } else if (numResizeEvents === 2) {
+      ok(true, 'Resize event when changing src');
+      iframe1.removeEventListener('mozbrowserresize', iframeScrollAreaChanged);
+      SimpleTest.finish();
+    }
+  }
+
+  function iframeLoadedHandler() {
+    iframe1.removeEventListener('mozbrowserloadend', iframeLoadedHandler);
+    mm = SpecialPowers.getBrowserFrameMessageManager(iframe1);
+    iframe1.getContentDimensions().onsuccess = function(e) {
+      ok(typeof e.target.result.width === 'number', 'Received width');
+      ok(typeof e.target.result.height === 'number', 'Received height');
+      ok(e.target.result.height <= iframeHeight, 'Iframes content is smaller than iframe');
+      ok(e.target.result.width <= iframeWidth, 'Iframes content is smaller than iframe');
+      iframe1.addEventListener('mozbrowserscrollareachanged', iframeScrollAreaChanged);
+      mm.loadFrameScript('data:,(' + resizeContent.toString() + ')();', false);
+    }
+  }
+
+  iframe1.addEventListener('mozbrowserloadend', iframeLoadedHandler);
+}
+
+addEventListener('load', function() {
+  SimpleTest.executeSoon(runTest);
+});
--- a/dom/browser-element/mochitest/mochitest-oop.ini
+++ b/dom/browser-element/mochitest/mochitest-oop.ini
@@ -90,8 +90,9 @@ skip-if = (toolkit == 'gonk' && !debug)
 disabled = bug 930449
 # Disabled until bug 924771 makes them stop timing out
 [test_browserElement_oop_CloseFromOpener.html]
 disabled = bug 924771
 [test_browserElement_oop_CloseApp.html]
 disabled = bug 924771
 [test_browserElement_oop_ExposableURI.html]
 disabled = bug 924771
+[test_browserElement_oop_GetContentDimensions.html]
--- a/dom/browser-element/mochitest/mochitest.ini
+++ b/dom/browser-element/mochitest/mochitest.ini
@@ -61,16 +61,18 @@ support-files =
   browserElement_TargetTop.js
   browserElement_Titlechange.js
   browserElement_TopBarrier.js
   browserElement_VisibilityChange.js
   browserElement_XFrameOptions.js
   browserElement_XFrameOptionsAllowFrom.js
   browserElement_XFrameOptionsDeny.js
   browserElement_XFrameOptionsSameOrigin.js
+  browserElement_XFrameOptionsSameOrigin.js
+  browserElement_GetContentDimensions.js
   file_browserElement_AlertInFrame.html
   file_browserElement_AlertInFrame_Inner.html
   file_browserElement_AppFramePermission.html
   file_browserElement_AppWindowNamespace.html
   file_browserElement_ThemeColor.html
   file_browserElement_BrowserWindowNamespace.html
   file_browserElement_CloseApp.html
   file_browserElement_CloseFromOpener.html
@@ -196,8 +198,9 @@ skip-if = (toolkit == 'gonk' && !debug)
 [test_browserElement_inproc_XFrameOptionsSameOrigin.html]
 [test_browserElement_oop_NextPaint.html]
 # Disabled due to https://bugzilla.mozilla.org/show_bug.cgi?id=774100
 [test_browserElement_inproc_Reload.html]
 disabled = bug 774100
 # Disabled due to focus issues (no bug that I'm aware of)
 [test_browserElement_oop_KeyEvents.html]
 disabled =
+[test_browserElement_inproc_GetContentDimensions.html]
new file mode 100644
--- /dev/null
+++ b/dom/browser-element/mochitest/test_browserElement_inproc_GetContentDimensions.html
@@ -0,0 +1,13 @@
+<!DOCTYPE HTML>
+<html>
+<head>
+  <title>Test of browser element.</title>
+  <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+  <script type="application/javascript" src="browserElementTestHelpers.js"></script>
+  <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head>
+<body>
+<script type="application/javascript;version=1.7" src="browserElement_GetContentDimensions.js">
+</script>
+</body>
+</html>
new file mode 100644
--- /dev/null
+++ b/dom/browser-element/mochitest/test_browserElement_oop_GetContentDimensions.html
@@ -0,0 +1,13 @@
+<!DOCTYPE HTML>
+<html>
+<head>
+  <title>Test of browser element.</title>
+  <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+  <script type="application/javascript" src="browserElementTestHelpers.js"></script>
+  <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head>
+<body>
+<script type="application/javascript;version=1.7" src="browserElement_GetContentDimensions.js">
+</script>
+</body>
+</html>
--- a/dom/canvas/WebGLExtensions.h
+++ b/dom/canvas/WebGLExtensions.h
@@ -48,230 +48,230 @@ protected:
     WebGLExtensionType::WrapObject(JSContext *cx) { \
         return dom::WebGLExtensionType##Binding::Wrap(cx, this); \
     }
 
 class WebGLExtensionCompressedTextureATC
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionCompressedTextureATC(WebGLContext*);
+    explicit WebGLExtensionCompressedTextureATC(WebGLContext*);
     virtual ~WebGLExtensionCompressedTextureATC();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionCompressedTextureETC1
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionCompressedTextureETC1(WebGLContext*);
+    explicit WebGLExtensionCompressedTextureETC1(WebGLContext*);
     virtual ~WebGLExtensionCompressedTextureETC1();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionCompressedTexturePVRTC
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionCompressedTexturePVRTC(WebGLContext*);
+    explicit WebGLExtensionCompressedTexturePVRTC(WebGLContext*);
     virtual ~WebGLExtensionCompressedTexturePVRTC();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionCompressedTextureS3TC
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionCompressedTextureS3TC(WebGLContext*);
+    explicit WebGLExtensionCompressedTextureS3TC(WebGLContext*);
     virtual ~WebGLExtensionCompressedTextureS3TC();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionDebugRendererInfo
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionDebugRendererInfo(WebGLContext*);
+    explicit WebGLExtensionDebugRendererInfo(WebGLContext*);
     virtual ~WebGLExtensionDebugRendererInfo();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionDebugShaders
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionDebugShaders(WebGLContext*);
+    explicit WebGLExtensionDebugShaders(WebGLContext*);
     virtual ~WebGLExtensionDebugShaders();
 
     void GetTranslatedShaderSource(WebGLShader* shader, nsAString& retval);
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionDepthTexture
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionDepthTexture(WebGLContext*);
+    explicit WebGLExtensionDepthTexture(WebGLContext*);
     virtual ~WebGLExtensionDepthTexture();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionElementIndexUint
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionElementIndexUint(WebGLContext*);
+    explicit WebGLExtensionElementIndexUint(WebGLContext*);
     virtual ~WebGLExtensionElementIndexUint();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionFragDepth
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionFragDepth(WebGLContext*);
+    explicit WebGLExtensionFragDepth(WebGLContext*);
     virtual ~WebGLExtensionFragDepth();
 
     static bool IsSupported(const WebGLContext* context);
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionLoseContext
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionLoseContext(WebGLContext*);
+    explicit WebGLExtensionLoseContext(WebGLContext*);
     virtual ~WebGLExtensionLoseContext();
 
     void LoseContext();
     void RestoreContext();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionSRGB
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionSRGB(WebGLContext*);
+    explicit WebGLExtensionSRGB(WebGLContext*);
     virtual ~WebGLExtensionSRGB();
 
     static bool IsSupported(const WebGLContext* context);
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionStandardDerivatives
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionStandardDerivatives(WebGLContext*);
+    explicit WebGLExtensionStandardDerivatives(WebGLContext*);
     virtual ~WebGLExtensionStandardDerivatives();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionShaderTextureLod
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionShaderTextureLod(WebGLContext*);
+    explicit WebGLExtensionShaderTextureLod(WebGLContext*);
     virtual ~WebGLExtensionShaderTextureLod();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionTextureFilterAnisotropic
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionTextureFilterAnisotropic(WebGLContext*);
+    explicit WebGLExtensionTextureFilterAnisotropic(WebGLContext*);
     virtual ~WebGLExtensionTextureFilterAnisotropic();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionTextureFloat
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionTextureFloat(WebGLContext*);
+    explicit WebGLExtensionTextureFloat(WebGLContext*);
     virtual ~WebGLExtensionTextureFloat();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionTextureFloatLinear
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionTextureFloatLinear(WebGLContext*);
+    explicit WebGLExtensionTextureFloatLinear(WebGLContext*);
     virtual ~WebGLExtensionTextureFloatLinear();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionTextureHalfFloat
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionTextureHalfFloat(WebGLContext*);
+    explicit WebGLExtensionTextureHalfFloat(WebGLContext*);
     virtual ~WebGLExtensionTextureHalfFloat();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionTextureHalfFloatLinear
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionTextureHalfFloatLinear(WebGLContext*);
+    explicit WebGLExtensionTextureHalfFloatLinear(WebGLContext*);
     virtual ~WebGLExtensionTextureHalfFloatLinear();
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionColorBufferFloat
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionColorBufferFloat(WebGLContext*);
+    explicit WebGLExtensionColorBufferFloat(WebGLContext*);
     virtual ~WebGLExtensionColorBufferFloat();
 
     static bool IsSupported(const WebGLContext*);
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionColorBufferHalfFloat
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionColorBufferHalfFloat(WebGLContext*);
+    explicit WebGLExtensionColorBufferHalfFloat(WebGLContext*);
     virtual ~WebGLExtensionColorBufferHalfFloat();
 
     static bool IsSupported(const WebGLContext*);
 
     DECL_WEBGL_EXTENSION_GOOP
 };
 
 class WebGLExtensionDrawBuffers
     : public WebGLExtensionBase
 {
 public:
-    WebGLExtensionDrawBuffers(WebGLContext*);
+    explicit WebGLExtensionDrawBuffers(WebGLContext*);
     virtual ~WebGLExtensionDrawBuffers();
 
     void DrawBuffersWEBGL(const dom::Sequence<GLenum>& buffers);
 
     static bool IsSupported(const WebGLContext*);
 
     static const size_t sMinColorAttachments = 4;
     static const size_t sMinDrawBuffers = 4;
--- a/dom/canvas/test/webgl-conformance/generate-wrappers-and-manifest.py
+++ b/dom/canvas/test/webgl-conformance/generate-wrappers-and-manifest.py
@@ -21,17 +21,17 @@ def GetTestList():
 # Internals
 
 BASE_TEST_LIST_FILENAME = '00_test_list.txt'
 
 def AccumTests(path, listFile, out_testList):
     listFilePath = os.path.join(path, listFile)
     assert os.path.exists(listFilePath), 'Bad `listFilePath`: ' + listFilePath
 
-    with open(listFilePath) as fIn:
+    with open(listFilePath, 'rb') as fIn:
         for line in fIn:
             line = line.rstrip()
             if not line:
                 continue
 
             strippedLine = line.lstrip()
             if strippedLine.startswith('//'):
                 continue
@@ -41,16 +41,17 @@ def AccumTests(path, listFile, out_testL
                 continue
 
             split = line.rsplit('.', 1)
             assert len(split) == 2, 'Bad split for `line`: ' + line
             (name, ext) = split
 
             if ext == 'html':
                 newTestFilePath = os.path.join(path, line)
+                newTestFilePath = newTestFilePath.replace(os.sep, '/')
                 out_testList.append(newTestFilePath)
                 continue
 
             assert ext == 'txt', 'Bad `ext` on `line`: ' + line
 
             split = line.rsplit('/', 1)
             nextListFile = split[-1]
             nextPath = ''
@@ -68,24 +69,24 @@ def AccumTests(path, listFile, out_testL
 
 def FillTemplate(inFilePath, templateDict, outFilePath):
     templateShell = ImportTemplate(inFilePath)
     OutputFilledTemplate(templateShell, templateDict, outFilePath)
     return
 
 
 def ImportTemplate(inFilePath):
-    with open(inFilePath, 'r') as f:
+    with open(inFilePath, 'rb') as f:
         return TemplateShell(f)
 
 
 def OutputFilledTemplate(templateShell, templateDict, outFilePath):
     spanStrList = templateShell.Fill(templateDict)
 
-    with open(outFilePath, 'w') as f:
+    with open(outFilePath, 'wb') as f:
         f.writelines(spanStrList)
     return
 
 ##############################
 # Internals
 
 def WrapWithIndent(lines, indentLen):
   split = lines.split('\n')
@@ -183,63 +184,62 @@ class TemplateShell:
                 indentLen += len(span)
             continue
 
         return ret
 
 ########################################################################
 # Output
 
-def WriteWrappers(testFilePathList):
+def WriteWrappers(testWebPathList):
     templateShell = ImportTemplate(WRAPPER_TEMPLATE_FILEPATH)
 
     if not os.path.exists(WRAPPERS_DIR):
         os.mkdir(WRAPPERS_DIR)
     assert os.path.isdir(WRAPPERS_DIR)
 
-    wrapperFilePathList = []
-    for testFilePath in testFilePathList:
+    wrapperManifestPathList = []
+    for testWebPath in testWebPathList:
         # Mochitests must start with 'test_' or similar, or the test
         # runner will ignore our tests.
         # The error text is "is not a valid test".
-        wrapperFilePath = 'test_' + testFilePath.replace(os.sep, '__')
+        wrapperFilePath = 'test_' + testWebPath.replace('/', '__')
         wrapperFilePath = os.path.join(WRAPPERS_DIR, wrapperFilePath)
 
-        testFilePath = testFilePath.replace(os.sep, '/')
-
         templateDict = {
-            'TEST_PATH': testFilePath,
+            'TEST_PATH': testWebPath,
         }
 
         print('Writing \'' + wrapperFilePath + '\'')
         OutputFilledTemplate(templateShell, templateDict,
                              wrapperFilePath)
 
-        wrapperFilePathList.append(wrapperFilePath)
+        wrapperManifestPath = wrapperFilePath.replace(os.sep, '/')
+        wrapperManifestPathList.append(wrapperManifestPath)
         continue
 
-    return wrapperFilePathList
+    return wrapperManifestPathList
 
 
-def WriteManifest(wrapperFilePathList, supportFilePathList):
+def WriteManifest(wrapperManifestPathList, supportFilePathList):
     errataMap = LoadErrata()
 
     # DEFAULT_ERRATA
     defaultHeader = '[DEFAULT]'
     defaultErrataStr = ''
     if defaultHeader in errataMap:
         defaultErrataStr = '\n'.join(errataMap[defaultHeader])
         del errataMap[defaultHeader]
 
     # SUPPORT_FILES
     supportFilePathList = sorted(supportFilePathList)
     supportFilesStr = '\n'.join(supportFilePathList)
 
     # MANIFEST_TESTS
-    headerList = ['[' + x + ']' for x in wrapperFilePathList]
+    headerList = ['[' + x + ']' for x in wrapperManifestPathList]
 
     manifestTestLineList = []
     for header in headerList:
         manifestTestLineList.append(header)
 
         if not header in errataMap:
             continue
 
@@ -274,17 +274,17 @@ ERRATA_FILEPATH = 'mochitest-errata.ini'
 kManifestHeaderRegex = re.compile(r'\[[^\]]*?\]')
 
 
 def LoadErrata():
     nodeMap = {}
 
     nodeHeader = None
     nodeLineList = []
-    with open(ERRATA_FILEPATH, 'r') as f:
+    with open(ERRATA_FILEPATH, 'rb') as f:
         for line in f:
             line = line.rstrip()
             cur = line.lstrip()
             if cur.startswith('#'):
                 continue
 
             if not cur:
                 continue
@@ -326,27 +326,28 @@ def GetSupportFileList():
     return ret
 
 
 def GetFilePathListForDir(baseDir):
     ret = []
     for root, folders, files in os.walk(baseDir):
         for f in files:
             filePath = os.path.join(root, f)
+            filePath = filePath.replace(os.sep, '/')
             ret.append(filePath)
 
     return ret
 
 
 if __name__ == '__main__':
     fileDir = os.path.dirname(__file__)
     assert not fileDir, 'Run this file from its directory, not ' + fileDir
 
-    testFilePathList = GetTestList()
+    testWebPathList = GetTestList()
 
-    wrapperFilePathList = WriteWrappers(testFilePathList)
+    wrapperFilePathList = WriteWrappers(testWebPathList)
 
     supportFilePathList = GetSupportFileList()
     WriteManifest(wrapperFilePathList, supportFilePathList)
 
     print('Done!')
 
 
--- a/dom/events/ScrollAreaEvent.cpp
+++ b/dom/events/ScrollAreaEvent.cpp
@@ -11,19 +11,19 @@
 
 namespace mozilla {
 namespace dom {
 
 ScrollAreaEvent::ScrollAreaEvent(EventTarget* aOwner,
                                  nsPresContext* aPresContext,
                                  InternalScrollAreaEvent* aEvent)
   : UIEvent(aOwner, aPresContext, aEvent)
-  , mClientArea(nullptr)
+  , mClientArea(new DOMRect(nullptr))
 {
-  mClientArea.SetLayoutRect(aEvent ? aEvent->mArea : nsRect());
+  mClientArea->SetLayoutRect(aEvent ? aEvent->mArea : nsRect());
 }
 
 NS_IMPL_ADDREF_INHERITED(ScrollAreaEvent, UIEvent)
 NS_IMPL_RELEASE_INHERITED(ScrollAreaEvent, UIEvent)
 
 NS_INTERFACE_MAP_BEGIN(ScrollAreaEvent)
   NS_INTERFACE_MAP_ENTRY(nsIDOMScrollAreaEvent)
 NS_INTERFACE_MAP_END_INHERITING(UIEvent)
@@ -52,17 +52,17 @@ ScrollAreaEvent::InitScrollAreaEvent(con
                                      float aY,
                                      float aWidth,
                                      float aHeight)
 {
   nsresult rv =
     UIEvent::InitUIEvent(aEventType, aCanBubble, aCancelable, aView, aDetail);
   NS_ENSURE_SUCCESS(rv, rv);
 
-  mClientArea.SetRect(aX, aY, aWidth, aHeight);
+  mClientArea->SetRect(aX, aY, aWidth, aHeight);
 
   return NS_OK;
 }
 
 NS_IMETHODIMP_(void)
 ScrollAreaEvent::Serialize(IPC::Message* aMsg,
                            bool aSerializeInterfaceType)
 {
@@ -83,17 +83,17 @@ ScrollAreaEvent::Deserialize(const IPC::
 {
   NS_ENSURE_TRUE(Event::Deserialize(aMsg, aIter), false);
 
   float x, y, width, height;
   NS_ENSURE_TRUE(IPC::ReadParam(aMsg, aIter, &x), false);
   NS_ENSURE_TRUE(IPC::ReadParam(aMsg, aIter, &y), false);
   NS_ENSURE_TRUE(IPC::ReadParam(aMsg, aIter, &width), false);
   NS_ENSURE_TRUE(IPC::ReadParam(aMsg, aIter, &height), false);
-  mClientArea.SetRect(x, y, width, height);
+  mClientArea->SetRect(x, y, width, height);
 
   return true;
 }
 
 } // namespace dom
 } // namespace mozilla
 
 using namespace mozilla;
--- a/dom/events/ScrollAreaEvent.h
+++ b/dom/events/ScrollAreaEvent.h
@@ -40,32 +40,32 @@ public:
 
   virtual JSObject* WrapObject(JSContext* aCx) MOZ_OVERRIDE
   {
     return ScrollAreaEventBinding::Wrap(aCx, this);
   }
 
   float X() const
   {
-    return mClientArea.Left();
+    return mClientArea->Left();
   }
 
   float Y() const
   {
-    return mClientArea.Top();
+    return mClientArea->Top();
   }
 
   float Width() const
   {
-    return mClientArea.Width();
+    return mClientArea->Width();
   }
 
   float Height() const
   {
-    return mClientArea.Height();
+    return mClientArea->Height();
   }
 
   void InitScrollAreaEvent(const nsAString& aType,
                            bool aCanBubble,
                            bool aCancelable,
                            nsIDOMWindow* aView,
                            int32_t aDetail,
                            float aX, float aY,
@@ -74,15 +74,15 @@ public:
   {
     aRv = InitScrollAreaEvent(aType, aCanBubble, aCancelable, aView,
                               aDetail, aX, aY, aWidth, aHeight);
   }
 
 protected:
   ~ScrollAreaEvent() {}
 
-  DOMRect mClientArea;
+  nsRefPtr<DOMRect> mClientArea;
 };
 
 } // namespace dom
 } // namespace mozilla
 
 #endif // mozilla_dom_ScrollAreaEvent_h_
--- a/dom/interfaces/base/nsIServiceWorkerManager.idl
+++ b/dom/interfaces/base/nsIServiceWorkerManager.idl
@@ -3,17 +3,17 @@
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #include "domstubs.idl"
 
 interface nsIDocument;
 interface nsIURI;
 
-[uuid(91b9d3fc-1654-44da-b438-15123cdbe7aa)]
+[uuid(8d2f64db-5585-4876-a1c9-391e16549068)]
 interface nsIServiceWorkerManager : nsISupports
 {
   /**
    * Registers a ServiceWorker with script loaded from `aScriptURI` to act as
    * the ServiceWorker for aScope.  Requires a valid entry settings object on
    * the stack. This means you must call this from content code 'within'
    * a window.
    *
@@ -56,20 +56,29 @@ interface nsIServiceWorkerManager : nsIS
 
   /**
    * Documents that have called MaybeStartControlling() should call this when
    * they are destroyed. This function may be called multiple times, and is
    * idempotent.
    */
   [notxpcom,nostdcall] void MaybeStopControlling(in nsIDocument aDoc);
 
-  // Returns a ServiceWorker
-  [noscript] nsISupports GetInstalling(in nsIDOMWindow aWindow);
-  [noscript] nsISupports GetWaiting(in nsIDOMWindow aWindow);
-  [noscript] nsISupports GetActive(in nsIDOMWindow aWindow);
+  /*
+   * Returns a ServiceWorker.
+   * window is the window of the caller. scope is the registration's scope and must be
+   * a valid entry that window is allowed to load, otherwise this will return nullptr.
+   * These are only meant to be called from ServiceWorkerRegistration instances.
+   */
+  [noscript] nsISupports GetInstalling(in nsIDOMWindow aWindow, in DOMString aScope);
+  [noscript] nsISupports GetWaiting(in nsIDOMWindow aWindow, in DOMString aScope);
+  [noscript] nsISupports GetActive(in nsIDOMWindow aWindow, in DOMString aScope);
+
+  /*
+   * Returns a ServiceWorker.
+   */
   [noscript] nsISupports GetDocumentController(in nsIDOMWindow aWindow);
 
   // Testing
   DOMString getScopeForUrl(in DOMString path);
 };
 
 %{ C++
 #define SERVICEWORKERMANAGER_CONTRACTID "@mozilla.org/serviceworkers/manager;1"
--- a/dom/plugins/base/nsPluginHost.h
+++ b/dom/plugins/base/nsPluginHost.h
@@ -53,20 +53,20 @@ public:
   nsCString   mFullPath;
   int64_t     mLastModifiedTime;
   bool        mSeen;
 
   nsRefPtr<nsInvalidPluginTag> mPrev;
   nsRefPtr<nsInvalidPluginTag> mNext;
 };
 
-class nsPluginHost : public nsIPluginHost,
-                     public nsIObserver,
-                     public nsITimerCallback,
-                     public nsSupportsWeakReference
+class nsPluginHost MOZ_FINAL : public nsIPluginHost,
+                               public nsIObserver,
+                               public nsITimerCallback,
+                               public nsSupportsWeakReference
 {
   virtual ~nsPluginHost();
 public:
   nsPluginHost();
 
   static already_AddRefed<nsPluginHost> GetInst();
 
   NS_DECL_AND_IMPL_ZEROING_OPERATOR_NEW
@@ -302,17 +302,17 @@ private:
   static nsPluginHost* sInst;
 };
 
 class MOZ_STACK_CLASS PluginDestructionGuard : protected PRCList
 {
 public:
   explicit PluginDestructionGuard(nsNPAPIPluginInstance *aInstance);
 
-  PluginDestructionGuard(NPP npp);
+  explicit PluginDestructionGuard(NPP npp);
 
   ~PluginDestructionGuard();
 
   static bool DelayDestroy(nsNPAPIPluginInstance *aInstance);
 
 protected:
   void Init()
   {
--- a/dom/settings/SettingsDB.jsm
+++ b/dom/settings/SettingsDB.jsm
@@ -25,17 +25,17 @@ const TYPED_ARRAY_THINGS = new Set([
   "Uint16Array",
   "Int32Array",
   "Uint32Array",
   "Float32Array",
   "Float64Array",
 ]);
 
 this.SETTINGSDB_NAME = "settings";
-this.SETTINGSDB_VERSION = 4;
+this.SETTINGSDB_VERSION = 5;
 this.SETTINGSSTORE_NAME = "settings";
 
 Cu.import("resource://gre/modules/IndexedDBHelper.jsm");
 Cu.import("resource://gre/modules/FileUtils.jsm");
 Cu.import("resource://gre/modules/NetUtil.jsm");
 
 this.SettingsDB = function SettingsDB() {}
 
--- a/dom/smil/nsSMILAnimationController.h
+++ b/dom/smil/nsSMILAnimationController.h
@@ -35,18 +35,18 @@ class SVGAnimationElement;
 // at most one animation controller per nsDocument so that frame-rate tuning can
 // be performed at a document-level.
 //
 // The animation controller can contain many child time containers (timed
 // document root objects) which may correspond to SVG document fragments within
 // a compound document. These time containers can be paused individually or
 // here, at the document level.
 //
-class nsSMILAnimationController : public nsSMILTimeContainer,
-                                  public nsARefreshObserver
+class nsSMILAnimationController MOZ_FINAL : public nsSMILTimeContainer,
+                                            public nsARefreshObserver
 {
 public:
   explicit nsSMILAnimationController(nsIDocument* aDoc);
 
   // Clears mDocument pointer. (Called by our nsIDocument when it's going away)
   void Disconnect();
 
   // nsSMILContainer
--- a/dom/workers/ServiceWorkerManager.cpp
+++ b/dom/workers/ServiceWorkerManager.cpp
@@ -571,18 +571,39 @@ ServiceWorkerManager::Register(const nsA
   // Although the spec says that the same-origin checks should also be done
   // asynchronously, we do them in sync because the Promise created by the
   // WebIDL infrastructure due to a returned error will be resolved
   // asynchronously. We aren't making any internal state changes in these
   // checks, so ordering of multiple calls is not affected.
 
   nsCOMPtr<nsIURI> documentURI = doc->GetBaseURI();
 
+  bool httpsNeeded = true;
+
   // FIXME(nsm): Bug 1003991. Disable check when devtools are open.
-  if (!Preferences::GetBool("dom.serviceWorkers.testing.enabled")) {
+  if (Preferences::GetBool("dom.serviceWorkers.testing.enabled")) {
+    httpsNeeded = false;
+  }
+
+  // No https needed for localhost.
+  if (httpsNeeded) {
+    nsAutoCString host;
+    result = documentURI->GetHost(host);
+    if (NS_WARN_IF(result.Failed())) {
+      return result.ErrorCode();
+    }
+
+    if (host.Equals("127.0.0.1") ||
+        host.Equals("localhost") ||
+        host.Equals("::1")) {
+      httpsNeeded = false;
+    }
+  }
+
+  if (httpsNeeded) {
     bool isHttps;
     result = documentURI->SchemeIs("https", &isHttps);
     if (result.Failed() || !isHttps) {
       NS_WARNING("ServiceWorker registration from insecure websites is not allowed.");
       return NS_ERROR_DOM_SECURITY_ERR;
     }
   }
 
@@ -1921,30 +1942,60 @@ ServiceWorkerManager::FireEventOnService
       }
 
       target->DispatchTrustedEvent(aName);
     }
   }
 }
 
 /*
- * This is used for installing, waiting and active, and uses the registration
- * most specifically matching the current scope.
+ * This is used for installing, waiting and active.
  */
 NS_IMETHODIMP
-ServiceWorkerManager::GetServiceWorkerForWindow(nsIDOMWindow* aWindow,
-                                                WhichServiceWorker aWhichWorker,
-                                                nsISupports** aServiceWorker)
+ServiceWorkerManager::GetServiceWorkerForScope(nsIDOMWindow* aWindow,
+                                               const nsAString& aScope,
+                                               WhichServiceWorker aWhichWorker,
+                                               nsISupports** aServiceWorker)
 {
+  AssertIsOnMainThread();
+
   nsCOMPtr<nsPIDOMWindow> window = do_QueryInterface(aWindow);
-  MOZ_ASSERT(window);
+  if (!window) {
+    return NS_ERROR_FAILURE;
+  }
+
+  nsCOMPtr<nsIDocument> doc = window->GetExtantDoc();
+  MOZ_ASSERT(doc);
+
+  ///////////////////////////////////////////
+  // Security check
+  nsCString scope = NS_ConvertUTF16toUTF8(aScope);
+  nsCOMPtr<nsIURI> scopeURI;
+  // We pass nullptr as the base URI since scopes obtained from
+  // ServiceWorkerRegistrations MUST be fully qualified URIs.
+  nsresult rv = NS_NewURI(getter_AddRefs(scopeURI), scope, nullptr, nullptr);
+  if (NS_WARN_IF(NS_FAILED(rv))) {
+    return NS_ERROR_DOM_SECURITY_ERR;
+  }
+
+  nsCOMPtr<nsIPrincipal> documentPrincipal = doc->NodePrincipal();
+  rv = documentPrincipal->CheckMayLoad(scopeURI, true /* report */,
+                                       false /* allowIfInheritsPrinciple */);
+  if (NS_WARN_IF(NS_FAILED(rv))) {
+    return NS_ERROR_DOM_SECURITY_ERR;
+  }
+  ////////////////////////////////////////////
+
+  nsRefPtr<ServiceWorkerDomainInfo> domainInfo = GetDomainInfo(scope);
+  if (!domainInfo) {
+    return NS_ERROR_FAILURE;
+  }
 
   nsRefPtr<ServiceWorkerRegistrationInfo> registration =
-    GetServiceWorkerRegistrationInfo(window);
-
+    domainInfo->GetRegistration(scope);
   if (!registration) {
     return NS_ERROR_FAILURE;
   }
 
   nsRefPtr<ServiceWorkerInfo> info;
   if (aWhichWorker == WhichServiceWorker::INSTALLING_WORKER) {
     info = registration->mInstallingWorker;
   } else if (aWhichWorker == WhichServiceWorker::WAITING_WORKER) {
@@ -1955,20 +2006,20 @@ ServiceWorkerManager::GetServiceWorkerFo
     MOZ_CRASH("Invalid worker type");
   }
 
   if (!info) {
     return NS_ERROR_DOM_NOT_FOUND_ERR;
   }
 
   nsRefPtr<ServiceWorker> serviceWorker;
-  nsresult rv = CreateServiceWorkerForWindow(window,
-                                             info->GetScriptSpec(),
-                                             registration->mScope,
-                                             getter_AddRefs(serviceWorker));
+  rv = CreateServiceWorkerForWindow(window,
+                                    info->GetScriptSpec(),
+                                    registration->mScope,
+                                    getter_AddRefs(serviceWorker));
   if (NS_WARN_IF(NS_FAILED(rv))) {
     return rv;
   }
 
   serviceWorker.forget(aServiceWorker);
   return NS_OK;
 }
 
@@ -2010,35 +2061,42 @@ ServiceWorkerManager::GetDocumentControl
   }
 
   serviceWorker.forget(aServiceWorker);
   return NS_OK;
 }
 
 NS_IMETHODIMP
 ServiceWorkerManager::GetInstalling(nsIDOMWindow* aWindow,
+                                    const nsAString& aScope,
                                     nsISupports** aServiceWorker)
 {
-  return GetServiceWorkerForWindow(aWindow, WhichServiceWorker::INSTALLING_WORKER,
-                                   aServiceWorker);
+  return GetServiceWorkerForScope(aWindow, aScope,
+                                  WhichServiceWorker::INSTALLING_WORKER,
+                                  aServiceWorker);
 }
 
 NS_IMETHODIMP
 ServiceWorkerManager::GetWaiting(nsIDOMWindow* aWindow,
+                                 const nsAString& aScope,
                                  nsISupports** aServiceWorker)
 {
-  return GetServiceWorkerForWindow(aWindow, WhichServiceWorker::WAITING_WORKER,
-                                   aServiceWorker);
+  return GetServiceWorkerForScope(aWindow, aScope,
+                                  WhichServiceWorker::WAITING_WORKER,
+                                  aServiceWorker);
 }
 
 NS_IMETHODIMP
-ServiceWorkerManager::GetActive(nsIDOMWindow* aWindow, nsISupports** aServiceWorker)
+ServiceWorkerManager::GetActive(nsIDOMWindow* aWindow,
+                                const nsAString& aScope,
+                                nsISupports** aServiceWorker)
 {
-  return GetServiceWorkerForWindow(aWindow, WhichServiceWorker::ACTIVE_WORKER,
-                                   aServiceWorker);
+  return GetServiceWorkerForScope(aWindow, aScope,
+                                  WhichServiceWorker::ACTIVE_WORKER,
+                                  aServiceWorker);
 }
 
 NS_IMETHODIMP
 ServiceWorkerManager::CreateServiceWorker(const nsACString& aScriptSpec,
                                           const nsACString& aScope,
                                           ServiceWorker** aServiceWorker)
 {
   AssertIsOnMainThread();
--- a/dom/workers/ServiceWorkerManager.h
+++ b/dom/workers/ServiceWorkerManager.h
@@ -356,19 +356,20 @@ private:
 
   already_AddRefed<ServiceWorkerDomainInfo>
   GetDomainInfo(nsIURI* aURI);
 
   already_AddRefed<ServiceWorkerDomainInfo>
   GetDomainInfo(const nsCString& aURL);
 
   NS_IMETHODIMP
-  GetServiceWorkerForWindow(nsIDOMWindow* aWindow,
-                            WhichServiceWorker aWhichWorker,
-                            nsISupports** aServiceWorker);
+  GetServiceWorkerForScope(nsIDOMWindow* aWindow,
+                           const nsAString& aScope,
+                           WhichServiceWorker aWhichWorker,
+                           nsISupports** aServiceWorker);
 
   void
   InvalidateServiceWorkerRegistrationWorker(ServiceWorkerRegistrationInfo* aRegistration,
                                             WhichServiceWorker aWhichOnes);
 
   already_AddRefed<ServiceWorkerRegistrationInfo>
   GetServiceWorkerRegistrationInfo(nsPIDOMWindow* aWindow);
 
--- a/dom/workers/ServiceWorkerRegistration.cpp
+++ b/dom/workers/ServiceWorkerRegistration.cpp
@@ -118,33 +118,38 @@ ServiceWorkerRegistration::Unregister(Er
   nsRefPtr<Promise> ret = static_cast<Promise*>(promise.get());
   MOZ_ASSERT(ret);
   return ret.forget();
 }
 
 already_AddRefed<workers::ServiceWorker>
 ServiceWorkerRegistration::GetWorkerReference(WhichServiceWorker aWhichOne)
 {
+  nsCOMPtr<nsPIDOMWindow> window = GetOwner();
+  if (!window) {
+    return nullptr;
+  }
+
   nsresult rv;
   nsCOMPtr<nsIServiceWorkerManager> swm =
     do_GetService(SERVICEWORKERMANAGER_CONTRACTID, &rv);
   if (NS_WARN_IF(NS_FAILED(rv))) {
     return nullptr;
   }
 
   nsCOMPtr<nsISupports> serviceWorker;
   switch(aWhichOne) {
     case WhichServiceWorker::INSTALLING_WORKER:
-      rv = swm->GetInstalling(GetOwner(), getter_AddRefs(serviceWorker));
+      rv = swm->GetInstalling(window, mScope, getter_AddRefs(serviceWorker));
       break;
     case WhichServiceWorker::WAITING_WORKER:
-      rv = swm->GetWaiting(GetOwner(), getter_AddRefs(serviceWorker));
+      rv = swm->GetWaiting(window, mScope, getter_AddRefs(serviceWorker));
       break;
     case WhichServiceWorker::ACTIVE_WORKER:
-      rv = swm->GetActive(GetOwner(), getter_AddRefs(serviceWorker));
+      rv = swm->GetActive(window, mScope, getter_AddRefs(serviceWorker));
       break;
     default:
       MOZ_CRASH("Invalid enum value");
   }
 
   if (NS_WARN_IF(NS_FAILED(rv))) {
     return nullptr;
   }
--- a/dom/workers/WorkerScope.cpp
+++ b/dom/workers/WorkerScope.cpp
@@ -51,25 +51,27 @@ WorkerGlobalScope::~WorkerGlobalScope()
 
 NS_IMPL_CYCLE_COLLECTION_CLASS(WorkerGlobalScope)
 
 NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(WorkerGlobalScope,
                                                   DOMEventTargetHelper)
   tmp->mWorkerPrivate->AssertIsOnWorkerThread();
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mConsole)
   NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mPerformance)
-  // XXXbz what about mLocation and mNavigator?
+  NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mLocation)
+  NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mNavigator)
 NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
 
 NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(WorkerGlobalScope,
                                                 DOMEventTargetHelper)
   tmp->mWorkerPrivate->AssertIsOnWorkerThread();
   NS_IMPL_CYCLE_COLLECTION_UNLINK(mConsole)
   NS_IMPL_CYCLE_COLLECTION_UNLINK(mPerformance)
-  // XXXbz what about mLocation and mNavigator?
+  NS_IMPL_CYCLE_COLLECTION_UNLINK(mLocation)
+  NS_IMPL_CYCLE_COLLECTION_UNLINK(mNavigator)
 NS_IMPL_CYCLE_COLLECTION_UNLINK_END
 
 NS_IMPL_CYCLE_COLLECTION_TRACE_BEGIN_INHERITED(WorkerGlobalScope,
                                                DOMEventTargetHelper)
   tmp->mWorkerPrivate->AssertIsOnWorkerThread();
 
   tmp->mWorkerPrivate->TraceTimeouts(aCallbacks, aClosure);
 NS_IMPL_CYCLE_COLLECTION_TRACE_END
new file mode 100644
--- /dev/null
+++ b/dom/workers/test/bug1060621_worker.js
@@ -0,0 +1,2 @@
+navigator.foobar = 42;
+postMessage('done');
--- a/dom/workers/test/mochitest.ini
+++ b/dom/workers/test/mochitest.ini
@@ -77,16 +77,17 @@ support-files =
   urlSearchParams_worker.js
   subdir/relativeLoad_sub_worker.js
   subdir/relativeLoad_sub_worker2.js
   subdir/relativeLoad_sub_import.js
   test_worker_interfaces.js
   test_worker_performance_now.js
   worker_driver.js
   worker_wrapper.js
+  bug1060621_worker.js
 
 [test_404.html]
 [test_atob.html]
 [test_blobConstructor.html]
 [test_blobWorkers.html]
 [test_bug1002702.html]
 [test_bug949946.html]
 [test_bug1010784.html]
@@ -165,8 +166,9 @@ skip-if = buildapp == 'b2g' || e10s
 [test_xhr_responseURL.html]
 [test_xhr_system.html]
 skip-if = buildapp == 'b2g' || e10s
 [test_xhr_system.js]
 [test_xhr_timeout.html]
 skip-if = (os == "win") || (os == "mac") || toolkit == 'android' || e10s #bug 798220
 [test_url_exceptions.html]
 [test_urlSearchParams.html]
+[test_bug1060621.html]
--- a/dom/workers/test/serviceworkers/test_installation_simple.html
+++ b/dom/workers/test/serviceworkers/test_installation_simple.html
@@ -57,17 +57,23 @@
 
   function realWorker() {
     var p = navigator.serviceWorker.register("worker.js", { scope: "realworker" });
     return p.then(function(wr) {
       ok(wr instanceof ServiceWorkerRegistration, "Register a ServiceWorker");
 
       info(wr.scope);
       ok(wr.scope == (new URL("realworker", document.baseURI)).href, "Scope should match");
-
+      // active, waiting, installing should return valid worker instances
+      // because the registration is for the realworker scope, so the workers
+      // should be obtained for that scope and not for
+      // test_installation_simple.html
+      var worker = wr.installing || wr.waiting || wr.active;
+      ok(worker && worker.scope.match(/realworker$/) &&
+         worker.url.match(/worker.js$/), "Valid worker instance should be available.");
     }, function(e) {
       info("Error: " + e.name);
       ok(false, "realWorker Registration should have succeeded!");
     });
   }
 
   function abortPrevious() {
     var p = navigator.serviceWorker.register("worker2.js", { scope: "foo/" });
--- a/dom/workers/test/serviceworkers/test_unregister.html
+++ b/dom/workers/test/serviceworkers/test_unregister.html
@@ -17,70 +17,74 @@
 
   function simpleRegister() {
     return navigator.serviceWorker.register("worker.js", { scope: "unregister/" });
   }
 
   function testControlled() {
     var testPromise = new Promise(function(res, rej) {
       window.onmessage = function(e) {
-        if (e.data === "READY") {
-          w.postMessage({ "controlled": true }, "*");
-        } else if (e.data === "SUCCESS") {
-          ok(true, "New window should be controlled.");
-          res();
-        } else if (e.data === "FAIL") {
-          ok(false, "New window should be controlled");
-          res();
+        if (!("controlled" in e.data)) {
+          ok(false, "Something went wrong.");
+          rej();
+          return;
         }
+
+        ok(e.data.controlled, "New window should be controlled.");
+        res();
       }
+    })
+
+    var div = document.getElementById("content");
+    ok(div, "Parent exists");
+
+    var ifr = document.createElement("iframe");
+    ifr.setAttribute('src', "unregister/index.html");
+    div.appendChild(ifr);
+
+    return testPromise.then(function() {
+      div.removeChild(ifr);
     });
-
-    // This setTimeout is temporary to allow the ServiceWorker to get
-    // activated. Once Bug 1025077 is implemented, this can be replaced to use
-    // ready().
-
-    var w;
-    setTimeout(function() {
-      w = window.open("unregister/index.html", "_blank", "width=700, height=400");
-    }, 150);
-    return testPromise.then(() => w.close());
   }
 
   function unregister() {
     return navigator.serviceWorker.getRegistration("unregister/")
            .then(function(reg) {
              return reg.unregister().then(function(v) {
                ok(v, "Unregister should resolve to true");
              }, function(e) {
                ok(false, "Unregister failed with " + e.name);
              });
            });
   }
 
   function testUncontrolled() {
     var testPromise = new Promise(function(res, rej) {
       window.onmessage = function(e) {
-        if (e.data === "READY") {
-          w.postMessage({ "controlled": false }, "*");
-        } else if (e.data === "SUCCESS") {
-          ok(true, "New window should not be controlled.");
-          res();
-        } else if (e.data === "FAIL") {
-          ok(false, "New window should not be controlled");
-          res();
+        if (!("controlled" in e.data)) {
+          ok(false, "Something went wrong.");
+          rej();
+          return;
         }
+
+        ok(!e.data.controlled, "New window should not be controlled.");
+        res();
       }
     });
 
-    var w;
-    setTimeout(function() {
-      w = window.open("unregister/index.html", "_blank", "width=700, height=400");
-    }, 150);
-    return testPromise.then(() => w.close());
+    var div = document.getElementById("content");
+    ok(div, "Parent exists");
+
+    var ifr = document.createElement("iframe");
+    ifr.setAttribute('src', "unregister/index.html");
+    div.appendChild(ifr);
+
+    return testPromise.then(function() {
+      div.removeChild(ifr);
+    });
   }
 
   function runTest() {
     simpleRegister()
       .then(testControlled)
       .then(unregister)
       .then(testUncontrolled)
       .then(function() {
--- a/dom/workers/test/serviceworkers/unregister/index.html
+++ b/dom/workers/test/serviceworkers/unregister/index.html
@@ -9,38 +9,32 @@
   <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
   <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
 </head>
 <body>
 <p id="display"></p>
 <div id="content" style="display: none"></div>
 <pre id="test"></pre>
 <script class="testbody" type="text/javascript">
-  function fail(msg) {
-  info("unregister/index.html: " + msg);
-    opener.postMessage("FAIL", "*");
-  }
 
-  if (!opener) {
+  if (!parent) {
     info("unregister/index.html should not to be launched directly!");
   }
 
-  window.addEventListener("message", function(e) {
-    if (!e.data) {
-      return fail("Message had no data!");
+  var tId = setTimeout(function() {
+    parent.postMessage({ controlled: false }, "*");
+    tId = null;
+  }, 2000);
+
+  navigator.serviceWorker.ready.then(function() {
+    if (tId == null) {
+      parent.postMessage("FAIL!!!", "*");
+      return;
     }
 
-    if (e.data.controlled === true && !navigator.serviceWorker.controller) {
-      return fail("Not controlled!");
-    } else if (e.data.controlled === false && navigator.serviceWorker.controller) {
-      return fail("Controlled when it shouldn't be!");
-    }
+    clearTimeout(tId);
+    parent.postMessage({ controlled: true }, "*");
+  });
 
-    opener.postMessage("SUCCESS", "*");
-  }, false);
-
-  window.onload = function() {
-    opener.postMessage("READY", "*");
-  }
 </script>
 </pre>
 </body>
 </html>
new file mode 100644
--- /dev/null
+++ b/dom/workers/test/test_bug1060621.html
@@ -0,0 +1,30 @@
+<!--
+  Any copyright is dedicated to the Public Domain.
+  http://creativecommons.org/publicdomain/zero/1.0/
+-->
+<!DOCTYPE HTML>
+<html>
+<head>
+  <title>Test for URLSearchParams object in workers</title>
+  <script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+  <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
+</head>
+<body>
+<p id="display"></p>
+<div id="content" style="display: none"></div>
+<pre id="test"></pre>
+<script class="testbody" type="text/javascript">
+
+  var worker = new Worker("bug1060621_worker.js");
+
+  worker.onmessage = function(event) {
+    ok(true, "The operation is done. We should not leak.");
+    SimpleTest.finish();
+  };
+
+  SimpleTest.waitForExplicitFinish();
+
+</script>
+</pre>
+</body>
+</html>
--- a/editor/composer/nsEditingSession.h
+++ b/editor/composer/nsEditingSession.h
@@ -38,19 +38,19 @@ class nsITimer;
 
 class nsComposerCommandsUpdater;
 class nsIChannel;
 class nsIControllers;
 class nsIDocShell;
 class nsIEditor;
 class nsIWebProgress;
 
-class nsEditingSession : public nsIEditingSession,
-                         public nsIWebProgressListener,
-                         public nsSupportsWeakReference
+class nsEditingSession MOZ_FINAL : public nsIEditingSession,
+                                   public nsIWebProgressListener,
+                                   public nsSupportsWeakReference
 {
 public:
 
   nsEditingSession();
 
   // nsISupports
   NS_DECL_ISUPPORTS
 
--- a/embedding/browser/nsDocShellTreeOwner.h
+++ b/embedding/browser/nsDocShellTreeOwner.h
@@ -54,23 +54,23 @@ class nsICDocShellTreeOwner : public nsI
 {
 public:
     NS_DECLARE_STATIC_IID_ACCESSOR(NS_ICDOCSHELLTREEOWNER_IID)
 };
 
 NS_DEFINE_STATIC_IID_ACCESSOR(nsICDocShellTreeOwner,
                               NS_ICDOCSHELLTREEOWNER_IID)
 
-class nsDocShellTreeOwner : public nsIDocShellTreeOwner,
-                            public nsIBaseWindow,
-                            public nsIInterfaceRequestor,
-                            public nsIWebProgressListener,
-                            public nsIDOMEventListener,
-                            public nsICDocShellTreeOwner,
-                            public nsSupportsWeakReference
+class nsDocShellTreeOwner MOZ_FINAL : public nsIDocShellTreeOwner,
+                                      public nsIBaseWindow,
+                                      public nsIInterfaceRequestor,
+                                      public nsIWebProgressListener,
+                                      public nsIDOMEventListener,
+                                      public nsICDocShellTreeOwner,
+                                      public nsSupportsWeakReference
 {
 friend class nsWebBrowser;
 friend class nsCommandHandler;
 
 public:
     NS_DECL_ISUPPORTS
 
     NS_DECL_NSIBASEWINDOW
@@ -139,17 +139,17 @@ protected:
 //
 // class ChromeTooltipListener
 //
 // The class that listens to the chrome events and tells the embedding
 // chrome to show tooltips, as appropriate. Handles registering itself
 // with the DOM with AddChromeListeners() and removing itself with
 // RemoveChromeListeners().
 //
-class ChromeTooltipListener : public nsIDOMEventListener
+class ChromeTooltipListener MOZ_FINAL : public nsIDOMEventListener
 {
 protected:
   virtual ~ChromeTooltipListener ( ) ;
 
 public:
   NS_DECL_ISUPPORTS
   
   ChromeTooltipListener ( nsWebBrowser* inBrowser, nsIWebBrowserChrome* inChrome ) ;
--- a/embedding/components/commandhandler/nsCommandGroup.cpp
+++ b/embedding/components/commandhandler/nsCommandGroup.cpp
@@ -13,17 +13,17 @@
 #include "nsCommandGroup.h"
 #include "nsIControllerCommand.h"
 #include "nsCRT.h"
 
 
 class nsGroupsEnumerator : public nsISimpleEnumerator
 {
 public:
-  nsGroupsEnumerator(nsControllerCommandGroup::GroupsHashtable &inHashTable);
+  explicit nsGroupsEnumerator(nsControllerCommandGroup::GroupsHashtable &inHashTable);
 
   NS_DECL_ISUPPORTS
   NS_DECL_NSISIMPLEENUMERATOR
 
 protected:
   virtual ~nsGroupsEnumerator();
 
   static PLDHashOperator HashEnum(const nsACString &aKey, nsTArray<nsCString> *aData, void *aClosure);
@@ -127,17 +127,17 @@ nsGroupsEnumerator::Initialize()
 
 #if 0
 #pragma mark -
 #endif
 
 class nsNamedGroupEnumerator : public nsISimpleEnumerator
 {
 public:
-  nsNamedGroupEnumerator(nsTArray<nsCString> *inArray);
+  explicit nsNamedGroupEnumerator(nsTArray<nsCString> *inArray);
 
   NS_DECL_ISUPPORTS
   NS_DECL_NSISIMPLEENUMERATOR
 
 protected:
   virtual ~nsNamedGroupEnumerator();
 
   nsTArray<nsCString> *mGroupArray;
--- a/embedding/components/find/nsFind.cpp
+++ b/embedding/components/find/nsFind.cpp
@@ -77,17 +77,17 @@ PR_STATIC_ASSERT(CH_SHY <= 255);
 // inner-iterator and then reposition the outer-iterator outside.
 //
 // 5) The implementation assumes that First() and Next() are only called
 // in find-forward mode, while Last() and Prev() are used in find-backward.
 
 class nsFindContentIterator : public nsIContentIterator
 {
 public:
-  nsFindContentIterator(bool aFindBackward)
+  explicit nsFindContentIterator(bool aFindBackward)
     : mStartOffset(0),
       mEndOffset(0),
       mFindBackward(aFindBackward)
   {
   }
 
   // nsISupports
   NS_DECL_CYCLE_COLLECTING_ISUPPORTS
--- a/embedding/components/printingui/unixshared/nsPrintProgress.h
+++ b/embedding/components/printingui/unixshared/nsPrintProgress.h
@@ -19,17 +19,17 @@
 class nsPrintProgress : public nsIPrintProgress, public nsIPrintStatusFeedback
 {
 public: 
 	NS_DECL_THREADSAFE_ISUPPORTS
   NS_DECL_NSIPRINTPROGRESS
   NS_DECL_NSIWEBPROGRESSLISTENER
   NS_DECL_NSIPRINTSTATUSFEEDBACK
 
-	nsPrintProgress(nsIPrintSettings* aPrintSettings);
+  explicit nsPrintProgress(nsIPrintSettings* aPrintSettings);
 
 protected:
 	virtual ~nsPrintProgress();
 
 private:
   nsresult ReleaseListeners();
 
   bool                              m_closeProgress;
--- a/embedding/components/webbrowserpersist/nsWebBrowserPersist.cpp
+++ b/embedding/components/webbrowserpersist/nsWebBrowserPersist.cpp
@@ -149,17 +149,17 @@ struct OutputData
 };
 
 struct UploadData
 {
     nsCOMPtr<nsIURI> mFile;
     int64_t mSelfProgress;
     int64_t mSelfProgressMax;
 
-    UploadData(nsIURI *aFile) :
+    explicit UploadData(nsIURI *aFile) :
         mFile(aFile),
         mSelfProgress(0),
         mSelfProgressMax(10000)
     {
     }
 };
 
 struct CleanupData
--- a/embedding/components/windowwatcher/nsAutoWindowStateHelper.h
+++ b/embedding/components/windowwatcher/nsAutoWindowStateHelper.h
@@ -14,17 +14,17 @@
  * windows.
  */
 
 class nsPIDOMWindow;
 
 class nsAutoWindowStateHelper
 {
 public:
-  nsAutoWindowStateHelper(nsPIDOMWindow *aWindow);
+  explicit nsAutoWindowStateHelper(nsPIDOMWindow *aWindow);
   ~nsAutoWindowStateHelper();
 
   bool DefaultEnabled()
   {
     return mDefaultEnabled;
   }
 
 protected:
--- a/embedding/components/windowwatcher/nsWindowWatcher.cpp
+++ b/embedding/components/windowwatcher/nsWindowWatcher.cpp
@@ -137,17 +137,17 @@ void nsWatcherWindowEntry::ReferenceSelf
 
 /****************************************************************
  ****************** nsWatcherWindowEnumerator *******************
  ****************************************************************/
 
 class nsWatcherWindowEnumerator : public nsISimpleEnumerator {
 
 public:
-  nsWatcherWindowEnumerator(nsWindowWatcher *inWatcher);
+  explicit nsWatcherWindowEnumerator(nsWindowWatcher *inWatcher);
   NS_IMETHOD HasMoreElements(bool *retval);
   NS_IMETHOD GetNext(nsISupports **retval);
 
   NS_DECL_ISUPPORTS
 
 protected:
   virtual ~nsWatcherWindowEnumerator();
 
--- a/extensions/auth/nsAuthGSSAPI.h
+++ b/extensions/auth/nsAuthGSSAPI.h
@@ -36,17 +36,17 @@
  */
 
 class nsAuthGSSAPI MOZ_FINAL : public nsIAuthModule
 {
 public:
     NS_DECL_THREADSAFE_ISUPPORTS
     NS_DECL_NSIAUTHMODULE
 
-    nsAuthGSSAPI(pType package);
+    explicit nsAuthGSSAPI(pType package);
 
     static void Shutdown();
 
 private:
     ~nsAuthGSSAPI() { Reset(); }
 
     void    Reset();
     gss_OID GetOID() { return mMechOID; }
--- a/extensions/cookie/nsPermissionManager.cpp
+++ b/extensions/cookie/nsPermissionManager.cpp
@@ -301,17 +301,17 @@ class DeleteFromMozHostListener MOZ_FINA
 
 public:
   NS_DECL_ISUPPORTS
   NS_DECL_MOZISTORAGESTATEMENTCALLBACK
 
   /**
    * @param aManager The owning manager.
    */
-  DeleteFromMozHostListener(nsPermissionManager* aManager);
+  explicit DeleteFromMozHostListener(nsPermissionManager* aManager);
 
 protected:
   nsRefPtr<nsPermissionManager> mManager;
 };
 
 NS_IMPL_ISUPPORTS(DeleteFromMozHostListener, mozIStorageStatementCallback)
 
 DeleteFromMozHostListener::
--- a/extensions/cookie/nsPermissionManager.h
+++ b/extensions/cookie/nsPermissionManager.h
@@ -23,19 +23,19 @@
 
 class nsIPermission;
 class nsIIDNService;
 class mozIStorageConnection;
 class mozIStorageAsyncStatement;
 
 ////////////////////////////////////////////////////////////////////////////////
 
-class nsPermissionManager : public nsIPermissionManager,
-                            public nsIObserver,
-                            public nsSupportsWeakReference
+class nsPermissionManager MOZ_FINAL : public nsIPermissionManager,
+                                      public nsIObserver,
+                                      public nsSupportsWeakReference
 {
 public:
   class PermissionEntry
   {
   public:
     PermissionEntry(int64_t aID, uint32_t aType, uint32_t aPermission,
                     uint32_t aExpireType, int64_t aExpireTime)
      : mID(aID)
@@ -62,17 +62,17 @@ public:
    * PermissionKey is the key used by PermissionHashKey hash table.
    *
    * NOTE: It could be implementing nsIHashable but there is no reason to worry
    * with XPCOM interfaces while we don't need to.
    */
   class PermissionKey
   {
   public:
-    PermissionKey(nsIPrincipal* aPrincipal);
+    explicit PermissionKey(nsIPrincipal* aPrincipal);
     PermissionKey(const nsACString& aHost,
                   uint32_t aAppId,
                   bool aIsInBrowserElement)
       : mHost(aHost)
       , mAppId(aAppId)
       , mIsInBrowserElement(aIsInBrowserElement)
     {
     }
@@ -104,17 +104,17 @@ public:
 
     // Dtor shouldn't be used outside of the class.
     ~PermissionKey() {};
   };
 
   class PermissionHashKey : public nsRefPtrHashKey<PermissionKey>
   {
   public:
-    PermissionHashKey(const PermissionKey* aPermissionKey)
+    explicit PermissionHashKey(const PermissionKey* aPermissionKey)
       : nsRefPtrHashKey<PermissionKey>(aPermissionKey)
     {}
 
     PermissionHashKey(const PermissionHashKey& toCopy)
       : nsRefPtrHashKey<PermissionKey>(toCopy)
       , mPermissions(toCopy.mPermissions)
     {}
 
--- a/extensions/gio/nsGIOProtocolHandler.cpp
+++ b/extensions/gio/nsGIOProtocolHandler.cpp
@@ -138,17 +138,17 @@ static void mount_operation_ask_password
 class nsGIOInputStream MOZ_FINAL : public nsIInputStream
 {
    ~nsGIOInputStream() { Close(); }
 
   public:
     NS_DECL_THREADSAFE_ISUPPORTS
     NS_DECL_NSIINPUTSTREAM
 
-    nsGIOInputStream(const nsCString &uriSpec)
+    explicit nsGIOInputStream(const nsCString &uriSpec)
       : mSpec(uriSpec)
       , mChannel(nullptr)
       , mHandle(nullptr)
       , mStream(nullptr)
       , mBytesRemaining(UINT64_MAX)
       , mStatus(NS_OK)
       , mDirList(nullptr)
       , mDirListPtr(nullptr)
--- a/extensions/spellcheck/src/mozInlineSpellChecker.h
+++ b/extensions/spellcheck/src/mozInlineSpellChecker.h
@@ -111,20 +111,20 @@ protected:
   nsresult FillNoCheckRangeFromAnchor(mozInlineSpellWordUtil& aWordUtil);
 
   nsresult GetDocument(nsIDOMDocument** aDocument);
   nsresult PositionToCollapsedRange(nsIDOMDocument* aDocument,
                                     nsIDOMNode* aNode, int32_t aOffset,
                                     nsIDOMRange** aRange);
 };
 
-class mozInlineSpellChecker : public nsIInlineSpellChecker,
-                              public nsIEditActionListener,
-                              public nsIDOMEventListener,
-                              public nsSupportsWeakReference
+class mozInlineSpellChecker MOZ_FINAL : public nsIInlineSpellChecker,
+                                        public nsIEditActionListener,
+                                        public nsIDOMEventListener,
+                                        public nsSupportsWeakReference
 {
 private:
   friend class mozInlineSpellStatus;
   friend class InitEditorSpellCheckCallback;
   friend class UpdateCurrentDictionaryCallback;
   friend class AutoChangeNumPendingSpellChecks;
   friend class mozInlineSpellResume;
 
--- a/gfx/2d/DrawTargetCG.cpp
+++ b/gfx/2d/DrawTargetCG.cpp
@@ -249,17 +249,22 @@ GetRetainedImageFromSourceSurface(Source
 
 TemporaryRef<SourceSurface>
 DrawTargetCG::OptimizeSourceSurface(SourceSurface *aSurface) const
 {
   if (aSurface->GetType() == SurfaceType::COREGRAPHICS_IMAGE ||
       aSurface->GetType() == SurfaceType::COREGRAPHICS_CGCONTEXT) {
     return aSurface;
   }
-  return aSurface->GetDataSurface();
+  RefPtr<DataSourceSurface> data = aSurface->GetDataSurface();
+
+  return CreateSourceSurfaceFromData(data->GetData(),
+                                     data->GetSize(),
+                                     data->Stride(),
+                                     data->GetFormat());
 }
 
 class UnboundnessFixer
 {
     CGRect mClipBounds;
     CGLayerRef mLayer;
     CGContextRef mCg;
   public:
--- a/gfx/2d/DrawTargetSkia.cpp
+++ b/gfx/2d/DrawTargetSkia.cpp
@@ -580,17 +580,17 @@ DrawTargetSkia::MaskSurface(const Patter
   } else {
     SkPaint maskPaint;
     TempBitmap tmpBitmap;
     SetPaintPattern(maskPaint, SurfacePattern(aMask, ExtendMode::CLAMP), tmpBitmap);
 
     SkMatrix transform = maskPaint.getShader()->getLocalMatrix();
     transform.postTranslate(SkFloatToScalar(aOffset.x), SkFloatToScalar(aOffset.y));
     SkShader* matrixShader = SkShader::CreateLocalMatrixShader(maskPaint.getShader(), transform);
-    maskPaint.setShader(matrixShader);
+    SkSafeUnref(maskPaint.setShader(matrixShader));
 
     SkLayerRasterizer::Builder builder;
     builder.addLayer(maskPaint);
     SkAutoTUnref<SkRasterizer> raster(builder.detachRasterizer());
     paint.mPaint.setRasterizer(raster.get());
 
     IntSize size = aMask->GetSize();
     Rect rect = Rect(aOffset.x, aOffset.y, size.width, size.height);
--- a/gfx/2d/DrawTargetTiled.cpp
+++ b/gfx/2d/DrawTargetTiled.cpp
@@ -1,13 +1,16 @@
 /* -*- Mode: C++; tab-width: 20; indent-tabs-mode: nil; c-basic-offset: 2 -*-
  * This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
+#define _USE_MATH_DEFINES
+#include <cmath>
+
 #include "DrawTargetTiled.h"
 #include "Logging.h"
 
 using namespace std;
 
 namespace mozilla {
 namespace gfx {
 
@@ -19,17 +22,17 @@ bool
 DrawTargetTiled::Init(const TileSet& aTiles)
 {
   if (!aTiles.mTileCount) {
     return false;
   }
 
   mTiles.reserve(aTiles.mTileCount);
   for (size_t i = 0; i < aTiles.mTileCount; ++i) {
-    mTiles.push_back(aTiles.mTiles[i]);
+    mTiles.push_back(TileInternal(aTiles.mTiles[i]));
     if (!aTiles.mTiles[i].mDrawTarget) {
       return false;
     }
     if (mTiles[0].mDrawTarget->GetFormat() != mTiles.back().mDrawTarget->GetFormat() ||
         mTiles[0].mDrawTarget->GetBackendType() != mTiles.back().mDrawTarget->GetBackendType()) {
       return false;
     }
     uint32_t newXMost = max(mRect.XMost(),
@@ -40,136 +43,140 @@ DrawTargetTiled::Init(const TileSet& aTi
     mRect.y = min(mRect.y, mTiles[i].mTileOrigin.y);
     mRect.width = newXMost - mRect.x;
     mRect.height = newYMost - mRect.y;
   }
   mFormat = mTiles[0].mDrawTarget->GetFormat();
   return true;
 }
 
-class SnapshotTiled : public SourceSurface
-{
-public:
-  SnapshotTiled(const vector<Tile>& aTiles, const IntRect& aRect)
-    : mRect(aRect)
-  {
-    for (size_t i = 0; i < aTiles.size(); i++) {
-      mSnapshots.push_back(aTiles[i].mDrawTarget->Snapshot());
-      mOrigins.push_back(aTiles[i].mTileOrigin);
-    }
-  }
-
-  virtual SurfaceType GetType() const { return SurfaceType::TILED; }
-  virtual IntSize GetSize() const { return IntSize(mRect.XMost(), mRect.YMost()); }
-  virtual SurfaceFormat GetFormat() const { return mSnapshots[0]->GetFormat(); }
-
-  virtual TemporaryRef<DataSourceSurface> GetDataSurface()
-  {
-    RefPtr<DataSourceSurface> surf = Factory::CreateDataSourceSurface(GetSize(), GetFormat());
-    if (MOZ2D_WARN_IF(!surf)) {
-      return nullptr;
-    }
-
-    DataSourceSurface::MappedSurface mappedSurf;
-    surf->Map(DataSourceSurface::MapType::WRITE, &mappedSurf);
-
-    {
-      RefPtr<DrawTarget> dt =
-        Factory::CreateDrawTargetForData(BackendType::CAIRO, mappedSurf.mData,
-        GetSize(), mappedSurf.mStride, GetFormat());
-
-      for (size_t i = 0; i < mSnapshots.size(); i++) {
-        RefPtr<DataSourceSurface> dataSurf = mSnapshots[i]->GetDataSurface();
-        dt->CopySurface(dataSurf, IntRect(IntPoint(0, 0), mSnapshots[i]->GetSize()), mOrigins[i]);
-      }
-    }
-    surf->Unmap();
-
-    return surf.forget();
-  }
-private:
-  vector<RefPtr<SourceSurface>> mSnapshots;
-  vector<IntPoint> mOrigins;
-  IntRect mRect;
-};
-
 TemporaryRef<SourceSurface>
 DrawTargetTiled::Snapshot()
 {
   return new SnapshotTiled(mTiles, mRect);
 }
 
+// Skip the mClippedOut check since this is only used for Flush() which
+// should happen even if we're clipped.
 #define TILED_COMMAND(command) \
   void \
   DrawTargetTiled::command() \
   { \
     for (size_t i = 0; i < mTiles.size(); i++) { \
-    \
-    \
-    mTiles[i].mDrawTarget->command(); \
+      mTiles[i].mDrawTarget->command(); \
     } \
   }
 #define TILED_COMMAND1(command, type1) \
   void \
   DrawTargetTiled::command(type1 arg1) \
   { \
     for (size_t i = 0; i < mTiles.size(); i++) { \
-    \
-    \
-    mTiles[i].mDrawTarget->command(arg1); \
+      if (!mTiles[i].mClippedOut) \
+        mTiles[i].mDrawTarget->command(arg1); \
     } \
   }
 #define TILED_COMMAND3(command, type1, type2, type3) \
   void \
   DrawTargetTiled::command(type1 arg1, type2 arg2, type3 arg3) \
   { \
     for (size_t i = 0; i < mTiles.size(); i++) { \
-    \
-    \
-    mTiles[i].mDrawTarget->command(arg1, arg2, arg3); \
+      if (!mTiles[i].mClippedOut) \
+        mTiles[i].mDrawTarget->command(arg1, arg2, arg3); \
     } \
   }
 #define TILED_COMMAND4(command, type1, type2, type3, type4) \
   void \
   DrawTargetTiled::command(type1 arg1, type2 arg2, type3 arg3, type4 arg4) \
   { \
     for (size_t i = 0; i < mTiles.size(); i++) { \
-    \
-    \
-    mTiles[i].mDrawTarget->command(arg1, arg2, arg3, arg4); \
+      if (!mTiles[i].mClippedOut) \
+        mTiles[i].mDrawTarget->command(arg1, arg2, arg3, arg4); \
     } \
   }
 #define TILED_COMMAND5(command, type1, type2, type3, type4, type5) \
   void \
   DrawTargetTiled::command(type1 arg1, type2 arg2, type3 arg3, type4 arg4, type5 arg5) \
   { \
     for (size_t i = 0; i < mTiles.size(); i++) { \
-    \
-    \
-    mTiles[i].mDrawTarget->command(arg1, arg2, arg3, arg4, arg5); \
+      if (!mTiles[i].mClippedOut) \
+        mTiles[i].mDrawTarget->command(arg1, arg2, arg3, arg4, arg5); \
     } \
   }
 
 TILED_COMMAND(Flush)
-TILED_COMMAND5(DrawSurface, SourceSurface*, const Rect&,
-                            const Rect&, const DrawSurfaceOptions&,
-                            const DrawOptions&)
 TILED_COMMAND4(DrawFilter, FilterNode*, const Rect&, const Point&, const DrawOptions&)
 TILED_COMMAND1(ClearRect, const Rect&)
 TILED_COMMAND4(MaskSurface, const Pattern&, SourceSurface*, Point, const DrawOptions&)
-TILED_COMMAND3(FillRect, const Rect&, const Pattern&, const DrawOptions&)
 TILED_COMMAND4(StrokeRect, const Rect&, const Pattern&, const StrokeOptions&, const DrawOptions&)
 TILED_COMMAND5(StrokeLine, const Point&, const Point&, const Pattern&, const StrokeOptions&, const DrawOptions&)
-TILED_COMMAND4(Stroke, const Path*, const Pattern&, const StrokeOptions&, const DrawOptions&)
-TILED_COMMAND3(Fill, const Path*, const Pattern&, const DrawOptions&)
 TILED_COMMAND5(FillGlyphs, ScaledFont*, const GlyphBuffer&, const Pattern&, const DrawOptions&, const GlyphRenderingOptions*)
 TILED_COMMAND3(Mask, const Pattern&, const Pattern&, const DrawOptions&)
-TILED_COMMAND1(PushClip, const Path*)
-TILED_COMMAND1(PushClipRect, const Rect&)
-TILED_COMMAND(PopClip)
+
+void
+DrawTargetTiled::PushClip(const Path* aPath)
+{
+  mClippedOutTilesStack.push_back(std::vector<uint32_t>());
+  std::vector<uint32_t>& clippedTiles = mClippedOutTilesStack.back();
+
+  Rect deviceRect = aPath->GetBounds(mTransform);
+
+  for (size_t i = 0; i < mTiles.size(); i++) {
+    if (!mTiles[i].mClippedOut) {
+      if (deviceRect.Intersects(Rect(mTiles[i].mTileOrigin.x,
+                                   mTiles[i].mTileOrigin.y,
+                                   mTiles[i].mDrawTarget->GetSize().width,
+                                   mTiles[i].mDrawTarget->GetSize().height))) {
+        mTiles[i].mDrawTarget->PushClip(aPath);
+      } else {
+        mTiles[i].mClippedOut = true;
+        clippedTiles.push_back(i);
+      }
+    }
+  }
+}
+
+void
+DrawTargetTiled::PushClipRect(const Rect& aRect)
+{
+  mClippedOutTilesStack.push_back(std::vector<uint32_t>());
+  std::vector<uint32_t>& clippedTiles = mClippedOutTilesStack.back();
+
+  Rect deviceRect = mTransform.TransformBounds(aRect);
+
+  for (size_t i = 0; i < mTiles.size(); i++) {
+    if (!mTiles[i].mClippedOut) {
+      if (deviceRect.Intersects(Rect(mTiles[i].mTileOrigin.x,
+                                   mTiles[i].mTileOrigin.y,
+                                   mTiles[i].mDrawTarget->GetSize().width,
+                                   mTiles[i].mDrawTarget->GetSize().height))) {
+        mTiles[i].mDrawTarget->PushClipRect(aRect);
+      } else {
+        mTiles[i].mClippedOut = true;
+        clippedTiles.push_back(i);
+      }
+    }
+  }
+}
+
+void
+DrawTargetTiled::PopClip()
+{
+  for (size_t i = 0; i < mTiles.size(); i++) {
+    if (!mTiles[i].mClippedOut) {
+      mTiles[i].mDrawTarget->PopClip();
+    }
+  }
+
+  std::vector<uint32_t>& clippedTiles = mClippedOutTilesStack.back();
+  for (size_t i = 0; i < clippedTiles.size(); i++) {
+    mTiles[clippedTiles[i]].mClippedOut = false;
+  }
+
+  mClippedOutTilesStack.pop_back();
+}
 
 void
 DrawTargetTiled::CopySurface(SourceSurface *aSurface,
                              const IntRect &aSourceRect,
                              const IntPoint &aDestination)
 {
   // CopySurface ignores the transform, account for that here.
   for (size_t i = 0; i < mTiles.size(); i++) {
@@ -193,10 +200,100 @@ DrawTargetTiled::SetTransform(const Matr
   for (size_t i = 0; i < mTiles.size(); i++) {
     Matrix mat = aTransform;
     mat.PostTranslate(Float(-mTiles[i].mTileOrigin.x), Float(-mTiles[i].mTileOrigin.y));
     mTiles[i].mDrawTarget->SetTransform(mat);
   }
   DrawTarget::SetTransform(aTransform);
 }
 
+void
+DrawTargetTiled::DrawSurface(SourceSurface* aSurface, const Rect& aDest, const Rect& aSource, const DrawSurfaceOptions& aSurfaceOptions, const DrawOptions& aDrawOptions)
+{
+  Rect deviceRect = mTransform.TransformBounds(aDest);
+  for (size_t i = 0; i < mTiles.size(); i++) {
+    if (!mTiles[i].mClippedOut &&
+        deviceRect.Intersects(Rect(mTiles[i].mTileOrigin.x,
+                                   mTiles[i].mTileOrigin.y,
+                                   mTiles[i].mDrawTarget->GetSize().width,
+                                   mTiles[i].mDrawTarget->GetSize().height))) {
+      mTiles[i].mDrawTarget->DrawSurface(aSurface, aDest, aSource, aSurfaceOptions, aDrawOptions);
+    }
+  }
+}
+
+void
+DrawTargetTiled::FillRect(const Rect& aRect, const Pattern& aPattern, const DrawOptions& aDrawOptions)
+{
+  Rect deviceRect = mTransform.TransformBounds(aRect);
+  for (size_t i = 0; i < mTiles.size(); i++) {
+    if (!mTiles[i].mClippedOut &&
+        deviceRect.Intersects(Rect(mTiles[i].mTileOrigin.x,
+                                   mTiles[i].mTileOrigin.y,
+                                   mTiles[i].mDrawTarget->GetSize().width,
+                                   mTiles[i].mDrawTarget->GetSize().height))) {
+      mTiles[i].mDrawTarget->FillRect(aRect, aPattern, aDrawOptions);
+    }
+  }
+}
+
+// The logic for this comes from _cairo_stroke_style_max_distance_from_path
+static Rect
+PathExtentsToMaxStrokeExtents(const StrokeOptions &aStrokeOptions,
+                              const Rect &aRect,
+                              const Matrix &aTransform)
+{
+  double styleExpansionFactor = 0.5f;
+
+  if (aStrokeOptions.mLineCap == CapStyle::SQUARE) {
+    styleExpansionFactor = M_SQRT1_2;
+  }
+
+  if (aStrokeOptions.mLineJoin == JoinStyle::MITER &&
+      styleExpansionFactor < M_SQRT2 * aStrokeOptions.mMiterLimit) {
+    styleExpansionFactor = M_SQRT2 * aStrokeOptions.mMiterLimit;
+  }
+
+  styleExpansionFactor *= aStrokeOptions.mLineWidth;
+
+  double dx = styleExpansionFactor * hypot(aTransform._11, aTransform._21);
+  double dy = styleExpansionFactor * hypot(aTransform._22, aTransform._12);
+
+  Rect result = aRect;
+  result.Inflate(dx, dy);
+  return result;
+}
+
+void
+DrawTargetTiled::Stroke(const Path* aPath, const Pattern& aPattern, const StrokeOptions& aStrokeOptions, const DrawOptions& aDrawOptions)
+{
+  // Approximate the stroke extents, since Path::GetStrokeExtents can be slow
+  Rect deviceRect = PathExtentsToMaxStrokeExtents(aStrokeOptions,
+                                                 aPath->GetBounds(mTransform),
+                                                 mTransform);
+  for (size_t i = 0; i < mTiles.size(); i++) {
+    if (!mTiles[i].mClippedOut &&
+        deviceRect.Intersects(Rect(mTiles[i].mTileOrigin.x,
+                                   mTiles[i].mTileOrigin.y,
+                                   mTiles[i].mDrawTarget->GetSize().width,
+                                   mTiles[i].mDrawTarget->GetSize().height))) {
+      mTiles[i].mDrawTarget->Stroke(aPath, aPattern, aStrokeOptions, aDrawOptions);
+    }
+  }
+}
+
+void
+DrawTargetTiled::Fill(const Path* aPath, const Pattern& aPattern, const DrawOptions& aDrawOptions)
+{
+  Rect deviceRect = aPath->GetBounds(mTransform);
+  for (size_t i = 0; i < mTiles.size(); i++) {
+    if (!mTiles[i].mClippedOut &&
+        deviceRect.Intersects(Rect(mTiles[i].mTileOrigin.x,
+                                   mTiles[i].mTileOrigin.y,
+                                   mTiles[i].mDrawTarget->GetSize().width,
+                                   mTiles[i].mDrawTarget->GetSize().height))) {
+      mTiles[i].mDrawTarget->Fill(aPath, aPattern, aDrawOptions);
+    }
+  }
+}
+
 }
 }
--- a/gfx/2d/DrawTargetTiled.h
+++ b/gfx/2d/DrawTargetTiled.h
@@ -9,16 +9,30 @@
 #include "2D.h"
 #include "Filters.h"
 
 #include <vector>
 
 namespace mozilla {
 namespace gfx {
 
+struct TileInternal : public Tile {
+  TileInternal()
+    : mClippedOut(false)
+  {}
+
+  explicit TileInternal(const Tile& aOther)
+    : Tile(aOther)
+    , mClippedOut(false)
+  {}
+
+  bool mClippedOut;
+};
+
+
 class DrawTargetTiled : public DrawTarget
 {
 public:
   DrawTargetTiled();
 
   bool Init(const TileSet& mTiles);
 
   virtual bool IsTiledDrawTarget() const { return true; }
@@ -125,16 +139,60 @@ public:
     return mTiles[0].mDrawTarget->CreateGradientStops(aStops, aNumStops, aExtendMode);
   }
   virtual TemporaryRef<FilterNode> CreateFilter(FilterType aType)
   {
     return mTiles[0].mDrawTarget->CreateFilter(aType);
   }
 
 private:
-  std::vector<Tile> mTiles;
+  std::vector<TileInternal> mTiles;
+  std::vector<std::vector<uint32_t> > mClippedOutTilesStack;
+  IntRect mRect;
+};
+
+class SnapshotTiled : public SourceSurface
+{
+public:
+  SnapshotTiled(const std::vector<TileInternal>& aTiles, const IntRect& aRect)
+    : mRect(aRect)
+  {
+    for (size_t i = 0; i < aTiles.size(); i++) {
+      mSnapshots.push_back(aTiles[i].mDrawTarget->Snapshot());
+      mOrigins.push_back(aTiles[i].mTileOrigin);
+    }
+  }
+
+  virtual SurfaceType GetType() const { return SurfaceType::TILED; }
+  virtual IntSize GetSize() const { return IntSize(mRect.XMost(), mRect.YMost()); }
+  virtual SurfaceFormat GetFormat() const { return mSnapshots[0]->GetFormat(); }
+
+  virtual TemporaryRef<DataSourceSurface> GetDataSurface()
+  {
+    RefPtr<DataSourceSurface> surf = Factory::CreateDataSourceSurface(GetSize(), GetFormat());
+
+    DataSourceSurface::MappedSurface mappedSurf;
+    surf->Map(DataSourceSurface::MapType::WRITE, &mappedSurf);
+
+    {
+      RefPtr<DrawTarget> dt =
+        Factory::CreateDrawTargetForData(BackendType::CAIRO, mappedSurf.mData,
+        GetSize(), mappedSurf.mStride, GetFormat());
+
+      for (size_t i = 0; i < mSnapshots.size(); i++) {
+        RefPtr<DataSourceSurface> dataSurf = mSnapshots[i]->GetDataSurface();
+        dt->CopySurface(dataSurf, IntRect(IntPoint(0, 0), mSnapshots[i]->GetSize()), mOrigins[i]);
+      }
+    }
+    surf->Unmap();
+
+    return surf.forget();
+  }
+
+  std::vector<RefPtr<SourceSurface>> mSnapshots;
+  std::vector<IntPoint> mOrigins;
   IntRect mRect;
 };
 
 }
 }
 
 #endif
--- a/gfx/2d/moz.build
+++ b/gfx/2d/moz.build
@@ -16,16 +16,17 @@ EXPORTS.mozilla.gfx += [
     'BasePoint3D.h',
     'BasePoint4D.h',
     'BaseRect.h',
     'BaseSize.h',
     'Blur.h',
     'BorrowedContext.h',
     'Coord.h',
     'DataSurfaceHelpers.h',
+    'DrawTargetTiled.h',
     'Filters.h',
     'Helpers.h',
     'Logging.h',
     'Matrix.h',
     'PathHelpers.h',
     'Point.h',
     'Rect.h',
     'Scale.h',
@@ -102,17 +103,16 @@ UNIFIED_SOURCES += [
     'DataSourceSurface.cpp',
     'DataSurfaceHelpers.cpp',
     'DrawEventRecorder.cpp',
     'DrawTarget.cpp',
     'DrawTargetCairo.cpp',
     'DrawTargetCapture.cpp',
     'DrawTargetDual.cpp',
     'DrawTargetRecording.cpp',
-    'DrawTargetTiled.cpp',
     'Factory.cpp',
     'FilterNodeSoftware.cpp',
     'FilterProcessing.cpp',
     'FilterProcessingScalar.cpp',
     'ImageScaling.cpp',
     'Matrix.cpp',
     'Path.cpp',
     'PathCairo.cpp',
@@ -121,16 +121,20 @@ UNIFIED_SOURCES += [
     'RecordedEvent.cpp',
     'Scale.cpp',
     'ScaledFontBase.cpp',
     'ScaledFontCairo.cpp',
     'SourceSurfaceCairo.cpp',
     'SourceSurfaceRawData.cpp',
 ]
 
+SOURCES += [
+    'DrawTargetTiled.cpp',
+]
+
 if CONFIG['MOZ_WIDGET_TOOLKIT'] == 'cocoa':
     SOURCES += [
         'MacIOSurface.cpp',
         'QuartzSupport.mm',
     ]
 
 FAIL_ON_WARNINGS = True
 
--- a/gfx/gl/SharedSurface.cpp
+++ b/gfx/gl/SharedSurface.cpp
@@ -1,17 +1,18 @@
 /* -*- Mode: c++; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40; -*- */
 /* This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #include "SharedSurface.h"
 
+#include "GLBlitHelper.h"
 #include "GLContext.h"
-#include "GLBlitHelper.h"
+#include "nsThreadUtils.h"
 #include "ScopedGLHelpers.h"
 #include "SharedSurfaceGL.h"
 
 namespace mozilla {
 namespace gl {
 
 /*static*/ void
 SharedSurface::ProdCopy(SharedSurface* src, SharedSurface* dest,
@@ -190,16 +191,34 @@ SharedSurface::ProdCopy(SharedSurface* s
     }
 
     MOZ_CRASH("Unhandled src->mAttachType.");
 }
 
 ////////////////////////////////////////////////////////////////////////
 // SharedSurface
 
+
+SharedSurface::SharedSurface(SharedSurfaceType type,
+                             AttachmentType attachType,
+                             GLContext* gl,
+                             const gfx::IntSize& size,
+                             bool hasAlpha)
+    : mType(type)
+    , mAttachType(attachType)
+    , mGL(gl)
+    , mSize(size)
+    , mHasAlpha(hasAlpha)
+    , mIsLocked(false)
+#ifdef DEBUG
+    , mOwningThread(NS_GetCurrentThread())
+#endif
+{
+}
+
 void
 SharedSurface::LockProd()
 {
     MOZ_ASSERT(!mIsLocked);
 
     LockProdImpl();
 
     mGL->LockSurface(this);
@@ -213,16 +232,39 @@ SharedSurface::UnlockProd()
         return;
 
     UnlockProdImpl();
 
     mGL->UnlockSurface(this);
     mIsLocked = false;
 }
 
+void
+SharedSurface::Fence_ContentThread()
+{
+    MOZ_ASSERT(NS_GetCurrentThread() == mOwningThread);
+    Fence_ContentThread_Impl();
+}
+
+bool
+SharedSurface::WaitSync_ContentThread()
+{
+    MOZ_ASSERT(NS_GetCurrentThread() == mOwningThread);
+    return WaitSync_ContentThread_Impl();
+}
+
+bool
+SharedSurface::PollSync_ContentThread()
+{
+    MOZ_ASSERT(NS_GetCurrentThread() == mOwningThread);
+    return PollSync_ContentThread_Impl();
+}
+
+
+
 ////////////////////////////////////////////////////////////////////////
 // SurfaceFactory
 
 static void
 ChooseBufferBits(const SurfaceCaps& caps,
                  SurfaceCaps* const out_drawCaps,
                  SurfaceCaps* const out_readCaps)
 {
--- a/gfx/gl/SharedSurface.h
+++ b/gfx/gl/SharedSurface.h
@@ -16,21 +16,24 @@
 #define SHARED_SURFACE_H_
 
 #include <queue>
 #include <stdint.h>
 
 #include "GLContextTypes.h"
 #include "GLDefs.h"
 #include "mozilla/Attributes.h"
+#include "mozilla/DebugOnly.h"
 #include "mozilla/gfx/Point.h"
 #include "mozilla/UniquePtr.h"
 #include "mozilla/WeakPtr.h"
 #include "SurfaceTypes.h"
 
+class nsIThread;
+
 namespace mozilla {
 namespace gl {
 
 class GLContext;
 class SurfaceFactory;
 
 class SharedSurface
 {
@@ -40,30 +43,23 @@ public:
 
     const SharedSurfaceType mType;
     const AttachmentType mAttachType;
     GLContext* const mGL;
     const gfx::IntSize mSize;
     const bool mHasAlpha;
 protected:
     bool mIsLocked;
+    DebugOnly<nsIThread* const> mOwningThread;
 
     SharedSurface(SharedSurfaceType type,
                   AttachmentType attachType,
                   GLContext* gl,
                   const gfx::IntSize& size,
-                  bool hasAlpha)
-        : mType(type)
-        , mAttachType(attachType)
-        , mGL(gl)
-        , mSize(size)
-        , mHasAlpha(hasAlpha)
-        , mIsLocked(false)
-    {
-    }
+                  bool hasAlpha);
 
 public:
     virtual ~SharedSurface() {
     }
 
     bool IsLocked() const {
         return mIsLocked;
     }
@@ -79,16 +75,34 @@ protected:
     virtual void LockProdImpl() = 0;
     virtual void UnlockProdImpl() = 0;
 
 public:
     virtual void Fence() = 0;
     virtual bool WaitSync() = 0;
     virtual bool PollSync() = 0;
 
+    // Use these if you can. They can only be called from the Content
+    // thread, though!
+    void Fence_ContentThread();
+    bool WaitSync_ContentThread();
+    bool PollSync_ContentThread();
+
+protected:
+    virtual void Fence_ContentThread_Impl() {
+        Fence();
+    }
+    virtual bool WaitSync_ContentThread_Impl() {
+        return WaitSync();
+    }
+    virtual bool PollSync_ContentThread_Impl() {
+        return PollSync();
+    }
+
+public:
     // This function waits until the buffer is no longer being used.
     // To optimize the performance, some implementaions recycle SharedSurfaces
     // even when its buffer is still being used.
     virtual void WaitForBufferOwnership() {}
 
     // For use when AttachType is correct.
     virtual GLenum ProdTextureTarget() const {
         MOZ_ASSERT(mAttachType == AttachmentType::GLTexture);
--- a/gfx/gl/SharedSurfaceANGLE.cpp
+++ b/gfx/gl/SharedSurfaceANGLE.cpp
@@ -12,20 +12,46 @@ namespace mozilla {
 namespace gl {
 
 EGLDisplay
 SharedSurface_ANGLEShareHandle::Display()
 {
     return mEGL->Display();
 }
 
+SharedSurface_ANGLEShareHandle::SharedSurface_ANGLEShareHandle(GLContext* gl,
+                                                               GLLibraryEGL* egl,
+                                                               const gfx::IntSize& size,
+                                                               bool hasAlpha,
+                                                               EGLContext context,
+                                                               EGLSurface pbuffer,
+                                                               HANDLE shareHandle,
+                                                               GLuint fence)
+    : SharedSurface(SharedSurfaceType::EGLSurfaceANGLE,
+                    AttachmentType::Screen,
+                    gl,
+                    size,
+                    hasAlpha)
+    , mEGL(egl)
+    , mContext(context)
+    , mPBuffer(pbuffer)
+    , mShareHandle(shareHandle)
+    , mFence(fence)
+{
+}
+
 
 SharedSurface_ANGLEShareHandle::~SharedSurface_ANGLEShareHandle()
 {
     mEGL->fDestroySurface(Display(), mPBuffer);
+
+    if (mFence) {
+        mGL->MakeCurrent();
+        mGL->fDeleteFences(1, &mFence);
+    }
 }
 
 void
 SharedSurface_ANGLEShareHandle::LockProdImpl()
 {
     GLContextEGL::Cast(mGL)->SetEGLSurfaceOverride(mPBuffer);
 }
 
@@ -35,16 +61,64 @@ SharedSurface_ANGLEShareHandle::UnlockPr
 }
 
 void
 SharedSurface_ANGLEShareHandle::Fence()
 {
     mGL->fFinish();
 }
 
+bool
+SharedSurface_ANGLEShareHandle::WaitSync()
+{
+    return true;
+}
+
+bool
+SharedSurface_ANGLEShareHandle::PollSync()
+{
+    return true;
+}
+
+void
+SharedSurface_ANGLEShareHandle::Fence_ContentThread_Impl()
+{
+    if (mFence) {
+        MOZ_ASSERT(mGL->IsExtensionSupported(GLContext::NV_fence));
+        mGL->fSetFence(mFence, LOCAL_GL_ALL_COMPLETED_NV);
+        mGL->fFlush();
+        return;
+    }
+
+    Fence();
+}
+
+bool
+SharedSurface_ANGLEShareHandle::WaitSync_ContentThread_Impl()
+{
+    if (mFence) {
+        mGL->MakeCurrent();
+        mGL->fFinishFence(mFence);
+        return true;
+    }
+
+    return WaitSync();
+}
+
+bool
+SharedSurface_ANGLEShareHandle::PollSync_ContentThread_Impl()
+{
+    if (mFence) {
+        mGL->MakeCurrent();
+        return mGL->fTestFence(mFence);
+    }
+
+    return PollSync();
+}
+
 static void
 FillPBufferAttribs_ByBits(nsTArray<EGLint>& aAttrs,
                           int redBits, int greenBits,
                           int blueBits, int alphaBits,
                           int depthBits, int stencilBits)
 {
     aAttrs.Clear();
 
@@ -194,19 +268,25 @@ SharedSurface_ANGLEShareHandle::Create(G
                                              pbuffer,
                                              LOCAL_EGL_D3D_TEXTURE_2D_SHARE_HANDLE_ANGLE,
                                              &shareHandle);
     if (!ok) {
         egl->fDestroySurface(egl->Display(), pbuffer);
         return nullptr;
     }
 
+    GLuint fence = 0;
+    if (gl->IsExtensionSupported(GLContext::NV_fence)) {
+        gl->MakeCurrent();
+        gl->fGenFences(1, &fence);
+    }
+
     typedef SharedSurface_ANGLEShareHandle ptrT;
     UniquePtr<ptrT> ret( new ptrT(gl, egl, size, hasAlpha, context,
-                                  pbuffer, shareHandle) );
+                                  pbuffer, shareHandle, fence) );
     return Move(ret);
 }
 
 /*static*/ UniquePtr<SurfaceFactory_ANGLEShareHandle>
 SurfaceFactory_ANGLEShareHandle::Create(GLContext* gl,
                                         const SurfaceCaps& caps)
 {
     GLLibraryEGL* egl = &sEGLLibrary;
--- a/gfx/gl/SharedSurfaceANGLE.h
+++ b/gfx/gl/SharedSurfaceANGLE.h
@@ -32,46 +32,42 @@ public:
         return (SharedSurface_ANGLEShareHandle*)surf;
     }
 
 protected:
     GLLibraryEGL* const mEGL;
     const EGLContext mContext;
     const EGLSurface mPBuffer;
     const HANDLE mShareHandle;
+    const GLuint mFence;
 
     SharedSurface_ANGLEShareHandle(GLContext* gl,
                                    GLLibraryEGL* egl,
                                    const gfx::IntSize& size,
                                    bool hasAlpha,
                                    EGLContext context,
                                    EGLSurface pbuffer,
-                                   HANDLE shareHandle)
-        : SharedSurface(SharedSurfaceType::EGLSurfaceANGLE,
-                        AttachmentType::Screen,
-                        gl,
-                        size,
-                        hasAlpha)
-        , mEGL(egl)
-        , mContext(context)
-        , mPBuffer(pbuffer)
-        , mShareHandle(shareHandle)
-    {}
+                                   HANDLE shareHandle,
+                                   GLuint fence);
 
     EGLDisplay Display();
 
 public:
     virtual ~SharedSurface_ANGLEShareHandle();
 
     virtual void LockProdImpl() MOZ_OVERRIDE;
     virtual void UnlockProdImpl() MOZ_OVERRIDE;
 
     virtual void Fence() MOZ_OVERRIDE;
-    virtual bool WaitSync() MOZ_OVERRIDE { return true; } // Fence is glFinish.
-    virtual bool PollSync() MOZ_OVERRIDE { return true; }
+    virtual bool WaitSync() MOZ_OVERRIDE;
+    virtual bool PollSync() MOZ_OVERRIDE;
+
+    virtual void Fence_ContentThread_Impl() MOZ_OVERRIDE;
+    virtual bool WaitSync_ContentThread_Impl() MOZ_OVERRIDE;
+    virtual bool PollSync_ContentThread_Impl() MOZ_OVERRIDE;
 
     // Implementation-specific functions below:
     HANDLE GetShareHandle() {
         return mShareHandle;
     }
 };
 
 
--- a/gfx/gl/SharedSurfaceGL.cpp
+++ b/gfx/gl/SharedSurfaceGL.cpp
@@ -1,20 +1,20 @@
 /* -*- Mode: c++; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40; -*- */
 /* This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #include "SharedSurfaceGL.h"
 
+#include "GLBlitHelper.h"
 #include "GLContext.h"
-#include "GLBlitHelper.h"
+#include "GLReadTexImageHelper.h"
+#include "mozilla/gfx/2D.h"
 #include "ScopedGLHelpers.h"
-#include "mozilla/gfx/2D.h"
-#include "GLReadTexImageHelper.h"
 
 namespace mozilla {
 namespace gl {
 
 using gfx::IntSize;
 using gfx::SurfaceFormat;
 
 /*static*/ UniquePtr<SharedSurface_Basic>
@@ -65,16 +65,17 @@ SharedSurface_Basic::SharedSurface_Basic
                                          GLuint tex)
     : SharedSurface(SharedSurfaceType::Basic,
                     AttachmentType::GLTexture,
                     gl,
                     size,
                     hasAlpha)
     , mTex(tex)
     , mFB(0)
+    , mIsDataCurrent(false)
 {
     mGL->MakeCurrent();
     mGL->fGenFramebuffers(1, &mFB);
 
     ScopedBindFramebuffer autoFB(mGL, mFB);
     mGL->fFramebufferTexture2D(LOCAL_GL_FRAMEBUFFER,
                               LOCAL_GL_COLOR_ATTACHMENT0,
                               LOCAL_GL_TEXTURE_2D,
@@ -110,16 +111,61 @@ SharedSurface_Basic::Fence()
     // The constructor can fail to get us mData, we should deal with it:
     if (NS_WARN_IF(!mData)) {
         return;
     }
 
     mGL->MakeCurrent();
     ScopedBindFramebuffer autoFB(mGL, mFB);
     ReadPixelsIntoDataSurface(mGL, mData);
+    mIsDataCurrent = true;
+}
+
+bool
+SharedSurface_Basic::WaitSync()
+{
+    MOZ_ASSERT(mIsDataCurrent);
+    return true;
+}
+
+bool
+SharedSurface_Basic::PollSync()
+{
+    MOZ_ASSERT(mIsDataCurrent);
+    return true;
+}
+
+void
+SharedSurface_Basic::Fence_ContentThread_Impl()
+{
+    mIsDataCurrent = false;
+}
+
+bool
+SharedSurface_Basic::WaitSync_ContentThread_Impl()
+{
+    if (!mIsDataCurrent) {
+        mGL->MakeCurrent();
+        ScopedBindFramebuffer autoFB(mGL, mFB);
+        ReadPixelsIntoDataSurface(mGL, mData);
+        mIsDataCurrent = true;
+    }
+    return true;
+}
+
+bool
+SharedSurface_Basic::PollSync_ContentThread_Impl()
+{
+    if (!mIsDataCurrent) {
+        mGL->MakeCurrent();
+        ScopedBindFramebuffer autoFB(mGL, mFB);
+        ReadPixelsIntoDataSurface(mGL, mData);
+        mIsDataCurrent = true;
+    }
+    return true;
 }
 
 ////////////////////////////////////////////////////////////////////////
 // SharedSurface_GLTexture
 
 /*static*/ UniquePtr<SharedSurface_GLTexture>
 SharedSurface_GLTexture::Create(GLContext* prodGL,
                                 GLContext* consGL,
--- a/gfx/gl/SharedSurfaceGL.h
+++ b/gfx/gl/SharedSurfaceGL.h
@@ -11,17 +11,16 @@
 #include "SurfaceTypes.h"
 #include "GLContextTypes.h"
 #include "nsAutoPtr.h"
 #include "gfxTypes.h"
 #include "mozilla/Mutex.h"
 
 #include <queue>
 
-// Forwards:
 namespace mozilla {
     namespace gl {
         class GLContext;
     }
     namespace gfx {
         class DataSourceSurface;
     }
 }
@@ -43,39 +42,39 @@ public:
         MOZ_ASSERT(surf->mType == SharedSurfaceType::Basic);
 
         return (SharedSurface_Basic*)surf;
     }
 
 protected:
     const GLuint mTex;
     GLuint mFB;
-
     RefPtr<gfx::DataSourceSurface> mData;
+    bool mIsDataCurrent;
 
     SharedSurface_Basic(GLContext* gl,
                         const gfx::IntSize& size,
                         bool hasAlpha,
                         gfx::SurfaceFormat format,
                         GLuint tex);
 
 public:
     virtual ~SharedSurface_Basic();
 
     virtual void LockProdImpl() MOZ_OVERRIDE {}
     virtual void UnlockProdImpl() MOZ_OVERRIDE {}
 
 
     virtual void Fence() MOZ_OVERRIDE;
+    virtual bool WaitSync() MOZ_OVERRIDE;
+    virtual bool PollSync() MOZ_OVERRIDE;
 
-    virtual bool WaitSync() MOZ_OVERRIDE {
-        // Since we already store the data in Fence, we're always done already.
-        return true;
-    }
-    virtual bool PollSync() MOZ_OVERRIDE { return true; }
+    virtual void Fence_ContentThread_Impl() MOZ_OVERRIDE;
+    virtual bool WaitSync_ContentThread_Impl() MOZ_OVERRIDE;
+    virtual bool PollSync_ContentThread_Impl() MOZ_OVERRIDE;
 
     virtual GLuint ProdTexture() MOZ_OVERRIDE {
         return mTex;
     }
 
     // Implementation-specific functions below:
     gfx::DataSourceSurface* GetData() {
         return mData;
--- a/gfx/layers/client/ClientThebesLayer.cpp
+++ b/gfx/layers/client/ClientThebesLayer.cpp
@@ -158,17 +158,17 @@ ClientLayerManager::CreateThebesLayer()
 already_AddRefed<ThebesLayer>
 ClientLayerManager::CreateThebesLayerWithHint(ThebesLayerCreationHint aHint)
 {
   NS_ASSERTION(InConstruction(), "Only allowed in construction phase");
   if (
 #ifdef MOZ_B2G
       aHint == SCROLLABLE &&
 #endif
-      gfxPrefs::LayersTilesEnabled() &&
+      gfxPlatform::GetPlatform()->UseTiling() &&
       (AsShadowForwarder()->GetCompositorBackendType() == LayersBackend::LAYERS_OPENGL ||
        AsShadowForwarder()->GetCompositorBackendType() == LayersBackend::LAYERS_D3D9 ||
        AsShadowForwarder()->GetCompositorBackendType() == LayersBackend::LAYERS_D3D11)) {
     if (gfxPrefs::LayersUseSimpleTiles()) {
       nsRefPtr<SimpleClientTiledThebesLayer> layer =
         new SimpleClientTiledThebesLayer(this, aHint);
       CREATE_SHADOW(Thebes);
       return layer.forget();
--- a/gfx/layers/client/TextureClient.cpp
+++ b/gfx/layers/client/TextureClient.cpp
@@ -684,16 +684,17 @@ BufferTextureClient::AllocateForSurface(
 
 gfx::DrawTarget*
 BufferTextureClient::BorrowDrawTarget()
 {
   MOZ_ASSERT(IsValid());
   MOZ_ASSERT(mLocked, "BorrowDrawTarget should be called on locked textures only");
 
   if (mDrawTarget) {
+    mDrawTarget->SetTransform(Matrix());
     return mDrawTarget;
   }
 
   ImageDataSerializer serializer(GetBuffer(), GetBufferSize());
   if (!serializer.IsValid()) {
     return nullptr;
   }
 
@@ -733,17 +734,16 @@ BufferTextureClient::Unlock()
 
   if (mReadbackSink) {
     RefPtr<SourceSurface> snapshot = mDrawTarget->Snapshot();
     RefPtr<DataSourceSurface> dataSurf = snapshot->GetDataSurface();
     mReadbackSink->ProcessReadback(dataSurf);
   }
 
   mDrawTarget->Flush();
-  mDrawTarget = nullptr;
 }
 
 bool
 BufferTextureClient::UpdateYCbCr(const PlanarYCbCrData& aData)
 {
   MOZ_ASSERT(mLocked);
   MOZ_ASSERT(mFormat == gfx::SurfaceFormat::YUV, "This textureClient can only use YCbCr data");
   MOZ_ASSERT(!IsImmutable());
--- a/gfx/layers/composite/LayerManagerComposite.cpp
+++ b/gfx/layers/composite/LayerManagerComposite.cpp
@@ -346,18 +346,17 @@ LayerManagerComposite::RenderDebugOverla
       mFPS = MakeUnique<FPSState>();
     }
 
 #ifdef ANDROID
     // Draw a translation delay warning overlay
     int width;
     int border;
     float alpha = 1;
-    if ((now - mWarnTime).ToMilliseconds() < 150) {
-      printf_stderr("Draw\n");
+    if ((now - mWarnTime).ToMilliseconds() < kVisualWarningDuration) {
       EffectChain effects;
 
       // Black blorder
       border = 4;
       width = 6;
       effects.mPrimaryEffect = new EffectSolidColor(gfx::Color(0, 0, 0, 1));
       mCompositor->DrawQuad(gfx::Rect(border, border, aBounds.width - 2 * border, width),
                             aBounds, effects, alpha, gfx::Matrix4x4());
--- a/gfx/layers/composite/LayerManagerComposite.h
+++ b/gfx/layers/composite/LayerManagerComposite.h
@@ -62,16 +62,20 @@ class LayerComposite;
 class RefLayerComposite;
 class SurfaceDescriptor;
 class ThebesLayerComposite;
 class TiledLayerComposer;
 class TextRenderer;
 class CompositingRenderTarget;
 struct FPSState;
 
+static const int kVisualWarningTrigger = 200; // ms
+static const int kVisualWarningMax = 1000; // ms
+static const int kVisualWarningDuration = 150; // ms
+
 class LayerManagerComposite MOZ_FINAL : public LayerManager
 {
   typedef mozilla::gfx::DrawTarget DrawTarget;
   typedef mozilla::gfx::IntSize IntSize;
   typedef mozilla::gfx::SurfaceFormat SurfaceFormat;
 
 public:
   explicit LayerManagerComposite(Compositor* aCompositor);
@@ -240,18 +244,19 @@ public:
   TextRenderer* GetTextRenderer() { return mTextRenderer; }
 
   /**
    * Add an on frame warning.
    * @param severity ranges from 0 to 1. It's used to compute the warning color.
    */
   void VisualFrameWarning(float severity) {
     mozilla::TimeStamp now = TimeStamp::Now();
-    if (severity > mWarningLevel ||
-        mWarnTime + TimeDuration::FromMilliseconds(1500) < now) {
+    if (mWarnTime.IsNull() ||
+        severity > mWarningLevel ||
+        mWarnTime + TimeDuration::FromMilliseconds(kVisualWarningDuration) < now) {
       mWarnTime = now;
       mWarningLevel = severity;
     }
   }
 
 private:
   /** Region we're clipping our current drawing to. */
   nsIntRegion mClippingRegion;
--- a/gfx/layers/ipc/ImageBridgeChild.h
+++ b/gfx/layers/ipc/ImageBridgeChild.h
@@ -96,19 +96,19 @@ bool InImageBridgeChildThread();
  * frame before the first layer transaction that will pass the container ID to the
  * CompositableHost happens. In this (unlikely) case the layer is not composited
  * until the layer transaction happens. This means this scenario is not harmful.
  *
  * Since sending an image through imageBridge triggers compositing, the main thread is
  * not used at all (except for the very first transaction that provides the
  * CompositableHost with an AsyncID).
  */
-class ImageBridgeChild : public PImageBridgeChild
-                       , public CompositableForwarder
-                       , public AsyncTransactionTrackersHolder
+class ImageBridgeChild MOZ_FINAL : public PImageBridgeChild
+                                 , public CompositableForwarder
+                                 , public AsyncTransactionTrackersHolder
 {
   friend class ImageContainer;
   typedef InfallibleTArray<AsyncParentMessageData> AsyncParentMessageArray;
 public:
 
   /**
    * Creates the image bridge with a dedicated thread for ImageBridgeChild.
    *
--- a/gfx/layers/ipc/LayerTransactionParent.cpp
+++ b/gfx/layers/ipc/LayerTransactionParent.cpp
@@ -566,18 +566,19 @@ LayerTransactionParent::RecvUpdate(const
   int compositeTime = (int)(mozilla::TimeStamp::Now() - updateStart).ToMilliseconds();
   if (compositeTime > 15) {
     printf_stderr("Compositor: Layers update took %i ms (blocking gecko).\n", compositeTime);
   }
 #endif
 
   TimeDuration latency = TimeStamp::Now() - aTransactionStart;
   // Theshold is 200ms to trigger, 1000ms to hit red
-  if (latency > TimeDuration::FromMilliseconds(200)) {
-    float severity = (latency - TimeDuration::FromMilliseconds(200)).ToMilliseconds() / 800;
+  if (latency > TimeDuration::FromMilliseconds(kVisualWarningTrigger)) {
+    float severity = (latency - TimeDuration::FromMilliseconds(kVisualWarningTrigger)).ToMilliseconds() /
+                       (kVisualWarningMax - kVisualWarningTrigger);
     if (severity > 1.f) {
       severity = 1.f;
     }
     mLayerManager->VisualFrameWarning(severity);
   }
 
   return true;
 }
--- a/gfx/skia/trunk/include/config/SkUserConfig.h
+++ b/gfx/skia/trunk/include/config/SkUserConfig.h
@@ -199,9 +199,11 @@
 #define SK_B32_SHIFT 0
 
 #define SK_ALLOW_STATIC_GLOBAL_INITIALIZERS 0
 
 #define SK_SUPPORT_LEGACY_GETDEVICE
 #define SK_SUPPORT_LEGACY_GETTOPDEVICE
 #define SK_IGNORE_ETC1_SUPPORT
 
+#define SK_RASTERIZE_EVEN_ROUNDING
+
 #endif
--- a/gfx/skia/trunk/src/core/SkEdge.cpp
+++ b/gfx/skia/trunk/src/core/SkEdge.cpp
@@ -31,21 +31,28 @@ static inline SkFixed SkFDot6ToFixedDiv2
 
 /////////////////////////////////////////////////////////////////////////
 
 int SkEdge::setLine(const SkPoint& p0, const SkPoint& p1, const SkIRect* clip,
                     int shift) {
     SkFDot6 x0, y0, x1, y1;
 
     {
+#ifdef SK_RASTERIZE_EVEN_ROUNDING
+        x0 = SkScalarRoundToFDot6(p0.fX, shift);
+        y0 = SkScalarRoundToFDot6(p0.fY, shift);
+        x1 = SkScalarRoundToFDot6(p1.fX, shift);
+        y1 = SkScalarRoundToFDot6(p1.fY, shift);
+#else
         float scale = float(1 << (shift + 6));
         x0 = int(p0.fX * scale);
         y0 = int(p0.fY * scale);
         x1 = int(p1.fX * scale);
         y1 = int(p1.fY * scale);
+#endif
     }
 
     int winding = 1;
 
     if (y0 > y1) {
         SkTSwap(x0, x1);
         SkTSwap(y0, y1);
         winding = -1;
@@ -166,23 +173,32 @@ static inline int diff_to_shift(SkFDot6 
     return (32 - SkCLZ(dist)) >> 1;
 }
 
 int SkQuadraticEdge::setQuadratic(const SkPoint pts[3], int shift)
 {
     SkFDot6 x0, y0, x1, y1, x2, y2;
 
     {
+#ifdef SK_RASTERIZE_EVEN_ROUNDING
+        x0 = SkScalarRoundToFDot6(pts[0].fX, shift);
+        y0 = SkScalarRoundToFDot6(pts[0].fY, shift);
+        x1 = SkScalarRoundToFDot6(pts[1].fX, shift);
+        y1 = SkScalarRoundToFDot6(pts[1].fY, shift);
+        x2 = SkScalarRoundToFDot6(pts[2].fX, shift);
+        y2 = SkScalarRoundToFDot6(pts[2].fY, shift);
+#else
         float scale = float(1 << (shift + 6));
         x0 = int(pts[0].fX * scale);
         y0 = int(pts[0].fY * scale);
         x1 = int(pts[1].fX * scale);
         y1 = int(pts[1].fY * scale);
         x2 = int(pts[2].fX * scale);
         y2 = int(pts[2].fY * scale);
+#endif
     }
 
     int winding = 1;
     if (y0 > y2)
     {
         SkTSwap(x0, x2);
         SkTSwap(y0, y2);
         winding = -1;
@@ -316,25 +332,36 @@ static SkFDot6 cubic_delta_from_line(SkF
     return SkMax32(SkAbs32(oneThird), SkAbs32(twoThird));
 }
 
 int SkCubicEdge::setCubic(const SkPoint pts[4], const SkIRect* clip, int shift)
 {
     SkFDot6 x0, y0, x1, y1, x2, y2, x3, y3;
 
     {
+#ifdef SK_RASTERIZE_EVEN_ROUNDING
+        x0 = SkScalarRoundToFDot6(pts[0].fX, shift);
+        y0 = SkScalarRoundToFDot6(pts[0].fY, shift);
+        x1 = SkScalarRoundToFDot6(pts[1].fX, shift);
+        y1 = SkScalarRoundToFDot6(pts[1].fY, shift);
+        x2 = SkScalarRoundToFDot6(pts[2].fX, shift);
+        y2 = SkScalarRoundToFDot6(pts[2].fY, shift);
+        x3 = SkScalarRoundToFDot6(pts[3].fX, shift);
+        y3 = SkScalarRoundToFDot6(pts[3].fY, shift);
+#else
         float scale = float(1 << (shift + 6));
         x0 = int(pts[0].fX * scale);
         y0 = int(pts[0].fY * scale);
         x1 = int(pts[1].fX * scale);
         y1 = int(pts[1].fY * scale);
         x2 = int(pts[2].fX * scale);
         y2 = int(pts[2].fY * scale);
         x3 = int(pts[3].fX * scale);
         y3 = int(pts[3].fY * scale);
+#endif
     }
 
     int winding = 1;
     if (y0 > y3)
     {
         SkTSwap(x0, x3);
         SkTSwap(x1, x2);
         SkTSwap(y0, y3);
--- a/gfx/skia/trunk/src/core/SkEdge.h
+++ b/gfx/skia/trunk/src/core/SkEdge.h
@@ -84,21 +84,28 @@ struct SkCubicEdge : public SkEdge {
     int setCubic(const SkPoint pts[4], const SkIRect* clip, int shiftUp);
     int updateCubic();
 };
 
 int SkEdge::setLine(const SkPoint& p0, const SkPoint& p1, int shift) {
     SkFDot6 x0, y0, x1, y1;
 
     {
+#ifdef SK_RASTERIZE_EVEN_ROUNDING
+        x0 = SkScalarRoundToFDot6(p0.fX, shift);
+        y0 = SkScalarRoundToFDot6(p0.fY, shift);
+        x1 = SkScalarRoundToFDot6(p1.fX, shift);
+        y1 = SkScalarRoundToFDot6(p1.fY, shift);
+#else
         float scale = float(1 << (shift + 6));
         x0 = int(p0.fX * scale);
         y0 = int(p0.fY * scale);
         x1 = int(p1.fX * scale);
         y1 = int(p1.fY * scale);
+#endif
     }
 
     int winding = 1;
 
     if (y0 > y1) {
         SkTSwap(x0, x1);
         SkTSwap(y0, y1);
         winding = -1;
--- a/gfx/skia/trunk/src/core/SkFDot6.h
+++ b/gfx/skia/trunk/src/core/SkFDot6.h
@@ -10,16 +10,38 @@
 #ifndef SkFDot6_DEFINED
 #define SkFDot6_DEFINED
 
 #include "SkScalar.h"
 #include "SkMath.h"
 
 typedef int32_t SkFDot6;
 
+/* This uses the magic number approach suggested here:
+ * http://stereopsis.com/sree/fpu2006.html and used in
+ * _cairo_fixed_from_double. It does banker's rounding
+ * (i.e. round to nearest even)
+ */
+inline SkFDot6 SkScalarRoundToFDot6(SkScalar x, int shift = 0)
+{
+    union {
+        double  fDouble;
+        int32_t fBits[2];
+    } tmp;
+    int fractionalBits = 6 + shift;
+    double magic = (1LL << (52 - (fractionalBits))) * 1.5;
+
+    tmp.fDouble = SkScalarToDouble(x) + magic;
+#ifdef SK_CPU_BENDIAN
+    return tmp.fBits[1];
+#else
+    return tmp.fBits[0];
+#endif
+}
+
 #define SK_FDot6One         (64)
 #define SK_FDot6Half        (32)
 
 #ifdef SK_DEBUG
     inline SkFDot6 SkIntToFDot6(S16CPU x) {
         SkASSERT(SkToS16(x) == x);
         return x << 6;
     }
--- a/gfx/src/nsDeviceContext.cpp
+++ b/gfx/src/nsDeviceContext.cpp
@@ -394,16 +394,20 @@ nsDeviceContext::CreateRenderingContext(
     }
 #endif
     nsRefPtr<nsRenderingContext> pContext = new nsRenderingContext();
 
     RefPtr<gfx::DrawTarget> dt =
       gfxPlatform::GetPlatform()->CreateDrawTargetForSurface(printingSurface,
                                                              gfx::IntSize(mWidth, mHeight));
 
+#ifdef XP_MACOSX
+    dt->AddUserData(&gfxContext::sDontUseAsSourceKey, dt, nullptr);
+#endif
+
     pContext->Init(this, dt);
     pContext->ThebesContext()->SetFlag(gfxContext::FLAG_DISABLE_SNAPPING);
     pContext->Scale(mPrintingScale, mPrintingScale);
 
     return pContext.forget();
 }
 
 nsresult
--- a/gfx/thebes/gfxContext.cpp
+++ b/gfx/thebes/gfxContext.cpp
@@ -19,16 +19,17 @@
 #include "gfxUtils.h"
 #include "gfxASurface.h"
 #include "gfxPattern.h"
 #include "gfxPlatform.h"
 #include "gfxTeeSurface.h"
 #include "GeckoProfiler.h"
 #include "gfx2DGlue.h"
 #include "mozilla/gfx/PathHelpers.h"
+#include "mozilla/gfx/DrawTargetTiled.h"
 #include <algorithm>
 
 #if CAIRO_HAS_DWRITE_FONT
 #include "gfxWindowsPlatform.h"
 #endif
 
 using namespace mozilla;
 using namespace mozilla::gfx;
@@ -1113,22 +1114,42 @@ gfxContext::PushGroupAndCopyBackground(g
     DrawTarget *oldDT = mDT;
     RefPtr<SourceSurface> source = mDT->Snapshot();
     Point oldDeviceOffset = CurrentState().deviceOffset;
 
     PushNewDT(gfxContentType::COLOR);
 
     Point offset = CurrentState().deviceOffset - oldDeviceOffset;
     Rect surfRect(0, 0, Float(mDT->GetSize().width), Float(mDT->GetSize().height));
-    Rect sourceRect = surfRect;
-    sourceRect.x += offset.x;
-    sourceRect.y += offset.y;
+    Rect sourceRect = surfRect + offset;
 
     mDT->SetTransform(Matrix());
-    mDT->DrawSurface(source, surfRect, sourceRect);
+
+    // XXX: It's really sad that we have to do this (for performance).
+    // Once DrawTarget gets a PushLayer API we can implement this within
+    // DrawTargetTiled.
+    if (source->GetType() == SurfaceType::TILED) {
+      SnapshotTiled *sourceTiled = static_cast<SnapshotTiled*>(source.get());
+      for (uint32_t i = 0; i < sourceTiled->mSnapshots.size(); i++) {
+        Rect tileSourceRect = sourceRect.Intersect(Rect(sourceTiled->mOrigins[i].x,
+                                                        sourceTiled->mOrigins[i].y,
+                                                        sourceTiled->mSnapshots[i]->GetSize().width,
+                                                        sourceTiled->mSnapshots[i]->GetSize().height));
+
+        if (tileSourceRect.IsEmpty()) {
+          continue;
+        }
+        Rect tileDestRect = tileSourceRect - offset;
+        tileSourceRect -= sourceTiled->mOrigins[i];
+
+        mDT->DrawSurface(sourceTiled->mSnapshots[i], tileDestRect, tileSourceRect);
+      }
+    } else {
+      mDT->DrawSurface(source, surfRect, sourceRect);
+    }
     mDT->SetOpaqueRect(oldDT->GetOpaqueRect());
 
     PushClipsToDT(mDT);
     mDT->SetTransform(GetDTTransform());
     return;
   }
   PushGroup(content);
 }
--- a/gfx/thebes/gfxPlatform.cpp
+++ b/gfx/thebes/gfxPlatform.cpp
@@ -900,16 +900,19 @@ gfxPlatform::GetSkiaGLGlue()
 void
 gfxPlatform::PurgeSkiaCache()
 {
 #ifdef USE_SKIA_GPU
   if (!mSkiaGlue)
       return;
 
   mSkiaGlue->GetGrContext()->freeGpuResources();
+  // GrContext::flush() doesn't call glFlush. Call it here.
+  mSkiaGlue->GetGLContext()->MakeCurrent();
+  mSkiaGlue->GetGLContext()->fFlush();
 #endif
 }
 
 TemporaryRef<DrawTarget>
 gfxPlatform::CreateDrawTargetForBackend(BackendType aBackend, const IntSize& aSize, SurfaceFormat aFormat)
 {
   // There is a bunch of knowledge in the gfxPlatform heirarchy about how to
   // create the best offscreen surface for the current system and situation. We
--- a/gfx/thebes/gfxPlatform.h
+++ b/gfx/thebes/gfxPlatform.h
@@ -247,16 +247,18 @@ public:
 
     bool SupportsAzureContentForType(mozilla::gfx::BackendType aType) {
       return BackendTypeBit(aType) & mContentBackendBitmask;
     }
 
     virtual bool UseAcceleratedSkiaCanvas();
     virtual void InitializeSkiaCacheLimits();
 
+    virtual bool UseTiling() { return gfxPrefs::LayersTilesEnabled(); }
+
     void GetAzureBackendInfo(mozilla::widget::InfoObject &aObj) {
       aObj.DefineProperty("AzureCanvasBackend", GetBackendName(mPreferredCanvasBackend));
       aObj.DefineProperty("AzureSkiaAccelerated", UseAcceleratedSkiaCanvas());
       aObj.DefineProperty("AzureFallbackCanvasBackend", GetBackendName(mFallbackCanvasBackend));
       aObj.DefineProperty("AzureContentBackend", GetBackendName(mContentBackend));
     }
 
     mozilla::gfx::BackendType GetContentBackend() {
--- a/gfx/thebes/gfxPlatformMac.cpp
+++ b/gfx/thebes/gfxPlatformMac.cpp
@@ -13,16 +13,17 @@
 #include "gfxMacFont.h"
 #include "gfxCoreTextShaper.h"
 #include "gfxUserFontSet.h"
 
 #include "nsTArray.h"
 #include "mozilla/Preferences.h"
 #include "qcms.h"
 #include "gfx2DGlue.h"
+#include "gfxPrefs.h"
 
 #include <dlfcn.h>
 
 #include "nsCocoaFeatures.h"
 
 using namespace mozilla;
 using namespace mozilla::gfx;
 
@@ -381,16 +382,26 @@ gfxPlatformMac::ReadAntiAliasingThreshol
 
 bool
 gfxPlatformMac::UseAcceleratedCanvas()
 {
   // Lion or later is required
   return nsCocoaFeatures::OnLionOrLater() && Preferences::GetBool("gfx.canvas.azure.accelerated", false);
 }
 
+bool
+gfxPlatformMac::UseTiling()
+{
+  if (gfxPrefs::LayersTilesForceEnabled()) {
+    return true;
+  }
+  // Tiling seems to be slow on 10.6 so disable it until we figure it out
+  return nsCocoaFeatures::OnLionOrLater() && gfxPlatform::UseTiling();
+}
+
 void
 gfxPlatformMac::GetPlatformCMSOutputProfile(void* &mem, size_t &size)
 {
     mem = nullptr;
     size = 0;
 
     CGColorSpaceRef cspace = ::CGDisplayCopyColorSpace(::CGMainDisplayID());
     if (!cspace) {
--- a/gfx/thebes/gfxPlatformMac.h
+++ b/gfx/thebes/gfxPlatformMac.h
@@ -56,16 +56,18 @@ public:
     nsresult UpdateFontList();
 
     virtual void GetCommonFallbackFonts(const uint32_t aCh,
                                         int32_t aRunScript,
                                         nsTArray<const char*>& aFontList);
 
     bool UseAcceleratedCanvas();
 
+    virtual bool UseTiling() MOZ_OVERRIDE;
+
     // lower threshold on font anti-aliasing
     uint32_t GetAntiAliasingThreshold() { return mFontAntiAliasingThreshold; }
 
 private:
     virtual void GetPlatformCMSOutputProfile(void* &mem, size_t &size);
 
     // read in the pref value for the lower threshold on font anti-aliasing
     static uint32_t ReadAntiAliasingThreshold();
--- a/gfx/thebes/gfxPrefs.h
+++ b/gfx/thebes/gfxPrefs.h
@@ -232,16 +232,17 @@ private:
 
   // 0 is "no change" for contrast, positive values increase it, negative values
   // decrease it until we hit mid gray at -1 contrast, after that it gets weird.
   DECL_GFX_PREF(Live, "layers.effect.contrast",                LayersEffectContrast, float, 0.0f);
   DECL_GFX_PREF(Live, "layers.effect.grayscale",               LayersEffectGrayscale, bool, false);
   DECL_GFX_PREF(Live, "layers.effect.invert",                  LayersEffectInvert, bool, false);
 
   DECL_GFX_PREF(Once, "layers.enable-tiles",                   LayersTilesEnabled, bool, false);
+  DECL_GFX_PREF(Once, "layers.force-enable-tiles",             LayersTilesForceEnabled, bool, false);
   DECL_GFX_PREF(Once, "layers.simple-tiles",                   LayersUseSimpleTiles, bool, false);
   DECL_GFX_PREF(Once, "layers.force-per-tile-drawing",         PerTileDrawing, bool, false);
   DECL_GFX_PREF(Once, "layers.tiled-drawtarget.enabled",       TiledDrawTargetEnabled, bool, false);
   // We allow for configurable and rectangular tile size to avoid wasting memory on devices whose
   // screen size does not align nicely to the default tile size. Although layers can be any size,
   // they are often the same size as the screen, especially for width.
   DECL_GFX_PREF(Once, "layers.tile-width",                     LayersTileWidth, int32_t, 256);
   DECL_GFX_PREF(Once, "layers.tile-height",                    LayersTileHeight, int32_t, 256);
--- a/image/test/browser/browser.ini
+++ b/image/test/browser/browser.ini
@@ -5,8 +5,9 @@ support-files =
   big.png
   head.js
   image.html
   imageX2.html
 
 [browser_bug666317.js]
 skip-if = e10s # Bug 948194 - Decoded Images seem to not be discarded on memory-pressure notification with e10s enabled
 [browser_image.js]
+skip-if = e10s
--- a/ipc/chromium/moz.build
+++ b/ipc/chromium/moz.build
@@ -32,46 +32,41 @@ else:
     elif CONFIG['OS_ARCH'] == 'OpenBSD':
         os_openbsd = 1
         os_bsd = 1
     else:
         os_linux = 1
 
 UNIFIED_SOURCES += [
     'src/base/at_exit.cc',
-    'src/base/base_paths.cc',
     'src/base/base_switches.cc',
     'src/base/command_line.cc',
     'src/base/debug_util.cc',
     'src/base/file_path.cc',
     'src/base/file_util.cc',
     'src/base/histogram.cc',
     'src/base/lazy_instance.cc',
     'src/base/lock.cc',
     'src/base/logging.cc',
     'src/base/memory_debug.cc',
     'src/base/message_loop.cc',
     'src/base/message_pump_default.cc',
     'src/base/non_thread_safe.cc',
-    'src/base/path_service.cc',
     'src/base/pickle.cc',
     'src/base/rand_util.cc',
     'src/base/ref_counted.cc',
     'src/base/revocable_store.cc',
     'src/base/scoped_temp_dir.cc',
     'src/base/simple_thread.cc',
-    'src/base/stats_table.cc',
     'src/base/string_piece.cc',
     'src/base/string_util.cc',
-    'src/base/system_monitor.cc',
     'src/base/thread.cc',
     'src/base/thread_collision_warner.cc',
     'src/base/time.cc',
     'src/base/timer.cc',
-    'src/base/trace_event.cc',
     'src/base/tracked.cc',
     'src/base/tracked_objects.cc',
     'src/chrome/common/child_process.cc',
     'src/chrome/common/child_process_host.cc',
     'src/chrome/common/child_process_info.cc',
     'src/chrome/common/child_thread.cc',
     'src/chrome/common/chrome_switches.cc',
     'src/chrome/common/debug_flags.cc',
@@ -83,17 +78,16 @@ UNIFIED_SOURCES += [
     'src/chrome/common/ipc_sync_message.cc',
     'src/chrome/common/message_router.cc',
     'src/chrome/common/notification_service.cc',
     'src/chrome/common/task_queue.cc',
 ]
 
 if os_win:
     SOURCES += [
-        'src/base/base_paths_win.cc',
         'src/base/condition_variable_win.cc',
         'src/base/cpu.cc',
         'src/base/debug_util_win.cc',
         'src/base/event_recorder.cc',
         'src/base/file_util_win.cc',
         'src/base/idle_timer.cc',
         'src/base/lock_impl_win.cc',
         'src/base/message_pump_win.cc',
@@ -102,17 +96,16 @@ if os_win:
         'src/base/platform_thread_win.cc',
         'src/base/process_util_win.cc',
         'src/base/process_win.cc',
         'src/base/rand_util_win.cc',
         'src/base/registry.cc',
         'src/base/shared_memory_win.cc',
         'src/base/sys_info_win.cc',
         'src/base/sys_string_conversions_win.cc',
-        'src/base/system_monitor_win.cc',
         'src/base/thread_local_storage_win.cc',
         'src/base/thread_local_win.cc',
         'src/base/time_win.cc',
         'src/base/waitable_event_watcher_win.cc',
         'src/base/waitable_event_win.cc',
         'src/base/win_util.cc',
         'src/chrome/common/ipc_channel_win.cc',
         'src/chrome/common/process_watcher_win.cc',
@@ -159,17 +152,16 @@ if os_posix:
         'src/base/platform_file_posix.cc',
         'src/base/platform_thread_posix.cc',
         'src/base/process_posix.cc',
         'src/base/process_util_posix.cc',
         'src/base/rand_util_posix.cc',
         'src/base/shared_memory_posix.cc',
         'src/base/string16.cc',
         'src/base/sys_info_posix.cc',
-        'src/base/system_monitor_posix.cc',
         'src/base/thread_local_posix.cc',
         'src/base/thread_local_storage_posix.cc',
         'src/base/waitable_event_posix.cc',
         'src/base/waitable_event_watcher_posix.cc',
         'src/chrome/common/file_descriptor_set_posix.cc',
         'src/chrome/common/ipc_channel_posix.cc',
         'src/chrome/common/process_watcher_posix_sigchld.cc',
     ]
@@ -178,46 +170,42 @@ if os_posix:
             'src/base/message_pump_android.cc',
         ]
         DEFINES['ANDROID'] = True
         DEFINES['_POSIX_MONOTONIC_CLOCK'] = 0
 
 if os_macosx:
     UNIFIED_SOURCES += [
         'src/base/debug_util_mac.cc',
-        'src/base/hmac_mac.cc',
         'src/base/idle_timer.cc',
         'src/base/sys_info_mac.cc',
         'src/base/time_mac.cc',
         'src/chrome/common/mach_message_source_mac.cc',
         'src/chrome/common/transport_dib_mac.cc',
     ]
     SOURCES += [
-        'src/base/base_paths_mac.mm',
         'src/base/chrome_application_mac.mm',
         'src/base/file_util_mac.mm',
         'src/base/mac_util.mm',
         'src/base/message_pump_mac.mm',
         'src/base/platform_thread_mac.mm',
         'src/base/process_util_mac.mm',
         'src/base/scoped_nsautorelease_pool.mm',
         'src/base/sys_string_conversions_mac.mm',
-        'src/base/worker_pool_mac.mm',
         'src/chrome/common/mach_ipc_mac.mm',
     ]
     if not CONFIG['MOZ_NATIVE_LIBEVENT']:
         UNIFIED_SOURCES += [
             'src/third_party/libevent/kqueue.c',
         ]
         LOCAL_INCLUDES += ['src/third_party/libevent/mac']
 
 if os_linux:
     SOURCES += [
         'src/base/atomicops_internals_x86_gcc.cc',
-        'src/base/base_paths_linux.cc',
         'src/base/idle_timer_none.cc',
         'src/base/process_util_linux.cc',
         'src/base/time_posix.cc',
     ]
     if CONFIG['MOZ_WIDGET_GTK']:
         SOURCES += [
             'src/base/message_pump_glib.cc',
         ]
deleted file mode 100644
--- a/ipc/chromium/src/base/base_paths.cc
+++ /dev/null
@@ -1,38 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/base_paths.h"
-
-#include "base/file_path.h"
-#include "base/file_util.h"
-#include "base/path_service.h"
-
-namespace base {
-
-bool PathProvider(int key, FilePath* result) {
-  // NOTE: DIR_CURRENT is a special cased in PathService::Get
-
-  FilePath cur;
-  switch (key) {
-    case base::DIR_EXE:
-      PathService::Get(base::FILE_EXE, &cur);
-      cur = cur.DirName();
-      break;
-    case base::DIR_MODULE:
-      PathService::Get(base::FILE_MODULE, &cur);
-      cur = cur.DirName();
-      break;
-    case base::DIR_TEMP:
-      if (!file_util::GetTempDir(&cur))
-        return false;
-      break;
-    default:
-      return false;
-  }
-
-  *result = cur;
-  return true;
-}
-
-}  // namespace base
deleted file mode 100644
--- a/ipc/chromium/src/base/base_paths.h
+++ /dev/null
@@ -1,35 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef BASE_BASE_PATHS_H_
-#define BASE_BASE_PATHS_H_
-
-// This file declares path keys for the base module.  These can be used with
-// the PathService to access various special directories and files.
-
-#include "base/basictypes.h"
-#if defined(OS_WIN)
-#include "base/base_paths_win.h"
-#elif defined(OS_MACOSX)
-#include "base/base_paths_mac.h"
-#elif defined(OS_LINUX) || defined(OS_BSD)
-#include "base/base_paths_linux.h"
-#endif
-#include "base/path_service.h"
-
-namespace base {
-
-enum {
-  PATH_START = 0,
-
-  DIR_CURRENT,  // current directory
-  DIR_EXE,      // directory containing FILE_EXE
-  DIR_MODULE,   // directory containing FILE_MODULE
-  DIR_TEMP,     // temporary directory
-  PATH_END
-};
-
-}  // namespace base
-
-#endif  // BASE_BASE_PATHS_H_
deleted file mode 100644
--- a/ipc/chromium/src/base/base_paths_linux.cc
+++ /dev/null
@@ -1,46 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/base_paths_linux.h"
-
-#include <unistd.h>
-
-#include "base/file_path.h"
-#include "base/file_util.h"
-#include "base/logging.h"
-#include "base/path_service.h"
-#include "base/string_piece.h"
-#include "base/sys_string_conversions.h"
-
-namespace base {
-
-bool PathProviderLinux(int key, FilePath* result) {
-  FilePath path;
-  switch (key) {
-    case base::FILE_EXE:
-    case base::FILE_MODULE: { // TODO(evanm): is this correct?
-      char bin_dir[PATH_MAX + 1];
-      int bin_dir_size = readlink("/proc/self/exe", bin_dir, PATH_MAX);
-      if (bin_dir_size < 0 || bin_dir_size > PATH_MAX) {
-        NOTREACHED() << "Unable to resolve /proc/self/exe.";
-        return false;
-      }
-      bin_dir[bin_dir_size] = 0;
-      *result = FilePath(bin_dir);
-      return true;
-    }
-    case base::DIR_SOURCE_ROOT:
-      // On linux, unit tests execute two levels deep from the source root.
-      // For example:  sconsbuild/{Debug|Release}/net_unittest
-      if (!PathService::Get(base::DIR_EXE, &path))
-        return false;
-      path = path.Append(FilePath::kParentDirectory)
-                 .Append(FilePath::kParentDirectory);
-      *result = path;
-      return true;
-  }
-  return false;
-}
-
-}  // namespace base
deleted file mode 100644
--- a/ipc/chromium/src/base/base_paths_linux.h
+++ /dev/null
@@ -1,30 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef BASE_BASE_PATHS_LINUX_H_
-#define BASE_BASE_PATHS_LINUX_H_
-
-// This file declares Linux-specific path keys for the base module.
-// These can be used with the PathService to access various special
-// directories and files.
-
-namespace base {
-
-enum {
-  PATH_LINUX_START = 200,
-
-  FILE_EXE,     // Path and filename of the current executable.
-  FILE_MODULE,  // Path and filename of the module containing the code for the
-                // PathService (which could differ from FILE_EXE if the
-                // PathService were compiled into a shared object, for example).
-  DIR_SOURCE_ROOT,  // Returns the root of the source tree.  This key is useful
-                    // for tests that need to locate various resources.  It
-                    // should not be used outside of test code.
-
-  PATH_LINUX_END
-};
-
-}  // namespace base
-
-#endif  // BASE_BASE_PATHS_LINUX_H_
deleted file mode 100644
--- a/ipc/chromium/src/base/base_paths_mac.h
+++ /dev/null
@@ -1,31 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef BASE_BASE_PATHS_MAC_H_
-#define BASE_BASE_PATHS_MAC_H_
-
-// This file declares Mac-specific path keys for the base module.
-// These can be used with the PathService to access various special
-// directories and files.
-
-namespace base {
-
-enum {
-  PATH_MAC_START = 200,
-
-  FILE_EXE,     // path and filename of the current executable
-  FILE_MODULE,  // path and filename of the module containing the code for the
-                // PathService (which could differ from FILE_EXE if the
-                // PathService were compiled into a library, for example)
-  DIR_APP_DATA,  // ~/Library/Application Support/Google/Chrome
-  DIR_LOCAL_APP_DATA,  // same as above (can we remove?)
-  DIR_SOURCE_ROOT,  // Returns the root of the source tree.  This key is useful
-                    // for tests that need to locate various resources.  It
-                    // should not be used outside of test code.
-  PATH_MAC_END
-};
-
-}  // namespace base
-
-#endif  // BASE_BASE_PATHS_MAC_H_
deleted file mode 100644
--- a/ipc/chromium/src/base/base_paths_mac.mm
+++ /dev/null
@@ -1,58 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/base_paths_mac.h"
-
-#import <Cocoa/Cocoa.h>
-
-#include "base/file_path.h"
-#include "base/file_util.h"
-#include "base/logging.h"
-#include "base/mac_util.h"
-#include "base/path_service.h"
-#include "base/string_util.h"
-
-namespace base {
-
-bool PathProviderMac(int key, FilePath* result) {
-  std::string cur;
-  switch (key) {
-    case base::FILE_EXE:
-    case base::FILE_MODULE: {
-      // Executable path can have relative references ("..") depending on
-      // how the app was launched.
-      NSString* path =
-          [[[NSBundle mainBundle] executablePath] stringByStandardizingPath];
-      cur = [path fileSystemRepresentation];
-      break;
-    }
-    case base::DIR_SOURCE_ROOT: {
-      FilePath path;
-      PathService::Get(base::DIR_EXE, &path);
-      if (mac_util::AmIBundled()) {
-        // The bundled app executables (Chromium, TestShell, etc) live five
-        // levels down, eg:
-        // src/xcodebuild/{Debug|Release}/Chromium.app/Contents/MacOS/Chromium.
-        path = path.DirName();
-        path = path.DirName();
-        path = path.DirName();
-        path = path.DirName();
-        *result = path.DirName();
-      } else {
-        // Unit tests execute two levels deep from the source root, eg:
-        // src/xcodebuild/{Debug|Release}/base_unittests
-        path = path.DirName();
-        *result = path.DirName();
-      }
-      return true;
-    }
-    default:
-      return false;
-  }
-
-  *result = FilePath(cur);
-  return true;
-}
-
-}  // namespace base
deleted file mode 100644
--- a/ipc/chromium/src/base/base_paths_win.cc
+++ /dev/null
@@ -1,118 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/base_paths_win.h"
-
-#include <windows.h>
-#include <shlobj.h>
-
-#include "base/file_path.h"
-#include "base/file_util.h"
-#include "base/path_service.h"
-#include "base/win_util.h"
-
-// http://blogs.msdn.com/oldnewthing/archive/2004/10/25/247180.aspx
-extern "C" IMAGE_DOS_HEADER __ImageBase;
-
-namespace base {
-
-bool PathProviderWin(int key, FilePath* result) {
-
-  // We need to go compute the value. It would be nice to support paths with
-  // names longer than MAX_PATH, but the system functions don't seem to be
-  // designed for it either, with the exception of GetTempPath (but other
-  // things will surely break if the temp path is too long, so we don't bother
-  // handling it.
-  wchar_t system_buffer[MAX_PATH];
-  system_buffer[0] = 0;
-
-  FilePath cur;
-  std::wstring wstring_path;
-  switch (key) {
-    case base::FILE_EXE:
-      GetModuleFileName(NULL, system_buffer, MAX_PATH);
-      cur = FilePath(system_buffer);
-      break;
-    case base::FILE_MODULE: {
-      // the resource containing module is assumed to be the one that
-      // this code lives in, whether that's a dll or exe
-      HMODULE this_module = reinterpret_cast<HMODULE>(&__ImageBase);
-      GetModuleFileName(this_module, system_buffer, MAX_PATH);
-      cur = FilePath(system_buffer);
-      break;
-    }
-    case base::DIR_WINDOWS:
-      GetWindowsDirectory(system_buffer, MAX_PATH);
-      cur = FilePath(system_buffer);
-      break;
-    case base::DIR_SYSTEM:
-      GetSystemDirectory(system_buffer, MAX_PATH);
-      cur = FilePath(system_buffer);
-      break;
-    case base::DIR_PROGRAM_FILES:
-      if (FAILED(SHGetFolderPath(NULL, CSIDL_PROGRAM_FILES, NULL,
-                                 SHGFP_TYPE_CURRENT, system_buffer)))
-        return false;
-      cur = FilePath(system_buffer);
-      break;
-    case base::DIR_IE_INTERNET_CACHE:
-      if (FAILED(SHGetFolderPath(NULL, CSIDL_INTERNET_CACHE, NULL,
-                                 SHGFP_TYPE_CURRENT, system_buffer)))
-        return false;
-      cur = FilePath(system_buffer);
-      break;
-    case base::DIR_COMMON_START_MENU:
-      if (FAILED(SHGetFolderPath(NULL, CSIDL_COMMON_PROGRAMS, NULL,
-                                 SHGFP_TYPE_CURRENT, system_buffer)))
-        return false;
-      cur = FilePath(system_buffer);
-      break;
-    case base::DIR_START_MENU:
-      if (FAILED(SHGetFolderPath(NULL, CSIDL_PROGRAMS, NULL,
-                                 SHGFP_TYPE_CURRENT, system_buffer)))
-        return false;
-      cur = FilePath(system_buffer);
-      break;
-    case base::DIR_APP_DATA:
-      if (FAILED(SHGetFolderPath(NULL, CSIDL_APPDATA, NULL, SHGFP_TYPE_CURRENT,
-                                 system_buffer)))
-        return false;
-      cur = FilePath(system_buffer);
-      break;
-    case base::DIR_LOCAL_APP_DATA_LOW:
-      if (win_util::GetWinVersion() < win_util::WINVERSION_VISTA) {
-        return false;
-      }
-      // TODO(nsylvain): We should use SHGetKnownFolderPath instead. Bug 1281128
-      if (FAILED(SHGetFolderPath(NULL, CSIDL_APPDATA, NULL, SHGFP_TYPE_CURRENT,
-                                 system_buffer)))
-        return false;
-      wstring_path = system_buffer;
-      file_util::UpOneDirectory(&wstring_path);
-      file_util::AppendToPath(&wstring_path, L"LocalLow");
-      cur = FilePath(wstring_path);
-      break;
-    case base::DIR_LOCAL_APP_DATA:
-      if (FAILED(SHGetFolderPath(NULL, CSIDL_LOCAL_APPDATA, NULL,
-                                 SHGFP_TYPE_CURRENT, system_buffer)))
-        return false;
-      cur = FilePath(system_buffer);
-      break;
-    case base::DIR_SOURCE_ROOT:
-      // On Windows, unit tests execute two levels deep from the source root.
-      // For example:  chrome/{Debug|Release}/ui_tests.exe
-      PathService::Get(base::DIR_EXE, &wstring_path);
-      file_util::UpOneDirectory(&wstring_path);
-      file_util::UpOneDirectory(&wstring_path);
-      cur = FilePath(wstring_path);
-      break;
-    default:
-      return false;
-  }
-
-  *result = cur;
-  return true;
-}
-
-}  // namespace base
deleted file mode 100644
--- a/ipc/chromium/src/base/base_paths_win.h
+++ /dev/null
@@ -1,42 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef BASE_BASE_PATHS_WIN_H__
-#define BASE_BASE_PATHS_WIN_H__
-
-// This file declares windows-specific path keys for the base module.
-// These can be used with the PathService to access various special
-// directories and files.
-
-namespace base {
-
-enum {
-  PATH_WIN_START = 100,
-
-  FILE_EXE,     // path and filename of the current executable
-  FILE_MODULE,  // path and filename of the module containing the code for the
-                // PathService (which could differ from FILE_EXE if the
-                // PathService were compiled into a DLL, for example)
-  DIR_WINDOWS,  // Windows directory, usually "c:\windows"
-  DIR_SYSTEM,   // Usually c:\windows\system32"
-  DIR_PROGRAM_FILES, // Usually c:\program files
-
-  DIR_IE_INTERNET_CACHE,  // Temporary Internet Files directory.
-  DIR_COMMON_START_MENU,  // Usually "C:\Documents and Settings\All Users\
-                          // Start Menu\Programs"
-  DIR_START_MENU,         // Usually "C:\Documents and Settings\<user>\
-                          // Start Menu\Programs"
-  DIR_APP_DATA,  // Application Data directory under the user profile.
-  DIR_LOCAL_APP_DATA_LOW,  // Local AppData directory for low integrity level.
-  DIR_LOCAL_APP_DATA,  // "Local Settings\Application Data" directory under the
-                       // user profile.
-  DIR_SOURCE_ROOT,  // Returns the root of the source tree.  This key is useful
-                    // for tests that need to locate various resources.  It
-                    // should not be used outside of test code.
-  PATH_WIN_END
-};
-
-}  // namespace base
-
-#endif  // BASE_BASE_PATHS_WIN_H__
deleted file mode 100644
--- a/ipc/chromium/src/base/hmac.h
+++ /dev/null
@@ -1,56 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-// Utility class for calculating the HMAC for a given message. We currently
-// only support SHA1 for the hash algorithm, but this can be extended easily.
-
-#ifndef BASE_HMAC_H_
-#define BASE_HMAC_H_
-
-#include <string>
-
-#include "base/basictypes.h"
-#include "base/scoped_ptr.h"
-
-namespace base {
-
-// Simplify the interface and reduce includes by abstracting out the internals.
-struct HMACPlatformData;
-
-class HMAC {
- public:
-  // The set of supported hash functions. Extend as required.
-  enum HashAlgorithm {
-    SHA1
-  };
-
-  explicit HMAC(HashAlgorithm hash_alg);
-  ~HMAC();
-
-  // Initializes this instance using |key| of the length |key_length|. Call Init
-  // only once. It returns false on the second or later calls.
-  bool Init(const unsigned char* key, int key_length);
-
-  // Initializes this instance using |key|. Call Init only once. It returns
-  // false on the second or later calls.
-  bool Init(const std::string& key) {
-    return Init(reinterpret_cast<const unsigned char*>(key.data()),
-                static_cast<int>(key.size()));
-  }
-
-  // Calculates the HMAC for the message in |data| using the algorithm supplied
-  // to the constructor and the key supplied to the Init method. The HMAC is
-  // returned in |digest|, which has |digest_length| bytes of storage available.
-  bool Sign(const std::string& data, unsigned char* digest, int digest_length);
-
- private:
-  HashAlgorithm hash_alg_;
-  scoped_ptr<HMACPlatformData> plat_;
-
-  DISALLOW_COPY_AND_ASSIGN(HMAC);
-};
-
-}  // namespace base
-
-#endif  // BASE_HMAC_H_
deleted file mode 100644
--- a/ipc/chromium/src/base/hmac_mac.cc
+++ /dev/null
@@ -1,69 +0,0 @@
-// Copyright (c) 2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/hmac.h"
-
-#include <CommonCrypto/CommonHMAC.h>
-
-#include "base/logging.h"
-
-namespace base {
-
-struct HMACPlatformData {
-  std::string key_;
-};
-
-HMAC::HMAC(HashAlgorithm hash_alg)
-    : hash_alg_(hash_alg), plat_(new HMACPlatformData()) {
-  // Only SHA-1 digest is supported now.
-  DCHECK(hash_alg_ == SHA1);
-}
-
-bool HMAC::Init(const unsigned char *key, int key_length) {
-  if (!plat_->key_.empty()) {
-    // Init must not be called more than once on the same HMAC object.
-    NOTREACHED();
-    return false;
-  }
-
-  plat_->key_.assign(reinterpret_cast<const char*>(key), key_length);
-
-  return true;
-}
-
-HMAC::~HMAC() {
-  // Zero out key copy.
-  plat_->key_.assign(plat_->key_.length(), std::string::value_type());
-  plat_->key_.clear();
-  plat_->key_.reserve(0);
-}
-
-bool HMAC::Sign(const std::string& data,
-                unsigned char* digest,
-                int digest_length) {
-  CCHmacAlgorithm algorithm;
-  int algorithm_digest_length;
-  switch (hash_alg_) {
-    case SHA1:
-      algorithm = kCCHmacAlgSHA1;
-      algorithm_digest_length = CC_SHA1_DIGEST_LENGTH;
-      break;
-    default:
-      NOTREACHED();
-      return false;
-  }
-
-  if (digest_length < algorithm_digest_length) {
-    NOTREACHED();
-    return false;
-  }
-
-  CCHmac(algorithm,
-         plat_->key_.data(), plat_->key_.length(), data.data(), data.length(),
-         digest);
-
-  return true;
-}
-
-}  // namespace base
deleted file mode 100644
--- a/ipc/chromium/src/base/path_service.cc
+++ /dev/null
@@ -1,267 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/path_service.h"
-
-#ifdef OS_WIN
-#include <windows.h>
-#include <shellapi.h>
-#include <shlobj.h>
-#endif
-
-#include "base/file_path.h"
-#include "base/file_util.h"
-#include "base/hash_tables.h"
-#include "base/lock.h"
-#include "base/logging.h"
-#include "base/singleton.h"
-#include "base/string_util.h"
-
-namespace base {
-  bool PathProvider(int key, FilePath* result);
-#if defined(OS_WIN)
-  bool PathProviderWin(int key, FilePath* result);
-#elif defined(OS_MACOSX)
-  bool PathProviderMac(int key, FilePath* result);
-#elif defined(OS_LINUX)
-  bool PathProviderLinux(int key, FilePath* result);
-#endif
-}
-
-namespace {
-
-typedef base::hash_map<int, FilePath> PathMap;
-typedef base::hash_set<int> PathSet;
-
-// We keep a linked list of providers.  In a debug build we ensure that no two
-// providers claim overlapping keys.
-struct Provider {
-  PathService::ProviderFunc func;
-  struct Provider* next;
-#ifndef NDEBUG
-  int key_start;
-  int key_end;
-#endif
-  bool is_static;
-};
-
-static Provider base_provider = {
-  base::PathProvider,
-  NULL,
-#ifndef NDEBUG
-  base::PATH_START,
-  base::PATH_END,
-#endif
-  true
-};
-
-#ifdef OS_WIN
-static Provider base_provider_win = {
-  base::PathProviderWin,
-  &base_provider,
-#ifndef NDEBUG
-  base::PATH_WIN_START,
-  base::PATH_WIN_END,
-#endif
-  true
-};
-#endif
-
-#ifdef OS_MACOSX
-static Provider base_provider_mac = {
-  base::PathProviderMac,
-  &base_provider,
-#ifndef NDEBUG
-  base::PATH_MAC_START,
-  base::PATH_MAC_END,
-#endif
-  true
-};
-#endif
-
-#if defined(OS_LINUX)
-static Provider base_provider_linux = {
-  base::PathProviderLinux,
-  &base_provider,
-#ifndef NDEBUG
-  base::PATH_LINUX_START,
-  base::PATH_LINUX_END,
-#endif
-  true
-};
-#endif
-
-
-struct PathData {
-  Lock      lock;
-  PathMap   cache;      // Track mappings from path key to path value.
-  PathSet   overrides;  // Track whether a path has been overridden.
-  Provider* providers;  // Linked list of path service providers.
-
-  PathData() {
-#if defined(OS_WIN)
-    providers = &base_provider_win;
-#elif defined(OS_MACOSX)
-    providers = &base_provider_mac;
-#elif defined(OS_LINUX)
-    providers = &base_provider_linux;
-#endif
-  }
-
-  ~PathData() {
-    Provider* p = providers;
-    while (p) {
-      Provider* next = p->next;
-      if (!p->is_static)
-        delete p;
-      p = next;
-    }
-  }
-};
-
-static PathData* GetPathData() {
-  return Singleton<PathData>::get();
-}
-
-}  // namespace
-
-
-// static
-bool PathService::GetFromCache(int key, FilePath* result) {
-  PathData* path_data = GetPathData();
-  AutoLock scoped_lock(path_data->lock);
-
-  // check for a cached version
-  PathMap::const_iterator it = path_data->cache.find(key);
-  if (it != path_data->cache.end()) {
-    *result = it->second;
-    return true;
-  }
-  return false;
-}
-
-// static
-void PathService::AddToCache(int key, const FilePath& path) {
-  PathData* path_data = GetPathData();
-  AutoLock scoped_lock(path_data->lock);
-  // Save the computed path in our cache.
-  path_data->cache[key] = path;
-}
-
-// TODO(brettw): this function does not handle long paths (filename > MAX_PATH)
-// characters). This isn't supported very well by Windows right now, so it is
-// moot, but we should keep this in mind for the future.
-// static
-bool PathService::Get(int key, FilePath* result) {
-  PathData* path_data = GetPathData();
-  DCHECK(path_data);
-  DCHECK(result);
-  DCHECK(key >= base::DIR_CURRENT);
-
-  // special case the current directory because it can never be cached
-  if (key == base::DIR_CURRENT)
-    return file_util::GetCurrentDirectory(result);
-
-  if (GetFromCache(key, result))
-    return true;
-
-  FilePath path;
-
-  // search providers for the requested path
-  // NOTE: it should be safe to iterate here without the lock
-  // since RegisterProvider always prepends.
-  Provider* provider = path_data->providers;
-  while (provider) {
-    if (provider->func(key, &path))
-      break;
-    DCHECK(path.empty()) << "provider should not have modified path";
-    provider = provider->next;
-  }
-
-  if (path.empty())
-    return false;
-
-  AddToCache(key, path);
-
-  *result = path;
-  return true;
-}
-
-// static
-bool PathService::Get(int key, std::wstring* result) {
-  // Deprecated compatibility function.
-  FilePath path;
-  if (!Get(key, &path))
-    return false;
-  *result = path.ToWStringHack();
-  return true;
-}
-
-bool PathService::IsOverridden(int key) {
-  PathData* path_data = GetPathData();
-  DCHECK(path_data);
-
-  AutoLock scoped_lock(path_data->lock);
-  return path_data->overrides.find(key) != path_data->overrides.end();
-}
-
-bool PathService::Override(int key, const std::wstring& path) {
-  PathData* path_data = GetPathData();
-  DCHECK(path_data);
-  DCHECK(key > base::DIR_CURRENT) << "invalid path key";
-
-  std::wstring file_path = path;
-#if defined(OS_WIN)
-  // On Windows we switch the current working directory to load plugins (at
-  // least). That's not the case on POSIX.
-  // Also, on POSIX, AbsolutePath fails if called on a non-existant path.
-  if (!file_util::AbsolutePath(&file_path))
-    return false;
-#endif
-
-  // make sure the directory exists:
-  if (!file_util::CreateDirectory(file_path))
-    return false;
-
-  file_util::TrimTrailingSeparator(&file_path);
-
-  AutoLock scoped_lock(path_data->lock);
-  path_data->cache[key] = FilePath::FromWStringHack(file_path);
-  path_data->overrides.insert(key);
-  return true;
-}
-
-bool PathService::SetCurrentDirectory(const std::wstring& current_directory) {
-  return file_util::SetCurrentDirectory(current_directory);
-}
-
-void PathService::RegisterProvider(ProviderFunc func, int key_start,
-                                   int key_end) {
-  PathData* path_data = GetPathData();
-  DCHECK(path_data);
-  DCHECK(key_end > key_start);
-
-  AutoLock scoped_lock(path_data->lock);
-
-  Provider* p;
-
-#ifndef NDEBUG
-  p = path_data->providers;
-  while (p) {
-    DCHECK(key_start >= p->key_end || key_end <= p->key_start) <<
-      "path provider collision";
-    p = p->next;
-  }
-#endif
-
-  p = new Provider;
-  p->is_static = false;
-  p->func = func;
-  p->next = path_data->providers;
-#ifndef NDEBUG
-  p->key_start = key_start;
-  p->key_end = key_end;
-#endif
-  path_data->providers = p;
-}
deleted file mode 100644
--- a/ipc/chromium/src/base/path_service.h
+++ /dev/null
@@ -1,80 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef BASE_PATH_SERVICE_H__
-#define BASE_PATH_SERVICE_H__
-
-#include "build/build_config.h"
-#ifdef OS_WIN
-// TODO(erikkay): this should be removable, but because SetCurrentDirectory
-// is the name of a Windows function, it gets macro-ized to SetCurrentDirectoryW
-// by windows.h, which leads to a different name in the header vs. the impl.
-// Even if we could fix that, it would still hose all callers of the function.
-// The right thing is likely to rename.
-#include <windows.h>
-#endif
-
-#include <string>
-
-#include "base/base_paths.h"
-
-class FilePath;
-
-// The path service is a global table mapping keys to file system paths.  It is
-// OK to use this service from multiple threads.
-//
-class PathService {
- public:
-  // Retrieves a path to a special directory or file and places it into the
-  // string pointed to by 'path'. If you ask for a directory it is guaranteed
-  // to NOT have a path separator at the end. For example, "c:\windows\temp"
-  // Directories are also guaranteed to exist when this function succeeds.
-  //
-  // Returns true if the directory or file was successfully retrieved. On
-  // failure, 'path' will not be changed.
-  static bool Get(int key, FilePath* path);
-  // This version, producing a wstring, is deprecated and only kept around
-  // until we can fix all callers.
-  static bool Get(int key, std::wstring* path);
-
-  // Overrides the path to a special directory or file.  This cannot be used to
-  // change the value of DIR_CURRENT, but that should be obvious.  Also, if the
-  // path specifies a directory that does not exist, the directory will be
-  // created by this method.  This method returns true if successful.
-  //
-  // If the given path is relative, then it will be resolved against
-  // DIR_CURRENT.
-  //
-  // WARNING: Consumers of PathService::Get may expect paths to be constant
-  // over the lifetime of the app, so this method should be used with caution.
-  static bool Override(int key, const std::wstring& path);
-
-  // Return whether a path was overridden.
-  static bool IsOverridden(int key);
-
-  // Sets the current directory.
-  static bool SetCurrentDirectory(const std::wstring& current_directory);
-
-  // To extend the set of supported keys, you can register a path provider,
-  // which is just a function mirroring PathService::Get.  The ProviderFunc
-  // returns false if it cannot provide a non-empty path for the given key.
-  // Otherwise, true is returned.
-  //
-  // WARNING: This function could be called on any thread from which the
-  // PathService is used, so the ProviderFunc MUST BE THREADSAFE.
-  //
-  typedef bool (*ProviderFunc)(int, FilePath*);
-
-  // Call to register a path provider.  You must specify the range "[key_start,
-  // key_end)" of supported path keys.
-  static void RegisterProvider(ProviderFunc provider,
-                               int key_start,
-                               int key_end);
- private:
-  static bool GetFromCache(int key, FilePath* path);
-  static void AddToCache(int key, const FilePath& path);
-
-};
-
-#endif // BASE_PATH_SERVICE_H__
deleted file mode 100644
--- a/ipc/chromium/src/base/stats_counters.h
+++ /dev/null
@@ -1,257 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-
-#ifndef BASE_STATS_COUNTERS_H__
-#define BASE_STATS_COUNTERS_H__
-
-#include <string>
-#include "base/stats_table.h"
-#include "base/time.h"
-
-// StatsCounters are dynamically created values which can be tracked in
-// the StatsTable.  They are designed to be lightweight to create and
-// easy to use.
-//
-// Since StatsCounters can be created dynamically by name, there is
-// a hash table lookup to find the counter in the table.  A StatsCounter
-// object can be created once and used across multiple threads safely.
-//
-// Example usage:
-//    {
-//      StatsCounter request_count("RequestCount");
-//      request_count.Increment();
-//    }
-//
-// Note that creating counters on the stack does work, however creating
-// the counter object requires a hash table lookup.  For inner loops, it
-// may be better to create the counter either as a member of another object
-// (or otherwise outside of the loop) for maximum performance.
-//
-// Internally, a counter represents a value in a row of a StatsTable.
-// The row has a 32bit value for each process/thread in the table and also
-// a name (stored in the table metadata).
-//
-// NOTE: In order to make stats_counters usable in lots of different code,
-// avoid any dependencies inside this header file.
-//
-
-//------------------------------------------------------------------------------
-// Define macros for ease of use. They also allow us to change definitions
-// as the implementation varies, or depending on compile options.
-//------------------------------------------------------------------------------
-// First provide generic macros, which exist in production as well as debug.
-#define STATS_COUNTER(name, delta) do { \
-  static StatsCounter counter(name); \
-  counter.Add(delta); \
-} while (0)
-
-#define SIMPLE_STATS_COUNTER(name) STATS_COUNTER(name, 1)
-
-#define RATE_COUNTER(name, duration) do { \
-  static StatsRate hit_count(name); \
-  hit_count.AddTime(duration); \
-} while (0)
-
-// Define Debug vs non-debug flavors of macros.
-#ifndef NDEBUG
-
-#define DSTATS_COUNTER(name, delta) STATS_COUNTER(name, delta)
-#define DSIMPLE_STATS_COUNTER(name) SIMPLE_STATS_COUNTER(name)
-#define DRATE_COUNTER(name, duration) RATE_COUNTER(name, duration)
-
-#else  // NDEBUG
-
-#define DSTATS_COUNTER(name, delta) do {} while (0)
-#define DSIMPLE_STATS_COUNTER(name) do {} while (0)
-#define DRATE_COUNTER(name, duration) do {} while (0)
-
-#endif  // NDEBUG
-
-//------------------------------------------------------------------------------
-// StatsCounter represents a counter in the StatsTable class.
-class StatsCounter {
- public:
-  // Create a StatsCounter object.
-  explicit StatsCounter(const std::string& name)
-       : counter_id_(-1) {
-    // We prepend the name with 'c:' to indicate that it is a counter.
-    name_ = "c:";
-    name_.append(name);
-  };
-
-  virtual ~StatsCounter() {}
-
-  // Sets the counter to a specific value.
-  void Set(int value) {
-    int* loc = GetPtr();
-    if (loc) *loc = value;
-  }
-
-  // Increments the counter.
-  void Increment() {
-    Add(1);
-  }
-
-  virtual void Add(int value) {
-    int* loc = GetPtr();
-    if (loc)
-      (*loc) += value;
-  }
-
-  // Decrements the counter.
-  void Decrement() {
-    Add(-1);
-  }
-
-  void Subtract(int value) {
-    Add(-value);
-  }
-
-  // Is this counter enabled?
-  // Returns false if table is full.
-  bool Enabled() {
-    return GetPtr() != NULL;
-  }
-
-  int value() {
-    int* loc = GetPtr();
-    if (loc) return *loc;
-    return 0;
-  }
-
- protected:
-  StatsCounter()
-    : counter_id_(-1) {
-  }
-
-  // Returns the cached address of this counter location.
-  int* GetPtr() {
-    StatsTable* table = StatsTable::current();
-    if (!table)
-      return NULL;
-
-    // If counter_id_ is -1, then we haven't looked it up yet.
-    if (counter_id_ == -1) {
-      counter_id_ = table->FindCounter(name_);
-      if (table->GetSlot() == 0) {
-        if (!table->RegisterThread("")) {
-          // There is no room for this thread.  This thread
-          // cannot use counters.
-          counter_id_ = 0;
-          return NULL;
-        }
-      }
-    }
-
-    // If counter_id_ is > 0, then we have a valid counter.
-    if (counter_id_ > 0)
-      return table->GetLocation(counter_id_, table->GetSlot());
-
-    // counter_id_ was zero, which means the table is full.
-    return NULL;
-  }
-
-  std::string name_;
-  // The counter id in the table.  We initialize to -1 (an invalid value)
-  // and then cache it once it has been looked up.  The counter_id is
-  // valid across all threads and processes.
-  int32_t counter_id_;
-};
-
-
-// A StatsCounterTimer is a StatsCounter which keeps a timer during
-// the scope of the StatsCounterTimer.  On destruction, it will record
-// its time measurement.
-class StatsCounterTimer : protected StatsCounter {
- public:
-  // Constructs and starts the timer.
-  explicit StatsCounterTimer(const std::string& name) {
-    // we prepend the name with 't:' to indicate that it is a timer.
-    name_ = "t:";
-    name_.append(name);
-  }
-
-  // Start the timer.
-  void Start() {
-    if (!Enabled())
-      return;
-    start_time_ = base::TimeTicks::Now();
-    stop_time_ = base::TimeTicks();
-  }
-
-  // Stop the timer and record the results.
-  void Stop() {
-    if (!Enabled() || !Running())
-      return;
-    stop_time_ = base::TimeTicks::Now();
-    Record();
-  }
-
-  // Returns true if the timer is running.
-  bool Running() {
-    return Enabled() && !start_time_.is_null() && stop_time_.is_null();
-  }
-
-  // Accept a TimeDelta to increment.
-  virtual void AddTime(base::TimeDelta time) {
-    Add(static_cast<int>(time.InMilliseconds()));
-  }
-
- protected:
-  // Compute the delta between start and stop, in milliseconds.
-  void Record() {
-    AddTime(stop_time_ - start_time_);
-  }
-
-  base::TimeTicks start_time_;
-  base::TimeTicks stop_time_;
-};
-
-// A StatsRate is a timer that keeps a count of the number of intervals added so
-// that several statistics can be produced:
-//    min, max, avg, count, total
-class StatsRate : public StatsCounterTimer {
- public:
-  // Constructs and starts the timer.
-  explicit StatsRate(const char* name)
-      : StatsCounterTimer(name),
-      counter_(name),
-      largest_add_(std::string(" ").append(name).append("MAX").c_str()) {
-  }
-
-  virtual void Add(int value) {
-    counter_.Increment();
-    StatsCounterTimer::Add(value);
-    if (value > largest_add_.value())
-      largest_add_.Set(value);
-  }
-
- private:
-  StatsCounter counter_;
-  StatsCounter largest_add_;
-};
-
-
-// Helper class for scoping a timer or rate.
-template<class T> class StatsScope {
- public:
-  explicit StatsScope<T>(T& timer)
-      : timer_(timer) {
-    timer_.Start();
-  }
-
-  ~StatsScope() {
-    timer_.Stop();
-  }
-
-  void Stop() {
-    timer_.Stop();
-  }
-
- private:
-  T& timer_;
-};
-
-#endif  // BASE_STATS_COUNTERS_H__
deleted file mode 100644
--- a/ipc/chromium/src/base/stats_table.cc
+++ /dev/null
@@ -1,559 +0,0 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/stats_table.h"
-
-#include "base/logging.h"
-#include "base/platform_thread.h"
-#include "base/process_util.h"
-#include "base/scoped_ptr.h"
-#include "base/shared_memory.h"
-#include "base/string_piece.h"
-#include "base/string_util.h"
-#include "base/sys_string_conversions.h"
-#include "base/thread_local_storage.h"
-
-#if defined(OS_POSIX)
-#include "errno.h"
-#endif
-
-// The StatsTable uses a shared memory segment that is laid out as follows
-//
-// +-------------------------------------------+
-// | Version | Size | MaxCounters | MaxThreads |
-// +-------------------------------------------+
-// | Thread names table                        |
-// +-------------------------------------------+
-// | Thread TID table                          |
-// +-------------------------------------------+
-// | Thread PID table                          |
-// +-------------------------------------------+
-// | Counter names table                       |
-// +-------------------------------------------+
-// | Data                                      |
-// +-------------------------------------------+
-//
-// The data layout is a grid, where the columns are the thread_ids and the
-// rows are the counter_ids.
-//
-// If the first character of the thread_name is '\0', then that column is
-// empty.
-// If the first character of the counter_name is '\0', then that row is
-// empty.
-//
-// About Locking:
-// This class is designed to be both multi-thread and multi-process safe.
-// Aside from initialization, this is done by partitioning the data which
-// each thread uses so that no locking is required.  However, to allocate
-// the rows and columns of the table to particular threads, locking is
-// required.
-//
-// At the shared-memory level, we have a lock.  This lock protects the
-// shared-memory table only, and is used when we create new counters (e.g.
-// use rows) or when we register new threads (e.g. use columns).  Reading
-// data from the table does not require any locking at the shared memory
-// level.
-//
-// Each process which accesses the table will create a StatsTable object.
-// The StatsTable maintains a hash table of the existing counters in the
-// table for faster lookup.  Since the hash table is process specific,
-// each process maintains its own cache.  We avoid complexity here by never
-// de-allocating from the hash table.  (Counters are dynamically added,
-// but not dynamically removed).
-
-// In order for external viewers to be able to read our shared memory,
-// we all need to use the same size ints.
-COMPILE_ASSERT(sizeof(int)==4, expect_4_byte_ints);
-
-namespace {
-
-// An internal version in case we ever change the format of this
-// file, and so that we can identify our table.
-const int kTableVersion = 0x13131313;
-
-// The name for un-named counters and threads in the table.
-const char kUnknownName[] = "<unknown>";
-
-// Calculates delta to align an offset to the size of an int
-inline int AlignOffset(int offset) {
-  return (sizeof(int) - (offset % sizeof(int))) % sizeof(int);
-}
-
-inline int AlignedSize(int size) {
-  return size + AlignOffset(size);
-}
-
-// StatsTableTLSData carries the data stored in the TLS slots for the
-// StatsTable.  This is used so that we can properly cleanup when the
-// thread exits and return the table slot.
-//
-// Each thread that calls RegisterThread in the StatsTable will have
-// a StatsTableTLSData stored in its TLS.
-struct StatsTableTLSData {
-  StatsTable* table;
-  int slot;
-};
-
-}  // namespace
-
-// The StatsTablePrivate maintains convenience pointers into the
-// shared memory segment.  Use this class to keep the data structure
-// clean and accessible.
-class StatsTablePrivate {
- public:
-  // Various header information contained in the memory mapped segment.
-  struct TableHeader {
-    int version;
-    int size;
-    int max_counters;
-    int max_threads;
-  };
-
-  // Construct a new StatsTablePrivate based on expected size parameters, or
-  // return NULL on failure.
-  static StatsTablePrivate* New(const std::string& name, int size,
-                                int max_threads, int max_counters);
-
-  base::SharedMemory* shared_memory() { return &shared_memory_; }
-
-  // Accessors for our header pointers
-  TableHeader* table_header() const { return table_header_; }
-  int version() const { return table_header_->version; }
-  int size() const { return table_header_->size; }
-  int max_counters() const { return table_header_->max_counters; }
-  int max_threads() const { return table_header_->max_threads; }
-
-  // Accessors for our tables
-  char* thread_name(int slot_id) const {
-    return &thread_names_table_[
-      (slot_id-1) * (StatsTable::kMaxThreadNameLength)];
-  }
-  PlatformThreadId* thread_tid(int slot_id) const {
-    return &(thread_tid_table_[slot_id-1]);
-  }
-  int* thread_pid(int slot_id) const {
-    return &(thread_pid_table_[slot_id-1]);
-  }
-  char* counter_name(int counter_id) const {
-    return &counter_names_table_[
-      (counter_id-1) * (StatsTable::kMaxCounterNameLength)];
-  }
-  int* row(int counter_id) const {
-    return &data_table_[(counter_id-1) * max_threads()];
-  }
-
- private:
-  // Constructor is private because you should use New() instead.
-  StatsTablePrivate() {}
-
-  // Initializes the table on first access.  Sets header values
-  // appropriately and zeroes all counters.
-  void InitializeTable(void* memory, int size, int max_counters,
-                       int max_threads);
-
-  // Initializes our in-memory pointers into a pre-created StatsTable.
-  void ComputeMappedPointers(void* memory);
-
-  base::SharedMemory shared_memory_;
-  TableHeader* table_header_;
-  char* thread_names_table_;
-  PlatformThreadId* thread_tid_table_;
-  int* thread_pid_table_;
-  char* counter_names_table_;
-  int* data_table_;
-};
-
-// static
-StatsTablePrivate* StatsTablePrivate::New(const std::string& name,
-                                          int size,
-                                          int max_threads,
-                                          int max_counters) {
-  scoped_ptr<StatsTablePrivate> priv(new StatsTablePrivate());
-  if (!priv->shared_memory_.Create(name, false, true, size))
-    return NULL;
-  if (!priv->shared_memory_.Map(size))
-    return NULL;
-  void* memory = priv->shared_memory_.memory();
-
-  TableHeader* header = static_cast<TableHeader*>(memory);
-
-  // If the version does not match, then assume the table needs
-  // to be initialized.
-  if (header->version != kTableVersion)
-    priv->InitializeTable(memory, size, max_counters, max_threads);
-
-  // We have a valid table, so compute our pointers.
-  priv->ComputeMappedPointers(memory);
-
-  return priv.release();
-}
-
-void StatsTablePrivate::InitializeTable(void* memory, int size,
-                                        int max_counters,
-                                        int max_threads) {
-  // Zero everything.
-  memset(memory, 0, size);
-
-  // Initialize the header.
-  TableHeader* header = static_cast<TableHeader*>(memory);
-  header->version = kTableVersion;
-  header->size = size;
-  header->max_counters = max_counters;
-  header->max_threads = max_threads;
-}
-
-void StatsTablePrivate::ComputeMappedPointers(void* memory) {
-  char* data = static_cast<char*>(memory);
-  int offset = 0;
-
-  table_header_ = reinterpret_cast<TableHeader*>(data);
-  offset += sizeof(*table_header_);
-  offset += AlignOffset(offset);
-
-  // Verify we're looking at a valid StatsTable.
-  DCHECK_EQ(table_header_->version, kTableVersion);
-
-  thread_names_table_ = reinterpret_cast<char*>(data + offset);
-  offset += sizeof(char) *
-            max_threads() * StatsTable::kMaxThreadNameLength;
-  offset += AlignOffset(offset);
-
-  thread_tid_table_ = reinterpret_cast<PlatformThreadId*>(data + offset);
-  offset += sizeof(int) * max_threads();
-  offset += AlignOffset(offset);
-
-  thread_pid_table_ = reinterpret_cast<int*>(data + offset);
-  offset += sizeof(int) * max_threads();
-  offset += AlignOffset(offset);
-
-  counter_names_table_ = reinterpret_cast<char*>(data + offset);
-  offset += sizeof(char) *
-            max_counters() * StatsTable::kMaxCounterNameLength;
-  offset += AlignOffset(offset);
-
-  data_table_ = reinterpret_cast<int*>(data + offset);
-  offset += sizeof(int) * max_threads() * max_counters();
-
-  DCHECK_EQ(offset, size());
-}
-
-
-
-// We keep a singleton table which can be easily accessed.
-StatsTable* StatsTable::global_table_ = NULL;
-
-StatsTable::StatsTable(const std::string& name, int max_threads,
-                       int max_counters)
-    : impl_(NULL),
-      tls_index_(SlotReturnFunction) {
-  int table_size =
-    AlignedSize(sizeof(StatsTablePrivate::TableHeader)) +
-    AlignedSize((max_counters * sizeof(char) * kMaxCounterNameLength)) +
-    AlignedSize((max_threads * sizeof(char) * kMaxThreadNameLength)) +
-    AlignedSize(max_threads * sizeof(int)) +
-    AlignedSize(max_threads * sizeof(int)) +
-    AlignedSize((sizeof(int) * (max_counters * max_threads)));
-
-  impl_ = StatsTablePrivate::New(name, table_size, max_threads, max_counters);
-
-  // TODO(port): clean up this error reporting.
-#if defined(OS_WIN)
-  if (!impl_)
-    CHROMIUM_LOG(ERROR) << "StatsTable did not initialize:" << GetLastError();
-#elif defined(OS_POSIX)
-  if (!impl_)
-    CHROMIUM_LOG(ERROR) << "StatsTable did not initialize:" << strerror(errno);
-#endif
-}
-
-StatsTable::~StatsTable() {
-  // Before we tear down our copy of the table, be sure to
-  // unregister our thread.
-  UnregisterThread();
-
-  // Return ThreadLocalStorage.  At this point, if any registered threads
-  // still exist, they cannot Unregister.
-  tls_index_.Free();
-
-  // Cleanup our shared memory.
-  delete impl_;
-
-  // If we are the global table, unregister ourselves.
-  if (global_table_ == this)
-    global_table_ = NULL;
-}
-
-int StatsTable::RegisterThread(const std::string& name) {
-  int slot = 0;
-
-  // Registering a thread requires that we lock the shared memory
-  // so that two threads don't grab the same slot.  Fortunately,
-  // thread creation shouldn't happen in inner loops.
-  {
-    base::SharedMemoryAutoLock lock(impl_->shared_memory());
-    slot = FindEmptyThread();
-    if (!slot) {
-      return 0;
-    }
-
-    DCHECK(impl_);
-
-    // We have space, so consume a column in the table.
-    std::string thread_name = name;
-    if (name.empty())
-      thread_name = kUnknownName;
-    base::strlcpy(impl_->thread_name(slot), thread_name.c_str(),
-                  kMaxThreadNameLength);
-    *(impl_->thread_tid(slot)) = PlatformThread::CurrentId();
-    *(impl_->thread_pid(slot)) = base::GetCurrentProcId();
-  }
-
-  // Set our thread local storage.
-  StatsTableTLSData* data = new StatsTableTLSData;
-  data->table = this;
-  data->slot = slot;
-  tls_index_.Set(data);
-  return slot;
-}
-
-StatsTableTLSData* StatsTable::GetTLSData() const {
-  StatsTableTLSData* data =
-    static_cast<StatsTableTLSData*>(tls_index_.Get());
-  if (!data)
-    return NULL;
-
-  DCHECK(data->slot);
-  DCHECK_EQ(data->table, this);
-  return data;
-}
-
-void StatsTable::UnregisterThread() {
-  UnregisterThread(GetTLSData());
-}
-
-void StatsTable::UnregisterThread(StatsTableTLSData* data) {
-  if (!data)
-    return;
-  DCHECK(impl_);
-
-  // Mark the slot free by zeroing out the thread name.
-  char* name = impl_->thread_name(data->slot);
-  *name = '\0';
-
-  // Remove the calling thread's TLS so that it cannot use the slot.
-  tls_index_.Set(NULL);
-  delete data;
-}
-
-void StatsTable::SlotReturnFunction(void* data) {
-  // This is called by the TLS destructor, which on some platforms has
-  // already cleared the TLS info, so use the tls_data argument
-  // rather than trying to fetch it ourselves.
-  StatsTableTLSData* tls_data = static_cast<StatsTableTLSData*>(data);
-  if (tls_data) {
-    DCHECK(tls_data->table);
-    tls_data->table->UnregisterThread(tls_data);
-  }
-}
-
-int StatsTable::CountThreadsRegistered() const {
-  if (!impl_)
-    return 0;
-
-  // Loop through the shared memory and count the threads that are active.
-  // We intentionally do not lock the table during the operation.
-  int count = 0;
-  for (int index = 1; index <= impl_->max_threads(); index++) {
-    char* name = impl_->thread_name(index);
-    if (*name != '\0')
-      count++;
-  }
-  return count;
-}
-
-int StatsTable::GetSlot() const {
-  StatsTableTLSData* data = GetTLSData();
-  if (!data)
-    return 0;
-  return data->slot;
-}
-
-int StatsTable::FindEmptyThread() const {
-  // Note: the API returns slots numbered from 1..N, although
-  // internally, the array is 0..N-1.  This is so that we can return
-  // zero as "not found".
-  //
-  // The reason for doing this is because the thread 'slot' is stored
-  // in TLS, which is always initialized to zero, not -1.  If 0 were
-  // returned as a valid slot number, it would be confused with the
-  // uninitialized state.
-  if (!impl_)
-    return 0;
-
-  int index = 1;
-  for (; index <= impl_->max_threads(); index++) {
-    char* name = impl_->thread_name(index);
-    if (!*name)
-      break;
-  }
-  if (index > impl_->max_threads())
-    return 0;  // The table is full.
-  return index;
-}
-
-int StatsTable::FindCounterOrEmptyRow(const std::string& name) const {
-  // Note: the API returns slots numbered from 1..N, although
-  // internally, the array is 0..N-1.  This is so that we can return
-  // zero as "not found".
-  //
-  // There isn't much reason for this other than to be consistent
-  // with the way we track columns for thread slots.  (See comments
-  // in FindEmptyThread for why it is done this way).
-  if (!impl_)
-    return 0;
-
-  int free_slot = 0;
-  for (int index = 1; index <= impl_->max_counters(); index++) {
-    char* row_name = impl_->counter_name(index);
-    if (!*row_name && !free_slot)
-      free_slot = index;  // save that we found a free slot
-    else if (!strncmp(row_name, name.c_str(), kMaxCounterNameLength))
-      return index;
-  }
-  return free_slot;
-}
-
-int StatsTable::FindCounter(const std::string& name) {
-  // Note: the API returns counters numbered from 1..N, although
-  // internally, the array is 0..N-1.  This is so that we can return
-  // zero as "not found".
-  if (!impl_)
-    return 0;
-
-  // Create a scope for our auto-lock.
-  {
-    AutoLock scoped_lock(counters_lock_);
-
-    // Attempt to find the counter.
-    CountersMap::const_iterator iter;
-    iter = counters_.find(name);
-    if (iter != counters_.end())
-      return iter->second;
-  }
-
-  // Counter does not exist, so add it.
-  return AddCounter(name);
-}
-
-int StatsTable::AddCounter(const std::string& name) {
-  DCHECK(impl_);
-
-  if (!impl_)
-    return 0;
-
-  int counter_id = 0;
-  {
-    // To add a counter to the shared memory, we need the
-    // shared memory lock.
-    base::SharedMemoryAutoLock lock(impl_->shared_memory());
-
-    // We have space, so create a new counter.
-    counter_id = FindCounterOrEmptyRow(name);
-    if (!counter_id)
-      return 0;
-
-    std::string counter_name = name;
-    if (name.empty())
-      counter_name = kUnknownName;
-    base::strlcpy(impl_->counter_name(counter_id), counter_name.c_str(),
-                  kMaxCounterNameLength);
-  }
-
-  // now add to our in-memory cache
-  {
-    AutoLock lock(counters_lock_);
-    counters_[name] = counter_id;
-  }
-  return counter_id;
-}
-
-int* StatsTable::GetLocation(int counter_id, int slot_id) const {
-  if (!impl_)
-    return NULL;
-  if (slot_id > impl_->max_threads())
-    return NULL;
-
-  int* row = impl_->row(counter_id);
-  return &(row[slot_id-1]);