Пример #1
0
        public static double ConvertToDouble(this uint input)
        {
            double output;

            output = Double.FromByteArray(DWord.ToByteArray(input));
            return(output);
        }
Пример #2
0
            private void ReKey() //процедура расширения ключа
            {
                var Me = new DWord[this.Key.Length / 2];
                var Mo = new DWord[this.Key.Length / 2];

                var kCnt = this.Key.Length / 2;

                for (var i = 0; i < kCnt; i++)
                {
                    Me[i]            = this.Key[2 * i];
                    Mo[i]            = this.Key[2 * i + 1];
                    this.SBoxKeys[i] = GenericSBoxKey(Me[i], Mo[i]);
                }


                var keyLen = this.Key.Length * 4 * 8;

                for (var i = 0; i < 20; i++)
                {
                    var A = F32((DWord)(i * 2 * p), Me, keyLen);
                    var B = F32((DWord)(i * 2 * p + p), Mo, keyLen);
                    B = RotateLeft(B, 8);
                    this.SubKeys[2 * i]     = A + B;
                    this.SubKeys[2 * i + 1] = RotateLeft(A + 2 * B, 9);
                }
            }
Пример #3
0
        /// <summary>
        /// Converts from float to DWord (DBD)
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        public static UInt32 ConvertToUInt(this float input)
        {
            uint output;

            output = DWord.FromByteArray(Single.ToByteArray(input));
            return(output);
        }
Пример #4
0
            /// <summary>
            /// Initialize the Twofish key schedule from key32
            /// </summary>
            private void ReKey()
            {
                BuildMds(); //built only first time it is accessed

                var k32e = new DWord[this.Key.Length / 2];
                var k32o = new DWord[this.Key.Length / 2]; //even/odd key dwords

                var k64Cnt = this.Key.Length / 2;

                for (var i = 0; i < k64Cnt; i++)   //split into even/odd key dwords
                {
                    k32e[i] = this.Key[2 * i];
                    k32o[i] = this.Key[2 * i + 1];
                    this.SBoxKeys[k64Cnt - 1 - i] = ReedSolomonMdsEncode(k32e[i], k32o[i]); //compute S-box keys using (12,8) Reed-Solomon code over GF(256)
                }

                int subkeyCnt = RoundSubkeys + 2 * Rounds;
                var keyLen    = this.Key.Length * 4 * 8;

                for (var i = 0; i < subkeyCnt / 2; i++)                              //compute round subkeys for PHT
                {
                    var A = F32((DWord)(i * SubkeyStep), k32e, keyLen);              //A uses even key dwords
                    var B = F32((DWord)(i * SubkeyStep + SubkeyBump), k32o, keyLen); //B uses odd  key dwords
                    B = RotateLeft(B, 8);
                    this.SubKeys[2 * i]     = A + B;                                 //combine with a PHT
                    this.SubKeys[2 * i + 1] = RotateLeft(A + 2 * B, SubkeyRotateLeft);
                }
            }
Пример #5
0
            /// <summary>
            /// Run four bytes through keyed S-boxes and apply MDS matrix.
            /// </summary>
            private static DWord F32(DWord x, DWord[] k32, int keyLen)
            {
                if (keyLen >= 256)
                {
                    x.B0 = (byte)(P8x8[P_04, x.B0] ^ k32[3].B0);
                    x.B1 = (byte)(P8x8[P_14, x.B1] ^ k32[3].B1);
                    x.B2 = (byte)(P8x8[P_24, x.B2] ^ k32[3].B2);
                    x.B3 = (byte)(P8x8[P_34, x.B3] ^ k32[3].B3);
                }
                if (keyLen >= 192)
                {
                    x.B0 = (byte)(P8x8[P_03, x.B0] ^ k32[2].B0);
                    x.B1 = (byte)(P8x8[P_13, x.B1] ^ k32[2].B1);
                    x.B2 = (byte)(P8x8[P_23, x.B2] ^ k32[2].B2);
                    x.B3 = (byte)(P8x8[P_33, x.B3] ^ k32[2].B3);
                }
                if (keyLen >= 128)
                {
                    x = MdsTable[0, P8x8[P_01, P8x8[P_02, x.B0] ^ k32[1].B0] ^ k32[0].B0]
                        ^ MdsTable[1, P8x8[P_11, P8x8[P_12, x.B1] ^ k32[1].B1] ^ k32[0].B1]
                        ^ MdsTable[2, P8x8[P_21, P8x8[P_22, x.B2] ^ k32[1].B2] ^ k32[0].B2]
                        ^ MdsTable[3, P8x8[P_31, P8x8[P_32, x.B3] ^ k32[1].B3] ^ k32[0].B3];
                }

                return(x);
            }
Пример #6
0
        /// <summary>
        /// Converts from DWord (DBD) to float
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        public static float ConvertToFloat(this uint input)
        {
            float output;

            output = Single.FromByteArray(DWord.ToByteArray(input));
            return(output);
        }
Пример #7
0
        private DWord ReadDword(BinaryReader reader)
        {
            DWord result = new DWord {
                Value = reader.ReadUInt32()
            };

            return(result);
        }
Пример #8
0
            /// <summary>
            /// Decrypt block(s) of data using Twofish.
            /// </summary>
            internal void BlockDecrypt(byte[] inputBuffer, int inputOffset, byte[] outputBuffer, int outputBufferOffset)
            {
                var x     = new DWord[BlockSize / 32];
                var input = new DWord[BlockSize / 32];

                for (var i = 0; i < BlockSize / 32; i++)
                {
                    //copy in the block, add whitening
                    input[i] = new DWord(inputBuffer, inputOffset + i * 4);
                    x[i]     = input[i] ^ SubKeys[OutputWhiten + i];
                }

                var keyLen = Key.Length * 4 * 8;

                for (var r = Rounds - 1; r >= 0; r--)
                {
                    //main Twofish decryption loop
                    var t0 = F32(x[0], SBoxKeys, keyLen);
                    var t1 = F32(RotateLeft(x[1], 8), SBoxKeys, keyLen);

                    x[2]  = RotateLeft(x[2], 1);
                    x[2] ^= t0 + t1 + SubKeys[RoundSubkeys + 2 * r]; //PHT, round keys
                    x[3] ^= t0 + 2 * t1 + SubKeys[RoundSubkeys + 2 * r + 1];
                    x[3]  = RotateRight(x[3], 1);

                    if (r > 0)
                    {
                        //unswap, except for last round
                        t0   = x[0];
                        x[0] = x[2];
                        x[2] = t0;
                        t1   = x[1];
                        x[1] = x[3];
                        x[3] = t1;
                    }
                }

                for (var i = 0; i < BlockSize / 32; i++)
                {
                    //copy out, with whitening
                    x[i] ^= SubKeys[InputWhiten + i];
                    if (CipherMode == CipherMode.CBC)
                    {
                        x[i] ^= IV[i];
                        IV[i] = input[i];
                    }

                    outputBuffer[outputBufferOffset + i * 4 + 0] = x[i].B0;
                    outputBuffer[outputBufferOffset + i * 4 + 1] = x[i].B1;
                    outputBuffer[outputBufferOffset + i * 4 + 2] = x[i].B2;
                    outputBuffer[outputBufferOffset + i * 4 + 3] = x[i].B3;
                }
            }
Пример #9
0
            /// <summary>
            /// Encrypt block(s) of data using Twofish.
            /// </summary>
            internal void BlockEncrypt(byte[] inputBuffer, int inputOffset, byte[] outputBuffer, int outputBufferOffset)
            {
                var x = new DWord[BlockSize / 32];

                for (var i = 0; i < BlockSize / 32; i++)
                {
                    //copy in the block, add whitening
                    x[i] = new DWord(inputBuffer, inputOffset + i * 4) ^ SubKeys[InputWhiten + i];
                    if (CipherMode == CipherMode.CBC)
                    {
                        x[i] ^= IV[i];
                    }
                }

                var keyLen = Key.Length * 4 * 8;

                for (var r = 0; r < Rounds; r++)
                {
                    //main Twofish encryption loop
                    var t0 = F32(x[0], SBoxKeys, keyLen);
                    var t1 = F32(RotateLeft(x[1], 8), SBoxKeys, keyLen);

                    x[3]  = RotateLeft(x[3], 1);
                    x[2] ^= t0 + t1 + SubKeys[RoundSubkeys + 2 * r]; //PHT, round keys
                    x[3] ^= t0 + 2 * t1 + SubKeys[RoundSubkeys + 2 * r + 1];
                    x[2]  = RotateRight(x[2], 1);

                    if (r < Rounds - 1)
                    {
                        //swap for next round
                        var tmp = x[0];
                        x[0] = x[2];
                        x[2] = tmp;
                        tmp  = x[1];
                        x[1] = x[3];
                        x[3] = tmp;
                    }
                }

                for (var i = 0; i < BlockSize / 32; i++)
                {
                    //copy out, with whitening
                    var outValue = x[i] ^ SubKeys[OutputWhiten + i];
                    outputBuffer[outputBufferOffset + i * 4 + 0] = outValue.B0;
                    outputBuffer[outputBufferOffset + i * 4 + 1] = outValue.B1;
                    outputBuffer[outputBufferOffset + i * 4 + 2] = outValue.B2;
                    outputBuffer[outputBufferOffset + i * 4 + 3] = outValue.B3;
                    if (CipherMode == CipherMode.CBC)
                    {
                        IV[i] = outValue;
                    }
                }
            }
Пример #10
0
            private static DWord GenericSBoxKey(DWord k0, DWord k1)
            {
                var r = new DWord();

                r.B0 = (byte)(M2[0, 0] * k0.B0 + M2[0, 1] * k0.B1 + M2[0, 2] * k0.B2 + M2[0, 3] * k0.B3
                              + M2[0, 4] * k1.B0 + M2[0, 5] * k1.B1 + M2[0, 6] * k1.B2 + M2[0, 7] * k1.B3);
                r.B1 = (byte)(M2[1, 0] * k0.B0 + M2[1, 1] * k0.B1 + M2[1, 2] * k0.B2 + M2[1, 3] * k0.B3
                              + M2[1, 4] * k1.B0 + M2[1, 5] * k1.B1 + M2[1, 6] * k1.B2 + M2[1, 7] * k1.B3);
                r.B2 = (byte)(M2[2, 0] * k0.B0 + M2[2, 1] * k0.B1 + M2[2, 2] * k0.B2 + M2[2, 3] * k0.B3
                              + M2[2, 4] * k1.B0 + M2[2, 5] * k1.B1 + M2[2, 6] * k1.B2 + M2[2, 7] * k1.B3);
                r.B3 = (byte)(M2[3, 0] * k0.B0 + M2[3, 1] * k0.B1 + M2[3, 2] * k0.B2 + M2[3, 3] * k0.B3
                              + M2[3, 4] * k1.B0 + M2[3, 5] * k1.B1 + M2[3, 6] * k1.B2 + M2[3, 7] * k1.B3);

                return(r);
            }
Пример #11
0
            private const uint RS_GF_FDBK = 0x14D; //field generator

            /// <summary>
            /// Use (12,8) Reed-Solomon code over GF(256) to produce a key S-box dword from two key material dwords.
            /// </summary>
            /// <param name="k0">1st dword</param>
            /// <param name="k1">2nd dword</param>
            private static DWord ReedSolomonMdsEncode(DWord k0, DWord k1)
            {
                var r = new DWord();

                for (var i = 0; i < 2; i++)
                {
                    r ^= (i > 0) ? k0 : k1;     //merge in 32 more key bits
                    for (var j = 0; j < 4; j++) //shift one byte at a time
                    {
                        var b  = (byte)(r >> 24);
                        var g2 = (byte)((b << 1) ^ (((b & 0x80) > 0) ? RS_GF_FDBK : 0));
                        var g3 = (byte)(((b >> 1) & 0x7F) ^ (((b & 1) > 0) ? RS_GF_FDBK >> 1 : 0) ^ g2);
                        r.B3 = (byte)(r.B2 ^ g3);
                        r.B2 = (byte)(r.B1 ^ g2);
                        r.B1 = (byte)(r.B0 ^ g3);
                        r.B0 = b;
                    }
                }
                return(r);
            }
Пример #12
0
            public TwofishImplementation(uint[] key, uint[] iv, CipherMode cipherMode)
            {
                Key = new DWord[key.Length];
                for (var i = 0; i < Key.Length; i++)
                {
                    Key[i] = (DWord)key[i];
                }

                if (iv != null)
                {
                    IV = new DWord[iv.Length];
                    for (var i = 0; i < IV.Length; i++)
                    {
                        IV[i] = (DWord)iv[i];
                    }
                }

                CipherMode = cipherMode;

                ReKey();
            }
Пример #13
0
            internal void BlockDecrypt(byte[] inputBuffer, int inputOffset, byte[] outputBuffer, int outputBufferOffset)
            {
                var x     = new DWord[BlockSize / 32];
                var input = new DWord[BlockSize / 32];

                for (var i = 0; i < BlockSize / 32; i++)
                {
                    input[i] = new DWord(inputBuffer, inputOffset + i * 4);
                    x[i]     = input[i] ^ this.SubKeys[OutputWhiten + i];
                }

                var keyLen = this.Key.Length * 4 * 8;

                for (var r = Rounds - 1; r >= 0; r--)
                {
                    var t0 = F32(x[0], this.SBoxKeys, keyLen);
                    var t1 = F32(RotateLeft(x[1], 8), this.SBoxKeys, keyLen);

                    x[2]  = RotateLeft(x[2], 1);
                    x[2] ^= t0 + t1 + this.SubKeys[8 + 2 * r];
                    x[3] ^= t0 + 2 * t1 + this.SubKeys[9 + 2 * r];
                    x[3]  = RotateRight(x[3], 1);

                    if (r > 0)
                    {
                        t0 = x[0]; x[0] = x[2]; x[2] = t0;
                        t1 = x[1]; x[1] = x[3]; x[3] = t1;
                    }
                }

                for (var i = 0; i < BlockSize / 32; i++)
                {
                    x[i] ^= this.SubKeys[InputWhiten + i];

                    outputBuffer[outputBufferOffset + i * 4 + 0] = x[i].B0;
                    outputBuffer[outputBufferOffset + i * 4 + 1] = x[i].B1;
                    outputBuffer[outputBufferOffset + i * 4 + 2] = x[i].B2;
                    outputBuffer[outputBufferOffset + i * 4 + 3] = x[i].B3;
                }
            }
Пример #14
0
            //функция g

            private static DWord F32(DWord x, DWord[] k32, int keyLen)
            {
                DWord r = new DWord();

                if (keyLen == 256)
                {
                    x.B0 = (byte)(g01(x.B0, 1) ^ k32[3].B0);
                    x.B1 = (byte)(g01(x.B1, 0) ^ k32[3].B1);
                    x.B2 = (byte)(g01(x.B2, 0) ^ k32[3].B2);
                    x.B3 = (byte)(g01(x.B3, 1) ^ k32[3].B3);
                }
                if (keyLen == 192)
                {
                    x.B0 = (byte)(g01(x.B0, 0) ^ k32[2].B0);
                    x.B1 = (byte)(g01(x.B1, 0) ^ k32[2].B1);
                    x.B2 = (byte)(g01(x.B2, 1) ^ k32[2].B2);
                    x.B3 = (byte)(g01(x.B3, 1) ^ k32[2].B3);
                }
                if (keyLen == 128)
                {
                    x.B0 = (byte)(g01(x.B0, 1) ^ k32[1].B0);
                    x.B1 = (byte)(g01(x.B1, 0) ^ k32[1].B1);
                    x.B2 = (byte)(g01(x.B2, 1) ^ k32[1].B2);
                    x.B3 = (byte)(g01(x.B3, 0) ^ k32[1].B3);

                    x.B0 = (byte)(g01(x.B0, 1) ^ k32[0].B0);
                    x.B1 = (byte)(g01(x.B1, 1) ^ k32[0].B1);
                    x.B2 = (byte)(g01(x.B2, 0) ^ k32[0].B2);
                    x.B3 = (byte)(g01(x.B3, 0) ^ k32[0].B3);

                    r.B0 = (byte)(g01(x.B0, 0) * Mds[0, 0] + g01(x.B1, 1) * Mds[0, 1] + g01(x.B2, 0) * Mds[0, 2] + g01(x.B3, 1) * Mds[0, 3]);
                    r.B1 = (byte)(g01(x.B0, 0) * Mds[1, 0] + g01(x.B1, 1) * Mds[1, 1] + g01(x.B2, 0) * Mds[1, 2] + g01(x.B3, 1) * Mds[1, 3]);
                    r.B2 = (byte)(g01(x.B0, 0) * Mds[2, 0] + g01(x.B1, 1) * Mds[2, 1] + g01(x.B2, 0) * Mds[2, 2] + g01(x.B3, 1) * Mds[2, 3]);
                    r.B3 = (byte)(g01(x.B0, 0) * Mds[3, 0] + g01(x.B1, 1) * Mds[3, 1] + g01(x.B2, 0) * Mds[3, 2] + g01(x.B3, 1) * Mds[3, 3]);
                }

                return(r);
            }
Пример #15
0
            internal void BlockEncrypt(byte[] inputBuffer, int inputOffset, byte[] outputBuffer, int outputBufferOffset)
            {
                var x = new DWord[BlockSize / 32];

                for (var i = 0; i < BlockSize / 32; i++)
                {
                    x[i] = new DWord(inputBuffer, inputOffset + i * 4) ^ this.SubKeys[InputWhiten + i];
                }

                var keyLen = this.Key.Length * 4 * 8;

                for (var r = 0; r < Rounds; r++)
                {
                    var a = F32(x[0], this.SBoxKeys, keyLen);
                    var b = F32(RotateLeft(x[1], 8), this.SBoxKeys, keyLen);

                    x[3]  = RotateLeft(x[3], 1);
                    x[2] ^= a + b + this.SubKeys[8 + 2 * r];
                    x[3] ^= a + 2 * b + this.SubKeys[9 + 2 * r];
                    x[2]  = RotateRight(x[2], 1);

                    if (r < Rounds - 1)
                    {
                        var tmp = x[0]; x[0] = x[2]; x[2] = tmp;
                        tmp = x[1]; x[1] = x[3]; x[3] = tmp;
                    }
                }

                for (var i = 0; i < BlockSize / 32; i++)//выходное отбеливание
                {
                    var outValue = x[i] ^ this.SubKeys[OutputWhiten + i];
                    outputBuffer[outputBufferOffset + i * 4 + 0] = outValue.B0;
                    outputBuffer[outputBufferOffset + i * 4 + 1] = outValue.B1;
                    outputBuffer[outputBufferOffset + i * 4 + 2] = outValue.B2;
                    outputBuffer[outputBufferOffset + i * 4 + 3] = outValue.B3;
                }
            }
Пример #16
0
 public void SetUp()
 {
     _mplc  = Substitute.For <IMPLCProvider>();
     _dWord = new DWord(_mplc, StartAddress);
 }
Пример #17
0
 private static DWord RotateRight(DWord x, int n)
 {
     return((x >> n) | (x << (32 - n)));
 }
Пример #18
0
 private static DWord RotateLeft(DWord x, int n)
 {
     return((x << n) | (x >> (32 - n)));
 }
Пример #19
0
        private void SendPackage(IDVPMaster modbus, Device dv, DataBlock db)
        {
            try
            {
                SendDone.WaitOne(-1);

                switch (db.DataType)
                {
                case "Bit":

                    byte[] bitArys = null;
                    switch (db.TypeOfRead)
                    {
                    case "ReadCoilStatus":
                        bitArys = modbus.ReadCoilStatus((byte)dv.SlaveId, $"{db.Tags[0].Address}",
                                                        db.Length);
                        break;

                    case "ReadInputStatus":
                        bitArys = modbus.ReadInputStatus((byte)dv.SlaveId, $"{db.Tags[0].Address}",
                                                         db.Length);
                        break;

                    default:
                        break;
                    }
                    var BitRs = Bit.ToArray(bitArys);
                    // _RequestAndResponseMessage = new RequestAndResponseMessage("ResponseRead", BitRs);

                    if (BitRs.Length > db.Tags.Count)
                    {
                        return;
                    }
                    for (var j = 0; j < BitRs.Length; j++)
                    {
                        db.Tags[j].Value        = BitRs[j];
                        db.Tags[j].Checked      = BitRs[j];
                        db.Tags[j].Enabled      = BitRs[j];
                        db.Tags[j].Visible      = BitRs[j];
                        db.Tags[j].ValueSelect1 = BitRs[j];
                        db.Tags[j].ValueSelect2 = BitRs[j];
                        db.Tags[j].Timestamp    = DateTime.Now;
                    }
                    break;

                case "Byte":
                    var BytArys = modbus.ReadInputStatus((byte)dv.SlaveId, $"{db.Tags[0].Address}",
                                                         db.Length);
                    var BytRs = Bit.ToArray(BytArys);
                    //_RequestAndResponseMessage = new RequestAndResponseMessage("ResponseRead", BytRs);

                    if (BytRs.Length > db.Tags.Count)
                    {
                        return;
                    }
                    for (var j = 0; j < BytRs.Length; j++)
                    {
                        db.Tags[j].Value        = BytRs[j];
                        db.Tags[j].Checked      = BytRs[j];
                        db.Tags[j].Enabled      = BytRs[j];
                        db.Tags[j].Visible      = BytRs[j];
                        db.Tags[j].ValueSelect1 = BytRs[j];
                        db.Tags[j].ValueSelect2 = BytRs[j];
                        db.Tags[j].Timestamp    = DateTime.Now;
                    }
                    break;

                case "Int":
                    var IntArys = modbus.ReadHoldingRegisters((byte)dv.SlaveId,
                                                              $"{db.Tags[0].Address}", db.Length);
                    var IntRs = Int.ToArray(IntArys);
                    if (IntRs.Length > db.Tags.Count)
                    {
                        return;
                    }
                    for (var j = 0; j < IntRs.Length; j++)
                    {
                        db.Tags[j].Value     = IntRs[j];
                        db.Tags[j].Timestamp = DateTime.Now;
                    }
                    break;

                case "DInt":
                    var DIntArys = modbus.ReadHoldingRegisters((byte)dv.SlaveId,
                                                               $"{db.Tags[0].Address}", db.Length);
                    var DIntRs = Int.ToArray(DIntArys);
                    if (DIntRs.Length > db.Tags.Count)
                    {
                        return;
                    }
                    for (var j = 0; j < DIntRs.Length; j++)
                    {
                        db.Tags[j].Value     = DIntRs[j];
                        db.Tags[j].Timestamp = DateTime.Now;
                    }
                    break;

                case "Word":

                    byte[] wdArys = null;
                    switch (db.TypeOfRead)
                    {
                    case "ReadHoldingRegisters":
                        wdArys = modbus.ReadHoldingRegisters((byte)dv.SlaveId, $"{db.Tags[0].Address}", db.Length);

                        break;

                    case "ReadInputRegisters":
                        wdArys = modbus.ReadInputRegisters((byte)dv.SlaveId, $"{db.Tags[0].Address}", db.Length);

                        break;

                    default:
                        break;
                    }
                    // Array.Reverse(wdArys);

                    var wdRs = Word.ToArray(wdArys);
                    //_RequestAndResponseMessage = new RequestAndResponseMessage("ResponseRead", dresult);
                    if (wdRs.Length > db.Tags.Count)
                    {
                        return;
                    }
                    for (var j = 0; j < wdRs.Length; j++)
                    {
                        db.Tags[j].Value     = wdRs[j];
                        db.Tags[j].Timestamp = DateTime.Now;
                    }
                    break;

                case "DWord":
                    var dwArys = modbus.ReadHoldingRegisters((byte)dv.SlaveId,
                                                             $"{db.Tags[0].Address}", db.Length);
                    var dwRs = DWord.ToArray(dwArys);
                    for (var j = 0; j < dwRs.Length; j++)
                    {
                        db.Tags[j].Value     = dwRs[j];
                        db.Tags[j].Timestamp = DateTime.Now;
                    }
                    break;

                case "Real":
                    var rl1Arys = modbus.ReadHoldingRegisters((byte)dv.SlaveId,
                                                              $"{db.Tags[0].Address}", db.Length);
                    var rl1Rs = Real.ToArray(rl1Arys);
                    for (var j = 0; j < rl1Rs.Length; j++)
                    {
                        db.Tags[j].Value     = rl1Rs[j];
                        db.Tags[j].Timestamp = DateTime.Now;
                    }
                    break;
                }
            }
            catch (Exception ex)
            {
                IsConnected = false;
                EventscadaException?.Invoke(this.GetType().Name, ex.Message);
            }
        }
        public bool WriteItems(Tag tag, object value)
        {
            lock (this)
            {
                try
                {
                    if (!IsConnected())
                    {
                        return(false);
                    }

                    if (tag.TagType == "string") //在创建TagType时已经转为小写
                    {
                        var pLcAddress = DbAddress[tag.Address];
                        var strValue   = value.ToString();
                        var strlen     = (byte)strValue.Length;
                        var valueByte  = new byte[strlen + 1];
                        var strbyte    = Encoding.ASCII.GetBytes(strValue);

                        if (strbyte.Length != strlen)
                        {
                            throw new InvalidOperationException("写入" + tag.Address + "出错,解析的字符串长度与GetBytes数组长度不一致!");
                        }

                        if (strlen > pLcAddress.BitOffset)
                        {
                            throw new InvalidOperationException("写入" + tag.Address + "出错,输入的字符串的长度过长!");
                        }

                        valueByte[0] = strlen;
                        strbyte.CopyTo(valueByte, 1);

                        _plc.Write(DataType.DataBlock, pLcAddress.DBBlockID, pLcAddress.Offset + 1,
                                   valueByte);

                        /*if (result != ErrorCode.NoError)
                         *  throw new InvalidOperationException(result + "\n" + "Tag: " + tag.Address);*/

                        return(true);
                    }
                    //2020/6/11 ByteArray

                    if (tag.TagType == "bytearray") //在创建TagType时已经转为小写
                    {
                        var pLcAddress = DbAddress[tag.Address];
                        var strValue   = value.ToString();
                        var strlen     = strValue.Length;
                        var valueByte  = new byte[strlen];
                        var strbyte    = Encoding.ASCII.GetBytes(strValue);

                        if (strbyte.Length != strlen)
                        {
                            throw new InvalidOperationException("写入" + tag.Address + "出错,解析的字符串长度与GetBytes数组长度不一致!");
                        }

                        if (strlen != pLcAddress.BitOffset)
                        {
                            throw new InvalidOperationException("写入" + tag.Address + "出错,输入的字符串长度与定义长度不匹配!");
                        }

                        strbyte.CopyTo(valueByte, 0);

                        _plc.WriteBytes(DataType.DataBlock, pLcAddress.DBBlockID, pLcAddress.Offset,
                                        valueByte);

                        /*if (result != ErrorCode.NoError)
                         *  throw new InvalidOperationException(result + "\n" + "Tag: " + tag.Address);*/

                        return(true);
                    }
                    else
                    {
                        switch (value)
                        {
                        case double d:
                        {
                            var bytes = Double.ToByteArray(d);
                            value = DWord.FromByteArray(bytes);
                            break;
                        }

                        case bool b:
                            value = b ? 1 : 0;
                            break;
                        }

                        _plc.Write(tag.Address, value);

                        /*if (result != ErrorCode.NoError)
                         *  throw new InvalidOperationException(result + "\n" + "Tag: " + tag.Address);*/

                        return(true);
                    }
                }
                catch (Exception ex)
                {
                    //LOG.Error(string.Format("S7 Driver写入地址{0},值{1},出错{2}", tag.Address, value,ex));
                    Log.Error($"S7 Driver writes address:{tag.Address}, value:{value}, Message:{ex}");
                    return(false);
                }
            }
        }
Пример #21
0
        /// <summary>
        /// Given a S7 variable type (Bool, Word, DWord, etc.), it converts the bytes in the appropriate C# format.
        /// </summary>
        /// <param name="varType"></param>
        /// <param name="bytes"></param>
        /// <param name="varCount"></param>
        /// <param name="bitAdr"></param>
        /// <returns></returns>
        private object ParseBytes(VarType varType, byte[] bytes, int varCount, byte bitAdr = 0)
        {
            if (bytes == null || bytes.Length == 0)
            {
                return(null);
            }

            switch (varType)
            {
            case VarType.Byte:
                if (varCount == 1)
                {
                    return(bytes[0]);
                }
                else
                {
                    return(bytes);
                }

            case VarType.Word:
                if (varCount == 1)
                {
                    return(Word.FromByteArray(bytes));
                }
                else
                {
                    return(Word.ToArray(bytes));
                }

            case VarType.Int:
                if (varCount == 1)
                {
                    return(Int.FromByteArray(bytes));
                }
                else
                {
                    return(Int.ToArray(bytes));
                }

            case VarType.DWord:
                if (varCount == 1)
                {
                    return(DWord.FromByteArray(bytes));
                }
                else
                {
                    return(DWord.ToArray(bytes));
                }

            case VarType.DInt:
                if (varCount == 1)
                {
                    return(DInt.FromByteArray(bytes));
                }
                else
                {
                    return(DInt.ToArray(bytes));
                }

            case VarType.Real:
                if (varCount == 1)
                {
                    return(Types.Single.FromByteArray(bytes));
                }
                else
                {
                    return(Types.Single.ToArray(bytes));
                }

            case VarType.String:
                return(Types.String.FromByteArray(bytes));

            case VarType.StringEx:
                return(StringEx.FromByteArray(bytes));

            case VarType.Timer:
                if (varCount == 1)
                {
                    return(Timer.FromByteArray(bytes));
                }
                else
                {
                    return(Timer.ToArray(bytes));
                }

            case VarType.Counter:
                if (varCount == 1)
                {
                    return(Counter.FromByteArray(bytes));
                }
                else
                {
                    return(Counter.ToArray(bytes));
                }

            case VarType.Bit:
                if (varCount == 1)
                {
                    if (bitAdr > 7)
                    {
                        return(null);
                    }
                    else
                    {
                        return(Bit.FromByte(bytes[0], bitAdr));
                    }
                }
                else
                {
                    return(Bit.ToBitArray(bytes));
                }

            default:
                return(null);
            }
        }
Пример #22
0
        /// <summary>
        /// Creates a struct of a specified type by an array of bytes.
        /// </summary>
        /// <param name="structType">The struct type</param>
        /// <param name="bytes">The array of bytes</param>
        /// <returns>The object depending on the struct type or null if fails(array-length != struct-length</returns>
        public static object FromBytes(DataBlock structType, byte[] bytes, PLC plc)
        {
            if (bytes == null)
            {
                return(null);
            }

            if (bytes.Length != GetStructSize(structType))
            {
                return(null);
            }

            // and decode it
            int    bytePos  = 0;
            int    bitPos   = 0;
            double numBytes = 0.0;

            var infos = structType.Tags;

            foreach (Tag info in infos)
            {
                switch (info.DataType.ToString())
                {
                case "Bit":
                    // get the value
                    bytePos = (int)Math.Floor(numBytes);
                    bitPos  = (int)((numBytes - (double)bytePos) / 0.125);
                    if ((bytes[bytePos] & (int)Math.Pow(2, bitPos)) != 0)
                    {
                        info.Value        = true;
                        info.Checked      = true;
                        info.Enabled      = true;
                        info.Visible      = true;
                        info.ValueSelect1 = true;
                        info.ValueSelect2 = true;
                        info.Timestamp    = DateTime.Now;
                    }


                    else
                    {
                        info.Value        = false;
                        info.Checked      = false;
                        info.Enabled      = false;
                        info.Visible      = false;
                        info.ValueSelect1 = false;
                        info.ValueSelect2 = false;
                        info.Timestamp    = DateTime.Now;
                    }

                    numBytes += 0.125;

                    break;

                case "Byte":
                    numBytes = Math.Ceiling(numBytes);
                    info.Value((bytes[(int)numBytes]));
                    info.Timestamp = DateTime.Now;
                    numBytes++;
                    break;

                case "Int":
                    numBytes = Math.Ceiling(numBytes);
                    if ((numBytes / 2 - Math.Floor(numBytes / 2.0)) > 0)
                    {
                        numBytes++;
                    }
                    // hier auswerten
                    ushort source = Word.FromBytes(bytes[(int)numBytes + 1], bytes[(int)numBytes]);
                    info.Value     = source.ConvertToShort();
                    info.Timestamp = DateTime.Now;
                    numBytes      += 2;
                    break;

                case "Word":
                    numBytes = Math.Ceiling(numBytes);
                    if ((numBytes / 2 - Math.Floor(numBytes / 2.0)) > 0)
                    {
                        numBytes++;
                    }
                    // hier auswerten
                    info.Value = Word.FromBytes(bytes[(int)numBytes + 1],
                                                bytes[(int)numBytes]);



                    info.Timestamp = DateTime.Now;
                    numBytes      += 2;
                    break;

                case "DWord":

                    numBytes = Math.Ceiling(numBytes);
                    if ((numBytes / 2 - Math.Floor(numBytes / 2.0)) > 0)
                    {
                        numBytes++;
                    }
                    // hier auswerten
                    uint sourceUInt = DWord.FromBytes(bytes[(int)numBytes + 3],
                                                      bytes[(int)numBytes + 2],
                                                      bytes[(int)numBytes + 1],
                                                      bytes[(int)numBytes + 0]);
                    info.Value = sourceUInt.ConvertToInt();

                    info.Timestamp = DateTime.Now;
                    numBytes      += 4;
                    break;

                case "Real":
                    numBytes = Math.Ceiling(numBytes);
                    if ((numBytes / 2 - Math.Floor(numBytes / 2.0)) > 0)
                    {
                        numBytes++;
                    }
                    // hier auswerten
                    info.Value = S7.Net.Types.Double.FromByteArray(new byte[] { bytes[(int)numBytes],
                                                                                bytes[(int)numBytes + 1],
                                                                                bytes[(int)numBytes + 2],
                                                                                bytes[(int)numBytes + 3] });
                    info.Timestamp = DateTime.Now;
                    numBytes      += 4;
                    break;

                case "Single":
                    numBytes = Math.Ceiling(numBytes);
                    if ((numBytes / 2 - Math.Floor(numBytes / 2.0)) > 0)
                    {
                        numBytes++;
                    }
                    // hier auswerten
                    info.Value = S7.Net.Types.Single.FromByteArray(new byte[] { bytes[(int)numBytes],
                                                                                bytes[(int)numBytes + 1],
                                                                                bytes[(int)numBytes + 2],
                                                                                bytes[(int)numBytes + 3] });
                    numBytes += 4;
                    break;

                case "String":


                    // info.Value = plc.ReadStrings(info.Address);
                    info.Timestamp = DateTime.Now;

                    break;

                default:

                    break;
                }
            }
            return(infos);
        }
Пример #23
0
 private DWord ReadDword(BinaryReader reader)
 {
     DWord result = new DWord {
         Value = reader.ReadUInt32()
     };
     return result;
 }