1bf215546Sopenharmony_ci/* 2bf215546Sopenharmony_ci * Copyright © 2020 Intel Corporation 3bf215546Sopenharmony_ci * 4bf215546Sopenharmony_ci * Permission is hereby granted, free of charge, to any person obtaining a 5bf215546Sopenharmony_ci * copy of this software and associated documentation files (the "Software"), 6bf215546Sopenharmony_ci * to deal in the Software without restriction, including without limitation 7bf215546Sopenharmony_ci * the rights to use, copy, modify, merge, publish, distribute, sublicense, 8bf215546Sopenharmony_ci * and/or sell copies of the Software, and to permit persons to whom the 9bf215546Sopenharmony_ci * Software is furnished to do so, subject to the following conditions: 10bf215546Sopenharmony_ci * 11bf215546Sopenharmony_ci * The above copyright notice and this permission notice (including the next 12bf215546Sopenharmony_ci * paragraph) shall be included in all copies or substantial portions of the 13bf215546Sopenharmony_ci * Software. 14bf215546Sopenharmony_ci * 15bf215546Sopenharmony_ci * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16bf215546Sopenharmony_ci * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17bf215546Sopenharmony_ci * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 18bf215546Sopenharmony_ci * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19bf215546Sopenharmony_ci * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 20bf215546Sopenharmony_ci * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 21bf215546Sopenharmony_ci * DEALINGS IN THE SOFTWARE. 22bf215546Sopenharmony_ci */ 23bf215546Sopenharmony_ci 24bf215546Sopenharmony_ci#include <stdio.h> 25bf215546Sopenharmony_ci#include <stdlib.h> 26bf215546Sopenharmony_ci#include <unistd.h> 27bf215546Sopenharmony_ci#include <sys/ioctl.h> 28bf215546Sopenharmony_ci#include <sys/mman.h> 29bf215546Sopenharmony_ci#include <sys/types.h> 30bf215546Sopenharmony_ci#include <sys/socket.h> 31bf215546Sopenharmony_ci#include <sys/time.h> 32bf215546Sopenharmony_ci#include <sys/resource.h> 33bf215546Sopenharmony_ci#include <sys/un.h> 34bf215546Sopenharmony_ci 35bf215546Sopenharmony_ci#include "common/intel_gem.h" 36bf215546Sopenharmony_ci#include "dev/intel_device_info.h" 37bf215546Sopenharmony_ci#include "drm-uapi/i915_drm.h" 38bf215546Sopenharmony_ci#include "drm-shim/drm_shim.h" 39bf215546Sopenharmony_ci#include "util/macros.h" 40bf215546Sopenharmony_ci#include "util/vma.h" 41bf215546Sopenharmony_ci 42bf215546Sopenharmony_cistruct i915_device { 43bf215546Sopenharmony_ci struct intel_device_info devinfo; 44bf215546Sopenharmony_ci uint32_t device_id; 45bf215546Sopenharmony_ci}; 46bf215546Sopenharmony_ci 47bf215546Sopenharmony_cistruct i915_bo { 48bf215546Sopenharmony_ci struct shim_bo base; 49bf215546Sopenharmony_ci uint32_t tiling_mode; 50bf215546Sopenharmony_ci uint32_t stride; 51bf215546Sopenharmony_ci}; 52bf215546Sopenharmony_ci 53bf215546Sopenharmony_cistatic struct i915_device i915 = {}; 54bf215546Sopenharmony_ci 55bf215546Sopenharmony_cibool drm_shim_driver_prefers_first_render_node = true; 56bf215546Sopenharmony_ci 57bf215546Sopenharmony_cistatic int 58bf215546Sopenharmony_cii915_ioctl_noop(int fd, unsigned long request, void *arg) 59bf215546Sopenharmony_ci{ 60bf215546Sopenharmony_ci return 0; 61bf215546Sopenharmony_ci} 62bf215546Sopenharmony_ci 63bf215546Sopenharmony_cistatic int 64bf215546Sopenharmony_cii915_ioctl_gem_set_tiling(int fd, unsigned long request, void *arg) 65bf215546Sopenharmony_ci{ 66bf215546Sopenharmony_ci struct shim_fd *shim_fd = drm_shim_fd_lookup(fd); 67bf215546Sopenharmony_ci struct drm_i915_gem_set_tiling *tiling_arg = arg; 68bf215546Sopenharmony_ci struct i915_bo *bo = (struct i915_bo *) drm_shim_bo_lookup(shim_fd, tiling_arg->handle); 69bf215546Sopenharmony_ci 70bf215546Sopenharmony_ci if (!bo) 71bf215546Sopenharmony_ci return -1; 72bf215546Sopenharmony_ci 73bf215546Sopenharmony_ci bo->tiling_mode = tiling_arg->tiling_mode; 74bf215546Sopenharmony_ci bo->stride = tiling_arg->stride; 75bf215546Sopenharmony_ci 76bf215546Sopenharmony_ci return 0; 77bf215546Sopenharmony_ci} 78bf215546Sopenharmony_ci 79bf215546Sopenharmony_cistatic int 80bf215546Sopenharmony_cii915_ioctl_gem_get_tiling(int fd, unsigned long request, void *arg) 81bf215546Sopenharmony_ci{ 82bf215546Sopenharmony_ci struct shim_fd *shim_fd = drm_shim_fd_lookup(fd); 83bf215546Sopenharmony_ci struct drm_i915_gem_get_tiling *tiling_arg = arg; 84bf215546Sopenharmony_ci struct i915_bo *bo = (struct i915_bo *) drm_shim_bo_lookup(shim_fd, tiling_arg->handle); 85bf215546Sopenharmony_ci 86bf215546Sopenharmony_ci if (!bo) 87bf215546Sopenharmony_ci return -1; 88bf215546Sopenharmony_ci 89bf215546Sopenharmony_ci tiling_arg->tiling_mode = bo->tiling_mode; 90bf215546Sopenharmony_ci tiling_arg->swizzle_mode = I915_BIT_6_SWIZZLE_NONE; 91bf215546Sopenharmony_ci tiling_arg->phys_swizzle_mode = I915_BIT_6_SWIZZLE_NONE; 92bf215546Sopenharmony_ci 93bf215546Sopenharmony_ci return 0; 94bf215546Sopenharmony_ci} 95bf215546Sopenharmony_ci 96bf215546Sopenharmony_cistatic int 97bf215546Sopenharmony_cii915_ioctl_gem_create(int fd, unsigned long request, void *arg) 98bf215546Sopenharmony_ci{ 99bf215546Sopenharmony_ci struct shim_fd *shim_fd = drm_shim_fd_lookup(fd); 100bf215546Sopenharmony_ci struct drm_i915_gem_create *create = arg; 101bf215546Sopenharmony_ci struct i915_bo *bo = calloc(1, sizeof(*bo)); 102bf215546Sopenharmony_ci 103bf215546Sopenharmony_ci drm_shim_bo_init(&bo->base, create->size); 104bf215546Sopenharmony_ci 105bf215546Sopenharmony_ci create->handle = drm_shim_bo_get_handle(shim_fd, &bo->base); 106bf215546Sopenharmony_ci 107bf215546Sopenharmony_ci drm_shim_bo_put(&bo->base); 108bf215546Sopenharmony_ci 109bf215546Sopenharmony_ci return 0; 110bf215546Sopenharmony_ci} 111bf215546Sopenharmony_ci 112bf215546Sopenharmony_cistatic int 113bf215546Sopenharmony_cii915_ioctl_gem_mmap(int fd, unsigned long request, void *arg) 114bf215546Sopenharmony_ci{ 115bf215546Sopenharmony_ci struct shim_fd *shim_fd = drm_shim_fd_lookup(fd); 116bf215546Sopenharmony_ci struct drm_i915_gem_mmap *mmap_arg = arg; 117bf215546Sopenharmony_ci struct shim_bo *bo = drm_shim_bo_lookup(shim_fd, mmap_arg->handle); 118bf215546Sopenharmony_ci 119bf215546Sopenharmony_ci if (!bo) 120bf215546Sopenharmony_ci return -1; 121bf215546Sopenharmony_ci 122bf215546Sopenharmony_ci if (!bo->map) 123bf215546Sopenharmony_ci bo->map = drm_shim_mmap(shim_fd, bo->size, PROT_READ | PROT_WRITE, MAP_SHARED, -1, 124bf215546Sopenharmony_ci drm_shim_bo_get_mmap_offset(shim_fd, bo)); 125bf215546Sopenharmony_ci 126bf215546Sopenharmony_ci mmap_arg->addr_ptr = (uint64_t) (bo->map + mmap_arg->offset); 127bf215546Sopenharmony_ci 128bf215546Sopenharmony_ci return 0; 129bf215546Sopenharmony_ci} 130bf215546Sopenharmony_ci 131bf215546Sopenharmony_cistatic int 132bf215546Sopenharmony_cii915_ioctl_gem_userptr(int fd, unsigned long request, void *arg) 133bf215546Sopenharmony_ci{ 134bf215546Sopenharmony_ci struct shim_fd *shim_fd = drm_shim_fd_lookup(fd); 135bf215546Sopenharmony_ci struct drm_i915_gem_userptr *userptr = arg; 136bf215546Sopenharmony_ci struct i915_bo *bo = calloc(1, sizeof(*bo)); 137bf215546Sopenharmony_ci 138bf215546Sopenharmony_ci drm_shim_bo_init(&bo->base, userptr->user_size); 139bf215546Sopenharmony_ci 140bf215546Sopenharmony_ci userptr->handle = drm_shim_bo_get_handle(shim_fd, &bo->base); 141bf215546Sopenharmony_ci 142bf215546Sopenharmony_ci drm_shim_bo_put(&bo->base); 143bf215546Sopenharmony_ci 144bf215546Sopenharmony_ci return 0; 145bf215546Sopenharmony_ci} 146bf215546Sopenharmony_ci 147bf215546Sopenharmony_cistatic int 148bf215546Sopenharmony_cii915_ioctl_gem_context_create(int fd, unsigned long request, void *arg) 149bf215546Sopenharmony_ci{ 150bf215546Sopenharmony_ci struct drm_i915_gem_context_create *create = arg; 151bf215546Sopenharmony_ci 152bf215546Sopenharmony_ci create->ctx_id = 1; /* Just return a fake non zero ID. */ 153bf215546Sopenharmony_ci 154bf215546Sopenharmony_ci return 0; 155bf215546Sopenharmony_ci} 156bf215546Sopenharmony_ci 157bf215546Sopenharmony_cistatic int 158bf215546Sopenharmony_cii915_ioctl_gem_context_getparam(int fd, unsigned long request, void *arg) 159bf215546Sopenharmony_ci{ 160bf215546Sopenharmony_ci struct drm_i915_gem_context_param *param = arg; 161bf215546Sopenharmony_ci 162bf215546Sopenharmony_ci if (param->param == I915_CONTEXT_PARAM_GTT_SIZE) { 163bf215546Sopenharmony_ci if (i915.devinfo.ver >= 8 && i915.devinfo.platform != INTEL_PLATFORM_CHV) 164bf215546Sopenharmony_ci param->value = 1ull << 48; 165bf215546Sopenharmony_ci else 166bf215546Sopenharmony_ci param->value = 1ull << 31; 167bf215546Sopenharmony_ci } else { 168bf215546Sopenharmony_ci param->value = 0; 169bf215546Sopenharmony_ci } 170bf215546Sopenharmony_ci 171bf215546Sopenharmony_ci return 0; 172bf215546Sopenharmony_ci} 173bf215546Sopenharmony_ci 174bf215546Sopenharmony_cistatic int 175bf215546Sopenharmony_cii915_ioctl_get_param(int fd, unsigned long request, void *arg) 176bf215546Sopenharmony_ci{ 177bf215546Sopenharmony_ci drm_i915_getparam_t *gp = arg; 178bf215546Sopenharmony_ci 179bf215546Sopenharmony_ci switch (gp->param) { 180bf215546Sopenharmony_ci case I915_PARAM_CHIPSET_ID: 181bf215546Sopenharmony_ci *gp->value = i915.device_id; 182bf215546Sopenharmony_ci return 0; 183bf215546Sopenharmony_ci case I915_PARAM_REVISION: 184bf215546Sopenharmony_ci *gp->value = 0; 185bf215546Sopenharmony_ci return 0; 186bf215546Sopenharmony_ci case I915_PARAM_CS_TIMESTAMP_FREQUENCY: 187bf215546Sopenharmony_ci *gp->value = i915.devinfo.timestamp_frequency; 188bf215546Sopenharmony_ci return 0; 189bf215546Sopenharmony_ci case I915_PARAM_HAS_ALIASING_PPGTT: 190bf215546Sopenharmony_ci if (i915.devinfo.ver < 6) 191bf215546Sopenharmony_ci *gp->value = I915_GEM_PPGTT_NONE; 192bf215546Sopenharmony_ci else if (i915.devinfo.ver <= 7) 193bf215546Sopenharmony_ci *gp->value = I915_GEM_PPGTT_ALIASING; 194bf215546Sopenharmony_ci else 195bf215546Sopenharmony_ci *gp->value = I915_GEM_PPGTT_FULL; 196bf215546Sopenharmony_ci return 0; 197bf215546Sopenharmony_ci 198bf215546Sopenharmony_ci case I915_PARAM_NUM_FENCES_AVAIL: 199bf215546Sopenharmony_ci *gp->value = 8; /* gfx2/3 value, unused in brw/iris */ 200bf215546Sopenharmony_ci return 0; 201bf215546Sopenharmony_ci 202bf215546Sopenharmony_ci case I915_PARAM_HAS_BLT: 203bf215546Sopenharmony_ci *gp->value = 1; /* gfx2/3 value, unused in brw/iris */ 204bf215546Sopenharmony_ci return 0; 205bf215546Sopenharmony_ci 206bf215546Sopenharmony_ci case I915_PARAM_HAS_BSD: 207bf215546Sopenharmony_ci case I915_PARAM_HAS_LLC: 208bf215546Sopenharmony_ci case I915_PARAM_HAS_VEBOX: 209bf215546Sopenharmony_ci *gp->value = 0; /* gfx2/3 value, unused in brw/iris */ 210bf215546Sopenharmony_ci return 0; 211bf215546Sopenharmony_ci 212bf215546Sopenharmony_ci case I915_PARAM_HAS_GEM: 213bf215546Sopenharmony_ci case I915_PARAM_HAS_RELAXED_DELTA: 214bf215546Sopenharmony_ci case I915_PARAM_HAS_RELAXED_FENCING: 215bf215546Sopenharmony_ci case I915_PARAM_HAS_WAIT_TIMEOUT: 216bf215546Sopenharmony_ci case I915_PARAM_HAS_EXECBUF2: 217bf215546Sopenharmony_ci case I915_PARAM_HAS_EXEC_SOFTPIN: 218bf215546Sopenharmony_ci case I915_PARAM_HAS_EXEC_CAPTURE: 219bf215546Sopenharmony_ci case I915_PARAM_HAS_EXEC_FENCE: 220bf215546Sopenharmony_ci case I915_PARAM_HAS_EXEC_FENCE_ARRAY: 221bf215546Sopenharmony_ci case I915_PARAM_HAS_CONTEXT_ISOLATION: 222bf215546Sopenharmony_ci case I915_PARAM_HAS_EXEC_ASYNC: 223bf215546Sopenharmony_ci case I915_PARAM_HAS_EXEC_NO_RELOC: 224bf215546Sopenharmony_ci case I915_PARAM_HAS_EXEC_BATCH_FIRST: 225bf215546Sopenharmony_ci *gp->value = true; 226bf215546Sopenharmony_ci return 0; 227bf215546Sopenharmony_ci case I915_PARAM_HAS_EXEC_TIMELINE_FENCES: 228bf215546Sopenharmony_ci *gp->value = false; 229bf215546Sopenharmony_ci return 0; 230bf215546Sopenharmony_ci case I915_PARAM_CMD_PARSER_VERSION: 231bf215546Sopenharmony_ci /* Most recent version in drivers/gpu/drm/i915/i915_cmd_parser.c */ 232bf215546Sopenharmony_ci *gp->value = 10; 233bf215546Sopenharmony_ci return 0; 234bf215546Sopenharmony_ci case I915_PARAM_MMAP_VERSION: 235bf215546Sopenharmony_ci case I915_PARAM_MMAP_GTT_VERSION: 236bf215546Sopenharmony_ci *gp->value = 1; 237bf215546Sopenharmony_ci return 0; 238bf215546Sopenharmony_ci case I915_PARAM_SUBSLICE_TOTAL: 239bf215546Sopenharmony_ci *gp->value = 0; 240bf215546Sopenharmony_ci for (uint32_t s = 0; s < i915.devinfo.num_slices; s++) 241bf215546Sopenharmony_ci *gp->value += i915.devinfo.num_subslices[s]; 242bf215546Sopenharmony_ci return 0; 243bf215546Sopenharmony_ci case I915_PARAM_EU_TOTAL: 244bf215546Sopenharmony_ci *gp->value = 0; 245bf215546Sopenharmony_ci for (uint32_t s = 0; s < i915.devinfo.num_slices; s++) 246bf215546Sopenharmony_ci *gp->value += i915.devinfo.num_subslices[s] * i915.devinfo.max_eus_per_subslice; 247bf215546Sopenharmony_ci return 0; 248bf215546Sopenharmony_ci case I915_PARAM_PERF_REVISION: 249bf215546Sopenharmony_ci *gp->value = 3; 250bf215546Sopenharmony_ci return 0; 251bf215546Sopenharmony_ci case I915_PARAM_HAS_USERPTR_PROBE: 252bf215546Sopenharmony_ci *gp->value = 0; 253bf215546Sopenharmony_ci return 0; 254bf215546Sopenharmony_ci default: 255bf215546Sopenharmony_ci break; 256bf215546Sopenharmony_ci } 257bf215546Sopenharmony_ci 258bf215546Sopenharmony_ci fprintf(stderr, "Unknown DRM_IOCTL_I915_GET_PARAM %d\n", gp->param); 259bf215546Sopenharmony_ci return -1; 260bf215546Sopenharmony_ci} 261bf215546Sopenharmony_ci 262bf215546Sopenharmony_cistatic int 263bf215546Sopenharmony_ciquery_write_topology(struct drm_i915_query_item *item) 264bf215546Sopenharmony_ci{ 265bf215546Sopenharmony_ci struct drm_i915_query_topology_info *info = 266bf215546Sopenharmony_ci (void *) (uintptr_t) item->data_ptr; 267bf215546Sopenharmony_ci int32_t length = 268bf215546Sopenharmony_ci sizeof(*info) + 269bf215546Sopenharmony_ci DIV_ROUND_UP(i915.devinfo.num_slices, 8) + 270bf215546Sopenharmony_ci i915.devinfo.num_slices * DIV_ROUND_UP(i915.devinfo.num_subslices[0], 8) + 271bf215546Sopenharmony_ci i915.devinfo.num_slices * i915.devinfo.num_subslices[0] * 272bf215546Sopenharmony_ci DIV_ROUND_UP(i915.devinfo.max_eus_per_subslice, 8); 273bf215546Sopenharmony_ci 274bf215546Sopenharmony_ci if (item->length == 0) { 275bf215546Sopenharmony_ci item->length = length; 276bf215546Sopenharmony_ci return 0; 277bf215546Sopenharmony_ci } 278bf215546Sopenharmony_ci 279bf215546Sopenharmony_ci if (item->length < length) { 280bf215546Sopenharmony_ci fprintf(stderr, "size too small\n"); 281bf215546Sopenharmony_ci return -EINVAL; 282bf215546Sopenharmony_ci } 283bf215546Sopenharmony_ci 284bf215546Sopenharmony_ci if (info->flags) { 285bf215546Sopenharmony_ci fprintf(stderr, "invalid topology flags\n"); 286bf215546Sopenharmony_ci return -EINVAL; 287bf215546Sopenharmony_ci } 288bf215546Sopenharmony_ci 289bf215546Sopenharmony_ci info->max_slices = i915.devinfo.num_slices; 290bf215546Sopenharmony_ci info->max_subslices = i915.devinfo.num_subslices[0]; 291bf215546Sopenharmony_ci info->max_eus_per_subslice = i915.devinfo.max_eus_per_subslice; 292bf215546Sopenharmony_ci 293bf215546Sopenharmony_ci info->subslice_offset = DIV_ROUND_UP(i915.devinfo.num_slices, 8); 294bf215546Sopenharmony_ci info->subslice_stride = DIV_ROUND_UP(i915.devinfo.num_subslices[0], 8); 295bf215546Sopenharmony_ci info->eu_offset = info->subslice_offset + info->max_slices * info->subslice_stride; 296bf215546Sopenharmony_ci info->eu_stride = DIV_ROUND_UP(info->max_eus_per_subslice, 8); 297bf215546Sopenharmony_ci 298bf215546Sopenharmony_ci uint32_t slice_mask = (1u << i915.devinfo.num_slices) - 1; 299bf215546Sopenharmony_ci for (uint32_t i = 0; i < info->subslice_offset; i++) 300bf215546Sopenharmony_ci info->data[i] = (slice_mask >> (8 * i)) & 0xff; 301bf215546Sopenharmony_ci 302bf215546Sopenharmony_ci for (uint32_t s = 0; s < i915.devinfo.num_slices; s++) { 303bf215546Sopenharmony_ci uint32_t subslice_mask = (1u << i915.devinfo.num_subslices[s]) - 1; 304bf215546Sopenharmony_ci for (uint32_t i = 0; i < info->subslice_stride; i++) { 305bf215546Sopenharmony_ci info->data[info->subslice_offset + s * info->subslice_stride + i] = 306bf215546Sopenharmony_ci (subslice_mask >> (8 * i)) & 0xff; 307bf215546Sopenharmony_ci } 308bf215546Sopenharmony_ci } 309bf215546Sopenharmony_ci 310bf215546Sopenharmony_ci for (uint32_t s = 0; s < i915.devinfo.num_slices; s++) { 311bf215546Sopenharmony_ci for (uint32_t ss = 0; ss < i915.devinfo.num_subslices[s]; ss++) { 312bf215546Sopenharmony_ci uint32_t eu_mask = (1u << info->max_eus_per_subslice) - 1; 313bf215546Sopenharmony_ci for (uint32_t i = 0; i < DIV_ROUND_UP(info->max_eus_per_subslice, 8); i++) { 314bf215546Sopenharmony_ci info->data[info->eu_offset + 315bf215546Sopenharmony_ci (s * info->max_subslices + ss) * DIV_ROUND_UP(info->max_eus_per_subslice, 8) + i] = 316bf215546Sopenharmony_ci (eu_mask >> (8 * i)) & 0xff; 317bf215546Sopenharmony_ci } 318bf215546Sopenharmony_ci } 319bf215546Sopenharmony_ci } 320bf215546Sopenharmony_ci 321bf215546Sopenharmony_ci return 0; 322bf215546Sopenharmony_ci} 323bf215546Sopenharmony_ci 324bf215546Sopenharmony_cistatic int 325bf215546Sopenharmony_cii915_ioctl_query(int fd, unsigned long request, void *arg) 326bf215546Sopenharmony_ci{ 327bf215546Sopenharmony_ci struct drm_i915_query *query = arg; 328bf215546Sopenharmony_ci struct drm_i915_query_item *items = (void *) (uintptr_t) query->items_ptr; 329bf215546Sopenharmony_ci 330bf215546Sopenharmony_ci if (query->flags) { 331bf215546Sopenharmony_ci fprintf(stderr, "invalid query flags\n"); 332bf215546Sopenharmony_ci return -EINVAL; 333bf215546Sopenharmony_ci } 334bf215546Sopenharmony_ci 335bf215546Sopenharmony_ci for (uint32_t i = 0; i < query->num_items; i++) { 336bf215546Sopenharmony_ci struct drm_i915_query_item *item = &items[i]; 337bf215546Sopenharmony_ci 338bf215546Sopenharmony_ci switch (item->query_id) { 339bf215546Sopenharmony_ci case DRM_I915_QUERY_TOPOLOGY_INFO: { 340bf215546Sopenharmony_ci int ret = query_write_topology(item); 341bf215546Sopenharmony_ci if (ret) 342bf215546Sopenharmony_ci item->length = ret; 343bf215546Sopenharmony_ci break; 344bf215546Sopenharmony_ci } 345bf215546Sopenharmony_ci 346bf215546Sopenharmony_ci case DRM_I915_QUERY_ENGINE_INFO: { 347bf215546Sopenharmony_ci uint32_t num_copy = 1; 348bf215546Sopenharmony_ci uint32_t num_render = 1; 349bf215546Sopenharmony_ci uint32_t num_engines = num_copy + num_render; 350bf215546Sopenharmony_ci 351bf215546Sopenharmony_ci struct drm_i915_query_engine_info *info = 352bf215546Sopenharmony_ci (struct drm_i915_query_engine_info*)(uintptr_t)item->data_ptr; 353bf215546Sopenharmony_ci 354bf215546Sopenharmony_ci int32_t data_length = 355bf215546Sopenharmony_ci sizeof(*info) + 356bf215546Sopenharmony_ci num_engines * sizeof(info->engines[0]); 357bf215546Sopenharmony_ci 358bf215546Sopenharmony_ci if (item->length == 0) { 359bf215546Sopenharmony_ci item->length = data_length; 360bf215546Sopenharmony_ci return 0; 361bf215546Sopenharmony_ci } else if (item->length < data_length) { 362bf215546Sopenharmony_ci item->length = -EINVAL; 363bf215546Sopenharmony_ci return -1; 364bf215546Sopenharmony_ci } else { 365bf215546Sopenharmony_ci memset(info, 0, data_length); 366bf215546Sopenharmony_ci 367bf215546Sopenharmony_ci for (uint32_t e = 0; e < num_render; e++, info->num_engines++) { 368bf215546Sopenharmony_ci info->engines[info->num_engines].engine.engine_class = 369bf215546Sopenharmony_ci I915_ENGINE_CLASS_RENDER; 370bf215546Sopenharmony_ci info->engines[info->num_engines].engine.engine_instance = e; 371bf215546Sopenharmony_ci } 372bf215546Sopenharmony_ci 373bf215546Sopenharmony_ci for (uint32_t e = 0; e < num_copy; e++, info->num_engines++) { 374bf215546Sopenharmony_ci info->engines[info->num_engines].engine.engine_class = 375bf215546Sopenharmony_ci I915_ENGINE_CLASS_COPY; 376bf215546Sopenharmony_ci info->engines[info->num_engines].engine.engine_instance = e; 377bf215546Sopenharmony_ci } 378bf215546Sopenharmony_ci 379bf215546Sopenharmony_ci assert(info->num_engines == num_engines); 380bf215546Sopenharmony_ci 381bf215546Sopenharmony_ci if (item->length > data_length) 382bf215546Sopenharmony_ci item->length = data_length; 383bf215546Sopenharmony_ci 384bf215546Sopenharmony_ci return 0; 385bf215546Sopenharmony_ci } 386bf215546Sopenharmony_ci } 387bf215546Sopenharmony_ci 388bf215546Sopenharmony_ci case DRM_I915_QUERY_PERF_CONFIG: 389bf215546Sopenharmony_ci /* This is known but not supported by the shim. Handling this here 390bf215546Sopenharmony_ci * suppresses some spurious warning messages in shader-db runs. 391bf215546Sopenharmony_ci */ 392bf215546Sopenharmony_ci item->length = -EINVAL; 393bf215546Sopenharmony_ci break; 394bf215546Sopenharmony_ci 395bf215546Sopenharmony_ci case DRM_I915_QUERY_MEMORY_REGIONS: { 396bf215546Sopenharmony_ci uint32_t num_regions = i915.devinfo.has_local_mem ? 2 : 1; 397bf215546Sopenharmony_ci struct drm_i915_query_memory_regions *info = 398bf215546Sopenharmony_ci (struct drm_i915_query_memory_regions*)(uintptr_t)item->data_ptr; 399bf215546Sopenharmony_ci size_t data_length = sizeof(struct drm_i915_query_memory_regions) + 400bf215546Sopenharmony_ci num_regions * sizeof(struct drm_i915_memory_region_info); 401bf215546Sopenharmony_ci 402bf215546Sopenharmony_ci if (item->length == 0) { 403bf215546Sopenharmony_ci item->length = data_length; 404bf215546Sopenharmony_ci return 0; 405bf215546Sopenharmony_ci } else if (item->length < (int32_t)data_length) { 406bf215546Sopenharmony_ci item->length = -EINVAL; 407bf215546Sopenharmony_ci return -1; 408bf215546Sopenharmony_ci } else { 409bf215546Sopenharmony_ci memset(info, 0, data_length); 410bf215546Sopenharmony_ci info->num_regions = num_regions; 411bf215546Sopenharmony_ci info->regions[0].region.memory_class = I915_MEMORY_CLASS_SYSTEM; 412bf215546Sopenharmony_ci info->regions[0].region.memory_instance = 0; 413bf215546Sopenharmony_ci /* Report 4Gb even if it's not actually true, it looks more like a 414bf215546Sopenharmony_ci * real device. 415bf215546Sopenharmony_ci */ 416bf215546Sopenharmony_ci info->regions[0].probed_size = 4ull * 1024 * 1024 * 1024; 417bf215546Sopenharmony_ci info->regions[0].unallocated_size = -1ll; 418bf215546Sopenharmony_ci if (i915.devinfo.has_local_mem) { 419bf215546Sopenharmony_ci info->regions[1].region.memory_class = I915_MEMORY_CLASS_DEVICE; 420bf215546Sopenharmony_ci info->regions[1].region.memory_instance = 0; 421bf215546Sopenharmony_ci info->regions[1].probed_size = 4ull * 1024 * 1024 * 1024; 422bf215546Sopenharmony_ci info->regions[1].unallocated_size = -1ll; 423bf215546Sopenharmony_ci } 424bf215546Sopenharmony_ci return 0; 425bf215546Sopenharmony_ci } 426bf215546Sopenharmony_ci break; 427bf215546Sopenharmony_ci } 428bf215546Sopenharmony_ci 429bf215546Sopenharmony_ci default: 430bf215546Sopenharmony_ci fprintf(stderr, "Unknown drm_i915_query_item id=%lli\n", item->query_id); 431bf215546Sopenharmony_ci item->length = -EINVAL; 432bf215546Sopenharmony_ci break; 433bf215546Sopenharmony_ci } 434bf215546Sopenharmony_ci } 435bf215546Sopenharmony_ci 436bf215546Sopenharmony_ci return 0; 437bf215546Sopenharmony_ci} 438bf215546Sopenharmony_ci 439bf215546Sopenharmony_cistatic int 440bf215546Sopenharmony_cii915_gem_get_aperture(int fd, unsigned long request, void *arg) 441bf215546Sopenharmony_ci{ 442bf215546Sopenharmony_ci struct drm_i915_gem_get_aperture *aperture = arg; 443bf215546Sopenharmony_ci 444bf215546Sopenharmony_ci if (i915.devinfo.ver >= 8 && 445bf215546Sopenharmony_ci i915.devinfo.platform != INTEL_PLATFORM_CHV) { 446bf215546Sopenharmony_ci aperture->aper_size = 1ull << 48; 447bf215546Sopenharmony_ci aperture->aper_available_size = 1ull << 48; 448bf215546Sopenharmony_ci } else { 449bf215546Sopenharmony_ci aperture->aper_size = 1ull << 31; 450bf215546Sopenharmony_ci aperture->aper_size = 1ull << 31; 451bf215546Sopenharmony_ci } 452bf215546Sopenharmony_ci 453bf215546Sopenharmony_ci return 0; 454bf215546Sopenharmony_ci} 455bf215546Sopenharmony_ci 456bf215546Sopenharmony_cistatic ioctl_fn_t driver_ioctls[] = { 457bf215546Sopenharmony_ci [DRM_I915_GETPARAM] = i915_ioctl_get_param, 458bf215546Sopenharmony_ci [DRM_I915_QUERY] = i915_ioctl_query, 459bf215546Sopenharmony_ci 460bf215546Sopenharmony_ci [DRM_I915_GET_RESET_STATS] = i915_ioctl_noop, 461bf215546Sopenharmony_ci 462bf215546Sopenharmony_ci [DRM_I915_GEM_CREATE] = i915_ioctl_gem_create, 463bf215546Sopenharmony_ci [DRM_I915_GEM_MMAP] = i915_ioctl_gem_mmap, 464bf215546Sopenharmony_ci [DRM_I915_GEM_SET_TILING] = i915_ioctl_gem_set_tiling, 465bf215546Sopenharmony_ci [DRM_I915_GEM_CONTEXT_CREATE] = i915_ioctl_gem_context_create, 466bf215546Sopenharmony_ci [DRM_I915_GEM_CONTEXT_DESTROY] = i915_ioctl_noop, 467bf215546Sopenharmony_ci [DRM_I915_GEM_CONTEXT_GETPARAM] = i915_ioctl_gem_context_getparam, 468bf215546Sopenharmony_ci [DRM_I915_GEM_CONTEXT_SETPARAM] = i915_ioctl_noop, 469bf215546Sopenharmony_ci [DRM_I915_GEM_EXECBUFFER2] = i915_ioctl_noop, 470bf215546Sopenharmony_ci /* [DRM_I915_GEM_EXECBUFFER2_WR] = i915_ioctl_noop, 471bf215546Sopenharmony_ci same value as DRM_I915_GEM_EXECBUFFER2. */ 472bf215546Sopenharmony_ci 473bf215546Sopenharmony_ci [DRM_I915_GEM_USERPTR] = i915_ioctl_gem_userptr, 474bf215546Sopenharmony_ci 475bf215546Sopenharmony_ci [DRM_I915_GEM_GET_APERTURE] = i915_gem_get_aperture, 476bf215546Sopenharmony_ci 477bf215546Sopenharmony_ci [DRM_I915_REG_READ] = i915_ioctl_noop, 478bf215546Sopenharmony_ci 479bf215546Sopenharmony_ci [DRM_I915_GEM_SET_DOMAIN] = i915_ioctl_noop, 480bf215546Sopenharmony_ci [DRM_I915_GEM_GET_CACHING] = i915_ioctl_noop, 481bf215546Sopenharmony_ci [DRM_I915_GEM_SET_CACHING] = i915_ioctl_noop, 482bf215546Sopenharmony_ci [DRM_I915_GEM_GET_TILING] = i915_ioctl_gem_get_tiling, 483bf215546Sopenharmony_ci [DRM_I915_GEM_MADVISE] = i915_ioctl_noop, 484bf215546Sopenharmony_ci [DRM_I915_GEM_WAIT] = i915_ioctl_noop, 485bf215546Sopenharmony_ci [DRM_I915_GEM_BUSY] = i915_ioctl_noop, 486bf215546Sopenharmony_ci}; 487bf215546Sopenharmony_ci 488bf215546Sopenharmony_civoid 489bf215546Sopenharmony_cidrm_shim_driver_init(void) 490bf215546Sopenharmony_ci{ 491bf215546Sopenharmony_ci const char *user_platform = getenv("INTEL_STUB_GPU_PLATFORM"); 492bf215546Sopenharmony_ci 493bf215546Sopenharmony_ci /* Use SKL if nothing is specified. */ 494bf215546Sopenharmony_ci i915.device_id = intel_device_name_to_pci_device_id(user_platform ?: "skl"); 495bf215546Sopenharmony_ci if (!intel_get_device_info_from_pci_id(i915.device_id, &i915.devinfo)) 496bf215546Sopenharmony_ci return; 497bf215546Sopenharmony_ci 498bf215546Sopenharmony_ci shim_device.bus_type = DRM_BUS_PCI; 499bf215546Sopenharmony_ci shim_device.driver_name = "i915"; 500bf215546Sopenharmony_ci shim_device.driver_ioctls = driver_ioctls; 501bf215546Sopenharmony_ci shim_device.driver_ioctl_count = ARRAY_SIZE(driver_ioctls); 502bf215546Sopenharmony_ci 503bf215546Sopenharmony_ci char uevent_content[1024]; 504bf215546Sopenharmony_ci snprintf(uevent_content, sizeof(uevent_content), 505bf215546Sopenharmony_ci "DRIVER=i915\n" 506bf215546Sopenharmony_ci "PCI_CLASS=30000\n" 507bf215546Sopenharmony_ci "PCI_ID=8086:%x\n" 508bf215546Sopenharmony_ci "PCI_SUBSYS_ID=1028:075B\n" 509bf215546Sopenharmony_ci "PCI_SLOT_NAME=0000:00:02.0\n" 510bf215546Sopenharmony_ci "MODALIAS=pci:v00008086d00005916sv00001028sd0000075Bbc03sc00i00\n", 511bf215546Sopenharmony_ci i915.device_id); 512bf215546Sopenharmony_ci drm_shim_override_file(uevent_content, 513bf215546Sopenharmony_ci "/sys/dev/char/%d:%d/device/uevent", 514bf215546Sopenharmony_ci DRM_MAJOR, render_node_minor); 515bf215546Sopenharmony_ci drm_shim_override_file("0x0\n", 516bf215546Sopenharmony_ci "/sys/dev/char/%d:%d/device/revision", 517bf215546Sopenharmony_ci DRM_MAJOR, render_node_minor); 518bf215546Sopenharmony_ci char device_content[10]; 519bf215546Sopenharmony_ci snprintf(device_content, sizeof(device_content), 520bf215546Sopenharmony_ci "0x%x\n", i915.device_id); 521bf215546Sopenharmony_ci drm_shim_override_file("0x8086", 522bf215546Sopenharmony_ci "/sys/dev/char/%d:%d/device/vendor", 523bf215546Sopenharmony_ci DRM_MAJOR, render_node_minor); 524bf215546Sopenharmony_ci drm_shim_override_file("0x8086", 525bf215546Sopenharmony_ci "/sys/devices/pci0000:00/0000:00:02.0/vendor"); 526bf215546Sopenharmony_ci drm_shim_override_file(device_content, 527bf215546Sopenharmony_ci "/sys/dev/char/%d:%d/device/device", 528bf215546Sopenharmony_ci DRM_MAJOR, render_node_minor); 529bf215546Sopenharmony_ci drm_shim_override_file(device_content, 530bf215546Sopenharmony_ci "/sys/devices/pci0000:00/0000:00:02.0/device"); 531bf215546Sopenharmony_ci drm_shim_override_file("0x1234", 532bf215546Sopenharmony_ci "/sys/dev/char/%d:%d/device/subsystem_vendor", 533bf215546Sopenharmony_ci DRM_MAJOR, render_node_minor); 534bf215546Sopenharmony_ci drm_shim_override_file("0x1234", 535bf215546Sopenharmony_ci "/sys/devices/pci0000:00/0000:00:02.0/subsystem_vendor"); 536bf215546Sopenharmony_ci drm_shim_override_file("0x1234", 537bf215546Sopenharmony_ci "/sys/dev/char/%d:%d/device/subsystem_device", 538bf215546Sopenharmony_ci DRM_MAJOR, render_node_minor); 539bf215546Sopenharmony_ci drm_shim_override_file("0x1234", 540bf215546Sopenharmony_ci "/sys/devices/pci0000:00/0000:00:02.0/subsystem_device"); 541bf215546Sopenharmony_ci} 542