public void Queue(RtmpEvent message, int streamId, int messageStreamId)
        {
            var header = new RtmpHeader();
            var packet = new RtmpPacket(header, message);

            header.StreamId = streamId;
            header.Timestamp = message.Timestamp;
            header.MessageStreamId = messageStreamId;
            header.MessageType = message.MessageType;
            if (message.Header != null)
                header.IsTimerRelative = message.Header.IsTimerRelative;
            queuedPackets.Enqueue(packet);
            packetAvailableEvent.Set();
        }
        void WriteCommandOrData(AmfWriter writer, RtmpEvent o, ObjectEncoding encoding)
        {
            var command = o as Command;
            var methodCall = command.MethodCall;
            var isInvoke = command is Invoke;

            // write the method name or result type (first section)
            var isRequest = methodCall.CallStatus == CallStatus.Request;
            if (isRequest)
                writer.WriteAmfItem(encoding, methodCall.Name);
            else
                writer.WriteAmfItem(encoding, methodCall.IsSuccess ? "_result" : "_error");

            if (isInvoke)
            {
                writer.WriteAmfItem(encoding, command.InvokeId);
                writer.WriteAmfItem(encoding, command.ConnectionParameters);
            }

            if (isRequest)
            {
                // write arguments
                foreach (var arg in methodCall.Parameters)
                    writer.WriteAmfItem(encoding, arg);
            }
            else if (isInvoke)
            {
                // write the result
                if (!methodCall.IsSuccess)
                    methodCall.Parameters = new object[] { new StatusAsObject(StatusCode.CallFailed, "error", "Call failed.") };
                writer.WriteAmfItem(encoding, methodCall.Parameters);
            }
        }
 void WriteData(AmfWriter writer, RtmpEvent o, ObjectEncoding encoding)
 {
     var command = o as Command;
     if (command.MethodCall == null)
         WriteCommandOrData(writer, o, encoding);
     else
         writer.WriteBytes(command.Buffer);
 }
 byte[] GetMessageBytes(RtmpEvent message, Action<AmfWriter, RtmpEvent> handler)
 {
     using (var stream = new MemoryStream())
     using (var messageWriter = new AmfWriter(stream, writer.SerializationContext, objectEncoding))
     {
         handler(messageWriter, message);
         return stream.ToArray();
     }
 }
        byte[] GetMessageBytes(RtmpHeader header, RtmpEvent message)
        {
            switch (header.MessageType)
            {
                case MessageType.SetChunkSize:
                    return GetMessageBytes(message, (w, o) => w.WriteInt32(((ChunkSize)o).Size));
                case MessageType.AbortMessage:
                    return GetMessageBytes(message, (w, o) => w.WriteInt32(((Abort)o).StreamId));
                case MessageType.Acknowledgement:
                    return GetMessageBytes(message, (w, o) => w.WriteInt32(((Acknowledgement)o).BytesRead));
                case MessageType.UserControlMessage:
                    return GetMessageBytes(message, (w, o) =>
                    {
                        var m = (UserControlMessage)o;
                        w.WriteUInt16((ushort)m.EventType);
                        foreach (var v in m.Values)
                            w.WriteInt32(v);
                    });
                case MessageType.WindowAcknowledgementSize:
                    return GetMessageBytes(message, (w, o) => w.WriteInt32(((WindowAcknowledgementSize)o).Count));
                case MessageType.SetPeerBandwith:
                    return GetMessageBytes(message, (w, o) =>
                    {
                        var m = (PeerBandwith)o;
                        w.WriteInt32(m.AcknowledgementWindowSize);
                        w.WriteByte((byte)m.LimitType);
                    });
                case MessageType.Audio:
                case MessageType.Video:
                    return GetMessageBytes(message, (w, o) => w.WriteBytes(((ByteData)o).Data));

                case MessageType.DataAmf0:
                    return GetMessageBytes(message, (w, o) => WriteData(w, o, ObjectEncoding.Amf0));
                case MessageType.SharedObjectAmf0:
                    return new byte[0]; // TODO: `SharedObject`s
                case MessageType.CommandAmf0:
                    return GetMessageBytes(message, (w, o) => WriteCommandOrData(w, o, ObjectEncoding.Amf0));

                case MessageType.DataAmf3:
                    return GetMessageBytes(message, (w, o) => WriteData(w, o, ObjectEncoding.Amf3));
                case MessageType.SharedObjectAmf3:
                    return new byte[0]; // TODO: `SharedObject`s
                case MessageType.CommandAmf3:
                    return GetMessageBytes(message, (w, o) =>
                    {
                        w.WriteByte(0);
                        WriteCommandOrData(w, o, ObjectEncoding.Amf3);
                    });

                case MessageType.Aggregate:
                    // TODO: Aggregate messages
                    System.Diagnostics.Debugger.Break();
                    return new byte[0]; // TODO: `Aggregate`
                default:
                    throw new ArgumentOutOfRangeException("Unknown RTMP message type: " + (int)header.MessageType);
            }
        }
 public RtmpPacket(RtmpHeader header, RtmpEvent body) : this(header)
 {
     Body = body;
     Length = header.PacketLength;
 }
 public RtmpPacket(RtmpEvent body)
 {
     Body = body;
 }
Example #8
0
 public ChannelDataReceivedEventArgs(ChannelType t, RtmpEvent e)
 {
     this.type = t;
     this.e    = e;
 }
 void WriteProtocolControlMessage(RtmpEvent @event)
 {
     writer.Queue(@event, 2, 0);
 }
 public EventReceivedEventArgs(RtmpEvent @event)
 {
     this.Event = @event;
 }