Merge branch 'gpu_drm29' into 'main'

Couple of DRM property related improvements

See merge request redox-os/base!178
This commit is contained in:
Jeremy Soller
2026-03-18 15:38:03 -06:00
4 changed files with 47 additions and 50 deletions
Generated
+1
View File
@@ -591,6 +591,7 @@ name = "driver-graphics"
version = "0.1.0"
dependencies = [
"common",
"drm-fourcc",
"drm-sys",
"edid",
"inputd",
@@ -5,6 +5,7 @@ version = "0.1.0"
edition = "2021"
[dependencies]
drm-fourcc = "2.2.0"
drm-sys.workspace = true
#TODO: edid is abandoned, fork it an maintain?
edid = "0.3.0"
@@ -1,5 +1,6 @@
use std::ffi::c_char;
use std::fmt::Debug;
use std::mem;
use std::sync::Mutex;
use drm_sys::{
@@ -19,28 +20,14 @@ impl<T: GraphicsAdapter> KmsObjects<T> {
atomic: bool,
kind: KmsPropertyKind,
) -> KmsObjectId {
if name.len() > DRM_PROP_NAME_LEN as usize {
panic!("Property name {name} is too long");
}
match &kind {
KmsPropertyKind::Range(start, end) => assert!(start < end),
KmsPropertyKind::Enum(variants) => {
KmsPropertyKind::Enum(_variants) => {
// FIXME check duplicate variant numbers
for (variant_name, _) in variants {
if variant_name.len() > DRM_PROP_NAME_LEN as usize {
panic!("Property variant name {variant_name} is too long");
}
}
}
KmsPropertyKind::Blob => {}
KmsPropertyKind::Bitmask(bitmask_flags) => {
KmsPropertyKind::Bitmask(_bitmask_flags) => {
// FIXME check overlapping flag numbers
for (flag_name, _) in bitmask_flags {
if flag_name.len() > DRM_PROP_NAME_LEN as usize {
panic!("Property bitflag name {flag_name} is too long");
}
}
}
KmsPropertyKind::Object => {}
KmsPropertyKind::SignedRange(start, end) => assert!(start < end),
@@ -52,7 +39,7 @@ impl<T: GraphicsAdapter> KmsObjects<T> {
}
self.add(KmsProperty {
name: name_bytes,
name: KmsPropertyName::new("Property name", name),
immutable,
atomic,
kind,
@@ -96,9 +83,34 @@ impl<T: GraphicsAdapter> KmsObjects<T> {
}
}
#[derive(Copy, Clone)]
pub struct KmsPropertyName(pub [c_char; DRM_PROP_NAME_LEN as usize]);
impl KmsPropertyName {
fn new(context: &str, name: &str) -> KmsPropertyName {
if name.len() > DRM_PROP_NAME_LEN as usize {
panic!("{context} {name} is too long");
}
let mut name_bytes = [0; DRM_PROP_NAME_LEN as usize];
for (to, &from) in name_bytes.iter_mut().zip(name.as_bytes()) {
*to = from as c_char;
}
KmsPropertyName(name_bytes)
}
}
impl Debug for KmsPropertyName {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
let u8_bytes = unsafe { mem::transmute::<&[c_char], &[u8]>(&self.0) };
f.write_str(&String::from_utf8_lossy(u8_bytes).trim_end_matches('\0'))
}
}
#[derive(Debug)]
pub struct KmsProperty {
pub name: [c_char; DRM_PROP_NAME_LEN as usize],
pub name: KmsPropertyName,
pub immutable: bool,
pub atomic: bool,
pub kind: KmsPropertyKind,
@@ -107,9 +119,9 @@ pub struct KmsProperty {
#[derive(Debug)]
pub enum KmsPropertyKind {
Range(u64, u64),
Enum(Vec<(&'static str, u64)>),
Enum(Vec<(KmsPropertyName, u64)>),
Blob,
Bitmask(Vec<(&'static str, u64)>),
Bitmask(Vec<(KmsPropertyName, u64)>),
Object,
SignedRange(i64, i64),
}
@@ -146,7 +158,9 @@ macro_rules! define_properties {
KmsPropertyKind::Range($start, $end)
};
(@prop_kind enum { $($variant:ident = $value:expr,)* }) => {
KmsPropertyKind::Enum(vec![$((stringify!($variant), $value)),*])
KmsPropertyKind::Enum(vec![
$((KmsPropertyName::new("Property variant name", stringify!($variant)), $value)),*]
)
};
(@prop_kind blob) => {
KmsPropertyKind::Blob
+10 -29
View File
@@ -1,7 +1,6 @@
#![feature(macro_metavar_expr)]
use std::collections::{BTreeMap, HashMap};
use std::ffi::c_char;
use std::fmt::Debug;
use std::fs::File;
use std::io::{self, Write};
@@ -9,11 +8,11 @@ use std::os::fd::BorrowedFd;
use std::sync::{Arc, Mutex};
use std::{cmp, mem};
use drm_fourcc::DrmFourcc;
use drm_sys::{
drm_mode_modeinfo, drm_mode_property_enum, DRM_MODE_CURSOR_BO, DRM_MODE_CURSOR_MOVE,
DRM_MODE_PROP_ATOMIC, DRM_MODE_PROP_BITMASK, DRM_MODE_PROP_BLOB, DRM_MODE_PROP_ENUM,
DRM_MODE_PROP_IMMUTABLE, DRM_MODE_PROP_OBJECT, DRM_MODE_PROP_RANGE, DRM_MODE_PROP_SIGNED_RANGE,
DRM_PROP_NAME_LEN,
};
use inputd::{DisplayHandle, VtEventKind};
use libredox::Fd;
@@ -447,8 +446,6 @@ impl<T: GraphicsAdapter> SchemeSync for GraphicsSchemeInner<T> {
) -> Result<usize> {
use redox_ioctl::drm as ipc;
const DRM_FORMAT_ARGB8888: u32 = 0x34325241; // 'AR24' fourcc code, for ARGB8888
fn id_index(id: u32) -> u32 {
id & 0xFF
}
@@ -656,7 +653,7 @@ impl<T: GraphicsAdapter> SchemeSync for GraphicsSchemeInner<T> {
}),
ipc::MODE_GET_PROPERTY => ipc::DrmModeGetProperty::with(payload, |mut data| {
let property = self.objects.get_property(KmsObjectId(data.prop_id()))?;
data.set_name(property.name);
data.set_name(property.name.0);
let mut flags = 0;
if property.immutable {
flags |= DRM_MODE_PROP_IMMUTABLE;
@@ -678,17 +675,9 @@ impl<T: GraphicsAdapter> SchemeSync for GraphicsSchemeInner<T> {
data.set_enum_blob_ptr(
&variants
.iter()
.map(|&(name, value)| {
let mut name_bytes = [0; DRM_PROP_NAME_LEN as usize];
for (to, &from) in
name_bytes.iter_mut().zip(name.as_bytes())
{
*to = from as c_char;
}
drm_mode_property_enum {
name: name_bytes,
value,
}
.map(|&(name, value)| drm_mode_property_enum {
name: name.0,
value,
})
.collect::<Vec<_>>(),
);
@@ -709,17 +698,9 @@ impl<T: GraphicsAdapter> SchemeSync for GraphicsSchemeInner<T> {
data.set_enum_blob_ptr(
&bitmask_flags
.iter()
.map(|&(name, value)| {
let mut name_bytes = [0; DRM_PROP_NAME_LEN as usize];
for (to, &from) in
name_bytes.iter_mut().zip(name.as_bytes())
{
*to = from as c_char;
}
drm_mode_property_enum {
name: name_bytes,
value,
}
.map(|&(name, value)| drm_mode_property_enum {
name: name.0,
value,
})
.collect::<Vec<_>>(),
);
@@ -906,7 +887,7 @@ impl<T: GraphicsAdapter> SchemeSync for GraphicsSchemeInner<T> {
data.set_crtc_id(crtc_id.0);
data.set_fb_id(crtc.lock().unwrap().fb_id.0);
data.set_possible_crtcs(1 << i);
data.set_format_type_ptr(&[DRM_FORMAT_ARGB8888]);
data.set_format_type_ptr(&[DrmFourcc::Argb8888 as u32]);
Ok(0)
}),
ipc::MODE_OBJ_GET_PROPERTIES => {
@@ -966,7 +947,7 @@ impl<T: GraphicsAdapter> SchemeSync for GraphicsSchemeInner<T> {
data.set_width(fb.width);
data.set_height(fb.height);
data.set_pixel_format(DRM_FORMAT_ARGB8888);
data.set_pixel_format(DrmFourcc::Argb8888 as u32);
data.set_handles([*next_id, 0, 0, 0]);
data.set_pitches([fb.width * 4, 0, 0, 0]);
data.set_offsets([0; 4]);