aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Grid/GridServer/GridManager.cs
diff options
context:
space:
mode:
authorMW2009-02-21 13:44:03 +0000
committerMW2009-02-21 13:44:03 +0000
commit25661b611d241534e5e8d7ce1731de8506481a7d (patch)
treed61ae89bcb909225c6aef295bf6bddb21668b718 /OpenSim/Grid/GridServer/GridManager.cs
parentAllow entry of '?' in http URIs. If the field being typed begins with (diff)
downloadopensim-SC_OLD-25661b611d241534e5e8d7ce1731de8506481a7d.zip
opensim-SC_OLD-25661b611d241534e5e8d7ce1731de8506481a7d.tar.gz
opensim-SC_OLD-25661b611d241534e5e8d7ce1731de8506481a7d.tar.bz2
opensim-SC_OLD-25661b611d241534e5e8d7ce1731de8506481a7d.tar.xz
Refactored the GridServer into a GridDBService and a set of "modules".
Currently they aren't plugin modules as the support for dynamically loading them isn't complete.
Diffstat (limited to 'OpenSim/Grid/GridServer/GridManager.cs')
-rw-r--r--OpenSim/Grid/GridServer/GridManager.cs1282
1 files changed, 0 insertions, 1282 deletions
diff --git a/OpenSim/Grid/GridServer/GridManager.cs b/OpenSim/Grid/GridServer/GridManager.cs
deleted file mode 100644
index 5dc186c..0000000
--- a/OpenSim/Grid/GridServer/GridManager.cs
+++ /dev/null
@@ -1,1282 +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 OpenSim 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.IO;
32using System.Reflection;
33using System.Xml;
34using log4net;
35using Nwc.XmlRpc;
36using OpenMetaverse;
37using OpenSim.Data;
38using OpenSim.Framework;
39using OpenSim.Framework.Communications;
40using OpenSim.Framework.Servers;
41
42namespace OpenSim.Grid.GridServer
43{
44 public class GridManager
45 {
46 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
47
48 private List<IGridDataPlugin> _plugins = new List<IGridDataPlugin>();
49 private List<ILogDataPlugin> _logplugins = new List<ILogDataPlugin>();
50
51 // This is here so that the grid server can hand out MessageServer settings to regions on registration
52 private List<MessageServerInfo> _MessageServers = new List<MessageServerInfo>();
53
54 public GridConfig Config;
55
56 /// <value>
57 /// Used to notify old regions as to which OpenSim version to upgrade to
58 /// </value>
59 private string m_opensimVersion;
60
61 /// <summary>
62 /// Constructor
63 /// </summary>
64 /// <param name="opensimVersion">
65 /// Used to notify old regions as to which OpenSim version to upgrade to
66 /// </param>
67 public GridManager(string opensimVersion)
68 {
69 m_opensimVersion = opensimVersion;
70 }
71
72 /// <summary>
73 /// Adds a list of grid and log data plugins, as described by
74 /// `provider' and `connect', to `_plugins' and `_logplugins',
75 /// respectively.
76 /// </summary>
77 /// <param name="provider">
78 /// The filename of the inventory server plugin DLL.
79 /// </param>
80 /// <param name="connect">
81 /// The connection string for the storage backend.
82 /// </param>
83 public void AddPlugin(string provider, string connect)
84 {
85 _plugins = DataPluginFactory.LoadDataPlugins<IGridDataPlugin>(provider, connect);
86 _logplugins = DataPluginFactory.LoadDataPlugins<ILogDataPlugin>(provider, connect);
87 }
88
89 /// <summary>
90 /// Logs a piece of information to the database
91 /// </summary>
92 /// <param name="target">What you were operating on (in grid server, this will likely be the region UUIDs)</param>
93 /// <param name="method">Which method is being called?</param>
94 /// <param name="args">What arguments are being passed?</param>
95 /// <param name="priority">How high priority is this? 1 = Max, 6 = Verbose</param>
96 /// <param name="message">The message to log</param>
97 private void logToDB(string target, string method, string args, int priority, string message)
98 {
99 foreach (ILogDataPlugin plugin in _logplugins)
100 {
101 try
102 {
103 plugin.saveLog("Gridserver", target, method, args, priority, message);
104 }
105 catch (Exception)
106 {
107 m_log.Warn("[storage]: Unable to write log via " + plugin.Name);
108 }
109 }
110 }
111
112 /// <summary>
113 /// Returns a region by argument
114 /// </summary>
115 /// <param name="uuid">A UUID key of the region to return</param>
116 /// <returns>A SimProfileData for the region</returns>
117 public RegionProfileData GetRegion(UUID uuid)
118 {
119 foreach (IGridDataPlugin plugin in _plugins)
120 {
121 try
122 {
123 return plugin.GetProfileByUUID(uuid);
124 }
125 catch (Exception e)
126 {
127 m_log.Warn("[storage]: GetRegion - " + e.Message);
128 }
129 }
130 return null;
131 }
132
133 /// <summary>
134 /// Returns a region by argument
135 /// </summary>
136 /// <param name="uuid">A regionHandle of the region to return</param>
137 /// <returns>A SimProfileData for the region</returns>
138 public RegionProfileData GetRegion(ulong handle)
139 {
140 foreach (IGridDataPlugin plugin in _plugins)
141 {
142 try
143 {
144 return plugin.GetProfileByHandle(handle);
145 }
146 catch (Exception ex)
147 {
148 m_log.Debug("[storage]: " + ex.Message);
149 m_log.Warn("[storage]: Unable to find region " + handle.ToString() + " via " + plugin.Name);
150 }
151 }
152 return null;
153 }
154
155 /// <summary>
156 /// Returns a region by argument
157 /// </summary>
158 /// <param name="regionName">A partial regionName of the region to return</param>
159 /// <returns>A SimProfileData for the region</returns>
160 public RegionProfileData GetRegion(string regionName)
161 {
162 foreach (IGridDataPlugin plugin in _plugins)
163 {
164 try
165 {
166 return plugin.GetProfileByString(regionName);
167 }
168 catch
169 {
170 m_log.Warn("[storage]: Unable to find region " + regionName + " via " + plugin.Name);
171 }
172 }
173 return null;
174 }
175
176 public List<RegionProfileData> GetRegions(uint xmin, uint ymin, uint xmax, uint ymax)
177 {
178 List<RegionProfileData> regions = new List<RegionProfileData>();
179
180 foreach (IGridDataPlugin plugin in _plugins)
181 {
182 try
183 {
184 regions.AddRange(plugin.GetProfilesInRange(xmin, ymin, xmax, ymax));
185 }
186 catch
187 {
188 m_log.Warn("[storage]: Unable to query regionblock via " + plugin.Name);
189 }
190 }
191
192 return regions;
193 }
194
195 public List<RegionProfileData> GetRegions(string name, int maxNum)
196 {
197 List<RegionProfileData> regions = new List<RegionProfileData>();
198 foreach (IGridDataPlugin plugin in _plugins)
199 {
200 try
201 {
202 int num = maxNum - regions.Count;
203 List <RegionProfileData> profiles = plugin.GetRegionsByName(name, (uint)num);
204 if (profiles != null) regions.AddRange(profiles);
205 }
206 catch
207 {
208 m_log.Warn("[storage]: Unable to query regionblock via " + plugin.Name);
209 }
210 }
211
212 return regions;
213 }
214
215 /// <summary>
216 /// Returns a XML String containing a list of the neighbouring regions
217 /// </summary>
218 /// <param name="reqhandle">The regionhandle for the center sim</param>
219 /// <returns>An XML string containing neighbour entities</returns>
220 public string GetXMLNeighbours(ulong reqhandle)
221 {
222 string response = String.Empty;
223 RegionProfileData central_region = GetRegion(reqhandle);
224 RegionProfileData neighbour;
225 for (int x = -1; x < 2; x++)
226 {
227 for (int y = -1; y < 2; y++)
228 {
229 if (
230 GetRegion(
231 Util.UIntsToLong((uint)((central_region.regionLocX + x) * Constants.RegionSize),
232 (uint)(central_region.regionLocY + y) * Constants.RegionSize)) != null)
233 {
234 neighbour =
235 GetRegion(
236 Util.UIntsToLong((uint)((central_region.regionLocX + x) * Constants.RegionSize),
237 (uint)(central_region.regionLocY + y) * Constants.RegionSize));
238
239 response += "<neighbour>";
240 response += "<sim_ip>" + neighbour.serverIP + "</sim_ip>";
241 response += "<sim_port>" + neighbour.serverPort.ToString() + "</sim_port>";
242 response += "<locx>" + neighbour.regionLocX.ToString() + "</locx>";
243 response += "<locy>" + neighbour.regionLocY.ToString() + "</locy>";
244 response += "<regionhandle>" + neighbour.regionHandle.ToString() + "</regionhandle>";
245 response += "</neighbour>";
246 }
247 }
248 }
249 return response;
250 }
251
252 /// <summary>
253 /// Checks that it's valid to replace the existing region data with new data
254 ///
255 /// Currently, this means ensure that the keys passed in by the new region
256 /// match those in the original region. (XXX Is this correct? Shouldn't we simply check
257 /// against the keys in the current configuration?)
258 /// </summary>
259 /// <param name="sim"></param>
260 /// <returns></returns>
261 protected virtual void ValidateOverwriteKeys(RegionProfileData sim, RegionProfileData existingSim)
262 {
263 if (!(existingSim.regionRecvKey == sim.regionRecvKey && existingSim.regionSendKey == sim.regionSendKey))
264 {
265 throw new LoginException(
266 String.Format(
267 "Authentication failed when trying to login existing region {0} at location {1} {2} currently occupied by {3}"
268 + " with the region's send key {4} (expected {5}) and the region's receive key {6} (expected {7})",
269 sim.regionName, sim.regionLocX, sim.regionLocY, existingSim.regionName,
270 sim.regionSendKey, existingSim.regionSendKey, sim.regionRecvKey, existingSim.regionRecvKey),
271 "The keys required to login your region did not match the grid server keys. Please check your grid send and receive keys.");
272 }
273 }
274
275 /// <summary>
276 /// Checks that the new region data is valid.
277 ///
278 /// Currently, this means checking that the keys passed in by the new region
279 /// match those in the grid server's configuration.
280 /// </summary>
281 ///
282 /// <param name="sim"></param>
283 /// <exception cref="LoginException">Thrown if region login failed</exception>
284 protected virtual void ValidateNewRegionKeys(RegionProfileData sim)
285 {
286 if (!(sim.regionRecvKey == Config.SimSendKey && sim.regionSendKey == Config.SimRecvKey))
287 {
288 throw new LoginException(
289 String.Format(
290 "Authentication failed when trying to login new region {0} at location {1} {2}"
291 + " with the region's send key {3} (expected {4}) and the region's receive key {5} (expected {6})",
292 sim.regionName, sim.regionLocX, sim.regionLocY,
293 sim.regionSendKey, Config.SimRecvKey, sim.regionRecvKey, Config.SimSendKey),
294 "The keys required to login your region did not match your existing region keys. Please check your grid send and receive keys.");
295 }
296 }
297
298 /// <summary>
299 /// Check that a region's http uri is externally contactable.
300 /// </summary>
301 /// <param name="sim"></param>
302 /// <exception cref="LoginException">Thrown if the region is not contactable</exception>
303 protected virtual void ValidateRegionContactable(RegionProfileData sim)
304 {
305 string regionStatusUrl = String.Format("{0}{1}", sim.httpServerURI, "simstatus/");
306 string regionStatusResponse;
307
308 RestClient rc = new RestClient(regionStatusUrl);
309 rc.RequestMethod = "GET";
310
311 m_log.DebugFormat("[LOGIN]: Contacting {0} for status of region {1}", regionStatusUrl, sim.regionName);
312
313 try
314 {
315 Stream rs = rc.Request();
316 StreamReader sr = new StreamReader(rs);
317 regionStatusResponse = sr.ReadToEnd();
318 sr.Close();
319 }
320 catch (Exception e)
321 {
322 throw new LoginException(
323 String.Format("Region status request to {0} failed", regionStatusUrl),
324 String.Format(
325 "The grid service could not contact the http url {0} at your region. Please make sure this url is reachable by the grid service",
326 regionStatusUrl),
327 e);
328 }
329
330 if (!regionStatusResponse.Equals("OK"))
331 {
332 throw new LoginException(
333 String.Format(
334 "Region {0} at {1} returned status response {2} rather than {3}",
335 sim.regionName, regionStatusUrl, regionStatusResponse, "OK"),
336 String.Format(
337 "When the grid service asked for the status of your region, it received the response {0} rather than {1}. Please check your status",
338 regionStatusResponse, "OK"));
339 }
340 }
341
342 /// <summary>
343 /// Construct an XMLRPC error response
344 /// </summary>
345 /// <param name="error"></param>
346 /// <returns></returns>
347 public static XmlRpcResponse ErrorResponse(string error)
348 {
349 XmlRpcResponse errorResponse = new XmlRpcResponse();
350 Hashtable errorResponseData = new Hashtable();
351 errorResponse.Value = errorResponseData;
352 errorResponseData["error"] = error;
353 return errorResponse;
354 }
355
356 /// <summary>
357 /// Performed when a region connects to the grid server initially.
358 /// </summary>
359 /// <param name="request">The XML RPC Request</param>
360 /// <returns>Startup parameters</returns>
361 public XmlRpcResponse XmlRpcSimulatorLoginMethod(XmlRpcRequest request)
362 {
363 RegionProfileData sim;
364 RegionProfileData existingSim;
365
366 Hashtable requestData = (Hashtable)request.Params[0];
367 UUID uuid;
368
369 if (!requestData.ContainsKey("UUID") || !UUID.TryParse((string)requestData["UUID"], out uuid))
370 {
371 m_log.Debug("[LOGIN PRELUDE]: Region connected without a UUID, sending back error response.");
372 return ErrorResponse("No UUID passed to grid server - unable to connect you");
373 }
374
375 try
376 {
377 sim = RegionFromRequest(requestData);
378 }
379 catch (FormatException e)
380 {
381 m_log.Debug("[LOGIN PRELUDE]: Invalid login parameters, sending back error response.");
382 return ErrorResponse("Wrong format in login parameters. Please verify parameters." + e.ToString());
383 }
384
385 m_log.InfoFormat("[LOGIN BEGIN]: Received login request from simulator: {0}", sim.regionName);
386
387 if (!Config.AllowRegionRegistration)
388 {
389 m_log.DebugFormat(
390 "[LOGIN END]: Disabled region registration blocked login request from simulator: {0}",
391 sim.regionName);
392
393 return ErrorResponse("This grid is currently not accepting region registrations.");
394 }
395
396 int majorInterfaceVersion = 0;
397 if (requestData.ContainsKey("major_interface_version"))
398 int.TryParse((string)requestData["major_interface_version"], out majorInterfaceVersion);
399
400 if (majorInterfaceVersion != VersionInfo.MajorInterfaceVersion)
401 {
402 return ErrorResponse(
403 String.Format(
404 "Your region service implements OGS1 interface version {0}"
405 + " but this grid requires that the region implement OGS1 interface version {1} to connect."
406 + " Try changing to OpenSimulator {2}",
407 majorInterfaceVersion, VersionInfo.MajorInterfaceVersion, m_opensimVersion));
408 }
409
410 existingSim = GetRegion(sim.regionHandle);
411
412 if (existingSim == null || existingSim.UUID == sim.UUID || sim.UUID != sim.originUUID)
413 {
414 try
415 {
416 if (existingSim == null)
417 {
418 ValidateNewRegionKeys(sim);
419 }
420 else
421 {
422 ValidateOverwriteKeys(sim, existingSim);
423 }
424
425 ValidateRegionContactable(sim);
426 }
427 catch (LoginException e)
428 {
429 string logMsg = e.Message;
430 if (e.InnerException != null)
431 logMsg += ", " + e.InnerException.Message;
432
433 m_log.WarnFormat("[LOGIN END]: {0}", logMsg);
434
435 return e.XmlRpcErrorResponse;
436 }
437
438 foreach (IGridDataPlugin plugin in _plugins)
439 {
440 try
441 {
442 DataResponse insertResponse;
443
444 if (existingSim == null)
445 {
446 insertResponse = plugin.AddProfile(sim);
447 }
448 else
449 {
450 insertResponse = plugin.UpdateProfile(sim);
451 }
452
453 switch (insertResponse)
454 {
455 case DataResponse.RESPONSE_OK:
456 m_log.Info("[LOGIN END]: " + (existingSim == null ? "New" : "Existing") + " sim login successful: " + sim.regionName);
457 break;
458 case DataResponse.RESPONSE_ERROR:
459 m_log.Warn("[LOGIN END]: Sim login failed (Error): " + sim.regionName);
460 break;
461 case DataResponse.RESPONSE_INVALIDCREDENTIALS:
462 m_log.Warn("[LOGIN END]: " +
463 "Sim login failed (Invalid Credentials): " + sim.regionName);
464 break;
465 case DataResponse.RESPONSE_AUTHREQUIRED:
466 m_log.Warn("[LOGIN END]: " +
467 "Sim login failed (Authentication Required): " +
468 sim.regionName);
469 break;
470 }
471 }
472 catch (Exception e)
473 {
474 m_log.Warn("[LOGIN END]: " +
475 "Unable to login region " + sim.ToString() + " via " + plugin.Name);
476 m_log.Warn("[LOGIN END]: " + e.ToString());
477 }
478 }
479
480 XmlRpcResponse response = CreateLoginResponse(sim);
481
482 return response;
483 }
484 else
485 {
486 m_log.Warn("[LOGIN END]: Failed to login region " + sim.regionName + " at location " + sim.regionLocX + " " + sim.regionLocY + " currently occupied by " + existingSim.regionName);
487 return ErrorResponse("Another region already exists at that location. Please try another.");
488 }
489 }
490
491 /// <summary>
492 /// Construct a successful response to a simulator's login attempt.
493 /// </summary>
494 /// <param name="sim"></param>
495 /// <returns></returns>
496 private XmlRpcResponse CreateLoginResponse(RegionProfileData sim)
497 {
498 XmlRpcResponse response = new XmlRpcResponse();
499 Hashtable responseData = new Hashtable();
500 response.Value = responseData;
501
502 ArrayList SimNeighboursData = GetSimNeighboursData(sim);
503
504 responseData["UUID"] = sim.UUID.ToString();
505 responseData["region_locx"] = sim.regionLocX.ToString();
506 responseData["region_locy"] = sim.regionLocY.ToString();
507 responseData["regionname"] = sim.regionName;
508 responseData["estate_id"] = "1";
509 responseData["neighbours"] = SimNeighboursData;
510
511 responseData["sim_ip"] = sim.serverIP;
512 responseData["sim_port"] = sim.serverPort.ToString();
513 responseData["asset_url"] = sim.regionAssetURI;
514 responseData["asset_sendkey"] = sim.regionAssetSendKey;
515 responseData["asset_recvkey"] = sim.regionAssetRecvKey;
516 responseData["user_url"] = sim.regionUserURI;
517 responseData["user_sendkey"] = sim.regionUserSendKey;
518 responseData["user_recvkey"] = sim.regionUserRecvKey;
519 responseData["authkey"] = sim.regionSecret;
520
521 // New! If set, use as URL to local sim storage (ie http://remotehost/region.Yap)
522 responseData["data_uri"] = sim.regionDataURI;
523
524 responseData["allow_forceful_banlines"] = Config.AllowForcefulBanlines;
525
526 // Instead of sending a multitude of message servers to the registering sim
527 // we should probably be sending a single one and parhaps it's backup
528 // that has responsibility over routing it's messages.
529
530 // The Sim won't be contacting us again about any of the message server stuff during it's time up.
531
532 responseData["messageserver_count"] = _MessageServers.Count;
533
534 for (int i = 0; i < _MessageServers.Count; i++)
535 {
536 responseData["messageserver_uri" + i] = _MessageServers[i].URI;
537 responseData["messageserver_sendkey" + i] = _MessageServers[i].sendkey;
538 responseData["messageserver_recvkey" + i] = _MessageServers[i].recvkey;
539 }
540 return response;
541 }
542
543 private ArrayList GetSimNeighboursData(RegionProfileData sim)
544 {
545 ArrayList SimNeighboursData = new ArrayList();
546
547 RegionProfileData neighbour;
548 Hashtable NeighbourBlock;
549
550 //First use the fast method. (not implemented in SQLLite)
551 List<RegionProfileData> neighbours = GetRegions(sim.regionLocX - 1, sim.regionLocY - 1, sim.regionLocX + 1, sim.regionLocY + 1);
552
553 if (neighbours.Count > 0)
554 {
555 foreach (RegionProfileData aSim in neighbours)
556 {
557 NeighbourBlock = new Hashtable();
558 NeighbourBlock["sim_ip"] = aSim.serverIP;
559 NeighbourBlock["sim_port"] = aSim.serverPort.ToString();
560 NeighbourBlock["region_locx"] = aSim.regionLocX.ToString();
561 NeighbourBlock["region_locy"] = aSim.regionLocY.ToString();
562 NeighbourBlock["UUID"] = aSim.ToString();
563 NeighbourBlock["regionHandle"] = aSim.regionHandle.ToString();
564
565 if (aSim.UUID != sim.UUID)
566 {
567 SimNeighboursData.Add(NeighbourBlock);
568 }
569 }
570 }
571 else
572 {
573 for (int x = -1; x < 2; x++)
574 {
575 for (int y = -1; y < 2; y++)
576 {
577 if (
578 GetRegion(
579 Utils.UIntsToLong((uint)((sim.regionLocX + x) * Constants.RegionSize),
580 (uint)(sim.regionLocY + y) * Constants.RegionSize)) != null)
581 {
582 neighbour =
583 GetRegion(
584 Utils.UIntsToLong((uint)((sim.regionLocX + x) * Constants.RegionSize),
585 (uint)(sim.regionLocY + y) * Constants.RegionSize));
586
587 NeighbourBlock = new Hashtable();
588 NeighbourBlock["sim_ip"] = neighbour.serverIP;
589 NeighbourBlock["sim_port"] = neighbour.serverPort.ToString();
590 NeighbourBlock["region_locx"] = neighbour.regionLocX.ToString();
591 NeighbourBlock["region_locy"] = neighbour.regionLocY.ToString();
592 NeighbourBlock["UUID"] = neighbour.UUID.ToString();
593 NeighbourBlock["regionHandle"] = neighbour.regionHandle.ToString();
594
595 if (neighbour.UUID != sim.UUID) SimNeighboursData.Add(NeighbourBlock);
596 }
597 }
598 }
599 }
600 return SimNeighboursData;
601 }
602
603 /// <summary>
604 /// Loads the grid's own RegionProfileData object with data from the XMLRPC simulator_login request from a region
605 /// </summary>
606 /// <param name="requestData"></param>
607 /// <returns></returns>
608 private RegionProfileData RegionFromRequest(Hashtable requestData)
609 {
610 RegionProfileData sim;
611 sim = new RegionProfileData();
612
613 sim.UUID = new UUID((string)requestData["UUID"]);
614 sim.originUUID = new UUID((string)requestData["originUUID"]);
615
616 sim.regionRecvKey = String.Empty;
617 sim.regionSendKey = String.Empty;
618
619 if (requestData.ContainsKey("region_secret"))
620 {
621 string regionsecret = (string)requestData["region_secret"];
622 if (regionsecret.Length > 0)
623 sim.regionSecret = regionsecret;
624 else
625 sim.regionSecret = Config.SimRecvKey;
626
627 }
628 else
629 {
630 sim.regionSecret = Config.SimRecvKey;
631 }
632
633 sim.regionDataURI = String.Empty;
634 sim.regionAssetURI = Config.DefaultAssetServer;
635 sim.regionAssetRecvKey = Config.AssetRecvKey;
636 sim.regionAssetSendKey = Config.AssetSendKey;
637 sim.regionUserURI = Config.DefaultUserServer;
638 sim.regionUserSendKey = Config.UserSendKey;
639 sim.regionUserRecvKey = Config.UserRecvKey;
640
641 sim.serverIP = (string)requestData["sim_ip"];
642 sim.serverPort = Convert.ToUInt32((string)requestData["sim_port"]);
643 sim.httpPort = Convert.ToUInt32((string)requestData["http_port"]);
644 sim.remotingPort = Convert.ToUInt32((string)requestData["remoting_port"]);
645 sim.regionLocX = Convert.ToUInt32((string)requestData["region_locx"]);
646 sim.regionLocY = Convert.ToUInt32((string)requestData["region_locy"]);
647 sim.regionLocZ = 0;
648
649 UUID textureID;
650 if (UUID.TryParse((string)requestData["map-image-id"], out textureID))
651 {
652 sim.regionMapTextureID = textureID;
653 }
654
655 // part of an initial brutish effort to provide accurate information (as per the xml region spec)
656 // wrt the ownership of a given region
657 // the (very bad) assumption is that this value is being read and handled inconsistently or
658 // not at all. Current strategy is to put the code in place to support the validity of this information
659 // and to roll forward debugging any issues from that point
660 //
661 // this particular section of the mod attempts to receive a value from the region's xml file by way of
662 // OSG1GridServices for the region's owner
663 sim.owner_uuid = (UUID)(string)requestData["master_avatar_uuid"];
664
665 try
666 {
667 sim.regionRecvKey = (string)requestData["recvkey"];
668 sim.regionSendKey = (string)requestData["authkey"];
669 }
670 catch (KeyNotFoundException) { }
671
672 sim.regionHandle = Utils.UIntsToLong((sim.regionLocX * Constants.RegionSize), (sim.regionLocY * Constants.RegionSize));
673 sim.serverURI = (string)requestData["server_uri"];
674
675 sim.httpServerURI = "http://" + sim.serverIP + ":" + sim.httpPort + "/";
676
677 sim.regionName = (string)requestData["sim_name"];
678 return sim;
679 }
680
681 /// <summary>
682 /// Returns an XML RPC response to a simulator profile request
683 /// Performed after moving a region.
684 /// </summary>
685 /// <param name="request"></param>
686 /// <returns></returns>
687 /// <param name="request">The XMLRPC Request</param>
688 /// <returns>Processing parameters</returns>
689 public XmlRpcResponse XmlRpcDeleteRegionMethod(XmlRpcRequest request)
690 {
691 XmlRpcResponse response = new XmlRpcResponse();
692 Hashtable responseData = new Hashtable();
693 response.Value = responseData;
694
695 //RegionProfileData TheSim = null;
696 string uuid;
697 Hashtable requestData = (Hashtable)request.Params[0];
698
699 if (requestData.ContainsKey("UUID"))
700 {
701 //TheSim = GetRegion(new UUID((string) requestData["UUID"]));
702 uuid = requestData["UUID"].ToString();
703 m_log.InfoFormat("[LOGOUT]: Logging out region: {0}", uuid);
704// logToDB((new LLUUID((string)requestData["UUID"])).ToString(),"XmlRpcDeleteRegionMethod","", 5,"Attempting delete with UUID.");
705 }
706 else
707 {
708 responseData["error"] = "No UUID or region_handle passed to grid server - unable to delete";
709 return response;
710 }
711
712 foreach (IGridDataPlugin plugin in _plugins)
713 {
714 //OpenSim.Data.MySQL.MySQLGridData dbengine = new OpenSim.Data.MySQL.MySQLGridData();
715 try
716 {
717 //Nice are we not using multiple databases?
718 //MySQLGridData mysqldata = (MySQLGridData)(plugin);
719
720 //DataResponse insertResponse = mysqldata.DeleteProfile(TheSim);
721 DataResponse insertResponse = plugin.DeleteProfile(uuid);
722
723 switch (insertResponse)
724 {
725 case DataResponse.RESPONSE_OK:
726 //MainLog.Instance.Verbose("grid", "Deleting region successful: " + uuid);
727 responseData["status"] = "Deleting region successful: " + uuid;
728 break;
729 case DataResponse.RESPONSE_ERROR:
730 //MainLog.Instance.Warn("storage", "Deleting region failed (Error): " + uuid);
731 responseData["status"] = "Deleting region failed (Error): " + uuid;
732 break;
733 case DataResponse.RESPONSE_INVALIDCREDENTIALS:
734 //MainLog.Instance.Warn("storage", "Deleting region failed (Invalid Credentials): " + uuid);
735 responseData["status"] = "Deleting region (Invalid Credentials): " + uuid;
736 break;
737 case DataResponse.RESPONSE_AUTHREQUIRED:
738 //MainLog.Instance.Warn("storage", "Deleting region failed (Authentication Required): " + uuid);
739 responseData["status"] = "Deleting region (Authentication Required): " + uuid;
740 break;
741 }
742 }
743 catch (Exception)
744 {
745 m_log.Error("storage Unable to delete region " + uuid + " via " + plugin.Name);
746 //MainLog.Instance.Warn("storage", e.ToString());
747 }
748 }
749
750 return response;
751 }
752
753 /// <summary>
754 /// Returns an XML RPC response to a simulator profile request
755 /// </summary>
756 /// <param name="request"></param>
757 /// <returns></returns>
758 public XmlRpcResponse XmlRpcSimulatorDataRequestMethod(XmlRpcRequest request)
759 {
760 Hashtable requestData = (Hashtable)request.Params[0];
761 Hashtable responseData = new Hashtable();
762 RegionProfileData simData = null;
763 if (requestData.ContainsKey("region_UUID"))
764 {
765 UUID regionID = new UUID((string)requestData["region_UUID"]);
766 simData = GetRegion(regionID);
767 if (simData == null)
768 {
769 m_log.WarnFormat("[DATA] didn't find region for regionID {0} from {1}",
770 regionID, request.Params.Count > 1 ? request.Params[1] : "unknwon source");
771 }
772 }
773 else if (requestData.ContainsKey("region_handle"))
774 {
775 //CFK: The if/else below this makes this message redundant.
776 //CFK: Console.WriteLine("requesting data for region " + (string) requestData["region_handle"]);
777 ulong regionHandle = Convert.ToUInt64((string)requestData["region_handle"]);
778 simData = GetRegion(regionHandle);
779 if (simData == null)
780 {
781 m_log.WarnFormat("[DATA] didn't find region for regionHandle {0} from {1}",
782 regionHandle, request.Params.Count > 1 ? request.Params[1] : "unknwon source");
783 }
784 }
785 else if (requestData.ContainsKey("region_name_search"))
786 {
787 string regionName = (string)requestData["region_name_search"];
788 simData = GetRegion(regionName);
789 if (simData == null)
790 {
791 m_log.WarnFormat("[DATA] didn't find region for regionName {0} from {1}",
792 regionName, request.Params.Count > 1 ? request.Params[1] : "unknwon source");
793 }
794 }
795 else m_log.Warn("[DATA] regionlookup without regionID, regionHandle or regionHame");
796
797 if (simData == null)
798 {
799 //Sim does not exist
800 responseData["error"] = "Sim does not exist";
801 }
802 else
803 {
804 m_log.Info("[DATA]: found " + (string)simData.regionName + " regionHandle = " +
805 (string)requestData["region_handle"]);
806 responseData["sim_ip"] = simData.serverIP;
807 responseData["sim_port"] = simData.serverPort.ToString();
808 responseData["server_uri"] = simData.serverURI;
809 responseData["http_port"] = simData.httpPort.ToString();
810 responseData["remoting_port"] = simData.remotingPort.ToString();
811 responseData["region_locx"] = simData.regionLocX.ToString();
812 responseData["region_locy"] = simData.regionLocY.ToString();
813 responseData["region_UUID"] = simData.UUID.Guid.ToString();
814 responseData["region_name"] = simData.regionName;
815 responseData["regionHandle"] = simData.regionHandle.ToString();
816 }
817
818 XmlRpcResponse response = new XmlRpcResponse();
819 response.Value = responseData;
820 return response;
821 }
822
823 public XmlRpcResponse XmlRpcMapBlockMethod(XmlRpcRequest request)
824 {
825 int xmin = 980, ymin = 980, xmax = 1020, ymax = 1020;
826
827 Hashtable requestData = (Hashtable)request.Params[0];
828 if (requestData.ContainsKey("xmin"))
829 {
830 xmin = (Int32)requestData["xmin"];
831 }
832 if (requestData.ContainsKey("ymin"))
833 {
834 ymin = (Int32)requestData["ymin"];
835 }
836 if (requestData.ContainsKey("xmax"))
837 {
838 xmax = (Int32)requestData["xmax"];
839 }
840 if (requestData.ContainsKey("ymax"))
841 {
842 ymax = (Int32)requestData["ymax"];
843 }
844 //CFK: The second log is more meaningful and either standard or fast generally occurs.
845 //CFK: m_log.Info("[MAP]: World map request for range (" + xmin + "," + ymin + ")..(" + xmax + "," + ymax + ")");
846
847 XmlRpcResponse response = new XmlRpcResponse();
848 Hashtable responseData = new Hashtable();
849 response.Value = responseData;
850 IList simProfileList = new ArrayList();
851
852 bool fastMode = (Config.DatabaseProvider == "OpenSim.Data.MySQL.dll" || Config.DatabaseProvider == "OpenSim.Data.MSSQL.dll");
853
854 if (fastMode)
855 {
856 List<RegionProfileData> neighbours = GetRegions((uint)xmin, (uint)ymin, (uint)xmax, (uint)ymax);
857
858 foreach (RegionProfileData aSim in neighbours)
859 {
860 Hashtable simProfileBlock = new Hashtable();
861 simProfileBlock["x"] = aSim.regionLocX.ToString();
862 simProfileBlock["y"] = aSim.regionLocY.ToString();
863 //m_log.DebugFormat("[MAP]: Sending neighbour info for {0},{1}", aSim.regionLocX, aSim.regionLocY);
864 simProfileBlock["name"] = aSim.regionName;
865 simProfileBlock["access"] = 21;
866 simProfileBlock["region-flags"] = 512;
867 simProfileBlock["water-height"] = 0;
868 simProfileBlock["agents"] = 1;
869 simProfileBlock["map-image-id"] = aSim.regionMapTextureID.ToString();
870
871 // For Sugilite compatibility
872 simProfileBlock["regionhandle"] = aSim.regionHandle.ToString();
873 simProfileBlock["sim_ip"] = aSim.serverIP;
874 simProfileBlock["sim_port"] = aSim.serverPort.ToString();
875 simProfileBlock["sim_uri"] = aSim.serverURI.ToString();
876 simProfileBlock["uuid"] = aSim.UUID.ToString();
877 simProfileBlock["remoting_port"] = aSim.remotingPort.ToString();
878 simProfileBlock["http_port"] = aSim.httpPort.ToString();
879
880 simProfileList.Add(simProfileBlock);
881 }
882 m_log.Info("[MAP]: Fast map " + simProfileList.Count.ToString() +
883 " regions @ (" + xmin + "," + ymin + ")..(" + xmax + "," + ymax + ")");
884 }
885 else
886 {
887 RegionProfileData simProfile;
888 for (int x = xmin; x < xmax + 1; x++)
889 {
890 for (int y = ymin; y < ymax + 1; y++)
891 {
892 ulong regHandle = Utils.UIntsToLong((uint)(x * Constants.RegionSize), (uint)(y * Constants.RegionSize));
893 simProfile = GetRegion(regHandle);
894 if (simProfile != null)
895 {
896 Hashtable simProfileBlock = new Hashtable();
897 simProfileBlock["x"] = x;
898 simProfileBlock["y"] = y;
899 simProfileBlock["name"] = simProfile.regionName;
900 simProfileBlock["access"] = 0;
901 simProfileBlock["region-flags"] = 0;
902 simProfileBlock["water-height"] = 20;
903 simProfileBlock["agents"] = 1;
904 simProfileBlock["map-image-id"] = simProfile.regionMapTextureID.ToString();
905
906 // For Sugilite compatibility
907 simProfileBlock["regionhandle"] = simProfile.regionHandle.ToString();
908 simProfileBlock["sim_ip"] = simProfile.serverIP.ToString();
909 simProfileBlock["sim_port"] = simProfile.serverPort.ToString();
910 simProfileBlock["sim_uri"] = simProfile.serverURI.ToString();
911 simProfileBlock["uuid"] = simProfile.UUID.ToString();
912 simProfileBlock["remoting_port"] = simProfile.remotingPort.ToString();
913 simProfileBlock["http_port"] = simProfile.httpPort;
914
915 simProfileList.Add(simProfileBlock);
916 }
917 }
918 }
919 m_log.Info("[MAP]: Std map " + simProfileList.Count.ToString() +
920 " regions @ (" + xmin + "," + ymin + ")..(" + xmax + "," + ymax + ")");
921 }
922
923 responseData["sim-profiles"] = simProfileList;
924
925 return response;
926 }
927
928 /// <summary>
929 /// Returns up to <code>maxNumber</code> profiles of regions that have a name starting with <code>name</code>
930 /// </summary>
931 /// <param name="request"></param>
932 /// <returns></returns>
933 public XmlRpcResponse XmlRpcSearchForRegionMethod(XmlRpcRequest request)
934 {
935 Hashtable requestData = (Hashtable)request.Params[0];
936
937 if (!requestData.ContainsKey("name") || !requestData.Contains("maxNumber"))
938 {
939 m_log.Warn("[DATA] Invalid region-search request; missing name or maxNumber");
940 return new XmlRpcResponse(500, "Missing name or maxNumber in region search request");
941 }
942
943 Hashtable responseData = new Hashtable();
944
945 string name = (string)requestData["name"];
946 int maxNumber = Convert.ToInt32((string)requestData["maxNumber"]);
947 if (maxNumber == 0 || name.Length < 3)
948 {
949 // either we didn't want any, or we were too unspecific
950 responseData["numFound"] = 0;
951 }
952 else
953 {
954 List<RegionProfileData> sims = GetRegions(name, maxNumber);
955
956 responseData["numFound"] = sims.Count;
957 for (int i = 0; i < sims.Count; ++i)
958 {
959 RegionProfileData sim = sims[i];
960 string prefix = "region" + i + ".";
961 responseData[prefix + "region_name"] = sim.regionName;
962 responseData[prefix + "region_UUID"] = sim.UUID.ToString();
963 responseData[prefix + "region_locx"] = sim.regionLocX.ToString();
964 responseData[prefix + "region_locy"] = sim.regionLocY.ToString();
965 responseData[prefix + "sim_ip"] = sim.serverIP.ToString();
966 responseData[prefix + "sim_port"] = sim.serverPort.ToString();
967 responseData[prefix + "remoting_port"] = sim.remotingPort.ToString();
968 responseData[prefix + "http_port"] = sim.httpPort.ToString();
969 responseData[prefix + "map_UUID"] = sim.regionMapTextureID.ToString();
970 }
971 }
972
973 XmlRpcResponse response = new XmlRpcResponse();
974 response.Value = responseData;
975 return response;
976 }
977
978 /// <summary>
979 /// Performs a REST Get Operation
980 /// </summary>
981 /// <param name="request"></param>
982 /// <param name="path"></param>
983 /// <param name="param"></param>
984 /// <param name="httpRequest">HTTP request header object</param>
985 /// <param name="httpResponse">HTTP response header object</param>
986 /// <returns></returns>
987 public string RestGetRegionMethod(string request, string path, string param,
988 OSHttpRequest httpRequest, OSHttpResponse httpResponse)
989 {
990 return RestGetSimMethod(String.Empty, "/sims/", param, httpRequest, httpResponse);
991 }
992
993 /// <summary>
994 /// Performs a REST Set Operation
995 /// </summary>
996 /// <param name="request"></param>
997 /// <param name="path"></param>
998 /// <param name="param"></param>
999 /// <param name="httpRequest">HTTP request header object</param>
1000 /// <param name="httpResponse">HTTP response header object</param>
1001 /// <returns></returns>
1002 public string RestSetRegionMethod(string request, string path, string param,
1003 OSHttpRequest httpRequest, OSHttpResponse httpResponse)
1004 {
1005 return RestSetSimMethod(String.Empty, "/sims/", param, httpRequest, httpResponse);
1006 }
1007
1008 /// <summary>
1009 /// Returns information about a sim via a REST Request
1010 /// </summary>
1011 /// <param name="request"></param>
1012 /// <param name="path"></param>
1013 /// <param name="param">A string representing the sim's UUID</param>
1014 /// <param name="httpRequest">HTTP request header object</param>
1015 /// <param name="httpResponse">HTTP response header object</param>
1016 /// <returns>Information about the sim in XML</returns>
1017 public string RestGetSimMethod(string request, string path, string param,
1018 OSHttpRequest httpRequest, OSHttpResponse httpResponse)
1019 {
1020 string respstring = String.Empty;
1021
1022 RegionProfileData TheSim;
1023
1024 UUID UUID;
1025 if (UUID.TryParse(param, out UUID))
1026 {
1027 TheSim = GetRegion(UUID);
1028
1029 if (!(TheSim == null))
1030 {
1031 respstring = "<Root>";
1032 respstring += "<authkey>" + TheSim.regionSendKey + "</authkey>";
1033 respstring += "<sim>";
1034 respstring += "<uuid>" + TheSim.UUID.ToString() + "</uuid>";
1035 respstring += "<regionname>" + TheSim.regionName + "</regionname>";
1036 respstring += "<sim_ip>" + TheSim.serverIP + "</sim_ip>";
1037 respstring += "<sim_port>" + TheSim.serverPort.ToString() + "</sim_port>";
1038 respstring += "<region_locx>" + TheSim.regionLocX.ToString() + "</region_locx>";
1039 respstring += "<region_locy>" + TheSim.regionLocY.ToString() + "</region_locy>";
1040 respstring += "<estate_id>1</estate_id>";
1041 respstring += "</sim>";
1042 respstring += "</Root>";
1043 }
1044 }
1045 else
1046 {
1047 respstring = "<Root>";
1048 respstring += "<error>Param must be a UUID</error>";
1049 respstring += "</Root>";
1050 }
1051
1052 return respstring;
1053 }
1054
1055 /// <summary>
1056 /// Creates or updates a sim via a REST Method Request
1057 /// BROKEN with SQL Update
1058 /// </summary>
1059 /// <param name="request"></param>
1060 /// <param name="path"></param>
1061 /// <param name="param"></param>
1062 /// <param name="httpRequest">HTTP request header object</param>
1063 /// <param name="httpResponse">HTTP response header object</param>
1064 /// <returns>"OK" or an error</returns>
1065 public string RestSetSimMethod(string request, string path, string param,
1066 OSHttpRequest httpRequest, OSHttpResponse httpResponse)
1067 {
1068 Console.WriteLine("Processing region update via REST method");
1069 RegionProfileData theSim;
1070 theSim = GetRegion(new UUID(param));
1071 if (theSim == null)
1072 {
1073 theSim = new RegionProfileData();
1074 UUID UUID = new UUID(param);
1075 theSim.UUID = UUID;
1076 theSim.regionRecvKey = Config.SimRecvKey;
1077 }
1078
1079 XmlDocument doc = new XmlDocument();
1080 doc.LoadXml(request);
1081 XmlNode rootnode = doc.FirstChild;
1082 XmlNode authkeynode = rootnode.ChildNodes[0];
1083 if (authkeynode.Name != "authkey")
1084 {
1085 return "ERROR! bad XML - expected authkey tag";
1086 }
1087
1088 XmlNode simnode = rootnode.ChildNodes[1];
1089 if (simnode.Name != "sim")
1090 {
1091 return "ERROR! bad XML - expected sim tag";
1092 }
1093
1094 //theSim.regionSendKey = Cfg;
1095 theSim.regionRecvKey = Config.SimRecvKey;
1096 theSim.regionSendKey = Config.SimSendKey;
1097 theSim.regionSecret = Config.SimRecvKey;
1098 theSim.regionDataURI = String.Empty;
1099 theSim.regionAssetURI = Config.DefaultAssetServer;
1100 theSim.regionAssetRecvKey = Config.AssetRecvKey;
1101 theSim.regionAssetSendKey = Config.AssetSendKey;
1102 theSim.regionUserURI = Config.DefaultUserServer;
1103 theSim.regionUserSendKey = Config.UserSendKey;
1104 theSim.regionUserRecvKey = Config.UserRecvKey;
1105
1106 for (int i = 0; i < simnode.ChildNodes.Count; i++)
1107 {
1108 switch (simnode.ChildNodes[i].Name)
1109 {
1110 case "regionname":
1111 theSim.regionName = simnode.ChildNodes[i].InnerText;
1112 break;
1113
1114 case "sim_ip":
1115 theSim.serverIP = simnode.ChildNodes[i].InnerText;
1116 break;
1117
1118 case "sim_port":
1119 theSim.serverPort = Convert.ToUInt32(simnode.ChildNodes[i].InnerText);
1120 break;
1121
1122 case "region_locx":
1123 theSim.regionLocX = Convert.ToUInt32((string)simnode.ChildNodes[i].InnerText);
1124 theSim.regionHandle = Utils.UIntsToLong((theSim.regionLocX * Constants.RegionSize), (theSim.regionLocY * Constants.RegionSize));
1125 break;
1126
1127 case "region_locy":
1128 theSim.regionLocY = Convert.ToUInt32((string)simnode.ChildNodes[i].InnerText);
1129 theSim.regionHandle = Utils.UIntsToLong((theSim.regionLocX * Constants.RegionSize), (theSim.regionLocY * Constants.RegionSize));
1130 break;
1131 }
1132 }
1133
1134 theSim.serverURI = "http://" + theSim.serverIP + ":" + theSim.serverPort + "/";
1135 bool requirePublic = false;
1136 bool requireValid = true;
1137
1138 if (requirePublic &&
1139 (theSim.serverIP.StartsWith("172.16") || theSim.serverIP.StartsWith("192.168") ||
1140 theSim.serverIP.StartsWith("10.") || theSim.serverIP.StartsWith("0.") ||
1141 theSim.serverIP.StartsWith("255.")))
1142 {
1143 return "ERROR! Servers must register with public addresses.";
1144 }
1145
1146 if (requireValid && (theSim.serverIP.StartsWith("0.") || theSim.serverIP.StartsWith("255.")))
1147 {
1148 return "ERROR! 0.*.*.* / 255.*.*.* Addresses are invalid, please check your server config and try again";
1149 }
1150
1151 try
1152 {
1153 m_log.Info("[DATA]: " +
1154 "Updating / adding via " + _plugins.Count + " storage provider(s) registered.");
1155
1156 foreach (IGridDataPlugin plugin in _plugins)
1157 {
1158 try
1159 {
1160 //Check reservations
1161 ReservationData reserveData =
1162 plugin.GetReservationAtPoint(theSim.regionLocX, theSim.regionLocY);
1163 if ((reserveData != null && reserveData.gridRecvKey == theSim.regionRecvKey) ||
1164 (reserveData == null && authkeynode.InnerText != theSim.regionRecvKey))
1165 {
1166 plugin.AddProfile(theSim);
1167 m_log.Info("[grid]: New sim added to grid (" + theSim.regionName + ")");
1168 logToDB(theSim.ToString(), "RestSetSimMethod", String.Empty, 5,
1169 "Region successfully updated and connected to grid.");
1170 }
1171 else
1172 {
1173 m_log.Warn("[grid]: " +
1174 "Unable to update region (RestSetSimMethod): Incorrect reservation auth key.");
1175 // Wanted: " + reserveData.gridRecvKey + ", Got: " + theSim.regionRecvKey + ".");
1176 return "Unable to update region (RestSetSimMethod): Incorrect auth key.";
1177 }
1178 }
1179 catch (Exception e)
1180 {
1181 m_log.Warn("[GRID]: GetRegionPlugin Handle " + plugin.Name + " unable to add new sim: " +
1182 e.ToString());
1183 }
1184 }
1185 return "OK";
1186 }
1187 catch (Exception e)
1188 {
1189 return "ERROR! Could not save to database! (" + e.ToString() + ")";
1190 }
1191 }
1192
1193 public XmlRpcResponse XmlRPCRegisterMessageServer(XmlRpcRequest request)
1194 {
1195 XmlRpcResponse response = new XmlRpcResponse();
1196 Hashtable requestData = (Hashtable)request.Params[0];
1197 Hashtable responseData = new Hashtable();
1198
1199 if (requestData.Contains("uri"))
1200 {
1201 string URI = (string)requestData["URI"];
1202 string sendkey = (string)requestData["sendkey"];
1203 string recvkey = (string)requestData["recvkey"];
1204 MessageServerInfo m = new MessageServerInfo();
1205 m.URI = URI;
1206 m.sendkey = sendkey;
1207 m.recvkey = recvkey;
1208 if (!_MessageServers.Contains(m))
1209 _MessageServers.Add(m);
1210 responseData["responsestring"] = "TRUE";
1211 response.Value = responseData;
1212 }
1213 return response;
1214 }
1215
1216 public XmlRpcResponse XmlRPCDeRegisterMessageServer(XmlRpcRequest request)
1217 {
1218 XmlRpcResponse response = new XmlRpcResponse();
1219 Hashtable requestData = (Hashtable)request.Params[0];
1220 Hashtable responseData = new Hashtable();
1221
1222 if (requestData.Contains("uri"))
1223 {
1224 string URI = (string)requestData["uri"];
1225 string sendkey = (string)requestData["sendkey"];
1226 string recvkey = (string)requestData["recvkey"];
1227 MessageServerInfo m = new MessageServerInfo();
1228 m.URI = URI;
1229 m.sendkey = sendkey;
1230 m.recvkey = recvkey;
1231 if (_MessageServers.Contains(m))
1232 _MessageServers.Remove(m);
1233 responseData["responsestring"] = "TRUE";
1234 response.Value = responseData;
1235 }
1236 return response;
1237 }
1238
1239 /// <summary>
1240 /// Construct an XMLRPC registration disabled response
1241 /// </summary>
1242 /// <param name="error"></param>
1243 /// <returns></returns>
1244 public static XmlRpcResponse XmlRPCRegionRegistrationDisabledResponse(string error)
1245 {
1246 XmlRpcResponse errorResponse = new XmlRpcResponse();
1247 Hashtable errorResponseData = new Hashtable();
1248 errorResponse.Value = errorResponseData;
1249 errorResponseData["restricted"] = error;
1250 return errorResponse;
1251 }
1252 }
1253
1254 /// <summary>
1255 /// Exception generated when a simulator fails to login to the grid
1256 /// </summary>
1257 public class LoginException : Exception
1258 {
1259 /// <summary>
1260 /// Return an XmlRpcResponse version of the exception message suitable for sending to a client
1261 /// </summary>
1262 /// <param name="message"></param>
1263 /// <param name="xmlRpcMessage"></param>
1264 public XmlRpcResponse XmlRpcErrorResponse
1265 {
1266 get { return m_xmlRpcErrorResponse; }
1267 }
1268 private XmlRpcResponse m_xmlRpcErrorResponse;
1269
1270 public LoginException(string message, string xmlRpcMessage) : base(message)
1271 {
1272 // FIXME: Might be neater to refactor and put the method inside here
1273 m_xmlRpcErrorResponse = GridManager.ErrorResponse(xmlRpcMessage);
1274 }
1275
1276 public LoginException(string message, string xmlRpcMessage, Exception e) : base(message, e)
1277 {
1278 // FIXME: Might be neater to refactor and put the method inside here
1279 m_xmlRpcErrorResponse = GridManager.ErrorResponse(xmlRpcMessage);
1280 }
1281 }
1282}