File Index
Files and directories
Sign in
FILE

commands.rs

File preview with syntax highlighting.

linux-6.19.14/drivers/gpu/nova-core/gsp/fw/commands.rs RUST
  1// SPDX-License-Identifier: GPL-2.0
  2
  3use kernel::prelude::*;
  4use kernel::transmute::{AsBytes, FromBytes};
  5use kernel::{device, pci};
  6
  7use crate::gsp::GSP_PAGE_SIZE;
  8
  9use super::bindings;
 10
 11/// Payload of the `GspSetSystemInfo` command.
 12#[repr(transparent)]
 13pub(crate) struct GspSetSystemInfo {
 14    inner: bindings::GspSystemInfo,
 15}
 16static_assert!(size_of::<GspSetSystemInfo>() < GSP_PAGE_SIZE);
 17
 18impl GspSetSystemInfo {
 19    /// Returns an in-place initializer for the `GspSetSystemInfo` command.
 20    #[allow(non_snake_case)]
 21    pub(crate) fn init<'a>(dev: &'a pci::Device<device::Bound>) -> impl Init<Self, Error> + 'a {
 22        type InnerGspSystemInfo = bindings::GspSystemInfo;
 23        let init_inner = try_init!(InnerGspSystemInfo {
 24            gpuPhysAddr: dev.resource_start(0)?,
 25            gpuPhysFbAddr: dev.resource_start(1)?,
 26            gpuPhysInstAddr: dev.resource_start(3)?,
 27            nvDomainBusDeviceFunc: u64::from(dev.dev_id()),
 28
 29            // Using TASK_SIZE in r535_gsp_rpc_set_system_info() seems wrong because
 30            // TASK_SIZE is per-task. That's probably a design issue in GSP-RM though.
 31            maxUserVa: (1 << 47) - 4096,
 32            pciConfigMirrorBase: 0x088000,
 33            pciConfigMirrorSize: 0x001000,
 34
 35            PCIDeviceID: (u32::from(dev.device_id()) << 16) | u32::from(dev.vendor_id().as_raw()),
 36            PCISubDeviceID: (u32::from(dev.subsystem_device_id()) << 16)
 37                | u32::from(dev.subsystem_vendor_id()),
 38            PCIRevisionID: u32::from(dev.revision_id()),
 39            bIsPrimary: 0,
 40            bPreserveVideoMemoryAllocations: 0,
 41            ..Zeroable::init_zeroed()
 42        });
 43
 44        try_init!(GspSetSystemInfo {
 45            inner <- init_inner,
 46        })
 47    }
 48}
 49
 50// SAFETY: These structs don't meet the no-padding requirements of AsBytes but
 51//         that is not a problem because they are not used outside the kernel.
 52unsafe impl AsBytes for GspSetSystemInfo {}
 53
 54// SAFETY: These structs don't meet the no-padding requirements of FromBytes but
 55//         that is not a problem because they are not used outside the kernel.
 56unsafe impl FromBytes for GspSetSystemInfo {}
 57
 58#[repr(transparent)]
 59pub(crate) struct PackedRegistryEntry(bindings::PACKED_REGISTRY_ENTRY);
 60
 61impl PackedRegistryEntry {
 62    pub(crate) fn new(offset: u32, value: u32) -> Self {
 63        Self({
 64            bindings::PACKED_REGISTRY_ENTRY {
 65                nameOffset: offset,
 66
 67                // We only support DWORD types for now. Support for other types
 68                // will come later if required.
 69                type_: bindings::REGISTRY_TABLE_ENTRY_TYPE_DWORD as u8,
 70                __bindgen_padding_0: Default::default(),
 71                data: value,
 72                length: 0,
 73            }
 74        })
 75    }
 76}
 77
 78// SAFETY: Padding is explicit and will not contain uninitialized data.
 79unsafe impl AsBytes for PackedRegistryEntry {}
 80
 81/// Payload of the `SetRegistry` command.
 82#[repr(transparent)]
 83pub(crate) struct PackedRegistryTable {
 84    inner: bindings::PACKED_REGISTRY_TABLE,
 85}
 86
 87impl PackedRegistryTable {
 88    #[allow(non_snake_case)]
 89    pub(crate) fn init(num_entries: u32, size: u32) -> impl Init<Self> {
 90        type InnerPackedRegistryTable = bindings::PACKED_REGISTRY_TABLE;
 91        let init_inner = init!(InnerPackedRegistryTable {
 92            numEntries: num_entries,
 93            size,
 94            entries: Default::default()
 95        });
 96
 97        init!(PackedRegistryTable { inner <- init_inner })
 98    }
 99}
100
101// SAFETY: Padding is explicit and will not contain uninitialized data.
102unsafe impl AsBytes for PackedRegistryTable {}
103
104// SAFETY: This struct only contains integer types for which all bit patterns
105// are valid.
106unsafe impl FromBytes for PackedRegistryTable {}
107
108/// Payload of the `GetGspStaticInfo` command and message.
109#[repr(transparent)]
110pub(crate) struct GspStaticConfigInfo(bindings::GspStaticConfigInfo_t);
111
112impl GspStaticConfigInfo {
113    /// Returns a bytes array containing the (hopefully) zero-terminated name of this GPU.
114    pub(crate) fn gpu_name_str(&self) -> [u8; 64] {
115        self.0.gpuNameString
116    }
117}
118
119// SAFETY: Padding is explicit and will not contain uninitialized data.
120unsafe impl AsBytes for GspStaticConfigInfo {}
121
122// SAFETY: This struct only contains integer types for which all bit patterns
123// are valid.
124unsafe impl FromBytes for GspStaticConfigInfo {}
125
126// SAFETY: This struct only contains integer types and fixed-size arrays for which
127// all bit patterns are valid.
128unsafe impl Zeroable for GspStaticConfigInfo {}
~/ Read-only file preview.