Пример #1
0
        public static async Task <ONIContextDisposable> ReserveContextAsync(ONIHardwareSlot slot, bool releaseWaiting = false, CancellationToken ct = default)
        {
#if DEBUG
            Console.WriteLine("Context async slot " + slot + " reserved by " + (new System.Diagnostics.StackTrace()).GetFrame(1).GetMethod().DeclaringType);
#endif
            return(await Task.Run(() => ReserveContext(slot, releaseWaiting), ct));
        }
Пример #2
0
        /// <summary>
        /// Reserve an ONI Context after it has already been opened by the appropriate call to
        /// <see cref="ReserveContext(ONIHardwareSlot, bool)"/>
        /// </summary>
        /// <param name="slot">Hardware slot to reserve.</param>
        /// <returns>Returns a <see cref="ONIContextDisposable"/> asynchronously after it has already been opened.</returns>
        public static async Task <ONIContextDisposable> ReserveOpenContextAsync(ONIHardwareSlot slot)
        {
#if DEBUG
            Console.WriteLine("Open context async slot " + slot + " reserved by " + (new System.Diagnostics.StackTrace()).GetFrame(1).GetMethod().DeclaringType);
#endif
            lock (openContextLock)
            {
                if (!contextWaitHandles.TryGetValue(slot.MakeKey(), out EventWaitHandle waitHandle))
                {
                    contextWaitHandles.Add(slot.MakeKey(), new EventWaitHandle(false, EventResetMode.ManualReset));
                }
            }

            return(await Task.Run(() =>
            {
                contextWaitHandles[slot.MakeKey()].WaitOne();
                return ReserveContext(slot);
            }));
        }
Пример #3
0
        public static ONIContextDisposable ReserveContext(ONIHardwareSlot slot, bool releaseWaiting = false, bool resetRunning = false)
        {
            var contextCounted = default(Tuple <ONIContextTask, RefCountDisposable>);

            lock (openContextLock)
            {
                if (string.IsNullOrEmpty(slot.Driver))
                {
                    contextCounted = openContexts.Count == 1
                        ? openContexts.Values.Single()
                        : throw new ArgumentException("An ONI hardware slot must be specified.", nameof(slot));
                }

                if (!openContexts.TryGetValue(slot.MakeKey(), out contextCounted))
                {
                    var configuration = LoadConfiguration();
                    if (configuration.Contains(slot.MakeKey()))
                    {
                        slot = configuration[slot.MakeKey()];
                    }

                    var ctx = new ONIContextTask(slot.Driver, slot.Index);

                    var dispose = Disposable.Create(() =>
                    {
                        ctx.Dispose();
                        contextWaitHandles[slot.MakeKey()].Reset();

                        // Context and wait handles are removed from dictionaries together
                        openContexts.Remove(slot.MakeKey());
                        contextWaitHandles.Remove(slot.MakeKey());
                    });

                    if (!contextWaitHandles.TryGetValue(slot.MakeKey(), out EventWaitHandle waitHandle))
                    {
                        contextWaitHandles.Add(slot.MakeKey(), new EventWaitHandle(false, EventResetMode.ManualReset));
                    }

                    if (releaseWaiting)
                    {
                        contextWaitHandles[slot.MakeKey()].Set();
                    }

                    var referenenceCount = new RefCountDisposable(dispose);
                    contextCounted = Tuple.Create(ctx, referenenceCount);
                    openContexts.Add(slot.MakeKey(), contextCounted);
                    return(new ONIContextDisposable(ctx, referenenceCount, openContextLock));
                }

                if (resetRunning)
                {
                    contextCounted.Item1.Reset();
                }
                if (releaseWaiting)
                {
                    // Will already be created if we in this portion of code.
                    contextWaitHandles[slot.MakeKey()].Set();
                }

#if DEBUG
                Console.WriteLine("Context slot " + slot + " reserved by " + new System.Diagnostics.StackTrace().GetFrame(1).GetMethod().DeclaringType);
#endif

                return(new ONIContextDisposable(contextCounted.Item1, contextCounted.Item2.GetDisposable(), openContextLock));
            }
        }