drivers/gpu/drm/amd/amdkfd/kfd_process.c
Source file repositories/reference/linux-study-clean/drivers/gpu/drm/amd/amdkfd/kfd_process.c
File Facts
- System
- Linux kernel
- Corpus path
drivers/gpu/drm/amd/amdkfd/kfd_process.c- Extension
.c- Size
- 61699 bytes
- Lines
- 2387
- Domain
- Driver Families
- Bucket
- drivers/gpu
- Inferred role
- Driver Families: implementation source
- Status
- source implementation candidate
Why This File Exists
Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Touches user memory; correctness depends on fault-safe copying and privilege boundary handling.
- Uses kernel synchronization; read lock ordering, sleepability, and interrupt context assumptions before translating.
- Allocates kernel memory; connect allocation flags and lifetime to context constraints.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/mutex.hlinux/log2.hlinux/sched.hlinux/sched/mm.hlinux/sched/task.hlinux/mmu_context.hlinux/slab.hlinux/notifier.hlinux/compat.hlinux/mman.hlinux/file.hlinux/pm_runtime.hamdgpu_amdkfd.hamdgpu.hamdgpu_reset.hkfd_priv.hkfd_device_queue_manager.hkfd_svm.hkfd_smi_events.hkfd_debug.h
Detected Declarations
struct mm_structstruct kfd_procfs_treestruct kfd_sdma_activity_handler_workareastruct temp_sdma_queue_liststruct send_exception_work_handler_workareafunction kfd_sdma_activity_workerfunction list_for_each_entryfunction list_for_each_entryfunction list_for_each_entryfunction list_for_each_entry_safefunction kfd_get_cu_occupancyfunction kfd_procfs_showfunction kfd_procfs_kobj_releasefunction kfd_procfs_initfunction kfd_procfs_shutdownfunction kfd_procfs_queue_showfunction kfd_procfs_stats_showfunction kfd_sysfs_counters_showfunction kfd_procfs_add_queuefunction kfd_sysfs_create_filefunction kfd_procfs_add_sysfs_statsfunction kfd_procfs_add_sysfs_countersfunction kfd_procfs_add_sysfs_filesfunction kfd_procfs_del_queuefunction kfd_process_create_wqfunction kfd_process_destroy_wqfunction kfd_process_free_gpuvmfunction kfd_process_alloc_gpuvmfunction kfd_process_device_reserve_ib_memfunction kfd_process_device_destroy_ib_memfunction kfd_create_process_sysfsfunction kfd_process_alloc_idfunction kfd_process_free_idfunction kfd_unref_processfunction kfd_process_device_free_bosfunction kfd_process_free_outstanding_kfd_bosfunction kfd_process_free_outstanding_kfd_bosfunction kfd_process_profiler_releasefunction kfd_process_destroy_pddsfunction kfd_process_remove_sysfsfunction for_each_set_bitfunction kfd_process_wait_gpu_reset_completefunction kfd_process_wq_releasefunction kfd_process_ref_releasefunction kfd_process_free_notifierfunction kfd_process_table_removefunction kfd_process_notifier_release_internalfunction hash_for_each_rcu
Annotated Snippet
struct kfd_procfs_tree {
struct kobject *kobj;
};
static struct kfd_procfs_tree procfs;
/*
* Structure for SDMA activity tracking
*/
struct kfd_sdma_activity_handler_workarea {
struct work_struct sdma_activity_work;
struct kfd_process_device *pdd;
uint64_t sdma_activity_counter;
};
struct temp_sdma_queue_list {
uint64_t __user *rptr;
uint64_t sdma_val;
unsigned int queue_id;
struct list_head list;
};
static void kfd_sdma_activity_worker(struct work_struct *work)
{
struct kfd_sdma_activity_handler_workarea *workarea;
struct kfd_process_device *pdd;
uint64_t val;
struct mm_struct *mm;
struct queue *q;
struct qcm_process_device *qpd;
struct device_queue_manager *dqm;
int ret = 0;
struct temp_sdma_queue_list sdma_q_list;
struct temp_sdma_queue_list *sdma_q, *next;
workarea = container_of(work, struct kfd_sdma_activity_handler_workarea,
sdma_activity_work);
pdd = workarea->pdd;
if (!pdd)
return;
dqm = pdd->dev->dqm;
qpd = &pdd->qpd;
if (!dqm || !qpd)
return;
/*
* Total SDMA activity is current SDMA activity + past SDMA activity
* Past SDMA count is stored in pdd.
* To get the current activity counters for all active SDMA queues,
* we loop over all SDMA queues and get their counts from user-space.
*
* We cannot call get_user() with dqm_lock held as it can cause
* a circular lock dependency situation. To read the SDMA stats,
* we need to do the following:
*
* 1. Create a temporary list of SDMA queue nodes from the qpd->queues_list,
* with dqm_lock/dqm_unlock().
* 2. Call get_user() for each node in temporary list without dqm_lock.
* Save the SDMA count for each node and also add the count to the total
* SDMA count counter.
* Its possible, during this step, a few SDMA queue nodes got deleted
* from the qpd->queues_list.
* 3. Do a second pass over qpd->queues_list to check if any nodes got deleted.
* If any node got deleted, its SDMA count would be captured in the sdma
* past activity counter. So subtract the SDMA counter stored in step 2
* for this node from the total SDMA count.
*/
INIT_LIST_HEAD(&sdma_q_list.list);
/*
* Create the temp list of all SDMA queues
*/
dqm_lock(dqm);
list_for_each_entry(q, &qpd->queues_list, list) {
if ((q->properties.type != KFD_QUEUE_TYPE_SDMA) &&
(q->properties.type != KFD_QUEUE_TYPE_SDMA_XGMI))
continue;
sdma_q = kzalloc_obj(struct temp_sdma_queue_list);
if (!sdma_q) {
dqm_unlock(dqm);
goto cleanup;
}
INIT_LIST_HEAD(&sdma_q->list);
sdma_q->rptr = (uint64_t __user *)q->properties.read_ptr;
sdma_q->queue_id = q->properties.queue_id;
list_add_tail(&sdma_q->list, &sdma_q_list.list);
}
Annotation
- Immediate include surface: `linux/mutex.h`, `linux/log2.h`, `linux/sched.h`, `linux/sched/mm.h`, `linux/sched/task.h`, `linux/mmu_context.h`, `linux/slab.h`, `linux/notifier.h`.
- Detected declarations: `struct mm_struct`, `struct kfd_procfs_tree`, `struct kfd_sdma_activity_handler_workarea`, `struct temp_sdma_queue_list`, `struct send_exception_work_handler_workarea`, `function kfd_sdma_activity_worker`, `function list_for_each_entry`, `function list_for_each_entry`, `function list_for_each_entry`, `function list_for_each_entry_safe`.
- Atlas domain: Driver Families / drivers/gpu.
- Implementation status: source implementation candidate.
- This snippet crosses the user/kernel memory boundary; validate fault handling and access checks before translating the pattern.
- Synchronization appears in or near this file; preserve lock ordering, sleepability, and interrupt-context constraints.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.