Chromium Code Reviews| Index: third_party/WebKit/Source/platform/testing/ImageDecodeBench.cpp |
| diff --git a/third_party/WebKit/Source/platform/testing/ImageDecodeBench.cpp b/third_party/WebKit/Source/platform/testing/ImageDecodeBench.cpp |
| index 11742a16be9d362831a00d0c6d9890075da9d734..7d1539721d518f9862524e60695f92cc660d42d9 100644 |
| --- a/third_party/WebKit/Source/platform/testing/ImageDecodeBench.cpp |
| +++ b/third_party/WebKit/Source/platform/testing/ImageDecodeBench.cpp |
| @@ -10,6 +10,13 @@ |
| // % ninja -C out/Release image_decode_bench && |
| // ./out/Release/image_decode_bench file [iterations] |
| // |
| +// The output is formatted for use in a csv file (comma-separated variable). |
| +// Each row represents suceessive frames in an animated image. |
|
scroggo_chromium
2017/05/22 13:07:40
successive*
cblume
2017/05/23 00:43:56
Done.
|
| +// Each column represents a successive iteration of decoding the whole animated |
|
scroggo_chromium
2017/05/22 13:07:40
I don't think this is correct. A row shows a singl
cblume
2017/05/23 00:43:56
Hrmmm I think this comment is correct.
With the n
scroggo_chromium
2017/05/23 15:42:23
Agreed. This is covered by the comment above. ("Ea
cblume
2017/05/23 19:44:34
That is probably a good idea.
I'll add comments af
|
| +// image. |
| +// This means non-animated images will show up as a column. |
|
scroggo_chromium
2017/05/22 13:07:40
nit: Instead of saying "as a column", I think it w
cblume
2017/05/23 00:43:56
Done.
|
| +// Raster timing also shows up as a column. |
|
scroggo_chromium
2017/05/22 13:07:40
Since you've moved raster timing to its own patch,
cblume
2017/05/23 00:43:56
Done.
|
| +// |
| // TODO(noel): Consider adding md5 checksum support to WTF. Use it to compute |
| // the decoded image frame md5 and output that value. |
| // |
| @@ -18,6 +25,7 @@ |
| // to http://crbug.com/398235#c103 and http://crbug.com/258324#c5 |
| #include <memory> |
| +#include <vector> |
| #include "base/command_line.h" |
| #include "platform/SharedBuffer.h" |
| #include "platform/image-decoders/ImageDecoder.h" |
| @@ -204,26 +212,63 @@ PassRefPtr<SharedBuffer> ReadFile(const char* file_name) { |
| return SharedBuffer::Create(buffer.get(), file_size); |
| } |
| -bool DecodeImageData(SharedBuffer* data, |
| - bool color_correction, |
| - size_t packet_size) { |
| - std::unique_ptr<ImageDecoder> decoder = ImageDecoder::Create( |
| - data, true, ImageDecoder::kAlphaPremultiplied, |
| - color_correction ? ColorBehavior::TransformToTargetForTesting() |
| - : ColorBehavior::Ignore()); |
| - if (!packet_size) { |
| - bool all_data_received = true; |
| - decoder->SetData(data, all_data_received); |
| - |
| - int frame_count = decoder->FrameCount(); |
| - for (int i = 0; i < frame_count; ++i) { |
| - if (!decoder->FrameBufferAtIndex(i)) |
| - return false; |
| +using FrameTimings = std::vector<double>; |
|
scroggo_chromium
2017/05/22 13:07:40
The names help, but I think a comment here might b
cblume
2017/05/23 00:43:56
I agree. Your suggested comment is very clear. Tha
|
| +using IterationsOfFrameTimings = std::vector<FrameTimings>; |
| + |
| +void Print2DResults(const IterationsOfFrameTimings& timings) { |
| + for (const std::vector<double>& iteration : timings) { |
| + for (double frame_time : iteration) { |
| + printf("%f,", frame_time); |
| } |
| + printf("\n"); |
| + } |
| + printf("\n"); |
| +} |
| - return !decoder->Failed(); |
| +void TimeDecode(ImageDecoder* decoder, |
| + PassRefPtr<SharedBuffer> data, |
| + size_t iterations) { |
| + bool all_data_received = true; |
| + decoder->SetData(data.Get(), all_data_received); |
| + |
| + size_t frame_count = decoder->FrameCount(); |
| + |
| + IterationsOfFrameTimings timings(iterations, FrameTimings(frame_count, 0.0)); |
| + |
| + for (size_t iteration = 0; iteration < iterations; ++iteration) { |
| + for (size_t frame_index = 0; frame_index < frame_count; ++frame_index) { |
| + double start_time = GetCurrentTime(); |
| + ImageFrame* frame = decoder->FrameBufferAtIndex(frame_index); |
| + double elapsed_time = GetCurrentTime() - start_time; |
| + if (frame->GetStatus() != ImageFrame::kFrameComplete) { |
|
scroggo_chromium
2017/05/22 13:07:40
Should this print an error message?
cblume
2017/05/23 00:43:56
Done.
I also am using exit(3); to mirror current b
|
| + return; |
| + } |
| + timings[iteration][frame_index] = elapsed_time; |
| + } |
| } |
| + Print2DResults(timings); |
| +} |
| + |
| +// This function mimics deferred decoding in Chromium when not all data has been |
| +// received yet. |
| +void TimePacketedDecode(ImageDecoder* decoder, |
| + PassRefPtr<SharedBuffer> data, |
| + size_t packet_size, |
| + size_t iterations) { |
| + // Find total frame count. |
| + // Doing this requires a decoder with full data (no packet size). |
| + std::unique_ptr<ImageDecoder> frame_count_decoder = |
| + ImageDecoder::Create(data.Get(), true, ImageDecoder::kAlphaPremultiplied, |
| + ColorBehavior::Ignore()); |
| + |
| + constexpr bool total_all_data_received = true; |
| + frame_count_decoder->SetData(data.Get(), total_all_data_received); |
| + size_t total_frame_count = frame_count_decoder->FrameCount(); |
| + |
| + IterationsOfFrameTimings timings(iterations, |
| + FrameTimings(total_frame_count, 0.0)); |
| + |
| RefPtr<SharedBuffer> packet_data = SharedBuffer::Create(); |
| size_t position = 0; |
| size_t next_frame_to_decode = 0; |
| @@ -236,20 +281,27 @@ bool DecodeImageData(SharedBuffer* data, |
| position += length; |
| bool all_data_received = position == data->size(); |
| - decoder->SetData(packet_data.Get(), all_data_received); |
| size_t frame_count = decoder->FrameCount(); |
| - for (; next_frame_to_decode < frame_count; ++next_frame_to_decode) { |
| - ImageFrame* frame = decoder->FrameBufferAtIndex(next_frame_to_decode); |
| - if (frame->GetStatus() != ImageFrame::kFrameComplete) |
| - break; |
| + for (size_t iteration = 0; iteration < iterations; ++iteration) { |
|
scroggo_chromium
2017/05/22 13:07:40
nit: I think this would be easier to follow if you
cblume
2017/05/23 00:43:56
Done.
|
| + for (; next_frame_to_decode < frame_count; ++next_frame_to_decode) { |
| + decoder->SetData(packet_data.Get(), all_data_received); |
| + double start_time = GetCurrentTime(); |
| + ImageFrame* frame = decoder->FrameBufferAtIndex(next_frame_to_decode); |
| + double elapsed_time = GetCurrentTime() - start_time; |
| + if (frame->GetStatus() != ImageFrame::kFrameComplete) |
| + break; |
| + timings[iteration][next_frame_to_decode] = elapsed_time; |
| + decoder->SetData(PassRefPtr<SegmentReader>(nullptr), false); |
| + decoder->ClearCacheExceptFrame(next_frame_to_decode); |
|
scroggo_chromium
2017/05/22 13:07:40
I thought we had agreed to remove this? Was that o
cblume
2017/05/23 00:43:56
Right.
I thought I had removed it, too.
It looks l
scroggo_chromium
2017/05/23 15:42:23
I don't think rebasing works the way you expect. T
cblume
2017/05/23 19:44:34
Right. I hadn't rebased by the time you saw this l
|
| + } |
| } |
| if (all_data_received || decoder->Failed()) |
|
scroggo_chromium
2017/05/22 13:07:40
Should this print an error statement?
cblume
2017/05/23 00:43:56
Done.
|
| - break; |
| + return; |
| } |
| - return !decoder->Failed(); |
| + Print2DResults(timings); |
| } |
| } // namespace |
| @@ -260,9 +312,10 @@ int Main(int argc, char* argv[]) { |
| // If the platform supports color correction, allow it to be controlled. |
| bool apply_color_correction = false; |
| - |
| if (argc >= 2 && strcmp(argv[1], "--color-correct") == 0) { |
| - apply_color_correction = (--argc, ++argv, true); |
| + --argc; |
| + ++argv; |
| + apply_color_correction = true; |
| gfx::ICCProfile profile = gfx::ICCProfileForTestingColorSpin(); |
| ColorBehavior::SetGlobalTargetColorProfile(profile); |
| } |
| @@ -321,33 +374,19 @@ int Main(int argc, char* argv[]) { |
| data->Data(); |
| - // Warm-up: throw out the first iteration for more consistent results. |
| - |
| - if (!DecodeImageData(data.Get(), apply_color_correction, packet_size)) { |
| - fprintf(stderr, "Image decode failed [%s]\n", argv[1]); |
| - exit(3); |
| - } |
| - |
| // Image decode bench for iterations. |
| - double total_time = 0.0; |
| - |
| - for (size_t i = 0; i < iterations; ++i) { |
| - double start_time = GetCurrentTime(); |
| - bool decoded = |
| - DecodeImageData(data.Get(), apply_color_correction, packet_size); |
| - double elapsed_time = GetCurrentTime() - start_time; |
| - total_time += elapsed_time; |
| - if (!decoded) { |
| - fprintf(stderr, "Image decode failed [%s]\n", argv[1]); |
| - exit(3); |
| - } |
| + std::unique_ptr<ImageDecoder> decoder = ImageDecoder::Create( |
| + data, true, ImageDecoder::kAlphaPremultiplied, |
| + apply_color_correction ? ColorBehavior::TransformToTargetForTesting() |
| + : ColorBehavior::Ignore()); |
| + if (packet_size) { |
| + blink::TimePacketedDecode(decoder.get(), data.Get(), packet_size, |
|
scroggo_chromium
2017/05/22 13:07:40
This whole file looks to be inside namespace blink
cblume
2017/05/23 00:43:56
Done.
|
| + iterations); |
| + } else { |
| + blink::TimeDecode(decoder.get(), data.Get(), iterations); |
| } |
| - // Results to stdout. |
| - |
| - double average_time = total_time / static_cast<double>(iterations); |
| - printf("%f %f\n", total_time, average_time); |
| return 0; |
| } |