static struct pb_buffer * amdgpu_bo_create(struct radeon_winsys *rws, unsigned size, unsigned alignment, boolean use_reusable_pool, enum radeon_bo_domain domain, enum radeon_bo_flag flags) { struct amdgpu_winsys *ws = amdgpu_winsys(rws); struct amdgpu_winsys_bo *bo; unsigned usage = 0; /* Don't use VRAM if the GPU doesn't have much. This is only the initial * domain. The kernel is free to move the buffer if it wants to. * * 64MB means no VRAM by todays standards. */ if (domain & RADEON_DOMAIN_VRAM && ws->info.vram_size <= 64*1024*1024) { domain = RADEON_DOMAIN_GTT; flags = RADEON_FLAG_GTT_WC; } /* Align size to page size. This is the minimum alignment for normal * BOs. Aligning this here helps the cached bufmgr. Especially small BOs, * like constant/uniform buffers, can benefit from better and more reuse. */ size = align(size, ws->gart_page_size); /* Only set one usage bit each for domains and flags, or the cache manager * might consider different sets of domains / flags compatible */ if (domain == RADEON_DOMAIN_VRAM_GTT) usage = 1 << 2; else usage = domain >> 1; assert(flags < sizeof(usage) * 8 - 3); usage |= 1 << (flags + 3); /* Get a buffer from the cache. */ if (use_reusable_pool) { bo = (struct amdgpu_winsys_bo*) pb_cache_reclaim_buffer(&ws->bo_cache, size, alignment, usage); if (bo) return &bo->base; } /* Create a new one. */ bo = amdgpu_create_bo(ws, size, alignment, usage, domain, flags); if (!bo) { /* Clear the cache and try again. */ pb_cache_release_all_buffers(&ws->bo_cache); bo = amdgpu_create_bo(ws, size, alignment, usage, domain, flags); if (!bo) return NULL; } bo->use_reusable_pool = use_reusable_pool; return &bo->base; }
static struct pb_buffer * amdgpu_bo_create(struct radeon_winsys *rws, uint64_t size, unsigned alignment, enum radeon_bo_domain domain, enum radeon_bo_flag flags) { struct amdgpu_winsys *ws = amdgpu_winsys(rws); struct amdgpu_winsys_bo *bo; unsigned usage = 0; /* Align size to page size. This is the minimum alignment for normal * BOs. Aligning this here helps the cached bufmgr. Especially small BOs, * like constant/uniform buffers, can benefit from better and more reuse. */ size = align64(size, ws->info.gart_page_size); alignment = align(alignment, ws->info.gart_page_size); /* Only set one usage bit each for domains and flags, or the cache manager * might consider different sets of domains / flags compatible */ if (domain == RADEON_DOMAIN_VRAM_GTT) usage = 1 << 2; else usage = domain >> 1; assert(flags < sizeof(usage) * 8 - 3); usage |= 1 << (flags + 3); /* Get a buffer from the cache. */ bo = (struct amdgpu_winsys_bo*) pb_cache_reclaim_buffer(&ws->bo_cache, size, alignment, usage); if (bo) return &bo->base; /* Create a new one. */ bo = amdgpu_create_bo(ws, size, alignment, usage, domain, flags); if (!bo) { /* Clear the cache and try again. */ pb_cache_release_all_buffers(&ws->bo_cache); bo = amdgpu_create_bo(ws, size, alignment, usage, domain, flags); if (!bo) return NULL; } bo->use_reusable_pool = true; return &bo->base; }