Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
google
GitHub Repository: google/crosvm
Path: blob/main/devices/src/virtio/video/params.rs
5394 views
1
// Copyright 2020 The ChromiumOS Authors
2
// Use of this source code is governed by a BSD-style license that can be
3
// found in the LICENSE file.
4
5
//! Parameters for streams in virtio video devices.
6
7
use std::convert::From;
8
use std::convert::Into;
9
use std::convert::TryFrom;
10
11
use base::error;
12
use data_model::Le32;
13
14
use crate::virtio::video::command::QueueType;
15
use crate::virtio::video::command::ReadCmdError;
16
use crate::virtio::video::format::*;
17
use crate::virtio::video::protocol::*;
18
use crate::virtio::video::resource::ResourceType;
19
20
/// Safe wrapper of `virtio_video_params`.
21
/// Note that this struct doesn't have a field corresponding to `queue_type` in
22
/// `virtio_video_params`. The type of queue should be stored by one that has an `Params` instance.
23
#[derive(Debug, Default, Clone)]
24
pub struct Params {
25
// Use `Option<Format>` instead of `Format` because an image format may not be determined until
26
// video decoding is started in the decoder.
27
pub format: Option<Format>,
28
pub resource_type: ResourceType,
29
pub frame_width: u32,
30
pub frame_height: u32,
31
pub min_buffers: u32,
32
pub max_buffers: u32,
33
pub crop: Crop,
34
pub frame_rate: u32,
35
pub plane_formats: Vec<PlaneFormat>,
36
}
37
38
impl TryFrom<virtio_video_params> for Params {
39
type Error = ReadCmdError;
40
41
fn try_from(
42
virtio_video_params {
43
format,
44
frame_width,
45
frame_height,
46
min_buffers,
47
max_buffers,
48
crop,
49
frame_rate,
50
num_planes,
51
plane_formats,
52
..
53
}: virtio_video_params,
54
) -> Result<Self, Self::Error> {
55
let num_planes = Into::<u32>::into(num_planes); // as usize;
56
if num_planes as usize > plane_formats.len() {
57
error!(
58
"num_planes must not exceed {} but {}",
59
plane_formats.len(),
60
Into::<u32>::into(num_planes)
61
);
62
return Err(ReadCmdError::InvalidArgument);
63
}
64
let plane_formats = plane_formats[0..num_planes as usize]
65
.iter()
66
.map(|x| Into::<PlaneFormat>::into(*x))
67
.collect::<Vec<_>>();
68
69
Ok(Params {
70
format: Format::n(format.into()),
71
resource_type: Default::default(),
72
frame_width: frame_width.into(),
73
frame_height: frame_height.into(),
74
min_buffers: min_buffers.into(),
75
max_buffers: max_buffers.into(),
76
crop: crop.into(),
77
frame_rate: frame_rate.into(),
78
plane_formats,
79
})
80
}
81
}
82
83
impl TryFrom<virtio_video_params_ext> for Params {
84
type Error = ReadCmdError;
85
86
fn try_from(
87
virtio_video_params_ext {
88
base,
89
resource_type,
90
..
91
}: virtio_video_params_ext,
92
) -> Result<Self, Self::Error> {
93
let mut params = Params::try_from(base)?;
94
params.resource_type = match resource_type.into() {
95
VIRTIO_VIDEO_MEM_TYPE_GUEST_PAGES => ResourceType::GuestPages,
96
VIRTIO_VIDEO_MEM_TYPE_VIRTIO_OBJECT => ResourceType::VirtioObject,
97
_ => return Err(ReadCmdError::InvalidArgument),
98
};
99
100
Ok(params)
101
}
102
}
103
104
impl Params {
105
pub fn to_virtio_video_params(&self, queue_type: QueueType) -> virtio_video_params {
106
let Params {
107
format,
108
resource_type: _,
109
frame_width,
110
frame_height,
111
min_buffers,
112
max_buffers,
113
crop,
114
frame_rate,
115
plane_formats,
116
} = self;
117
let num_planes = Le32::from(plane_formats.len() as u32);
118
let mut p_fmts: [virtio_video_plane_format; VIRTIO_VIDEO_MAX_PLANES as usize] =
119
Default::default();
120
for (i, pf) in plane_formats.iter().enumerate() {
121
p_fmts[i] = Into::<virtio_video_plane_format>::into(*pf);
122
}
123
124
virtio_video_params {
125
queue_type: (queue_type as u32).into(),
126
format: format
127
.map(|f| Le32::from(f as u32))
128
.unwrap_or_else(|| Le32::from(0)),
129
frame_width: Le32::from(*frame_width),
130
frame_height: Le32::from(*frame_height),
131
min_buffers: Le32::from(*min_buffers),
132
max_buffers: Le32::from(*max_buffers),
133
crop: virtio_video_crop::from(*crop),
134
frame_rate: Le32::from(*frame_rate),
135
num_planes,
136
plane_formats: p_fmts,
137
}
138
}
139
140
pub fn to_virtio_video_params_ext(&self, queue_type: QueueType) -> virtio_video_params_ext {
141
let Params { resource_type, .. } = self;
142
143
let resource_type = match *resource_type {
144
ResourceType::GuestPages => VIRTIO_VIDEO_MEM_TYPE_GUEST_PAGES,
145
ResourceType::VirtioObject => VIRTIO_VIDEO_MEM_TYPE_VIRTIO_OBJECT,
146
};
147
148
virtio_video_params_ext {
149
base: self.to_virtio_video_params(queue_type),
150
resource_type: Le32::from(resource_type),
151
padding: Default::default(),
152
}
153
}
154
}
155
156