示例#1
0
 internal void DequeueConnect(PeripheralConnection.ConnectOperation con)
 {
     _connectOps.Remove(con);
     Reschedule();
 }
示例#2
0
        private async Task <bool> Schedule()
        {
            // reset trigger
            _tcsSchedule = new TaskCompletionSource <bool>();

            _logger.LogInformation("Scheduling...");

            // look for an active connection request
            PeripheralConnection.ConnectOperation conOp = null;
            int conTime  = 0;
            int conAfter = Environment.TickCount + (_scanning ? ScanStopDelay : 0);

            foreach (var con in _connectOps)
            {
                int t = con.GetNextAttempt(conAfter);
                if (conOp == null || (t - conTime) < 0)
                {
                    conOp   = con;
                    conTime = t;
                }
            }

            conAfter = conTime - Environment.TickCount;
            if (WantScan && conOp != null && conAfter > ScanStopDelay && !ActiveConnection)
            {
                if (!Scanning)
                {
                    _logger.LogDebug("Starting scanner until {Ticks} before connecting", conTime - ScanStopDelay);
                    StartScan();
                }
                // wait until it's time to connect
                if (await Delay(conTime - Environment.TickCount - ScanStopDelay))
                {
                    return(true);
                }
            }

            if (Scanning && (conOp != null || !WantScan))
            {
                if (conOp != null)
                {
                    _logger.LogInformation("Stopping scanner due to {Operation}", conOp);
                }
                else
                {
                    _logger.LogInformation("Stopping scanner, no observers left");
                }
                // stop scanning
                StopScan();
                // unconditional delay
                await Task.Delay(ScanStopDelay);
            }

            if (conOp != null)
            {
                _logger.LogInformation("Waiting until {Ticks} for {Operation}", conTime, conOp);
                // we are going to connect
                if (await Delay(conTime - Environment.TickCount))
                {
                    // reschedule
                    return(true);
                }

                _logger.LogInformation("Starting {Operation} attempt", conOp);
                int endOfAttempt = conOp.StartAttempt();
                while (await Delay(endOfAttempt - Environment.TickCount))
                {
                    if (conOp.Task.IsCompleted)
                    {
                        // connection completed one way or another, we can go schedule again
                        _logger.LogInformation("{Operation} complete", conOp);
                        return(true);
                    }
                    if (!conOp.IsConnecting)
                    {
                        // connection is no longer pending (probably failed), we can schedule something else
                        break;
                    }
                }
                // abort connection attempt and schedule something else
                _logger.LogInformation("Ending {Operation} attempt", conOp);
                await conOp.EndAttempt();

                return(true);
            }

            // nothing to connect, we can start scanning
            if (!_scanning && _scanObservers.Length > 0 && !ActiveConnection)
            {
                for (; ;)
                {
                    _logger.LogInformation("Starting scanner");
                    StartScan();
                    for (; ;)
                    {
                        _advSeen = false;
                        if (await Delay(ScanContinuousTime))
                        {
                            return(true);
                        }
                        if (!_advSeen)
                        {
                            break;
                        }
                    }
                    _logger.LogInformation("No event, interrupting scan for a while");
                    StopScan();
                    if (await Delay(ScanInterruptionTime))
                    {
                        return(true);
                    }
                }
            }

            return(false);
        }
示例#3
0
 internal void EnqueueConnect(PeripheralConnection.ConnectOperation con)
 {
     _connectOps.Add(con);
     Reschedule();
 }