pnw_MPEG2.c revision 4b5b72d7dd3fe944d75029ff0ca6db1e74600e59
1/* 2 * INTEL CONFIDENTIAL 3 * Copyright 2007 Intel Corporation. All Rights Reserved. 4 * Copyright 2005-2007 Imagination Technologies Limited. All Rights Reserved. 5 * 6 * The source code contained or described herein and all documents related to 7 * the source code ("Material") are owned by Intel Corporation or its suppliers 8 * or licensors. Title to the Material remains with Intel Corporation or its 9 * suppliers and licensors. The Material may contain trade secrets and 10 * proprietary and confidential information of Intel Corporation and its 11 * suppliers and licensors, and is protected by worldwide copyright and trade 12 * secret laws and treaty provisions. No part of the Material may be used, 13 * copied, reproduced, modified, published, uploaded, posted, transmitted, 14 * distributed, or disclosed in any way without Intel's prior express written 15 * permission. 16 * 17 * No license under any patent, copyright, trade secret or other intellectual 18 * property right is granted to or conferred upon you by disclosure or delivery 19 * of the Materials, either expressly, by implication, inducement, estoppel or 20 * otherwise. Any license under such intellectual property rights must be 21 * express and approved by Intel in writing. 22 */ 23 24 25#include "pnw_MPEG2.h" 26#include "psb_def.h" 27#include "psb_surface.h" 28#include "psb_cmdbuf.h" 29 30#include "hwdefs/reg_io2.h" 31#include "hwdefs/msvdx_offsets.h" 32#include "hwdefs/msvdx_cmds_io2.h" 33#include "hwdefs/msvdx_vec_reg_io2.h" 34#include "hwdefs/msvdx_vec_mpeg2_reg_io2.h" 35#include "hwdefs/dxva_fw_ctrl.h" 36 37#include <stdlib.h> 38#include <stdint.h> 39#include <string.h> 40 41#define GET_SURFACE_INFO_is_defined(psb_surface) ((int) (psb_surface->extra_info[0])) 42#define SET_SURFACE_INFO_is_defined(psb_surface, val) psb_surface->extra_info[0] = (uint32_t) val; 43#define GET_SURFACE_INFO_picture_structure(psb_surface) (psb_surface->extra_info[1]) 44#define SET_SURFACE_INFO_picture_structure(psb_surface, val) psb_surface->extra_info[1] = val; 45#define GET_SURFACE_INFO_picture_coding_type(psb_surface) ((int) (psb_surface->extra_info[2])) 46#define SET_SURFACE_INFO_picture_coding_type(psb_surface, val) psb_surface->extra_info[2] = (uint32_t) val; 47 48 49#define SLICEDATA_BUFFER_TYPE(type) ((type==VASliceDataBufferType)?"VASliceDataBufferType":"VAProtectedSliceDataBufferType") 50 51/* 52 * Frame types - format dependant! 53 */ 54#define PICTURE_CODING_I 0x01 55#define PICTURE_CODING_P 0x02 56#define PICTURE_CODING_B 0x03 57/* A special syntax is defined for D-pictures (picture_coding_type = 4). D-pictures are like I-pictures with only Intra-DC coefficients, 58 no End of Block, and a special end_of_macroblock code '1'. PICTURE_CODING_D is not allowed in MPEG2 */ 59#define PICTURE_CODING_D 0x04 60 61/************************************************************************************/ 62/* Variable length codes in 'packed' format */ 63/************************************************************************************/ 64 65/* Format is: opcode, width, symbol. All VLC tables are concatenated. Index */ 66/* infomation is stored in gui16mpeg2VlcIndexData[] */ 67#define VLC_PACK(a,b,c) ( ( (a) << 12 ) | ( (b) << 9 ) | (c) ) 68const static IMG_UINT16 gaui16mpeg2VlcTableDataPacked[] = 69{ 70 VLC_PACK( 6 , 0 , 0 ) , 71 VLC_PACK( 0 , 0 , 6 ) , 72 VLC_PACK( 4 , 2 , 4 ) , 73 VLC_PACK( 4 , 3 , 5 ) , 74 VLC_PACK( 4 , 4 , 6 ) , 75 VLC_PACK( 4 , 5 , 7 ) , 76 VLC_PACK( 1 , 1 , 3 ) , 77 VLC_PACK( 4 , 0 , 0 ) , 78 VLC_PACK( 4 , 0 , 3 ) , 79 VLC_PACK( 4 , 0 , 8 ) , 80 VLC_PACK( 4 , 1 , 9 ) , 81 VLC_PACK( 5 , 0 , 5 ) , 82 VLC_PACK( 5 , 0 , 0 ) , 83 VLC_PACK( 4 , 1 , 2 ) , 84 VLC_PACK( 4 , 2 , 3 ) , 85 VLC_PACK( 4 , 3 , 4 ) , 86 VLC_PACK( 4 , 4 , 5 ) , 87 VLC_PACK( 4 , 5 , 6 ) , 88 VLC_PACK( 1 , 2 , 1 ) , 89 VLC_PACK( 4 , 0 , 7 ) , 90 VLC_PACK( 4 , 1 , 8 ) , 91 VLC_PACK( 4 , 2 , 9 ) , 92 VLC_PACK( 5 , 0 , 5 ) , 93 VLC_PACK( 0 , 2 , 16 ) , 94 VLC_PACK( 0 , 1 , 87 ) , 95 VLC_PACK( 2 , 3 , 90 ) , 96 VLC_PACK( 0 , 0 , 98 ) , 97 VLC_PACK( 5 , 0 , 253 ) , 98 VLC_PACK( 5 , 0 , 366 ) , 99 VLC_PACK( 4 , 3 , 380 ) , 100 VLC_PACK( 4 , 3 , 381 ) , 101 VLC_PACK( 4 , 1 , 508 ) , 102 VLC_PACK( 4 , 1 , 508 ) , 103 VLC_PACK( 4 , 1 , 508 ) , 104 VLC_PACK( 4 , 1 , 508 ) , 105 VLC_PACK( 4 , 1 , 509 ) , 106 VLC_PACK( 4 , 1 , 509 ) , 107 VLC_PACK( 4 , 1 , 509 ) , 108 VLC_PACK( 4 , 1 , 509 ) , 109 VLC_PACK( 0 , 4 , 8 ) , 110 VLC_PACK( 0 , 2 , 63 ) , 111 VLC_PACK( 4 , 1 , 255 ) , 112 VLC_PACK( 4 , 1 , 255 ) , 113 VLC_PACK( 5 , 0 , 365 ) , 114 VLC_PACK( 5 , 0 , 470 ) , 115 VLC_PACK( 5 , 0 , 251 ) , 116 VLC_PACK( 5 , 0 , 471 ) , 117 VLC_PACK( 3 , 4 , 0 ) , 118 VLC_PACK( 0 , 1 , 31 ) , 119 VLC_PACK( 0 , 0 , 40 ) , 120 VLC_PACK( 2 , 2 , 41 ) , 121 VLC_PACK( 5 , 2 , 224 ) , 122 VLC_PACK( 5 , 2 , 228 ) , 123 VLC_PACK( 5 , 2 , 232 ) , 124 VLC_PACK( 5 , 2 , 236 ) , 125 VLC_PACK( 5 , 1 , 437 ) , 126 VLC_PACK( 0 , 0 , 39 ) , 127 VLC_PACK( 0 , 0 , 40 ) , 128 VLC_PACK( 0 , 0 , 41 ) , 129 VLC_PACK( 5 , 1 , 241 ) , 130 VLC_PACK( 0 , 0 , 41 ) , 131 VLC_PACK( 5 , 1 , 454 ) , 132 VLC_PACK( 5 , 1 , 456 ) , 133 VLC_PACK( 5 , 0 , 244 ) , 134 VLC_PACK( 5 , 0 , 439 ) , 135 VLC_PACK( 5 , 0 , 348 ) , 136 VLC_PACK( 5 , 0 , 245 ) , 137 VLC_PACK( 5 , 0 , 363 ) , 138 VLC_PACK( 5 , 0 , 325 ) , 139 VLC_PACK( 5 , 0 , 458 ) , 140 VLC_PACK( 5 , 0 , 459 ) , 141 VLC_PACK( 5 , 0 , 246 ) , 142 VLC_PACK( 5 , 0 , 460 ) , 143 VLC_PACK( 5 , 0 , 461 ) , 144 VLC_PACK( 5 , 0 , 186 ) , 145 VLC_PACK( 5 , 0 , 356 ) , 146 VLC_PACK( 5 , 0 , 247 ) , 147 VLC_PACK( 5 , 0 , 333 ) , 148 VLC_PACK( 5 , 0 , 462 ) , 149 VLC_PACK( 5 , 2 , 173 ) , 150 VLC_PACK( 2 , 1 , 3 ) , 151 VLC_PACK( 1 , 1 , 5 ) , 152 VLC_PACK( 5 , 2 , 449 ) , 153 VLC_PACK( 5 , 1 , 432 ) , 154 VLC_PACK( 5 , 0 , 431 ) , 155 VLC_PACK( 5 , 0 , 332 ) , 156 VLC_PACK( 5 , 1 , 434 ) , 157 VLC_PACK( 5 , 0 , 436 ) , 158 VLC_PACK( 5 , 0 , 448 ) , 159 VLC_PACK( 5 , 2 , 215 ) , 160 VLC_PACK( 5 , 2 , 219 ) , 161 VLC_PACK( 5 , 2 , 180 ) , 162 VLC_PACK( 5 , 1 , 178 ) , 163 VLC_PACK( 5 , 0 , 177 ) , 164 VLC_PACK( 5 , 0 , 223 ) , 165 VLC_PACK( 5 , 0 , 340 ) , 166 VLC_PACK( 5 , 0 , 355 ) , 167 VLC_PACK( 5 , 0 , 362 ) , 168 VLC_PACK( 5 , 0 , 184 ) , 169 VLC_PACK( 5 , 0 , 185 ) , 170 VLC_PACK( 5 , 0 , 240 ) , 171 VLC_PACK( 5 , 0 , 243 ) , 172 VLC_PACK( 5 , 0 , 453 ) , 173 VLC_PACK( 5 , 0 , 463 ) , 174 VLC_PACK( 5 , 0 , 341 ) , 175 VLC_PACK( 5 , 0 , 248 ) , 176 VLC_PACK( 5 , 0 , 364 ) , 177 VLC_PACK( 5 , 0 , 187 ) , 178 VLC_PACK( 5 , 0 , 464 ) , 179 VLC_PACK( 5 , 0 , 465 ) , 180 VLC_PACK( 5 , 0 , 349 ) , 181 VLC_PACK( 5 , 0 , 326 ) , 182 VLC_PACK( 5 , 0 , 334 ) , 183 VLC_PACK( 5 , 0 , 189 ) , 184 VLC_PACK( 5 , 0 , 342 ) , 185 VLC_PACK( 5 , 0 , 252 ) , 186 VLC_PACK( 0 , 1 , 4 ) , 187 VLC_PACK( 5 , 1 , 467 ) , 188 VLC_PACK( 5 , 0 , 249 ) , 189 VLC_PACK( 5 , 0 , 466 ) , 190 VLC_PACK( 5 , 0 , 357 ) , 191 VLC_PACK( 5 , 0 , 188 ) , 192 VLC_PACK( 5 , 0 , 250 ) , 193 VLC_PACK( 5 , 0 , 469 ) , 194 VLC_PACK( 5 , 0 , 350 ) , 195 VLC_PACK( 5 , 0 , 358 ) , 196 VLC_PACK( 0 , 2 , 16 ) , 197 VLC_PACK( 0 , 1 , 87 ) , 198 VLC_PACK( 2 , 3 , 90 ) , 199 VLC_PACK( 0 , 0 , 98 ) , 200 VLC_PACK( 5 , 0 , 253 ) , 201 VLC_PACK( 5 , 0 , 366 ) , 202 VLC_PACK( 4 , 3 , 380 ) , 203 VLC_PACK( 4 , 3 , 381 ) , 204 VLC_PACK( 4 , 1 , 254 ) , 205 VLC_PACK( 4 , 1 , 254 ) , 206 VLC_PACK( 4 , 1 , 254 ) , 207 VLC_PACK( 4 , 1 , 254 ) , 208 VLC_PACK( 4 , 2 , 508 ) , 209 VLC_PACK( 4 , 2 , 508 ) , 210 VLC_PACK( 4 , 2 , 509 ) , 211 VLC_PACK( 4 , 2 , 509 ) , 212 VLC_PACK( 0 , 4 , 8 ) , 213 VLC_PACK( 0 , 2 , 63 ) , 214 VLC_PACK( 4 , 1 , 255 ) , 215 VLC_PACK( 4 , 1 , 255 ) , 216 VLC_PACK( 5 , 0 , 365 ) , 217 VLC_PACK( 5 , 0 , 470 ) , 218 VLC_PACK( 5 , 0 , 251 ) , 219 VLC_PACK( 5 , 0 , 471 ) , 220 VLC_PACK( 3 , 4 , 0 ) , 221 VLC_PACK( 0 , 1 , 31 ) , 222 VLC_PACK( 0 , 0 , 40 ) , 223 VLC_PACK( 2 , 2 , 41 ) , 224 VLC_PACK( 5 , 2 , 224 ) , 225 VLC_PACK( 5 , 2 , 228 ) , 226 VLC_PACK( 5 , 2 , 232 ) , 227 VLC_PACK( 5 , 2 , 236 ) , 228 VLC_PACK( 5 , 1 , 437 ) , 229 VLC_PACK( 0 , 0 , 39 ) , 230 VLC_PACK( 0 , 0 , 40 ) , 231 VLC_PACK( 0 , 0 , 41 ) , 232 VLC_PACK( 5 , 1 , 241 ) , 233 VLC_PACK( 0 , 0 , 41 ) , 234 VLC_PACK( 5 , 1 , 454 ) , 235 VLC_PACK( 5 , 1 , 456 ) , 236 VLC_PACK( 5 , 0 , 244 ) , 237 VLC_PACK( 5 , 0 , 439 ) , 238 VLC_PACK( 5 , 0 , 348 ) , 239 VLC_PACK( 5 , 0 , 245 ) , 240 VLC_PACK( 5 , 0 , 363 ) , 241 VLC_PACK( 5 , 0 , 325 ) , 242 VLC_PACK( 5 , 0 , 458 ) , 243 VLC_PACK( 5 , 0 , 459 ) , 244 VLC_PACK( 5 , 0 , 246 ) , 245 VLC_PACK( 5 , 0 , 460 ) , 246 VLC_PACK( 5 , 0 , 461 ) , 247 VLC_PACK( 5 , 0 , 186 ) , 248 VLC_PACK( 5 , 0 , 356 ) , 249 VLC_PACK( 5 , 0 , 247 ) , 250 VLC_PACK( 5 , 0 , 333 ) , 251 VLC_PACK( 5 , 0 , 462 ) , 252 VLC_PACK( 5 , 2 , 173 ) , 253 VLC_PACK( 2 , 1 , 3 ) , 254 VLC_PACK( 1 , 1 , 5 ) , 255 VLC_PACK( 5 , 2 , 449 ) , 256 VLC_PACK( 5 , 1 , 432 ) , 257 VLC_PACK( 5 , 0 , 431 ) , 258 VLC_PACK( 5 , 0 , 332 ) , 259 VLC_PACK( 5 , 1 , 434 ) , 260 VLC_PACK( 5 , 0 , 436 ) , 261 VLC_PACK( 5 , 0 , 448 ) , 262 VLC_PACK( 5 , 2 , 215 ) , 263 VLC_PACK( 5 , 2 , 219 ) , 264 VLC_PACK( 5 , 2 , 180 ) , 265 VLC_PACK( 5 , 1 , 178 ) , 266 VLC_PACK( 5 , 0 , 177 ) , 267 VLC_PACK( 5 , 0 , 223 ) , 268 VLC_PACK( 5 , 0 , 340 ) , 269 VLC_PACK( 5 , 0 , 355 ) , 270 VLC_PACK( 5 , 0 , 362 ) , 271 VLC_PACK( 5 , 0 , 184 ) , 272 VLC_PACK( 5 , 0 , 185 ) , 273 VLC_PACK( 5 , 0 , 240 ) , 274 VLC_PACK( 5 , 0 , 243 ) , 275 VLC_PACK( 5 , 0 , 453 ) , 276 VLC_PACK( 5 , 0 , 463 ) , 277 VLC_PACK( 5 , 0 , 341 ) , 278 VLC_PACK( 5 , 0 , 248 ) , 279 VLC_PACK( 5 , 0 , 364 ) , 280 VLC_PACK( 5 , 0 , 187 ) , 281 VLC_PACK( 5 , 0 , 464 ) , 282 VLC_PACK( 5 , 0 , 465 ) , 283 VLC_PACK( 5 , 0 , 349 ) , 284 VLC_PACK( 5 , 0 , 326 ) , 285 VLC_PACK( 5 , 0 , 334 ) , 286 VLC_PACK( 5 , 0 , 189 ) , 287 VLC_PACK( 5 , 0 , 342 ) , 288 VLC_PACK( 5 , 0 , 252 ) , 289 VLC_PACK( 0 , 1 , 4 ) , 290 VLC_PACK( 5 , 1 , 467 ) , 291 VLC_PACK( 5 , 0 , 249 ) , 292 VLC_PACK( 5 , 0 , 466 ) , 293 VLC_PACK( 5 , 0 , 357 ) , 294 VLC_PACK( 5 , 0 , 188 ) , 295 VLC_PACK( 5 , 0 , 250 ) , 296 VLC_PACK( 5 , 0 , 469 ) , 297 VLC_PACK( 5 , 0 , 350 ) , 298 VLC_PACK( 5 , 0 , 358 ) , 299 VLC_PACK( 2 , 2 , 32 ) , 300 VLC_PACK( 0 , 1 , 87 ) , 301 VLC_PACK( 5 , 1 , 248 ) , 302 VLC_PACK( 0 , 0 , 89 ) , 303 VLC_PACK( 1 , 2 , 90 ) , 304 VLC_PACK( 5 , 0 , 366 ) , 305 VLC_PACK( 5 , 0 , 189 ) , 306 VLC_PACK( 5 , 0 , 358 ) , 307 VLC_PACK( 4 , 3 , 380 ) , 308 VLC_PACK( 4 , 3 , 380 ) , 309 VLC_PACK( 4 , 3 , 381 ) , 310 VLC_PACK( 4 , 3 , 381 ) , 311 VLC_PACK( 4 , 3 , 254 ) , 312 VLC_PACK( 4 , 3 , 254 ) , 313 VLC_PACK( 4 , 4 , 504 ) , 314 VLC_PACK( 4 , 4 , 505 ) , 315 VLC_PACK( 4 , 2 , 508 ) , 316 VLC_PACK( 4 , 2 , 508 ) , 317 VLC_PACK( 4 , 2 , 508 ) , 318 VLC_PACK( 4 , 2 , 508 ) , 319 VLC_PACK( 4 , 2 , 509 ) , 320 VLC_PACK( 4 , 2 , 509 ) , 321 VLC_PACK( 4 , 2 , 509 ) , 322 VLC_PACK( 4 , 2 , 509 ) , 323 VLC_PACK( 4 , 3 , 506 ) , 324 VLC_PACK( 4 , 3 , 506 ) , 325 VLC_PACK( 4 , 3 , 507 ) , 326 VLC_PACK( 4 , 3 , 507 ) , 327 VLC_PACK( 5 , 0 , 251 ) , 328 VLC_PACK( 5 , 0 , 250 ) , 329 VLC_PACK( 0 , 1 , 71 ) , 330 VLC_PACK( 0 , 2 , 74 ) , 331 VLC_PACK( 4 , 0 , 255 ) , 332 VLC_PACK( 0 , 1 , 3 ) , 333 VLC_PACK( 0 , 2 , 8 ) , 334 VLC_PACK( 0 , 3 , 17 ) , 335 VLC_PACK( 5 , 0 , 341 ) , 336 VLC_PACK( 5 , 0 , 465 ) , 337 VLC_PACK( 0 , 0 , 2 ) , 338 VLC_PACK( 5 , 0 , 464 ) , 339 VLC_PACK( 5 , 0 , 363 ) , 340 VLC_PACK( 5 , 0 , 463 ) , 341 VLC_PACK( 5 , 1 , 438 ) , 342 VLC_PACK( 5 , 1 , 348 ) , 343 VLC_PACK( 5 , 1 , 324 ) , 344 VLC_PACK( 5 , 1 , 458 ) , 345 VLC_PACK( 5 , 1 , 459 ) , 346 VLC_PACK( 5 , 1 , 461 ) , 347 VLC_PACK( 5 , 1 , 356 ) , 348 VLC_PACK( 0 , 0 , 1 ) , 349 VLC_PACK( 5 , 0 , 333 ) , 350 VLC_PACK( 5 , 0 , 462 ) , 351 VLC_PACK( 3 , 3 , 0 ) , 352 VLC_PACK( 0 , 1 , 15 ) , 353 VLC_PACK( 0 , 0 , 24 ) , 354 VLC_PACK( 2 , 2 , 25 ) , 355 VLC_PACK( 5 , 2 , 224 ) , 356 VLC_PACK( 5 , 2 , 228 ) , 357 VLC_PACK( 5 , 2 , 232 ) , 358 VLC_PACK( 5 , 2 , 236 ) , 359 VLC_PACK( 5 , 1 , 437 ) , 360 VLC_PACK( 0 , 0 , 23 ) , 361 VLC_PACK( 0 , 0 , 24 ) , 362 VLC_PACK( 5 , 1 , 185 ) , 363 VLC_PACK( 3 , 3 , 0 ) , 364 VLC_PACK( 5 , 1 , 452 ) , 365 VLC_PACK( 5 , 1 , 454 ) , 366 VLC_PACK( 5 , 1 , 456 ) , 367 VLC_PACK( 5 , 2 , 173 ) , 368 VLC_PACK( 2 , 1 , 3 ) , 369 VLC_PACK( 1 , 1 , 5 ) , 370 VLC_PACK( 5 , 2 , 449 ) , 371 VLC_PACK( 5 , 1 , 432 ) , 372 VLC_PACK( 5 , 0 , 431 ) , 373 VLC_PACK( 5 , 0 , 332 ) , 374 VLC_PACK( 5 , 1 , 434 ) , 375 VLC_PACK( 5 , 0 , 436 ) , 376 VLC_PACK( 5 , 0 , 448 ) , 377 VLC_PACK( 5 , 2 , 215 ) , 378 VLC_PACK( 5 , 2 , 219 ) , 379 VLC_PACK( 5 , 2 , 180 ) , 380 VLC_PACK( 5 , 1 , 178 ) , 381 VLC_PACK( 5 , 0 , 177 ) , 382 VLC_PACK( 5 , 0 , 223 ) , 383 VLC_PACK( 5 , 0 , 340 ) , 384 VLC_PACK( 5 , 0 , 355 ) , 385 VLC_PACK( 5 , 0 , 362 ) , 386 VLC_PACK( 5 , 0 , 184 ) , 387 VLC_PACK( 5 , 0 , 326 ) , 388 VLC_PACK( 5 , 0 , 471 ) , 389 VLC_PACK( 5 , 0 , 334 ) , 390 VLC_PACK( 5 , 0 , 365 ) , 391 VLC_PACK( 5 , 0 , 350 ) , 392 VLC_PACK( 5 , 0 , 342 ) , 393 VLC_PACK( 2 , 1 , 4 ) , 394 VLC_PACK( 5 , 1 , 466 ) , 395 VLC_PACK( 5 , 0 , 357 ) , 396 VLC_PACK( 5 , 0 , 187 ) , 397 VLC_PACK( 5 , 1 , 244 ) , 398 VLC_PACK( 5 , 0 , 468 ) , 399 VLC_PACK( 5 , 0 , 186 ) , 400 VLC_PACK( 5 , 0 , 470 ) , 401 VLC_PACK( 5 , 0 , 188 ) , 402 VLC_PACK( 5 , 0 , 469 ) , 403 VLC_PACK( 5 , 0 , 247 ) , 404 VLC_PACK( 4 , 2 , 492 ) , 405 VLC_PACK( 4 , 2 , 493 ) , 406 VLC_PACK( 5 , 0 , 243 ) , 407 VLC_PACK( 5 , 0 , 242 ) , 408 VLC_PACK( 5 , 0 , 364 ) , 409 VLC_PACK( 5 , 0 , 349 ) , 410 VLC_PACK( 5 , 0 , 241 ) , 411 VLC_PACK( 5 , 0 , 240 ) , 412 VLC_PACK( 4 , 0 , 30 ) , 413 VLC_PACK( 5 , 0 , 14 ) , 414 VLC_PACK( 5 , 0 , 13 ) , 415 VLC_PACK( 5 , 0 , 12 ) , 416 VLC_PACK( 0 , 0 , 3 ) , 417 VLC_PACK( 2 , 2 , 4 ) , 418 VLC_PACK( 0 , 1 , 7 ) , 419 VLC_PACK( 5 , 1 , 9 ) , 420 VLC_PACK( 5 , 0 , 11 ) , 421 VLC_PACK( 5 , 0 , 8 ) , 422 VLC_PACK( 5 , 1 , 6 ) , 423 VLC_PACK( 5 , 0 , 5 ) , 424 VLC_PACK( 5 , 1 , 3 ) , 425 VLC_PACK( 3 , 1 , 0 ) , 426 VLC_PACK( 2 , 2 , 3 ) , 427 VLC_PACK( 3 , 1 , 0 ) , 428 VLC_PACK( 2 , 1 , 5 ) , 429 VLC_PACK( 3 , 2 , 0 ) , 430 VLC_PACK( 3 , 2 , 0 ) , 431 VLC_PACK( 3 , 2 , 0 ) , 432 VLC_PACK( 4 , 2 , 226 ) , 433 VLC_PACK( 5 , 1 , 1 ) , 434 VLC_PACK( 5 , 0 , 0 ) , 435 VLC_PACK( 5 , 0 , 31 ) , 436 VLC_PACK( 4 , 0 , 62 ) , 437 VLC_PACK( 5 , 0 , 30 ) , 438 VLC_PACK( 5 , 0 , 29 ) , 439 VLC_PACK( 5 , 0 , 28 ) , 440 VLC_PACK( 0 , 0 , 3 ) , 441 VLC_PACK( 2 , 2 , 4 ) , 442 VLC_PACK( 1 , 1 , 7 ) , 443 VLC_PACK( 5 , 1 , 25 ) , 444 VLC_PACK( 5 , 0 , 27 ) , 445 VLC_PACK( 5 , 0 , 24 ) , 446 VLC_PACK( 5 , 1 , 22 ) , 447 VLC_PACK( 5 , 0 , 21 ) , 448 VLC_PACK( 5 , 1 , 19 ) , 449 VLC_PACK( 3 , 1 , 0 ) , 450 VLC_PACK( 3 , 1 , 0 ) , 451 VLC_PACK( 5 , 2 , 15 ) 452}; 453 454#define MAX_QUANT_TABLES (2) /* only 2 tables for 4:2:0 decode */ 455 456static int scan0[64] = // spec, fig 7-2 457{/*u 0 ..... 7*/ 458 0, 1, 5, 6, 14, 15, 27, 28, /* v = 0 */ 459 2, 4, 7, 13, 16, 26, 29, 42, 460 3, 8, 12, 17, 25, 30, 41, 43, 461 9, 11, 18, 24, 31, 40, 44, 53, 462 10, 19, 23, 32, 39, 45, 52, 54, 463 20, 22, 33, 38, 46, 51, 55, 60, 464 21, 34, 37, 47, 50, 56, 59, 61, 465 35, 36, 48, 49, 57, 58, 62, 63 /* v = 7 */ 466}; 467 468typedef enum 469{ 470 NONINTRA_LUMA_Q = 0, 471 INTRA_LUMA_Q = 1 472} QUANT_IDX; 473 474struct context_MPEG2_s { 475 object_context_p obj_context; /* back reference */ 476 477 /* Picture parameters */ 478 VAPictureParameterBufferMPEG2 *pic_params; 479 object_surface_p forward_ref_surface; 480 object_surface_p backward_ref_surface; 481 482 uint32_t coded_picture_width; /* in pixels */ 483 uint32_t coded_picture_height; /* in pixels */ 484 485 uint32_t picture_width_mb; /* in macroblocks */ 486 uint32_t picture_height_mb; /* in macroblocks */ 487 uint32_t size_mb; /* in macroblocks */ 488 489 uint32_t coded_picture_size; /* MSVDX format */ 490 uint32_t display_picture_size; /* MSVDX format */ 491 492 uint32_t BE_PPS0; 493 uint32_t BE_PPS1; 494 uint32_t BE_PPS2; 495 uint32_t BE_SPS0; 496 uint32_t BE_SPS1; 497 uint32_t FE_PPS0; 498 uint32_t FE_PPS1; 499 500 /* IQ Matrix */ 501 uint32_t qmatrix_data[MAX_QUANT_TABLES][16]; 502 int got_iq_matrix; 503 504 /* Split buffers */ 505 int split_buffer_pending; 506 507 /* List of VASliceParameterBuffers */ 508 object_buffer_p *slice_param_list; 509 int slice_param_list_size; 510 int slice_param_list_idx; 511 512 /* VLC packed data */ 513 struct psb_buffer_s vlc_packed_table; 514 515 /* Misc */ 516 unsigned int previous_slice_vertical_position; 517 518 uint32_t *p_range_mapping_base0; 519 uint32_t *p_range_mapping_base1; 520 uint32_t *p_slice_params; /* pointer to ui32SliceParams in CMD_HEADER */ 521 uint32_t *slice_first_pic_last; 522}; 523 524typedef struct context_MPEG2_s *context_MPEG2_p; 525 526#define INIT_CONTEXT_MPEG2 context_MPEG2_p ctx = (context_MPEG2_p) obj_context->format_data; 527 528#define SURFACE(id) ((object_surface_p) object_heap_lookup( &ctx->obj_context->driver_data->surface_heap, id )) 529 530 531static void pnw_MPEG2_QueryConfigAttributes( 532 VAProfile profile, 533 VAEntrypoint entrypoint, 534 VAConfigAttrib *attrib_list, 535 int num_attribs ) 536{ 537 /* No MPEG2 specific attributes */ 538} 539 540static VAStatus pnw_MPEG2_ValidateConfig( 541 object_config_p obj_config ) 542{ 543 int i; 544 /* Check all attributes */ 545 for(i = 0; i < obj_config->attrib_count; i++) 546 { 547 switch (obj_config->attrib_list[i].type) 548 { 549 case VAConfigAttribRTFormat: 550 /* Ignore */ 551 break; 552 553 default: 554 return VA_STATUS_ERROR_ATTR_NOT_SUPPORTED; 555 } 556 } 557 558 return VA_STATUS_SUCCESS; 559} 560 561static VAStatus psb__MPEG2_check_legal_picture(object_context_p obj_context, object_config_p obj_config) 562{ 563 VAStatus vaStatus = VA_STATUS_SUCCESS; 564 565 if (NULL == obj_context) 566 { 567 vaStatus = VA_STATUS_ERROR_INVALID_CONTEXT; 568 DEBUG_FAILURE; 569 return vaStatus; 570 } 571 572 if (NULL == obj_config) 573 { 574 vaStatus = VA_STATUS_ERROR_INVALID_CONFIG; 575 DEBUG_FAILURE; 576 return vaStatus; 577 } 578 579 /* MSVDX decode capability for MPEG2: 580 * MP@HL 581 * 582 * Refer to Table 8-11 (Upper bounds for luminance sample rate) of ISO/IEC 13818-2: 1995(E), 583 * and the "MSVDX MPEG2 decode capability" table of "Poulsbo Media Software Overview" 584 */ 585 586 switch (obj_config->profile) 587 { 588 case VAProfileMPEG2Simple: 589 if ((obj_context->picture_width <= 0) || (obj_context->picture_width > 352) 590 || (obj_context->picture_height <= 0) || (obj_context->picture_height > 288)) 591 { 592 vaStatus = VA_STATUS_ERROR_RESOLUTION_NOT_SUPPORTED; 593 } 594 break; 595 596 case VAProfileMPEG2Main: 597 if ((obj_context->picture_width <= 0) || (obj_context->picture_width > 1920) 598 || (obj_context->picture_height <= 0) || (obj_context->picture_height > 1088)) 599 { 600 vaStatus = VA_STATUS_ERROR_RESOLUTION_NOT_SUPPORTED; 601 } 602 break; 603 604 default: 605 vaStatus = VA_STATUS_ERROR_UNSUPPORTED_PROFILE; 606 break; 607 } 608 609 return vaStatus; 610} 611 612static void pnw_MPEG2_DestroyContext(object_context_p obj_context); 613 614static VAStatus pnw_MPEG2_CreateContext( 615 object_context_p obj_context, 616 object_config_p obj_config ) 617{ 618 VAStatus vaStatus = VA_STATUS_SUCCESS; 619 context_MPEG2_p ctx; 620 /* Validate flag */ 621 /* Validate picture dimensions */ 622 vaStatus = psb__MPEG2_check_legal_picture(obj_context, obj_config); 623 if (VA_STATUS_SUCCESS != vaStatus) 624 { 625 DEBUG_FAILURE; 626 return vaStatus; 627 } 628 629 if (obj_context->num_render_targets < 1) 630 { 631 vaStatus = VA_STATUS_ERROR_UNKNOWN; 632 DEBUG_FAILURE; 633 return vaStatus; 634 } 635 ctx = (context_MPEG2_p) calloc(1, sizeof(struct context_MPEG2_s)); 636 if (NULL == ctx) 637 { 638 vaStatus = VA_STATUS_ERROR_ALLOCATION_FAILED; 639 DEBUG_FAILURE; 640 return vaStatus; 641 } 642 643 obj_context->format_data = (void*) ctx; 644 ctx->obj_context = obj_context; 645 ctx->pic_params = NULL; 646 ctx->got_iq_matrix = FALSE; 647 ctx->previous_slice_vertical_position = ~1; 648 649 ctx->split_buffer_pending = FALSE; 650 651 ctx->slice_param_list_size = 8; 652 ctx->slice_param_list = (object_buffer_p*) calloc(1, sizeof(object_buffer_p)*ctx->slice_param_list_size); 653 ctx->slice_param_list_idx = 0; 654 655 if (NULL == ctx->slice_param_list) 656 { 657 vaStatus = VA_STATUS_ERROR_ALLOCATION_FAILED; 658 DEBUG_FAILURE; 659 } 660 661 if (vaStatus == VA_STATUS_SUCCESS) 662 { 663 vaStatus = psb_buffer_create( obj_context->driver_data, 664 sizeof(gaui16mpeg2VlcTableDataPacked), 665 psb_bt_cpu_vpu, 666 &ctx->vlc_packed_table ); 667 DEBUG_FAILURE; 668 } 669 if (vaStatus == VA_STATUS_SUCCESS) 670 { 671 void *vlc_packed_data_address; 672 if (0 == psb_buffer_map( &ctx->vlc_packed_table, &vlc_packed_data_address )) 673 { 674 memcpy( vlc_packed_data_address, gaui16mpeg2VlcTableDataPacked, sizeof(gaui16mpeg2VlcTableDataPacked)); 675 psb_buffer_unmap( &ctx->vlc_packed_table ); 676 } 677 else 678 { 679 vaStatus = VA_STATUS_ERROR_ALLOCATION_FAILED; 680 DEBUG_FAILURE; 681 } 682 } 683 684 if (vaStatus != VA_STATUS_SUCCESS) 685 { 686 pnw_MPEG2_DestroyContext(obj_context); 687 } 688 689 return vaStatus; 690} 691 692static void pnw_MPEG2_DestroyContext( 693 object_context_p obj_context) 694{ 695 INIT_CONTEXT_MPEG2 696 697 psb_buffer_destroy( &ctx->vlc_packed_table ); 698 699 if (ctx->pic_params) 700 { 701 free(ctx->pic_params); 702 ctx->pic_params = NULL; 703 } 704 705 if (ctx->slice_param_list) 706 { 707 free(ctx->slice_param_list); 708 ctx->slice_param_list = NULL; 709 } 710 711 free(obj_context->format_data); 712 obj_context->format_data = NULL; 713} 714 715static VAStatus psb__MPEG2_process_picture_param(context_MPEG2_p ctx, object_buffer_p obj_buffer) 716{ 717 ASSERT(obj_buffer->type == VAPictureParameterBufferType); 718 ASSERT(obj_buffer->num_elements == 1); 719 ASSERT(obj_buffer->size == sizeof(VAPictureParameterBufferMPEG2)); 720 721 if ((obj_buffer->num_elements != 1) || 722 (obj_buffer->size != sizeof(VAPictureParameterBufferMPEG2))) 723 { 724 return VA_STATUS_ERROR_UNKNOWN; 725 } 726 727 /* Transfer ownership of VAPictureParameterBufferMPEG2 data */ 728 if (ctx->pic_params) 729 { 730 free(ctx->pic_params); 731 } 732 ctx->pic_params = (VAPictureParameterBufferMPEG2 *) obj_buffer->buffer_data; 733 obj_buffer->buffer_data = NULL; 734 obj_buffer->size = 0; 735 736 /* Lookup surfaces for backward/forward references */ 737 switch (ctx->pic_params->picture_coding_type) 738 { 739 case PICTURE_CODING_I: 740 ctx->forward_ref_surface = NULL; 741 ctx->backward_ref_surface = NULL; 742 break; 743 744 case PICTURE_CODING_P: 745 ctx->forward_ref_surface = SURFACE(ctx->pic_params->forward_reference_picture); 746 ctx->backward_ref_surface = NULL; 747 if (NULL == ctx->forward_ref_surface) 748 { 749 return VA_STATUS_ERROR_INVALID_SURFACE; 750 } 751 break; 752 753 case PICTURE_CODING_B: 754 ctx->forward_ref_surface = SURFACE(ctx->pic_params->forward_reference_picture); 755 ctx->backward_ref_surface = SURFACE(ctx->pic_params->backward_reference_picture); 756 if ((NULL == ctx->forward_ref_surface) || 757 (NULL == ctx->backward_ref_surface)) 758 { 759 return VA_STATUS_ERROR_INVALID_SURFACE; 760 } 761 break; 762 763 default: 764 return VA_STATUS_ERROR_UNKNOWN; 765 } 766 767 ctx->picture_width_mb = (ctx->pic_params->horizontal_size + 15) / 16; 768 if (ctx->obj_context->va_flags & VA_PROGRESSIVE) 769 { 770 ctx->picture_height_mb = (ctx->pic_params->vertical_size + 15) / 16; 771 } 772 else 773 { 774 ctx->picture_height_mb = (ctx->pic_params->vertical_size + 31) / 32; 775 ctx->picture_height_mb *= 2; 776 } 777 ctx->coded_picture_width = ctx->picture_width_mb * 16; 778 ctx->coded_picture_height = ctx->picture_height_mb * 16; 779 780 ctx->size_mb = ctx->picture_width_mb * ctx->picture_height_mb; 781 782 /* Display picture size */ 783 ctx->display_picture_size = 0; 784/* 785 * coded_picture_width/height is aligned to the size of a macroblock.. 786 * Both coded_picture_height or vertical_size can be used for DISPLAY_SIZE and both give correct results, 787 * however Vista driver / test app uses the aligned value that's in coded_picture_height so we do too. 788 * See e.g. low4.m2v for an example clip where vertical_size will differ from coded_picture_height 789 */ 790#if 0 791 REGIO_WRITE_FIELD_LITE (ctx->display_picture_size, MSVDX_CMDS, DISPLAY_PICTURE_SIZE, DISPLAY_PICTURE_HEIGHT, ctx->pic_params->vertical_size - 1); 792 REGIO_WRITE_FIELD_LITE (ctx->display_picture_size, MSVDX_CMDS, DISPLAY_PICTURE_SIZE, DISPLAY_PICTURE_WIDTH, ctx->pic_params->horizontal_size - 1); 793#else 794 REGIO_WRITE_FIELD_LITE (ctx->display_picture_size, MSVDX_CMDS, DISPLAY_PICTURE_SIZE, DISPLAY_PICTURE_HEIGHT, ctx->coded_picture_height - 1); 795 REGIO_WRITE_FIELD_LITE (ctx->display_picture_size, MSVDX_CMDS, DISPLAY_PICTURE_SIZE, DISPLAY_PICTURE_WIDTH, ctx->coded_picture_width - 1); 796#endif 797 798 /* Coded picture size */ 799 ctx->coded_picture_size = 0; 800 REGIO_WRITE_FIELD_LITE (ctx->coded_picture_size, MSVDX_CMDS, CODED_PICTURE_SIZE, CODED_PICTURE_HEIGHT, ctx->coded_picture_height - 1); 801 REGIO_WRITE_FIELD_LITE (ctx->coded_picture_size, MSVDX_CMDS, CODED_PICTURE_SIZE, CODED_PICTURE_WIDTH, ctx->coded_picture_width - 1); 802 803 ctx->BE_SPS0 = 0; 804 REGIO_WRITE_FIELD_LITE (ctx->BE_SPS0,MSVDX_VEC_MPEG2,CR_VEC_MPEG2_BE_SPS0,BE_HORIZONTAL_SIZE_MINUS1, ctx->picture_width_mb - 1); 805 806 ctx->BE_SPS1 = 0; 807 REGIO_WRITE_FIELD_LITE (ctx->BE_SPS1,MSVDX_VEC_MPEG2,CR_VEC_MPEG2_BE_SPS1,BE_VERTICAL_SIZE_MINUS1, ctx->picture_height_mb); 808 809 ctx->FE_PPS0 = 0; 810 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS0, FE_ALTERNATE_SCAN, !!(ctx->pic_params->picture_coding_extension.bits.alternate_scan)); 811 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS0, FE_Q_SCALE_TYPE, !!(ctx->pic_params->picture_coding_extension.bits.q_scale_type)); 812 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS0, FE_INTRA_DC_PRECISION, ctx->pic_params->picture_coding_extension.bits.intra_dc_precision); 813 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS0, FE_TOP_FIELD_FIRST, !!(ctx->pic_params->picture_coding_extension.bits.top_field_first)); 814 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS0, FE_CONCEALMENT_MOTION_VECTORS, !!(ctx->pic_params->picture_coding_extension.bits.concealment_motion_vectors)); 815 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS0, FE_FRAME_PRED_FRAME_DCT, !!(ctx->pic_params->picture_coding_extension.bits.frame_pred_frame_dct)); 816 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS0, FE_PICTURE_STRUCTURE, ctx->pic_params->picture_coding_extension.bits.picture_structure); 817 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS0, FE_INTRA_VLC_FORMAT, !!(ctx->pic_params->picture_coding_extension.bits.intra_vlc_format)); 818 819 ctx->FE_PPS1 = 0; 820 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS1, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS1, FE_PICTURE_CODING_TYPE, ctx->pic_params->picture_coding_type); 821 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS1, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS1, FE_F_CODE00, (ctx->pic_params->f_code >> 12) & 0x0F); 822 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS1, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS1, FE_F_CODE01, (ctx->pic_params->f_code >> 8) & 0x0F); 823 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS1, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS1, FE_F_CODE10, (ctx->pic_params->f_code >> 4) & 0x0F); 824 REGIO_WRITE_FIELD_LITE (ctx->FE_PPS1, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS1, FE_F_CODE11, (ctx->pic_params->f_code >> 0) & 0x0F); 825 826 /* VEC Control register: Back-End MPEG2 PPS0 */ 827 ctx->BE_PPS0 = 0; 828 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS0, BE_FRAME_PRED_FRAME_DCT, !!(ctx->pic_params->picture_coding_extension.bits.frame_pred_frame_dct)); 829 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS0, BE_INTRA_DC_PRECISION, ctx->pic_params->picture_coding_extension.bits.intra_dc_precision); 830 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS0, BE_Q_SCALE_TYPE, !!(ctx->pic_params->picture_coding_extension.bits.q_scale_type)); 831 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS0, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS0, BE_ALTERNATE_SCAN, !!(ctx->pic_params->picture_coding_extension.bits.alternate_scan)); 832 833 ctx->BE_PPS1 = 0; 834 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS1, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS1, BE_F_CODE00, (ctx->pic_params->f_code >> 12) & 0x0F); 835 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS1, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS1, BE_F_CODE01, (ctx->pic_params->f_code >> 8) & 0x0F); 836 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS1, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS1, BE_F_CODE10, (ctx->pic_params->f_code >> 4) & 0x0F); 837 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS1, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS1, BE_F_CODE11, (ctx->pic_params->f_code >> 0) & 0x0F); 838 839 /* VEC Control register: Back-End MPEG2 PPS2 */ 840 ctx->BE_PPS2 = 0; 841 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS2, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS2, BE_PICTURE_CODING_TYPE, ctx->pic_params->picture_coding_type); 842 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS2, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS2, BE_TOP_FIELD_FIRST, !!(ctx->pic_params->picture_coding_extension.bits.top_field_first)); 843 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS2, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS2, BE_CONCEALMENT_MOTION_VECTORS, !!(ctx->pic_params->picture_coding_extension.bits.concealment_motion_vectors)); 844 REGIO_WRITE_FIELD_LITE (ctx->BE_PPS2, MSVDX_VEC_MPEG2, CR_VEC_MPEG2_BE_PPS2, BE_PICTURE_STRUCTURE, ctx->pic_params->picture_coding_extension.bits.picture_structure); 845 846 ctx->obj_context->operating_mode = 0; 847 REGIO_WRITE_FIELD_LITE (ctx->obj_context->operating_mode, MSVDX_CMDS, OPERATING_MODE, CHROMA_INTERLEAVED, 0); 848 REGIO_WRITE_FIELD_LITE (ctx->obj_context->operating_mode, MSVDX_CMDS, OPERATING_MODE, ROW_STRIDE, ctx->obj_context->current_render_target->psb_surface->stride_mode); 849 REGIO_WRITE_FIELD_LITE (ctx->obj_context->operating_mode, MSVDX_CMDS, OPERATING_MODE, CODEC_PROFILE, 1); /* MPEG2 profile */ 850 REGIO_WRITE_FIELD_LITE (ctx->obj_context->operating_mode, MSVDX_CMDS, OPERATING_MODE, CODEC_MODE, 3); /* MPEG2 mode */ 851 REGIO_WRITE_FIELD_LITE (ctx->obj_context->operating_mode, MSVDX_CMDS, OPERATING_MODE, ASYNC_MODE, 1); /* VDMC only */ 852 REGIO_WRITE_FIELD_LITE (ctx->obj_context->operating_mode, MSVDX_CMDS, OPERATING_MODE, CHROMA_FORMAT, 1); 853 854 return VA_STATUS_SUCCESS; 855} 856 857static void psb__MPEG2_convert_iq_matrix(uint32_t *dest32, unsigned char *src) 858{ 859 int i; 860 int *idx = scan0; 861 uint8_t *dest8 = (uint8_t*) dest32; 862 863 for (i = 0; i < 64; i++) 864 { 865 *dest8++ = src[*idx++]; 866 } 867} 868 869static VAStatus psb__MPEG2_process_iq_matrix(context_MPEG2_p ctx, object_buffer_p obj_buffer) 870{ 871 VAIQMatrixBufferMPEG2 *iq_matrix = (VAIQMatrixBufferMPEG2 *) obj_buffer->buffer_data; 872 ASSERT(obj_buffer->type == VAIQMatrixBufferType); 873 ASSERT(obj_buffer->num_elements == 1); 874 ASSERT(obj_buffer->size == sizeof(VAIQMatrixBufferMPEG2)); 875 876 if ((obj_buffer->num_elements != 1) || 877 (obj_buffer->size != sizeof(VAIQMatrixBufferMPEG2))) 878 { 879 return VA_STATUS_ERROR_UNKNOWN; 880 } 881 882 /* Only update the qmatrix data if the load flag is set */ 883 if (iq_matrix->load_non_intra_quantiser_matrix) 884 { 885 psb__MPEG2_convert_iq_matrix( ctx->qmatrix_data[NONINTRA_LUMA_Q], iq_matrix->non_intra_quantiser_matrix ); 886 } 887 if (iq_matrix->load_intra_quantiser_matrix) 888 { 889 psb__MPEG2_convert_iq_matrix( ctx->qmatrix_data[INTRA_LUMA_Q], iq_matrix->intra_quantiser_matrix ); 890 } 891 /* We ignore the Chroma tables because those are not supported with VA_RT_FORMAT_YUV420 */ 892 ctx->got_iq_matrix = TRUE; 893 894 return VA_STATUS_SUCCESS; 895} 896 897/* 898 * Adds a VASliceParameterBuffer to the list of slice params 899 */ 900static VAStatus psb__MPEG2_add_slice_param(context_MPEG2_p ctx, object_buffer_p obj_buffer) 901{ 902 ASSERT(obj_buffer->type == VASliceParameterBufferType); 903 if (ctx->slice_param_list_idx >= ctx->slice_param_list_size) 904 { 905 void *new_list; 906 ctx->slice_param_list_size += 8; 907 new_list = realloc(ctx->slice_param_list, 908 sizeof(object_buffer_p)*ctx->slice_param_list_size); 909 if (NULL == new_list) 910 { 911 return VA_STATUS_ERROR_ALLOCATION_FAILED; 912 } 913 ctx->slice_param_list = (object_buffer_p*) new_list; 914 } 915 ctx->slice_param_list[ctx->slice_param_list_idx] = obj_buffer; 916 ctx->slice_param_list_idx++; 917 return VA_STATUS_SUCCESS; 918} 919 920/* Precalculated values */ 921#define ADDR0 (0x00006000) 922#define ADDR1 (0x0003f017) 923#define ADDR2 (0x000ab0e5) 924#define ADDR3 (0x0000016e) 925#define WIDTH0 (0x0016c6ed) 926#define OPCODE0 (0x00002805) 927 928static void psb__MPEG2_write_VLC_tables(context_MPEG2_p ctx) 929{ 930 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 931 932 psb_cmdbuf_skip_start_block( cmdbuf, SKIP_ON_CONTEXT_SWITCH ); 933 /* VLC Table */ 934 /* Write a LLDMA Cmd to transfer VLD Table data */ 935 psb_cmdbuf_lldma_write_cmdbuf( cmdbuf, &ctx->vlc_packed_table, 0, 936 sizeof(gaui16mpeg2VlcTableDataPacked), 937 0, LLDMA_TYPE_VLC_TABLE ); 938 939 /* Write the vec registers with the index data for each of the tables and then write */ 940 /* the actual table data. */ 941 psb_cmdbuf_reg_start_block( cmdbuf ); 942 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET (MSVDX_VEC, CR_VEC_VLC_TABLE_ADDR0), ADDR0 ); 943 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET (MSVDX_VEC, CR_VEC_VLC_TABLE_ADDR1), ADDR1 ); 944 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET (MSVDX_VEC, CR_VEC_VLC_TABLE_ADDR2), ADDR2 ); 945 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET (MSVDX_VEC, CR_VEC_VLC_TABLE_ADDR3), ADDR3 ); 946 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET (MSVDX_VEC, CR_VEC_VLC_TABLE_INITIAL_WIDTH0), WIDTH0 ); 947 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET (MSVDX_VEC, CR_VEC_VLC_TABLE_INITIAL_OPCODE0),OPCODE0 ); 948 psb_cmdbuf_reg_end_block( cmdbuf ); 949 950 psb_cmdbuf_skip_end_block( cmdbuf ); 951} 952 953/* Programme the Alt output if there is a rotation*/ 954static void psb__MPEG2_setup_alternative_frame( context_MPEG2_p ctx, IMG_BOOL write_reg ) 955{ 956 uint32_t cmd; 957 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 958 psb_surface_p rotate_surface = ctx->obj_context->current_render_target->psb_surface_rotate; 959 object_context_p obj_context = ctx->obj_context; 960 961 if(rotate_surface->extra_info[5] != obj_context->rotate) 962 psb__error_message("Display rotate mode does not match surface rotate mode!\n"); 963 964 965 /* CRendecBlock RendecBlk( mCtrlAlloc , RENDEC_REGISTER_OFFSET(MSVDX_CMDS, VC1_LUMA_RANGE_MAPPING_BASE_ADDRESS) ); */ 966 psb_cmdbuf_rendec_start( cmdbuf, RENDEC_REGISTER_OFFSET(MSVDX_CMDS, VC1_LUMA_RANGE_MAPPING_BASE_ADDRESS) ); 967 968 psb_cmdbuf_rendec_write_address( cmdbuf, &rotate_surface->buf, rotate_surface->buf.buffer_ofs); 969 psb_cmdbuf_rendec_write_address( cmdbuf, &rotate_surface->buf, rotate_surface->buf.buffer_ofs + rotate_surface->chroma_offset); 970 971 RELOC(*ctx->p_range_mapping_base0, rotate_surface->buf.buffer_ofs, &rotate_surface->buf); 972 RELOC(*ctx->p_range_mapping_base1, rotate_surface->buf.buffer_ofs + rotate_surface->chroma_offset, &rotate_surface->buf); 973 974 psb_cmdbuf_rendec_end( cmdbuf ); 975 976 if(write_reg) { 977 /* Set the rotation registers */ 978 psb_cmdbuf_rendec_start( cmdbuf, RENDEC_REGISTER_OFFSET(MSVDX_CMDS, ALTERNATIVE_OUTPUT_PICTURE_ROTATION) ); 979 cmd = 0; 980 REGIO_WRITE_FIELD_LITE(cmd, MSVDX_CMDS,ALTERNATIVE_OUTPUT_PICTURE_ROTATION ,ALT_PICTURE_ENABLE,1 ); 981 REGIO_WRITE_FIELD_LITE(cmd, MSVDX_CMDS,ALTERNATIVE_OUTPUT_PICTURE_ROTATION ,ROTATION_ROW_STRIDE, rotate_surface->stride_mode); 982 REGIO_WRITE_FIELD_LITE(cmd, MSVDX_CMDS,ALTERNATIVE_OUTPUT_PICTURE_ROTATION ,RECON_WRITE_DISABLE, 0); /* FIXME Always has Rec */ 983 REGIO_WRITE_FIELD_LITE(cmd, MSVDX_CMDS,ALTERNATIVE_OUTPUT_PICTURE_ROTATION ,ROTATION_MODE, rotate_surface->extra_info[5]); 984 985 psb_cmdbuf_rendec_write( cmdbuf, cmd ); 986 987 psb_cmdbuf_rendec_end( cmdbuf ); 988 } 989} 990 991static void psb__MPEG2_set_operating_mode(context_MPEG2_p ctx) 992{ 993 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 994 psb_surface_p target_surface = ctx->obj_context->current_render_target->psb_surface; 995 996 if(ctx->obj_context->rotate != VA_ROTATION_NONE) 997 psb__MPEG2_setup_alternative_frame( ctx, ctx->pic_params->picture_coding_extension.bits.progressive_frame); 998 999 psb_cmdbuf_rendec_start( cmdbuf, RENDEC_REGISTER_OFFSET(MSVDX_CMDS, DISPLAY_PICTURE_SIZE) ); 1000 psb_cmdbuf_rendec_write( cmdbuf, ctx->display_picture_size ); 1001 psb_cmdbuf_rendec_write( cmdbuf, ctx->coded_picture_size ); 1002 psb_cmdbuf_rendec_write( cmdbuf, ctx->obj_context->operating_mode ); 1003 1004 /* LUMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1005 psb_cmdbuf_rendec_write_address( cmdbuf, &target_surface->buf, target_surface->buf.buffer_ofs); 1006 1007 /* CHROMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1008 psb_cmdbuf_rendec_write_address( cmdbuf, &target_surface->buf, target_surface->buf.buffer_ofs + target_surface->chroma_offset); 1009 1010 psb_cmdbuf_rendec_end( cmdbuf ); 1011} 1012 1013static void psb__MPEG2_set_reference_pictures(context_MPEG2_p ctx) 1014{ 1015 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 1016 psb_surface_p target_surface = ctx->obj_context->current_render_target->psb_surface; 1017 1018 psb_cmdbuf_rendec_start( cmdbuf, RENDEC_REGISTER_OFFSET(MSVDX_CMDS, REFERENCE_PICTURE_BASE_ADDRESSES) ); 1019 1020 /* In MPEG2, the registers at N=0 are always used to store the base address of the luma and chroma buffers 1021 of the most recently decoded reference picture. The registers at N=1 are used to store the base address 1022 of the luma and chroma buffers of the older reference picture, if more than one reference picture is used. 1023 This means that when decoding a P picture the forward reference picture�s address is at index 0. 1024 When decoding a B-picture the backward reference picture�s address is at index 0 and the address of the 1025 forward reference picture � which was decoded earlier than the backward reference � is at index 1. 1026 */ 1027 1028 switch (ctx->pic_params->picture_coding_type) 1029 { 1030 case PICTURE_CODING_I: 1031 psb__information_message(" I-Frame\n"); 1032 /* No reference pictures */ 1033 psb_cmdbuf_rendec_write( cmdbuf, 0 ); 1034 psb_cmdbuf_rendec_write( cmdbuf, 0 ); 1035 psb_cmdbuf_rendec_write( cmdbuf, 0 ); 1036 psb_cmdbuf_rendec_write( cmdbuf, 0 ); 1037 break; 1038 1039 case PICTURE_CODING_P: 1040 psb__information_message(" P-Frame\n"); 1041 if (ctx->pic_params->picture_coding_extension.bits.is_first_field) 1042 { 1043 /* forward reference picture */ 1044 /* LUMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1045 psb_cmdbuf_rendec_write_address( cmdbuf, &ctx->forward_ref_surface->psb_surface->buf, ctx->forward_ref_surface->psb_surface->buf.buffer_ofs); 1046 1047 /* CHROMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1048 psb_cmdbuf_rendec_write_address( cmdbuf, &ctx->forward_ref_surface->psb_surface->buf, ctx->forward_ref_surface->psb_surface\ 1049 ->buf.buffer_ofs + ctx->forward_ref_surface->psb_surface->chroma_offset); 1050 1051 /* No backward reference picture */ 1052 psb_cmdbuf_rendec_write( cmdbuf, 0 ); 1053 psb_cmdbuf_rendec_write( cmdbuf, 0 ); 1054 } 1055 else 1056 { 1057 /* backward reference picture */ 1058 /* LUMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1059 psb_cmdbuf_rendec_write_address( cmdbuf, &target_surface->buf, target_surface->buf.buffer_ofs); 1060 1061 /* CHROMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1062 psb_cmdbuf_rendec_write_address( cmdbuf, &target_surface->buf, target_surface->buf.buffer_ofs + target_surface->chroma_offset); 1063 1064 /* forward reference picture */ 1065 /* LUMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1066 psb_cmdbuf_rendec_write_address( cmdbuf, &ctx->forward_ref_surface->psb_surface->buf, ctx->forward_ref_surface->psb_surface->buf.buffer_ofs); 1067 1068 /* CHROMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1069 psb_cmdbuf_rendec_write_address( cmdbuf, &ctx->forward_ref_surface->psb_surface->buf, ctx->forward_ref_surface->psb_surface->buf.buffer_ofs + ctx->forward_ref_surface->psb_surface->chroma_offset); 1070 } 1071 break; 1072 1073 case PICTURE_CODING_B: 1074 psb__information_message(" B-Frame\n"); 1075 /* backward reference picture */ 1076 /* LUMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1077 psb_cmdbuf_rendec_write_address( cmdbuf, &ctx->backward_ref_surface->psb_surface->buf, ctx->backward_ref_surface->psb_surface->buf.buffer_ofs); 1078 1079 /* CHROMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1080 psb_cmdbuf_rendec_write_address( cmdbuf, &ctx->backward_ref_surface->psb_surface->buf, ctx->backward_ref_surface->psb_surface->buf.buffer_ofs + ctx->backward_ref_surface->psb_surface->chroma_offset); 1081 1082 /* forward reference picture */ 1083 /* LUMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1084 psb_cmdbuf_rendec_write_address( cmdbuf, &ctx->forward_ref_surface->psb_surface->buf, ctx->forward_ref_surface->psb_surface->buf.buffer_ofs); 1085 1086 /* CHROMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES */ 1087 psb_cmdbuf_rendec_write_address( cmdbuf, &ctx->forward_ref_surface->psb_surface->buf, ctx->forward_ref_surface->psb_surface->buf.buffer_ofs + ctx->forward_ref_surface->psb_surface->chroma_offset); 1088 break; 1089 } 1090 1091 psb_cmdbuf_rendec_end( cmdbuf ); 1092} 1093 1094static void psb__MPEG2_set_picture_header(context_MPEG2_p ctx, VASliceParameterBufferMPEG2 *slice_param) 1095{ 1096 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 1097 psb_surface_p target_surface = ctx->obj_context->current_render_target->psb_surface; 1098 uint32_t FE_slice; 1099 uint32_t BE_slice; 1100 1101 psb_cmdbuf_reg_start_block( cmdbuf ); 1102 1103 /* VEC Control register: Front-End MPEG2 PPS0 */ 1104 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET (MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS0) , ctx->FE_PPS0 ); 1105 1106 /* VEC Control register: Front-End MPEG2 PPS1 */ 1107 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET (MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_PPS1) , ctx->FE_PPS1 ); 1108 1109 /* Slice level */ 1110 FE_slice = 0; 1111 REGIO_WRITE_FIELD (FE_slice, 1112 MSVDX_VEC_MPEG2, 1113 CR_VEC_MPEG2_FE_SLICE, 1114 FE_FIRST_IN_ROW, 1115 (ctx->previous_slice_vertical_position != slice_param->slice_vertical_position)); 1116 1117 REGIO_WRITE_FIELD (FE_slice, 1118 MSVDX_VEC_MPEG2, 1119 CR_VEC_MPEG2_FE_SLICE, 1120 FE_SLICE_VERTICAL_POSITION_MINUS1, 1121 slice_param->slice_vertical_position); 1122 1123 REGIO_WRITE_FIELD (FE_slice, 1124 MSVDX_VEC_MPEG2, 1125 CR_VEC_MPEG2_FE_SLICE, 1126 FE_QUANTISER_SCALE_CODE, 1127 slice_param->quantiser_scale_code); 1128 1129 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET (MSVDX_VEC_MPEG2, CR_VEC_MPEG2_FE_SLICE) , FE_slice ); 1130 1131 psb_cmdbuf_reg_end_block( cmdbuf ); 1132 1133 1134 /* BE Section */ 1135 psb_cmdbuf_rendec_start( cmdbuf, RENDEC_REGISTER_OFFSET(MSVDX_VEC, MPEG2_CR_VEC_MPEG2_BE_SPS0) ); 1136 1137 psb_cmdbuf_rendec_write( cmdbuf, ctx->BE_SPS0 ); 1138 psb_cmdbuf_rendec_write( cmdbuf, ctx->BE_SPS1 ); 1139 psb_cmdbuf_rendec_write( cmdbuf, ctx->BE_PPS0 ); /* VEC Control register: Back-End MPEG2 PPS0 */ 1140 psb_cmdbuf_rendec_write( cmdbuf, ctx->BE_PPS1 ); /* VEC Control register: Back-End MPEG2 PPS1 */ 1141 psb_cmdbuf_rendec_write( cmdbuf, ctx->BE_PPS2 ); /* VEC Control register: Back-End MPEG2 PPS2 */ 1142 1143 BE_slice = 0; 1144 if( !ctx->pic_params->picture_coding_extension.bits.is_first_field ) 1145 { 1146 /* 1147 BE_IP_PAIR_FLAG is 1 if the current picture_data is a P-coded field which is the 2nd field of a frame, 1148 and which uses the first field of the frame (which was I-coded) as a reference. 0 otherwise. 1149 BE_IP_PAIR_FLAG will only be 1 if BE_SECOND_FIELD_FLAG is 1, and the condition 1150 of "this is a P-field which uses the accompanying I-field as a reference" is met. 1151 */ 1152 if( ctx->pic_params->picture_coding_type == PICTURE_CODING_P ) 1153 { 1154 if( GET_SURFACE_INFO_picture_coding_type(target_surface) == PICTURE_CODING_I ) { 1155 REGIO_WRITE_FIELD_LITE (BE_slice, 1156 MSVDX_VEC_MPEG2, 1157 CR_VEC_MPEG2_BE_SLICE, 1158 BE_IP_PAIR_FLAG, 1 ); 1159 } 1160 } 1161 1162 REGIO_WRITE_FIELD_LITE(BE_slice, 1163 MSVDX_VEC_MPEG2, 1164 CR_VEC_MPEG2_BE_SLICE, 1165 BE_SECOND_FIELD_FLAG, 1 ); 1166 1167 } 1168 else 1169 { 1170 // BE_IP_PAIR_FLAG = 0; 1171 // BE_SECOND_FIELD_FLAG = 0; 1172 1173 /* Update with current settings first field */ 1174 SET_SURFACE_INFO_is_defined(target_surface, TRUE); 1175 SET_SURFACE_INFO_picture_structure(target_surface, ctx->pic_params->picture_coding_extension.bits.picture_structure ); 1176 SET_SURFACE_INFO_picture_coding_type(target_surface, ctx->pic_params->picture_coding_type ); 1177 } 1178 1179 REGIO_WRITE_FIELD_LITE (BE_slice, 1180 MSVDX_VEC_MPEG2, 1181 CR_VEC_MPEG2_BE_SLICE, 1182 BE_FIRST_IN_ROW, 1183 (ctx->previous_slice_vertical_position != slice_param->slice_vertical_position)); 1184 1185 REGIO_WRITE_FIELD_LITE (BE_slice, 1186 MSVDX_VEC_MPEG2, 1187 CR_VEC_MPEG2_BE_SLICE, 1188 BE_SLICE_VERTICAL_POSITION_MINUS1, 1189 slice_param->slice_vertical_position); 1190 1191 REGIO_WRITE_FIELD_LITE (BE_slice, 1192 MSVDX_VEC_MPEG2, 1193 CR_VEC_MPEG2_BE_SLICE, 1194 BE_QUANTISER_SCALE_CODE, 1195 slice_param->quantiser_scale_code); 1196 1197psb__information_message("BE_slice = %08x first_field = %d\n", BE_slice, ctx->pic_params->picture_coding_extension.bits.is_first_field); 1198 1199 psb_cmdbuf_rendec_write( cmdbuf, BE_slice ); 1200 1201 psb_cmdbuf_rendec_end( cmdbuf ); 1202 1203 ctx->previous_slice_vertical_position = slice_param->slice_vertical_position; 1204} 1205 1206static void psb__MPEG2_set_slice_params(context_MPEG2_p ctx) 1207{ 1208 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 1209 1210 uint32_t cmd_data; 1211 1212 psb_cmdbuf_rendec_start( cmdbuf, RENDEC_REGISTER_OFFSET(MSVDX_CMDS, SLICE_PARAMS) ); 1213 1214 cmd_data = 0; /* Build slice parameters */ 1215 REGIO_WRITE_FIELD (cmd_data, 1216 MSVDX_CMDS, 1217 SLICE_PARAMS, 1218 SLICE_FIELD_TYPE, 1219 ctx->pic_params->picture_coding_extension.bits.picture_structure - 1); 1220 1221 REGIO_WRITE_FIELD (cmd_data, 1222 MSVDX_CMDS, 1223 SLICE_PARAMS, 1224 SLICE_CODE_TYPE, 1225 PICTURE_CODING_D == ctx->pic_params->picture_coding_type ? 0 : ctx->pic_params->picture_coding_type - 1); 1226 1227 psb_cmdbuf_rendec_write( cmdbuf, cmd_data ); 1228 1229 *ctx->p_slice_params = cmd_data; 1230 1231 psb_cmdbuf_rendec_end( cmdbuf ); 1232} 1233 1234static void psb__MPEG2_write_qmatrices(context_MPEG2_p ctx) 1235{ 1236 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 1237 int i; 1238 1239 /* Since we only decode 4:2:0 We only need to the Intra tables. 1240 Chroma quant tables are only used in Mpeg 4:2:2 and 4:4:4. 1241 The hardware wants non-intra followed by intra */ 1242 psb_cmdbuf_rendec_start( cmdbuf, REG_MSVDX_VEC_IQRAM_OFFSET ); 1243 1244 /* todo : optimisation here is to only load the need table */ 1245 1246 /* NONINTRA_LUMA_Q --> REG_MSVDX_VEC_IQRAM_OFFSET + 0 */ 1247 for (i = 0; i < 16; i++) 1248 { 1249 psb_cmdbuf_rendec_write( cmdbuf, ctx->qmatrix_data[NONINTRA_LUMA_Q][i] ); 1250// psb__information_message("NONINTRA_LUMA_Q[i] = %08x\n", ctx->qmatrix_data[NONINTRA_LUMA_Q][i]); 1251 } 1252 /* INTRA_LUMA_Q --> REG_MSVDX_VEC_IQRAM_OFFSET + (16*4) */ 1253 for (i = 0; i < 16; i++) 1254 { 1255 psb_cmdbuf_rendec_write( cmdbuf, ctx->qmatrix_data[INTRA_LUMA_Q][i] ); 1256// psb__information_message("INTRA_LUMA_Q[i] = %08x\n", ctx->qmatrix_data[INTRA_LUMA_Q][i]); 1257 } 1258 1259 psb_cmdbuf_rendec_end( cmdbuf ); 1260} 1261 1262static void psb__MPEG2_set_ent_dec(context_MPEG2_p ctx) 1263{ 1264 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 1265 1266 uint32_t cmd_data; 1267 1268 psb_cmdbuf_reg_start_block( cmdbuf ); 1269 1270 cmd_data = 0; /* Entdec Front-End controls */ 1271 REGIO_WRITE_FIELD_LITE(cmd_data, MSVDX_VEC, CR_VEC_ENTDEC_FE_CONTROL, ENTDEC_FE_PROFILE, 1); /* MPEG2 Main Profile */ 1272 REGIO_WRITE_FIELD_LITE(cmd_data, MSVDX_VEC, CR_VEC_ENTDEC_FE_CONTROL, ENTDEC_FE_MODE, 3); /* Set MPEG2 mode */ 1273 1274 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET (MSVDX_VEC, CR_VEC_ENTDEC_FE_CONTROL), cmd_data); 1275 1276 psb_cmdbuf_reg_end_block( cmdbuf ); 1277 1278 psb_cmdbuf_rendec_start( cmdbuf, RENDEC_REGISTER_OFFSET(MSVDX_VEC, CR_VEC_ENTDEC_BE_CONTROL) ); 1279 1280 cmd_data = 0; /* Entdec Back-End controls */ 1281 REGIO_WRITE_FIELD (cmd_data, 1282 MSVDX_VEC, 1283 CR_VEC_ENTDEC_BE_CONTROL, 1284 ENTDEC_BE_PROFILE, 1285 1); /* MPEG2 Main Profile */ 1286 1287 REGIO_WRITE_FIELD (cmd_data, 1288 MSVDX_VEC, 1289 CR_VEC_ENTDEC_BE_CONTROL, 1290 ENTDEC_BE_MODE, 1291 3); /* Set MPEG2 mode */ 1292 1293 psb_cmdbuf_rendec_write( cmdbuf, cmd_data ); 1294 1295 psb_cmdbuf_rendec_end( cmdbuf ); 1296} 1297 1298static void psb__MPEG2_write_kick(context_MPEG2_p ctx, VASliceParameterBufferMPEG2 *slice_param) 1299{ 1300 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 1301 1302 (void) slice_param; /* Unused for now */ 1303 1304 *cmdbuf->cmd_idx++ = CMD_COMPLETION; 1305} 1306 1307static void psb__MPEG2_FE_state(context_MPEG2_p ctx) 1308{ 1309 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 1310 1311 /* See RENDER_BUFFER_HEADER */ 1312 *cmdbuf->cmd_idx++ = CMD_HEADER_VC1; 1313 1314 ctx->p_range_mapping_base0 = cmdbuf->cmd_idx++; 1315 ctx->p_range_mapping_base1 = cmdbuf->cmd_idx++; 1316 1317 *ctx->p_range_mapping_base0 = 0; 1318 *ctx->p_range_mapping_base1 = 0; 1319 1320 ctx->p_slice_params = cmdbuf->cmd_idx; 1321 *cmdbuf->cmd_idx++ = 0; /* ui32SliceParams */ 1322 1323 *cmdbuf->cmd_idx++ = 0; /* skip two lldma addr field */ 1324 1325 *cmdbuf->cmd_idx++ = 0; 1326 ctx->slice_first_pic_last = cmdbuf->cmd_idx++; 1327} 1328 1329static VAStatus psb__MPEG2_process_slice(context_MPEG2_p ctx, 1330 VASliceParameterBufferMPEG2 *slice_param, 1331 object_buffer_p obj_buffer) 1332{ 1333 VAStatus vaStatus = VA_STATUS_SUCCESS; 1334 1335 ASSERT((obj_buffer->type == VASliceDataBufferType) || (obj_buffer->type == VAProtectedSliceDataBufferType)); 1336 1337 psb__information_message("MPEG2 process slice\n"); 1338 psb__information_message(" size = %08x offset = %08x\n", slice_param->slice_data_size, slice_param->slice_data_offset); 1339 psb__information_message(" vertical pos = %d\n", slice_param->slice_vertical_position); 1340 psb__information_message(" slice_data_flag = %d\n", slice_param->slice_data_flag); 1341 psb__information_message(" coded size = %dx%d\n", ctx->picture_width_mb, ctx->picture_height_mb); 1342 1343 if ((slice_param->slice_data_flag == VA_SLICE_DATA_FLAG_BEGIN) || 1344 (slice_param->slice_data_flag == VA_SLICE_DATA_FLAG_ALL)) 1345 { 1346 if (0 == slice_param->slice_data_size) 1347 { 1348 vaStatus = VA_STATUS_ERROR_UNKNOWN; 1349 DEBUG_FAILURE; 1350 return vaStatus; 1351 } 1352 1353 ASSERT( !ctx->split_buffer_pending ); 1354 1355 /* Initialise the command buffer */ 1356 psb_context_get_next_cmdbuf(ctx->obj_context); 1357 1358 psb__MPEG2_FE_state(ctx); 1359 psb__MPEG2_write_VLC_tables(ctx); 1360 1361 psb_cmdbuf_lldma_write_bitstream(ctx->obj_context->cmdbuf, 1362 obj_buffer->psb_buffer, 1363 obj_buffer->psb_buffer->buffer_ofs + slice_param->slice_data_offset, 1364 slice_param->slice_data_size, 1365 slice_param->macroblock_offset, 1366 0); 1367 1368 if (slice_param->slice_data_flag == VA_SLICE_DATA_FLAG_BEGIN) 1369 { 1370 ctx->split_buffer_pending = TRUE; 1371 } 1372 } 1373 else 1374 { 1375 ASSERT( ctx->split_buffer_pending ); 1376 ASSERT(0 == slice_param->slice_data_offset); 1377 /* Create LLDMA chain to continue buffer */ 1378 if (slice_param->slice_data_size) 1379 { 1380 psb_cmdbuf_lldma_write_bitstream_chained(ctx->obj_context->cmdbuf, 1381 obj_buffer->psb_buffer, 1382 slice_param->slice_data_size); 1383 } 1384 } 1385 1386 if ((slice_param->slice_data_flag == VA_SLICE_DATA_FLAG_ALL) || 1387 (slice_param->slice_data_flag == VA_SLICE_DATA_FLAG_END)) 1388 { 1389 if (slice_param->slice_data_flag == VA_SLICE_DATA_FLAG_END) 1390 { 1391 ASSERT( ctx->split_buffer_pending ); 1392 } 1393 1394 psb__MPEG2_set_operating_mode(ctx); 1395 1396 psb__MPEG2_set_reference_pictures(ctx); 1397 1398 psb__MPEG2_set_picture_header(ctx, slice_param); 1399 1400 psb__MPEG2_set_slice_params(ctx); 1401 1402 psb__MPEG2_write_qmatrices(ctx); 1403 1404 psb__MPEG2_set_ent_dec(ctx); 1405 1406 psb__MPEG2_write_kick(ctx, slice_param); 1407 1408 ctx->split_buffer_pending = FALSE; 1409 ctx->obj_context->video_op = psb_video_vld; 1410 ctx->obj_context->flags = FW_DXVA_RENDER_IS_VLD_NOT_MC; 1411 ctx->obj_context->first_mb = 0; 1412 1413 if(ctx->pic_params->picture_coding_extension.bits.progressive_frame) 1414 ctx->obj_context->last_mb = ((ctx->picture_height_mb - 1) << 8) | (ctx->picture_width_mb - 1); 1415 else 1416 ctx->obj_context->last_mb = ((ctx->picture_height_mb/2 - 1 ) << 8) | (ctx->picture_width_mb - 1); 1417 1418 *ctx->slice_first_pic_last = (ctx->obj_context->first_mb << 16) | (ctx->obj_context->last_mb); 1419 1420 if (psb_context_submit_cmdbuf(ctx->obj_context)) 1421 { 1422 vaStatus = VA_STATUS_ERROR_UNKNOWN; 1423 } 1424 } 1425 return vaStatus; 1426} 1427 1428static VAStatus psb__MPEG2_process_slice_data(context_MPEG2_p ctx, object_buffer_p obj_buffer) 1429{ 1430 VAStatus vaStatus = VA_STATUS_SUCCESS; 1431 VASliceParameterBufferMPEG2 *slice_param; 1432 int buffer_idx = 0; 1433 int element_idx = 0; 1434 1435 ASSERT((obj_buffer->type == VASliceDataBufferType) || (obj_buffer->type == VAProtectedSliceDataBufferType)); 1436 1437 ASSERT(ctx->got_iq_matrix); 1438 ASSERT(ctx->pic_params); 1439 ASSERT(ctx->slice_param_list_idx); 1440 1441 if (!ctx->got_iq_matrix || !ctx->pic_params) 1442 { 1443 /* IQ matrix or Picture params missing */ 1444 return VA_STATUS_ERROR_UNKNOWN; 1445 } 1446 if ((NULL == obj_buffer->psb_buffer) || 1447 (0 == obj_buffer->size)) 1448 { 1449 /* We need to have data in the bitstream buffer */ 1450 return VA_STATUS_ERROR_UNKNOWN; 1451 } 1452 1453 while(buffer_idx < ctx->slice_param_list_idx) 1454 { 1455 object_buffer_p slice_buf = ctx->slice_param_list[buffer_idx]; 1456 if (element_idx >= slice_buf->num_elements) 1457 { 1458 /* Move to next buffer */ 1459 element_idx = 0; 1460 buffer_idx++; 1461 continue; 1462 } 1463 1464 slice_param = (VASliceParameterBufferMPEG2 *) slice_buf->buffer_data; 1465 slice_param += element_idx; 1466 element_idx++; 1467 vaStatus = psb__MPEG2_process_slice(ctx, slice_param, obj_buffer); 1468 if (vaStatus != VA_STATUS_SUCCESS) 1469 { DEBUG_FAILURE; 1470 break; 1471 } 1472 } 1473 ctx->slice_param_list_idx = 0; 1474 1475 return vaStatus; 1476} 1477 1478static void psb__MEPG2_send_highlevel_cmd(context_MPEG2_p ctx) 1479{ 1480 uint32_t cmd; 1481 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 1482 psb_surface_p target_surface = ctx->obj_context->current_render_target->psb_surface; 1483 psb_surface_p rotate_surface = ctx->obj_context->current_render_target->psb_surface_rotate; 1484 object_context_p obj_context = ctx->obj_context; 1485 1486 psb_cmdbuf_reg_start_block( cmdbuf ); 1487 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET(MSVDX_CMDS, DISPLAY_PICTURE_SIZE), ctx->display_picture_size); 1488 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET(MSVDX_CMDS, CODED_PICTURE_SIZE), ctx->coded_picture_size); 1489 1490 cmd = 0; 1491 REGIO_WRITE_FIELD(cmd, MSVDX_CMDS, OPERATING_MODE, CHROMA_FORMAT, 1); 1492 REGIO_WRITE_FIELD(cmd, MSVDX_CMDS, OPERATING_MODE, ASYNC_MODE, 1); // 0 = VDMC and VDEB active. 1 = VDEB pass-thru. 1493 REGIO_WRITE_FIELD(cmd, MSVDX_CMDS, OPERATING_MODE, CODEC_MODE, 3); // MPEG2 1494 REGIO_WRITE_FIELD(cmd, MSVDX_CMDS, OPERATING_MODE, CODEC_PROFILE, 1); // MAIN 1495 REGIO_WRITE_FIELD(cmd, MSVDX_CMDS, OPERATING_MODE, ROW_STRIDE, target_surface->stride_mode ); 1496 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET(MSVDX_CMDS, OPERATING_MODE), cmd); 1497 1498 psb_cmdbuf_reg_set_RELOC(cmdbuf, REGISTER_OFFSET(MSVDX_CMDS, LUMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES), 1499 &target_surface->buf, target_surface->buf.buffer_ofs); 1500 1501 psb_cmdbuf_reg_set_RELOC(cmdbuf, REGISTER_OFFSET(MSVDX_CMDS, CHROMA_RECONSTRUCTED_PICTURE_BASE_ADDRESSES), 1502 &target_surface->buf, target_surface->buf.buffer_ofs + target_surface->chroma_offset); 1503 1504 psb_cmdbuf_reg_set_RELOC(cmdbuf, REGISTER_OFFSET(MSVDX_CMDS, REFERENCE_PICTURE_BASE_ADDRESSES) + (0 * 8), 1505 &target_surface->buf, target_surface->buf.buffer_ofs); 1506 1507 psb_cmdbuf_reg_set_RELOC(cmdbuf, REGISTER_OFFSET(MSVDX_CMDS, REFERENCE_PICTURE_BASE_ADDRESSES) + 4 + (0 * 8), 1508 &target_surface->buf, target_surface->buf.buffer_ofs + target_surface->chroma_offset); 1509 1510 psb_cmdbuf_reg_set_RELOC(cmdbuf, REGISTER_OFFSET(MSVDX_CMDS, REFERENCE_PICTURE_BASE_ADDRESSES) + (1 * 8), 1511 &target_surface->buf, target_surface->buf.buffer_ofs); 1512 1513 psb_cmdbuf_reg_set_RELOC(cmdbuf, REGISTER_OFFSET(MSVDX_CMDS, REFERENCE_PICTURE_BASE_ADDRESSES) + 4 + (1 * 8), 1514 &target_surface->buf, target_surface->buf.buffer_ofs + target_surface->chroma_offset); 1515 1516 cmd = 0; 1517 REGIO_WRITE_FIELD(cmd, MSVDX_CMDS, SLICE_PARAMS, SLICE_FIELD_TYPE, 2); /* FRAME PICTURE -- ui8SliceFldType */ 1518 REGIO_WRITE_FIELD(cmd, MSVDX_CMDS, SLICE_PARAMS, SLICE_CODE_TYPE, 1); /* P PICTURE -- (ui8PicType == WMF_PTYPE_BI) ? WMF_PTYPE_I : (ui8PicType & 0x3) */ 1519 psb_cmdbuf_reg_set(cmdbuf, REGISTER_OFFSET (MSVDX_CMDS, SLICE_PARAMS), cmd ); 1520 *ctx->p_slice_params = cmd; 1521 psb_cmdbuf_reg_end_block( cmdbuf ); 1522 1523 1524 psb_cmdbuf_reg_start_block( cmdbuf ); 1525 psb_cmdbuf_reg_set_RELOC(cmdbuf, REGISTER_OFFSET(MSVDX_CMDS, VC1_LUMA_RANGE_MAPPING_BASE_ADDRESS), 1526 &rotate_surface->buf, rotate_surface->buf.buffer_ofs); 1527 1528 psb_cmdbuf_reg_set_RELOC(cmdbuf, REGISTER_OFFSET (MSVDX_CMDS, VC1_CHROMA_RANGE_MAPPING_BASE_ADDRESS), 1529 &rotate_surface->buf, rotate_surface->buf.buffer_ofs + rotate_surface->chroma_offset); 1530 psb_cmdbuf_reg_end_block( cmdbuf ); 1531 1532 RELOC(*ctx->p_range_mapping_base0, rotate_surface->buf.buffer_ofs, &rotate_surface->buf); 1533 RELOC(*ctx->p_range_mapping_base1, rotate_surface->buf.buffer_ofs + rotate_surface->chroma_offset, &rotate_surface->buf); 1534} 1535 1536static void psb__MEPG2_send_blit_cmd(context_MPEG2_p ctx) 1537{ 1538 uint32_t cmd; 1539 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 1540 psb_surface_p rotate_surface = ctx->obj_context->current_render_target->psb_surface_rotate; 1541 object_context_p obj_context = ctx->obj_context; 1542 1543 psb_cmdbuf_reg_start_block( cmdbuf ); 1544 cmd = 0; 1545 REGIO_WRITE_FIELD_LITE(cmd, MSVDX_CMDS,ALTERNATIVE_OUTPUT_PICTURE_ROTATION ,ALT_PICTURE_ENABLE,1 ); 1546 REGIO_WRITE_FIELD_LITE(cmd, MSVDX_CMDS,ALTERNATIVE_OUTPUT_PICTURE_ROTATION ,ROTATION_ROW_STRIDE, rotate_surface->stride_mode); 1547 REGIO_WRITE_FIELD_LITE(cmd, MSVDX_CMDS,ALTERNATIVE_OUTPUT_PICTURE_ROTATION ,RECON_WRITE_DISABLE, 0); 1548 REGIO_WRITE_FIELD_LITE(cmd, MSVDX_CMDS,ALTERNATIVE_OUTPUT_PICTURE_ROTATION ,ROTATION_MODE, rotate_surface->extra_info[5]); 1549 psb_cmdbuf_reg_set( cmdbuf, REGISTER_OFFSET(MSVDX_CMDS, ALTERNATIVE_OUTPUT_PICTURE_ROTATION), cmd); 1550 psb_cmdbuf_reg_end_block( cmdbuf ); 1551 1552 *cmdbuf->cmd_idx++ = 0x40000000; /* CMD_BLIT_CMD */ 1553 *cmdbuf->cmd_idx++ = ctx->picture_width_mb; 1554 *cmdbuf->cmd_idx++ = ctx->picture_height_mb; /* FIXME */ 1555 *cmdbuf->cmd_idx++ = CMD_COMPLETION; 1556} 1557 1558static void psb__MPEG2_insert_blit_cmd_to_rotate( context_MPEG2_p ctx ) 1559{ 1560 psb_cmdbuf_p cmdbuf = ctx->obj_context->cmdbuf; 1561 1562 /* See RENDER_BUFFER_HEADER */ 1563 *cmdbuf->cmd_idx++ = CMD_HEADER_VC1; 1564 1565 ctx->p_range_mapping_base0 = cmdbuf->cmd_idx++; 1566 ctx->p_range_mapping_base1 = cmdbuf->cmd_idx++; 1567 1568 *ctx->p_range_mapping_base0 = 0; 1569 *ctx->p_range_mapping_base1 = 0; 1570 1571 ctx->p_slice_params = cmdbuf->cmd_idx; 1572 *cmdbuf->cmd_idx++ = 0; /* ui32SliceParams */ 1573 1574 *cmdbuf->cmd_idx++ = 0; /* skip two lldma addr field */ 1575 *cmdbuf->cmd_idx++ = 0; 1576 1577 ctx->slice_first_pic_last = cmdbuf->cmd_idx++; 1578 *ctx->slice_first_pic_last = 0; 1579 1580 psb__MEPG2_send_highlevel_cmd(ctx); 1581 psb__MEPG2_send_blit_cmd(ctx); 1582 1583 ctx->obj_context->video_op = psb_video_mc; 1584 ctx->obj_context->flags = FW_DXVA_RENDER_IS_LAST_SLICE; 1585 1586 if (psb_context_submit_cmdbuf(ctx->obj_context)) 1587 { 1588 ASSERT(0); 1589 } 1590} 1591 1592static VAStatus pnw_MPEG2_BeginPicture( 1593 object_context_p obj_context) 1594{ 1595 INIT_CONTEXT_MPEG2 1596 1597 psb__information_message("pnw_MPEG2_BeginPicture\n"); 1598 if (ctx->pic_params) 1599 { 1600 free(ctx->pic_params); 1601 ctx->pic_params = NULL; 1602 } 1603 ctx->previous_slice_vertical_position = ~1; 1604 1605 return VA_STATUS_SUCCESS; 1606} 1607 1608static VAStatus pnw_MPEG2_RenderPicture( 1609 object_context_p obj_context, 1610 object_buffer_p *buffers, 1611 int num_buffers) 1612{ 1613 int i; 1614 INIT_CONTEXT_MPEG2 1615 VAStatus vaStatus = VA_STATUS_SUCCESS; 1616 1617 for(i = 0; i < num_buffers; i++) 1618 { 1619 object_buffer_p obj_buffer = buffers[i]; 1620 1621 switch( obj_buffer->type) 1622 { 1623 case VAPictureParameterBufferType: 1624 psb__information_message("pnw_MPEG2_RenderPicture got VAPictureParameterBuffer\n"); 1625 vaStatus = psb__MPEG2_process_picture_param(ctx, obj_buffer); 1626 DEBUG_FAILURE; 1627 break; 1628 1629 case VAIQMatrixBufferType: 1630 psb__information_message("pnw_MPEG2_RenderPicture got VAIQMatrixBufferType\n"); 1631 vaStatus = psb__MPEG2_process_iq_matrix(ctx, obj_buffer); 1632 DEBUG_FAILURE; 1633 break; 1634 1635 case VASliceParameterBufferType: 1636 psb__information_message("pnw_MPEG2_RenderPicture got VASliceParameterBufferType\n"); 1637 vaStatus = psb__MPEG2_add_slice_param(ctx, obj_buffer); 1638 DEBUG_FAILURE; 1639 break; 1640 1641 case VASliceDataBufferType: 1642 case VAProtectedSliceDataBufferType: 1643 1644 psb__information_message("pnw_MPEG2_RenderPicture got %s\n", SLICEDATA_BUFFER_TYPE(obj_buffer->type)); 1645 vaStatus = psb__MPEG2_process_slice_data(ctx, obj_buffer); 1646 DEBUG_FAILURE; 1647 break; 1648 1649 default: 1650 vaStatus = VA_STATUS_ERROR_UNKNOWN; 1651 DEBUG_FAILURE; 1652 } 1653 if (vaStatus != VA_STATUS_SUCCESS) 1654 { 1655 break; 1656 } 1657 } 1658 1659 return vaStatus; 1660} 1661 1662static VAStatus pnw_MPEG2_EndPicture( 1663 object_context_p obj_context) 1664{ 1665 VAStatus vaStatus = VA_STATUS_SUCCESS; 1666 INIT_CONTEXT_MPEG2 1667 1668 psb__information_message("pnw_MPEG2_EndPicture\n"); 1669 1670 if(ctx->obj_context->rotate != VA_ROTATION_NONE) 1671 { 1672 if( !(ctx->pic_params->picture_coding_extension.bits.progressive_frame) && 1673 !(ctx->pic_params->picture_coding_extension.bits.is_first_field)) 1674 psb__MPEG2_insert_blit_cmd_to_rotate(ctx); 1675 } 1676 1677 if (psb_context_flush_cmdbuf(ctx->obj_context)) 1678 { 1679 vaStatus = VA_STATUS_ERROR_UNKNOWN; 1680 } 1681 1682 if (ctx->pic_params) 1683 { 1684 free(ctx->pic_params); 1685 ctx->pic_params = NULL; 1686 } 1687 1688 return vaStatus; 1689} 1690 1691struct format_vtable_s pnw_MPEG2_vtable = { 1692 queryConfigAttributes: pnw_MPEG2_QueryConfigAttributes, 1693 validateConfig: pnw_MPEG2_ValidateConfig, 1694 createContext: pnw_MPEG2_CreateContext, 1695 destroyContext: pnw_MPEG2_DestroyContext, 1696 beginPicture: pnw_MPEG2_BeginPicture, 1697 renderPicture: pnw_MPEG2_RenderPicture, 1698 endPicture: pnw_MPEG2_EndPicture 1699}; 1700