]> git.nihav.org Git - nihav-player.git/commitdiff
nihed-cros-libva: add exporting DRM Prime descriptor for pictures master
authorKostya Shishkov <kostya.shishkov@gmail.com>
Fri, 21 Mar 2025 14:05:22 +0000 (15:05 +0100)
committerKostya Shishkov <kostya.shishkov@gmail.com>
Fri, 21 Mar 2025 14:05:22 +0000 (15:05 +0100)
This may eventually come in handy if I ever get to exporting pictures
as EGL textures.

nihed-cros-libva/src/drmprime.rs [new file with mode: 0644]
nihed-cros-libva/src/lib.rs
nihed-cros-libva/src/picture.rs

diff --git a/nihed-cros-libva/src/drmprime.rs b/nihed-cros-libva/src/drmprime.rs
new file mode 100644 (file)
index 0000000..2089137
--- /dev/null
@@ -0,0 +1,128 @@
+/// Kernel DRM buffer memory type.
+pub const VA_SURFACE_ATTRIB_MEM_TYPE_KERNEL_DRM: u32 =      0x10000000;
+/// DRM PRIME memory type (old version)
+///
+/// This supports only single objects with restricted memory layout.
+/// Used with VASurfaceAttribExternalBuffers.
+pub const VA_SURFACE_ATTRIB_MEM_TYPE_DRM_PRIME: u32 =        0x20000000;
+/// DRM PRIME memory type
+///
+/// Used with VADRMPRIMESurfaceDescriptor.
+pub const VA_SURFACE_ATTRIB_MEM_TYPE_DRM_PRIME_2: u32 =      0x40000000;
+/// DRM PRIME3 memory type
+///
+/// Used with VADRMPRIME3SurfaceDescriptor.
+pub const VA_SURFACE_ATTRIB_MEM_TYPE_DRM_PRIME_3: u32 =      0x08000000;
+
+/// Surface object description.
+#[derive(Debug,Clone,Copy,Default)]
+#[repr(C)]
+pub struct VADRMPrimeObject {
+    /// DRM PRIME file descriptor for this object.
+    pub fd: i32,
+    /// Total size of this object (may include regions which are not part of the surface).
+    pub size: u32,
+    /// Format modifier applied to this object.
+    pub drm_format_modifier: u64,
+}
+
+/// Surface layer description.
+#[derive(Debug,Clone,Copy,Default)]
+#[repr(C)]
+pub struct VADRMPrimeLayer {
+    /// DRM format fourcc of this layer (DRM_FOURCC_*).
+    pub drm_format: u32,
+    /// Number of planes in this layer.
+    pub num_planes: u32,
+    /// Index in the objects array of the object containing each plane.
+    pub object_index: [u32; 4],
+    /// Offset within the object of each plane.
+    pub offset: [u32; 4],
+    /// Pitch of each plane.
+    pub pitch: [u32; 4],
+}
+
+/**
+ * External buffer descriptor for a DRM PRIME surface.
+ *
+ * For export, call vaExportSurfaceHandle() with mem_type set to
+ * VA_SURFACE_ATTRIB_MEM_TYPE_DRM_PRIME_2 and pass a pointer to an
+ * instance of this structure to fill.
+ * If VA_EXPORT_SURFACE_SEPARATE_LAYERS is specified on export, each
+ * layer will contain exactly one plane.  For example, an NV12
+ * surface will be exported as two layers, one of DRM_FORMAT_R8 and
+ * one of DRM_FORMAT_GR88.
+ * If VA_EXPORT_SURFACE_COMPOSED_LAYERS is specified on export,
+ * there will be exactly one layer.
+ *
+ * For import, call vaCreateSurfaces() with the MemoryType attribute
+ * set to VA_SURFACE_ATTRIB_MEM_TYPE_DRM_PRIME_2 and the
+ * ExternalBufferDescriptor attribute set to point to an array of
+ * num_surfaces instances of this structure.
+ * The number of planes which need to be provided for a given layer
+ * is dependent on both the format and the format modifier used for
+ * the objects containing it.  For example, the format DRM_FORMAT_RGBA
+ * normally requires one plane, but with the format modifier
+ * I915_FORMAT_MOD_Y_TILED_CCS it requires two planes - the first
+ * being the main data plane and the second containing the color
+ * control surface.
+ * Note that a given driver may only support a subset of possible
+ * representations of a particular format.  For example, it may only
+ * support NV12 surfaces when they are contained within a single DRM
+ * object, and therefore fail to create such surfaces if the two
+ * planes are in different DRM objects.
+ * Note that backend driver will retrieve the resource represent by fd,
+ * and a valid surface ID is generated. Backend driver will not close
+ * the file descriptor. Application should handle the release of the fd.
+ * releasing the fd will not impact the existence of the surface.
+ */
+#[derive(Debug,Clone,Copy,Default)]
+#[repr(C)]
+pub struct VADRMPRIMESurfaceDescriptor {
+    /// Pixel format fourcc of the whole surface (VA_FOURCC_*).
+    pub fourcc: u32,
+    /// Width of the surface in pixels.
+    pub width: u32,
+    /// Height of the surface in pixels.
+    pub height: u32,
+    /// Number of distinct DRM objects making up the surface.
+    pub num_objects: u32,
+    /// Description of each object.
+    pub objects: [VADRMPrimeObject; 4],
+    /// Number of layers making up the surface.
+    pub num_layers: u32,
+    /// Description of each layer in the surface.
+    pub layers: [VADRMPrimeLayer; 4],
+}
+
+/**
+ * External buffer descriptor for a DRM PRIME surface with flags
+ *
+ * This structure is an extention for VADRMPRIMESurfaceDescriptor,
+ * it has the same behavior as if used with VA_SURFACE_ATTRIB_MEM_TYPE_DRM_PRIME_2.
+ *
+ * The field "flags" is added, see "Surface external buffer descriptor flags".
+ * To use this structure, use VA_SURFACE_ATTRIB_MEM_TYPE_DRM_PRIME_3 instead.
+ */
+#[derive(Debug,Clone,Copy,Default)]
+#[repr(C)]
+pub struct VADRMPRIME3SurfaceDescriptor {
+    /// Pixel format fourcc of the whole surface (VA_FOURCC_*).
+    pub fourcc: u32,
+    /// Width of the surface in pixels.
+    pub width: u32,
+    /// Height of the surface in pixels.
+    pub height: u32,
+    /// Number of distinct DRM objects making up the surface.
+    pub num_objects: u32,
+    /// Description of each object.
+    pub objects: [VADRMPrimeObject; 4],
+    /// Number of layers making up the surface.
+    pub num_layers: u32,
+    /// Description of each layer in the surface.
+    pub layers: [VADRMPrimeLayer; 4],
+    /// flags. See "Surface external buffer descriptor flags".
+    pub flags: u32,
+    /// reserved bytes, must be zero
+    reserved: [u32; 8 - 1],
+}
index a095c1c35e69b268195251c003417a989106672f..2d3dbd5369c0cb85710058cc3307ec61a31679b0 100644 (file)
@@ -14,6 +14,7 @@ pub mod buffer;
 mod config;
 mod context;
 mod display;
+mod drmprime;
 mod formats;
 mod generic_value;
 mod image;
@@ -34,6 +35,7 @@ pub use buffer::*;
 pub use config::*;
 pub use context::*;
 pub use display::*;
+pub use drmprime::*;
 pub use formats::*;
 pub use generic_value::*;
 pub use image::*;
index 0d28b517edace6d979468f410464572a9e62f5b5..7dd579019fc59f52b8ef6351b68d644501a331b7 100644 (file)
@@ -12,6 +12,7 @@ use crate::bindings;
 use crate::buffer::Buffer;
 use crate::context::Context;
 use crate::display::Display;
+use crate::drmprime::*;
 use crate::status::*;
 use crate::surface::Surface;
 
@@ -244,6 +245,21 @@ impl<S: PictureState> Picture<S> {
     pub fn surface_size(&self) -> (u32, u32) {
         self.inner.surface.borrow().size()
     }
+
+    /// Returns DRM Prime surface descriptor.
+    pub fn surface_descriptor(&self) -> Option<VADRMPRIMESurfaceDescriptor> {
+        unsafe {
+            let mut desc = VADRMPRIMESurfaceDescriptor::default();
+            let display = self.inner.context.display().handle();
+            let handle = self.inner.surface.borrow().id();
+            let ret = crate::bindings::vaExportSurfaceHandle(display, handle, VA_SURFACE_ATTRIB_MEM_TYPE_DRM_PRIME_2, crate::constants::VA_EXPORT_SURFACE_READ_ONLY, &mut desc as *mut VADRMPRIMESurfaceDescriptor as *mut ::std::os::raw::c_void);
+            if ret == 0 {
+                Some(desc)
+            } else {
+                None
+            }
+        }
+    }
 }
 
 impl<S: PictureReclaimableSurface> Picture<S> {