author | Jean-Yves Avenard <jyavenard@mozilla.com> |
Tue, 02 Aug 2016 22:51:41 +1000 | |
changeset 403660 | 04b8e81af8044dbc05423505cc759492bcbda51b |
parent 403581 | f97a056ae6235de7855fd8aaa04fb1c8d183bd06 |
child 403661 | 630270a8ddb494d4a6639e68a9d4560cdcac94fc |
push id | 26983 |
push user | bmo:jyavenard@mozilla.com |
push date | Sun, 21 Aug 2016 19:12:56 +0000 |
reviewers | kentuckyfriedtakahe |
bugs | 1270016 |
milestone | 51.0a1 |
--- a/media/ffvpx/config_darwin32.h +++ b/media/ffvpx/config_darwin32.h @@ -571,21 +571,21 @@ #define CONFIG_BSWAPDSP 0 #define CONFIG_CABAC 0 #define CONFIG_DIRAC_PARSE 0 #define CONFIG_DVPROFILE 0 #define CONFIG_EXIF 0 #define CONFIG_FAANDCT 0 #define CONFIG_FAANIDCT 0 #define CONFIG_FDCTDSP 0 -#define CONFIG_FLACDSP 0 +#define CONFIG_FLACDSP 1 #define CONFIG_FMTCONVERT 0 #define CONFIG_FRAME_THREAD_ENCODER 0 #define CONFIG_G722DSP 0 -#define CONFIG_GOLOMB 0 +#define CONFIG_GOLOMB 1 #define CONFIG_GPLV3 0 #define CONFIG_H263DSP 0 #define CONFIG_H264CHROMA 0 #define CONFIG_H264DSP 0 #define CONFIG_H264PRED 1 #define CONFIG_H264QPEL 0 #define CONFIG_HPELDSP 0 #define CONFIG_HUFFMAN 0 @@ -917,17 +917,17 @@ #define CONFIG_DSD_LSBF_PLANAR_DECODER 0 #define CONFIG_DSD_MSBF_PLANAR_DECODER 0 #define CONFIG_DSICINAUDIO_DECODER 0 #define CONFIG_DSS_SP_DECODER 0 #define CONFIG_DST_DECODER 0 #define CONFIG_EAC3_DECODER 0 #define CONFIG_EVRC_DECODER 0 #define CONFIG_FFWAVESYNTH_DECODER 0 -#define CONFIG_FLAC_DECODER 0 +#define CONFIG_FLAC_DECODER 1 #define CONFIG_G723_1_DECODER 0 #define CONFIG_G729_DECODER 0 #define CONFIG_GSM_DECODER 0 #define CONFIG_GSM_MS_DECODER 0 #define CONFIG_IAC_DECODER 0 #define CONFIG_IMC_DECODER 0 #define CONFIG_INTERPLAY_ACM_DECODER 0 #define CONFIG_MACE3_DECODER 0 @@ -2099,17 +2099,17 @@ #define CONFIG_DCA_PARSER 0 #define CONFIG_DIRAC_PARSER 0 #define CONFIG_DNXHD_PARSER 0 #define CONFIG_DPX_PARSER 0 #define CONFIG_DVAUDIO_PARSER 0 #define CONFIG_DVBSUB_PARSER 0 #define CONFIG_DVDSUB_PARSER 0 #define CONFIG_DVD_NAV_PARSER 0 -#define CONFIG_FLAC_PARSER 0 +#define CONFIG_FLAC_PARSER 1 #define CONFIG_G729_PARSER 0 #define CONFIG_GSM_PARSER 0 #define CONFIG_H261_PARSER 0 #define CONFIG_H263_PARSER 0 #define CONFIG_H264_PARSER 0 #define CONFIG_HEVC_PARSER 0 #define CONFIG_MJPEG_PARSER 0 #define CONFIG_MLP_PARSER 0
--- a/media/ffvpx/config_darwin64.asm +++ b/media/ffvpx/config_darwin64.asm @@ -556,21 +556,21 @@ %define CONFIG_BSWAPDSP 0 %define CONFIG_CABAC 0 %define CONFIG_DIRAC_PARSE 0 %define CONFIG_DVPROFILE 0 %define CONFIG_EXIF 0 %define CONFIG_FAANDCT 0 %define CONFIG_FAANIDCT 0 %define CONFIG_FDCTDSP 0 -%define CONFIG_FLACDSP 0 +%define CONFIG_FLACDSP 1 %define CONFIG_FMTCONVERT 0 %define CONFIG_FRAME_THREAD_ENCODER 0 %define CONFIG_G722DSP 0 -%define CONFIG_GOLOMB 0 +%define CONFIG_GOLOMB 1 %define CONFIG_GPLV3 0 %define CONFIG_H263DSP 0 %define CONFIG_H264CHROMA 0 %define CONFIG_H264DSP 0 %define CONFIG_H264PRED 1 %define CONFIG_H264QPEL 0 %define CONFIG_HPELDSP 0 %define CONFIG_HUFFMAN 0 @@ -902,17 +902,17 @@ %define CONFIG_DSD_LSBF_PLANAR_DECODER 0 %define CONFIG_DSD_MSBF_PLANAR_DECODER 0 %define CONFIG_DSICINAUDIO_DECODER 0 %define CONFIG_DSS_SP_DECODER 0 %define CONFIG_DST_DECODER 0 %define CONFIG_EAC3_DECODER 0 %define CONFIG_EVRC_DECODER 0 %define CONFIG_FFWAVESYNTH_DECODER 0 -%define CONFIG_FLAC_DECODER 0 +%define CONFIG_FLAC_DECODER 1 %define CONFIG_G723_1_DECODER 0 %define CONFIG_G729_DECODER 0 %define CONFIG_GSM_DECODER 0 %define CONFIG_GSM_MS_DECODER 0 %define CONFIG_IAC_DECODER 0 %define CONFIG_IMC_DECODER 0 %define CONFIG_INTERPLAY_ACM_DECODER 0 %define CONFIG_MACE3_DECODER 0 @@ -2084,17 +2084,17 @@ %define CONFIG_DCA_PARSER 0 %define CONFIG_DIRAC_PARSER 0 %define CONFIG_DNXHD_PARSER 0 %define CONFIG_DPX_PARSER 0 %define CONFIG_DVAUDIO_PARSER 0 %define CONFIG_DVBSUB_PARSER 0 %define CONFIG_DVDSUB_PARSER 0 %define CONFIG_DVD_NAV_PARSER 0 -%define CONFIG_FLAC_PARSER 0 +%define CONFIG_FLAC_PARSER 1 %define CONFIG_G729_PARSER 0 %define CONFIG_GSM_PARSER 0 %define CONFIG_H261_PARSER 0 %define CONFIG_H263_PARSER 0 %define CONFIG_H264_PARSER 0 %define CONFIG_HEVC_PARSER 0 %define CONFIG_MJPEG_PARSER 0 %define CONFIG_MLP_PARSER 0
--- a/media/ffvpx/config_darwin64.h +++ b/media/ffvpx/config_darwin64.h @@ -571,21 +571,21 @@ #define CONFIG_BSWAPDSP 0 #define CONFIG_CABAC 0 #define CONFIG_DIRAC_PARSE 0 #define CONFIG_DVPROFILE 0 #define CONFIG_EXIF 0 #define CONFIG_FAANDCT 0 #define CONFIG_FAANIDCT 0 #define CONFIG_FDCTDSP 0 -#define CONFIG_FLACDSP 0 +#define CONFIG_FLACDSP 1 #define CONFIG_FMTCONVERT 0 #define CONFIG_FRAME_THREAD_ENCODER 0 #define CONFIG_G722DSP 0 -#define CONFIG_GOLOMB 0 +#define CONFIG_GOLOMB 1 #define CONFIG_GPLV3 0 #define CONFIG_H263DSP 0 #define CONFIG_H264CHROMA 0 #define CONFIG_H264DSP 0 #define CONFIG_H264PRED 1 #define CONFIG_H264QPEL 0 #define CONFIG_HPELDSP 0 #define CONFIG_HUFFMAN 0 @@ -917,17 +917,17 @@ #define CONFIG_DSD_LSBF_PLANAR_DECODER 0 #define CONFIG_DSD_MSBF_PLANAR_DECODER 0 #define CONFIG_DSICINAUDIO_DECODER 0 #define CONFIG_DSS_SP_DECODER 0 #define CONFIG_DST_DECODER 0 #define CONFIG_EAC3_DECODER 0 #define CONFIG_EVRC_DECODER 0 #define CONFIG_FFWAVESYNTH_DECODER 0 -#define CONFIG_FLAC_DECODER 0 +#define CONFIG_FLAC_DECODER 1 #define CONFIG_G723_1_DECODER 0 #define CONFIG_G729_DECODER 0 #define CONFIG_GSM_DECODER 0 #define CONFIG_GSM_MS_DECODER 0 #define CONFIG_IAC_DECODER 0 #define CONFIG_IMC_DECODER 0 #define CONFIG_INTERPLAY_ACM_DECODER 0 #define CONFIG_MACE3_DECODER 0 @@ -2099,17 +2099,17 @@ #define CONFIG_DCA_PARSER 0 #define CONFIG_DIRAC_PARSER 0 #define CONFIG_DNXHD_PARSER 0 #define CONFIG_DPX_PARSER 0 #define CONFIG_DVAUDIO_PARSER 0 #define CONFIG_DVBSUB_PARSER 0 #define CONFIG_DVDSUB_PARSER 0 #define CONFIG_DVD_NAV_PARSER 0 -#define CONFIG_FLAC_PARSER 0 +#define CONFIG_FLAC_PARSER 1 #define CONFIG_G729_PARSER 0 #define CONFIG_GSM_PARSER 0 #define CONFIG_H261_PARSER 0 #define CONFIG_H263_PARSER 0 #define CONFIG_H264_PARSER 0 #define CONFIG_HEVC_PARSER 0 #define CONFIG_MJPEG_PARSER 0 #define CONFIG_MLP_PARSER 0
--- a/media/ffvpx/config_unix32.h +++ b/media/ffvpx/config_unix32.h @@ -570,21 +570,21 @@ #define CONFIG_BSWAPDSP 0 #define CONFIG_CABAC 0 #define CONFIG_DIRAC_PARSE 0 #define CONFIG_DVPROFILE 0 #define CONFIG_EXIF 0 #define CONFIG_FAANDCT 0 #define CONFIG_FAANIDCT 0 #define CONFIG_FDCTDSP 0 -#define CONFIG_FLACDSP 0 +#define CONFIG_FLACDSP 1 #define CONFIG_FMTCONVERT 0 #define CONFIG_FRAME_THREAD_ENCODER 0 #define CONFIG_G722DSP 0 -#define CONFIG_GOLOMB 0 +#define CONFIG_GOLOMB 1 #define CONFIG_GPLV3 0 #define CONFIG_H263DSP 0 #define CONFIG_H264CHROMA 0 #define CONFIG_H264DSP 0 #define CONFIG_H264PRED 1 #define CONFIG_H264QPEL 0 #define CONFIG_HPELDSP 0 #define CONFIG_HUFFMAN 0 @@ -916,17 +916,17 @@ #define CONFIG_DSD_LSBF_PLANAR_DECODER 0 #define CONFIG_DSD_MSBF_PLANAR_DECODER 0 #define CONFIG_DSICINAUDIO_DECODER 0 #define CONFIG_DSS_SP_DECODER 0 #define CONFIG_DST_DECODER 0 #define CONFIG_EAC3_DECODER 0 #define CONFIG_EVRC_DECODER 0 #define CONFIG_FFWAVESYNTH_DECODER 0 -#define CONFIG_FLAC_DECODER 0 +#define CONFIG_FLAC_DECODER 1 #define CONFIG_G723_1_DECODER 0 #define CONFIG_G729_DECODER 0 #define CONFIG_GSM_DECODER 0 #define CONFIG_GSM_MS_DECODER 0 #define CONFIG_IAC_DECODER 0 #define CONFIG_IMC_DECODER 0 #define CONFIG_INTERPLAY_ACM_DECODER 0 #define CONFIG_MACE3_DECODER 0 @@ -2098,17 +2098,17 @@ #define CONFIG_DCA_PARSER 0 #define CONFIG_DIRAC_PARSER 0 #define CONFIG_DNXHD_PARSER 0 #define CONFIG_DPX_PARSER 0 #define CONFIG_DVAUDIO_PARSER 0 #define CONFIG_DVBSUB_PARSER 0 #define CONFIG_DVDSUB_PARSER 0 #define CONFIG_DVD_NAV_PARSER 0 -#define CONFIG_FLAC_PARSER 0 +#define CONFIG_FLAC_PARSER 1 #define CONFIG_G729_PARSER 0 #define CONFIG_GSM_PARSER 0 #define CONFIG_H261_PARSER 0 #define CONFIG_H263_PARSER 0 #define CONFIG_H264_PARSER 0 #define CONFIG_HEVC_PARSER 0 #define CONFIG_MJPEG_PARSER 0 #define CONFIG_MLP_PARSER 0
--- a/media/ffvpx/config_unix64.asm +++ b/media/ffvpx/config_unix64.asm @@ -556,21 +556,21 @@ %define CONFIG_BSWAPDSP 0 %define CONFIG_CABAC 0 %define CONFIG_DIRAC_PARSE 0 %define CONFIG_DVPROFILE 0 %define CONFIG_EXIF 0 %define CONFIG_FAANDCT 0 %define CONFIG_FAANIDCT 0 %define CONFIG_FDCTDSP 0 -%define CONFIG_FLACDSP 0 +%define CONFIG_FLACDSP 1 %define CONFIG_FMTCONVERT 0 %define CONFIG_FRAME_THREAD_ENCODER 0 %define CONFIG_G722DSP 0 -%define CONFIG_GOLOMB 0 +%define CONFIG_GOLOMB 1 %define CONFIG_GPLV3 0 %define CONFIG_H263DSP 0 %define CONFIG_H264CHROMA 0 %define CONFIG_H264DSP 0 %define CONFIG_H264PRED 1 %define CONFIG_H264QPEL 0 %define CONFIG_HPELDSP 0 %define CONFIG_HUFFMAN 0 @@ -902,17 +902,17 @@ %define CONFIG_DSD_LSBF_PLANAR_DECODER 0 %define CONFIG_DSD_MSBF_PLANAR_DECODER 0 %define CONFIG_DSICINAUDIO_DECODER 0 %define CONFIG_DSS_SP_DECODER 0 %define CONFIG_DST_DECODER 0 %define CONFIG_EAC3_DECODER 0 %define CONFIG_EVRC_DECODER 0 %define CONFIG_FFWAVESYNTH_DECODER 0 -%define CONFIG_FLAC_DECODER 0 +%define CONFIG_FLAC_DECODER 1 %define CONFIG_G723_1_DECODER 0 %define CONFIG_G729_DECODER 0 %define CONFIG_GSM_DECODER 0 %define CONFIG_GSM_MS_DECODER 0 %define CONFIG_IAC_DECODER 0 %define CONFIG_IMC_DECODER 0 %define CONFIG_INTERPLAY_ACM_DECODER 0 %define CONFIG_MACE3_DECODER 0 @@ -2084,17 +2084,17 @@ %define CONFIG_DCA_PARSER 0 %define CONFIG_DIRAC_PARSER 0 %define CONFIG_DNXHD_PARSER 0 %define CONFIG_DPX_PARSER 0 %define CONFIG_DVAUDIO_PARSER 0 %define CONFIG_DVBSUB_PARSER 0 %define CONFIG_DVDSUB_PARSER 0 %define CONFIG_DVD_NAV_PARSER 0 -%define CONFIG_FLAC_PARSER 0 +%define CONFIG_FLAC_PARSER 1 %define CONFIG_G729_PARSER 0 %define CONFIG_GSM_PARSER 0 %define CONFIG_H261_PARSER 0 %define CONFIG_H263_PARSER 0 %define CONFIG_H264_PARSER 0 %define CONFIG_HEVC_PARSER 0 %define CONFIG_MJPEG_PARSER 0 %define CONFIG_MLP_PARSER 0
--- a/media/ffvpx/config_unix64.h +++ b/media/ffvpx/config_unix64.h @@ -571,21 +571,21 @@ #define CONFIG_BSWAPDSP 0 #define CONFIG_CABAC 0 #define CONFIG_DIRAC_PARSE 0 #define CONFIG_DVPROFILE 0 #define CONFIG_EXIF 0 #define CONFIG_FAANDCT 0 #define CONFIG_FAANIDCT 0 #define CONFIG_FDCTDSP 0 -#define CONFIG_FLACDSP 0 +#define CONFIG_FLACDSP 1 #define CONFIG_FMTCONVERT 0 #define CONFIG_FRAME_THREAD_ENCODER 0 #define CONFIG_G722DSP 0 -#define CONFIG_GOLOMB 0 +#define CONFIG_GOLOMB 1 #define CONFIG_GPLV3 0 #define CONFIG_H263DSP 0 #define CONFIG_H264CHROMA 0 #define CONFIG_H264DSP 0 #define CONFIG_H264PRED 1 #define CONFIG_H264QPEL 0 #define CONFIG_HPELDSP 0 #define CONFIG_HUFFMAN 0 @@ -917,17 +917,17 @@ #define CONFIG_DSD_LSBF_PLANAR_DECODER 0 #define CONFIG_DSD_MSBF_PLANAR_DECODER 0 #define CONFIG_DSICINAUDIO_DECODER 0 #define CONFIG_DSS_SP_DECODER 0 #define CONFIG_DST_DECODER 0 #define CONFIG_EAC3_DECODER 0 #define CONFIG_EVRC_DECODER 0 #define CONFIG_FFWAVESYNTH_DECODER 0 -#define CONFIG_FLAC_DECODER 0 +#define CONFIG_FLAC_DECODER 1 #define CONFIG_G723_1_DECODER 0 #define CONFIG_G729_DECODER 0 #define CONFIG_GSM_DECODER 0 #define CONFIG_GSM_MS_DECODER 0 #define CONFIG_IAC_DECODER 0 #define CONFIG_IMC_DECODER 0 #define CONFIG_INTERPLAY_ACM_DECODER 0 #define CONFIG_MACE3_DECODER 0 @@ -2099,17 +2099,17 @@ #define CONFIG_DCA_PARSER 0 #define CONFIG_DIRAC_PARSER 0 #define CONFIG_DNXHD_PARSER 0 #define CONFIG_DPX_PARSER 0 #define CONFIG_DVAUDIO_PARSER 0 #define CONFIG_DVBSUB_PARSER 0 #define CONFIG_DVDSUB_PARSER 0 #define CONFIG_DVD_NAV_PARSER 0 -#define CONFIG_FLAC_PARSER 0 +#define CONFIG_FLAC_PARSER 1 #define CONFIG_G729_PARSER 0 #define CONFIG_GSM_PARSER 0 #define CONFIG_H261_PARSER 0 #define CONFIG_H263_PARSER 0 #define CONFIG_H264_PARSER 0 #define CONFIG_HEVC_PARSER 0 #define CONFIG_MJPEG_PARSER 0 #define CONFIG_MLP_PARSER 0
--- a/media/ffvpx/config_win32.asm +++ b/media/ffvpx/config_win32.asm @@ -556,21 +556,21 @@ %define CONFIG_BSWAPDSP 0 %define CONFIG_CABAC 0 %define CONFIG_DIRAC_PARSE 0 %define CONFIG_DVPROFILE 0 %define CONFIG_EXIF 0 %define CONFIG_FAANDCT 0 %define CONFIG_FAANIDCT 0 %define CONFIG_FDCTDSP 0 -%define CONFIG_FLACDSP 0 +%define CONFIG_FLACDSP 1 %define CONFIG_FMTCONVERT 0 %define CONFIG_FRAME_THREAD_ENCODER 0 %define CONFIG_G722DSP 0 -%define CONFIG_GOLOMB 0 +%define CONFIG_GOLOMB 1 %define CONFIG_GPLV3 0 %define CONFIG_H263DSP 0 %define CONFIG_H264CHROMA 0 %define CONFIG_H264DSP 0 %define CONFIG_H264PRED 1 %define CONFIG_H264QPEL 0 %define CONFIG_HPELDSP 0 %define CONFIG_HUFFMAN 0 @@ -902,17 +902,17 @@ %define CONFIG_DSD_LSBF_PLANAR_DECODER 0 %define CONFIG_DSD_MSBF_PLANAR_DECODER 0 %define CONFIG_DSICINAUDIO_DECODER 0 %define CONFIG_DSS_SP_DECODER 0 %define CONFIG_DST_DECODER 0 %define CONFIG_EAC3_DECODER 0 %define CONFIG_EVRC_DECODER 0 %define CONFIG_FFWAVESYNTH_DECODER 0 -%define CONFIG_FLAC_DECODER 0 +%define CONFIG_FLAC_DECODER 1 %define CONFIG_G723_1_DECODER 0 %define CONFIG_G729_DECODER 0 %define CONFIG_GSM_DECODER 0 %define CONFIG_GSM_MS_DECODER 0 %define CONFIG_IAC_DECODER 0 %define CONFIG_IMC_DECODER 0 %define CONFIG_INTERPLAY_ACM_DECODER 0 %define CONFIG_MACE3_DECODER 0 @@ -2084,17 +2084,17 @@ %define CONFIG_DCA_PARSER 0 %define CONFIG_DIRAC_PARSER 0 %define CONFIG_DNXHD_PARSER 0 %define CONFIG_DPX_PARSER 0 %define CONFIG_DVAUDIO_PARSER 0 %define CONFIG_DVBSUB_PARSER 0 %define CONFIG_DVDSUB_PARSER 0 %define CONFIG_DVD_NAV_PARSER 0 -%define CONFIG_FLAC_PARSER 0 +%define CONFIG_FLAC_PARSER 1 %define CONFIG_G729_PARSER 0 %define CONFIG_GSM_PARSER 0 %define CONFIG_H261_PARSER 0 %define CONFIG_H263_PARSER 0 %define CONFIG_H264_PARSER 0 %define CONFIG_HEVC_PARSER 0 %define CONFIG_MJPEG_PARSER 0 %define CONFIG_MLP_PARSER 0
--- a/media/ffvpx/config_win32.h +++ b/media/ffvpx/config_win32.h @@ -571,21 +571,21 @@ #define CONFIG_BSWAPDSP 0 #define CONFIG_CABAC 0 #define CONFIG_DIRAC_PARSE 0 #define CONFIG_DVPROFILE 0 #define CONFIG_EXIF 0 #define CONFIG_FAANDCT 0 #define CONFIG_FAANIDCT 0 #define CONFIG_FDCTDSP 0 -#define CONFIG_FLACDSP 0 +#define CONFIG_FLACDSP 1 #define CONFIG_FMTCONVERT 0 #define CONFIG_FRAME_THREAD_ENCODER 0 #define CONFIG_G722DSP 0 -#define CONFIG_GOLOMB 0 +#define CONFIG_GOLOMB 1 #define CONFIG_GPLV3 0 #define CONFIG_H263DSP 0 #define CONFIG_H264CHROMA 0 #define CONFIG_H264DSP 0 #define CONFIG_H264PRED 1 #define CONFIG_H264QPEL 0 #define CONFIG_HPELDSP 0 #define CONFIG_HUFFMAN 0 @@ -917,17 +917,17 @@ #define CONFIG_DSD_LSBF_PLANAR_DECODER 0 #define CONFIG_DSD_MSBF_PLANAR_DECODER 0 #define CONFIG_DSICINAUDIO_DECODER 0 #define CONFIG_DSS_SP_DECODER 0 #define CONFIG_DST_DECODER 0 #define CONFIG_EAC3_DECODER 0 #define CONFIG_EVRC_DECODER 0 #define CONFIG_FFWAVESYNTH_DECODER 0 -#define CONFIG_FLAC_DECODER 0 +#define CONFIG_FLAC_DECODER 1 #define CONFIG_G723_1_DECODER 0 #define CONFIG_G729_DECODER 0 #define CONFIG_GSM_DECODER 0 #define CONFIG_GSM_MS_DECODER 0 #define CONFIG_IAC_DECODER 0 #define CONFIG_IMC_DECODER 0 #define CONFIG_INTERPLAY_ACM_DECODER 0 #define CONFIG_MACE3_DECODER 0 @@ -2099,17 +2099,17 @@ #define CONFIG_DCA_PARSER 0 #define CONFIG_DIRAC_PARSER 0 #define CONFIG_DNXHD_PARSER 0 #define CONFIG_DPX_PARSER 0 #define CONFIG_DVAUDIO_PARSER 0 #define CONFIG_DVBSUB_PARSER 0 #define CONFIG_DVDSUB_PARSER 0 #define CONFIG_DVD_NAV_PARSER 0 -#define CONFIG_FLAC_PARSER 0 +#define CONFIG_FLAC_PARSER 1 #define CONFIG_G729_PARSER 0 #define CONFIG_GSM_PARSER 0 #define CONFIG_H261_PARSER 0 #define CONFIG_H263_PARSER 0 #define CONFIG_H264_PARSER 0 #define CONFIG_HEVC_PARSER 0 #define CONFIG_MJPEG_PARSER 0 #define CONFIG_MLP_PARSER 0
--- a/media/ffvpx/config_win64.asm +++ b/media/ffvpx/config_win64.asm @@ -556,21 +556,21 @@ %define CONFIG_BSWAPDSP 0 %define CONFIG_CABAC 0 %define CONFIG_DIRAC_PARSE 0 %define CONFIG_DVPROFILE 0 %define CONFIG_EXIF 0 %define CONFIG_FAANDCT 0 %define CONFIG_FAANIDCT 0 %define CONFIG_FDCTDSP 0 -%define CONFIG_FLACDSP 0 +%define CONFIG_FLACDSP 1 %define CONFIG_FMTCONVERT 0 %define CONFIG_FRAME_THREAD_ENCODER 0 %define CONFIG_G722DSP 0 -%define CONFIG_GOLOMB 0 +%define CONFIG_GOLOMB 1 %define CONFIG_GPLV3 0 %define CONFIG_H263DSP 0 %define CONFIG_H264CHROMA 0 %define CONFIG_H264DSP 0 %define CONFIG_H264PRED 1 %define CONFIG_H264QPEL 0 %define CONFIG_HPELDSP 0 %define CONFIG_HUFFMAN 0 @@ -902,17 +902,17 @@ %define CONFIG_DSD_LSBF_PLANAR_DECODER 0 %define CONFIG_DSD_MSBF_PLANAR_DECODER 0 %define CONFIG_DSICINAUDIO_DECODER 0 %define CONFIG_DSS_SP_DECODER 0 %define CONFIG_DST_DECODER 0 %define CONFIG_EAC3_DECODER 0 %define CONFIG_EVRC_DECODER 0 %define CONFIG_FFWAVESYNTH_DECODER 0 -%define CONFIG_FLAC_DECODER 0 +%define CONFIG_FLAC_DECODER 1 %define CONFIG_G723_1_DECODER 0 %define CONFIG_G729_DECODER 0 %define CONFIG_GSM_DECODER 0 %define CONFIG_GSM_MS_DECODER 0 %define CONFIG_IAC_DECODER 0 %define CONFIG_IMC_DECODER 0 %define CONFIG_INTERPLAY_ACM_DECODER 0 %define CONFIG_MACE3_DECODER 0 @@ -2084,17 +2084,17 @@ %define CONFIG_DCA_PARSER 0 %define CONFIG_DIRAC_PARSER 0 %define CONFIG_DNXHD_PARSER 0 %define CONFIG_DPX_PARSER 0 %define CONFIG_DVAUDIO_PARSER 0 %define CONFIG_DVBSUB_PARSER 0 %define CONFIG_DVDSUB_PARSER 0 %define CONFIG_DVD_NAV_PARSER 0 -%define CONFIG_FLAC_PARSER 0 +%define CONFIG_FLAC_PARSER 1 %define CONFIG_G729_PARSER 0 %define CONFIG_GSM_PARSER 0 %define CONFIG_H261_PARSER 0 %define CONFIG_H263_PARSER 0 %define CONFIG_H264_PARSER 0 %define CONFIG_HEVC_PARSER 0 %define CONFIG_MJPEG_PARSER 0 %define CONFIG_MLP_PARSER 0
--- a/media/ffvpx/config_win64.h +++ b/media/ffvpx/config_win64.h @@ -571,21 +571,21 @@ #define CONFIG_BSWAPDSP 0 #define CONFIG_CABAC 0 #define CONFIG_DIRAC_PARSE 0 #define CONFIG_DVPROFILE 0 #define CONFIG_EXIF 0 #define CONFIG_FAANDCT 0 #define CONFIG_FAANIDCT 0 #define CONFIG_FDCTDSP 0 -#define CONFIG_FLACDSP 0 +#define CONFIG_FLACDSP 1 #define CONFIG_FMTCONVERT 0 #define CONFIG_FRAME_THREAD_ENCODER 0 #define CONFIG_G722DSP 0 -#define CONFIG_GOLOMB 0 +#define CONFIG_GOLOMB 1 #define CONFIG_GPLV3 0 #define CONFIG_H263DSP 0 #define CONFIG_H264CHROMA 0 #define CONFIG_H264DSP 0 #define CONFIG_H264PRED 1 #define CONFIG_H264QPEL 0 #define CONFIG_HPELDSP 0 #define CONFIG_HUFFMAN 0 @@ -917,17 +917,17 @@ #define CONFIG_DSD_LSBF_PLANAR_DECODER 0 #define CONFIG_DSD_MSBF_PLANAR_DECODER 0 #define CONFIG_DSICINAUDIO_DECODER 0 #define CONFIG_DSS_SP_DECODER 0 #define CONFIG_DST_DECODER 0 #define CONFIG_EAC3_DECODER 0 #define CONFIG_EVRC_DECODER 0 #define CONFIG_FFWAVESYNTH_DECODER 0 -#define CONFIG_FLAC_DECODER 0 +#define CONFIG_FLAC_DECODER 1 #define CONFIG_G723_1_DECODER 0 #define CONFIG_G729_DECODER 0 #define CONFIG_GSM_DECODER 0 #define CONFIG_GSM_MS_DECODER 0 #define CONFIG_IAC_DECODER 0 #define CONFIG_IMC_DECODER 0 #define CONFIG_INTERPLAY_ACM_DECODER 0 #define CONFIG_MACE3_DECODER 0 @@ -2099,17 +2099,17 @@ #define CONFIG_DCA_PARSER 0 #define CONFIG_DIRAC_PARSER 0 #define CONFIG_DNXHD_PARSER 0 #define CONFIG_DPX_PARSER 0 #define CONFIG_DVAUDIO_PARSER 0 #define CONFIG_DVBSUB_PARSER 0 #define CONFIG_DVDSUB_PARSER 0 #define CONFIG_DVD_NAV_PARSER 0 -#define CONFIG_FLAC_PARSER 0 +#define CONFIG_FLAC_PARSER 1 #define CONFIG_G729_PARSER 0 #define CONFIG_GSM_PARSER 0 #define CONFIG_H261_PARSER 0 #define CONFIG_H263_PARSER 0 #define CONFIG_H264_PARSER 0 #define CONFIG_HEVC_PARSER 0 #define CONFIG_MJPEG_PARSER 0 #define CONFIG_MLP_PARSER 0
--- a/media/ffvpx/libavcodec/dummy_funcs.c +++ b/media/ffvpx/libavcodec/dummy_funcs.c @@ -5,16 +5,17 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ #include "avcodec.h" typedef struct H264PredContext H264PredContext; typedef struct VideoDSPContext VideoDSPContext; typedef struct VP8DSPContext VP8DSPContext; typedef struct VP9DSPContext VP9DSPContext; +typedef struct FLACDSPContext FLACDSPContext; AVHWAccel ff_h263_vaapi_hwaccel; AVHWAccel ff_h263_vdpau_hwaccel; AVHWAccel ff_h263_videotoolbox_hwaccel; AVHWAccel ff_h264_d3d11va_hwaccel; AVHWAccel ff_h264_dxva2_hwaccel; AVHWAccel ff_h264_mmal_hwaccel; AVHWAccel ff_h264_qsv_hwaccel; @@ -395,17 +396,16 @@ AVCodec ff_dsd_lsbf_planar_decoder; AVCodec ff_dsd_msbf_planar_decoder; AVCodec ff_dsicinaudio_decoder; AVCodec ff_dss_sp_decoder; AVCodec ff_eac3_encoder; AVCodec ff_eac3_decoder; AVCodec ff_evrc_decoder; AVCodec ff_ffwavesynth_decoder; AVCodec ff_flac_encoder; -AVCodec ff_flac_decoder; AVCodec ff_g723_1_encoder; AVCodec ff_g723_1_decoder; AVCodec ff_g729_decoder; AVCodec ff_gsm_decoder; AVCodec ff_gsm_ms_decoder; AVCodec ff_iac_decoder; AVCodec ff_imc_decoder; AVCodec ff_mace3_decoder; @@ -724,17 +724,16 @@ AVCodecParser ff_cook_parser; AVCodecParser ff_dca_parser; AVCodecParser ff_dirac_parser; AVCodecParser ff_dnxhd_parser; AVCodecParser ff_dpx_parser; AVCodecParser ff_dvaudio_parser; AVCodecParser ff_dvbsub_parser; AVCodecParser ff_dvdsub_parser; AVCodecParser ff_dvd_nav_parser; -AVCodecParser ff_flac_parser; AVCodecParser ff_g729_parser; AVCodecParser ff_gsm_parser; AVCodecParser ff_h261_parser; AVCodecParser ff_h263_parser; AVCodecParser ff_h264_parser; AVCodecParser ff_hevc_parser; AVCodecParser ff_mjpeg_parser; AVCodecParser ff_mlp_parser; @@ -780,17 +779,23 @@ void ff_videodsp_init_aarch64(VideoDSPCo void ff_videodsp_init_arm(VideoDSPContext *ctx, int bpc) {} void ff_videodsp_init_ppc(VideoDSPContext *ctx, int bpc) {} void ff_vp7dsp_init(VP8DSPContext *c) {} void ff_vp78dsp_init_arm(VP8DSPContext *c) {} void ff_vp78dsp_init_ppc(VP8DSPContext *c) {} void ff_vp8dsp_init_arm(VP8DSPContext *c) {} void ff_vp8dsp_init_mips(VP8DSPContext *c) {} void ff_vp9dsp_init_mips(VP9DSPContext *dsp, int bpp) {} - +void ff_flacdsp_init_arm(FLACDSPContext *c, enum AVSampleFormat fmt, int channels, int bps) {} +#if !defined(HAVE_64BIT_BUILD) +void ff_flac_decorrelate_indep8_16_sse2(uint8_t **out, int32_t **in, int channels, int len, int shift) {} +void ff_flac_decorrelate_indep8_32_avx(uint8_t **out, int32_t **in, int channels, int len, int shift) {} +void ff_flac_decorrelate_indep8_16_avx(uint8_t **out, int32_t **in, int channels, int len, int shift) {} +void ff_flac_decorrelate_indep8_32_sse2(uint8_t **out, int32_t **in, int channels, int len, int shift) {} +#endif void av_bitstream_filter_close(AVBitStreamFilterContext *bsf) {} int av_bitstream_filter_filter(AVBitStreamFilterContext *bsfc, AVCodecContext *avctx, const char *args, uint8_t **poutbuf, int *poutbuf_size, const uint8_t *buf, int buf_size, int keyframe) { return 0; } AVBitStreamFilterContext *av_bitstream_filter_init(const char *name) { return NULL;} AVBitStreamFilter *av_bitstream_filter_next(const AVBitStreamFilter *f) { return NULL; } void av_register_bitstream_filter(AVBitStreamFilter *bsf) {}
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/flac.c @@ -0,0 +1,237 @@ +/* + * FLAC common code + * Copyright (c) 2009 Justin Ruggles + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include "libavutil/channel_layout.h" +#include "libavutil/crc.h" +#include "libavutil/log.h" +#include "bytestream.h" +#include "get_bits.h" +#include "flac.h" +#include "flacdata.h" + +static const int8_t sample_size_table[] = { 0, 8, 12, 0, 16, 20, 24, 0 }; + +static const uint64_t flac_channel_layouts[8] = { + AV_CH_LAYOUT_MONO, + AV_CH_LAYOUT_STEREO, + AV_CH_LAYOUT_SURROUND, + AV_CH_LAYOUT_QUAD, + AV_CH_LAYOUT_5POINT0, + AV_CH_LAYOUT_5POINT1, + AV_CH_LAYOUT_6POINT1, + AV_CH_LAYOUT_7POINT1 +}; + +static int64_t get_utf8(GetBitContext *gb) +{ + int64_t val; + GET_UTF8(val, get_bits(gb, 8), return -1;) + return val; +} + +int ff_flac_decode_frame_header(AVCodecContext *avctx, GetBitContext *gb, + FLACFrameInfo *fi, int log_level_offset) +{ + int bs_code, sr_code, bps_code; + + /* frame sync code */ + if ((get_bits(gb, 15) & 0x7FFF) != 0x7FFC) { + av_log(avctx, AV_LOG_ERROR + log_level_offset, "invalid sync code\n"); + return AVERROR_INVALIDDATA; + } + + /* variable block size stream code */ + fi->is_var_size = get_bits1(gb); + + /* block size and sample rate codes */ + bs_code = get_bits(gb, 4); + sr_code = get_bits(gb, 4); + + /* channels and decorrelation */ + fi->ch_mode = get_bits(gb, 4); + if (fi->ch_mode < FLAC_MAX_CHANNELS) { + fi->channels = fi->ch_mode + 1; + fi->ch_mode = FLAC_CHMODE_INDEPENDENT; + } else if (fi->ch_mode < FLAC_MAX_CHANNELS + FLAC_CHMODE_MID_SIDE) { + fi->channels = 2; + fi->ch_mode -= FLAC_MAX_CHANNELS - 1; + } else { + av_log(avctx, AV_LOG_ERROR + log_level_offset, + "invalid channel mode: %d\n", fi->ch_mode); + return AVERROR_INVALIDDATA; + } + + /* bits per sample */ + bps_code = get_bits(gb, 3); + if (bps_code == 3 || bps_code == 7) { + av_log(avctx, AV_LOG_ERROR + log_level_offset, + "invalid sample size code (%d)\n", + bps_code); + return AVERROR_INVALIDDATA; + } + fi->bps = sample_size_table[bps_code]; + + /* reserved bit */ + if (get_bits1(gb)) { + av_log(avctx, AV_LOG_ERROR + log_level_offset, + "broken stream, invalid padding\n"); + return AVERROR_INVALIDDATA; + } + + /* sample or frame count */ + fi->frame_or_sample_num = get_utf8(gb); + if (fi->frame_or_sample_num < 0) { + av_log(avctx, AV_LOG_ERROR + log_level_offset, + "sample/frame number invalid; utf8 fscked\n"); + return AVERROR_INVALIDDATA; + } + + /* blocksize */ + if (bs_code == 0) { + av_log(avctx, AV_LOG_ERROR + log_level_offset, + "reserved blocksize code: 0\n"); + return AVERROR_INVALIDDATA; + } else if (bs_code == 6) { + fi->blocksize = get_bits(gb, 8) + 1; + } else if (bs_code == 7) { + fi->blocksize = get_bits(gb, 16) + 1; + } else { + fi->blocksize = ff_flac_blocksize_table[bs_code]; + } + + /* sample rate */ + if (sr_code < 12) { + fi->samplerate = ff_flac_sample_rate_table[sr_code]; + } else if (sr_code == 12) { + fi->samplerate = get_bits(gb, 8) * 1000; + } else if (sr_code == 13) { + fi->samplerate = get_bits(gb, 16); + } else if (sr_code == 14) { + fi->samplerate = get_bits(gb, 16) * 10; + } else { + av_log(avctx, AV_LOG_ERROR + log_level_offset, + "illegal sample rate code %d\n", + sr_code); + return AVERROR_INVALIDDATA; + } + + /* header CRC-8 check */ + skip_bits(gb, 8); + if (av_crc(av_crc_get_table(AV_CRC_8_ATM), 0, gb->buffer, + get_bits_count(gb)/8)) { + av_log(avctx, AV_LOG_ERROR + log_level_offset, + "header crc mismatch\n"); + return AVERROR_INVALIDDATA; + } + + return 0; +} + +int ff_flac_get_max_frame_size(int blocksize, int ch, int bps) +{ + /* Technically, there is no limit to FLAC frame size, but an encoder + should not write a frame that is larger than if verbatim encoding mode + were to be used. */ + + int count; + + count = 16; /* frame header */ + count += ch * ((7+bps+7)/8); /* subframe headers */ + if (ch == 2) { + /* for stereo, need to account for using decorrelation */ + count += (( 2*bps+1) * blocksize + 7) / 8; + } else { + count += ( ch*bps * blocksize + 7) / 8; + } + count += 2; /* frame footer */ + + return count; +} + +int ff_flac_is_extradata_valid(AVCodecContext *avctx, + enum FLACExtradataFormat *format, + uint8_t **streaminfo_start) +{ + if (!avctx->extradata || avctx->extradata_size < FLAC_STREAMINFO_SIZE) { + av_log(avctx, AV_LOG_ERROR, "extradata NULL or too small.\n"); + return 0; + } + if (AV_RL32(avctx->extradata) != MKTAG('f','L','a','C')) { + /* extradata contains STREAMINFO only */ + if (avctx->extradata_size != FLAC_STREAMINFO_SIZE) { + av_log(avctx, AV_LOG_WARNING, "extradata contains %d bytes too many.\n", + FLAC_STREAMINFO_SIZE-avctx->extradata_size); + } + *format = FLAC_EXTRADATA_FORMAT_STREAMINFO; + *streaminfo_start = avctx->extradata; + } else { + if (avctx->extradata_size < 8+FLAC_STREAMINFO_SIZE) { + av_log(avctx, AV_LOG_ERROR, "extradata too small.\n"); + return 0; + } + *format = FLAC_EXTRADATA_FORMAT_FULL_HEADER; + *streaminfo_start = &avctx->extradata[8]; + } + return 1; +} + +void ff_flac_set_channel_layout(AVCodecContext *avctx) +{ + if (avctx->channels <= FF_ARRAY_ELEMS(flac_channel_layouts)) + avctx->channel_layout = flac_channel_layouts[avctx->channels - 1]; + else + avctx->channel_layout = 0; +} + +void ff_flac_parse_streaminfo(AVCodecContext *avctx, struct FLACStreaminfo *s, + const uint8_t *buffer) +{ + GetBitContext gb; + init_get_bits(&gb, buffer, FLAC_STREAMINFO_SIZE*8); + + skip_bits(&gb, 16); /* skip min blocksize */ + s->max_blocksize = get_bits(&gb, 16); + if (s->max_blocksize < FLAC_MIN_BLOCKSIZE) { + av_log(avctx, AV_LOG_WARNING, "invalid max blocksize: %d\n", + s->max_blocksize); + s->max_blocksize = 16; + } + + skip_bits(&gb, 24); /* skip min frame size */ + s->max_framesize = get_bits_long(&gb, 24); + + s->samplerate = get_bits_long(&gb, 20); + s->channels = get_bits(&gb, 3) + 1; + s->bps = get_bits(&gb, 5) + 1; + + avctx->channels = s->channels; + avctx->sample_rate = s->samplerate; + avctx->bits_per_raw_sample = s->bps; + + if (!avctx->channel_layout || + av_get_channel_layout_nb_channels(avctx->channel_layout) != avctx->channels) + ff_flac_set_channel_layout(avctx); + + s->samples = get_bits64(&gb, 36); + + skip_bits_long(&gb, 64); /* md5 sum */ + skip_bits_long(&gb, 64); /* md5 sum */ +}
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/flac.h @@ -0,0 +1,153 @@ +/* + * FLAC (Free Lossless Audio Codec) decoder/demuxer common functions + * Copyright (c) 2008 Justin Ruggles + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/** + * @file + * FLAC (Free Lossless Audio Codec) decoder/demuxer common functions + */ + +#ifndef AVCODEC_FLAC_H +#define AVCODEC_FLAC_H + +#include "avcodec.h" +#include "bytestream.h" +#include "get_bits.h" + +#define FLAC_STREAMINFO_SIZE 34 +#define FLAC_MAX_CHANNELS 8 +#define FLAC_MIN_BLOCKSIZE 16 +#define FLAC_MAX_BLOCKSIZE 65535 +#define FLAC_MIN_FRAME_SIZE 11 + +enum { + FLAC_CHMODE_INDEPENDENT = 0, + FLAC_CHMODE_LEFT_SIDE = 1, + FLAC_CHMODE_RIGHT_SIDE = 2, + FLAC_CHMODE_MID_SIDE = 3, +}; + +enum { + FLAC_METADATA_TYPE_STREAMINFO = 0, + FLAC_METADATA_TYPE_PADDING, + FLAC_METADATA_TYPE_APPLICATION, + FLAC_METADATA_TYPE_SEEKTABLE, + FLAC_METADATA_TYPE_VORBIS_COMMENT, + FLAC_METADATA_TYPE_CUESHEET, + FLAC_METADATA_TYPE_PICTURE, + FLAC_METADATA_TYPE_INVALID = 127 +}; + +enum FLACExtradataFormat { + FLAC_EXTRADATA_FORMAT_STREAMINFO = 0, + FLAC_EXTRADATA_FORMAT_FULL_HEADER = 1 +}; + +#define FLACCOMMONINFO \ + int samplerate; /**< sample rate */\ + int channels; /**< number of channels */\ + int bps; /**< bits-per-sample */\ + +/** + * Data needed from the Streaminfo header for use by the raw FLAC demuxer + * and/or the FLAC decoder. + */ +#define FLACSTREAMINFO \ + FLACCOMMONINFO \ + int max_blocksize; /**< maximum block size, in samples */\ + int max_framesize; /**< maximum frame size, in bytes */\ + int64_t samples; /**< total number of samples */\ + +typedef struct FLACStreaminfo { + FLACSTREAMINFO +} FLACStreaminfo; + +typedef struct FLACFrameInfo { + FLACCOMMONINFO + int blocksize; /**< block size of the frame */ + int ch_mode; /**< channel decorrelation mode */ + int64_t frame_or_sample_num; /**< frame number or sample number */ + int is_var_size; /**< specifies if the stream uses variable + block sizes or a fixed block size; + also determines the meaning of + frame_or_sample_num */ +} FLACFrameInfo; + +/** + * Parse the Streaminfo metadata block + * @param[out] avctx codec context to set basic stream parameters + * @param[out] s where parsed information is stored + * @param[in] buffer pointer to start of 34-byte streaminfo data + */ +void ff_flac_parse_streaminfo(AVCodecContext *avctx, struct FLACStreaminfo *s, + const uint8_t *buffer); + +/** + * Validate the FLAC extradata. + * @param[in] avctx codec context containing the extradata. + * @param[out] format extradata format. + * @param[out] streaminfo_start pointer to start of 34-byte STREAMINFO data. + * @return 1 if valid, 0 if not valid. + */ +int ff_flac_is_extradata_valid(AVCodecContext *avctx, + enum FLACExtradataFormat *format, + uint8_t **streaminfo_start); + +/** + * Calculate an estimate for the maximum frame size based on verbatim mode. + * @param blocksize block size, in samples + * @param ch number of channels + * @param bps bits-per-sample + */ +int ff_flac_get_max_frame_size(int blocksize, int ch, int bps); + +/** + * Validate and decode a frame header. + * @param avctx AVCodecContext to use as av_log() context + * @param gb GetBitContext from which to read frame header + * @param[out] fi frame information + * @param log_level_offset log level offset. can be used to silence error messages. + * @return non-zero on error, 0 if ok + */ +int ff_flac_decode_frame_header(AVCodecContext *avctx, GetBitContext *gb, + FLACFrameInfo *fi, int log_level_offset); + +void ff_flac_set_channel_layout(AVCodecContext *avctx); + +/** + * Parse the metadata block parameters from the header. + * @param[in] block_header header data, at least 4 bytes + * @param[out] last indicator for last metadata block + * @param[out] type metadata block type + * @param[out] size metadata block size + */ +static av_always_inline void flac_parse_block_header(const uint8_t *block_header, + int *last, int *type, int *size) +{ + int tmp = bytestream_get_byte(&block_header); + if (last) + *last = tmp & 0x80; + if (type) + *type = tmp & 0x7F; + if (size) + *size = bytestream_get_be24(&block_header); +} + +#endif /* AVCODEC_FLAC_H */
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/flac_parser.c @@ -0,0 +1,755 @@ +/* + * FLAC parser + * Copyright (c) 2010 Michael Chinen + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/** + * @file + * FLAC parser + * + * The FLAC parser buffers input until FLAC_MIN_HEADERS has been found. + * Each time it finds and verifies a CRC-8 header it sees which of the + * FLAC_MAX_SEQUENTIAL_HEADERS that came before it have a valid CRC-16 footer + * that ends at the newly found header. + * Headers are scored by FLAC_HEADER_BASE_SCORE plus the max of its crc-verified + * children, penalized by changes in sample rate, frame number, etc. + * The parser returns the frame with the highest score. + **/ + +#include "libavutil/attributes.h" +#include "libavutil/crc.h" +#include "libavutil/fifo.h" +#include "bytestream.h" +#include "parser.h" +#include "flac.h" + +/** maximum number of adjacent headers that compare CRCs against each other */ +#define FLAC_MAX_SEQUENTIAL_HEADERS 4 +/** minimum number of headers buffered and checked before returning frames */ +#define FLAC_MIN_HEADERS 10 +/** estimate for average size of a FLAC frame */ +#define FLAC_AVG_FRAME_SIZE 8192 + +/** scoring settings for score_header */ +#define FLAC_HEADER_BASE_SCORE 10 +#define FLAC_HEADER_CHANGED_PENALTY 7 +#define FLAC_HEADER_CRC_FAIL_PENALTY 50 +#define FLAC_HEADER_NOT_PENALIZED_YET 100000 +#define FLAC_HEADER_NOT_SCORED_YET -100000 + +/** largest possible size of flac header */ +#define MAX_FRAME_HEADER_SIZE 16 + +typedef struct FLACHeaderMarker { + int offset; /**< byte offset from start of FLACParseContext->buffer */ + int *link_penalty; /**< pointer to array of local scores between this header + and the one at a distance equal array position */ + int max_score; /**< maximum score found after checking each child that + has a valid CRC */ + FLACFrameInfo fi; /**< decoded frame header info */ + struct FLACHeaderMarker *next; /**< next CRC-8 verified header that + immediately follows this one in + the bytestream */ + struct FLACHeaderMarker *best_child; /**< following frame header with + which this frame has the best + score with */ +} FLACHeaderMarker; + +typedef struct FLACParseContext { + AVCodecParserContext *pc; /**< parent context */ + AVCodecContext *avctx; /**< codec context pointer for logging */ + FLACHeaderMarker *headers; /**< linked-list that starts at the first + CRC-8 verified header within buffer */ + FLACHeaderMarker *best_header; /**< highest scoring header within buffer */ + int nb_headers_found; /**< number of headers found in the last + flac_parse() call */ + int nb_headers_buffered; /**< number of headers that are buffered */ + int best_header_valid; /**< flag set when the parser returns junk; + if set return best_header next time */ + AVFifoBuffer *fifo_buf; /**< buffer to store all data until headers + can be verified */ + int end_padded; /**< specifies if fifo_buf's end is padded */ + uint8_t *wrap_buf; /**< general fifo read buffer when wrapped */ + int wrap_buf_allocated_size; /**< actual allocated size of the buffer */ + FLACFrameInfo last_fi; /**< last decoded frame header info */ + int last_fi_valid; /**< set if last_fi is valid */ +} FLACParseContext; + +static int frame_header_is_valid(AVCodecContext *avctx, const uint8_t *buf, + FLACFrameInfo *fi) +{ + GetBitContext gb; + init_get_bits(&gb, buf, MAX_FRAME_HEADER_SIZE * 8); + return !ff_flac_decode_frame_header(avctx, &gb, fi, 127); +} + +/** + * Non-destructive fast fifo pointer fetching + * Returns a pointer from the specified offset. + * If possible the pointer points within the fifo buffer. + * Otherwise (if it would cause a wrap around,) a pointer to a user-specified + * buffer is used. + * The pointer can be NULL. In any case it will be reallocated to hold the size. + * If the returned pointer will be used after subsequent calls to flac_fifo_read_wrap + * then the subsequent calls should pass in a different wrap_buf so as to not + * overwrite the contents of the previous wrap_buf. + * This function is based on av_fifo_generic_read, which is why there is a comment + * about a memory barrier for SMP. + */ +static uint8_t* flac_fifo_read_wrap(FLACParseContext *fpc, int offset, int len, + uint8_t** wrap_buf, int* allocated_size) +{ + AVFifoBuffer *f = fpc->fifo_buf; + uint8_t *start = f->rptr + offset; + uint8_t *tmp_buf; + + if (start >= f->end) + start -= f->end - f->buffer; + if (f->end - start >= len) + return start; + + tmp_buf = av_fast_realloc(*wrap_buf, allocated_size, len); + + if (!tmp_buf) { + av_log(fpc->avctx, AV_LOG_ERROR, + "couldn't reallocate wrap buffer of size %d", len); + return NULL; + } + *wrap_buf = tmp_buf; + do { + int seg_len = FFMIN(f->end - start, len); + memcpy(tmp_buf, start, seg_len); + tmp_buf = (uint8_t*)tmp_buf + seg_len; +// memory barrier needed for SMP here in theory + + start += seg_len - (f->end - f->buffer); + len -= seg_len; + } while (len > 0); + + return *wrap_buf; +} + +/** + * Return a pointer in the fifo buffer where the offset starts at until + * the wrap point or end of request. + * len will contain the valid length of the returned buffer. + * A second call to flac_fifo_read (with new offset and len) should be called + * to get the post-wrap buf if the returned len is less than the requested. + **/ +static uint8_t* flac_fifo_read(FLACParseContext *fpc, int offset, int *len) +{ + AVFifoBuffer *f = fpc->fifo_buf; + uint8_t *start = f->rptr + offset; + + if (start >= f->end) + start -= f->end - f->buffer; + *len = FFMIN(*len, f->end - start); + return start; +} + +static int find_headers_search_validate(FLACParseContext *fpc, int offset) +{ + FLACFrameInfo fi; + uint8_t *header_buf; + int size = 0; + header_buf = flac_fifo_read_wrap(fpc, offset, + MAX_FRAME_HEADER_SIZE, + &fpc->wrap_buf, + &fpc->wrap_buf_allocated_size); + if (frame_header_is_valid(fpc->avctx, header_buf, &fi)) { + FLACHeaderMarker **end_handle = &fpc->headers; + int i; + + size = 0; + while (*end_handle) { + end_handle = &(*end_handle)->next; + size++; + } + + *end_handle = av_mallocz(sizeof(**end_handle)); + if (!*end_handle) { + av_log(fpc->avctx, AV_LOG_ERROR, + "couldn't allocate FLACHeaderMarker\n"); + return AVERROR(ENOMEM); + } + (*end_handle)->fi = fi; + (*end_handle)->offset = offset; + (*end_handle)->link_penalty = av_malloc(sizeof(int) * + FLAC_MAX_SEQUENTIAL_HEADERS); + if (!(*end_handle)->link_penalty) { + av_freep(end_handle); + av_log(fpc->avctx, AV_LOG_ERROR, + "couldn't allocate link_penalty\n"); + return AVERROR(ENOMEM); + } + + for (i = 0; i < FLAC_MAX_SEQUENTIAL_HEADERS; i++) + (*end_handle)->link_penalty[i] = FLAC_HEADER_NOT_PENALIZED_YET; + + fpc->nb_headers_found++; + size++; + } + return size; +} + +static int find_headers_search(FLACParseContext *fpc, uint8_t *buf, int buf_size, + int search_start) + +{ + int size = 0, mod_offset = (buf_size - 1) % 4, i, j; + uint32_t x; + + for (i = 0; i < mod_offset; i++) { + if ((AV_RB16(buf + i) & 0xFFFE) == 0xFFF8) + size = find_headers_search_validate(fpc, search_start + i); + } + + for (; i < buf_size - 1; i += 4) { + x = AV_RB32(buf + i); + if (((x & ~(x + 0x01010101)) & 0x80808080)) { + for (j = 0; j < 4; j++) { + if ((AV_RB16(buf + i + j) & 0xFFFE) == 0xFFF8) + size = find_headers_search_validate(fpc, search_start + i + j); + } + } + } + return size; +} + +static int find_new_headers(FLACParseContext *fpc, int search_start) +{ + FLACHeaderMarker *end; + int search_end, size = 0, read_len, temp; + uint8_t *buf; + fpc->nb_headers_found = 0; + + /* Search for a new header of at most 16 bytes. */ + search_end = av_fifo_size(fpc->fifo_buf) - (MAX_FRAME_HEADER_SIZE - 1); + read_len = search_end - search_start + 1; + buf = flac_fifo_read(fpc, search_start, &read_len); + size = find_headers_search(fpc, buf, read_len, search_start); + search_start += read_len - 1; + + /* If fifo end was hit do the wrap around. */ + if (search_start != search_end) { + uint8_t wrap[2]; + + wrap[0] = buf[read_len - 1]; + read_len = search_end - search_start + 1; + + /* search_start + 1 is the post-wrap offset in the fifo. */ + buf = flac_fifo_read(fpc, search_start + 1, &read_len); + wrap[1] = buf[0]; + + if ((AV_RB16(wrap) & 0xFFFE) == 0xFFF8) { + temp = find_headers_search_validate(fpc, search_start); + size = FFMAX(size, temp); + } + search_start++; + + /* Continue to do the last half of the wrap. */ + temp = find_headers_search(fpc, buf, read_len, search_start); + size = FFMAX(size, temp); + search_start += read_len - 1; + } + + /* Return the size even if no new headers were found. */ + if (!size && fpc->headers) + for (end = fpc->headers; end; end = end->next) + size++; + return size; +} + +static int check_header_fi_mismatch(FLACParseContext *fpc, + FLACFrameInfo *header_fi, + FLACFrameInfo *child_fi, + int log_level_offset) +{ + int deduction = 0; + if (child_fi->samplerate != header_fi->samplerate) { + deduction += FLAC_HEADER_CHANGED_PENALTY; + av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset, + "sample rate change detected in adjacent frames\n"); + } + if (child_fi->bps != header_fi->bps) { + deduction += FLAC_HEADER_CHANGED_PENALTY; + av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset, + "bits per sample change detected in adjacent frames\n"); + } + if (child_fi->is_var_size != header_fi->is_var_size) { + /* Changing blocking strategy not allowed per the spec */ + deduction += FLAC_HEADER_BASE_SCORE; + av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset, + "blocking strategy change detected in adjacent frames\n"); + } + if (child_fi->channels != header_fi->channels) { + deduction += FLAC_HEADER_CHANGED_PENALTY; + av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset, + "number of channels change detected in adjacent frames\n"); + } + return deduction; +} + +static int check_header_mismatch(FLACParseContext *fpc, + FLACHeaderMarker *header, + FLACHeaderMarker *child, + int log_level_offset) +{ + FLACFrameInfo *header_fi = &header->fi, *child_fi = &child->fi; + int deduction, deduction_expected = 0, i; + deduction = check_header_fi_mismatch(fpc, header_fi, child_fi, + log_level_offset); + /* Check sample and frame numbers. */ + if ((child_fi->frame_or_sample_num - header_fi->frame_or_sample_num + != header_fi->blocksize) && + (child_fi->frame_or_sample_num + != header_fi->frame_or_sample_num + 1)) { + FLACHeaderMarker *curr; + int expected_frame_num, expected_sample_num; + /* If there are frames in the middle we expect this deduction, + as they are probably valid and this one follows it */ + + expected_frame_num = expected_sample_num = header_fi->frame_or_sample_num; + curr = header; + while (curr != child) { + /* Ignore frames that failed all crc checks */ + for (i = 0; i < FLAC_MAX_SEQUENTIAL_HEADERS; i++) { + if (curr->link_penalty[i] < FLAC_HEADER_CRC_FAIL_PENALTY) { + expected_frame_num++; + expected_sample_num += curr->fi.blocksize; + break; + } + } + curr = curr->next; + } + + if (expected_frame_num == child_fi->frame_or_sample_num || + expected_sample_num == child_fi->frame_or_sample_num) + deduction_expected = deduction ? 0 : 1; + + deduction += FLAC_HEADER_CHANGED_PENALTY; + av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset, + "sample/frame number mismatch in adjacent frames\n"); + } + + /* If we have suspicious headers, check the CRC between them */ + if (deduction && !deduction_expected) { + FLACHeaderMarker *curr; + int read_len; + uint8_t *buf; + uint32_t crc = 1; + int inverted_test = 0; + + /* Since CRC is expensive only do it if we haven't yet. + This assumes a CRC penalty is greater than all other check penalties */ + curr = header->next; + for (i = 0; i < FLAC_MAX_SEQUENTIAL_HEADERS && curr != child; i++) + curr = curr->next; + + if (header->link_penalty[i] < FLAC_HEADER_CRC_FAIL_PENALTY || + header->link_penalty[i] == FLAC_HEADER_NOT_PENALIZED_YET) { + FLACHeaderMarker *start, *end; + + /* Although overlapping chains are scored, the crc should never + have to be computed twice for a single byte. */ + start = header; + end = child; + if (i > 0 && + header->link_penalty[i - 1] >= FLAC_HEADER_CRC_FAIL_PENALTY) { + while (start->next != child) + start = start->next; + inverted_test = 1; + } else if (i > 0 && + header->next->link_penalty[i-1] >= + FLAC_HEADER_CRC_FAIL_PENALTY ) { + end = header->next; + inverted_test = 1; + } + + read_len = end->offset - start->offset; + buf = flac_fifo_read(fpc, start->offset, &read_len); + crc = av_crc(av_crc_get_table(AV_CRC_16_ANSI), 0, buf, read_len); + read_len = (end->offset - start->offset) - read_len; + + if (read_len) { + buf = flac_fifo_read(fpc, end->offset - read_len, &read_len); + crc = av_crc(av_crc_get_table(AV_CRC_16_ANSI), crc, buf, read_len); + } + } + + if (!crc ^ !inverted_test) { + deduction += FLAC_HEADER_CRC_FAIL_PENALTY; + av_log(fpc->avctx, AV_LOG_WARNING + log_level_offset, + "crc check failed from offset %i (frame %"PRId64") to %i (frame %"PRId64")\n", + header->offset, header_fi->frame_or_sample_num, + child->offset, child_fi->frame_or_sample_num); + } + } + return deduction; +} + +/** + * Score a header. + * + * Give FLAC_HEADER_BASE_SCORE points to a frame for existing. + * If it has children, (subsequent frames of which the preceding CRC footer + * validates against this one,) then take the maximum score of the children, + * with a penalty of FLAC_HEADER_CHANGED_PENALTY applied for each change to + * bps, sample rate, channels, but not decorrelation mode, or blocksize, + * because it can change often. + **/ +static int score_header(FLACParseContext *fpc, FLACHeaderMarker *header) +{ + FLACHeaderMarker *child; + int dist = 0; + int child_score; + int base_score = FLAC_HEADER_BASE_SCORE; + if (header->max_score != FLAC_HEADER_NOT_SCORED_YET) + return header->max_score; + + /* Modify the base score with changes from the last output header */ + if (fpc->last_fi_valid) { + /* Silence the log since this will be repeated if selected */ + base_score -= check_header_fi_mismatch(fpc, &fpc->last_fi, &header->fi, + AV_LOG_DEBUG); + } + + header->max_score = base_score; + + /* Check and compute the children's scores. */ + child = header->next; + for (dist = 0; dist < FLAC_MAX_SEQUENTIAL_HEADERS && child; dist++) { + /* Look at the child's frame header info and penalize suspicious + changes between the headers. */ + if (header->link_penalty[dist] == FLAC_HEADER_NOT_PENALIZED_YET) { + header->link_penalty[dist] = check_header_mismatch(fpc, header, + child, AV_LOG_DEBUG); + } + child_score = score_header(fpc, child) - header->link_penalty[dist]; + + if (FLAC_HEADER_BASE_SCORE + child_score > header->max_score) { + /* Keep the child because the frame scoring is dynamic. */ + header->best_child = child; + header->max_score = base_score + child_score; + } + child = child->next; + } + + return header->max_score; +} + +static void score_sequences(FLACParseContext *fpc) +{ + FLACHeaderMarker *curr; + int best_score = 0;//FLAC_HEADER_NOT_SCORED_YET; + /* First pass to clear all old scores. */ + for (curr = fpc->headers; curr; curr = curr->next) + curr->max_score = FLAC_HEADER_NOT_SCORED_YET; + + /* Do a second pass to score them all. */ + for (curr = fpc->headers; curr; curr = curr->next) { + if (score_header(fpc, curr) > best_score) { + fpc->best_header = curr; + best_score = curr->max_score; + } + } +} + +static int get_best_header(FLACParseContext* fpc, const uint8_t **poutbuf, + int *poutbuf_size) +{ + FLACHeaderMarker *header = fpc->best_header; + FLACHeaderMarker *child = header->best_child; + if (!child) { + *poutbuf_size = av_fifo_size(fpc->fifo_buf) - header->offset; + } else { + *poutbuf_size = child->offset - header->offset; + + /* If the child has suspicious changes, log them */ + check_header_mismatch(fpc, header, child, 0); + } + + if (header->fi.channels != fpc->avctx->channels || + !fpc->avctx->channel_layout) { + fpc->avctx->channels = header->fi.channels; + ff_flac_set_channel_layout(fpc->avctx); + } + fpc->avctx->sample_rate = header->fi.samplerate; + fpc->pc->duration = header->fi.blocksize; + *poutbuf = flac_fifo_read_wrap(fpc, header->offset, *poutbuf_size, + &fpc->wrap_buf, + &fpc->wrap_buf_allocated_size); + + + if (fpc->pc->flags & PARSER_FLAG_USE_CODEC_TS){ + if (header->fi.is_var_size) + fpc->pc->pts = header->fi.frame_or_sample_num; + else if (header->best_child) + fpc->pc->pts = header->fi.frame_or_sample_num * header->fi.blocksize; + } + + fpc->best_header_valid = 0; + fpc->last_fi_valid = 1; + fpc->last_fi = header->fi; + + /* Return the negative overread index so the client can compute pos. + This should be the amount overread to the beginning of the child */ + if (child) + return child->offset - av_fifo_size(fpc->fifo_buf); + return 0; +} + +static int flac_parse(AVCodecParserContext *s, AVCodecContext *avctx, + const uint8_t **poutbuf, int *poutbuf_size, + const uint8_t *buf, int buf_size) +{ + FLACParseContext *fpc = s->priv_data; + FLACHeaderMarker *curr; + int nb_headers; + const uint8_t *read_end = buf; + const uint8_t *read_start = buf; + + if (s->flags & PARSER_FLAG_COMPLETE_FRAMES) { + FLACFrameInfo fi; + if (frame_header_is_valid(avctx, buf, &fi)) { + s->duration = fi.blocksize; + if (!avctx->sample_rate) + avctx->sample_rate = fi.samplerate; + if (fpc->pc->flags & PARSER_FLAG_USE_CODEC_TS){ + fpc->pc->pts = fi.frame_or_sample_num; + if (!fi.is_var_size) + fpc->pc->pts *= fi.blocksize; + } + } + *poutbuf = buf; + *poutbuf_size = buf_size; + return buf_size; + } + + fpc->avctx = avctx; + if (fpc->best_header_valid) + return get_best_header(fpc, poutbuf, poutbuf_size); + + /* If a best_header was found last call remove it with the buffer data. */ + if (fpc->best_header && fpc->best_header->best_child) { + FLACHeaderMarker *temp; + FLACHeaderMarker *best_child = fpc->best_header->best_child; + + /* Remove headers in list until the end of the best_header. */ + for (curr = fpc->headers; curr != best_child; curr = temp) { + if (curr != fpc->best_header) { + av_log(avctx, AV_LOG_DEBUG, + "dropping low score %i frame header from offset %i to %i\n", + curr->max_score, curr->offset, curr->next->offset); + } + temp = curr->next; + av_freep(&curr->link_penalty); + av_free(curr); + fpc->nb_headers_buffered--; + } + /* Release returned data from ring buffer. */ + av_fifo_drain(fpc->fifo_buf, best_child->offset); + + /* Fix the offset for the headers remaining to match the new buffer. */ + for (curr = best_child->next; curr; curr = curr->next) + curr->offset -= best_child->offset; + + fpc->nb_headers_buffered--; + best_child->offset = 0; + fpc->headers = best_child; + if (fpc->nb_headers_buffered >= FLAC_MIN_HEADERS) { + fpc->best_header = best_child; + return get_best_header(fpc, poutbuf, poutbuf_size); + } + fpc->best_header = NULL; + } else if (fpc->best_header) { + /* No end frame no need to delete the buffer; probably eof */ + FLACHeaderMarker *temp; + + for (curr = fpc->headers; curr != fpc->best_header; curr = temp) { + temp = curr->next; + av_freep(&curr->link_penalty); + av_free(curr); + } + fpc->headers = fpc->best_header->next; + av_freep(&fpc->best_header->link_penalty); + av_freep(&fpc->best_header); + } + + /* Find and score new headers. */ + /* buf_size is to zero when padding, so check for this since we do */ + /* not want to try to read more input once we have found the end. */ + /* Note that as (non-modified) parameters, buf can be non-NULL, */ + /* while buf_size is 0. */ + while ((buf && buf_size && read_end < buf + buf_size && + fpc->nb_headers_buffered < FLAC_MIN_HEADERS) + || ((!buf || !buf_size) && !fpc->end_padded)) { + int start_offset; + + /* Pad the end once if EOF, to check the final region for headers. */ + if (!buf || !buf_size) { + fpc->end_padded = 1; + buf_size = MAX_FRAME_HEADER_SIZE; + read_end = read_start + MAX_FRAME_HEADER_SIZE; + } else { + /* The maximum read size is the upper-bound of what the parser + needs to have the required number of frames buffered */ + int nb_desired = FLAC_MIN_HEADERS - fpc->nb_headers_buffered + 1; + read_end = read_end + FFMIN(buf + buf_size - read_end, + nb_desired * FLAC_AVG_FRAME_SIZE); + } + + if (!av_fifo_space(fpc->fifo_buf) && + av_fifo_size(fpc->fifo_buf) / FLAC_AVG_FRAME_SIZE > + fpc->nb_headers_buffered * 20) { + /* There is less than one valid flac header buffered for 20 headers + * buffered. Therefore the fifo is most likely filled with invalid + * data and the input is not a flac file. */ + goto handle_error; + } + + /* Fill the buffer. */ + if ( av_fifo_space(fpc->fifo_buf) < read_end - read_start + && av_fifo_realloc2(fpc->fifo_buf, (read_end - read_start) + 2*av_fifo_size(fpc->fifo_buf)) < 0) { + av_log(avctx, AV_LOG_ERROR, + "couldn't reallocate buffer of size %"PTRDIFF_SPECIFIER"\n", + (read_end - read_start) + av_fifo_size(fpc->fifo_buf)); + goto handle_error; + } + + if (buf && buf_size) { + av_fifo_generic_write(fpc->fifo_buf, (void*) read_start, + read_end - read_start, NULL); + } else { + int8_t pad[MAX_FRAME_HEADER_SIZE] = { 0 }; + av_fifo_generic_write(fpc->fifo_buf, (void*) pad, sizeof(pad), NULL); + } + + /* Tag headers and update sequences. */ + start_offset = av_fifo_size(fpc->fifo_buf) - + ((read_end - read_start) + (MAX_FRAME_HEADER_SIZE - 1)); + start_offset = FFMAX(0, start_offset); + nb_headers = find_new_headers(fpc, start_offset); + + if (nb_headers < 0) { + av_log(avctx, AV_LOG_ERROR, + "find_new_headers couldn't allocate FLAC header\n"); + goto handle_error; + } + + fpc->nb_headers_buffered = nb_headers; + /* Wait till FLAC_MIN_HEADERS to output a valid frame. */ + if (!fpc->end_padded && fpc->nb_headers_buffered < FLAC_MIN_HEADERS) { + if (buf && read_end < buf + buf_size) { + read_start = read_end; + continue; + } else { + goto handle_error; + } + } + + /* If headers found, update the scores since we have longer chains. */ + if (fpc->end_padded || fpc->nb_headers_found) + score_sequences(fpc); + + /* restore the state pre-padding */ + if (fpc->end_padded) { + int warp = fpc->fifo_buf->wptr - fpc->fifo_buf->buffer < MAX_FRAME_HEADER_SIZE; + /* HACK: drain the tail of the fifo */ + fpc->fifo_buf->wptr -= MAX_FRAME_HEADER_SIZE; + fpc->fifo_buf->wndx -= MAX_FRAME_HEADER_SIZE; + if (warp) { + fpc->fifo_buf->wptr += fpc->fifo_buf->end - + fpc->fifo_buf->buffer; + } + buf_size = 0; + read_start = read_end = NULL; + } + } + + for (curr = fpc->headers; curr; curr = curr->next) { + if (curr->max_score > 0 && + (!fpc->best_header || curr->max_score > fpc->best_header->max_score)) { + fpc->best_header = curr; + } + } + + if (fpc->best_header) { + fpc->best_header_valid = 1; + if (fpc->best_header->offset > 0) { + /* Output a junk frame. */ + av_log(avctx, AV_LOG_DEBUG, "Junk frame till offset %i\n", + fpc->best_header->offset); + + /* Set duration to 0. It is unknown or invalid in a junk frame. */ + s->duration = 0; + *poutbuf_size = fpc->best_header->offset; + *poutbuf = flac_fifo_read_wrap(fpc, 0, *poutbuf_size, + &fpc->wrap_buf, + &fpc->wrap_buf_allocated_size); + return buf_size ? (read_end - buf) : (fpc->best_header->offset - + av_fifo_size(fpc->fifo_buf)); + } + if (!buf_size) + return get_best_header(fpc, poutbuf, poutbuf_size); + } + +handle_error: + *poutbuf = NULL; + *poutbuf_size = 0; + return buf_size ? read_end - buf : 0; +} + +static av_cold int flac_parse_init(AVCodecParserContext *c) +{ + FLACParseContext *fpc = c->priv_data; + fpc->pc = c; + /* There will generally be FLAC_MIN_HEADERS buffered in the fifo before + it drains. This is allocated early to avoid slow reallocation. */ + fpc->fifo_buf = av_fifo_alloc_array(FLAC_MIN_HEADERS + 3, FLAC_AVG_FRAME_SIZE); + if (!fpc->fifo_buf) { + av_log(fpc->avctx, AV_LOG_ERROR, + "couldn't allocate fifo_buf\n"); + return AVERROR(ENOMEM); + } + return 0; +} + +static void flac_parse_close(AVCodecParserContext *c) +{ + FLACParseContext *fpc = c->priv_data; + FLACHeaderMarker *curr = fpc->headers, *temp; + + while (curr) { + temp = curr->next; + av_freep(&curr->link_penalty); + av_free(curr); + curr = temp; + } + av_fifo_freep(&fpc->fifo_buf); + av_freep(&fpc->wrap_buf); +} + +AVCodecParser ff_flac_parser = { + .codec_ids = { AV_CODEC_ID_FLAC }, + .priv_data_size = sizeof(FLACParseContext), + .parser_init = flac_parse_init, + .parser_parse = flac_parse, + .parser_close = flac_parse_close, +};
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/flacdata.c @@ -0,0 +1,33 @@ +/* + * FLAC data + * Copyright (c) 2003 Alex Beregszaszi + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include "internal.h" + +const int ff_flac_sample_rate_table[16] = +{ 0, + 88200, 176400, 192000, + 8000, 16000, 22050, 24000, 32000, 44100, 48000, 96000, + 0, 0, 0, 0 }; + +const int32_t ff_flac_blocksize_table[16] = { + 0, 192, 576<<0, 576<<1, 576<<2, 576<<3, 0, 0, +256<<0, 256<<1, 256<<2, 256<<3, 256<<4, 256<<5, 256<<6, 256<<7 +};
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/flacdata.h @@ -0,0 +1,31 @@ +/* + * FLAC data header + * Copyright (c) 2003 Alex Beregszaszi + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#ifndef AVCODEC_FLACDATA_H +#define AVCODEC_FLACDATA_H + +#include "internal.h" + +extern const int ff_flac_sample_rate_table[16]; + +extern const int32_t ff_flac_blocksize_table[16]; + +#endif /* AVCODEC_FLACDATA_H */
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/flacdec.c @@ -0,0 +1,677 @@ +/* + * FLAC (Free Lossless Audio Codec) decoder + * Copyright (c) 2003 Alex Beregszaszi + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/** + * @file + * FLAC (Free Lossless Audio Codec) decoder + * @author Alex Beregszaszi + * @see http://flac.sourceforge.net/ + * + * This decoder can be used in 1 of 2 ways: Either raw FLAC data can be fed + * through, starting from the initial 'fLaC' signature; or by passing the + * 34-byte streaminfo structure through avctx->extradata[_size] followed + * by data starting with the 0xFFF8 marker. + */ + +#include <limits.h> + +#include "libavutil/avassert.h" +#include "libavutil/crc.h" +#include "libavutil/opt.h" +#include "avcodec.h" +#include "internal.h" +#include "get_bits.h" +#include "bytestream.h" +#include "golomb.h" +#include "flac.h" +#include "flacdata.h" +#include "flacdsp.h" +#include "thread.h" +#include "unary.h" + + +typedef struct FLACContext { + AVClass *class; + struct FLACStreaminfo flac_stream_info; + + AVCodecContext *avctx; ///< parent AVCodecContext + GetBitContext gb; ///< GetBitContext initialized to start at the current frame + + int blocksize; ///< number of samples in the current frame + int sample_shift; ///< shift required to make output samples 16-bit or 32-bit + int ch_mode; ///< channel decorrelation type in the current frame + int got_streaminfo; ///< indicates if the STREAMINFO has been read + + int32_t *decoded[FLAC_MAX_CHANNELS]; ///< decoded samples + uint8_t *decoded_buffer; + unsigned int decoded_buffer_size; + int buggy_lpc; ///< use workaround for old lavc encoded files + + FLACDSPContext dsp; +} FLACContext; + +static int allocate_buffers(FLACContext *s); + +static void flac_set_bps(FLACContext *s) +{ + enum AVSampleFormat req = s->avctx->request_sample_fmt; + int need32 = s->flac_stream_info.bps > 16; + int want32 = av_get_bytes_per_sample(req) > 2; + int planar = av_sample_fmt_is_planar(req); + + if (need32 || want32) { + if (planar) + s->avctx->sample_fmt = AV_SAMPLE_FMT_S32P; + else + s->avctx->sample_fmt = AV_SAMPLE_FMT_S32; + s->sample_shift = 32 - s->flac_stream_info.bps; + } else { + if (planar) + s->avctx->sample_fmt = AV_SAMPLE_FMT_S16P; + else + s->avctx->sample_fmt = AV_SAMPLE_FMT_S16; + s->sample_shift = 16 - s->flac_stream_info.bps; + } +} + +static av_cold int flac_decode_init(AVCodecContext *avctx) +{ + enum FLACExtradataFormat format; + uint8_t *streaminfo; + int ret; + FLACContext *s = avctx->priv_data; + s->avctx = avctx; + + /* for now, the raw FLAC header is allowed to be passed to the decoder as + frame data instead of extradata. */ + if (!avctx->extradata) + return 0; + + if (!ff_flac_is_extradata_valid(avctx, &format, &streaminfo)) + return AVERROR_INVALIDDATA; + + /* initialize based on the demuxer-supplied streamdata header */ + ff_flac_parse_streaminfo(avctx, &s->flac_stream_info, streaminfo); + ret = allocate_buffers(s); + if (ret < 0) + return ret; + flac_set_bps(s); + ff_flacdsp_init(&s->dsp, avctx->sample_fmt, + s->flac_stream_info.channels, s->flac_stream_info.bps); + s->got_streaminfo = 1; + + return 0; +} + +static void dump_headers(AVCodecContext *avctx, FLACStreaminfo *s) +{ + av_log(avctx, AV_LOG_DEBUG, " Max Blocksize: %d\n", s->max_blocksize); + av_log(avctx, AV_LOG_DEBUG, " Max Framesize: %d\n", s->max_framesize); + av_log(avctx, AV_LOG_DEBUG, " Samplerate: %d\n", s->samplerate); + av_log(avctx, AV_LOG_DEBUG, " Channels: %d\n", s->channels); + av_log(avctx, AV_LOG_DEBUG, " Bits: %d\n", s->bps); +} + +static int allocate_buffers(FLACContext *s) +{ + int buf_size; + int ret; + + av_assert0(s->flac_stream_info.max_blocksize); + + buf_size = av_samples_get_buffer_size(NULL, s->flac_stream_info.channels, + s->flac_stream_info.max_blocksize, + AV_SAMPLE_FMT_S32P, 0); + if (buf_size < 0) + return buf_size; + + av_fast_malloc(&s->decoded_buffer, &s->decoded_buffer_size, buf_size); + if (!s->decoded_buffer) + return AVERROR(ENOMEM); + + ret = av_samples_fill_arrays((uint8_t **)s->decoded, NULL, + s->decoded_buffer, + s->flac_stream_info.channels, + s->flac_stream_info.max_blocksize, + AV_SAMPLE_FMT_S32P, 0); + return ret < 0 ? ret : 0; +} + +/** + * Parse the STREAMINFO from an inline header. + * @param s the flac decoding context + * @param buf input buffer, starting with the "fLaC" marker + * @param buf_size buffer size + * @return non-zero if metadata is invalid + */ +static int parse_streaminfo(FLACContext *s, const uint8_t *buf, int buf_size) +{ + int metadata_type, metadata_size, ret; + + if (buf_size < FLAC_STREAMINFO_SIZE+8) { + /* need more data */ + return 0; + } + flac_parse_block_header(&buf[4], NULL, &metadata_type, &metadata_size); + if (metadata_type != FLAC_METADATA_TYPE_STREAMINFO || + metadata_size != FLAC_STREAMINFO_SIZE) { + return AVERROR_INVALIDDATA; + } + ff_flac_parse_streaminfo(s->avctx, &s->flac_stream_info, &buf[8]); + ret = allocate_buffers(s); + if (ret < 0) + return ret; + flac_set_bps(s); + ff_flacdsp_init(&s->dsp, s->avctx->sample_fmt, + s->flac_stream_info.channels, s->flac_stream_info.bps); + s->got_streaminfo = 1; + + return 0; +} + +/** + * Determine the size of an inline header. + * @param buf input buffer, starting with the "fLaC" marker + * @param buf_size buffer size + * @return number of bytes in the header, or 0 if more data is needed + */ +static int get_metadata_size(const uint8_t *buf, int buf_size) +{ + int metadata_last, metadata_size; + const uint8_t *buf_end = buf + buf_size; + + buf += 4; + do { + if (buf_end - buf < 4) + return 0; + flac_parse_block_header(buf, &metadata_last, NULL, &metadata_size); + buf += 4; + if (buf_end - buf < metadata_size) { + /* need more data in order to read the complete header */ + return 0; + } + buf += metadata_size; + } while (!metadata_last); + + return buf_size - (buf_end - buf); +} + +static int decode_residuals(FLACContext *s, int32_t *decoded, int pred_order) +{ + int i, tmp, partition, method_type, rice_order; + int rice_bits, rice_esc; + int samples; + + method_type = get_bits(&s->gb, 2); + if (method_type > 1) { + av_log(s->avctx, AV_LOG_ERROR, "illegal residual coding method %d\n", + method_type); + return AVERROR_INVALIDDATA; + } + + rice_order = get_bits(&s->gb, 4); + + samples= s->blocksize >> rice_order; + if (samples << rice_order != s->blocksize) { + av_log(s->avctx, AV_LOG_ERROR, "invalid rice order: %i blocksize %i\n", + rice_order, s->blocksize); + return AVERROR_INVALIDDATA; + } + + if (pred_order > samples) { + av_log(s->avctx, AV_LOG_ERROR, "invalid predictor order: %i > %i\n", + pred_order, samples); + return AVERROR_INVALIDDATA; + } + + rice_bits = 4 + method_type; + rice_esc = (1 << rice_bits) - 1; + + decoded += pred_order; + i= pred_order; + for (partition = 0; partition < (1 << rice_order); partition++) { + tmp = get_bits(&s->gb, rice_bits); + if (tmp == rice_esc) { + tmp = get_bits(&s->gb, 5); + for (; i < samples; i++) + *decoded++ = get_sbits_long(&s->gb, tmp); + } else { + for (; i < samples; i++) { + *decoded++ = get_sr_golomb_flac(&s->gb, tmp, INT_MAX, 0); + } + } + i= 0; + } + + return 0; +} + +static int decode_subframe_fixed(FLACContext *s, int32_t *decoded, + int pred_order, int bps) +{ + const int blocksize = s->blocksize; + int av_uninit(a), av_uninit(b), av_uninit(c), av_uninit(d), i; + int ret; + + /* warm up samples */ + for (i = 0; i < pred_order; i++) { + decoded[i] = get_sbits_long(&s->gb, bps); + } + + if ((ret = decode_residuals(s, decoded, pred_order)) < 0) + return ret; + + if (pred_order > 0) + a = decoded[pred_order-1]; + if (pred_order > 1) + b = a - decoded[pred_order-2]; + if (pred_order > 2) + c = b - decoded[pred_order-2] + decoded[pred_order-3]; + if (pred_order > 3) + d = c - decoded[pred_order-2] + 2*decoded[pred_order-3] - decoded[pred_order-4]; + + switch (pred_order) { + case 0: + break; + case 1: + for (i = pred_order; i < blocksize; i++) + decoded[i] = a += decoded[i]; + break; + case 2: + for (i = pred_order; i < blocksize; i++) + decoded[i] = a += b += decoded[i]; + break; + case 3: + for (i = pred_order; i < blocksize; i++) + decoded[i] = a += b += c += decoded[i]; + break; + case 4: + for (i = pred_order; i < blocksize; i++) + decoded[i] = a += b += c += d += decoded[i]; + break; + default: + av_log(s->avctx, AV_LOG_ERROR, "illegal pred order %d\n", pred_order); + return AVERROR_INVALIDDATA; + } + + return 0; +} + +static void lpc_analyze_remodulate(int32_t *decoded, const int coeffs[32], + int order, int qlevel, int len, int bps) +{ + int i, j; + int ebps = 1 << (bps-1); + unsigned sigma = 0; + + for (i = order; i < len; i++) + sigma |= decoded[i] + ebps; + + if (sigma < 2*ebps) + return; + + for (i = len - 1; i >= order; i--) { + int64_t p = 0; + for (j = 0; j < order; j++) + p += coeffs[j] * (int64_t)decoded[i-order+j]; + decoded[i] -= p >> qlevel; + } + for (i = order; i < len; i++, decoded++) { + int32_t p = 0; + for (j = 0; j < order; j++) + p += coeffs[j] * (uint32_t)decoded[j]; + decoded[j] += p >> qlevel; + } +} + +static int decode_subframe_lpc(FLACContext *s, int32_t *decoded, int pred_order, + int bps) +{ + int i, ret; + int coeff_prec, qlevel; + int coeffs[32]; + + /* warm up samples */ + for (i = 0; i < pred_order; i++) { + decoded[i] = get_sbits_long(&s->gb, bps); + } + + coeff_prec = get_bits(&s->gb, 4) + 1; + if (coeff_prec == 16) { + av_log(s->avctx, AV_LOG_ERROR, "invalid coeff precision\n"); + return AVERROR_INVALIDDATA; + } + qlevel = get_sbits(&s->gb, 5); + if (qlevel < 0) { + av_log(s->avctx, AV_LOG_ERROR, "qlevel %d not supported, maybe buggy stream\n", + qlevel); + return AVERROR_INVALIDDATA; + } + + for (i = 0; i < pred_order; i++) { + coeffs[pred_order - i - 1] = get_sbits(&s->gb, coeff_prec); + } + + if ((ret = decode_residuals(s, decoded, pred_order)) < 0) + return ret; + + if ( ( s->buggy_lpc && s->flac_stream_info.bps <= 16) + || ( !s->buggy_lpc && bps <= 16 + && bps + coeff_prec + av_log2(pred_order) <= 32)) { + s->dsp.lpc16(decoded, coeffs, pred_order, qlevel, s->blocksize); + } else { + s->dsp.lpc32(decoded, coeffs, pred_order, qlevel, s->blocksize); + if (s->flac_stream_info.bps <= 16) + lpc_analyze_remodulate(decoded, coeffs, pred_order, qlevel, s->blocksize, bps); + } + + return 0; +} + +static inline int decode_subframe(FLACContext *s, int channel) +{ + int32_t *decoded = s->decoded[channel]; + int type, wasted = 0; + int bps = s->flac_stream_info.bps; + int i, tmp, ret; + + if (channel == 0) { + if (s->ch_mode == FLAC_CHMODE_RIGHT_SIDE) + bps++; + } else { + if (s->ch_mode == FLAC_CHMODE_LEFT_SIDE || s->ch_mode == FLAC_CHMODE_MID_SIDE) + bps++; + } + + if (get_bits1(&s->gb)) { + av_log(s->avctx, AV_LOG_ERROR, "invalid subframe padding\n"); + return AVERROR_INVALIDDATA; + } + type = get_bits(&s->gb, 6); + + if (get_bits1(&s->gb)) { + int left = get_bits_left(&s->gb); + if ( left <= 0 || + (left < bps && !show_bits_long(&s->gb, left)) || + !show_bits_long(&s->gb, bps)) { + av_log(s->avctx, AV_LOG_ERROR, + "Invalid number of wasted bits > available bits (%d) - left=%d\n", + bps, left); + return AVERROR_INVALIDDATA; + } + wasted = 1 + get_unary(&s->gb, 1, get_bits_left(&s->gb)); + bps -= wasted; + } + if (bps > 32) { + avpriv_report_missing_feature(s->avctx, "Decorrelated bit depth > 32"); + return AVERROR_PATCHWELCOME; + } + +//FIXME use av_log2 for types + if (type == 0) { + tmp = get_sbits_long(&s->gb, bps); + for (i = 0; i < s->blocksize; i++) + decoded[i] = tmp; + } else if (type == 1) { + for (i = 0; i < s->blocksize; i++) + decoded[i] = get_sbits_long(&s->gb, bps); + } else if ((type >= 8) && (type <= 12)) { + if ((ret = decode_subframe_fixed(s, decoded, type & ~0x8, bps)) < 0) + return ret; + } else if (type >= 32) { + if ((ret = decode_subframe_lpc(s, decoded, (type & ~0x20)+1, bps)) < 0) + return ret; + } else { + av_log(s->avctx, AV_LOG_ERROR, "invalid coding type\n"); + return AVERROR_INVALIDDATA; + } + + if (wasted) { + int i; + for (i = 0; i < s->blocksize; i++) + decoded[i] <<= wasted; + } + + return 0; +} + +static int decode_frame(FLACContext *s) +{ + int i, ret; + GetBitContext *gb = &s->gb; + FLACFrameInfo fi; + + if ((ret = ff_flac_decode_frame_header(s->avctx, gb, &fi, 0)) < 0) { + av_log(s->avctx, AV_LOG_ERROR, "invalid frame header\n"); + return ret; + } + + if ( s->flac_stream_info.channels + && fi.channels != s->flac_stream_info.channels + && s->got_streaminfo) { + s->flac_stream_info.channels = s->avctx->channels = fi.channels; + ff_flac_set_channel_layout(s->avctx); + ret = allocate_buffers(s); + if (ret < 0) + return ret; + } + s->flac_stream_info.channels = s->avctx->channels = fi.channels; + if (!s->avctx->channel_layout) + ff_flac_set_channel_layout(s->avctx); + s->ch_mode = fi.ch_mode; + + if (!s->flac_stream_info.bps && !fi.bps) { + av_log(s->avctx, AV_LOG_ERROR, "bps not found in STREAMINFO or frame header\n"); + return AVERROR_INVALIDDATA; + } + if (!fi.bps) { + fi.bps = s->flac_stream_info.bps; + } else if (s->flac_stream_info.bps && fi.bps != s->flac_stream_info.bps) { + av_log(s->avctx, AV_LOG_ERROR, "switching bps mid-stream is not " + "supported\n"); + return AVERROR_INVALIDDATA; + } + + if (!s->flac_stream_info.bps) { + s->flac_stream_info.bps = s->avctx->bits_per_raw_sample = fi.bps; + flac_set_bps(s); + } + + if (!s->flac_stream_info.max_blocksize) + s->flac_stream_info.max_blocksize = FLAC_MAX_BLOCKSIZE; + if (fi.blocksize > s->flac_stream_info.max_blocksize) { + av_log(s->avctx, AV_LOG_ERROR, "blocksize %d > %d\n", fi.blocksize, + s->flac_stream_info.max_blocksize); + return AVERROR_INVALIDDATA; + } + s->blocksize = fi.blocksize; + + if (!s->flac_stream_info.samplerate && !fi.samplerate) { + av_log(s->avctx, AV_LOG_ERROR, "sample rate not found in STREAMINFO" + " or frame header\n"); + return AVERROR_INVALIDDATA; + } + if (fi.samplerate == 0) + fi.samplerate = s->flac_stream_info.samplerate; + s->flac_stream_info.samplerate = s->avctx->sample_rate = fi.samplerate; + + if (!s->got_streaminfo) { + ret = allocate_buffers(s); + if (ret < 0) + return ret; + s->got_streaminfo = 1; + dump_headers(s->avctx, &s->flac_stream_info); + } + ff_flacdsp_init(&s->dsp, s->avctx->sample_fmt, + s->flac_stream_info.channels, s->flac_stream_info.bps); + +// dump_headers(s->avctx, &s->flac_stream_info); + + /* subframes */ + for (i = 0; i < s->flac_stream_info.channels; i++) { + if ((ret = decode_subframe(s, i)) < 0) + return ret; + } + + align_get_bits(gb); + + /* frame footer */ + skip_bits(gb, 16); /* data crc */ + + return 0; +} + +static int flac_decode_frame(AVCodecContext *avctx, void *data, + int *got_frame_ptr, AVPacket *avpkt) +{ + AVFrame *frame = data; + ThreadFrame tframe = { .f = data }; + const uint8_t *buf = avpkt->data; + int buf_size = avpkt->size; + FLACContext *s = avctx->priv_data; + int bytes_read = 0; + int ret; + + *got_frame_ptr = 0; + + if (s->flac_stream_info.max_framesize == 0) { + s->flac_stream_info.max_framesize = + ff_flac_get_max_frame_size(s->flac_stream_info.max_blocksize ? s->flac_stream_info.max_blocksize : FLAC_MAX_BLOCKSIZE, + FLAC_MAX_CHANNELS, 32); + } + + if (buf_size > 5 && !memcmp(buf, "\177FLAC", 5)) { + av_log(s->avctx, AV_LOG_DEBUG, "skipping flac header packet 1\n"); + return buf_size; + } + + if (buf_size > 0 && (*buf & 0x7F) == FLAC_METADATA_TYPE_VORBIS_COMMENT) { + av_log(s->avctx, AV_LOG_DEBUG, "skipping vorbis comment\n"); + return buf_size; + } + + /* check that there is at least the smallest decodable amount of data. + this amount corresponds to the smallest valid FLAC frame possible. + FF F8 69 02 00 00 9A 00 00 34 46 */ + if (buf_size < FLAC_MIN_FRAME_SIZE) + return buf_size; + + /* check for inline header */ + if (AV_RB32(buf) == MKBETAG('f','L','a','C')) { + if (!s->got_streaminfo && (ret = parse_streaminfo(s, buf, buf_size))) { + av_log(s->avctx, AV_LOG_ERROR, "invalid header\n"); + return ret; + } + return get_metadata_size(buf, buf_size); + } + + /* decode frame */ + if ((ret = init_get_bits8(&s->gb, buf, buf_size)) < 0) + return ret; + if ((ret = decode_frame(s)) < 0) { + av_log(s->avctx, AV_LOG_ERROR, "decode_frame() failed\n"); + return ret; + } + bytes_read = get_bits_count(&s->gb)/8; + + if ((s->avctx->err_recognition & (AV_EF_CRCCHECK|AV_EF_COMPLIANT)) && + av_crc(av_crc_get_table(AV_CRC_16_ANSI), + 0, buf, bytes_read)) { + av_log(s->avctx, AV_LOG_ERROR, "CRC error at PTS %"PRId64"\n", avpkt->pts); + if (s->avctx->err_recognition & AV_EF_EXPLODE) + return AVERROR_INVALIDDATA; + } + + /* get output buffer */ + frame->nb_samples = s->blocksize; + if ((ret = ff_thread_get_buffer(avctx, &tframe, 0)) < 0) + return ret; + + s->dsp.decorrelate[s->ch_mode](frame->data, s->decoded, + s->flac_stream_info.channels, + s->blocksize, s->sample_shift); + + if (bytes_read > buf_size) { + av_log(s->avctx, AV_LOG_ERROR, "overread: %d\n", bytes_read - buf_size); + return AVERROR_INVALIDDATA; + } + if (bytes_read < buf_size) { + av_log(s->avctx, AV_LOG_DEBUG, "underread: %d orig size: %d\n", + buf_size - bytes_read, buf_size); + } + + *got_frame_ptr = 1; + + return bytes_read; +} + +#if HAVE_THREADS +static int init_thread_copy(AVCodecContext *avctx) +{ + FLACContext *s = avctx->priv_data; + s->decoded_buffer = NULL; + s->decoded_buffer_size = 0; + s->avctx = avctx; + if (s->flac_stream_info.max_blocksize) + return allocate_buffers(s); + return 0; +} +#endif + +static av_cold int flac_decode_close(AVCodecContext *avctx) +{ + FLACContext *s = avctx->priv_data; + + av_freep(&s->decoded_buffer); + + return 0; +} + +static const AVOption options[] = { +{ "use_buggy_lpc", "emulate old buggy lavc behavior", offsetof(FLACContext, buggy_lpc), AV_OPT_TYPE_BOOL, {.i64 = 0 }, 0, 1, AV_OPT_FLAG_DECODING_PARAM | AV_OPT_FLAG_AUDIO_PARAM }, +{ NULL }, +}; + +static const AVClass flac_decoder_class = { + "FLAC decoder", + av_default_item_name, + options, + LIBAVUTIL_VERSION_INT, +}; + +AVCodec ff_flac_decoder = { + .name = "flac", + .long_name = NULL_IF_CONFIG_SMALL("FLAC (Free Lossless Audio Codec)"), + .type = AVMEDIA_TYPE_AUDIO, + .id = AV_CODEC_ID_FLAC, + .priv_data_size = sizeof(FLACContext), + .init = flac_decode_init, + .close = flac_decode_close, + .decode = flac_decode_frame, + .init_thread_copy = ONLY_IF_THREADS_ENABLED(init_thread_copy), + .capabilities = AV_CODEC_CAP_DR1 | AV_CODEC_CAP_FRAME_THREADS, + .sample_fmts = (const enum AVSampleFormat[]) { AV_SAMPLE_FMT_S16, + AV_SAMPLE_FMT_S16P, + AV_SAMPLE_FMT_S32, + AV_SAMPLE_FMT_S32P, + AV_SAMPLE_FMT_NONE }, + .priv_class = &flac_decoder_class, +};
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/flacdsp.c @@ -0,0 +1,130 @@ +/* + * Copyright (c) 2012 Mans Rullgard <mans@mansr.com> + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include "libavutil/attributes.h" +#include "libavutil/samplefmt.h" +#include "flacdsp.h" +#include "config.h" + +#define SAMPLE_SIZE 16 +#define PLANAR 0 +#include "flacdsp_template.c" +#include "flacdsp_lpc_template.c" + +#undef PLANAR +#define PLANAR 1 +#include "flacdsp_template.c" + +#undef SAMPLE_SIZE +#undef PLANAR +#define SAMPLE_SIZE 32 +#define PLANAR 0 +#include "flacdsp_template.c" +#include "flacdsp_lpc_template.c" + +#undef PLANAR +#define PLANAR 1 +#include "flacdsp_template.c" + +static void flac_lpc_16_c(int32_t *decoded, const int coeffs[32], + int pred_order, int qlevel, int len) +{ + int i, j; + + for (i = pred_order; i < len - 1; i += 2, decoded += 2) { + int c = coeffs[0]; + int d = decoded[0]; + int s0 = 0, s1 = 0; + for (j = 1; j < pred_order; j++) { + s0 += c*d; + d = decoded[j]; + s1 += c*d; + c = coeffs[j]; + } + s0 += c*d; + d = decoded[j] += s0 >> qlevel; + s1 += c*d; + decoded[j + 1] += s1 >> qlevel; + } + if (i < len) { + int sum = 0; + for (j = 0; j < pred_order; j++) + sum += coeffs[j] * decoded[j]; + decoded[j] += sum >> qlevel; + } +} + +static void flac_lpc_32_c(int32_t *decoded, const int coeffs[32], + int pred_order, int qlevel, int len) +{ + int i, j; + + for (i = pred_order; i < len; i++, decoded++) { + int64_t sum = 0; + for (j = 0; j < pred_order; j++) + sum += (int64_t)coeffs[j] * decoded[j]; + decoded[j] += sum >> qlevel; + } + +} + +av_cold void ff_flacdsp_init(FLACDSPContext *c, enum AVSampleFormat fmt, int channels, + int bps) +{ + c->lpc16 = flac_lpc_16_c; + c->lpc32 = flac_lpc_32_c; + c->lpc16_encode = flac_lpc_encode_c_16; + c->lpc32_encode = flac_lpc_encode_c_32; + + switch (fmt) { + case AV_SAMPLE_FMT_S32: + c->decorrelate[0] = flac_decorrelate_indep_c_32; + c->decorrelate[1] = flac_decorrelate_ls_c_32; + c->decorrelate[2] = flac_decorrelate_rs_c_32; + c->decorrelate[3] = flac_decorrelate_ms_c_32; + break; + + case AV_SAMPLE_FMT_S32P: + c->decorrelate[0] = flac_decorrelate_indep_c_32p; + c->decorrelate[1] = flac_decorrelate_ls_c_32p; + c->decorrelate[2] = flac_decorrelate_rs_c_32p; + c->decorrelate[3] = flac_decorrelate_ms_c_32p; + break; + + case AV_SAMPLE_FMT_S16: + c->decorrelate[0] = flac_decorrelate_indep_c_16; + c->decorrelate[1] = flac_decorrelate_ls_c_16; + c->decorrelate[2] = flac_decorrelate_rs_c_16; + c->decorrelate[3] = flac_decorrelate_ms_c_16; + break; + + case AV_SAMPLE_FMT_S16P: + c->decorrelate[0] = flac_decorrelate_indep_c_16p; + c->decorrelate[1] = flac_decorrelate_ls_c_16p; + c->decorrelate[2] = flac_decorrelate_rs_c_16p; + c->decorrelate[3] = flac_decorrelate_ms_c_16p; + break; + } + + if (ARCH_ARM) + ff_flacdsp_init_arm(c, fmt, channels, bps); + if (ARCH_X86) + ff_flacdsp_init_x86(c, fmt, channels, bps); +}
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/flacdsp.h @@ -0,0 +1,42 @@ +/* + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#ifndef AVCODEC_FLACDSP_H +#define AVCODEC_FLACDSP_H + +#include <stdint.h> +#include "libavutil/samplefmt.h" + +typedef struct FLACDSPContext { + void (*decorrelate[4])(uint8_t **out, int32_t **in, int channels, + int len, int shift); + void (*lpc16)(int32_t *samples, const int coeffs[32], int order, + int qlevel, int len); + void (*lpc32)(int32_t *samples, const int coeffs[32], int order, + int qlevel, int len); + void (*lpc16_encode)(int32_t *res, const int32_t *smp, int len, int order, + const int32_t coefs[32], int shift); + void (*lpc32_encode)(int32_t *res, const int32_t *smp, int len, int order, + const int32_t coefs[32], int shift); +} FLACDSPContext; + +void ff_flacdsp_init(FLACDSPContext *c, enum AVSampleFormat fmt, int channels, int bps); +void ff_flacdsp_init_arm(FLACDSPContext *c, enum AVSampleFormat fmt, int channels, int bps); +void ff_flacdsp_init_x86(FLACDSPContext *c, enum AVSampleFormat fmt, int channels, int bps); + +#endif /* AVCODEC_FLACDSP_H */
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/flacdsp_lpc_template.c @@ -0,0 +1,159 @@ +/* + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include <stdint.h> +#include "libavutil/avutil.h" +#include "mathops.h" + +#undef FUNC +#undef sum_type +#undef MUL +#undef CLIP +#undef FSUF + +#define FUNC(n) AV_JOIN(n ## _, SAMPLE_SIZE) + +#if SAMPLE_SIZE == 32 +# define sum_type int64_t +# define MUL(a, b) MUL64(a, b) +# define CLIP(x) av_clipl_int32(x) +#else +# define sum_type int32_t +# define MUL(a, b) ((a) * (b)) +# define CLIP(x) (x) +#endif + +#define LPC1(x) { \ + int c = coefs[(x)-1]; \ + p0 += MUL(c, s); \ + s = smp[i-(x)+1]; \ + p1 += MUL(c, s); \ +} + +static av_always_inline void FUNC(lpc_encode_unrolled)(int32_t *res, + const int32_t *smp, int len, int order, + const int32_t *coefs, int shift, int big) +{ + int i; + for (i = order; i < len; i += 2) { + int s = smp[i-order]; + sum_type p0 = 0, p1 = 0; + if (big) { + switch (order) { + case 32: LPC1(32) + case 31: LPC1(31) + case 30: LPC1(30) + case 29: LPC1(29) + case 28: LPC1(28) + case 27: LPC1(27) + case 26: LPC1(26) + case 25: LPC1(25) + case 24: LPC1(24) + case 23: LPC1(23) + case 22: LPC1(22) + case 21: LPC1(21) + case 20: LPC1(20) + case 19: LPC1(19) + case 18: LPC1(18) + case 17: LPC1(17) + case 16: LPC1(16) + case 15: LPC1(15) + case 14: LPC1(14) + case 13: LPC1(13) + case 12: LPC1(12) + case 11: LPC1(11) + case 10: LPC1(10) + case 9: LPC1( 9) + LPC1( 8) + LPC1( 7) + LPC1( 6) + LPC1( 5) + LPC1( 4) + LPC1( 3) + LPC1( 2) + LPC1( 1) + } + } else { + switch (order) { + case 8: LPC1( 8) + case 7: LPC1( 7) + case 6: LPC1( 6) + case 5: LPC1( 5) + case 4: LPC1( 4) + case 3: LPC1( 3) + case 2: LPC1( 2) + case 1: LPC1( 1) + } + } + res[i ] = smp[i ] - CLIP(p0 >> shift); + res[i+1] = smp[i+1] - CLIP(p1 >> shift); + } +} + +static void FUNC(flac_lpc_encode_c)(int32_t *res, const int32_t *smp, int len, + int order, const int32_t *coefs, int shift) +{ + int i; + for (i = 0; i < order; i++) + res[i] = smp[i]; +#if CONFIG_SMALL + for (i = order; i < len; i += 2) { + int j; + int s = smp[i]; + sum_type p0 = 0, p1 = 0; + for (j = 0; j < order; j++) { + int c = coefs[j]; + p1 += MUL(c, s); + s = smp[i-j-1]; + p0 += MUL(c, s); + } + res[i ] = smp[i ] - CLIP(p0 >> shift); + res[i+1] = smp[i+1] - CLIP(p1 >> shift); + } +#else + switch (order) { + case 1: FUNC(lpc_encode_unrolled)(res, smp, len, 1, coefs, shift, 0); break; + case 2: FUNC(lpc_encode_unrolled)(res, smp, len, 2, coefs, shift, 0); break; + case 3: FUNC(lpc_encode_unrolled)(res, smp, len, 3, coefs, shift, 0); break; + case 4: FUNC(lpc_encode_unrolled)(res, smp, len, 4, coefs, shift, 0); break; + case 5: FUNC(lpc_encode_unrolled)(res, smp, len, 5, coefs, shift, 0); break; + case 6: FUNC(lpc_encode_unrolled)(res, smp, len, 6, coefs, shift, 0); break; + case 7: FUNC(lpc_encode_unrolled)(res, smp, len, 7, coefs, shift, 0); break; + case 8: FUNC(lpc_encode_unrolled)(res, smp, len, 8, coefs, shift, 0); break; + default: FUNC(lpc_encode_unrolled)(res, smp, len, order, coefs, shift, 1); break; + } +#endif +} + +/* Comment for clarity/de-obfuscation. + * + * for (int i = order; i < len; i++) { + * int32_t p = 0; + * for (int j = 0; j < order; j++) { + * int c = coefs[j]; + * int s = smp[(i-1)-j]; + * p += c*s; + * } + * res[i] = smp[i] - (p >> shift); + * } + * + * The CONFIG_SMALL code above simplifies to this, in the case of SAMPLE_SIZE + * not being equal to 32 (at the present time that means for 16-bit audio). The + * code above does 2 samples per iteration. Commit bfdd5bc (made all the way + * back in 2007) says that way is faster. + */
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/flacdsp_template.c @@ -0,0 +1,103 @@ +/* + * Copyright (c) 2012 Mans Rullgard <mans@mansr.com> + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include <stdint.h> +#include "libavutil/avutil.h" + +#undef FUNC +#undef FSUF +#undef sample +#undef sample_type +#undef OUT +#undef S + +#if SAMPLE_SIZE == 32 +# define sample_type int32_t +#else +# define sample_type int16_t +#endif + +#if PLANAR +# define FSUF AV_JOIN(SAMPLE_SIZE, p) +# define sample sample_type * +# define OUT(n) n +# define S(s, c, i) (s[c][i]) +#else +# define FSUF SAMPLE_SIZE +# define sample sample_type +# define OUT(n) n[0] +# define S(s, c, i) (*s++) +#endif + +#define FUNC(n) AV_JOIN(n ## _, FSUF) + +static void FUNC(flac_decorrelate_indep_c)(uint8_t **out, int32_t **in, + int channels, int len, int shift) +{ + sample *samples = (sample *) OUT(out); + int i, j; + + for (j = 0; j < len; j++) + for (i = 0; i < channels; i++) + S(samples, i, j) = in[i][j] << shift; +} + +static void FUNC(flac_decorrelate_ls_c)(uint8_t **out, int32_t **in, + int channels, int len, int shift) +{ + sample *samples = (sample *) OUT(out); + int i; + + for (i = 0; i < len; i++) { + int a = in[0][i]; + int b = in[1][i]; + S(samples, 0, i) = a << shift; + S(samples, 1, i) = (a - b) << shift; + } +} + +static void FUNC(flac_decorrelate_rs_c)(uint8_t **out, int32_t **in, + int channels, int len, int shift) +{ + sample *samples = (sample *) OUT(out); + int i; + + for (i = 0; i < len; i++) { + int a = in[0][i]; + int b = in[1][i]; + S(samples, 0, i) = (a + b) << shift; + S(samples, 1, i) = b << shift; + } +} + +static void FUNC(flac_decorrelate_ms_c)(uint8_t **out, int32_t **in, + int channels, int len, int shift) +{ + sample *samples = (sample *) OUT(out); + int i; + + for (i = 0; i < len; i++) { + int a = in[0][i]; + int b = in[1][i]; + a -= b >> 1; + S(samples, 0, i) = (a + b) << shift; + S(samples, 1, i) = a << shift; + } +}
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/golomb.c @@ -0,0 +1,173 @@ +/* + * exp golomb vlc stuff + * Copyright (c) 2003 Michael Niedermayer <michaelni@gmx.at> + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/** + * @file + * @brief + * exp golomb vlc stuff + * @author Michael Niedermayer <michaelni@gmx.at> + */ + +#include "libavutil/common.h" + +const uint8_t ff_golomb_vlc_len[512]={ +19,17,15,15,13,13,13,13,11,11,11,11,11,11,11,11,9,9,9,9,9,9,9,9,9,9,9,9,9,9,9,9, +7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7, +5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5, +5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5, +3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3, +3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3, +3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3, +3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1 +}; + +const uint8_t ff_ue_golomb_vlc_code[512]={ +32,32,32,32,32,32,32,32,31,32,32,32,32,32,32,32,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30, + 7, 7, 7, 7, 8, 8, 8, 8, 9, 9, 9, 9,10,10,10,10,11,11,11,11,12,12,12,12,13,13,13,13,14,14,14,14, + 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, + 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 +}; + +const int8_t ff_se_golomb_vlc_code[512]={ + 17, 17, 17, 17, 17, 17, 17, 17, 16, 17, 17, 17, 17, 17, 17, 17, 8, -8, 9, -9, 10,-10, 11,-11, 12,-12, 13,-13, 14,-14, 15,-15, + 4, 4, 4, 4, -4, -4, -4, -4, 5, 5, 5, 5, -5, -5, -5, -5, 6, 6, 6, 6, -6, -6, -6, -6, 7, 7, 7, 7, -7, -7, -7, -7, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, -2, + 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, -3, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, + -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +}; + + +const uint8_t ff_ue_golomb_len[256]={ + 1, 3, 3, 5, 5, 5, 5, 7, 7, 7, 7, 7, 7, 7, 7, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9,11, +11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,13, +13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13, +13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,15, +15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15, +15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15, +15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15, +15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,17, +}; + +const uint8_t ff_interleaved_golomb_vlc_len[256]={ +9,9,7,7,9,9,7,7,5,5,5,5,5,5,5,5, +9,9,7,7,9,9,7,7,5,5,5,5,5,5,5,5, +3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3, +3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3, +9,9,7,7,9,9,7,7,5,5,5,5,5,5,5,5, +9,9,7,7,9,9,7,7,5,5,5,5,5,5,5,5, +3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3, +3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, +}; + +const uint8_t ff_interleaved_ue_golomb_vlc_code[256]={ + 15,16,7, 7, 17,18,8, 8, 3, 3, 3, 3, 3, 3, 3, 3, + 19,20,9, 9, 21,22,10,10,4, 4, 4, 4, 4, 4, 4, 4, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 23,24,11,11,25,26,12,12,5, 5, 5, 5, 5, 5, 5, 5, + 27,28,13,13,29,30,14,14,6, 6, 6, 6, 6, 6, 6, 6, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +}; + +const int8_t ff_interleaved_se_golomb_vlc_code[256]={ + 8, -8, 4, 4, 9, -9, -4, -4, 2, 2, 2, 2, 2, 2, 2, 2, + 10,-10, 5, 5, 11,-11, -5, -5, -2, -2, -2, -2, -2, -2, -2, -2, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 12,-12, 6, 6, 13,-13, -6, -6, 3, 3, 3, 3, 3, 3, 3, 3, + 14,-14, 7, 7, 15,-15, -7, -7, -3, -3, -3, -3, -3, -3, -3, -3, + -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, + -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +}; + +const uint8_t ff_interleaved_dirac_golomb_vlc_code[256]={ +0, 1, 0, 0, 2, 3, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, +4, 5, 2, 2, 6, 7, 3, 3, 1, 1, 1, 1, 1, 1, 1, 1, +0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +8, 9, 4, 4, 10,11,5, 5, 2, 2, 2, 2, 2, 2, 2, 2, +12,13,6, 6, 14,15,7, 7, 3, 3, 3, 3, 3, 3, 3, 3, +1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, +1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, +0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,};
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/golomb.h @@ -0,0 +1,579 @@ +/* + * exp golomb vlc stuff + * Copyright (c) 2003 Michael Niedermayer <michaelni@gmx.at> + * Copyright (c) 2004 Alex Beregszaszi + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/** + * @file + * @brief + * exp golomb vlc stuff + * @author Michael Niedermayer <michaelni@gmx.at> and Alex Beregszaszi + */ + +#ifndef AVCODEC_GOLOMB_H +#define AVCODEC_GOLOMB_H + +#include <stdint.h> + +#include "get_bits.h" +#include "put_bits.h" + +#define INVALID_VLC 0x80000000 + +extern const uint8_t ff_golomb_vlc_len[512]; +extern const uint8_t ff_ue_golomb_vlc_code[512]; +extern const int8_t ff_se_golomb_vlc_code[512]; +extern const uint8_t ff_ue_golomb_len[256]; + +extern const uint8_t ff_interleaved_golomb_vlc_len[256]; +extern const uint8_t ff_interleaved_ue_golomb_vlc_code[256]; +extern const int8_t ff_interleaved_se_golomb_vlc_code[256]; +extern const uint8_t ff_interleaved_dirac_golomb_vlc_code[256]; + +/** + * Read an unsigned Exp-Golomb code in the range 0 to 8190. + */ +static inline int get_ue_golomb(GetBitContext *gb) +{ + unsigned int buf; + + OPEN_READER(re, gb); + UPDATE_CACHE(re, gb); + buf = GET_CACHE(re, gb); + + if (buf >= (1 << 27)) { + buf >>= 32 - 9; + LAST_SKIP_BITS(re, gb, ff_golomb_vlc_len[buf]); + CLOSE_READER(re, gb); + + return ff_ue_golomb_vlc_code[buf]; + } else { + int log = 2 * av_log2(buf) - 31; + LAST_SKIP_BITS(re, gb, 32 - log); + CLOSE_READER(re, gb); + if (log < 7) { + av_log(NULL, AV_LOG_ERROR, "Invalid UE golomb code\n"); + return AVERROR_INVALIDDATA; + } + buf >>= log; + buf--; + + return buf; + } +} + +/** + * Read an unsigned Exp-Golomb code in the range 0 to UINT32_MAX-1. + */ +static inline unsigned get_ue_golomb_long(GetBitContext *gb) +{ + unsigned buf, log; + + buf = show_bits_long(gb, 32); + log = 31 - av_log2(buf); + skip_bits_long(gb, log); + + return get_bits_long(gb, log + 1) - 1; +} + +/** + * read unsigned exp golomb code, constraint to a max of 31. + * the return value is undefined if the stored value exceeds 31. + */ +static inline int get_ue_golomb_31(GetBitContext *gb) +{ + unsigned int buf; + + OPEN_READER(re, gb); + UPDATE_CACHE(re, gb); + buf = GET_CACHE(re, gb); + + buf >>= 32 - 9; + LAST_SKIP_BITS(re, gb, ff_golomb_vlc_len[buf]); + CLOSE_READER(re, gb); + + return ff_ue_golomb_vlc_code[buf]; +} + +static inline unsigned get_interleaved_ue_golomb(GetBitContext *gb) +{ + uint32_t buf; + + OPEN_READER(re, gb); + UPDATE_CACHE(re, gb); + buf = GET_CACHE(re, gb); + + if (buf & 0xAA800000) { + buf >>= 32 - 8; + LAST_SKIP_BITS(re, gb, ff_interleaved_golomb_vlc_len[buf]); + CLOSE_READER(re, gb); + + return ff_interleaved_ue_golomb_vlc_code[buf]; + } else { + unsigned ret = 1; + + do { + buf >>= 32 - 8; + LAST_SKIP_BITS(re, gb, + FFMIN(ff_interleaved_golomb_vlc_len[buf], 8)); + + if (ff_interleaved_golomb_vlc_len[buf] != 9) { + ret <<= (ff_interleaved_golomb_vlc_len[buf] - 1) >> 1; + ret |= ff_interleaved_dirac_golomb_vlc_code[buf]; + break; + } + ret = (ret << 4) | ff_interleaved_dirac_golomb_vlc_code[buf]; + UPDATE_CACHE(re, gb); + buf = GET_CACHE(re, gb); + } while (ret<0x8000000U && BITS_AVAILABLE(re, gb)); + + CLOSE_READER(re, gb); + return ret - 1; + } +} + +/** + * read unsigned truncated exp golomb code. + */ +static inline int get_te0_golomb(GetBitContext *gb, int range) +{ + av_assert2(range >= 1); + + if (range == 1) + return 0; + else if (range == 2) + return get_bits1(gb) ^ 1; + else + return get_ue_golomb(gb); +} + +/** + * read unsigned truncated exp golomb code. + */ +static inline int get_te_golomb(GetBitContext *gb, int range) +{ + av_assert2(range >= 1); + + if (range == 2) + return get_bits1(gb) ^ 1; + else + return get_ue_golomb(gb); +} + +/** + * read signed exp golomb code. + */ +static inline int get_se_golomb(GetBitContext *gb) +{ + unsigned int buf; + + OPEN_READER(re, gb); + UPDATE_CACHE(re, gb); + buf = GET_CACHE(re, gb); + + if (buf >= (1 << 27)) { + buf >>= 32 - 9; + LAST_SKIP_BITS(re, gb, ff_golomb_vlc_len[buf]); + CLOSE_READER(re, gb); + + return ff_se_golomb_vlc_code[buf]; + } else { + int log = av_log2(buf), sign; + LAST_SKIP_BITS(re, gb, 31 - log); + UPDATE_CACHE(re, gb); + buf = GET_CACHE(re, gb); + + buf >>= log; + + LAST_SKIP_BITS(re, gb, 32 - log); + CLOSE_READER(re, gb); + + sign = -(buf & 1); + buf = ((buf >> 1) ^ sign) - sign; + + return buf; + } +} + +static inline int get_se_golomb_long(GetBitContext *gb) +{ + unsigned int buf = get_ue_golomb_long(gb); + int sign = (buf & 1) - 1; + return ((buf >> 1) ^ sign) + 1; +} + +static inline int get_interleaved_se_golomb(GetBitContext *gb) +{ + unsigned int buf; + + OPEN_READER(re, gb); + UPDATE_CACHE(re, gb); + buf = GET_CACHE(re, gb); + + if (buf & 0xAA800000) { + buf >>= 32 - 8; + LAST_SKIP_BITS(re, gb, ff_interleaved_golomb_vlc_len[buf]); + CLOSE_READER(re, gb); + + return ff_interleaved_se_golomb_vlc_code[buf]; + } else { + int log; + LAST_SKIP_BITS(re, gb, 8); + UPDATE_CACHE(re, gb); + buf |= 1 | (GET_CACHE(re, gb) >> 8); + + if ((buf & 0xAAAAAAAA) == 0) + return INVALID_VLC; + + for (log = 31; (buf & 0x80000000) == 0; log--) + buf = (buf << 2) - ((buf << log) >> (log - 1)) + (buf >> 30); + + LAST_SKIP_BITS(re, gb, 63 - 2 * log - 8); + CLOSE_READER(re, gb); + + return (signed) (((((buf << log) >> log) - 1) ^ -(buf & 0x1)) + 1) >> 1; + } +} + +static inline int dirac_get_se_golomb(GetBitContext *gb) +{ + uint32_t ret = get_interleaved_ue_golomb(gb); + + if (ret) { + int sign = -get_bits1(gb); + ret = (ret ^ sign) - sign; + } + + return ret; +} + +/** + * read unsigned golomb rice code (ffv1). + */ +static inline int get_ur_golomb(GetBitContext *gb, int k, int limit, + int esc_len) +{ + unsigned int buf; + int log; + + OPEN_READER(re, gb); + UPDATE_CACHE(re, gb); + buf = GET_CACHE(re, gb); + + log = av_log2(buf); + + if (log > 31 - limit) { + buf >>= log - k; + buf += (30U - log) << k; + LAST_SKIP_BITS(re, gb, 32 + k - log); + CLOSE_READER(re, gb); + + return buf; + } else { + LAST_SKIP_BITS(re, gb, limit); + UPDATE_CACHE(re, gb); + + buf = SHOW_UBITS(re, gb, esc_len); + + LAST_SKIP_BITS(re, gb, esc_len); + CLOSE_READER(re, gb); + + return buf + limit - 1; + } +} + +/** + * read unsigned golomb rice code (jpegls). + */ +static inline int get_ur_golomb_jpegls(GetBitContext *gb, int k, int limit, + int esc_len) +{ + unsigned int buf; + int log; + + OPEN_READER(re, gb); + UPDATE_CACHE(re, gb); + buf = GET_CACHE(re, gb); + + log = av_log2(buf); + + if (log - k >= 32 - MIN_CACHE_BITS + (MIN_CACHE_BITS == 32) && + 32 - log < limit) { + buf >>= log - k; + buf += (30U - log) << k; + LAST_SKIP_BITS(re, gb, 32 + k - log); + CLOSE_READER(re, gb); + + return buf; + } else { + int i; + for (i = 0; i < limit && SHOW_UBITS(re, gb, 1) == 0; i++) { + if (gb->size_in_bits <= re_index) + return -1; + LAST_SKIP_BITS(re, gb, 1); + UPDATE_CACHE(re, gb); + } + SKIP_BITS(re, gb, 1); + + if (i < limit - 1) { + if (k) { + if (k > MIN_CACHE_BITS - 1) { + buf = SHOW_UBITS(re, gb, 16) << (k-16); + LAST_SKIP_BITS(re, gb, 16); + UPDATE_CACHE(re, gb); + buf |= SHOW_UBITS(re, gb, k-16); + LAST_SKIP_BITS(re, gb, k-16); + } else { + buf = SHOW_UBITS(re, gb, k); + LAST_SKIP_BITS(re, gb, k); + } + } else { + buf = 0; + } + + CLOSE_READER(re, gb); + return buf + (i << k); + } else if (i == limit - 1) { + buf = SHOW_UBITS(re, gb, esc_len); + LAST_SKIP_BITS(re, gb, esc_len); + CLOSE_READER(re, gb); + + return buf + 1; + } else + return -1; + } +} + +/** + * read signed golomb rice code (ffv1). + */ +static inline int get_sr_golomb(GetBitContext *gb, int k, int limit, + int esc_len) +{ + unsigned v = get_ur_golomb(gb, k, limit, esc_len); + return (v >> 1) ^ -(v & 1); +} + +/** + * read signed golomb rice code (flac). + */ +static inline int get_sr_golomb_flac(GetBitContext *gb, int k, int limit, + int esc_len) +{ + unsigned v = get_ur_golomb_jpegls(gb, k, limit, esc_len); + return (v >> 1) ^ -(v & 1); +} + +/** + * read unsigned golomb rice code (shorten). + */ +static inline unsigned int get_ur_golomb_shorten(GetBitContext *gb, int k) +{ + return get_ur_golomb_jpegls(gb, k, INT_MAX, 0); +} + +/** + * read signed golomb rice code (shorten). + */ +static inline int get_sr_golomb_shorten(GetBitContext *gb, int k) +{ + int uvar = get_ur_golomb_jpegls(gb, k + 1, INT_MAX, 0); + return (uvar >> 1) ^ -(uvar & 1); +} + +#ifdef TRACE + +static inline int get_ue(GetBitContext *s, const char *file, const char *func, + int line) +{ + int show = show_bits(s, 24); + int pos = get_bits_count(s); + int i = get_ue_golomb(s); + int len = get_bits_count(s) - pos; + int bits = show >> (24 - len); + + av_log(NULL, AV_LOG_DEBUG, "%5d %2d %3d ue @%5d in %s %s:%d\n", + bits, len, i, pos, file, func, line); + + return i; +} + +static inline int get_se(GetBitContext *s, const char *file, const char *func, + int line) +{ + int show = show_bits(s, 24); + int pos = get_bits_count(s); + int i = get_se_golomb(s); + int len = get_bits_count(s) - pos; + int bits = show >> (24 - len); + + av_log(NULL, AV_LOG_DEBUG, "%5d %2d %3d se @%5d in %s %s:%d\n", + bits, len, i, pos, file, func, line); + + return i; +} + +static inline int get_te(GetBitContext *s, int r, char *file, const char *func, + int line) +{ + int show = show_bits(s, 24); + int pos = get_bits_count(s); + int i = get_te0_golomb(s, r); + int len = get_bits_count(s) - pos; + int bits = show >> (24 - len); + + av_log(NULL, AV_LOG_DEBUG, "%5d %2d %3d te @%5d in %s %s:%d\n", + bits, len, i, pos, file, func, line); + + return i; +} + +#define get_ue_golomb(a) get_ue(a, __FILE__, __PRETTY_FUNCTION__, __LINE__) +#define get_se_golomb(a) get_se(a, __FILE__, __PRETTY_FUNCTION__, __LINE__) +#define get_te_golomb(a, r) get_te(a, r, __FILE__, __PRETTY_FUNCTION__, __LINE__) +#define get_te0_golomb(a, r) get_te(a, r, __FILE__, __PRETTY_FUNCTION__, __LINE__) + +#endif /* TRACE */ + +/** + * write unsigned exp golomb code. + */ +static inline void set_ue_golomb(PutBitContext *pb, int i) +{ + av_assert2(i >= 0); + + if (i < 256) + put_bits(pb, ff_ue_golomb_len[i], i + 1); + else { + int e = av_log2(i + 1); + put_bits(pb, 2 * e + 1, i + 1); + } +} + +/** + * write truncated unsigned exp golomb code. + */ +static inline void set_te_golomb(PutBitContext *pb, int i, int range) +{ + av_assert2(range >= 1); + av_assert2(i <= range); + + if (range == 2) + put_bits(pb, 1, i ^ 1); + else + set_ue_golomb(pb, i); +} + +/** + * write signed exp golomb code. 16 bits at most. + */ +static inline void set_se_golomb(PutBitContext *pb, int i) +{ +#if 0 + if (i <= 0) + i = -2 * i; + else + i = 2 * i - 1; +#elif 1 + i = 2 * i - 1; + if (i < 0) + i ^= -1; //FIXME check if gcc does the right thing +#else + i = 2 * i - 1; + i ^= (i >> 31); +#endif + set_ue_golomb(pb, i); +} + +/** + * write unsigned golomb rice code (ffv1). + */ +static inline void set_ur_golomb(PutBitContext *pb, int i, int k, int limit, + int esc_len) +{ + int e; + + av_assert2(i >= 0); + + e = i >> k; + if (e < limit) + put_bits(pb, e + k + 1, (1 << k) + av_mod_uintp2(i, k)); + else + put_bits(pb, limit + esc_len, i - limit + 1); +} + +/** + * write unsigned golomb rice code (jpegls). + */ +static inline void set_ur_golomb_jpegls(PutBitContext *pb, int i, int k, + int limit, int esc_len) +{ + int e; + + av_assert2(i >= 0); + + e = (i >> k) + 1; + if (e < limit) { + while (e > 31) { + put_bits(pb, 31, 0); + e -= 31; + } + put_bits(pb, e, 1); + if (k) + put_sbits(pb, k, i); + } else { + while (limit > 31) { + put_bits(pb, 31, 0); + limit -= 31; + } + put_bits(pb, limit, 1); + put_bits(pb, esc_len, i - 1); + } +} + +/** + * write signed golomb rice code (ffv1). + */ +static inline void set_sr_golomb(PutBitContext *pb, int i, int k, int limit, + int esc_len) +{ + int v; + + v = -2 * i - 1; + v ^= (v >> 31); + + set_ur_golomb(pb, v, k, limit, esc_len); +} + +/** + * write signed golomb rice code (flac). + */ +static inline void set_sr_golomb_flac(PutBitContext *pb, int i, int k, + int limit, int esc_len) +{ + int v; + + v = -2 * i - 1; + v ^= (v >> 31); + + set_ur_golomb_jpegls(pb, v, k, limit, esc_len); +} + +#endif /* AVCODEC_GOLOMB_H */
--- a/media/ffvpx/libavcodec/moz.build +++ b/media/ffvpx/libavcodec/moz.build @@ -13,16 +13,22 @@ SharedLibrary('mozavcodec') SOURCES += [ 'allcodecs.c', 'audioconvert.c', 'avpacket.c', 'avpicture.c', 'bitstream.c', 'codec_desc.c', 'dummy_funcs.c', + 'flac.c', + 'flac_parser.c', + 'flacdata.c', + 'flacdec.c', + 'flacdsp.c', + 'golomb.c', 'h264pred.c', 'imgconvert.c', 'log2_tab.c', 'mathtables.c', 'options.c', 'parser.c', 'profiles.c', 'pthread.c',
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/unary.h @@ -0,0 +1,56 @@ +/* + * copyright (c) 2004 Michael Niedermayer <michaelni@gmx.at> + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#ifndef AVCODEC_UNARY_H +#define AVCODEC_UNARY_H + +#include "get_bits.h" + +/** + * Get unary code of limited length + * @param gb GetBitContext + * @param[in] stop The bitstop value (unary code of 1's or 0's) + * @param[in] len Maximum length + * @return Unary length/index + */ +static inline int get_unary(GetBitContext *gb, int stop, int len) +{ + int i; + + for(i = 0; i < len && get_bits1(gb) != stop; i++); + return i; +} + +/** + * Get unary code terminated by a 0 with a maximum length of 33 + * @param gb GetBitContext + * @return Unary length/index + */ +static inline int get_unary_0_33(GetBitContext *gb) +{ + return get_unary(gb, 0, 33); +} + +static inline int get_unary_0_9(GetBitContext *gb) +{ + return get_unary(gb, 0, 9); +} + +#endif /* AVCODEC_UNARY_H */
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/x86/flacdsp.asm @@ -0,0 +1,313 @@ +;****************************************************************************** +;* FLAC DSP SIMD optimizations +;* +;* Copyright (C) 2014 Loren Merritt +;* Copyright (C) 2014 James Almer +;* +;* This file is part of FFmpeg. +;* +;* FFmpeg is free software; you can redistribute it and/or +;* modify it under the terms of the GNU Lesser General Public +;* License as published by the Free Software Foundation; either +;* version 2.1 of the License, or (at your option) any later version. +;* +;* FFmpeg is distributed in the hope that it will be useful, +;* but WITHOUT ANY WARRANTY; without even the implied warranty of +;* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +;* Lesser General Public License for more details. +;* +;* You should have received a copy of the GNU Lesser General Public +;* License along with FFmpeg; if not, write to the Free Software +;* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA +;****************************************************************************** + +%include "libavutil/x86/x86util.asm" + +SECTION .text + +%macro PMACSDQL 5 +%if cpuflag(xop) + pmacsdql %1, %2, %3, %1 +%else + pmuldq %2, %3 + paddq %1, %2 +%endif +%endmacro + +%macro LPC_32 1 +INIT_XMM %1 +cglobal flac_lpc_32, 5,6,5, decoded, coeffs, pred_order, qlevel, len, j + sub lend, pred_orderd + jle .ret + lea decodedq, [decodedq+pred_orderq*4-8] + lea coeffsq, [coeffsq+pred_orderq*4] + neg pred_orderq + movd m4, qlevelm +ALIGN 16 +.loop_sample: + movd m0, [decodedq+pred_orderq*4+8] + add decodedq, 8 + movd m1, [coeffsq+pred_orderq*4] + pxor m2, m2 + pxor m3, m3 + lea jq, [pred_orderq+1] + test jq, jq + jz .end_order +.loop_order: + PMACSDQL m2, m0, m1, m2, m0 + movd m0, [decodedq+jq*4] + PMACSDQL m3, m1, m0, m3, m1 + movd m1, [coeffsq+jq*4] + inc jq + jl .loop_order +.end_order: + PMACSDQL m2, m0, m1, m2, m0 + psrlq m2, m4 + movd m0, [decodedq] + paddd m0, m2 + movd [decodedq], m0 + sub lend, 2 + jl .ret + PMACSDQL m3, m1, m0, m3, m1 + psrlq m3, m4 + movd m1, [decodedq+4] + paddd m1, m3 + movd [decodedq+4], m1 + jg .loop_sample +.ret: + REP_RET +%endmacro + +%if HAVE_XOP_EXTERNAL +LPC_32 xop +%endif +LPC_32 sse4 + +;---------------------------------------------------------------------------------- +;void ff_flac_decorrelate_[lrm]s_16_sse2(uint8_t **out, int32_t **in, int channels, +; int len, int shift); +;---------------------------------------------------------------------------------- +%macro FLAC_DECORRELATE_16 3-4 +cglobal flac_decorrelate_%1_16, 2, 4, 4, out, in0, in1, len +%if ARCH_X86_32 + mov lend, lenm +%endif + movd m3, r4m + shl lend, 2 + mov in1q, [in0q + gprsize] + mov in0q, [in0q] + mov outq, [outq] + add in1q, lenq + add in0q, lenq + add outq, lenq + neg lenq + +align 16 +.loop: + mova m0, [in0q + lenq] + mova m1, [in1q + lenq] +%ifidn %1, ms + psrad m2, m1, 1 + psubd m0, m2 +%endif +%ifnidn %1, indep2 + p%4d m2, m0, m1 +%endif + packssdw m%2, m%2 + packssdw m%3, m%3 + punpcklwd m%2, m%3 + psllw m%2, m3 + mova [outq + lenq], m%2 + add lenq, 16 + jl .loop + REP_RET +%endmacro + +INIT_XMM sse2 +FLAC_DECORRELATE_16 ls, 0, 2, sub +FLAC_DECORRELATE_16 rs, 2, 1, add +FLAC_DECORRELATE_16 ms, 2, 0, add + +;---------------------------------------------------------------------------------- +;void ff_flac_decorrelate_[lrm]s_32_sse2(uint8_t **out, int32_t **in, int channels, +; int len, int shift); +;---------------------------------------------------------------------------------- +%macro FLAC_DECORRELATE_32 5 +cglobal flac_decorrelate_%1_32, 2, 4, 4, out, in0, in1, len +%if ARCH_X86_32 + mov lend, lenm +%endif + movd m3, r4m + mov in1q, [in0q + gprsize] + mov in0q, [in0q] + mov outq, [outq] + sub in1q, in0q + +align 16 +.loop: + mova m0, [in0q] + mova m1, [in0q + in1q] +%ifidn %1, ms + psrad m2, m1, 1 + psubd m0, m2 +%endif + p%5d m2, m0, m1 + pslld m%2, m3 + pslld m%3, m3 + + SBUTTERFLY dq, %2, %3, %4 + + mova [outq ], m%2 + mova [outq + mmsize], m%3 + + add in0q, mmsize + add outq, mmsize*2 + sub lend, mmsize/4 + jg .loop + REP_RET +%endmacro + +INIT_XMM sse2 +FLAC_DECORRELATE_32 ls, 0, 2, 1, sub +FLAC_DECORRELATE_32 rs, 2, 1, 0, add +FLAC_DECORRELATE_32 ms, 2, 0, 1, add + +;----------------------------------------------------------------------------------------- +;void ff_flac_decorrelate_indep<ch>_<bps>_<opt>(uint8_t **out, int32_t **in, int channels, +; int len, int shift); +;----------------------------------------------------------------------------------------- +;%1 = bps +;%2 = channels +;%3 = last xmm reg used +;%4 = word/dword (shift instruction) +%macro FLAC_DECORRELATE_INDEP 4 +%define REPCOUNT %2/(32/%1) ; 16bits = channels / 2; 32bits = channels +cglobal flac_decorrelate_indep%2_%1, 2, %2+2, %3+1, out, in0, in1, len, in2, in3, in4, in5, in6, in7 +%if ARCH_X86_32 +%if %2 == 6 + DEFINE_ARGS out, in0, in1, in2, in3, in4, in5 + %define lend dword r3m +%else + mov lend, lenm +%endif +%endif + movd m%3, r4m + +%assign %%i 1 +%rep %2-1 + mov in %+ %%i %+ q, [in0q+%%i*gprsize] +%assign %%i %%i+1 +%endrep + + mov in0q, [in0q] + mov outq, [outq] + +%assign %%i 1 +%rep %2-1 + sub in %+ %%i %+ q, in0q +%assign %%i %%i+1 +%endrep + +align 16 +.loop: + mova m0, [in0q] + +%assign %%i 1 +%rep REPCOUNT-1 + mova m %+ %%i, [in0q + in %+ %%i %+ q] +%assign %%i %%i+1 +%endrep + +%if %1 == 32 + +%if %2 == 8 + TRANSPOSE8x4D 0, 1, 2, 3, 4, 5, 6, 7, 8 +%elif %2 == 6 + SBUTTERFLY dq, 0, 1, 6 + SBUTTERFLY dq, 2, 3, 6 + SBUTTERFLY dq, 4, 5, 6 + + punpcklqdq m6, m0, m2 + punpckhqdq m2, m4 + shufps m4, m0, 0xe4 + punpcklqdq m0, m1, m3 + punpckhqdq m3, m5 + shufps m5, m1, 0xe4 + SWAP 0,6,1,4,5,3 +%elif %2 == 4 + TRANSPOSE4x4D 0, 1, 2, 3, 4 +%else ; %2 == 2 + SBUTTERFLY dq, 0, 1, 2 +%endif + +%else ; %1 == 16 + +%if %2 == 8 + packssdw m0, [in0q + in4q] + packssdw m1, [in0q + in5q] + packssdw m2, [in0q + in6q] + packssdw m3, [in0q + in7q] + TRANSPOSE2x4x4W 0, 1, 2, 3, 4 +%elif %2 == 6 + packssdw m0, [in0q + in3q] + packssdw m1, [in0q + in4q] + packssdw m2, [in0q + in5q] + pshufd m3, m0, q1032 + punpcklwd m0, m1 + punpckhwd m1, m2 + punpcklwd m2, m3 + + shufps m3, m0, m2, q2020 + shufps m0, m1, q2031 + shufps m2, m1, q3131 + shufps m1, m2, m3, q3120 + shufps m3, m0, q0220 + shufps m0, m2, q3113 + SWAP 2, 0, 3 +%else ; %2 == 4 + packssdw m0, [in0q + in2q] + packssdw m1, [in0q + in3q] + SBUTTERFLY wd, 0, 1, 2 + SBUTTERFLY dq, 0, 1, 2 +%endif + +%endif + +%assign %%i 0 +%rep REPCOUNT + psll%4 m %+ %%i, m%3 +%assign %%i %%i+1 +%endrep + +%assign %%i 0 +%rep REPCOUNT + mova [outq + %%i*mmsize], m %+ %%i +%assign %%i %%i+1 +%endrep + + add in0q, mmsize + add outq, mmsize*REPCOUNT + sub lend, mmsize/4 + jg .loop + REP_RET +%endmacro + +INIT_XMM sse2 +FLAC_DECORRELATE_16 indep2, 0, 1 ; Reuse stereo 16bits macro +FLAC_DECORRELATE_INDEP 32, 2, 3, d +FLAC_DECORRELATE_INDEP 16, 4, 3, w +FLAC_DECORRELATE_INDEP 32, 4, 5, d +FLAC_DECORRELATE_INDEP 16, 6, 4, w +FLAC_DECORRELATE_INDEP 32, 6, 7, d +%if ARCH_X86_64 +FLAC_DECORRELATE_INDEP 16, 8, 5, w +FLAC_DECORRELATE_INDEP 32, 8, 9, d +%endif + +INIT_XMM avx +FLAC_DECORRELATE_INDEP 32, 4, 5, d +FLAC_DECORRELATE_INDEP 32, 6, 7, d +%if ARCH_X86_64 +FLAC_DECORRELATE_INDEP 16, 8, 5, w +FLAC_DECORRELATE_INDEP 32, 8, 9, d +%endif
new file mode 100644 --- /dev/null +++ b/media/ffvpx/libavcodec/x86/flacdsp_init.c @@ -0,0 +1,115 @@ +/* + * Copyright (c) 2014 James Almer + * + * This file is part of FFmpeg. + * + * FFmpeg is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * FFmpeg is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with FFmpeg; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include "libavcodec/flacdsp.h" +#include "libavutil/x86/cpu.h" +#include "config.h" + +void ff_flac_lpc_32_sse4(int32_t *samples, const int coeffs[32], int order, + int qlevel, int len); +void ff_flac_lpc_32_xop(int32_t *samples, const int coeffs[32], int order, + int qlevel, int len); + +void ff_flac_enc_lpc_16_sse4(int32_t *, const int32_t *, int, int, const int32_t *,int); + +#define DECORRELATE_FUNCS(fmt, opt) \ +void ff_flac_decorrelate_ls_##fmt##_##opt(uint8_t **out, int32_t **in, int channels, \ + int len, int shift); \ +void ff_flac_decorrelate_rs_##fmt##_##opt(uint8_t **out, int32_t **in, int channels, \ + int len, int shift); \ +void ff_flac_decorrelate_ms_##fmt##_##opt(uint8_t **out, int32_t **in, int channels, \ + int len, int shift); \ +void ff_flac_decorrelate_indep2_##fmt##_##opt(uint8_t **out, int32_t **in, int channels, \ + int len, int shift); \ +void ff_flac_decorrelate_indep4_##fmt##_##opt(uint8_t **out, int32_t **in, int channels, \ + int len, int shift); \ +void ff_flac_decorrelate_indep6_##fmt##_##opt(uint8_t **out, int32_t **in, int channels, \ + int len, int shift); \ +void ff_flac_decorrelate_indep8_##fmt##_##opt(uint8_t **out, int32_t **in, int channels, \ + int len, int shift) + +DECORRELATE_FUNCS(16, sse2); +DECORRELATE_FUNCS(16, avx); +DECORRELATE_FUNCS(32, sse2); +DECORRELATE_FUNCS(32, avx); + +av_cold void ff_flacdsp_init_x86(FLACDSPContext *c, enum AVSampleFormat fmt, int channels, + int bps) +{ +#if HAVE_YASM + int cpu_flags = av_get_cpu_flags(); + +#if CONFIG_FLAC_DECODER + if (EXTERNAL_SSE2(cpu_flags)) { + if (fmt == AV_SAMPLE_FMT_S16) { + if (channels == 2) + c->decorrelate[0] = ff_flac_decorrelate_indep2_16_sse2; + else if (channels == 4) + c->decorrelate[0] = ff_flac_decorrelate_indep4_16_sse2; + else if (channels == 6) + c->decorrelate[0] = ff_flac_decorrelate_indep6_16_sse2; + else if (ARCH_X86_64 && channels == 8) + c->decorrelate[0] = ff_flac_decorrelate_indep8_16_sse2; + c->decorrelate[1] = ff_flac_decorrelate_ls_16_sse2; + c->decorrelate[2] = ff_flac_decorrelate_rs_16_sse2; + c->decorrelate[3] = ff_flac_decorrelate_ms_16_sse2; + } else if (fmt == AV_SAMPLE_FMT_S32) { + if (channels == 2) + c->decorrelate[0] = ff_flac_decorrelate_indep2_32_sse2; + else if (channels == 4) + c->decorrelate[0] = ff_flac_decorrelate_indep4_32_sse2; + else if (channels == 6) + c->decorrelate[0] = ff_flac_decorrelate_indep6_32_sse2; + else if (ARCH_X86_64 && channels == 8) + c->decorrelate[0] = ff_flac_decorrelate_indep8_32_sse2; + c->decorrelate[1] = ff_flac_decorrelate_ls_32_sse2; + c->decorrelate[2] = ff_flac_decorrelate_rs_32_sse2; + c->decorrelate[3] = ff_flac_decorrelate_ms_32_sse2; + } + } + if (EXTERNAL_SSE4(cpu_flags)) { + c->lpc32 = ff_flac_lpc_32_sse4; + } + if (EXTERNAL_AVX(cpu_flags)) { + if (fmt == AV_SAMPLE_FMT_S16) { + if (ARCH_X86_64 && channels == 8) + c->decorrelate[0] = ff_flac_decorrelate_indep8_16_avx; + } else if (fmt == AV_SAMPLE_FMT_S32) { + if (channels == 4) + c->decorrelate[0] = ff_flac_decorrelate_indep4_32_avx; + else if (channels == 6) + c->decorrelate[0] = ff_flac_decorrelate_indep6_32_avx; + else if (ARCH_X86_64 && channels == 8) + c->decorrelate[0] = ff_flac_decorrelate_indep8_32_avx; + } + } + if (EXTERNAL_XOP(cpu_flags)) { + c->lpc32 = ff_flac_lpc_32_xop; + } +#endif + +#if CONFIG_FLAC_ENCODER + if (EXTERNAL_SSE4(cpu_flags)) { + if (CONFIG_GPL) + c->lpc16_encode = ff_flac_enc_lpc_16_sse4; + } +#endif +#endif /* HAVE_YASM */ +}
--- a/media/ffvpx/libavcodec/x86/moz.build +++ b/media/ffvpx/libavcodec/x86/moz.build @@ -1,16 +1,18 @@ # -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*- # vim: set filetype=python: # This Source Code Form is subject to the terms of the Mozilla Public # License, v. 2.0. If a copy of the MPL was not distributed with this # file, You can obtain one at http://mozilla.org/MPL/2.0/. SOURCES += [ 'constants.c', + 'flacdsp.asm', + 'flacdsp_init.c', 'h264_intrapred.asm', 'h264_intrapred_10bit.asm', 'h264_intrapred_init.c', 'videodsp.asm', 'videodsp_init.c', 'vp8dsp.asm', 'vp8dsp_init.c', 'vp8dsp_loopfilter.asm',