/*****************************************************************************************************/
 static void handler_OnReadPropertyMultipleRequest(BacnetClient sender, BacnetAddress adr, byte invoke_id, IList <BacnetReadAccessSpecification> properties, BacnetMaxSegments max_segments)
 {
     lock (device)
     {
         try
         {
             IList <BacnetPropertyValue>   value;
             List <BacnetReadAccessResult> values = new List <BacnetReadAccessResult>();
             foreach (BacnetReadAccessSpecification p in properties)
             {
                 if (p.propertyReferences.Count == 1 && p.propertyReferences[0].propertyIdentifier == (uint)BacnetPropertyIds.PROP_ALL)
                 {
                     BaCSharpObject bacobj = device.FindBacnetObject(p.objectIdentifier);
                     if (!bacobj.ReadPropertyAll(sender, adr, out value))
                     {
                         sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_READ_PROP_MULTIPLE, invoke_id, BacnetErrorClasses.ERROR_CLASS_OBJECT, BacnetErrorCodes.ERROR_CODE_UNKNOWN_OBJECT);
                         return;
                     }
                 }
                 else
                 {
                     BaCSharpObject bacobj = device.FindBacnetObject(p.objectIdentifier);
                     bacobj.ReadPropertyMultiple(sender, adr, p.propertyReferences, out value);
                 }
                 values.Add(new BacnetReadAccessResult(p.objectIdentifier, value));
             }
             sender.ReadPropertyMultipleResponse(adr, invoke_id, sender.GetSegmentBuffer(max_segments), values);
         }
         catch (Exception)
         {
             sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_READ_PROP_MULTIPLE, invoke_id, BacnetErrorClasses.ERROR_CLASS_DEVICE, BacnetErrorCodes.ERROR_CODE_OTHER);
         }
     }
 }
        /*****************************************************************************************************/
        static void handler_OnWritePropertyRequest(BacnetClient sender, BacnetAddress adr, byte invoke_id, BacnetObjectId object_id, BacnetPropertyValue value, BacnetMaxSegments max_segments)
        {
            lock (device)
            {
                BaCSharpObject bacobj = device.FindBacnetObject(object_id);
                if (bacobj != null)
                {
                    ErrorCodes error = bacobj.WritePropertyValue(sender, adr, value, true);
                    if (error == ErrorCodes.Good)
                    {
                        sender.SimpleAckResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_WRITE_PROPERTY, invoke_id);
                    }
                    else
                    {
                        BacnetErrorCodes bacEr = BacnetErrorCodes.ERROR_CODE_OTHER;
                        if (error == ErrorCodes.WriteAccessDenied)
                        {
                            bacEr = BacnetErrorCodes.ERROR_CODE_WRITE_ACCESS_DENIED;
                        }
                        if (error == ErrorCodes.OutOfRange)
                        {
                            bacEr = BacnetErrorCodes.ERROR_CODE_VALUE_OUT_OF_RANGE;
                        }

                        sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_WRITE_PROPERTY, invoke_id, BacnetErrorClasses.ERROR_CLASS_DEVICE, bacEr);
                    }
                }
                else
                {
                    sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_READ_PROPERTY, invoke_id, BacnetErrorClasses.ERROR_CLASS_OBJECT, BacnetErrorCodes.ERROR_CODE_UNKNOWN_OBJECT);
                }
            }
        }
        /*****************************************************************************************************/
        static void handler_OnReadPropertyRequest(BacnetClient sender, BacnetAddress adr, byte invoke_id, BacnetObjectId object_id, BacnetPropertyReference property, BacnetMaxSegments max_segments)
        {
            lock (device)
            {
                BaCSharpObject bacobj = device.FindBacnetObject(object_id);

                if (bacobj != null)
                {
                    IList <BacnetValue> value;
                    ErrorCodes          error = bacobj.ReadPropertyValue(sender, adr, property, out value);
                    if (error == ErrorCodes.Good)
                    {
                        sender.ReadPropertyResponse(adr, invoke_id, sender.GetSegmentBuffer(max_segments), object_id, property, value);
                    }
                    else
                    if (error == ErrorCodes.IndexNotExist)
                    {
                        sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_READ_PROPERTY, invoke_id, BacnetErrorClasses.ERROR_CLASS_PROPERTY, BacnetErrorCodes.ERROR_CODE_INVALID_ARRAY_INDEX);
                    }
                    else
                    {
                        sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_READ_PROPERTY, invoke_id, BacnetErrorClasses.ERROR_CLASS_DEVICE, BacnetErrorCodes.ERROR_CODE_UNKNOWN_PROPERTY);
                    }
                }
                else
                {
                    sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_READ_PROPERTY, invoke_id, BacnetErrorClasses.ERROR_CLASS_OBJECT, BacnetErrorCodes.ERROR_CODE_UNKNOWN_OBJECT);
                }
            }
        }
        /*****************************************************************************************************/
        static void handler_OnSubscribeCOV(BacnetClient sender, BacnetAddress adr, byte invoke_id, uint subscriberProcessIdentifier, BacnetObjectId monitoredObjectIdentifier, bool cancellationRequest, bool issueConfirmedNotifications, uint lifetime, BacnetMaxSegments max_segments)
        {
            lock (device)
            {
                BaCSharpObject bacobj = device.FindBacnetObject(monitoredObjectIdentifier);
                if (bacobj != null)
                {
                    //create
                    Subscription sub = SubscriptionManager.HandleSubscriptionRequest(sender, adr, invoke_id, subscriberProcessIdentifier, monitoredObjectIdentifier, (uint)BacnetPropertyIds.PROP_ALL, cancellationRequest, issueConfirmedNotifications, lifetime, 0);

                    //send confirm
                    sender.SimpleAckResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_SUBSCRIBE_COV, invoke_id);

                    //also send first values
                    if (!cancellationRequest)
                    {
                        System.Threading.ThreadPool.QueueUserWorkItem((o) =>
                        {
                            IList <BacnetPropertyValue> values;
                            if (bacobj.ReadPropertyAll(sender, adr, out values))
                            {
                                sender.Notify(adr, sub.subscriberProcessIdentifier, deviceId, sub.monitoredObjectIdentifier, (uint)sub.GetTimeRemaining(), sub.issueConfirmedNotifications, values);
                            }
                        }, null);
                    }
                }
                else
                {
                    sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_SUBSCRIBE_COV, invoke_id, BacnetErrorClasses.ERROR_CLASS_DEVICE, BacnetErrorCodes.ERROR_CODE_OTHER);
                }
            }
        }
        /*****************************************************************************************************/
        static void handler_OnCOVManagementNotify(BaCSharpObject sender, BacnetPropertyIds propId)
        {
            System.Threading.ThreadPool.QueueUserWorkItem((o) =>
            {
                lock (device)
                {
                    //remove old leftovers
                    SubscriptionManager.RemoveOldSubscriptions();

                    //find subscription
                    List <Subscription> subs = SubscriptionManager.GetSubscriptionsForObject(sender.PROP_OBJECT_IDENTIFIER);

                    if (subs == null)
                    {
                        return;             // nobody
                    }
                    //Read the property
                    IList <BacnetValue> value;
                    BacnetPropertyReference br = new BacnetPropertyReference((uint)propId, (uint)System.IO.BACnet.Serialize.ASN1.BACNET_ARRAY_ALL);
                    ErrorCodes error           = sender.ReadPropertyValue(br, out value);

                    List <BacnetPropertyValue> values = new List <BacnetPropertyValue>();
                    BacnetPropertyValue tmp           = new BacnetPropertyValue();
                    tmp.value    = value;
                    tmp.property = br;
                    values.Add(tmp);

                    //send to all
                    foreach (Subscription sub in subs)
                    {
                        if (sub.monitoredProperty.propertyIdentifier == (uint)BacnetPropertyIds.PROP_ALL || sub.monitoredProperty.propertyIdentifier == (uint)propId)
                        {
                            tmp.property = sub.monitoredProperty;
                            if (!sub.reciever.Notify(sub.reciever_address, sub.subscriberProcessIdentifier, deviceId, sub.monitoredObjectIdentifier, (uint)sub.GetTimeRemaining(), sub.issueConfirmedNotifications, values))
                            {
                                SubscriptionManager.RemoveReceiver(sub.reciever_address);
                            }
                        }
                    }
                }
            }, null);
        }
        private static void handler_OnAtomicReadFileRequest(BacnetClient sender, BacnetAddress adr, byte invoke_id, bool is_stream, BacnetObjectId object_id, int position, uint count, BacnetMaxSegments max_segments)
        {
            lock (device)
            {
                BaCSharpObject File = device.FindBacnetObject(object_id);
                if (File is BacnetFile)
                {
                    try
                    {
                        BacnetFile f = (BacnetFile)File;

                        int  filesize    = (int)f.PROP_FILE_SIZE;
                        bool end_of_file = (position + count) >= filesize;
                        count = (uint)Math.Min(count, filesize - position);
                        int max_filebuffer_size = sender.GetFileBufferMaxSize();
                        if (count > max_filebuffer_size && max_segments > 0)
                        {
                            //create segmented message!!!
                        }
                        else
                        {
                            count = (uint)Math.Min(count, max_filebuffer_size);     //trim
                        }

                        byte[] file_buffer = f.ReadFileBlock(position, (int)count);
                        sender.ReadFileResponse(adr, invoke_id, sender.GetSegmentBuffer(max_segments), position, count, end_of_file, file_buffer);
                    }
                    catch (Exception)
                    {
                        sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_ATOMIC_READ_FILE, invoke_id, BacnetErrorClasses.ERROR_CLASS_DEVICE, BacnetErrorCodes.ERROR_CODE_OTHER);
                    }
                }
                else
                {
                    sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_ATOMIC_READ_FILE, invoke_id, BacnetErrorClasses.ERROR_CLASS_DEVICE, BacnetErrorCodes.ERROR_CODE_OTHER);
                }
            }
        }
        /*****************************************************************************************************/
        static void handler_OnReadRange(BacnetClient sender, BacnetAddress adr, byte invoke_id, BacnetObjectId objectId, BacnetPropertyReference property, System.IO.BACnet.Serialize.BacnetReadRangeRequestTypes requestType, uint position, DateTime time, int count, BacnetMaxSegments max_segments)
        {
            lock (device)
            {
                BaCSharpObject trend = device.FindBacnetObject(objectId);

                if (trend is TrendLog)
                {
                    BacnetResultFlags status;
                    byte[]            application_data = (trend as TrendLog).GetEncodedTrends(position, count, out status);

                    if (application_data != null)
                    {
                        //send
                        sender.ReadRangeResponse(adr, invoke_id, sender.GetSegmentBuffer(max_segments), objectId, property, status, (uint)count, application_data, requestType, position);
                    }
                }
                else
                {
                    sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_READ_RANGE, invoke_id, BacnetErrorClasses.ERROR_CLASS_DEVICE, BacnetErrorCodes.ERROR_CODE_OTHER);
                }
            }
        }
        // Here something could be done to avoid a to big fill to be written on the disk
        private static void handler_OnAtomicWriteFileRequest(BacnetClient sender, BacnetAddress adr, byte invoke_id, bool is_stream, BacnetObjectId object_id, int position, uint block_count, byte[][] blocks, int[] counts, BacnetMaxSegments max_segments)
        {
            lock (device)
            {
                BaCSharpObject File = device.FindBacnetObject(object_id);
                if (File is BacnetFile)
                {
                    try
                    {
                        BacnetFile f = (BacnetFile)File;

                        if (f.PROP_READ_ONLY == false)
                        {
                            int currentposition = position;
                            for (int i = 0; i < block_count; i++)
                            {
                                f.WriteFileBlock(blocks[i], currentposition, counts[i]);
                                currentposition += counts[i];
                            }
                            sender.WriteFileResponse(adr, invoke_id, sender.GetSegmentBuffer(max_segments), position);
                        }
                        else
                        {
                            sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_ATOMIC_WRITE_FILE, invoke_id, BacnetErrorClasses.ERROR_CLASS_DEVICE, BacnetErrorCodes.ERROR_CODE_WRITE_ACCESS_DENIED);
                        }
                    }
                    catch (Exception)
                    {
                        sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_ATOMIC_WRITE_FILE, invoke_id, BacnetErrorClasses.ERROR_CLASS_DEVICE, BacnetErrorCodes.ERROR_CODE_OTHER);
                    }
                }
                else
                {
                    sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_ATOMIC_WRITE_FILE, invoke_id, BacnetErrorClasses.ERROR_CLASS_DEVICE, BacnetErrorCodes.ERROR_CODE_OTHER);
                }
            }
        }
예제 #9
0
        /*****************************************************************************************************/
        void handler_OnSubscribeCOVProperty(BacnetClient sender, BacnetAddress adr, byte invoke_id, uint subscriberProcessIdentifier, BacnetObjectId monitoredObjectIdentifier, BacnetPropertyReference monitoredProperty, bool cancellationRequest, bool issueConfirmedNotifications, uint lifetime, float covIncrement, BacnetMaxSegments max_segments)
        {
            lock (device)
            {
                BaCSharpObject bacobj = device.FindBacnetObject(monitoredObjectIdentifier);
                if (bacobj != null)
                {
                    //create
                    Subscription sub = SubscriptionManager.HandleSubscriptionRequest(sender, adr, invoke_id, subscriberProcessIdentifier, monitoredObjectIdentifier, monitoredProperty.propertyIdentifier, cancellationRequest, issueConfirmedNotifications, lifetime, covIncrement);

                    //send confirm
                    sender.SimpleAckResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_SUBSCRIBE_COV_PROPERTY, invoke_id);

                    //also send first values
                    if (!cancellationRequest)
                    {
                        System.Threading.ThreadPool.QueueUserWorkItem((o) =>
                        {
                            IList <BacnetValue> _values;
                            bacobj.ReadPropertyValue(sender, adr, monitoredProperty, out _values);

                            List <BacnetPropertyValue> values = new List <BacnetPropertyValue>();
                            BacnetPropertyValue tmp           = new BacnetPropertyValue();
                            tmp.property = sub.monitoredProperty;
                            tmp.value    = _values;
                            values.Add(tmp);

                            sender.Notify(adr, sub.subscriberProcessIdentifier, deviceId, sub.monitoredObjectIdentifier, (uint)sub.GetTimeRemaining(), sub.issueConfirmedNotifications, values);
                        }, null);
                    }
                }
                else
                {
                    sender.ErrorResponse(adr, BacnetConfirmedServices.SERVICE_CONFIRMED_SUBSCRIBE_COV_PROPERTY, invoke_id, BacnetErrorClasses.ERROR_CLASS_DEVICE, BacnetErrorCodes.ERROR_CODE_OTHER);
                }
            }
        }
예제 #10
0
 /*****************************************************************************************************/
 static void handler_OnWriteNotify(BaCSharpObject sender, BacnetPropertyIds propId)
 {
     // External Write ... could be internaly made !!! for instance by Schedule Object
     Console.WriteLine("Write success into object : " + sender.ToString());
 }