1/* 2 * Copyright © 2016 Red Hat. 3 * Copyright © 2016 Bas Nieuwenhuizen 4 * 5 * Based on radeon_winsys.h which is: 6 * Copyright 2008 Corbin Simpson <MostAwesomeDude@gmail.com> 7 * Copyright 2010 Marek Olšák <maraeo@gmail.com> 8 * 9 * Permission is hereby granted, free of charge, to any person obtaining a 10 * copy of this software and associated documentation files (the "Software"), 11 * to deal in the Software without restriction, including without limitation 12 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 13 * and/or sell copies of the Software, and to permit persons to whom the 14 * Software is furnished to do so, subject to the following conditions: 15 * 16 * The above copyright notice and this permission notice (including the next 17 * paragraph) shall be included in all copies or substantial portions of the 18 * Software. 19 * 20 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 21 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 22 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 23 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 24 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 25 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS 26 * IN THE SOFTWARE. 27 */ 28 29#ifndef RADV_RADEON_WINSYS_H 30#define RADV_RADEON_WINSYS_H 31 32#include <stdbool.h> 33#include <stdint.h> 34#include <stdio.h> 35#include <stdlib.h> 36#include <string.h> 37#include "util/u_math.h" 38#include "util/u_memory.h" 39#include <vulkan/vulkan.h> 40#include "amd_family.h" 41 42struct radeon_info; 43struct ac_surf_info; 44struct radeon_surf; 45 46enum radeon_bo_domain { /* bitfield */ 47 RADEON_DOMAIN_GTT = 2, 48 RADEON_DOMAIN_VRAM = 4, 49 RADEON_DOMAIN_VRAM_GTT = RADEON_DOMAIN_VRAM | RADEON_DOMAIN_GTT, 50 RADEON_DOMAIN_GDS = 8, 51 RADEON_DOMAIN_OA = 16, 52}; 53 54enum radeon_bo_flag { /* bitfield */ 55 RADEON_FLAG_GTT_WC = (1 << 0), 56 RADEON_FLAG_CPU_ACCESS = (1 << 1), 57 RADEON_FLAG_NO_CPU_ACCESS = (1 << 2), 58 RADEON_FLAG_VIRTUAL = (1 << 3), 59 RADEON_FLAG_VA_UNCACHED = (1 << 4), 60 RADEON_FLAG_IMPLICIT_SYNC = (1 << 5), 61 RADEON_FLAG_NO_INTERPROCESS_SHARING = (1 << 6), 62 RADEON_FLAG_READ_ONLY = (1 << 7), 63 RADEON_FLAG_32BIT = (1 << 8), 64 RADEON_FLAG_PREFER_LOCAL_BO = (1 << 9), 65 RADEON_FLAG_ZERO_VRAM = (1 << 10), 66 RADEON_FLAG_REPLAYABLE = (1 << 11), 67}; 68 69enum radeon_ctx_priority { 70 RADEON_CTX_PRIORITY_INVALID = -1, 71 RADEON_CTX_PRIORITY_LOW = 0, 72 RADEON_CTX_PRIORITY_MEDIUM, 73 RADEON_CTX_PRIORITY_HIGH, 74 RADEON_CTX_PRIORITY_REALTIME, 75}; 76 77enum radeon_value_id { 78 RADEON_ALLOCATED_VRAM, 79 RADEON_ALLOCATED_VRAM_VIS, 80 RADEON_ALLOCATED_GTT, 81 RADEON_TIMESTAMP, 82 RADEON_NUM_BYTES_MOVED, 83 RADEON_NUM_EVICTIONS, 84 RADEON_NUM_VRAM_CPU_PAGE_FAULTS, 85 RADEON_VRAM_USAGE, 86 RADEON_VRAM_VIS_USAGE, 87 RADEON_GTT_USAGE, 88 RADEON_GPU_TEMPERATURE, 89 RADEON_CURRENT_SCLK, 90 RADEON_CURRENT_MCLK, 91}; 92 93struct radeon_cmdbuf { 94 unsigned cdw; /* Number of used dwords. */ 95 unsigned max_dw; /* Maximum number of dwords. */ 96 uint32_t *buf; /* The base pointer of the chunk. */ 97}; 98 99#define RADEON_SURF_TYPE_MASK 0xFF 100#define RADEON_SURF_TYPE_SHIFT 0 101#define RADEON_SURF_TYPE_1D 0 102#define RADEON_SURF_TYPE_2D 1 103#define RADEON_SURF_TYPE_3D 2 104#define RADEON_SURF_TYPE_CUBEMAP 3 105#define RADEON_SURF_TYPE_1D_ARRAY 4 106#define RADEON_SURF_TYPE_2D_ARRAY 5 107#define RADEON_SURF_MODE_MASK 0xFF 108#define RADEON_SURF_MODE_SHIFT 8 109 110#define RADEON_SURF_GET(v, field) \ 111 (((v) >> RADEON_SURF_##field##_SHIFT) & RADEON_SURF_##field##_MASK) 112#define RADEON_SURF_SET(v, field) (((v)&RADEON_SURF_##field##_MASK) << RADEON_SURF_##field##_SHIFT) 113#define RADEON_SURF_CLR(v, field) \ 114 ((v) & ~(RADEON_SURF_##field##_MASK << RADEON_SURF_##field##_SHIFT)) 115 116enum radeon_bo_layout { 117 RADEON_LAYOUT_LINEAR = 0, 118 RADEON_LAYOUT_TILED, 119 RADEON_LAYOUT_SQUARETILED, 120 121 RADEON_LAYOUT_UNKNOWN 122}; 123 124/* Tiling info for display code, DRI sharing, and other data. */ 125struct radeon_bo_metadata { 126 /* Tiling flags describing the texture layout for display code 127 * and DRI sharing. 128 */ 129 union { 130 struct { 131 enum radeon_bo_layout microtile; 132 enum radeon_bo_layout macrotile; 133 unsigned pipe_config; 134 unsigned bankw; 135 unsigned bankh; 136 unsigned tile_split; 137 unsigned mtilea; 138 unsigned num_banks; 139 unsigned stride; 140 bool scanout; 141 } legacy; 142 143 struct { 144 /* surface flags */ 145 unsigned swizzle_mode : 5; 146 bool scanout; 147 uint32_t dcc_offset_256b; 148 uint32_t dcc_pitch_max; 149 bool dcc_independent_64b_blocks; 150 bool dcc_independent_128b_blocks; 151 unsigned dcc_max_compressed_block_size; 152 } gfx9; 153 } u; 154 155 /* Additional metadata associated with the buffer, in bytes. 156 * The maximum size is 64 * 4. This is opaque for the winsys & kernel. 157 * Supported by amdgpu only. 158 */ 159 uint32_t size_metadata; 160 uint32_t metadata[64]; 161}; 162 163struct radeon_winsys_ctx; 164 165struct radeon_winsys_bo { 166 uint64_t va; 167 bool is_local; 168 bool vram_no_cpu_access; 169 bool use_global_list; 170 enum radeon_bo_domain initial_domain; 171}; 172struct radv_winsys_sem_counts { 173 uint32_t syncobj_count; 174 uint32_t syncobj_reset_count; /* for wait only, whether to reset the syncobj */ 175 uint32_t timeline_syncobj_count; 176 uint32_t *syncobj; 177 uint64_t *points; 178}; 179 180struct radv_winsys_sem_info { 181 bool cs_emit_signal; 182 bool cs_emit_wait; 183 struct radv_winsys_sem_counts wait; 184 struct radv_winsys_sem_counts signal; 185}; 186 187struct radv_winsys_bo_list { 188 struct radeon_winsys_bo **bos; 189 unsigned count; 190}; 191 192/* Kernel effectively allows 0-31. This sets some priorities for fixed 193 * functionality buffers */ 194enum { 195 RADV_BO_PRIORITY_APPLICATION_MAX = 28, 196 197 /* virtual buffers have 0 priority since the priority is not used. */ 198 RADV_BO_PRIORITY_VIRTUAL = 0, 199 200 RADV_BO_PRIORITY_METADATA = 10, 201 /* This should be considerably lower than most of the stuff below, 202 * but how much lower is hard to say since we don't know application 203 * assignments. Put it pretty high since it is GTT anyway. */ 204 RADV_BO_PRIORITY_QUERY_POOL = 29, 205 206 RADV_BO_PRIORITY_DESCRIPTOR = 30, 207 RADV_BO_PRIORITY_UPLOAD_BUFFER = 30, 208 RADV_BO_PRIORITY_FENCE = 30, 209 RADV_BO_PRIORITY_SHADER = 31, 210 RADV_BO_PRIORITY_SCRATCH = 31, 211 RADV_BO_PRIORITY_CS = 31, 212}; 213 214struct radeon_winsys { 215 void (*destroy)(struct radeon_winsys *ws); 216 217 void (*query_info)(struct radeon_winsys *ws, struct radeon_info *info); 218 219 uint64_t (*query_value)(struct radeon_winsys *ws, enum radeon_value_id value); 220 221 bool (*read_registers)(struct radeon_winsys *ws, unsigned reg_offset, unsigned num_registers, 222 uint32_t *out); 223 224 const char *(*get_chip_name)(struct radeon_winsys *ws); 225 226 VkResult (*buffer_create)(struct radeon_winsys *ws, uint64_t size, unsigned alignment, 227 enum radeon_bo_domain domain, enum radeon_bo_flag flags, 228 unsigned priority, uint64_t address, struct radeon_winsys_bo **out_bo); 229 230 void (*buffer_destroy)(struct radeon_winsys *ws, struct radeon_winsys_bo *bo); 231 void *(*buffer_map)(struct radeon_winsys_bo *bo); 232 233 VkResult (*buffer_from_ptr)(struct radeon_winsys *ws, void *pointer, uint64_t size, 234 unsigned priority, struct radeon_winsys_bo **out_bo); 235 236 VkResult (*buffer_from_fd)(struct radeon_winsys *ws, int fd, unsigned priority, 237 struct radeon_winsys_bo **out_bo, uint64_t *alloc_size); 238 239 bool (*buffer_get_fd)(struct radeon_winsys *ws, struct radeon_winsys_bo *bo, int *fd); 240 241 bool (*buffer_get_flags_from_fd)(struct radeon_winsys *ws, int fd, 242 enum radeon_bo_domain *domains, enum radeon_bo_flag *flags); 243 244 void (*buffer_unmap)(struct radeon_winsys_bo *bo); 245 246 void (*buffer_set_metadata)(struct radeon_winsys *ws, struct radeon_winsys_bo *bo, 247 struct radeon_bo_metadata *md); 248 void (*buffer_get_metadata)(struct radeon_winsys *ws, struct radeon_winsys_bo *bo, 249 struct radeon_bo_metadata *md); 250 251 VkResult (*buffer_virtual_bind)(struct radeon_winsys *ws, struct radeon_winsys_bo *parent, 252 uint64_t offset, uint64_t size, struct radeon_winsys_bo *bo, 253 uint64_t bo_offset); 254 255 VkResult (*buffer_make_resident)(struct radeon_winsys *ws, struct radeon_winsys_bo *bo, 256 bool resident); 257 258 VkResult (*ctx_create)(struct radeon_winsys *ws, enum radeon_ctx_priority priority, 259 struct radeon_winsys_ctx **ctx); 260 void (*ctx_destroy)(struct radeon_winsys_ctx *ctx); 261 262 bool (*ctx_wait_idle)(struct radeon_winsys_ctx *ctx, enum ring_type ring_type, int ring_index); 263 264 enum radeon_bo_domain (*cs_domain)(const struct radeon_winsys *ws); 265 266 struct radeon_cmdbuf *(*cs_create)(struct radeon_winsys *ws, enum ring_type ring_type); 267 268 void (*cs_destroy)(struct radeon_cmdbuf *cs); 269 270 void (*cs_reset)(struct radeon_cmdbuf *cs); 271 272 VkResult (*cs_finalize)(struct radeon_cmdbuf *cs); 273 274 void (*cs_grow)(struct radeon_cmdbuf *cs, size_t min_size); 275 276 VkResult (*cs_submit)(struct radeon_winsys_ctx *ctx, int queue_index, 277 struct radeon_cmdbuf **cs_array, unsigned cs_count, 278 struct radeon_cmdbuf *initial_preamble_cs, 279 struct radeon_cmdbuf *continue_preamble_cs, 280 struct radv_winsys_sem_info *sem_info, bool can_patch); 281 282 void (*cs_add_buffer)(struct radeon_cmdbuf *cs, struct radeon_winsys_bo *bo); 283 284 void (*cs_execute_secondary)(struct radeon_cmdbuf *parent, struct radeon_cmdbuf *child, 285 bool allow_ib2); 286 287 void (*cs_dump)(struct radeon_cmdbuf *cs, FILE *file, const int *trace_ids, int trace_id_count); 288 289 void (*dump_bo_ranges)(struct radeon_winsys *ws, FILE *file); 290 291 void (*dump_bo_log)(struct radeon_winsys *ws, FILE *file); 292 293 int (*surface_init)(struct radeon_winsys *ws, const struct ac_surf_info *surf_info, 294 struct radeon_surf *surf); 295 296 int (*create_syncobj)(struct radeon_winsys *ws, bool create_signaled, uint32_t *handle); 297 void (*destroy_syncobj)(struct radeon_winsys *ws, uint32_t handle); 298 299 void (*reset_syncobj)(struct radeon_winsys *ws, uint32_t handle); 300 void (*signal_syncobj)(struct radeon_winsys *ws, uint32_t handle, uint64_t point); 301 VkResult (*query_syncobj)(struct radeon_winsys *ws, uint32_t handle, uint64_t *point); 302 bool (*wait_syncobj)(struct radeon_winsys *ws, const uint32_t *handles, uint32_t handle_count, 303 bool wait_all, uint64_t timeout); 304 bool (*wait_timeline_syncobj)(struct radeon_winsys *ws, const uint32_t *handles, 305 const uint64_t *points, uint32_t handle_count, bool wait_all, 306 bool available, uint64_t timeout); 307 308 int (*export_syncobj)(struct radeon_winsys *ws, uint32_t syncobj, int *fd); 309 int (*import_syncobj)(struct radeon_winsys *ws, int fd, uint32_t *syncobj); 310 311 int (*export_syncobj_to_sync_file)(struct radeon_winsys *ws, uint32_t syncobj, int *fd); 312 313 /* Note that this, unlike the normal import, uses an existing syncobj. */ 314 int (*import_syncobj_from_sync_file)(struct radeon_winsys *ws, uint32_t syncobj, int fd); 315}; 316 317static inline void 318radeon_emit(struct radeon_cmdbuf *cs, uint32_t value) 319{ 320 cs->buf[cs->cdw++] = value; 321} 322 323static inline void 324radeon_emit_array(struct radeon_cmdbuf *cs, const uint32_t *values, unsigned count) 325{ 326 memcpy(cs->buf + cs->cdw, values, count * 4); 327 cs->cdw += count; 328} 329 330static inline uint64_t 331radv_buffer_get_va(struct radeon_winsys_bo *bo) 332{ 333 return bo->va; 334} 335 336static inline void 337radv_cs_add_buffer(struct radeon_winsys *ws, struct radeon_cmdbuf *cs, struct radeon_winsys_bo *bo) 338{ 339 if (bo->use_global_list) 340 return; 341 342 ws->cs_add_buffer(cs, bo); 343} 344 345#endif /* RADV_RADEON_WINSYS_H */ 346