1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27#include <linux/firmware.h>
28#include <linux/module.h>
29#include <linux/pci.h>
30
31#include "amdgpu.h"
32#include "amdgpu_pm.h"
33#include "amdgpu_vcn.h"
34#include "soc15d.h"
35
36
37#define FIRMWARE_RAVEN "amdgpu/raven_vcn.bin"
38#define FIRMWARE_PICASSO "amdgpu/picasso_vcn.bin"
39#define FIRMWARE_RAVEN2 "amdgpu/raven2_vcn.bin"
40#define FIRMWARE_ARCTURUS "amdgpu/arcturus_vcn.bin"
41#define FIRMWARE_RENOIR "amdgpu/renoir_vcn.bin"
42#define FIRMWARE_NAVI10 "amdgpu/navi10_vcn.bin"
43#define FIRMWARE_NAVI14 "amdgpu/navi14_vcn.bin"
44#define FIRMWARE_NAVI12 "amdgpu/navi12_vcn.bin"
45
46MODULE_FIRMWARE(FIRMWARE_RAVEN);
47MODULE_FIRMWARE(FIRMWARE_PICASSO);
48MODULE_FIRMWARE(FIRMWARE_RAVEN2);
49MODULE_FIRMWARE(FIRMWARE_ARCTURUS);
50MODULE_FIRMWARE(FIRMWARE_RENOIR);
51MODULE_FIRMWARE(FIRMWARE_NAVI10);
52MODULE_FIRMWARE(FIRMWARE_NAVI14);
53MODULE_FIRMWARE(FIRMWARE_NAVI12);
54
55static void amdgpu_vcn_idle_work_handler(struct work_struct *work);
56
57int amdgpu_vcn_sw_init(struct amdgpu_device *adev)
58{
59 unsigned long bo_size;
60 const char *fw_name;
61 const struct common_firmware_header *hdr;
62 unsigned char fw_check;
63 int i, r;
64
65 INIT_DELAYED_WORK(&adev->vcn.idle_work, amdgpu_vcn_idle_work_handler);
66
67 switch (adev->asic_type) {
68 case CHIP_RAVEN:
69 if (adev->rev_id >= 8)
70 fw_name = FIRMWARE_RAVEN2;
71 else if (adev->pdev->device == 0x15d8)
72 fw_name = FIRMWARE_PICASSO;
73 else
74 fw_name = FIRMWARE_RAVEN;
75 break;
76 case CHIP_ARCTURUS:
77 fw_name = FIRMWARE_ARCTURUS;
78 if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
79 (adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
80 adev->vcn.indirect_sram = true;
81 break;
82 case CHIP_RENOIR:
83 fw_name = FIRMWARE_RENOIR;
84 if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
85 (adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
86 adev->vcn.indirect_sram = true;
87 break;
88 case CHIP_NAVI10:
89 fw_name = FIRMWARE_NAVI10;
90 if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
91 (adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
92 adev->vcn.indirect_sram = true;
93 break;
94 case CHIP_NAVI14:
95 fw_name = FIRMWARE_NAVI14;
96 if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
97 (adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
98 adev->vcn.indirect_sram = true;
99 break;
100 case CHIP_NAVI12:
101 fw_name = FIRMWARE_NAVI12;
102 if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
103 (adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
104 adev->vcn.indirect_sram = true;
105 break;
106 default:
107 return -EINVAL;
108 }
109
110 r = request_firmware(&adev->vcn.fw, fw_name, adev->dev);
111 if (r) {
112 dev_err(adev->dev, "amdgpu_vcn: Can't load firmware \"%s\"\n",
113 fw_name);
114 return r;
115 }
116
117 r = amdgpu_ucode_validate(adev->vcn.fw);
118 if (r) {
119 dev_err(adev->dev, "amdgpu_vcn: Can't validate firmware \"%s\"\n",
120 fw_name);
121 release_firmware(adev->vcn.fw);
122 adev->vcn.fw = NULL;
123 return r;
124 }
125
126 hdr = (const struct common_firmware_header *)adev->vcn.fw->data;
127 adev->vcn.fw_version = le32_to_cpu(hdr->ucode_version);
128
129
130
131
132
133
134
135 fw_check = (le32_to_cpu(hdr->ucode_version) >> 20) & 0xf;
136 if (fw_check) {
137 unsigned int dec_ver, enc_major, enc_minor, vep, fw_rev;
138
139 fw_rev = le32_to_cpu(hdr->ucode_version) & 0xfff;
140 enc_minor = (le32_to_cpu(hdr->ucode_version) >> 12) & 0xff;
141 enc_major = fw_check;
142 dec_ver = (le32_to_cpu(hdr->ucode_version) >> 24) & 0xf;
143 vep = (le32_to_cpu(hdr->ucode_version) >> 28) & 0xf;
144 DRM_INFO("Found VCN firmware Version ENC: %hu.%hu DEC: %hu VEP: %hu Revision: %hu\n",
145 enc_major, enc_minor, dec_ver, vep, fw_rev);
146 } else {
147 unsigned int version_major, version_minor, family_id;
148
149 family_id = le32_to_cpu(hdr->ucode_version) & 0xff;
150 version_major = (le32_to_cpu(hdr->ucode_version) >> 24) & 0xff;
151 version_minor = (le32_to_cpu(hdr->ucode_version) >> 8) & 0xff;
152 DRM_INFO("Found VCN firmware Version: %hu.%hu Family ID: %hu\n",
153 version_major, version_minor, family_id);
154 }
155
156 bo_size = AMDGPU_VCN_STACK_SIZE + AMDGPU_VCN_CONTEXT_SIZE;
157 if (adev->firmware.load_type != AMDGPU_FW_LOAD_PSP)
158 bo_size += AMDGPU_GPU_PAGE_ALIGN(le32_to_cpu(hdr->ucode_size_bytes) + 8);
159
160 for (i = 0; i < adev->vcn.num_vcn_inst; i++) {
161 if (adev->vcn.harvest_config & (1 << i))
162 continue;
163
164 r = amdgpu_bo_create_kernel(adev, bo_size, PAGE_SIZE,
165 AMDGPU_GEM_DOMAIN_VRAM, &adev->vcn.inst[i].vcpu_bo,
166 &adev->vcn.inst[i].gpu_addr, &adev->vcn.inst[i].cpu_addr);
167 if (r) {
168 dev_err(adev->dev, "(%d) failed to allocate vcn bo\n", r);
169 return r;
170 }
171
172 if (adev->vcn.indirect_sram) {
173 r = amdgpu_bo_create_kernel(adev, 64 * 2 * 4, PAGE_SIZE,
174 AMDGPU_GEM_DOMAIN_VRAM, &adev->vcn.inst[i].dpg_sram_bo,
175 &adev->vcn.inst[i].dpg_sram_gpu_addr, &adev->vcn.inst[i].dpg_sram_cpu_addr);
176 if (r) {
177 dev_err(adev->dev, "VCN %d (%d) failed to allocate DPG bo\n", i, r);
178 return r;
179 }
180 }
181 }
182
183 return 0;
184}
185
186int amdgpu_vcn_sw_fini(struct amdgpu_device *adev)
187{
188 int i, j;
189
190 cancel_delayed_work_sync(&adev->vcn.idle_work);
191
192 for (j = 0; j < adev->vcn.num_vcn_inst; ++j) {
193 if (adev->vcn.harvest_config & (1 << j))
194 continue;
195 if (adev->vcn.indirect_sram) {
196 amdgpu_bo_free_kernel(&adev->vcn.inst[j].dpg_sram_bo,
197 &adev->vcn.inst[j].dpg_sram_gpu_addr,
198 (void **)&adev->vcn.inst[j].dpg_sram_cpu_addr);
199 }
200 kvfree(adev->vcn.inst[j].saved_bo);
201
202 amdgpu_bo_free_kernel(&adev->vcn.inst[j].vcpu_bo,
203 &adev->vcn.inst[j].gpu_addr,
204 (void **)&adev->vcn.inst[j].cpu_addr);
205
206 amdgpu_ring_fini(&adev->vcn.inst[j].ring_dec);
207
208 for (i = 0; i < adev->vcn.num_enc_rings; ++i)
209 amdgpu_ring_fini(&adev->vcn.inst[j].ring_enc[i]);
210 }
211
212 release_firmware(adev->vcn.fw);
213
214 return 0;
215}
216
217int amdgpu_vcn_suspend(struct amdgpu_device *adev)
218{
219 unsigned size;
220 void *ptr;
221 int i;
222
223 cancel_delayed_work_sync(&adev->vcn.idle_work);
224
225 for (i = 0; i < adev->vcn.num_vcn_inst; ++i) {
226 if (adev->vcn.harvest_config & (1 << i))
227 continue;
228 if (adev->vcn.inst[i].vcpu_bo == NULL)
229 return 0;
230
231 size = amdgpu_bo_size(adev->vcn.inst[i].vcpu_bo);
232 ptr = adev->vcn.inst[i].cpu_addr;
233
234 adev->vcn.inst[i].saved_bo = kvmalloc(size, GFP_KERNEL);
235 if (!adev->vcn.inst[i].saved_bo)
236 return -ENOMEM;
237
238 memcpy_fromio(adev->vcn.inst[i].saved_bo, ptr, size);
239 }
240 return 0;
241}
242
243int amdgpu_vcn_resume(struct amdgpu_device *adev)
244{
245 unsigned size;
246 void *ptr;
247 int i;
248
249 for (i = 0; i < adev->vcn.num_vcn_inst; ++i) {
250 if (adev->vcn.harvest_config & (1 << i))
251 continue;
252 if (adev->vcn.inst[i].vcpu_bo == NULL)
253 return -EINVAL;
254
255 size = amdgpu_bo_size(adev->vcn.inst[i].vcpu_bo);
256 ptr = adev->vcn.inst[i].cpu_addr;
257
258 if (adev->vcn.inst[i].saved_bo != NULL) {
259 memcpy_toio(ptr, adev->vcn.inst[i].saved_bo, size);
260 kvfree(adev->vcn.inst[i].saved_bo);
261 adev->vcn.inst[i].saved_bo = NULL;
262 } else {
263 const struct common_firmware_header *hdr;
264 unsigned offset;
265
266 hdr = (const struct common_firmware_header *)adev->vcn.fw->data;
267 if (adev->firmware.load_type != AMDGPU_FW_LOAD_PSP) {
268 offset = le32_to_cpu(hdr->ucode_array_offset_bytes);
269 memcpy_toio(adev->vcn.inst[i].cpu_addr, adev->vcn.fw->data + offset,
270 le32_to_cpu(hdr->ucode_size_bytes));
271 size -= le32_to_cpu(hdr->ucode_size_bytes);
272 ptr += le32_to_cpu(hdr->ucode_size_bytes);
273 }
274 memset_io(ptr, 0, size);
275 }
276 }
277 return 0;
278}
279
280static void amdgpu_vcn_idle_work_handler(struct work_struct *work)
281{
282 struct amdgpu_device *adev =
283 container_of(work, struct amdgpu_device, vcn.idle_work.work);
284 unsigned int fences = 0, fence[AMDGPU_MAX_VCN_INSTANCES] = {0};
285 unsigned int i, j;
286
287 for (j = 0; j < adev->vcn.num_vcn_inst; ++j) {
288 if (adev->vcn.harvest_config & (1 << j))
289 continue;
290
291 for (i = 0; i < adev->vcn.num_enc_rings; ++i) {
292 fence[j] += amdgpu_fence_count_emitted(&adev->vcn.inst[j].ring_enc[i]);
293 }
294
295 if (adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG) {
296 struct dpg_pause_state new_state;
297
298 if (fence[j])
299 new_state.fw_based = VCN_DPG_STATE__PAUSE;
300 else
301 new_state.fw_based = VCN_DPG_STATE__UNPAUSE;
302
303 adev->vcn.pause_dpg_mode(adev, j, &new_state);
304 }
305
306 fence[j] += amdgpu_fence_count_emitted(&adev->vcn.inst[j].ring_dec);
307 fences += fence[j];
308 }
309
310 if (fences == 0) {
311 amdgpu_gfx_off_ctrl(adev, true);
312 amdgpu_device_ip_set_powergating_state(adev, AMD_IP_BLOCK_TYPE_VCN,
313 AMD_PG_STATE_GATE);
314 } else {
315 schedule_delayed_work(&adev->vcn.idle_work, VCN_IDLE_TIMEOUT);
316 }
317}
318
319void amdgpu_vcn_ring_begin_use(struct amdgpu_ring *ring)
320{
321 struct amdgpu_device *adev = ring->adev;
322 bool set_clocks = !cancel_delayed_work_sync(&adev->vcn.idle_work);
323
324 if (set_clocks) {
325 amdgpu_gfx_off_ctrl(adev, false);
326 amdgpu_device_ip_set_powergating_state(adev, AMD_IP_BLOCK_TYPE_VCN,
327 AMD_PG_STATE_UNGATE);
328 }
329
330 if (adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG) {
331 struct dpg_pause_state new_state;
332 unsigned int fences = 0;
333 unsigned int i;
334
335 for (i = 0; i < adev->vcn.num_enc_rings; ++i) {
336 fences += amdgpu_fence_count_emitted(&adev->vcn.inst[ring->me].ring_enc[i]);
337 }
338 if (fences)
339 new_state.fw_based = VCN_DPG_STATE__PAUSE;
340 else
341 new_state.fw_based = VCN_DPG_STATE__UNPAUSE;
342
343 if (ring->funcs->type == AMDGPU_RING_TYPE_VCN_ENC)
344 new_state.fw_based = VCN_DPG_STATE__PAUSE;
345
346 adev->vcn.pause_dpg_mode(adev, ring->me, &new_state);
347 }
348}
349
350void amdgpu_vcn_ring_end_use(struct amdgpu_ring *ring)
351{
352 schedule_delayed_work(&ring->adev->vcn.idle_work, VCN_IDLE_TIMEOUT);
353}
354
355int amdgpu_vcn_dec_ring_test_ring(struct amdgpu_ring *ring)
356{
357 struct amdgpu_device *adev = ring->adev;
358 uint32_t tmp = 0;
359 unsigned i;
360 int r;
361
362 WREG32(adev->vcn.inst[ring->me].external.scratch9, 0xCAFEDEAD);
363 r = amdgpu_ring_alloc(ring, 3);
364 if (r)
365 return r;
366 amdgpu_ring_write(ring, PACKET0(adev->vcn.internal.scratch9, 0));
367 amdgpu_ring_write(ring, 0xDEADBEEF);
368 amdgpu_ring_commit(ring);
369 for (i = 0; i < adev->usec_timeout; i++) {
370 tmp = RREG32(adev->vcn.inst[ring->me].external.scratch9);
371 if (tmp == 0xDEADBEEF)
372 break;
373 udelay(1);
374 }
375
376 if (i >= adev->usec_timeout)
377 r = -ETIMEDOUT;
378
379 return r;
380}
381
382static int amdgpu_vcn_dec_send_msg(struct amdgpu_ring *ring,
383 struct amdgpu_bo *bo,
384 struct dma_fence **fence)
385{
386 struct amdgpu_device *adev = ring->adev;
387 struct dma_fence *f = NULL;
388 struct amdgpu_job *job;
389 struct amdgpu_ib *ib;
390 uint64_t addr;
391 int i, r;
392
393 r = amdgpu_job_alloc_with_ib(adev, 64, &job);
394 if (r)
395 goto err;
396
397 ib = &job->ibs[0];
398 addr = amdgpu_bo_gpu_offset(bo);
399 ib->ptr[0] = PACKET0(adev->vcn.internal.data0, 0);
400 ib->ptr[1] = addr;
401 ib->ptr[2] = PACKET0(adev->vcn.internal.data1, 0);
402 ib->ptr[3] = addr >> 32;
403 ib->ptr[4] = PACKET0(adev->vcn.internal.cmd, 0);
404 ib->ptr[5] = 0;
405 for (i = 6; i < 16; i += 2) {
406 ib->ptr[i] = PACKET0(adev->vcn.internal.nop, 0);
407 ib->ptr[i+1] = 0;
408 }
409 ib->length_dw = 16;
410
411 r = amdgpu_job_submit_direct(job, ring, &f);
412 if (r)
413 goto err_free;
414
415 amdgpu_bo_fence(bo, f, false);
416 amdgpu_bo_unreserve(bo);
417 amdgpu_bo_unref(&bo);
418
419 if (fence)
420 *fence = dma_fence_get(f);
421 dma_fence_put(f);
422
423 return 0;
424
425err_free:
426 amdgpu_job_free(job);
427
428err:
429 amdgpu_bo_unreserve(bo);
430 amdgpu_bo_unref(&bo);
431 return r;
432}
433
434static int amdgpu_vcn_dec_get_create_msg(struct amdgpu_ring *ring, uint32_t handle,
435 struct dma_fence **fence)
436{
437 struct amdgpu_device *adev = ring->adev;
438 struct amdgpu_bo *bo = NULL;
439 uint32_t *msg;
440 int r, i;
441
442 r = amdgpu_bo_create_reserved(adev, 1024, PAGE_SIZE,
443 AMDGPU_GEM_DOMAIN_VRAM,
444 &bo, NULL, (void **)&msg);
445 if (r)
446 return r;
447
448 msg[0] = cpu_to_le32(0x00000028);
449 msg[1] = cpu_to_le32(0x00000038);
450 msg[2] = cpu_to_le32(0x00000001);
451 msg[3] = cpu_to_le32(0x00000000);
452 msg[4] = cpu_to_le32(handle);
453 msg[5] = cpu_to_le32(0x00000000);
454 msg[6] = cpu_to_le32(0x00000001);
455 msg[7] = cpu_to_le32(0x00000028);
456 msg[8] = cpu_to_le32(0x00000010);
457 msg[9] = cpu_to_le32(0x00000000);
458 msg[10] = cpu_to_le32(0x00000007);
459 msg[11] = cpu_to_le32(0x00000000);
460 msg[12] = cpu_to_le32(0x00000780);
461 msg[13] = cpu_to_le32(0x00000440);
462 for (i = 14; i < 1024; ++i)
463 msg[i] = cpu_to_le32(0x0);
464
465 return amdgpu_vcn_dec_send_msg(ring, bo, fence);
466}
467
468static int amdgpu_vcn_dec_get_destroy_msg(struct amdgpu_ring *ring, uint32_t handle,
469 struct dma_fence **fence)
470{
471 struct amdgpu_device *adev = ring->adev;
472 struct amdgpu_bo *bo = NULL;
473 uint32_t *msg;
474 int r, i;
475
476 r = amdgpu_bo_create_reserved(adev, 1024, PAGE_SIZE,
477 AMDGPU_GEM_DOMAIN_VRAM,
478 &bo, NULL, (void **)&msg);
479 if (r)
480 return r;
481
482 msg[0] = cpu_to_le32(0x00000028);
483 msg[1] = cpu_to_le32(0x00000018);
484 msg[2] = cpu_to_le32(0x00000000);
485 msg[3] = cpu_to_le32(0x00000002);
486 msg[4] = cpu_to_le32(handle);
487 msg[5] = cpu_to_le32(0x00000000);
488 for (i = 6; i < 1024; ++i)
489 msg[i] = cpu_to_le32(0x0);
490
491 return amdgpu_vcn_dec_send_msg(ring, bo, fence);
492}
493
494int amdgpu_vcn_dec_ring_test_ib(struct amdgpu_ring *ring, long timeout)
495{
496 struct amdgpu_device *adev = ring->adev;
497 struct dma_fence *fence;
498 long r;
499
500
501 if (amdgpu_sriov_vf(adev))
502 return 0;
503
504 r = amdgpu_vcn_dec_get_create_msg(ring, 1, NULL);
505 if (r)
506 goto error;
507
508 r = amdgpu_vcn_dec_get_destroy_msg(ring, 1, &fence);
509 if (r)
510 goto error;
511
512 r = dma_fence_wait_timeout(fence, false, timeout);
513 if (r == 0)
514 r = -ETIMEDOUT;
515 else if (r > 0)
516 r = 0;
517
518 dma_fence_put(fence);
519error:
520 return r;
521}
522
523int amdgpu_vcn_enc_ring_test_ring(struct amdgpu_ring *ring)
524{
525 struct amdgpu_device *adev = ring->adev;
526 uint32_t rptr;
527 unsigned i;
528 int r;
529
530 r = amdgpu_ring_alloc(ring, 16);
531 if (r)
532 return r;
533
534 rptr = amdgpu_ring_get_rptr(ring);
535
536 amdgpu_ring_write(ring, VCN_ENC_CMD_END);
537 amdgpu_ring_commit(ring);
538
539 for (i = 0; i < adev->usec_timeout; i++) {
540 if (amdgpu_ring_get_rptr(ring) != rptr)
541 break;
542 udelay(1);
543 }
544
545 if (i >= adev->usec_timeout)
546 r = -ETIMEDOUT;
547
548 return r;
549}
550
551static int amdgpu_vcn_enc_get_create_msg(struct amdgpu_ring *ring, uint32_t handle,
552 struct amdgpu_bo *bo,
553 struct dma_fence **fence)
554{
555 const unsigned ib_size_dw = 16;
556 struct amdgpu_job *job;
557 struct amdgpu_ib *ib;
558 struct dma_fence *f = NULL;
559 uint64_t addr;
560 int i, r;
561
562 r = amdgpu_job_alloc_with_ib(ring->adev, ib_size_dw * 4, &job);
563 if (r)
564 return r;
565
566 ib = &job->ibs[0];
567 addr = amdgpu_bo_gpu_offset(bo);
568
569 ib->length_dw = 0;
570 ib->ptr[ib->length_dw++] = 0x00000018;
571 ib->ptr[ib->length_dw++] = 0x00000001;
572 ib->ptr[ib->length_dw++] = handle;
573 ib->ptr[ib->length_dw++] = upper_32_bits(addr);
574 ib->ptr[ib->length_dw++] = addr;
575 ib->ptr[ib->length_dw++] = 0x0000000b;
576
577 ib->ptr[ib->length_dw++] = 0x00000014;
578 ib->ptr[ib->length_dw++] = 0x00000002;
579 ib->ptr[ib->length_dw++] = 0x0000001c;
580 ib->ptr[ib->length_dw++] = 0x00000000;
581 ib->ptr[ib->length_dw++] = 0x00000000;
582
583 ib->ptr[ib->length_dw++] = 0x00000008;
584 ib->ptr[ib->length_dw++] = 0x08000001;
585
586 for (i = ib->length_dw; i < ib_size_dw; ++i)
587 ib->ptr[i] = 0x0;
588
589 r = amdgpu_job_submit_direct(job, ring, &f);
590 if (r)
591 goto err;
592
593 if (fence)
594 *fence = dma_fence_get(f);
595 dma_fence_put(f);
596
597 return 0;
598
599err:
600 amdgpu_job_free(job);
601 return r;
602}
603
604static int amdgpu_vcn_enc_get_destroy_msg(struct amdgpu_ring *ring, uint32_t handle,
605 struct amdgpu_bo *bo,
606 struct dma_fence **fence)
607{
608 const unsigned ib_size_dw = 16;
609 struct amdgpu_job *job;
610 struct amdgpu_ib *ib;
611 struct dma_fence *f = NULL;
612 uint64_t addr;
613 int i, r;
614
615 r = amdgpu_job_alloc_with_ib(ring->adev, ib_size_dw * 4, &job);
616 if (r)
617 return r;
618
619 ib = &job->ibs[0];
620 addr = amdgpu_bo_gpu_offset(bo);
621
622 ib->length_dw = 0;
623 ib->ptr[ib->length_dw++] = 0x00000018;
624 ib->ptr[ib->length_dw++] = 0x00000001;
625 ib->ptr[ib->length_dw++] = handle;
626 ib->ptr[ib->length_dw++] = upper_32_bits(addr);
627 ib->ptr[ib->length_dw++] = addr;
628 ib->ptr[ib->length_dw++] = 0x0000000b;
629
630 ib->ptr[ib->length_dw++] = 0x00000014;
631 ib->ptr[ib->length_dw++] = 0x00000002;
632 ib->ptr[ib->length_dw++] = 0x0000001c;
633 ib->ptr[ib->length_dw++] = 0x00000000;
634 ib->ptr[ib->length_dw++] = 0x00000000;
635
636 ib->ptr[ib->length_dw++] = 0x00000008;
637 ib->ptr[ib->length_dw++] = 0x08000002;
638
639 for (i = ib->length_dw; i < ib_size_dw; ++i)
640 ib->ptr[i] = 0x0;
641
642 r = amdgpu_job_submit_direct(job, ring, &f);
643 if (r)
644 goto err;
645
646 if (fence)
647 *fence = dma_fence_get(f);
648 dma_fence_put(f);
649
650 return 0;
651
652err:
653 amdgpu_job_free(job);
654 return r;
655}
656
657int amdgpu_vcn_enc_ring_test_ib(struct amdgpu_ring *ring, long timeout)
658{
659 struct amdgpu_device *adev = ring->adev;
660 struct dma_fence *fence = NULL;
661 struct amdgpu_bo *bo = NULL;
662 long r;
663
664
665 if (amdgpu_sriov_vf(adev))
666 return 0;
667
668 r = amdgpu_bo_create_reserved(ring->adev, 128 * 1024, PAGE_SIZE,
669 AMDGPU_GEM_DOMAIN_VRAM,
670 &bo, NULL, NULL);
671 if (r)
672 return r;
673
674 r = amdgpu_vcn_enc_get_create_msg(ring, 1, bo, NULL);
675 if (r)
676 goto error;
677
678 r = amdgpu_vcn_enc_get_destroy_msg(ring, 1, bo, &fence);
679 if (r)
680 goto error;
681
682 r = dma_fence_wait_timeout(fence, false, timeout);
683 if (r == 0)
684 r = -ETIMEDOUT;
685 else if (r > 0)
686 r = 0;
687
688error:
689 dma_fence_put(fence);
690 amdgpu_bo_unreserve(bo);
691 amdgpu_bo_unref(&bo);
692 return r;
693}
694