public override string Execute(string[] args, LLUUID fromAgentID) { if (args.Length != 1) return Description; LLUUID targetID; ReceivedProperties = false; ReceivedInterests = false; try { targetID = new LLUUID(args[0]); } catch (Exception) { return Description; } Client.Avatars.RequestAvatarProperties(targetID); ReceivedProfileEvent.Reset(); ReceivedProfileEvent.WaitOne(5000, false); if (!ReceivedInterests || !ReceivedProperties) return "Failed to retrieve a complete profile for that UUID"; Client.Self.ProfileInterests = Interests; Client.Self.ProfileProperties = Properties; Client.Self.SetAvatarInformation(); return "Synchronized our profile to the profile of " + targetID.ToStringHyphenated(); }
static void Main(string[] args) { SecondLife client = new SecondLife(); if (args.Length < 4) { Console.WriteLine("Usage: Key2Name [loginfirstname] [loginlastname] [password] [key]"); return; } Console.WriteLine("Attempting to connect and login to Second Life."); // Setup Login to Second Life Dictionary<string, object> loginParams = client.Network.DefaultLoginValues(args[0], args[1], args[2], "00:00:00:00:00:00", "last", "Win", "0", "key2name", "*****@*****.**"); Dictionary<string, object> loginReply = new Dictionary<string, object>(); if (!client.Network.Login(loginParams)) { // Login failed Console.WriteLine("Error logging in: " + client.Network.LoginError); return; } AvatarTracker avatarTracker = new AvatarTracker(client); LLUUID lookup = new LLUUID(args[3]); Console.WriteLine("Looking up name for " + lookup.ToStringHyphenated()); string name = avatarTracker.GetAvatarName(lookup); Console.WriteLine("Name: " + name + ". Press enter to logout."); Console.ReadLine(); client.Network.Logout(); }
static void Main(string[] args) { if (args.Length < 4) { Console.WriteLine("Usage: Key2Name [loginfirstname] [loginlastname] [password] [key]"); return; } SecondLife client = new SecondLife(); Console.WriteLine("Attempting to connect and login to Second Life."); // Login to Second Life if (!client.Network.Login(args[0], args[1], args[2], "key2name", "*****@*****.**")) { // Login failed Console.WriteLine("Error logging in: " + client.Network.LoginMessage); return; } AvatarTracker avatarTracker = new AvatarTracker(client); LLUUID lookup = new LLUUID(); LLUUID.TryParse(args[3], out lookup); Console.WriteLine("Looking up name for " + lookup.ToStringHyphenated()); string name = avatarTracker.GetAvatarName(lookup); Console.WriteLine("Name: " + name + Environment.NewLine + "Press enter to logout."); Console.ReadLine(); client.Network.Logout(); }
private void Avatars_OnEffect(MainAvatar.EffectType type, LLUUID sourceID, LLUUID targetID, LLVector3d targetPos, float duration, LLUUID id) { if (ShowEffects) Console.WriteLine( "ViewerEffect [{0}]: SourceID: {1} TargetID: {2} TargetPos: {3} Duration: {4} ID: {5}", type, sourceID.ToStringHyphenated(), targetID.ToStringHyphenated(), targetPos, duration, id.ToStringHyphenated()); }
private void Avatars_OnLookAt(LLUUID sourceID, LLUUID targetID, LLVector3d targetPos, MainAvatar.LookAtType lookType, float duration, LLUUID id) { if (ShowEffects) Console.WriteLine( "ViewerEffect [LookAt]: SourceID: {0} TargetID: {1} TargetPos: {2} Type: {3} Duration: {4} ID: {5}", sourceID.ToStringHyphenated(), targetID.ToStringHyphenated(), targetPos, lookType, duration, id.ToStringHyphenated()); }
/// <summary> /// /// </summary> /// <param name="prey"></param> public void KickUser(LLUUID prey) { EstateOwnerMessagePacket estate = new EstateOwnerMessagePacket(); estate.AgentData.AgentID = Client.Network.AgentID; estate.AgentData.SessionID = Client.Network.SessionID; estate.MethodData.Invoice = LLUUID.GenerateUUID(); estate.MethodData.Method = Helpers.StringToField("kick"); estate.ParamList = new EstateOwnerMessagePacket.ParamListBlock[2]; estate.ParamList[0].Parameter = Helpers.StringToField(Client.Network.AgentID.ToStringHyphenated()); estate.ParamList[1].Parameter = Helpers.StringToField(prey.ToStringHyphenated()); Client.Network.SendPacket((Packet)estate); }
/// <summary> /// /// </summary> /// <param name="prey"></param> public void KickUser(LLUUID prey) { EstateOwnerMessagePacket estate = new EstateOwnerMessagePacket(); estate.AgentData.AgentID = Client.Network.AgentID; estate.AgentData.SessionID = Client.Network.SessionID; estate.MethodData.Invoice = LLUUID.GenerateUUID(); estate.MethodData.Method = Helpers.StringToField("kick"); estate.ParamList = new EstateOwnerMessagePacket.ParamListBlock[2]; estate.ParamList[0].Parameter = Helpers.StringToField(Client.Network.AgentID.ToStringHyphenated()); estate.ParamList[1].Parameter = Helpers.StringToField(prey.ToStringHyphenated()); Client.Network.SendPacket((Packet)estate); }
public override string Execute(string[] args, LLUUID fromAgentID) { if (args.Length != 1) return Description; LLUUID targetID; ReceivedProperties = false; ReceivedInterests = false; ReceivedGroups = false; try { targetID = new LLUUID(args[0]); } catch (Exception) { return Description; } // Request all of the packets that make up an avatar profile Client.Avatars.RequestAvatarProperties(targetID); // Wait for all the packets to arrive ReceivedProfileEvent.Reset(); ReceivedProfileEvent.WaitOne(5000, false); // Check if everything showed up if (!ReceivedInterests || !ReceivedProperties || !ReceivedGroups) return "Failed to retrieve a complete profile for that UUID"; // Synchronize our profile Client.Self.UpdateInterests(Interests); Client.Self.UpdateProfile(Properties); // TODO: Leave all the groups we're currently a member of? This could // break TestClient connectivity that might be relying on group authentication // Attempt to join all the groups foreach (LLUUID groupID in Groups) { Client.Groups.RequestJoinGroup(groupID); } return "Synchronized our profile to the profile of " + targetID.ToStringHyphenated(); }
public void LLUUIDs() { // Creation LLUUID a = new LLUUID(); byte[] bytes = a.GetBytes(); for (int i = 0; i < 16; i++) Assert.IsTrue(bytes[i] == 0x00); // Comparison a = new LLUUID(new byte[] { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, 0xFF, 0xFF }, 0); LLUUID b = new LLUUID(new byte[] { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F }, 0); Assert.IsTrue(a == b, "LLUUID comparison operator failed, " + a.ToString() + " should equal " + b.ToString()); // From string a = new LLUUID(new byte[] { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F }, 0); string zeroonetwo = "00010203-0405-0607-0809-0a0b0c0d0e0f"; b = new LLUUID(zeroonetwo); Assert.IsTrue(a == b, "LLUUID hyphenated string constructor failed, should have " + a.ToString() + " but we got " + b.ToString()); // ToString() string one = a.ToString(); string two = b.ToString(); Assert.IsTrue(a == b); one = a.ToStringHyphenated(); two = b.ToStringHyphenated(); Assert.IsTrue(a == b); Assert.IsTrue(a == zeroonetwo); // TODO: CRC test }
private void NewImageRetrievedCallBack( LLUUID ImageID, byte[] data, bool wasCached, string statusMsg ) { if (wasCached) { Console.WriteLine("Cache ( " + data.Length + "): " + ImageID); } else { if (data == null) { Console.WriteLine("Image Data is null (" + statusMsg + "): " + ImageID); } else { Console.WriteLine("Finished ( " + data.Length + "): " + ImageID); String filename = Path.Combine(OutputDirectory, ImageID.ToStringHyphenated()) + ".tif"; TiffJob tj = new TiffJob(filename, data); Thread t = new Thread(tj.RunMe); t.Start(); } } }
/// <summary> /// Send an avatar back to their home location /// </summary> /// <param name="pest">Key of avatar to send home</param> public void TeleportHomeUser(LLUUID pest) { List<string> listParams = new List<string>(); listParams.Add(Client.Network.AgentID.ToStringHyphenated()); listParams.Add(pest.ToStringHyphenated()); EstateOwnerMessage("teleporthomeuser", listParams); }
/// <summary>Unban an avatar from an estate</summary> public void UnbanUser(LLUUID userID) { List<string> listParams = new List<string>(); listParams.Add(Client.Network.AgentID.ToStringHyphenated()); listParams.Add(EstateAccessDelta.UnbanUser.ToString()); listParams.Add(userID.ToStringHyphenated()); EstateOwnerMessage("estateaccessdelta", listParams); }
/// <summary> /// Kick an avatar from an estate /// </summary> /// <param name="prey">Key of Avatar to kick</param> public void KickUser(LLUUID userID) { EstateOwnerMessage("kickestate", userID.ToStringHyphenated()); }
void Groups_OnGroupJoined(LLUUID groupID, bool success) { Console.WriteLine(Client.ToString() + (success ? " joined " : " failed to join ") + groupID.ToStringHyphenated()); if (success) { Console.WriteLine(Client.ToString() + " setting " + groupID.ToStringHyphenated() + " as the active group"); Client.Groups.ActivateGroup(groupID); } }
// ProxyLogin: proxy a login request private void ProxyLogin(StreamReader reader, StreamWriter writer) { lock(this) { string line; int contentLength = 0; // read HTTP header do { // read one line of the header line = reader.ReadLine(); // check for premature EOF if (line == null) throw new Exception("EOF in client HTTP header"); // look for Content-Length Match match = (new Regex(@"Content-Length: (\d+)$")).Match(line); if (match.Success) contentLength = Convert.ToInt32(match.Groups[1].Captures[0].ToString()); } while (line != ""); // read the HTTP body into a buffer char[] content = new char[contentLength]; reader.Read(content, 0, contentLength); XmlRpcRequest request = (XmlRpcRequest)(new XmlRpcRequestDeserializer()).Deserialize(new String(content)); if(request.MethodName == "login_to_simulator") { Hashtable requestData = (Hashtable)request.Params[0]; string first; string last; string passwd; LLUUID Agent; LLUUID Session; //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)) { // Fail miserably writer.WriteLine("HTTP/1.0 403 Authentication Forbidden"); writer.WriteLine(); return; } NumClients++; //create a agent and session LLUUID Agent = GetAgentId( first, last ); int SessionRand = this.RandomClass.Next(1,999); Session = new LLUUID("aaaabbbb-0200-"+SessionRand.ToString("0000")+"-8664-58f53e442797"); XmlRpcResponse response =(XmlRpcResponse)(new XmlRpcResponseDeserializer()).Deserialize(this._defaultResponse); Hashtable responseData = (Hashtable)response.Value; responseData["sim_port"] = Globals.Instance.SimPort; responseData["sim_ip"] = Globals.Instance.SimIPAddress; responseData["agent_id"] = Agent.ToStringHyphenated(); responseData["session_id"] = Session.ToStringHyphenated(); 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"] = "Base"; Inventory2["folder_id"] = BaseFolderID.ToStringHyphenated(); Inventory2["type_default"] =6; 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 ); this._login = new Logon(); //copy data to login object _login.First = first; _login.Last = last; _login.Agent = Agent; _login.Session = Session; _login.BaseFolder = BaseFolderID; _login.InventoryFolder = InventoryFolderID; lock(Globals.Instance.IncomingLogins) { Globals.Instance.IncomingLogins.Add(_login); } // forward the XML-RPC response to the client writer.WriteLine("HTTP/1.0 200 OK"); writer.WriteLine("Content-type: text/xml"); writer.WriteLine(); XmlTextWriter responseWriter = new XmlTextWriter(writer); XmlRpcResponseSerializer.Singleton.Serialize(responseWriter, response); responseWriter.Close(); } else { writer.WriteLine("HTTP/1.0 403 Authentication Forbidden"); writer.WriteLine(); } } }
public bool UpdateItemDetails(LLUUID itemID, UpdateInventoryItemPacket.InventoryDataBlock packet) { Console.WriteLine("updating inventory item details"); if (this.InventoryItems.ContainsKey(itemID)) { Console.WriteLine("changing name to "+ Util.FieldToString(packet.Name)); InventoryItem Item = this.InventoryItems[itemID]; Item.Name = Util.FieldToString(packet.Name); Console.WriteLine("updated inventory item " + itemID.ToStringHyphenated()); //TODO need to update the rest of the info } return true; }
private void CacheImage(LLUUID ImageID, byte[] ImageData) { switch (CacheType) { case CacheTypes.Memory: CacheTable[ImageID] = ImageData; break; case CacheTypes.Disk: String filepath = Path.Combine(CacheDirectory, ImageID.ToStringHyphenated()); File.WriteAllBytes(filepath, ImageData); CachedDiskIndex.Add(ImageID); break; default: break; } }
public bool UpdateItemAsset(LLUUID itemID, AssetBase asset) { if(this.InventoryItems.ContainsKey(itemID)) { InventoryItem Item = this.InventoryItems[itemID]; Item.AssetID = asset.FullID; Console.WriteLine("updated inventory item " + itemID.ToStringHyphenated() + " so it now is set to asset " + asset.FullID.ToStringHyphenated()); //TODO need to update the rest of the info } return true; }
public bool isCachedImage(LLUUID ImageID) { if (ImageID == null) { throw new Exception("Don't go calling isCachedImage() with a null..."); } switch (CacheType) { case CacheTypes.Memory: return CacheTable.ContainsKey(ImageID); case CacheTypes.Disk: if (CachedDiskIndex.Contains(ImageID)) { return true; } else { String filepath = Path.Combine(CacheDirectory, ImageID.ToStringHyphenated()); if (File.Exists(filepath)) { CachedDiskIndex.Add(ImageID); return true; } else { return false; } } default: return false; } }
public static void LLSDWriteOne(XmlTextWriter writer, object obj) { if (obj == null) { writer.WriteStartElement("", "undef", ""); writer.WriteEndElement(); return; } Type t = obj.GetType(); if (t == typeof(string)) { writer.WriteStartElement("", "string", ""); writer.WriteString((string)obj); writer.WriteEndElement(); } else if (t == typeof(long)) { writer.WriteStartElement("", "integer", ""); writer.WriteString(obj.ToString()); writer.WriteEndElement(); } else if (t == typeof(double)) { writer.WriteStartElement("", "real", ""); writer.WriteString(obj.ToString()); writer.WriteEndElement(); } else if (t == typeof(bool)) { bool b = (bool)obj; writer.WriteStartElement("", "boolean", ""); if (b) { writer.WriteString("1"); } else { writer.WriteString("0"); } writer.WriteEndElement(); } else if (t == typeof(LLUUID)) { LLUUID u = (LLUUID)obj; writer.WriteStartElement("", "uuid", ""); writer.WriteString(u.ToStringHyphenated()); writer.WriteEndElement(); } else if (t == typeof(Hashtable)) { Hashtable h = (Hashtable)obj; writer.WriteStartElement("", "map", ""); foreach (string key in h.Keys) { writer.WriteStartElement("", "key", ""); writer.WriteString(key); writer.WriteEndElement(); LLSDWriteOne(writer, h[key]); } writer.WriteEndElement(); } else if (t == typeof(ArrayList)) { ArrayList a = (ArrayList)obj; writer.WriteStartElement("", "array", ""); foreach (object item in a) { LLSDWriteOne(writer, item); } writer.WriteEndElement(); } else if (t == typeof(byte[])) { byte[] b = (byte[])obj; writer.WriteStartElement("", "binary", ""); writer.WriteStartAttribute("", "encoding", ""); writer.WriteString("base64"); writer.WriteEndAttribute(); char[] tmp = new char[b.Length * 2]; // too much int i = Convert.ToBase64CharArray(b, 0, b.Length, tmp, 0); Array.Resize(ref tmp, i); writer.WriteString(new String(tmp)); writer.WriteEndElement(); } else { throw new LLSDSerializeException("Unknown type " + t.Name); } }
/// <summary> /// By using the bracket operator on this class, the program can get the /// InventoryObject designated by the specified uuid. If the value for the corresponding /// UUID is null, the call is equivelant to a call to <code>RemoveNodeFor(this[uuid])</code>. /// If the value is non-null, it is equivelant to a call to <code>UpdateNodeFor(value)</code>, /// the uuid parameter is ignored. /// </summary> /// <param name="uuid">The UUID of the InventoryObject to get or set, ignored if set to non-null value.</param> /// <returns>The InventoryObject corresponding to <code>uuid</code>.</returns> public InventoryBase this[LLUUID uuid] { get { InventoryNode node = Items[uuid]; return node.Data; } set { if (value != null) { // Log a warning if there is a UUID mismatch, this will cause problems if (value.UUID != uuid) Client.Log("Inventory[uuid]: uuid " + uuid.ToStringHyphenated() + " is not equal to value.UUID " + value.UUID.ToStringHyphenated(), Helpers.LogLevel.Warning); UpdateNodeFor(value); } else { InventoryNode node; if (Items.TryGetValue(uuid, out node)) { RemoveNodeFor(node.Data); } } } }
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(regionX, regionY); //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; }
/// <summary> /// Requests an image from SecondLife and blocks until it's received. /// </summary> /// <param name="ImageID">The Image's AssetID</param> public byte[] RequestImage(LLUUID ImageID) { byte[] imgData = CachedImage(ImageID); if (imgData != null) { return imgData; } TransferRequest tr; lock (htDownloadRequests) { if (htDownloadRequests.ContainsKey(ImageID) == false) { tr = new TransferRequest(); tr.Size = int.MaxValue; // Number of bytes expected tr.Received = 0; // Number of bytes received tr.TimeOfLastPacket = Helpers.GetUnixTime(); // last time we recevied a packet for this request htDownloadRequests[ImageID] = tr; Packet packet = ImagePacketHelper.RequestImage(ImageID); slClient.Network.SendPacket(packet); } else { tr = htDownloadRequests[ImageID]; } } // Wait for transfer to complete. while( !tr.Completed.WaitOne(10000, false) ) //If it times out, then check, otherwise loop again until WaitOne returns true { slClient.Log("Warning long running texture download: " + ImageID.ToStringHyphenated(), Helpers.LogLevel.Warning); Console.WriteLine("Downloaded : " + tr.Received); if( (Helpers.GetUnixTime() - tr.TimeOfLastPacket) > 10 ) { tr.Status = false; tr.StatusMsg = "Timeout while downloading image."; slClient.Log(tr.StatusMsg, Helpers.LogLevel.Error); tr.Completed.Set(); } } if (tr.Status == true) { return tr.AssetData; } else { throw new Exception("RequestImage: " + tr.StatusMsg); } }
/// <summary>Unban an avatar from an estate</summary> public void UnbanUser(LLUUID userID) { List<string> listParams = new List<string>(); uint flag = (uint)EstateAccessDelta.BanUser; listParams.Add(Client.Self.AgentID.ToStringHyphenated()); listParams.Add(flag.ToString()); listParams.Add(userID.ToStringHyphenated()); EstateOwnerMessage("estateaccessdelta", listParams); }
private byte[] CachedImage(LLUUID ImageID) { switch (CacheType) { case CacheTypes.Memory: if (CacheTable.ContainsKey(ImageID)) { return CacheTable[ImageID]; } else { return null; } case CacheTypes.Disk: String filepath = Path.Combine(CacheDirectory, ImageID.ToStringHyphenated()); if (File.Exists(filepath)) { return File.ReadAllBytes(filepath); } else { return null; } default: return null; } }
/// <summary> /// Used to track when inventory is dropped onto/into agent /// </summary> /// <param name="fromAgentID"></param> /// <param name="fromAgentName"></param> /// <param name="toAgentID"></param> /// <param name="parentEstateID"></param> /// <param name="regionID"></param> /// <param name="position"></param> /// <param name="dialog"></param> /// <param name="groupIM"></param> /// <param name="imSessionID"></param> /// <param name="timestamp"></param> /// <param name="message"></param> /// <param name="offline"></param> /// <param name="binaryBucket"></param> void Self_OnInstantMessage(LLUUID fromAgentID, string fromAgentName, LLUUID toAgentID, uint parentEstateID, LLUUID regionID, LLVector3 position, MainAvatar.InstantMessageDialog dialog, bool groupIM, LLUUID imSessionID, DateTime timestamp, string message, MainAvatar.InstantMessageOnline offline, byte[] binaryBucket) { if ((dialog == MainAvatar.InstantMessageDialog.InventoryOffered) && ((OnInventoryItemReceived != null) || (OnInventoryFolderReceived !=null))) { sbyte IncomingItemType = (sbyte)binaryBucket[0]; LLUUID IncomingUUID = new LLUUID(binaryBucket, 1); // Update root folders InventoryFolder root = GetRootFolder(); if (root.GetContents().Count == 0) { root.RequestDownloadContents(false, true, false).RequestComplete.WaitOne(3000, false); } // Handle the case of the incoming inventory folder if (IncomingItemType == (sbyte)InventoryManager.InventoryType.Folder) { if (OnInventoryFolderReceived == null) { // Short-circuit early exit, we're not interested... return; } InventoryFolder iFolder = null; int numAttempts = 6; int timeBetweenAttempts = 500; while( numAttempts-- > 0 ) { foreach( InventoryBase ib in root.GetContents() ) { if (ib is InventoryFolder) { InventoryFolder tiFolder = (InventoryFolder)ib; if (tiFolder.FolderID == IncomingUUID) { iFolder = tiFolder; break; } } } if ( iFolder != null) { try { OnInventoryFolderReceived(fromAgentID, fromAgentName, parentEstateID, regionID, position, timestamp, iFolder); } catch (Exception e) { slClient.Log(e.ToString(), Helpers.LogLevel.Error); } return; } else { Thread.Sleep(timeBetweenAttempts); timeBetweenAttempts *= 2; root.RequestDownloadContents(false, true, false).RequestComplete.WaitOne(3000, false); } } slClient.Log("Incoming folder [" + IncomingUUID.ToStringHyphenated() + "] not found in inventory.", Helpers.LogLevel.Error); return; } if (OnInventoryItemReceived == null) { // Short-circuit, early exit, we're not interested return; } // Make sure we have a folder lookup by type table ready. lock (FolderByType) { if (FolderByType.Count == 0) { foreach (InventoryBase ib in root.GetContents()) { if (ib is InventoryFolder) { InventoryFolder iFolder = (InventoryFolder)ib; FolderByType[iFolder.Type] = iFolder; } } } } // Get a reference to the incoming/receiving folder if (!FolderByType.ContainsKey(IncomingItemType)) { slClient.Log("Incoming item specifies type (" + IncomingItemType + ") with no matching inventory folder found.", Helpers.LogLevel.Error); } InventoryFolder incomingFolder = FolderByType[IncomingItemType]; InventoryItem incomingItem = null; // lock just incase another item comes into the same directory while processing this one. lock (incomingFolder) { // Refresh contents of receiving folder incomingFolder.RequestDownloadContents(false, false, true).RequestComplete.WaitOne(3000, false); int numAttempts = 2; while( numAttempts-- > 0 ) { // Search folder for incoming item foreach (InventoryBase ib2 in incomingFolder.GetContents()) { if (ib2 is InventoryItem) { InventoryItem tiItem = (InventoryItem)ib2; if (tiItem.ItemID == IncomingUUID) { incomingItem = tiItem; break; } } } // If found, send out notification if (incomingItem != null) { try { OnInventoryItemReceived(fromAgentID, fromAgentName, parentEstateID, regionID, position, timestamp, incomingItem); } catch (Exception e) { slClient.Log(e.ToString(), Helpers.LogLevel.Error); } return; } else { Thread.Sleep(500); incomingFolder.RequestDownloadContents(false, false, true).RequestComplete.WaitOne(3000, false); } } } slClient.Log("Incoming item/folder [" + IncomingUUID.ToStringHyphenated() + "] not found in inventory.", Helpers.LogLevel.Error); } }