* Rex merges, Messaging server

afrisby-3
Adam Frisby 2008-02-23 02:51:54 +00:00
parent ce0d1132f8
commit 6f00175d89
3 changed files with 688 additions and 693 deletions

View File

@ -1,160 +1,157 @@
/* /*
* Copyright (c) Contributors, http://opensimulator.org/ * Copyright (c) Contributors, http://opensimulator.org/
* See CONTRIBUTORS.TXT for a full list of copyright holders. * See CONTRIBUTORS.TXT for a full list of copyright holders.
* *
* Redistribution and use in source and binary forms, with or without * Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met: * modification, are permitted provided that the following conditions are met:
* * Redistributions of source code must retain the above copyright * * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer. * notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above copyright * * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the * notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution. * documentation and/or other materials provided with the distribution.
* * Neither the name of the OpenSim Project nor the * * Neither the name of the OpenSim Project nor the
* names of its contributors may be used to endorse or promote products * names of its contributors may be used to endorse or promote products
* derived from this software without specific prior written permission. * derived from this software without specific prior written permission.
* *
* THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * 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 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
* *
*/ */
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.IO; using System.IO;
using libsecondlife; using libsecondlife;
using OpenSim.Framework; using OpenSim.Framework;
using OpenSim.Framework.Communications.Cache; using OpenSim.Framework.Communications.Cache;
using OpenSim.Framework.Console; using OpenSim.Framework.Console;
using OpenSim.Framework.Servers; using OpenSim.Framework.Servers;
namespace OpenSim.Grid.MessagingServer namespace OpenSim.Grid.MessagingServer
{ {
/// <summary> /// <summary>
/// </summary> /// </summary>
public class OpenMessage_Main : conscmd_callback public class OpenMessage_Main : BaseOpenSimServer, conscmd_callback
{ {
private MessageServerConfig Cfg; private static readonly log4net.ILog m_log = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
//public UserManager m_userManager; private MessageServerConfig Cfg;
//public UserLoginService m_loginService;
//public UserManager m_userManager;
private LogBase m_console; //public UserLoginService m_loginService;
private LLUUID m_lastCreatedUser = LLUUID.Random();
private LLUUID m_lastCreatedUser = LLUUID.Random();
[STAThread]
public static void Main(string[] args) [STAThread]
{ public static void Main(string[] args)
Console.WriteLine("Launching MessagingServer..."); {
log4net.Config.XmlConfigurator.Configure();
OpenMessage_Main messageserver = new OpenMessage_Main();
m_log.Info("Launching MessagingServer...");
messageserver.Startup();
messageserver.Work(); OpenMessage_Main messageserver = new OpenMessage_Main();
}
messageserver.Startup();
private OpenMessage_Main() messageserver.Work();
{ }
if (!Directory.Exists(Util.logDir()))
{ private OpenMessage_Main()
Directory.CreateDirectory(Util.logDir()); {
} m_console = new ConsoleBase("OpenMessage", this);
m_console = MainConsole.Instance = m_console;
new LogBase((Path.Combine(Util.logDir(), "opengrid-messagingserver-console.log")), "OpenMessage", this, true); }
MainLog.Instance = m_console;
} private void Work()
{
private void Work() m_console.Notice("Enter help for a list of commands\n");
{
m_console.Notice("Enter help for a list of commands\n"); while (true)
{
while (true) m_console.Prompt();
{ }
m_console.MainLogPrompt(); }
}
} public void Startup()
{
public void Startup() Cfg = new MessageServerConfig("MESSAGING SERVER", (Path.Combine(Util.configDir(), "MessagingServer_Config.xml")));
{
Cfg = new MessageServerConfig("MESSAGING SERVER", (Path.Combine(Util.configDir(), "MessagingServer_Config.xml"))); m_log.Info("[REGION]: Starting HTTP process");
BaseHttpServer httpServer = new BaseHttpServer(Cfg.HttpPort);
//httpServer.AddXmlRPCHandler("login_to_simulator", m_loginService.XmlRpcLoginMethod);
MainLog.Instance.Verbose("REGION", "Starting HTTP process");
BaseHttpServer httpServer = new BaseHttpServer(Cfg.HttpPort); //httpServer.AddXmlRPCHandler("get_user_by_name", m_userManager.XmlRPCGetUserMethodName);
//httpServer.AddXmlRPCHandler("get_user_by_uuid", m_userManager.XmlRPCGetUserMethodUUID);
//httpServer.AddXmlRPCHandler("login_to_simulator", m_loginService.XmlRpcLoginMethod); //httpServer.AddXmlRPCHandler("get_avatar_picker_avatar", m_userManager.XmlRPCGetAvatarPickerAvatar);
//httpServer.AddXmlRPCHandler("add_new_user_friend", m_userManager.XmlRpcResponseXmlRPCAddUserFriend);
//httpServer.AddXmlRPCHandler("get_user_by_name", m_userManager.XmlRPCGetUserMethodName); //httpServer.AddXmlRPCHandler("remove_user_friend", m_userManager.XmlRpcResponseXmlRPCRemoveUserFriend);
//httpServer.AddXmlRPCHandler("get_user_by_uuid", m_userManager.XmlRPCGetUserMethodUUID); //httpServer.AddXmlRPCHandler("update_user_friend_perms", m_userManager.XmlRpcResponseXmlRPCUpdateUserFriendPerms);
//httpServer.AddXmlRPCHandler("get_avatar_picker_avatar", m_userManager.XmlRPCGetAvatarPickerAvatar); //httpServer.AddXmlRPCHandler("get_user_friend_list", m_userManager.XmlRpcResponseXmlRPCGetUserFriendList);
//httpServer.AddXmlRPCHandler("add_new_user_friend", m_userManager.XmlRpcResponseXmlRPCAddUserFriend);
//httpServer.AddXmlRPCHandler("remove_user_friend", m_userManager.XmlRpcResponseXmlRPCRemoveUserFriend);
//httpServer.AddXmlRPCHandler("update_user_friend_perms", m_userManager.XmlRpcResponseXmlRPCUpdateUserFriendPerms); //httpServer.AddStreamHandler(
//httpServer.AddXmlRPCHandler("get_user_friend_list", m_userManager.XmlRpcResponseXmlRPCGetUserFriendList); //new RestStreamHandler("DELETE", "/usersessions/", m_userManager.RestDeleteUserSessionMethod));
httpServer.Start();
//httpServer.AddStreamHandler( m_log.Info("[SERVER]: Messageserver 0.5 - Startup complete");
//new RestStreamHandler("DELETE", "/usersessions/", m_userManager.RestDeleteUserSessionMethod)); }
httpServer.Start(); public void do_create(string what)
m_console.Status("SERVER", "Messageserver 0.4 - Startup complete"); {
} switch (what)
{
case "user":
public void do_create(string what)
{ try
switch (what) {
{ //userID =
case "user": //m_userManager.AddUserProfile(tempfirstname, templastname, tempMD5Passwd, regX, regY);
} catch (Exception ex)
try {
{ m_console.Error("[SERVER]: Error creating user: {0}", ex.ToString());
//userID = }
//m_userManager.AddUserProfile(tempfirstname, templastname, tempMD5Passwd, regX, regY);
} catch (Exception ex) try
{ {
m_console.Error("SERVER", "Error creating user: {0}", ex.ToString()); //RestObjectPoster.BeginPostObject<Guid>(m_userManager._config.InventoryUrl + "CreateInventory/",
} //userID.UUID);
}
try catch (Exception ex)
{ {
//RestObjectPoster.BeginPostObject<Guid>(m_userManager._config.InventoryUrl + "CreateInventory/", m_console.Error("[SERVER]: Error creating inventory for user: {0}", ex.ToString());
//userID.UUID); }
} // m_lastCreatedUser = userID;
catch (Exception ex) break;
{ }
m_console.Error("SERVER", "Error creating inventory for user: {0}", ex.ToString()); }
}
// m_lastCreatedUser = userID; public override void RunCmd(string cmd, string[] cmdparams)
break; {
} base.RunCmd(cmd, cmdparams);
}
switch (cmd)
public void RunCmd(string cmd, string[] cmdparams) {
{ case "help":
switch (cmd) m_console.Notice("shutdown - shutdown the message server (USE CAUTION!)");
{ break;
case "help":
m_console.Notice("shutdown - shutdown the message server (USE CAUTION!)"); case "shutdown":
break; m_console.Close();
Environment.Exit(0);
case "shutdown": break;
m_console.Close(); }
Environment.Exit(0); }
break;
} public void Show(string ShowWhat)
} {
}
public void Show(string ShowWhat) }
{ }
}
}
}

View File

@ -1,480 +1,478 @@
/* /*
* Copyright (c) Contributors, http://opensimulator.org/ * Copyright (c) Contributors, http://opensimulator.org/
* See CONTRIBUTORS.TXT for a full list of copyright holders. * See CONTRIBUTORS.TXT for a full list of copyright holders.
* *
* Redistribution and use in source and binary forms, with or without * Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met: * modification, are permitted provided that the following conditions are met:
* * Redistributions of source code must retain the above copyright * * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer. * notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above copyright * * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the * notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution. * documentation and/or other materials provided with the distribution.
* * Neither the name of the OpenSim Project nor the * * Neither the name of the OpenSim Project nor the
* names of its contributors may be used to endorse or promote products * names of its contributors may be used to endorse or promote products
* derived from this software without specific prior written permission. * derived from this software without specific prior written permission.
* *
* THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * 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 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
* *
*/ */
using System; using System;
using System.Net; using System.Net;
using System.Net.Sockets; using System.Net.Sockets;
using System.Collections; using System.Collections;
using System.Collections.Generic; using System.Collections.Generic;
//using System.Xml; //using System.Xml;
using libsecondlife; using libsecondlife;
using Nwc.XmlRpc; using Nwc.XmlRpc;
using OpenSim.Framework; using OpenSim.Framework;
using OpenSim.Framework.Console; using OpenSim.Framework.Console;
using OpenSim.Framework.Data; using OpenSim.Framework.Data;
using OpenSim.Framework.Servers; using OpenSim.Framework.Servers;
using FriendRights = libsecondlife.FriendRights; using FriendRights = libsecondlife.FriendRights;
namespace OpenSim.Grid.MessagingServer namespace OpenSim.Grid.MessagingServer
{ {
public class MessageService public class MessageService
{ {
private LogBase m_log; private static readonly log4net.ILog m_log = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
private MessageServerConfig m_cfg;
private MessageServerConfig m_cfg;
//A hashtable of all current presences this server knows about
private Hashtable m_presences = new Hashtable(); //A hashtable of all current presences this server knows about
private Hashtable m_presences = new Hashtable();
//a hashtable of all current regions this server knows about
private Hashtable m_regionInfoCache = new Hashtable(); //a hashtable of all current regions this server knows about
private Hashtable m_regionInfoCache = new Hashtable();
//A hashtable containing lists of UUIDs keyed by UUID for fast backreferencing
private Hashtable m_presence_BackReferences = new Hashtable(); //A hashtable containing lists of UUIDs keyed by UUID for fast backreferencing
private Hashtable m_presence_BackReferences = new Hashtable();
// Hashtable containing work units that need to be processed
private Hashtable m_unProcessedWorkUnits = new Hashtable(); // Hashtable containing work units that need to be processed
private Hashtable m_unProcessedWorkUnits = new Hashtable();
public MessageService(LogBase log, MessageServerConfig cfg) public MessageService(MessageServerConfig cfg)
{ {
m_log = log; m_cfg = cfg;
m_cfg = cfg; }
}
#region RegionComms Methods
#region RegionComms Methods /// <summary>
/// Informs a region about an Agent
/// <summary> /// </summary>
/// Informs a region about an Agent /// <param name="TalkingAbout">User to talk about</param>
/// </summary> /// <param name="UserToUpdate">User we're sending this too (contains the region)</param>
/// <param name="TalkingAbout">User to talk about</param> public void SendRegionPresenceUpdate(UserPresenceData TalkingAbout, UserPresenceData UserToUpdate)
/// <param name="UserToUpdate">User we're sending this too (contains the region)</param> {
public void SendRegionPresenceUpdate(UserPresenceData TalkingAbout, UserPresenceData UserToUpdate) // TODO: Fill in pertenant Presence Data from 'TalkingAbout'
{
// TODO: Fill in pertenant Presence Data from 'TalkingAbout' RegionProfileData whichRegion = UserToUpdate.regionData;
//whichRegion.httpServerURI
RegionProfileData whichRegion = UserToUpdate.regionData;
//whichRegion.httpServerURI Hashtable PresenceParams = new Hashtable();
ArrayList SendParams = new ArrayList();
Hashtable PresenceParams = new Hashtable(); SendParams.Add(PresenceParams);
ArrayList SendParams = new ArrayList();
SendParams.Add(PresenceParams); m_log.Info("[PRESENCE]: Informing " + whichRegion.regionName + " at " + whichRegion.httpServerURI);
// Send
MainLog.Instance.Verbose("PRESENCE", "Informing " + whichRegion.regionName + " at " + whichRegion.httpServerURI); XmlRpcRequest RegionReq = new XmlRpcRequest("presence_update", SendParams);
// Send XmlRpcResponse RegionResp = RegionReq.Send(whichRegion.httpServerURI, 6000);
XmlRpcRequest RegionReq = new XmlRpcRequest("presence_update", SendParams); }
XmlRpcResponse RegionResp = RegionReq.Send(whichRegion.httpServerURI, 6000);
}
#endregion
#endregion #region FriendList Methods
#region FriendList Methods
/// <summary>
/// Process Friendlist subscriptions for a user
/// <summary> /// The login method calls this for a User
/// Process Friendlist subscriptions for a user /// </summary>
/// The login method calls this for a User /// <param name="userpresence">The Agent we're processing the friendlist subscriptions</param>
/// </summary> public void ProcessFriendListSubscriptions(UserPresenceData userpresence)
/// <param name="userpresence">The Agent we're processing the friendlist subscriptions</param> {
public void ProcessFriendListSubscriptions(UserPresenceData userpresence) List<FriendListItem> uFriendList = userpresence.friendData;
{ for (int i = 0; i < uFriendList.Count; i++)
List<FriendListItem> uFriendList = userpresence.friendData; {
for (int i = 0; i < uFriendList.Count; i++) m_presence_BackReferences.Add(userpresence.agentData.AgentID, uFriendList[i].Friend);
{ m_presence_BackReferences.Add(uFriendList[i].Friend, userpresence.agentData.AgentID);
m_presence_BackReferences.Add(userpresence.agentData.AgentID, uFriendList[i].Friend);
m_presence_BackReferences.Add(uFriendList[i].Friend, userpresence.agentData.AgentID); if (m_presences.Contains(uFriendList[i].Friend))
{
if (m_presences.Contains(uFriendList[i].Friend)) UserPresenceData friendup = (UserPresenceData)m_presences[uFriendList[i]];
{ // Add backreference
UserPresenceData friendup = (UserPresenceData)m_presences[uFriendList[i]];
// Add backreference SubscribeToPresenceUpdates(userpresence, friendup, uFriendList[i],i);
}
SubscribeToPresenceUpdates(userpresence, friendup, uFriendList[i],i); }
}
} m_presences.Add(userpresence.agentData.AgentID, userpresence);
}
m_presences.Add(userpresence.agentData.AgentID, userpresence);
} /// <summary>
/// Does the necessary work to subscribe one agent to another's presence notifications
/// <summary> /// Gets called by ProcessFriendListSubscriptions. You shouldn't call this directly
/// Does the necessary work to subscribe one agent to another's presence notifications /// unless you know what you're doing
/// Gets called by ProcessFriendListSubscriptions. You shouldn't call this directly /// </summary>
/// unless you know what you're doing /// <param name="userpresence">P1</param>
/// </summary> /// <param name="friendpresence">P2</param>
/// <param name="userpresence">P1</param> /// <param name="uFriendListItem"></param>
/// <param name="friendpresence">P2</param> /// <param name="uFriendListIndex"></param>
/// <param name="uFriendListItem"></param> public void SubscribeToPresenceUpdates(UserPresenceData userpresence, UserPresenceData friendpresence,
/// <param name="uFriendListIndex"></param> FriendListItem uFriendListItem, int uFriendListIndex)
public void SubscribeToPresenceUpdates(UserPresenceData userpresence, UserPresenceData friendpresence, {
FriendListItem uFriendListItem, int uFriendListIndex)
{ if ((uFriendListItem.FriendListOwnerPerms & (uint)FriendRights.CanSeeOnline) != 0)
{
if ((uFriendListItem.FriendListOwnerPerms & (uint)FriendRights.CanSeeOnline) != 0) // Subscribe and Send Out updates
{ if (!friendpresence.subscriptionData.Contains(friendpresence.agentData.AgentID))
// Subscribe and Send Out updates {
if (!friendpresence.subscriptionData.Contains(friendpresence.agentData.AgentID)) userpresence.subscriptionData.Add(friendpresence.agentData.AgentID);
{ //Send Region Notice....
userpresence.subscriptionData.Add(friendpresence.agentData.AgentID);
//Send Region Notice.... }
else
} {
else // we need to send out online status update, but the user is already subscribed
{
// we need to send out online status update, but the user is already subscribed }
SendRegionPresenceUpdate(friendpresence, userpresence);
} }
SendRegionPresenceUpdate(friendpresence, userpresence); if ((uFriendListItem.FriendPerms & (uint)FriendRights.CanSeeOnline) != 0)
} {
if ((uFriendListItem.FriendPerms & (uint)FriendRights.CanSeeOnline) != 0) if (!friendpresence.subscriptionData.Contains(userpresence.agentData.AgentID))
{ {
if (!friendpresence.subscriptionData.Contains(userpresence.agentData.AgentID)) friendpresence.subscriptionData.Add(userpresence.agentData.AgentID);
{ //Send Region Notice....
friendpresence.subscriptionData.Add(userpresence.agentData.AgentID); }
//Send Region Notice.... else
} {
else // we need to send out online status update, but the user is already subscribed
{
// we need to send out online status update, but the user is already subscribed }
SendRegionPresenceUpdate(userpresence, friendpresence);
} }
SendRegionPresenceUpdate(userpresence, friendpresence);
} }
}
/// <summary>
/// Adds a backreference so presence specific data doesn't have to be
/// <summary> /// enumerated for each logged in user every time someone logs on or off.
/// Adds a backreference so presence specific data doesn't have to be /// </summary>
/// enumerated for each logged in user every time someone logs on or off. /// <param name="agentID"></param>
/// </summary> /// <param name="friendID"></param>
/// <param name="agentID"></param> public void addBackReference(LLUUID agentID, LLUUID friendID)
/// <param name="friendID"></param> {
public void addBackReference(LLUUID agentID, LLUUID friendID) if (m_presence_BackReferences.Contains(friendID))
{ {
if (m_presence_BackReferences.Contains(friendID)) List<LLUUID> presenseBackReferences = (List<LLUUID>)m_presence_BackReferences[friendID];
{ if (!presenseBackReferences.Contains(agentID))
List<LLUUID> presenseBackReferences = (List<LLUUID>)m_presence_BackReferences[friendID]; {
if (!presenseBackReferences.Contains(agentID)) presenseBackReferences.Add(agentID);
{ }
presenseBackReferences.Add(agentID); m_presence_BackReferences[friendID] = presenseBackReferences;
} }
m_presence_BackReferences[friendID] = presenseBackReferences; else
} {
else List<LLUUID> presenceBackReferences = new List<LLUUID>();
{ presenceBackReferences.Add(agentID);
List<LLUUID> presenceBackReferences = new List<LLUUID>(); m_presence_BackReferences[friendID] = presenceBackReferences;
presenceBackReferences.Add(agentID); }
m_presence_BackReferences[friendID] = presenceBackReferences; }
}
} /// <summary>
/// Removes a backreference to free up some memory
/// <summary> /// </summary>
/// Removes a backreference to free up some memory /// <param name="agentID"></param>
/// </summary> /// <param name="friendID"></param>
/// <param name="agentID"></param> public void removeBackReference(LLUUID agentID, LLUUID friendID)
/// <param name="friendID"></param> {
public void removeBackReference(LLUUID agentID, LLUUID friendID) if (m_presence_BackReferences.Contains(friendID))
{ {
if (m_presence_BackReferences.Contains(friendID)) List<LLUUID> presenseBackReferences = (List<LLUUID>)m_presence_BackReferences[friendID];
{ if (presenseBackReferences.Contains(agentID))
List<LLUUID> presenseBackReferences = (List<LLUUID>)m_presence_BackReferences[friendID]; {
if (presenseBackReferences.Contains(agentID)) presenseBackReferences.Remove(agentID);
{ }
presenseBackReferences.Remove(agentID);
} // If there are no more backreferences for this agent,
// remove it to free up memory.
// If there are no more backreferences for this agent, if (presenseBackReferences.Count == 0)
// remove it to free up memory. {
if (presenseBackReferences.Count == 0) m_presence_BackReferences.Remove(agentID);
{ }
m_presence_BackReferences.Remove(agentID); }
} }
} /// <summary>
} /// Logoff Processor. Call this to clean up agent presence data and send logoff presence notifications
/// <summary> /// </summary>
/// Logoff Processor. Call this to clean up agent presence data and send logoff presence notifications /// <param name="AgentID"></param>
/// </summary> private void ProcessLogOff(LLUUID AgentID)
/// <param name="AgentID"></param> {
private void ProcessLogOff(LLUUID AgentID) if (m_presences.Contains(AgentID))
{ {
if (m_presences.Contains(AgentID)) UserPresenceData AgentData = (UserPresenceData)m_presences[AgentID];
{
UserPresenceData AgentData = (UserPresenceData)m_presences[AgentID]; if (m_presence_BackReferences.Contains(AgentID))
{
if (m_presence_BackReferences.Contains(AgentID)) List<LLUUID> AgentsNeedingNotification = (List<LLUUID>)m_presence_BackReferences[AgentID];
{ for (int i = 0; i < AgentsNeedingNotification.Count; i++)
List<LLUUID> AgentsNeedingNotification = (List<LLUUID>)m_presence_BackReferences[AgentID]; {
for (int i = 0; i < AgentsNeedingNotification.Count; i++) // TODO: Do Region Notifications
{ if (m_presences.Contains(AgentsNeedingNotification[i]))
// TODO: Do Region Notifications {
if (m_presences.Contains(AgentsNeedingNotification[i])) UserPresenceData friendd = (UserPresenceData)m_presences[AgentsNeedingNotification[i]];
{
UserPresenceData friendd = (UserPresenceData)m_presences[AgentsNeedingNotification[i]]; // This might need to be enumerated and checked before we try to remove it.
friendd.subscriptionData.Remove(AgentID);
// This might need to be enumerated and checked before we try to remove it.
friendd.subscriptionData.Remove(AgentID); List<FriendListItem> fl = friendd.friendData;
for (int j = 0; j < fl.Count; j++)
List<FriendListItem> fl = friendd.friendData; {
for (int j = 0; j < fl.Count; j++) if (fl[j].Friend == AgentID)
{ {
if (fl[j].Friend == AgentID) fl[j].onlinestatus = false;
{ }
fl[j].onlinestatus = false;
} }
friendd.friendData = fl;
}
friendd.friendData = fl; SendRegionPresenceUpdate(AgentData, friendd);
SendRegionPresenceUpdate(AgentData, friendd); }
removeBackReference(AgentID, AgentsNeedingNotification[i]);
}
removeBackReference(AgentID, AgentsNeedingNotification[i]); }
}
} }
} }
}
}
#endregion
#endregion #region UserServer Comms
#region UserServer Comms /// <summary>
/// Returns a list of FriendsListItems that describe the friends and permissions in the friend relationship for LLUUID friendslistowner
/// <summary> /// </summary>
/// Returns a list of FriendsListItems that describe the friends and permissions in the friend relationship for LLUUID friendslistowner /// <param name="friendlistowner">The agent that we're retreiving the friends Data.</param>
/// </summary> public List<FriendListItem> GetUserFriendList(LLUUID friendlistowner)
/// <param name="friendlistowner">The agent that we're retreiving the friends Data.</param> {
public List<FriendListItem> GetUserFriendList(LLUUID friendlistowner) List<FriendListItem> buddylist = new List<FriendListItem>();
{
List<FriendListItem> buddylist = new List<FriendListItem>(); try
{
try Hashtable param = new Hashtable();
{ param["ownerID"] = friendlistowner.UUID.ToString();
Hashtable param = new Hashtable();
param["ownerID"] = friendlistowner.UUID.ToString(); IList parameters = new ArrayList();
parameters.Add(param);
IList parameters = new ArrayList(); XmlRpcRequest req = new XmlRpcRequest("get_user_friend_list", parameters);
parameters.Add(param); XmlRpcResponse resp = req.Send(m_cfg.UserServerURL, 3000);
XmlRpcRequest req = new XmlRpcRequest("get_user_friend_list", parameters); Hashtable respData = (Hashtable)resp.Value;
XmlRpcResponse resp = req.Send(m_cfg.UserServerURL, 3000);
Hashtable respData = (Hashtable)resp.Value; if (respData.Contains("avcount"))
{
if (respData.Contains("avcount")) buddylist = ConvertXMLRPCDataToFriendListItemList(respData);
{ }
buddylist = ConvertXMLRPCDataToFriendListItemList(respData);
} }
catch (WebException e)
} {
catch (WebException e) m_log.Warn("Error when trying to fetch Avatar's friends list: " +
{ e.Message);
MainLog.Instance.Warn("Error when trying to fetch Avatar's friends list: " + // Return Empty list (no friends)
e.Message); }
// Return Empty list (no friends) return buddylist;
}
return buddylist; }
} /// <summary>
/// Converts XMLRPC Friend List to FriendListItem Object
/// <summary> /// </summary>
/// Converts XMLRPC Friend List to FriendListItem Object /// <param name="data">XMLRPC response data Hashtable</param>
/// </summary> /// <returns></returns>
/// <param name="data">XMLRPC response data Hashtable</param> public List<FriendListItem> ConvertXMLRPCDataToFriendListItemList(Hashtable data)
/// <returns></returns> {
public List<FriendListItem> ConvertXMLRPCDataToFriendListItemList(Hashtable data) List<FriendListItem> buddylist = new List<FriendListItem>();
{ int buddycount = Convert.ToInt32((string)data["avcount"]);
List<FriendListItem> buddylist = new List<FriendListItem>();
int buddycount = Convert.ToInt32((string)data["avcount"]);
for (int i = 0; i < buddycount; i++)
{
for (int i = 0; i < buddycount; i++) FriendListItem buddylistitem = new FriendListItem();
{
FriendListItem buddylistitem = new FriendListItem(); buddylistitem.FriendListOwner = new LLUUID((string)data["ownerID" + i.ToString()]);
buddylistitem.Friend = new LLUUID((string)data["friendID" + i.ToString()]);
buddylistitem.FriendListOwner = new LLUUID((string)data["ownerID" + i.ToString()]); buddylistitem.FriendListOwnerPerms = (uint)Convert.ToInt32((string)data["ownerPerms" + i.ToString()]);
buddylistitem.Friend = new LLUUID((string)data["friendID" + i.ToString()]); buddylistitem.FriendPerms = (uint)Convert.ToInt32((string)data["friendPerms" + i.ToString()]);
buddylistitem.FriendListOwnerPerms = (uint)Convert.ToInt32((string)data["ownerPerms" + i.ToString()]);
buddylistitem.FriendPerms = (uint)Convert.ToInt32((string)data["friendPerms" + i.ToString()]); buddylist.Add(buddylistitem);
}
buddylist.Add(buddylistitem);
}
return buddylist;
}
return buddylist; /// <summary>
} /// UserServer sends an expect_user method
/// <summary> /// this handles the method and provisions the
/// UserServer sends an expect_user method /// necessary info for presence to work
/// this handles the method and provisions the /// </summary>
/// necessary info for presence to work /// <param name="request">UserServer Data</param>
/// </summary> /// <returns></returns>
/// <param name="request">UserServer Data</param> public XmlRpcResponse UserLoggedOn(XmlRpcRequest request)
/// <returns></returns> {
public XmlRpcResponse UserLoggedOn(XmlRpcRequest request)
{ Hashtable requestData = (Hashtable)request.Params[0];
AgentCircuitData agentData = new AgentCircuitData();
Hashtable requestData = (Hashtable)request.Params[0]; agentData.SessionID = new LLUUID((string)requestData["session_id"]);
AgentCircuitData agentData = new AgentCircuitData(); agentData.SecureSessionID = new LLUUID((string)requestData["secure_session_id"]);
agentData.SessionID = new LLUUID((string)requestData["session_id"]); agentData.firstname = (string)requestData["firstname"];
agentData.SecureSessionID = new LLUUID((string)requestData["secure_session_id"]); agentData.lastname = (string)requestData["lastname"];
agentData.firstname = (string)requestData["firstname"]; agentData.AgentID = new LLUUID((string)requestData["agent_id"]);
agentData.lastname = (string)requestData["lastname"]; agentData.circuitcode = Convert.ToUInt32(requestData["circuit_code"]);
agentData.AgentID = new LLUUID((string)requestData["agent_id"]); agentData.CapsPath = (string)requestData["caps_path"];
agentData.circuitcode = Convert.ToUInt32(requestData["circuit_code"]);
agentData.CapsPath = (string)requestData["caps_path"]; if (requestData.ContainsKey("child_agent") && requestData["child_agent"].Equals("1"))
{
if (requestData.ContainsKey("child_agent") && requestData["child_agent"].Equals("1")) agentData.child = true;
{ }
agentData.child = true; else
} {
else agentData.startpos =
{ new LLVector3(Convert.ToUInt32(requestData["startpos_x"]),
agentData.startpos = Convert.ToUInt32(requestData["startpos_y"]),
new LLVector3(Convert.ToUInt32(requestData["startpos_x"]), Convert.ToUInt32(requestData["startpos_z"]));
Convert.ToUInt32(requestData["startpos_y"]), agentData.child = false;
Convert.ToUInt32(requestData["startpos_z"])); }
agentData.child = false;
} ulong regionHandle = Convert.ToUInt64((string)requestData["regionhandle"]);
ulong regionHandle = Convert.ToUInt64((string)requestData["regionhandle"]); UserPresenceData up = new UserPresenceData();
up.agentData = agentData;
UserPresenceData up = new UserPresenceData(); List<FriendListItem> flData = GetUserFriendList(agentData.AgentID);
up.agentData = agentData; up.friendData = flData;
List<FriendListItem> flData = GetUserFriendList(agentData.AgentID); RegionProfileData riData = GetRegionInfo(regionHandle);
up.friendData = flData; up.regionData = riData;
RegionProfileData riData = GetRegionInfo(regionHandle);
up.regionData = riData; ProcessFriendListSubscriptions(up);
ProcessFriendListSubscriptions(up);
return new XmlRpcResponse();
}
return new XmlRpcResponse();
} /// <summary>
/// The UserServer got a Logoff message
/// <summary> /// Cleanup time for that user. Send out presence notifications
/// The UserServer got a Logoff message /// </summary>
/// Cleanup time for that user. Send out presence notifications /// <param name="request"></param>
/// </summary> /// <returns></returns>
/// <param name="request"></param> public XmlRpcResponse UserLoggedOff(XmlRpcRequest request)
/// <returns></returns> {
public XmlRpcResponse UserLoggedOff(XmlRpcRequest request)
{ Hashtable requestData = (Hashtable)request.Params[0];
Hashtable requestData = (Hashtable)request.Params[0]; LLUUID AgentID = new LLUUID((string)requestData["agent_id"]);
LLUUID AgentID = new LLUUID((string)requestData["agent_id"]);
//ProcessLogOff(AgentID);
ProcessLogOff(AgentID);
return new XmlRpcResponse();
}
return new XmlRpcResponse();
} #endregion
#region regioninfo gathering
#endregion
#region regioninfo gathering /// <summary>
/// Gets and caches a RegionInfo object from the gridserver based on regionhandle
/// <summary> /// if the regionhandle is already cached, use the cached values
/// Gets and caches a RegionInfo object from the gridserver based on regionhandle /// </summary>
/// if the regionhandle is already cached, use the cached values /// <param name="regionhandle">handle to the XY of the region we're looking for</param>
/// </summary> /// <returns>A RegionInfo object to stick in the presence info</returns>
/// <param name="regionhandle">handle to the XY of the region we're looking for</param> public RegionProfileData GetRegionInfo(ulong regionhandle)
/// <returns>A RegionInfo object to stick in the presence info</returns> {
public RegionProfileData GetRegionInfo(ulong regionhandle) RegionProfileData regionInfo = null;
{ if (m_regionInfoCache.Contains(regionhandle))
RegionProfileData regionInfo = null; {
if (m_regionInfoCache.Contains(regionhandle)) regionInfo = (RegionProfileData)m_regionInfoCache[regionhandle];
{ }
regionInfo = (RegionProfileData)m_regionInfoCache[regionhandle]; else
} {
else regionInfo = RequestRegionInfo(regionhandle);
{ }
regionInfo = RequestRegionInfo(regionhandle); return regionInfo;
} }
return regionInfo; /// <summary>
} /// Get RegionProfileData from the GridServer
/// <summary> /// We'll Cache this information and use it for presence updates
/// Get RegionProfileData from the GridServer /// </summary>
/// We'll Cache this information and use it for presence updates /// <param name="regionHandle"></param>
/// </summary> /// <returns></returns>
/// <param name="regionHandle"></param> public RegionProfileData RequestRegionInfo(ulong regionHandle)
/// <returns></returns> { RegionProfileData regionProfile = null;
public RegionProfileData RequestRegionInfo(ulong regionHandle) try
{ RegionProfileData regionProfile = null; {
try
{ Hashtable requestData = new Hashtable();
requestData["region_handle"] = regionHandle.ToString();
Hashtable requestData = new Hashtable(); requestData["authkey"] = m_cfg.GridSendKey;
requestData["region_handle"] = regionHandle.ToString(); ArrayList SendParams = new ArrayList();
requestData["authkey"] = m_cfg.GridSendKey; SendParams.Add(requestData);
ArrayList SendParams = new ArrayList(); XmlRpcRequest GridReq = new XmlRpcRequest("simulator_data_request", SendParams);
SendParams.Add(requestData); XmlRpcResponse GridResp = GridReq.Send(m_cfg.GridServerURL, 3000);
XmlRpcRequest GridReq = new XmlRpcRequest("simulator_data_request", SendParams);
XmlRpcResponse GridResp = GridReq.Send(m_cfg.GridServerURL, 3000); Hashtable responseData = (Hashtable)GridResp.Value;
Hashtable responseData = (Hashtable)GridResp.Value; if (responseData.ContainsKey("error"))
{
if (responseData.ContainsKey("error")) m_log.Error("[GRID]: error received from grid server" + responseData["error"]);
{ return null;
m_log.Error("GRID","error received from grid server" + responseData["error"]); }
return null;
} uint regX = Convert.ToUInt32((string)responseData["region_locx"]);
uint regY = Convert.ToUInt32((string)responseData["region_locy"]);
uint regX = Convert.ToUInt32((string)responseData["region_locx"]); string internalIpStr = (string)responseData["sim_ip"];
uint regY = Convert.ToUInt32((string)responseData["region_locy"]); uint port = Convert.ToUInt32(responseData["sim_port"]);
string internalIpStr = (string)responseData["sim_ip"]; string externalUri = (string)responseData["sim_uri"];
uint port = Convert.ToUInt32(responseData["sim_port"]); string neighbourExternalUri = externalUri;
string externalUri = (string)responseData["sim_uri"];
string neighbourExternalUri = externalUri; regionProfile = new RegionProfileData();
regionProfile.httpPort = (uint)Convert.ToInt32((string)responseData["http_port"]);
regionProfile = new RegionProfileData(); regionProfile.httpServerURI = "http://" + internalIpStr + ":" + regionProfile.httpPort + "/";
regionProfile.httpPort = (uint)Convert.ToInt32((string)responseData["http_port"]); regionProfile.regionHandle = Helpers.UIntsToLong((regX * Constants.RegionSize), (regY * Constants.RegionSize));
regionProfile.httpServerURI = "http://" + internalIpStr + ":" + regionProfile.httpPort + "/"; regionProfile.regionLocX = regX;
regionProfile.regionHandle = Helpers.UIntsToLong((regX * 256), (regY * 256)); regionProfile.regionLocY = regY;
regionProfile.regionLocX = regX;
regionProfile.regionLocY = regY; regionProfile.remotingPort = Convert.ToUInt32((string)responseData["remoting_port"]);
regionProfile.UUID = new LLUUID((string)responseData["region_UUID"]);
regionProfile.remotingPort = Convert.ToUInt32((string)responseData["remoting_port"]); regionProfile.regionName = (string)responseData["region_name"];
regionProfile.UUID = new LLUUID((string)responseData["region_UUID"]);
regionProfile.regionName = (string)responseData["region_name"]; m_regionInfoCache.Add(regionHandle, regionProfile);
}
m_regionInfoCache.Add(regionHandle, regionProfile); catch (WebException)
} {
catch (WebException) m_log.Error("[GRID]: " +
{ "Region lookup failed for: " + regionHandle.ToString() +
MainLog.Instance.Error("GRID", " - Is the GridServer down?");
"Region lookup failed for: " + regionHandle.ToString() + return null;
" - Is the GridServer down?"); }
return null;
}
return regionProfile;
}
return regionProfile; #endregion
} }
#endregion
} }
}

View File

@ -1,53 +1,53 @@
/* /*
* Copyright (c) Contributors, http://opensimulator.org/ * Copyright (c) Contributors, http://opensimulator.org/
* See CONTRIBUTORS.TXT for a full list of copyright holders. * See CONTRIBUTORS.TXT for a full list of copyright holders.
* *
* Redistribution and use in source and binary forms, with or without * Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met: * modification, are permitted provided that the following conditions are met:
* * Redistributions of source code must retain the above copyright * * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer. * notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above copyright * * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the * notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution. * documentation and/or other materials provided with the distribution.
* * Neither the name of the OpenSim Project nor the * * Neither the name of the OpenSim Project nor the
* names of its contributors may be used to endorse or promote products * names of its contributors may be used to endorse or promote products
* derived from this software without specific prior written permission. * derived from this software without specific prior written permission.
* *
* THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * 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 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
* *
*/ */
using System; using System;
using System.Collections; using System.Collections;
using System.Collections.Generic; using System.Collections.Generic;
using libsecondlife; using libsecondlife;
using OpenSim.Framework; using OpenSim.Framework;
using OpenSim.Framework.Data; using OpenSim.Framework.Data;
namespace OpenSim.Grid.MessagingServer namespace OpenSim.Grid.MessagingServer
{ {
public class UserPresenceData public class UserPresenceData
{ {
public AgentCircuitData agentData = new AgentCircuitData(); public AgentCircuitData agentData = new AgentCircuitData();
public RegionProfileData regionData = new RegionProfileData(); public RegionProfileData regionData = new RegionProfileData();
public string httpURI = ""; public string httpURI = String.Empty;
public List<FriendListItem> friendData = new List<FriendListItem> (); public List<FriendListItem> friendData = new List<FriendListItem> ();
public List<LLUUID> subscriptionData = new List<LLUUID>(); public List<LLUUID> subscriptionData = new List<LLUUID>();
public UserPresenceData() public UserPresenceData()
{ {
} }
} }
} }