aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Services/Connectors/SimianGrid
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Services/Connectors/SimianGrid')
-rw-r--r--OpenSim/Services/Connectors/SimianGrid/SimianGridMaptileModule.cs261
-rw-r--r--OpenSim/Services/Connectors/SimianGrid/SimianGridServiceConnector.cs90
-rw-r--r--OpenSim/Services/Connectors/SimianGrid/SimianUserAccountServiceConnector.cs5
3 files changed, 94 insertions, 262 deletions
diff --git a/OpenSim/Services/Connectors/SimianGrid/SimianGridMaptileModule.cs b/OpenSim/Services/Connectors/SimianGrid/SimianGridMaptileModule.cs
deleted file mode 100644
index dd8fe2b..0000000
--- a/OpenSim/Services/Connectors/SimianGrid/SimianGridMaptileModule.cs
+++ /dev/null
@@ -1,261 +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.Generic;
30using System.Reflection;
31using System.Net;
32using System.IO;
33using System.Timers;
34using System.Drawing;
35using System.Drawing.Imaging;
36
37using log4net;
38using Mono.Addins;
39using Nini.Config;
40using OpenSim.Framework;
41using OpenSim.Region.Framework.Interfaces;
42using OpenSim.Region.Framework.Scenes;
43using OpenMetaverse;
44using OpenMetaverse.StructuredData;
45
46namespace OpenSim.Region.OptionalModules.Simian
47{
48 /// <summary>
49 /// </summary>
50 /// <remarks>
51 /// </remarks>
52
53 [Extension(Path = "/OpenSim/RegionModules", NodeName = "RegionModule", Id = "SimianGridMaptile")]
54 public class SimianGridMaptile : ISharedRegionModule
55 {
56 private static readonly ILog m_log =
57 LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
58
59 private bool m_enabled = false;
60 private string m_serverUrl = String.Empty;
61 private Dictionary<UUID, Scene> m_scenes = new Dictionary<UUID, Scene>();
62
63 private int m_refreshtime = 0;
64 private int m_lastrefresh = 0;
65 private System.Timers.Timer m_refreshTimer = new System.Timers.Timer();
66
67 #region ISharedRegionModule
68
69 public Type ReplaceableInterface { get { return null; } }
70 public string Name { get { return "SimianGridMaptile"; } }
71 public void RegionLoaded(Scene scene) { }
72 public void Close() { }
73
74 ///<summary>
75 ///
76 ///</summary>
77 public void Initialise(IConfigSource source)
78 {
79 IConfig config = source.Configs["SimianGridMaptiles"];
80 if (config == null)
81 return;
82
83 if (! config.GetBoolean("Enabled", false))
84 return;
85
86 m_serverUrl = config.GetString("MaptileURL");
87 if (String.IsNullOrEmpty(m_serverUrl))
88 return;
89
90 m_refreshtime = Convert.ToInt32(config.GetString("RefreshTime"));
91 if (m_refreshtime <= 0)
92 return;
93
94 m_log.InfoFormat("[SIMIAN MAPTILE] enabled with refresh timeout {0} and URL {1}",
95 m_refreshtime,m_serverUrl);
96
97 m_enabled = true;
98 }
99
100 ///<summary>
101 ///
102 ///</summary>
103 public void PostInitialise()
104 {
105 if (m_enabled)
106 {
107 m_refreshTimer.Enabled = true;
108 m_refreshTimer.AutoReset = true;
109 m_refreshTimer.Interval = 5 * 60 * 1000; // every 5 minutes
110 m_refreshTimer.Elapsed += new ElapsedEventHandler(HandleMaptileRefresh);
111 }
112 }
113
114
115 ///<summary>
116 ///
117 ///</summary>
118 public void AddRegion(Scene scene)
119 {
120 if (! m_enabled)
121 return;
122
123 // Every shared region module has to maintain an indepedent list of
124 // currently running regions
125 lock (m_scenes)
126 m_scenes[scene.RegionInfo.RegionID] = scene;
127 }
128
129 ///<summary>
130 ///
131 ///</summary>
132 public void RemoveRegion(Scene scene)
133 {
134 if (! m_enabled)
135 return;
136
137 lock (m_scenes)
138 m_scenes.Remove(scene.RegionInfo.RegionID);
139 }
140
141 #endregion ISharedRegionModule
142
143 ///<summary>
144 ///
145 ///</summary>
146 private void HandleMaptileRefresh(object sender, EventArgs ea)
147 {
148 // this approach is a bit convoluted becase we want to wait for the
149 // first upload to happen on startup but after all the objects are
150 // loaded and initialized
151 if (m_lastrefresh > 0 && Util.EnvironmentTickCountSubtract(m_lastrefresh) < m_refreshtime)
152 return;
153
154 m_log.DebugFormat("[SIMIAN MAPTILE] map refresh fired");
155 lock (m_scenes)
156 {
157 foreach (IScene scene in m_scenes.Values)
158 {
159 try
160 {
161 UploadMapTile(scene);
162 }
163 catch (Exception ex)
164 {
165 m_log.WarnFormat("[SIMIAN MAPTILE] something bad happened {0}",ex.Message);
166 }
167 }
168 }
169
170 m_lastrefresh = Util.EnvironmentTickCount();
171 }
172
173 ///<summary>
174 ///
175 ///</summary>
176 private void UploadMapTile(IScene scene)
177 {
178 m_log.DebugFormat("[SIMIAN MAPTILE]: upload maptile for {0}",scene.RegionInfo.RegionName);
179
180 // Create a PNG map tile and upload it to the AddMapTile API
181 byte[] pngData = Utils.EmptyBytes;
182 IMapImageGenerator tileGenerator = scene.RequestModuleInterface<IMapImageGenerator>();
183 if (tileGenerator == null)
184 {
185 m_log.Warn("[SIMIAN MAPTILE]: Cannot upload PNG map tile without an ImageGenerator");
186 return;
187 }
188
189 using (Image mapTile = tileGenerator.CreateMapTile())
190 {
191 using (MemoryStream stream = new MemoryStream())
192 {
193 mapTile.Save(stream, ImageFormat.Png);
194 pngData = stream.ToArray();
195 }
196 }
197
198 List<MultipartForm.Element> postParameters = new List<MultipartForm.Element>()
199 {
200 new MultipartForm.Parameter("X", scene.RegionInfo.RegionLocX.ToString()),
201 new MultipartForm.Parameter("Y", scene.RegionInfo.RegionLocY.ToString()),
202 new MultipartForm.File("Tile", "tile.png", "image/png", pngData)
203 };
204
205 string errorMessage = null;
206 int tickstart = Util.EnvironmentTickCount();
207
208 // Make the remote storage request
209 try
210 {
211 HttpWebRequest request = (HttpWebRequest)HttpWebRequest.Create(m_serverUrl);
212 request.Timeout = 20000;
213 request.ReadWriteTimeout = 5000;
214
215 using (HttpWebResponse response = MultipartForm.Post(request, postParameters))
216 {
217 using (Stream responseStream = response.GetResponseStream())
218 {
219 string responseStr = responseStream.GetStreamString();
220 OSD responseOSD = OSDParser.Deserialize(responseStr);
221 if (responseOSD.Type == OSDType.Map)
222 {
223 OSDMap responseMap = (OSDMap)responseOSD;
224 if (responseMap["Success"].AsBoolean())
225 return;
226
227 errorMessage = "Upload failed: " + responseMap["Message"].AsString();
228 }
229 else
230 {
231 errorMessage = "Response format was invalid:\n" + responseStr;
232 }
233 }
234 }
235 }
236 catch (WebException we)
237 {
238 errorMessage = we.Message;
239 if (we.Status == WebExceptionStatus.ProtocolError)
240 {
241 HttpWebResponse webResponse = (HttpWebResponse)we.Response;
242 errorMessage = String.Format("[{0}] {1}",
243 webResponse.StatusCode,webResponse.StatusDescription);
244 }
245 }
246 catch (Exception ex)
247 {
248 errorMessage = ex.Message;
249 }
250 finally
251 {
252 // This just dumps a warning for any operation that takes more than 100 ms
253 int tickdiff = Util.EnvironmentTickCountSubtract(tickstart);
254 m_log.DebugFormat("[SIMIAN MAPTILE]: map tile uploaded in {0}ms",tickdiff);
255 }
256
257 m_log.WarnFormat("[SIMIAN MAPTILE]: Failed to store {0} byte tile for {1}: {2}",
258 pngData.Length, scene.RegionInfo.RegionName, errorMessage);
259 }
260 }
261} \ No newline at end of file
diff --git a/OpenSim/Services/Connectors/SimianGrid/SimianGridServiceConnector.cs b/OpenSim/Services/Connectors/SimianGrid/SimianGridServiceConnector.cs
index 918544f..feea196 100644
--- a/OpenSim/Services/Connectors/SimianGrid/SimianGridServiceConnector.cs
+++ b/OpenSim/Services/Connectors/SimianGrid/SimianGridServiceConnector.cs
@@ -28,6 +28,8 @@
28using System; 28using System;
29using System.Collections.Generic; 29using System.Collections.Generic;
30using System.Collections.Specialized; 30using System.Collections.Specialized;
31using System.Drawing;
32using System.Drawing.Imaging;
31using System.IO; 33using System.IO;
32using System.Net; 34using System.Net;
33using System.Reflection; 35using System.Reflection;
@@ -100,6 +102,15 @@ namespace OpenSim.Services.Connectors.SimianGrid
100 102
101 public string RegisterRegion(UUID scopeID, GridRegion regionInfo) 103 public string RegisterRegion(UUID scopeID, GridRegion regionInfo)
102 { 104 {
105 IPEndPoint ext = regionInfo.ExternalEndPoint;
106 if (ext == null) return "Region registration for " + regionInfo.RegionName + " failed: Could not resolve EndPoint";
107 // Generate and upload our map tile in PNG format to the SimianGrid AddMapTile service
108// Scene scene;
109// if (m_scenes.TryGetValue(regionInfo.RegionID, out scene))
110// UploadMapTile(scene);
111// else
112// m_log.Warn("Registering region " + regionInfo.RegionName + " (" + regionInfo.RegionID + ") that we are not tracking");
113
103 Vector3d minPosition = new Vector3d(regionInfo.RegionLocX, regionInfo.RegionLocY, 0.0); 114 Vector3d minPosition = new Vector3d(regionInfo.RegionLocX, regionInfo.RegionLocY, 0.0);
104 Vector3d maxPosition = minPosition + new Vector3d(Constants.RegionSize, Constants.RegionSize, 4096.0); 115 Vector3d maxPosition = minPosition + new Vector3d(Constants.RegionSize, Constants.RegionSize, 4096.0);
105 116
@@ -108,7 +119,7 @@ namespace OpenSim.Services.Connectors.SimianGrid
108 { "ServerURI", OSD.FromString(regionInfo.ServerURI) }, 119 { "ServerURI", OSD.FromString(regionInfo.ServerURI) },
109 { "InternalAddress", OSD.FromString(regionInfo.InternalEndPoint.Address.ToString()) }, 120 { "InternalAddress", OSD.FromString(regionInfo.InternalEndPoint.Address.ToString()) },
110 { "InternalPort", OSD.FromInteger(regionInfo.InternalEndPoint.Port) }, 121 { "InternalPort", OSD.FromInteger(regionInfo.InternalEndPoint.Port) },
111 { "ExternalAddress", OSD.FromString(regionInfo.ExternalEndPoint.Address.ToString()) }, 122 { "ExternalAddress", OSD.FromString(ext.Address.ToString()) },
112 { "ExternalPort", OSD.FromInteger(regionInfo.ExternalEndPoint.Port) }, 123 { "ExternalPort", OSD.FromInteger(regionInfo.ExternalEndPoint.Port) },
113 { "MapTexture", OSD.FromUUID(regionInfo.TerrainImage) }, 124 { "MapTexture", OSD.FromUUID(regionInfo.TerrainImage) },
114 { "Access", OSD.FromInteger(regionInfo.Access) }, 125 { "Access", OSD.FromInteger(regionInfo.Access) },
@@ -371,6 +382,83 @@ namespace OpenSim.Services.Connectors.SimianGrid
371 382
372 #endregion IGridService 383 #endregion IGridService
373 384
385 private void UploadMapTile(IScene scene)
386 {
387 string errorMessage = null;
388
389 // Create a PNG map tile and upload it to the AddMapTile API
390 byte[] pngData = Utils.EmptyBytes;
391 IMapImageGenerator tileGenerator = scene.RequestModuleInterface<IMapImageGenerator>();
392 if (tileGenerator == null)
393 {
394 m_log.Warn("[SIMIAN GRID CONNECTOR]: Cannot upload PNG map tile without an IMapImageGenerator");
395 return;
396 }
397
398 using (Image mapTile = tileGenerator.CreateMapTile())
399 {
400 using (MemoryStream stream = new MemoryStream())
401 {
402 mapTile.Save(stream, ImageFormat.Png);
403 pngData = stream.ToArray();
404 }
405 }
406
407 List<MultipartForm.Element> postParameters = new List<MultipartForm.Element>()
408 {
409 new MultipartForm.Parameter("X", scene.RegionInfo.RegionLocX.ToString()),
410 new MultipartForm.Parameter("Y", scene.RegionInfo.RegionLocY.ToString()),
411 new MultipartForm.File("Tile", "tile.png", "image/png", pngData)
412 };
413
414 // Make the remote storage request
415 try
416 {
417 HttpWebRequest request = (HttpWebRequest)HttpWebRequest.Create(m_ServerURI);
418
419 HttpWebResponse response = MultipartForm.Post(request, postParameters);
420 using (Stream responseStream = response.GetResponseStream())
421 {
422 string responseStr = null;
423
424 try
425 {
426 responseStr = responseStream.GetStreamString();
427 OSD responseOSD = OSDParser.Deserialize(responseStr);
428 if (responseOSD.Type == OSDType.Map)
429 {
430 OSDMap responseMap = (OSDMap)responseOSD;
431 if (responseMap["Success"].AsBoolean())
432 m_log.Info("[SIMIAN GRID CONNECTOR]: Uploaded " + pngData.Length + " byte PNG map tile to AddMapTile");
433 else
434 errorMessage = "Upload failed: " + responseMap["Message"].AsString();
435 }
436 else
437 {
438 errorMessage = "Response format was invalid:\n" + responseStr;
439 }
440 }
441 catch (Exception ex)
442 {
443 if (!String.IsNullOrEmpty(responseStr))
444 errorMessage = "Failed to parse the response:\n" + responseStr;
445 else
446 errorMessage = "Failed to retrieve the response: " + ex.Message;
447 }
448 }
449 }
450 catch (WebException ex)
451 {
452 errorMessage = ex.Message;
453 }
454
455 if (!String.IsNullOrEmpty(errorMessage))
456 {
457 m_log.WarnFormat("[SIMIAN GRID CONNECTOR]: Failed to store {0} byte PNG map tile for {1}: {2}",
458 pngData.Length, scene.RegionInfo.RegionName, errorMessage.Replace('\n', ' '));
459 }
460 }
461
374 private GridRegion GetNearestRegion(Vector3d position, bool onlyEnabled) 462 private GridRegion GetNearestRegion(Vector3d position, bool onlyEnabled)
375 { 463 {
376 NameValueCollection requestArgs = new NameValueCollection 464 NameValueCollection requestArgs = new NameValueCollection
diff --git a/OpenSim/Services/Connectors/SimianGrid/SimianUserAccountServiceConnector.cs b/OpenSim/Services/Connectors/SimianGrid/SimianUserAccountServiceConnector.cs
index 91e2976..801b424 100644
--- a/OpenSim/Services/Connectors/SimianGrid/SimianUserAccountServiceConnector.cs
+++ b/OpenSim/Services/Connectors/SimianGrid/SimianUserAccountServiceConnector.cs
@@ -191,6 +191,11 @@ namespace OpenSim.Services.Connectors.SimianGrid
191 return accounts; 191 return accounts;
192 } 192 }
193 193
194 public List<UserAccount> GetUserAccountsWhere(UUID scopeID, string query)
195 {
196 return null;
197 }
198
194 public bool StoreUserAccount(UserAccount data) 199 public bool StoreUserAccount(UserAccount data)
195 { 200 {
196// m_log.InfoFormat("[SIMIAN ACCOUNT CONNECTOR]: Storing user account for " + data.Name); 201// m_log.InfoFormat("[SIMIAN ACCOUNT CONNECTOR]: Storing user account for " + data.Name);