Return results for fallible media APIs

Antonio Scandurra created

Change summary

Cargo.lock                               |  1 
crates/gpui/src/platform/mac/renderer.rs | 21 +++++++++++--------
crates/media/Cargo.toml                  |  1 
crates/media/build.rs                    |  1 
crates/media/src/bindings.h              |  3 +
crates/media/src/media.rs                | 28 +++++++++++++++----------
6 files changed, 34 insertions(+), 21 deletions(-)

Detailed changes

Cargo.lock 🔗

@@ -3033,6 +3033,7 @@ dependencies = [
 name = "media"
 version = "0.1.0"
 dependencies = [
+ "anyhow",
  "bindgen",
  "block",
  "core-foundation",

crates/gpui/src/platform/mac/renderer.rs 🔗

@@ -132,7 +132,7 @@ impl Renderer {
             "underline_fragment",
             pixel_format,
         );
-        let cv_texture_cache = CVMetalTextureCache::new(device.as_ptr());
+        let cv_texture_cache = CVMetalTextureCache::new(device.as_ptr()).unwrap();
         Self {
             sprite_cache,
             image_cache,
@@ -825,14 +825,17 @@ impl Renderer {
                 panic!("unsupported pixel format")
             };
 
-            let texture = self.cv_texture_cache.create_texture_from_image(
-                surface.image_buffer.as_concrete_TypeRef(),
-                ptr::null(),
-                pixel_format,
-                source_size.x() as usize,
-                source_size.y() as usize,
-                0,
-            );
+            let texture = self
+                .cv_texture_cache
+                .create_texture_from_image(
+                    surface.image_buffer.as_concrete_TypeRef(),
+                    ptr::null(),
+                    pixel_format,
+                    source_size.x() as usize,
+                    source_size.y() as usize,
+                    0,
+                )
+                .unwrap();
 
             align_offset(offset);
             let next_offset = *offset + mem::size_of::<shaders::GPUIImage>();

crates/media/Cargo.toml 🔗

@@ -8,6 +8,7 @@ path = "src/media.rs"
 doctest = false
 
 [dependencies]
+anyhow = "1.0"
 block = "0.1"
 core-foundation = "0.9.3"
 foreign-types = "0.3"

crates/media/build.rs 🔗

@@ -17,6 +17,7 @@ fn main() {
         .clang_arg(format!("-isysroot{}", sdk_path))
         .clang_arg("-xobjective-c")
         .allowlist_var("kCVPixelFormatType_.*")
+        .allowlist_var("kCVReturn.*")
         .parse_callbacks(Box::new(bindgen::CargoCallbacks))
         .layout_tests(false)
         .generate()

crates/media/src/bindings.h 🔗

@@ -1 +1,2 @@
-#import <CoreVideo/CVPixelFormatDescription.h>
+#import <CoreVideo/CVPixelFormatDescription.h>
+#import <CoreVideo/CVReturn.h>

crates/media/src/media.rs 🔗

@@ -33,16 +33,16 @@ pub mod io_surface {
 pub mod core_video {
     #![allow(non_snake_case)]
 
-    use std::ptr;
-
     use super::*;
     pub use crate::bindings::*;
+    use anyhow::{anyhow, Result};
     use core_foundation::{
         base::kCFAllocatorDefault, dictionary::CFDictionaryRef, mach_port::CFAllocatorRef,
     };
     use foreign_types::ForeignTypeRef;
     use io_surface::{IOSurface, IOSurfaceRef};
-    use metal::{MTLDevice, MTLPixelFormat, MTLTexture};
+    use metal::{MTLDevice, MTLPixelFormat};
+    use std::ptr;
 
     #[repr(C)]
     pub struct __CVImageBuffer(c_void);
@@ -97,7 +97,7 @@ pub mod core_video {
     impl_CFTypeDescription!(CVMetalTextureCache);
 
     impl CVMetalTextureCache {
-        pub fn new(metal_device: *mut MTLDevice) -> Self {
+        pub fn new(metal_device: *mut MTLDevice) -> Result<Self> {
             unsafe {
                 let mut this = ptr::null();
                 let result = CVMetalTextureCacheCreate(
@@ -107,8 +107,11 @@ pub mod core_video {
                     ptr::null_mut(),
                     &mut this,
                 );
-                // TODO: Check result
-                CVMetalTextureCache::wrap_under_create_rule(this)
+                if result == kCVReturnSuccess {
+                    Ok(CVMetalTextureCache::wrap_under_create_rule(this))
+                } else {
+                    Err(anyhow!("could not create texture cache, code: {}", result))
+                }
             }
         }
 
@@ -120,7 +123,7 @@ pub mod core_video {
             width: usize,
             height: usize,
             plane_index: usize,
-        ) -> CVMetalTexture {
+        ) -> Result<CVMetalTexture> {
             unsafe {
                 let mut this = ptr::null();
                 let result = CVMetalTextureCacheCreateTextureFromImage(
@@ -134,8 +137,11 @@ pub mod core_video {
                     plane_index,
                     &mut this,
                 );
-                // TODO: Check result
-                CVMetalTexture::wrap_under_create_rule(this)
+                if result == kCVReturnSuccess {
+                    Ok(CVMetalTexture::wrap_under_create_rule(this))
+                } else {
+                    Err(anyhow!("could not create texture, code: {}", result))
+                }
             }
         }
     }
@@ -149,7 +155,7 @@ pub mod core_video {
             metal_device: *const MTLDevice,
             texture_attributes: CFDictionaryRef,
             cache_out: *mut CVMetalTextureCacheRef,
-        ) -> i32; // TODO: This should be a CVReturn enum
+        ) -> CVReturn;
         fn CVMetalTextureCacheCreateTextureFromImage(
             allocator: CFAllocatorRef,
             texture_cache: CVMetalTextureCacheRef,
@@ -160,7 +166,7 @@ pub mod core_video {
             height: usize,
             plane_index: usize,
             texture_out: *mut CVMetalTextureRef,
-        ) -> i32;
+        ) -> CVReturn;
     }
 
     #[repr(C)]