From bea8e2b82654b558f7131fa262a613de62df9124 Mon Sep 17 00:00:00 2001 From: MW Date: Wed, 11 Apr 2007 13:40:29 +0000 Subject: Renamed the Servers directory to OpenSim.Servers --- OpenSim.Servers/BaseHttpServer.cs | 224 ++++++++++++++++ OpenSim.Servers/IRestHandler.cs | 8 + OpenSim.Servers/LocalUserProfileManager.cs | 109 ++++++++ OpenSim.Servers/LoginResponse.cs | 398 +++++++++++++++++++++++++++++ OpenSim.Servers/LoginServer.cs | 283 ++++++++++++++++++++ OpenSim.Servers/OpenSim.Servers.csproj | 115 +++++++++ OpenSim.Servers/OpenSim.Servers.dll.build | 48 ++++ OpenSim.Servers/XmlRpcMethod.cs | 7 + 8 files changed, 1192 insertions(+) create mode 100644 OpenSim.Servers/BaseHttpServer.cs create mode 100644 OpenSim.Servers/IRestHandler.cs create mode 100644 OpenSim.Servers/LocalUserProfileManager.cs create mode 100644 OpenSim.Servers/LoginResponse.cs create mode 100644 OpenSim.Servers/LoginServer.cs create mode 100644 OpenSim.Servers/OpenSim.Servers.csproj create mode 100644 OpenSim.Servers/OpenSim.Servers.dll.build create mode 100644 OpenSim.Servers/XmlRpcMethod.cs (limited to 'OpenSim.Servers') diff --git a/OpenSim.Servers/BaseHttpServer.cs b/OpenSim.Servers/BaseHttpServer.cs new file mode 100644 index 0000000..2f73f46 --- /dev/null +++ b/OpenSim.Servers/BaseHttpServer.cs @@ -0,0 +1,224 @@ +using System; +using System.Collections.Generic; +using System.Net; +using System.Text; +using System.Text.RegularExpressions; +using System.Threading; +//using OpenSim.CAPS; +using Nwc.XmlRpc; +using System.Collections; + +namespace OpenSim.Servers +{ + public class BaseHttpServer + { + protected Thread m_workerThread; + protected HttpListener m_httpListener; + protected Dictionary m_restHandlers = new Dictionary(); + protected Dictionary m_rpcHandlers = new Dictionary(); + protected int m_port; + + public BaseHttpServer(int port) + { + m_port = port; + } + + public bool AddRestHandler(string method, string path, RestMethod handler) + { + string methodKey = String.Format("{0}: {1}", method, path); + + if (!this.m_restHandlers.ContainsKey(methodKey)) + { + this.m_restHandlers.Add(methodKey, handler); + return true; + } + + //must already have a handler for that path so return false + return false; + } + + public bool AddXmlRPCHandler(string method, XmlRpcMethod handler) + { + if (!this.m_rpcHandlers.ContainsKey(method)) + { + this.m_rpcHandlers.Add(method, handler); + return true; + } + + //must already have a handler for that path so return false + return false; + } + + protected virtual string ProcessXMLRPCMethod(string methodName, XmlRpcRequest request) + { + XmlRpcResponse response; + + XmlRpcMethod method; + if( this.m_rpcHandlers.TryGetValue( methodName, out method ) ) + { + response = method(request); + } + else + { + response = new XmlRpcResponse(); + Hashtable unknownMethodError = new Hashtable(); + unknownMethodError["reason"] = "XmlRequest"; ; + unknownMethodError["message"] = "Unknown Rpc request"; + unknownMethodError["login"] = "false"; + response.Value = unknownMethodError; + } + + return XmlRpcResponseSerializer.Singleton.Serialize(response); + } + + protected virtual string ParseREST(string request, string path, string method) + { + string response; + RestMethod handler; + + string requestKey = String.Format("{0}: {1}", method, path); + + string bestMatch = String.Empty; + foreach( string currentKey in m_restHandlers.Keys ) + { + if( requestKey.StartsWith( currentKey )) + { + if(currentKey.Length > bestMatch.Length ) + { + bestMatch = currentKey; + } + } + } + + if (m_restHandlers.TryGetValue(bestMatch, out handler)) + { + response = handler(request, path); + + } + else + { + response = String.Empty; + } + + return response; + } + + protected virtual string ParseLLSDXML(string requestBody) + { + // dummy function for now - IMPLEMENT ME! + return ""; + } + + protected virtual string ParseXMLRPC(string requestBody) + { + string responseString = String.Empty; + + try + { + XmlRpcRequest request = (XmlRpcRequest)(new XmlRpcRequestDeserializer()).Deserialize(requestBody); + + string methodName = request.MethodName; + + responseString = ProcessXMLRPCMethod(methodName, request ); + } + catch (Exception e) + { + Console.WriteLine(e.ToString()); + } + return responseString; + } + + public virtual void HandleRequest(Object stateinfo) + { + HttpListenerContext context = (HttpListenerContext)stateinfo; + + HttpListenerRequest request = context.Request; + HttpListenerResponse response = context.Response; + + response.KeepAlive = false; + response.SendChunked = false; + + System.IO.Stream body = request.InputStream; + System.Text.Encoding encoding = System.Text.Encoding.UTF8; + System.IO.StreamReader reader = new System.IO.StreamReader(body, encoding); + + string requestBody = reader.ReadToEnd(); + body.Close(); + reader.Close(); + + //Console.WriteLine(request.HttpMethod + " " + request.RawUrl + " Http/" + request.ProtocolVersion.ToString() + " content type: " + request.ContentType); + //Console.WriteLine(requestBody); + + string responseString = ""; + switch (request.ContentType) + { + case "text/xml": + // must be XML-RPC, so pass to the XML-RPC parser + + responseString = ParseXMLRPC(requestBody); + responseString = Regex.Replace(responseString, "utf-16", "utf-8"); + + response.AddHeader("Content-type", "text/xml"); + break; + + case "application/xml": + // probably LLSD we hope, otherwise it should be ignored by the parser + responseString = ParseLLSDXML(requestBody); + response.AddHeader("Content-type", "application/xml"); + break; + + case "application/x-www-form-urlencoded": + // a form data POST so send to the REST parser + responseString = ParseREST(requestBody, request.RawUrl, request.HttpMethod); + response.AddHeader("Content-type", "text/html"); + break; + + case null: + // must be REST or invalid crap, so pass to the REST parser + responseString = ParseREST(requestBody, request.RawUrl, request.HttpMethod); + response.AddHeader("Content-type", "text/html"); + break; + + } + + byte[] buffer = System.Text.Encoding.UTF8.GetBytes(responseString); + System.IO.Stream output = response.OutputStream; + response.SendChunked = false; + response.ContentLength64 = buffer.Length; + output.Write(buffer, 0, buffer.Length); + output.Close(); + } + + public void Start() + { + OpenSim.Framework.Console.MainConsole.Instance.WriteLine("BaseHttpServer.cs: Starting up HTTP Server"); + + m_workerThread = new Thread(new ThreadStart(StartHTTP)); + m_workerThread.IsBackground = true; + m_workerThread.Start(); + } + + private void StartHTTP() + { + try + { + OpenSim.Framework.Console.MainConsole.Instance.WriteLine("BaseHttpServer.cs: StartHTTP() - Spawned main thread OK"); + m_httpListener = new HttpListener(); + + m_httpListener.Prefixes.Add("http://+:" + m_port + "/"); + m_httpListener.Start(); + + HttpListenerContext context; + while (true) + { + context = m_httpListener.GetContext(); + ThreadPool.QueueUserWorkItem(new WaitCallback(HandleRequest), context); + } + } + catch (Exception e) + { + OpenSim.Framework.Console.MainConsole.Instance.WriteLine(e.Message); + } + } + } +} diff --git a/OpenSim.Servers/IRestHandler.cs b/OpenSim.Servers/IRestHandler.cs new file mode 100644 index 0000000..08737cc --- /dev/null +++ b/OpenSim.Servers/IRestHandler.cs @@ -0,0 +1,8 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace OpenSim.Servers +{ + public delegate string RestMethod( string request, string path ); +} diff --git a/OpenSim.Servers/LocalUserProfileManager.cs b/OpenSim.Servers/LocalUserProfileManager.cs new file mode 100644 index 0000000..6166e02 --- /dev/null +++ b/OpenSim.Servers/LocalUserProfileManager.cs @@ -0,0 +1,109 @@ +/* +* Copyright (c) OpenSim project, http://sim.opensecondlife.org/ +* +* Redistribution and use in source and binary forms, with or without +* modification, are permitted provided that the following conditions are met: +* * Redistributions of source code must retain the above copyright +* notice, this list of conditions and the following disclaimer. +* * Redistributions in binary form must reproduce the above copyright +* notice, this list of conditions and the following disclaimer in the +* documentation and/or other materials provided with the distribution. +* * Neither the name of the nor the +* names of its contributors may be used to endorse or promote products +* derived from this software without specific prior written permission. +* +* THIS SOFTWARE IS PROVIDED BY ``AS IS'' AND ANY +* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +* DISCLAIMED. IN NO EVENT SHALL BE LIABLE FOR ANY +* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +* +*/ + +using System; +using System.Collections.Generic; +using System.Collections; +using System.Text; +using OpenSim.Framework.User; +using OpenSim.Framework.Grid; +using OpenSim.Framework.Inventory; +using OpenSim.Framework.Interfaces; +using libsecondlife; + +namespace OpenSim.UserServer +{ + public class LocalUserProfileManager : UserProfileManager + { + private IGridServer m_gridServer; + private int m_port; + private string m_ipAddr; + + public LocalUserProfileManager(IGridServer gridServer, int simPort, string ipAddr) + { + m_gridServer = gridServer; + m_port = simPort; + m_ipAddr = ipAddr; + } + + public override void InitUserProfiles() + { + // TODO: need to load from database + } + + public override void CustomiseResponse(ref System.Collections.Hashtable response, UserProfile theUser) + { + Int32 circode = (Int32)response["circuit_code"]; + theUser.AddSimCircuit((uint)circode, LLUUID.Random()); + response["home"] = "{'region_handle':[r" + (997 * 256).ToString() + ",r" + (996 * 256).ToString() + "], 'position':[r" + theUser.homepos.X.ToString() + ",r" + theUser.homepos.Y.ToString() + ",r" + theUser.homepos.Z.ToString() + "], 'look_at':[r" + theUser.homelookat.X.ToString() + ",r" + theUser.homelookat.Y.ToString() + ",r" + theUser.homelookat.Z.ToString() + "]}"; + response["sim_port"] = m_port; + response["sim_ip"] = m_ipAddr; + response["region_y"] = (Int32)996 * 256; + response["region_x"] = (Int32)997* 256; + + string first; + string last; + if (response.Contains("first_name")) + { + first = (string)response["first_name"]; + } + else + { + first = "test"; + } + + if (response.Contains("last_name")) + { + last = (string)response["last_name"]; + } + else + { + last = "User"; + } + + ArrayList InventoryList = (ArrayList)response["inventory-skeleton"]; + Hashtable Inventory1 = (Hashtable)InventoryList[0]; + + Login _login = new Login(); + //copy data to login object + _login.First = first; + _login.Last = last; + _login.Agent = new LLUUID((string)response["agent_id"]) ; + _login.Session = new LLUUID((string)response["session_id"]); + _login.SecureSession = new LLUUID((string)response["secure_session_id"]); + _login.BaseFolder = null; + _login.InventoryFolder = new LLUUID((string)Inventory1["folder_id"]); + + //working on local computer if so lets add to the gridserver's list of sessions? + if (m_gridServer.GetName() == "Local") + { + Console.WriteLine("adding login data to gridserver"); + ((LocalGridBase)this.m_gridServer).AddNewSession(_login); + } + } + } +} diff --git a/OpenSim.Servers/LoginResponse.cs b/OpenSim.Servers/LoginResponse.cs new file mode 100644 index 0000000..2e29889 --- /dev/null +++ b/OpenSim.Servers/LoginResponse.cs @@ -0,0 +1,398 @@ +/* +* Copyright (c) OpenSim project, http://sim.opensecondlife.org/ +* +* Redistribution and use in source and binary forms, with or without +* modification, are permitted provided that the following conditions are met: +* * Redistributions of source code must retain the above copyright +* notice, this list of conditions and the following disclaimer. +* * Redistributions in binary form must reproduce the above copyright +* notice, this list of conditions and the following disclaimer in the +* documentation and/or other materials provided with the distribution. +* * Neither the name of the nor the +* names of its contributors may be used to endorse or promote products +* derived from this software without specific prior written permission. +* +* THIS SOFTWARE IS PROVIDED BY ``AS IS'' AND ANY +* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +* DISCLAIMED. IN NO EVENT SHALL BE LIABLE FOR ANY +* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +* +*/ + +using Nwc.XmlRpc; +using System; +using System.IO; +using System.Net; +using System.Net.Sockets; +using System.Text; +using System.Text.RegularExpressions; +using System.Threading; +using System.Collections; +using System.Security.Cryptography; +using System.Xml; +using libsecondlife; +using OpenSim; +using OpenSim.Framework.Interfaces; +using OpenSim.Framework.Grid; +using OpenSim.Framework.Inventory; +using OpenSim.Framework.User; +using OpenSim.Framework.Utilities; + +namespace OpenSim.UserServer +{ + /// + /// A temp class to handle login response. + /// Should make use of UserProfileManager where possible. + /// + + public class LoginResponse + { + private Hashtable loginFlagsHash; + private Hashtable globalTexturesHash; + private Hashtable loginError; + + private ArrayList loginFlags; + private ArrayList globalTextures; + + // Login Flags + private string dst; + private string stipendSinceLogin; + private string gendered; + private string everLoggedIn; + private string login; + private string simPort; + private string simAddress; + private string agentID; + private string sessionID; + private string secureSessionID; + private Int32 circuitCode; + + // Global Textures + private string sunTexture; + private string cloudTexture; + private string moonTexture; + + // Error Flags + private string errorReason; + private string errorMessage; + + // Response + private XmlRpcResponse xmlRpcResponse; + private XmlRpcResponse defaultXmlRpcResponse; + private string defaultTextResponse; + + public LoginResponse() + { + this.loginFlags = new ArrayList(); + this.globalTextures = new ArrayList(); + this.SetDefaultValues(); + } // LoginServer + + // This will go away as we replace new-login.dat: + private void GetDefaultResponse() + { + try + { + // read in default response string + StreamReader SR; + string lines; + SR = File.OpenText("new-login.dat"); + + this.defaultTextResponse = ""; + while (!SR.EndOfStream) + { + lines = SR.ReadLine(); + this.defaultTextResponse += lines; + } + SR.Close(); + this.defaultXmlRpcResponse = (XmlRpcResponse)(new XmlRpcResponseDeserializer()).Deserialize(this.defaultTextResponse); + } + catch (Exception E) + { + Console.WriteLine(E.ToString()); + } + } // GetDefaultResponse + + public void SetDefaultValues() + { + this.GetDefaultResponse(); + + this.DST = "N"; + this.StipendSinceLogin = "N"; + this.Gendered = "Y"; + this.EverLoggedIn = "Y"; + this.login = "false"; + + this.SunTexture = "cce0f112-878f-4586-a2e2-a8f104bba271"; + this.CloudTexture = "fc4b9f0b-d008-45c6-96a4-01dd947ac621"; + this.MoonTexture = "fc4b9f0b-d008-45c6-96a4-01dd947ac621"; + + this.ErrorMessage = "You have entered an invalid name/password combination. Check Caps/lock."; + this.ErrorReason = "key"; + + } // SetDefaultValues + + private XmlRpcResponse GenerateResponse(string reason, string message, string login) + { + // Overwrite any default values; + this.xmlRpcResponse = new XmlRpcResponse(); + + // Ensure Login Failed message/reason; + this.ErrorMessage = message; + this.ErrorReason = reason; + + this.loginError = new Hashtable(); + this.loginError["reason"] = this.ErrorReason; + this.loginError["message"] = this.ErrorMessage; + this.loginError["login"] = login; + this.xmlRpcResponse.Value = this.loginError; + return (this.xmlRpcResponse); + } // GenerateResponse + + public XmlRpcResponse LoginFailedResponse() + { + return (this.GenerateResponse("key", "You have entered an invalid name/password combination. Check Caps/lock.", "false")); + } // LoginFailedResponse + + public XmlRpcResponse ConnectionFailedResponse() + { + return (this.LoginFailedResponse()); + } // CreateErrorConnectingToGridResponse() + + public XmlRpcResponse CreateAlreadyLoggedInResponse() + { + return(this.GenerateResponse("presence", "You appear to be already logged in, if this is not the case please wait for your session to timeout, if this takes longer than a few minutes please contact the grid owner", "false")); + } // CreateAlreadyLoggedInResponse() + + public XmlRpcResponse ToXmlRpcResponse() + { + this.xmlRpcResponse = this.defaultXmlRpcResponse; + Hashtable responseData = (Hashtable)this.xmlRpcResponse.Value; + + this.loginFlagsHash = new Hashtable(); + this.loginFlagsHash["daylight_savings"] = this.DST; + this.loginFlagsHash["stipend_since_login"] = this.StipendSinceLogin; + this.loginFlagsHash["gendered"] = this.Gendered; + this.loginFlagsHash["ever_logged_in"] = this.EverLoggedIn; + this.loginFlags.Add(this.loginFlagsHash); + + this.globalTexturesHash = new Hashtable(); + this.globalTexturesHash["sun_texture_id"] = this.SunTexture; + this.globalTexturesHash["cloud_texture_id"] = this.CloudTexture; + this.globalTexturesHash["moon_texture_id"] = this.MoonTexture; + this.globalTextures.Add(this.globalTexturesHash); + + responseData["sim_port"] = this.SimPort; + responseData["sim_ip"] = this.SimAddress; + responseData["agent_id"] = this.AgentID; + responseData["session_id"] = this.SessionID; + responseData["secure_session_id"] = this.SecureSessionID; + responseData["circuit_code"] = this.CircuitCode; + responseData["seconds_since_epoch"] = (Int32)(DateTime.UtcNow - new DateTime(1970, 1, 1)).TotalSeconds; + responseData["login-flags"] = this.loginFlags; + responseData["global-textures"] = this.globalTextures; + + return (this.xmlRpcResponse); + + } // ToXmlRpcResponse + + public string Login + { + get + { + return this.login; + } + set + { + this.login = value; + } + } // Login + + public string DST + { + get + { + return this.dst; + } + set + { + this.dst = value; + } + } // DST + + public string StipendSinceLogin + { + get + { + return this.stipendSinceLogin; + } + set + { + this.stipendSinceLogin = value; + } + } // StipendSinceLogin + + public string Gendered + { + get + { + return this.gendered; + } + set + { + this.gendered = value; + } + } // Gendered + + public string EverLoggedIn + { + get + { + return this.everLoggedIn; + } + set + { + this.everLoggedIn = value; + } + } // EverLoggedIn + + public string SimPort + { + get + { + return this.simPort; + } + set + { + this.simPort = value; + } + } // SimPort + + public string SimAddress + { + get + { + return this.simAddress; + } + set + { + this.simAddress = value; + } + } // SimAddress + + public string AgentID + { + get + { + return this.agentID; + } + set + { + this.agentID = value; + } + } // AgentID + + public string SessionID + { + get + { + return this.sessionID; + } + set + { + this.sessionID = value; + } + } // SessionID + + public string SecureSessionID + { + get + { + return this.secureSessionID; + } + set + { + this.secureSessionID = value; + } + } // SecureSessionID + + public Int32 CircuitCode + { + get + { + return this.circuitCode; + } + set + { + this.circuitCode = value; + } + } // CircuitCode + + public string SunTexture + { + get + { + return this.sunTexture; + } + set + { + this.sunTexture = value; + } + } // SunTexture + + public string CloudTexture + { + get + { + return this.cloudTexture; + } + set + { + this.cloudTexture = value; + } + } // CloudTexture + + public string MoonTexture + { + get + { + return this.moonTexture; + } + set + { + this.moonTexture = value; + } + } // MoonTexture + + public string ErrorReason + { + get + { + return this.errorReason; + } + set + { + this.errorReason = value; + } + } // ErrorReason + + public string ErrorMessage + { + get + { + return this.errorMessage; + } + set + { + this.errorMessage = value; + } + } // ErrorMessage + + } // LoginResponse +} // namespace OpenSim.UserServer \ No newline at end of file diff --git a/OpenSim.Servers/LoginServer.cs b/OpenSim.Servers/LoginServer.cs new file mode 100644 index 0000000..b814639 --- /dev/null +++ b/OpenSim.Servers/LoginServer.cs @@ -0,0 +1,283 @@ +/* +* Copyright (c) OpenSim project, http://sim.opensecondlife.org/ +* +* Redistribution and use in source and binary forms, with or without +* modification, are permitted provided that the following conditions are met: +* * Redistributions of source code must retain the above copyright +* notice, this list of conditions and the following disclaimer. +* * Redistributions in binary form must reproduce the above copyright +* notice, this list of conditions and the following disclaimer in the +* documentation and/or other materials provided with the distribution. +* * Neither the name of the nor the +* names of its contributors may be used to endorse or promote products +* derived from this software without specific prior written permission. +* +* THIS SOFTWARE IS PROVIDED BY ``AS IS'' AND ANY +* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +* DISCLAIMED. IN NO EVENT SHALL BE LIABLE FOR ANY +* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +* +*/ + +using Nwc.XmlRpc; +using System; +using System.IO; +using System.Net; +using System.Net.Sockets; +using System.Text; +using System.Text.RegularExpressions; +using System.Threading; +using System.Collections; +using System.Security.Cryptography; +using System.Xml; +using libsecondlife; +using OpenSim; +using OpenSim.Framework.Interfaces; +using OpenSim.Framework.Grid; +using OpenSim.Framework.Inventory; +using OpenSim.Framework.User; +using OpenSim.Framework.Utilities; + +namespace OpenSim.UserServer +{ + /// + /// When running in local (default) mode , handles client logins. + /// + public class LoginServer : LoginService, IUserServer + { + private IGridServer m_gridServer; + public IPAddress clientAddress = IPAddress.Loopback; + public IPAddress remoteAddress = IPAddress.Any; + private int NumClients; + private string _defaultResponse; + private bool userAccounts = false; + private string _mpasswd; + private bool _needPasswd = false; + private LocalUserProfileManager userManager; + private int m_simPort; + private string m_simAddr; + + public LocalUserProfileManager LocalUserManager + { + get + { + return userManager; + } + } + + public LoginServer(IGridServer gridServer, string simAddr, int simPort, bool useAccounts) + { + m_gridServer = gridServer; + m_simPort = simPort; + m_simAddr = simAddr; + this.userAccounts = useAccounts; + } + + public void Startup() + { + this._needPasswd = false; + // read in default response string + /* StreamReader SR; + string lines; + SR = File.OpenText("new-login.dat"); + + while (!SR.EndOfStream) + { + lines = SR.ReadLine(); + _defaultResponse += lines; + } + SR.Close(); + * */ + + this._mpasswd = EncodePassword("testpass"); + + userManager = new LocalUserProfileManager(this.m_gridServer, m_simPort, m_simAddr); + //userManager.InitUserProfiles(); + userManager.SetKeys("", "", "", "Welcome to OpenSim"); + } + + public XmlRpcResponse XmlRpcLoginMethod(XmlRpcRequest request) + { + Console.WriteLine("login attempt"); + Hashtable requestData = (Hashtable)request.Params[0]; + string first; + string last; + string passwd; + LLUUID Agent; + LLUUID Session; + + LoginResponse loginResponse = new LoginResponse(); + + //get login name + if (requestData.Contains("first")) + { + first = (string)requestData["first"]; + } + else + { + first = "test"; + } + + if (requestData.Contains("last")) + { + last = (string)requestData["last"]; + } + else + { + last = "User" + NumClients.ToString(); + } + + if (requestData.Contains("passwd")) + { + passwd = (string)requestData["passwd"]; + } + else + { + passwd = "notfound"; + } + + if (!Authenticate(first, last, passwd)) + { + return loginResponse.LoginFailedResponse(); + } + + NumClients++; + + // Create a agent and session LLUUID + Agent = GetAgentId(first, last); + int SessionRand = Util.RandomClass.Next(1, 999); + Session = new LLUUID("aaaabbbb-0200-" + SessionRand.ToString("0000") + "-8664-58f53e442797"); + LLUUID secureSess = LLUUID.Random(); + + loginResponse.SimPort = m_simPort.ToString(); + loginResponse.SimAddress = m_simAddr.ToString(); + loginResponse.AgentID = Agent.ToStringHyphenated(); + loginResponse.SessionID = Session.ToStringHyphenated(); + loginResponse.SecureSessionID = secureSess.ToStringHyphenated(); + loginResponse.CircuitCode = (Int32)(Util.RandomClass.Next()); + XmlRpcResponse response = loginResponse.ToXmlRpcResponse(); + Hashtable responseData = (Hashtable)response.Value; + + // inventory + ArrayList InventoryList = (ArrayList)responseData["inventory-skeleton"]; + Hashtable Inventory1 = (Hashtable)InventoryList[0]; + Hashtable Inventory2 = (Hashtable)InventoryList[1]; + LLUUID BaseFolderID = LLUUID.Random(); + LLUUID InventoryFolderID = LLUUID.Random(); + Inventory2["name"] = "Textures"; + Inventory2["folder_id"] = BaseFolderID.ToStringHyphenated(); + Inventory2["type_default"] = 0; + Inventory1["folder_id"] = InventoryFolderID.ToStringHyphenated(); + + ArrayList InventoryRoot = (ArrayList)responseData["inventory-root"]; + Hashtable Inventoryroot = (Hashtable)InventoryRoot[0]; + Inventoryroot["folder_id"] = InventoryFolderID.ToStringHyphenated(); + + CustomiseLoginResponse(responseData, first, last); + + Login _login = new Login(); + //copy data to login object + _login.First = first; + _login.Last = last; + _login.Agent = Agent; + _login.Session = Session; + _login.SecureSession = secureSess; + _login.BaseFolder = BaseFolderID; + _login.InventoryFolder = InventoryFolderID; + + //working on local computer if so lets add to the gridserver's list of sessions? + if (m_gridServer.GetName() == "Local") + { + ((LocalGridBase)m_gridServer).AddNewSession(_login); + } + + return response; + } + + protected virtual void CustomiseLoginResponse(Hashtable responseData, string first, string last) + { + } + + protected virtual LLUUID GetAgentId(string firstName, string lastName) + { + LLUUID Agent; + int AgentRand = Util.RandomClass.Next(1, 9999); + Agent = new LLUUID("99998888-0100-" + AgentRand.ToString("0000") + "-8ec1-0b1d5cd6aead"); + return Agent; + } + + protected virtual bool Authenticate(string first, string last, string passwd) + { + if (this._needPasswd) + { + //every user needs the password to login + string encodedPass = passwd.Remove(0, 3); //remove $1$ + if (encodedPass == this._mpasswd) + { + return true; + } + else + { + return false; + } + } + else + { + //do not need password to login + return true; + } + } + + private static string EncodePassword(string passwd) + { + Byte[] originalBytes; + Byte[] encodedBytes; + MD5 md5; + + md5 = new MD5CryptoServiceProvider(); + originalBytes = ASCIIEncoding.Default.GetBytes(passwd); + encodedBytes = md5.ComputeHash(originalBytes); + + return Regex.Replace(BitConverter.ToString(encodedBytes), "-", "").ToLower(); + } + + public bool CreateUserAccount(string firstName, string lastName, string password) + { + Console.WriteLine("creating new user account"); + string mdPassword = EncodePassword(password); + Console.WriteLine("with password: " + mdPassword); + this.userManager.CreateNewProfile(firstName, lastName, mdPassword); + return true; + } + + //IUserServer implementation + public AgentInventory RequestAgentsInventory(LLUUID agentID) + { + AgentInventory aInventory = null; + if (this.userAccounts) + { + aInventory = this.userManager.GetUsersInventory(agentID); + } + + return aInventory; + } + + public bool UpdateAgentsInventory(LLUUID agentID, AgentInventory inventory) + { + return true; + } + + public void SetServerInfo(string ServerUrl, string SendKey, string RecvKey) + { + + } + } + + +} diff --git a/OpenSim.Servers/OpenSim.Servers.csproj b/OpenSim.Servers/OpenSim.Servers.csproj new file mode 100644 index 0000000..652d9ce --- /dev/null +++ b/OpenSim.Servers/OpenSim.Servers.csproj @@ -0,0 +1,115 @@ + + + Local + 8.0.50727 + 2.0 + {8BB20F0A-0000-0000-0000-000000000000} + Debug + AnyCPU + + + + OpenSim.Servers + JScript + Grid + IE50 + false + Library + + OpenSim.Servers + + + + + + False + 285212672 + False + + + TRACE;DEBUG + + True + 4096 + False + ..\bin\ + False + False + False + 4 + + + + False + 285212672 + False + + + TRACE + + False + 4096 + True + ..\bin\ + False + False + False + 4 + + + + + System.dll + False + + + System.Xml.dll + False + + + ..\bin\libsecondlife.dll + False + + + + + OpenSim.Framework + {8ACA2445-0000-0000-0000-000000000000} + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} + False + + + OpenSim.Framework.Console + {A7CD0630-0000-0000-0000-000000000000} + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} + False + + + + + Code + + + Code + + + Code + + + Code + + + Code + + + Code + + + + + + + + + + diff --git a/OpenSim.Servers/OpenSim.Servers.dll.build b/OpenSim.Servers/OpenSim.Servers.dll.build new file mode 100644 index 0000000..1d4b496 --- /dev/null +++ b/OpenSim.Servers/OpenSim.Servers.dll.build @@ -0,0 +1,48 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/OpenSim.Servers/XmlRpcMethod.cs b/OpenSim.Servers/XmlRpcMethod.cs new file mode 100644 index 0000000..2295405 --- /dev/null +++ b/OpenSim.Servers/XmlRpcMethod.cs @@ -0,0 +1,7 @@ +using System; +using Nwc.XmlRpc; + +namespace OpenSim.Servers +{ + public delegate XmlRpcResponse XmlRpcMethod( XmlRpcRequest request ); +} -- cgit v1.1