| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121 | using PlcSiemens.O;using PlcSiemens.Protocol.Common;using PlcSiemens.Protocol.Header;namespace PlcSiemens.Protocol.Iso{    public class IsoControlPdu : IBuildRequest, IBuildResponse    {        public TpktHeader Tpkt { get; set; } // TPKT Header        public CotpHeader Cotp { get; set; } // COPT Header for CONNECTION stuffs        public int IsoPduSize { get; set; }        public ushort SrcRef { get; set; }        public ushort DstRef { get; set; }        public ushort SrcTSap { get; set; }        public ushort DstTSap { get; set; }        /// <summary>        /// 该报发送长度和接受长度都应该为22        /// </summary>        public IsoControlPdu()        {            Tpkt = new TpktHeader();            Cotp = new CotpHeader();        }        public void Build()        {            Cotp.Params.PduSizeCode = 0xC0;            Cotp.Params.PduSizeLen = 0x01;            switch (IsoPduSize)            {                case 128:                    Cotp.Params.PduSizeVal = 0x07;                    break;                case 256:                    Cotp.Params.PduSizeVal = 0x08;                    break;                case 512:                    Cotp.Params.PduSizeVal = 0x09;                    break;                case 1024:                    Cotp.Params.PduSizeVal = 0x0A;                    break;                case 2048:                    Cotp.Params.PduSizeVal = 0x0B;                    break;                case 4096:                    Cotp.Params.PduSizeVal = 0x0C;                    break;                case 8192:                    Cotp.Params.PduSizeVal = 0x0D;                    break;                default:                    Cotp.Params.PduSizeVal = 0x0B;  // Our Default                    break;            }            // Build TSAPs            Cotp.Params.Tsap[0] = 0xC1;   // code that identifies source TSAP            Cotp.Params.Tsap[1] = 2;      // source TSAP Len            Cotp.Params.Tsap[2] = (byte)((SrcTSap >> 8) & 0xFF); // HI part            Cotp.Params.Tsap[3] = (byte)(SrcTSap & 0xFF); // LO part            Cotp.Params.Tsap[4] = 0xC2; // code that identifies dest TSAP            Cotp.Params.Tsap[5] = 2;    // dest TSAP Len            Cotp.Params.Tsap[6] = (byte)((DstTSap >> 8) & 0xFF); // HI part            Cotp.Params.Tsap[7] = (byte)(DstTSap & 0xFF); // LO part            Cotp.Params.TsapLenth = 8;            // Params length            var parLen = 11;            // 2 Src TSAP (Code+field Len)      +                                        // 2 Src TSAP len                   +                                        // 2 Dst TSAP (Code+field Len)      +                                        // 2 Src TSAP len                   +                                        // 3 PDU size (Code+field Len+Val)  = 11                                        // Telegram length            var isoLen = 4 + // TPKT Header                    7 +           // COTP Header Size without params                    parLen;       // COTP params            Tpkt.Version = StaticConst.IsoTcpVersion;            Tpkt.Reserved = 0;            Tpkt.Length = (ushort)isoLen;            Cotp.Length = (byte)(parLen + 6);  // <-- 6 = 7 - 1 (COTP Header size - 1)            Cotp.PduType = (byte)PduType.ConnRequest; // Connection Request            Cotp.DstRef = DstRef;      // Destination reference            Cotp.SrcRef = SrcRef;      // Source reference            Cotp.CoR = 0x00;        // Class + Option : RFC0983 states that it must be always 0x40                                    // but for some equipment (S7) must be 0 in disaccord of specifications !!!        }        public void Build(byte[] resBytes)        {            ByteBuffer buffer = ByteBuffer.Allocate();            buffer.Push(resBytes);            Tpkt.InitByBuffer(buffer);            Cotp.InitByBuffer(buffer);        }        public ByteBuffer GetBuffer()        {            ByteBuffer buffer = ByteBuffer.Allocate();            Tpkt.GetByteBuffer(buffer);            Cotp.GetByteBuffer(buffer);            return buffer;        }        public void Build(ByteBuffer buffer)        {            Tpkt.InitByBuffer(buffer);            Cotp.InitByBuffer(buffer);        }    }}
 |