1 /* 2 * Copyright 2011-2013 Maarten Lankhorst 3 * 4 * Permission is hereby granted, free of charge, to any person obtaining a 5 * copy of this software and associated documentation files (the "Software"), 6 * to deal in the Software without restriction, including without limitation 7 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 8 * and/or sell copies of the Software, and to permit persons to whom the 9 * Software is furnished to do so, subject to the following conditions: 10 * 11 * The above copyright notice and this permission notice shall be included in 12 * all copies or substantial portions of the Software. 13 * 14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 17 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR 18 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 19 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 20 * OTHER DEALINGS IN THE SOFTWARE. 21 */ 22 23 #include "nouveau_vp3_video.h" 24 25 struct mpeg12_picparm_vp { 26 uint16_t width; // 00 in mb units 27 uint16_t height; // 02 in mb units 28 29 uint32_t unk04; // 04 stride for Y? 30 uint32_t unk08; // 08 stride for CbCr? 31 32 uint32_t ofs[6]; // 1c..20 ofs 33 uint32_t bucket_size; // 24 34 uint32_t inter_ring_data_size; // 28 35 uint16_t unk2c; // 2c 36 uint16_t alternate_scan; // 2e 37 uint16_t unk30; // 30 not seen set yet 38 uint16_t picture_structure; // 32 39 uint16_t pad2[3]; 40 uint16_t unk3a; // 3a set on I frame? 41 42 uint32_t f_code[4]; // 3c 43 uint32_t picture_coding_type; // 4c 44 uint32_t intra_dc_precision; // 50 45 uint32_t q_scale_type; // 54 46 uint32_t top_field_first; // 58 47 uint32_t full_pel_forward_vector; // 5c 48 uint32_t full_pel_backward_vector; // 60 49 uint8_t intra_quantizer_matrix[0x40]; // 64 50 uint8_t non_intra_quantizer_matrix[0x40]; // a4 51 }; 52 53 struct mpeg4_picparm_vp { 54 uint32_t width; // 00 in normal units 55 uint32_t height; // 04 in normal units 56 uint32_t unk08; // stride 1 57 uint32_t unk0c; // stride 2 58 uint32_t ofs[6]; // 10..24 ofs 59 uint32_t bucket_size; // 28 60 uint32_t pad1; // 2c, pad 61 uint32_t pad2; // 30 62 uint32_t inter_ring_data_size; // 34 63 64 uint32_t trd[2]; // 38, 3c 65 uint32_t trb[2]; // 40, 44 66 uint32_t u48; // XXX codec selection? Should test with different values of VdpDecoderProfile 67 uint16_t f_code_fw; // 4c 68 uint16_t f_code_bw; // 4e 69 uint8_t interlaced; // 50 70 71 uint8_t quant_type; // bool, written to 528 72 uint8_t quarter_sample; // bool, written to 548 73 uint8_t short_video_header; // bool, negated written to 528 shifted by 1 74 uint8_t u54; // bool, written to 0x740 75 uint8_t vop_coding_type; // 55 76 uint8_t rounding_control; // 56 77 uint8_t alternate_vertical_scan_flag; // 57 bool 78 uint8_t top_field_first; // bool, written to vuc 79 80 uint8_t pad4[3]; // 59, 5a, 5b, contains garbage on blob 81 82 uint32_t intra[0x10]; // 5c 83 uint32_t non_intra[0x10]; // 9c 84 uint32_t pad5[0x10]; // bc what does this do? 85 // udc..uff pad? 86 }; 87 88 // Full version, with data pumped from BSP 89 struct vc1_picparm_vp { 90 uint32_t bucket_size; // 00 91 uint32_t pad; // 04 92 93 uint32_t inter_ring_data_size; // 08 94 uint32_t unk0c; // stride 1 95 uint32_t unk10; // stride 2 96 uint32_t ofs[6]; // 14..28 ofs 97 98 uint16_t width; // 2c 99 uint16_t height; // 2e 100 101 uint8_t profile; // 30 0 = simple, 1 = main, 2 = advanced 102 uint8_t loopfilter; // 31 written into vuc 103 uint8_t fastuvmc; // 32, written into vuc 104 uint8_t dquant; // 33 105 106 uint8_t overlap; // 34 107 uint8_t quantizer; // 35 108 uint8_t u36; // 36, bool 109 uint8_t pad2; // 37, to align to 0x38 110 }; 111 112 struct h264_picparm_vp { // 700..a00 113 uint16_t width, height; 114 uint32_t stride1, stride2; // 04 08 115 uint32_t ofs[6]; // 0c..24 in-image offset 116 117 uint32_t tmp_stride; 118 uint32_t bucket_size; // 28 bucket size 119 uint32_t inter_ring_data_size; // 2c 120 121 unsigned mb_adaptive_frame_field_flag : 1; // 0 122 unsigned direct_8x8_inference_flag : 1; // 1 0x02: into vuc ofs 56 123 unsigned weighted_pred_flag : 1; // 2 0x04 124 unsigned constrained_intra_pred_flag : 1; // 3 0x08: into vuc ofs 68 125 unsigned is_reference : 1; // 4 126 unsigned interlace : 1; // 5 field_pic_flag 127 unsigned bottom_field_flag : 1; // 6 128 unsigned second_field : 1; // 7 0x80: nfi yet 129 130 signed log2_max_frame_num_minus4 : 4; // 31 0..3 131 unsigned chroma_format_idc : 2; // 31 4..5 132 unsigned pic_order_cnt_type : 2; // 31 6..7 133 signed pic_init_qp_minus26 : 6; // 32 0..5 134 signed chroma_qp_index_offset : 5; // 32 6..10 135 signed second_chroma_qp_index_offset : 5; // 32 11..15 136 137 unsigned weighted_bipred_idc : 2; // 34 0..1 138 unsigned fifo_dec_index : 7; // 34 2..8 139 unsigned tmp_idx : 5; // 34 9..13 140 unsigned frame_number : 16; // 34 14..29 141 unsigned u34_3030 : 1; // 34 30..30 pp.u34[30:30] 142 unsigned u34_3131 : 1; // 34 31..31 pad? 143 144 uint32_t field_order_cnt[2]; // 38, 3c 145 146 struct { // 40 147 unsigned fifo_idx : 7; // 00 0..6 148 unsigned tmp_idx : 5; // 00 7..11 149 unsigned top_is_reference : 1; // 00 12 150 unsigned bottom_is_reference : 1; // 00 13 151 unsigned is_long_term : 1; // 00 14 152 unsigned notseenyet : 1; // 00 15 pad? 153 unsigned field_pic_flag : 1; // 00 16 154 unsigned top_field_marking : 4; // 00 17..20 155 unsigned bottom_field_marking : 4; // 00 21..24 156 unsigned pad : 7; // 00 d25..31 157 158 uint32_t field_order_cnt[2]; // 04,08 159 uint32_t frame_idx; // 0c 160 } refs[0x10]; 161 162 uint8_t m4x4[6][16]; // 140 163 uint8_t m8x8[2][64]; // 1a0 164 uint32_t u220; // 220 number of extra reorder_list to append? 165 uint8_t u224[0x20]; // 224..244 reorder_list append ? 166 uint8_t nfi244[0xb0]; // add some pad to make sure nulls are read 167 }; 168 169 static void 170 nouveau_vp3_handle_references(struct nouveau_vp3_decoder *dec, struct nouveau_vp3_video_buffer *refs[16], unsigned seq, struct nouveau_vp3_video_buffer *target) 171 { 172 unsigned i, idx, empty_spot = ~0; 173 174 for (i = 0; i < dec->base.max_references; ++i) { 175 if (!refs[i]) 176 continue; 177 178 idx = refs[i]->valid_ref; 179 //debug_printf("ref[%i] %p in slot %i\n", i, refs[i], idx); 180 181 if (dec->refs[idx].vidbuf != refs[i]) { 182 debug_printf("%p is not a real ref\n", refs[i]); 183 // FIXME: Maybe do m2mf copy here if a application really depends on it? 184 continue; 185 } 186 187 assert(dec->refs[idx].vidbuf == refs[i]); 188 dec->refs[idx].last_used = seq; 189 } 190 191 if (dec->refs[target->valid_ref].vidbuf == target) { 192 dec->refs[target->valid_ref].last_used = seq; 193 return; 194 } 195 196 /* Try to find a real empty spot first, there should be one.. 197 */ 198 for (i = 0; i < dec->base.max_references + 1; ++i) { 199 if (dec->refs[i].vidbuf == target) { 200 empty_spot = i; 201 break; 202 } else if (!dec->refs[i].last_used) { 203 empty_spot = i; 204 } else if (empty_spot == ~0U && dec->refs[i].last_used != seq) 205 empty_spot = i; 206 } 207 208 assert(empty_spot < dec->base.max_references+1); 209 dec->refs[empty_spot].last_used = seq; 210 // debug_printf("Kicked %p to add %p to slot %i\n", dec->refs[empty_spot].vidbuf, target, empty_spot); 211 dec->refs[empty_spot].vidbuf = target; 212 dec->refs[empty_spot].decoded_bottom = dec->refs[empty_spot].decoded_top = 0; 213 target->valid_ref = empty_spot; 214 } 215 216 static uint32_t 217 nouveau_vp3_fill_picparm_mpeg12_vp(struct nouveau_vp3_decoder *dec, 218 struct pipe_mpeg12_picture_desc *desc, 219 struct nouveau_vp3_video_buffer *refs[16], 220 unsigned *is_ref, 221 char *map) 222 { 223 struct mpeg12_picparm_vp pic_vp_stub = {}, *pic_vp = &pic_vp_stub; 224 uint32_t i, ret = 0x01010, ring; // !async_shutdown << 16 | watchdog << 12 | irq_record << 4 | unk; 225 assert(!(dec->base.width & 0xf)); 226 *is_ref = desc->picture_coding_type <= 2; 227 228 if (dec->base.profile == PIPE_VIDEO_PROFILE_MPEG1) 229 pic_vp->picture_structure = 3; 230 else 231 pic_vp->picture_structure = desc->picture_structure; 232 233 assert(desc->picture_structure != 4); 234 if (desc->picture_structure == 4) // Untested, but should work 235 ret |= 0x100; 236 pic_vp->width = mb(dec->base.width); 237 pic_vp->height = mb(dec->base.height); 238 pic_vp->unk08 = pic_vp->unk04 = (dec->base.width+0xf)&~0xf; // Stride 239 240 nouveau_vp3_ycbcr_offsets(dec, &pic_vp->ofs[1], &pic_vp->ofs[3], &pic_vp->ofs[4]); 241 pic_vp->ofs[5] = pic_vp->ofs[3]; 242 pic_vp->ofs[0] = pic_vp->ofs[2] = 0; 243 nouveau_vp3_inter_sizes(dec, 1, &ring, &pic_vp->bucket_size, &pic_vp->inter_ring_data_size); 244 245 pic_vp->alternate_scan = desc->alternate_scan; 246 pic_vp->pad2[0] = pic_vp->pad2[1] = pic_vp->pad2[2] = 0; 247 pic_vp->unk30 = desc->picture_structure < 3 && (desc->picture_structure == 2 - desc->top_field_first); 248 pic_vp->unk3a = (desc->picture_coding_type == 1); 249 for (i = 0; i < 4; ++i) 250 pic_vp->f_code[i] = desc->f_code[i/2][i%2] + 1; // FU 251 pic_vp->picture_coding_type = desc->picture_coding_type; 252 pic_vp->intra_dc_precision = desc->intra_dc_precision; 253 pic_vp->q_scale_type = desc->q_scale_type; 254 pic_vp->top_field_first = desc->top_field_first; 255 pic_vp->full_pel_forward_vector = desc->full_pel_forward_vector; 256 pic_vp->full_pel_backward_vector = desc->full_pel_backward_vector; 257 memcpy(pic_vp->intra_quantizer_matrix, desc->intra_matrix, 0x40); 258 memcpy(pic_vp->non_intra_quantizer_matrix, desc->non_intra_matrix, 0x40); 259 memcpy(map, pic_vp, sizeof(*pic_vp)); 260 refs[0] = (struct nouveau_vp3_video_buffer *)desc->ref[0]; 261 refs[!!refs[0]] = (struct nouveau_vp3_video_buffer *)desc->ref[1]; 262 return ret | (dec->base.profile != PIPE_VIDEO_PROFILE_MPEG1); 263 } 264 265 static uint32_t 266 nouveau_vp3_fill_picparm_mpeg4_vp(struct nouveau_vp3_decoder *dec, 267 struct pipe_mpeg4_picture_desc *desc, 268 struct nouveau_vp3_video_buffer *refs[16], 269 unsigned *is_ref, 270 char *map) 271 { 272 struct mpeg4_picparm_vp pic_vp_stub = {}, *pic_vp = &pic_vp_stub; 273 uint32_t ring, ret = 0x01014; // !async_shutdown << 16 | watchdog << 12 | irq_record << 4 | unk; 274 *is_ref = desc->vop_coding_type <= 1; 275 276 pic_vp->width = dec->base.width; 277 pic_vp->height = mb(dec->base.height)<<4; 278 pic_vp->unk0c = pic_vp->unk08 = mb(dec->base.width)<<4; // Stride 279 280 nouveau_vp3_ycbcr_offsets(dec, &pic_vp->ofs[1], &pic_vp->ofs[3], &pic_vp->ofs[4]); 281 pic_vp->ofs[5] = pic_vp->ofs[3]; 282 pic_vp->ofs[0] = pic_vp->ofs[2] = 0; 283 pic_vp->pad1 = pic_vp->pad2 = 0; 284 nouveau_vp3_inter_sizes(dec, 1, &ring, &pic_vp->bucket_size, &pic_vp->inter_ring_data_size); 285 286 pic_vp->trd[0] = desc->trd[0]; 287 pic_vp->trd[1] = desc->trd[1]; 288 pic_vp->trb[0] = desc->trb[0]; 289 pic_vp->trb[1] = desc->trb[1]; 290 pic_vp->u48 = 0; // Codec? 291 pic_vp->pad1 = pic_vp->pad2 = 0; 292 pic_vp->f_code_fw = desc->vop_fcode_forward; 293 pic_vp->f_code_bw = desc->vop_fcode_backward; 294 pic_vp->interlaced = desc->interlaced; 295 pic_vp->quant_type = desc->quant_type; 296 pic_vp->quarter_sample = desc->quarter_sample; 297 pic_vp->short_video_header = desc->short_video_header; 298 pic_vp->u54 = 0; 299 pic_vp->vop_coding_type = desc->vop_coding_type; 300 pic_vp->rounding_control = desc->rounding_control; 301 pic_vp->alternate_vertical_scan_flag = desc->alternate_vertical_scan_flag; 302 pic_vp->top_field_first = desc->top_field_first; 303 304 memcpy(pic_vp->intra, desc->intra_matrix, 0x40); 305 memcpy(pic_vp->non_intra, desc->non_intra_matrix, 0x40); 306 memcpy(map, pic_vp, sizeof(*pic_vp)); 307 refs[0] = (struct nouveau_vp3_video_buffer *)desc->ref[0]; 308 refs[!!refs[0]] = (struct nouveau_vp3_video_buffer *)desc->ref[1]; 309 return ret; 310 } 311 312 static uint32_t 313 nouveau_vp3_fill_picparm_h264_vp(struct nouveau_vp3_decoder *dec, 314 const struct pipe_h264_picture_desc *d, 315 struct nouveau_vp3_video_buffer *refs[16], 316 unsigned *is_ref, 317 char *map) 318 { 319 struct h264_picparm_vp stub_h = {}, *h = &stub_h; 320 unsigned ring, i, j = 0; 321 assert(offsetof(struct h264_picparm_vp, u224) == 0x224); 322 *is_ref = d->is_reference; 323 dec->last_frame_num = d->frame_num; 324 325 h->width = mb(dec->base.width); 326 h->height = mb(dec->base.height); 327 h->stride1 = h->stride2 = mb(dec->base.width)*16; 328 nouveau_vp3_ycbcr_offsets(dec, &h->ofs[1], &h->ofs[3], &h->ofs[4]); 329 h->ofs[5] = h->ofs[3]; 330 h->ofs[0] = h->ofs[2] = 0; 331 h->tmp_stride = dec->tmp_stride >> 8; 332 assert(h->tmp_stride); 333 nouveau_vp3_inter_sizes(dec, d->slice_count, &ring, &h->bucket_size, &h->inter_ring_data_size); 334 335 h->u220 = 0; 336 h->mb_adaptive_frame_field_flag = d->pps->sps->mb_adaptive_frame_field_flag; 337 h->direct_8x8_inference_flag = d->pps->sps->direct_8x8_inference_flag; 338 h->weighted_pred_flag = d->pps->weighted_pred_flag; 339 h->constrained_intra_pred_flag = d->pps->constrained_intra_pred_flag; 340 h->is_reference = d->is_reference; 341 h->interlace = d->field_pic_flag; 342 h->bottom_field_flag = d->bottom_field_flag; 343 h->second_field = 0; // set in nouveau_vp3_fill_picparm_h264_vp_refs 344 345 h->log2_max_frame_num_minus4 = d->pps->sps->log2_max_frame_num_minus4; 346 h->chroma_format_idc = 1; 347 348 h->pic_order_cnt_type = d->pps->sps->pic_order_cnt_type; 349 h->pic_init_qp_minus26 = d->pps->pic_init_qp_minus26; 350 h->chroma_qp_index_offset = d->pps->chroma_qp_index_offset; 351 h->second_chroma_qp_index_offset = d->pps->second_chroma_qp_index_offset; 352 h->weighted_bipred_idc = d->pps->weighted_bipred_idc; 353 h->tmp_idx = 0; // set in h264_vp_refs below 354 h->fifo_dec_index = 0; // always set to 0 to be fifo compatible with other codecs 355 h->frame_number = d->frame_num; 356 h->u34_3030 = h->u34_3131 = 0; 357 h->field_order_cnt[0] = d->field_order_cnt[0]; 358 h->field_order_cnt[1] = d->field_order_cnt[1]; 359 memcpy(h->m4x4, d->pps->ScalingList4x4, sizeof(h->m4x4)); 360 memcpy(h->m8x8, d->pps->ScalingList8x8, sizeof(h->m8x8)); 361 h->u220 = 0; 362 for (i = 0; i < d->num_ref_frames; ++i) { 363 if (!d->ref[i]) 364 break; 365 refs[j] = (struct nouveau_vp3_video_buffer *)d->ref[i]; 366 h->refs[j].fifo_idx = j + 1; 367 h->refs[j].tmp_idx = refs[j]->valid_ref; 368 assert(dec->refs[refs[j]->valid_ref].vidbuf == refs[j]); 369 h->refs[j].field_order_cnt[0] = d->field_order_cnt_list[i][0]; 370 h->refs[j].field_order_cnt[1] = d->field_order_cnt_list[i][1]; 371 h->refs[j].frame_idx = d->frame_num_list[i]; 372 if (!dec->refs[refs[j]->valid_ref].field_pic_flag) { 373 h->refs[j].top_is_reference = d->top_is_reference[i]; 374 h->refs[j].bottom_is_reference = d->bottom_is_reference[i]; 375 } 376 h->refs[j].is_long_term = d->is_long_term[i]; 377 h->refs[j].notseenyet = 0; 378 h->refs[j].field_pic_flag = dec->refs[refs[j]->valid_ref].field_pic_flag; 379 h->refs[j].top_field_marking = 380 dec->refs[refs[j]->valid_ref].decoded_top && d->top_is_reference[i] ? 381 1 + d->is_long_term[i] : 0; 382 h->refs[j].bottom_field_marking = 383 dec->refs[refs[j]->valid_ref].decoded_bottom && d->bottom_is_reference[i] ? 384 1 + d->is_long_term[i] : 0; 385 h->refs[j].pad = 0; 386 j++; 387 } 388 for (; i < 16; ++i) 389 assert(!d->ref[i]); 390 assert(d->num_ref_frames <= dec->base.max_references); 391 392 for (; i < d->num_ref_frames; ++i) 393 h->refs[j].field_pic_flag = d->field_pic_flag; 394 *(struct h264_picparm_vp *)map = *h; 395 396 return 0x1113; 397 } 398 399 static void 400 nouveau_vp3_fill_picparm_h264_vp_refs(struct nouveau_vp3_decoder *dec, 401 struct pipe_h264_picture_desc *d, 402 struct nouveau_vp3_video_buffer *refs[16], 403 struct nouveau_vp3_video_buffer *target, 404 char *map) 405 { 406 struct h264_picparm_vp *h = (struct h264_picparm_vp *)map; 407 assert(dec->refs[target->valid_ref].vidbuf == target); 408 // debug_printf("Target: %p\n", target); 409 410 if (!dec->refs[target->valid_ref].decoded_top && 411 !dec->refs[target->valid_ref].decoded_bottom) 412 dec->refs[target->valid_ref].decoded_first = d->bottom_field_flag; 413 else if (dec->refs[target->valid_ref].decoded_first != d->bottom_field_flag) 414 h->second_field = 1; 415 416 h->tmp_idx = target->valid_ref; 417 dec->refs[target->valid_ref].field_pic_flag = d->field_pic_flag; 418 if (!d->field_pic_flag || d->bottom_field_flag) 419 dec->refs[target->valid_ref].decoded_bottom = 1; 420 if (!d->field_pic_flag || !d->bottom_field_flag) 421 dec->refs[target->valid_ref].decoded_top = 1; 422 } 423 424 static uint32_t 425 nouveau_vp3_fill_picparm_vc1_vp(struct nouveau_vp3_decoder *dec, 426 struct pipe_vc1_picture_desc *d, 427 struct nouveau_vp3_video_buffer *refs[16], 428 unsigned *is_ref, 429 char *map) 430 { 431 struct vc1_picparm_vp *vc = (struct vc1_picparm_vp *)map; 432 unsigned ring; 433 assert(dec->base.profile != PIPE_VIDEO_PROFILE_VC1_SIMPLE); 434 *is_ref = d->picture_type <= 1; 435 436 nouveau_vp3_ycbcr_offsets(dec, &vc->ofs[1], &vc->ofs[3], &vc->ofs[4]); 437 vc->ofs[5] = vc->ofs[3]; 438 vc->ofs[0] = vc->ofs[2] = 0; 439 vc->width = dec->base.width; 440 vc->height = mb(dec->base.height)<<4; 441 vc->unk0c = vc->unk10 = mb(dec->base.width)<<4; // Stride 442 vc->pad = vc->pad2 = 0; 443 nouveau_vp3_inter_sizes(dec, 1, &ring, &vc->bucket_size, &vc->inter_ring_data_size); 444 vc->profile = dec->base.profile - PIPE_VIDEO_PROFILE_VC1_SIMPLE; 445 vc->loopfilter = d->loopfilter; 446 vc->fastuvmc = d->fastuvmc; 447 vc->dquant = d->dquant; 448 vc->overlap = d->overlap; 449 vc->quantizer = d->quantizer; 450 vc->u36 = 0; // ? No idea what this one is.. 451 refs[0] = (struct nouveau_vp3_video_buffer *)d->ref[0]; 452 refs[!!refs[0]] = (struct nouveau_vp3_video_buffer *)d->ref[1]; 453 return 0x12; 454 } 455 456 void nouveau_vp3_vp_caps(struct nouveau_vp3_decoder *dec, union pipe_desc desc, 457 struct nouveau_vp3_video_buffer *target, unsigned comm_seq, 458 unsigned *caps, unsigned *is_ref, 459 struct nouveau_vp3_video_buffer *refs[16]) 460 { 461 struct nouveau_bo *bsp_bo = dec->bsp_bo[comm_seq % NOUVEAU_VP3_VIDEO_QDEPTH]; 462 enum pipe_video_format codec = u_reduce_video_profile(dec->base.profile); 463 char *vp = bsp_bo->map + VP_OFFSET; 464 465 switch (codec){ 466 case PIPE_VIDEO_FORMAT_MPEG12: 467 *caps = nouveau_vp3_fill_picparm_mpeg12_vp(dec, desc.mpeg12, refs, is_ref, vp); 468 nouveau_vp3_handle_references(dec, refs, dec->fence_seq, target); 469 switch (desc.mpeg12->picture_structure) { 470 case PIPE_MPEG12_PICTURE_STRUCTURE_FIELD_TOP: 471 dec->refs[target->valid_ref].decoded_top = 1; 472 break; 473 case PIPE_MPEG12_PICTURE_STRUCTURE_FIELD_BOTTOM: 474 dec->refs[target->valid_ref].decoded_bottom = 1; 475 break; 476 default: 477 dec->refs[target->valid_ref].decoded_top = 1; 478 dec->refs[target->valid_ref].decoded_bottom = 1; 479 break; 480 } 481 return; 482 case PIPE_VIDEO_FORMAT_MPEG4: 483 *caps = nouveau_vp3_fill_picparm_mpeg4_vp(dec, desc.mpeg4, refs, is_ref, vp); 484 nouveau_vp3_handle_references(dec, refs, dec->fence_seq, target); 485 // XXX: Correct? 486 if (!desc.mpeg4->interlaced) { 487 dec->refs[target->valid_ref].decoded_top = 1; 488 dec->refs[target->valid_ref].decoded_bottom = 1; 489 } else if (desc.mpeg4->top_field_first) { 490 if (!dec->refs[target->valid_ref].decoded_top) 491 dec->refs[target->valid_ref].decoded_top = 1; 492 else 493 dec->refs[target->valid_ref].decoded_bottom = 1; 494 } else { 495 if (!dec->refs[target->valid_ref].decoded_bottom) 496 dec->refs[target->valid_ref].decoded_bottom = 1; 497 else 498 dec->refs[target->valid_ref].decoded_top = 1; 499 } 500 return; 501 case PIPE_VIDEO_FORMAT_VC1: { 502 *caps = nouveau_vp3_fill_picparm_vc1_vp(dec, desc.vc1, refs, is_ref, vp); 503 nouveau_vp3_handle_references(dec, refs, dec->fence_seq, target); 504 if (desc.vc1->frame_coding_mode == 3) 505 debug_printf("Field-Interlaced possibly incorrectly handled\n"); 506 dec->refs[target->valid_ref].decoded_top = 1; 507 dec->refs[target->valid_ref].decoded_bottom = 1; 508 return; 509 } 510 case PIPE_VIDEO_FORMAT_MPEG4_AVC: { 511 *caps = nouveau_vp3_fill_picparm_h264_vp(dec, desc.h264, refs, is_ref, vp); 512 nouveau_vp3_handle_references(dec, refs, dec->fence_seq, target); 513 nouveau_vp3_fill_picparm_h264_vp_refs(dec, desc.h264, refs, target, vp); 514 return; 515 } 516 default: assert(0); return; 517 } 518 } 519