00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "avcodec.h"
00024 #include "fmtconvert.h"
00025
00026 static void int32_to_float_fmul_scalar_c(float *dst, const int *src, float mul, int len){
00027 int i;
00028 for(i=0; i<len; i++)
00029 dst[i] = src[i] * mul;
00030 }
00031
00032 static av_always_inline int float_to_int16_one(const float *src){
00033 return av_clip_int16(lrintf(*src));
00034 }
00035
00036 static void float_to_int16_c(int16_t *dst, const float *src, long len)
00037 {
00038 int i;
00039 for(i=0; i<len; i++)
00040 dst[i] = float_to_int16_one(src+i);
00041 }
00042
00043 static void float_to_int16_interleave_c(int16_t *dst, const float **src,
00044 long len, int channels)
00045 {
00046 int i,j,c;
00047 if(channels==2){
00048 for(i=0; i<len; i++){
00049 dst[2*i] = float_to_int16_one(src[0]+i);
00050 dst[2*i+1] = float_to_int16_one(src[1]+i);
00051 }
00052 }else{
00053 for(c=0; c<channels; c++)
00054 for(i=0, j=c; i<len; i++, j+=channels)
00055 dst[j] = float_to_int16_one(src[c]+i);
00056 }
00057 }
00058
00059 void ff_float_interleave_c(float *dst, const float **src, unsigned int len,
00060 int channels)
00061 {
00062 int j, c;
00063 unsigned int i;
00064 if (channels == 2) {
00065 for (i = 0; i < len; i++) {
00066 dst[2*i] = src[0][i];
00067 dst[2*i+1] = src[1][i];
00068 }
00069 } else if (channels == 1 && len < INT_MAX / sizeof(float)) {
00070 memcpy(dst, src[0], len * sizeof(float));
00071 } else {
00072 for (c = 0; c < channels; c++)
00073 for (i = 0, j = c; i < len; i++, j += channels)
00074 dst[j] = src[c][i];
00075 }
00076 }
00077
00078 av_cold void ff_fmt_convert_init(FmtConvertContext *c, AVCodecContext *avctx)
00079 {
00080 c->int32_to_float_fmul_scalar = int32_to_float_fmul_scalar_c;
00081 c->float_to_int16 = float_to_int16_c;
00082 c->float_to_int16_interleave = float_to_int16_interleave_c;
00083 c->float_interleave = ff_float_interleave_c;
00084
00085 if (ARCH_ARM) ff_fmt_convert_init_arm(c, avctx);
00086 if (HAVE_ALTIVEC) ff_fmt_convert_init_altivec(c, avctx);
00087 if (HAVE_MMX) ff_fmt_convert_init_x86(c, avctx);
00088 }
00089
00090
00091 void float_interleave(float *dst, const float **src, long len, int channels)
00092 {
00093 int i,j,c;
00094 if(channels==2){
00095 for(i=0; i<len; i++){
00096 dst[2*i] = src[0][i] / 32768.0f;
00097 dst[2*i+1] = src[1][i] / 32768.0f;
00098 }
00099 }else{
00100 for(c=0; c<channels; c++)
00101 for(i=0, j=c; i<len; i++, j+=channels)
00102 dst[j] = src[c][i] / 32768.0f;
00103 }
00104 }
00105
00106 void float_interleave_noscale(float *dst, const float **src, long len, int channels)
00107 {
00108 int i,j,c;
00109 if(channels==2){
00110 for(i=0; i<len; i++){
00111 dst[2*i] = src[0][i];
00112 dst[2*i+1] = src[1][i];
00113 }
00114 }else{
00115 for(c=0; c<channels; c++)
00116 for(i=0, j=c; i<len; i++, j+=channels)
00117 dst[j] = src[c][i];
00118 }
00119 }