aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/CoreModules
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/CoreModules')
-rw-r--r--OpenSim/Region/CoreModules/Agent/Capabilities/CapabilitiesModule.cs255
-rw-r--r--OpenSim/Region/CoreModules/Avatar/Assets/GetMeshModule.cs211
-rw-r--r--OpenSim/Region/CoreModules/Avatar/Assets/GetTextureModule.cs402
-rw-r--r--OpenSim/Region/CoreModules/Avatar/Assets/NewFileAgentInventoryVariablePriceModule.cs275
-rw-r--r--OpenSim/Region/CoreModules/Avatar/ObjectCaps/ObjectAdd.cs370
-rw-r--r--OpenSim/Region/CoreModules/Avatar/ObjectCaps/UploadObjectAssetModule.cs374
-rw-r--r--OpenSim/Region/CoreModules/Framework/EventQueue/EventQueueGetModule.cs719
-rw-r--r--OpenSim/Region/CoreModules/Framework/EventQueue/EventQueueHelper.cs399
8 files changed, 0 insertions, 3005 deletions
diff --git a/OpenSim/Region/CoreModules/Agent/Capabilities/CapabilitiesModule.cs b/OpenSim/Region/CoreModules/Agent/Capabilities/CapabilitiesModule.cs
deleted file mode 100644
index 1d8e70e..0000000
--- a/OpenSim/Region/CoreModules/Agent/Capabilities/CapabilitiesModule.cs
+++ /dev/null
@@ -1,255 +0,0 @@
1/*
2 * Copyright (c) Contributors, http://opensimulator.org/
3 * See CONTRIBUTORS.TXT for a full list of copyright holders.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyrightD
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of the OpenSimulator Project nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27
28using System;
29using System.Collections;
30using System.Collections.Generic;
31using System.Reflection;
32using log4net;
33using Nini.Config;
34using OpenMetaverse;
35using OpenSim.Framework;
36using OpenSim.Framework.Console;
37using OpenSim.Region.Framework.Interfaces;
38using OpenSim.Region.Framework.Scenes;
39using Caps=OpenSim.Framework.Capabilities.Caps;
40
41namespace OpenSim.Region.CoreModules.Agent.Capabilities
42{
43 public class CapabilitiesModule : INonSharedRegionModule, ICapabilitiesModule
44 {
45 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
46
47 protected Scene m_scene;
48
49 /// <summary>
50 /// Each agent has its own capabilities handler.
51 /// </summary>
52 protected Dictionary<UUID, Caps> m_capsHandlers = new Dictionary<UUID, Caps>();
53
54 protected Dictionary<UUID, string> capsPaths = new Dictionary<UUID, string>();
55 protected Dictionary<UUID, Dictionary<ulong, string>> childrenSeeds
56 = new Dictionary<UUID, Dictionary<ulong, string>>();
57
58 public void Initialise(IConfigSource source)
59 {
60 }
61
62 public void AddRegion(Scene scene)
63 {
64 m_scene = scene;
65 m_scene.RegisterModuleInterface<ICapabilitiesModule>(this);
66 MainConsole.Instance.Commands.AddCommand("Capabilities", false, "show caps",
67 "show capabilities",
68 "Shows all registered capabilities", CapabilitiesCommand);
69 }
70
71 public void RegionLoaded(Scene scene)
72 {
73 }
74
75 public void RemoveRegion(Scene scene)
76 {
77 m_scene.UnregisterModuleInterface<ICapabilitiesModule>(this);
78 }
79
80 public void PostInitialise()
81 {
82 }
83
84 public void Close() {}
85
86 public string Name
87 {
88 get { return "Capabilities Module"; }
89 }
90
91 public Type ReplaceableInterface
92 {
93 get { return null; }
94 }
95
96 public void AddCapsHandler(UUID agentId)
97 {
98 if (m_scene.RegionInfo.EstateSettings.IsBanned(agentId))
99 return;
100
101 String capsObjectPath = GetCapsPath(agentId);
102
103 if (m_capsHandlers.ContainsKey(agentId))
104 {
105 Caps oldCaps = m_capsHandlers[agentId];
106
107 m_log.DebugFormat(
108 "[CAPS]: Reregistering caps for agent {0}. Old caps path {1}, new caps path {2}. ",
109 agentId, oldCaps.CapsObjectPath, capsObjectPath);
110 // This should not happen. The caller code is confused. We need to fix that.
111 // CAPs can never be reregistered, or the client will be confused.
112 // Hence this return here.
113 //return;
114 }
115
116 Caps caps
117 = new Caps(m_scene,
118 m_scene.AssetService, MainServer.Instance, m_scene.RegionInfo.ExternalHostName,
119 (MainServer.Instance == null) ? 0: MainServer.Instance.Port,
120 capsObjectPath, agentId, m_scene.DumpAssetsToFile, m_scene.RegionInfo.RegionName);
121
122 caps.RegisterHandlers();
123
124 m_scene.EventManager.TriggerOnRegisterCaps(agentId, caps);
125
126 caps.AddNewInventoryItem = m_scene.AddUploadedInventoryItem;
127 caps.ItemUpdatedCall = m_scene.CapsUpdateInventoryItemAsset;
128 caps.TaskScriptUpdatedCall = m_scene.CapsUpdateTaskInventoryScriptAsset;
129 caps.CAPSFetchInventoryDescendents = m_scene.HandleFetchInventoryDescendentsCAPS;
130 caps.GetClient = m_scene.SceneContents.GetControllingClient;
131
132 m_capsHandlers[agentId] = caps;
133 }
134
135 public void RemoveCapsHandler(UUID agentId)
136 {
137 if (childrenSeeds.ContainsKey(agentId))
138 {
139 childrenSeeds.Remove(agentId);
140 }
141
142 lock (m_capsHandlers)
143 {
144 if (m_capsHandlers.ContainsKey(agentId))
145 {
146 m_capsHandlers[agentId].DeregisterHandlers();
147 m_scene.EventManager.TriggerOnDeregisterCaps(agentId, m_capsHandlers[agentId]);
148 m_capsHandlers.Remove(agentId);
149 }
150 else
151 {
152 m_log.WarnFormat(
153 "[CAPS]: Received request to remove CAPS handler for root agent {0} in {1}, but no such CAPS handler found!",
154 agentId, m_scene.RegionInfo.RegionName);
155 }
156 }
157 }
158
159 public Caps GetCapsHandlerForUser(UUID agentId)
160 {
161 lock (m_capsHandlers)
162 {
163 if (m_capsHandlers.ContainsKey(agentId))
164 {
165 return m_capsHandlers[agentId];
166 }
167 }
168
169 return null;
170 }
171
172 public void NewUserConnection(AgentCircuitData agent)
173 {
174 capsPaths[agent.AgentID] = agent.CapsPath;
175 childrenSeeds[agent.AgentID]
176 = ((agent.ChildrenCapSeeds == null) ? new Dictionary<ulong, string>() : agent.ChildrenCapSeeds);
177 }
178
179 public string GetCapsPath(UUID agentId)
180 {
181 if (capsPaths.ContainsKey(agentId))
182 {
183 return capsPaths[agentId];
184 }
185
186 return null;
187 }
188
189 public Dictionary<ulong, string> GetChildrenSeeds(UUID agentID)
190 {
191 Dictionary<ulong, string> seeds = null;
192 if (childrenSeeds.TryGetValue(agentID, out seeds))
193 return seeds;
194 return new Dictionary<ulong, string>();
195 }
196
197 public void DropChildSeed(UUID agentID, ulong handle)
198 {
199 Dictionary<ulong, string> seeds;
200 if (childrenSeeds.TryGetValue(agentID, out seeds))
201 {
202 seeds.Remove(handle);
203 }
204 }
205
206 public string GetChildSeed(UUID agentID, ulong handle)
207 {
208 Dictionary<ulong, string> seeds;
209 string returnval;
210 if (childrenSeeds.TryGetValue(agentID, out seeds))
211 {
212 if (seeds.TryGetValue(handle, out returnval))
213 return returnval;
214 }
215 return null;
216 }
217
218 public void SetChildrenSeed(UUID agentID, Dictionary<ulong, string> seeds)
219 {
220 //m_log.DebugFormat(" !!! Setting child seeds in {0} to {1}", m_scene.RegionInfo.RegionName, seeds.Count);
221 childrenSeeds[agentID] = seeds;
222 }
223
224 public void DumpChildrenSeeds(UUID agentID)
225 {
226 m_log.Info("================ ChildrenSeed "+m_scene.RegionInfo.RegionName+" ================");
227 foreach (KeyValuePair<ulong, string> kvp in childrenSeeds[agentID])
228 {
229 uint x, y;
230 Utils.LongToUInts(kvp.Key, out x, out y);
231 x = x / Constants.RegionSize;
232 y = y / Constants.RegionSize;
233 m_log.Info(" >> "+x+", "+y+": "+kvp.Value);
234 }
235 }
236
237 private void CapabilitiesCommand(string module, string[] cmdparams)
238 {
239 System.Text.StringBuilder caps = new System.Text.StringBuilder();
240 caps.AppendFormat("Region {0}:\n", m_scene.RegionInfo.RegionName);
241
242 foreach (KeyValuePair<UUID, Caps> kvp in m_capsHandlers)
243 {
244 caps.AppendFormat("** User {0}:\n", kvp.Key);
245 for (IDictionaryEnumerator kvp2 = kvp.Value.CapsHandlers.CapsDetails.GetEnumerator(); kvp2.MoveNext(); )
246 {
247 Uri uri = new Uri(kvp2.Value.ToString());
248 caps.AppendFormat(" {0} = {1}\n", kvp2.Key, uri.PathAndQuery);
249 }
250 }
251
252 MainConsole.Instance.Output(caps.ToString());
253 }
254 }
255}
diff --git a/OpenSim/Region/CoreModules/Avatar/Assets/GetMeshModule.cs b/OpenSim/Region/CoreModules/Avatar/Assets/GetMeshModule.cs
deleted file mode 100644
index fc1ddef..0000000
--- a/OpenSim/Region/CoreModules/Avatar/Assets/GetMeshModule.cs
+++ /dev/null
@@ -1,211 +0,0 @@
1/*
2 * Copyright (c) Contributors, http://opensimulator.org/
3 * See CONTRIBUTORS.TXT for a full list of copyright holders.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of the OpenSimulator Project nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27
28using System;
29using System.Collections;
30using System.Collections.Specialized;
31using System.Reflection;
32using System.IO;
33using System.Web;
34using Mono.Addins;
35using log4net;
36using Nini.Config;
37using OpenMetaverse;
38using OpenMetaverse.StructuredData;
39using OpenSim.Framework;
40using OpenSim.Framework.Servers;
41using OpenSim.Framework.Servers.HttpServer;
42using OpenSim.Region.Framework.Interfaces;
43using OpenSim.Region.Framework.Scenes;
44using OpenSim.Services.Interfaces;
45using Caps = OpenSim.Framework.Capabilities.Caps;
46
47namespace OpenSim.Region.CoreModules.Avatar.Assets
48{
49 [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule")]
50 public class GetMeshModule : INonSharedRegionModule
51 {
52// private static readonly ILog m_log =
53// LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
54
55 private Scene m_scene;
56 private IAssetService m_assetService;
57 private bool m_enabled = true;
58
59 #region IRegionModuleBase Members
60
61
62 public Type ReplaceableInterface
63 {
64 get { return null; }
65 }
66
67 public void Initialise(IConfigSource source)
68 {
69 IConfig meshConfig = source.Configs["Mesh"];
70 if (meshConfig == null)
71 return;
72
73 m_enabled = meshConfig.GetBoolean("AllowMeshUpload", true);
74 }
75
76 public void AddRegion(Scene pScene)
77 {
78 m_scene = pScene;
79 }
80
81 public void RemoveRegion(Scene scene)
82 {
83
84 m_scene.EventManager.OnRegisterCaps -= RegisterCaps;
85 m_scene = null;
86 }
87
88 public void RegionLoaded(Scene scene)
89 {
90
91 m_assetService = m_scene.RequestModuleInterface<IAssetService>();
92 m_scene.EventManager.OnRegisterCaps += RegisterCaps;
93 }
94
95 #endregion
96
97
98 #region IRegionModule Members
99
100
101
102 public void Close() { }
103
104 public string Name { get { return "GetMeshModule"; } }
105
106
107 public void RegisterCaps(UUID agentID, Caps caps)
108 {
109 if(!m_enabled)
110 return;
111
112 UUID capID = UUID.Random();
113
114// m_log.Info("[GETMESH]: /CAPS/" + capID);
115
116 caps.RegisterHandler("GetMesh",
117 new RestHTTPHandler("GET", "/CAPS/" + capID,
118 delegate(Hashtable m_dhttpMethod)
119 {
120 return ProcessGetMesh(m_dhttpMethod, agentID, caps);
121 }));
122 }
123
124 #endregion
125
126 public Hashtable ProcessGetMesh(Hashtable request, UUID AgentId, Caps cap)
127 {
128
129 Hashtable responsedata = new Hashtable();
130 responsedata["int_response_code"] = 400; //501; //410; //404;
131 responsedata["content_type"] = "text/plain";
132 responsedata["keepalive"] = false;
133 responsedata["str_response_string"] = "Request wasn't what was expected";
134
135 string meshStr = string.Empty;
136
137 if (request.ContainsKey("mesh_id"))
138 meshStr = request["mesh_id"].ToString();
139
140
141 UUID meshID = UUID.Zero;
142 if (!String.IsNullOrEmpty(meshStr) && UUID.TryParse(meshStr, out meshID))
143 {
144 if (m_assetService == null)
145 {
146 responsedata["int_response_code"] = 404; //501; //410; //404;
147 responsedata["content_type"] = "text/plain";
148 responsedata["keepalive"] = false;
149 responsedata["str_response_string"] = "The asset service is unavailable. So is your mesh.";
150 return responsedata;
151 }
152
153 AssetBase mesh;
154 // Only try to fetch locally cached textures. Misses are redirected
155 mesh = m_assetService.GetCached(meshID.ToString());
156 if (mesh != null)
157 {
158 if (mesh.Type == (SByte)AssetType.Mesh)
159 {
160 responsedata["str_response_string"] = Convert.ToBase64String(mesh.Data);
161 responsedata["content_type"] = "application/vnd.ll.mesh";
162 responsedata["int_response_code"] = 200;
163 }
164 // Optionally add additional mesh types here
165 else
166 {
167 responsedata["int_response_code"] = 404; //501; //410; //404;
168 responsedata["content_type"] = "text/plain";
169 responsedata["keepalive"] = false;
170 responsedata["str_response_string"] = "Unfortunately, this asset isn't a mesh.";
171 return responsedata;
172 }
173 }
174 else
175 {
176 mesh = m_assetService.Get(meshID.ToString());
177 if (mesh != null)
178 {
179 if (mesh.Type == (SByte)AssetType.Mesh)
180 {
181 responsedata["str_response_string"] = Convert.ToBase64String(mesh.Data);
182 responsedata["content_type"] = "application/vnd.ll.mesh";
183 responsedata["int_response_code"] = 200;
184 }
185 // Optionally add additional mesh types here
186 else
187 {
188 responsedata["int_response_code"] = 404; //501; //410; //404;
189 responsedata["content_type"] = "text/plain";
190 responsedata["keepalive"] = false;
191 responsedata["str_response_string"] = "Unfortunately, this asset isn't a mesh.";
192 return responsedata;
193 }
194 }
195
196 else
197 {
198 responsedata["int_response_code"] = 404; //501; //410; //404;
199 responsedata["content_type"] = "text/plain";
200 responsedata["keepalive"] = false;
201 responsedata["str_response_string"] = "Your Mesh wasn't found. Sorry!";
202 return responsedata;
203 }
204 }
205
206 }
207
208 return responsedata;
209 }
210 }
211}
diff --git a/OpenSim/Region/CoreModules/Avatar/Assets/GetTextureModule.cs b/OpenSim/Region/CoreModules/Avatar/Assets/GetTextureModule.cs
deleted file mode 100644
index df4d561..0000000
--- a/OpenSim/Region/CoreModules/Avatar/Assets/GetTextureModule.cs
+++ /dev/null
@@ -1,402 +0,0 @@
1/*
2 * Copyright (c) Contributors, http://opensimulator.org/
3 * See CONTRIBUTORS.TXT for a full list of copyright holders.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of the OpenSimulator Project nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27
28using System;
29using System.Collections;
30using System.Collections.Specialized;
31using System.Drawing;
32using System.Drawing.Imaging;
33using System.Reflection;
34using System.IO;
35using System.Web;
36using log4net;
37using Nini.Config;
38using OpenMetaverse;
39using OpenMetaverse.StructuredData;
40using OpenMetaverse.Imaging;
41using OpenSim.Framework;
42using OpenSim.Framework.Servers;
43using OpenSim.Framework.Servers.HttpServer;
44using OpenSim.Region.Framework.Interfaces;
45using OpenSim.Region.Framework.Scenes;
46using OpenSim.Services.Interfaces;
47using Caps = OpenSim.Framework.Capabilities.Caps;
48
49namespace OpenSim.Region.CoreModules.Avatar.ObjectCaps
50{
51 #region Stream Handler
52
53 public delegate byte[] StreamHandlerCallback(string path, Stream request, OSHttpRequest httpRequest, OSHttpResponse httpResponse);
54
55 public class StreamHandler : BaseStreamHandler
56 {
57 StreamHandlerCallback m_callback;
58
59 public StreamHandler(string httpMethod, string path, StreamHandlerCallback callback)
60 : base(httpMethod, path)
61 {
62 m_callback = callback;
63 }
64
65 public override byte[] Handle(string path, Stream request, OSHttpRequest httpRequest, OSHttpResponse httpResponse)
66 {
67 return m_callback(path, request, httpRequest, httpResponse);
68 }
69 }
70
71 #endregion Stream Handler
72
73 public class GetTextureModule : IRegionModule
74 {
75 private static readonly ILog m_log =
76 LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
77 private Scene m_scene;
78 private IAssetService m_assetService;
79
80 public const string DefaultFormat = "x-j2c";
81
82 // TODO: Change this to a config option
83 const string REDIRECT_URL = null;
84
85
86 #region IRegionModule Members
87
88 public void Initialise(Scene pScene, IConfigSource pSource)
89 {
90 m_scene = pScene;
91 }
92
93 public void PostInitialise()
94 {
95 m_assetService = m_scene.RequestModuleInterface<IAssetService>();
96 m_scene.EventManager.OnRegisterCaps += RegisterCaps;
97 }
98
99 public void Close() { }
100
101 public string Name { get { return "GetTextureModule"; } }
102 public bool IsSharedModule { get { return false; } }
103
104 public void RegisterCaps(UUID agentID, Caps caps)
105 {
106 UUID capID = UUID.Random();
107
108// m_log.InfoFormat("[GETTEXTURE]: /CAPS/{0} in region {1}", capID, m_scene.RegionInfo.RegionName);
109 caps.RegisterHandler("GetTexture", new StreamHandler("GET", "/CAPS/" + capID, ProcessGetTexture));
110 }
111
112 #endregion
113
114 private byte[] ProcessGetTexture(string path, Stream request, OSHttpRequest httpRequest, OSHttpResponse httpResponse)
115 {
116 //m_log.DebugFormat("[GETTEXTURE]: called in {0}", m_scene.RegionInfo.RegionName);
117
118 // Try to parse the texture ID from the request URL
119 NameValueCollection query = HttpUtility.ParseQueryString(httpRequest.Url.Query);
120 string textureStr = query.GetOne("texture_id");
121 string format = query.GetOne("format");
122
123 if (m_assetService == null)
124 {
125 m_log.Error("[GETTEXTURE]: Cannot fetch texture " + textureStr + " without an asset service");
126 httpResponse.StatusCode = (int)System.Net.HttpStatusCode.NotFound;
127 return null;
128 }
129
130 UUID textureID;
131 if (!String.IsNullOrEmpty(textureStr) && UUID.TryParse(textureStr, out textureID))
132 {
133 string[] formats;
134 if (format != null && format != string.Empty)
135 {
136 formats = new string[1] { format.ToLower() };
137 }
138 else
139 {
140 formats = WebUtil.GetPreferredImageTypes(httpRequest.Headers.Get("Accept"));
141 if (formats.Length == 0)
142 formats = new string[1] { DefaultFormat }; // default
143
144 }
145 // OK, we have an array with preferred formats, possibly with only one entry
146
147 httpResponse.StatusCode = (int)System.Net.HttpStatusCode.NotFound;
148 foreach (string f in formats)
149 {
150 if (FetchTexture(httpRequest, httpResponse, textureID, f))
151 break;
152 }
153
154 }
155 else
156 {
157 m_log.Warn("[GETTEXTURE]: Failed to parse a texture_id from GetTexture request: " + httpRequest.Url);
158 }
159
160 httpResponse.Send();
161 return null;
162 }
163
164 /// <summary>
165 ///
166 /// </summary>
167 /// <param name="httpRequest"></param>
168 /// <param name="httpResponse"></param>
169 /// <param name="textureID"></param>
170 /// <param name="format"></param>
171 /// <returns>False for "caller try another codec"; true otherwise</returns>
172 private bool FetchTexture(OSHttpRequest httpRequest, OSHttpResponse httpResponse, UUID textureID, string format)
173 {
174// m_log.DebugFormat("[GETTEXTURE]: {0} with requested format {1}", textureID, format);
175 AssetBase texture;
176
177 string fullID = textureID.ToString();
178 if (format != DefaultFormat)
179 fullID = fullID + "-" + format;
180
181 if (!String.IsNullOrEmpty(REDIRECT_URL))
182 {
183 // Only try to fetch locally cached textures. Misses are redirected
184 texture = m_assetService.GetCached(fullID);
185
186 if (texture != null)
187 {
188 if (texture.Type != (sbyte)AssetType.Texture)
189 {
190 httpResponse.StatusCode = (int)System.Net.HttpStatusCode.NotFound;
191 return true;
192 }
193 WriteTextureData(httpRequest, httpResponse, texture, format);
194 }
195 else
196 {
197 string textureUrl = REDIRECT_URL + textureID.ToString();
198 m_log.Debug("[GETTEXTURE]: Redirecting texture request to " + textureUrl);
199 httpResponse.RedirectLocation = textureUrl;
200 return true;
201 }
202 }
203 else // no redirect
204 {
205 // try the cache
206 texture = m_assetService.GetCached(fullID);
207
208 if (texture == null)
209 {
210 //m_log.DebugFormat("[GETTEXTURE]: texture was not in the cache");
211
212 // Fetch locally or remotely. Misses return a 404
213 texture = m_assetService.Get(textureID.ToString());
214
215 if (texture != null)
216 {
217 if (texture.Type != (sbyte)AssetType.Texture)
218 {
219 httpResponse.StatusCode = (int)System.Net.HttpStatusCode.NotFound;
220 return true;
221 }
222 if (format == DefaultFormat)
223 {
224 WriteTextureData(httpRequest, httpResponse, texture, format);
225 return true;
226 }
227 else
228 {
229 AssetBase newTexture = new AssetBase(texture.ID + "-" + format, texture.Name, (sbyte)AssetType.Texture, texture.Metadata.CreatorID);
230 newTexture.Data = ConvertTextureData(texture, format);
231 if (newTexture.Data.Length == 0)
232 return false; // !!! Caller try another codec, please!
233
234 newTexture.Flags = AssetFlags.Collectable;
235 newTexture.Temporary = true;
236 m_assetService.Store(newTexture);
237 WriteTextureData(httpRequest, httpResponse, newTexture, format);
238 return true;
239 }
240 }
241 }
242 else // it was on the cache
243 {
244 //m_log.DebugFormat("[GETTEXTURE]: texture was in the cache");
245 WriteTextureData(httpRequest, httpResponse, texture, format);
246 return true;
247 }
248 }
249
250 // not found
251// m_log.Warn("[GETTEXTURE]: Texture " + textureID + " not found");
252 httpResponse.StatusCode = (int)System.Net.HttpStatusCode.NotFound;
253 return true;
254 }
255
256 private void WriteTextureData(OSHttpRequest request, OSHttpResponse response, AssetBase texture, string format)
257 {
258 string range = request.Headers.GetOne("Range");
259 //m_log.DebugFormat("[GETTEXTURE]: Range {0}", range);
260 if (!String.IsNullOrEmpty(range)) // JP2's only
261 {
262 // Range request
263 int start, end;
264 if (TryParseRange(range, out start, out end))
265 {
266 // Before clamping start make sure we can satisfy it in order to avoid
267 // sending back the last byte instead of an error status
268 if (start >= texture.Data.Length)
269 {
270 response.StatusCode = (int)System.Net.HttpStatusCode.RequestedRangeNotSatisfiable;
271 return;
272 }
273
274 end = Utils.Clamp(end, 0, texture.Data.Length - 1);
275 start = Utils.Clamp(start, 0, end);
276 int len = end - start + 1;
277
278 //m_log.Debug("Serving " + start + " to " + end + " of " + texture.Data.Length + " bytes for texture " + texture.ID);
279
280 if (len < texture.Data.Length)
281 response.StatusCode = (int)System.Net.HttpStatusCode.PartialContent;
282
283 response.ContentLength = len;
284 response.ContentType = texture.Metadata.ContentType;
285 response.AddHeader("Content-Range", String.Format("bytes {0}-{1}/{2}", start, end, texture.Data.Length));
286
287 response.Body.Write(texture.Data, start, len);
288 }
289 else
290 {
291 m_log.Warn("[GETTEXTURE]: Malformed Range header: " + range);
292 response.StatusCode = (int)System.Net.HttpStatusCode.BadRequest;
293 }
294 }
295 else // JP2's or other formats
296 {
297 // Full content request
298 response.StatusCode = (int)System.Net.HttpStatusCode.OK;
299 response.ContentLength = texture.Data.Length;
300 if (format == DefaultFormat)
301 response.ContentType = texture.Metadata.ContentType;
302 else
303 response.ContentType = "image/" + format;
304 response.Body.Write(texture.Data, 0, texture.Data.Length);
305 }
306 }
307
308 private bool TryParseRange(string header, out int start, out int end)
309 {
310 if (header.StartsWith("bytes="))
311 {
312 string[] rangeValues = header.Substring(6).Split('-');
313 if (rangeValues.Length == 2)
314 {
315 if (Int32.TryParse(rangeValues[0], out start) && Int32.TryParse(rangeValues[1], out end))
316 return true;
317 }
318 }
319
320 start = end = 0;
321 return false;
322 }
323
324
325 private byte[] ConvertTextureData(AssetBase texture, string format)
326 {
327 m_log.DebugFormat("[GETTEXTURE]: Converting texture {0} to {1}", texture.ID, format);
328 byte[] data = new byte[0];
329
330 MemoryStream imgstream = new MemoryStream();
331 Bitmap mTexture = new Bitmap(1, 1);
332 ManagedImage managedImage;
333 Image image = (Image)mTexture;
334
335 try
336 {
337 // Taking our jpeg2000 data, decoding it, then saving it to a byte array with regular data
338
339 imgstream = new MemoryStream();
340
341 // Decode image to System.Drawing.Image
342 if (OpenJPEG.DecodeToImage(texture.Data, out managedImage, out image))
343 {
344 // Save to bitmap
345 mTexture = new Bitmap(image);
346
347 EncoderParameters myEncoderParameters = new EncoderParameters();
348 myEncoderParameters.Param[0] = new EncoderParameter(Encoder.Quality, 95L);
349
350 // Save bitmap to stream
351 ImageCodecInfo codec = GetEncoderInfo("image/" + format);
352 if (codec != null)
353 {
354 mTexture.Save(imgstream, codec, myEncoderParameters);
355 // Write the stream to a byte array for output
356 data = imgstream.ToArray();
357 }
358 else
359 m_log.WarnFormat("[GETTEXTURE]: No such codec {0}", format);
360
361 }
362 }
363 catch (Exception e)
364 {
365 m_log.WarnFormat("[GETTEXTURE]: Unable to convert texture {0} to {1}: {2}", texture.ID, format, e.Message);
366 }
367 finally
368 {
369 // Reclaim memory, these are unmanaged resources
370 // If we encountered an exception, one or more of these will be null
371 if (mTexture != null)
372 mTexture.Dispose();
373
374 if (image != null)
375 image.Dispose();
376
377 if (imgstream != null)
378 {
379 imgstream.Close();
380 imgstream.Dispose();
381 }
382 }
383
384 return data;
385 }
386
387 // From msdn
388 private static ImageCodecInfo GetEncoderInfo(String mimeType)
389 {
390 ImageCodecInfo[] encoders;
391 encoders = ImageCodecInfo.GetImageEncoders();
392 for (int j = 0; j < encoders.Length; ++j)
393 {
394 if (encoders[j].MimeType == mimeType)
395 return encoders[j];
396 }
397 return null;
398 }
399
400
401 }
402}
diff --git a/OpenSim/Region/CoreModules/Avatar/Assets/NewFileAgentInventoryVariablePriceModule.cs b/OpenSim/Region/CoreModules/Avatar/Assets/NewFileAgentInventoryVariablePriceModule.cs
deleted file mode 100644
index 3d4c7b7..0000000
--- a/OpenSim/Region/CoreModules/Avatar/Assets/NewFileAgentInventoryVariablePriceModule.cs
+++ /dev/null
@@ -1,275 +0,0 @@
1/*
2 * Copyright (c) Contributors, http://opensimulator.org/
3 * See CONTRIBUTORS.TXT for a full list of copyright holders.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of the OpenSimulator Project nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27
28using System;
29using System.Collections;
30using System.Collections.Specialized;
31using System.Reflection;
32using System.IO;
33using System.Web;
34using Mono.Addins;
35using log4net;
36using Nini.Config;
37using OpenMetaverse;
38using OpenMetaverse.StructuredData;
39using OpenSim.Framework;
40using OpenSim.Framework.Servers;
41using OpenSim.Framework.Servers.HttpServer;
42using OpenSim.Region.Framework.Interfaces;
43using OpenSim.Region.Framework.Scenes;
44using OpenSim.Services.Interfaces;
45using Caps = OpenSim.Framework.Capabilities.Caps;
46using OpenSim.Framework.Capabilities;
47
48namespace OpenSim.Region.CoreModules.Avatar.Assets
49{
50 [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule")]
51 public class NewFileAgentInventoryVariablePriceModule : INonSharedRegionModule
52 {
53// private static readonly ILog m_log =
54// LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
55
56 private Scene m_scene;
57// private IAssetService m_assetService;
58 private bool m_dumpAssetsToFile = false;
59 private bool m_enabled = true;
60
61 #region IRegionModuleBase Members
62
63
64 public Type ReplaceableInterface
65 {
66 get { return null; }
67 }
68
69 public void Initialise(IConfigSource source)
70 {
71 IConfig meshConfig = source.Configs["Mesh"];
72 if (meshConfig == null)
73 return;
74
75 m_enabled = meshConfig.GetBoolean("AllowMeshUpload", true);
76 }
77
78 public void AddRegion(Scene pScene)
79 {
80 m_scene = pScene;
81 }
82
83 public void RemoveRegion(Scene scene)
84 {
85
86 m_scene.EventManager.OnRegisterCaps -= RegisterCaps;
87 m_scene = null;
88 }
89
90 public void RegionLoaded(Scene scene)
91 {
92
93// m_assetService = m_scene.RequestModuleInterface<IAssetService>();
94 m_scene.EventManager.OnRegisterCaps += RegisterCaps;
95 }
96
97 #endregion
98
99
100 #region IRegionModule Members
101
102
103
104 public void Close() { }
105
106 public string Name { get { return "NewFileAgentInventoryVariablePriceModule"; } }
107
108
109 public void RegisterCaps(UUID agentID, Caps caps)
110 {
111 if(!m_enabled)
112 return;
113
114 UUID capID = UUID.Random();
115
116// m_log.Debug("[NEW FILE AGENT INVENTORY VARIABLE PRICE]: /CAPS/" + capID);
117 caps.RegisterHandler("NewFileAgentInventoryVariablePrice",
118
119 new LLSDStreamhandler<LLSDAssetUploadRequest, LLSDNewFileAngentInventoryVariablePriceReplyResponse>("POST",
120 "/CAPS/" + capID.ToString(),
121 delegate(LLSDAssetUploadRequest req)
122 {
123 return NewAgentInventoryRequest(req,agentID);
124 }));
125
126 }
127
128 #endregion
129
130 public LLSDNewFileAngentInventoryVariablePriceReplyResponse NewAgentInventoryRequest(LLSDAssetUploadRequest llsdRequest, UUID agentID)
131 {
132
133 //TODO: The Mesh uploader uploads many types of content. If you're going to implement a Money based limit
134 // You need to be aware of this and
135
136
137 //if (llsdRequest.asset_type == "texture" ||
138 // llsdRequest.asset_type == "animation" ||
139 // llsdRequest.asset_type == "sound")
140 // {
141 IClientAPI client = null;
142
143
144 IMoneyModule mm = m_scene.RequestModuleInterface<IMoneyModule>();
145
146 if (mm != null)
147 {
148 if (m_scene.TryGetClient(agentID, out client))
149 {
150 if (!mm.UploadCovered(client, mm.UploadCharge))
151 {
152 if (client != null)
153 client.SendAgentAlertMessage("Unable to upload asset. Insufficient funds.", false);
154
155 LLSDNewFileAngentInventoryVariablePriceReplyResponse errorResponse = new LLSDNewFileAngentInventoryVariablePriceReplyResponse();
156 errorResponse.rsvp = "";
157 errorResponse.state = "error";
158 return errorResponse;
159 }
160 }
161 }
162 // }
163
164
165
166 string assetName = llsdRequest.name;
167 string assetDes = llsdRequest.description;
168 string capsBase = "/CAPS/NewFileAgentInventoryVariablePrice/";
169 UUID newAsset = UUID.Random();
170 UUID newInvItem = UUID.Random();
171 UUID parentFolder = llsdRequest.folder_id;
172 string uploaderPath = Util.RandomClass.Next(5000, 8000).ToString("0000") + "/";
173
174 Caps.AssetUploader uploader =
175 new Caps.AssetUploader(assetName, assetDes, newAsset, newInvItem, parentFolder, llsdRequest.inventory_type,
176 llsdRequest.asset_type, capsBase + uploaderPath, MainServer.Instance, m_dumpAssetsToFile);
177 MainServer.Instance.AddStreamHandler(
178 new BinaryStreamHandler("POST", capsBase + uploaderPath, uploader.uploaderCaps));
179
180 string protocol = "http://";
181
182 if (MainServer.Instance.UseSSL)
183 protocol = "https://";
184
185 string uploaderURL = protocol + m_scene.RegionInfo.ExternalHostName + ":" + MainServer.Instance.Port.ToString() + capsBase +
186 uploaderPath;
187
188
189 LLSDNewFileAngentInventoryVariablePriceReplyResponse uploadResponse = new LLSDNewFileAngentInventoryVariablePriceReplyResponse();
190
191
192 uploadResponse.rsvp = uploaderURL;
193 uploadResponse.state = "upload";
194 uploadResponse.resource_cost = 0;
195 uploadResponse.upload_price = 0;
196
197 uploader.OnUpLoad += //UploadCompleteHandler;
198
199 delegate(
200 string passetName, string passetDescription, UUID passetID,
201 UUID pinventoryItem, UUID pparentFolder, byte[] pdata, string pinventoryType,
202 string passetType)
203 {
204 UploadCompleteHandler(passetName, passetDescription, passetID,
205 pinventoryItem, pparentFolder, pdata, pinventoryType,
206 passetType,agentID);
207 };
208 return uploadResponse;
209 }
210
211
212 public void UploadCompleteHandler(string assetName, string assetDescription, UUID assetID,
213 UUID inventoryItem, UUID parentFolder, byte[] data, string inventoryType,
214 string assetType,UUID AgentID)
215 {
216
217 sbyte assType = 0;
218 sbyte inType = 0;
219
220 if (inventoryType == "sound")
221 {
222 inType = 1;
223 assType = 1;
224 }
225 else if (inventoryType == "animation")
226 {
227 inType = 19;
228 assType = 20;
229 }
230 else if (inventoryType == "wearable")
231 {
232 inType = 18;
233 switch (assetType)
234 {
235 case "bodypart":
236 assType = 13;
237 break;
238 case "clothing":
239 assType = 5;
240 break;
241 }
242 }
243 else if (inventoryType == "mesh")
244 {
245 inType = (sbyte)InventoryType.Mesh;
246 assType = (sbyte)AssetType.Mesh;
247 }
248
249 AssetBase asset;
250 asset = new AssetBase(assetID, assetName, assType, AgentID.ToString());
251 asset.Data = data;
252
253 if (m_scene.AssetService != null)
254 m_scene.AssetService.Store(asset);
255
256 InventoryItemBase item = new InventoryItemBase();
257 item.Owner = AgentID;
258 item.CreatorId = AgentID.ToString();
259 item.ID = inventoryItem;
260 item.AssetID = asset.FullID;
261 item.Description = assetDescription;
262 item.Name = assetName;
263 item.AssetType = assType;
264 item.InvType = inType;
265 item.Folder = parentFolder;
266 item.CurrentPermissions = (uint)PermissionMask.All;
267 item.BasePermissions = (uint)PermissionMask.All;
268 item.EveryOnePermissions = 0;
269 item.NextPermissions = (uint)(PermissionMask.Move | PermissionMask.Modify | PermissionMask.Transfer);
270 item.CreationDate = Util.UnixTimeSinceEpoch();
271 m_scene.AddInventoryItem(item);
272
273 }
274 }
275}
diff --git a/OpenSim/Region/CoreModules/Avatar/ObjectCaps/ObjectAdd.cs b/OpenSim/Region/CoreModules/Avatar/ObjectCaps/ObjectAdd.cs
deleted file mode 100644
index a0d72ed..0000000
--- a/OpenSim/Region/CoreModules/Avatar/ObjectCaps/ObjectAdd.cs
+++ /dev/null
@@ -1,370 +0,0 @@
1/*
2 * Copyright (c) Contributors, http://opensimulator.org/
3 * See CONTRIBUTORS.TXT for a full list of copyright holders.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of the OpenSimulator Project nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27
28using System;
29using System.Collections;
30using System.Reflection;
31using log4net;
32using Nini.Config;
33using OpenMetaverse;
34using OpenMetaverse.StructuredData;
35using OpenSim.Framework;
36using OpenSim.Framework.Servers;
37using OpenSim.Framework.Servers.HttpServer;
38using OpenSim.Region.Framework.Interfaces;
39using OpenSim.Region.Framework.Scenes;
40using Caps=OpenSim.Framework.Capabilities.Caps;
41
42namespace OpenSim.Region.CoreModules.Avatar.ObjectCaps
43{
44 public class ObjectAdd : IRegionModule
45 {
46// private static readonly ILog m_log =
47// LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
48
49 private Scene m_scene;
50 #region IRegionModule Members
51
52 public void Initialise(Scene pScene, IConfigSource pSource)
53 {
54 m_scene = pScene;
55 m_scene.EventManager.OnRegisterCaps += RegisterCaps;
56 }
57
58 public void PostInitialise()
59 {
60
61 }
62
63 public void RegisterCaps(UUID agentID, Caps caps)
64 {
65 UUID capuuid = UUID.Random();
66
67// m_log.InfoFormat("[OBJECTADD]: {0}", "/CAPS/OA/" + capuuid + "/");
68
69 caps.RegisterHandler("ObjectAdd",
70 new RestHTTPHandler("POST", "/CAPS/OA/" + capuuid + "/",
71 delegate(Hashtable m_dhttpMethod)
72 {
73 return ProcessAdd(m_dhttpMethod, agentID, caps);
74 }));
75 }
76
77 public Hashtable ProcessAdd(Hashtable request, UUID AgentId, Caps cap)
78 {
79 Hashtable responsedata = new Hashtable();
80 responsedata["int_response_code"] = 400; //501; //410; //404;
81 responsedata["content_type"] = "text/plain";
82 responsedata["keepalive"] = false;
83 responsedata["str_response_string"] = "Request wasn't what was expected";
84 ScenePresence avatar;
85
86 if (!m_scene.TryGetScenePresence(AgentId, out avatar))
87 return responsedata;
88
89
90 OSD r = OSDParser.DeserializeLLSDXml((string)request["requestbody"]);
91 //UUID session_id = UUID.Zero;
92 bool bypass_raycast = false;
93 uint everyone_mask = 0;
94 uint group_mask = 0;
95 uint next_owner_mask = 0;
96 uint flags = 0;
97 UUID group_id = UUID.Zero;
98 int hollow = 0;
99 int material = 0;
100 int p_code = 0;
101 int path_begin = 0;
102 int path_curve = 0;
103 int path_end = 0;
104 int path_radius_offset = 0;
105 int path_revolutions = 0;
106 int path_scale_x = 0;
107 int path_scale_y = 0;
108 int path_shear_x = 0;
109 int path_shear_y = 0;
110 int path_skew = 0;
111 int path_taper_x = 0;
112 int path_taper_y = 0;
113 int path_twist = 0;
114 int path_twist_begin = 0;
115 int profile_begin = 0;
116 int profile_curve = 0;
117 int profile_end = 0;
118 Vector3 ray_end = Vector3.Zero;
119 bool ray_end_is_intersection = false;
120 Vector3 ray_start = Vector3.Zero;
121 UUID ray_target_id = UUID.Zero;
122 Quaternion rotation = Quaternion.Identity;
123 Vector3 scale = Vector3.Zero;
124 int state = 0;
125
126 if (r.Type != OSDType.Map) // not a proper req
127 return responsedata;
128
129 OSDMap rm = (OSDMap)r;
130
131 if (rm.ContainsKey("ObjectData")) //v2
132 {
133 if (rm["ObjectData"].Type != OSDType.Map)
134 {
135 responsedata["str_response_string"] = "Has ObjectData key, but data not in expected format";
136 return responsedata;
137 }
138
139 OSDMap ObjMap = (OSDMap) rm["ObjectData"];
140
141 bypass_raycast = ObjMap["BypassRaycast"].AsBoolean();
142 everyone_mask = readuintval(ObjMap["EveryoneMask"]);
143 flags = readuintval(ObjMap["Flags"]);
144 group_mask = readuintval(ObjMap["GroupMask"]);
145 material = ObjMap["Material"].AsInteger();
146 next_owner_mask = readuintval(ObjMap["NextOwnerMask"]);
147 p_code = ObjMap["PCode"].AsInteger();
148
149 if (ObjMap.ContainsKey("Path"))
150 {
151 if (ObjMap["Path"].Type != OSDType.Map)
152 {
153 responsedata["str_response_string"] = "Has Path key, but data not in expected format";
154 return responsedata;
155 }
156
157 OSDMap PathMap = (OSDMap)ObjMap["Path"];
158 path_begin = PathMap["Begin"].AsInteger();
159 path_curve = PathMap["Curve"].AsInteger();
160 path_end = PathMap["End"].AsInteger();
161 path_radius_offset = PathMap["RadiusOffset"].AsInteger();
162 path_revolutions = PathMap["Revolutions"].AsInteger();
163 path_scale_x = PathMap["ScaleX"].AsInteger();
164 path_scale_y = PathMap["ScaleY"].AsInteger();
165 path_shear_x = PathMap["ShearX"].AsInteger();
166 path_shear_y = PathMap["ShearY"].AsInteger();
167 path_skew = PathMap["Skew"].AsInteger();
168 path_taper_x = PathMap["TaperX"].AsInteger();
169 path_taper_y = PathMap["TaperY"].AsInteger();
170 path_twist = PathMap["Twist"].AsInteger();
171 path_twist_begin = PathMap["TwistBegin"].AsInteger();
172
173 }
174
175 if (ObjMap.ContainsKey("Profile"))
176 {
177 if (ObjMap["Profile"].Type != OSDType.Map)
178 {
179 responsedata["str_response_string"] = "Has Profile key, but data not in expected format";
180 return responsedata;
181 }
182
183 OSDMap ProfileMap = (OSDMap)ObjMap["Profile"];
184
185 profile_begin = ProfileMap["Begin"].AsInteger();
186 profile_curve = ProfileMap["Curve"].AsInteger();
187 profile_end = ProfileMap["End"].AsInteger();
188 hollow = ProfileMap["Hollow"].AsInteger();
189 }
190 ray_end_is_intersection = ObjMap["RayEndIsIntersection"].AsBoolean();
191
192 ray_target_id = ObjMap["RayTargetId"].AsUUID();
193 state = ObjMap["State"].AsInteger();
194 try
195 {
196 ray_end = ((OSDArray) ObjMap["RayEnd"]).AsVector3();
197 ray_start = ((OSDArray) ObjMap["RayStart"]).AsVector3();
198 scale = ((OSDArray) ObjMap["Scale"]).AsVector3();
199 rotation = ((OSDArray)ObjMap["Rotation"]).AsQuaternion();
200 }
201 catch (Exception)
202 {
203 responsedata["str_response_string"] = "RayEnd, RayStart, Scale or Rotation wasn't in the expected format";
204 return responsedata;
205 }
206
207 if (rm.ContainsKey("AgentData"))
208 {
209 if (rm["AgentData"].Type != OSDType.Map)
210 {
211 responsedata["str_response_string"] = "Has AgentData key, but data not in expected format";
212 return responsedata;
213 }
214
215 OSDMap AgentDataMap = (OSDMap) rm["AgentData"];
216
217 //session_id = AgentDataMap["SessionId"].AsUUID();
218 group_id = AgentDataMap["GroupId"].AsUUID();
219 }
220
221 }
222 else
223 { //v1
224 bypass_raycast = rm["bypass_raycast"].AsBoolean();
225
226 everyone_mask = readuintval(rm["everyone_mask"]);
227 flags = readuintval(rm["flags"]);
228 group_id = rm["group_id"].AsUUID();
229 group_mask = readuintval(rm["group_mask"]);
230 hollow = rm["hollow"].AsInteger();
231 material = rm["material"].AsInteger();
232 next_owner_mask = readuintval(rm["next_owner_mask"]);
233 hollow = rm["hollow"].AsInteger();
234 p_code = rm["p_code"].AsInteger();
235 path_begin = rm["path_begin"].AsInteger();
236 path_curve = rm["path_curve"].AsInteger();
237 path_end = rm["path_end"].AsInteger();
238 path_radius_offset = rm["path_radius_offset"].AsInteger();
239 path_revolutions = rm["path_revolutions"].AsInteger();
240 path_scale_x = rm["path_scale_x"].AsInteger();
241 path_scale_y = rm["path_scale_y"].AsInteger();
242 path_shear_x = rm["path_shear_x"].AsInteger();
243 path_shear_y = rm["path_shear_y"].AsInteger();
244 path_skew = rm["path_skew"].AsInteger();
245 path_taper_x = rm["path_taper_x"].AsInteger();
246 path_taper_y = rm["path_taper_y"].AsInteger();
247 path_twist = rm["path_twist"].AsInteger();
248 path_twist_begin = rm["path_twist_begin"].AsInteger();
249 profile_begin = rm["profile_begin"].AsInteger();
250 profile_curve = rm["profile_curve"].AsInteger();
251 profile_end = rm["profile_end"].AsInteger();
252
253 ray_end_is_intersection = rm["ray_end_is_intersection"].AsBoolean();
254
255 ray_target_id = rm["ray_target_id"].AsUUID();
256
257
258 //session_id = rm["session_id"].AsUUID();
259 state = rm["state"].AsInteger();
260 try
261 {
262 ray_end = ((OSDArray)rm["ray_end"]).AsVector3();
263 ray_start = ((OSDArray)rm["ray_start"]).AsVector3();
264 rotation = ((OSDArray)rm["rotation"]).AsQuaternion();
265 scale = ((OSDArray)rm["scale"]).AsVector3();
266 }
267 catch (Exception)
268 {
269 responsedata["str_response_string"] = "RayEnd, RayStart, Scale or Rotation wasn't in the expected format";
270 return responsedata;
271 }
272 }
273
274
275
276 Vector3 pos = m_scene.GetNewRezLocation(ray_start, ray_end, ray_target_id, rotation, (bypass_raycast) ? (byte)1 : (byte)0, (ray_end_is_intersection) ? (byte)1 : (byte)0, true, scale, false);
277
278 PrimitiveBaseShape pbs = PrimitiveBaseShape.CreateBox();
279
280 pbs.PathBegin = (ushort)path_begin;
281 pbs.PathCurve = (byte)path_curve;
282 pbs.PathEnd = (ushort)path_end;
283 pbs.PathRadiusOffset = (sbyte)path_radius_offset;
284 pbs.PathRevolutions = (byte)path_revolutions;
285 pbs.PathScaleX = (byte)path_scale_x;
286 pbs.PathScaleY = (byte)path_scale_y;
287 pbs.PathShearX = (byte) path_shear_x;
288 pbs.PathShearY = (byte)path_shear_y;
289 pbs.PathSkew = (sbyte)path_skew;
290 pbs.PathTaperX = (sbyte)path_taper_x;
291 pbs.PathTaperY = (sbyte)path_taper_y;
292 pbs.PathTwist = (sbyte)path_twist;
293 pbs.PathTwistBegin = (sbyte)path_twist_begin;
294 pbs.HollowShape = (HollowShape) hollow;
295 pbs.PCode = (byte)p_code;
296 pbs.ProfileBegin = (ushort) profile_begin;
297 pbs.ProfileCurve = (byte) profile_curve;
298 pbs.ProfileEnd = (ushort)profile_end;
299 pbs.Scale = scale;
300 pbs.State = (byte)state;
301
302 SceneObjectGroup obj = null; ;
303
304 if (m_scene.Permissions.CanRezObject(1, avatar.UUID, pos))
305 {
306 // rez ON the ground, not IN the ground
307 // pos.Z += 0.25F;
308
309 obj = m_scene.AddNewPrim(avatar.UUID, group_id, pos, rotation, pbs);
310 }
311
312
313 if (obj == null)
314 return responsedata;
315
316 SceneObjectPart rootpart = obj.RootPart;
317 rootpart.Shape = pbs;
318 rootpart.Flags |= (PrimFlags)flags;
319 rootpart.EveryoneMask = everyone_mask;
320 rootpart.GroupID = group_id;
321 rootpart.GroupMask = group_mask;
322 rootpart.NextOwnerMask = next_owner_mask;
323 rootpart.Material = (byte)material;
324
325
326
327 m_scene.PhysicsScene.AddPhysicsActorTaint(rootpart.PhysActor);
328
329 responsedata["int_response_code"] = 200; //501; //410; //404;
330 responsedata["content_type"] = "text/plain";
331 responsedata["keepalive"] = false;
332 responsedata["str_response_string"] = String.Format("<llsd><map><key>local_id</key>{0}</map></llsd>",ConvertUintToBytes(obj.LocalId));
333
334 return responsedata;
335 }
336
337 private uint readuintval(OSD obj)
338 {
339 byte[] tmp = obj.AsBinary();
340 if (BitConverter.IsLittleEndian)
341 Array.Reverse(tmp);
342 return Utils.BytesToUInt(tmp);
343
344 }
345 private string ConvertUintToBytes(uint val)
346 {
347 byte[] resultbytes = Utils.UIntToBytes(val);
348 if (BitConverter.IsLittleEndian)
349 Array.Reverse(resultbytes);
350 return String.Format("<binary encoding=\"base64\">{0}</binary>",Convert.ToBase64String(resultbytes));
351 }
352
353 public void Close()
354 {
355
356 }
357
358 public string Name
359 {
360 get { return "ObjectAddModule"; }
361 }
362
363 public bool IsSharedModule
364 {
365 get { return false; }
366 }
367
368 #endregion
369 }
370}
diff --git a/OpenSim/Region/CoreModules/Avatar/ObjectCaps/UploadObjectAssetModule.cs b/OpenSim/Region/CoreModules/Avatar/ObjectCaps/UploadObjectAssetModule.cs
deleted file mode 100644
index 3114d7f..0000000
--- a/OpenSim/Region/CoreModules/Avatar/ObjectCaps/UploadObjectAssetModule.cs
+++ /dev/null
@@ -1,374 +0,0 @@
1/*
2 * Copyright (c) Contributors, http://opensimulator.org/
3 * See CONTRIBUTORS.TXT for a full list of copyright holders.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of the OpenSimulator Project nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27
28using System;
29using System.Collections;
30using System.Collections.Specialized;
31using System.Reflection;
32using System.IO;
33using System.Web;
34using Mono.Addins;
35using log4net;
36using Nini.Config;
37using OpenMetaverse;
38using OpenMetaverse.StructuredData;
39using OpenMetaverse.Messages.Linden;
40using OpenSim.Framework;
41using OpenSim.Framework.Servers;
42using OpenSim.Framework.Servers.HttpServer;
43using OpenSim.Region.Framework.Interfaces;
44using OpenSim.Region.Framework.Scenes;
45using OpenSim.Services.Interfaces;
46using Caps = OpenSim.Framework.Capabilities.Caps;
47using OSD = OpenMetaverse.StructuredData.OSD;
48using OSDMap = OpenMetaverse.StructuredData.OSDMap;
49using OpenSim.Framework.Capabilities;
50using ExtraParamType = OpenMetaverse.ExtraParamType;
51
52namespace OpenSim.Region.CoreModules.Avatar.ObjectCaps
53{
54 [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule")]
55 public class UploadObjectAssetModule : INonSharedRegionModule
56 {
57 private static readonly ILog m_log =
58 LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
59 private Scene m_scene;
60
61 #region IRegionModuleBase Members
62
63
64 public Type ReplaceableInterface
65 {
66 get { return null; }
67 }
68
69 public void Initialise(IConfigSource source)
70 {
71
72 }
73
74 public void AddRegion(Scene pScene)
75 {
76 m_scene = pScene;
77 }
78
79 public void RemoveRegion(Scene scene)
80 {
81
82 m_scene.EventManager.OnRegisterCaps -= RegisterCaps;
83 m_scene = null;
84 }
85
86 public void RegionLoaded(Scene scene)
87 {
88
89 m_scene.EventManager.OnRegisterCaps += RegisterCaps;
90 }
91
92 #endregion
93
94
95 #region IRegionModule Members
96
97
98
99 public void Close() { }
100
101 public string Name { get { return "UploadObjectAssetModuleModule"; } }
102
103
104 public void RegisterCaps(UUID agentID, Caps caps)
105 {
106 UUID capID = UUID.Random();
107
108// m_log.Debug("[UPLOAD OBJECT ASSET MODULE]: /CAPS/" + capID);
109 caps.RegisterHandler("UploadObjectAsset",
110 new RestHTTPHandler("POST", "/CAPS/OA/" + capID + "/",
111 delegate(Hashtable m_dhttpMethod)
112 {
113 return ProcessAdd(m_dhttpMethod, agentID, caps);
114 }));
115 /*
116 caps.RegisterHandler("NewFileAgentInventoryVariablePrice",
117
118 new LLSDStreamhandler<LLSDAssetUploadRequest, LLSDNewFileAngentInventoryVariablePriceReplyResponse>("POST",
119 "/CAPS/" + capID.ToString(),
120 delegate(LLSDAssetUploadRequest req)
121 {
122 return NewAgentInventoryRequest(req,agentID);
123 }));
124 */
125
126 }
127
128 #endregion
129
130
131 /// <summary>
132 /// Parses ad request
133 /// </summary>
134 /// <param name="request"></param>
135 /// <param name="AgentId"></param>
136 /// <param name="cap"></param>
137 /// <returns></returns>
138 public Hashtable ProcessAdd(Hashtable request, UUID AgentId, Caps cap)
139 {
140 Hashtable responsedata = new Hashtable();
141 responsedata["int_response_code"] = 400; //501; //410; //404;
142 responsedata["content_type"] = "text/plain";
143 responsedata["keepalive"] = false;
144 responsedata["str_response_string"] = "Request wasn't what was expected";
145 ScenePresence avatar;
146
147 if (!m_scene.TryGetScenePresence(AgentId, out avatar))
148 return responsedata;
149
150 OSDMap r = (OSDMap)OSDParser.Deserialize((string)request["requestbody"]);
151 UploadObjectAssetMessage message = new UploadObjectAssetMessage();
152 try
153 {
154 message.Deserialize(r);
155
156 }
157 catch (Exception ex)
158 {
159 m_log.Error("[UPLOAD OBJECT ASSET MODULE]: Error deserializing message " + ex.ToString());
160 message = null;
161 }
162
163 if (message == null)
164 {
165 responsedata["int_response_code"] = 400; //501; //410; //404;
166 responsedata["content_type"] = "text/plain";
167 responsedata["keepalive"] = false;
168 responsedata["str_response_string"] =
169 "<llsd><map><key>error</key><string>Error parsing Object</string></map></llsd>";
170
171 return responsedata;
172 }
173
174 Vector3 pos = avatar.AbsolutePosition + (Vector3.UnitX * avatar.Rotation);
175 Quaternion rot = Quaternion.Identity;
176 Vector3 rootpos = Vector3.Zero;
177// Quaternion rootrot = Quaternion.Identity;
178
179 SceneObjectGroup rootGroup = null;
180 SceneObjectGroup[] allparts = new SceneObjectGroup[message.Objects.Length];
181 for (int i = 0; i < message.Objects.Length; i++)
182 {
183 UploadObjectAssetMessage.Object obj = message.Objects[i];
184 PrimitiveBaseShape pbs = PrimitiveBaseShape.CreateBox();
185
186 if (i == 0)
187 {
188 rootpos = obj.Position;
189// rootrot = obj.Rotation;
190 }
191
192 // Combine the extraparams data into it's ugly blob again....
193 //int bytelength = 0;
194 //for (int extparams = 0; extparams < obj.ExtraParams.Length; extparams++)
195 //{
196 // bytelength += obj.ExtraParams[extparams].ExtraParamData.Length;
197 //}
198 //byte[] extraparams = new byte[bytelength];
199 //int position = 0;
200
201
202
203 //for (int extparams = 0; extparams < obj.ExtraParams.Length; extparams++)
204 //{
205 // Buffer.BlockCopy(obj.ExtraParams[extparams].ExtraParamData, 0, extraparams, position,
206 // obj.ExtraParams[extparams].ExtraParamData.Length);
207 //
208 // position += obj.ExtraParams[extparams].ExtraParamData.Length;
209 // }
210
211 //pbs.ExtraParams = extraparams;
212 for (int extparams = 0; extparams < obj.ExtraParams.Length; extparams++)
213 {
214 UploadObjectAssetMessage.Object.ExtraParam extraParam = obj.ExtraParams[extparams];
215 switch ((ushort)extraParam.Type)
216 {
217 case (ushort)ExtraParamType.Sculpt:
218 Primitive.SculptData sculpt = new Primitive.SculptData(extraParam.ExtraParamData, 0);
219
220 pbs.SculptEntry = true;
221
222 pbs.SculptTexture = obj.SculptID;
223 pbs.SculptType = (byte)sculpt.Type;
224
225 break;
226 case (ushort)ExtraParamType.Flexible:
227 Primitive.FlexibleData flex = new Primitive.FlexibleData(extraParam.ExtraParamData, 0);
228 pbs.FlexiEntry = true;
229 pbs.FlexiDrag = flex.Drag;
230 pbs.FlexiForceX = flex.Force.X;
231 pbs.FlexiForceY = flex.Force.Y;
232 pbs.FlexiForceZ = flex.Force.Z;
233 pbs.FlexiGravity = flex.Gravity;
234 pbs.FlexiSoftness = flex.Softness;
235 pbs.FlexiTension = flex.Tension;
236 pbs.FlexiWind = flex.Wind;
237 break;
238 case (ushort)ExtraParamType.Light:
239 Primitive.LightData light = new Primitive.LightData(extraParam.ExtraParamData, 0);
240 pbs.LightColorA = light.Color.A;
241 pbs.LightColorB = light.Color.B;
242 pbs.LightColorG = light.Color.G;
243 pbs.LightColorR = light.Color.R;
244 pbs.LightCutoff = light.Cutoff;
245 pbs.LightEntry = true;
246 pbs.LightFalloff = light.Falloff;
247 pbs.LightIntensity = light.Intensity;
248 pbs.LightRadius = light.Radius;
249 break;
250 case 0x40:
251 pbs.ReadProjectionData(extraParam.ExtraParamData, 0);
252 break;
253
254 }
255
256
257 }
258 pbs.PathBegin = (ushort) obj.PathBegin;
259 pbs.PathCurve = (byte) obj.PathCurve;
260 pbs.PathEnd = (ushort) obj.PathEnd;
261 pbs.PathRadiusOffset = (sbyte) obj.RadiusOffset;
262 pbs.PathRevolutions = (byte) obj.Revolutions;
263 pbs.PathScaleX = (byte) obj.ScaleX;
264 pbs.PathScaleY = (byte) obj.ScaleY;
265 pbs.PathShearX = (byte) obj.ShearX;
266 pbs.PathShearY = (byte) obj.ShearY;
267 pbs.PathSkew = (sbyte) obj.Skew;
268 pbs.PathTaperX = (sbyte) obj.TaperX;
269 pbs.PathTaperY = (sbyte) obj.TaperY;
270 pbs.PathTwist = (sbyte) obj.Twist;
271 pbs.PathTwistBegin = (sbyte) obj.TwistBegin;
272 pbs.HollowShape = (HollowShape) obj.ProfileHollow;
273 pbs.PCode = (byte) PCode.Prim;
274 pbs.ProfileBegin = (ushort) obj.ProfileBegin;
275 pbs.ProfileCurve = (byte) obj.ProfileCurve;
276 pbs.ProfileEnd = (ushort) obj.ProfileEnd;
277 pbs.Scale = obj.Scale;
278 pbs.State = (byte) 0;
279 SceneObjectPart prim = new SceneObjectPart();
280 prim.UUID = UUID.Random();
281 prim.CreatorID = AgentId;
282 prim.OwnerID = AgentId;
283 prim.GroupID = obj.GroupID;
284 prim.LastOwnerID = prim.OwnerID;
285 prim.CreationDate = Util.UnixTimeSinceEpoch();
286 prim.Name = obj.Name;
287 prim.Description = "";
288
289 prim.PayPrice[0] = -2;
290 prim.PayPrice[1] = -2;
291 prim.PayPrice[2] = -2;
292 prim.PayPrice[3] = -2;
293 prim.PayPrice[4] = -2;
294 Primitive.TextureEntry tmp =
295 new Primitive.TextureEntry(UUID.Parse("89556747-24cb-43ed-920b-47caed15465f"));
296
297 for (int j = 0; j < obj.Faces.Length; j++)
298 {
299 UploadObjectAssetMessage.Object.Face face = obj.Faces[j];
300
301 Primitive.TextureEntryFace primFace = tmp.CreateFace((uint) j);
302
303 primFace.Bump = face.Bump;
304 primFace.RGBA = face.Color;
305 primFace.Fullbright = face.Fullbright;
306 primFace.Glow = face.Glow;
307 primFace.TextureID = face.ImageID;
308 primFace.Rotation = face.ImageRot;
309 primFace.MediaFlags = ((face.MediaFlags & 1) != 0);
310
311 primFace.OffsetU = face.OffsetS;
312 primFace.OffsetV = face.OffsetT;
313 primFace.RepeatU = face.ScaleS;
314 primFace.RepeatV = face.ScaleT;
315 primFace.TexMapType = (MappingType) (face.MediaFlags & 6);
316 }
317 pbs.TextureEntry = tmp.GetBytes();
318 prim.Shape = pbs;
319 prim.Scale = obj.Scale;
320
321
322 SceneObjectGroup grp = new SceneObjectGroup();
323
324 grp.SetRootPart(prim);
325 prim.ParentID = 0;
326 if (i == 0)
327 {
328 rootGroup = grp;
329
330 }
331 grp.AttachToScene(m_scene);
332 grp.AbsolutePosition = obj.Position;
333 prim.RotationOffset = obj.Rotation;
334
335 grp.RootPart.IsAttachment = false;
336 // Required for linking
337 grp.RootPart.UpdateFlag = 0;
338
339 if (m_scene.Permissions.CanRezObject(1, avatar.UUID, pos))
340 {
341 m_scene.AddSceneObject(grp);
342 grp.AbsolutePosition = obj.Position;
343 }
344 allparts[i] = grp;
345
346 }
347
348 for (int j = 1; j < allparts.Length; j++)
349 {
350 rootGroup.RootPart.UpdateFlag = 0;
351 allparts[j].RootPart.UpdateFlag = 0;
352 rootGroup.LinkToGroup(allparts[j]);
353 }
354
355 rootGroup.ScheduleGroupForFullUpdate();
356 pos = m_scene.GetNewRezLocation(Vector3.Zero, rootpos, UUID.Zero, rot, (byte)1, 1, true, allparts[0].GroupScale(), false);
357
358 responsedata["int_response_code"] = 200; //501; //410; //404;
359 responsedata["content_type"] = "text/plain";
360 responsedata["keepalive"] = false;
361 responsedata["str_response_string"] = String.Format("<llsd><map><key>local_id</key>{0}</map></llsd>", ConvertUintToBytes(allparts[0].LocalId));
362
363 return responsedata;
364 }
365
366 private string ConvertUintToBytes(uint val)
367 {
368 byte[] resultbytes = Utils.UIntToBytes(val);
369 if (BitConverter.IsLittleEndian)
370 Array.Reverse(resultbytes);
371 return String.Format("<binary encoding=\"base64\">{0}</binary>", Convert.ToBase64String(resultbytes));
372 }
373 }
374} \ No newline at end of file
diff --git a/OpenSim/Region/CoreModules/Framework/EventQueue/EventQueueGetModule.cs b/OpenSim/Region/CoreModules/Framework/EventQueue/EventQueueGetModule.cs
deleted file mode 100644
index 05fe3ee..0000000
--- a/OpenSim/Region/CoreModules/Framework/EventQueue/EventQueueGetModule.cs
+++ /dev/null
@@ -1,719 +0,0 @@
1/*
2 * Copyright (c) Contributors, http://opensimulator.org/
3 * See CONTRIBUTORS.TXT for a full list of copyright holders.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of the OpenSimulator Project nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27
28using System;
29using System.Collections;
30using System.Collections.Generic;
31using System.Net;
32using System.Reflection;
33using System.Threading;
34using log4net;
35using Nini.Config;
36using OpenMetaverse;
37using OpenMetaverse.Messages.Linden;
38using OpenMetaverse.Packets;
39using OpenMetaverse.StructuredData;
40using OpenSim.Framework;
41using OpenSim.Framework.Servers;
42using OpenSim.Framework.Servers.HttpServer;
43using OpenSim.Region.Framework.Interfaces;
44using OpenSim.Region.Framework.Scenes;
45using BlockingLLSDQueue = OpenSim.Framework.BlockingQueue<OpenMetaverse.StructuredData.OSD>;
46using Caps=OpenSim.Framework.Capabilities.Caps;
47
48namespace OpenSim.Region.CoreModules.Framework.EventQueue
49{
50 public struct QueueItem
51 {
52 public int id;
53 public OSDMap body;
54 }
55
56 public class EventQueueGetModule : IEventQueue, IRegionModule
57 {
58 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
59 protected Scene m_scene = null;
60 private IConfigSource m_gConfig;
61 bool enabledYN = false;
62
63 private Dictionary<UUID, int> m_ids = new Dictionary<UUID, int>();
64
65 private Dictionary<UUID, Queue<OSD>> queues = new Dictionary<UUID, Queue<OSD>>();
66 private Dictionary<UUID, UUID> m_QueueUUIDAvatarMapping = new Dictionary<UUID, UUID>();
67 private Dictionary<UUID, UUID> m_AvatarQueueUUIDMapping = new Dictionary<UUID, UUID>();
68
69 #region IRegionModule methods
70 public virtual void Initialise(Scene scene, IConfigSource config)
71 {
72 m_gConfig = config;
73
74 IConfig startupConfig = m_gConfig.Configs["Startup"];
75
76 ReadConfigAndPopulate(scene, startupConfig, "Startup");
77
78 if (enabledYN)
79 {
80 m_scene = scene;
81 scene.RegisterModuleInterface<IEventQueue>(this);
82
83 // Register fallback handler
84 // Why does EQG Fail on region crossings!
85
86 //scene.CommsManager.HttpServer.AddLLSDHandler("/CAPS/EQG/", EventQueueFallBack);
87
88 scene.EventManager.OnNewClient += OnNewClient;
89
90 // TODO: Leaving these open, or closing them when we
91 // become a child is incorrect. It messes up TP in a big
92 // way. CAPS/EQ need to be active as long as the UDP
93 // circuit is there.
94
95 scene.EventManager.OnClientClosed += ClientClosed;
96 scene.EventManager.OnMakeChildAgent += MakeChildAgent;
97 scene.EventManager.OnRegisterCaps += OnRegisterCaps;
98 }
99 else
100 {
101 m_gConfig = null;
102 }
103
104 }
105
106 private void ReadConfigAndPopulate(Scene scene, IConfig startupConfig, string p)
107 {
108 enabledYN = startupConfig.GetBoolean("EventQueue", true);
109 }
110
111 public void PostInitialise()
112 {
113 }
114
115 public virtual void Close()
116 {
117 }
118
119 public virtual string Name
120 {
121 get { return "EventQueueGetModule"; }
122 }
123
124 public bool IsSharedModule
125 {
126 get { return false; }
127 }
128 #endregion
129
130 /// <summary>
131 /// Always returns a valid queue
132 /// </summary>
133 /// <param name="agentId"></param>
134 /// <returns></returns>
135 private Queue<OSD> TryGetQueue(UUID agentId)
136 {
137 lock (queues)
138 {
139 if (!queues.ContainsKey(agentId))
140 {
141 /*
142 m_log.DebugFormat(
143 "[EVENTQUEUE]: Adding new queue for agent {0} in region {1}",
144 agentId, m_scene.RegionInfo.RegionName);
145 */
146 queues[agentId] = new Queue<OSD>();
147 }
148
149 return queues[agentId];
150 }
151 }
152
153 /// <summary>
154 /// May return a null queue
155 /// </summary>
156 /// <param name="agentId"></param>
157 /// <returns></returns>
158 private Queue<OSD> GetQueue(UUID agentId)
159 {
160 lock (queues)
161 {
162 if (queues.ContainsKey(agentId))
163 {
164 return queues[agentId];
165 }
166 else
167 return null;
168 }
169 }
170
171 #region IEventQueue Members
172
173 public bool Enqueue(OSD ev, UUID avatarID)
174 {
175 //m_log.DebugFormat("[EVENTQUEUE]: Enqueuing event for {0} in region {1}", avatarID, m_scene.RegionInfo.RegionName);
176 try
177 {
178 Queue<OSD> queue = GetQueue(avatarID);
179 if (queue != null)
180 queue.Enqueue(ev);
181 }
182 catch(NullReferenceException e)
183 {
184 m_log.Error("[EVENTQUEUE] Caught exception: " + e);
185 return false;
186 }
187
188 return true;
189 }
190
191 #endregion
192
193 private void OnNewClient(IClientAPI client)
194 {
195 //client.OnLogout += ClientClosed;
196 }
197
198// private void ClientClosed(IClientAPI client)
199// {
200// ClientClosed(client.AgentId);
201// }
202
203 private void ClientClosed(UUID AgentID, Scene scene)
204 {
205 //m_log.DebugFormat("[EVENTQUEUE]: Closed client {0} in region {1}", AgentID, m_scene.RegionInfo.RegionName);
206
207 int count = 0;
208 while (queues.ContainsKey(AgentID) && queues[AgentID].Count > 0 && count++ < 5)
209 {
210 Thread.Sleep(1000);
211 }
212
213 lock (queues)
214 {
215 queues.Remove(AgentID);
216 }
217 List<UUID> removeitems = new List<UUID>();
218 lock (m_AvatarQueueUUIDMapping)
219 {
220 foreach (UUID ky in m_AvatarQueueUUIDMapping.Keys)
221 {
222 if (ky == AgentID)
223 {
224 removeitems.Add(ky);
225 }
226 }
227
228 foreach (UUID ky in removeitems)
229 {
230 m_AvatarQueueUUIDMapping.Remove(ky);
231 MainServer.Instance.RemovePollServiceHTTPHandler("","/CAPS/EQG/" + ky.ToString() + "/");
232 }
233
234 }
235 UUID searchval = UUID.Zero;
236
237 removeitems.Clear();
238
239 lock (m_QueueUUIDAvatarMapping)
240 {
241 foreach (UUID ky in m_QueueUUIDAvatarMapping.Keys)
242 {
243 searchval = m_QueueUUIDAvatarMapping[ky];
244
245 if (searchval == AgentID)
246 {
247 removeitems.Add(ky);
248 }
249 }
250
251 foreach (UUID ky in removeitems)
252 m_QueueUUIDAvatarMapping.Remove(ky);
253
254 }
255 }
256
257 private void MakeChildAgent(ScenePresence avatar)
258 {
259 //m_log.DebugFormat("[EVENTQUEUE]: Make Child agent {0} in region {1}.", avatar.UUID, m_scene.RegionInfo.RegionName);
260 //lock (m_ids)
261 // {
262 //if (m_ids.ContainsKey(avatar.UUID))
263 //{
264 // close the event queue.
265 //m_ids[avatar.UUID] = -1;
266 //}
267 //}
268 }
269
270 public void OnRegisterCaps(UUID agentID, Caps caps)
271 {
272 // Register an event queue for the client
273
274 //m_log.DebugFormat(
275 // "[EVENTQUEUE]: OnRegisterCaps: agentID {0} caps {1} region {2}",
276 // agentID, caps, m_scene.RegionInfo.RegionName);
277
278 // Let's instantiate a Queue for this agent right now
279 TryGetQueue(agentID);
280
281 string capsBase = "/CAPS/EQG/";
282 UUID EventQueueGetUUID = UUID.Zero;
283
284 lock (m_AvatarQueueUUIDMapping)
285 {
286 // Reuse open queues. The client does!
287 if (m_AvatarQueueUUIDMapping.ContainsKey(agentID))
288 {
289 //m_log.DebugFormat("[EVENTQUEUE]: Found Existing UUID!");
290 EventQueueGetUUID = m_AvatarQueueUUIDMapping[agentID];
291 }
292 else
293 {
294 EventQueueGetUUID = UUID.Random();
295 //m_log.DebugFormat("[EVENTQUEUE]: Using random UUID!");
296 }
297 }
298
299 lock (m_QueueUUIDAvatarMapping)
300 {
301 if (!m_QueueUUIDAvatarMapping.ContainsKey(EventQueueGetUUID))
302 m_QueueUUIDAvatarMapping.Add(EventQueueGetUUID, agentID);
303 }
304
305 lock (m_AvatarQueueUUIDMapping)
306 {
307 if (!m_AvatarQueueUUIDMapping.ContainsKey(agentID))
308 m_AvatarQueueUUIDMapping.Add(agentID, EventQueueGetUUID);
309 }
310
311 // Register this as a caps handler
312 caps.RegisterHandler("EventQueueGet",
313 new RestHTTPHandler("POST", capsBase + EventQueueGetUUID.ToString() + "/",
314 delegate(Hashtable m_dhttpMethod)
315 {
316 return ProcessQueue(m_dhttpMethod, agentID, caps);
317 }));
318
319 // This will persist this beyond the expiry of the caps handlers
320 MainServer.Instance.AddPollServiceHTTPHandler(
321 capsBase + EventQueueGetUUID.ToString() + "/", EventQueuePoll, new PollServiceEventArgs(null, HasEvents, GetEvents, NoEvents, agentID));
322
323 Random rnd = new Random(Environment.TickCount);
324 lock (m_ids)
325 {
326 if (!m_ids.ContainsKey(agentID))
327 m_ids.Add(agentID, rnd.Next(30000000));
328 }
329 }
330
331 public bool HasEvents(UUID requestID, UUID agentID)
332 {
333 // Don't use this, because of race conditions at agent closing time
334 //Queue<OSD> queue = TryGetQueue(agentID);
335
336 Queue<OSD> queue = GetQueue(agentID);
337 if (queue != null)
338 lock (queue)
339 {
340 if (queue.Count > 0)
341 return true;
342 else
343 return false;
344 }
345 return false;
346 }
347
348 public Hashtable GetEvents(UUID requestID, UUID pAgentId, string request)
349 {
350 Queue<OSD> queue = TryGetQueue(pAgentId);
351 OSD element;
352 lock (queue)
353 {
354 if (queue.Count == 0)
355 return NoEvents(requestID, pAgentId);
356 element = queue.Dequeue(); // 15s timeout
357 }
358
359
360
361 int thisID = 0;
362 lock (m_ids)
363 thisID = m_ids[pAgentId];
364
365 OSDArray array = new OSDArray();
366 if (element == null) // didn't have an event in 15s
367 {
368 // Send it a fake event to keep the client polling! It doesn't like 502s like the proxys say!
369 array.Add(EventQueueHelper.KeepAliveEvent());
370 //m_log.DebugFormat("[EVENTQUEUE]: adding fake event for {0} in region {1}", pAgentId, m_scene.RegionInfo.RegionName);
371 }
372 else
373 {
374 array.Add(element);
375 lock (queue)
376 {
377 while (queue.Count > 0)
378 {
379 array.Add(queue.Dequeue());
380 thisID++;
381 }
382 }
383 }
384
385 OSDMap events = new OSDMap();
386 events.Add("events", array);
387
388 events.Add("id", new OSDInteger(thisID));
389 lock (m_ids)
390 {
391 m_ids[pAgentId] = thisID + 1;
392 }
393 Hashtable responsedata = new Hashtable();
394 responsedata["int_response_code"] = 200;
395 responsedata["content_type"] = "application/xml";
396 responsedata["keepalive"] = false;
397 responsedata["reusecontext"] = false;
398 responsedata["str_response_string"] = OSDParser.SerializeLLSDXmlString(events);
399 //m_log.DebugFormat("[EVENTQUEUE]: sending response for {0} in region {1}: {2}", pAgentId, m_scene.RegionInfo.RegionName, responsedata["str_response_string"]);
400 return responsedata;
401 }
402
403 public Hashtable NoEvents(UUID requestID, UUID agentID)
404 {
405 Hashtable responsedata = new Hashtable();
406 responsedata["int_response_code"] = 502;
407 responsedata["content_type"] = "text/plain";
408 responsedata["keepalive"] = false;
409 responsedata["reusecontext"] = false;
410 responsedata["str_response_string"] = "Upstream error: ";
411 responsedata["error_status_text"] = "Upstream error:";
412 responsedata["http_protocol_version"] = "HTTP/1.0";
413 return responsedata;
414 }
415
416 public Hashtable ProcessQueue(Hashtable request, UUID agentID, Caps caps)
417 {
418 // TODO: this has to be redone to not busy-wait (and block the thread),
419 // TODO: as soon as we have a non-blocking way to handle HTTP-requests.
420
421// if (m_log.IsDebugEnabled)
422// {
423// String debug = "[EVENTQUEUE]: Got request for agent {0} in region {1} from thread {2}: [ ";
424// foreach (object key in request.Keys)
425// {
426// debug += key.ToString() + "=" + request[key].ToString() + " ";
427// }
428// m_log.DebugFormat(debug + " ]", agentID, m_scene.RegionInfo.RegionName, System.Threading.Thread.CurrentThread.Name);
429// }
430
431 Queue<OSD> queue = TryGetQueue(agentID);
432 OSD element = queue.Dequeue(); // 15s timeout
433
434 Hashtable responsedata = new Hashtable();
435
436 int thisID = 0;
437 lock (m_ids)
438 thisID = m_ids[agentID];
439
440 if (element == null)
441 {
442 //m_log.ErrorFormat("[EVENTQUEUE]: Nothing to process in " + m_scene.RegionInfo.RegionName);
443 if (thisID == -1) // close-request
444 {
445 m_log.ErrorFormat("[EVENTQUEUE]: 404 in " + m_scene.RegionInfo.RegionName);
446 responsedata["int_response_code"] = 404; //501; //410; //404;
447 responsedata["content_type"] = "text/plain";
448 responsedata["keepalive"] = false;
449 responsedata["str_response_string"] = "Closed EQG";
450 return responsedata;
451 }
452 responsedata["int_response_code"] = 502;
453 responsedata["content_type"] = "text/plain";
454 responsedata["keepalive"] = false;
455 responsedata["str_response_string"] = "Upstream error: ";
456 responsedata["error_status_text"] = "Upstream error:";
457 responsedata["http_protocol_version"] = "HTTP/1.0";
458 return responsedata;
459 }
460
461 OSDArray array = new OSDArray();
462 if (element == null) // didn't have an event in 15s
463 {
464 // Send it a fake event to keep the client polling! It doesn't like 502s like the proxys say!
465 array.Add(EventQueueHelper.KeepAliveEvent());
466 //m_log.DebugFormat("[EVENTQUEUE]: adding fake event for {0} in region {1}", agentID, m_scene.RegionInfo.RegionName);
467 }
468 else
469 {
470 array.Add(element);
471 while (queue.Count > 0)
472 {
473 array.Add(queue.Dequeue());
474 thisID++;
475 }
476 }
477
478 OSDMap events = new OSDMap();
479 events.Add("events", array);
480
481 events.Add("id", new OSDInteger(thisID));
482 lock (m_ids)
483 {
484 m_ids[agentID] = thisID + 1;
485 }
486
487 responsedata["int_response_code"] = 200;
488 responsedata["content_type"] = "application/xml";
489 responsedata["keepalive"] = false;
490 responsedata["str_response_string"] = OSDParser.SerializeLLSDXmlString(events);
491 //m_log.DebugFormat("[EVENTQUEUE]: sending response for {0} in region {1}: {2}", agentID, m_scene.RegionInfo.RegionName, responsedata["str_response_string"]);
492
493 return responsedata;
494 }
495
496 public Hashtable EventQueuePoll(Hashtable request)
497 {
498 return new Hashtable();
499 }
500
501 public Hashtable EventQueuePath2(Hashtable request)
502 {
503 string capuuid = (string)request["uri"]; //path.Replace("/CAPS/EQG/","");
504 // pull off the last "/" in the path.
505 Hashtable responsedata = new Hashtable();
506 capuuid = capuuid.Substring(0, capuuid.Length - 1);
507 capuuid = capuuid.Replace("/CAPS/EQG/", "");
508 UUID AvatarID = UUID.Zero;
509 UUID capUUID = UUID.Zero;
510
511 // parse the path and search for the avatar with it registered
512 if (UUID.TryParse(capuuid, out capUUID))
513 {
514 lock (m_QueueUUIDAvatarMapping)
515 {
516 if (m_QueueUUIDAvatarMapping.ContainsKey(capUUID))
517 {
518 AvatarID = m_QueueUUIDAvatarMapping[capUUID];
519 }
520 }
521 if (AvatarID != UUID.Zero)
522 {
523 return ProcessQueue(request, AvatarID, m_scene.CapsModule.GetCapsHandlerForUser(AvatarID));
524 }
525 else
526 {
527 responsedata["int_response_code"] = 404;
528 responsedata["content_type"] = "text/plain";
529 responsedata["keepalive"] = false;
530 responsedata["str_response_string"] = "Not Found";
531 responsedata["error_status_text"] = "Not Found";
532 responsedata["http_protocol_version"] = "HTTP/1.0";
533 return responsedata;
534 // return 404
535 }
536 }
537 else
538 {
539 responsedata["int_response_code"] = 404;
540 responsedata["content_type"] = "text/plain";
541 responsedata["keepalive"] = false;
542 responsedata["str_response_string"] = "Not Found";
543 responsedata["error_status_text"] = "Not Found";
544 responsedata["http_protocol_version"] = "HTTP/1.0";
545 return responsedata;
546 // return 404
547 }
548
549 }
550
551 public OSD EventQueueFallBack(string path, OSD request, string endpoint)
552 {
553 // This is a fallback element to keep the client from loosing EventQueueGet
554 // Why does CAPS fail sometimes!?
555 m_log.Warn("[EVENTQUEUE]: In the Fallback handler! We lost the Queue in the rest handler!");
556 string capuuid = path.Replace("/CAPS/EQG/","");
557 capuuid = capuuid.Substring(0, capuuid.Length - 1);
558
559// UUID AvatarID = UUID.Zero;
560 UUID capUUID = UUID.Zero;
561 if (UUID.TryParse(capuuid, out capUUID))
562 {
563/* Don't remove this yet code cleaners!
564 * Still testing this!
565 *
566 lock (m_QueueUUIDAvatarMapping)
567 {
568 if (m_QueueUUIDAvatarMapping.ContainsKey(capUUID))
569 {
570 AvatarID = m_QueueUUIDAvatarMapping[capUUID];
571 }
572 }
573
574
575 if (AvatarID != UUID.Zero)
576 {
577 // Repair the CAP!
578 //OpenSim.Framework.Capabilities.Caps caps = m_scene.GetCapsHandlerForUser(AvatarID);
579 //string capsBase = "/CAPS/EQG/";
580 //caps.RegisterHandler("EventQueueGet",
581 //new RestHTTPHandler("POST", capsBase + capUUID.ToString() + "/",
582 //delegate(Hashtable m_dhttpMethod)
583 //{
584 // return ProcessQueue(m_dhttpMethod, AvatarID, caps);
585 //}));
586 // start new ID sequence.
587 Random rnd = new Random(System.Environment.TickCount);
588 lock (m_ids)
589 {
590 if (!m_ids.ContainsKey(AvatarID))
591 m_ids.Add(AvatarID, rnd.Next(30000000));
592 }
593
594
595 int thisID = 0;
596 lock (m_ids)
597 thisID = m_ids[AvatarID];
598
599 BlockingLLSDQueue queue = GetQueue(AvatarID);
600 OSDArray array = new OSDArray();
601 LLSD element = queue.Dequeue(15000); // 15s timeout
602 if (element == null)
603 {
604
605 array.Add(EventQueueHelper.KeepAliveEvent());
606 }
607 else
608 {
609 array.Add(element);
610 while (queue.Count() > 0)
611 {
612 array.Add(queue.Dequeue(1));
613 thisID++;
614 }
615 }
616 OSDMap events = new OSDMap();
617 events.Add("events", array);
618
619 events.Add("id", new LLSDInteger(thisID));
620
621 lock (m_ids)
622 {
623 m_ids[AvatarID] = thisID + 1;
624 }
625
626 return events;
627 }
628 else
629 {
630 return new LLSD();
631 }
632*
633*/
634 }
635 else
636 {
637 //return new LLSD();
638 }
639
640 return new OSDString("shutdown404!");
641 }
642
643 public void DisableSimulator(ulong handle, UUID avatarID)
644 {
645 OSD item = EventQueueHelper.DisableSimulator(handle);
646 Enqueue(item, avatarID);
647 }
648
649 public virtual void EnableSimulator(ulong handle, IPEndPoint endPoint, UUID avatarID)
650 {
651 OSD item = EventQueueHelper.EnableSimulator(handle, endPoint);
652 Enqueue(item, avatarID);
653 }
654
655 public virtual void EstablishAgentCommunication(UUID avatarID, IPEndPoint endPoint, string capsPath)
656 {
657 OSD item = EventQueueHelper.EstablishAgentCommunication(avatarID, endPoint.ToString(), capsPath);
658 Enqueue(item, avatarID);
659 }
660
661 public virtual void TeleportFinishEvent(ulong regionHandle, byte simAccess,
662 IPEndPoint regionExternalEndPoint,
663 uint locationID, uint flags, string capsURL,
664 UUID avatarID)
665 {
666 OSD item = EventQueueHelper.TeleportFinishEvent(regionHandle, simAccess, regionExternalEndPoint,
667 locationID, flags, capsURL, avatarID);
668 Enqueue(item, avatarID);
669 }
670
671 public virtual void CrossRegion(ulong handle, Vector3 pos, Vector3 lookAt,
672 IPEndPoint newRegionExternalEndPoint,
673 string capsURL, UUID avatarID, UUID sessionID)
674 {
675 OSD item = EventQueueHelper.CrossRegion(handle, pos, lookAt, newRegionExternalEndPoint,
676 capsURL, avatarID, sessionID);
677 Enqueue(item, avatarID);
678 }
679
680 public void ChatterboxInvitation(UUID sessionID, string sessionName,
681 UUID fromAgent, string message, UUID toAgent, string fromName, byte dialog,
682 uint timeStamp, bool offline, int parentEstateID, Vector3 position,
683 uint ttl, UUID transactionID, bool fromGroup, byte[] binaryBucket)
684 {
685 OSD item = EventQueueHelper.ChatterboxInvitation(sessionID, sessionName, fromAgent, message, toAgent, fromName, dialog,
686 timeStamp, offline, parentEstateID, position, ttl, transactionID,
687 fromGroup, binaryBucket);
688 Enqueue(item, toAgent);
689 //m_log.InfoFormat("########### eq ChatterboxInvitation #############\n{0}", item);
690
691 }
692
693 public void ChatterBoxSessionAgentListUpdates(UUID sessionID, UUID fromAgent, UUID toAgent, bool canVoiceChat,
694 bool isModerator, bool textMute)
695 {
696 OSD item = EventQueueHelper.ChatterBoxSessionAgentListUpdates(sessionID, fromAgent, canVoiceChat,
697 isModerator, textMute);
698 Enqueue(item, toAgent);
699 //m_log.InfoFormat("########### eq ChatterBoxSessionAgentListUpdates #############\n{0}", item);
700 }
701
702 public void ParcelProperties(ParcelPropertiesMessage parcelPropertiesMessage, UUID avatarID)
703 {
704 OSD item = EventQueueHelper.ParcelProperties(parcelPropertiesMessage);
705 Enqueue(item, avatarID);
706 }
707
708 public void GroupMembership(AgentGroupDataUpdatePacket groupUpdate, UUID avatarID)
709 {
710 OSD item = EventQueueHelper.GroupMembership(groupUpdate);
711 Enqueue(item, avatarID);
712 }
713 public void QueryReply(PlacesReplyPacket groupUpdate, UUID avatarID)
714 {
715 OSD item = EventQueueHelper.PlacesQuery(groupUpdate);
716 Enqueue(item, avatarID);
717 }
718 }
719}
diff --git a/OpenSim/Region/CoreModules/Framework/EventQueue/EventQueueHelper.cs b/OpenSim/Region/CoreModules/Framework/EventQueue/EventQueueHelper.cs
deleted file mode 100644
index 0d7d16a..0000000
--- a/OpenSim/Region/CoreModules/Framework/EventQueue/EventQueueHelper.cs
+++ /dev/null
@@ -1,399 +0,0 @@
1/*
2 * Copyright (c) Contributors, http://opensimulator.org/
3 * See CONTRIBUTORS.TXT for a full list of copyright holders.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of the OpenSimulator Project nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27
28using System;
29using System.Net;
30using OpenMetaverse;
31using OpenMetaverse.Packets;
32using OpenMetaverse.StructuredData;
33using OpenMetaverse.Messages.Linden;
34
35namespace OpenSim.Region.CoreModules.Framework.EventQueue
36{
37 public class EventQueueHelper
38 {
39 private EventQueueHelper() {} // no construction possible, it's an utility class
40
41 private static byte[] ulongToByteArray(ulong uLongValue)
42 {
43 // Reverse endianness of RegionHandle
44 return new byte[]
45 {
46 (byte)((uLongValue >> 56) % 256),
47 (byte)((uLongValue >> 48) % 256),
48 (byte)((uLongValue >> 40) % 256),
49 (byte)((uLongValue >> 32) % 256),
50 (byte)((uLongValue >> 24) % 256),
51 (byte)((uLongValue >> 16) % 256),
52 (byte)((uLongValue >> 8) % 256),
53 (byte)(uLongValue % 256)
54 };
55 }
56
57// private static byte[] uintToByteArray(uint uIntValue)
58// {
59// byte[] result = new byte[4];
60// Utils.UIntToBytesBig(uIntValue, result, 0);
61// return result;
62// }
63
64 public static OSD buildEvent(string eventName, OSD eventBody)
65 {
66 OSDMap llsdEvent = new OSDMap(2);
67 llsdEvent.Add("message", new OSDString(eventName));
68 llsdEvent.Add("body", eventBody);
69
70 return llsdEvent;
71 }
72
73 public static OSD EnableSimulator(ulong handle, IPEndPoint endPoint)
74 {
75 OSDMap llsdSimInfo = new OSDMap(3);
76
77 llsdSimInfo.Add("Handle", new OSDBinary(ulongToByteArray(handle)));
78 llsdSimInfo.Add("IP", new OSDBinary(endPoint.Address.GetAddressBytes()));
79 llsdSimInfo.Add("Port", new OSDInteger(endPoint.Port));
80
81 OSDArray arr = new OSDArray(1);
82 arr.Add(llsdSimInfo);
83
84 OSDMap llsdBody = new OSDMap(1);
85 llsdBody.Add("SimulatorInfo", arr);
86
87 return buildEvent("EnableSimulator", llsdBody);
88 }
89
90 public static OSD DisableSimulator(ulong handle)
91 {
92 //OSDMap llsdSimInfo = new OSDMap(1);
93
94 //llsdSimInfo.Add("Handle", new OSDBinary(regionHandleToByteArray(handle)));
95
96 //OSDArray arr = new OSDArray(1);
97 //arr.Add(llsdSimInfo);
98
99 OSDMap llsdBody = new OSDMap(0);
100 //llsdBody.Add("SimulatorInfo", arr);
101
102 return buildEvent("DisableSimulator", llsdBody);
103 }
104
105 public static OSD CrossRegion(ulong handle, Vector3 pos, Vector3 lookAt,
106 IPEndPoint newRegionExternalEndPoint,
107 string capsURL, UUID agentID, UUID sessionID)
108 {
109 OSDArray lookAtArr = new OSDArray(3);
110 lookAtArr.Add(OSD.FromReal(lookAt.X));
111 lookAtArr.Add(OSD.FromReal(lookAt.Y));
112 lookAtArr.Add(OSD.FromReal(lookAt.Z));
113
114 OSDArray positionArr = new OSDArray(3);
115 positionArr.Add(OSD.FromReal(pos.X));
116 positionArr.Add(OSD.FromReal(pos.Y));
117 positionArr.Add(OSD.FromReal(pos.Z));
118
119 OSDMap infoMap = new OSDMap(2);
120 infoMap.Add("LookAt", lookAtArr);
121 infoMap.Add("Position", positionArr);
122
123 OSDArray infoArr = new OSDArray(1);
124 infoArr.Add(infoMap);
125
126 OSDMap agentDataMap = new OSDMap(2);
127 agentDataMap.Add("AgentID", OSD.FromUUID(agentID));
128 agentDataMap.Add("SessionID", OSD.FromUUID(sessionID));
129
130 OSDArray agentDataArr = new OSDArray(1);
131 agentDataArr.Add(agentDataMap);
132
133 OSDMap regionDataMap = new OSDMap(4);
134 regionDataMap.Add("RegionHandle", OSD.FromBinary(ulongToByteArray(handle)));
135 regionDataMap.Add("SeedCapability", OSD.FromString(capsURL));
136 regionDataMap.Add("SimIP", OSD.FromBinary(newRegionExternalEndPoint.Address.GetAddressBytes()));
137 regionDataMap.Add("SimPort", OSD.FromInteger(newRegionExternalEndPoint.Port));
138
139 OSDArray regionDataArr = new OSDArray(1);
140 regionDataArr.Add(regionDataMap);
141
142 OSDMap llsdBody = new OSDMap(3);
143 llsdBody.Add("Info", infoArr);
144 llsdBody.Add("AgentData", agentDataArr);
145 llsdBody.Add("RegionData", regionDataArr);
146
147 return buildEvent("CrossedRegion", llsdBody);
148 }
149
150 public static OSD TeleportFinishEvent(
151 ulong regionHandle, byte simAccess, IPEndPoint regionExternalEndPoint,
152 uint locationID, uint flags, string capsURL, UUID agentID)
153 {
154 OSDMap info = new OSDMap();
155 info.Add("AgentID", OSD.FromUUID(agentID));
156 info.Add("LocationID", OSD.FromInteger(4)); // TODO what is this?
157 info.Add("RegionHandle", OSD.FromBinary(ulongToByteArray(regionHandle)));
158 info.Add("SeedCapability", OSD.FromString(capsURL));
159 info.Add("SimAccess", OSD.FromInteger(simAccess));
160 info.Add("SimIP", OSD.FromBinary(regionExternalEndPoint.Address.GetAddressBytes()));
161 info.Add("SimPort", OSD.FromInteger(regionExternalEndPoint.Port));
162 info.Add("TeleportFlags", OSD.FromULong(1L << 4)); // AgentManager.TeleportFlags.ViaLocation
163
164 OSDArray infoArr = new OSDArray();
165 infoArr.Add(info);
166
167 OSDMap body = new OSDMap();
168 body.Add("Info", infoArr);
169
170 return buildEvent("TeleportFinish", body);
171 }
172
173 public static OSD ScriptRunningReplyEvent(UUID objectID, UUID itemID, bool running, bool mono)
174 {
175 OSDMap script = new OSDMap();
176 script.Add("ObjectID", OSD.FromUUID(objectID));
177 script.Add("ItemID", OSD.FromUUID(itemID));
178 script.Add("Running", OSD.FromBoolean(running));
179 script.Add("Mono", OSD.FromBoolean(mono));
180
181 OSDArray scriptArr = new OSDArray();
182 scriptArr.Add(script);
183
184 OSDMap body = new OSDMap();
185 body.Add("Script", scriptArr);
186
187 return buildEvent("ScriptRunningReply", body);
188 }
189
190 public static OSD EstablishAgentCommunication(UUID agentID, string simIpAndPort, string seedcap)
191 {
192 OSDMap body = new OSDMap(3);
193 body.Add("agent-id", new OSDUUID(agentID));
194 body.Add("sim-ip-and-port", new OSDString(simIpAndPort));
195 body.Add("seed-capability", new OSDString(seedcap));
196
197 return buildEvent("EstablishAgentCommunication", body);
198 }
199
200 public static OSD KeepAliveEvent()
201 {
202 return buildEvent("FAKEEVENT", new OSDMap());
203 }
204
205 public static OSD AgentParams(UUID agentID, bool checkEstate, int godLevel, bool limitedToEstate)
206 {
207 OSDMap body = new OSDMap(4);
208
209 body.Add("agent_id", new OSDUUID(agentID));
210 body.Add("check_estate", new OSDInteger(checkEstate ? 1 : 0));
211 body.Add("god_level", new OSDInteger(godLevel));
212 body.Add("limited_to_estate", new OSDInteger(limitedToEstate ? 1 : 0));
213
214 return body;
215 }
216
217 public static OSD InstantMessageParams(UUID fromAgent, string message, UUID toAgent,
218 string fromName, byte dialog, uint timeStamp, bool offline, int parentEstateID,
219 Vector3 position, uint ttl, UUID transactionID, bool fromGroup, byte[] binaryBucket)
220 {
221 OSDMap messageParams = new OSDMap(15);
222 messageParams.Add("type", new OSDInteger((int)dialog));
223
224 OSDArray positionArray = new OSDArray(3);
225 positionArray.Add(OSD.FromReal(position.X));
226 positionArray.Add(OSD.FromReal(position.Y));
227 positionArray.Add(OSD.FromReal(position.Z));
228 messageParams.Add("position", positionArray);
229
230 messageParams.Add("region_id", new OSDUUID(UUID.Zero));
231 messageParams.Add("to_id", new OSDUUID(toAgent));
232 messageParams.Add("source", new OSDInteger(0));
233
234 OSDMap data = new OSDMap(1);
235 data.Add("binary_bucket", OSD.FromBinary(binaryBucket));
236 messageParams.Add("data", data);
237 messageParams.Add("message", new OSDString(message));
238 messageParams.Add("id", new OSDUUID(transactionID));
239 messageParams.Add("from_name", new OSDString(fromName));
240 messageParams.Add("timestamp", new OSDInteger((int)timeStamp));
241 messageParams.Add("offline", new OSDInteger(offline ? 1 : 0));
242 messageParams.Add("parent_estate_id", new OSDInteger(parentEstateID));
243 messageParams.Add("ttl", new OSDInteger((int)ttl));
244 messageParams.Add("from_id", new OSDUUID(fromAgent));
245 messageParams.Add("from_group", new OSDInteger(fromGroup ? 1 : 0));
246
247 return messageParams;
248 }
249
250 public static OSD InstantMessage(UUID fromAgent, string message, UUID toAgent,
251 string fromName, byte dialog, uint timeStamp, bool offline, int parentEstateID,
252 Vector3 position, uint ttl, UUID transactionID, bool fromGroup, byte[] binaryBucket,
253 bool checkEstate, int godLevel, bool limitedToEstate)
254 {
255 OSDMap im = new OSDMap(2);
256 im.Add("message_params", InstantMessageParams(fromAgent, message, toAgent,
257 fromName, dialog, timeStamp, offline, parentEstateID,
258 position, ttl, transactionID, fromGroup, binaryBucket));
259
260 im.Add("agent_params", AgentParams(fromAgent, checkEstate, godLevel, limitedToEstate));
261
262 return im;
263 }
264
265
266 public static OSD ChatterboxInvitation(UUID sessionID, string sessionName,
267 UUID fromAgent, string message, UUID toAgent, string fromName, byte dialog,
268 uint timeStamp, bool offline, int parentEstateID, Vector3 position,
269 uint ttl, UUID transactionID, bool fromGroup, byte[] binaryBucket)
270 {
271 OSDMap body = new OSDMap(5);
272 body.Add("session_id", new OSDUUID(sessionID));
273 body.Add("from_name", new OSDString(fromName));
274 body.Add("session_name", new OSDString(sessionName));
275 body.Add("from_id", new OSDUUID(fromAgent));
276
277 body.Add("instantmessage", InstantMessage(fromAgent, message, toAgent,
278 fromName, dialog, timeStamp, offline, parentEstateID, position,
279 ttl, transactionID, fromGroup, binaryBucket, true, 0, true));
280
281 OSDMap chatterboxInvitation = new OSDMap(2);
282 chatterboxInvitation.Add("message", new OSDString("ChatterBoxInvitation"));
283 chatterboxInvitation.Add("body", body);
284 return chatterboxInvitation;
285 }
286
287 public static OSD ChatterBoxSessionAgentListUpdates(UUID sessionID,
288 UUID agentID, bool canVoiceChat, bool isModerator, bool textMute)
289 {
290 OSDMap body = new OSDMap();
291 OSDMap agentUpdates = new OSDMap();
292 OSDMap infoDetail = new OSDMap();
293 OSDMap mutes = new OSDMap();
294
295 mutes.Add("text", OSD.FromBoolean(textMute));
296 infoDetail.Add("can_voice_chat", OSD.FromBoolean(canVoiceChat));
297 infoDetail.Add("is_moderator", OSD.FromBoolean(isModerator));
298 infoDetail.Add("mutes", mutes);
299 OSDMap info = new OSDMap();
300 info.Add("info", infoDetail);
301 agentUpdates.Add(agentID.ToString(), info);
302 body.Add("agent_updates", agentUpdates);
303 body.Add("session_id", OSD.FromUUID(sessionID));
304 body.Add("updates", new OSD());
305
306 OSDMap chatterBoxSessionAgentListUpdates = new OSDMap();
307 chatterBoxSessionAgentListUpdates.Add("message", OSD.FromString("ChatterBoxSessionAgentListUpdates"));
308 chatterBoxSessionAgentListUpdates.Add("body", body);
309
310 return chatterBoxSessionAgentListUpdates;
311 }
312
313 public static OSD GroupMembership(AgentGroupDataUpdatePacket groupUpdatePacket)
314 {
315 OSDMap groupUpdate = new OSDMap();
316 groupUpdate.Add("message", OSD.FromString("AgentGroupDataUpdate"));
317
318 OSDMap body = new OSDMap();
319 OSDArray agentData = new OSDArray();
320 OSDMap agentDataMap = new OSDMap();
321 agentDataMap.Add("AgentID", OSD.FromUUID(groupUpdatePacket.AgentData.AgentID));
322 agentData.Add(agentDataMap);
323 body.Add("AgentData", agentData);
324
325 OSDArray groupData = new OSDArray();
326
327 foreach (AgentGroupDataUpdatePacket.GroupDataBlock groupDataBlock in groupUpdatePacket.GroupData)
328 {
329 OSDMap groupDataMap = new OSDMap();
330 groupDataMap.Add("ListInProfile", OSD.FromBoolean(false));
331 groupDataMap.Add("GroupID", OSD.FromUUID(groupDataBlock.GroupID));
332 groupDataMap.Add("GroupInsigniaID", OSD.FromUUID(groupDataBlock.GroupInsigniaID));
333 groupDataMap.Add("Contribution", OSD.FromInteger(groupDataBlock.Contribution));
334 groupDataMap.Add("GroupPowers", OSD.FromBinary(ulongToByteArray(groupDataBlock.GroupPowers)));
335 groupDataMap.Add("GroupName", OSD.FromString(Utils.BytesToString(groupDataBlock.GroupName)));
336 groupDataMap.Add("AcceptNotices", OSD.FromBoolean(groupDataBlock.AcceptNotices));
337
338 groupData.Add(groupDataMap);
339
340 }
341 body.Add("GroupData", groupData);
342 groupUpdate.Add("body", body);
343
344 return groupUpdate;
345 }
346
347 public static OSD PlacesQuery(PlacesReplyPacket PlacesReply)
348 {
349 OSDMap placesReply = new OSDMap();
350 placesReply.Add("message", OSD.FromString("PlacesReplyMessage"));
351
352 OSDMap body = new OSDMap();
353 OSDArray agentData = new OSDArray();
354 OSDMap agentDataMap = new OSDMap();
355 agentDataMap.Add("AgentID", OSD.FromUUID(PlacesReply.AgentData.AgentID));
356 agentDataMap.Add("QueryID", OSD.FromUUID(PlacesReply.AgentData.QueryID));
357 agentDataMap.Add("TransactionID", OSD.FromUUID(PlacesReply.TransactionData.TransactionID));
358 agentData.Add(agentDataMap);
359 body.Add("AgentData", agentData);
360
361 OSDArray QueryData = new OSDArray();
362
363 foreach (PlacesReplyPacket.QueryDataBlock groupDataBlock in PlacesReply.QueryData)
364 {
365 OSDMap QueryDataMap = new OSDMap();
366 QueryDataMap.Add("ActualArea", OSD.FromInteger(groupDataBlock.ActualArea));
367 QueryDataMap.Add("BillableArea", OSD.FromInteger(groupDataBlock.BillableArea));
368 QueryDataMap.Add("Description", OSD.FromBinary(groupDataBlock.Desc));
369 QueryDataMap.Add("Dwell", OSD.FromInteger((int)groupDataBlock.Dwell));
370 QueryDataMap.Add("Flags", OSD.FromString(Convert.ToString(groupDataBlock.Flags)));
371 QueryDataMap.Add("GlobalX", OSD.FromInteger((int)groupDataBlock.GlobalX));
372 QueryDataMap.Add("GlobalY", OSD.FromInteger((int)groupDataBlock.GlobalY));
373 QueryDataMap.Add("GlobalZ", OSD.FromInteger((int)groupDataBlock.GlobalZ));
374 QueryDataMap.Add("Name", OSD.FromBinary(groupDataBlock.Name));
375 QueryDataMap.Add("OwnerID", OSD.FromUUID(groupDataBlock.OwnerID));
376 QueryDataMap.Add("SimName", OSD.FromBinary(groupDataBlock.SimName));
377 QueryDataMap.Add("SnapShotID", OSD.FromUUID(groupDataBlock.SnapshotID));
378 QueryDataMap.Add("ProductSku", OSD.FromInteger(0));
379 QueryDataMap.Add("Price", OSD.FromInteger(groupDataBlock.Price));
380
381 QueryData.Add(QueryDataMap);
382 }
383 body.Add("QueryData", QueryData);
384 placesReply.Add("QueryData[]", body);
385
386 return placesReply;
387 }
388
389 public static OSD ParcelProperties(ParcelPropertiesMessage parcelPropertiesMessage)
390 {
391 OSDMap message = new OSDMap();
392 message.Add("message", OSD.FromString("ParcelProperties"));
393 OSD message_body = parcelPropertiesMessage.Serialize();
394 message.Add("body", message_body);
395 return message;
396 }
397
398 }
399}