Esempio n. 1
0
        static public byte[] ReadReadout(IGXMedia media, string data, int wt)
        {
            ReceiveParameters <byte[]> p = new ReceiveParameters <byte[]>()
            {
                Eop      = GetEops(),
                WaitTime = wt
            };

            lock (media.Synchronous)
            {
                if (data != null)
                {
                    media.Send(data, null);
                }
                do
                {
                    if (!media.Receive(p))
                    {
                        //There is no eop or CRC.
                        break;
                    }
                }while (p.Reply[p.Reply.Length - 1] != 0x3);
                //Read CRC if EOP is found.
                if (p.Reply[p.Reply.Length - 1] == 0x3)
                {
                    p.Eop   = null;
                    p.Count = 1;
                    if (!media.Receive(p))
                    {
                        throw new Exception("Failed to receive reply from the device in given time.");
                    }
                }
            }
            return(p.Reply);
        }
Esempio n. 2
0
        /// <summary>
        /// Read DLMS Data from the device.
        /// </summary>
        /// <remarks>
        /// If access is denied return null.
        /// </remarks>
        /// <param name="data">Data to send.</param>
        /// <returns>Received data.</returns>
        public void ReadDLMSPacket(byte[] data, GXReplyData reply)
        {
            if ((data == null || data.Length == 0) && !reply.IsStreaming())
            {
                return;
            }
            GXReplyData notify = new GXReplyData();

            reply.Error = 0;
            object eop = (byte)0x7E;

            //In network connection terminator is not used.
            if (client.InterfaceType == InterfaceType.WRAPPER && !parent.UseRemoteSerial)
            {
                eop = null;
            }
            ReceiveParameters <byte[]> p = new ReceiveParameters <byte[]>()
            {
                AllData  = false,
                Eop      = eop,
                Count    = 5,
                WaitTime = parent.WaitTime * 1000,
            };
            var          answer = Send(data);
            GXByteBuffer rd     = new GXByteBuffer(answer.Body);

            try
            {
                //Loop until whole COSEM packet is received.
                while (!client.GetData(rd, reply, notify))
                {
                    p.Reply = null;
                    if (notify.Data.Size != 0)
                    {
                        // Handle notify.
                        if (!notify.IsMoreData)
                        {
                            rd.Trim();
                            notify.Clear();
                            p.Eop = eop;
                        }
                        continue;
                    }
                    //If Eop is not set read one byte at time.
                    if (p.Eop == null)
                    {
                        p.Count = client.GetFrameSize(rd);
                    }
                    rd.Set(p.Reply);
                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
            if (reply.Error != 0)
            {
                throw new GXDLMSException(reply.Error);
            }
        }
Esempio n. 3
0
 /// <inheritdoc cref="IGXMedia.Receive"/>
 public bool Receive <T>(ReceiveParameters <T> args)
 {
     if (!IsOpen)
     {
         throw new InvalidOperationException("Media is closed.");
     }
     return(syncBase.Receive(args));
 }
Esempio n. 4
0
        /// <summary>
        /// Try to find client and server address from the meter.
        /// </summary>
        private void DiscoverMeters(object sender, GXAsyncWork work, object[] parameters)
        {
            GXDLMSClient cl = new GXDLMSClient(true, 16, 1, Authentication.None, null, (InterfaceType)Settings.Default.PlcInterface);

            byte[] data = cl.Plc.DiscoverRequest();
            ReceiveParameters <byte[]> p = new ReceiveParameters <byte[]>()
            {
                AllData  = false,
                Count    = 8,
                WaitTime = 10000,
            };
            DateTime     start = DateTime.Now;
            GXByteBuffer rd    = new GXByteBuffer();

            lock (media.Synchronous)
            {
                if (data != null)
                {
                    media.Send(data, null);
                    start = DateTime.Now;
                }
                GXReplyData reply = new GXReplyData();
                rd = new GXByteBuffer(p.Reply);
                try
                {
                    while (!work.IsCanceled)
                    {
                        p.Reply = null;
                        //If Eop is not set read one byte at time.
                        if (p.Eop == null)
                        {
                            p.Count = cl.GetFrameSize(rd);
                        }
                        if (!media.IsOpen)
                        {
                            throw new InvalidOperationException("Media is closed.");
                        }
                        if (!media.Receive(p))
                        {
                            //It's OK if there is no reply. Read again
                            continue;
                        }
                        rd.Position = 0;
                        rd.Set(p.Reply);
                        if (cl.GetData(rd, reply))
                        {
                            List <GXDLMSPlcMeterInfo> list = cl.Plc.ParseDiscover(reply.Data, (UInt16)reply.TargetAddress, (UInt16)reply.SourceAddress);
                            BeginInvoke(new AppendMeterEventHandler(OnAppendMeter), list);
                        }
                    }
                }
                catch (Exception)
                {
                    //Throw original exception.
                    throw;
                }
            }
        }
Esempio n. 5
0
        public static async Task Receive(ReceiveParameters param)
        {
            if (param.deviceName == null)
            {
                param.deviceName = Environment.MachineName;
            }
            try
            {
                using (var socket = new Socket(AddressFamily.InterNetwork,
                                               SocketType.Stream,
                                               ProtocolType.Tcp))
                {
                    using (var sd = new ServiceDiscovery())
                    {
                        var endPoint = new IPEndPoint(IPAddress.Any, 0);
                        socket.Bind(endPoint);
                        var port           = ((IPEndPoint)socket.LocalEndPoint).Port;
                        var serviceProfile = new ServiceProfile(param.deviceName, ADropDomainName, (ushort)port);
                        sd.Advertise(serviceProfile);
                        socket.Listen(1);
                        var incoming = socket.Accept();
                        Console.WriteLine($"{incoming.RemoteEndPoint} connect, receiving metadata.");
                        using (var receiver = new Receiver(incoming))
                        {
                            var meta = receiver.ReadMetadata();
                            Console.WriteLine($"MetaInfo: {meta.FileInfos.Count()} files with type:\n{meta.FileInfos}");

                            receiver.SendAction(Proto.Action.Types.ActionType.Accepted);

                            for (int i = 0; i < meta.FileInfos.Count(); i++)
                            {
                                var mimeType = meta.FileInfos[i].FileType;
                                var result   = await receiver.ReadFile();

                                if (mimeType == "text/plain")
                                {
                                    Console.WriteLine($"received text: \n{Encoding.UTF8.GetString(result)}");
                                }
                                else
                                {
                                    var extension = MimeTypes.MimeTypeMap.GetExtension(mimeType) ?? ".dat";
                                    File.WriteAllBytes($"{i}{extension}", result);
                                }
                            }
                        }
                    }
                    return;
                }
            }
            catch (SocketException e)
            {
                Console.WriteLine(e);
            }

            return;
        }
Esempio n. 6
0
        /// <summary>
        /// Read table data from the meter.
        /// </summary>
        /// <remarks>
        /// With commmand R6 data can be read one row at the time and it is parsed on the fly.
        /// With other commands all data must first read before data can be parse.
        /// </remarks>
        /// <param name="media"></param>
        /// <param name="wt"></param>
        /// <param name="name"></param>
        /// <param name="start"></param>
        /// <param name="end"></param>
        /// <param name="level"></param>
        /// <returns></returns>
        public static object[][] ReadTable(Gurux.Common.IGXMedia media, int wt, string name, DateTime start, DateTime end, string parameters, int level, int count, out string[] columns)
        {
            columns = null;
            List <byte> reply = new List <byte>();
            string      header, frame;
            //Read CRC.
            ReceiveParameters <byte[]> crc = new ReceiveParameters <byte[]>()
            {
                Count    = 1,
                WaitTime = wt
            };
            List <byte> data = new List <byte>();

            data.Add(1);
            data.AddRange(GenerateReadTable(name, start, end, parameters, level, count));
            data.Add(3);
            data.Add(CalculateChecksum(data, 1, data.Count - 1));
            lock (media.Synchronous)
            {
                do
                {
                    List <byte> tmp = new List <byte>(SendData(media, data == null ? null : data.ToArray(), '\0', wt, true, level == 6, false));
                    data = null;
                    if (level != 6 && tmp[tmp.Count - 1] == 0x3)
                    {
                        crc.Count = 1;
                        if (!media.Receive(crc))
                        {
                            throw new Exception("Failed to receive reply from the device in given time.");
                        }
                        tmp.AddRange(crc.Reply);
                    }
                    else if (level == 6)
                    {
                        if (GetPacket(tmp, true, out header, out frame) == null)
                        {
                            throw new Exception("Failed to receive reply from the device in given time.");
                        }
                        if (tmp[tmp.Count - 2] == 0x4)
                        {
                            //Send ACK if more data is left.
                            data = new List <byte>();
                            data.Add(6);
                            System.Threading.Thread.Sleep(200);
                        }
                    }
                    reply.AddRange(tmp);
                }while (reply[reply.Count - 2] != 0x3);
            }
            int      status = 0;
            DateTime tm     = DateTime.MinValue;
            int      add    = 0;

            return(ParseTableData(reply.ToArray(), ref columns, ref status, ref tm, ref add, name));
        }
        /// <summary>
        /// Send IEC disconnect message.
        /// </summary>
        void DiscIEC()
        {
            ReceiveParameters <string> p = new ReceiveParameters <string>()
            {
                AllData  = false,
                Eop      = (byte)0x0A,
                WaitTime = parent.WaitTime * 1000
            };
            string data = (char)0x01 + "B0" + (char)0x03 + "\r\n";

            media.Send(data, null);
            p.Count = 1;
            media.Receive(p);
        }
Esempio n. 8
0
        /// <summary>
        /// Send IEC disconnect message.
        /// </summary>
        private static void DiscIEC(Media media)
        {
            ReceiveParameters <string> p = new ReceiveParameters <string>()
            {
                AllData  = false,
                Eop      = (byte)0x0A,
                WaitTime = media.WaitTime * 1000
            };
            string data = (char)0x01 + "B0" + (char)0x03 + "\r\n";

            media.Target.Send(data, null);
            p.Count = 1;
            media.Target.Receive(p);
        }
Esempio n. 9
0
 /// <summary>
 /// Disconnect.
 /// </summary>
 /// <param name="serial"></param>
 /// <param name="tryCount"></param>
 public static void Disconnect(IGXMedia media, int tryCount)
 {
     lock (media.Synchronous)
     {
         ReceiveParameters <byte[]> p = new ReceiveParameters <byte[]>()
         {
             Eop      = GetEops(),
             WaitTime = 1000
         };
         List <byte> data = new List <byte>();
         data.Add(0x01);
         data.Add((byte)'B');
         data.Add((byte)'0');
         data.Add(0x03);
         data.Add(CalculateChecksum(data, 1, data.Count - 1));
         byte[] data1 = data.ToArray();
         string header, frame;
         media.Send(data1, null);
         media.Receive(p);
         while (--tryCount > -1)
         {
             if (media.Receive(p))
             {
                 GetPacket(new List <byte>(p.Reply), false, out header, out frame);
                 if (header == "B0")
                 {
                     break;
                 }
                 if (p.Reply.Length > 11)
                 {
                     p.Reply = null;
                 }
             }
             media.Send(data1, null);
         }
     }
 }
        private ReceiveMessageResponse ReceiveTestMessage()
        {
            var input = new ReceiveParameters
            {
                QueueUrl            = queueURL,
                MaxNumberOfMessages = 1
            };

            var options = new ReceiveOptions
            {
                DeleteMessageAfterReceiving = true,
                VisibilityTimeout           = 30,
                WaitTimeSeconds             = 5
            };

            var awsOptions = new AWSOptions
            {
                AWSCredentials        = SQS.GetBasicAWSCredentials(credParams),
                UseDefaultCredentials = false,
                Region = region
            };

            return(SQS.ReceiveMessage(input, options, awsOptions, new System.Threading.CancellationToken()).Result);
        }
        public bool Receive <T>(ReceiveParameters <T> args)
        {
            if (args.Eop == null && args.Count == 0 && !args.AllData)
            {
                throw new ArgumentException("Either Count or Eop must be set.");
            }
            int nSize = 0;

            byte[] terminator = null;
            if (args.Eop != null)
            {
                if (args.Eop is Array)
                {
                    Array arr = args.Eop as Array;
                    terminator = GXCommon.GetAsByteArray(arr.GetValue(0));
                }
                else
                {
                    terminator = GXCommon.GetAsByteArray(args.Eop);
                }
                nSize = terminator.Length;
            }

            int nMinSize = (int)Math.Max(args.Count, nSize);

            if (nMinSize == 0)
            {
                nMinSize = 1;
            }
            int waitTime = args.WaitTime;

            if (waitTime <= 0)
            {
                waitTime = -1;
            }

            //Wait until reply occurred.
            int      nFound       = -1;
            int      LastBuffSize = 0;
            DateTime StartTime    = DateTime.Now;
            bool     retValue     = true;

            do
            {
                if (waitTime == 0)
                {
                    //If we do not want to read all data.
                    if (!args.AllData)
                    {
                        return(false);
                    }
                    retValue = false;
                    break;
                }
                if (waitTime != -1)
                {
                    waitTime -= (int)(DateTime.Now - StartTime).TotalMilliseconds;
                    StartTime = DateTime.Now;
                    if (waitTime < 0)
                    {
                        waitTime = 0;
                    }
                }
                bool received;
                lock (receivedSync)
                {
                    received = !(LastBuffSize == receivedSize || receivedSize < nMinSize);
                }
                //Do not wait if there is data on the buffer...
                if (!received)
                {
                    if (waitTime == -1)
                    {
                        received = receivedEvent.WaitOne();
                    }
                    else
                    {
                        received = receivedEvent.WaitOne(waitTime);
                    }
                    if (!received && args.Eop == null)
                    {
                        lock (receivedSync)
                        {
                            received = !(LastBuffSize == receivedSize || receivedSize < nMinSize);
                        }
                    }
                }
                if (this.Exception != null)
                {
                    Exception ex = this.Exception;
                    this.Exception = null;
                    throw ex;
                }
                //If timeout occurred.
                if (!received)
                {
                    //If we do not want to read all data.
                    if (!args.AllData)
                    {
                        return(false);
                    }
                    retValue = false;
                    break;
                }
                lock (receivedSync)
                {
                    LastBuffSize = receivedSize;
                    //Read more data, if not enough
                    if (receivedSize < nMinSize)
                    {
                        continue;
                    }
                    //If only byte count matters.
                    if (nSize == 0)
                    {
                        nFound = args.Count;
                    }
                    else
                    {
                        int index = lastPosition != 0 && lastPosition < receivedSize ? lastPosition : args.Count;
                        //If terminator found.
                        if (args.Eop is Array)
                        {
                            foreach (object it in args.Eop as Array)
                            {
                                byte[] term = GXCommon.GetAsByteArray(it);
                                if (term.Length != 1 && receivedSize - index < term.Length)
                                {
                                    index = receivedSize - term.Length;
                                }
                                nFound = GXCommon.IndexOf(m_Received, term, index, receivedSize);
                                if (nFound != -1)
                                {
                                    break;
                                }
                            }
                        }
                        else
                        {
                            if (terminator.Length != 1 && receivedSize - index < terminator.Length)
                            {
                                index = receivedSize - terminator.Length;
                            }
                            nFound = GXCommon.IndexOf(m_Received, terminator, index, receivedSize);
                        }
                        lastPosition = receivedSize;
                        if (nFound != -1)
                        {
                            nFound += terminator.Length;
                        }
                    }
                }
            }while (nFound == -1);
            if (nSize == 0) //If terminator is not given read only bytes that are needed.
            {
                nFound = args.Count;
            }
            if (args.AllData) //If all data is copied.
            {
                nFound = receivedSize;
            }
            if (nFound == 0)
            {
                retValue = false;
            }
            //Convert bytes to object.
            byte[] tmp = new byte[nFound];
            lock (receivedSync)
            {
                Array.Copy(m_Received, tmp, nFound);
            }
            int    readBytes = 0;
            object data      = GXCommon.ByteArrayToObject(tmp, typeof(T), out readBytes);

            //Remove read data.
            receivedSize -= nFound;
            //Received size can go less than zero if we have received data and we try to read more.
            if (receivedSize < 0)
            {
                receivedSize = 0;
            }
            if (receivedSize != 0)
            {
                lock (receivedSync)
                {
                    Array.Copy(m_Received, nFound, m_Received, 0, receivedSize);
                }
            }
            else
            {
                lastPosition = 0;
            }
            //Reset count after read.
            args.Count = 0;
            //Append data.
            int oldReplySize = 0;

            if (args.Reply == null)
            {
                args.Reply = (T)data;
            }
            else
            {
                if (args.Reply is Array)
                {
                    Array oldArray = args.Reply as Array;
                    Array newArray = data as Array;
                    if (newArray == null)
                    {
                        throw new ArgumentException();
                    }
                    oldReplySize = oldArray.Length;
                    int   len = oldArray.Length + newArray.Length;
                    Array arr = (Array)Activator.CreateInstance(typeof(T), len);
                    //Copy old values.
                    Array.Copy(args.Reply as Array, arr, oldArray.Length);
                    //Copy new values.
                    Array.Copy(newArray, 0, arr, oldArray.Length, newArray.Length);
                    object tmp2 = arr;
                    args.Reply = (T)tmp2;
                }
                else if (args.Reply is string)
                {
                    string str = args.Reply as string;
                    str       += (string)data;
                    data       = str;
                    args.Reply = (T)data;
                }
            }
            return(retValue);
        }
 static byte[] SendData(IGXMedia media, byte[] data, char baudRate, int wt, bool useCrcSend, bool useCrcReply, bool readAllDataOnce)
 {
     ReceiveParameters<byte[]> p = new ReceiveParameters<byte[]>()
     {
         Eop = GetEops(),
         WaitTime = wt
     };
     lock (media.Synchronous)
     {
         if (data != null)
         {
             media.Send(data, null);
             if (baudRate != '\0' && media.MediaType == "Serial")
             {
                 Gurux.Serial.GXSerial serial = media as Gurux.Serial.GXSerial;
                 while (serial.BytesToWrite != 0)
                 {
                     System.Threading.Thread.Sleep(100);
                 }
                 System.Threading.Thread.Sleep(200);
                 switch (baudRate)
                 {
                     case '0':
                         serial.BaudRate = 300;
                         break;
                     case '1':
                     case 'A':
                         serial.BaudRate = 600;
                         break;
                     case '2':
                     case 'B':
                         serial.BaudRate = 1200;
                         break;
                     case '3':
                     case 'C':
                         serial.BaudRate = 2400;
                         break;
                     case '4':
                     case 'D':
                         serial.BaudRate = 4800;
                         break;
                     case '5':
                     case 'E':
                         serial.BaudRate = 9600;
                         break;
                     case '6':
                     case 'F':
                         serial.BaudRate = 19200;
                         break;
                     default:
                         throw new Exception("Unknown baud rate.");
                 }
             }
         }
         if (!media.Receive(p))
         {
             throw new Exception("Failed to receive reply from the device in given time.");
         }
         List<byte> reply2 = new List<byte>();
         reply2.AddRange(p.Reply);
         p.Reply = null;
         string header, frame;
         byte[] packet = null;
         if (useCrcSend && data != null)
         {                    
             while ((packet = GetPacket(reply2, false, out header, out frame)) == null)
             {
                 p.Eop = null;
                 p.Count = 1;
                 if (!media.Receive(p))
                 {
                     throw new Exception("Failed to receive reply from the device in given time.");
                 }
                 reply2.AddRange(p.Reply);
                 p.Reply = null;
             }
             p.Eop = GetEops();
         }
         else
         {
             for (int pos = 0; pos != reply2.Count; ++pos)
             {
                 if (reply2[pos] == 0xA)
                 {
                     ++pos;
                     packet = new byte[pos];
                     reply2.CopyTo(0, packet, 0, pos);
                     break;
                 }
             }
         }
         //Remove echo.
         if (data != null && EqualBytes(data, packet))
         {
             reply2.RemoveRange(0, data.Length);
             if (useCrcReply && reply2.Count != 0)// && !(data != null && data[data.Length - 1] == 0xA))
             {
                 while (GetPacket(reply2, false, out header, out frame) == null)
                 {
                     p.Eop = null;
                     p.Count = 1;
                     if (!media.Receive(p))
                     {
                         throw new Exception("Failed to receive reply from the device in given time.");
                     }
                     reply2.AddRange(p.Reply);
                     p.Reply = null;
                 }
             }
             else
             {
                 if (GetPacket(reply2, false, out header, out frame) == null)
                 {
                     reply2.AddRange(SendData(media, null, baudRate, wt, useCrcSend, useCrcReply, readAllDataOnce));
                 }
             }
             //If there is more data available.
             if (readAllDataOnce && reply2[reply2.Count - 2] == 0x4)
             {                        
                 reply2.AddRange(SendData(media, new byte[] { 6 }, '\0', wt, useCrcSend, useCrcReply, readAllDataOnce));
             }
             return reply2.ToArray();
         }
         if (useCrcReply && !(data != null && data[data.Length - 1] == 0xA))
         {
             while (GetPacket(reply2, false, out header, out frame) == null)
             {
                 p.Eop = null;
                 p.Count = 1;
                 if (!media.Receive(p))
                 {
                     throw new Exception("Failed to receive reply from the device in given time.");
                 }
                 reply2.AddRange(p.Reply);
                 p.Reply = null;
             }
         }
         return reply2.ToArray();
     }
 }
        void InitializeIEC()
        {
            GXManufacturer manufacturer = this.Parent.Manufacturers.FindByIdentification(Parent.Manufacturer);

            if (manufacturer == null)
            {
                throw new Exception("Unknown manufacturer " + Parent.Manufacturer);
            }
            GXSerial serial     = Media as GXSerial;
            byte     Terminator = (byte)0x0A;

            if (serial != null && Parent.StartProtocol == StartProtocolType.IEC)
            {
                serial.BaudRate = 300;
                serial.DataBits = 7;
                serial.Parity   = Parity.Even;
                serial.StopBits = StopBits.One;
            }
            Media.Open();
            //Query device information.
            if (Media != null && Parent.StartProtocol == StartProtocolType.IEC)
            {
                string data = "/?!\r\n";
                if (this.Parent.HDLCAddressing == HDLCAddressType.SerialNumber)
                {
                    data = "/?" + this.Parent.PhysicalAddress + "!\r\n";
                }
                GXLogWriter.WriteLog("HDLC sending:" + data);
                ReceiveParameters <string> p = new ReceiveParameters <string>()
                {
                    AllData  = false,
                    Eop      = Terminator,
                    WaitTime = Parent.WaitTime * 1000
                };
                lock (Media.Synchronous)
                {
                    Media.Send(data, null);
                    if (!Media.Receive(p))
                    {
                        //Try to move away from mode E.
                        try
                        {
                            this.ReadDLMSPacket(this.DisconnectRequest(), 1);
                        }
                        catch (Exception ex)
                        {
                        }
                        data = (char)0x01 + "B0" + (char)0x03 + "\r\n";
                        Media.Send(data, null);
                        p.Count = 1;
                        Media.Receive(p);
                        data = "Failed to receive reply from the device in given time.";
                        GXLogWriter.WriteLog(data);
                        throw new Exception(data);
                    }
                    //If echo is used.
                    if (p.Reply == data)
                    {
                        p.Reply = null;
                        if (!Media.Receive(p))
                        {
                            //Try to move away from mode E.
                            this.ReadDLMSPacket(this.DisconnectRequest(), 1);
                            if (serial != null)
                            {
                                data = (char)0x01 + "B0" + (char)0x03 + "\r\n";
                                Media.Send(data, null);
                                p.Count = 1;
                                if (!Media.Receive(p))
                                {
                                }
                                serial.DtrEnable = serial.RtsEnable = false;
                                serial.BaudRate  = 9600;
                                serial.DtrEnable = serial.RtsEnable = true;
                                data             = (char)0x01 + "B0" + (char)0x03 + "\r\n";
                                Media.Send(data, null);
                                p.Count = 1;
                                Media.Receive(p);
                            }

                            data = "Failed to receive reply from the device in given time.";
                            GXLogWriter.WriteLog(data);
                            throw new Exception(data);
                        }
                    }
                }
                GXLogWriter.WriteLog("HDLC received: " + p.Reply);
                if (p.Reply[0] != '/')
                {
                    p.WaitTime = 100;
                    Media.Receive(p);
                    throw new Exception("Invalid responce.");
                }
                string manufactureID = p.Reply.Substring(1, 3);
                UpdateManufactureSettings(manufactureID);
                char baudrate = p.Reply[4];
                int  BaudRate = 0;
                switch (baudrate)
                {
                case '0':
                    BaudRate = 300;
                    break;

                case '1':
                    BaudRate = 600;
                    break;

                case '2':
                    BaudRate = 1200;
                    break;

                case '3':
                    BaudRate = 2400;
                    break;

                case '4':
                    BaudRate = 4800;
                    break;

                case '5':
                    BaudRate = 9600;
                    break;

                case '6':
                    BaudRate = 19200;
                    break;

                default:
                    throw new Exception("Unknown baud rate.");
                }
                GXLogWriter.WriteLog("BaudRate is : " + BaudRate.ToString());
                //Send ACK
                //Send Protocol control character
                byte controlCharacter = (byte)'2';// "2" HDLC protocol procedure (Mode E)
                //Send Baud rate character
                //Mode control character
                byte ModeControlCharacter = (byte)'2';//"2" //(HDLC protocol procedure) (Binary mode)
                //Set mode E.
                byte[] arr = new byte[] { 0x06, controlCharacter, (byte)baudrate, ModeControlCharacter, 13, 10 };
                GXLogWriter.WriteLog("Moving to mode E.", arr);
                lock (Media.Synchronous)
                {
                    Media.Send(arr, null);
                    System.Threading.Thread.Sleep(500);
                    serial.BaudRate = BaudRate;
                    p.Reply         = null;
                    p.WaitTime      = 100;
                    //Note! All meters do not echo this.
                    Media.Receive(p);
                    if (p.Reply != null)
                    {
                        GXLogWriter.WriteLog("Received: " + p.Reply);
                    }
                    serial.Close();
                    serial.DataBits = 8;
                    serial.Parity   = Parity.None;
                    serial.StopBits = StopBits.One;
                    serial.Open();
                    System.Threading.Thread.Sleep(500);
                }
            }
        }
Esempio n. 14
0
        /// <summary>
        /// Read DLMS Data from the device.
        /// </summary>
        /// <param name="data">Data to send.</param>
        /// <returns>Received data.</returns>
        public void ReadDLMSPacket(byte[] data, GXReplyData reply)
        {
            if (data == null && !reply.IsStreaming())
            {
                return;
            }
            reply.Error = 0;
            object eop = (byte)0x7E;

            //In network connection terminator is not used.
            if (Client.InterfaceType == InterfaceType.WRAPPER && Media is GXNet)
            {
                eop = null;
            }
            int  pos       = 0;
            bool succeeded = false;
            ReceiveParameters <byte[]> p = new ReceiveParameters <byte[]>()
            {
                Eop      = eop,
                Count    = 5,
                WaitTime = WaitTime,
            };
            GXReplyData notify = new GXReplyData();

            lock (Media.Synchronous)
            {
                while (!succeeded && pos != 3)
                {
                    if (!reply.IsStreaming())
                    {
                        WriteTrace(true, "TX:\t" + DateTime.Now.ToString("hh:mm:ss") + "\t" + GXCommon.ToHex(data, true));
                        Media.Send(data, null);
                    }
                    succeeded = Media.Receive(p);
                    if (!succeeded)
                    {
                        if (++pos >= RetryCount)
                        {
                            throw new Exception("Failed to receive reply from the device in given time.");
                        }
                        //If Eop is not set read one byte at time.
                        if (p.Eop == null)
                        {
                            p.Count = 1;
                        }
                        //Try to read again...
                        System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                    }
                }
                try
                {
                    pos = 0;
                    //Loop until whole COSEM packet is received.
                    while (!Client.GetData(p.Reply, reply, notify))
                    {
                        // If all data is received.
                        if (notify.IsComplete && !notify.IsMoreData)
                        {
                            /*
                             * try
                             * {
                             *  if (GXNotifyListener.Parser != null)
                             *  {
                             *      GXAMIClient cl = new GXAMIClient();
                             *      GXNotifyListener.Parser.Parse(Media.ToString(), notify.Value, cl.GetData, cl.SetData);
                             *  }
                             * }
                             * catch (Exception ex)
                             * {
                             *  //TODO: Save error to the database.
                             * }
                             */
                            notify.Clear();
                        }

                        //If Eop is not set read one byte at time.
                        if (p.Eop == null)
                        {
                            p.Count = 1;
                        }
                        while (!Media.Receive(p))
                        {
                            if (++pos >= RetryCount)
                            {
                                throw new Exception("Failed to receive reply from the device in given time.");
                            }
                            //If echo.
                            if (p.Reply == null || p.Reply.Length == data.Length)
                            {
                                Media.Send(data, null);
                            }
                            //Try to read again...
                            System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                        }
                    }
                }
                catch (Exception ex)
                {
                    WriteTrace(false, "RX:\t" + DateTime.Now.ToString("hh:mm:ss") + "\t" + GXCommon.ToHex(p.Reply, true));
                    throw ex;
                }
            }
            WriteTrace(false, "RX:\t" + DateTime.Now.ToString("hh:mm:ss") + "\t" + GXCommon.ToHex(p.Reply, true));
            if (reply.Error != 0)
            {
                if (reply.Error == (short)ErrorCode.Rejected)
                {
                    Thread.Sleep(1000);
                    ReadDLMSPacket(data, reply);
                }
                else
                {
                    throw new GXDLMSException(reply.Error);
                }
            }
        }
 /// <summary>
 /// Read DLMS Data from the device.
 /// </summary>
 /// <param name="data">Data to send.</param>
 /// <returns>Received data.</returns>
 public byte[] ReadDLMSPacket(byte[] data)
 {
     if (data == null)
     {
         return null;
     }
     object eop = (byte)0x7E;
     //In network connection terminator is not used.
     if (Client.InterfaceType == InterfaceType.Net && Media is GXNet)
     {
         eop = null;
     }
     int pos = 0;
     bool succeeded = false;
     ReceiveParameters<byte[]> p = new ReceiveParameters<byte[]>()
     {
         AllData = true,
         Eop = eop,
         Count = 5,
         WaitTime = WaitTime,
     };
     lock (Media.Synchronous)
     {
         while (!succeeded && pos != 3)
         {
             WriteTrace("<- " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(data, true));
             Media.Send(data, null);
             succeeded = Media.Receive(p);
             if (!succeeded)
             {
                 //If Eop is not set read one byte at time.
                 if (p.Eop == null)
                 {
                     p.Count = 1;
                 }
                 //Try to read again...
                 if (++pos != 3)
                 {
                     System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                     continue;
                 }
                 throw new Exception("Failed to receive reply from the device in given time.");
             }
         }
         //Loop until whole Cosem packet is received.
         while (!Client.IsDLMSPacketComplete(p.Reply))
         {
             //If Eop is not set read one byte at time.
             if (p.Eop == null)
             {
                 p.Count = 1;
             }
             if (!Media.Receive(p))
             {
                 //Try to read again...
                 if (++pos != 3)
                 {
                     System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                     continue;
                 }
                 throw new Exception("Failed to receive reply from the device in given time.");
             }
         }
     }
     WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(p.Reply, true));
     object errors = Client.CheckReplyErrors(data, p.Reply);
     if (errors != null)
     {
         object[,] arr = (object[,])errors;
         int error = (int)arr[0, 0];
         throw new GXDLMSException(error);
     }
     return p.Reply;
 }
Esempio n. 16
0
        /// <summary>
        /// Initialize optical head.
        /// </summary>
        void InitializeOpticalHead()
        {
            if (Client.InterfaceType != InterfaceType.HdlcWithModeE)
            {
                return;
            }
            GXSerial serial     = Media as GXSerial;
            byte     Terminator = (byte)0x0A;

            Media.Open();
            //Some meters need a little break.
            Thread.Sleep(1000);
            //Query device information.
            string data = "/?!\r\n";

            if (Trace > TraceLevel.Info)
            {
                Console.WriteLine("IEC Sending:" + data);
            }
            ReceiveParameters <string> p = new ReceiveParameters <string>()
            {
                AllData  = false,
                Eop      = Terminator,
                WaitTime = WaitTime * 1000
            };

            lock (Media.Synchronous)
            {
                Media.Send(data, null);
                if (!Media.Receive(p))
                {
                    //Try to move away from mode E.
                    try
                    {
                        Disconnect();
                    }
                    catch (Exception)
                    {
                    }
                    DiscIEC();
                    string str = "Failed to receive reply from the device in given time.";
                    if (Trace > TraceLevel.Info)
                    {
                        Console.WriteLine(str);
                    }
                    Media.Send(data, null);
                    if (!Media.Receive(p))
                    {
                        throw new Exception(str);
                    }
                }
                //If echo is used.
                if (p.Reply == data)
                {
                    p.Reply = null;
                    if (!Media.Receive(p))
                    {
                        //Try to move away from mode E.
                        GXReplyData reply = new GXReplyData();
                        Disconnect();
                        if (serial != null)
                        {
                            DiscIEC();
                            serial.DtrEnable = serial.RtsEnable = false;
                            serial.BaudRate  = 9600;
                            serial.DtrEnable = serial.RtsEnable = true;
                            DiscIEC();
                        }
                        data = "Failed to receive reply from the device in given time.";
                        if (Trace > TraceLevel.Info)
                        {
                            Console.WriteLine(data);
                        }
                        throw new Exception(data);
                    }
                }
            }
            if (Trace > TraceLevel.Info)
            {
                Console.WriteLine("HDLC received: " + p.Reply);
            }
            if (p.Reply[0] != '/')
            {
                p.WaitTime = 100;
                Media.Receive(p);
                DiscIEC();
                throw new Exception("Invalid responce.");
            }
            string manufactureID = p.Reply.Substring(1, 3);
            char   baudrate      = p.Reply[4];
            int    BaudRate      = 0;

            switch (baudrate)
            {
            case '0':
                BaudRate = 300;
                break;

            case '1':
                BaudRate = 600;
                break;

            case '2':
                BaudRate = 1200;
                break;

            case '3':
                BaudRate = 2400;
                break;

            case '4':
                BaudRate = 4800;
                break;

            case '5':
                BaudRate = 9600;
                break;

            case '6':
                BaudRate = 19200;
                break;

            default:
                throw new Exception("Unknown baud rate.");
            }
            if (Trace > TraceLevel.Info)
            {
                Console.WriteLine("BaudRate is : " + BaudRate.ToString());
            }
            //Send ACK
            //Send Protocol control character
            // "2" HDLC protocol procedure (Mode E)
            byte controlCharacter = (byte)'2';
            //Send Baud rate character
            //Mode control character
            byte ModeControlCharacter = (byte)'2';

            //"2" //(HDLC protocol procedure) (Binary mode)
            //Set mode E.
            byte[] arr = new byte[] { 0x06, controlCharacter, (byte)baudrate, ModeControlCharacter, 13, 10 };
            if (Trace > TraceLevel.Info)
            {
                Console.WriteLine("Moving to mode E.", arr);
            }
            lock (Media.Synchronous)
            {
                p.Reply = null;
                Media.Send(arr, null);
                //Some meters need this sleep. Do not remove.
                Thread.Sleep(200);
                p.WaitTime = 2000;
                //Note! All meters do not echo this.
                Media.Receive(p);
                if (p.Reply != null)
                {
                    if (Trace > TraceLevel.Info)
                    {
                        Console.WriteLine("Received: " + p.Reply);
                    }
                }
                serial.BaudRate = BaudRate;
                serial.DataBits = 8;
                serial.Parity   = Parity.None;
                serial.StopBits = StopBits.One;
                //Some meters need this sleep. Do not remove.
                Thread.Sleep(800);
            }
        }
Esempio n. 17
0
 void InitSerial()
 {
     GXSerial serial = Media as GXSerial;
     byte Terminator = (byte)0x0A;
     if (serial != null && InitializeIEC)
     {
         serial.BaudRate = 300;
         serial.DataBits = 7;
         serial.Parity = Parity.Even;
         serial.StopBits = StopBits.One;
     }
     Media.Open();
     //Query device information.
     if (Media != null && InitializeIEC)
     {
         string data = "/?001!\r\n";
         if (Trace)
         {
             Console.WriteLine("HDLC sending:" + data);
         }
         ReceiveParameters<string> p = new ReceiveParameters<string>()
         {
             Eop = Terminator,
             WaitTime = WaitTime
         };
         lock (Media.Synchronous)
         {
             Media.Send(data, null);
             if (!Media.Receive(p))
             {
                 //Try to move away from mode E.
                 throw new Exception("Failed to receive reply from the device in given time.");
             }
             //If echo is used.
             if (p.Reply == data)
             {
                 p.Reply = null;
                 if (!Media.Receive(p))
                 {
                     //Try to move away from mode E.
                     throw new Exception("Failed to receive reply from the device in given time.");
                 }
             }
         }
         if (Trace)
         {
             Console.WriteLine("HDLC received: " + p.Reply);
         }
         if (p.Reply[0] != '/')
         {
             p.WaitTime = 100;
             Media.Receive(p);
             throw new Exception("Invalid responce.");
         }
         string manufactureID = p.Reply.Substring(1, 3);
         //UpdateManufactureSettings(manufactureID);
         char baudrate = p.Reply[4];
         int BaudRate = 0;
         switch (baudrate)
         {
             case '0':
                 BaudRate = 300;
                 break;
             case '1':
                 BaudRate = 600;
                 break;
             case '2':
                 BaudRate = 1200;
                 break;
             case '3':
                 BaudRate = 2400;
                 break;
             case '4':
                 BaudRate = 4800;
                 break;
             case '5':
                 BaudRate = 9600;
                 break;
             case '6':
                 BaudRate = 19200;
                 break;
             default:
                 throw new Exception("Unknown baud rate.");
         }
         Console.WriteLine("BaudRate is :", BaudRate.ToString());
         //Send ACK
         //Send Protocol control character
         byte controlCharacter = (byte)'2';// "2" HDLC protocol procedure (Mode E)
         //Send Baudrate character
         //Mode control character
         byte ModeControlCharacter = (byte)'2';//"2" //(HDLC protocol procedure) (Binary mode)
         //Set mode E.
         byte[] arr = new byte[] { 0x06, controlCharacter, (byte)baudrate, ModeControlCharacter, 13, 10 };
         if (Trace)
         {
             Console.WriteLine("Moving to mode E", BitConverter.ToString(arr));
         }
         lock (Media.Synchronous)
         {
             Media.Send(arr, null);
             p.Reply = null;
             p.WaitTime = 500;
             if (!Media.Receive(p))
             {
                 //Try to move away from mode E.
                 this.ReadDLMSPacket(m_Parser.DisconnectRequest());
                 throw new Exception("Failed to receive reply from the device in given time.");
             }
         }
         if (serial != null)
         {
             serial.BaudRate = BaudRate;
             serial.DataBits = 8;
             serial.Parity = Parity.None;
             serial.StopBits = StopBits.One;
         }
     }
 }
Esempio n. 18
0
        /// <summary>
        /// Read DLMS Data from the device.
        /// </summary>
        /// <param name="data">Data to send.</param>
        /// <returns>Received data.</returns>
        public byte[] ReadDLMSPacket(byte[] data)
        {
            if (data == null)
            {
                return(null);
            }
            object eop = (byte)0x7E;

            //In network connection terminator is not used.
            if (Client.InterfaceType == InterfaceType.Net && Media is GXNet)
            {
                eop = null;
            }
            int  pos       = 0;
            bool succeeded = false;
            ReceiveParameters <byte[]> p = new ReceiveParameters <byte[]>()
            {
                AllData  = true,
                Eop      = eop,
                Count    = 5,
                WaitTime = WaitTime,
            };

            lock (Media.Synchronous)
            {
                while (!succeeded && pos != 3)
                {
                    WriteTrace("<- " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(data, true));
                    Media.Send(data, null);
                    succeeded = Media.Receive(p);
                    if (!succeeded)
                    {
                        //If Eop is not set read one byte at time.
                        if (p.Eop == null)
                        {
                            p.Count = 1;
                        }
                        //Try to read again...
                        if (++pos != 3)
                        {
                            System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                            continue;
                        }
                        throw new Exception("Failed to receive reply from the device in given time.");
                    }
                }
                //Loop until whole Cosem packet is received.
                while (!Client.IsDLMSPacketComplete(p.Reply))
                {
                    //If Eop is not set read one byte at time.
                    if (p.Eop == null)
                    {
                        p.Count = 1;
                    }
                    if (!Media.Receive(p))
                    {
                        //Try to read again...
                        if (++pos != 3)
                        {
                            System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                            continue;
                        }
                        throw new Exception("Failed to receive reply from the device in given time.");
                    }
                }
            }
            WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(p.Reply, true));
            object errors = Client.CheckReplyErrors(data, p.Reply);

            if (errors != null)
            {
                object[,] arr = (object[, ])errors;
                int error = (int)arr[0, 0];
                throw new GXDLMSException(error);
            }
            return(p.Reply);
        }
Esempio n. 19
0
        public override void ImportFromDevice(Control[] addinPages, GXDevice device, IGXMedia media)
        {
            media.Open();
            GXMBusDevice dev = device as GXMBusDevice;
            object data;
            //Handshake
            ShortFrame sf = new ShortFrame();
            sf.AddressField = dev.DeviceAddress;
            sf.ControlField = (byte)CFieldFunctions.SendSlaveInit;
            sf.CountChecksum();
            data = sf.ToByteArray();
            ReceiveParameters<byte[]> recParams = new ReceiveParameters<byte[]>()
            {                
                Count = 1,
                Peek = false,
                WaitTime = device.WaitTime
            };

            lock (media.Synchronous)
            {
                media.Send(data, null);
                if (!media.Receive(recParams))
                {
                    throw new Exception("Failed to receive reply from the device in given time.");
                }
                if (recParams.Reply.Length < 1 || recParams.Reply[0] != 0xE5)
                {
                    throw new Exception("Handshake failed.");
                }

                bool morePacketsAvailable = false;
                byte fcb = 1;

                List<MBusRegister> items = new List<MBusRegister>();
                do
                {
                    sf = new ShortFrame();
                    sf.AddressField = dev.DeviceAddress;
                    if (fcb == 1)
                    {
                        sf.ControlField = (byte)CFieldFunctions.RequestClass2Data;
                    }
                    else
                    {
                        sf.ControlField = (byte)CFieldFunctions.RequestClass2Data | (byte)CFieldRequest.FrameCountBit;
                    }
                    sf.CountChecksum();

                    recParams.AllData = true;
                    recParams.Count = 1;
                    recParams.Eop = (byte)0x16;
                    recParams.Reply = null;    
                    int cnt = 0;
                    //Some meters can't answer right a way.
                    do
                    {
                        media.Send(sf.ToByteArray(), null);
                        if (++cnt == 6)
                        {
                            throw new Exception("Failed to receive reply from the device in given time.");
                        }                        
                    }
                    while (!media.Receive(recParams));
                    while (!VerifyReadReplyCheckSum(recParams.Reply))
                    {
                        recParams.Count = 0;
                        recParams.Reply = null;
                        bool gotData = media.Receive(recParams);
                        if (!gotData)
                        {
                            break;
                        }
                    }
                    morePacketsAvailable = recParams.Reply.Length > 5 && (recParams.Reply[4] & 0x10) != 0;
                    items.AddRange(ParseReadReply(recParams.Reply));
                }
                while (morePacketsAvailable);

                GXMBusCategory defaultCategory = null;
                if ((defaultCategory = (GXMBusCategory)device.Categories.Find("Default")) == null)
                {
                    defaultCategory = new GXMBusCategory();
                    defaultCategory.Name = "Default";
                    device.Categories.Add(defaultCategory);
                }
                for (int pos = 0; pos < items.Count; ++pos)
                {
                    MBusRegister item = items[pos];
                    GXMBusProperty prop = new GXMBusProperty();                    
                    prop.Ordinal = pos;
                    if (item.IsVariableData)
                    {
                        string name = item.MBusType;
                        int len = name.IndexOf('_');
                        if (len != -1)
                        {
                            name = name.Substring(0, len);
                        }
                        name += " " + item.Function.ToString();
                        if (item.Tariff != 0)
                        {
                            name += " Tariff " + item.Tariff.ToString();
                        }
                        prop.Name = name;
                        prop.Unit = item.Unit;
                        prop.DataLength = item.DataLength;
                        item.Mask.Reverse();
                        prop.InfoMask = item.Mask.ToArray();
                        prop.Type = item.Type;                                                
                        if (item.MBusType.ToLower().Contains("date") || item.MBusType.ToLower().Contains("timepoint"))
                        {
                            prop.ValueType = typeof(DateTime);
                        }
                        else
                        {                            
                            prop.ValueType = typeof(string);
                        }                         
                    }
                    else
                    {
                        prop.Name = item.MBusType;
                        prop.Unit = item.Unit;
                        prop.ValueType = typeof(string);
                        prop.DataLength = 4;
                    }                    
                    prop.InfoBytes = item.InformationBytes.Reverse().ToArray();
                    defaultCategory.Properties.Add(prop);
                }
            }
        }
 /// <summary>
 /// Read table data from the meter.
 /// </summary>
 /// <remarks>
 /// With commmand R6 data can be read one row at the time and it is parsed on the fly.
 /// With other commands all data must first read before data can be parse.
 /// </remarks>
 /// <param name="media"></param>
 /// <param name="wt"></param>
 /// <param name="name"></param>
 /// <param name="start"></param>
 /// <param name="end"></param>
 /// <param name="level"></param>
 /// <returns></returns>
 public static object[][] ReadTable(Gurux.Common.IGXMedia media, int wt, string name, DateTime start, DateTime end, string parameters, int level, int count, out string[] columns)
 {
     columns = null;
     List<byte> reply = new List<byte>();
     string header, frame;
     //Read CRC.
     ReceiveParameters<byte[]> crc = new ReceiveParameters<byte[]>()
     {
         Count = 1,
         WaitTime = wt
     };
     List<byte> data = new List<byte>();
     data.Add(1);
     data.AddRange(GenerateReadTable(name, start, end, parameters, level, count));
     data.Add(3);
     data.Add(CalculateChecksum(data, 1, data.Count - 1));
     lock (media.Synchronous)
     {
         do
         {
             List<byte> tmp = new List<byte>(SendData(media, data == null ? null : data.ToArray(), '\0', wt, true, level == 6, false));
             data = null;
             if (level != 6 && tmp[tmp.Count - 1] == 0x3)
             {
                 crc.Count = 1;
                 if (!media.Receive(crc))
                 {
                     throw new Exception("Failed to receive reply from the device in given time.");
                 }
                 tmp.AddRange(crc.Reply);
             }
             else if (level == 6)
             {                        
                 if (GetPacket(tmp, true, out header, out frame) == null)
                 {
                     throw new Exception("Failed to receive reply from the device in given time.");
                 }
                 if (tmp[tmp.Count - 2] == 0x4)
                 {
                     //Send ACK if more data is left.
                     data = new List<byte>();
                     data.Add(6);
                     System.Threading.Thread.Sleep(200);
                 }
             }
             reply.AddRange(tmp);
         }
         while (reply[reply.Count - 2] != 0x3);
     }
     int status = 0;
     DateTime tm = DateTime.MinValue;
     int add = 0;
     return ParseTableData(reply.ToArray(), ref columns, ref status, ref tm, ref add, name);        
 }
Esempio n. 21
0
        static byte[] SendData(IGXMedia media, byte[] data, char baudRate, int wt, bool useCrcSend, bool useCrcReply, bool readAllDataOnce)
        {
            ReceiveParameters <byte[]> p = new ReceiveParameters <byte[]>()
            {
                Eop      = GetEops(),
                WaitTime = wt
            };

            lock (media.Synchronous)
            {
                if (data != null)
                {
                    media.Send(data, null);
                    if (baudRate != '\0' && media.MediaType == "Serial")
                    {
                        Gurux.Serial.GXSerial serial = media as Gurux.Serial.GXSerial;
                        while (serial.BytesToWrite != 0)
                        {
                            System.Threading.Thread.Sleep(100);
                        }
                        System.Threading.Thread.Sleep(200);
                        switch (baudRate)
                        {
                        case '0':
                            serial.BaudRate = 300;
                            break;

                        case '1':
                        case 'A':
                            serial.BaudRate = 600;
                            break;

                        case '2':
                        case 'B':
                            serial.BaudRate = 1200;
                            break;

                        case '3':
                        case 'C':
                            serial.BaudRate = 2400;
                            break;

                        case '4':
                        case 'D':
                            serial.BaudRate = 4800;
                            break;

                        case '5':
                        case 'E':
                            serial.BaudRate = 9600;
                            break;

                        case '6':
                        case 'F':
                            serial.BaudRate = 19200;
                            break;

                        default:
                            throw new Exception("Unknown baud rate.");
                        }
                    }
                }
                if (!media.Receive(p))
                {
                    throw new Exception("Failed to receive reply from the device in given time.");
                }
                List <byte> reply2 = new List <byte>();
                reply2.AddRange(p.Reply);
                p.Reply = null;
                string header, frame;
                byte[] packet = null;
                if (useCrcSend && data != null)
                {
                    while ((packet = GetPacket(reply2, false, out header, out frame)) == null)
                    {
                        p.Eop   = null;
                        p.Count = 1;
                        if (!media.Receive(p))
                        {
                            throw new Exception("Failed to receive reply from the device in given time.");
                        }
                        reply2.AddRange(p.Reply);
                        p.Reply = null;
                    }
                    p.Eop = GetEops();
                }
                else
                {
                    for (int pos = 0; pos != reply2.Count; ++pos)
                    {
                        if (reply2[pos] == 0xA)
                        {
                            ++pos;
                            packet = new byte[pos];
                            reply2.CopyTo(0, packet, 0, pos);
                            break;
                        }
                    }
                }
                //Remove echo.
                if (data != null && EqualBytes(data, packet))
                {
                    reply2.RemoveRange(0, data.Length);
                    if (useCrcReply && reply2.Count != 0)// && !(data != null && data[data.Length - 1] == 0xA))
                    {
                        while (GetPacket(reply2, false, out header, out frame) == null)
                        {
                            p.Eop   = null;
                            p.Count = 1;
                            if (!media.Receive(p))
                            {
                                throw new Exception("Failed to receive reply from the device in given time.");
                            }
                            reply2.AddRange(p.Reply);
                            p.Reply = null;
                        }
                    }
                    else
                    {
                        if (GetPacket(reply2, false, out header, out frame) == null)
                        {
                            reply2.AddRange(SendData(media, null, baudRate, wt, useCrcSend, useCrcReply, readAllDataOnce));
                        }
                    }
                    //If there is more data available.
                    if (readAllDataOnce && reply2[reply2.Count - 2] == 0x4)
                    {
                        reply2.AddRange(SendData(media, new byte[] { 6 }, '\0', wt, useCrcSend, useCrcReply, readAllDataOnce));
                    }
                    return(reply2.ToArray());
                }
                if (useCrcReply && !(data != null && data[data.Length - 1] == 0xA))
                {
                    while (GetPacket(reply2, false, out header, out frame) == null)
                    {
                        p.Eop   = null;
                        p.Count = 1;
                        if (!media.Receive(p))
                        {
                            throw new Exception("Failed to receive reply from the device in given time.");
                        }
                        reply2.AddRange(p.Reply);
                        p.Reply = null;
                    }
                }
                return(reply2.ToArray());
            }
        }
 public void InitializeConnection()
 {
     if (!string.IsNullOrEmpty(parent.Manufacturer))
     {
         UpdateManufactureSettings(parent.Manufacturer);
     }
     if (media is GXSerial)
     {
         GXLogWriter.WriteLog("Initializing serial connection.");
         InitSerial();
         connectionStartTime = DateTime.Now;
     }
     else if (media is GXNet)
     {
         GXLogWriter.WriteLog("Initializing Network connection.");
         InitNet();
         //Some Electricity meters need some time before first message can be send.
         System.Threading.Thread.Sleep(500);
     }
     else if (media is Gurux.Terminal.GXTerminal)
     {
         GXLogWriter.WriteLog("Initializing Terminal connection.");
         InitTerminal();
     }
     else
     {
         throw new Exception("Unknown media type.");
     }
     try
     {
         GXReplyData reply = new GXReplyData();
         byte[] data;
         data = SNRMRequest();
         if (data != null)
         {
             GXLogWriter.WriteLog("Send SNRM request.", data);
             ReadDLMSPacket(data, 1, reply);
             GXLogWriter.WriteLog("Parsing UA reply.\r\n" + reply.Data.ToString());
             //Has server accepted client.
             ParseUAResponse(reply.Data);
             GXLogWriter.WriteLog("Parsing UA reply succeeded.");
         }
         //Generate AARQ request.
         //Split requests to multiple packets if needed.
         //If password is used all data might not fit to one packet.
         foreach (byte[] it in AARQRequest())
         {
             GXLogWriter.WriteLog("Send AARQ request", it);
             reply.Clear();
             ReadDLMSPacket(it, reply);
         }
         GXLogWriter.WriteLog("Parsing AARE reply\r\n" + reply.Data.ToString());
         try
         {
             //Parse reply.
             ParseAAREResponse(reply.Data);
         }
         catch (Exception Ex)
         {
             reply.Clear();
             ReadDLMSPacket(DisconnectRequest(), 1, reply);
             throw Ex;
         }
         //If authentication is required.
         if (client.IsAuthenticationRequired)
         {
             foreach (byte[] it in client.GetApplicationAssociationRequest())
             {
                 GXLogWriter.WriteLog("Authenticating", it);
                 reply.Clear();
                 ReadDLMSPacket(it, reply);
             }
             client.ParseApplicationAssociationResponse(reply.Data);
         }
     }
     catch (Exception ex)
     {
         if (media is GXSerial && parent.StartProtocol == StartProtocolType.IEC)
         {
             ReceiveParameters<string> p = new ReceiveParameters<string>()
             {
                 Eop = (byte) 0xA,
                 WaitTime = parent.WaitTime * 1000
             };
             lock (media.Synchronous)
             {
                 string data = (char)0x01 + "B0" + (char)0x03 + "\r\n";
                 media.Send(data, null);
                 media.Receive(p);
             }
         }
         throw ex;
     }
     GXLogWriter.WriteLog("Parsing AARE reply succeeded.");
     parent.KeepAliveStart();
 }
        void InitRead(object sender, GXPacket GXPacket)
        {
            LastNotifiedTransactionProgress = 0;
            parser = new Gurux.DLMS.GXDLMSClient();
            GXDLMSDevice device = sender as GXDLMSDevice;
            parser.UseLogicalNameReferencing = device.UseLogicalNameReferencing;
            Gurux.Common.IGXMedia media = device.GXClient.Media as Gurux.Common.IGXMedia;
            SupportNetworkSpecificSettings = device.SupportNetworkSpecificSettings && media is GXNet;            
            if (SupportNetworkSpecificSettings)
            {
                parser.InterfaceType = Gurux.DLMS.InterfaceType.Net;
            }
            else
            {
                media.Eop = (byte)0x7E;
            }
            if (device.Manufacturers == null)
            {
                device.Manufacturers = new GXManufacturerCollection();
                GXManufacturerCollection.ReadManufacturerSettings(device.Manufacturers);
            }
            GXManufacturer man = device.Manufacturers.FindByIdentification(device.Identification);
			if (man == null)
			{
				throw new Exception("Unknown DLMS manufacturer type: " + device.Identification);
			}
            if (!string.IsNullOrEmpty(man.Extension))
            {
                Type t = Type.GetType(man.Extension);
                Extension = Activator.CreateInstance(t) as IGXManufacturerExtension;
            }            
            if (media is GXSerial && device.StartProtocol == StartProtocolType.IEC)
            {                                
                byte Terminator = 0xA;
                GXSerial serial = media as GXSerial;
                serial.Eop = Terminator;
                ReceiveParameters<string> p = new ReceiveParameters<string>()
                {
                    Eop = Terminator,                    
                    WaitTime = device.WaitTime * 1000                    
                };
                lock (media.Synchronous)
                {
                    //Init IEC connection. This must done first with serial connections.
                    string data = "/?!\r\n";
                    if (device.HDLCAddressing == HDLCAddressType.SerialNumber)
                    {
                        data = "/?" + device.SerialNumber + "!\r\n";
                    }
                    media.Send(data, null);
                    if (!media.Receive(p))
                    {
                        //Try to move away from mode E.
                        //TODO: this.ReadDLMSPacket(this.DisconnectRequest());
                        data = "Failed to receive reply from the device in given time.";
                        GXLogWriter.WriteLog(data);
                        throw new Exception(data);
                    }
                    //If echo is used.
                    if (p.Reply == data)
                    {
                        p.Reply = null;
                        if (!media.Receive(p))
                        {
                            //Try to move away from mode E.
                            //TODO: this.ReadDLMSPacket(this.DisconnectRequest());
                            data = "Failed to receive reply from the device in given time.";
                            GXLogWriter.WriteLog(data);
                            throw new Exception(data);
                        }
                    }
                }    
                string manufactureID = p.Reply.Substring(1, 3);
                char baudrate = p.Reply[4];
                int bitrate = 0;
                switch (baudrate)
                {
                    case '0':
                        bitrate = 300;
                        break;
                    case '1':
                        bitrate = 600;
                        break;
                    case '2':
                        bitrate = 1200;
                        break;
                    case '3':
                        bitrate = 2400;
                        break;
                    case '4':
                        bitrate = 4800;
                        break;
                    case '5':
                        bitrate = 9600;
                        break;
                    case '6':
                        bitrate = 19200;
                        break;
                    default:
                        throw new Exception("Unknown baud rate.");
                }                
                //Send ACK
                //Send Protocol control character
                byte controlCharacter = (byte)'2';// "2" HDLC protocol procedure (Mode E)
                //Send Baudrate character
                //Mode control character 
                byte ModeControlCharacter = (byte)'2';//"2" //(HDLC protocol procedure) (Binary mode)
                //We are not receive anything.
                lock (media.Synchronous)
                {
                    media.Send(new byte[] { 0x06, controlCharacter, (byte)baudrate, ModeControlCharacter, 0x8D, 0x0A }, null);
                    System.Threading.Thread.Sleep(1000);
                    serial.BaudRate = bitrate;
                    ReceiveParameters<byte[]> args = new ReceiveParameters<byte[]>();
                    args.Eop = (byte)0x0A;
                    args.WaitTime = 500;
                    media.Receive(args);
                }
                serial.DataBits = 8;
                serial.Parity = System.IO.Ports.Parity.None;
                serial.StopBits = System.IO.Ports.StopBits.One;
                serial.ResetSynchronousBuffer();
                serial.Eop = (byte)0x7E;
            }            
        }
        /// <summary>
        /// Read DLMS Data from the device.
        /// </summary>
        /// <remarks>
        /// If access is denied return null.
        /// </remarks>
        /// <param name="data">Data to send.</param>
        /// <returns>Received data.</returns>
        public void ReadDLMSPacket(byte[] data, int tryCount, GXReplyData reply)
        {
            if (data == null)
            {
                return;
            }
            object eop = (byte)0x7E;

            //In network connection terminator is not used.
            if (client.InterfaceType == InterfaceType.WRAPPER && media is GXNet && !parent.UseRemoteSerial)
            {
                eop = null;
            }
            int  pos       = 0;
            bool succeeded = false;
            ReceiveParameters <byte[]> p = new ReceiveParameters <byte[]>()
            {
                AllData  = false,
                Eop      = eop,
                Count    = 5,
                WaitTime = parent.WaitTime * 1000,
            };

            lock (media.Synchronous)
            {
                if (data != null)
                {
                    media.Send(data, null);
                }
                while (!succeeded && pos != 3)
                {
                    succeeded = media.Receive(p);
                    if (!succeeded)
                    {
                        //Try to read again...
                        if (++pos != tryCount)
                        {
                            //If Eop is not set read one byte at time.
                            if (p.Eop == null)
                            {
                                p.Count = 1;
                            }
                            System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                            media.Send(data, null);
                            continue;
                        }
                        string err = "Failed to receive reply from the device in given time.";
                        GXLogWriter.WriteLog(err, p.Reply);
                        throw new Exception(err);
                    }
                }
                try
                {
                    //Loop until whole COSEM packet is received.
                    while (!client.GetData(p.Reply, reply))
                    {
                        //If Eop is not set read one byte at time.
                        if (p.Eop == null)
                        {
                            p.Count = 1;
                        }
                        if (!media.Receive(p))
                        {
                            //Try to read again...
                            if (++pos != tryCount)
                            {
                                System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                                continue;
                            }
                            string err = "Failed to receive reply from the device in given time.";
                            GXLogWriter.WriteLog(err, p.Reply);
                            throw new Exception(err);
                        }
                    }
                }
                catch (Exception ex)
                {
                    GXLogWriter.WriteLog("Received data:", p.Reply);
                    throw ex;
                }
            }
            GXLogWriter.WriteLog(null, p.Reply);
            if (parent.OnTrace != null)
            {
                parent.OnTrace(parent, "-> " + DateTime.Now.ToLongTimeString(), p.Reply);
            }
            if (reply.Error != 0)
            {
                if (reply.Error == (int)ErrorCode.Rejected)
                {
                    Thread.Sleep(1000);
                    ReadDLMSPacket(data, tryCount, reply);
                }
                else
                {
                    throw new GXDLMSException(reply.Error);
                }
            }
        }
Esempio n. 25
0
        internal byte[] ReadDLMSPacket(GXDLMSClient cosem, Gurux.Common.IGXMedia media, byte[] data, int wt)
		{
			if (data == null)
			{
				return null;
			}
            ReceiveParameters<byte[]> args = new ReceiveParameters<byte[]>()
            {
                Eop = (byte)0x7E,
                Count = 5,
                WaitTime = wt
            };
            if (cosem.InterfaceType == InterfaceType.Net)
            {
                args.Eop = null;
                args.Count = 8;
                args.AllData = true;
            }
            int pos = 0;
            bool succeeded = false;
            lock (media.Synchronous)
            {
                media.Send(data, null);
                while (!succeeded && pos != 3)
                {
                    succeeded = media.Receive(args);
                    if (!succeeded)
                    {
                        //Try to read again...
                        if (++pos != 3)
                        {
                            System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                            continue;
                        }
                        string err = "Failed to receive reply from the device in given time.";
                        GXLogWriter.WriteLog(err, (byte[])args.Reply);
                        throw new Exception(err);
                    }
                }                
                //Loop until whole m_Cosem packet is received.                
                while (!(succeeded = cosem.IsDLMSPacketComplete(args.Reply)))
                {
                    if (!media.Receive(args))
                    {
                        //Try to read again...
                        if (++pos != 3)
                        {
                            System.Diagnostics.Debug.WriteLine("Data receive failed. Try to resend " + pos.ToString() + "/3");
                            continue;
                        }
                        string err = "Failed to receive reply from the device in given time.";
                        GXLogWriter.WriteLog(err, (byte[])args.Reply);
                        throw new Exception(err);
                    }
                }                
            }
            object[,] errors = cosem.CheckReplyErrors(data, args.Reply);
            if (errors != null)
            {
                int error = (int)errors[0, 0];
                throw new GXDLMSException(error);
            }
            return args.Reply;
		}
 /// <summary>
 /// Disconnect.
 /// </summary>
 /// <param name="serial"></param>
 /// <param name="tryCount"></param>
 public static void Disconnect(IGXMedia media, int tryCount)
 {
     lock (media.Synchronous)
     {
         ReceiveParameters<byte[]> p = new ReceiveParameters<byte[]>()
         {
             Eop = GetEops(),
             WaitTime = 1000
         };
         List<byte> data = new List<byte>();
         data.Add(0x01);
         data.Add((byte)'B');
         data.Add((byte)'0');
         data.Add(0x03);
         data.Add(CalculateChecksum(data, 1, data.Count - 1));
         byte[] data1 = data.ToArray();
         string header, frame;                
         media.Send(data1, null);
         media.Receive(p);
         while (--tryCount > -1)
         {
             if (media.Receive(p))
             {                        
                 GetPacket(new List<byte>(p.Reply), false, out header, out frame);
                 if (header == "B0")
                 {
                     break;
                 }
                 if (p.Reply.Length > 11)
                 {
                     p.Reply = null;
                 }
             }
             media.Send(data1, null);
         }
     }
 }
Esempio n. 27
0
		/// <summary>
		/// Import properties from the device.
		/// </summary>
        /// <param name="addinPages">Addin pages.</param>
        /// <param name="device">The target GXDevice to put imported items.</param>
		/// <param name="media">A media connection to the device.</param>
		/// <returns>True if there were no errors, otherwise false.</returns>
        public override void ImportFromDevice(Control[] addinPages, GXDevice device, IGXMedia media)
		{
            media.Open();
			GXDLMSDevice Device = (GXDLMSDevice)device;            
			int wt = Device.WaitTime;
			GXDLMSClient cosem = null;
            byte[] data, reply = null;            
            IGXManufacturerExtension Extension = null;
			try
			{                
				//Initialize connection.
                cosem = new GXDLMSClient();
                cosem.UseLogicalNameReferencing = Device.UseLogicalNameReferencing;				
                if (Device.Manufacturers == null)
                {
                    Device.Manufacturers = new GXManufacturerCollection();
                    GXManufacturerCollection.ReadManufacturerSettings(Device.Manufacturers);
                }
                GXManufacturer man = Device.Manufacturers.FindByIdentification(Device.Identification);
                if (!string.IsNullOrEmpty(man.Extension))
                {
                    Type t = Type.GetType(man.Extension);
                    Extension = Activator.CreateInstance(t) as IGXManufacturerExtension;
                }

                if (!Device.UseRemoteSerial && media is GXNet) //If media is network.
				{
                    if (Device.SupportNetworkSpecificSettings)
                    {
                        cosem.InterfaceType = Gurux.DLMS.InterfaceType.Net;
                    }
				}
				else if (media is GXSerial) //If media is serial.
				{
                    byte terminator = 0xA;
                    if (Device.StartProtocol == StartProtocolType.IEC)
                    {
                        GXSerial serial = media as GXSerial;
                        serial.Eop = terminator;
                        serial.Eop = terminator;
                        //Init IEC connection. This must done first with serial connections.
                        string str = "/?" + Device.SerialNumber + "!\r\n";
                        ReceiveParameters<string> args = new ReceiveParameters<string>()
                        {
                            Eop = terminator,
                            WaitTime = wt
                        };
                        lock (media.Synchronous)
                        {
                            media.Send(str, null);
                            do
                            {
                                args.Reply = null;                                
                                if (!media.Receive(args))
                                {
                                    throw new Exception("Failed to receive reply from the device in given time.");
                                }
                            }
                            while (str == args.Reply);//Remove echo
                        }
                        string answer = args.Reply.ToString();                        
                        if (answer[0] != '/')
                        {
                            throw new Exception("Invalid responce.");
                        }
                        string manufactureID = answer.Substring(1, 3);
                        char baudrate = answer[4];
                        if (baudrate == ' ')
                        {
                            baudrate = '5';
                        }
                        int baudRate = 0;
                        switch (baudrate)
                        {
                            case '0':
                                baudRate = 300;
                                break;
                            case '1':
                                baudRate = 600;
                                break;
                            case '2':
                                baudRate = 1200;
                                break;
                            case '3':
                                baudRate = 2400;
                                break;
                            case '4':
                                baudRate = 4800;
                                break;
                            case '5':                            
                                baudRate = 9600;
                                break;
                            case '6':
                                baudRate = 19200;
                                break;
                            default:
                                throw new Exception("Unknown baud rate.");
                        }                        
                        //Send ACK
                        //Send Protocol control character
                        byte controlCharacter = (byte)'2';// "2" HDLC protocol procedure (Mode E)
                        //Send Baudrate character
                        //Mode control character 
                        byte ModeControlCharacter = (byte)'2';//"2" //(HDLC protocol procedure) (Binary mode)
                        //We are not receive anything.
                        data = new byte[] { 0x06, controlCharacter, (byte)baudrate, ModeControlCharacter, 0x0D, 0x0A };                        
                        lock (media.Synchronous)
                        {
                            args.Reply = null;                            
                            media.Send(data, null);                                                       
                            //This is in standard. Do not remove sleep.
                            //Some meters work without it, but some do not.
                            System.Threading.Thread.Sleep(500);
                            serial.BaudRate = baudRate;
                            ReceiveParameters<byte[]> args2 = new ReceiveParameters<byte[]>()
                            {
                                Eop = terminator,
                                WaitTime = 100
                            };
                            //If this fails, just read all data.
                            if (!media.Receive(args2))
                            {
                                //Read buffer.
                                args2.AllData = true;
                                args2.WaitTime = 1;
                                media.Receive(args2);
                            }
                            serial.DataBits = 8;
                            serial.Parity = Parity.None;
                            serial.StopBits = StopBits.One;
                            serial.DiscardInBuffer();
                            serial.DiscardOutBuffer();
                            serial.ResetSynchronousBuffer();
                        }                        
                    }
				}
                media.Eop = (byte) 0x7E;
                cosem.Authentication = (Gurux.DLMS.Authentication)Device.Authentication;
                object clientAdd = null;
                if (cosem.Authentication == Authentication.None)
                {
                    clientAdd = Device.ClientID;
                }
                else if (cosem.Authentication == Authentication.Low)
                {
                    clientAdd = Device.ClientIDLow;
                }
                else if (cosem.Authentication == Authentication.High)
                {
                    clientAdd = Device.ClientIDHigh;
                }
                if (!string.IsNullOrEmpty(Device.Password))
                {
                    cosem.Password = ASCIIEncoding.ASCII.GetBytes(Device.Password);
                }
                else
                {
                    cosem.Password = null;
                }
                //If network media is used check is manufacturer supporting IEC 62056-47
                if (!Device.UseRemoteSerial && media is GXNet && Device.SupportNetworkSpecificSettings)
                {
                    cosem.InterfaceType = InterfaceType.Net;
                    media.Eop = null;
                    cosem.ClientID = Convert.ToUInt16(clientAdd);
                    cosem.ServerID = Convert.ToUInt16(Device.PhysicalAddress);
                }
                else
                {
                    if (Device.HDLCAddressing == HDLCAddressType.Custom)
                    {
                        cosem.ClientID = clientAdd;
                    }
                    else
                    {
                        cosem.ClientID = (byte)(Convert.ToByte(clientAdd) << 1 | 0x1);
                    }
                    if (Device.HDLCAddressing == HDLCAddressType.SerialNumber)
                    {
                        cosem.ServerID = GXManufacturer.CountServerAddress(Device.HDLCAddressing, Device.SNFormula, Convert.ToUInt32(Device.SerialNumber), Device.LogicalAddress);
                    }
                    else
                    {
                        cosem.ServerID = GXManufacturer.CountServerAddress(Device.HDLCAddressing, Device.SNFormula, Device.PhysicalAddress, Device.LogicalAddress);
                    }                    
                }
                byte[] allData = null;
                data = cosem.SNRMRequest();
				//General Network connection don't need SNRMRequest.
				if (data != null)
				{
					Trace("--- Initialize DLMS connection\r\n");
					try
					{
						reply = ReadDLMSPacket(cosem, media, data, wt);
					}
					catch (Exception Ex)
					{
						throw new Exception("DLMS Initialize failed. " + Ex.Message);
					}
					//Has server accepted client.
					cosem.ParseUAResponse(reply);
				}
				Trace("Connecting\r\n");
                media.ResetSynchronousBuffer();
				try
				{                    
                    foreach (byte[] it in cosem.AARQRequest(null))
                    {                        
                        reply = ReadDLMSPacket(cosem, media, it, wt);
                    }
				}
				catch (Exception Ex)
				{
					throw new Exception("DLMS AARQRequest failed. " + Ex.Message);
				}
                cosem.ParseAAREResponse(reply);
                //Now 1/5 or actions is done.
                Progress(1, 5);
                Trace("Read Objects\r\n");
                try
				{
                    allData = ReadDataBlock(cosem, media, cosem.GetObjectsRequest(), wt, 1);
				}
				catch (Exception Ex)
				{
					throw new Exception("DLMS AARQRequest failed. " + Ex.Message);
				}
                Trace("--- Parse Objects ---\r\n");
                GXDLMSObjectCollection objs = cosem.ParseObjects((byte[])allData, true);

			    allData = null;
				//Now we know exact number of read registers. Update progress bar again.
                int max = objs.Count;				                
				Trace("--- Read scalars ---\r\n");
				//Now 2/5 or actions is done.
                Progress(2 * max, 5 * max);
                GXCategory dataItems = new GXCategory();
                dataItems.Name = "Data Items";
                GXCategory registers = new GXCategory();
                registers.Name = "Registers";
                Device.Categories.Add(dataItems);
                Device.Categories.Add(registers);
                int pos = 0;
                foreach (GXDLMSObject it in objs)
                {
                    ++pos;
                    //Skip association views.
                    if (it.ObjectType == ObjectType.AssociationLogicalName ||
                        it.ObjectType == ObjectType.AssociationShortName)
                    {
                        continue;
                    }
                    if (it.ObjectType != ObjectType.ProfileGeneric)
                    {
                        object prop = UpdateData(media, Device, wt, cosem, man, it, dataItems, registers);
                        //Read scaler and unit
                        if (it.ObjectType == ObjectType.Register)
                        {
                            try
                            {
                                data = cosem.Read(it.Name, it.ObjectType, 3)[0];
                                allData = ReadDataBlock(cosem, media, data, wt, 2);
                                cosem.UpdateValue(allData, it, 3);
                                Gurux.DLMS.Objects.GXDLMSRegister item = it as Gurux.DLMS.Objects.GXDLMSRegister;
                                GXDLMSRegister r = prop as GXDLMSRegister;
                                r.Scaler = item.Scaler;
                                r.Unit = item.Unit.ToString();
                            }
                            //Ignore HW error and read next.
                            catch (GXDLMSException)
                            {
                                continue;
                            }
                            catch (Exception Ex)
                            {
                                throw new Exception("DLMS Register Scaler and Unit read failed. " + Ex.Message);
                            }
                        }
                        //Read scaler and unit
                        else if (it.ObjectType == ObjectType.ExtendedRegister)
                        {
                            try
                            {
                                data = cosem.Read(it.Name, it.ObjectType, 3)[0];
                                allData = ReadDataBlock(cosem, media, data, wt, 2);
                                cosem.UpdateValue(allData, it, 3);
                                Gurux.DLMS.Objects.GXDLMSExtendedRegister item = it as Gurux.DLMS.Objects.GXDLMSExtendedRegister;
                                GXDLMSCategory cat = prop as GXDLMSCategory;
                                GXDLMSRegister r = cat.Properties[0] as GXDLMSRegister;
                                r.Scaler = item.Scaler;
                                r.Unit = item.Unit.ToString();
                                cat.Properties[1].SetValue(item.Scaler.ToString() + ", " + item.Unit.ToString(), true, PropertyStates.None);
                            }
                            //Ignore HW error and read next.
                            catch (GXDLMSException)
                            {
                                continue;
                            }
                            catch (Exception Ex)
                            {
                                throw new Exception("DLMS Register Scaler and Unit read failed. " + Ex.Message);
                            }
                        }
                        //Read scaler and unit
                        else if (it.ObjectType == ObjectType.DemandRegister)
                        {
                            try
                            {
                                data = cosem.Read(it.Name, it.ObjectType, 3)[0];
                                allData = ReadDataBlock(cosem, media, data, wt, 2);
                                cosem.UpdateValue(allData, it, 3);
                                Gurux.DLMS.Objects.GXDLMSDemandRegister item = it as Gurux.DLMS.Objects.GXDLMSDemandRegister;
                                GXDLMSCategory cat = prop as GXDLMSCategory;
                                cat.Properties[2].SetValue(item.Scaler.ToString() + ", " + item.Unit.ToString(), true, PropertyStates.None);

                                GXDLMSRegister r = cat.Properties[0] as GXDLMSRegister;
                                r.Scaler = item.Scaler;
                                r.Unit = item.Unit.ToString();
                                r = cat.Properties[1] as GXDLMSRegister;
                                r.Scaler = item.Scaler;
                                r.Unit = item.Unit.ToString();
                            }
                            //Ignore HW error and read next.
                            catch (GXDLMSException)
                            {
                                continue;
                            }
                            catch (Exception Ex)
                            {
                                throw new Exception("DLMS Register Scaler and Unit read failed. " + Ex.Message);
                            }
                        }                        
                    }
                    //Now 3/5 actions is done.
                    double tmp = pos * max; 
                    tmp /= max;
                    tmp += 2 * max;
                    Progress((int) tmp , 5 * max);
                }
                //Now 3/5 actions is done.
                Progress(3 * max, 5 * max);
                Trace("--- Read Generic profiles ---\r\n");
                GXDLMSObjectCollection pg = objs.GetObjects(ObjectType.ProfileGeneric);
                foreach (GXDLMSProfileGeneric it in pg)
                {
                    try
                    {
                        allData = ReadDataBlock(cosem, media, cosem.Read(it.Name, it.ObjectType, 3)[0], wt, 3);
                        cosem.UpdateValue(allData, it, 3);
                        UpdateData(media, Device, wt, cosem, man, it, dataItems, registers);
                    }
                    //Ignore HW error and read next.
                    catch (GXDLMSException)
                    {
                        continue;
                    }
                    catch (Exception Ex)
                    {
                        Trace("DLMS Generic Profile read failed. " + Ex.Message + Environment.NewLine);
                    }
                }
                //Now 4/5 actions is done.
                Progress(4 * max, 5 * max);            

                //Update IEC HDLC interval if found. 
                GXDLMSObjectCollection objects = objs.GetObjects(ObjectType.IecHdlcSetup);
                if (objects.Count != 0)
                {
                    allData = ReadDataBlock(cosem, media, cosem.Read(objects[0].Name, objects[0].ObjectType, 8)[0], wt, 5);
                    //Minus 10 second.
                    Device.Keepalive.Interval = (Convert.ToInt32(cosem.GetValue(allData)) - 10) * 1000;
                }

                //Now all actions are done.
                Progress(max, max);
                Trace("--- Succeeded ---\r\n");
			}
			finally
			{                
                if (cosem != null && media != null)
				{
					Trace("--- Disconnecting ---\r\n");
                    byte[] allData = null;
					if (cosem != null)
					{
						//Network standard don't need this.					
                        if (!(media is GXNet && Device.SupportNetworkSpecificSettings))
						{
							try
							{
								reply = ReadDLMSPacket(cosem, media, cosem.DisconnectRequest(), wt);
								cosem.GetDataFromPacket(reply, ref allData);
							}
							catch (Exception Ex)
							{
								Trace("DisconnectRequest failed. " + Ex.Message);
							}
						}
					}
					if (media != null)
					{
						media.Close();
						media = null;
					}
					Trace("--- Disconnected ---\r\n--- Done---\r\n");					
				}
			}			
		}
Esempio n. 28
0
        /// <summary>
        /// Read DLMS Data from the device.
        /// </summary>
        /// <param name="data">Data to send.</param>
        /// <returns>Received data.</returns>
        public void ReadDLMSPacket(byte[] data, GXReplyData reply)
        {
            if (data == null && !reply.IsStreaming())
            {
                return;
            }
            GXReplyData notify = new GXReplyData();

            reply.Error = 0;
            object eop = (byte)0x7E;

            //In network connection terminator is not used.
            if (Client.InterfaceType == InterfaceType.WRAPPER)
            {
                eop = null;
            }
            int  pos       = 0;
            bool succeeded = false;
            ReceiveParameters <byte[]> p = new ReceiveParameters <byte[]>()
            {
                Eop      = eop,
                WaitTime = WaitTime,
            };

            if (eop == null)
            {
                p.Count = 8;
            }
            else
            {
                p.Count = 5;
            }
            GXByteBuffer rd = new GXByteBuffer();

            lock (Media.Synchronous)
            {
                while (!succeeded && pos != 3)
                {
                    if (!reply.IsStreaming())
                    {
                        WriteTrace("TX:\t" + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(data, true));
                        Media.Send(data, null);
                    }
                    succeeded = Media.Receive(p);
                    if (!succeeded)
                    {
                        if (++pos >= RetryCount)
                        {
                            throw new Exception("Failed to receive reply from the device in given time.");
                        }
                        //If Eop is not set read one byte at time.
                        if (p.Eop == null)
                        {
                            p.Count = 1;
                        }
                        //Try to read again...
                        System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                    }
                }
                rd = new GXByteBuffer(p.Reply);
                try
                {
                    pos = 0;
                    //Loop until whole COSEM packet is received.
                    while (!Client.GetData(rd, reply, notify))
                    {
                        p.Reply = null;
                        if (notify.IsComplete && notify.Data.Data != null)
                        {
                            //Handle notify.
                            if (!notify.IsMoreData)
                            {
                                //Show received push message as XML.
                                string           xml;
                                GXDLMSTranslator t = new GXDLMSTranslator(TranslatorOutputType.SimpleXml);
                                t.DataToXml(notify.Data, out xml);
                                Console.WriteLine(xml);
                                notify.Clear();
                                continue;
                            }
                        }
                        if (p.Eop == null)
                        {
                            p.Count = Client.GetFrameSize(rd);
                        }
                        while (!Media.Receive(p))
                        {
                            if (++pos >= RetryCount)
                            {
                                throw new Exception("Failed to receive reply from the device in given time.");
                            }
                            //If echo.
                            if (rd == null || rd.Size == data.Length)
                            {
                                Media.Send(data, null);
                            }
                            //Try to read again...
                            System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                        }
                        rd.Set(p.Reply);
                    }
                }
                catch (Exception ex)
                {
                    WriteTrace("RX:\t" + DateTime.Now.ToLongTimeString() + "\t" + rd);
                    throw ex;
                }
            }
            WriteTrace("RX:\t" + DateTime.Now.ToLongTimeString() + "\t" + rd);
            if (reply.Error != 0)
            {
                if (reply.Error == (short)ErrorCode.Rejected)
                {
                    Thread.Sleep(1000);
                    ReadDLMSPacket(data, reply);
                }
                else
                {
                    throw new GXDLMSException(reply.Error);
                }
            }
        }
Esempio n. 29
0
        private static void InitializeIEC(TraceLevel trace, Media media)
        {
            GXSerial serial = (GXSerial)media.Target;

            serial.BaudRate = 300;
            serial.DataBits = 7;
            serial.Parity   = Parity.Even;
            serial.StopBits = StopBits.One;
            byte Terminator = (byte)0x0A;

            //Some meters need a little break.
            Thread.Sleep(1000);
            //Query device information.
            string data = "/?!\r\n";

            WriteLog(trace, "IEC Sending:" + data);
            if (media.WaitTime == 0)
            {
                media.WaitTime = 5;
            }
            ReceiveParameters <string> p = new ReceiveParameters <string>()
            {
                AllData  = false,
                Eop      = Terminator,
                WaitTime = media.WaitTime * 1000
            };

            lock (media.Target.Synchronous)
            {
                media.Target.Send(data, null);
                if (!media.Target.Receive(p))
                {
                    DiscIEC(media);
                    string str = "Failed to receive reply from the device in given time.";
                    WriteLog(trace, str);
                    media.Target.Send(data, null);
                    if (!media.Target.Receive(p))
                    {
                        throw new Exception(str);
                    }
                }
                //If echo is used.
                if (p.Reply == data)
                {
                    p.Reply = null;
                    if (!media.Target.Receive(p))
                    {
                        data = "Failed to receive reply from the device in given time.";
                        WriteLog(trace, data);
                        throw new Exception(data);
                    }
                }
            }
            WriteLog(trace, "IEC received: " + p.Reply);
            if (p.Reply[0] != '/')
            {
                p.WaitTime = 100;
                media.Target.Receive(p);
                throw new Exception("Invalid responce.");
            }
            string manufactureID = p.Reply.Substring(1, 3);
            char   baudrate      = p.Reply[4];
            int    BaudRate;

            switch (baudrate)
            {
            case '0':
                BaudRate = 300;
                break;

            case '1':
                BaudRate = 600;
                break;

            case '2':
                BaudRate = 1200;
                break;

            case '3':
                BaudRate = 2400;
                break;

            case '4':
                BaudRate = 4800;
                break;

            case '5':
                BaudRate = 9600;
                break;

            case '6':
                BaudRate = 19200;
                break;

            default:
                throw new Exception("Unknown baud rate.");
            }
            if (media.MaximumBaudRate != 0)
            {
                BaudRate = media.MaximumBaudRate;
                baudrate = GetIecBaudRate(BaudRate);
                WriteLog(trace, "Maximum BaudRate is set to : " + BaudRate.ToString());
            }
            WriteLog(trace, "BaudRate is : " + BaudRate.ToString());
            //Send ACK
            //Send Protocol control character
            // "2" HDLC protocol procedure (Mode E)
            byte controlCharacter = (byte)'2';
            //Send Baud rate character
            //Mode control character
            byte ModeControlCharacter = (byte)'2';

            //"2" //(HDLC protocol procedure) (Binary mode)
            //Set mode E.
            byte[] arr = new byte[] { 0x06, controlCharacter, (byte)baudrate, ModeControlCharacter, 13, 10 };
            WriteLog(trace, "Moving to mode E. " + GXCommon.ToHex(arr));
            lock (media.Target.Synchronous)
            {
                p.Reply = null;
                media.Target.Send(arr, null);
                p.WaitTime = 2000;
                //Note! All meters do not echo this.
                media.Target.Receive(p);
                if (p.Reply != null)
                {
                    WriteLog(trace, "Received: " + p.Reply);
                }
                media.Target.Close();
                serial.BaudRate = BaudRate;
                serial.DataBits = 8;
                serial.Parity   = Parity.None;
                serial.StopBits = StopBits.One;
                serial.Open();
                //Some meters need this sleep. Do not remove.
                Thread.Sleep(1000);
            }
        }
        void InitSerial()
        {
            GXSerial serial = Media as GXSerial;
            byte Terminator = (byte)0x0A;
            if (serial != null && InitializeIEC)
            {
                serial.BaudRate = 300;
                serial.DataBits = 7;
                serial.Parity = Parity.Even;
                serial.StopBits = StopBits.One;
            }
            Media.Open();
            //Query device information.
            if (Media != null && InitializeIEC)
            {
                string data = "/?!\r\n";
                if (Trace)
                {
                    Console.WriteLine("IEC sending:" + data);
                }
                ReceiveParameters<string> p = new ReceiveParameters<string>()
                {
                    Eop = Terminator,
                    WaitTime = WaitTime
                };
                lock (Media.Synchronous)
                {
                    WriteTrace("<- " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(ASCIIEncoding.ASCII.GetBytes(data), true));
                    Media.Send(data, null);
                    if (!Media.Receive(p))
                    {
                        //Try to move away from mode E.
                        try
                        {
                            ReadDLMSPacket(Client.DisconnectRequest());
                        }
                        catch (Exception)
                        {
                        }
                        data = (char)0x01 + "B0" + (char)0x03;
                        Media.Send(data, null);
                        p.Count = 1;
                        if (!Media.Receive(p))
                        {
                        }
                        data = "Failed to receive reply from the device in given time.";
                        Console.WriteLine(data);
                        throw new Exception(data);
                    }
                    WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(ASCIIEncoding.ASCII.GetBytes(p.Reply), true));
                    //If echo is used.
                    if (p.Reply == data)
                    {
                        p.Reply = null;
                        if (!Media.Receive(p))
                        {
                            //Try to move away from mode E.
                            ReadDLMSPacket(Client.DisconnectRequest());
                            if (serial != null)
                            {
                                data = (char)0x01 + "B0" + (char)0x03;
                                Media.Send(data, null);
                                p.Count = 1;
                                Media.Receive(p);
                                serial.BaudRate = 9600;
                                data = (char)0x01 + "B0" + (char)0x03 + "\r\n";
                                Media.Send(data, null);
                                p.Count = 1;
                                Media.Receive(p);
                            }

                            data = "Failed to receive reply from the device in given time.";
                            Console.WriteLine(data);
                            throw new Exception(data);
                        }
                        WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(ASCIIEncoding.ASCII.GetBytes(p.Reply), true));
                    }
                }
                Console.WriteLine("IEC received: " + p.Reply);
                if (p.Reply[0] != '/')
                {
                    p.WaitTime = 100;
                    Media.Receive(p);
                    throw new Exception("Invalid responce.");
                }
                string manufactureID = p.Reply.Substring(1, 3);
                UpdateManufactureSettings(manufactureID);
                char baudrate = p.Reply[4];
                int BaudRate = 0;
                switch (baudrate)
                {
                    case '0':
                        BaudRate = 300;
                        break;
                    case '1':
                        BaudRate = 600;
                        break;
                    case '2':
                        BaudRate = 1200;
                        break;
                    case '3':
                        BaudRate = 2400;
                        break;
                    case '4':
                        BaudRate = 4800;
                        break;
                    case '5':
                        BaudRate = 9600;
                        break;
                    case '6':
                        BaudRate = 19200;
                        break;
                    default:
                        throw new Exception("Unknown baud rate.");
                }
                Console.WriteLine("BaudRate is : " + BaudRate.ToString());
                //Send ACK
                //Send Protocol control character
                byte controlCharacter = (byte)'2';// "2" HDLC protocol procedure (Mode E)
                //Send Baudrate character
                //Mode control character
                byte ModeControlCharacter = (byte)'2';//"2" //(HDLC protocol procedure) (Binary mode)
                //Set mode E.
                byte[] arr = new byte[] { 0x06, controlCharacter, (byte)baudrate, ModeControlCharacter, 13, 10 };
                Console.WriteLine("Moving to mode E.", arr);
                lock (Media.Synchronous)
                {
                    WriteTrace("<- " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(arr, true));
                    Media.Send(arr, null);
                    p.Reply = null;
                    if (!Media.Receive(p))
                    {
                        //Try to move away from mode E.
                        ReadDLMSPacket(Client.DisconnectRequest());
                        data = "Failed to receive reply from the device in given time.";
                        Console.WriteLine(data);
                        throw new Exception(data);
                    }
                    WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(ASCIIEncoding.ASCII.GetBytes(p.Reply), true));
                    Console.WriteLine("Received: " + p.Reply);
                    if (serial != null)
                    {
                        serial.BaudRate = BaudRate;
                        serial.DataBits = 8;
                        serial.Parity = Parity.None;
                        serial.StopBits = StopBits.One;
                        System.Threading.Thread.Sleep(300);
                        serial.ResetSynchronousBuffer();
                    }
                }
            }
        }
        void InitializeIEC()
        {
            GXManufacturer manufacturer = this.parent.Manufacturers.FindByIdentification(parent.Manufacturer);
            if (manufacturer == null)
            {
                throw new Exception("Unknown manufacturer " + parent.Manufacturer);
            }
            GXSerial serial = media as GXSerial;
            byte Terminator = (byte)0x0A;
            media.Open();
            //Query device information.
            if (media != null && parent.StartProtocol == StartProtocolType.IEC)
            {
                string data = "/?!\r\n";
                if (this.parent.HDLCAddressing == HDLCAddressType.SerialNumber)
                {
                    data = "/?" + this.parent.PhysicalAddress + "!\r\n";
                }
                GXLogWriter.WriteLog("HDLC sending:" + data);
                ReceiveParameters<string> p = new ReceiveParameters<string>()
                {
                    AllData = false,
                    Eop = Terminator,
                    WaitTime = parent.WaitTime * 1000
                };
                lock (media.Synchronous)
                {
                    media.Send(data, null);
                    if (!media.Receive(p))
                    {
                        //Try to move away from mode E.
                        try
                        {
                            GXReplyData reply = new GXReplyData();
                            this.ReadDLMSPacket(this.DisconnectRequest(), 1, reply);
                        }
                        catch (Exception)
                        {
                        }
                        data = (char)0x01 + "B0" + (char)0x03 + "\r\n";
                        media.Send(data, null);
                        p.Count = 1;
                        media.Receive(p);
                        data = "Failed to receive reply from the device in given time.";
                        GXLogWriter.WriteLog(data);
                        throw new Exception(data);
                    }
                    //If echo is used.
                    if (p.Reply == data)
                    {
                        p.Reply = null;
                        if (!media.Receive(p))
                        {
                            //Try to move away from mode E.
                            GXReplyData reply = new GXReplyData();
                            this.ReadDLMSPacket(this.DisconnectRequest(), 1, reply);
                            if (serial != null)
                            {
                                data = (char)0x01 + "B0" + (char)0x03 + "\r\n";
                                media.Send(data, null);
                                p.Count = 1;
                                if (!media.Receive(p))
                                {
                                }
                                serial.DtrEnable = serial.RtsEnable = false;
                                serial.BaudRate = 9600;
                                serial.DtrEnable = serial.RtsEnable = true;
                                data = (char)0x01 + "B0" + (char)0x03 + "\r\n";
                                media.Send(data, null);
                                p.Count = 1;
                                media.Receive(p);
                            }

                            data = "Failed to receive reply from the device in given time.";
                            GXLogWriter.WriteLog(data);
                            throw new Exception(data);
                        }
                    }
                }
                GXLogWriter.WriteLog("HDLC received: " + p.Reply);
                if (p.Reply[0] != '/')
                {
                    p.WaitTime = 100;
                    media.Receive(p);
                    throw new Exception("Invalid responce.");
                }
                string manufactureID = p.Reply.Substring(1, 3);
                UpdateManufactureSettings(manufactureID);
                char baudrate = p.Reply[4];
                int BaudRate = 0;
                switch (baudrate)
                {
                    case '0':
                        BaudRate = 300;
                        break;
                    case '1':
                        BaudRate = 600;
                        break;
                    case '2':
                        BaudRate = 1200;
                        break;
                    case '3':
                        BaudRate = 2400;
                        break;
                    case '4':
                        BaudRate = 4800;
                        break;
                    case '5':
                        BaudRate = 9600;
                        break;
                    case '6':
                        BaudRate = 19200;
                        break;
                    default:
                        throw new Exception("Unknown baud rate.");
                }
                if (parent.MaximumBaudRate != 0)
                {
                    BaudRate = parent.MaximumBaudRate;
                    GXLogWriter.WriteLog("Maximum BaudRate is set to : " + BaudRate.ToString());
                }
                GXLogWriter.WriteLog("BaudRate is : " + BaudRate.ToString());
                //Send ACK
                //Send Protocol control character
                byte controlCharacter = (byte)'2';// "2" HDLC protocol procedure (Mode E)
                //Send Baud rate character
                //Mode control character
                byte ModeControlCharacter = (byte)'2';//"2" //(HDLC protocol procedure) (Binary mode)
                //Set mode E.
                byte[] arr = new byte[] { 0x06, controlCharacter, (byte)baudrate, ModeControlCharacter, 13, 10 };
                GXLogWriter.WriteLog("Moving to mode E.", arr);
                lock (media.Synchronous)
                {
                    media.Send(arr, null);
                    System.Threading.Thread.Sleep(500);
                    serial.BaudRate = BaudRate;
                    p.Reply = null;
                    p.WaitTime = 100;
                    //Note! All meters do not echo this.
                    media.Receive(p);
                    if (p.Reply != null)
                    {
                        GXLogWriter.WriteLog("Received: " + p.Reply);
                    }
                    serial.Close();
                    serial.DataBits = 8;
                    serial.Parity = Parity.None;
                    serial.StopBits = StopBits.One;
                    serial.Open();
                }
            }
        }
        /// <summary>
        /// Read DLMS Data from the device.
        /// </summary>
        /// <remarks>
        /// If access is denied return null.
        /// </remarks>
        /// <param name="data">Data to send.</param>
        /// <returns>Received data.</returns>
        public byte[] ReadDLMSPacket(byte[] data, int tryCount)
        {
            if (data == null)
            {
                return(null);
            }
            object eop = (byte)0x7E;

            //In network connection terminator is not used.
            if (m_Cosem.InterfaceType == InterfaceType.Net && Media is GXNet && !Parent.UseRemoteSerial)
            {
                eop = null;
            }
            int  pos       = 0;
            bool succeeded = false;
            ReceiveParameters <byte[]> p = new ReceiveParameters <byte[]>()
            {
                AllData  = false,
                Eop      = eop,
                Count    = 5,
                WaitTime = Parent.WaitTime * 1000,
            };

            lock (Media.Synchronous)
            {
                if (data != null)
                {
                    Media.Send(data, null);
                }
                while (!succeeded && pos != 3)
                {
                    succeeded = Media.Receive(p);
                    if (!succeeded)
                    {
                        //Try to read again...
                        if (++pos != tryCount)
                        {
                            //If Eop is not set read one byte at time.
                            if (p.Eop == null)
                            {
                                p.Count = 1;
                            }
                            System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                            Media.Send(data, null);
                            continue;
                        }
                        string err = "Failed to receive reply from the device in given time.";
                        GXLogWriter.WriteLog(err, p.Reply);
                        throw new Exception(err);
                    }
                }
                //Loop until whole COSEM packet is received.
                while (!m_Cosem.IsDLMSPacketComplete(p.Reply))
                {
                    //If Eop is not set read one byte at time.
                    if (p.Eop == null)
                    {
                        p.Count = 1;
                    }
                    if (!Media.Receive(p))
                    {
                        //Try to read again...
                        if (++pos != tryCount)
                        {
                            System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                            continue;
                        }
                        string err = "Failed to receive reply from the device in given time.";
                        GXLogWriter.WriteLog(err, p.Reply);
                        throw new Exception(err);
                    }
                }
            }
            GXLogWriter.WriteLog("Received data", p.Reply);
            object errors = m_Cosem.CheckReplyErrors(data, p.Reply);

            if (errors != null)
            {
                object[,] arr = (object[, ])errors;
                int error = (int)arr[0, 0];
                if (error == -1)
                {
                    //If data is reply to the previous packet sent.
                    //This might happens sometimes.
                    if (m_Cosem.IsPreviousPacket(data, p.Reply))
                    {
                        return(ReadDLMSPacket(null));
                    }
                    else
                    {
                        throw new Exception(arr[0, 1].ToString());
                    }
                }
                throw new GXDLMSException(error);
            }
            return(p.Reply);
        }
 static public byte[] ReadReadout(IGXMedia media, string data, int wt)
 {
     ReceiveParameters<byte[]> p = new ReceiveParameters<byte[]>()
     {
         Eop = GetEops(),
         WaitTime = wt
     };
     lock (media.Synchronous)
     {
         if (data != null)
         {
             media.Send(data, null);
         }
         do
         {
             if (!media.Receive(p))
             {
                 //There is no eop or CRC.
                 break;
             }
         }
         while (p.Reply[p.Reply.Length - 1] != 0x3);
         //Read CRC if EOP is found.
         if (p.Reply[p.Reply.Length - 1] == 0x3)
         {
             p.Eop = null;
             p.Count = 1;
             if (!media.Receive(p))
             {
                 throw new Exception("Failed to receive reply from the device in given time.");
             }
         }
     }
     return p.Reply;
 }
 public void InitializeConnection()
 {
     if (!string.IsNullOrEmpty(Parent.Manufacturer))
     {
         UpdateManufactureSettings(Parent.Manufacturer);
     }
     if (Media is GXSerial)
     {
         GXLogWriter.WriteLog("Initializing serial connection.");
         InitSerial();
         ConnectionStartTime = DateTime.Now;
     }
     else if (Media is GXNet)
     {
         GXLogWriter.WriteLog("Initializing Network connection.");
         InitNet();
         //Some Electricity meters need some time before first message can be send.
         System.Threading.Thread.Sleep(500);
     }
     else if (Media is Gurux.Terminal.GXTerminal)
     {
         GXLogWriter.WriteLog("Initializing Terminal connection.");
         InitTerminal();
     }
     else
     {
         throw new Exception("Unknown media type.");
     }
     try
     {
         byte[] data, reply = null;
         data = SNRMRequest();
         if (data != null)
         {
             GXLogWriter.WriteLog("Send SNRM request.", data);
             reply = ReadDLMSPacket(data, 1);
             GXLogWriter.WriteLog("Parsing UA reply.", reply);
             //Has server accepted client.
             ParseUAResponse(reply);
             GXLogWriter.WriteLog("Parsing UA reply succeeded.");
         }
         //Generate AARQ request.
         //Split requests to multiple packets if needed.
         //If password is used all data might not fit to one packet.
         foreach (byte[] it in AARQRequest())
         {
             GXLogWriter.WriteLog("Send AARQ request", it);
             reply = ReadDLMSPacket(it);
         }
         GXLogWriter.WriteLog("Parsing AARE reply", (byte[])reply);
         try
         {
             //Parse reply.
             ParseAAREResponse(reply);
         }
         catch (Exception Ex)
         {
             ReadDLMSPacket(DisconnectRequest(), 1);
             throw Ex;
         }
         //If authentication is required.
         if (m_Cosem.IsAuthenticationRequired)
         {
             foreach (byte[] it in m_Cosem.GetApplicationAssociationRequest())
             {
                 GXLogWriter.WriteLog("Authenticating", it);
                 reply = ReadDLMSPacket(it);
             }
             m_Cosem.ParseApplicationAssociationResponse(reply);
         }
     }
     catch (Exception ex)
     {
         if (Media is GXSerial && Parent.StartProtocol == StartProtocolType.IEC)
         {
             ReceiveParameters <string> p = new ReceiveParameters <string>()
             {
                 Eop      = (byte)0xA,
                 WaitTime = Parent.WaitTime * 1000
             };
             lock (Media.Synchronous)
             {
                 string data = (char)0x01 + "B0" + (char)0x03 + "\r\n";
                 Media.Send(data, null);
                 Media.Receive(p);
             }
         }
         throw ex;
     }
     GXLogWriter.WriteLog("Parsing AARE reply succeeded.");
     Parent.KeepAliveStart();
 }
 /// <summary>
 /// Read DLMS Data from the device.
 /// </summary>
 /// <remarks>
 /// If access is denied return null.
 /// </remarks>
 /// <param name="data">Data to send.</param>
 /// <returns>Received data.</returns>
 public byte[] ReadDLMSPacket(byte[] data, int tryCount)
 {
     if (data == null)
     {
         return null;
     }
     object eop = (byte)0x7E;
     //In network connection terminator is not used.
     if (m_Cosem.InterfaceType == InterfaceType.Net && Media is GXNet && !Parent.UseRemoteSerial)
     {
         eop = null;
     }
     int pos = 0;
     bool succeeded = false;
     ReceiveParameters<byte[]> p = new ReceiveParameters<byte[]>()
     {
         AllData = false,
         Eop = eop,
         Count = 5,
         WaitTime = Parent.WaitTime * 1000,
     };
     lock (Media.Synchronous)
     {
         if (data != null)
         {
             Media.Send(data, null);
         }
         while (!succeeded && pos != 3)
         {
             succeeded = Media.Receive(p);
             if (!succeeded)
             {
                 //Try to read again...
                 if (++pos != tryCount)
                 {
                     //If Eop is not set read one byte at time.
                     if (p.Eop == null)
                     {
                         p.Count = 1;
                     }
                     System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                     Media.Send(data, null);
                     continue;
                 }
                 string err = "Failed to receive reply from the device in given time.";
                 GXLogWriter.WriteLog(err, p.Reply);
                 throw new Exception(err);
             }
         }
         //Loop until whole COSEM packet is received.
         while (!m_Cosem.IsDLMSPacketComplete(p.Reply))
         {
             //If Eop is not set read one byte at time.
             if (p.Eop == null)
             {
                 p.Count = 1;
             }
             if (!Media.Receive(p))
             {
                 //Try to read again...
                 if (++pos != tryCount)
                 {
                     System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                     continue;
                 }
                 string err = "Failed to receive reply from the device in given time.";
                 GXLogWriter.WriteLog(err, p.Reply);
                 throw new Exception(err);
             }
         }
     }
     GXLogWriter.WriteLog("Received data", p.Reply);
     object errors = m_Cosem.CheckReplyErrors(data, p.Reply);
     if (errors != null)
     {
         object[,] arr = (object[,])errors;
         int error = (int)arr[0, 0];
         if (error == -1)
         {
             //If data is reply to the previous packet sent.
             //This might happens sometimes.
             if (m_Cosem.IsPreviousPacket(data, p.Reply))
             {
                 return ReadDLMSPacket(null);
             }
             else
             {
                 throw new Exception(arr[0, 1].ToString());
             }
         }
         throw new GXDLMSException(error);
     }
     return p.Reply;
 }
		private void Readout(object sender, GXPacket packet)
		{			
			GXMBusDevice device = (GXMBusDevice)GetDeviceFromSender(sender);
			IGXMedia media = (IGXMedia)device.GXClient.Media;

			bool isSerial = device.GXClient.MediaType == "Serial";
			if (isSerial)
			{
				((Gurux.Serial.GXSerial)media).BaudRate = 2400;
				((Gurux.Serial.GXSerial)media).DataBits = 8;
				((Gurux.Serial.GXSerial)media).Parity = System.IO.Ports.Parity.Even;
				((Gurux.Serial.GXSerial)media).StopBits = System.IO.Ports.StopBits.One;
			}


			List<byte> buff = new List<byte>(new byte[] {0x10, 0x40, device.DeviceAddress});
			buff.Add(CountShortFrameChecksum(buff.ToArray()));
			buff.Add(0x16);

			ReceiveParameters<byte[]> recParams = new ReceiveParameters<byte[]>();			
			lock (media.Synchronous)
			{
				recParams.AllData = true;
				recParams.Count = 1;
				recParams.Peek = false;
				recParams.Eop = null;
				recParams.Reply = null;
				recParams.WaitTime = device.WaitTime;

				media.Send(buff.ToArray(), null);
				if (!media.Receive(recParams))
				{
					throw new Exception("Handshake timeout.");
				}
			}
			System.Threading.Thread.Sleep(2000);

			if (!(recParams.Reply.Length > 0 && recParams.Reply[0] == 0xE5))
			{
				throw new Exception("Invalid handshake response.");
			}

			packet.Bop = (byte)0x10;
			packet.Eop = (byte)0x16;
			packet.ChecksumSettings.Position = -2;
            packet.ChecksumSettings.Type = ChecksumType.Sum8Bit;
			packet.ChecksumSettings.Start = 1;
			packet.ChecksumSettings.Count = -2;
			packet.AppendData((byte)0x5B);
			packet.AppendData(device.DeviceAddress);

			m_PreviousFCB = -1;
		}
        public override void ImportFromDevice(Control[] addinPages, GXDevice device, Gurux.Common.IGXMedia media)
        {            			
			media.Eop = device.GXClient.Eop;			
            GXDLT645Device dev = device as GXDLT645Device;
            dev.Parser.IgnoreFrame = false;
            Dictionary<ulong, object> items = GXDLT645Property.ReadDataID();
            GXCategory cat = device.Categories.Find("Default");
            if (cat == null)
            {
                cat = new GXCategory("Default");
                device.Categories.Add(cat);
            }
            media.Open();
            int count = 0;
            foreach (var it in items)
            {
                Progress(++count, items.Count);
                byte[] data = dev.Parser.ReadValue(it.Key);
                lock (media.Synchronous)
                {					
                    media.Send(data, null);
                    ReceiveParameters<byte[]> p = new ReceiveParameters<byte[]>()
                    {
                        Eop = media.Eop,
                        WaitTime = device.WaitTime
                    };
                    bool compleate = false;
                    try
                    {
                        while (!(compleate = dev.Parser.IsPacketComplete(it.Key, p.Reply)))
                        {
                            if (!media.Receive<byte[]>(p))
                            {
                                break;
                            }
                        }
                    }
                    catch (Exception ex)
                    {
                        Trace(ex.Message + Environment.NewLine);
                    }
                    // If data is not received or error has occurred.
                    if (!compleate || dev.Parser.IsError(p.Reply))
                    {
                        continue;
                    }
                    GXDLT645Data d = it.Value as GXDLT645Data;
                    if (d != null)
                    {
                        Trace(it.Key + " " + d.Name + Environment.NewLine);
                        cat.Properties.Add(new GXDLT645Property(it.Key, d.Name, d.Type, d.Access));
                    }
                    else
                    {
                        GXDLT645TableTemplate t = it.Value as GXDLT645TableTemplate;
                        Trace(it.Key + " " + t.Name + Environment.NewLine);
                        GXDLT645Table table = new GXDLT645Table();
                        table.Name = t.Name;
                        table.DataID = it.Key;
                        foreach (GXDLT645Data col in t.Columns)
                        {
                            table.Columns.Add(new GXDLT645Property(it.Key, col.Name, col.Type, col.Access));
                        }
                        device.Tables.Add(table);
                    }
                }
            }            
        }       
Esempio n. 38
0
        private void StartWithIec()
        {
            //Query device information.
            GXSerial serial = Media as GXSerial;

            if (serial == null)
            {
                return;
            }
            if (UseIec)
            {
                serial.BaudRate = 300;
                serial.DataBits = 7;
                serial.Parity   = System.IO.Ports.Parity.Even;
                serial.StopBits = System.IO.Ports.StopBits.One;
            }
            else
            {
                serial.BaudRate = 9600;
                serial.DataBits = 8;
                serial.Parity   = System.IO.Ports.Parity.None;
                serial.StopBits = System.IO.Ports.StopBits.One;
            }

            byte   Terminator = (byte)0x0A;
            string data       = "/?!\r\n";

            if (Trace > TraceLevel.Info)
            {
                Console.WriteLine("IEC sending:" + data);
            }
            ReceiveParameters <string> p = new ReceiveParameters <string>()
            {
                Eop      = Terminator,
                WaitTime = WaitTime
            };

            lock (Media.Synchronous)
            {
                WriteTrace("<- " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(ASCIIEncoding.ASCII.GetBytes(data), true));
                Media.Send(data, null);
                if (!Media.Receive(p))
                {
                    //Try to move away from mode E.
                    try
                    {
                        GXReplyData reply = new GXReplyData();
                        ReadDLMSPacket(Client.DisconnectRequest(), reply);
                    }
                    catch (Exception)
                    {
                    }
                    data = (char)0x01 + "B0" + (char)0x03;
                    Media.Send(data, null);
                    p.Count = 1;
                    if (!Media.Receive(p))
                    {
                    }
                    data = "Failed to receive reply from the device in given time.";
                    Console.WriteLine(data);
                    throw new Exception(data);
                }
                WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(ASCIIEncoding.ASCII.GetBytes(p.Reply), true));
                //If echo is used.
                if (p.Reply == data)
                {
                    p.Reply = null;
                    if (!Media.Receive(p))
                    {
                        //Try to move away from mode E.
                        GXReplyData reply = new GXReplyData();
                        ReadDLMSPacket(Client.DisconnectRequest(), reply);
                        if (serial != null)
                        {
                            data = (char)0x01 + "B0" + (char)0x03;
                            Media.Send(data, null);
                            p.Count = 1;
                            Media.Receive(p);
                            serial.BaudRate = 9600;
                            data            = (char)0x01 + "B0" + (char)0x03 + "\r\n";
                            Media.Send(data, null);
                            p.Count = 1;
                            Media.Receive(p);
                        }

                        data = "Failed to receive reply from the device in given time.";
                        Console.WriteLine(data);
                        throw new Exception(data);
                    }
                    WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(ASCIIEncoding.ASCII.GetBytes(p.Reply), true));
                }
            }
            Console.WriteLine("IEC received: " + p.Reply);
            if (p.Reply[0] != '/')
            {
                p.WaitTime = 100;
                Media.Receive(p);
                throw new Exception("Invalid responce.");
            }
            string manufactureID = p.Reply.Substring(1, 3);
            char   baudrate      = p.Reply[4];
            int    BaudRate      = 0;

            switch (baudrate)
            {
            case '0':
                BaudRate = 300;
                break;

            case '1':
                BaudRate = 600;
                break;

            case '2':
                BaudRate = 1200;
                break;

            case '3':
                BaudRate = 2400;
                break;

            case '4':
                BaudRate = 4800;
                break;

            case '5':
                BaudRate = 9600;
                break;

            case '6':
                BaudRate = 19200;
                break;

            default:
                throw new Exception("Unknown baud rate.");
            }
            Console.WriteLine("BaudRate is : " + BaudRate.ToString());
            //Send ACK
            //Send Protocol control character
            byte controlCharacter = (byte)'2';     // "2" HDLC protocol procedure (Mode E)
                                                   //Send Baudrate character
                                                   //Mode control character
            byte ModeControlCharacter = (byte)'2'; //"2" //(HDLC protocol procedure) (Binary mode)

            //Set mode E.
            byte[] arr = new byte[] { 0x06, controlCharacter, (byte)baudrate, ModeControlCharacter, 13, 10 };
            Console.WriteLine("Moving to mode E.", arr);
            lock (Media.Synchronous)
            {
                WriteTrace("<- " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(arr, true));
                Media.Send(arr, null);
                p.Reply = null;

                p.WaitTime = 2000;
                //Note! All meters do not echo this.
                Media.Receive(p);
                if (p.Reply != null)
                {
                    WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(ASCIIEncoding.ASCII.GetBytes(p.Reply), true));
                    Console.WriteLine("Received: " + p.Reply);
                }
                if (serial != null)
                {
                    Media.Close();
                    serial.BaudRate = BaudRate;
                    serial.DataBits = 8;
                    serial.Parity   = Parity.None;
                    serial.StopBits = StopBits.One;
                    Media.Open();
                    //Some meters need this sleep. Do not remove.
                    Thread.Sleep(1000);
                }
            }
        }
Esempio n. 39
0
 /// <summary>
 /// Read DLMS Data from the device.
 /// </summary>
 /// <param name="data">Data to send.</param>
 /// <returns>Received data.</returns>
 public void ReadDLMSPacket(byte[] data, GXReplyData reply)
 {
     if (data == null)
     {
         return;
     }
     reply.Error = 0;
     object eop = (byte)0x7E;
     //In network connection terminator is not used.
     if (Client.InterfaceType == InterfaceType.WRAPPER && Media is GXNet)
     {
         eop = null;
     }
     int pos = 0;
     bool succeeded = false;
     ReceiveParameters<byte[]> p = new ReceiveParameters<byte[]>()
     {
         Eop = eop,
         Count = 5,
         WaitTime = WaitTime,
     };
     lock (Media.Synchronous)
     {
         while (!succeeded && pos != 3)
         {
             WriteTrace("<- " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(data, true));
             Media.Send(data, null);
             succeeded = Media.Receive(p);
             if (!succeeded)
             {
                 //If Eop is not set read one byte at time.
                 if (p.Eop == null)
                 {
                     p.Count = 1;
                 }
                 //Try to read again...
                 if (++pos != 3)
                 {
                     System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                     continue;
                 }
                 throw new Exception("Failed to receive reply from the device in given time.");
             }
         }
         try
         {
             //Loop until whole COSEM packet is received.
             while (!Client.GetData(p.Reply, reply))
             {
                 //If Eop is not set read one byte at time.
                 if (p.Eop == null)
                 {
                     p.Count = 1;
                 }
                 while (!Media.Receive(p))
                 {
                     //If echo.
                     if (p.Reply.Length == data.Length)
                     {
                         Media.Send(data, null);
                     }
                     //Try to read again...
                     if (++pos != 3)
                     {
                         System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                         continue;
                     }
                     throw new Exception("Failed to receive reply from the device in given time.");
                 }
             }
         }
         catch (Exception ex)
         {
             WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(p.Reply, true));
             throw ex;
         }
     }
     WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(p.Reply, true));
     if (reply.Error != 0)
     {
         if (reply.Error == (short)ErrorCode.Rejected)
         {
             Thread.Sleep(1000);
             ReadDLMSPacket(data, reply);
         }
         else
         {
             throw new GXDLMSException(reply.Error);
         }
     }
 }
 /// <summary>
 /// Read DLMS Data from the device.
 /// </summary>
 /// <remarks>
 /// If access is denied return null.
 /// </remarks>
 /// <param name="data">Data to send.</param>
 /// <returns>Received data.</returns>
 public void ReadDLMSPacket(byte[] data, int tryCount, GXReplyData reply)
 {
     if (data == null)
     {
         return;
     }
     object eop = (byte)0x7E;
     //In network connection terminator is not used.
     if (client.InterfaceType == InterfaceType.WRAPPER && media is GXNet && !parent.UseRemoteSerial)
     {
         eop = null;
     }
     int pos = 0;
     bool succeeded = false;
     ReceiveParameters<byte[]> p = new ReceiveParameters<byte[]>()
     {
         AllData = false,
         Eop = eop,
         Count = 5,
         WaitTime = parent.WaitTime * 1000,
     };
     lock (media.Synchronous)
     {
         if (data != null)
         {
             media.Send(data, null);
         }
         while (!succeeded && pos != 3)
         {
             succeeded = media.Receive(p);
             if (!succeeded)
             {
                 //Try to read again...
                 if (++pos != tryCount)
                 {
                     //If Eop is not set read one byte at time.
                     if (p.Eop == null)
                     {
                         p.Count = 1;
                     }
                     System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                     media.Send(data, null);
                     continue;
                 }
                 string err = "Failed to receive reply from the device in given time.";
                 GXLogWriter.WriteLog(err, p.Reply);
                 throw new Exception(err);
             }
         }
         try
         {
             //Loop until whole COSEM packet is received.
             while (!client.GetData(p.Reply, reply))
             {
                 //If Eop is not set read one byte at time.
                 if (p.Eop == null)
                 {
                     p.Count = 1;
                 }
                 if (!media.Receive(p))
                 {
                     //Try to read again...
                     if (++pos != tryCount)
                     {
                         System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                         continue;
                     }
                     string err = "Failed to receive reply from the device in given time.";
                     GXLogWriter.WriteLog(err, p.Reply);
                     throw new Exception(err);
                 }
             }
         }
         catch (Exception ex)
         {
             GXLogWriter.WriteLog("Received data", p.Reply);
             throw ex;
         }
     }
     GXLogWriter.WriteLog("Received data", p.Reply);
     if (reply.Error != 0)
     {
         if (reply.Error == (int)ErrorCode.Rejected)
         {
             Thread.Sleep(1000);
             ReadDLMSPacket(data, tryCount, reply);
         }
         else
         {
             throw new GXDLMSException(reply.Error);
         }
     }
 }
        public void InitializeConnection()
        {
            if (!string.IsNullOrEmpty(parent.Manufacturer))
            {
                UpdateManufactureSettings(parent.Manufacturer);
            }
            if (media is GXSerial)
            {
                GXLogWriter.WriteLog("Initializing serial connection.");
                InitSerial();
                connectionStartTime = DateTime.Now;
            }
            else if (media is GXNet)
            {
                GXLogWriter.WriteLog("Initializing Network connection.");
                InitNet();
                //Some Electricity meters need some time before first message can be send.
                System.Threading.Thread.Sleep(500);
            }
            else if (media is Gurux.Terminal.GXTerminal)
            {
                GXLogWriter.WriteLog("Initializing Terminal connection.");
                InitTerminal();
            }
            else
            {
                media.Open();
            }
            try
            {
                GXReplyData reply = new GXReplyData();
                byte[]      data;
                client.Limits.WindowSizeRX = parent.WindowSizeRX;
                client.Limits.WindowSizeTX = parent.WindowSizeTX;
                client.Limits.MaxInfoRX    = parent.MaxInfoRX;
                client.Limits.MaxInfoTX    = parent.MaxInfoTX;
                client.MaxReceivePDUSize   = parent.PduSize;
                client.Priority            = parent.Priority;
                client.ServiceClass        = parent.ServiceClass;

                data = SNRMRequest();
                if (data != null)
                {
                    ReadDataBlock(data, "Send SNRM request.", reply);
                    GXLogWriter.WriteLog("Parsing UA reply succeeded.");
                    //Has server accepted client.
                    ParseUAResponse(reply.Data);
                }
                //Generate AARQ request.
                //Split requests to multiple packets if needed.
                //If password is used all data might not fit to one packet.
                reply.Clear();
                ReadDataBlock(AARQRequest(), "Send AARQ request.", reply);
                try
                {
                    //Parse reply.
                    ParseAAREResponse(reply.Data);
                    GXLogWriter.WriteLog("Parsing AARE reply succeeded.");
                }
                catch (Exception Ex)
                {
                    reply.Clear();
                    ReadDLMSPacket(DisconnectRequest(), 1, reply);
                    throw Ex;
                }
                //If authentication is required.
                if (client.Authentication > Authentication.Low)
                {
                    foreach (byte[] it in client.GetApplicationAssociationRequest())
                    {
                        GXLogWriter.WriteLog("Authenticating", it);
                        reply.Clear();
                        ReadDLMSPacket(it, reply);
                    }
                    client.ParseApplicationAssociationResponse(reply.Data);
                }
            }
            catch (Exception ex)
            {
                if (media is GXSerial && parent.StartProtocol == StartProtocolType.IEC)
                {
                    ReceiveParameters <string> p = new ReceiveParameters <string>()
                    {
                        Eop      = (byte)0xA,
                        WaitTime = parent.WaitTime * 1000
                    };
                    lock (media.Synchronous)
                    {
                        string data = (char)0x01 + "B0" + (char)0x03 + "\r\n";
                        media.Send(data, null);
                        media.Receive(p);
                    }
                }
                throw ex;
            }
            parent.KeepAliveStart();
        }
Esempio n. 42
0
        /// <summary>
        /// Read DLMS Data from the device.
        /// </summary>
        /// <param name="data">Data to send.</param>
        /// <returns>Received data.</returns>
        public void ReadDLMSPacket(byte[] data, GXReplyData reply)
        {
            if (data == null)
            {
                return;
            }
            reply.Error = 0;
            object eop = (byte)0x7E;

            //In network connection terminator is not used.
            if (Client.InterfaceType == InterfaceType.WRAPPER && Media is GXNet)
            {
                eop = null;
            }
            int  pos       = 0;
            bool succeeded = false;
            ReceiveParameters <byte[]> p = new ReceiveParameters <byte[]>()
            {
                Eop      = eop,
                Count    = 5,
                WaitTime = WaitTime,
            };

            lock (Media.Synchronous)
            {
                while (!succeeded && pos != 3)
                {
                    WriteTrace("<- " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(data, true));
                    Media.Send(data, null);
                    succeeded = Media.Receive(p);
                    if (!succeeded)
                    {
                        //If Eop is not set read one byte at time.
                        if (p.Eop == null)
                        {
                            p.Count = 1;
                        }
                        //Try to read again...
                        if (++pos != 3)
                        {
                            System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                            continue;
                        }
                        throw new Exception("Failed to receive reply from the device in given time.");
                    }
                }
                try
                {
                    //Loop until whole COSEM packet is received.
                    while (!Client.GetData(p.Reply, reply))
                    {
                        //If Eop is not set read one byte at time.
                        if (p.Eop == null)
                        {
                            p.Count = 1;
                        }
                        while (!Media.Receive(p))
                        {
                            //If echo.
                            if (p.Reply.Length == data.Length)
                            {
                                Media.Send(data, null);
                            }
                            //Try to read again...
                            if (++pos != 3)
                            {
                                System.Diagnostics.Debug.WriteLine("Data send failed. Try to resend " + pos.ToString() + "/3");
                                continue;
                            }
                            throw new Exception("Failed to receive reply from the device in given time.");
                        }
                    }
                }
                catch (Exception ex)
                {
                    WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(p.Reply, true));
                    throw ex;
                }
            }
            WriteTrace("-> " + DateTime.Now.ToLongTimeString() + "\t" + GXCommon.ToHex(p.Reply, true));
            if (reply.Error != 0)
            {
                if (reply.Error == (short)ErrorCode.Rejected)
                {
                    Thread.Sleep(1000);
                    ReadDLMSPacket(data, reply);
                }
                else
                {
                    throw new GXDLMSException(reply.Error);
                }
            }
        }
Esempio n. 43
0
        void InitSerial()
        {
            GXSerial serial     = Media as GXSerial;
            byte     Terminator = (byte)0x0A;

            if (serial != null && InitializeIEC)
            {
                serial.BaudRate = 300;
                serial.DataBits = 7;
                serial.Parity   = Parity.Even;
                serial.StopBits = StopBits.One;
            }
            Media.Open();
            //Query device information.
            if (Media != null && InitializeIEC)
            {
                string data = "/?001!\r\n";
                if (Trace)
                {
                    Console.WriteLine("HDLC sending:" + data);
                }
                ReceiveParameters <string> p = new ReceiveParameters <string>()
                {
                    Eop      = Terminator,
                    WaitTime = WaitTime
                };
                lock (Media.Synchronous)
                {
                    Media.Send(data, null);
                    if (!Media.Receive(p))
                    {
                        //Try to move away from mode E.
                        throw new Exception("Failed to receive reply from the device in given time.");
                    }
                    //If echo is used.
                    if (p.Reply == data)
                    {
                        p.Reply = null;
                        if (!Media.Receive(p))
                        {
                            //Try to move away from mode E.
                            throw new Exception("Failed to receive reply from the device in given time.");
                        }
                    }
                }
                if (Trace)
                {
                    Console.WriteLine("HDLC received: " + p.Reply);
                }
                if (p.Reply[0] != '/')
                {
                    p.WaitTime = 100;
                    Media.Receive(p);
                    throw new Exception("Invalid responce.");
                }
                string manufactureID = p.Reply.Substring(1, 3);
                //UpdateManufactureSettings(manufactureID);
                char baudrate = p.Reply[4];
                int  BaudRate = 0;
                switch (baudrate)
                {
                case '0':
                    BaudRate = 300;
                    break;

                case '1':
                    BaudRate = 600;
                    break;

                case '2':
                    BaudRate = 1200;
                    break;

                case '3':
                    BaudRate = 2400;
                    break;

                case '4':
                    BaudRate = 4800;
                    break;

                case '5':
                    BaudRate = 9600;
                    break;

                case '6':
                    BaudRate = 19200;
                    break;

                default:
                    throw new Exception("Unknown baud rate.");
                }
                Console.WriteLine("BaudRate is :", BaudRate.ToString());
                //Send ACK
                //Send Protocol control character
                byte controlCharacter = (byte)'2';// "2" HDLC protocol procedure (Mode E)
                //Send Baudrate character
                //Mode control character
                byte ModeControlCharacter = (byte)'2';//"2" //(HDLC protocol procedure) (Binary mode)
                //Set mode E.
                byte[] arr = new byte[] { 0x06, controlCharacter, (byte)baudrate, ModeControlCharacter, 13, 10 };
                if (Trace)
                {
                    Console.WriteLine("Moving to mode E", BitConverter.ToString(arr));
                }
                lock (Media.Synchronous)
                {
                    Media.Send(arr, null);
                    p.Reply    = null;
                    p.WaitTime = 500;
                    if (!Media.Receive(p))
                    {
                        //Try to move away from mode E.
                        this.ReadDLMSPacket(m_Parser.DisconnectRequest());
                        throw new Exception("Failed to receive reply from the device in given time.");
                    }
                }
                if (serial != null)
                {
                    serial.BaudRate = BaudRate;
                    serial.DataBits = 8;
                    serial.Parity   = Parity.None;
                    serial.StopBits = StopBits.One;
                }
            }
        }