Esempio n. 1
0
        public bool Update()
        {
            var bitStream = downloader.DownloadStream;
            var reader    = new EndianBinaryReader(EndianBitConverter.Big, bitStream);

            if (bitStream != null)
            {
                var stream = new StreamReader(bitStream);
                {
                    reader.ReadBytes(3); //"FLV"
                    reader.ReadBytes(6); //Other starter shit

                    while (true)
                    {
                        try
                        {
                            var footer = reader.ReadUInt32();
                            var tag    = new FlvTag();
                            tag.Load(reader);

                            AddedTag(tag);
                        }
                        catch (Exception)
                        {
                            reader.Close();
                            //End of stream
                            return(false);
                        }
                    }
                }
            }

            return(true);
        }
Esempio n. 2
0
        public bool Update()
        {
            var bitStream = downloader.DownloadStream;
            var reader = new EndianBinaryReader(EndianBitConverter.Big, bitStream);

            if(bitStream != null)
            {
                var stream = new StreamReader(bitStream);
                {
                    reader.ReadBytes(3); //"FLV"
                    reader.ReadBytes(6); //Other starter shit

                    while (true)
                    {
                        try
                        {
                            var footer = reader.ReadUInt32();
                            var tag = new FlvTag();
                            tag.Load(reader);

                            AddedTag(tag);

                        }
                        catch (Exception)
                        {
                            reader.Close();
                            //End of stream
                            return false;
                        }
                    }
                }
            }

            return true;
        }
Esempio n. 3
0
        private static int RunExtractAndReturnExitCode(LaunchOptions.Extract opts)
        {
            Quite = opts.Quite;

            using var flv_stream = File.Open(opts.InputPath, FileMode.Open, FileAccess.Read, FileShare.Read);
            var tags = FlvReader.ReadFlvFile(flv_stream, opts.TagNum + 1);

            if (tags.Length > opts.TagNum)
            {
                FlvTag tag = tags[opts.TagNum];
                if (string.IsNullOrWhiteSpace(opts.OutputPath))
                {
                    var s = new MemoryStream();
                    if (tag.TagType == TagType.Script && !opts.Byte)
                    {
                        FlvWriter.WriteTagData(s, flv_stream, tag);
                        s.Position = 0;
                        var body = ScriptTagBody.Parse(s);
                        Console.WriteLine(body.ToJson());
                    }
                    else
                    {
                        FlvWriter.WriteTag(s, flv_stream, tag);
                        var str = BitConverter.ToString(s.ToArray()).Replace("-", "");
                        str = string.Join('\n', str.SplitInParts(64));
                        Console.WriteLine(str);
                    }
                    return(0);
                }
                else
                {
                    var fi = new FileInfo(opts.OutputPath);
                    if (fi.Exists && !opts.Overwrite)
                    {
                        if (!Quite)
                        {
                            Console.WriteLine("文件已经存在,使用 --force 参数覆盖目标位置文件");
                        }
                        return(1);
                    }

                    using var output = fi.Open(FileMode.Create, FileAccess.ReadWrite, FileShare.Read);
                    FlvWriter.WriteTag(output, flv_stream, tag);
                    return(0);
                }
            }
            else
            {
                if (!Quite)
                {
                    Console.WriteLine($"文件中只有个 {tags.Length} Tag,而需要第 {opts.TagNum} 个 Tag");
                }
                return(1);
            }
        }
Esempio n. 4
0
        public void Remove(int index)
        {
            if (index < 0 || index >= Tags.Count)
            {
                return;
            }
            FlvTag tag = Tags[index];

            //if (Duration <= tag.TimeStamp) {
            //    RefreshDuration();
            //}
            this.Length -= tag.DataSize + 11;
            Tags.RemoveAt(index);
        }
Esempio n. 5
0
        public FlvParser(Stream stream, Predicate <FlvTag> exec)
        {
            FLVHeader header = FLVHeader.ReadHeader(stream);

            if (!header.IsFlv)
            {
                this.IsFlv = false;
                return;
            }
            this.IsFlv = true;
            stream.Seek(header.Length, SeekOrigin.Begin);
            Tags = new List <FlvTag>();
            FlvTag tag;

            while ((tag = FlvTag.ReadTag(stream)) != null)
            {
                if (tag is ScriptTag)
                {
                    this.MetaTag = tag as ScriptTag;
                }
                Tags.Add(tag);
                if (Duration < tag.TimeStamp)
                {
                    Duration = tag.TimeStamp;
                }
                if (exec != null)
                {
                    if (!exec(tag))
                    {
                        break;
                    }
                }
            }
            if (Tags.Count > 1)
            {
                this.Length = stream.Length - Tags[1].Offset + 11; //+ FlvMain.c_HeaderSize;
                this.Rate   = (this.Duration == 0 ? 0 : this.Length * 8 / this.Duration);
            }
        }
Esempio n. 6
0
        private void flvStreamSource_SampleRequested(MediaStreamSource sender, MediaStreamSourceSampleRequestedEventArgs args)
        {
            MediaStreamSourceSampleRequest         request = args.Request;
            MediaStreamSourceSampleRequestDeferral deferal = request.GetDeferral();

            FlvFile           flvFile = mediaStreamFileSource as FlvFile;
            FlvTag            flvTag  = null;
            MemoryStream      stream  = null;
            MediaStreamSample sample  = null;

            try
            {
                if (flvFile != null)
                {
                    if (request.StreamDescriptor is VideoStreamDescriptor)
                    {
                        flvTag = flvFile.FlvFileBody.CurrentVideoTag;

                        if (flvTag.VideoData.CodecID == CodecID.AVC)
                        {
                            byte[] by = flvTag.VideoData.AVCVideoPacket.NALUs;

                            if (by != null && by.Length > 0)
                            {
                                MemoryStream srcStream = new MemoryStream(by);
                                stream = new MemoryStream();

                                if (flvTag.VideoData.FrameType == FrameType.Keyframe)
                                {
                                    if (NALUnitHeader != null)
                                    {
                                        stream.Write(NALUnitHeader, 0, NALUnitHeader.Length);
                                    }
                                }

                                using (BinaryReader reader = new BinaryReader(srcStream))
                                {
                                    var sampleSize = srcStream.Length;
                                    while (sampleSize > 4L)
                                    {
                                        var ui32  = reader.ReadUInt32();
                                        var count = OldSkool.swaplong(ui32);
                                        stream.Write(h264StartCode, 0, h264StartCode.Length);
                                        stream.Write(reader.ReadBytes((int)count), 0, (int)count);
                                        sampleSize -= 4 + (uint)count;
                                    }
                                }

                                if (stream != null && stream.Length > 0)
                                {
                                    IBuffer buffer = stream.ToArray().AsBuffer();
                                    stream.Position = 0;
                                    sample          = MediaStreamSample.CreateFromBuffer(buffer, TimeSpan.FromTicks(flvTag.Timestamp));
                                    sample.KeyFrame = flvTag.VideoData.FrameType == FrameType.Keyframe;
                                }
                            }
                        }
                        else
                        {
                            IBuffer buffer = flvTag.VideoData.RawData.AsBuffer();
                            sample          = MediaStreamSample.CreateFromBuffer(buffer, TimeSpan.FromTicks(flvTag.Timestamp));
                            sample.KeyFrame = flvTag.VideoData.FrameType == FrameType.Keyframe;
                        }
                    }
                    else
                    {
                        byte[] by = null;
                        flvTag = flvFile.FlvFileBody.CurrentAudioTag;

                        switch (flvTag.AudioData.SoundFormat)
                        {
                        case SoundFormat.AAC:
                            by = (flvTag.AudioData.SoundData as AACAudioData).RawAACFrameData;
                            break;

                        case SoundFormat.MP3:
                            by = flvTag.AudioData.SoundData.RawData;
                            break;

                        case SoundFormat.ADPCM:
                            by = flvTag.AudioData.SoundData.RawData;
                            break;
                        }


                        if (by != null && by.Length > 0)
                        {
                            stream = new MemoryStream(by);
                            IBuffer buffer = by.AsBuffer();

                            sample          = MediaStreamSample.CreateFromBuffer(buffer, TimeSpan.FromTicks(flvTag.Timestamp));
                            sample.KeyFrame = true;
                            request.Sample  = sample;
                        }
                    }
                }

                //샘플보고
                request.Sample = sample;
            }
            catch (Exception e)
            {
                System.Diagnostics.Debug.WriteLine("샘플오류 " + e.Message);
                sender.NotifyError(MediaStreamSourceErrorStatus.DecodeError);
            }
            finally
            {
                if (deferal != null)
                {
                    deferal.Complete();
                }
            }
        }
Esempio n. 7
0
        private void SetNalUnitParameterSets(FlvTag videoInfoFlvTag)
        {
            List <byte[]> sequenceParameterSets = new List <byte[]>();
            List <byte[]> pictureParameterSets  = new List <byte[]>();

            //Video
            byte[] abyte = videoInfoFlvTag.VideoData.AVCVideoPacket.AVCDecoderConfigurationRecord;
            using (MemoryStream sm = new MemoryStream(abyte))
            {
                long offset = 0;
                uint configurationVersion = sm.ReadUInt8(ref offset);
                uint AVCProfileIndication = sm.ReadUInt8(ref offset);

                uint profile_compatibility = sm.ReadUInt8(ref offset);
                uint AVCLevelIndication    = sm.ReadUInt8(ref offset);
                uint t1 = sm.ReadUInt8(ref offset);

                uint lengthSizeMinusOne            = (t1 & 3);
                uint lengthSizeMinusOnePaddingBits = (t1 >> 2);

                uint t2 = sm.ReadUInt8(ref offset);

                uint numberOfSeuqenceParameterSets            = (t2 & 7);
                uint numberOfSequenceParameterSetsPaddingBits = (t2 >> 5);

                for (int i = 0; i < numberOfSeuqenceParameterSets; i++)
                {
                    byte[] by = new byte[2];
                    sm.Read(by, 0, by.Length);

                    Array.Reverse(by);

                    int    sequenceParameterSetLength  = BitConverter.ToInt16(by, 0);
                    byte[] sequenceParameterSetNALUnit = new byte[sequenceParameterSetLength];
                    sm.Read(sequenceParameterSetNALUnit, 0, sequenceParameterSetLength);
                    sequenceParameterSets.Add(sequenceParameterSetNALUnit);
                }
                offset = sm.Position;
                uint numberOfPictureParameterSets = sm.ReadUInt8(ref offset);
                for (int i = 0; i < numberOfPictureParameterSets; i++)
                {
                    byte[] by = new byte[2];
                    sm.Read(by, 0, by.Length);
                    Array.Reverse(by);

                    int    pictureParameterSetLength  = BitConverter.ToInt16(by, 0);
                    byte[] pictureParameterSetNALUnit = new byte[pictureParameterSetLength];
                    sm.Read(pictureParameterSetNALUnit, 0, pictureParameterSetLength);
                    pictureParameterSets.Add(pictureParameterSetNALUnit);
                }

                //NAL Sequence Parameter Set, Picture Parameter Set
                using (MemoryStream ms = new MemoryStream())
                {
                    var sps = sequenceParameterSets[0];
                    var pps = pictureParameterSets[0];

                    ms.Write(h264StartCode, 0, h264StartCode.Length);
                    ms.Write(sps, 0, sps.Length);
                    ms.Write(h264StartCode, 0, h264StartCode.Length);
                    ms.Write(pps, 0, pps.Length);

                    NALUnitHeader = ms.ToArray();
                }
            }
        }
Esempio n. 8
0
        IMediaStreamDescriptor GetFlvAudioDescriptor(FlvTag audioInfoFlvTag)
        {
            AudioEncodingProperties audioEncodingProperites = null;
            AudioStreamDescriptor   audioStreamDescriptor   = null;
            uint sampleRate   = 0;
            uint channelCount = 0;
            uint bitRate      = 0;

            switch (audioInfoFlvTag.AudioData.SoundRate)
            {
            case SoundRate._5kHz:
                sampleRate = 5512;
                break;

            case SoundRate._11kHz:
                sampleRate = 11025;
                break;

            case SoundRate._22kHz:
                sampleRate = 22050;
                break;

            case SoundRate._44kHz:
                sampleRate = 44100;
                break;
            }

            switch (audioInfoFlvTag.AudioData.SoundSize)
            {
            case SoundSize.snd8Bit:
                bitRate = 8;
                break;

            case SoundSize.snd16Bit:
                bitRate = 16;
                break;
            }


            switch (audioInfoFlvTag.AudioData.SoundType)
            {
            case SoundType.sndMono:
                channelCount = 1;
                break;

            case SoundType.sndStereo:
                channelCount = 2;
                break;
            }

            switch (audioInfoFlvTag.AudioData.SoundFormat)
            {
            case SoundFormat.AAC:
                if ((audioInfoFlvTag.AudioData.SoundData as AACAudioData).AudioSpecificConfig != null)
                {
                    var acfg = (audioInfoFlvTag.AudioData.SoundData as AACAudioData).AudioSpecificConfig;

                    int offset = 0;
                    var type   = BitHelper.Read(acfg, ref offset, 5);
                    if (type == 31)
                    {
                        type = BitHelper.Read(acfg, ref offset, 6) + 32;
                    }
                    var feqIndex = BitHelper.Read(acfg, ref offset, 4);
                    if (feqIndex == 15)
                    {
                        sampleRate = (uint)BitHelper.Read(acfg, ref offset, 24);
                    }
                    else
                    {
                        sampleRate = Mp4AudioSpecificConfig.GetSamplingFrequency(feqIndex);
                    }
                    channelCount = (uint)BitHelper.Read(acfg, ref offset, 4);
                }
                audioEncodingProperites = AudioEncodingProperties.CreateAac(sampleRate, channelCount, bitRate);
                break;

            case SoundFormat.ADPCM:
                audioEncodingProperites = AudioEncodingProperties.CreatePcm(sampleRate, channelCount, bitRate);
                break;

            case SoundFormat.MP3:
                audioEncodingProperites = AudioEncodingProperties.CreateMp3(sampleRate, channelCount, bitRate);
                break;

            default:
                break;
            }

            audioStreamDescriptor = new AudioStreamDescriptor(audioEncodingProperites);
            return(audioStreamDescriptor);
        }
Esempio n. 9
0
 internal static FlvTag ReadTag(Stream stream)
 {
     try {
         FlvTag tag;
         byte[] buffer = new byte[4];
         int rtn;
         rtn = stream.Read(buffer, 0, 4);
         if (rtn <= 0) {
             return null;
         }
         int type = stream.ReadByte();
         if (type == 8)
             tag = new AudioTag();
         else if (type == 9)
             tag = new VideoTag();
         else if (type == 0x12)
             tag = new ScriptTag();
         else
             tag = new FlvTag();
         tag.presize = ByteUtil.ByteToUInt(buffer, 4);
         tag.tagtype = type;
         tag.datasize = ByteUtil.ReadUI24(stream);
         tag.timestamp = ByteUtil.ReadUI24(stream);
         tag.timestamp_ex = stream.ReadByte();
         tag.streamid = ByteUtil.ReadUI24(stream);
         tag.offset = stream.Position;
         if (tag is ScriptTag) {
             (tag as ScriptTag).ReadScript(stream);
             stream.Seek(tag.offset + tag.DataSize, SeekOrigin.Begin);
         } else if (tag is AudioTag) {
             rtn = stream.Read(buffer, 0, 1);
             if (rtn <= 0)
                 return null;
             tag.taginfo = buffer[0];
             stream.Seek(tag.DataSize - 1, SeekOrigin.Current);
         } else if (tag is VideoTag) {
             rtn = stream.Read(buffer, 0, 2);
             if (rtn <= 0)
                 return null;
             tag.taginfo = buffer[0];
             tag.avcpaktype = buffer[1];
             stream.Seek(tag.DataSize - 2, SeekOrigin.Current);
         }
         return tag;
     } catch {
         return null;
     }
 }
Esempio n. 10
0
 internal static FlvTag ReadTag(Stream stream)
 {
     try {
         FlvTag tag;
         byte[] buffer = new byte[4];
         int    rtn;
         rtn = stream.Read(buffer, 0, 4);
         if (rtn <= 0)
         {
             return(null);
         }
         int type = stream.ReadByte();
         if (type == 8)
         {
             tag = new AudioTag();
         }
         else if (type == 9)
         {
             tag = new VideoTag();
         }
         else if (type == 0x12)
         {
             tag = new ScriptTag();
         }
         else
         {
             tag = new FlvTag();
         }
         tag.presize      = ByteUtil.ByteToUInt(buffer, 4);
         tag.tagtype      = type;
         tag.datasize     = ByteUtil.ReadUI24(stream);
         tag.timestamp    = ByteUtil.ReadUI24(stream);
         tag.timestamp_ex = stream.ReadByte();
         tag.streamid     = ByteUtil.ReadUI24(stream);
         tag.offset       = stream.Position;
         if (tag is ScriptTag)
         {
             (tag as ScriptTag).ReadScript(stream);
             stream.Seek(tag.offset + tag.DataSize, SeekOrigin.Begin);
         }
         else if (tag is AudioTag)
         {
             rtn = stream.Read(buffer, 0, 1);
             if (rtn <= 0)
             {
                 return(null);
             }
             tag.taginfo = buffer[0];
             stream.Seek(tag.DataSize - 1, SeekOrigin.Current);
         }
         else if (tag is VideoTag)
         {
             rtn = stream.Read(buffer, 0, 2);
             if (rtn <= 0)
             {
                 return(null);
             }
             tag.taginfo    = buffer[0];
             tag.avcpaktype = buffer[1];
             stream.Seek(tag.DataSize - 2, SeekOrigin.Current);
         }
         return(tag);
     } catch {
         return(null);
     }
 }
        private int ComputeOffset(Span <FlvTag> span, int index, int audioDiff, int videoDiff)
        {
            try
            {
                FlvTag beforeVideo = new FlvTag(), afterVideo, beforeAudio = new FlvTag(), afterAudio;
                bool   findA = false, findV = false;

                if (span[index].TagType == TagType.Audio)
                {
                    afterAudio = span[index];
                    int i = 1;
                    do
                    {
                        if ((!span[index + i].Flag.HasFlag(TagFlag.SameAsLastTimestamp)) && span[index + i].TagType == TagType.Video)
                        {
                            afterVideo = span[index + i];
                            break;
                        }
                        i++;
                    } while (true);
                }
                else
                {
                    afterVideo = span[index];
                    int i = 1;
                    do
                    {
                        if ((!span[index + i].Flag.HasFlag(TagFlag.SameAsLastTimestamp)) && span[index + i].TagType == TagType.Audio)
                        {
                            afterAudio = span[index + i];
                            break;
                        }
                        i++;
                    } while (true);
                }

                {
                    int i = 1;
                    do
                    {
                        FlvTag curr = span[index - i];
                        if (!curr.Flag.HasFlag(TagFlag.SameAsLastTimestamp))
                        {
                            if (!findA && curr.TagType == TagType.Audio)
                            {
                                findA       = true;
                                beforeAudio = curr;
                            }
                            else if (!findV && curr.TagType == TagType.Video)
                            {
                                findV       = true;
                                beforeVideo = curr;
                            }
                        }
                        i++;
                    } while (!(findA && findV));
                }

                var vtimstamp = beforeVideo.TimeStamp + videoDiff;
                if (vtimstamp <= beforeAudio.TimeStamp)
                {
                    vtimstamp = beforeAudio.TimeStamp + 1;
                }

                var atimestamp = beforeAudio.TimeStamp + audioDiff;
                if (atimestamp <= beforeVideo.TimeStamp)
                {
                    atimestamp = beforeVideo.TimeStamp + 1;
                }

                if (atimestamp > vtimstamp)
                {
                    return(atimestamp - afterAudio.TimeStamp);
                }
                else
                {
                    return(vtimstamp - afterVideo.TimeStamp);
                }
            }
            catch (IndexOutOfRangeException)
            {
                Console.WriteLine("请反馈问题:计算偏移量失败,i" + index);
                return(0);
            }
        }
        private FlvTag[] ReadAllTagsFromInput(Stream stream)
        {
            List <FlvTag> tags = new List <FlvTag>(1800);

            byte[] b = new byte[4];

            do
            {
                FlvTag tag = new FlvTag();
                // ----------------------------- //
                if (4 != stream.Read(b, 0, 4))
                {
                    break;
                }
                // ----------------------------- //
                tag.Position = stream.Position;
                tag.TagType  = (TagType)stream.ReadByte();
                if (tag.TagType != TagType.Audio && tag.TagType != TagType.Video && tag.TagType != TagType.Script)
                {
                    break;
                }
                // ----------------------------- //
                b[0] = 0;
                if (3 != stream.Read(b, 1, 3))
                {
                    break;
                }
                tag.TagSize = BitConverter.ToInt32(b.ToBE(), 0);
                // ----------------------------- //
                if (3 != stream.Read(b, 1, 3))
                {
                    break;
                }
                var temp = stream.ReadByte();
                if (temp == -1)
                {
                    break;
                }
                b[0]          = (byte)temp;
                tag.TimeStamp = BitConverter.ToInt32(b.ToBE(), 0);
                // ----------------------------- //
                switch (tag.TagType)
                {
                case TagType.Audio:
                {
                    if (4 != stream.Read(b, 0, 4))
                    {
                        goto break_out;
                    }
                    tag.Flag = stream.ReadByte() == 0 ? TagFlag.Header : TagFlag.None;
                    var totalSkip = tag.TagSize - 2;
                    if (totalSkip != stream.SkipBytes(totalSkip))
                    {
                        goto break_out;
                    }
                }
                break;

                case TagType.Video:
                {
                    if (3 != stream.Read(b, 0, 3))
                    {
                        goto break_out;
                    }
                    if (stream.ReadByte() == 0x17)
                    {
                        tag.Flag |= TagFlag.Keyframe;
                    }
                    switch (stream.ReadByte())
                    {
                    case 0:
                        tag.Flag |= TagFlag.Header;
                        break;

                    case 2:
                        tag.Flag |= TagFlag.End;
                        break;
                    }
                    var totalSkip = tag.TagSize - 2;
                    if (totalSkip != stream.SkipBytes(totalSkip))
                    {
                        goto break_out;
                    }
                }
                break;

                default:
                {
                    var totalSkip = 3 + tag.TagSize;
                    if (totalSkip != stream.SkipBytes(totalSkip))
                    {
                        goto break_out;
                    }
                }
                break;
                }
                // ----------------------------- //
                tags.Add(tag);
            } while (true);

break_out:

            return(tags.ToArray());
        }