示例#1
0
        /// <summary>
        /// Starts a runner instance
        /// </summary>
        /// <returns>The awaitable task.</returns>
        /// <param name="domain">The AppDomain to use.</param>
        /// <param name="config">The server configuration.</param>
        /// <param name="usessl">If set to <c>true</c> use ssl.</param>
        /// <param name="port">The port to listen on.</param>
        private async Task StartRunnerAsync(System.AppDomain domain, ServerConfig config, bool usessl, string address, int port)
        {
            var enabled = !string.IsNullOrWhiteSpace(address);

            // Ensure it parses
            ParseUtil.ParseEndPoint(address, port);

            var prev = m_handlers.Where(x => x.UseSSL == usessl).FirstOrDefault();

            if (enabled)
            {
                var addcrashhandler = true;
                var wrapper         = new AppDomainWrapper(domain);
                wrapper.SetupFromFile(usessl, m_path, config.Storage);
                if (prev == null)
                {
                    prev = new RunnerInstance(wrapper, address, port, usessl, config);
                    m_handlers.Add(prev);
                }
                else
                {
                    if (prev.RunnerTask.IsFaulted || prev.RunnerTask.IsCanceled || prev.RunnerTask.IsCompleted)
                    {
                        var cur = new RunnerInstance(wrapper, address, port, usessl, config);
                        m_handlers.Remove(prev);
                        m_handlers.Add(cur);

                        prev = cur;
                    }
                    else if (prev.Port != port || !string.Equals(prev.Address, address, StringComparison.Ordinal))
                    {
                        // Address or port change, start new listener first
                        var cur = new RunnerInstance(wrapper, address, port, usessl, config);

                        if (!prev.RunnerTask.IsFaulted)
                        {
                            await prev.StopAsync();
                        }

                        m_handlers.Remove(prev);
                        m_handlers.Add(cur);

                        prev = cur;
                    }
                    else if (prev.Config.SocketBacklog != config.SocketBacklog)
                    {
                        await prev.RestartAsync(wrapper, address, port, usessl, config);
                    }
                    else
                    {
                        addcrashhandler = false;   // We already have it
                        prev.Wrapper    = wrapper; // Assign the new wrapper
                    }
                }

                if (addcrashhandler)
                {
                    var dummy = prev.RunnerTask.ContinueWith(x =>
                    {
                        if (!prev.ShouldStop && InstanceCrashed != null)
                        {
                            InstanceCrashed(address, usessl, x.IsFaulted ? x.Exception : new Exception("Unexpected stop"));
                        }
                    });
                }
            }
            else if (prev != null)
            {
                await prev.StopAsync();

                m_handlers.Remove(prev);
            }
        }