/// <summary> /// Updates a result list based on the request options and sets the handles for use by the client. /// </summary> public ItemIdentifier[] ApplyFilters(int filters, ItemIdentifier[] results) { if (results == null) { return(null); } foreach (ItemIdentifier result in results) { if (result.ServerHandle != null) { SubscriptionItem item = (SubscriptionItem)m_items[result.ServerHandle]; if (item != null) { result.ItemName = ((filters & (int)ResultFilter.ItemName) != 0)?item.ItemID:null; result.ItemPath = null; result.ServerHandle = result.ServerHandle; result.ClientHandle = ((filters & (int)ResultFilter.ClientHandle) != 0)?item.ClientHandle:null; } } if ((filters & (int)ResultFilter.ItemTime) == 0) { if (typeof(ItemValue).IsInstanceOfType(result)) { ((ItemValueResult)result).Timestamp = DateTime.MinValue; ((ItemValueResult)result).TimestampSpecified = false; } } } return(results); }
/// <remarks/> public IdentifiedResult[] Write(ItemValue[] items) { if (items == null) { throw new ArgumentNullException("items"); } lock (this) { // handle trivial case. if (items.Length == 0) { return(new IdentifiedResult[0]); } // create item results. IdentifiedResult[] results = new IdentifiedResult[items.Length]; for (int ii = 0; ii < items.Length; ii++) { // initialize result with item. results[ii] = new IdentifiedResult(items[ii]); // check for invalid handle. if (items[ii].ServerHandle == null) { results[ii].ResultID = ResultID.Da.E_INVALIDHANDLE; continue; } // lookup subscription item. SubscriptionItem item = (SubscriptionItem)m_items[items[ii].ServerHandle]; if (item == null) { results[ii].ResultID = ResultID.Da.E_INVALIDHANDLE; continue; } // write the item value. results[ii] = item.Write(m_state.Locale, items[ii]); results[ii].ServerHandle = items[ii].ServerHandle; } // apply result filters. ApplyFilters(m_filters, results); // return results. return(results); } }
/// <remarks/> public IdentifiedResult[] RemoveItems(ItemIdentifier[] items) { if (items == null) { throw new ArgumentNullException("items"); } lock (this) { // handle trivial case. if (items.Length == 0) { return(new IdentifiedResult[0]); } // create item results. IdentifiedResult[] results = new IdentifiedResult[items.Length]; for (int ii = 0; ii < items.Length; ii++) { // initialize result with item. results[ii] = new IdentifiedResult(items[ii]); // check for invalid handle. if (items[ii].ServerHandle == null) { results[ii].ResultID = ResultID.Da.E_INVALIDHANDLE; continue; } // lookup subscription item. SubscriptionItem item = (SubscriptionItem)m_items[items[ii].ServerHandle]; if (item == null) { results[ii].ResultID = ResultID.Da.E_INVALIDHANDLE; continue; } // remove item. m_items.Remove(items[ii].ServerHandle); results[ii].ResultID = ResultID.S_OK; } // return results. return(results); } }
/// <summary> /// Begins an asynchronous write operation for a set of items. /// </summary> /// <param name="items">The set of item values to write (must include the server handle).</param> /// <param name="requestHandle">An identifier for the request assigned by the caller.</param> /// <param name="callback">A delegate used to receive notifications when the request completes.</param> /// <param name="request">An object that contains the state of the request (used to cancel the request).</param> /// <returns>A set of results containing any errors encountered when the server validated the items.</returns> public IdentifiedResult[] Write( ItemValue[] items, object requestHandle, WriteCompleteEventHandler callback, out IRequest request) { if (items == null) { throw new ArgumentNullException("items"); } lock (this) { request = null; // handle trivial case. if (items.Length == 0) { return(new IdentifiedResult[0]); } // validate the items. ArrayList validItems = new ArrayList(); IdentifiedResult[] results = new IdentifiedResult[items.Length]; for (int ii = 0; ii < items.Length; ii++) { // initialize result with item. results[ii] = new IdentifiedResult(items[ii]); // check for invalid handle. if (items[ii].ServerHandle == null) { results[ii].ResultID = ResultID.Da.E_INVALIDHANDLE; continue; } // lookup subscription item. SubscriptionItem item = (SubscriptionItem)m_items[items[ii].ServerHandle]; if (item == null) { results[ii].ResultID = ResultID.Da.E_INVALIDHANDLE; continue; } // at least one valid item exists. validItems.Add(items[ii]); } if (validItems.Count > 0) { request = new Opc.Da.Request(this, requestHandle); m_requests.Add(request, callback); m_writeQueue.Enqueue(new object[] { request, validItems.ToArray(typeof(ItemValue)) }); ThreadPool.QueueUserWorkItem(new WaitCallback(OnWrite)); } // apply result filters. ApplyFilters(m_filters, results); // return results. return(results); } }
/// <remarks/> public ItemResult[] ModifyItems(int masks, Item[] items) { if (items == null) { throw new ArgumentNullException("items"); } lock (this) { // handle trivial case. if (items.Length == 0) { return(new ItemResult[0]); } // create item results. ItemResult[] results = new ItemResult[items.Length]; for (int ii = 0; ii < items.Length; ii++) { // initialize result with item. results[ii] = new ItemResult(items[ii]); // check for invalid handle. if (items[ii].ServerHandle == null) { results[ii].ResultID = ResultID.Da.E_INVALIDHANDLE; continue; } // lookup existing item. SubscriptionItem item = (SubscriptionItem)m_items[items[ii].ServerHandle]; // check that the item is valid. if (m_items.Contains(items)) { results[ii].ResultID = ResultID.Da.E_INVALIDHANDLE; continue; } // update subscription item. System.Type reqType = item.ReqType; bool active = item.Active; object clientHandle = item.ClientHandle; float deadband = item.Deadband; int samplingRate = item.SamplingRate; bool enableBuffering = item.BufferEnabled; // requested data type. if ((masks & (int)StateMask.ReqType) != 0) { // check that requested datatype is valid. if (items[ii].ReqType == Type.ILLEGAL_TYPE) { results[ii].ResultID = ResultID.Da.E_BADTYPE; continue; } reqType = items[ii].ReqType; } // client handle. if ((masks & (int)StateMask.ClientHandle) != 0) { clientHandle = items[ii].ClientHandle; } // deadband. if ((masks & (int)StateMask.Deadband) != 0) { if (items[ii].DeadbandSpecified) { deadband = items[ii].Deadband; if (deadband < 0.0 || deadband > 100.0) { results[ii].ResultID = ResultID.E_INVALIDARG; continue; } } else { deadband = -1; } } // sampling rate. if ((masks & (int)StateMask.SamplingRate) != 0) { samplingRate = (items[ii].SamplingRateSpecified)?items[ii].SamplingRate:-1; int requestedSamplingRate = samplingRate; if (samplingRate != -1) { samplingRate = Cache.AdjustUpdateRate(requestedSamplingRate); } if (requestedSamplingRate != samplingRate) { results[ii].ResultID = ResultID.Da.S_UNSUPPORTEDRATE; } } if ((masks & (int)StateMask.EnableBuffering) != 0) { enableBuffering = (items[ii].EnableBufferingSpecified)?items[ii].EnableBuffering:false; } // active. if ((masks & (int)StateMask.Active) != 0) { active = (items[ii].ActiveSpecified)?items[ii].Active:item.Active; // ensure a callback is sent on the next update. if (active && !item.Active) { item.ResetLastUpdate(); } } // save new values. item.ReqType = reqType; item.Active = active; item.ClientHandle = clientHandle; item.Deadband = deadband; item.SamplingRate = samplingRate; item.BufferEnabled = enableBuffering; // update result object. results[ii].Active = item.Active; results[ii].ActiveSpecified = true; results[ii].ClientHandle = item.ClientHandle; results[ii].ReqType = item.ReqType; results[ii].Deadband = (item.Deadband != -1)?item.Deadband:0; results[ii].DeadbandSpecified = item.Deadband != -1; results[ii].SamplingRate = (item.SamplingRate != -1)?item.SamplingRate:0; results[ii].SamplingRateSpecified = item.SamplingRate != -1; results[ii].EnableBuffering = item.BufferEnabled; results[ii].EnableBufferingSpecified = item.BufferEnabled; } // return results. return(results); } }
/// <remarks/> public ItemResult[] AddItems(Item[] items) { if (items == null) { throw new ArgumentNullException("items"); } lock (this) { // handle trivial case. if (items.Length == 0) { return(new ItemResult[0]); } // create item results. ItemResult[] results = new ItemResult[items.Length]; for (int ii = 0; ii < items.Length; ii++) { // initialize result with item. results[ii] = new ItemResult((ItemIdentifier)items[ii]); // check that the item is valid. if (items[ii].ItemName == null || items[ii].ItemName.Length == 0) { results[ii].ResultID = ResultID.Da.E_INVALID_ITEM_NAME; continue; } // check that the item exists. if (!m_cache.IsValidItem(items[ii].ItemName)) { results[ii].ResultID = ResultID.Da.E_UNKNOWN_ITEM_NAME; continue; } // check that requested datatype is valid. if (items[ii].ReqType == typeof(Opc.Type)) { results[ii].ResultID = ResultID.Da.E_BADTYPE; continue; } // create a new subscription item. SubscriptionItem item = new SubscriptionItem(items[ii].ItemName, m_cache); item.Active = (items[ii].ActiveSpecified)?items[ii].Active:true; item.ClientHandle = items[ii].ClientHandle; item.ReqType = items[ii].ReqType; item.Deadband = (items[ii].DeadbandSpecified)?items[ii].Deadband:-1; item.SamplingRate = (items[ii].SamplingRateSpecified)?items[ii].SamplingRate:-1; item.BufferEnabled = (items[ii].EnableBufferingSpecified)?items[ii].EnableBuffering:false; // update sampling rate. if (item.SamplingRate != -1) { item.SamplingRate = Cache.AdjustUpdateRate(item.SamplingRate); } // assign unique server handle. results[ii].ServerHandle = item.ServerHandle = AssignHandle(); // update result object. results[ii].Active = item.Active; results[ii].ActiveSpecified = true; results[ii].ClientHandle = item.ClientHandle; results[ii].ReqType = item.ReqType; results[ii].Deadband = (item.Deadband != -1)?item.Deadband:0; results[ii].DeadbandSpecified = item.Deadband != -1; results[ii].SamplingRate = (item.SamplingRate != -1)?item.SamplingRate:0; results[ii].SamplingRateSpecified = item.SamplingRate != -1; results[ii].EnableBuffering = item.BufferEnabled; results[ii].EnableBufferingSpecified = item.SamplingRate != -1; // save reference to new item. m_items[results[ii].ServerHandle] = item; } // return results. return(results); } }