| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166 |
- /* SPDX-License-Identifier: GPL-2.0-only OR MIT */
- /* Copyright (c) 2023 Imagination Technologies Ltd. */
- #ifndef PVR_HWRT_H
- #define PVR_HWRT_H
- #include <linux/compiler_attributes.h>
- #include <linux/kref.h>
- #include <linux/list.h>
- #include <linux/types.h>
- #include <linux/xarray.h>
- #include <uapi/drm/pvr_drm.h>
- #include "pvr_device.h"
- #include "pvr_rogue_fwif_shared.h"
- /* Forward declaration from pvr_free_list.h. */
- struct pvr_free_list;
- /* Forward declaration from pvr_gem.h. */
- struct pvr_fw_object;
- /**
- * struct pvr_hwrt_data - structure representing HWRT data
- */
- struct pvr_hwrt_data {
- /** @fw_obj: FW object representing the FW-side structure. */
- struct pvr_fw_object *fw_obj;
- /** @data: Local copy of FW-side structure. */
- struct rogue_fwif_hwrtdata data;
- /** @freelist_node: List node connecting this HWRT to the local freelist. */
- struct list_head freelist_node;
- /**
- * @srtc_obj: FW object representing shadow render target cache.
- *
- * Only valid if @max_rts > 1.
- */
- struct pvr_fw_object *srtc_obj;
- /**
- * @raa_obj: FW object representing renders accumulation array.
- *
- * Only valid if @max_rts > 1.
- */
- struct pvr_fw_object *raa_obj;
- /** @hwrt_dataset: Back pointer to owning HWRT dataset. */
- struct pvr_hwrt_dataset *hwrt_dataset;
- };
- /**
- * struct pvr_hwrt_dataset - structure representing a HWRT data set.
- */
- struct pvr_hwrt_dataset {
- /** @ref_count: Reference count of object. */
- struct kref ref_count;
- /** @pvr_dev: Pointer to device that owns this object. */
- struct pvr_device *pvr_dev;
- /** @common_fw_obj: FW object representing common FW-side structure. */
- struct pvr_fw_object *common_fw_obj;
- /** @common: Common HWRT data. */
- struct rogue_fwif_hwrtdata_common common;
- /** @data: HWRT data structures belonging to this set. */
- struct pvr_hwrt_data data[ROGUE_FWIF_NUM_RTDATAS];
- /** @free_lists: Free lists used by HWRT data set. */
- struct pvr_free_list *free_lists[ROGUE_FWIF_NUM_RTDATA_FREELISTS];
- /** @max_rts: Maximum render targets for this HWRT data set. */
- u16 max_rts;
- };
- struct pvr_hwrt_dataset *
- pvr_hwrt_dataset_create(struct pvr_file *pvr_file,
- struct drm_pvr_ioctl_create_hwrt_dataset_args *args);
- void
- pvr_destroy_hwrt_datasets_for_file(struct pvr_file *pvr_file);
- /**
- * pvr_hwrt_dataset_lookup() - Lookup HWRT dataset pointer from handle
- * @pvr_file: Pointer to pvr_file structure.
- * @handle: Object handle.
- *
- * Takes reference on dataset object. Call pvr_hwrt_dataset_put() to release.
- *
- * Returns:
- * * The requested object on success, or
- * * %NULL on failure (object does not exist in list, or is not a HWRT
- * dataset)
- */
- static __always_inline struct pvr_hwrt_dataset *
- pvr_hwrt_dataset_lookup(struct pvr_file *pvr_file, u32 handle)
- {
- struct pvr_hwrt_dataset *hwrt;
- xa_lock(&pvr_file->hwrt_handles);
- hwrt = xa_load(&pvr_file->hwrt_handles, handle);
- if (hwrt)
- kref_get(&hwrt->ref_count);
- xa_unlock(&pvr_file->hwrt_handles);
- return hwrt;
- }
- void
- pvr_hwrt_dataset_put(struct pvr_hwrt_dataset *hwrt);
- /**
- * pvr_hwrt_data_lookup() - Lookup HWRT data pointer from handle and index
- * @pvr_file: Pointer to pvr_file structure.
- * @handle: Object handle.
- * @index: Index of RT data within dataset.
- *
- * Takes reference on dataset object. Call pvr_hwrt_data_put() to release.
- *
- * Returns:
- * * The requested object on success, or
- * * %NULL on failure (object does not exist in list, or is not a HWRT
- * dataset, or index is out of range)
- */
- static __always_inline struct pvr_hwrt_data *
- pvr_hwrt_data_lookup(struct pvr_file *pvr_file, u32 handle, u32 index)
- {
- struct pvr_hwrt_dataset *hwrt_dataset = pvr_hwrt_dataset_lookup(pvr_file, handle);
- if (hwrt_dataset) {
- if (index < ARRAY_SIZE(hwrt_dataset->data))
- return &hwrt_dataset->data[index];
- pvr_hwrt_dataset_put(hwrt_dataset);
- }
- return NULL;
- }
- /**
- * pvr_hwrt_data_put() - Release reference on HWRT data
- * @hwrt: Pointer to HWRT data to release reference on
- */
- static __always_inline void
- pvr_hwrt_data_put(struct pvr_hwrt_data *hwrt)
- {
- if (hwrt)
- pvr_hwrt_dataset_put(hwrt->hwrt_dataset);
- }
- static __always_inline struct pvr_hwrt_data *
- pvr_hwrt_data_get(struct pvr_hwrt_data *hwrt)
- {
- if (hwrt)
- kref_get(&hwrt->hwrt_dataset->ref_count);
- return hwrt;
- }
- #endif /* PVR_HWRT_H */
|