/// <summary>
        /// Remove a callback by reference.
        /// </summary>
        /// <param name="callback">Callback to remove.</param>
        public static void RemoveCallback(ClockCallback callback)
        {
            // remove callback
#if LOCKFREEE
            // NOTE (steveb): this code does NOT guarantee that the removed callback won't be invoked after this method call!
            var current = _head;
            while (current != null)
            {
                if (current.Item.Value == callback)
                {
                    current.Item = new NamedClockCallback(current.Item.Key, null);
                    return;
                }
                current = current.Next;
            }
#else
            lock (_syncRoot) {
                for (int i = 0; i < _callbacks.Length; ++i)
                {
                    if (_callbacks[i].Value == callback)
                    {
                        _callbacks[i] = new NamedClockCallback(null, null);
                    }
                }
            }
#endif
        }
Example #2
0
 /// <summary>
 /// Remove a callback by reference.
 /// </summary>
 /// <param name="callback">Callback to remove.</param>
 public static void RemoveCallback(ClockCallback callback)
 {
     // remove callback
     lock (_syncRoot) {
         for (var i = 0; i < _callbacks.Length; ++i)
         {
             if (_callbacks[i].Value == callback)
             {
                 _callbacks[i] = new NamedClockCallback(null, null);
             }
         }
     }
 }
        //--- Class Methods ---

        /// <summary>
        /// Add a named callback to the clock.
        /// </summary>
        /// <param name="name">Unique key for the callback.</param>
        /// <param name="callback">Callback action.</param>
        public static void AddCallback(string name, ClockCallback callback)
        {
            if (string.IsNullOrEmpty(name))
            {
                throw new ArgumentNullException("name", "name cannot be null or empty");
            }
            if (callback == null)
            {
                throw new ArgumentNullException("callback");
            }

            // add callback
#if LOCKFREEE
            var newNode = new SingleLinkNode <NamedClockCallback>(new NamedClockCallback(name, callback));
            do
            {
                newNode.Next = _head;
            } while(!SysUtil.CAS(ref _head, newNode.Next, newNode));
#else
            lock (_syncRoot) {
                int index;

                // check if there is an empty slot in the callbacks array
                for (index = 0; index < _callbacks.Length; ++index)
                {
                    if (_callbacks[index].Value == null)
                    {
                        _callbacks[index] = new NamedClockCallback(name, callback);
                        return;
                    }
                }

                // make room to add a new thread by doubling the array size and copying over the existing entries
                var newArray = new NamedClockCallback[2 * _callbacks.Length];
                Array.Copy(_callbacks, newArray, _callbacks.Length);

                // assign new thread
                newArray[index] = new NamedClockCallback(name, callback);

                // update instance field
                _callbacks = newArray;
            }
#endif
        }
        //--- Class Methods ---

        /// <summary>
        /// Add a named callback to the clock.
        /// </summary>
        /// <param name="name">Unique key for the callback.</param>
        /// <param name="callback">Callback action.</param>
        public static void AddCallback(string name, ClockCallback callback) {
            if(string.IsNullOrEmpty(name)) {
                throw new ArgumentNullException("name", "name cannot be null or empty");
            }
            if(callback == null) {
                throw new ArgumentNullException("callback");
            }

            // add callback
#if LOCKFREEE
            var newNode = new SingleLinkNode<NamedClockCallback>(new NamedClockCallback(name, callback));
            do {
                newNode.Next = _head;
            } while(!SysUtil.CAS(ref _head, newNode.Next, newNode));
#else
            lock(_syncRoot) {
                int index;

                // check if there is an empty slot in the callbacks array
                for(index = 0; index < _callbacks.Length; ++index) {
                    if(_callbacks[index].Value == null) {
                        _callbacks[index] = new NamedClockCallback(name, callback);
                        return;
                    }
                }

                // make room to add a new thread by doubling the array size and copying over the existing entries
                var newArray = new NamedClockCallback[2 * _callbacks.Length];
                Array.Copy(_callbacks, newArray, _callbacks.Length);

                // assign new thread
                newArray[index] = new NamedClockCallback(name, callback);

                // update instance field
                _callbacks = newArray;
            }
#endif
        }
Example #5
0
        //--- Class Methods ---

        /// <summary>
        /// Add a named callback to the clock.
        /// </summary>
        /// <param name="name">Unique key for the callback.</param>
        /// <param name="callback">Callback action.</param>
        public static void AddCallback(string name, ClockCallback callback)
        {
            if (string.IsNullOrEmpty(name))
            {
                throw new ArgumentNullException("name", "name cannot be null or empty");
            }
            if (callback == null)
            {
                throw new ArgumentNullException("callback");
            }

            // add callback
            lock (_syncRoot) {
                int index;

                // check if there is an empty slot in the callbacks array
                for (index = 0; index < _callbacks.Length; ++index)
                {
                    if (_callbacks[index].Value == null)
                    {
                        _callbacks[index] = new NamedClockCallback(name, callback);
                        return;
                    }
                }

                // make room to add a new thread by doubling the array size and copying over the existing entries
                var newArray = new NamedClockCallback[2 * _callbacks.Length];
                Array.Copy(_callbacks, newArray, _callbacks.Length);

                // assign new thread
                newArray[index] = new NamedClockCallback(name, callback);

                // update instance field
                _callbacks = newArray;
            }
        }
        /// <summary>
        /// Remove a callback by reference.
        /// </summary>
        /// <param name="callback">Callback to remove.</param>
        public static void RemoveCallback(ClockCallback callback) {

            // remove callback
#if LOCKFREEE

            // NOTE (steveb): this code does NOT guarantee that the removed callback won't be invoked after this method call!
            var current = _head;
            while(current != null) {
                if(current.Item.Value == callback) {
                    current.Item = new NamedClockCallback(current.Item.Key, null);
                    return;
                }
                current = current.Next;
            }
#else
            lock(_syncRoot) {
                for(int i = 0; i < _callbacks.Length; ++i) {
                    if(_callbacks[i].Value == callback) {
                        _callbacks[i] = new NamedClockCallback(null, null);
                    }
                }
            }
#endif
        }