00001
00015 #include "global.h"
00016 #include "intra4x4_pred.h"
00017 #include "mb_access.h"
00018 #include "image.h"
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032 #define P_X (PredPel[0])
00033 #define P_A (PredPel[1])
00034 #define P_B (PredPel[2])
00035 #define P_C (PredPel[3])
00036 #define P_D (PredPel[4])
00037 #define P_E (PredPel[5])
00038 #define P_F (PredPel[6])
00039 #define P_G (PredPel[7])
00040 #define P_H (PredPel[8])
00041 #define P_I (PredPel[9])
00042 #define P_J (PredPel[10])
00043 #define P_K (PredPel[11])
00044 #define P_L (PredPel[12])
00045
00046
00057 static inline int intra4x4_dc_pred(ImageParameters *img,
00058 Macroblock *currMB,
00059 ColorPlane pl,
00060 int ioff,
00061 int joff)
00062 {
00063 int i,j;
00064 int s0 = 0;
00065 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00066
00067 PixelPos pix_a[4], pix_b;
00068
00069 int block_available_up;
00070 int block_available_left;
00071
00072 imgpel **mb_pred = img->mb_pred[pl];
00073
00074 for (i=0;i<4;i++)
00075 {
00076 getNeighbour(currMB, ioff - 1, joff + i, img->mb_size[IS_LUMA], &pix_a[i]);
00077 }
00078 getNeighbour(currMB, ioff , joff -1 , img->mb_size[IS_LUMA], &pix_b);
00079
00080 if (active_pps->constrained_intra_pred_flag)
00081 {
00082 for (i=0, block_available_left=1; i<4;i++)
00083 block_available_left &= pix_a[i].available ? img->intra_block[pix_a[i].mb_addr]: 0;
00084 block_available_up = pix_b.available ? img->intra_block [pix_b.mb_addr] : 0;
00085 }
00086 else
00087 {
00088 block_available_left = pix_a[0].available;
00089 block_available_up = pix_b.available;
00090 }
00091
00092
00093 if (block_available_up)
00094 {
00095 s0 += imgY[pix_b.pos_y][pix_b.pos_x + 0];
00096 s0 += imgY[pix_b.pos_y][pix_b.pos_x + 1];
00097 s0 += imgY[pix_b.pos_y][pix_b.pos_x + 2];
00098 s0 += imgY[pix_b.pos_y][pix_b.pos_x + 3];
00099 }
00100
00101 if (block_available_left)
00102 {
00103 s0 += imgY[pix_a[0].pos_y][pix_a[0].pos_x];
00104 s0 += imgY[pix_a[1].pos_y][pix_a[1].pos_x];
00105 s0 += imgY[pix_a[2].pos_y][pix_a[2].pos_x];
00106 s0 += imgY[pix_a[3].pos_y][pix_a[3].pos_x];
00107 }
00108
00109 if (block_available_up && block_available_left)
00110 {
00111
00112 s0 = (s0 + 4)>>3;
00113 }
00114 else if (!block_available_up && block_available_left)
00115 {
00116
00117 s0 = (s0 + 2)>>2;
00118 }
00119 else if (block_available_up && !block_available_left)
00120 {
00121
00122 s0 = (s0 + 2)>>2;
00123 }
00124 else
00125 {
00126
00127 s0 = img->dc_pred_value_comp[pl];
00128 }
00129
00130 for (j=joff; j < joff + BLOCK_SIZE; j++)
00131 {
00132 for (i=ioff; i < ioff + BLOCK_SIZE; i++)
00133 {
00134
00135 mb_pred[j][i] = (imgpel) s0;
00136 }
00137 }
00138 return DECODING_OK;
00139 }
00140
00151 static inline int intra4x4_vert_pred(ImageParameters *img,
00152 Macroblock *currMB,
00153 ColorPlane pl,
00154 int ioff,
00155 int joff)
00156 {
00157 int j;
00158 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00159
00160 int block_available_up;
00161
00162 PixelPos pix_b;
00163
00164 imgpel **mb_pred = img->mb_pred[pl];
00165
00166 getNeighbour(currMB, ioff, joff - 1 , img->mb_size[IS_LUMA], &pix_b);
00167
00168 if (active_pps->constrained_intra_pred_flag)
00169 {
00170 block_available_up = pix_b.available ? img->intra_block [pix_b.mb_addr] : 0;
00171 }
00172 else
00173 {
00174 block_available_up = pix_b.available;
00175 }
00176
00177 if (!block_available_up)
00178 printf ("warning: Intra_4x4_Vertical prediction mode not allowed at mb %d\n", (int) img->current_mb_nr);
00179
00180 for(j = joff; j < joff + BLOCK_SIZE; j++)
00181 memcpy(&(mb_pred[j][ioff]), &(imgY[pix_b.pos_y][pix_b.pos_x]), BLOCK_SIZE * sizeof(imgpel));
00182
00183 return DECODING_OK;
00184 }
00185
00196 static inline int intra4x4_hor_pred(ImageParameters *img,
00197 Macroblock *currMB,
00198 ColorPlane pl,
00199 int ioff,
00200 int joff)
00201 {
00202 int i,j;
00203 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00204
00205 PixelPos pix_a[4];
00206
00207 int block_available_left;
00208
00209 imgpel *predrow, prediction, **mb_pred = img->mb_pred[pl];
00210
00211 for (i=0;i<4;i++)
00212 {
00213 getNeighbour(currMB, ioff -1 , joff +i , img->mb_size[IS_LUMA], &pix_a[i]);
00214 }
00215
00216 if (active_pps->constrained_intra_pred_flag)
00217 {
00218 for (i=0, block_available_left=1; i<4;i++)
00219 block_available_left &= pix_a[i].available ? img->intra_block[pix_a[i].mb_addr]: 0;
00220 }
00221 else
00222 {
00223 block_available_left = pix_a[0].available;
00224 }
00225
00226 if (!block_available_left)
00227 printf ("warning: Intra_4x4_Horizontal prediction mode not allowed at mb %d\n",(int) img->current_mb_nr);
00228
00229 for(j=0;j<BLOCK_SIZE;j++)
00230 {
00231 predrow = mb_pred[j+joff];
00232 prediction = imgY[pix_a[j].pos_y][pix_a[j].pos_x];
00233 for(i = ioff;i < ioff + BLOCK_SIZE;i++)
00234 predrow[i]= prediction;
00235 }
00236
00237 return DECODING_OK;
00238 }
00239
00250 static inline int intra4x4_diag_down_right_pred(ImageParameters *img,
00251 Macroblock *currMB,
00252 ColorPlane pl,
00253 int ioff,
00254 int joff)
00255 {
00256 int i;
00257 imgpel PredPel[13];
00258 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00259
00260 PixelPos pix_a[4];
00261 PixelPos pix_b, pix_d;
00262
00263 int block_available_up;
00264 int block_available_left;
00265 int block_available_up_left;
00266
00267 int jpos0 = joff, jpos1 = joff + 1, jpos2 = joff + 2, jpos3 = joff + 3;
00268 int ipos0 = ioff, ipos1 = ioff + 1, ipos2 = ioff + 2, ipos3 = ioff + 3;
00269 imgpel **mb_pred = img->mb_pred[pl];
00270
00271 for (i=0;i<4;i++)
00272 {
00273 getNeighbour(currMB, ioff -1 , joff +i , img->mb_size[IS_LUMA], &pix_a[i]);
00274 }
00275
00276 getNeighbour(currMB, ioff , joff -1 , img->mb_size[IS_LUMA], &pix_b);
00277 getNeighbour(currMB, ioff -1 , joff -1 , img->mb_size[IS_LUMA], &pix_d);
00278
00279 if (active_pps->constrained_intra_pred_flag)
00280 {
00281 for (i=0, block_available_left=1; i<4;i++)
00282 block_available_left &= pix_a[i].available ? img->intra_block[pix_a[i].mb_addr]: 0;
00283 block_available_up = pix_b.available ? img->intra_block [pix_b.mb_addr] : 0;
00284 block_available_up_left = pix_d.available ? img->intra_block [pix_d.mb_addr] : 0;
00285 }
00286 else
00287 {
00288 block_available_left = pix_a[0].available;
00289 block_available_up = pix_b.available;
00290 block_available_up_left = pix_d.available;
00291 }
00292
00293 if ((!block_available_up)||(!block_available_left)||(!block_available_up_left))
00294 printf ("warning: Intra_4x4_Diagonal_Down_Right prediction mode not allowed at mb %d\n",(int) img->current_mb_nr);
00295
00296
00297 P_A = imgY[pix_b.pos_y][pix_b.pos_x + 0];
00298 P_B = imgY[pix_b.pos_y][pix_b.pos_x + 1];
00299 P_C = imgY[pix_b.pos_y][pix_b.pos_x + 2];
00300 P_D = imgY[pix_b.pos_y][pix_b.pos_x + 3];
00301
00302 P_I = imgY[pix_a[0].pos_y][pix_a[0].pos_x];
00303 P_J = imgY[pix_a[1].pos_y][pix_a[1].pos_x];
00304 P_K = imgY[pix_a[2].pos_y][pix_a[2].pos_x];
00305 P_L = imgY[pix_a[3].pos_y][pix_a[3].pos_x];
00306
00307 P_X = imgY[pix_d.pos_y][pix_d.pos_x];
00308
00309 mb_pred[jpos3][ipos0] = (imgpel) ((P_L + 2*P_K + P_J + 2) >> 2);
00310 mb_pred[jpos2][ipos0] =
00311 mb_pred[jpos3][ipos1] = (imgpel) ((P_K + 2*P_J + P_I + 2) >> 2);
00312 mb_pred[jpos1][ipos0] =
00313 mb_pred[jpos2][ipos1] =
00314 mb_pred[jpos3][ipos2] = (imgpel) ((P_J + 2*P_I + P_X + 2) >> 2);
00315 mb_pred[jpos0][ipos0] =
00316 mb_pred[jpos1][ipos1] =
00317 mb_pred[jpos2][ipos2] =
00318 mb_pred[jpos3][ipos3] = (imgpel) ((P_I + 2*P_X + P_A + 2) >> 2);
00319 mb_pred[jpos0][ipos1] =
00320 mb_pred[jpos1][ipos2] =
00321 mb_pred[jpos2][ipos3] = (imgpel) ((P_X + 2*P_A + P_B + 2) >> 2);
00322 mb_pred[jpos0][ipos2] =
00323 mb_pred[jpos1][ipos3] = (imgpel) ((P_A + 2*P_B + P_C + 2) >> 2);
00324 mb_pred[jpos0][ipos3] = (imgpel) ((P_B + 2*P_C + P_D + 2) >> 2);
00325
00326 return DECODING_OK;
00327 }
00328
00339 static inline int intra4x4_diag_down_left_pred(ImageParameters *img,
00340 Macroblock *currMB,
00341 ColorPlane pl,
00342 int ioff,
00343 int joff)
00344 {
00345 imgpel PredPel[13];
00346 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00347
00348 PixelPos pix_b, pix_c;
00349
00350 int block_available_up;
00351 int block_available_up_right;
00352
00353 int jpos0 = joff, jpos1 = joff + 1, jpos2 = joff + 2, jpos3 = joff + 3;
00354 int ipos0 = ioff, ipos1 = ioff + 1, ipos2 = ioff + 2, ipos3 = ioff + 3;
00355 imgpel **mb_pred = img->mb_pred[pl];
00356
00357 getNeighbour(currMB, ioff , joff - 1, img->mb_size[IS_LUMA], &pix_b);
00358 getNeighbour(currMB, ioff + 4, joff - 1, img->mb_size[IS_LUMA], &pix_c);
00359
00360 pix_c.available = pix_c.available && !((ioff==4) && ((joff==4)||(joff==12)));
00361
00362 if (active_pps->constrained_intra_pred_flag)
00363 {
00364 block_available_up = pix_b.available ? img->intra_block [pix_b.mb_addr] : 0;
00365 block_available_up_right = pix_c.available ? img->intra_block [pix_c.mb_addr] : 0;
00366 }
00367 else
00368 {
00369 block_available_up = pix_b.available;
00370 block_available_up_right = pix_c.available;
00371 }
00372
00373 if (!block_available_up)
00374 printf ("warning: Intra_4x4_Diagonal_Down_Left prediction mode not allowed at mb %d\n", (int) img->current_mb_nr);
00375
00376
00377 P_A = imgY[pix_b.pos_y][pix_b.pos_x + 0];
00378 P_B = imgY[pix_b.pos_y][pix_b.pos_x + 1];
00379 P_C = imgY[pix_b.pos_y][pix_b.pos_x + 2];
00380 P_D = imgY[pix_b.pos_y][pix_b.pos_x + 3];
00381
00382 if (block_available_up_right)
00383 {
00384 P_E = imgY[pix_c.pos_y][pix_c.pos_x + 0];
00385 P_F = imgY[pix_c.pos_y][pix_c.pos_x + 1];
00386 P_G = imgY[pix_c.pos_y][pix_c.pos_x + 2];
00387 P_H = imgY[pix_c.pos_y][pix_c.pos_x + 3];
00388 }
00389 else
00390 {
00391 P_E = P_F = P_G = P_H = P_D;
00392 }
00393
00394 mb_pred[jpos0][ipos0] = (imgpel) ((P_A + P_C + 2*(P_B) + 2) >> 2);
00395 mb_pred[jpos0][ipos1] =
00396 mb_pred[jpos1][ipos0] = (imgpel) ((P_B + P_D + 2*(P_C) + 2) >> 2);
00397 mb_pred[jpos0][ipos2] =
00398 mb_pred[jpos1][ipos1] =
00399 mb_pred[jpos2][ipos0] = (imgpel) ((P_C + P_E + 2*(P_D) + 2) >> 2);
00400 mb_pred[jpos0][ipos3] =
00401 mb_pred[jpos1][ipos2] =
00402 mb_pred[jpos2][ipos1] =
00403 mb_pred[jpos3][ipos0] = (imgpel) ((P_D + P_F + 2*(P_E) + 2) >> 2);
00404 mb_pred[jpos1][ipos3] =
00405 mb_pred[jpos2][ipos2] =
00406 mb_pred[jpos3][ipos1] = (imgpel) ((P_E + P_G + 2*(P_F) + 2) >> 2);
00407 mb_pred[jpos2][ipos3] =
00408 mb_pred[jpos3][ipos2] = (imgpel) ((P_F + P_H + 2*(P_G) + 2) >> 2);
00409 mb_pred[jpos3][ipos3] = (imgpel) ((P_G + 3*(P_H) + 2) >> 2);
00410
00411 return DECODING_OK;
00412 }
00413
00424 static inline int intra4x4_vert_right_pred(ImageParameters *img,
00425 Macroblock *currMB,
00426 ColorPlane pl,
00427 int ioff,
00428 int joff)
00429 {
00430 int i;
00431 imgpel PredPel[13];
00432 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00433
00434 PixelPos pix_a[4];
00435 PixelPos pix_b, pix_d;
00436
00437 int block_available_up;
00438 int block_available_left;
00439 int block_available_up_left;
00440
00441 int jpos0 = joff, jpos1 = joff + 1, jpos2 = joff + 2, jpos3 = joff + 3;
00442 int ipos0 = ioff, ipos1 = ioff + 1, ipos2 = ioff + 2, ipos3 = ioff + 3;
00443 imgpel **mb_pred = img->mb_pred[pl];
00444
00445 for (i=0;i<4;i++)
00446 {
00447 getNeighbour(currMB, ioff -1 , joff +i , img->mb_size[IS_LUMA], &pix_a[i]);
00448 }
00449
00450 getNeighbour(currMB, ioff , joff -1 , img->mb_size[IS_LUMA], &pix_b);
00451 getNeighbour(currMB, ioff -1 , joff -1 , img->mb_size[IS_LUMA], &pix_d);
00452
00453 if (active_pps->constrained_intra_pred_flag)
00454 {
00455 for (i=0, block_available_left=1; i<4;i++)
00456 block_available_left &= pix_a[i].available ? img->intra_block[pix_a[i].mb_addr]: 0;
00457 block_available_up = pix_b.available ? img->intra_block [pix_b.mb_addr] : 0;
00458 block_available_up_left = pix_d.available ? img->intra_block [pix_d.mb_addr] : 0;
00459 }
00460 else
00461 {
00462 block_available_left = pix_a[0].available;
00463 block_available_up = pix_b.available;
00464 block_available_up_left = pix_d.available;
00465 }
00466
00467 if ((!block_available_up)||(!block_available_left)||(!block_available_up_left))
00468 printf ("warning: Intra_4x4_Vertical_Right prediction mode not allowed at mb %d\n", (int) img->current_mb_nr);
00469
00470
00471 P_A = imgY[pix_b.pos_y][pix_b.pos_x + 0];
00472 P_B = imgY[pix_b.pos_y][pix_b.pos_x + 1];
00473 P_C = imgY[pix_b.pos_y][pix_b.pos_x + 2];
00474 P_D = imgY[pix_b.pos_y][pix_b.pos_x + 3];
00475
00476 P_I = imgY[pix_a[0].pos_y][pix_a[0].pos_x];
00477 P_J = imgY[pix_a[1].pos_y][pix_a[1].pos_x];
00478 P_K = imgY[pix_a[2].pos_y][pix_a[2].pos_x];
00479 P_L = imgY[pix_a[3].pos_y][pix_a[3].pos_x];
00480
00481 P_X = imgY[pix_d.pos_y][pix_d.pos_x];
00482
00483 mb_pred[jpos0][ipos0] =
00484 mb_pred[jpos2][ipos1] = (imgpel) ((P_X + P_A + 1) >> 1);
00485 mb_pred[jpos0][ipos1] =
00486 mb_pred[jpos2][ipos2] = (imgpel) ((P_A + P_B + 1) >> 1);
00487 mb_pred[jpos0][ipos2] =
00488 mb_pred[jpos2][ipos3] = (imgpel) ((P_B + P_C + 1) >> 1);
00489 mb_pred[jpos0][ipos3] = (imgpel) ((P_C + P_D + 1) >> 1);
00490 mb_pred[jpos1][ipos0] =
00491 mb_pred[jpos3][ipos1] = (imgpel) ((P_I + 2*P_X + P_A + 2) >> 2);
00492 mb_pred[jpos1][ipos1] =
00493 mb_pred[jpos3][ipos2] = (imgpel) ((P_X + 2*P_A + P_B + 2) >> 2);
00494 mb_pred[jpos1][ipos2] =
00495 mb_pred[jpos3][ipos3] = (imgpel) ((P_A + 2*P_B + P_C + 2) >> 2);
00496 mb_pred[jpos1][ipos3] = (imgpel) ((P_B + 2*P_C + P_D + 2) >> 2);
00497 mb_pred[jpos2][ipos0] = (imgpel) ((P_X + 2*P_I + P_J + 2) >> 2);
00498 mb_pred[jpos3][ipos0] = (imgpel) ((P_I + 2*P_J + P_K + 2) >> 2);
00499
00500 return DECODING_OK;
00501 }
00502
00503
00514 static inline int intra4x4_vert_left_pred(ImageParameters *img,
00515 Macroblock *currMB,
00516 ColorPlane pl,
00517 int ioff,
00518 int joff)
00519 {
00520 imgpel PredPel[13];
00521 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00522
00523 PixelPos pix_b, pix_c;
00524
00525 int block_available_up;
00526 int block_available_up_right;
00527
00528 int jpos0 = joff, jpos1 = joff + 1, jpos2 = joff + 2, jpos3 = joff + 3;
00529 int ipos0 = ioff, ipos1 = ioff + 1, ipos2 = ioff + 2, ipos3 = ioff + 3;
00530 imgpel **mb_pred = img->mb_pred[pl];
00531
00532 getNeighbour(currMB, ioff , joff -1 , img->mb_size[IS_LUMA], &pix_b);
00533 getNeighbour(currMB, ioff +4 , joff -1 , img->mb_size[IS_LUMA], &pix_c);
00534
00535 pix_c.available = pix_c.available && !((ioff==4) && ((joff==4)||(joff==12)));
00536
00537 if (active_pps->constrained_intra_pred_flag)
00538 {
00539 block_available_up = pix_b.available ? img->intra_block [pix_b.mb_addr] : 0;
00540 block_available_up_right = pix_c.available ? img->intra_block [pix_c.mb_addr] : 0;
00541 }
00542 else
00543 {
00544 block_available_up = pix_b.available;
00545 block_available_up_right = pix_c.available;
00546 }
00547
00548
00549 if (!block_available_up)
00550 printf ("warning: Intra_4x4_Vertical_Left prediction mode not allowed at mb %d\n", (int) img->current_mb_nr);
00551
00552
00553 P_A = imgY[pix_b.pos_y][pix_b.pos_x + 0];
00554 P_B = imgY[pix_b.pos_y][pix_b.pos_x + 1];
00555 P_C = imgY[pix_b.pos_y][pix_b.pos_x + 2];
00556 P_D = imgY[pix_b.pos_y][pix_b.pos_x + 3];
00557
00558 if (block_available_up_right)
00559 {
00560 P_E = imgY[pix_c.pos_y][pix_c.pos_x + 0];
00561 P_F = imgY[pix_c.pos_y][pix_c.pos_x + 1];
00562 P_G = imgY[pix_c.pos_y][pix_c.pos_x + 2];
00563 P_H = imgY[pix_c.pos_y][pix_c.pos_x + 3];
00564 }
00565 else
00566 {
00567 P_E = P_F = P_G = P_H = P_D;
00568 }
00569
00570 mb_pred[jpos0][ipos0] = (imgpel) ((P_A + P_B + 1) >> 1);
00571 mb_pred[jpos0][ipos1] =
00572 mb_pred[jpos2][ipos0] = (imgpel) ((P_B + P_C + 1) >> 1);
00573 mb_pred[jpos0][ipos2] =
00574 mb_pred[jpos2][ipos1] = (imgpel) ((P_C + P_D + 1) >> 1);
00575 mb_pred[jpos0][ipos3] =
00576 mb_pred[jpos2][ipos2] = (imgpel) ((P_D + P_E + 1) >> 1);
00577 mb_pred[jpos2][ipos3] = (imgpel) ((P_E + P_F + 1) >> 1);
00578 mb_pred[jpos1][ipos0] = (imgpel) ((P_A + 2*P_B + P_C + 2) >> 2);
00579 mb_pred[jpos1][ipos1] =
00580 mb_pred[jpos3][ipos0] = (imgpel) ((P_B + 2*P_C + P_D + 2) >> 2);
00581 mb_pred[jpos1][ipos2] =
00582 mb_pred[jpos3][ipos1] = (imgpel) ((P_C + 2*P_D + P_E + 2) >> 2);
00583 mb_pred[jpos1][ipos3] =
00584 mb_pred[jpos3][ipos2] = (imgpel) ((P_D + 2*P_E + P_F + 2) >> 2);
00585 mb_pred[jpos3][ipos3] = (imgpel) ((P_E + 2*P_F + P_G + 2) >> 2);
00586
00587 return DECODING_OK;
00588 }
00589
00600 static inline int intra4x4_hor_up_pred(ImageParameters *img,
00601 Macroblock *currMB,
00602 ColorPlane pl,
00603 int ioff,
00604 int joff)
00605 {
00606 int i;
00607 imgpel PredPel[13];
00608 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00609
00610 PixelPos pix_a[4];
00611
00612 int block_available_left;
00613
00614 int jpos0 = joff, jpos1 = joff + 1, jpos2 = joff + 2, jpos3 = joff + 3;
00615 int ipos0 = ioff, ipos1 = ioff + 1, ipos2 = ioff + 2, ipos3 = ioff + 3;
00616 imgpel **mb_pred = img->mb_pred[pl];
00617
00618 for (i=0;i<4;i++)
00619 {
00620 getNeighbour(currMB, ioff -1 , joff +i , img->mb_size[IS_LUMA], &pix_a[i]);
00621 }
00622
00623 if (active_pps->constrained_intra_pred_flag)
00624 {
00625 for (i=0, block_available_left=1; i<4;i++)
00626 block_available_left &= pix_a[i].available ? img->intra_block[pix_a[i].mb_addr]: 0;
00627 }
00628 else
00629 {
00630 block_available_left = pix_a[0].available;
00631 }
00632
00633 if (!block_available_left)
00634 printf ("warning: Intra_4x4_Horizontal_Up prediction mode not allowed at mb %d\n",(int) img->current_mb_nr);
00635
00636
00637 P_I = imgY[pix_a[0].pos_y][pix_a[0].pos_x];
00638 P_J = imgY[pix_a[1].pos_y][pix_a[1].pos_x];
00639 P_K = imgY[pix_a[2].pos_y][pix_a[2].pos_x];
00640 P_L = imgY[pix_a[3].pos_y][pix_a[3].pos_x];
00641
00642 mb_pred[jpos0][ipos0] = (imgpel) ((P_I + P_J + 1) >> 1);
00643 mb_pred[jpos0][ipos1] = (imgpel) ((P_I + 2*P_J + P_K + 2) >> 2);
00644 mb_pred[jpos0][ipos2] =
00645 mb_pred[jpos1][ipos0] = (imgpel) ((P_J + P_K + 1) >> 1);
00646 mb_pred[jpos0][ipos3] =
00647 mb_pred[jpos1][ipos1] = (imgpel) ((P_J + 2*P_K + P_L + 2) >> 2);
00648 mb_pred[jpos1][ipos2] =
00649 mb_pred[jpos2][ipos0] = (imgpel) ((P_K + P_L + 1) >> 1);
00650 mb_pred[jpos1][ipos3] =
00651 mb_pred[jpos2][ipos1] = (imgpel) ((P_K + 2*P_L + P_L + 2) >> 2);
00652 mb_pred[jpos2][ipos3] =
00653 mb_pred[jpos3][ipos1] =
00654 mb_pred[jpos3][ipos0] =
00655 mb_pred[jpos2][ipos2] =
00656 mb_pred[jpos3][ipos2] =
00657 mb_pred[jpos3][ipos3] = (imgpel) P_L;
00658
00659 return DECODING_OK;
00660 }
00661
00672 static inline int intra4x4_hor_down_pred(ImageParameters *img,
00673 Macroblock *currMB,
00674 ColorPlane pl,
00675 int ioff,
00676 int joff)
00677 {
00678 int i;
00679 imgpel PredPel[13];
00680 imgpel **imgY = (pl) ? dec_picture->imgUV[pl - 1] : dec_picture->imgY;
00681
00682 PixelPos pix_a[4];
00683 PixelPos pix_b, pix_d;
00684
00685 int block_available_up;
00686 int block_available_left;
00687 int block_available_up_left;
00688
00689 int jpos0 = joff, jpos1 = joff + 1, jpos2 = joff + 2, jpos3 = joff + 3;
00690 int ipos0 = ioff, ipos1 = ioff + 1, ipos2 = ioff + 2, ipos3 = ioff + 3;
00691 imgpel **mb_pred = img->mb_pred[pl];
00692
00693 for (i=0;i<4;i++)
00694 {
00695 getNeighbour(currMB, ioff -1 , joff +i , img->mb_size[IS_LUMA], &pix_a[i]);
00696 }
00697
00698 getNeighbour(currMB, ioff , joff -1 , img->mb_size[IS_LUMA], &pix_b);
00699 getNeighbour(currMB, ioff -1 , joff -1 , img->mb_size[IS_LUMA], &pix_d);
00700
00701 if (active_pps->constrained_intra_pred_flag)
00702 {
00703 for (i=0, block_available_left=1; i<4;i++)
00704 block_available_left &= pix_a[i].available ? img->intra_block[pix_a[i].mb_addr]: 0;
00705 block_available_up = pix_b.available ? img->intra_block [pix_b.mb_addr] : 0;
00706 block_available_up_left = pix_d.available ? img->intra_block [pix_d.mb_addr] : 0;
00707 }
00708 else
00709 {
00710 block_available_left = pix_a[0].available;
00711 block_available_up = pix_b.available;
00712 block_available_up_left = pix_d.available;
00713 }
00714
00715 if ((!block_available_up)||(!block_available_left)||(!block_available_up_left))
00716 printf ("warning: Intra_4x4_Horizontal_Down prediction mode not allowed at mb %d\n", (int) img->current_mb_nr);
00717
00718
00719 P_A = imgY[pix_b.pos_y][pix_b.pos_x + 0];
00720 P_B = imgY[pix_b.pos_y][pix_b.pos_x + 1];
00721 P_C = imgY[pix_b.pos_y][pix_b.pos_x + 2];
00722 P_D = imgY[pix_b.pos_y][pix_b.pos_x + 3];
00723
00724 P_I = imgY[pix_a[0].pos_y][pix_a[0].pos_x];
00725 P_J = imgY[pix_a[1].pos_y][pix_a[1].pos_x];
00726 P_K = imgY[pix_a[2].pos_y][pix_a[2].pos_x];
00727 P_L = imgY[pix_a[3].pos_y][pix_a[3].pos_x];
00728
00729 P_X = imgY[pix_d.pos_y][pix_d.pos_x];
00730
00731 mb_pred[jpos0][ipos0] =
00732 mb_pred[jpos1][ipos2] = (imgpel) ((P_X + P_I + 1) >> 1);
00733 mb_pred[jpos0][ipos1] =
00734 mb_pred[jpos1][ipos3] = (imgpel) ((P_I + 2*P_X + P_A + 2) >> 2);
00735 mb_pred[jpos0][ipos2] = (imgpel) ((P_X + 2*P_A + P_B + 2) >> 2);
00736 mb_pred[jpos0][ipos3] = (imgpel) ((P_A + 2*P_B + P_C + 2) >> 2);
00737 mb_pred[jpos1][ipos0] =
00738 mb_pred[jpos2][ipos2] = (imgpel) ((P_I + P_J + 1) >> 1);
00739 mb_pred[jpos1][ipos1] =
00740 mb_pred[jpos2][ipos3] = (imgpel) ((P_X + 2*P_I + P_J + 2) >> 2);
00741 mb_pred[jpos2][ipos0] =
00742 mb_pred[jpos3][ipos2] = (imgpel) ((P_J + P_K + 1) >> 1);
00743 mb_pred[jpos2][ipos1] =
00744 mb_pred[jpos3][ipos3] = (imgpel) ((P_I + 2*P_J + P_K + 2) >> 2);
00745 mb_pred[jpos3][ipos0] = (imgpel) ((P_K + P_L + 1) >> 1);
00746 mb_pred[jpos3][ipos1] = (imgpel) ((P_J + 2*P_K + P_L + 2) >> 2);
00747
00748 return DECODING_OK;
00749 }
00750
00751
00762 int intrapred(ImageParameters *img,
00763 Macroblock *currMB,
00764 ColorPlane pl,
00765 int ioff,
00766 int joff,
00767 int img_block_x,
00768 int img_block_y)
00769 {
00770 byte predmode = img->ipredmode[img_block_y][img_block_x];
00771 ipmode_DPCM = predmode;
00772
00773 switch (predmode)
00774 {
00775 case DC_PRED:
00776 return (intra4x4_dc_pred(img, currMB, pl, ioff, joff));
00777 break;
00778 case VERT_PRED:
00779 return (intra4x4_vert_pred(img, currMB, pl, ioff, joff));
00780 break;
00781 case HOR_PRED:
00782 return (intra4x4_hor_pred(img, currMB, pl, ioff, joff));
00783 break;
00784 case DIAG_DOWN_RIGHT_PRED:
00785 return (intra4x4_diag_down_right_pred(img, currMB, pl, ioff, joff));
00786 break;
00787 case DIAG_DOWN_LEFT_PRED:
00788 return (intra4x4_diag_down_left_pred(img, currMB, pl, ioff, joff));
00789 break;
00790 case VERT_RIGHT_PRED:
00791 return (intra4x4_vert_right_pred(img, currMB, pl, ioff, joff));
00792 break;
00793 case VERT_LEFT_PRED:
00794 return (intra4x4_vert_left_pred(img, currMB, pl, ioff, joff));
00795 break;
00796 case HOR_UP_PRED:
00797 return (intra4x4_hor_up_pred(img, currMB, pl, ioff, joff));
00798 break;
00799 case HOR_DOWN_PRED:
00800 return (intra4x4_hor_down_pred(img, currMB, pl, ioff, joff));
00801 default:
00802 printf("Error: illegal intra_4x4 prediction mode: %d\n", (int) predmode);
00803 return SEARCH_SYNC;
00804 break;
00805 }
00806
00807 return DECODING_OK;
00808 }