1 /* basic set of prime tests between intel and nouveau */
4 1. share buffer from intel -> nouveau.
5 2. share buffer from nouveau -> intel
6 3. share intel->nouveau, map on both, write intel, read nouveau
7 4. share intel->nouveau, blit intel fill, readback on nouveau
8 test 1 + map buffer, read/write, map other size.
9 do some hw actions on the buffer
10 some illegal operations -
11 close prime fd try and map
13 TODO add some nouveau rendering tests
23 #include <sys/ioctl.h>
26 #include "intel_bufmgr.h"
28 #include "intel_gpu_tools.h"
29 #include "intel_batchbuffer.h"
32 int intel_fd = -1, nouveau_fd = -1;
33 drm_intel_bufmgr *bufmgr;
34 struct nouveau_device *ndev;
35 struct nouveau_client *nclient;
37 struct intel_batchbuffer *intel_batch;
39 #define BO_SIZE (256*1024)
41 static int find_and_open_devices(void)
49 for (i = 0; i < 9; i++) {
52 sprintf(path, "/sys/class/drm/card%d/device/vendor", i);
56 fl = fopen(path, "r");
60 ret = fgets(vendor_id, 8, fl);
64 venid = strtoul(vendor_id, NULL, 16);
65 sprintf(path, "/dev/dri/card%d", i);
66 if (venid == 0x8086) {
67 intel_fd = open(path, O_RDWR);
70 } else if (venid == 0x10de) {
71 nouveau_fd = open(path, O_RDWR);
81 * allocate buffer on intel,
82 * set prime on buffer,
83 * retrive buffer from nouveau,
87 static int test_i915_nv_sharing(void)
90 drm_intel_bo *test_intel_bo;
92 struct nouveau_bo *nvbo;
94 test_intel_bo = drm_intel_bo_alloc(bufmgr, "test bo", BO_SIZE, 4096);
96 drm_intel_bo_gem_export_to_prime(test_intel_bo, &prime_fd);
98 ret = nouveau_bo_prime_handle_ref(ndev, prime_fd, &nvbo);
103 nouveau_bo_ref(NULL, &nvbo);
104 drm_intel_bo_unreference(test_intel_bo);
110 * allocate buffer on nouveau
111 * set prime on buffer,
112 * retrive buffer from intel
116 static int test_nv_i915_sharing(void)
119 drm_intel_bo *test_intel_bo;
121 struct nouveau_bo *nvbo;
123 ret = nouveau_bo_new(ndev, NOUVEAU_BO_GART | NOUVEAU_BO_MAP,
124 0, BO_SIZE, NULL, &nvbo);
127 ret = nouveau_bo_set_prime(nvbo, &prime_fd);
131 test_intel_bo = drm_intel_bo_gem_create_from_prime(bufmgr, prime_fd, BO_SIZE);
136 nouveau_bo_ref(NULL, &nvbo);
137 drm_intel_bo_unreference(test_intel_bo);
142 * allocate intel, give to nouveau, map on nouveau
143 * write 0xdeadbeef, non-gtt map on intel, read
145 static int test_nv_write_i915_cpu_mmap_read(void)
148 drm_intel_bo *test_intel_bo;
150 struct nouveau_bo *nvbo = NULL;
153 test_intel_bo = drm_intel_bo_alloc(bufmgr, "test bo", BO_SIZE, 4096);
155 drm_intel_bo_gem_export_to_prime(test_intel_bo, &prime_fd);
157 ret = nouveau_bo_prime_handle_ref(ndev, prime_fd, &nvbo);
159 fprintf(stderr,"failed to ref prime buffer %d\n", ret);
166 ret = nouveau_bo_map(nvbo, NOUVEAU_BO_RDWR, nclient);
168 fprintf(stderr,"failed to map nouveau bo\n");
175 drm_intel_bo_map(test_intel_bo, 1);
177 ptr = test_intel_bo->virtual;
179 if (*ptr != 0xdeadbeef) {
180 fprintf(stderr,"mapped value doesn't match\n");
184 nouveau_bo_ref(NULL, &nvbo);
186 drm_intel_bo_unreference(test_intel_bo);
191 * allocate intel, give to nouveau, map on nouveau
192 * write 0xdeadbeef, gtt map on intel, read
194 static int test_nv_write_i915_gtt_mmap_read(void)
197 drm_intel_bo *test_intel_bo;
199 struct nouveau_bo *nvbo = NULL;
202 test_intel_bo = drm_intel_bo_alloc(bufmgr, "test bo", BO_SIZE, 4096);
204 drm_intel_bo_gem_export_to_prime(test_intel_bo, &prime_fd);
206 ret = nouveau_bo_prime_handle_ref(ndev, prime_fd, &nvbo);
209 fprintf(stderr,"failed to ref prime buffer\n");
213 ret = nouveau_bo_map(nvbo, NOUVEAU_BO_RDWR, nclient);
215 fprintf(stderr,"failed to map nouveau bo\n");
223 drm_intel_gem_bo_map_gtt(test_intel_bo);
224 ptr = test_intel_bo->virtual;
226 if (*ptr != 0xdeadbeef) {
227 fprintf(stderr,"mapped value doesn't match\n");
231 nouveau_bo_ref(NULL, &nvbo);
232 drm_intel_bo_unreference(test_intel_bo);
236 /* test drm_intel_bo_map doesn't work properly,
237 this tries to map the backing shmem fd, which doesn't exist
239 static int test_i915_import_cpu_mmap(void)
242 drm_intel_bo *test_intel_bo;
244 struct nouveau_bo *nvbo;
247 ret = nouveau_bo_new(ndev, NOUVEAU_BO_GART | NOUVEAU_BO_MAP,
248 0, BO_SIZE, NULL, &nvbo);
251 ret = nouveau_bo_set_prime(nvbo, &prime_fd);
255 test_intel_bo = drm_intel_bo_gem_create_from_prime(bufmgr, prime_fd, BO_SIZE);
260 ret = nouveau_bo_map(nvbo, NOUVEAU_BO_RDWR, nclient);
262 fprintf(stderr,"failed to map nouveau bo\n");
269 ret = drm_intel_bo_map(test_intel_bo, 0);
271 fprintf(stderr,"failed to map imported bo on intel side\n");
274 if (!test_intel_bo->virtual) {
278 ptr = test_intel_bo->virtual;
280 if (*ptr != 0xdeadbeef) {
281 fprintf(stderr,"mapped value doesn't match %08x\n", *ptr);
285 nouveau_bo_ref(NULL, &nvbo);
286 drm_intel_bo_unreference(test_intel_bo);
290 /* test drm_intel_bo_map_gtt works properly,
291 this tries to map the backing shmem fd, which doesn't exist
293 static int test_i915_import_gtt_mmap(void)
296 drm_intel_bo *test_intel_bo;
298 struct nouveau_bo *nvbo;
301 ret = nouveau_bo_new(ndev, NOUVEAU_BO_GART | NOUVEAU_BO_MAP,
302 0, BO_SIZE, NULL, &nvbo);
305 ret = nouveau_bo_set_prime(nvbo, &prime_fd);
309 test_intel_bo = drm_intel_bo_gem_create_from_prime(bufmgr, prime_fd, BO_SIZE);
314 ret = nouveau_bo_map(nvbo, NOUVEAU_BO_RDWR, nclient);
316 fprintf(stderr,"failed to map nouveau bo\n");
322 *(ptr + 1) = 0xa55a55;
324 ret = drm_intel_gem_bo_map_gtt(test_intel_bo);
326 fprintf(stderr,"failed to map bo\n");
329 if (!test_intel_bo->virtual) {
331 fprintf(stderr,"failed to map bo\n");
334 ptr = test_intel_bo->virtual;
336 if (*ptr != 0xdeadbeef) {
337 fprintf(stderr,"mapped value doesn't match %08x %08x\n", *ptr, *(ptr + 1));
341 nouveau_bo_ref(NULL, &nvbo);
342 drm_intel_bo_unreference(test_intel_bo);
346 /* test 7 - import from nouveau into intel, test pread/pwrite fail */
347 static int test_i915_import_pread_pwrite(void)
350 drm_intel_bo *test_intel_bo;
352 struct nouveau_bo *nvbo;
356 ret = nouveau_bo_new(ndev, NOUVEAU_BO_GART | NOUVEAU_BO_MAP,
357 0, BO_SIZE, NULL, &nvbo);
360 ret = nouveau_bo_set_prime(nvbo, &prime_fd);
364 test_intel_bo = drm_intel_bo_gem_create_from_prime(bufmgr, prime_fd, BO_SIZE);
369 ret = nouveau_bo_map(nvbo, NOUVEAU_BO_RDWR, nclient);
371 fprintf(stderr,"failed to map nouveau bo\n");
378 gem_read(intel_fd, test_intel_bo->handle, 0, buf, 256);
381 gem_write(intel_fd, test_intel_bo->handle, 0, buf, 4);
383 nouveau_bo_ref(NULL, &nvbo);
384 drm_intel_bo_unreference(test_intel_bo);
389 set_bo(drm_intel_bo *bo, uint32_t val, int width, int height)
391 int size = width * height;
394 drm_intel_gem_bo_start_gtt_access(bo, true);
400 static drm_intel_bo *
401 create_bo(drm_intel_bufmgr *ibufmgr, uint32_t val, int width, int height)
405 bo = drm_intel_bo_alloc(ibufmgr, "bo", 4*width*height, 0);
408 /* gtt map doesn't have a write parameter, so just keep the mapping
409 * around (to avoid the set_domain with the gtt write domain set) and
410 * manually tell the kernel when we start access the gtt. */
411 drm_intel_gem_bo_map_gtt(bo);
413 set_bo(bo, val, width, height);
418 /* use intel hw to fill the BO with a blit from another BO,
419 then readback from the nouveau bo, check value is correct */
420 static int test_i915_blt_fill_nv_read(void)
423 drm_intel_bo *test_intel_bo, *src_bo;
425 struct nouveau_bo *nvbo = NULL;
428 src_bo = create_bo(bufmgr, 0xaa55aa55, 256, 1);
430 test_intel_bo = drm_intel_bo_alloc(bufmgr, "test bo", BO_SIZE, 4096);
432 drm_intel_bo_gem_export_to_prime(test_intel_bo, &prime_fd);
434 ret = nouveau_bo_prime_handle_ref(ndev, prime_fd, &nvbo);
437 fprintf(stderr,"failed to ref prime buffer\n");
441 intel_copy_bo(intel_batch, test_intel_bo, src_bo, 256, 1);
443 ret = nouveau_bo_map(nvbo, NOUVEAU_BO_RDWR, nclient);
445 fprintf(stderr,"failed to map nouveau bo\n");
449 drm_intel_bo_map(test_intel_bo, 0);
452 if (*ptr != 0xaa55aa55) {
453 fprintf(stderr,"mapped value doesn't match\n");
457 nouveau_bo_ref(NULL, &nvbo);
458 drm_intel_bo_unreference(test_intel_bo);
462 /* test 8 use nouveau to do blit */
464 /* test 9 nouveau copy engine?? */
466 int main(int argc, char **argv)
470 ret = find_and_open_devices();
474 drmtest_subtest_init(argc, argv);
476 if (nouveau_fd == -1 || intel_fd == -1) {
477 fprintf(stderr,"failed to find intel and nouveau GPU\n");
478 if (!drmtest_only_list_subtests())
482 /* set up intel bufmgr */
483 bufmgr = drm_intel_bufmgr_gem_init(intel_fd, 4096);
486 /* Do not enable reuse, we share (almost) all buffers. */
487 //drm_intel_bufmgr_gem_enable_reuse(bufmgr);
489 /* set up nouveau bufmgr */
490 ret = nouveau_device_wrap(nouveau_fd, 0, &ndev);
492 fprintf(stderr,"failed to wrap nouveau device\n");
496 ret = nouveau_client_new(ndev, &nclient);
498 fprintf(stderr,"failed to setup nouveau client\n");
502 /* set up an intel batch buffer */
503 devid = intel_get_drm_devid(intel_fd);
504 intel_batch = intel_batchbuffer_alloc(bufmgr, devid);
506 #define xtest(name) \
507 drmtest_subtest(#name) \
511 xtest(i915_nv_sharing);
512 xtest(nv_i915_sharing);
513 xtest(nv_write_i915_cpu_mmap_read);
514 xtest(nv_write_i915_gtt_mmap_read);
515 xtest(i915_import_cpu_mmap);
516 xtest(i915_import_gtt_mmap);
517 xtest(i915_import_pread_pwrite);
518 xtest(i915_blt_fill_nv_read);
520 intel_batchbuffer_free(intel_batch);
522 nouveau_device_del(&ndev);
523 drm_intel_bufmgr_destroy(bufmgr);