00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016 #include "global.h"
00017 #include "mbuffer.h"
00018 #include "mb_access.h"
00019 #include "macroblock.h"
00020 #include "errdo.h"
00021 #include "errdo_mc_prediction.h"
00022
00023
00024
00025 #if defined(USEMMX)
00026 #if defined(_MSC_VER) || defined(__INTEL_COMPILER) // ICC
00027 __declspec(align(16)) imgpel tmp_block_l0[MB_BLOCK_SIZE][MB_BLOCK_SIZE];
00028 __declspec(align(16)) imgpel tmp_block_l1[MB_BLOCK_SIZE][MB_BLOCK_SIZE];
00029 # else
00030 imgpel tmp_block_l0[MB_BLOCK_SIZE][MB_BLOCK_SIZE] __attribute__ ((aligned (16)));
00031 imgpel tmp_block_l1[MB_BLOCK_SIZE][MB_BLOCK_SIZE] __attribute__ ((aligned (16)));
00032 # endif
00033 #else
00034 imgpel tmp_block_l0[MB_BLOCK_SIZE][MB_BLOCK_SIZE];
00035 imgpel tmp_block_l1[MB_BLOCK_SIZE][MB_BLOCK_SIZE];
00036 #endif
00037
00038
00039 static const int COEF[6] = { 1, -5, 20, 20, -5, 1 };
00040
00041
00042
00043
00044
00045
00046 static inline void mc_prediction(imgpel** mb_pred,
00047 int ver_block_size,
00048 int hor_block_size,
00049 int ioff,
00050 imgpel block[MB_BLOCK_SIZE][MB_BLOCK_SIZE])
00051 {
00052 static int jj;
00053
00054 if (hor_block_size == MB_BLOCK_SIZE)
00055 {
00056 memcpy(&(mb_pred[0][ioff]), &(block[0][0]), hor_block_size * ver_block_size * sizeof(imgpel));
00057 }
00058 else
00059 {
00060 for(jj = 0; jj < ver_block_size; jj++)
00061 {
00062 memcpy(&(mb_pred[jj][ioff]), &(block[jj][0]), hor_block_size * sizeof(imgpel));
00063 }
00064 }
00065 }
00066
00067
00068
00069
00070
00071
00072
00073 static inline void weighted_mc_prediction(imgpel** mb_pred,
00074 int ver_block_size,
00075 int hor_block_size,
00076 int ioff,
00077 imgpel block[MB_BLOCK_SIZE][MB_BLOCK_SIZE],
00078 int wp_scale,
00079 int wp_offset,
00080 int weight_denom,
00081 int color_clip)
00082 {
00083 static int ii, jj;
00084 static imgpel *mpr, *b0;
00085
00086 for(jj=0;jj<ver_block_size;jj++)
00087 {
00088 mpr = &mb_pred[jj][ioff];
00089 b0 = block[jj];
00090 for(ii=0;ii<hor_block_size;ii++)
00091 *(mpr++) = (imgpel) iClip1(color_clip, (rshift_rnd((wp_scale * *(b0++)), weight_denom) + wp_offset ));
00092 }
00093 }
00094
00095
00096
00097
00098
00099
00100
00101
00102 static inline void bi_prediction(imgpel** mb_pred,
00103 imgpel block_l0[MB_BLOCK_SIZE][MB_BLOCK_SIZE],
00104 imgpel block_l1[MB_BLOCK_SIZE][MB_BLOCK_SIZE],
00105 int ver_block_size,
00106 int hor_block_size,
00107 int ioff)
00108 {
00109 static int ii, jj;
00110 static imgpel *mpr, *b0, *b1;
00111
00112 for(jj = 0;jj < ver_block_size;jj++)
00113 {
00114 mpr = &mb_pred[jj][ioff];
00115 b0 = block_l0[jj];
00116 b1 = block_l1[jj];
00117 for(ii = 0; ii < hor_block_size;ii++)
00118 *(mpr++) = (imgpel) rshift_rnd_sf((*(b0++) + *(b1++)), 1);
00119 }
00120 }
00121
00122
00123
00124
00125
00126
00127
00128 static inline void weighted_bi_prediction(imgpel** mb_pred,
00129 imgpel block_l0[MB_BLOCK_SIZE][MB_BLOCK_SIZE],
00130 imgpel block_l1[MB_BLOCK_SIZE][MB_BLOCK_SIZE],
00131 int ver_block_size,
00132 int hor_block_size,
00133 int ioff,
00134 int wp_scale_l0,
00135 int wp_scale_l1,
00136 int wp_offset,
00137 int weight_denom,
00138 int color_clip)
00139 {
00140 static int ii, jj;
00141 static imgpel *mpr, *b0, *b1;
00142
00143 for(jj = 0; jj < ver_block_size; jj++)
00144 {
00145 mpr = &mb_pred[jj][ioff];
00146 b0 = block_l0[jj];
00147 b1 = block_l1[jj];
00148
00149 for(ii=0;ii<hor_block_size;ii++)
00150 *(mpr++) = (imgpel) iClip1(color_clip, (rshift_rnd((wp_scale_l0 * *(b0++) + wp_scale_l1 * *(b1++)), weight_denom) + wp_offset));
00151 }
00152 }
00153
00154 void get_block_luma(int decoder, ColorPlane pl, StorablePicture* dec_picture, StorablePicture *curr_ref, int x_pos, int y_pos, int hor_block_size, int ver_block_size, ImageParameters *img, imgpel block[MB_BLOCK_SIZE][MB_BLOCK_SIZE])
00155 {
00156 static int tmp_res[21][21];
00157 static int *tmp_line;
00158 static imgpel *p0, *p1, *p2, *p3, *p4, *p5;
00159 static int *x0, *x1, *x2, *x3, *x4, *x5;
00160
00161 static imgpel **cur_imgY, *cur_lineY;
00162 static int ipos_m2, ipos_m1, ipos, ipos_p1, ipos_p2, ipos_p3;
00163 static imgpel *orig_line;
00164 int tmp_pos;
00165
00166 int dx = (x_pos & 3), dy = (y_pos & 3);
00167 int i, j, jj;
00168 int shift_x = dec_picture->size_x;
00169 int maxold_x = dec_picture->size_x - 1;
00170 int maxold_y = (dec_picture->motion.mb_field[img->current_mb_nr]) ? (dec_picture->size_y >> 1) - 1 : dec_picture->size_y - 1;
00171 int result;
00172 int pres_x;
00173 int max_imgpel_value = img->max_imgpel_value_comp[pl];
00174
00175
00176 if( IS_INDEPENDENT(params) )
00177 {
00178 cur_imgY = curr_ref->p_dec_img[img->colour_plane_id][decoder];
00179 }
00180 else
00181 {
00182 cur_imgY = curr_ref->p_dec_img[pl][decoder];
00183 }
00184
00185 x_pos = x_pos >> 2;
00186 y_pos = y_pos >> 2;
00187
00188 if ( (y_pos > 1) && (y_pos < maxold_y - 2 - ver_block_size) && (x_pos > 1) && (x_pos < maxold_x - 2 - hor_block_size))
00189 {
00190 cur_imgY = &cur_imgY[ y_pos];
00191 if (dx == 0 && dy == 0)
00192 {
00193 for (j = 0; j < ver_block_size; j++)
00194 {
00195 memcpy(&(block[j][0]), &(cur_imgY[j][x_pos]), hor_block_size * sizeof(imgpel));
00196 }
00197 }
00198 else
00199 {
00200
00201 if (dy == 0)
00202 {
00203 for (j = 0; j < ver_block_size; j++)
00204 {
00205 p0 = &cur_imgY[j][x_pos - 2];
00206 p1 = p0 + 1;
00207 p2 = p1 + 1;
00208 p3 = p2 + 1;
00209 p4 = p3 + 1;
00210 p5 = p4 + 1;
00211 orig_line = block[j];
00212
00213 for (i = 0; i < hor_block_size; i++)
00214 {
00215 result = (*(p0++) + *(p5++)) * COEF[0]
00216 + (*(p1++) + *(p4++)) * COEF[1]
00217 + (*(p2++) + *(p3++)) * COEF[2];
00218
00219 *orig_line++ = (imgpel) iClip1(max_imgpel_value, ((result + 16)>>5));
00220 }
00221 }
00222
00223 if ((dx&1) == 1)
00224 {
00225 for (j = 0; j < ver_block_size; j++)
00226 {
00227 cur_lineY = &(cur_imgY[j][x_pos + (dx >> 1)]);
00228 orig_line = block[j];
00229 for (i = 0; i < hor_block_size; i++)
00230 {
00231 *orig_line = (imgpel) ((*orig_line + *(cur_lineY++) + 1 ) >> 1);
00232 orig_line++;
00233 }
00234 }
00235 }
00236 }
00237 else if (dx == 0)
00238 {
00239 p0 = &(cur_imgY[ - 2][x_pos]);
00240 for (j = 0; j < ver_block_size; j++)
00241 {
00242 p1 = p0 + shift_x;
00243 p2 = p1 + shift_x;
00244 p3 = p2 + shift_x;
00245 p4 = p3 + shift_x;
00246 p5 = p4 + shift_x;
00247 orig_line = block[j];
00248
00249 for (i = 0; i < hor_block_size; i++)
00250 {
00251 result = (*(p0++) + *(p5++)) * COEF[0]
00252 + (*(p1++) + *(p4++)) * COEF[1]
00253 + (*(p2++) + *(p3++)) * COEF[2];
00254
00255 *orig_line++ = (imgpel) iClip1(max_imgpel_value, ((result + 16)>>5));
00256 }
00257 p0 = p1 - hor_block_size;
00258 }
00259
00260 if ((dy&1) == 1)
00261 {
00262 jj = (dy >> 1);
00263 for (j = 0; j < ver_block_size; j++)
00264 {
00265 cur_lineY = &(cur_imgY[jj++][x_pos]);
00266 orig_line = block[j];
00267 for (i = 0; i < hor_block_size; i++)
00268 {
00269 *orig_line = (imgpel) ((*orig_line + *(cur_lineY++) + 1 ) >> 1);
00270 orig_line++;
00271 }
00272 }
00273 }
00274 }
00275 else if (dx == 2)
00276 {
00277 jj = - 2;
00278 for (j = 0; j < ver_block_size + 5; j++)
00279 {
00280 p0 = &cur_imgY[jj++][x_pos - 2];
00281 p1 = p0 + 1;
00282 p2 = p1 + 1;
00283 p3 = p2 + 1;
00284 p4 = p3 + 1;
00285 p5 = p4 + 1;
00286 orig_line = block[j];
00287 tmp_line = tmp_res[j];
00288
00289 for (i = 0; i < hor_block_size; i++)
00290 {
00291 *(tmp_line++) = (*(p0++) + *(p5++)) * COEF[0]
00292 + (*(p1++) + *(p4++)) * COEF[1]
00293 + (*(p2++) + *(p3++)) * COEF[2];
00294 }
00295 }
00296
00297 for (j = 0; j < ver_block_size; j++)
00298 {
00299 x0 = tmp_res[j ];
00300 x1 = tmp_res[j + 1];
00301 x2 = tmp_res[j + 2];
00302 x3 = tmp_res[j + 3];
00303 x4 = tmp_res[j + 4];
00304 x5 = tmp_res[j + 5];
00305 orig_line = block[j];
00306
00307 for (i = 0; i < hor_block_size; i++)
00308 {
00309 result = (*x0++ + *x5++) * COEF[0]
00310 + (*x1++ + *x4++) * COEF[1]
00311 + (*x2++ + *x3++) * COEF[2];
00312
00313 *(orig_line++) = (imgpel) iClip1(max_imgpel_value, ((result+512)>>10));
00314 }
00315 }
00316
00317 if ((dy&1) == 1)
00318 {
00319 jj = 2 + (dy>>1);
00320 for (j = 0; j < ver_block_size; j++)
00321 {
00322 tmp_line = tmp_res[jj++];
00323 orig_line = block[j];
00324 for (i = 0; i < hor_block_size; i++)
00325 {
00326 *orig_line = (imgpel) ((*orig_line + iClip1(max_imgpel_value, ((*(tmp_line++) + 16) >> 5)) + 1 )>> 1);
00327 orig_line++;
00328 }
00329 }
00330 }
00331 }
00332 else if (dy == 2)
00333 {
00334 p0 = &(cur_imgY[ -2][x_pos - 2]);
00335 for (j = 0; j < ver_block_size; j++)
00336 {
00337 p1 = p0 + shift_x;
00338 p2 = p1 + shift_x;
00339 p3 = p2 + shift_x;
00340 p4 = p3 + shift_x;
00341 p5 = p4 + shift_x;
00342 tmp_line = tmp_res[j];
00343
00344 for (i = 0; i < hor_block_size + 5; i++)
00345 {
00346 *(tmp_line++) = (*(p0++) + *(p5++)) * COEF[0]
00347 + (*(p1++) + *(p4++)) * COEF[1]
00348 + (*(p2++) + *(p3++)) * COEF[2];
00349 }
00350 p0 = p1 - (hor_block_size + 5);
00351 }
00352
00353 for (j = 0; j < ver_block_size; j++)
00354 {
00355 orig_line = block[j];
00356 x0 = tmp_res[j];
00357 x1 = x0 + 1;
00358 x2 = x1 + 1;
00359 x3 = x2 + 1;
00360 x4 = x3 + 1;
00361 x5 = x4 + 1;
00362
00363 for (i = 0; i < hor_block_size; i++)
00364 {
00365 result = (*(x0++) + *(x5++)) * COEF[0]
00366 + (*(x1++) + *(x4++)) * COEF[1]
00367 + (*(x2++) + *(x3++)) * COEF[2];
00368
00369 *(orig_line++) = (imgpel) iClip1(max_imgpel_value, ((result + 512)>>10));
00370 }
00371 }
00372
00373 if ((dx&1) == 1)
00374 {
00375 for (j = 0; j < ver_block_size; j++)
00376 {
00377 tmp_line = &tmp_res[j][2 + (dx>>1)];
00378 orig_line = block[j];
00379 for (i = 0; i < hor_block_size; i++)
00380 {
00381 *orig_line = (imgpel) ((*orig_line + iClip1(max_imgpel_value, ((*(tmp_line++) + 16)>>5))+1)>>1);
00382 orig_line ++;
00383 }
00384 }
00385 }
00386 }
00387 else
00388 {
00389 jj = (dy == 1 ? 0 : 1);
00390
00391 for (j = 0; j < ver_block_size; j++)
00392 {
00393 p0 = &cur_imgY[jj++][x_pos - 2];
00394 p1 = p0 + 1;
00395 p2 = p1 + 1;
00396 p3 = p2 + 1;
00397 p4 = p3 + 1;
00398 p5 = p4 + 1;
00399
00400 orig_line = block[j];
00401
00402 for (i = 0; i < hor_block_size; i++)
00403 {
00404 result = (*(p0++) + *(p5++)) * COEF[0]
00405 + (*(p1++) + *(p4++)) * COEF[1]
00406 + (*(p2++) + *(p3++)) * COEF[2];
00407
00408 *(orig_line++) = (imgpel) iClip1(max_imgpel_value, ((result + 16)>>5));
00409 }
00410 }
00411
00412 p0 = &(cur_imgY[-2][(dx == 1 ? x_pos : x_pos + 1)]);
00413 for (j = 0; j < ver_block_size; j++)
00414 {
00415 p1 = p0 + shift_x;
00416 p2 = p1 + shift_x;
00417 p3 = p2 + shift_x;
00418 p4 = p3 + shift_x;
00419 p5 = p4 + shift_x;
00420 orig_line = block[j];
00421
00422 for (i = 0; i < hor_block_size; i++)
00423 {
00424 result = (*(p0++) + *(p5++)) * COEF[0]
00425 + (*(p1++) + *(p4++)) * COEF[1]
00426 + (*(p2++) + *(p3++)) * COEF[2];
00427
00428 *orig_line = (imgpel) ((*orig_line + iClip1(max_imgpel_value, ((result + 16) >> 5)) + 1) >> 1);
00429 orig_line++;
00430 }
00431 p0 = p1 - hor_block_size ;
00432 }
00433 }
00434 }
00435 }
00436 else
00437 {
00438 if (dx == 0 && dy == 0)
00439 {
00440 for (j = 0; j < ver_block_size; j++)
00441 {
00442 cur_lineY = cur_imgY[iClip3(0, maxold_y, y_pos + j)];
00443 orig_line = block[j];
00444 for (i = 0; i < hor_block_size; i++)
00445 {
00446 *(orig_line++) = cur_lineY[iClip3(0, maxold_x, x_pos + i )];
00447 }
00448 }
00449 }
00450 else
00451 {
00452
00453 if (dy == 0)
00454 {
00455 tmp_pos = x_pos - 2;
00456 for (i = 0; i < hor_block_size; i++)
00457 {
00458 ipos_m2 = iClip3(0, maxold_x, tmp_pos++);
00459 ipos_m1 = iClip3(0, maxold_x, tmp_pos++);
00460 ipos = iClip3(0, maxold_x, tmp_pos++);
00461 ipos_p1 = iClip3(0, maxold_x, tmp_pos++);
00462 ipos_p2 = iClip3(0, maxold_x, tmp_pos++);
00463 ipos_p3 = iClip3(0, maxold_x, tmp_pos );
00464 tmp_pos -= 4;
00465
00466 for (j = 0; j < ver_block_size; j++)
00467 {
00468 cur_lineY = cur_imgY[iClip3(0,maxold_y,y_pos+j)];
00469
00470 result = (cur_lineY[ipos_m2] + cur_lineY[ipos_p3]) * COEF[0];
00471 result += (cur_lineY[ipos_m1] + cur_lineY[ipos_p2]) * COEF[1];
00472 result += (cur_lineY[ipos ] + cur_lineY[ipos_p1]) * COEF[2];
00473
00474 block[j][i] = (imgpel) iClip1(max_imgpel_value, ((result + 16)>>5));
00475 }
00476 }
00477
00478 if ((dx&1) == 1)
00479 {
00480 for (j = 0; j < ver_block_size; j++)
00481 {
00482 cur_lineY = cur_imgY[iClip3(0,maxold_y,y_pos+j)];
00483 orig_line = block[j];
00484 for (i = 0; i < hor_block_size; i++)
00485 {
00486 *orig_line = (imgpel) ((*orig_line + cur_lineY[iClip3(0, maxold_x, x_pos + i + (dx >> 1))] + 1 ) >> 1);
00487 orig_line++;
00488 }
00489 }
00490 }
00491 }
00492 else if (dx == 0)
00493 {
00494 tmp_pos = y_pos - 2;
00495 for (j = 0; j < ver_block_size; j++)
00496 {
00497 p0 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00498 p1 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00499 p2 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00500 p3 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00501 p4 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00502 p5 = cur_imgY[iClip3(0, maxold_y, tmp_pos )];
00503
00504 tmp_pos -= 4;
00505 orig_line = block[j];
00506
00507 for (i = 0; i < hor_block_size; i++)
00508 {
00509 pres_x = iClip3(0,maxold_x,x_pos+i);
00510
00511 result = (p0[pres_x] + p5[pres_x]) * COEF[0];
00512 result += (p1[pres_x] + p4[pres_x]) * COEF[1];
00513 result += (p2[pres_x] + p3[pres_x]) * COEF[2];
00514 *(orig_line++) = (imgpel) iClip1(max_imgpel_value, ((result+16)>>5));
00515 }
00516 }
00517
00518 if ((dy&1) == 1)
00519 {
00520 for (j = 0; j < ver_block_size; j++)
00521 {
00522 cur_lineY = cur_imgY[iClip3(0,maxold_y,y_pos+j+(dy>>1))];
00523 orig_line = block[j];
00524 for (i = 0; i < hor_block_size; i++)
00525 {
00526 *orig_line = (imgpel) ((*orig_line + cur_lineY[iClip3(0, maxold_x, x_pos + i)] + 1 ) >> 1);
00527 orig_line++;
00528 }
00529 }
00530 }
00531 }
00532 else if (dx == 2)
00533 {
00534 tmp_pos = x_pos - 2;
00535 for (i = 0; i < hor_block_size; i++)
00536 {
00537 ipos_m2 = iClip3(0, maxold_x, tmp_pos++);
00538 ipos_m1 = iClip3(0, maxold_x, tmp_pos++);
00539 ipos = iClip3(0, maxold_x, tmp_pos++);
00540 ipos_p1 = iClip3(0, maxold_x, tmp_pos++);
00541 ipos_p2 = iClip3(0, maxold_x, tmp_pos++);
00542 ipos_p3 = iClip3(0, maxold_x, tmp_pos );
00543 tmp_pos -= 4;
00544
00545 for (j = 0; j < ver_block_size + 5; j++)
00546 {
00547 cur_lineY = cur_imgY[iClip3(0,maxold_y,y_pos + j - 2)];
00548
00549 tmp_res[j][i] = (cur_lineY[ipos_m2] + cur_lineY[ipos_p3]) * COEF[0];
00550 tmp_res[j][i] += (cur_lineY[ipos_m1] + cur_lineY[ipos_p2]) * COEF[1];
00551 tmp_res[j][i] += (cur_lineY[ipos ] + cur_lineY[ipos_p1]) * COEF[2];
00552 }
00553 }
00554
00555 for (j = 0; j < ver_block_size; j++)
00556 {
00557 x0 = tmp_res[j ];
00558 x1 = tmp_res[j + 1];
00559 x2 = tmp_res[j + 2];
00560 x3 = tmp_res[j + 3];
00561 x4 = tmp_res[j + 4];
00562 x5 = tmp_res[j + 5];
00563 orig_line = block[j];
00564
00565 for (i = 0; i < hor_block_size; i++)
00566 {
00567 result = (*x0++ + *x5++) * COEF[0]
00568 + (*x1++ + *x4++) * COEF[1]
00569 + (*x2++ + *x3++) * COEF[2];
00570
00571 *(orig_line++) = (imgpel) iClip1(max_imgpel_value, ((result+512)>>10));
00572 }
00573 }
00574
00575 if ((dy&1) == 1)
00576 {
00577 for (j = 0; j < ver_block_size; j++)
00578 {
00579 tmp_line = tmp_res[j + 2 + (dy>>1)];
00580 orig_line = block[j];
00581 for (i = 0; i < hor_block_size; i++)
00582 {
00583 *orig_line = (imgpel) ((*orig_line + iClip1(max_imgpel_value, ((*(tmp_line++) + 16) >> 5)) + 1 )>>1);
00584 orig_line++;
00585 }
00586 }
00587 }
00588 }
00589 else if (dy == 2)
00590 {
00591
00592 tmp_pos = y_pos - 2;
00593 for (j = 0; j < ver_block_size; j++)
00594 {
00595 p0 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00596 p1 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00597 p2 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00598 p3 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00599 p4 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00600 p5 = cur_imgY[iClip3(0, maxold_y, tmp_pos )];
00601
00602 tmp_pos -= 4;
00603
00604 for (i = 0; i < hor_block_size + 5; i++)
00605 {
00606 pres_x = iClip3(0,maxold_x, x_pos + i - 2);
00607 result = (p0[pres_x] + p5[pres_x])*COEF[0]
00608 + (p1[pres_x] + p4[pres_x])*COEF[1]
00609 + (p2[pres_x] + p3[pres_x])*COEF[2];
00610 tmp_res[j][i] = result;
00611 }
00612 }
00613
00614 for (j = 0; j < ver_block_size; j++)
00615 {
00616 orig_line = block[j];
00617 tmp_line = tmp_res[j];
00618 x0 = tmp_res[j];
00619 x1 = x0 + 1;
00620 x2 = x1 + 1;
00621 x3 = x2 + 1;
00622 x4 = x3 + 1;
00623 x5 = x4 + 1;
00624
00625 for (i = 0; i < hor_block_size; i++)
00626 {
00627 result = (*(x0++) + *(x5++)) * COEF[0]
00628 + (*(x1++) + *(x4++)) * COEF[1]
00629 + (*(x2++) + *(x3++)) * COEF[2];
00630
00631 *(orig_line++) = (imgpel) iClip1(max_imgpel_value, ((result + 512)>>10));
00632 }
00633 }
00634
00635 if ((dx&1) == 1)
00636 {
00637 for (j = 0; j < ver_block_size; j++)
00638 {
00639 tmp_line = &tmp_res[j][2 + (dx>>1)];
00640 orig_line = block[j];
00641 for (i = 0; i < hor_block_size; i++)
00642 {
00643 *orig_line = (imgpel) ((*orig_line + iClip1(max_imgpel_value, ((*(tmp_line++) + 16)>>5)) + 1)>> 1);
00644 orig_line++;
00645 }
00646 }
00647 }
00648 }
00649 else
00650 {
00651 tmp_pos = x_pos - 2;
00652 for (i = 0; i < hor_block_size; i++)
00653 {
00654 ipos_m2 = iClip3(0, maxold_x, tmp_pos++);
00655 ipos_m1 = iClip3(0, maxold_x, tmp_pos++);
00656 ipos = iClip3(0, maxold_x, tmp_pos++);
00657 ipos_p1 = iClip3(0, maxold_x, tmp_pos++);
00658 ipos_p2 = iClip3(0, maxold_x, tmp_pos++);
00659 ipos_p3 = iClip3(0, maxold_x, tmp_pos );
00660 tmp_pos -= 4;
00661
00662 for (j = 0; j < ver_block_size; j++)
00663 {
00664 cur_lineY = cur_imgY[iClip3(0,maxold_y,(dy == 1 ? y_pos+j : y_pos+j+1))];
00665
00666 result = (cur_lineY[ipos_m2] + cur_lineY[ipos_p3]) * COEF[0];
00667 result += (cur_lineY[ipos_m1] + cur_lineY[ipos_p2]) * COEF[1];
00668 result += (cur_lineY[ipos ] + cur_lineY[ipos_p1]) * COEF[2];
00669
00670 block[j][i] = (imgpel) iClip1(max_imgpel_value, ((result+16)>>5));
00671 }
00672 }
00673
00674 tmp_pos = y_pos - 2;
00675 for (j = 0; j < ver_block_size; j++)
00676 {
00677 p0 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00678 p1 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00679 p2 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00680 p3 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00681 p4 = cur_imgY[iClip3(0, maxold_y, tmp_pos++)];
00682 p5 = cur_imgY[iClip3(0, maxold_y, tmp_pos )];
00683
00684 tmp_pos -= 4;
00685 orig_line = block[j];
00686
00687 for (i = 0; i < hor_block_size; i++)
00688 {
00689 pres_x = dx == 1 ? x_pos+i : x_pos+i+1;
00690 pres_x = iClip3(0, maxold_x, pres_x);
00691
00692 result = (p0[pres_x] + p5[pres_x]) * COEF[0];
00693 result += (p1[pres_x] + p4[pres_x]) * COEF[1];
00694 result += (p2[pres_x] + p3[pres_x]) * COEF[2];
00695
00696 *orig_line = (imgpel) ((*orig_line + iClip1(max_imgpel_value, ((result+16)>>5)) + 1 ) >> 1);
00697 orig_line++;
00698 }
00699 }
00700 }
00701 }
00702 }
00703 }
00704
00705 void get_block_chroma(int decoder, int uv, StorablePicture* dec_picture, StorablePicture *curr_ref, int x_pos, int y_pos, int hor_block_size, int ver_block_size, ImageParameters *img, imgpel block[MB_BLOCK_SIZE][MB_BLOCK_SIZE])
00706 {
00707 int subpel_x = img->mb_cr_size_x == 8 ? 7 : 3;
00708 int subpel_y = img->mb_cr_size_y == 8 ? 7 : 3;
00709 int shiftpel_x = img->mb_cr_size_x == 8 ? 3 : 2;
00710 int shiftpel_y = img->mb_cr_size_y == 8 ? 3 : 2;
00711 int total_scale = shiftpel_x + shiftpel_y;
00712
00713 int dx = (x_pos & subpel_x);
00714 int dy = (y_pos & subpel_y);
00715 int dxcur = (subpel_x + 1 - dx);
00716 int dycur = (subpel_y + 1 - dy);
00717
00718 int w00 = dxcur * dycur;
00719 int w01 = dxcur * dy;
00720 int w10 = dx * dycur;
00721 int w11 = dx * dy;
00722
00723 int i, j;
00724 int maxold_x = dec_picture->size_x_cr - 1;
00725 int maxold_y = (dec_picture->motion.mb_field[img->current_mb_nr]) ? (dec_picture->size_y_cr >> 1) - 1 : dec_picture->size_y_cr - 1;
00726 int result;
00727
00728 static imgpel **cur_img, *blk_line;
00729 static imgpel *cur_line, *cur_line_p1;
00730 int tmp_pos;
00731 static int ipos, ipos_p1;
00732 int max_imgpel_value = img->max_imgpel_value_comp[uv + 1];
00733
00734 #if 0
00735 if (curr_ref == no_reference_picture && img->framepoc < img->recovery_poc)
00736 {
00737 printf("list[ref_frame] is equal to 'no reference picture' before RAP\n");
00738
00739
00740 for (j = 0; j < ver_block_size; j++)
00741 for (i = 0; i < hor_block_size; i++)
00742 block[j][i] = 128;
00743 return;
00744 }
00745 #endif
00746
00747 cur_img = curr_ref->p_dec_img[uv+1][decoder];
00748
00749 x_pos = x_pos >> shiftpel_x;
00750 y_pos = y_pos >> shiftpel_y;
00751
00752 if ((y_pos >= 0) && (y_pos < maxold_y - ver_block_size) && (x_pos >= 0) && (x_pos < maxold_x - hor_block_size))
00753 {
00754 if (dx == 0 && dy == 0)
00755 {
00756 for (j = 0; j < ver_block_size; j++)
00757 {
00758 memcpy(&(block[j][0]), &(cur_img[ y_pos + j ][x_pos]), hor_block_size * sizeof(imgpel));
00759 }
00760 }
00761 else if (dx == 0)
00762 {
00763 for (j = 0; j < ver_block_size; j++)
00764 {
00765 cur_line = &cur_img[y_pos + j ][x_pos];
00766 cur_line_p1 = &cur_img[y_pos + j + 1][x_pos];
00767 blk_line = block[j];
00768
00769 for (i = 0; i < hor_block_size; i++)
00770 {
00771 result = (w00 * *cur_line++ + w01 * *cur_line_p1++);
00772 *(blk_line++) = (imgpel) iClip1(max_imgpel_value, rshift_rnd_sf(result, total_scale));
00773 }
00774 }
00775 }
00776 else if (dy == 0)
00777 {
00778 for (j = 0; j < ver_block_size; j++)
00779 {
00780 cur_line = &cur_img[y_pos + j][x_pos];
00781 cur_line_p1 = cur_line + 1;
00782 blk_line = block[j];
00783
00784 for (i = 0; i < hor_block_size; i++)
00785 {
00786 result = (w00 * *cur_line++ + w10 * *cur_line_p1++);
00787 *(blk_line++) = (imgpel) iClip1(max_imgpel_value, rshift_rnd_sf(result, total_scale));
00788 }
00789 }
00790 }
00791 else
00792 {
00793 for (j = 0; j < ver_block_size; j++)
00794 {
00795 cur_line = &cur_img[y_pos + j ][x_pos];
00796 cur_line_p1 = &cur_img[y_pos + j + 1][x_pos];
00797 blk_line = block[j];
00798
00799 for (i = 0; i < hor_block_size; i++)
00800 {
00801 result = (w00 * *(cur_line++) + w01 * *(cur_line_p1++));
00802 result += (w10 * *(cur_line ) + w11 * *(cur_line_p1 ));
00803 *(blk_line++) = (imgpel) iClip1(max_imgpel_value, rshift_rnd_sf(result, total_scale));
00804 }
00805 }
00806 }
00807 }
00808 else
00809 {
00810 if (dx == 0 && dy == 0)
00811 {
00812 for (j = 0; j < ver_block_size; j++)
00813 {
00814 cur_line = cur_img[iClip3(0, maxold_y, y_pos + j)];
00815 blk_line = block[j];
00816 for (i = 0; i < hor_block_size; i++)
00817 {
00818 *(blk_line++) = cur_line[iClip3(0, maxold_x, x_pos + i )];
00819 }
00820 }
00821 }
00822 else if (dx == 0)
00823 {
00824 for (j = 0; j < ver_block_size; j++)
00825 {
00826 cur_line = cur_img[iClip3(0, maxold_y, y_pos + j)];
00827 cur_line_p1 = cur_img[iClip3(0, maxold_y, y_pos + j + 1)];
00828 tmp_pos = x_pos;
00829 blk_line = block[j];
00830
00831 for (i = 0; i < hor_block_size; i++)
00832 {
00833 ipos = iClip3(0, maxold_x, tmp_pos++);
00834
00835 result = (w00 * cur_line[ipos] + w01 * cur_line_p1[ipos]);
00836 *(blk_line++) = (imgpel) iClip1(max_imgpel_value, rshift_rnd_sf(result, total_scale));
00837 }
00838 }
00839 }
00840 else if (dy == 0)
00841 {
00842 for (j = 0; j < ver_block_size; j++)
00843 {
00844 cur_line = cur_img[iClip3(0, maxold_y, y_pos + j)];
00845 tmp_pos = x_pos;
00846 blk_line = block[j];
00847
00848 for (i = 0; i < hor_block_size; i++)
00849 {
00850 ipos = iClip3(0, maxold_x, tmp_pos++);
00851 ipos_p1 = iClip3(0, maxold_x, tmp_pos );
00852
00853 result = (w00 * cur_line[ipos ] + w10 * cur_line[ipos_p1]);
00854 *(blk_line++) = (imgpel)iClip1(max_imgpel_value, rshift_rnd_sf(result, total_scale));
00855 }
00856 }
00857 }
00858 else
00859 {
00860 for (j = 0; j < ver_block_size; j++)
00861 {
00862 cur_line = cur_img[iClip3(0, maxold_y, y_pos + j)];
00863 cur_line_p1 = cur_img[iClip3(0, maxold_y, y_pos + j + 1)];
00864 tmp_pos = x_pos;
00865 blk_line = block[j];
00866
00867 for (i = 0; i < hor_block_size; i++)
00868 {
00869 ipos = iClip3(0, maxold_x, tmp_pos++);
00870 ipos_p1 = iClip3(0, maxold_x, tmp_pos );
00871
00872 result = (
00873 w00 * cur_line [ipos ] +
00874 w10 * cur_line [ipos_p1] +
00875 w01 * cur_line_p1[ipos ] +
00876 w11 * cur_line_p1[ipos_p1]);
00877 *(blk_line++) = (imgpel) iClip1(max_imgpel_value, rshift_rnd_sf(result, total_scale));
00878 }
00879 }
00880 }
00881 }
00882 }
00883
00884 #if 0
00885 void intra_cr_decoding(Macroblock *currMB, int yuv, ImageParameters *img, int smb)
00886 {
00887 imgpel **curUV, *cur_img;
00888 int (*m7UV)[16], *m7;
00889 int uv;
00890 int b8,b4;
00891 int ioff, joff, ii, jj;
00892
00893 for(uv = 0; uv < 2; uv++)
00894 {
00895 Boolean lossless_qpprime = (Boolean) ((img->lossless_qpprime_flag == 1) &&((img->qp + dec_picture->chroma_qp_offset[uv] + img->bitdepth_chroma_qp_scale) == 0));
00896 itrans_4x4 = (!lossless_qpprime) ? itrans4x4 : itrans4x4_ls;
00897
00898 curUV = dec_picture->imgUV[uv];
00899 m7UV = img->mb_rres[uv+1];
00900 intrapred_chroma(img, currMB, uv);
00901
00902 if (!smb && (currMB->cbp >> 4))
00903 {
00904 for (b8 = 0; b8 < (img->num_uv_blocks); b8++)
00905 {
00906 for(b4 = 0; b4 < 4; b4++)
00907 {
00908 joff = subblk_offset_y[yuv][b8][b4];
00909 ioff = subblk_offset_x[yuv][b8][b4];
00910
00911 itrans_4x4(img, (ColorPlane) (uv + 1), ioff, joff);
00912
00913 for(jj=joff; jj<joff + 4;jj++)
00914 {
00915 cur_img = &curUV[img->pix_c_y+jj][img->pix_c_x + ioff];
00916 m7 = &m7UV[jj][ioff];
00917
00918 for(ii=0; ii<4;ii++)
00919 {
00920 *cur_img++ = (imgpel) *m7++;
00921 }
00922 }
00923 }
00924 }
00925 }
00926 else if ((currMB->cbp >> 4) == 0)
00927 {
00928 for (b8 = 0; b8 < (img->num_uv_blocks); b8++)
00929 {
00930 for(b4 = 0; b4 < 4; b4++)
00931 {
00932 joff = subblk_offset_y[yuv][b8][b4];
00933 ioff = subblk_offset_x[yuv][b8][b4];
00934
00935 for(jj = joff; jj < 4 + joff;jj++)
00936 memcpy(&(curUV[img->pix_c_y + jj][img->pix_c_x + ioff]), &(img->mb_pred[uv + 1][jj][ioff]), BLOCK_SIZE * sizeof(imgpel));
00937 }
00938 }
00939 }
00940 else
00941 {
00942 itrans_sp_cr(img, uv);
00943
00944 for (joff = 0; joff < 8; joff += 4)
00945 {
00946 for(ioff = 0; ioff < 8;ioff+=4)
00947 {
00948 itrans_4x4(img, (ColorPlane) (uv + 1), ioff, joff);
00949
00950 for(jj = joff; jj < joff + 4; jj++)
00951 for(ii = ioff; ii < ioff + 4; ii++)
00952 {
00953 curUV[img->pix_c_y+jj][ii + img->pix_c_x] = (imgpel) img->mb_rres[uv+1][jj][ii];
00954 }
00955 }
00956 }
00957 }
00958 }
00959 }
00960
00961 void prepare_direct_params(Macroblock *currMB, StorablePicture *dec_picture, ImageParameters *img, short pmvl0[2], short pmvl1[2],char *l0_rFrame, char *l1_rFrame)
00962 {
00963 char l0_rFrameL, l0_rFrameU, l0_rFrameUR;
00964 char l1_rFrameL, l1_rFrameU, l1_rFrameUR;
00965 PicMotionParams *motion = &dec_picture->motion;
00966
00967 PixelPos mb_a, mb_b, mb_d, mb_c;
00968
00969 get_neighbors(currMB, &mb_a, &mb_b, &mb_c, &mb_d, 0, 0, 16);
00970
00971 if (!img->MbaffFrameFlag)
00972 {
00973 l0_rFrameL = (char) (mb_a.available ? motion->ref_idx[LIST_0][mb_a.pos_y][mb_a.pos_x] : -1);
00974 l0_rFrameU = (char) (mb_b.available ? motion->ref_idx[LIST_0][mb_b.pos_y][mb_b.pos_x] : -1);
00975 l0_rFrameUR = (char) (mb_c.available ? motion->ref_idx[LIST_0][mb_c.pos_y][mb_c.pos_x] : -1);
00976
00977 l1_rFrameL = (char) (mb_a.available ? motion->ref_idx[LIST_1][mb_a.pos_y][mb_a.pos_x] : -1);
00978 l1_rFrameU = (char) (mb_b.available ? motion->ref_idx[LIST_1][mb_b.pos_y][mb_b.pos_x] : -1);
00979 l1_rFrameUR = (char) (mb_c.available ? motion->ref_idx[LIST_1][mb_c.pos_y][mb_c.pos_x] : -1);
00980 }
00981 else
00982 {
00983 if (currMB->mb_field)
00984 {
00985 l0_rFrameL = (char) (mb_a.available
00986 ? img->mb_data[mb_a.mb_addr].mb_field || motion->ref_idx[LIST_0][mb_a.pos_y][mb_a.pos_x] < 0
00987 ? motion->ref_idx[LIST_0][mb_a.pos_y][mb_a.pos_x]
00988 : motion->ref_idx[LIST_0][mb_a.pos_y][mb_a.pos_x] * 2: -1);
00989
00990 l0_rFrameU = (char) (mb_b.available
00991 ? img->mb_data[mb_b.mb_addr].mb_field || motion->ref_idx[LIST_0][mb_b.pos_y][mb_b.pos_x] < 0
00992 ? motion->ref_idx[LIST_0][mb_b.pos_y][mb_b.pos_x]
00993 : motion->ref_idx[LIST_0][mb_b.pos_y][mb_b.pos_x] * 2: -1);
00994
00995 l0_rFrameUR = (char) (mb_c.available
00996 ? img->mb_data[mb_c.mb_addr].mb_field || motion->ref_idx[LIST_0][mb_c.pos_y][mb_c.pos_x] < 0
00997 ? motion->ref_idx[LIST_0][mb_c.pos_y][mb_c.pos_x]
00998 : motion->ref_idx[LIST_0][mb_c.pos_y][mb_c.pos_x] * 2: -1);
00999
01000 l1_rFrameL = (char) (mb_a.available
01001 ? img->mb_data[mb_a.mb_addr].mb_field || motion->ref_idx[LIST_1][mb_a.pos_y][mb_a.pos_x] < 0
01002 ? motion->ref_idx[LIST_1][mb_a.pos_y][mb_a.pos_x]
01003 : motion->ref_idx[LIST_1][mb_a.pos_y][mb_a.pos_x] * 2: -1);
01004
01005 l1_rFrameU = (char) (mb_b.available
01006 ? img->mb_data[mb_b.mb_addr].mb_field || motion->ref_idx[LIST_1][mb_b.pos_y][mb_b.pos_x] < 0
01007 ? motion->ref_idx[LIST_1][mb_b.pos_y][mb_b.pos_x]
01008 : motion->ref_idx[LIST_1][mb_b.pos_y][mb_b.pos_x] * 2: -1);
01009
01010 l1_rFrameUR = (char) (mb_c.available
01011 ? img->mb_data[mb_c.mb_addr].mb_field || motion->ref_idx[LIST_1][mb_c.pos_y][mb_c.pos_x] < 0
01012 ? motion->ref_idx[LIST_1][mb_c.pos_y][mb_c.pos_x]
01013 : motion->ref_idx[LIST_1][mb_c.pos_y][mb_c.pos_x] * 2: -1);
01014 }
01015 else
01016 {
01017 l0_rFrameL = (char) (mb_a.available
01018 ? img->mb_data[mb_a.mb_addr].mb_field || motion->ref_idx[LIST_0][mb_a.pos_y][mb_a.pos_x] < 0
01019 ? motion->ref_idx[LIST_0][mb_a.pos_y][mb_a.pos_x] >> 1
01020 : motion->ref_idx[LIST_0][mb_a.pos_y][mb_a.pos_x]: -1);
01021
01022 l0_rFrameU = (char) (mb_b.available
01023 ? img->mb_data[mb_b.mb_addr].mb_field || motion->ref_idx[LIST_0][mb_b.pos_y][mb_b.pos_x] < 0
01024 ? motion->ref_idx[LIST_0][mb_b.pos_y][mb_b.pos_x] >> 1
01025 : motion->ref_idx[LIST_0][mb_b.pos_y][mb_b.pos_x] : -1);
01026
01027 l0_rFrameUR = (char) (mb_c.available
01028 ? img->mb_data[mb_c.mb_addr].mb_field || motion->ref_idx[LIST_0][mb_c.pos_y][mb_c.pos_x] < 0
01029 ? motion->ref_idx[LIST_0][mb_c.pos_y][mb_c.pos_x] >> 1
01030 : motion->ref_idx[LIST_0][mb_c.pos_y][mb_c.pos_x] : -1);
01031
01032 l1_rFrameL = (char) (mb_a.available
01033 ? img->mb_data[mb_a.mb_addr].mb_field || motion->ref_idx[LIST_1][mb_a.pos_y][mb_a.pos_x] < 0
01034 ? motion->ref_idx[LIST_1][mb_a.pos_y][mb_a.pos_x] >> 1
01035 : motion->ref_idx[LIST_1][mb_a.pos_y][mb_a.pos_x] : -1);
01036
01037 l1_rFrameU = (char) (mb_b.available
01038 ? img->mb_data[mb_b.mb_addr].mb_field || motion->ref_idx[LIST_1][mb_b.pos_y][mb_b.pos_x] < 0
01039 ? motion->ref_idx[LIST_1][mb_b.pos_y][mb_b.pos_x] >> 1
01040 : motion->ref_idx[LIST_1][mb_b.pos_y][mb_b.pos_x] : -1);
01041
01042 l1_rFrameUR = (char) (mb_c.available
01043 ? img->mb_data[mb_c.mb_addr].mb_field || motion->ref_idx[LIST_1][mb_c.pos_y][mb_c.pos_x] < 0
01044 ? motion->ref_idx[LIST_1][mb_c.pos_y][mb_c.pos_x] >> 1
01045 : motion->ref_idx[LIST_1][mb_c.pos_y][mb_c.pos_x] : -1);
01046 }
01047 }
01048
01049 *l0_rFrame = (char) ((l0_rFrameL >= 0 && l0_rFrameU >= 0) ? imin(l0_rFrameL,l0_rFrameU) : imax(l0_rFrameL,l0_rFrameU));
01050 *l0_rFrame = (char) ((*l0_rFrame >= 0 && l0_rFrameUR >= 0) ? imin(*l0_rFrame,l0_rFrameUR): imax(*l0_rFrame,l0_rFrameUR));
01051
01052 *l1_rFrame = (char) ((l1_rFrameL >= 0 && l1_rFrameU >= 0) ? imin(l1_rFrameL,l1_rFrameU) : imax(l1_rFrameL,l1_rFrameU));
01053 *l1_rFrame = (char) ((*l1_rFrame >= 0 && l1_rFrameUR >= 0) ? imin(*l1_rFrame,l1_rFrameUR): imax(*l1_rFrame,l1_rFrameUR));
01054
01055 if (*l0_rFrame >=0)
01056 GetMotionVectorPredictor (currMB, &mb_a, &mb_b, &mb_c, pmvl0, *l0_rFrame, motion->ref_idx[LIST_0], motion->mv[LIST_0], 0, 0, 16, 16);
01057
01058 if (*l1_rFrame >=0)
01059 GetMotionVectorPredictor (currMB, &mb_a, &mb_b, &mb_c, pmvl1, *l1_rFrame, motion->ref_idx[LIST_1], motion->mv[LIST_1], 0, 0, 16, 16);
01060 }
01061
01062
01063 void check_motion_vector_range(ImageParameters *img, short mv_x, short mv_y)
01064 {
01065 if (mv_x > 8191 || mv_x < -8192)
01066 {
01067 fprintf(stderr,"ERROR! Horizontal motion vector %d is out of allowed range {-8192, 8191} in picture %d, macroblock %d\n", mv_x, img->number, img->current_mb_nr);
01068 error("invalid stream: too big horizontal motion vector", 500);
01069 }
01070
01071 if (mv_y > (img->max_mb_vmv_r - 1) || mv_y < (-img->max_mb_vmv_r))
01072 {
01073 fprintf(stderr,"ERROR! Vertical motion vector %d is out of allowed range {%d, %d} in picture %d, macroblock %d\n", mv_y, (-img->max_mb_vmv_r), (img->max_mb_vmv_r - 1), img->number, img->current_mb_nr);
01074 error("invalid stream: too big vertical motion vector", 500);
01075 }
01076 }
01077 #endif
01078
01079 void perform_mc(int decoder, ColorPlane pl, StorablePicture *dec_picture, ImageParameters *img, Macroblock* currMB, int pred_dir, int l0_mode, int l1_mode, char*** ref_idx_buf, int i, int j, int block_size_x, int block_size_y, short bipred_me)
01080 {
01081 static int vec1_x=0, vec1_y=0;
01082 static int vec2_x=0, vec2_y=0;
01083
01084 static int alpha_l0, alpha_l1, wp_off;
01085 int max_imgpel_value = img->max_imgpel_value_comp[pl];
01086 int apply_weights = ( (active_pps->weighted_pred_flag && (img->type== P_SLICE || img->type == SP_SLICE)) ||
01087 (active_pps->weighted_bipred_idc && (img->type== B_SLICE)));
01088 static const int mv_mul = 16;
01089
01090 int i4 = img->block_x + i;
01091 int j4 = img->block_y + j;
01092 int ioff = (i << 2);
01093 int joff = (j << 2);
01094
01095 assert (pred_dir<=2);
01096
01097 if (pred_dir != 2)
01098 {
01099
01100 short ref_idx = ref_idx_buf[pred_dir][j4][i4];
01101 short ref_idx_wp = ref_idx;
01102 short ***mv_array = img->all_mv[pred_dir][ref_idx][l0_mode];
01103 StorablePicture **list = listX[currMB->list_offset + pred_dir];
01104
01105 vec1_x = i4 * mv_mul + mv_array[j][i][0];
01106
01107 vec1_y = j4 * mv_mul + mv_array[j][i][1];
01108
01109 get_block_luma (decoder, pl, dec_picture, list[ref_idx], vec1_x, vec1_y, block_size_x, block_size_y, img, tmp_block_l0);
01110
01111 if (apply_weights)
01112 {
01113 if (currMB->mb_field)
01114 {
01115 ref_idx_wp >>=1;
01116 }
01117 alpha_l0 = wp_weight[pred_dir][ref_idx_wp][0];
01118 wp_off = wp_offset[pred_dir][ref_idx_wp][0];
01119
01120 weighted_mc_prediction(&decs->dec_mb_pred[decoder][joff], block_size_y, block_size_x, ioff, tmp_block_l0, alpha_l0, wp_off, luma_log_weight_denom, max_imgpel_value);
01121 }
01122 else
01123 {
01124 mc_prediction(&decs->dec_mb_pred[decoder][joff], block_size_y, block_size_x, ioff, tmp_block_l0);
01125 }
01126
01127 #if 0
01128 if ((dec_picture->chroma_format_idc != YUV400) && (dec_picture->chroma_format_idc != YUV444) )
01129 {
01130 int uv;
01131
01132 int ioff_cr = (img->mb_cr_size_x == MB_BLOCK_SIZE) ? ioff : ioff >> 1;
01133 int joff_cr = (img->mb_cr_size_y == MB_BLOCK_SIZE) ? joff : joff >> 1;
01134 int block_size_x_cr = img->mb_cr_size_x == MB_BLOCK_SIZE ? block_size_x : block_size_x >> 1;
01135 int block_size_y_cr = img->mb_cr_size_y == MB_BLOCK_SIZE ? block_size_y : block_size_y >> 1;
01136
01137 vec1_y_cr = vec1_y + ((active_sps->chroma_format_idc == 1)? list[ref_idx]->chroma_vector_adjustment : 0);
01138
01139 for(uv=0;uv<2;uv++)
01140 {
01141 get_block_chroma (uv, list[ref_idx], vec1_x, vec1_y_cr, block_size_x_cr, block_size_y_cr, img, tmp_block_l0);
01142
01143 if (img->apply_weights)
01144 {
01145 alpha_l0 = img->wp_weight[pred_dir][ref_idx_wp][uv + 1];
01146 wp_offset = img->wp_offset[pred_dir][ref_idx_wp][uv + 1];
01147
01148 weighted_mc_prediction(&img->mb_pred[uv + 1][joff_cr], block_size_y_cr, block_size_x_cr, ioff_cr, tmp_block_l0, alpha_l0, wp_offset, img->chroma_log2_weight_denom, img->max_imgpel_value_comp[uv + 1]);
01149 }
01150 else
01151 {
01152 mc_prediction(&img->mb_pred[uv + 1][joff_cr], block_size_y_cr, block_size_x_cr, ioff_cr, tmp_block_l0);
01153 }
01154 }
01155 }
01156 #endif
01157 }
01158 else
01159 {
01160
01161 short l0_ref = ref_idx_buf[LIST_0][j4][i4];
01162 short l1_ref = ref_idx_buf[LIST_1][j4][i4];
01163
01164 short ***l0_mv_array = (bipred_me ? img->bipred_mv[bipred_me-1][LIST_0][l0_ref][l0_mode]:img->all_mv[LIST_0][l0_ref][l0_mode]);
01165 short ***l1_mv_array = (bipred_me ? img->bipred_mv[bipred_me-1][LIST_1][l1_ref][l1_mode]:img->all_mv[LIST_1][l1_ref][l1_mode]);
01166
01167 vec1_x = i4 * mv_mul + l0_mv_array[j][i][0];
01168 vec2_x = i4 * mv_mul + l1_mv_array[j][i][0];
01169
01170 vec1_y = j4 * mv_mul + l0_mv_array[j][i][1];
01171 vec2_y = j4 * mv_mul + l1_mv_array[j][i][1];
01172
01173 get_block_luma (decoder, pl, dec_picture, listX[LIST_0 + currMB->list_offset][l0_ref], vec1_x, vec1_y, block_size_x, block_size_y, img, tmp_block_l0);
01174 get_block_luma (decoder, pl, dec_picture, listX[LIST_1 + currMB->list_offset][l1_ref], vec2_x, vec2_y, block_size_x, block_size_y, img, tmp_block_l1);
01175
01176 if(apply_weights)
01177 {
01178 int wt_list_offset = (active_pps->weighted_bipred_idc==2)? currMB->list_offset : 0;
01179
01180
01181
01182 if (currMB->mb_field)
01183 {
01184 l0_ref >>=1;
01185 l1_ref >>=1;
01186 }
01187
01188 alpha_l0 = wbp_weight[LIST_0 + wt_list_offset][l0_ref][l1_ref][0];
01189 alpha_l1 = wbp_weight[LIST_1 + wt_list_offset][l0_ref][l1_ref][0];
01190 wp_off = ((wp_offset [LIST_0 + wt_list_offset][l0_ref][0] + wp_offset[LIST_1 + wt_list_offset][l1_ref][0] + 1) >>1);
01191
01192 weighted_bi_prediction(&decs->dec_mb_pred[decoder][joff], tmp_block_l0, tmp_block_l1, block_size_y, block_size_x, ioff, alpha_l0, alpha_l1, wp_off, (luma_log_weight_denom + 1), max_imgpel_value);
01193 }
01194 else
01195 {
01196 bi_prediction(&decs->dec_mb_pred[decoder][joff], tmp_block_l0, tmp_block_l1, block_size_y, block_size_x, ioff);
01197 }
01198 #if 0
01199 if ((dec_picture->chroma_format_idc != YUV400) && (dec_picture->chroma_format_idc != YUV444) )
01200 {
01201 int uv;
01202
01203 int ioff_cr = img->mb_cr_size_x == MB_BLOCK_SIZE ? ioff : ioff >> 1;
01204 int joff_cr = img->mb_cr_size_y == MB_BLOCK_SIZE ? joff : joff >> 1;
01205 int block_size_x_cr = img->mb_cr_size_x == MB_BLOCK_SIZE ? block_size_x : block_size_x >> 1;
01206 int block_size_y_cr = img->mb_cr_size_y == MB_BLOCK_SIZE ? block_size_y : block_size_y >> 1;
01207
01208 vec1_y_cr = vec1_y + ((active_sps->chroma_format_idc == 1)? listX[LIST_0 + list_offset][l0_refframe]->chroma_vector_adjustment : 0);
01209 vec2_y_cr = vec2_y + ((active_sps->chroma_format_idc == 1)? listX[LIST_1 + list_offset][l1_refframe]->chroma_vector_adjustment : 0);
01210
01211 for(uv=0;uv<2;uv++)
01212 {
01213 get_block_chroma (uv, listX[LIST_0 + list_offset][l0_refframe], vec1_x, vec1_y_cr, block_size_x_cr, block_size_y_cr, img, tmp_block_l0);
01214 get_block_chroma (uv, listX[LIST_1 + list_offset][l1_refframe], vec2_x, vec2_y_cr, block_size_x_cr, block_size_y_cr, img, tmp_block_l1);
01215
01216 if(img->apply_weights)
01217 {
01218 int wt_list_offset = (active_pps->weighted_bipred_idc==2)? list_offset : 0;
01219
01220 alpha_l0 = img->wbp_weight[LIST_0 + wt_list_offset][l0_ref_idx][l1_ref_idx][uv + 1];
01221 alpha_l1 = img->wbp_weight[LIST_1 + wt_list_offset][l0_ref_idx][l1_ref_idx][uv + 1];
01222 wp_offset = ((img->wp_offset [LIST_0 + wt_list_offset][l0_ref_idx][uv + 1] + img->wp_offset[LIST_1 + wt_list_offset][l1_ref_idx][uv + 1] + 1) >>1);
01223
01224 weighted_bi_prediction(&img->mb_pred[uv+1][joff_cr], tmp_block_l0, tmp_block_l1, block_size_y_cr, block_size_x_cr, ioff_cr, alpha_l0, alpha_l1, wp_offset, (img->chroma_log2_weight_denom + 1), img->max_imgpel_value_comp[uv + 1]);
01225 }
01226 else
01227 {
01228 bi_prediction(&img->mb_pred[uv + 1][joff_cr], tmp_block_l0, tmp_block_l1, block_size_y_cr, block_size_x_cr, ioff_cr);
01229 }
01230 }
01231 }
01232 #endif
01233 }
01234 }
01235
01236 void perform_mc_concealment(int decoder, ColorPlane pl, StorablePicture *dec_picture, ImageParameters *img, Macroblock* currMB, int pred_dir, int l0_mode, int l1_mode, char*** ref_idx_buf, int i, int j, int block_size_x, int block_size_y)
01237 {
01238 static int vec1_x=0, vec1_y=0;
01239 static int vec2_x=0, vec2_y=0;
01240
01241 static int alpha_l0, alpha_l1, wp_off;
01242 int max_imgpel_value = img->max_imgpel_value_comp[pl];
01243 int apply_weights = ( (active_pps->weighted_pred_flag && (img->type== P_SLICE || img->type == SP_SLICE)) ||
01244 (active_pps->weighted_bipred_idc && (img->type== B_SLICE)));
01245 static const int mv_mul = 16;
01246
01247 int i4 = img->block_x + i;
01248 int j4 = img->block_y + j;
01249 int ioff = (i << 2);
01250 int joff = (j << 2);
01251
01252 assert (pred_dir<=2);
01253
01254 if (pred_dir != 2)
01255 {
01256
01257 short ref_idx = ref_idx_buf[pred_dir][j4][i4];
01258 short ref_idx_wp = ref_idx;
01259 short ***mv_array = dec_picture->motion.mv[pred_dir];
01260 StorablePicture **list = listX[currMB->list_offset + pred_dir];
01261
01262 vec1_x = i4 * mv_mul + mv_array[j4][i4][0];
01263
01264 vec1_y = j4 * mv_mul + mv_array[j4][i4][1];
01265
01266 get_block_luma (decoder, pl, dec_picture, list[ref_idx], vec1_x, vec1_y, block_size_x, block_size_y, img, tmp_block_l0);
01267
01268 if (apply_weights)
01269 {
01270 if (currMB->mb_field)
01271 {
01272 ref_idx_wp >>=1;
01273 }
01274 alpha_l0 = wp_weight[pred_dir][ref_idx_wp][0];
01275 wp_off = wp_offset[pred_dir][ref_idx_wp][0];
01276
01277 weighted_mc_prediction(&decs->dec_mb_pred[decoder][joff], block_size_y, block_size_x, ioff, tmp_block_l0, alpha_l0, wp_off, luma_log_weight_denom, max_imgpel_value);
01278 }
01279 else
01280 {
01281 mc_prediction(&decs->dec_mb_pred[decoder][joff], block_size_y, block_size_x, ioff, tmp_block_l0);
01282 }
01283 }
01284 else
01285 {
01286
01287 short l0_ref = ref_idx_buf[LIST_0][j4][i4];
01288 short l1_ref = ref_idx_buf[LIST_1][j4][i4];
01289
01290 short ***l0_mv_array = dec_picture->motion.mv[LIST_0];
01291 short ***l1_mv_array = dec_picture->motion.mv[LIST_1];
01292
01293 vec1_x = i4 * mv_mul + l0_mv_array[j4][i4][0];
01294 vec2_x = i4 * mv_mul + l1_mv_array[j4][i4][0];
01295
01296 vec1_y = j4 * mv_mul + l0_mv_array[j4][i4][1];
01297 vec2_y = j4 * mv_mul + l1_mv_array[j4][i4][1];
01298
01299 get_block_luma (decoder, pl, dec_picture, listX[LIST_0 + currMB->list_offset][l0_ref], vec1_x, vec1_y, block_size_x, block_size_y, img, tmp_block_l0);
01300 get_block_luma (decoder, pl, dec_picture, listX[LIST_1 + currMB->list_offset][l1_ref], vec2_x, vec2_y, block_size_x, block_size_y, img, tmp_block_l1);
01301
01302 if(apply_weights)
01303 {
01304 int wt_list_offset = (active_pps->weighted_bipred_idc==2)? currMB->list_offset : 0;
01305
01306
01307
01308 if (currMB->mb_field)
01309 {
01310 l0_ref >>=1;
01311 l1_ref >>=1;
01312 }
01313
01314 alpha_l0 = wbp_weight[LIST_0 + wt_list_offset][l0_ref][l1_ref][0];
01315 alpha_l1 = wbp_weight[LIST_1 + wt_list_offset][l0_ref][l1_ref][0];
01316 wp_off = ((wp_offset [LIST_0 + wt_list_offset][l0_ref][0] + wp_offset[LIST_1 + wt_list_offset][l1_ref][0] + 1) >>1);
01317
01318 weighted_bi_prediction(&decs->dec_mb_pred[decoder][joff], tmp_block_l0, tmp_block_l1, block_size_y, block_size_x, ioff, alpha_l0, alpha_l1, wp_off, (luma_log_weight_denom + 1), max_imgpel_value);
01319 }
01320 else
01321 {
01322 bi_prediction(&decs->dec_mb_pred[decoder][joff], tmp_block_l0, tmp_block_l1, block_size_y, block_size_x, ioff);
01323 }
01324 }
01325 }