Example #1
0
 public BACnetListener(AppManager apm, BACnetManager bnm)
 {
     _apm     = apm;
     this.bnm = bnm;
 }
Example #2
0
 public void DumpException(AppManager apm)
 {
     apm.MessageProtocolError(message);
 }
Example #3
0
        public static void RespondToAPDU(AppManager apm, BACnetManager bnm, BACnetPacket incomingPacket)
        {
            byte[]    outbuf = new byte[2000];
            int       optr;
            PacketLog pktlog;

            BACnetPacket outgoingBACpacket = new BACnetPacket(apm, bnm);

            // fill in some CRP parameters for packet log display
            outgoingBACpacket.confirmedServiceChoice       = incomingPacket.confirmedServiceChoice;
            outgoingBACpacket.apduConfirmedServiceTypeFlag = incomingPacket.apduConfirmedServiceTypeFlag;
            outgoingBACpacket.propertyID = incomingPacket.propertyID;
            outgoingBACpacket.apduUnconfirmedServiceFlag = incomingPacket.apduUnconfirmedServiceFlag;
            outgoingBACpacket.pduType = incomingPacket.pduType;
            outgoingBACpacket.unconfirmedServiceChoice            = incomingPacket.unconfirmedServiceChoice;
            outgoingBACpacket.directlyConnectedIPEndPointOfDevice = incomingPacket.directlyConnectedIPEndPointOfDevice;

            BACnetPacket incomingBACpacket = (BACnetPacket)incomingPacket;

            if (incomingBACpacket.apduConfirmedServiceTypeFlag == true)
            {
                switch (incomingBACpacket.confirmedServiceChoice)
                {
                case BACnetEnums.BACNET_CONFIRMED_SERVICE.SERVICE_CONFIRMED_READ_PROPERTY:

                    switch (incomingBACpacket.propertyID)
                    {
                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_OBJECT_NAME:
                        // supply the first (and only) (device) object
                        optr = InsertReadPropertyResponse(apm, incomingBACpacket, outgoingBACpacket, outbuf, incomingBACpacket.propertyID);
                        // Device Object ID
                        InsertContextOpeningTag(outbuf, ref optr, 3);
                        InsertApplicationTagString(outbuf, ref optr, apm.ourDeviceName);
                        InsertContextClosingTag(outbuf, ref optr, 3);
                        // Send it off
                        SendOffPacket(apm, outgoingBACpacket, outbuf, optr);
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_PROTOCOL_OBJECT_TYPES_SUPPORTED:
                        optr = InsertReadPropertyResponse(apm, incomingBACpacket, outgoingBACpacket, outbuf, incomingBACpacket.propertyID);
                        BACnetLibraryCL.InsertContextOpeningTag(outbuf, ref optr, 3);

                        // hardcode the bitstring until we see where else it can be used, then generalized.

                        outbuf[optr++] = 0x83;          // Assume length = 3, including unused bits byte
                        // outbuf[optr++] = 0x03;
                        outbuf[optr++] = 0x06;          // trailing bits not used

                        InsertBitString(outbuf, optr, 2, (int)BACnetEnums.BACNET_OBJECT_TYPE.OBJECT_DEVICE);
                        optr += 2;

                        BACnetLibraryCL.InsertContextClosingTag(outbuf, ref optr, 3);

                        SendOffPacket(apm, outgoingBACpacket, outbuf, optr);
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_PROTOCOL_SERVICES_SUPPORTED:

                        optr = InsertReadPropertyResponse(apm, incomingBACpacket, outgoingBACpacket, outbuf, incomingBACpacket.propertyID);

                        BACnetLibraryCL.InsertContextOpeningTag(outbuf, ref optr, 3);


                        //List<BACnetEnums.BACNET_SERVICES_SUPPORTED> servicesList = new List<BACnetEnums.BACNET_SERVICES_SUPPORTED>();

                        //servicesList.Add(BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_READ_PROPERTY);
                        //// servicesList.Add(BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_WRITE_PROPERTY);
                        //servicesList.Add(BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_DEVICE_COMMUNICATION_CONTROL);
                        ////servicesList.Add(BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_REINITIALIZE_DEVICE);
                        //servicesList.Add(BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_TIME_SYNCHRONIZATION);
                        //servicesList.Add(BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_WHO_IS);
                        //// todo, what about i-am ?
                        //BACnetLibraryCL.InsertApplicationTagString(outbuf, ref optr, servicesList );

                        // hardcode the bitstring until we see where else it can be used, then generalized.

                        outbuf[optr++] = 0x85;          // Assume length = 6
                        outbuf[optr++] = 0x06;          // Length, including the next byte
                        outbuf[optr++] = 0x05;          // 5 trailing bits not used

                        InsertBitString(outbuf, optr, 5, (int)BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_READ_PROPERTY);
                        InsertBitString(outbuf, optr, 5, (int)BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_DEVICE_COMMUNICATION_CONTROL);
                        InsertBitString(outbuf, optr, 5, (int)BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_TIME_SYNCHRONIZATION);
                        InsertBitString(outbuf, optr, 5, (int)BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_WHO_IS);

                        InsertBitString(outbuf, optr, 5, (int)BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_WRITE_PROPERTY);
                        InsertBitString(outbuf, optr, 5, (int)BACnetEnums.BACNET_SERVICES_SUPPORTED.SERVICE_SUPPORTED_REINITIALIZE_DEVICE);

                        optr += 5;

                        BACnetLibraryCL.InsertContextClosingTag(outbuf, ref optr, 3);

                        SendOffPacket(apm, outgoingBACpacket, outbuf, optr);
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_OBJECT_LIST:
                        // Only respond if array index specified
                        if (!incomingPacket.arrayIndexDecoded)
                        {
                            throw new Exception("m0058 - Not expecting open object list");
                        }

                        if (incomingPacket.arrayIndex == 0)
                        {
                            optr = InsertReadPropertyResponse(apm, incomingBACpacket, outgoingBACpacket, outbuf, incomingBACpacket.propertyID);

                            // arrayIndex 0
                            InsertContextTag(outbuf, ref optr, 2, 0);

                            // Object count
                            InsertContextOpeningTag(outbuf, ref optr, 3);
                            InsertApplicationTag(outbuf, ref optr, BACnetEnums.BACNET_APPLICATION_TAG.BACNET_APPLICATION_TAG_UNSIGNED_INT, 1);
                            InsertContextClosingTag(outbuf, ref optr, 3);

                            // Send it off
                            SendOffPacket(apm, outgoingBACpacket, outbuf, optr);
                            break;

                            // supply the number of objects
                        }
                        else if (incomingPacket.arrayIndex == 1)
                        {
                            // supply the first (and only) (device) object
                            optr = InsertReadPropertyResponse(apm, incomingBACpacket, outgoingBACpacket, outbuf, incomingBACpacket.propertyID);

                            // arrayIndex 1
                            InsertContextTag(outbuf, ref optr, 2, 1);

                            // Device Object ID
                            InsertContextOpeningTag(outbuf, ref optr, 3);
                            incomingPacket.objectID.EncodeApplicationTag(outbuf, ref optr);
                            InsertContextClosingTag(outbuf, ref optr, 3);

                            // Send it off
                            SendOffPacket(apm, outgoingBACpacket, outbuf, optr);
                        }
                        else
                        {
                            throw new Exception("m0059 - Illegal object list index");
                        }
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_OBJECT_TYPE:
                        // supply the first (and only) (device) object
                        optr = InsertReadPropertyResponse(apm, incomingBACpacket, outgoingBACpacket, outbuf, incomingBACpacket.propertyID);
                        // Device Object ID
                        InsertContextOpeningTag(outbuf, ref optr, 3);
                        InsertApplicationTag(outbuf, ref optr, BACnetEnums.BACNET_APPLICATION_TAG.BACNET_APPLICATION_TAG_ENUMERATED, (uint)BACnetEnums.BACNET_OBJECT_TYPE.OBJECT_DEVICE);
                        InsertContextClosingTag(outbuf, ref optr, 3);
                        // Send it off
                        SendOffPacket(apm, outgoingBACpacket, outbuf, optr);
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_SYSTEM_STATUS:
                        // supply the first (and only) (device) object
                        optr = InsertReadPropertyResponse(apm, incomingBACpacket, outgoingBACpacket, outbuf, incomingBACpacket.propertyID);
                        // Device Object ID
                        InsertContextOpeningTag(outbuf, ref optr, 3);
                        InsertApplicationTag(outbuf, ref optr, BACnetEnums.BACNET_APPLICATION_TAG.BACNET_APPLICATION_TAG_ENUMERATED, (uint)BACnetEnums.BACNET_DEVICE_STATUS.STATUS_OPERATIONAL);
                        InsertContextClosingTag(outbuf, ref optr, 3);
                        // Send it off
                        SendOffPacket(apm, outgoingBACpacket, outbuf, optr);
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_OBJECT_IDENTIFIER:
                        // supply the first (and only) (device) object
                        optr = InsertReadPropertyResponse(apm, incomingBACpacket, outgoingBACpacket, outbuf, incomingBACpacket.propertyID);
                        // Device Object ID
                        InsertContextOpeningTag(outbuf, ref optr, 3);
                        incomingPacket.objectID.EncodeApplicationTag(outbuf, ref optr);
                        InsertContextClosingTag(outbuf, ref optr, 3);
                        // Send it off
                        SendOffPacket(apm, outgoingBACpacket, outbuf, optr);
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_VENDOR_NAME:
                        // supply the first (and only) (device) object
                        optr = InsertReadPropertyResponse(apm, incomingBACpacket, outgoingBACpacket, outbuf, incomingBACpacket.propertyID);
                        // Device Object ID
                        InsertContextOpeningTag(outbuf, ref optr, 3);
                        InsertApplicationTagString(outbuf, ref optr, apm.ourVendorName);
                        InsertContextClosingTag(outbuf, ref optr, 3);
                        // Send it off
                        SendOffPacket(apm, outgoingBACpacket, outbuf, optr);
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_MODEL_NAME:
                        // supply the first (and only) (device) object
                        optr = InsertReadPropertyResponse(apm, incomingBACpacket, outgoingBACpacket, outbuf, incomingBACpacket.propertyID);
                        // Device Object ID
                        InsertContextOpeningTag(outbuf, ref optr, 3);
                        InsertApplicationTagString(outbuf, ref optr, apm.ourModelName);
                        InsertContextClosingTag(outbuf, ref optr, 3);
                        // Send it off
                        SendOffPacket(apm, outgoingBACpacket, outbuf, optr);
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_FIRMWARE_REVISION:
                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_APPLICATION_SOFTWARE_VERSION:
                        RespondReadPropertyWithString(apm, incomingBACpacket, outgoingBACpacket, outbuf, apm.ourFirmwareRevision);
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_VENDOR_IDENTIFIER:
                        RespondReadPropertyWithUint(apm, incomingBACpacket, outgoingBACpacket, outbuf, apm.ourVendorID);
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_PROTOCOL_VERSION:
                        RespondReadPropertyWithUint(apm, incomingBACpacket, outgoingBACpacket, outbuf, 1);
                        break;

                    case BACnetEnums.BACNET_PROPERTY_ID.PROP_PROTOCOL_REVISION:
                        RespondReadPropertyWithUint(apm, incomingBACpacket, outgoingBACpacket, outbuf, 4);
                        break;

                    default:
                        apm.MessageTodo("m0046 - Implement read property " + incomingBACpacket.propertyID.ToString());
                        break;
                    }
                    break;

                default:
                    apm.MessageTodo("m0044 - Implement confirmed service " + incomingBACpacket.confirmedServiceChoice.ToString());
                    break;
                }
            }

            if (incomingBACpacket.apduUnconfirmedServiceFlag == true)
            {
                switch (incomingBACpacket.pduType)
                {
                case BACnetEnums.BACNET_PDU_TYPE.PDU_TYPE_UNCONFIRMED_SERVICE_REQUEST:
                    switch (incomingBACpacket.unconfirmedServiceChoice)
                    {
                    case BACnetEnums.BACNET_UNCONFIRMED_SERVICE.SERVICE_UNCONFIRMED_WHO_IS:

                        // we need to respond

                        // ONLY if we are in the range, and if not, ignore.

                        if (incomingBACpacket.lowRange != 0 || incomingBACpacket.highRange != 0)
                        {
                            if (apm.ourDeviceId < incomingBACpacket.lowRange || apm.ourDeviceId > incomingBACpacket.highRange)
                            {
                                // This packet not for us
                                apm.MessageLog("m0034 - Ranged Who-Is not addressed to us, ignoring");
                                break;
                            }
                        }

                        // Compose the response (I-am)

                        outgoingBACpacket.BACnetPort = incomingPacket.BACnetPort;

                        outgoingBACpacket.npdu.isBroadcast = true;
                        outgoingBACpacket.hopcount         = 256;

                        // destination address of the BACnet packet. (Must either be b'cast or directlyConnectedIPEP

                        optr = 0;

                        outgoingBACpacket.npdu.isNPDUmessage       = false;   // makes it an APDU
                        outgoingBACpacket.pduType                  = BACnetEnums.BACNET_PDU_TYPE.PDU_TYPE_UNCONFIRMED_SERVICE_REQUEST;
                        outgoingBACpacket.unconfirmedServiceChoice = BACnetEnums.BACNET_UNCONFIRMED_SERVICE.SERVICE_UNCONFIRMED_I_AM;

                        outgoingBACpacket.EncodeBACnetNew(outbuf, ref optr);

                        // send the message

                        // if there is no available adapter, this try will throw
                        try
                        {
                            apm.bnm.bacnet_listen_socket.SendTo(outbuf, optr, SocketFlags.None, incomingPacket.directlyConnectedIPEndPointOfDevice);

                            pktlog = new PacketLog(true, incomingPacket.directlyConnectedIPEndPointOfDevice, outgoingBACpacket);
                            pktlog.BACnetPacket = (BACnetPacket)outgoingBACpacket;
                            apm.bnm.BACnetMessageLog.Enqueue(pktlog);
                        }
                        catch (SocketException)
                        {
                            apm.MessageTodo("Either the network cable is unplugged, or there is no configured Ethernet Port on this computer");
                        }
                        break;

                    case BACnetEnums.BACNET_UNCONFIRMED_SERVICE.SERVICE_UNCONFIRMED_I_AM:
                        break;

                    default:
                        apm.MessageTodo("Implement " + incomingBACpacket.unconfirmedServiceChoice.ToString());
                        break;
                    }
                    break;

                default:
                    apm.MessageTodo("Implement " + incomingBACpacket.pduType.ToString());
                    break;
                }
            }
        }
Example #4
0
        public static void TreeViewUpdate(AppManager apm, BACnetManager bnm, TreeView treeViewMessageLog, bool logmessages)
        {
            if (bnm.BACnetMessageLog.Count > 0)
            {
                while (bnm.BACnetMessageLog.Count > 0)
                {
                    // remove the first treenode

                    _count++;

                    PacketLog pktlog = bnm.BACnetMessageLog.Dequeue();

                    if (!logmessages)
                    {
                        // discard the message, unless it has been logged as an error
                        if (pktlog.BACnetPacket != null && !pktlog.BACnetPacket.errorFlag)
                        {
                            continue;
                        }
                    }


                    TreeNode           ntn           = new TreeNode();
                    TreeNodeCollection addBACnetHere = treeViewMessageLog.Nodes;

                    if (pktlog.BACnetPacket != null)
                    {
                        // bump the rest up a level
                        TreeNode nntn = new TreeNode();
                        nntn.Text = "BACnet";

                        if (pktlog.sending == true)
                        {
                            nntn.Text      = _count.ToString() + " BACnet Sent";
                            nntn.BackColor = Color.LightPink;
                        }
                        else
                        {
                            nntn.Text      = _count.ToString() + " BACnet Recd";
                            nntn.BackColor = Color.LightGreen;
                        }

                        // display some NPDU parameters

                        if (pktlog.BACnetPacket.npdu.isBroadcast)
                        {
                            nntn.Nodes.Add("To:   Broadcast");
                        }
                        else
                        {
                            if (pktlog.BACnetPacket.dadr != null)
                            {
                                nntn.Nodes.Add("To:   " + pktlog.BACnetPacket.dadr.ToString());
                            }
                        }

                        // From address

                        if (pktlog.BACnetPacket.directlyConnectedIPEndPointOfDevice != null)
                        {
                            nntn.Nodes.Add("From: " + pktlog.BACnetPacket.directlyConnectedIPEndPointOfDevice.ToString());
                        }


                        if (pktlog.BACnetPacket.npdu.expectingReply)
                        {
                            nntn.Nodes.Add("Expecting Reply");
                        }

                        if (!pktlog.BACnetPacket.npdu.isNPDUmessage)
                        {
                            switch (pktlog.BACnetPacket.pduType)
                            {
                            case BACnetEnums.BACNET_PDU_TYPE.PDU_TYPE_UNCONFIRMED_SERVICE_REQUEST:
                                nntn.Text += " Unconfirmed Service Request -";
                                switch (pktlog.BACnetPacket.unconfirmedServiceChoice)
                                {
                                case BACnetEnums.BACNET_UNCONFIRMED_SERVICE.SERVICE_UNCONFIRMED_I_AM:
                                    nntn.Text += " I-Am";
                                    break;

                                case BACnetEnums.BACNET_UNCONFIRMED_SERVICE.SERVICE_UNCONFIRMED_WHO_IS:
                                    nntn.Text += " Who-Is";
                                    break;

                                default:
                                    nntn.Text += " m0019 Unknown BACnet unconfirmed service type - fix line 196 PacketLog.cs";
                                    break;
                                }
                                break;


                            case BACnetEnums.BACNET_PDU_TYPE.PDU_TYPE_CONFIRMED_SERVICE_REQUEST:
                                nntn.Text += " Confirmed Service Request";
                                switch (pktlog.BACnetPacket.confirmedServiceChoice)
                                {
                                case BACnetEnums.BACNET_CONFIRMED_SERVICE.SERVICE_CONFIRMED_READ_PROPERTY:
                                    nntn.Nodes.Add("Read Property " + pktlog.BACnetPacket.propertyID.ToString());
                                    break;

                                case BACnetEnums.BACNET_CONFIRMED_SERVICE.SERVICE_CONFIRMED_READ_PROP_MULTIPLE:
                                    nntn.Nodes.Add("Read Property Multiple");
                                    break;

                                default:
                                    nntn.Nodes.Add("m0014 Unknown BACnet confirmed service type " + pktlog.BACnetPacket.confirmedServiceChoice.ToString());
                                    break;
                                }
                                break;

                            case BACnetEnums.BACNET_PDU_TYPE.PDU_TYPE_COMPLEX_ACK:
                                nntn.Text += " Complex ACK -";
                                switch (pktlog.BACnetPacket.confirmedServiceChoice)
                                {
                                case BACnetEnums.BACNET_CONFIRMED_SERVICE.SERVICE_CONFIRMED_READ_PROPERTY:
                                    nntn.Text += " Read Property " + pktlog.BACnetPacket.propertyID.ToString();
                                    break;

                                case BACnetEnums.BACNET_CONFIRMED_SERVICE.SERVICE_CONFIRMED_READ_PROP_MULTIPLE:
                                    nntn.Text += " Read Property Multiple";
                                    break;

                                default:
                                    nntn.Text += " m0036 Unknown BACnet confirmed service type";
                                    break;
                                }
                                break;

                            case BACnetEnums.BACNET_PDU_TYPE.PDU_TYPE_REJECT:
                                nntn.Text += " Reject PDU - " + pktlog.BACnetPacket.pduRejectReason.ToString() + " [" + pktlog.BACnetPacket.invokeID.ToString() + "]";
                                break;

                            case BACnetEnums.BACNET_PDU_TYPE.PDU_TYPE_ABORT:
                                apm.MessageTodo("m0092 Resolve pktlog.bacnetpacket.pdutyp " + pktlog.BACnetPacket.pduType.ToString());
                                break;

                            default:
                                apm.MessageTodo("m0015 Resolve pktlog.bacnetpacket.pdutyp " + pktlog.BACnetPacket.pduType.ToString());
                                break;
                            }
                        }
                        else if (pktlog.BACnetPacket.apdu_present)
                        {
                            apm.MessageTodo("m0018 I dont expect to see this");
                        }
                        else
                        {
                            // todo, clean up this flag one day
                            nntn.Nodes.Add("NPDU Function: " + pktlog.BACnetPacket.npdu.function.ToString());
                        }
                        addBACnetHere.Add(nntn);
                    }

                    treeViewMessageLog.ExpandAll();

                    // remove all the earlier nodes...
                    while (treeViewMessageLog.Nodes.Count > 150)
                    {
                        treeViewMessageLog.Nodes.RemoveAt(0);
                    }
                }
            }
        }
Example #5
0
 public DeviceTreeView(AppManager apm, TreeView tv)
 {
     _apm         = apm;
     TreeViewOnUI = tv;
 }