Пример #1
0
        public static WaveFormatExtensible FromMediaType(AMMediaType pMediaType)
        {
            if (MediaType.Audio != pMediaType.majorType)
            {
                throw new Exception("not Audio");
            }
            if (FormatType.WaveEx != pMediaType.formatType || pMediaType.formatSize < 18)
            {
                throw new Exception("not WaveEx");
            }
            WaveFormatEx pWfx = new WaveFormatEx();

            Marshal.PtrToStructure(pMediaType.formatPtr, pWfx);
            if (pWfx.wFormatTag == unchecked ((short)WAVE_FORMAT_EXTENSIBLE) && pWfx.cbSize >= 22)
            {
                var pWfe = new WaveFormatExtensible();
                Marshal.PtrToStructure(pMediaType.formatPtr, pWfe);
                return(pWfe);
            }
            return(new WaveFormatExtensible()
            {
                nChannels = pWfx.nChannels,
                nSamplesPerSec = pWfx.nSamplesPerSec,
                nBlockAlign = pWfx.nBlockAlign,
                wBitsPerSample = pWfx.wBitsPerSample,
                nAvgBytesPerSec = pWfx.nAvgBytesPerSec,
                wFormatTag = pWfx.wFormatTag,
                cbSize = 0
            });
        }
Пример #2
0
        public WMAWriter(string path, WMAWriterSettings settings)
        {
            this.m_settings = settings;
            this.outputPath = path;

            try
            {
                m_pWriter = settings.GetWriter();
                int cInputs;
                m_pWriter.GetInputCount(out cInputs);
                if (cInputs < 1)
                {
                    throw new InvalidOperationException();
                }
                IWMInputMediaProps pInput;
                m_pWriter.GetInputProps(0, out pInput);
                try
                {
                    int         cbType     = 0;
                    AMMediaType pMediaType = null;
                    pInput.GetMediaType(pMediaType, ref cbType);
                    pMediaType            = new AMMediaType();
                    pMediaType.formatSize = cbType - Marshal.SizeOf(typeof(AMMediaType));
                    pInput.GetMediaType(pMediaType, ref cbType);
                    try
                    {
                        var wfe = new WaveFormatExtensible(m_settings.PCM);
                        Marshal.FreeCoTaskMem(pMediaType.formatPtr);
                        pMediaType.formatPtr  = IntPtr.Zero;
                        pMediaType.formatSize = 0;
                        pMediaType.formatPtr  = Marshal.AllocCoTaskMem(Marshal.SizeOf(wfe));
                        pMediaType.formatSize = Marshal.SizeOf(wfe);
                        Marshal.StructureToPtr(wfe, pMediaType.formatPtr, false);
                        pInput.SetMediaType(pMediaType);
                        m_pWriter.SetInputProps(0, pInput);
                    }
                    finally
                    {
                        WMUtils.FreeWMMediaType(pMediaType);
                    }
                }
                finally
                {
                    Marshal.ReleaseComObject(pInput);
                }
            }
            catch (Exception ex)
            {
                if (m_pWriter != null)
                {
                    Marshal.ReleaseComObject(m_pWriter);
                    m_pWriter = null;
                }
                throw ex;
            }
        }
Пример #3
0
        public AudioDecoder(string path, Stream IO)
        {
            m_path = path;
            isValid(path);
            bool pfIsProtected;

            WMUtils.WMIsContentProtected(path, out pfIsProtected);
            if (pfIsProtected)
            {
                throw new Exception("DRM present");
            }
            WMUtils.WMCreateSyncReader(IntPtr.Zero, Rights.None, out m_syncReader);

            if (path == null)
            {
                m_IO            = IO != null ? IO : new FileStream(path, FileMode.Open, FileAccess.Read, FileShare.Read, 0x10000);
                m_streamWrapper = new StreamWrapper(m_IO);
                m_syncReader.OpenStream(m_streamWrapper);
            }
            else
            {
                m_syncReader.Open(path);
            }
            var pProfile = (m_syncReader as IWMProfile);
            int dwStreamCount;

            pProfile.GetStreamCount(out dwStreamCount);
            for (int dwIndex = 0; dwIndex < dwStreamCount; dwIndex++)
            {
                IWMStreamConfig pConfig = null;
                pProfile.GetStream(dwIndex, out pConfig);
                try
                {
                    Guid guid;
                    pConfig.GetStreamType(out guid);
                    if (MediaType.Audio != guid)
                    {
                        continue;
                    }
                    short wStreamNum;
                    pConfig.GetStreamNumber(out wStreamNum);
                    int dwBitrate = -1;
                    pConfig.GetBitrate(out dwBitrate);
                    var pIWMMediaProps = pConfig as IWMMediaProps;
                    int cbType         = 0;
                    pIWMMediaProps.GetMediaType(null, ref cbType);
                    var pMediaType = new AMMediaType();
                    pMediaType.formatSize = cbType;
                    pIWMMediaProps.GetMediaType(pMediaType, ref cbType);
                    if (pMediaType.formatType != FormatType.WaveEx)
                    {
                        continue;
                    }
                    if (pMediaType.subType != MediaSubType.WMAudio_Lossless)
                    {
                        continue;
                    }
                    m_wStreamNum = wStreamNum;
                    pcm          = WaveFormatExtensible.FromMediaType(pMediaType).GetConfig();
                    break;
                }
                finally
                {
                    Marshal.ReleaseComObject(pConfig);
                }
            }
            if (m_wStreamNum == -1)
            {
                throw new Exception("No WMA lossless streams found");
            }

            m_syncReader.SetReadStreamSamples(m_wStreamNum, false);
            bool pfCompressed;

            m_syncReader.GetReadStreamSamples(m_wStreamNum, out pfCompressed);
            if (pfCompressed)
            {
                throw new Exception("doesn't decompress");
            }
            m_syncReader.GetOutputNumberForStream(m_wStreamNum, out m_dwAudioOutputNum);
            IWMOutputMediaProps pProps;

            m_syncReader.GetOutputProps(m_dwAudioOutputNum, out pProps);

            try
            {
                StringBuilder sName      = null;
                AMMediaType   pMediaType = null;
                int           cbType     = 0;

                cbType     = 0;
                pMediaType = null;
                pProps.GetMediaType(pMediaType, ref cbType);

                // Get the name of the output we'll be using
                sName = null;
                short iName = 0;
                pProps.GetConnectionName(sName, ref iName);

                sName = new StringBuilder(iName);
                pProps.GetConnectionName(sName, ref iName);

                if (pcm.ChannelCount > 2)
                {
                    m_syncReader.SetOutputSetting(m_dwAudioOutputNum, Constants.g_wszEnableDiscreteOutput, AttrDataType.BOOL, new byte[] { 1, 0, 0, 0 }, 4);
                    m_syncReader.SetOutputSetting(m_dwAudioOutputNum, Constants.g_wszSpeakerConfig, AttrDataType.DWORD, new byte[] { 0, 0, 0, 0 }, 4);
                }

                pMediaType            = new AMMediaType();
                pMediaType.formatSize = cbType - Marshal.SizeOf(typeof(AMMediaType));

                //
                // Get the value for MediaType
                //
                pProps.GetMediaType(pMediaType, ref cbType);

                try
                {
                    if (MediaType.Audio != pMediaType.majorType)
                    {
                        throw new Exception("not Audio");
                    }
                    if (FormatType.WaveEx != pMediaType.formatType)
                    {
                        throw new Exception("not WaveEx");
                    }
                    var wfe = new WaveFormatExtensible(pcm);
                    Marshal.FreeCoTaskMem(pMediaType.formatPtr);
                    pMediaType.formatPtr  = IntPtr.Zero;
                    pMediaType.formatSize = 0;
                    pMediaType.formatPtr  = Marshal.AllocCoTaskMem(Marshal.SizeOf(wfe));
                    pMediaType.formatSize = Marshal.SizeOf(wfe);
                    Marshal.StructureToPtr(wfe, pMediaType.formatPtr, false);
                    pProps.SetMediaType(pMediaType);
                    m_syncReader.SetOutputProps(m_dwAudioOutputNum, pProps);
                }
                finally
                {
                    WMUtils.FreeWMMediaType(pMediaType);
                }
            }
            finally
            {
                Marshal.ReleaseComObject(pProps);
            }

            //try
            //{
            //    AttrDataType wmtType;
            //    short cbLength = 0;
            //    short wAnyStream = 0;
            //    var pHeaderInfo = m_syncReader as IWMHeaderInfo;
            //    pHeaderInfo.GetAttributeByName(ref wAnyStream, Constants.g_wszWMDuration, out wmtType, null, ref cbLength);
            //    var pbValue = new byte[cbLength];
            //    pHeaderInfo.GetAttributeByName(ref wAnyStream, Constants.g_wszWMDuration, out wmtType, pbValue, ref cbLength);
            //    var m_cnsFileDuration = BitConverter.ToInt64(pbValue, 0);
            //    _sampleCount = m_cnsFileDuration * m_pWfx.nSamplesPerSec / 10000000;
            //    // NOT ACCURATE ENOUGH (~1ms precision observed)
            //}
            //catch (COMException)
            //{
            //}

            //try
            //{
            //    var pHeaderInfo = m_syncReader as IWMHeaderInfo2;
            //    int nCodec;
            //    pHeaderInfo.GetCodecInfoCount(out nCodec);
            //    for (int wIndex = 0; wIndex < nCodec; wIndex++)
            //    {
            //        CodecInfoType enumCodecType;
            //        short cchName = 0;
            //        short cchDescription = 0;
            //        short cbCodecInfo = 0;
            //        pHeaderInfo.GetCodecInfo(wIndex, ref cchName, null,
            //            ref cchDescription, null, out enumCodecType,
            //            ref cbCodecInfo, null);
            //        var pwszName = new StringBuilder(cchName);
            //        var pwszDescription = new StringBuilder(cchDescription);
            //        var pbCodecInfo = new byte[cbCodecInfo];
            //        pHeaderInfo.GetCodecInfo(wIndex, ref cchName, pwszName,
            //            ref cchDescription, pwszDescription, out enumCodecType,
            //            ref cbCodecInfo, pbCodecInfo);
            //        if (enumCodecType == CodecInfoType.Audio)
            //        {
            //            // pbCodecInfo = {99,1} ??/
            //        }
            //    }
            //}
            //catch (COMException)
            //{
            //}

            //int cbMax;
            //m_syncReader.GetMaxOutputSampleSize(m_dwAudioOutputNum, out cbMax);
        }
Пример #4
0
        internal IEnumerable <WMAFormatInfo> EnumerateFormatInfo(IWMProfileManager pProfileManager2)
        {
            IWMProfileManager pProfileManager = null;

            try
            {
                if (pProfileManager2 == null)
                {
                    WMUtils.WMCreateProfileManager(out pProfileManager);
                }
                var pCodecInfo3 = (pProfileManager2 ?? pProfileManager) as IWMCodecInfo3;
                int cCodecs;
                pCodecInfo3.GetCodecInfoCount(MediaType.Audio, out cCodecs);
                for (int iCodec = 0; iCodec < cCodecs; iCodec++)
                {
                    int szCodecName = 0;
                    pCodecInfo3.GetCodecName(MediaType.Audio, iCodec, null, ref szCodecName);
                    var codecName = new StringBuilder(szCodecName);
                    pCodecInfo3.GetCodecName(MediaType.Audio, iCodec, codecName, ref szCodecName);
                    var    attrDataType = new AttrDataType();
                    int    dwAttrSize   = 0;
                    byte[] pAttrValue   = new byte[4];
                    pCodecInfo3.GetCodecProp(MediaType.Audio, iCodec, Constants.g_wszIsVBRSupported, out attrDataType, pAttrValue, ref dwAttrSize);
                    if (pAttrValue[0] != 1)
                    {
                        continue;
                    }
                    if (m_vbr)
                    {
                        pCodecInfo3.SetCodecEnumerationSetting(MediaType.Audio, iCodec, Constants.g_wszVBREnabled, AttrDataType.BOOL, new byte[] { 1, 0, 0, 0 }, 4);
                        pCodecInfo3.SetCodecEnumerationSetting(MediaType.Audio, iCodec, Constants.g_wszNumPasses, AttrDataType.DWORD, new byte[] { 1, 0, 0, 0 }, 4);
                    }
                    else
                    {
                        pCodecInfo3.SetCodecEnumerationSetting(MediaType.Audio, iCodec, Constants.g_wszVBREnabled, AttrDataType.BOOL, new byte[] { 0, 0, 0, 0 }, 4);
                    }

                    int cFormat;
                    pCodecInfo3.GetCodecFormatCount(MediaType.Audio, iCodec, out cFormat);
                    for (int iFormat = 0; iFormat < cFormat; iFormat++)
                    {
                        IWMStreamConfig pStreamConfig;
                        int             cchDesc = 1024;
                        StringBuilder   szDesc  = new StringBuilder(cchDesc);
                        pCodecInfo3.GetCodecFormatDesc(MediaType.Audio, iCodec, iFormat, out pStreamConfig, szDesc, ref cchDesc);
                        if (szDesc.ToString().Contains("(A/V)"))
                        {
                            continue;
                        }
                        try
                        {
                            var         pProps     = pStreamConfig as IWMMediaProps;
                            int         cbType     = 0;
                            AMMediaType pMediaType = null;
                            pProps.GetMediaType(pMediaType, ref cbType);
                            pMediaType            = new AMMediaType();
                            pMediaType.formatSize = cbType - Marshal.SizeOf(typeof(AMMediaType));
                            pProps.GetMediaType(pMediaType, ref cbType);
                            try
                            {
                                if (pMediaType.majorType == MediaType.Audio && pMediaType.formatType == FormatType.WaveEx && pMediaType.subType == m_subType)
                                {
                                    var pcm = WaveFormatExtensible.FromMediaType(pMediaType).GetConfig();
                                    if (PCM == null || (pcm.ChannelCount == PCM.ChannelCount && pcm.SampleRate == PCM.SampleRate && pcm.BitsPerSample >= PCM.BitsPerSample))
                                    {
                                        yield return new WMAFormatInfo()
                                               {
                                                   codec      = iCodec,
                                                   codecName  = codecName.ToString(),
                                                   format     = iFormat,
                                                   formatName = szDesc.ToString(),
                                                   subType    = pMediaType.subType,
                                                   pcm        = pcm
                                               }
                                    }
                                    ;
                                }
                            }
                            finally
                            {
                                WMUtils.FreeWMMediaType(pMediaType);
                            }
                        }
                        finally
                        {
                            Marshal.ReleaseComObject(pStreamConfig);
                        }
                    }
                }
            }
            finally
            {
                if (pProfileManager != null)
                {
                    Marshal.ReleaseComObject(pProfileManager);
                }
            }
        }