/// <summary> /// Read object. /// </summary> /// <param name="InitialValues"></param> /// <param name="obj"></param> /// <param name="attribute">Attribute index to read.</param> /// <param name="forceRead">Force all attributes read.</param> public void Read(object sender, GXDLMSObject obj, int attribute, bool forceRead) { GXReplyData reply = new GXReplyData(); if (forceRead) { obj.ClearReadTime(); } foreach (int it in (obj as IGXDLMSBase).GetAttributeIndexToRead()) { reply.Clear(); if (obj is GXDLMSProfileGeneric && it == 2) { if (OnBeforeRead != null) { OnBeforeRead(obj, it); } try { byte[][] tmp; CurrentProfileGeneric = obj as GXDLMSProfileGeneric; OnDataReceived += new GXDLMSCommunicator.DataReceivedEventHandler(this.OnProfileGenericDataReceived); if (CurrentProfileGeneric.AccessSelector == AccessRange.Range || CurrentProfileGeneric.AccessSelector == AccessRange.Last) { GXDateTime start = CurrentProfileGeneric.From as GXDateTime; if (start == null) { start = Convert.ToDateTime(CurrentProfileGeneric.From); } GXDateTime end = CurrentProfileGeneric.To as GXDateTime; if (end == null) { end = Convert.ToDateTime(CurrentProfileGeneric.To); } tmp = client.ReadRowsByRange(CurrentProfileGeneric, start, end); ReadDataBlock(tmp, "Reading profile generic data", 1, reply); } else if (CurrentProfileGeneric.AccessSelector == AccessRange.Entry) { tmp = client.ReadRowsByEntry(CurrentProfileGeneric, Convert.ToInt32(CurrentProfileGeneric.From), Convert.ToInt32(CurrentProfileGeneric.To)); ReadDataBlock(tmp, "Reading profile generic data " + CurrentProfileGeneric.Name, 1, reply); } else //Read all. { tmp = client.Read(CurrentProfileGeneric, 2); ReadDataBlock(tmp, "Reading profile generic data " + CurrentProfileGeneric.Name, 1, reply); } } finally { if (OnAfterRead != null) { OnAfterRead(obj, it); } OnDataReceived -= new GXDLMSCommunicator.DataReceivedEventHandler(OnProfileGenericDataReceived); } continue; } else { if (OnBeforeRead != null) { OnBeforeRead(obj, it); } byte[] data = client.Read(obj.Name, obj.ObjectType, it)[0]; try { ReadDataBlock(data, "Read object type " + obj.ObjectType + " index: " + it, reply); } catch (GXDLMSException ex) { if (ex.ErrorCode == (int)ErrorCode.ReadWriteDenied || ex.ErrorCode == (int)ErrorCode.UndefinedObject || ex.ErrorCode == (int)ErrorCode.UnavailableObject || //Actaris returns access violation error. ex.ErrorCode == (int)ErrorCode.AccessViolated) { obj.SetAccess(it, AccessMode.NoAccess); continue; } else { throw ex; } } if (obj is IGXDLMSBase) { object value = reply.Value; DataType type; if (value is byte[] && (type = obj.GetUIDataType(it)) != DataType.None) { value = GXDLMSClient.ChangeType((byte[])value, type); } client.UpdateValue(obj, it, value); } if (OnAfterRead != null) { OnAfterRead(obj, it); } obj.SetLastReadTime(it, DateTime.Now); //If only selected attribute is read. if (attribute != 0) { break; } } } }