Lines Matching refs:dec
97 static int flush(struct ruvd_decoder *dec, unsigned flags)
99 return dec->ws->cs_flush(&dec->cs, flags, NULL);
103 static void set_reg(struct ruvd_decoder *dec, unsigned reg, uint32_t val)
105 radeon_emit(&dec->cs, RUVD_PKT0(reg >> 2, 0));
106 radeon_emit(&dec->cs, val);
110 static void send_cmd(struct ruvd_decoder *dec, unsigned cmd, struct pb_buffer *buf, uint32_t off,
115 reloc_idx = dec->ws->cs_add_buffer(&dec->cs, buf, usage | RADEON_USAGE_SYNCHRONIZED, domain);
116 if (!dec->use_legacy) {
118 addr = dec->ws->buffer_get_virtual_address(buf);
120 set_reg(dec, dec->reg.data0, addr);
121 set_reg(dec, dec->reg.data1, addr >> 32);
123 off += dec->ws->buffer_get_reloc_offset(buf);
124 set_reg(dec, RUVD_GPCOM_VCPU_DATA0, off);
125 set_reg(dec, RUVD_GPCOM_VCPU_DATA1, reloc_idx * 4);
127 set_reg(dec, dec->reg.cmd, cmd << 1);
131 static bool have_it(struct ruvd_decoder *dec)
133 return dec->stream_type == RUVD_CODEC_H264_PERF || dec->stream_type == RUVD_CODEC_H265;
137 static void map_msg_fb_it_buf(struct ruvd_decoder *dec)
143 buf = &dec->msg_fb_it_buffers[dec->cur_buffer];
147 dec->ws->buffer_map(dec->ws, buf->res->buf, &dec->cs, PIPE_MAP_WRITE | RADEON_MAP_TEMPORARY);
150 dec->msg = (struct ruvd_msg *)ptr;
151 memset(dec->msg, 0, sizeof(*dec->msg));
153 dec->fb = (uint32_t *)(ptr + FB_BUFFER_OFFSET);
154 if (have_it(dec))
155 dec->it = (uint8_t *)(ptr + FB_BUFFER_OFFSET + dec->fb_size);
159 static void send_msg_buf(struct ruvd_decoder *dec)
164 if (!dec->msg || !dec->fb)
168 buf = &dec->msg_fb_it_buffers[dec->cur_buffer];
171 dec->ws->buffer_unmap(dec->ws, buf->res->buf);
172 dec->msg = NULL;
173 dec->fb = NULL;
174 dec->it = NULL;
176 if (dec->sessionctx.res)
177 send_cmd(dec, RUVD_CMD_SESSION_CONTEXT_BUFFER, dec->sessionctx.res->buf, 0,
181 send_cmd(dec, RUVD_CMD_MSG_BUFFER, buf->res->buf, 0, RADEON_USAGE_READ, RADEON_DOMAIN_GTT);
185 static void next_buffer(struct ruvd_decoder *dec)
187 ++dec->cur_buffer;
188 dec->cur_buffer %= NUM_BUFFERS;
192 static uint32_t profile2stream_type(struct ruvd_decoder *dec, unsigned family)
194 switch (u_reduce_video_profile(dec->base.profile)) {
219 static unsigned calc_ctx_size_h264_perf(struct ruvd_decoder *dec)
222 unsigned width = align(dec->base.width, VL_MACROBLOCK_WIDTH);
223 unsigned height = align(dec->base.height, VL_MACROBLOCK_HEIGHT);
225 unsigned max_references = dec->base.max_references + 1;
231 if (!dec->use_legacy) {
234 switch (dec->base.level) {
273 static unsigned calc_ctx_size_h265_main(struct ruvd_decoder *dec)
275 unsigned width = align(dec->base.width, VL_MACROBLOCK_WIDTH);
276 unsigned height = align(dec->base.height, VL_MACROBLOCK_HEIGHT);
278 unsigned max_references = dec->base.max_references + 1;
280 if (dec->base.width * dec->base.height >= 4096 * 2000)
290 static unsigned calc_ctx_size_h265_main10(struct ruvd_decoder *dec,
297 unsigned width = align(dec->base.width, VL_MACROBLOCK_WIDTH);
298 unsigned height = align(dec->base.height, VL_MACROBLOCK_HEIGHT);
302 unsigned max_references = dec->base.max_references + 1;
304 if (dec->base.width * dec->base.height >= 4096 * 2000)
325 static unsigned get_db_pitch_alignment(struct ruvd_decoder *dec)
327 if (((struct si_screen *)dec->screen)->info.family < CHIP_VEGA10)
334 static unsigned calc_dpb_size(struct ruvd_decoder *dec)
339 unsigned width = align(dec->base.width, VL_MACROBLOCK_WIDTH);
340 unsigned height = align(dec->base.height, VL_MACROBLOCK_HEIGHT);
343 unsigned max_references = dec->base.max_references + 1;
346 image_size = align(width, get_db_pitch_alignment(dec)) * height;
354 switch (u_reduce_video_profile(dec->base.profile)) {
356 if (!dec->use_legacy) {
360 if (dec->stream_type == RUVD_CODEC_H264_PERF)
362 switch (dec->base.level) {
391 if ((dec->stream_type != RUVD_CODEC_H264_PERF) ||
392 (((struct si_screen *)dec->screen)->info.family < CHIP_POLARIS10)) {
401 if ((dec->stream_type != RUVD_CODEC_H264_PERF) ||
402 (((struct si_screen *)dec->screen)->info.family < CHIP_POLARIS10)) {
413 if (dec->base.width * dec->base.height >= 4096 * 2000)
420 if (dec->base.profile == PIPE_VIDEO_PROFILE_HEVC_MAIN_10)
421 dpb_size = align((align(width, get_db_pitch_alignment(dec)) * height * 9) / 4, 256) *
424 dpb_size = align((align(width, get_db_pitch_alignment(dec)) * height * 3) / 2, 256) *
488 static struct ruvd_h264 get_h264_msg(struct ruvd_decoder *dec, struct pipe_h264_picture_desc *pic)
512 result.level = dec->base.level;
526 switch (dec->base.chroma_format) {
564 if (dec->stream_type == RUVD_CODEC_H264_PERF) {
565 memcpy(dec->it, result.scaling_list_4x4, 6 * 16);
566 memcpy((dec->it + 96), result.scaling_list_8x8, 2 * 64);
586 static struct ruvd_h265 get_h265_msg(struct ruvd_decoder *dec, struct pipe_video_buffer *target,
604 if (((struct si_screen *)dec->screen)->info.family == CHIP_CARRIZO)
680 if (dec->render_pic_list[i] == pic->ref[j])
683 dec->render_pic_list[i] = NULL;
685 dec->render_pic_list[i] = NULL;
689 if (dec->render_pic_list[i] == NULL) {
690 dec->render_pic_list[i] = target;
696 vl_video_buffer_set_associated_data(target, &dec->base, (void *)(uintptr_t)result.curr_idx,
706 ref_pic = (uintptr_t)vl_video_buffer_get_associated_data(ref, &dec->base);
733 memcpy(dec->it, pic->pps->sps->ScalingList4x4, 6 * 16);
734 memcpy(dec->it + 96, pic->pps->sps->ScalingList8x8, 6 * 64);
735 memcpy(dec->it + 480, pic->pps->sps->ScalingList16x16, 6 * 64);
736 memcpy(dec->it + 864, pic->pps->sps->ScalingList32x32, 2 * 64);
844 static uint32_t get_ref_pic_idx(struct ruvd_decoder *dec, struct pipe_video_buffer *ref)
846 uint32_t min = MAX2(dec->frame_number, NUM_MPEG2_REFS) - NUM_MPEG2_REFS;
847 uint32_t max = MAX2(dec->frame_number, 1) - 1;
855 frame = (uintptr_t)vl_video_buffer_get_associated_data(ref, &dec->base);
862 static struct ruvd_mpeg2 get_mpeg2_msg(struct ruvd_decoder *dec,
870 result.decoded_pic_idx = dec->frame_number;
872 result.ref_pic_idx[i] = get_ref_pic_idx(dec, pic->ref[i]);
908 static struct ruvd_mpeg4 get_mpeg4_msg(struct ruvd_decoder *dec,
915 result.decoded_pic_idx = dec->frame_number;
917 result.ref_pic_idx[i] = get_ref_pic_idx(dec, pic->ref[i]);
925 result.video_object_layer_width = dec->base.width;
926 result.video_object_layer_height = dec->base.height;
973 struct ruvd_decoder *dec = (struct ruvd_decoder *)decoder;
978 map_msg_fb_it_buf(dec);
979 dec->msg->size = sizeof(*dec->msg);
980 dec->msg->msg_type = RUVD_MSG_DESTROY;
981 dec->msg->stream_handle = dec->stream_handle;
982 send_msg_buf(dec);
984 flush(dec, 0);
986 dec->ws->cs_destroy(&dec->cs);
989 si_vid_destroy_buffer(&dec->msg_fb_it_buffers[i]);
990 si_vid_destroy_buffer(&dec->bs_buffers[i]);
993 si_vid_destroy_buffer(&dec->dpb);
994 si_vid_destroy_buffer(&dec->ctx);
995 si_vid_destroy_buffer(&dec->sessionctx);
997 FREE(dec);
1006 struct ruvd_decoder *dec = (struct ruvd_decoder *)decoder;
1011 frame = ++dec->frame_number;
1015 dec->bs_size = 0;
1016 dec->bs_ptr = dec->ws->buffer_map(dec->ws, dec->bs_buffers[dec->cur_buffer].res->buf, &dec->cs,
1041 struct ruvd_decoder *dec = (struct ruvd_decoder *)decoder;
1046 if (!dec->bs_ptr)
1050 struct rvid_buffer *buf = &dec->bs_buffers[dec->cur_buffer];
1051 unsigned new_size = dec->bs_size + sizes[i];
1054 dec->ws->buffer_unmap(dec->ws, buf->res->buf);
1055 if (!si_vid_resize_buffer(dec->screen, &dec->cs, buf, new_size)) {
1060 dec->bs_ptr = dec->ws->buffer_map(dec->ws, buf->res->buf, &dec->cs,
1062 if (!dec->bs_ptr)
1065 dec->bs_ptr += dec->bs_size;
1068 memcpy(dec->bs_ptr, buffers[i], sizes[i]);
1069 dec->bs_size += sizes[i];
1070 dec->bs_ptr += sizes[i];
1080 struct ruvd_decoder *dec = (struct ruvd_decoder *)decoder;
1087 if (!dec->bs_ptr)
1090 msg_fb_it_buf = &dec->msg_fb_it_buffers[dec->cur_buffer];
1091 bs_buf = &dec->bs_buffers[dec->cur_buffer];
1093 bs_size = align(dec->bs_size, 128);
1094 memset(dec->bs_ptr, 0, bs_size - dec->bs_size);
1095 dec->ws->buffer_unmap(dec->ws, bs_buf->res->buf);
1097 map_msg_fb_it_buf(dec);
1098 dec->msg->size = sizeof(*dec->msg);
1099 dec->msg->msg_type = RUVD_MSG_DECODE;
1100 dec->msg->stream_handle = dec->stream_handle;
1101 dec->msg->status_report_feedback_number = dec->frame_number;
1103 dec->msg->body.decode.stream_type = dec->stream_type;
1104 dec->msg->body.decode.decode_flags = 0x1;
1105 dec->msg->body.decode.width_in_samples = dec->base.width;
1106 dec->msg->body.decode.height_in_samples = dec->base.height;
1110 dec->msg->body.decode.width_in_samples =
1111 align(dec->msg->body.decode.width_in_samples, 16) / 16;
1112 dec->msg->body.decode.height_in_samples =
1113 align(dec->msg->body.decode.height_in_samples, 16) / 16;
1116 if (dec->dpb.res)
1117 dec->msg->body.decode.dpb_size = dec->dpb.res->buf->size;
1118 dec->msg->body.decode.bsd_size = bs_size;
1119 dec->msg->body.decode.db_pitch = align(dec->base.width, get_db_pitch_alignment(dec));
1121 if (dec->stream_type == RUVD_CODEC_H264_PERF &&
1122 ((struct si_screen *)dec->screen)->info.family >= CHIP_POLARIS10)
1123 dec->msg->body.decode.dpb_reserved = dec->ctx.res->buf->size;
1125 dt = dec->set_dtb(dec->msg, (struct vl_video_buffer *)target);
1126 if (((struct si_screen *)dec->screen)->info.family >= CHIP_STONEY)
1127 dec->msg->body.decode.dt_wa_chroma_top_offset = dec->msg->body.decode.dt_pitch / 2;
1131 dec->msg->body.decode.codec.h264 =
1132 get_h264_msg(dec, (struct pipe_h264_picture_desc *)picture);
1136 dec->msg->body.decode.codec.h265 =
1137 get_h265_msg(dec, target, (struct pipe_h265_picture_desc *)picture);
1138 if (dec->ctx.res == NULL) {
1140 if (dec->base.profile == PIPE_VIDEO_PROFILE_HEVC_MAIN_10)
1141 ctx_size = calc_ctx_size_h265_main10(dec, (struct pipe_h265_picture_desc *)picture);
1143 ctx_size = calc_ctx_size_h265_main(dec);
1144 if (!si_vid_create_buffer(dec->screen, &dec->ctx, ctx_size, PIPE_USAGE_DEFAULT)) {
1147 si_vid_clear_buffer(decoder->context, &dec->ctx);
1150 if (dec->ctx.res)
1151 dec->msg->body.decode.dpb_reserved = dec->ctx.res->buf->size;
1155 dec->msg->body.decode.codec.vc1 = get_vc1_msg((struct pipe_vc1_picture_desc *)picture);
1159 dec->msg->body.decode.codec.mpeg2 =
1160 get_mpeg2_msg(dec, (struct pipe_mpeg12_picture_desc *)picture);
1164 dec->msg->body.decode.codec.mpeg4 =
1165 get_mpeg4_msg(dec, (struct pipe_mpeg4_picture_desc *)picture);
1176 dec->msg->body.decode.db_surf_tile_config = dec->msg->body.decode.dt_surf_tile_config;
1177 dec->msg->body.decode.extension_support = 0x1;
1180 dec->fb[0] = dec->fb_size;
1182 send_msg_buf(dec);
1184 if (dec->dpb.res)
1185 send_cmd(dec, RUVD_CMD_DPB_BUFFER, dec->dpb.res->buf, 0, RADEON_USAGE_READWRITE,
1188 if (dec->ctx.res)
1189 send_cmd(dec, RUVD_CMD_CONTEXT_BUFFER, dec->ctx.res->buf, 0, RADEON_USAGE_READWRITE,
1191 send_cmd(dec, RUVD_CMD_BITSTREAM_BUFFER, bs_buf->res->buf, 0, RADEON_USAGE_READ,
1193 send_cmd(dec, RUVD_CMD_DECODING_TARGET_BUFFER, dt, 0, RADEON_USAGE_WRITE, RADEON_DOMAIN_VRAM);
1194 send_cmd(dec, RUVD_CMD_FEEDBACK_BUFFER, msg_fb_it_buf->res->buf, FB_BUFFER_OFFSET,
1196 if (have_it(dec))
1197 send_cmd(dec, RUVD_CMD_ITSCALING_TABLE_BUFFER, msg_fb_it_buf->res->buf,
1198 FB_BUFFER_OFFSET + dec->fb_size, RADEON_USAGE_READ, RADEON_DOMAIN_GTT);
1199 set_reg(dec, dec->reg.cntl, 1);
1201 flush(dec, PIPE_FLUSH_ASYNC);
1202 next_buffer(dec);
1224 struct ruvd_decoder *dec;
1246 dec = CALLOC_STRUCT(ruvd_decoder);
1248 if (!dec)
1252 dec->use_legacy = true;
1254 dec->base = *templ;
1255 dec->base.context = context;
1256 dec->base.width = width;
1257 dec->base.height = height;
1259 dec->base.destroy = ruvd_destroy;
1260 dec->base.begin_frame = ruvd_begin_frame;
1261 dec->base.decode_macroblock = ruvd_decode_macroblock;
1262 dec->base.decode_bitstream = ruvd_decode_bitstream;
1263 dec->base.end_frame = ruvd_end_frame;
1264 dec->base.flush = ruvd_flush;
1266 dec->stream_type = profile2stream_type(dec, sctx->family);
1267 dec->set_dtb = set_dtb;
1268 dec->stream_handle = si_vid_alloc_stream_handle();
1269 dec->screen = context->screen;
1270 dec->ws = ws;
1272 if (!ws->cs_create(&dec->cs, sctx->ctx, AMD_IP_UVD, NULL, NULL, false)) {
1278 dec->render_pic_list[i] = NULL;
1279 dec->fb_size = (sctx->family == CHIP_TONGA) ? FB_BUFFER_SIZE_TONGA : FB_BUFFER_SIZE;
1282 unsigned msg_fb_it_size = FB_BUFFER_OFFSET + dec->fb_size;
1284 if (have_it(dec))
1286 if (!si_vid_create_buffer(dec->screen, &dec->msg_fb_it_buffers[i], msg_fb_it_size,
1292 if (!si_vid_create_buffer(dec->screen, &dec->bs_buffers[i], bs_buf_size,
1298 si_vid_clear_buffer(context, &dec->msg_fb_it_buffers[i]);
1299 si_vid_clear_buffer(context, &dec->bs_buffers[i]);
1302 dpb_size = calc_dpb_size(dec);
1304 if (!si_vid_create_buffer(dec->screen, &dec->dpb, dpb_size, PIPE_USAGE_DEFAULT)) {
1308 si_vid_clear_buffer(context, &dec->dpb);
1311 if (dec->stream_type == RUVD_CODEC_H264_PERF && sctx->family >= CHIP_POLARIS10) {
1312 unsigned ctx_size = calc_ctx_size_h264_perf(dec);
1313 if (!si_vid_create_buffer(dec->screen, &dec->ctx, ctx_size, PIPE_USAGE_DEFAULT)) {
1317 si_vid_clear_buffer(context, &dec->ctx);
1321 if (!si_vid_create_buffer(dec->screen, &dec->sessionctx, UVD_SESSION_CONTEXT_SIZE,
1326 si_vid_clear_buffer(context, &dec->sessionctx);
1330 dec->reg.data0 = RUVD_GPCOM_VCPU_DATA0_SOC15;
1331 dec->reg.data1 = RUVD_GPCOM_VCPU_DATA1_SOC15;
1332 dec->reg.cmd = RUVD_GPCOM_VCPU_CMD_SOC15;
1333 dec->reg.cntl = RUVD_ENGINE_CNTL_SOC15;
1335 dec->reg.data0 = RUVD_GPCOM_VCPU_DATA0;
1336 dec->reg.data1 = RUVD_GPCOM_VCPU_DATA1;
1337 dec->reg.cmd = RUVD_GPCOM_VCPU_CMD;
1338 dec->reg.cntl = RUVD_ENGINE_CNTL;
1341 map_msg_fb_it_buf(dec);
1342 dec->msg->size = sizeof(*dec->msg);
1343 dec->msg->msg_type = RUVD_MSG_CREATE;
1344 dec->msg->stream_handle = dec->stream_handle;
1345 dec->msg->body.create.stream_type = dec->stream_type;
1346 dec->msg->body.create.width_in_samples = dec->base.width;
1347 dec->msg->body.create.height_in_samples = dec->base.height;
1348 dec->msg->body.create.dpb_size = dpb_size;
1349 send_msg_buf(dec);
1350 r = flush(dec, 0);
1354 next_buffer(dec);
1356 return &dec->base;
1359 dec->ws->cs_destroy(&dec->cs);
1362 si_vid_destroy_buffer(&dec->msg_fb_it_buffers[i]);
1363 si_vid_destroy_buffer(&dec->bs_buffers[i]);
1366 si_vid_destroy_buffer(&dec->dpb);
1367 si_vid_destroy_buffer(&dec->ctx);
1368 si_vid_destroy_buffer(&dec->sessionctx);
1370 FREE(dec);