internal override void OnMessage(InsteonMessage message)
        {
            var cmd2 = (byte)message.Properties[PropertyKey.Cmd2];

            if (message.MessageType == InsteonMessageType.OnCleanup)
            {
                if (cmd2 == 0x01)
                {
                    logger.InfoFormat("Dry State detected in device {0}", Address.ToString());
                    OnDeviceStatusChanged(InsteonDeviceStatus.DryDetected);
                }
                else if (cmd2 == 0x02)
                {
                    logger.InfoFormat("Wet State detect in device {0}", Address.ToString());
                    OnDeviceStatusChanged(InsteonDeviceStatus.WetDetected);
                }
                else if (cmd2 == 0x04)
                {
                    logger.InfoFormat("Heartbeat from device {0}", Address.ToString());
                    LastHeartbeat = DateTime.Now;
                    OnDeviceStatusChanged(InsteonDeviceStatus.Heartbeat);
                }
            }
            else
            {
                base.OnMessage(message);
            }
        }
Exemple #2
0
 private void OnSetButtonPressed(InsteonMessage message)
 {
     if (Identity.IsEmpty)
     {
         var devCat          = (byte)message.Properties[PropertyKey.DevCat];
         var subCat          = (byte)message.Properties[PropertyKey.SubCat];
         var firmwareVersion = (byte)message.Properties[PropertyKey.FirmwareVersion];
         Identity = new InsteonIdentity(devCat, subCat, firmwareVersion);
     }
     OnDeviceIdentified();
 }
Exemple #3
0
        internal virtual void OnMessage(InsteonMessage message)
        {
            switch (message.MessageType)
            {
            case InsteonMessageType.Ack:
                PendingCommandAck(message);
                break;

            case InsteonMessageType.OnCleanup:
                OnDeviceStatusChanged(InsteonDeviceStatus.On);
                break;

            case InsteonMessageType.OffCleanup:
                OnDeviceStatusChanged(InsteonDeviceStatus.Off);
                break;

            case InsteonMessageType.FastOnCleanup:
                OnDeviceStatusChanged(InsteonDeviceStatus.On);
                OnDeviceStatusChanged(InsteonDeviceStatus.FastOn);
                break;

            case InsteonMessageType.FastOffCleanup:
                OnDeviceStatusChanged(InsteonDeviceStatus.Off);
                OnDeviceStatusChanged(InsteonDeviceStatus.FastOff);
                break;

            case InsteonMessageType.IncrementBeginBroadcast:
                dimmerDirection = message.Properties[PropertyKey.IncrementDirection] != 0 ? DimmerDirection.Up : DimmerDirection.Down;
                break;

            case InsteonMessageType.IncrementEndBroadcast:
                if (dimmerDirection == DimmerDirection.Up)
                {
                    OnDeviceStatusChanged(InsteonDeviceStatus.Brighten);
                }
                else if (dimmerDirection == DimmerDirection.Down)
                {
                    OnDeviceStatusChanged(InsteonDeviceStatus.Dim);
                }
                break;

            case InsteonMessageType.SetButtonPressed:
                OnSetButtonPressed(message);
                break;

            default:
                logger.Warn("Unhandled message type");
                break;
            }
        }
        private bool IsDuplicateMessage(InsteonMessage message)
        {
            lock (this.duplicates)
            {
                // determine if message key matches an entry in the list
                foreach (var item in this.duplicates)
                    if (message.Key == item.Key)
                        return true;

                // create a new duplicte entry
                var timer = new Timer(new TimerCallback(this.DuplicateMessageTimerCallback), message.Key, 0, 1000);
                this.duplicates.Add(message.Key, timer);

                return false;
            }
        }
        private static bool DeviceLinkCleanupMessage(byte[] data, int offset, out int count, out InsteonMessage message)
        {
            message = null;
            count = 0;
            if (data.Length <= offset + 8)
                return false;

            byte messageId = data[offset];
            InsteonMessageType messageType = InsteonMessageType.DeviceLinkCleanup;
            Dictionary<PropertyKey, int> properties = new Dictionary<PropertyKey, int>();

            properties[PropertyKey.LinkStatus] = data[offset + 1];
            count = 2;

            message = new InsteonMessage(messageId, messageType, properties);
            return true;
        }
Exemple #6
0
 internal override void OnMessage(InsteonMessage message)
 {
     if (message.MessageType == InsteonMessageType.OnCleanup)
     {
         SensorStatus = IOState.Closed;
         OnDeviceStatusChanged(InsteonDeviceStatus.SensorTriggerOn);
     }
     else if (message.MessageType == InsteonMessageType.OffCleanup)
     {
         SensorStatus = IOState.Open;
         OnDeviceStatusChanged(InsteonDeviceStatus.SensorTriggerOff);
     }
     else
     {
         base.OnMessage(message);
     }
 }
        internal override void OnMessage(InsteonMessage message)
        {
            var cmd2 = (byte)message.Properties[PropertyKey.Cmd2];

            if (cmd2 == 0x03 && message.MessageType == InsteonMessageType.OnCleanup)
            {
                logger.WarnFormat("Low battery in device {0}", Address.ToString());
                LowBattery = true;
                OnDeviceStatusChanged(InsteonDeviceStatus.LowBattery);
            }
            else if (cmd2 == 0x02 && message.MessageType == InsteonMessageType.OffCleanup)
            {
                logger.WarnFormat("Light detect in device {0}", Address.ToString());
                OnDeviceStatusChanged(InsteonDeviceStatus.LightDetected);
            }
            else
            {
                base.OnMessage(message);
            }
        }
Exemple #8
0
 // if a command is pending determines whether the current message completes the pending command
 private void PendingCommandAck(InsteonMessage message)
 {
     lock (pendingEvent)
     {
         if (pendingCommand != null)
         {
             var cmd1 = message.Properties[PropertyKey.Cmd1];
             if (System.Enum.IsDefined(typeof(InsteonDirectCommands), cmd1))
             {
                 var command = (InsteonDirectCommands)cmd1;
                 if (pendingCommand.Value == command)
                 {
                     pendingCommand = null;
                     pendingValue   = 0;
                     ackTimer.Change(Timeout.Infinite, Timeout.Infinite); // stop ACK timeout timer
                     pendingEvent.Set();                                  // unblock any thread that may be waiting on the pending command
                 }
             }
         }
     }
 }
        private static bool DeviceLinkMessage(byte[] data, int offset, out int count, out InsteonMessage message)
        {
            message = null;
            count = 0;
            if (data.Length < offset + 9)
                return false;

            byte messageId = data[offset];
            InsteonMessageType messageType = InsteonMessageType.DeviceLink;
            Dictionary<PropertyKey, int> properties = new Dictionary<PropertyKey, int>();

            properties[PropertyKey.LinkType] = data[offset + 1];
            properties[PropertyKey.LinkGroup] = data[offset + 2];
            GetAddressProperty(PropertyKey.Address, data, offset + 3, out count, properties);
            properties[PropertyKey.DevCat] = data[offset + 6];
            properties[PropertyKey.SubCat] = data[offset + 7];
            properties[PropertyKey.FirmwareVersion] = data[offset + 8];
            count = 9;

            message = new InsteonMessage(messageId, messageType, properties);
            return true;
        }
        private static bool DeviceLinkRecordMessage(byte[] data, int offset, out int count, out InsteonMessage message)
        {
            message = null;
            count = 0;
            if (data.Length < offset + 9)
                return false;

            byte messageId = data[offset];
            InsteonMessageType messageType = InsteonMessageType.DeviceLinkRecord;
            Dictionary<PropertyKey, int> properties = new Dictionary<PropertyKey, int>();
            
            properties[PropertyKey.LinkRecordFlags] = data[offset + 1];
            properties[PropertyKey.LinkGroup] = data[offset + 2];
            properties[PropertyKey.LinkAddress] = new InsteonAddress(data[offset + 3], data[offset + 4], data[offset + 5]).Value;
            properties[PropertyKey.LinkData1] = data[offset + 6];
            properties[PropertyKey.LinkData2] = data[offset + 7];
            properties[PropertyKey.LinkData3] = data[offset + 8];
            count = 9;

            message = new InsteonMessage(messageId, messageType, properties);
            return true;
        }
 internal void OnMessage(InsteonMessage message)
 {
     if (message.MessageType == InsteonMessageType.DeviceLink)
     {
         InsteonAddress address = new InsteonAddress(message.Properties[PropertyKey.Address]);
         InsteonIdentity identity = new InsteonIdentity((byte)message.Properties[PropertyKey.DevCat], (byte)message.Properties[PropertyKey.SubCat], (byte)message.Properties[PropertyKey.FirmwareVersion]);
         InsteonDevice device = network.Devices.Add(address, identity);
         timer.Stop();
         IsInLinkingMode = false;
         if (linkingMode.HasValue)
         {
             if (linkingMode != InsteonLinkMode.Delete)
                 OnDeviceLinked(device);
             else
                 OnDeviceUnlinked(device);
         }
         else
         {
             OnDeviceLinked(device);
         }
     }
 }
Exemple #12
0
 private void OnSetButtonPressed(InsteonMessage message)
 {
     if (this.Identity.IsEmpty)
     {
         var devCat = (byte)message.Properties[PropertyKey.DevCat];
         var subCat = (byte)message.Properties[PropertyKey.DevCat];
         var firmwareVersion = (byte)message.Properties[PropertyKey.DevCat];
         this.Identity = new InsteonIdentity(devCat, subCat, firmwareVersion);
     }
     this.OnDeviceIdentified();
 }
 private void UpdateWaitItems(InsteonMessage message)
 {
     lock (this.waitList)
     {
         for (var i = 0; i < this.waitList.Count; ++i)
         {
             var item = this.waitList[i];
             if (message.MessageId == item.MessageId)
                 if (item.Message == null)
                 {
                     item.Message = message;
                     item.MessageEvent.Set();
                 }
         }
     }
 }
Exemple #14
0
        // if a command is pending determines whether the current message completes the pending command
        private InsteonDeviceCommands? PendingCommandAck(InsteonMessage message)
        {
            lock (this.pendingEvent)
            {
                if (this.pendingCommand != null)
                {
                    var cmd1 = message.Properties[PropertyKey.Cmd1];
                    if (Enum.IsDefined(typeof(InsteonDeviceCommands), cmd1))
                    {
                        var command = (InsteonDeviceCommands)cmd1;
                        if (this.pendingCommand.Value == command)
                        {
                            this.pendingCommand = null;
                            this.pendingValue = 0;
                            this.ackTimer.Change(Timeout.Infinite, Timeout.Infinite); // stop ACK timeout timer
                            this.pendingEvent.Set(); // unblock any thread that may be waiting on the pending command
                            return command;
                        }
                    }
                }
            }

            return null;
        }
 private void OnMessage(InsteonMessage message)
 {
     if (message.Properties.ContainsKey(PropertyKey.FromAddress))
     {
         var address = message.Properties[PropertyKey.FromAddress];
         if (this.network.Devices.ContainsKey(address))
         {
             Log.WriteLine("Device {0} received message {1}", InsteonAddress.Format(address), message.ToString());
             var device = this.network.Devices.Find(address);
             device.OnMessage(message);
         }
         else if (message.MessageType == InsteonMessageType.SetButtonPressed)
         {
             // don't warn about SetButtonPressed message from unknown devices, because it may be from a device about to be added
         }
         else if (this.network.AutoAdd)
         {
             Log.WriteLine("Unknown device {0} received message {1}, adding device", InsteonAddress.Format(address), message.ToString());
             var device = this.network.Devices.Add(new InsteonAddress(address), new InsteonIdentity());
             device.OnMessage(message);
         }
         else
         {
             Log.WriteLine("WARNING: Unknown device {0} received message {1}", InsteonAddress.Format(address), message.ToString());
         }
     }
     else
     {
         Log.WriteLine("Controller received message {0}", message.ToString());
         this.network.Controller.OnMessage(message);
     }
 }
        public EchoStatus TrySendEchoCommand(byte[] message, bool retryOnNak, int echoLength, out Dictionary<PropertyKey, int> properties)
        {
            this.echoMessage = null;

            this.echoCommand = true;
            var status = this.TrySend(message, retryOnNak, echoLength);
            this.echoCommand = false;

            properties = this.echoMessage != null ? this.echoMessage.Properties : null;
            this.echoMessage = null;
            return status;
        }
        private static bool GetIMInfo(byte[] data, int offset, out int count, out InsteonMessage message)
        {
            message = null;
            count = 0;
            if (data.Length < offset + 7)
                return false;

            byte messageId = data[offset];
            InsteonMessageType messageType = InsteonMessageType.GetIMInfo;
            Dictionary<PropertyKey, int> properties = new Dictionary<PropertyKey, int>();

            properties[PropertyKey.Address] = new InsteonAddress(data[offset + 1], data[offset + 2], data[offset + 3]).Value;
            properties[PropertyKey.DevCat] = data[offset + 4];
            properties[PropertyKey.SubCat] = data[offset + 5];
            properties[PropertyKey.FirmwareVersion] = data[offset + 6];
            count = 7;

            message = new InsteonMessage(messageId, messageType, properties);
            return true;
        }
        public static bool ProcessMessage(byte[] data, int offset, out int count, out InsteonMessage message)
        {
            message = null;
            count = 0;
            if (data.Length <= offset)
                return false;

            switch (data[offset])
            {
                case 0x50: return InsteonMessageProcessor.StandardMessage(data, offset, out count, out message);
                case 0x51: return InsteonMessageProcessor.ExtendedMessage(data, offset, out count, out message);
                case 0x53: return InsteonMessageProcessor.DeviceLinkMessage(data, offset, out count, out message);
                case 0x57: return InsteonMessageProcessor.DeviceLinkRecordMessage(data, offset, out count, out message);
                case 0x58: return InsteonMessageProcessor.DeviceLinkCleanupMessage(data, offset, out count, out message);
                case 0x60: return InsteonMessageProcessor.GetIMInfo(data, offset, out count, out message);
            }

            return false;
        }
        private static bool StandardMessage(byte[] data, int offset, out int count, out InsteonMessage message)
        {
            message = null;
            count = 0;
            if (data.Length < offset + 10)
                return false;

            byte messageId = data[offset];
            Dictionary<PropertyKey, int> properties = new Dictionary<PropertyKey, int>();

            GetAddressProperty(PropertyKey.FromAddress, data, offset + 1, out count, properties);
            GetMessageFlagProperty(data, offset, out count, properties);
            if (properties[PropertyKey.MessageFlagsBroadcast] == 0)
                GetAddressProperty(PropertyKey.ToAddress, data, offset + 4, out count, properties);
            properties[PropertyKey.Cmd1] = data[offset + 8];
            properties[PropertyKey.Cmd2] = data[offset + 9];
            count = 10;

            InsteonMessageType messageType = GetMessageType(data, offset, properties);
            message = new InsteonMessage(messageId, messageType, properties);
            return true;
        }
        private static bool ExtendedMessage(byte[] data, int offset, out int count, out InsteonMessage message)
        {
            message = null;
            count = 0;
            if (data.Length < offset + 23)
                return false;

            StandardMessage(data, offset, out count, out message);
            message.Properties[PropertyKey.Data1] = data[offset + 10];
            message.Properties[PropertyKey.Data2] = data[offset + 11];
            message.Properties[PropertyKey.Data3] = data[offset + 12];
            message.Properties[PropertyKey.Data4] = data[offset + 13];
            message.Properties[PropertyKey.Data5] = data[offset + 14];
            message.Properties[PropertyKey.Data6] = data[offset + 15];
            message.Properties[PropertyKey.Data7] = data[offset + 16];
            message.Properties[PropertyKey.Data8] = data[offset + 17];
            message.Properties[PropertyKey.Data9] = data[offset + 18];
            message.Properties[PropertyKey.Data10] = data[offset + 19];
            message.Properties[PropertyKey.Data11] = data[offset + 20];
            message.Properties[PropertyKey.Data12] = data[offset + 21];
            message.Properties[PropertyKey.Data13] = data[offset + 22];
            message.Properties[PropertyKey.Data14] = data[offset + 23];
            count = 23;
            return true;
        }
Exemple #21
0
        internal void OnMessage(InsteonMessage message)
        {
            switch (message.MessageType)
            {
                case InsteonMessageType.Ack:
                    var cmd = this.PendingCommandAck(message);

                    if (cmd.HasValue)
                    {
                        // This feels wrong, but I'm not seeing the 'DeviceStatusChanged' as a result of setting the status.
                        // Could probably use some sort of 'map' here to map command to status.
                        switch (cmd.Value)
                        {
                            case InsteonDeviceCommands.On:
                                this.OnDeviceStatusChanged(InsteonDeviceStatus.On);
                                break;
                            case InsteonDeviceCommands.Off:
                                this.OnDeviceStatusChanged(InsteonDeviceStatus.Off);
                                break;
                        }
                    }
                    break;

                case InsteonMessageType.OnCleanup:
                    this.OnDeviceStatusChanged(InsteonDeviceStatus.On);
                    break;

                case InsteonMessageType.OffCleanup:
                    this.OnDeviceStatusChanged(InsteonDeviceStatus.Off);
                    break;

                case InsteonMessageType.FastOnCleanup:
                    this.OnDeviceStatusChanged(InsteonDeviceStatus.On);
                    this.OnDeviceStatusChanged(InsteonDeviceStatus.FastOn);
                    break;

                case InsteonMessageType.FastOffCleanup:
                    this.OnDeviceStatusChanged(InsteonDeviceStatus.Off);
                    this.OnDeviceStatusChanged(InsteonDeviceStatus.FastOff);
                    break;

                case InsteonMessageType.IncrementBeginBroadcast:
                    this.dimmerDirection = message.Properties[PropertyKey.IncrementDirection] != 0 ? DimmerDirection.Up : DimmerDirection.Down;
                    break;

                case InsteonMessageType.IncrementEndBroadcast:
                    if (this.dimmerDirection == DimmerDirection.Up)
                    {
                        this.OnDeviceStatusChanged(InsteonDeviceStatus.Brighten);
                    }
                    else if (this.dimmerDirection == DimmerDirection.Down)
                    {
                        this.OnDeviceStatusChanged(InsteonDeviceStatus.Dim);
                    }
                    break;

                case InsteonMessageType.SetButtonPressed:
                    this.OnSetButtonPressed(message);
                    break;
            }
        }