drivers/gpu/drm/xe/xe_bo.c
Source file repositories/reference/linux-study-clean/drivers/gpu/drm/xe/xe_bo.c
File Facts
- System
- Linux kernel
- Corpus path
drivers/gpu/drm/xe/xe_bo.c- Extension
.c- Size
- 105443 bytes
- Lines
- 3897
- 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.
- Touches IRQ or DMA behavior; this matters for the representative real-device path.
- 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
xe_bo.hlinux/dma-buf.hlinux/nospec.hdrm/drm_drv.hdrm/drm_dumb_buffers.hdrm/drm_gem_ttm_helper.hdrm/drm_managed.hdrm/ttm/ttm_backup.hdrm/ttm/ttm_device.hdrm/ttm/ttm_placement.hdrm/ttm/ttm_tt.huapi/drm/xe_drm.hkunit/static_stub.htrace/events/gpu_mem.hxe_device.hxe_dma_buf.hxe_drm_client.hxe_ggtt.hxe_map.hxe_migrate.hxe_pat.hxe_pm.hxe_preempt_fence.hxe_pxp.hxe_res_cursor.hxe_shrinker.hxe_sriov_vf_ccs.hxe_tile.hxe_trace_bo.hxe_ttm_stolen_mgr.hxe_vm.hxe_vram_types.h
Detected Declarations
struct xe_ttm_ttfunction for_each_iffunction resource_is_stolen_vramfunction resource_is_vramfunction xe_bo_is_vramfunction xe_bo_is_stolenfunction xe_bo_has_single_placementfunction devmemfunction xe_bo_is_vm_boundfunction xe_bo_is_userfunction mem_type_to_migratefunction try_add_systemfunction force_contiguousfunction vram_bo_flag_to_tile_idfunction bo_vram_flags_to_vram_placementfunction add_vramfunction try_add_vramfunction for_each_set_bo_vram_flagfunction try_add_stolenfunction __xe_bo_placement_for_flagsfunction xe_bo_placement_for_flagsfunction xe_evict_flagsfunction xe_tt_map_sgfunction xe_tt_unmap_sgfunction xe_ttm_tt_account_addfunction xe_ttm_tt_account_subtractfunction update_global_total_pagesfunction xe_ttm_tt_populatefunction xe_ttm_tt_unpopulatefunction xe_ttm_tt_destroyfunction xe_ttm_resource_visiblefunction xe_bo_is_visible_vramfunction xe_ttm_io_mem_reservefunction xe_bo_trigger_rebindfunction drm_gem_for_each_gpuvm_bofunction drm_gpuvm_bo_for_each_vafunction unmap_attachmentfunction xe_bo_move_notifyfunction usfunction xe_bo_set_purgeable_shrinkerfunction xe_bo_set_purgeable_statefunction xe_ttm_bo_purgefunction xe_bo_movefunction xe_bo_shrink_purgefunction xe_bo_eviction_valuablefunction drm_gem_for_each_gpuvm_bofunction xe_bo_shrinkfunction xe_bo_notifier_prepare_pinned
Annotated Snippet
struct xe_ttm_tt {
struct ttm_tt ttm;
struct sg_table sgt;
struct sg_table *sg;
/** @purgeable: Whether the content of the pages of @ttm is purgeable. */
bool purgeable;
};
static int xe_tt_map_sg(struct xe_device *xe, struct ttm_tt *tt)
{
struct xe_ttm_tt *xe_tt = container_of(tt, struct xe_ttm_tt, ttm);
unsigned long num_pages = tt->num_pages;
int ret;
XE_WARN_ON((tt->page_flags & TTM_TT_FLAG_EXTERNAL) &&
!(tt->page_flags & TTM_TT_FLAG_EXTERNAL_MAPPABLE));
if (xe_tt->sg)
return 0;
ret = sg_alloc_table_from_pages_segment(&xe_tt->sgt, tt->pages,
num_pages, 0,
(u64)num_pages << PAGE_SHIFT,
xe_sg_segment_size(xe->drm.dev),
GFP_KERNEL);
if (ret)
return ret;
xe_tt->sg = &xe_tt->sgt;
ret = dma_map_sgtable(xe->drm.dev, xe_tt->sg, DMA_BIDIRECTIONAL,
DMA_ATTR_SKIP_CPU_SYNC);
if (ret) {
sg_free_table(xe_tt->sg);
xe_tt->sg = NULL;
return ret;
}
return 0;
}
static void xe_tt_unmap_sg(struct xe_device *xe, struct ttm_tt *tt)
{
struct xe_ttm_tt *xe_tt = container_of(tt, struct xe_ttm_tt, ttm);
if (xe_tt->sg) {
dma_unmap_sgtable(xe->drm.dev, xe_tt->sg,
DMA_BIDIRECTIONAL, 0);
sg_free_table(xe_tt->sg);
xe_tt->sg = NULL;
}
}
struct sg_table *xe_bo_sg(struct xe_bo *bo)
{
struct ttm_tt *tt = bo->ttm.ttm;
struct xe_ttm_tt *xe_tt = container_of(tt, struct xe_ttm_tt, ttm);
return xe_tt->sg;
}
/*
* Account ttm pages against the device shrinker's shrinkable and
* purgeable counts.
*/
static void xe_ttm_tt_account_add(struct xe_device *xe, struct ttm_tt *tt)
{
struct xe_ttm_tt *xe_tt = container_of(tt, struct xe_ttm_tt, ttm);
if (xe_tt->purgeable)
xe_shrinker_mod_pages(xe->mem.shrinker, 0, tt->num_pages);
else
xe_shrinker_mod_pages(xe->mem.shrinker, tt->num_pages, 0);
}
static void xe_ttm_tt_account_subtract(struct xe_device *xe, struct ttm_tt *tt)
{
struct xe_ttm_tt *xe_tt = container_of(tt, struct xe_ttm_tt, ttm);
if (xe_tt->purgeable)
xe_shrinker_mod_pages(xe->mem.shrinker, 0, -(long)tt->num_pages);
else
xe_shrinker_mod_pages(xe->mem.shrinker, -(long)tt->num_pages, 0);
}
static void update_global_total_pages(struct ttm_device *ttm_dev,
long num_pages)
{
#if IS_ENABLED(CONFIG_TRACE_GPU_MEM)
struct xe_device *xe = ttm_to_xe_device(ttm_dev);
u64 global_total_pages =
Annotation
- Immediate include surface: `xe_bo.h`, `linux/dma-buf.h`, `linux/nospec.h`, `drm/drm_drv.h`, `drm/drm_dumb_buffers.h`, `drm/drm_gem_ttm_helper.h`, `drm/drm_managed.h`, `drm/ttm/ttm_backup.h`.
- Detected declarations: `struct xe_ttm_tt`, `function for_each_if`, `function resource_is_stolen_vram`, `function resource_is_vram`, `function xe_bo_is_vram`, `function xe_bo_is_stolen`, `function xe_bo_has_single_placement`, `function devmem`, `function xe_bo_is_vm_bound`, `function xe_bo_is_user`.
- 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.
- IRQ or DMA behavior appears here, which is relevant to the selected PCIe/NVMe device path.
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.