Example #1
0
        private void LoginMethodCallback(IAsyncResult result)
        {
            object[]            asyncState   = result.AsyncState as object[];
            LoginProxy          proxy        = asyncState[0] as LoginProxy;
            LoginContext        context      = asyncState[1] as LoginContext;
            XmlRpcAsyncResult   clientResult = result as XmlRpcAsyncResult;
            LoginMethodResponse reply;
            IPAddress           simIP = IPAddress.Any; // Temporary
            ushort simPort            = 0;
            uint   regionX            = 0;
            uint   regionY            = 0;
            bool   loginSuccess       = false;

            // Fetch the login response
            try
            {
                reply = proxy.EndLoginToSimulator(clientResult);
                if (context != CurrentContext)
                {
                    return;
                }
            }
            catch (Exception ex)
            {
                Client.DebugLog(ex.ToString());

                UpdateLoginStatus(LoginStatus.Failed, "Error retrieving the login response from the server");
                return;
            }

            string reason  = reply.reason;
            string message = reply.message;

            if (reply.login == "true")
            {
                loginSuccess = true;

                // FIXME: No information should be set here, everything can take care of itself
                // through login reply handlers

                #region Critical Information

                try
                {
                    // Networking
                    Client.Network.CircuitCode = (uint)reply.circuit_code;
                    regionX = (uint)reply.region_x;
                    regionY = (uint)reply.region_y;
                    simPort = (ushort)reply.sim_port;
                    Helpers.TryParse(reply.sim_ip, out simIP);
                    LoginSeedCapability = reply.seed_capability;
                }
                catch (Exception)
                {
                    UpdateLoginStatus(LoginStatus.Failed, "Login server failed to return critical information");
                    return;
                }

                #endregion Critical Information
            }

            bool redirect = (reply.login == "indeterminate");

            try
            {
                if (OnLoginResponse != null)
                {
                    LoginResponseData data = new LoginResponseData();
                    if (loginSuccess)
                    {
                        data.Parse(reply);
                    }
                    try { OnLoginResponse(loginSuccess, redirect, message, reason, data); }
                    catch (Exception ex) { Client.Log(ex.ToString(), Helpers.LogLevel.Error); }
                }
            }
            catch (Exception ex) { Client.Log(ex.ToString(), Helpers.LogLevel.Error); }

            // Make the next network jump, if needed
            if (redirect)
            {
                UpdateLoginStatus(LoginStatus.Redirecting, "Redirecting login...");

                // Handle indeterminate logins
                CurrentContext.Params.URI        = reply.next_url;
                CurrentContext.Params.MethodName = reply.next_method;

                // Ignore next_options and next_duration for now
                BeginLogin();
            }
            else if (loginSuccess)
            {
                UpdateLoginStatus(LoginStatus.ConnectingToSim, "Connecting to simulator...");

                ulong handle = Helpers.UIntsToLong(regionX, regionY);

                // Connect to the sim given in the login reply
                if (Connect(simIP, simPort, handle, true, LoginSeedCapability) != null)
                {
                    // Request the economy data right after login
                    SendPacket(new EconomyDataRequestPacket());

                    // Update the login message with the MOTD returned from the server
                    UpdateLoginStatus(LoginStatus.Success, message);

                    // Fire an event for connecting to the grid
                    if (OnConnected != null)
                    {
                        try { OnConnected(this.Client); }
                        catch (Exception e) { Client.Log(e.ToString(), Helpers.LogLevel.Error); }
                    }
                }
                else
                {
                    UpdateLoginStatus(LoginStatus.Failed, "Unable to connect to simulator");
                }
            }
            else
            {
                // Make sure a usable error key is set
                if (!String.IsNullOrEmpty(reason))
                {
                    InternalErrorKey = reason;
                }
                else
                {
                    InternalErrorKey = "unknown";
                }

                UpdateLoginStatus(LoginStatus.Failed, message);
            }
        }