⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 wmv9_filters.c

📁 au1200 linux2.6.11 硬件解码mae驱动和maiplayer播放器源码
💻 C
📖 第 1 页 / 共 5 页
字号:
/* <LIC_AMD_STD> * Copyright (C) 2003-2005 Advanced Micro Devices, Inc.  All Rights Reserved. *  * Unless otherwise designated in writing, this software and any related  * documentation are the confidential proprietary information of AMD.  * THESE MATERIALS ARE PROVIDED "AS IS" WITHOUT ANY * UNLESS OTHERWISE NOTED IN WRITING, EXPRESS OR IMPLIED WARRANTY OF ANY  * KIND, INCLUDING BUT NOT LIMITED TO WARRANTIES OF MERCHANTABILITY,  * NONINFRINGEMENT, TITLE, FITNESS FOR ANY PARTICULAR PURPOSE AND IN NO  * EVENT SHALL AMD OR ITS LICENSORS BE LIABLE FOR ANY DAMAGES WHATSOEVER.  *  * AMD does not assume any responsibility for any errors which may appear  * in the Materials nor any responsibility to support or update the * Materials.  AMD retains the right to modify the Materials at any time,  * without notice, and is not obligated to provide such modified  * Materials to you. AMD is not obligated to furnish, support, or make * any further information available to you. * </LIC_AMD_STD>  *//* <CTL_AMD_STD> * </CTL_AMD_STD>  *//* <DOC_AMD_STD> * </DOC_AMD_STD>  */#ifdef HAVE_MAE
  #include "fcov.h"
#else
  #define fcov_coverage_point_hit(x)
#endif
#include "mae_global.h"
#include <stdio.h>  // for printf
#include <string.h>

#define MAE_TRUE 1
#define MAE_FALSE 0

#ifdef REF_WMV9

  extern int nFileUpdates;
  extern unsigned int nFrameNumber;

  void PrintLoopFilterForMAE(MAE_CWMVMBMode*, MAE_tWMVDecInternalMember *, int, int, int);
#endif

/****************************************************************************************
  MAE_OverlapMBRow : complete overlapped transform reconstruction for I blocks in row of MBs
  // TBD: speedup (e.g. skip if no intra blocks in current and previous rows)
****************************************************************************************/

void MAE_OverlapMBRow (MAE_tWMVDecInternalMember * MAE_pWMVDec, I32_WMV imbY, U8_WMV *ppxliRecnY, U8_WMV *ppxliRecnU,
                   U8_WMV *ppxliRecnV, I32_WMV iMBYEnd, I32_WMV iMBYStart,
                   I32_WMV iThreadID)
{
  I32_WMV  ii; 
  I32_WMV  iXBlocks = (I32_WMV) MAE_pWMVDec->m_uintNumMBX * 2;    // Number of 8x8 blocks
  I32_WMV  iStrideUV = (I32_WMV) MAE_pWMVDec->m_uintNumMBX * 8;   // Width of UV frame in pixels
  I32_WMV  iStride = iStrideUV * 2;                           // Width of Y frame in pixels
  I32_WMV  iBlockIndex = imbY * iXBlocks * 2;                 // R->L, T->B, 8x8 block index
  I16_WMV  *pMotion = MAE_pWMVDec->m_pXMotion + iBlockIndex;      // m_pXMotion is array that tells if 8x8 
                                                              // is Intra or not (for Y)
  I16_WMV  *pMotionUV = MAE_pWMVDec->m_pXMotionC + imbY           // m_pXMotionC is array that tells if 8x8 
                        * (I32_WMV) MAE_pWMVDec->m_uintNumMBX;    // is Intra or not (for UV)
  I16_WMV  **pIntraBlockRow, **pIntraMBRowU, **pIntraMBRowV;
//int i,j;
  // Note that for Luma, 
  // pIntraBlockRow[0] == top row of 8x8 in current row of MBs
  // pIntraBlockRow[1] == row of 8x8 above current row of MBs
  // pIntraBlockRow[2] == bottom row of 8x8 in current row of MBs
  // Note that for chroma, 
  // pIntraMBRow[U/V][0] == current row of 8x8 in current row of MBs
  // pIntraMBRow[U/V][1] == row of 8x8 above current row of MBs
  pIntraBlockRow = MAE_pWMVDec->m_pIntraBlockRow0;
  pIntraMBRowU = MAE_pWMVDec->m_pIntraMBRowU0;
  pIntraMBRowV = MAE_pWMVDec->m_pIntraMBRowV0;

  // Not Used
  if (iThreadID) {
    pIntraBlockRow = MAE_pWMVDec->m_pIntraBlockRow1;
    pIntraMBRowU = MAE_pWMVDec->m_pIntraMBRowU1;
    pIntraMBRowV = MAE_pWMVDec->m_pIntraMBRowV1;
  }

/*
log_printf("Row %d: Before Vertical, Above Row Y:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStride; j++) {
    log_printf("%x ", pIntraBlockRow[1][i*iStride+j]);
  }
  log_printf("\n");
}
log_printf("Row %d: Before Vertical, Top Row Y:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStride; j++) {
    log_printf("%x ", pIntraBlockRow[0][i*iStride+j]);
  }
  log_printf("\n");
}
log_printf("Row %d: Before Vertical, Bottom Row Y:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStride; j++) {
    log_printf("%x ", pIntraBlockRow[2][i*iStride+j]);
  }
  log_printf("\n");
}
*/
  // as long as there are I blocks in the current rows, filter vertical edges
  // Don't do this if last row?????
  if (imbY < iMBYEnd) {

    // Luma Vertical
    for (ii = 1; ii < iXBlocks; ii++) {  // For each 8x8 in row
      // if top 8x8 and 8x8 to left are both Intra, filter vertically
      if (pMotion[ii] == MAE_IBLOCKMV && pMotion[ii - 1] == MAE_IBLOCKMV) {  
        MAE_g_OverlapBlockVerticalEdge (pIntraBlockRow[0] + ii * 8, iStride);
      }
      // if bottom 8x8 and 8x8 to left of it are both Intra, filter vertically
      if (pMotion[ii + iXBlocks] == MAE_IBLOCKMV && pMotion[ii + iXBlocks - 1] == MAE_IBLOCKMV) {
        MAE_g_OverlapBlockVerticalEdge (pIntraBlockRow[2] + ii * 8, iStride);
      }
    }

/*
log_printf("Row %d: After Vertical, Above Row Y:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStride; j++) {
    log_printf("%x ", pIntraBlockRow[1][i*iStride+j]);
  }
  log_printf("\n");
}
log_printf("Row %d: After Vertical, Top Row Y:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStride; j++) {
    log_printf("%x ", pIntraBlockRow[0][i*iStride+j]);
  }
  log_printf("\n");
}
log_printf("Row %d: After Vertical, Bottom Row Y:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStride; j++) {
    log_printf("%x ", pIntraBlockRow[2][i*iStride+j]);
  }
  log_printf("\n");
}

log_printf("Row %d: Before Vertical, Above Row Cb:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStrideUV; j++) {
    log_printf("%x ", pIntraMBRowU[1][i*iStrideUV+j]);
  }
  log_printf("\n");
}
log_printf("Row %d: Before Vertical, Top Row Cb:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStrideUV; j++) {
    log_printf("%x ", pIntraBlockRow[0][i*iStrideUV+j]);
  }
  log_printf("\n");
}
*/
    // Chroma Vertical
    for (ii = 1; ii < (I32_WMV) MAE_pWMVDec->m_uintNumMBX; ii++) {  // For each 8x8 in row
      // if 8x8 and 8x8 to left are both Intra, filter vertically
      if (pMotionUV[ii] == MAE_IBLOCKMV && pMotionUV[ii - 1] == MAE_IBLOCKMV) {
        MAE_g_OverlapBlockVerticalEdge (pIntraMBRowU[0] + ii * 8, iStrideUV);
        MAE_g_OverlapBlockVerticalEdge (pIntraMBRowV[0] + ii * 8, iStrideUV);
      }
    }
  }
/*
log_printf("Row %d: After Vertical, Above Row Cb:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStrideUV; j++) {
    log_printf("%x ", pIntraMBRowU[1][i*iStrideUV+j]);
  }
  log_printf("\n");
}
log_printf("Row %d: After Vertical, Top Row Cb:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStrideUV; j++) {
    log_printf("%x ", pIntraBlockRow[0][i*iStrideUV+j]);
  }
  log_printf("\n");
}
*/
  // Luma Horizontal
  for (ii = 0; ii < iXBlocks; ii++) {
    Bool_WMV  bTop = (imbY > iMBYStart) && pMotion[ii - iXBlocks] == MAE_IBLOCKMV;  // bTop set if 8x8 above is Intra
    Bool_WMV  bDn  = (imbY < iMBYEnd), bUp = MAE_FALSE;  
    if (bDn) {                                       // Don't set bUp or bDn if last row
      bUp = pMotion[ii] == MAE_IBLOCKMV;                 // bUp set if top 8x8 is Intra
      bDn = pMotion[ii + iXBlocks] == MAE_IBLOCKMV;      // bDn set if bottom 8x8 is Intra
    }

    // If either 8x8 above or top 8x8 is Intra, Filter top horizontal edge
    if  (bTop || bUp) {
      // In this case, top row == pIntraBlockRow[1], current row == pIntraBlockRow[0]
      MAE_g_OverlapBlockHorizontalEdge ( pIntraBlockRow[1] + ii * 8, pIntraBlockRow[0] + ii * 8,
          iStride, ppxliRecnY + ii * 8, MAE_pWMVDec->m_iWidthPrevY, bTop, bUp, MAE_FALSE);
    }

    // If either top 8x8 or bottom 8x8 is Intra, Filter middle horizontal edge
    if  (bUp || bDn) {
      // In this case, top row == pIntraBlockRow[0], current row == pIntraBlockRow[2]
      MAE_g_OverlapBlockHorizontalEdge ( pIntraBlockRow[0] + ii * 8, pIntraBlockRow[2] + ii * 8,
          iStride, ppxliRecnY + MAE_pWMVDec->m_iWidthPrevY * 8 + ii * 8, MAE_pWMVDec->m_iWidthPrevY, bUp, bDn, MAE_FALSE);
    }
  }
/*
log_printf("Row %d: After Horizontal, Top Row Y:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStride; j++) {
    log_printf("%x ", ppxliRecnY[i*iStride+j]);
  }
  log_printf("\n");
}
log_printf("Row %d: After Horizontal, Bottom Row Y:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStride; j++) {
    log_printf("%x ", (ppxliRecnY+ MAE_pWMVDec->m_iWidthPrevY * 8)[i*iStride+j]);
  }
  log_printf("\n");
}
*/

  // Chroma Horizontal
  for (ii = 0; ii < (I32_WMV) MAE_pWMVDec->m_uintNumMBX; ii++) {
    Bool_WMV  bUp = (imbY > iMBYStart) && (pMotionUV[ii - (I32_WMV) MAE_pWMVDec->m_uintNumMBX] == MAE_IBLOCKMV);
    Bool_WMV  bDn = (imbY < iMBYEnd) && (pMotionUV[ii] == MAE_IBLOCKMV);

    // If either 8x8 above or current 8x8 is Intra, Filter top horizontal edge
    if  (bUp || bDn) {
      MAE_g_OverlapBlockHorizontalEdge ( pIntraMBRowU[1] + ii * 8, pIntraMBRowU[0] + ii * 8,
        iStrideUV, ppxliRecnU + ii * 8, MAE_pWMVDec->m_iWidthPrevUV, bUp, bDn, MAE_FALSE);
      MAE_g_OverlapBlockHorizontalEdge ( pIntraMBRowV[1] + ii * 8, pIntraMBRowV[0] + ii * 8,
        iStrideUV, ppxliRecnV + ii * 8, MAE_pWMVDec->m_iWidthPrevUV, bUp, bDn, MAE_FALSE);
    }
  }
/*
log_printf("Row %d: After Horizontal, Top Row Cb:\n", imbY);
for(i = 0; i < 8; i++) {
  for(j =0; j < iStrideUV; j++) {
    log_printf("%x ", ppxliRecnU[i*iStrideUV+j]);
  }
  log_printf("\n");
}
*/
  // switch pointers - use pMotion as a temp
  if (iThreadID == 0) {
/*
    pMotion = MAE_pWMVDec->m_pIntraBlockRow0[1];
    MAE_pWMVDec->m_pIntraBlockRow0[1] = MAE_pWMVDec->m_pIntraBlockRow0[2];  // bottom -> above
    MAE_pWMVDec->m_pIntraBlockRow0[2] = pMotion;                        // above -> bottom???

    pMotion = MAE_pWMVDec->m_pIntraMBRowU0[0];
    MAE_pWMVDec->m_pIntraMBRowU0[0] = MAE_pWMVDec->m_pIntraMBRowU0[1];      // above -> current???
    MAE_pWMVDec->m_pIntraMBRowU0[1] = pMotion;                          // current -> above

    pMotion = MAE_pWMVDec->m_pIntraMBRowV0[0];
    MAE_pWMVDec->m_pIntraMBRowV0[0] = MAE_pWMVDec->m_pIntraMBRowV0[1];      // above -> current???
    MAE_pWMVDec->m_pIntraMBRowV0[1] = pMotion;                          // current -> above
*/
  } else {
  // Not used
    if (imbY == iMBYStart) {
      // move block row 0 to backup area 3
      pMotion = MAE_pWMVDec->m_pIntraBlockRow1[3];
      MAE_pWMVDec->m_pIntraBlockRow1[3] = MAE_pWMVDec->m_pIntraBlockRow1[0];
      MAE_pWMVDec->m_pIntraBlockRow1[0] = pMotion;

      // copy to backup for UV
      memcpy (MAE_pWMVDec->m_pIntraMBRowU1[2], MAE_pWMVDec->m_pIntraMBRowU1[0], MAE_pWMVDec->m_uintNumMBX * 8 * 8);
      memcpy (MAE_pWMVDec->m_pIntraMBRowV1[2], MAE_pWMVDec->m_pIntraMBRowV1[0], MAE_pWMVDec->m_uintNumMBX * 8 * 8);
    }
    pMotion = MAE_pWMVDec->m_pIntraBlockRow1[1];
    MAE_pWMVDec->m_pIntraBlockRow1[1] = MAE_pWMVDec->m_pIntraBlockRow1[2];
    MAE_pWMVDec->m_pIntraBlockRow1[2] = pMotion;

    pMotion = MAE_pWMVDec->m_pIntraMBRowU1[0];
    MAE_pWMVDec->m_pIntraMBRowU1[0] = MAE_pWMVDec->m_pIntraMBRowU1[1];
    MAE_pWMVDec->m_pIntraMBRowU1[1] = pMotion;

    pMotion = MAE_pWMVDec->m_pIntraMBRowV1[0];
    MAE_pWMVDec->m_pIntraMBRowV1[0] = MAE_pWMVDec->m_pIntraMBRowV1[1];
    MAE_pWMVDec->m_pIntraMBRowV1[1] = pMotion;
  }

}

/****************************************************************************************

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -