YVU9 -> YV12
untested special converters
- YV12/I420 -> BGR15/BGR24/BGR32 (it is the yuv2rgb stuff, so it should be ok)
+ YV12/I420 -> BGR15/BGR24/BGR32 (it is the yuv2rgb stuff, so it should be OK)
YV12/I420 -> YV12/I420
YUY2/BGR15/BGR24/BGR32/RGB24/RGB32 -> same format
BGR24 -> BGR32 & RGB24 -> RGB32
#include <unistd.h>
#include "config.h"
#include <assert.h>
-#ifdef HAVE_SYS_MMAN_H
+#if HAVE_SYS_MMAN_H
#include <sys/mman.h>
#if defined(MAP_ANON) && !defined(MAP_ANONYMOUS)
#define MAP_ANONYMOUS MAP_ANON
//#define WORDS_BIGENDIAN
#define DITHER1XBPP
-#define FAST_BGR2YV12 // use 7 bit coeffs instead of 15bit
+#define FAST_BGR2YV12 // use 7 bit coefficients instead of 15 bit
-#define RET 0xC3 //near return opcode for X86
+#define RET 0xC3 //near return opcode for x86
#ifdef M_PI
#define PI M_PI
|| isRGB(x) \
|| isBGR(x) \
)
+#define usePal(x) ( \
+ (x)==PIX_FMT_PAL8 \
+ || (x)==PIX_FMT_BGR4_BYTE \
+ || (x)==PIX_FMT_RGB4_BYTE \
+ || (x)==PIX_FMT_BGR8 \
+ || (x)==PIX_FMT_RGB8 \
+ )
#define RGB2YUV_SHIFT 15
#define BY ( (int)(0.114*219/255*(1<<RGB2YUV_SHIFT)+0.5))
TODO
more intelligent misalignment avoidance for the horizontal scaler
write special vertical cubic upscale version
-Optimize C code (yv12 / minmax)
-add support for packed pixel yuv input & output
+optimize C code (YV12 / minmax)
+add support for packed pixel YUV input & output
add support for Y8 output
-optimize bgr24 & bgr32
+optimize BGR24 & BGR32
add BGR4 output support
write special BGR->BGR scaler
*/
-#if defined(ARCH_X86) && defined (CONFIG_GPL)
+#if ARCH_X86 && CONFIG_GPL
DECLARE_ASM_CONST(8, uint64_t, bF8)= 0xF8F8F8F8F8F8F8F8LL;
DECLARE_ASM_CONST(8, uint64_t, bFC)= 0xFCFCFCFCFCFCFCFCLL;
DECLARE_ASM_CONST(8, uint64_t, w10)= 0x0010001000100010LL;
DECLARE_ALIGNED(8, const uint64_t, ff_bgr2UVOffset) = 0x8080808080808080ULL;
DECLARE_ALIGNED(8, const uint64_t, ff_w1111) = 0x0001000100010001ULL;
-DECLARE_ALIGNED(8, const uint64_t, ff_bgr24toY1Coeff) = 0x0C88000040870C88ULL;
-DECLARE_ALIGNED(8, const uint64_t, ff_bgr24toY2Coeff) = 0x20DE4087000020DEULL;
-DECLARE_ALIGNED(8, const uint64_t, ff_rgb24toY1Coeff) = 0x20DE0000408720DEULL;
-DECLARE_ALIGNED(8, const uint64_t, ff_rgb24toY2Coeff) = 0x0C88408700000C88ULL;
-DECLARE_ALIGNED(8, const uint64_t, ff_bgr24toYOffset) = 0x0008400000084000ULL;
+DECLARE_ASM_CONST(8, uint64_t, ff_bgr24toY1Coeff) = 0x0C88000040870C88ULL;
+DECLARE_ASM_CONST(8, uint64_t, ff_bgr24toY2Coeff) = 0x20DE4087000020DEULL;
+DECLARE_ASM_CONST(8, uint64_t, ff_rgb24toY1Coeff) = 0x20DE0000408720DEULL;
+DECLARE_ASM_CONST(8, uint64_t, ff_rgb24toY2Coeff) = 0x0C88408700000C88ULL;
+DECLARE_ASM_CONST(8, uint64_t, ff_bgr24toYOffset) = 0x0008400000084000ULL;
-DECLARE_ALIGNED(8, const uint64_t, ff_bgr24toUV[2][4]) = {
+DECLARE_ASM_CONST(8, uint64_t, ff_bgr24toUV[2][4]) = {
{0x38380000DAC83838ULL, 0xECFFDAC80000ECFFULL, 0xF6E40000D0E3F6E4ULL, 0x3838D0E300003838ULL},
{0xECFF0000DAC8ECFFULL, 0x3838DAC800003838ULL, 0x38380000D0E33838ULL, 0xF6E4D0E30000F6E4ULL},
};
-DECLARE_ALIGNED(8, const uint64_t, ff_bgr24toUVOffset)= 0x0040400000404000ULL;
+DECLARE_ASM_CONST(8, uint64_t, ff_bgr24toUVOffset)= 0x0040400000404000ULL;
-#endif /* defined(ARCH_X86) */
+#endif /* ARCH_X86 && CONFIG_GPL */
// clipping helper table for C implementations:
static unsigned char clip_table[768];
static SwsVector *sws_getConvVec(SwsVector *a, SwsVector *b);
-const uint8_t __attribute__((aligned(8))) dither_2x2_4[2][8]={
+static const uint8_t __attribute__((aligned(8))) dither_2x2_4[2][8]={
{ 1, 3, 1, 3, 1, 3, 1, 3, },
{ 2, 0, 2, 0, 2, 0, 2, 0, },
};
-const uint8_t __attribute__((aligned(8))) dither_2x2_8[2][8]={
+static const uint8_t __attribute__((aligned(8))) dither_2x2_8[2][8]={
{ 6, 2, 6, 2, 6, 2, 6, 2, },
{ 0, 4, 0, 4, 0, 4, 0, 4, },
};
return "nv21";
case PIX_FMT_YUV440P:
return "yuv440p";
+ case PIX_FMT_VDPAU_H264:
+ return "vdpau_h264";
+ case PIX_FMT_VDPAU_MPEG1:
+ return "vdpau_mpeg1";
+ case PIX_FMT_VDPAU_MPEG2:
+ return "vdpau_mpeg2";
+ case PIX_FMT_VDPAU_WMV3:
+ return "vdpau_wmv3";
+ case PIX_FMT_VDPAU_VC1:
+ return "vdpau_vc1";
default:
return "Unknown format";
}
int16_t *chrFilter, int16_t **chrSrc, int chrFilterSize,
uint8_t *dest, uint8_t *uDest, uint8_t *vDest, int dstW, int chrDstW)
{
- //FIXME Optimize (just quickly writen not opti..)
+ //FIXME Optimize (just quickly written not optimized..)
int i;
for (i=0; i<dstW; i++)
{
int16_t *chrFilter, int16_t **chrSrc, int chrFilterSize,
uint8_t *dest, uint8_t *uDest, int dstW, int chrDstW, int dstFormat)
{
- //FIXME Optimize (just quickly writen not opti..)
+ //FIXME Optimize (just quickly written not optimized..)
int i;
for (i=0; i<dstW; i++)
{
}
#define YSCALE_YUV_2_RGBX_C(type) \
- YSCALE_YUV_2_PACKEDX_C(type) /* FIXME fix tables so that cliping is not needed and then use _NOCLIP*/\
+ YSCALE_YUV_2_PACKEDX_C(type) /* FIXME fix tables so that clipping is not needed and then use _NOCLIP*/\
r = (type *)c->table_rV[V]; \
g = (type *)(c->table_gU[U] + c->table_gV[V]); \
b = (type *)c->table_bU[U]; \
}
}
-//Note: we have C, X86, MMX, MMX2, 3DNOW version therse no 3DNOW+MMX2 one
+//Note: we have C, X86, MMX, MMX2, 3DNOW versions, there is no 3DNOW+MMX2 one
//Plain C versions
-#if !defined (HAVE_MMX) || defined (RUNTIME_CPUDETECT) || !defined(CONFIG_GPL)
+#if !HAVE_MMX || defined (RUNTIME_CPUDETECT) || !CONFIG_GPL
#define COMPILE_C
#endif
-#ifdef ARCH_POWERPC
-#if (defined (HAVE_ALTIVEC) || defined (RUNTIME_CPUDETECT)) && defined (CONFIG_GPL)
+#if ARCH_PPC
+#if (HAVE_ALTIVEC || defined (RUNTIME_CPUDETECT)) && CONFIG_GPL
#define COMPILE_ALTIVEC
-#endif //HAVE_ALTIVEC
-#endif //ARCH_POWERPC
+#endif
+#endif //ARCH_PPC
-#if defined(ARCH_X86)
+#if ARCH_X86
-#if ((defined (HAVE_MMX) && !defined (HAVE_3DNOW) && !defined (HAVE_MMX2)) || defined (RUNTIME_CPUDETECT)) && defined (CONFIG_GPL)
+#if ((HAVE_MMX && !HAVE_3DNOW && !HAVE_MMX2) || defined (RUNTIME_CPUDETECT)) && CONFIG_GPL
#define COMPILE_MMX
#endif
-#if (defined (HAVE_MMX2) || defined (RUNTIME_CPUDETECT)) && defined (CONFIG_GPL)
+#if (HAVE_MMX2 || defined (RUNTIME_CPUDETECT)) && CONFIG_GPL
#define COMPILE_MMX2
#endif
-#if ((defined (HAVE_3DNOW) && !defined (HAVE_MMX2)) || defined (RUNTIME_CPUDETECT)) && defined (CONFIG_GPL)
+#if ((HAVE_3DNOW && !HAVE_MMX2) || defined (RUNTIME_CPUDETECT)) && CONFIG_GPL
#define COMPILE_3DNOW
#endif
-#endif //ARCH_X86 || ARCH_X86_64
+#endif //ARCH_X86
#undef HAVE_MMX
#undef HAVE_MMX2
#undef HAVE_3DNOW
+#undef HAVE_ALTIVEC
+#define HAVE_MMX 0
+#define HAVE_MMX2 0
+#define HAVE_3DNOW 0
+#define HAVE_ALTIVEC 0
#ifdef COMPILE_C
-#undef HAVE_MMX
-#undef HAVE_MMX2
-#undef HAVE_3DNOW
-#undef HAVE_ALTIVEC
#define RENAME(a) a ## _C
#include "swscale_template.c"
#endif
#ifdef COMPILE_ALTIVEC
#undef RENAME
-#define HAVE_ALTIVEC
+#undef HAVE_ALTIVEC
+#define HAVE_ALTIVEC 1
#define RENAME(a) a ## _altivec
#include "swscale_template.c"
#endif
-#if defined(ARCH_X86)
+#if ARCH_X86
-//X86 versions
+//x86 versions
/*
#undef RENAME
#undef HAVE_MMX
//MMX versions
#ifdef COMPILE_MMX
#undef RENAME
-#define HAVE_MMX
+#undef HAVE_MMX
#undef HAVE_MMX2
#undef HAVE_3DNOW
+#define HAVE_MMX 1
+#define HAVE_MMX2 0
+#define HAVE_3DNOW 0
#define RENAME(a) a ## _MMX
#include "swscale_template.c"
#endif
//MMX2 versions
#ifdef COMPILE_MMX2
#undef RENAME
-#define HAVE_MMX
-#define HAVE_MMX2
+#undef HAVE_MMX
+#undef HAVE_MMX2
#undef HAVE_3DNOW
+#define HAVE_MMX 1
+#define HAVE_MMX2 1
+#define HAVE_3DNOW 0
#define RENAME(a) a ## _MMX2
#include "swscale_template.c"
#endif
//3DNOW versions
#ifdef COMPILE_3DNOW
#undef RENAME
-#define HAVE_MMX
+#undef HAVE_MMX
#undef HAVE_MMX2
-#define HAVE_3DNOW
+#undef HAVE_3DNOW
+#define HAVE_MMX 1
+#define HAVE_MMX2 0
+#define HAVE_3DNOW 1
#define RENAME(a) a ## _3DNow
#include "swscale_template.c"
#endif
-#endif //ARCH_X86 || ARCH_X86_64
+#endif //ARCH_X86
-// minor note: the HAVE_xyz is messed up after that line so don't use it
+// minor note: the HAVE_xyz are messed up after this line so don't use them
static double getSplineCoeff(double a, double b, double c, double d, double dist)
{
int64_t *filter2=NULL;
const int64_t fone= 1LL<<54;
int ret= -1;
-#if defined(ARCH_X86)
+#if ARCH_X86
if (flags & SWS_CPU_CAPS_MMX)
- asm volatile("emms\n\t"::: "memory"); //FIXME this should not be required but it IS (even for non-MMX versions)
+ __asm__ volatile("emms\n\t"::: "memory"); //FIXME this should not be required but it IS (even for non-MMX versions)
#endif
- // Note the +1 is for the MMXscaler which reads over the end
+ // NOTE: the +1 is for the MMX scaler which reads over the end
*filterPos = av_malloc((dstW+1)*sizeof(int16_t));
if (FFABS(xInc - 0x10000) <10) // unscaled
int j;
(*filterPos)[i]= xx;
- //Bilinear upscale / linear interpolate / Area averaging
+ //bilinear upscale / linear interpolate / area averaging
for (j=0; j<filterSize; j++)
{
int64_t coeff= fone - FFABS((xx<<16) - xDstInSrc)*(fone>>16);
/* preserve monotonicity because the core can't handle the filter otherwise */
if (i<dstW-1 && (*filterPos)[i] >= (*filterPos)[i+1]) break;
- // Move filter coeffs left
+ // move filter coefficients left
for (k=1; k<filter2Size; k++)
filter2[i*filter2Size + k - 1]= filter2[i*filter2Size + k];
filter2[i*filter2Size + k - 1]= 0;
if (minFilterSize < 5)
filterAlign = 4;
- // we really don't want to waste our time
- // doing useless computation, so fall-back on
- // the scalar C code for very small filter.
- // vectorizing is worth it only if you have
+ // We really don't want to waste our time
+ // doing useless computation, so fall back on
+ // the scalar C code for very small filters.
+ // Vectorizing is worth it only if you have a
// decent-sized vector.
if (minFilterSize < 3)
filterAlign = 1;
}
- //FIXME try to align filterpos if possible
+ //FIXME try to align filterPos if possible
//fix borders
for (i=0; i<dstW; i++)
int j;
if ((*filterPos)[i] < 0)
{
- // Move filter coeffs left to compensate for filterPos
+ // move filter coefficients left to compensate for filterPos
for (j=1; j<filterSize; j++)
{
int left= FFMAX(j + (*filterPos)[i], 0);
if ((*filterPos)[i] + filterSize > srcW)
{
int shift= (*filterPos)[i] + filterSize - srcW;
- // Move filter coeffs right to compensate for filterPos
+ // move filter coefficients right to compensate for filterPos
for (j=filterSize-2; j>=0; j--)
{
int right= FFMIN(j + shift, filterSize-1);
}
}
- // Note the +1 is for the MMXscaler which reads over the end
+ // Note the +1 is for the MMX scaler which reads over the end
/* align at 16 for AltiVec (needed by hScale_altivec_real) */
*outFilter= av_mallocz(*outFilterSize*(dstW+1)*sizeof(int16_t));
- /* Normalize & Store in outFilter */
+ /* normalize & store in outFilter */
for (i=0; i<dstW; i++)
{
int j;
//code fragment
- asm volatile(
+ __asm__ volatile(
"jmp 9f \n\t"
// Begin
"0: \n\t"
"=r" (fragmentLengthA)
);
- asm volatile(
+ __asm__ volatile(
"jmp 9f \n\t"
// Begin
"0: \n\t"
static SwsFunc getSwsFunc(int flags){
-#if defined(RUNTIME_CPUDETECT) && defined (CONFIG_GPL)
-#if defined(ARCH_X86)
+#if defined(RUNTIME_CPUDETECT) && CONFIG_GPL
+#if ARCH_X86
// ordered per speed fastest first
if (flags & SWS_CPU_CAPS_MMX2)
return swScale_MMX2;
return swScale_C;
#else
-#ifdef ARCH_POWERPC
+#if ARCH_PPC
if (flags & SWS_CPU_CAPS_ALTIVEC)
return swScale_altivec;
else
return swScale_C;
#endif
return swScale_C;
-#endif /* defined(ARCH_X86) */
+#endif /* ARCH_X86 */
#else //RUNTIME_CPUDETECT
-#ifdef HAVE_MMX2
+#if HAVE_MMX2
return swScale_MMX2;
-#elif defined (HAVE_3DNOW)
+#elif HAVE_3DNOW
return swScale_3DNow;
-#elif defined (HAVE_MMX)
+#elif HAVE_MMX
return swScale_MMX;
-#elif defined (HAVE_ALTIVEC)
+#elif HAVE_ALTIVEC
return swScale_altivec;
#else
return swScale_C;
return srcSliceH;
}
+static int pal2rgbWrapper(SwsContext *c, uint8_t* src[], int srcStride[], int srcSliceY,
+ int srcSliceH, uint8_t* dst[], int dstStride[]){
+ const enum PixelFormat srcFormat= c->srcFormat;
+ const enum PixelFormat dstFormat= c->dstFormat;
+ void (*conv)(const uint8_t *src, uint8_t *dst, long num_pixels,
+ const uint8_t *palette)=NULL;
+ int i;
+ uint8_t *dstPtr= dst[0] + dstStride[0]*srcSliceY;
+ uint8_t *srcPtr= src[0];
+
+ if (!usePal(srcFormat))
+ av_log(c, AV_LOG_ERROR, "internal error %s -> %s converter\n",
+ sws_format_name(srcFormat), sws_format_name(dstFormat));
+
+ switch(dstFormat){
+ case PIX_FMT_RGB32 : conv = palette8topacked32; break;
+ case PIX_FMT_BGR32 : conv = palette8topacked32; break;
+ case PIX_FMT_BGR32_1: conv = palette8topacked32; break;
+ case PIX_FMT_RGB32_1: conv = palette8topacked32; break;
+ case PIX_FMT_RGB24 : conv = palette8topacked24; break;
+ case PIX_FMT_BGR24 : conv = palette8topacked24; break;
+ default: av_log(c, AV_LOG_ERROR, "internal error %s -> %s converter\n",
+ sws_format_name(srcFormat), sws_format_name(dstFormat)); break;
+ }
+
+
+ for (i=0; i<srcSliceH; i++) {
+ conv(srcPtr, dstPtr, c->srcW, (uint8_t *) c->pal_rgb);
+ srcPtr+= srcStride[0];
+ dstPtr+= dstStride[0];
+ }
+
+ return srcSliceH;
+}
+
/* {RGB,BGR}{15,16,24,32,32_1} -> {RGB,BGR}{15,16,24,32} */
static int rgb2rgbWrapper(SwsContext *c, uint8_t* src[], int srcStride[], int srcSliceY,
int srcSliceH, uint8_t* dst[], int dstStride[]){
}
/**
- * @param inv_table the yuv2rgb coeffs, normally Inverse_Table_6_9[x]
+ * @param inv_table the yuv2rgb coefficients, normally Inverse_Table_6_9[x]
* @param fullRange if 1 then the luma range is 0..255 if 0 it is 16..235
* @return -1 if not supported
*/
return 0;
}
-static int handle_jpeg(int *format)
+static int handle_jpeg(enum PixelFormat *format)
{
switch (*format) {
case PIX_FMT_YUVJ420P:
int unscaled, needsDither;
int srcRange, dstRange;
SwsFilter dummyFilter= {NULL, NULL, NULL, NULL};
-#if defined(ARCH_X86)
+#if ARCH_X86
if (flags & SWS_CPU_CAPS_MMX)
- asm volatile("emms\n\t"::: "memory");
+ __asm__ volatile("emms\n\t"::: "memory");
#endif
-#if !defined(RUNTIME_CPUDETECT) || !defined (CONFIG_GPL) //ensure that the flags match the compiled variant if cpudetect is off
+#if !defined(RUNTIME_CPUDETECT) || !CONFIG_GPL //ensure that the flags match the compiled variant if cpudetect is off
flags &= ~(SWS_CPU_CAPS_MMX|SWS_CPU_CAPS_MMX2|SWS_CPU_CAPS_3DNOW|SWS_CPU_CAPS_ALTIVEC|SWS_CPU_CAPS_BFIN);
-#ifdef HAVE_MMX2
+#if HAVE_MMX2
flags |= SWS_CPU_CAPS_MMX|SWS_CPU_CAPS_MMX2;
-#elif defined (HAVE_3DNOW)
+#elif HAVE_3DNOW
flags |= SWS_CPU_CAPS_MMX|SWS_CPU_CAPS_3DNOW;
-#elif defined (HAVE_MMX)
+#elif HAVE_MMX
flags |= SWS_CPU_CAPS_MMX;
-#elif defined (HAVE_ALTIVEC)
+#elif HAVE_ALTIVEC
flags |= SWS_CPU_CAPS_ALTIVEC;
-#elif defined (ARCH_BFIN)
+#elif ARCH_BFIN
flags |= SWS_CPU_CAPS_BFIN;
#endif
#endif /* RUNTIME_CPUDETECT */
|SWS_BICUBLIN);
if(!i || (i & (i-1)))
{
- av_log(NULL, AV_LOG_ERROR, "swScaler: Exactly one scaler algorithm must be choosen\n");
+ av_log(NULL, AV_LOG_ERROR, "swScaler: Exactly one scaler algorithm must be chosen\n");
return NULL;
}
return NULL;
}
if(srcW > VOFW || dstW > VOFW){
- av_log(NULL, AV_LOG_ERROR, "swScaler: Compile time max width is "AV_STRINGIFY(VOFW)" change VOF/VOFW and recompile\n");
+ av_log(NULL, AV_LOG_ERROR, "swScaler: Compile-time maximum width is "AV_STRINGIFY(VOFW)" change VOF/VOFW and recompile\n");
return NULL;
}
getSubSampleFactors(&c->chrSrcHSubSample, &c->chrSrcVSubSample, srcFormat);
getSubSampleFactors(&c->chrDstHSubSample, &c->chrDstVSubSample, dstFormat);
- // reuse chroma for 2 pixles rgb/bgr unless user wants full chroma interpolation
+ // reuse chroma for 2 pixels RGB/BGR unless user wants full chroma interpolation
if ((isBGR(dstFormat) || isRGB(dstFormat)) && !(flags&SWS_FULL_CHR_H_INT)) c->chrDstHSubSample=1;
// drop some chroma lines if the user wants it
c->vChrDrop= (flags&SWS_SRC_V_CHR_DROP_MASK)>>SWS_SRC_V_CHR_DROP_SHIFT;
c->chrSrcVSubSample+= c->vChrDrop;
- // drop every 2. pixel for chroma calculation unless user wants full chroma
+ // drop every other pixel for chroma calculation unless user wants full chroma
if ((isBGR(srcFormat) || isRGB(srcFormat)) && !(flags&SWS_FULL_CHR_H_INP)
&& srcFormat!=PIX_FMT_RGB8 && srcFormat!=PIX_FMT_BGR8
&& srcFormat!=PIX_FMT_RGB4 && srcFormat!=PIX_FMT_BGR4
sws_setColorspaceDetails(c, Inverse_Table_6_9[SWS_CS_DEFAULT], srcRange, Inverse_Table_6_9[SWS_CS_DEFAULT] /* FIXME*/, dstRange, 0, 1<<16, 1<<16);
- /* unscaled special Cases */
+ /* unscaled special cases */
if (unscaled && !usesHFilter && !usesVFilter && (srcRange == dstRange || isBGR(dstFormat) || isRGB(dstFormat)))
{
/* yv12_to_nv12 */
{
c->swScale= PlanarToNV12Wrapper;
}
-#ifdef CONFIG_GPL
+#if CONFIG_GPL
/* yuv2bgr */
if ((srcFormat==PIX_FMT_YUV420P || srcFormat==PIX_FMT_YUV422P) && (isBGR(dstFormat) || isRGB(dstFormat))
- && !(flags & SWS_ACCURATE_RND))
+ && !(flags & SWS_ACCURATE_RND) && !(dstH&1))
{
c->swScale= yuv2rgb_get_func_ptr(c);
}
if (srcFormat==PIX_FMT_BGR24 && dstFormat==PIX_FMT_YUV420P && !(flags & SWS_ACCURATE_RND))
c->swScale= bgr24toyv12Wrapper;
- /* rgb/bgr -> rgb/bgr (no dither needed forms) */
+ /* RGB/BGR -> RGB/BGR (no dither needed forms) */
if ( (isBGR(srcFormat) || isRGB(srcFormat))
&& (isBGR(dstFormat) || isRGB(dstFormat))
&& srcFormat != PIX_FMT_BGR8 && dstFormat != PIX_FMT_BGR8
&& (!needsDither || (c->flags&(SWS_FAST_BILINEAR|SWS_POINT))))
c->swScale= rgb2rgbWrapper;
+ if ((usePal(srcFormat) && (
+ dstFormat == PIX_FMT_RGB32 ||
+ dstFormat == PIX_FMT_RGB32_1 ||
+ dstFormat == PIX_FMT_RGB24 ||
+ dstFormat == PIX_FMT_BGR32 ||
+ dstFormat == PIX_FMT_BGR32_1 ||
+ dstFormat == PIX_FMT_BGR24)))
+ c->swScale= pal2rgbWrapper;
+
if (srcFormat == PIX_FMT_YUV422P)
{
if (dstFormat == PIX_FMT_YUYV422)
c->swScale= gray16swap;
}
-#ifdef ARCH_BFIN
+#if ARCH_BFIN
if (flags & SWS_CPU_CAPS_BFIN)
ff_bfin_get_unscaled_swscale (c);
#endif
if (!c->canMMX2BeUsed && dstW >=srcW && (srcW&15)==0 && (flags&SWS_FAST_BILINEAR))
{
if (flags&SWS_PRINT_INFO)
- av_log(c, AV_LOG_INFO, "output Width is not a multiple of 32 -> no MMX2 scaler\n");
+ av_log(c, AV_LOG_INFO, "output width is not a multiple of 32 -> no MMX2 scaler\n");
}
if (usesHFilter) c->canMMX2BeUsed=0;
}
c->lumXInc+= 20;
c->chrXInc+= 20;
}
- //we don't use the x86asm scaler if mmx is available
+ //we don't use the x86 asm scaler if MMX is available
else if (flags & SWS_CPU_CAPS_MMX)
{
c->lumXInc = ((srcW-2)<<16)/(dstW-2) - 20;
initMMX2HScaler(c->chrDstW, c->chrXInc, c->funnyUVCode, c->chrMmx2Filter, c->chrMmx2FilterPos, 4);
}
#endif /* defined(COMPILE_MMX2) */
- } // Init Horizontal stuff
+ } // initialize horizontal stuff
(flags&SWS_BICUBLIN) ? (flags|SWS_BILINEAR) : flags,
srcFilter->chrV, dstFilter->chrV, c->param);
-#ifdef HAVE_ALTIVEC
+#if HAVE_ALTIVEC
c->vYCoeffsBank = av_malloc(sizeof (vector signed short)*c->vLumFilterSize*c->dstH);
c->vCCoeffsBank = av_malloc(sizeof (vector signed short)*c->vChrFilterSize*c->chrDstH);
#endif
}
- // Calculate Buffer Sizes so that they won't run out while handling these damn slices
+ // calculate buffer sizes so that they won't run out while handling these damn slices
c->vLumBufSize= c->vLumFilterSize;
c->vChrBufSize= c->vChrFilterSize;
for (i=0; i<dstH; i++)
// allocate pixbufs (we use dynamic allocation because otherwise we would need to
c->lumPixBuf= av_malloc(c->vLumBufSize*2*sizeof(int16_t*));
c->chrPixBuf= av_malloc(c->vChrBufSize*2*sizeof(int16_t*));
- //Note we need at least one pixel more at the end because of the mmx code (just in case someone wanna replace the 4000/8000)
+ //Note we need at least one pixel more at the end because of the MMX code (just in case someone wanna replace the 4000/8000)
/* align at 16 bytes for AltiVec */
for (i=0; i<c->vLumBufSize; i++)
c->lumPixBuf[i]= c->lumPixBuf[i+c->vLumBufSize]= av_mallocz(VOF+1);
}
else
{
-#if defined(ARCH_X86)
- av_log(c, AV_LOG_VERBOSE, "using X86-Asm scaler for horizontal scaling\n");
+#if ARCH_X86
+ av_log(c, AV_LOG_VERBOSE, "using x86 asm scaler for horizontal scaling\n");
#else
if (flags & SWS_FAST_BILINEAR)
av_log(c, AV_LOG_VERBOSE, "using FAST_BILINEAR C scaler for horizontal scaling\n");
}
if (dstFormat==PIX_FMT_BGR24)
- av_log(c, AV_LOG_VERBOSE, "using %s YV12->BGR24 Converter\n",
+ av_log(c, AV_LOG_VERBOSE, "using %s YV12->BGR24 converter\n",
(flags & SWS_CPU_CAPS_MMX2) ? "MMX2" : ((flags & SWS_CPU_CAPS_MMX) ? "MMX" : "C"));
else if (dstFormat==PIX_FMT_RGB32)
- av_log(c, AV_LOG_VERBOSE, "using %s YV12->BGR32 Converter\n", (flags & SWS_CPU_CAPS_MMX) ? "MMX" : "C");
+ av_log(c, AV_LOG_VERBOSE, "using %s YV12->BGR32 converter\n", (flags & SWS_CPU_CAPS_MMX) ? "MMX" : "C");
else if (dstFormat==PIX_FMT_BGR565)
- av_log(c, AV_LOG_VERBOSE, "using %s YV12->BGR16 Converter\n", (flags & SWS_CPU_CAPS_MMX) ? "MMX" : "C");
+ av_log(c, AV_LOG_VERBOSE, "using %s YV12->BGR16 converter\n", (flags & SWS_CPU_CAPS_MMX) ? "MMX" : "C");
else if (dstFormat==PIX_FMT_BGR555)
- av_log(c, AV_LOG_VERBOSE, "using %s YV12->BGR15 Converter\n", (flags & SWS_CPU_CAPS_MMX) ? "MMX" : "C");
+ av_log(c, AV_LOG_VERBOSE, "using %s YV12->BGR15 converter\n", (flags & SWS_CPU_CAPS_MMX) ? "MMX" : "C");
av_log(c, AV_LOG_VERBOSE, "%dx%d -> %dx%d\n", srcW, srcH, dstW, dstH);
}
if (flags & SWS_PRINT_INFO)
{
- av_log(c, AV_LOG_DEBUG, "Lum srcW=%d srcH=%d dstW=%d dstH=%d xInc=%d yInc=%d\n",
+ av_log(c, AV_LOG_DEBUG, "lum srcW=%d srcH=%d dstW=%d dstH=%d xInc=%d yInc=%d\n",
c->srcW, c->srcH, c->dstW, c->dstH, c->lumXInc, c->lumYInc);
- av_log(c, AV_LOG_DEBUG, "Chr srcW=%d srcH=%d dstW=%d dstH=%d xInc=%d yInc=%d\n",
+ av_log(c, AV_LOG_DEBUG, "chr srcW=%d srcH=%d dstW=%d dstH=%d xInc=%d yInc=%d\n",
c->chrSrcW, c->chrSrcH, c->chrDstW, c->chrDstH, c->chrXInc, c->chrYInc);
}
/**
* swscale wrapper, so we don't need to export the SwsContext.
- * assumes planar YUV to be in YUV order instead of YVU
+ * Assumes planar YUV to be in YUV order instead of YVU.
*/
int sws_scale(SwsContext *c, uint8_t* src[], int srcStride[], int srcSliceY,
int srcSliceH, uint8_t* dst[], int dstStride[]){
int i;
uint8_t* src2[4]= {src[0], src[1], src[2]};
- uint32_t pal[256];
- int use_pal= c->srcFormat == PIX_FMT_PAL8
- || c->srcFormat == PIX_FMT_BGR4_BYTE
- || c->srcFormat == PIX_FMT_RGB4_BYTE
- || c->srcFormat == PIX_FMT_BGR8
- || c->srcFormat == PIX_FMT_RGB8;
if (c->sliceDir == 0 && srcSliceY != 0 && srcSliceY + srcSliceH != c->srcH) {
av_log(c, AV_LOG_ERROR, "Slices start in the middle!\n");
if (srcSliceY == 0) c->sliceDir = 1; else c->sliceDir = -1;
}
- if (use_pal){
+ if (usePal(c->srcFormat)){
for (i=0; i<256; i++){
int p, r, g, b,y,u,v;
if(c->srcFormat == PIX_FMT_PAL8){
r= (i>>3 )*255;
g= ((i>>1)&3)*85;
b= (i&1 )*255;
- }else if(c->srcFormat == PIX_FMT_BGR4_BYTE){
+ }else {
+ assert(c->srcFormat == PIX_FMT_BGR4_BYTE);
b= (i>>3 )*255;
g= ((i>>1)&3)*85;
r= (i&1 )*255;
y= av_clip_uint8((RY*r + GY*g + BY*b + ( 33<<(RGB2YUV_SHIFT-1)))>>RGB2YUV_SHIFT);
u= av_clip_uint8((RU*r + GU*g + BU*b + (257<<(RGB2YUV_SHIFT-1)))>>RGB2YUV_SHIFT);
v= av_clip_uint8((RV*r + GV*g + BV*b + (257<<(RGB2YUV_SHIFT-1)))>>RGB2YUV_SHIFT);
- pal[i]= y + (u<<8) + (v<<16);
+ c->pal_yuv[i]= y + (u<<8) + (v<<16);
+
+
+ switch(c->dstFormat) {
+ case PIX_FMT_BGR32:
+#ifndef WORDS_BIGENDIAN
+ case PIX_FMT_RGB24:
+#endif
+ c->pal_rgb[i]= r + (g<<8) + (b<<16);
+ break;
+ case PIX_FMT_BGR32_1:
+#ifdef WORDS_BIGENDIAN
+ case PIX_FMT_BGR24:
+#endif
+ c->pal_rgb[i]= (r + (g<<8) + (b<<16)) << 8;
+ break;
+ case PIX_FMT_RGB32_1:
+#ifdef WORDS_BIGENDIAN
+ case PIX_FMT_RGB24:
+#endif
+ c->pal_rgb[i]= (b + (g<<8) + (r<<16)) << 8;
+ break;
+ case PIX_FMT_RGB32:
+#ifndef WORDS_BIGENDIAN
+ case PIX_FMT_BGR24:
+#endif
+ default:
+ c->pal_rgb[i]= b + (g<<8) + (r<<16);
+ }
}
- src2[1]= (uint8_t*)pal;
}
// copy strides, so they can safely be modified
int dstStride2[4]= {-dstStride[0], -dstStride[1], -dstStride[2]};
src2[0] += (srcSliceH-1)*srcStride[0];
- if (!use_pal)
+ if (!usePal(c->srcFormat))
src2[1] += ((srcSliceH>>c->chrSrcVSubSample)-1)*srcStride[1];
src2[2] += ((srcSliceH>>c->chrSrcVSubSample)-1)*srcStride[2];
}
/**
- * swscale wrapper, so we don't need to export the SwsContext
+ * swscale wrapper, so we don't need to export the SwsContext.
*/
int sws_scale_ordered(SwsContext *c, uint8_t* src[], int srcStride[], int srcSliceY,
int srcSliceH, uint8_t* dst[], int dstStride[]){
}
/**
- * returns a normalized gaussian curve used to filter stuff
- * quality=3 is high quality, lowwer is lowwer quality
+ * Returns a normalized Gaussian curve used to filter stuff
+ * quality=3 is high quality, lower is lower quality.
*/
SwsVector *sws_getGaussianVec(double variance, double quality){
const int length= (int)(variance*quality + 0.5) | 1;
av_freep(&c->vChrFilter);
av_freep(&c->hLumFilter);
av_freep(&c->hChrFilter);
-#ifdef HAVE_ALTIVEC
+#if HAVE_ALTIVEC
av_freep(&c->vYCoeffsBank);
av_freep(&c->vCCoeffsBank);
#endif
av_freep(&c->hLumFilterPos);
av_freep(&c->hChrFilterPos);
-#if defined(ARCH_X86) && defined(CONFIG_GPL)
+#if ARCH_X86 && CONFIG_GPL
#ifdef MAP_ANONYMOUS
if (c->funnyYCode) munmap(c->funnyYCode, MAX_FUNNY_CODE_SIZE);
if (c->funnyUVCode) munmap(c->funnyUVCode, MAX_FUNNY_CODE_SIZE);
#endif
c->funnyYCode=NULL;
c->funnyUVCode=NULL;
-#endif /* defined(ARCH_X86) */
+#endif /* ARCH_X86 && CONFIG_GPL */
av_freep(&c->lumMmx2Filter);
av_freep(&c->chrMmx2Filter);
/**
* Checks if context is valid or reallocs a new one instead.
* If context is NULL, just calls sws_getContext() to get a new one.
- * Otherwise, checks if the parameters are the same already saved in context.
+ * Otherwise, checks if the parameters are the ones already saved in context.
* If that is the case, returns the current context.
* Otherwise, frees context and gets a new one.
*