Commit 4bb4e770 authored by ccameron's avatar ccameron Committed by Commit bot

Add CVPixelBufferRef memory tracking

Create a separate sequence number for GLImages created from
CVPixelBufferRefs (previously they had no sequence number, so they
would alias each other).

Make VTVideoDecodeAccelerator be a dump provider. This dumps through
the GLImage interface, and so it will correctly link the
CVPixelBufferRefs that with the command buffer textures.

Fix TextureManager's dump code to not assume that GLImage presence
and texture state BOUND are related (a texture can have a GLImage but
not be BOUND because it can't be textured out of directly).

BUG=704792
CQ_INCLUDE_TRYBOTS=master.tryserver.chromium.android:android_optional_gpu_tests_rel;master.tryserver.chromium.linux:linux_optional_gpu_tests_rel;master.tryserver.chromium.mac:mac_optional_gpu_tests_rel;master.tryserver.chromium.win:win_optional_gpu_tests_rel

Review-Url: https://codereview.chromium.org/2771923006
Cr-Commit-Position: refs/heads/master@{#460566}
parent 609da81d
......@@ -1756,17 +1756,15 @@ void Texture::DumpLevelMemory(base::trace_event::ProcessMemoryDump* pmd,
continue;
// If a level has a GLImage, ask the GLImage to dump itself.
// If a level does not have a GLImage bound to it, then dump the
// texture allocation also as the storage is not provided by the
// GLImage in that case.
if (level_infos[level_index].image) {
level_infos[level_index].image->OnMemoryDump(
pmd, client_tracing_id,
base::StringPrintf("%s/face_%d/level_%d", dump_name.c_str(),
face_index, level_index));
}
// If a level does not have a GLImage bound to it, then dump the
// texture allocation also as the storage is not provided by the
// GLImage in that case.
if (level_infos[level_index].image_state != BOUND) {
} else {
MemoryAllocatorDump* dump = pmd->CreateAllocatorDump(base::StringPrintf(
"%s/face_%d/level_%d", dump_name.c_str(), face_index, level_index));
dump->AddScalar(
......
......@@ -12,15 +12,18 @@
#include <algorithm>
#include <memory>
#include "base/atomic_sequence_num.h"
#include "base/bind.h"
#include "base/logging.h"
#include "base/mac/mac_logging.h"
#include "base/macros.h"
#include "base/memory/ptr_util.h"
#include "base/metrics/histogram_macros.h"
#include "base/strings/stringprintf.h"
#include "base/sys_byteorder.h"
#include "base/sys_info.h"
#include "base/threading/thread_task_runner_handle.h"
#include "base/trace_event/memory_dump_manager.h"
#include "base/version.h"
#include "media/base/limits.h"
#include "media/gpu/shared_memory_region.h"
......@@ -40,6 +43,12 @@ namespace media {
namespace {
// A sequence of ids for memory tracing.
base::StaticAtomicSequenceNumber g_memory_dump_ids;
// A sequence of shared memory ids for CVPixelBufferRefs.
base::StaticAtomicSequenceNumber g_cv_pixel_buffer_ids;
// Only H.264 with 4:2:0 chroma sampling is supported.
const VideoCodecProfile kSupportedProfiles[] = {
H264PROFILE_BASELINE, H264PROFILE_EXTENDED, H264PROFILE_MAIN,
......@@ -296,11 +305,34 @@ VTVideoDecodeAccelerator::VTVideoDecodeAccelerator(
callback_.decompressionOutputCallback = OutputThunk;
callback_.decompressionOutputRefCon = this;
weak_this_ = weak_this_factory_.GetWeakPtr();
memory_dump_id_ = g_memory_dump_ids.GetNext();
base::trace_event::MemoryDumpManager::GetInstance()->RegisterDumpProvider(
this, "VTVideoDecodeAccelerator", gpu_task_runner_);
}
VTVideoDecodeAccelerator::~VTVideoDecodeAccelerator() {
DVLOG(1) << __func__;
DCHECK(gpu_task_runner_->BelongsToCurrentThread());
base::trace_event::MemoryDumpManager::GetInstance()->UnregisterDumpProvider(
this);
}
bool VTVideoDecodeAccelerator::OnMemoryDump(
const base::trace_event::MemoryDumpArgs& args,
base::trace_event::ProcessMemoryDump* pmd) {
for (const auto& it : picture_info_map_) {
int32_t picture_id = it.first;
PictureInfo* picture_info = it.second.get();
if (picture_info->gl_image) {
std::string dump_name =
base::StringPrintf("media/vt_video_decode_accelerator_%d/picture_%d",
memory_dump_id_, picture_id);
picture_info->gl_image->OnMemoryDump(pmd, 0, dump_name);
}
}
return true;
}
bool VTVideoDecodeAccelerator::Initialize(const Config& config,
......@@ -1090,7 +1122,8 @@ bool VTVideoDecodeAccelerator::SendFrame(const Frame& frame) {
scoped_refptr<gl::GLImageIOSurface> gl_image(
new gl::GLImageIOSurface(frame.image_size, GL_BGRA_EXT));
if (!gl_image->InitializeWithCVPixelBuffer(
frame.image.get(), gfx::GenericSharedMemoryId(),
frame.image.get(),
gfx::GenericSharedMemoryId(g_cv_pixel_buffer_ids.GetNext()),
gfx::BufferFormat::YUV_420_BIPLANAR)) {
NOTIFY_STATUS("Failed to initialize GLImageIOSurface", PLATFORM_FAILURE,
SFT_PLATFORM_ERROR);
......
......@@ -20,6 +20,7 @@
#include "base/message_loop/message_loop.h"
#include "base/threading/thread.h"
#include "base/threading/thread_checker.h"
#include "base/trace_event/memory_dump_provider.h"
#include "media/filters/h264_parser.h"
#include "media/gpu/gpu_video_decode_accelerator_helpers.h"
#include "media/gpu/media_gpu_export.h"
......@@ -36,7 +37,8 @@ MEDIA_GPU_EXPORT bool InitializeVideoToolbox();
// VideoToolbox.framework implementation of the VideoDecodeAccelerator
// interface for Mac OS X (currently limited to 10.9+).
class VTVideoDecodeAccelerator : public VideoDecodeAccelerator {
class VTVideoDecodeAccelerator : public VideoDecodeAccelerator,
public base::trace_event::MemoryDumpProvider {
public:
explicit VTVideoDecodeAccelerator(
const MakeGLContextCurrentCallback& make_context_current_cb,
......@@ -58,6 +60,10 @@ class VTVideoDecodeAccelerator : public VideoDecodeAccelerator {
const scoped_refptr<base::SingleThreadTaskRunner>& decode_task_runner)
override;
// MemoryDumpProvider implementation.
bool OnMemoryDump(const base::trace_event::MemoryDumpArgs& args,
base::trace_event::ProcessMemoryDump* pmd) override;
// Called by OutputThunk() when VideoToolbox finishes decoding a frame.
void Output(void* source_frame_refcon,
OSStatus status,
......@@ -268,6 +274,9 @@ class VTVideoDecodeAccelerator : public VideoDecodeAccelerator {
bool missing_idr_logged_ = false;
H264POC poc_;
// Id number for this instance for memory dumps.
int memory_dump_id_ = 0;
//
// Shared state (set up and torn down on GPU thread).
//
......
......@@ -361,6 +361,14 @@ void GLImageIOSurface::OnMemoryDump(base::trace_event::ProcessMemoryDump* pmd,
base::trace_event::MemoryAllocatorDump::kUnitsBytes,
static_cast<uint64_t>(size_bytes));
// The process tracing id is to identify the GpuMemoryBuffer client that
// created the allocation. For CVPixelBufferRefs, there is no corresponding
// GpuMemoryBuffer, so use an invalid process id.
if (cv_pixel_buffer_) {
process_tracing_id =
base::trace_event::MemoryDumpManager::kInvalidTracingProcessId;
}
auto guid =
GetGenericSharedMemoryGUIDForTracing(process_tracing_id, io_surface_id_);
pmd->CreateSharedGlobalAllocatorDump(guid);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment