]>
Commit | Line | Data |
---|---|---|
1 | // Copyright 2022 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 | use anyhow::anyhow; | |
6 | use anyhow::Result; | |
7 | ||
8 | use crate::bindings; | |
9 | ||
10 | /// A wrapper over `VAGenericValue` giving us safe access to the underlying union members. | |
11 | #[derive(Debug)] | |
12 | pub enum GenericValue { | |
13 | /// A wrapper over VAGenericValueTypeInteger | |
14 | Integer(i32), | |
15 | /// A wrapper over VAGenericValueTypeFloat | |
16 | Float(f32), | |
17 | /// A wrapper over VAGenericValueTypePointer | |
18 | Pointer(*mut std::os::raw::c_void), | |
19 | /// A wrapper over VAGenericValueTypeFunc | |
20 | Func(bindings::VAGenericFunc), | |
21 | } | |
22 | ||
23 | impl TryFrom<bindings::VAGenericValue> for GenericValue { | |
24 | type Error = anyhow::Error; | |
25 | ||
26 | fn try_from(value: bindings::VAGenericValue) -> Result<Self, Self::Error> { | |
27 | // Safe because we check the type before accessing the union. | |
28 | match value.type_ { | |
29 | // Safe because we check the type before accessing the union. | |
30 | bindings::VAGenericValueType::VAGenericValueTypeInteger => { | |
31 | Ok(Self::Integer(unsafe { value.value.i })) | |
32 | } | |
33 | bindings::VAGenericValueType::VAGenericValueTypeFloat => { | |
34 | Ok(Self::Float(unsafe { value.value.f })) | |
35 | } | |
36 | bindings::VAGenericValueType::VAGenericValueTypePointer => { | |
37 | Ok(Self::Pointer(unsafe { value.value.p })) | |
38 | } | |
39 | bindings::VAGenericValueType::VAGenericValueTypeFunc => { | |
40 | Ok(Self::Func(unsafe { value.value.fn_ })) | |
41 | } | |
42 | other => Err(anyhow!( | |
43 | "Conversion failed for unexpected VAGenericValueType: {}", | |
44 | other | |
45 | )), | |
46 | } | |
47 | } | |
48 | } |