Пример #1
0
        /// <summary>
        /// Generates Push message.
        /// </summary>
        /// <param name="objects">List of objects and attribute indexes to push.</param>
        /// <returns>Generated push message(s).</returns>
        public byte[][] GeneratePushMessage(DateTime date, List <KeyValuePair <GXDLMSObject, int> > objects)
        {
            DataType dt;
            object   value;

            if (objects == null)
            {
                throw new ArgumentNullException("objects");
            }
            GXByteBuffer buff = new GXByteBuffer();

            //Add data
            buff.SetUInt8(DataType.Structure);
            GXCommon.SetObjectCount(objects.Count, buff);
            foreach (KeyValuePair <GXDLMSObject, int> it in objects)
            {
                dt    = it.Key.GetDataType(it.Value);
                value = (it.Key as IGXDLMSBase).GetValue(Settings, it.Value, 0, null);
                if (dt == DataType.None && value != null)
                {
                    dt = GXCommon.GetValueType(value);
                }
                GXCommon.SetData(buff, dt, value);
            }
            List <byte[][]> list = GXDLMS.SplitPdu(Settings, Command.Push, 0, buff, ErrorCode.Ok, DateTime.MinValue);
            List <byte[]>   arr  = new List <byte[]>();

            foreach (byte[][] it in list)
            {
                arr.AddRange(it);
            }
            return(arr.ToArray());
        }
Пример #2
0
 object IGXDLMSBase.GetValue(int index, int selector, object parameters)
 {
     if (index == 1)
     {
         return(this.LogicalName);
     }
     if (index == 2)
     {
         int         cnt  = Scripts.Count;
         List <byte> data = new List <byte>();
         data.Add((byte)DataType.Array);
         //Add count
         GXCommon.SetObjectCount(cnt, data);
         if (cnt != 0)
         {
             foreach (var it in Scripts)
             {
                 data.Add((byte)DataType.Structure);
                 data.Add(2);                                                                 //Count
                 GXCommon.SetData(data, DataType.UInt16, it.Key);                             //Script_identifier:
                 data.Add((byte)DataType.Array);
                 data.Add(5);                                                                 //Count
                 GXDLMSScriptAction tmp = it.Value;
                 GXCommon.SetData(data, DataType.Enum, tmp.Type);                             //service_id
                 GXCommon.SetData(data, DataType.UInt16, tmp.ObjectType);                     //class_id
                 GXCommon.SetData(data, DataType.OctetString, tmp.LogicalName);               //logical_name
                 GXCommon.SetData(data, DataType.Int8, tmp.Index);                            //index
                 GXCommon.SetData(data, GXCommon.GetValueType(tmp.Parameter), tmp.Parameter); //parameter
             }
         }
         return(data.ToArray());
     }
     throw new ArgumentException("GetValue failed. Invalid attribute index.");
 }
Пример #3
0
        object IGXDLMSBase.GetValue(GXDLMSSettings settings, ValueEventArgs e)
        {
            if (e.Index == 1)
            {
                return(GXCommon.LogicalNameToBytes(LogicalName));
            }
            if (e.Index == 2)
            {
                int          cnt  = Scripts.Count;
                GXByteBuffer data = new GXByteBuffer();
                data.SetUInt8((byte)DataType.Array);
                //Add count
                GXCommon.SetObjectCount(cnt, data);
                foreach (GXDLMSScript it in Scripts)
                {
                    data.SetUInt8((byte)DataType.Structure);
                    data.SetUInt8(2);                                         //Count
                    GXCommon.SetData(settings, data, DataType.UInt16, it.Id); //Script_identifier:
                    data.SetUInt8((byte)DataType.Array);
                    data.SetUInt8((byte)it.Actions.Count);                    //Count
                    foreach (GXDLMSScriptAction a in it.Actions)
                    {
                        data.SetUInt8((byte)DataType.Structure);
                        //Count
                        data.SetUInt8(5);
                        //service_id
                        GXCommon.SetData(settings, data, DataType.Enum, a.Type);
                        if (a.Target == null)
                        {
#pragma warning disable CS0618
                            //class_id
                            GXCommon.SetData(settings, data, DataType.UInt16, a.ObjectType);
                            //logical_name
                            GXCommon.SetData(settings, data, DataType.OctetString, GXCommon.LogicalNameToBytes(a.LogicalName));
#pragma warning restore CS0618
                        }
                        else
                        {
                            //class_id
                            GXCommon.SetData(settings, data, DataType.UInt16, a.Target.ObjectType);
                            //logical_name
                            GXCommon.SetData(settings, data, DataType.OctetString, GXCommon.LogicalNameToBytes(a.Target.LogicalName));
                        }
                        //index
                        GXCommon.SetData(settings, data, DataType.Int8, a.Index);
                        //parameter
                        DataType tp = a.ParameterDataType;
                        if (tp == DataType.None)
                        {
                            tp = GXCommon.GetValueType(a.Parameter);
                        }
                        GXCommon.SetData(settings, data, tp, a.Parameter);
                    }
                }
                return(data.Array());
            }
            e.Error = ErrorCode.ReadWriteDenied;
            return(null);
        }
Пример #4
0
        /// <summary>
        /// Add value of COSEM object to byte buffer.
        /// </summary>
        /// <param name="obj">COSEM object.</param>
        /// <param name="index">Attribute index.</param>
        /// <param name="buff">Byte buffer.</param>
        /// <remarks>
        /// AddData method can be used with GetDataNotificationMessage -method.
        /// DLMS spesification do not specify the structure of Data-Notification body.
        /// So each manufacture can sent different data.
        /// </remarks>
        internal static void AddData(GXDLMSSettings settings, GXDLMSObject obj, int index, GXByteBuffer buff)
        {
            DataType dt;
            object   value = (obj as IGXDLMSBase).GetValue(settings, new ValueEventArgs(settings, obj, index, 0, null));

            dt = obj.GetDataType(index);
            if (dt == DataType.None && value != null)
            {
                dt = GXCommon.GetValueType(value);
            }
            GXCommon.SetData(settings, buff, dt, value);
        }
Пример #5
0
        /// <summary>
        /// Get data for Read command.
        /// </summary>
        /// <param name="list">received objects.</param>
        /// <param name="data">Data as byte array.</param>
        /// <returns>Response type.</returns>
        private static SingleReadResponse GetReadData(GXDLMSSettings settings, ValueEventArgs[] list, GXByteBuffer data)
        {
            object             value;
            bool               first = true;
            SingleReadResponse type  = SingleReadResponse.Data;

            foreach (ValueEventArgs e in list)
            {
                if (e.Handled)
                {
                    value = e.Value;
                }
                else
                {
                    //If action.
                    if (e.action)
                    {
                        value = ((IGXDLMSBase)e.Target).Invoke(settings, e);
                    }
                    else
                    {
                        value = (e.Target as IGXDLMSBase).GetValue(settings, e);
                    }
                }
                if (e.Error == 0)
                {
                    if (!first && list.Length != 1)
                    {
                        data.SetUInt8(SingleReadResponse.Data);
                    }
                    //If action.
                    if (e.action)
                    {
                        GXCommon.SetData(settings, data, GXCommon.GetValueType(value), value);
                    }
                    else
                    {
                        GXDLMS.AppendData(settings, e.Target, e.Index, data, value);
                    }
                }
                else
                {
                    if (!first && list.Length != 1)
                    {
                        data.SetUInt8(SingleReadResponse.DataAccessError);
                    }
                    data.SetUInt8(e.Error);
                    type = SingleReadResponse.DataAccessError;
                }
                first = false;
            }
            return(type);
        }
Пример #6
0
        /// <summary>
        /// Add value of COSEM object to byte buffer.
        /// </summary>
        /// <param name="obj">COSEM object.</param>
        /// <param name="index">Attribute index.</param>
        /// <param name="buff">Byte buffer.</param>
        /// <remarks>
        /// AddData method can be used with GetDataNotificationMessage -method.
        /// DLMS spesification do not specify the structure of Data-Notification body.
        /// So each manufacture can sent different data.
        /// </remarks>
        /// <seealso cref="GetDataNotificationMessage"/>
        public void AddData(GXDLMSObject obj, int index, GXByteBuffer buff)
        {
            DataType dt;
            object   value = (obj as IGXDLMSBase).GetValue(Settings, index, 0, null);

            dt = obj.GetDataType(index);
            if (dt == DataType.None && value != null)
            {
                dt = GXCommon.GetValueType(value);
            }
            GXCommon.SetData(buff, dt, value);
        }
Пример #7
0
 object IGXDLMSBase.GetValue(GXDLMSSettings settings, ValueEventArgs e)
 {
     if (e.Index == 1)
     {
         return(this.LogicalName);
     }
     if (e.Index == 2)
     {
         return(MaxHops);
     }
     if (e.Index == 3)
     {
         return(WeakLqiValue);
     }
     if (e.Index == 4)
     {
         return(SecurityLevel);
     }
     if (e.Index == 5)
     {
         GXByteBuffer bb = new GXByteBuffer();
         bb.SetUInt8((byte)DataType.Array);
         if (PrefixTable == null)
         {
             bb.SetUInt8(0);
         }
         else
         {
             GXCommon.SetObjectCount(PrefixTable.Length, bb);
             foreach (var it in PrefixTable)
             {
                 GXCommon.SetData(settings, bb, GXCommon.GetValueType(it), it);
             }
         }
         return(bb.Array());
     }
     if (e.Index == 6)
     {
         GXByteBuffer bb = new GXByteBuffer();
         bb.SetUInt8((byte)DataType.Array);
         if (RoutingConfiguration == null)
         {
             bb.SetUInt8(0);
         }
         else
         {
             GXCommon.SetObjectCount(RoutingConfiguration.Count, bb);
             foreach (GXDLMSRoutingConfiguration it in RoutingConfiguration)
             {
                 bb.SetUInt8((byte)DataType.Structure);
                 bb.SetUInt8(14);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.NetTraversalTime);
                 GXCommon.SetData(settings, bb, DataType.UInt16, it.RoutingTableEntryTtl);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.Kr);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.Km);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.Kc);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.Kq);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.Kh);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.Krt);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.RreqRetries);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.RreqRerrWait);
                 GXCommon.SetData(settings, bb, DataType.UInt16, it.BlacklistTableEntryTtl);
                 GXCommon.SetData(settings, bb, DataType.Boolean, it.UnicastRreqGenEnable);
                 GXCommon.SetData(settings, bb, DataType.Boolean, it.RlcEnabled);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.AddRevLinkCost);
             }
         }
         return(bb.Array());
     }
     if (e.Index == 7)
     {
         return(BroadcastLogTableEntryTtl);
     }
     if (e.Index == 8)
     {
         GXByteBuffer bb = new GXByteBuffer();
         bb.SetUInt8((byte)DataType.Array);
         if (RoutingTable == null)
         {
             bb.SetUInt8(0);
         }
         else
         {
             GXCommon.SetObjectCount(RoutingTable.Count, bb);
             foreach (GXDLMSRoutingTable it in RoutingTable)
             {
                 bb.SetUInt8((byte)DataType.Structure);
                 bb.SetUInt8(6);
                 GXCommon.SetData(settings, bb, DataType.UInt16, it.DestinationAddress);
                 GXCommon.SetData(settings, bb, DataType.UInt16, it.NextHopAddress);
                 GXCommon.SetData(settings, bb, DataType.UInt16, it.RouteCost);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.HopCount);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.WeakLinkCount);
                 GXCommon.SetData(settings, bb, DataType.UInt16, it.ValidTime);
             }
         }
         return(bb.Array());
     }
     if (e.Index == 9)
     {
         GXByteBuffer bb = new GXByteBuffer();
         bb.SetUInt8((byte)DataType.Array);
         if (ContextInformationTable == null)
         {
             bb.SetUInt8(0);
         }
         else
         {
             GXCommon.SetObjectCount(ContextInformationTable.Count, bb);
             foreach (GXDLMSContextInformationTable it in ContextInformationTable)
             {
                 bb.SetUInt8((byte)DataType.Structure);
                 bb.SetUInt8(5);
                 GXCommon.SetData(settings, bb, DataType.BitString, it.CID);
                 if (it.Context == null)
                 {
                     GXCommon.SetData(settings, bb, DataType.UInt8, 0);
                 }
                 else
                 {
                     GXCommon.SetData(settings, bb, DataType.UInt8, it.Context.Length);
                 }
                 GXCommon.SetData(settings, bb, DataType.OctetString, it.Context);
                 GXCommon.SetData(settings, bb, DataType.Boolean, it.Compression);
                 GXCommon.SetData(settings, bb, DataType.UInt16, it.ValidLifetime);
             }
         }
         return(bb.Array());
     }
     if (e.Index == 10)
     {
         GXByteBuffer bb = new GXByteBuffer();
         bb.SetUInt8((byte)DataType.Array);
         if (BlacklistTable == null)
         {
             bb.SetUInt8(0);
         }
         else
         {
             GXCommon.SetObjectCount(BlacklistTable.Count, bb);
             foreach (var it in BlacklistTable)
             {
                 bb.SetUInt8((byte)DataType.Structure);
                 bb.SetUInt8(2);
                 GXCommon.SetData(settings, bb, DataType.UInt16, it.Key);
                 GXCommon.SetData(settings, bb, DataType.UInt16, it.Value);
             }
         }
         return(bb.Array());
     }
     if (e.Index == 11)
     {
         GXByteBuffer bb = new GXByteBuffer();
         bb.SetUInt8((byte)DataType.Array);
         if (BroadcastLogTable == null)
         {
             bb.SetUInt8(0);
         }
         else
         {
             GXCommon.SetObjectCount(BroadcastLogTable.Count, bb);
             foreach (GXDLMSBroadcastLogTable it in BroadcastLogTable)
             {
                 bb.SetUInt8((byte)DataType.Structure);
                 bb.SetUInt8(3);
                 GXCommon.SetData(settings, bb, DataType.UInt16, it.SourceAddress);
                 GXCommon.SetData(settings, bb, DataType.UInt8, it.SequenceNumber);
                 GXCommon.SetData(settings, bb, DataType.UInt16, it.ValidTime);
             }
         }
         return(bb.Array());
     }
     if (e.Index == 12)
     {
         GXByteBuffer bb = new GXByteBuffer();
         bb.SetUInt8((byte)DataType.Array);
         if (GroupTable == null)
         {
             bb.SetUInt8(0);
         }
         else
         {
             GXCommon.SetObjectCount(GroupTable.Length, bb);
             foreach (UInt16 it in GroupTable)
             {
                 GXCommon.SetData(settings, bb, DataType.UInt16, it);
             }
         }
         return(bb.Array());
     }
     if (e.Index == 13)
     {
         return(MaxJoinWaitTime);
     }
     if (e.Index == 14)
     {
         return(PathDiscoveryTime);
     }
     if (e.Index == 15)
     {
         return(ActiveKeyIndex);
     }
     if (e.Index == 16)
     {
         return(MetricType);
     }
     if (e.Index == 17)
     {
         return(CoordShortAddress);
     }
     if (e.Index == 18)
     {
         return(DisableDefaultRouting);
     }
     if (e.Index == 19)
     {
         return(DeviceType);
     }
     e.Error = ErrorCode.ReadWriteDenied;
     return(null);
 }
Пример #8
0
 object IGXDLMSBase.GetValue(GXDLMSSettings settings, int index, int selector, object parameters)
 {
     if (index == 1)
     {
         return(this.LogicalName);
     }
     if (index == 2)
     {
         return(PHYReference);
     }
     if (index == 3)
     {
         GXByteBuffer data = new GXByteBuffer();
         data.SetUInt8((byte)DataType.Array);
         if (LCPOptions == null)
         {
             data.SetUInt8(0);
         }
         else
         {
             data.SetUInt8((byte)IPCPOptions.Length);
             foreach (GXDLMSPppSetupLcpOption it in LCPOptions)
             {
                 data.SetUInt8((byte)DataType.Structure);
                 data.SetUInt8((byte)3);
                 GXCommon.SetData(data, DataType.UInt8, it.Type);
                 GXCommon.SetData(data, DataType.UInt8, it.Length);
                 GXCommon.SetData(data, GXCommon.GetValueType(it.Data), it.Data);
             }
         }
         return(data.Array());
     }
     if (index == 4)
     {
         GXByteBuffer data = new GXByteBuffer();
         data.SetUInt8((byte)DataType.Array);
         if (IPCPOptions == null)
         {
             data.SetUInt8(0);
         }
         else
         {
             data.SetUInt8((byte)IPCPOptions.Length);
             foreach (GXDLMSPppSetupIPCPOption it in IPCPOptions)
             {
                 data.SetUInt8((byte)DataType.Structure);
                 data.SetUInt8((byte)3);
                 GXCommon.SetData(data, DataType.UInt8, it.Type);
                 GXCommon.SetData(data, DataType.UInt8, it.Length);
                 GXCommon.SetData(data, GXCommon.GetValueType(it.Data), it.Data);
             }
         }
         return(data.Array());
     }
     else if (index == 5)
     {
         GXByteBuffer data = new GXByteBuffer();
         data.SetUInt8((byte)DataType.Structure);
         data.SetUInt8(2);
         GXCommon.SetData(data, DataType.OctetString, UserName);
         GXCommon.SetData(data, DataType.OctetString, Password);
         return(data.Array());
     }
     throw new ArgumentException("GetValue failed. Invalid attribute index.");
 }
Пример #9
0
 object IGXDLMSBase.GetValue(GXDLMSSettings settings, ValueEventArgs e)
 {
     if (e.Index == 1)
     {
         return(GXCommon.LogicalNameToBytes(LogicalName));
     }
     if (e.Index == 2)
     {
         return(GXCommon.LogicalNameToBytes(PHYReference));
     }
     if (e.Index == 3)
     {
         GXByteBuffer data = new GXByteBuffer();
         data.SetUInt8((byte)DataType.Array);
         if (LCPOptions == null)
         {
             data.SetUInt8(0);
         }
         else
         {
             data.SetUInt8((byte)LCPOptions.Length);
             foreach (GXDLMSPppSetupLcpOption it in LCPOptions)
             {
                 data.SetUInt8((byte)DataType.Structure);
                 data.SetUInt8((byte)3);
                 GXCommon.SetData(settings, data, DataType.UInt8, it.Type);
                 GXCommon.SetData(settings, data, DataType.UInt8, it.Length);
                 GXCommon.SetData(settings, data, GXCommon.GetValueType(it.Data), it.Data);
             }
         }
         return(data.Array());
     }
     if (e.Index == 4)
     {
         GXByteBuffer data = new GXByteBuffer();
         data.SetUInt8((byte)DataType.Array);
         if (IPCPOptions == null)
         {
             data.SetUInt8(0);
         }
         else
         {
             data.SetUInt8((byte)IPCPOptions.Length);
             foreach (GXDLMSPppSetupIPCPOption it in IPCPOptions)
             {
                 data.SetUInt8((byte)DataType.Structure);
                 data.SetUInt8((byte)3);
                 GXCommon.SetData(settings, data, DataType.UInt8, it.Type);
                 GXCommon.SetData(settings, data, DataType.UInt8, it.Length);
                 GXCommon.SetData(settings, data, GXCommon.GetValueType(it.Data), it.Data);
             }
         }
         return(data.Array());
     }
     else if (e.Index == 5)
     {
         GXByteBuffer data = new GXByteBuffer();
         data.SetUInt8((byte)DataType.Structure);
         data.SetUInt8(2);
         GXCommon.SetData(settings, data, DataType.OctetString, UserName);
         GXCommon.SetData(settings, data, DataType.OctetString, Password);
         return(data.Array());
     }
     e.Error = ErrorCode.ReadWriteDenied;
     return(null);
 }
Пример #10
0
 /// <summary>
 /// Get DLMS data type.
 /// </summary>
 /// <param name="value">Object</param>
 /// <returns>DLMS data type.</returns>
 static public DataType GetDLMSDataType(object value)
 {
     return(GXCommon.GetValueType(value));
 }
        ///<summary>
        /// Handle action request.
        ///</summary>
        public static void HandleMethodRequest(GXDLMSSettings settings, GXDLMSServer server, GXByteBuffer data, GXDLMSConnectionEventArgs connectionInfo, GXByteBuffer replyData, GXDLMSTranslatorStructure xml)
        {
            ErrorCode    error = ErrorCode.Ok;
            GXByteBuffer bb    = new GXByteBuffer();
            // Get type.
            ActionRequestType type = (ActionRequestType)data.GetUInt8();
            // Get invoke ID and priority.
            byte invokeId = data.GetUInt8();
            // CI
            ObjectType ci = (ObjectType)data.GetUInt16();

            byte[] ln = new byte[6];
            data.Get(ln);
            // Attribute Id
            byte id = data.GetUInt8();
            // Get parameters.
            object parameters = null;
            byte   selection  = data.GetUInt8();

            if (xml != null)
            {
                xml.AppendStartTag(Command.MethodRequest);
                if (type == ActionRequestType.Normal)
                {
                    xml.AppendStartTag(Command.MethodRequest, ActionRequestType.Normal);
                    xml.AppendLine(TranslatorTags.InvokeId, "Value", xml.IntegerToHex(invokeId, 2));
                    AppendMethodDescriptor(xml, (int)ci, ln, id);
                    if (selection != 0)
                    {
                        //MethodInvocationParameters
                        xml.AppendStartTag(TranslatorTags.MethodInvocationParameters);
                        GXDataInfo di = new GXDataInfo();
                        di.xml = xml;
                        GXCommon.GetData(settings, data, di);
                        xml.AppendEndTag(TranslatorTags.MethodInvocationParameters);
                    }
                    xml.AppendEndTag(Command.MethodRequest, ActionRequestType.Normal);
                }
                xml.AppendEndTag(Command.MethodRequest);
                return;
            }
            if (selection != 0)
            {
                GXDataInfo info = new GXDataInfo();
                parameters = GXCommon.GetData(settings, data, info);
            }

            GXDLMSObject obj = settings.Objects.FindByLN(ci, GXCommon.ToLogicalName(ln));

            if (!settings.Connected && (ci != ObjectType.AssociationLogicalName || id != 1))
            {
                replyData.Set(GXDLMSServer.GenerateConfirmedServiceError(ConfirmedServiceError.InitiateError,
                                                                         ServiceError.Service, (byte)Service.Unsupported));
                return;
            }

            if (obj == null)
            {
                obj = server.NotifyFindObject(ci, 0, GXCommon.ToLogicalName(ln));
            }
            if (obj == null)
            {
                // Device reports a undefined object.
                error = ErrorCode.UndefinedObject;
            }
            else
            {
                ValueEventArgs e = new ValueEventArgs(server, obj, id, 0, parameters);
                e.InvokeId = invokeId;
                if (server.NotifyGetMethodAccess(e) == MethodAccessMode.NoAccess)
                {
                    error = ErrorCode.ReadWriteDenied;
                }
                else
                {
                    server.NotifyAction(new ValueEventArgs[] { e });
                    byte[] actionReply;
                    if (e.Handled)
                    {
                        actionReply = (byte[])e.Value;
                    }
                    else
                    {
                        actionReply = (obj as IGXDLMSBase).Invoke(settings, e);
                        server.NotifyPostAction(new ValueEventArgs[] { e });
                    }
                    //Set default action reply if not given.
                    if (actionReply != null && e.Error == 0)
                    {
                        //Add return parameters
                        bb.SetUInt8(1);
                        //Add parameters error code.
                        bb.SetUInt8(0);
                        GXCommon.SetData(settings, bb, GXCommon.GetValueType(actionReply), actionReply);
                    }
                    else
                    {
                        error = e.Error;
                        //Add return parameters
                        bb.SetUInt8(0);
                    }
                }
                invokeId = (byte)e.InvokeId;
            }

            GXDLMSLNParameters p = new GXDLMSLNParameters(settings, invokeId, Command.MethodResponse, 1, null, bb, (byte)error);

            GXDLMS.GetLNPdu(p, replyData);
            //If High level authentication fails.
            if (!settings.Connected && obj is GXDLMSAssociationLogicalName && id == 1)
            {
                server.NotifyInvalidConnection(connectionInfo);
            }
        }
Пример #12
0
        ///
        ///<summary>Handle read request.
        /// </summary>
        ///<returns> Reply to the client. </returns>
        ///
        private byte[][] HandleReadRequest()
        {
            GXByteBuffer data = Reply.Data;
            short        type;
            object       value = null;
            GXByteBuffer bb    = new GXByteBuffer();
            int          cnt   = GXCommon.GetObjectCount(data);

            GXCommon.SetObjectCount(cnt, bb);
            GXSNInfo info;

            for (int pos = 0; pos != cnt; ++pos)
            {
                type = data.GetUInt8();
                // GetRequest normal
                if (type == 2)
                {
                    int sn = data.GetUInt16();
                    info = FindSNObject(sn);
                    if (!info.IsAction)
                    {
                        ValueEventArgs e = new ValueEventArgs(info.Item, info.Index, 0, null);
                        Read(e);
                        if (e.Handled)
                        {
                            value = e.Value;
                        }
                        else
                        {
                            value = (info.Item as IGXDLMSBase).GetValue(Settings, info.Index, 0, null);
                        }
                        // Set status.
                        bb.SetUInt8(0);
                        GXDLMS.AppedData(info.Item, info.Index, bb, value);
                    }
                    else
                    {
                        ValueEventArgs e = new ValueEventArgs(info.Item, info.Index, 0, null);
                        Action(e);
                        if (e.Handled)
                        {
                            value = e.Value;
                        }
                        else
                        {
                            value = ((IGXDLMSBase)info.Item).Invoke(Settings, info.Index, null);
                        }
                        // Set status.
                        bb.SetUInt8(0);
                        // Add value
                        bb.SetUInt8(GXCommon.GetValueType(value));
                        bb.Add(value);
                    }
                }
                else if (type == 2)
                {
                    // Get request for next data block
                    throw new System.ArgumentException("TODO: Invalid Command.");
                }
                else if (type == 4)
                {
                    // Parameterised access.
                    int        sn         = data.GetUInt16();
                    int        selector   = data.GetUInt8();
                    GXDataInfo di         = new GXDataInfo();
                    object     parameters = GXCommon.GetData(data, di);
                    info = FindSNObject(sn);
                    if (!info.IsAction)
                    {
                        ValueEventArgs e = new ValueEventArgs(info.Item, info.Index, 0, parameters);
                        Read(e);
                        if (e.Handled)
                        {
                            value = e.Value;
                        }
                        else
                        {
                            value = (info.Item as IGXDLMSBase).GetValue(Settings, info.Index, selector, parameters);
                        }
                        // Set status.
                        bb.SetUInt8(0);
                        GXDLMS.AppedData(info.Item, info.Index, bb, value);
                    }
                    else
                    {
                        ValueEventArgs e = new ValueEventArgs(info.Item, info.Index, 0, parameters);
                        e.Value = parameters;
                        Action(e);
                        if (e.Handled)
                        {
                            value = e.Value;
                        }
                        else
                        {
                            value = ((IGXDLMSBase)info.Item).Invoke(Settings, info.Index, parameters);
                        }
                        // Add value
                        bb.Add(value);
                    }
                }
                else
                {
                    throw new System.ArgumentException("Invalid Command.");
                }
            }
            return(GXDLMS.SplitPdu(Settings, Command.ReadResponse, 1, bb,
                                   ErrorCode.Ok, DateTime.MinValue)[0]);
        }
Пример #13
0
        object IGXDLMSBase.GetValue(GXDLMSSettings settings, ValueEventArgs e)
        {
            switch (e.Index)
            {
            case 1:
                return(GXCommon.LogicalNameToBytes(LogicalName));

            case 2:
            {
                GXByteBuffer data = new GXByteBuffer();
                data.SetUInt8((byte)DataType.Structure);
                data.SetUInt8(4);
                if (ChangedParameter == null)
                {
                    GXCommon.SetData(settings, data, DataType.UInt16, 0);
                    GXCommon.SetData(settings, data, DataType.OctetString, new byte[] { 0, 0, 0, 0, 0, 0 });
                    GXCommon.SetData(settings, data, DataType.Int8, 1);
                    GXCommon.SetData(settings, data, DataType.None, null);
                }
                else
                {
                    GXCommon.SetData(settings, data, DataType.UInt16, ChangedParameter.Target.ObjectType);
                    GXCommon.SetData(settings, data, DataType.OctetString, GXCommon.LogicalNameToBytes(ChangedParameter.Target.LogicalName));
                    GXCommon.SetData(settings, data, DataType.Int8, ChangedParameter.AttributeIndex);
                    GXCommon.SetData(settings, data, GXCommon.GetValueType(ChangedParameter.Value), ChangedParameter.Value);
                }
                return(data.Array());
            }

            case 3:
                return(CaptureTime);

            case 4:
            {
                GXByteBuffer data = new GXByteBuffer();
                data.SetUInt8((byte)DataType.Array);
                if (Parameters == null)
                {
                    data.SetUInt8(0);
                }
                else
                {
                    data.SetUInt8((byte)Parameters.Count);
                    foreach (GXDLMSTarget it in Parameters)
                    {
                        data.SetUInt8((byte)DataType.Structure);
                        data.SetUInt8((byte)3);
                        GXCommon.SetData(settings, data, DataType.UInt16, it.Target.ObjectType);
                        GXCommon.SetData(settings, data, DataType.OctetString, GXCommon.LogicalNameToBytes(it.Target.LogicalName));
                        GXCommon.SetData(settings, data, DataType.Int8, it.AttributeIndex);
                    }
                }
                return(data.Array());
            }

            default:
                e.Error = ErrorCode.ReadWriteDenied;
                break;
            }
            return(null);
        }