diff options
author | posciak@chromium.org <posciak@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-06-17 22:55:22 +0000 |
---|---|---|
committer | posciak@chromium.org <posciak@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-06-17 22:55:22 +0000 |
commit | f7c0f6afd09a8b55db24eedc01ae440369b85871 (patch) | |
tree | d66d669f1571432b689eba49a7b780d624a5fda8 | |
parent | 09279e098d5360d558a6b10bccea46e98cc9bfe9 (diff) | |
download | chromium_src-f7c0f6afd09a8b55db24eedc01ae440369b85871.zip chromium_src-f7c0f6afd09a8b55db24eedc01ae440369b85871.tar.gz chromium_src-f7c0f6afd09a8b55db24eedc01ae440369b85871.tar.bz2 |
Error out if making a context current in VAVDA fails.
BUG=128423
TEST=Manual run.
Change-Id: Ic1d93a28e865dc13d6bd70edbcb7fa6a229f8503
Review URL: https://chromiumcodereview.appspot.com/10557025
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@142656 0039d316-1c4b-4281-b951-d872f2087c98
6 files changed, 71 insertions, 39 deletions
diff --git a/content/common/gpu/media/gpu_video_decode_accelerator.cc b/content/common/gpu/media/gpu_video_decode_accelerator.cc index 8ca1d87..935f806 100644 --- a/content/common/gpu/media/gpu_video_decode_accelerator.cc +++ b/content/common/gpu/media/gpu_video_decode_accelerator.cc @@ -37,9 +37,11 @@ using gpu::gles2::TextureManager; -static void MakeDecoderContextCurrent(gpu::gles2::GLES2Decoder* decoder) { +static bool MakeDecoderContextCurrent(gpu::gles2::GLES2Decoder* decoder) { bool success = decoder->MakeCurrent(); - DCHECK(success); + if (!success) + DLOG(ERROR) << "Failed to MakeCurrent()"; + return success; } GpuVideoDecodeAccelerator::GpuVideoDecodeAccelerator( @@ -136,8 +138,7 @@ void GpuVideoDecodeAccelerator::Initialize( #if !defined(OS_WIN) // Ensure we will be able to get a GL context at all before initializing // non-Windows VDAs. - if (!stub_->decoder()->MakeCurrent()) { - DLOG(ERROR) << "Failed to MakeCurrent()"; + if (!make_context_current_.Run()) { NotifyError(media::VideoDecodeAccelerator::PLATFORM_FAILURE); return; } diff --git a/content/common/gpu/media/gpu_video_decode_accelerator.h b/content/common/gpu/media/gpu_video_decode_accelerator.h index fa3938df..12c81f0 100644 --- a/content/common/gpu/media/gpu_video_decode_accelerator.h +++ b/content/common/gpu/media/gpu_video_decode_accelerator.h @@ -81,8 +81,9 @@ class GpuVideoDecodeAccelerator // Pointer to the underlying VideoDecodeAccelerator. scoped_refptr<media::VideoDecodeAccelerator> video_decode_accelerator_; - // Closure for making the relevant context current for GL calls. - base::Closure make_context_current_; + // Callback for making the relevant context current for GL calls. + // Returns false if failed. + base::Callback<bool(void)> make_context_current_; DISALLOW_IMPLICIT_CONSTRUCTORS(GpuVideoDecodeAccelerator); }; diff --git a/content/common/gpu/media/vaapi_h264_decoder.cc b/content/common/gpu/media/vaapi_h264_decoder.cc index d336b42..78859f8 100644 --- a/content/common/gpu/media/vaapi_h264_decoder.cc +++ b/content/common/gpu/media/vaapi_h264_decoder.cc @@ -156,7 +156,7 @@ class VaapiH264Decoder::DecodeSurface { DecodeSurface(const GLXFBConfig& fb_config, Display* x_display, VADisplay va_display, - const base::Closure& make_context_current, + const base::Callback<bool(void)>& make_context_current, VASurfaceID va_surface_id, int32 picture_buffer_id, uint32 texture_id, @@ -205,7 +205,7 @@ class VaapiH264Decoder::DecodeSurface { private: Display* x_display_; VADisplay va_display_; - base::Closure make_context_current_; + base::Callback<bool(void)> make_context_current_; VASurfaceID va_surface_id_; // Client-provided ids. @@ -233,7 +233,7 @@ VaapiH264Decoder::DecodeSurface::DecodeSurface( const GLXFBConfig& fb_config, Display* x_display, VADisplay va_display, - const base::Closure& make_context_current, + const base::Callback<bool(void)>& make_context_current, VASurfaceID va_surface_id, int32 picture_buffer_id, uint32 texture_id, @@ -246,10 +246,14 @@ VaapiH264Decoder::DecodeSurface::DecodeSurface( texture_id_(texture_id), width_(width), height_(height), - available_(false) { + available_(false), + x_pixmap_(0), + glx_pixmap_(0) { // Bind the surface to a texture of the given width and height, // allocating pixmaps as needed. - make_context_current_.Run(); + if (!make_context_current_.Run()) + return; + glEnable(GL_TEXTURE_2D); glBindTexture(GL_TEXTURE_2D, texture_id_); glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); @@ -271,8 +275,12 @@ VaapiH264Decoder::DecodeSurface::DecodeSurface( GL_NONE, }; - glx_pixmap_ = glXCreatePixmap(x_display_, fb_config, x_pixmap_, - pixmap_attr); + glx_pixmap_ = glXCreatePixmap(x_display_, fb_config, x_pixmap_, pixmap_attr); + if (!glx_pixmap_) { + // x_pixmap_ will be freed in the destructor. + DVLOG(1) << "Failed creating a GLX Pixmap for TFP"; + return; + } glBindTexture(GL_TEXTURE_2D, texture_id_); glXBindTexImageEXT(x_display_, glx_pixmap_, GLX_FRONT_LEFT_EXT, NULL); @@ -281,11 +289,14 @@ VaapiH264Decoder::DecodeSurface::DecodeSurface( } VaapiH264Decoder::DecodeSurface::~DecodeSurface() { - make_context_current_.Run(); // Unbind surface from texture and deallocate resources. - glXReleaseTexImageEXT(x_display_, glx_pixmap_, GLX_FRONT_LEFT_EXT); - glXDestroyGLXPixmap(x_display_, glx_pixmap_); - XFreePixmap(x_display_, x_pixmap_); + if (glx_pixmap_ && make_context_current_.Run()) { + glXReleaseTexImageEXT(x_display_, glx_pixmap_, GLX_FRONT_LEFT_EXT); + glXDestroyGLXPixmap(x_display_, glx_pixmap_); + } + + if (x_pixmap_) + XFreePixmap(x_display_, x_pixmap_); } void VaapiH264Decoder::DecodeSurface::Acquire(int32 input_id, int poc) { @@ -300,7 +311,9 @@ void VaapiH264Decoder::DecodeSurface::Release() { } bool VaapiH264Decoder::DecodeSurface::Sync() { - make_context_current_.Run(); + if (!make_context_current_.Run()) + return false; + // Put the decoded data into XPixmap bound to the texture. VAStatus va_res = VAAPI_PutSurface(va_display_, va_surface_id_, x_pixmap_, @@ -394,7 +407,8 @@ void VaapiH264Decoder::Destroy() { DestroyVASurfaces(); // fallthrough case kInitialized: - make_context_current_.Run(); + if (!make_context_current_.Run()) + break; va_res = VAAPI_DestroyConfig(va_display_, va_config_id_); VA_LOG_ON_ERROR(va_res, "vaDestroyConfig failed"); va_res = VAAPI_Terminate(va_display_); @@ -454,11 +468,12 @@ bool VaapiH264Decoder::InitializeFBConfig() { return true; } -bool VaapiH264Decoder::Initialize(media::VideoCodecProfile profile, - Display* x_display, - GLXContext glx_context, - const base::Closure& make_context_current, - const OutputPicCB& output_pic_cb) { +bool VaapiH264Decoder::Initialize( + media::VideoCodecProfile profile, + Display* x_display, + GLXContext glx_context, + const base::Callback<bool(void)>& make_context_current, + const OutputPicCB& output_pic_cb) { DCHECK_EQ(state_, kUninitialized); output_pic_cb_ = output_pic_cb; @@ -466,7 +481,9 @@ bool VaapiH264Decoder::Initialize(media::VideoCodecProfile profile, x_display_ = x_display; make_context_current_ = make_context_current; - make_context_current_.Run(); + if (!make_context_current_.Run()) + return false; + if (!SetProfile(profile)) { DVLOG(1) << "Unsupported profile"; return false; @@ -560,7 +577,8 @@ bool VaapiH264Decoder::CreateVASurfaces() { DCHECK_NE(pic_width_, -1); DCHECK_NE(pic_height_, -1); DCHECK_EQ(state_, kInitialized); - make_context_current_.Run(); + if (!make_context_current_.Run()) + return false; // Allocate VASurfaces in driver. VAStatus va_res = VAAPI_CreateSurfaces(va_display_, pic_width_, @@ -583,10 +601,11 @@ bool VaapiH264Decoder::CreateVASurfaces() { void VaapiH264Decoder::DestroyVASurfaces() { DCHECK(state_ == kDecoding || state_ == kError || state_ == kAfterReset); - make_context_current_.Run(); - decode_surfaces_.clear(); + if (!make_context_current_.Run()) + return; + VAStatus va_res = VAAPI_DestroyContext(va_display_, va_context_id_); VA_LOG_ON_ERROR(va_res, "vaDestroyContext failed"); @@ -699,7 +718,9 @@ VaapiH264Decoder::DecodeSurface* VaapiH264Decoder::UnassignSurfaceFromPoC( // Fill a VAPictureParameterBufferH264 to be later sent to the HW decoder. bool VaapiH264Decoder::SendPPS() { - make_context_current_.Run(); + if (!make_context_current_.Run()) + return false; + const H264PPS* pps = parser_.GetPPS(curr_pps_id_); DCHECK(pps); @@ -797,7 +818,9 @@ bool VaapiH264Decoder::SendPPS() { // Fill a VAIQMatrixBufferH264 to be later sent to the HW decoder. bool VaapiH264Decoder::SendIQMatrix() { - make_context_current_.Run(); + if (!make_context_current_.Run()) + return false; + const H264PPS* pps = parser_.GetPPS(curr_pps_id_); DCHECK(pps); @@ -844,7 +867,9 @@ bool VaapiH264Decoder::SendIQMatrix() { } bool VaapiH264Decoder::SendVASliceParam(H264SliceHeader* slice_hdr) { - make_context_current_.Run(); + if (!make_context_current_.Run()) + return false; + const H264PPS* pps = parser_.GetPPS(slice_hdr->pic_parameter_set_id); DCHECK(pps); @@ -948,7 +973,9 @@ bool VaapiH264Decoder::SendVASliceParam(H264SliceHeader* slice_hdr) { bool VaapiH264Decoder::SendSliceData(const uint8* ptr, size_t size) { - make_context_current_.Run(); + if (!make_context_current_.Run()) + return false; + // Can't help it, blame libva... void* non_const_ptr = const_cast<uint8*>(ptr); @@ -981,7 +1008,8 @@ bool VaapiH264Decoder::QueueSlice(H264SliceHeader* slice_hdr) { bool VaapiH264Decoder::DecodePicture() { DCHECK(!frame_ready_at_hw_); DCHECK(curr_pic_.get()); - make_context_current_.Run(); + if (!make_context_current_.Run()) + return false; static const size_t kMaxVABuffers = 32; DCHECK_LE(pending_va_bufs_.size(), kMaxVABuffers); diff --git a/content/common/gpu/media/vaapi_h264_decoder.h b/content/common/gpu/media/vaapi_h264_decoder.h index 9cfd35b..3d73abf 100644 --- a/content/common/gpu/media/vaapi_h264_decoder.h +++ b/content/common/gpu/media/vaapi_h264_decoder.h @@ -75,7 +75,7 @@ class VaapiH264Decoder { bool Initialize(media::VideoCodecProfile profile, Display* x_display, GLXContext glx_context, - const base::Closure& make_context_current, + const base::Callback<bool(void)>& make_context_current, const OutputPicCB& output_pic_cb) WARN_UNUSED_RESULT; void Destroy(); @@ -314,7 +314,7 @@ class VaapiH264Decoder { // make_context_current_.Run() is called at the top of the method. // X/GLX handles. Display* x_display_; - base::Closure make_context_current_; + base::Callback<bool(void)> make_context_current_; GLXFBConfig fb_config_; // VA handles. diff --git a/content/common/gpu/media/vaapi_video_decode_accelerator.cc b/content/common/gpu/media/vaapi_video_decode_accelerator.cc index 8acc1cc..29cc375 100644 --- a/content/common/gpu/media/vaapi_video_decode_accelerator.cc +++ b/content/common/gpu/media/vaapi_video_decode_accelerator.cc @@ -50,7 +50,8 @@ void VaapiVideoDecodeAccelerator::NotifyError(Error error) { } VaapiVideoDecodeAccelerator::VaapiVideoDecodeAccelerator( - Client* client, const base::Closure& make_context_current) + Client* client, + const base::Callback<bool(void)>& make_context_current) : make_context_current_(make_context_current), state_(kUninitialized), input_ready_(&lock_), diff --git a/content/common/gpu/media/vaapi_video_decode_accelerator.h b/content/common/gpu/media/vaapi_video_decode_accelerator.h index 27c8f3c..b4bd264 100644 --- a/content/common/gpu/media/vaapi_video_decode_accelerator.h +++ b/content/common/gpu/media/vaapi_video_decode_accelerator.h @@ -32,8 +32,9 @@ // Decoding tasks are performed in a separate decoding thread. class VaapiVideoDecodeAccelerator : public media::VideoDecodeAccelerator { public: - VaapiVideoDecodeAccelerator(Client* client, - const base::Closure& make_context_current); + VaapiVideoDecodeAccelerator( + Client* client, + const base::Callback<bool(void)>& make_context_current); // media::VideoDecodeAccelerator implementation. virtual bool Initialize(media::VideoCodecProfile profile) OVERRIDE; @@ -137,7 +138,7 @@ class VaapiVideoDecodeAccelerator : public media::VideoDecodeAccelerator { // Client-provided X/GLX state. Display* x_display_; GLXContext glx_context_; - base::Closure make_context_current_; + base::Callback<bool(void)> make_context_current_; // VAVDA state. enum State { |