| Index: cc/debug/rasterize_and_record_benchmark.cc
|
| diff --git a/cc/debug/rasterize_and_record_benchmark.cc b/cc/debug/rasterize_and_record_benchmark.cc
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..f56151d063862c92a69a8df1ed2d00d8946dc759
|
| --- /dev/null
|
| +++ b/cc/debug/rasterize_and_record_benchmark.cc
|
| @@ -0,0 +1,140 @@
|
| +// Copyright 2013 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 "cc/debug/rasterize_and_record_benchmark.h"
|
| +
|
| +#include <algorithm>
|
| +#include <limits>
|
| +
|
| +#include "base/basictypes.h"
|
| +#include "base/values.h"
|
| +#include "cc/debug/rasterize_and_record_benchmark_impl.h"
|
| +#include "cc/layers/layer.h"
|
| +#include "cc/layers/picture_layer.h"
|
| +#include "cc/trees/layer_tree_host.h"
|
| +#include "cc/trees/layer_tree_host_common.h"
|
| +#include "ui/gfx/rect.h"
|
| +
|
| +namespace cc {
|
| +
|
| +namespace {
|
| +
|
| +const int kTileGridSize = 512;
|
| +const int kTileGridBorder = 1;
|
| +
|
| +const int kDefaultRecordRepeatCount = 100;
|
| +
|
| +base::TimeTicks Now() {
|
| + return base::TimeTicks::IsThreadNowSupported()
|
| + ? base::TimeTicks::ThreadNow()
|
| + : base::TimeTicks::HighResNow();
|
| +}
|
| +
|
| +} // namespace
|
| +
|
| +RasterizeAndRecordBenchmark::RasterizeAndRecordBenchmark(
|
| + scoped_ptr<base::Value> value,
|
| + const MicroBenchmark::DoneCallback& callback)
|
| + : MicroBenchmark(callback),
|
| + record_repeat_count_(kDefaultRecordRepeatCount),
|
| + settings_(value.Pass()),
|
| + main_thread_benchmark_done_(false) {
|
| + base::DictionaryValue* settings = NULL;
|
| + settings_->GetAsDictionary(&settings);
|
| + if (!settings)
|
| + return;
|
| +
|
| + if (settings->HasKey("record_repeat_count"))
|
| + settings->GetInteger("record_repeat_count", &record_repeat_count_);
|
| +}
|
| +
|
| +RasterizeAndRecordBenchmark::~RasterizeAndRecordBenchmark() {}
|
| +
|
| +void RasterizeAndRecordBenchmark::DidUpdateLayers(LayerTreeHost* host) {
|
| + LayerTreeHostCommon::CallFunctionForSubtree(
|
| + host->root_layer(),
|
| + base::Bind(&RasterizeAndRecordBenchmark::Run, base::Unretained(this)));
|
| +
|
| + DCHECK(!results_.get());
|
| + results_ = make_scoped_ptr(new base::DictionaryValue);
|
| + results_->SetInteger("pixels_recorded", record_results_.pixels_recorded);
|
| + results_->SetDouble("record_time_ms",
|
| + record_results_.total_best_time.InMillisecondsF());
|
| + main_thread_benchmark_done_ = true;
|
| +}
|
| +
|
| +void RasterizeAndRecordBenchmark::RecordRasterResults(
|
| + scoped_ptr<base::Value> results_value) {
|
| + DCHECK(main_thread_benchmark_done_);
|
| +
|
| + base::DictionaryValue* results = NULL;
|
| + results_value->GetAsDictionary(&results);
|
| +
|
| + DCHECK(results);
|
| + DCHECK(results->HasKey("pixels_rasterized"));
|
| + DCHECK(results->HasKey("rasterize_time_ms"));
|
| +
|
| + int pixels_rasterized;
|
| + results->GetInteger("pixels_rasterized", &pixels_rasterized);
|
| + double rasterize_time_ms;
|
| + results->GetDouble("rasterize_time_ms", &rasterize_time_ms);
|
| +
|
| + results_->SetInteger("pixels_rasterized", pixels_rasterized);
|
| + results_->SetDouble("rasterize_time_ms", rasterize_time_ms);
|
| +
|
| + NotifyDone(results_.PassAs<base::Value>());
|
| +}
|
| +
|
| +scoped_ptr<MicroBenchmarkImpl> RasterizeAndRecordBenchmark::CreateBenchmarkImpl(
|
| + scoped_refptr<base::MessageLoopProxy> origin_loop) {
|
| + return scoped_ptr<MicroBenchmarkImpl>(new RasterizeAndRecordBenchmarkImpl(
|
| + origin_loop,
|
| + settings_.get(),
|
| + base::Bind(&RasterizeAndRecordBenchmark::RecordRasterResults,
|
| + base::Unretained(this))));
|
| +}
|
| +
|
| +void RasterizeAndRecordBenchmark::Run(Layer* layer) {
|
| + layer->RunMicroBenchmark(this);
|
| +}
|
| +
|
| +void RasterizeAndRecordBenchmark::RunOnLayer(PictureLayer* layer) {
|
| + ContentLayerClient* painter = layer->client();
|
| + gfx::Size content_bounds = layer->content_bounds();
|
| +
|
| + SkTileGridPicture::TileGridInfo tile_grid_info;
|
| + tile_grid_info.fTileInterval.set(kTileGridSize - 2 * kTileGridBorder,
|
| + kTileGridSize - 2 * kTileGridBorder);
|
| + tile_grid_info.fMargin.set(kTileGridBorder, kTileGridBorder);
|
| + tile_grid_info.fOffset.set(-kTileGridBorder, -kTileGridBorder);
|
| +
|
| + gfx::Rect visible_content_rect = gfx::ScaleToEnclosingRect(
|
| + layer->visible_content_rect(), 1.f / layer->contents_scale_x());
|
| + if (visible_content_rect.IsEmpty())
|
| + return;
|
| +
|
| + scoped_refptr<Picture> picture = Picture::Create(visible_content_rect);
|
| +
|
| + base::TimeDelta min_time =
|
| + base::TimeDelta::FromInternalValue(std::numeric_limits<int64>::max());
|
| + for (int i = 0; i < record_repeat_count_; ++i) {
|
| + base::TimeTicks start = Now();
|
| + picture->Record(painter, tile_grid_info);
|
| + base::TimeTicks end = Now();
|
| + base::TimeDelta duration = end - start;
|
| + if (duration < min_time)
|
| + min_time = duration;
|
| + }
|
| +
|
| + record_results_.pixels_recorded +=
|
| + visible_content_rect.width() * visible_content_rect.height();
|
| + record_results_.total_best_time += min_time;
|
| +}
|
| +
|
| +RasterizeAndRecordBenchmark::RecordResults::RecordResults()
|
| + : pixels_recorded(0) {}
|
| +
|
| +RasterizeAndRecordBenchmark::RecordResults::~RecordResults() {}
|
| +
|
| +} // namespace cc
|
|
|