|
23 | 23 |
|
24 | 24 | #include "amdgpu.h" |
25 | 25 | #include "amdgpu_jpeg.h" |
| 26 | +#include "amdgpu_cs.h" |
26 | 27 | #include "amdgpu_pm.h" |
27 | 28 | #include "soc15.h" |
28 | 29 | #include "soc15d.h" |
@@ -538,7 +539,11 @@ void jpeg_v2_0_dec_ring_emit_ib(struct amdgpu_ring *ring, |
538 | 539 |
|
539 | 540 | amdgpu_ring_write(ring, PACKETJ(mmUVD_LMI_JRBC_IB_VMID_INTERNAL_OFFSET, |
540 | 541 | 0, 0, PACKETJ_TYPE0)); |
541 | | - amdgpu_ring_write(ring, (vmid | (vmid << 4) | (vmid << 8))); |
| 542 | + |
| 543 | + if (ring->funcs->parse_cs) |
| 544 | + amdgpu_ring_write(ring, 0); |
| 545 | + else |
| 546 | + amdgpu_ring_write(ring, (vmid | (vmid << 4) | (vmid << 8))); |
542 | 547 |
|
543 | 548 | amdgpu_ring_write(ring, PACKETJ(mmUVD_LMI_JPEG_VMID_INTERNAL_OFFSET, |
544 | 549 | 0, 0, PACKETJ_TYPE0)); |
@@ -764,6 +769,7 @@ static const struct amdgpu_ring_funcs jpeg_v2_0_dec_ring_vm_funcs = { |
764 | 769 | .get_rptr = jpeg_v2_0_dec_ring_get_rptr, |
765 | 770 | .get_wptr = jpeg_v2_0_dec_ring_get_wptr, |
766 | 771 | .set_wptr = jpeg_v2_0_dec_ring_set_wptr, |
| 772 | + .parse_cs = jpeg_v2_dec_ring_parse_cs, |
767 | 773 | .emit_frame_size = |
768 | 774 | SOC15_FLUSH_GPU_TLB_NUM_WREG * 6 + |
769 | 775 | SOC15_FLUSH_GPU_TLB_NUM_REG_WAIT * 8 + |
@@ -810,3 +816,58 @@ const struct amdgpu_ip_block_version jpeg_v2_0_ip_block = { |
810 | 816 | .rev = 0, |
811 | 817 | .funcs = &jpeg_v2_0_ip_funcs, |
812 | 818 | }; |
| 819 | + |
| 820 | +/** |
| 821 | + * jpeg_v2_dec_ring_parse_cs - command submission parser |
| 822 | + * |
| 823 | + * @parser: Command submission parser context |
| 824 | + * @job: the job to parse |
| 825 | + * @ib: the IB to parse |
| 826 | + * |
| 827 | + * Parse the command stream, return -EINVAL for invalid packet, |
| 828 | + * 0 otherwise |
| 829 | + */ |
| 830 | +int jpeg_v2_dec_ring_parse_cs(struct amdgpu_cs_parser *parser, |
| 831 | + struct amdgpu_job *job, |
| 832 | + struct amdgpu_ib *ib) |
| 833 | +{ |
| 834 | + u32 i, reg, res, cond, type; |
| 835 | + struct amdgpu_device *adev = parser->adev; |
| 836 | + |
| 837 | + for (i = 0; i < ib->length_dw ; i += 2) { |
| 838 | + reg = CP_PACKETJ_GET_REG(ib->ptr[i]); |
| 839 | + res = CP_PACKETJ_GET_RES(ib->ptr[i]); |
| 840 | + cond = CP_PACKETJ_GET_COND(ib->ptr[i]); |
| 841 | + type = CP_PACKETJ_GET_TYPE(ib->ptr[i]); |
| 842 | + |
| 843 | + if (res) /* only support 0 at the moment */ |
| 844 | + return -EINVAL; |
| 845 | + |
| 846 | + switch (type) { |
| 847 | + case PACKETJ_TYPE0: |
| 848 | + if (cond != PACKETJ_CONDITION_CHECK0 || reg < JPEG_REG_RANGE_START || |
| 849 | + reg > JPEG_REG_RANGE_END) { |
| 850 | + dev_err(adev->dev, "Invalid packet [0x%08x]!\n", ib->ptr[i]); |
| 851 | + return -EINVAL; |
| 852 | + } |
| 853 | + break; |
| 854 | + case PACKETJ_TYPE3: |
| 855 | + if (cond != PACKETJ_CONDITION_CHECK3 || reg < JPEG_REG_RANGE_START || |
| 856 | + reg > JPEG_REG_RANGE_END) { |
| 857 | + dev_err(adev->dev, "Invalid packet [0x%08x]!\n", ib->ptr[i]); |
| 858 | + return -EINVAL; |
| 859 | + } |
| 860 | + break; |
| 861 | + case PACKETJ_TYPE6: |
| 862 | + if (ib->ptr[i] == CP_PACKETJ_NOP) |
| 863 | + continue; |
| 864 | + dev_err(adev->dev, "Invalid packet [0x%08x]!\n", ib->ptr[i]); |
| 865 | + return -EINVAL; |
| 866 | + default: |
| 867 | + dev_err(adev->dev, "Unknown packet type %d !\n", type); |
| 868 | + return -EINVAL; |
| 869 | + } |
| 870 | + } |
| 871 | + |
| 872 | + return 0; |
| 873 | +} |
0 commit comments