diff options
author | David Walter Seikel | 2016-11-03 21:44:39 +1000 |
---|---|---|
committer | David Walter Seikel | 2016-11-03 21:44:39 +1000 |
commit | 134f86e8d5c414409631b25b8c6f0ee45fbd8631 (patch) | |
tree | 216b89d3fb89acfb81be1e440c25c41ab09fa96d /OpenSim/Services/GridService/GridService.cs | |
parent | More changing to production grid. Double oops. (diff) | |
download | opensim-SC_OLD-134f86e8d5c414409631b25b8c6f0ee45fbd8631.zip opensim-SC_OLD-134f86e8d5c414409631b25b8c6f0ee45fbd8631.tar.gz opensim-SC_OLD-134f86e8d5c414409631b25b8c6f0ee45fbd8631.tar.bz2 opensim-SC_OLD-134f86e8d5c414409631b25b8c6f0ee45fbd8631.tar.xz |
Initial update to OpenSim 0.8.2.1 source code.
Diffstat (limited to '')
-rw-r--r-- | OpenSim/Services/GridService/GridService.cs | 415 |
1 files changed, 342 insertions, 73 deletions
diff --git a/OpenSim/Services/GridService/GridService.cs b/OpenSim/Services/GridService/GridService.cs index ee3b858..0c502a2 100644 --- a/OpenSim/Services/GridService/GridService.cs +++ b/OpenSim/Services/GridService/GridService.cs | |||
@@ -46,6 +46,7 @@ namespace OpenSim.Services.GridService | |||
46 | private static readonly ILog m_log = | 46 | private static readonly ILog m_log = |
47 | LogManager.GetLogger( | 47 | LogManager.GetLogger( |
48 | MethodBase.GetCurrentMethod().DeclaringType); | 48 | MethodBase.GetCurrentMethod().DeclaringType); |
49 | private string LogHeader = "[GRID SERVICE]"; | ||
49 | 50 | ||
50 | private bool m_DeleteOnUnregister = true; | 51 | private bool m_DeleteOnUnregister = true; |
51 | private static GridService m_RootInstance = null; | 52 | private static GridService m_RootInstance = null; |
@@ -56,6 +57,10 @@ namespace OpenSim.Services.GridService | |||
56 | protected bool m_AllowDuplicateNames = false; | 57 | protected bool m_AllowDuplicateNames = false; |
57 | protected bool m_AllowHypergridMapSearch = false; | 58 | protected bool m_AllowHypergridMapSearch = false; |
58 | 59 | ||
60 | protected bool m_SuppressVarregionOverlapCheckOnRegistration = false; | ||
61 | |||
62 | private static Dictionary<string,object> m_ExtraFeatures = new Dictionary<string, object>(); | ||
63 | |||
59 | public GridService(IConfigSource config) | 64 | public GridService(IConfigSource config) |
60 | : base(config) | 65 | : base(config) |
61 | { | 66 | { |
@@ -63,6 +68,9 @@ namespace OpenSim.Services.GridService | |||
63 | 68 | ||
64 | m_config = config; | 69 | m_config = config; |
65 | IConfig gridConfig = config.Configs["GridService"]; | 70 | IConfig gridConfig = config.Configs["GridService"]; |
71 | |||
72 | bool suppressConsoleCommands = false; | ||
73 | |||
66 | if (gridConfig != null) | 74 | if (gridConfig != null) |
67 | { | 75 | { |
68 | m_DeleteOnUnregister = gridConfig.GetBoolean("DeleteOnUnregister", true); | 76 | m_DeleteOnUnregister = gridConfig.GetBoolean("DeleteOnUnregister", true); |
@@ -76,32 +84,33 @@ namespace OpenSim.Services.GridService | |||
76 | } | 84 | } |
77 | m_AllowDuplicateNames = gridConfig.GetBoolean("AllowDuplicateNames", m_AllowDuplicateNames); | 85 | m_AllowDuplicateNames = gridConfig.GetBoolean("AllowDuplicateNames", m_AllowDuplicateNames); |
78 | m_AllowHypergridMapSearch = gridConfig.GetBoolean("AllowHypergridMapSearch", m_AllowHypergridMapSearch); | 86 | m_AllowHypergridMapSearch = gridConfig.GetBoolean("AllowHypergridMapSearch", m_AllowHypergridMapSearch); |
87 | |||
88 | m_SuppressVarregionOverlapCheckOnRegistration = gridConfig.GetBoolean("SuppressVarregionOverlapCheckOnRegistration", m_SuppressVarregionOverlapCheckOnRegistration); | ||
89 | |||
90 | // This service is also used locally by a simulator running in grid mode. This switches prevents | ||
91 | // inappropriate console commands from being registered | ||
92 | suppressConsoleCommands = gridConfig.GetBoolean("SuppressConsoleCommands", suppressConsoleCommands); | ||
79 | } | 93 | } |
80 | 94 | ||
81 | if (m_RootInstance == null) | 95 | if (m_RootInstance == null) |
82 | { | 96 | { |
83 | m_RootInstance = this; | 97 | m_RootInstance = this; |
84 | 98 | ||
85 | if (MainConsole.Instance != null) | 99 | if (!suppressConsoleCommands && MainConsole.Instance != null) |
86 | { | 100 | { |
87 | MainConsole.Instance.Commands.AddCommand("Regions", true, | 101 | MainConsole.Instance.Commands.AddCommand("Regions", true, |
88 | "deregister region id", | 102 | "deregister region id", |
89 | "deregister region id <Region UUID>", | 103 | "deregister region id <region-id>+", |
90 | "Deregister a region manually.", | 104 | "Deregister a region manually.", |
91 | String.Empty, | 105 | String.Empty, |
92 | HandleDeregisterRegion); | 106 | HandleDeregisterRegion); |
93 | 107 | ||
94 | // A messy way of stopping this command being added if we are in standalone (since the simulator | 108 | MainConsole.Instance.Commands.AddCommand("Regions", true, |
95 | // has an identically named command | 109 | "show regions", |
96 | // | 110 | "show regions", |
97 | // XXX: We're relying on the OpenSimulator version being registered first, which is not well defined. | 111 | "Show details on all regions", |
98 | if (MainConsole.Instance.Commands.Resolve(new string[] { "show", "regions" }).Length == 0) | 112 | String.Empty, |
99 | MainConsole.Instance.Commands.AddCommand("Regions", true, | 113 | HandleShowRegions); |
100 | "show regions", | ||
101 | "show regions", | ||
102 | "Show details on all regions", | ||
103 | String.Empty, | ||
104 | HandleShowRegions); | ||
105 | 114 | ||
106 | MainConsole.Instance.Commands.AddCommand("Regions", true, | 115 | MainConsole.Instance.Commands.AddCommand("Regions", true, |
107 | "show region name", | 116 | "show region name", |
@@ -117,17 +126,72 @@ namespace OpenSim.Services.GridService | |||
117 | "For example, show region at 1000 1000", | 126 | "For example, show region at 1000 1000", |
118 | HandleShowRegionAt); | 127 | HandleShowRegionAt); |
119 | 128 | ||
120 | MainConsole.Instance.Commands.AddCommand("Regions", true, | 129 | MainConsole.Instance.Commands.AddCommand("General", true, |
121 | "set region flags", | 130 | "show grid size", |
122 | "set region flags <Region name> <flags>", | 131 | "show grid size", |
123 | "Set database flags for region", | 132 | "Show the current grid size (excluding hyperlink references)", |
124 | String.Empty, | 133 | String.Empty, |
125 | HandleSetFlags); | 134 | HandleShowGridSize); |
135 | |||
136 | MainConsole.Instance.Commands.AddCommand("Regions", true, | ||
137 | "set region flags", | ||
138 | "set region flags <Region name> <flags>", | ||
139 | "Set database flags for region", | ||
140 | String.Empty, | ||
141 | HandleSetFlags); | ||
126 | } | 142 | } |
143 | |||
144 | if (!suppressConsoleCommands) | ||
145 | SetExtraServiceURLs(config); | ||
146 | |||
127 | m_HypergridLinker = new HypergridLinker(m_config, this, m_Database); | 147 | m_HypergridLinker = new HypergridLinker(m_config, this, m_Database); |
128 | } | 148 | } |
129 | } | 149 | } |
130 | 150 | ||
151 | private void SetExtraServiceURLs(IConfigSource config) | ||
152 | { | ||
153 | IConfig loginConfig = config.Configs["LoginService"]; | ||
154 | IConfig gridConfig = config.Configs["GridService"]; | ||
155 | |||
156 | if (loginConfig == null || gridConfig == null) | ||
157 | return; | ||
158 | |||
159 | string configVal; | ||
160 | |||
161 | configVal = loginConfig.GetString("SearchURL", string.Empty); | ||
162 | if (!string.IsNullOrEmpty(configVal)) | ||
163 | m_ExtraFeatures["search-server-url"] = configVal; | ||
164 | |||
165 | configVal = loginConfig.GetString("MapTileURL", string.Empty); | ||
166 | if (!string.IsNullOrEmpty(configVal)) | ||
167 | { | ||
168 | // This URL must end with '/', the viewer doesn't check | ||
169 | configVal = configVal.Trim(); | ||
170 | if (!configVal.EndsWith("/")) | ||
171 | configVal = configVal + "/"; | ||
172 | m_ExtraFeatures["map-server-url"] = configVal; | ||
173 | } | ||
174 | |||
175 | configVal = loginConfig.GetString("DestinationGuide", string.Empty); | ||
176 | if (!string.IsNullOrEmpty(configVal)) | ||
177 | m_ExtraFeatures["destination-guide-url"] = configVal; | ||
178 | |||
179 | configVal = Util.GetConfigVarFromSections<string>( | ||
180 | config, "GatekeeperURI", new string[] { "Startup", "Hypergrid" }, String.Empty); | ||
181 | if (!string.IsNullOrEmpty(configVal)) | ||
182 | m_ExtraFeatures["GridURL"] = configVal; | ||
183 | |||
184 | configVal = Util.GetConfigVarFromSections<string>( | ||
185 | config, "GridName", new string[] { "Const", "Hypergrid" }, String.Empty); | ||
186 | if (string.IsNullOrEmpty(configVal)) | ||
187 | configVal = Util.GetConfigVarFromSections<string>( | ||
188 | config, "gridname", new string[] { "GridInfo" }, String.Empty); | ||
189 | if (!string.IsNullOrEmpty(configVal)) | ||
190 | m_ExtraFeatures["GridName"] = configVal; | ||
191 | |||
192 | m_ExtraFeatures["ExportSupported"] = gridConfig.GetString("ExportSupported", "true"); | ||
193 | } | ||
194 | |||
131 | #region IGridService | 195 | #region IGridService |
132 | 196 | ||
133 | public string RegisterRegion(UUID scopeID, GridRegion regionInfos) | 197 | public string RegisterRegion(UUID scopeID, GridRegion regionInfos) |
@@ -137,12 +201,19 @@ namespace OpenSim.Services.GridService | |||
137 | if (regionInfos.RegionID == UUID.Zero) | 201 | if (regionInfos.RegionID == UUID.Zero) |
138 | return "Invalid RegionID - cannot be zero UUID"; | 202 | return "Invalid RegionID - cannot be zero UUID"; |
139 | 203 | ||
140 | RegionData region = m_Database.Get(regionInfos.RegionLocX, regionInfos.RegionLocY, scopeID); | 204 | String reason = "Region overlaps another region"; |
141 | if ((region != null) && (region.RegionID != regionInfos.RegionID)) | 205 | RegionData region = FindAnyConflictingRegion(regionInfos, scopeID, out reason); |
206 | // If there is a conflicting region, if it has the same ID and same coordinates | ||
207 | // then it is a region re-registering (permissions and ownership checked later). | ||
208 | if ((region != null) | ||
209 | && ( (region.coordX != regionInfos.RegionCoordX) | ||
210 | || (region.coordY != regionInfos.RegionCoordY) | ||
211 | || (region.RegionID != regionInfos.RegionID) ) | ||
212 | ) | ||
142 | { | 213 | { |
143 | m_log.WarnFormat("[GRID SERVICE]: Region {0} tried to register in coordinates {1}, {2} which are already in use in scope {3}.", | 214 | // If not same ID and same coordinates, this new region has conflicts and can't be registered. |
144 | regionInfos.RegionID, regionInfos.RegionLocX, regionInfos.RegionLocY, scopeID); | 215 | m_log.WarnFormat("{0} Register region conflict in scope {1}. {2}", LogHeader, scopeID, reason); |
145 | return "Region overlaps another region"; | 216 | return reason; |
146 | } | 217 | } |
147 | 218 | ||
148 | if (region != null) | 219 | if (region != null) |
@@ -185,15 +256,15 @@ namespace OpenSim.Services.GridService | |||
185 | 256 | ||
186 | if (!m_AllowDuplicateNames) | 257 | if (!m_AllowDuplicateNames) |
187 | { | 258 | { |
188 | List<RegionData> dupe = m_Database.Get(regionInfos.RegionName, scopeID); | 259 | List<RegionData> dupe = m_Database.Get(Util.EscapeForLike(regionInfos.RegionName), scopeID); |
189 | if (dupe != null && dupe.Count > 0) | 260 | if (dupe != null && dupe.Count > 0) |
190 | { | 261 | { |
191 | foreach (RegionData d in dupe) | 262 | foreach (RegionData d in dupe) |
192 | { | 263 | { |
193 | if (d.RegionID != regionInfos.RegionID) | 264 | if (d.RegionID != regionInfos.RegionID) |
194 | { | 265 | { |
195 | m_log.WarnFormat("[GRID SERVICE]: Region {0} tried to register duplicate name with ID {1}.", | 266 | m_log.WarnFormat("[GRID SERVICE]: Region tried to register using a duplicate name. New region: {0} ({1}), existing region: {2} ({3}).", |
196 | regionInfos.RegionName, regionInfos.RegionID); | 267 | regionInfos.RegionName, regionInfos.RegionID, d.RegionName, d.RegionID); |
197 | return "Duplicate region name"; | 268 | return "Duplicate region name"; |
198 | } | 269 | } |
199 | } | 270 | } |
@@ -265,12 +336,121 @@ namespace OpenSim.Services.GridService | |||
265 | m_log.DebugFormat("[GRID SERVICE]: Database exception: {0}", e); | 336 | m_log.DebugFormat("[GRID SERVICE]: Database exception: {0}", e); |
266 | } | 337 | } |
267 | 338 | ||
268 | m_log.DebugFormat("[GRID SERVICE]: Region {0} ({1}) registered successfully at {2}-{3}", | 339 | m_log.InfoFormat |
269 | regionInfos.RegionName, regionInfos.RegionID, regionInfos.RegionCoordX, regionInfos.RegionCoordY); | 340 | ("[GRID SERVICE]: Region {0} ({1}, {2}x{3}) registered at {4},{5} with flags {6}", |
341 | regionInfos.RegionName, regionInfos.RegionID, regionInfos.RegionSizeX, regionInfos.RegionSizeY, | ||
342 | regionInfos.RegionCoordX, regionInfos.RegionCoordY, | ||
343 | (OpenSim.Framework.RegionFlags)flags); | ||
270 | 344 | ||
271 | return String.Empty; | 345 | return String.Empty; |
272 | } | 346 | } |
273 | 347 | ||
348 | /// <summary> | ||
349 | /// Search the region map for regions conflicting with this region. | ||
350 | /// The region to be added is passed and we look for any existing regions that are | ||
351 | /// in the requested location, that are large varregions that overlap this region, or | ||
352 | /// are previously defined regions that would lie under this new region. | ||
353 | /// </summary> | ||
354 | /// <param name="regionInfos">Information on region requested to be added to the world map</param> | ||
355 | /// <param name="scopeID">Grid id for region</param> | ||
356 | /// <param name="reason">The reason the returned region conflicts with passed region</param> | ||
357 | /// <returns></returns> | ||
358 | private RegionData FindAnyConflictingRegion(GridRegion regionInfos, UUID scopeID, out string reason) | ||
359 | { | ||
360 | reason = "Reregistration"; | ||
361 | // First see if there is an existing region right where this region is trying to go | ||
362 | // (We keep this result so it can be returned if suppressing errors) | ||
363 | RegionData noErrorRegion = m_Database.Get(regionInfos.RegionLocX, regionInfos.RegionLocY, scopeID); | ||
364 | RegionData region = noErrorRegion; | ||
365 | if (region != null | ||
366 | && region.RegionID == regionInfos.RegionID | ||
367 | && region.sizeX == regionInfos.RegionSizeX | ||
368 | && region.sizeY == regionInfos.RegionSizeY) | ||
369 | { | ||
370 | // If this seems to be exactly the same region, return this as it could be | ||
371 | // a re-registration (permissions checked by calling routine). | ||
372 | m_log.DebugFormat("{0} FindAnyConflictingRegion: re-register of {1}", | ||
373 | LogHeader, RegionString(regionInfos)); | ||
374 | return region; | ||
375 | } | ||
376 | |||
377 | // No region exactly there or we're resizing an existing region. | ||
378 | // Fetch regions that could be varregions overlapping requested location. | ||
379 | int xmin = regionInfos.RegionLocX - (int)Constants.MaximumRegionSize + 10; | ||
380 | int xmax = regionInfos.RegionLocX; | ||
381 | int ymin = regionInfos.RegionLocY - (int)Constants.MaximumRegionSize + 10; | ||
382 | int ymax = regionInfos.RegionLocY; | ||
383 | List<RegionData> rdatas = m_Database.Get(xmin, ymin, xmax, ymax, scopeID); | ||
384 | foreach (RegionData rdata in rdatas) | ||
385 | { | ||
386 | // m_log.DebugFormat("{0} FindAnyConflictingRegion: find existing. Checking {1}", LogHeader, RegionString(rdata) ); | ||
387 | if ( (rdata.posX + rdata.sizeX > regionInfos.RegionLocX) | ||
388 | && (rdata.posY + rdata.sizeY > regionInfos.RegionLocY) ) | ||
389 | { | ||
390 | region = rdata; | ||
391 | m_log.WarnFormat("{0} FindAnyConflictingRegion: conflict of {1} by existing varregion {2}", | ||
392 | LogHeader, RegionString(regionInfos), RegionString(region)); | ||
393 | reason = String.Format("Region location is overlapped by existing varregion {0}", | ||
394 | RegionString(region)); | ||
395 | |||
396 | if (m_SuppressVarregionOverlapCheckOnRegistration) | ||
397 | region = noErrorRegion; | ||
398 | return region; | ||
399 | } | ||
400 | } | ||
401 | |||
402 | // There isn't a region that overlaps this potential region. | ||
403 | // See if this potential region overlaps an existing region. | ||
404 | // First, a shortcut of not looking for overlap if new region is legacy region sized | ||
405 | // and connot overlap anything. | ||
406 | if (regionInfos.RegionSizeX != Constants.RegionSize | ||
407 | || regionInfos.RegionSizeY != Constants.RegionSize) | ||
408 | { | ||
409 | // trim range looked for so we don't pick up neighbor regions just off the edges | ||
410 | xmin = regionInfos.RegionLocX; | ||
411 | xmax = regionInfos.RegionLocX + regionInfos.RegionSizeX - 10; | ||
412 | ymin = regionInfos.RegionLocY; | ||
413 | ymax = regionInfos.RegionLocY + regionInfos.RegionSizeY - 10; | ||
414 | rdatas = m_Database.Get(xmin, ymin, xmax, ymax, scopeID); | ||
415 | |||
416 | // If the region is being resized, the found region could be ourself. | ||
417 | foreach (RegionData rdata in rdatas) | ||
418 | { | ||
419 | // m_log.DebugFormat("{0} FindAnyConflictingRegion: see if overlap. Checking {1}", LogHeader, RegionString(rdata) ); | ||
420 | if (region == null || region.RegionID != regionInfos.RegionID) | ||
421 | { | ||
422 | region = rdata; | ||
423 | m_log.WarnFormat("{0} FindAnyConflictingRegion: conflict of varregion {1} overlaps existing region {2}", | ||
424 | LogHeader, RegionString(regionInfos), RegionString(region)); | ||
425 | reason = String.Format("Region {0} would overlap existing region {1}", | ||
426 | RegionString(regionInfos), RegionString(region)); | ||
427 | |||
428 | if (m_SuppressVarregionOverlapCheckOnRegistration) | ||
429 | region = noErrorRegion; | ||
430 | return region; | ||
431 | } | ||
432 | } | ||
433 | } | ||
434 | |||
435 | // If we get here, region is either null (nothing found here) or | ||
436 | // is the non-conflicting region found at the location being requested. | ||
437 | return region; | ||
438 | } | ||
439 | |||
440 | // String describing name and region location of passed region | ||
441 | private String RegionString(RegionData reg) | ||
442 | { | ||
443 | return String.Format("{0}/{1} at <{2},{3}>", | ||
444 | reg.RegionName, reg.RegionID, reg.coordX, reg.coordY); | ||
445 | } | ||
446 | |||
447 | // String describing name and region location of passed region | ||
448 | private String RegionString(GridRegion reg) | ||
449 | { | ||
450 | return String.Format("{0}/{1} at <{2},{3}>", | ||
451 | reg.RegionName, reg.RegionID, reg.RegionCoordX, reg.RegionCoordY); | ||
452 | } | ||
453 | |||
274 | public bool DeregisterRegion(UUID regionID) | 454 | public bool DeregisterRegion(UUID regionID) |
275 | { | 455 | { |
276 | RegionData region = m_Database.Get(regionID, UUID.Zero); | 456 | RegionData region = m_Database.Get(regionID, UUID.Zero); |
@@ -312,8 +492,10 @@ namespace OpenSim.Services.GridService | |||
312 | if (region != null) | 492 | if (region != null) |
313 | { | 493 | { |
314 | // Not really? Maybe? | 494 | // Not really? Maybe? |
315 | List<RegionData> rdatas = m_Database.Get(region.posX - (int)Constants.RegionSize - 1, region.posY - (int)Constants.RegionSize - 1, | 495 | // The adjacent regions are presumed to be the same size as the current region |
316 | region.posX + (int)Constants.RegionSize + 1, region.posY + (int)Constants.RegionSize + 1, scopeID); | 496 | List<RegionData> rdatas = m_Database.Get( |
497 | region.posX - region.sizeX - 1, region.posY - region.sizeY - 1, | ||
498 | region.posX + region.sizeX + 1, region.posY + region.sizeY + 1, scopeID); | ||
317 | 499 | ||
318 | foreach (RegionData rdata in rdatas) | 500 | foreach (RegionData rdata in rdatas) |
319 | { | 501 | { |
@@ -325,7 +507,11 @@ namespace OpenSim.Services.GridService | |||
325 | } | 507 | } |
326 | } | 508 | } |
327 | 509 | ||
328 | // m_log.DebugFormat("[GRID SERVICE]: region {0} has {1} neighbours", region.RegionName, rinfos.Count); | 510 | // string rNames = ""; |
511 | // foreach (GridRegion gr in rinfos) | ||
512 | // rNames += gr.RegionName + ","; | ||
513 | // m_log.DebugFormat("{0} region {1} has {2} neighbours ({3})", | ||
514 | // LogHeader, region.RegionName, rinfos.Count, rNames); | ||
329 | } | 515 | } |
330 | else | 516 | else |
331 | { | 517 | { |
@@ -346,20 +532,36 @@ namespace OpenSim.Services.GridService | |||
346 | return null; | 532 | return null; |
347 | } | 533 | } |
348 | 534 | ||
535 | // Get a region given its base coordinates. | ||
536 | // NOTE: this is NOT 'get a region by some point in the region'. The coordinate MUST | ||
537 | // be the base coordinate of the region. | ||
538 | // The snapping is technically unnecessary but is harmless because regions are always | ||
539 | // multiples of the legacy region size (256). | ||
349 | public GridRegion GetRegionByPosition(UUID scopeID, int x, int y) | 540 | public GridRegion GetRegionByPosition(UUID scopeID, int x, int y) |
350 | { | 541 | { |
351 | int snapX = (int)(x / Constants.RegionSize) * (int)Constants.RegionSize; | 542 | uint regionX = Util.WorldToRegionLoc((uint)x); |
352 | int snapY = (int)(y / Constants.RegionSize) * (int)Constants.RegionSize; | 543 | uint regionY = Util.WorldToRegionLoc((uint)y); |
544 | int snapX = (int)Util.RegionToWorldLoc(regionX); | ||
545 | int snapY = (int)Util.RegionToWorldLoc(regionY); | ||
546 | |||
353 | RegionData rdata = m_Database.Get(snapX, snapY, scopeID); | 547 | RegionData rdata = m_Database.Get(snapX, snapY, scopeID); |
354 | if (rdata != null) | 548 | if (rdata != null) |
549 | { | ||
550 | m_log.DebugFormat("{0} GetRegionByPosition. Found region {1} in database. Pos=<{2},{3}>", | ||
551 | LogHeader, rdata.RegionName, regionX, regionY); | ||
355 | return RegionData2RegionInfo(rdata); | 552 | return RegionData2RegionInfo(rdata); |
356 | 553 | } | |
357 | return null; | 554 | else |
555 | { | ||
556 | m_log.DebugFormat("{0} GetRegionByPosition. Did not find region in database. Pos=<{1},{2}>", | ||
557 | LogHeader, regionX, regionY); | ||
558 | return null; | ||
559 | } | ||
358 | } | 560 | } |
359 | 561 | ||
360 | public GridRegion GetRegionByName(UUID scopeID, string name) | 562 | public GridRegion GetRegionByName(UUID scopeID, string name) |
361 | { | 563 | { |
362 | List<RegionData> rdatas = m_Database.Get(name, scopeID); | 564 | List<RegionData> rdatas = m_Database.Get(Util.EscapeForLike(name), scopeID); |
363 | if ((rdatas != null) && (rdatas.Count > 0)) | 565 | if ((rdatas != null) && (rdatas.Count > 0)) |
364 | return RegionData2RegionInfo(rdatas[0]); // get the first | 566 | return RegionData2RegionInfo(rdatas[0]); // get the first |
365 | 567 | ||
@@ -377,7 +579,7 @@ namespace OpenSim.Services.GridService | |||
377 | { | 579 | { |
378 | // m_log.DebugFormat("[GRID SERVICE]: GetRegionsByName {0}", name); | 580 | // m_log.DebugFormat("[GRID SERVICE]: GetRegionsByName {0}", name); |
379 | 581 | ||
380 | List<RegionData> rdatas = m_Database.Get(name + "%", scopeID); | 582 | List<RegionData> rdatas = m_Database.Get(Util.EscapeForLike(name) + "%", scopeID); |
381 | 583 | ||
382 | int count = 0; | 584 | int count = 0; |
383 | List<GridRegion> rinfos = new List<GridRegion>(); | 585 | List<GridRegion> rinfos = new List<GridRegion>(); |
@@ -440,6 +642,8 @@ namespace OpenSim.Services.GridService | |||
440 | RegionData rdata = new RegionData(); | 642 | RegionData rdata = new RegionData(); |
441 | rdata.posX = (int)rinfo.RegionLocX; | 643 | rdata.posX = (int)rinfo.RegionLocX; |
442 | rdata.posY = (int)rinfo.RegionLocY; | 644 | rdata.posY = (int)rinfo.RegionLocY; |
645 | rdata.sizeX = rinfo.RegionSizeX; | ||
646 | rdata.sizeY = rinfo.RegionSizeY; | ||
443 | rdata.RegionID = rinfo.RegionID; | 647 | rdata.RegionID = rinfo.RegionID; |
444 | rdata.RegionName = rinfo.RegionName; | 648 | rdata.RegionName = rinfo.RegionName; |
445 | rdata.Data = rinfo.ToKeyValuePairs(); | 649 | rdata.Data = rinfo.ToKeyValuePairs(); |
@@ -453,6 +657,8 @@ namespace OpenSim.Services.GridService | |||
453 | GridRegion rinfo = new GridRegion(rdata.Data); | 657 | GridRegion rinfo = new GridRegion(rdata.Data); |
454 | rinfo.RegionLocX = rdata.posX; | 658 | rinfo.RegionLocX = rdata.posX; |
455 | rinfo.RegionLocY = rdata.posY; | 659 | rinfo.RegionLocY = rdata.posY; |
660 | rinfo.RegionSizeX = rdata.sizeX; | ||
661 | rinfo.RegionSizeY = rdata.sizeY; | ||
456 | rinfo.RegionID = rdata.RegionID; | 662 | rinfo.RegionID = rdata.RegionID; |
457 | rinfo.RegionName = rdata.RegionName; | 663 | rinfo.RegionName = rdata.RegionName; |
458 | rinfo.ScopeID = rdata.ScopeID; | 664 | rinfo.ScopeID = rdata.ScopeID; |
@@ -478,6 +684,33 @@ namespace OpenSim.Services.GridService | |||
478 | return ret; | 684 | return ret; |
479 | } | 685 | } |
480 | 686 | ||
687 | public List<GridRegion> GetDefaultHypergridRegions(UUID scopeID) | ||
688 | { | ||
689 | List<GridRegion> ret = new List<GridRegion>(); | ||
690 | |||
691 | List<RegionData> regions = m_Database.GetDefaultHypergridRegions(scopeID); | ||
692 | |||
693 | foreach (RegionData r in regions) | ||
694 | { | ||
695 | if ((Convert.ToInt32(r.Data["flags"]) & (int)OpenSim.Framework.RegionFlags.RegionOnline) != 0) | ||
696 | ret.Add(RegionData2RegionInfo(r)); | ||
697 | } | ||
698 | |||
699 | int hgDefaultRegionsFoundOnline = regions.Count; | ||
700 | |||
701 | // For now, hypergrid default regions will always be given precedence but we will also return simple default | ||
702 | // regions in case no specific hypergrid regions are specified. | ||
703 | ret.AddRange(GetDefaultRegions(scopeID)); | ||
704 | |||
705 | int normalDefaultRegionsFoundOnline = ret.Count - hgDefaultRegionsFoundOnline; | ||
706 | |||
707 | m_log.DebugFormat( | ||
708 | "[GRID SERVICE]: GetDefaultHypergridRegions returning {0} hypergrid default and {1} normal default regions", | ||
709 | hgDefaultRegionsFoundOnline, normalDefaultRegionsFoundOnline); | ||
710 | |||
711 | return ret; | ||
712 | } | ||
713 | |||
481 | public List<GridRegion> GetFallbackRegions(UUID scopeID, int x, int y) | 714 | public List<GridRegion> GetFallbackRegions(UUID scopeID, int x, int y) |
482 | { | 715 | { |
483 | List<GridRegion> ret = new List<GridRegion>(); | 716 | List<GridRegion> ret = new List<GridRegion>(); |
@@ -526,40 +759,41 @@ namespace OpenSim.Services.GridService | |||
526 | 759 | ||
527 | private void HandleDeregisterRegion(string module, string[] cmd) | 760 | private void HandleDeregisterRegion(string module, string[] cmd) |
528 | { | 761 | { |
529 | if (cmd.Length != 4) | 762 | if (cmd.Length < 4) |
530 | { | 763 | { |
531 | MainConsole.Instance.Output("Syntax: degregister region id <Region UUID>"); | 764 | MainConsole.Instance.Output("Usage: degregister region id <region-id>+"); |
532 | return; | 765 | return; |
533 | } | 766 | } |
534 | 767 | ||
535 | string rawRegionUuid = cmd[3]; | 768 | for (int i = 3; i < cmd.Length; i++) |
536 | UUID regionUuid; | ||
537 | |||
538 | if (!UUID.TryParse(rawRegionUuid, out regionUuid)) | ||
539 | { | 769 | { |
540 | MainConsole.Instance.OutputFormat("{0} is not a valid region uuid", rawRegionUuid); | 770 | string rawRegionUuid = cmd[i]; |
541 | return; | 771 | UUID regionUuid; |
542 | } | ||
543 | 772 | ||
544 | GridRegion region = GetRegionByUUID(UUID.Zero, regionUuid); | 773 | if (!UUID.TryParse(rawRegionUuid, out regionUuid)) |
774 | { | ||
775 | MainConsole.Instance.OutputFormat("{0} is not a valid region uuid", rawRegionUuid); | ||
776 | return; | ||
777 | } | ||
545 | 778 | ||
546 | if (region == null) | 779 | GridRegion region = GetRegionByUUID(UUID.Zero, regionUuid); |
547 | { | ||
548 | MainConsole.Instance.OutputFormat("No region with UUID {0}", regionUuid); | ||
549 | return; | ||
550 | } | ||
551 | 780 | ||
552 | if (DeregisterRegion(regionUuid)) | 781 | if (region == null) |
553 | { | 782 | { |
554 | MainConsole.Instance.OutputFormat("Deregistered {0} {1}", region.RegionName, regionUuid); | 783 | MainConsole.Instance.OutputFormat("No region with UUID {0}", regionUuid); |
555 | } | 784 | return; |
556 | else | 785 | } |
557 | { | ||
558 | // I don't think this can ever occur if we know that the region exists. | ||
559 | MainConsole.Instance.OutputFormat("Error deregistering {0} {1}", region.RegionName, regionUuid); | ||
560 | } | ||
561 | 786 | ||
562 | return; | 787 | if (DeregisterRegion(regionUuid)) |
788 | { | ||
789 | MainConsole.Instance.OutputFormat("Deregistered {0} {1}", region.RegionName, regionUuid); | ||
790 | } | ||
791 | else | ||
792 | { | ||
793 | // I don't think this can ever occur if we know that the region exists. | ||
794 | MainConsole.Instance.OutputFormat("Error deregistering {0} {1}", region.RegionName, regionUuid); | ||
795 | } | ||
796 | } | ||
563 | } | 797 | } |
564 | 798 | ||
565 | private void HandleShowRegions(string module, string[] cmd) | 799 | private void HandleShowRegions(string module, string[] cmd) |
@@ -575,6 +809,27 @@ namespace OpenSim.Services.GridService | |||
575 | OutputRegionsToConsoleSummary(regions); | 809 | OutputRegionsToConsoleSummary(regions); |
576 | } | 810 | } |
577 | 811 | ||
812 | private void HandleShowGridSize(string module, string[] cmd) | ||
813 | { | ||
814 | List<RegionData> regions = m_Database.Get(int.MinValue, int.MinValue, int.MaxValue, int.MaxValue, UUID.Zero); | ||
815 | |||
816 | double size = 0; | ||
817 | |||
818 | foreach (RegionData region in regions) | ||
819 | { | ||
820 | int flags = Convert.ToInt32(region.Data["flags"]); | ||
821 | |||
822 | if ((flags & (int)Framework.RegionFlags.Hyperlink) == 0) | ||
823 | size += region.sizeX * region.sizeY; | ||
824 | } | ||
825 | |||
826 | MainConsole.Instance.Output("This is a very rough approximation."); | ||
827 | MainConsole.Instance.Output("Although it will not count regions that are actually links to others over the Hypergrid, "); | ||
828 | MainConsole.Instance.Output("it will count regions that are inactive but were not deregistered from the grid service"); | ||
829 | MainConsole.Instance.Output("(e.g. simulator crashed rather than shutting down cleanly).\n"); | ||
830 | |||
831 | MainConsole.Instance.OutputFormat("Grid size: {0} km squared.", size / 1000000); | ||
832 | } | ||
578 | 833 | ||
579 | private void HandleShowRegion(string module, string[] cmd) | 834 | private void HandleShowRegion(string module, string[] cmd) |
580 | { | 835 | { |
@@ -586,7 +841,7 @@ namespace OpenSim.Services.GridService | |||
586 | 841 | ||
587 | string regionName = cmd[3]; | 842 | string regionName = cmd[3]; |
588 | 843 | ||
589 | List<RegionData> regions = m_Database.Get(regionName, UUID.Zero); | 844 | List<RegionData> regions = m_Database.Get(Util.EscapeForLike(regionName), UUID.Zero); |
590 | if (regions == null || regions.Count < 1) | 845 | if (regions == null || regions.Count < 1) |
591 | { | 846 | { |
592 | MainConsole.Instance.Output("No region with name {0} found", regionName); | 847 | MainConsole.Instance.Output("No region with name {0} found", regionName); |
@@ -604,20 +859,20 @@ namespace OpenSim.Services.GridService | |||
604 | return; | 859 | return; |
605 | } | 860 | } |
606 | 861 | ||
607 | int x, y; | 862 | uint x, y; |
608 | if (!int.TryParse(cmd[3], out x)) | 863 | if (!uint.TryParse(cmd[3], out x)) |
609 | { | 864 | { |
610 | MainConsole.Instance.Output("x-coord must be an integer"); | 865 | MainConsole.Instance.Output("x-coord must be an integer"); |
611 | return; | 866 | return; |
612 | } | 867 | } |
613 | 868 | ||
614 | if (!int.TryParse(cmd[4], out y)) | 869 | if (!uint.TryParse(cmd[4], out y)) |
615 | { | 870 | { |
616 | MainConsole.Instance.Output("y-coord must be an integer"); | 871 | MainConsole.Instance.Output("y-coord must be an integer"); |
617 | return; | 872 | return; |
618 | } | 873 | } |
619 | 874 | ||
620 | RegionData region = m_Database.Get(x * (int)Constants.RegionSize, y * (int)Constants.RegionSize, UUID.Zero); | 875 | RegionData region = m_Database.Get((int)Util.RegionToWorldLoc(x), (int)Util.RegionToWorldLoc(y), UUID.Zero); |
621 | if (region == null) | 876 | if (region == null) |
622 | { | 877 | { |
623 | MainConsole.Instance.OutputFormat("No region found at {0},{1}", x, y); | 878 | MainConsole.Instance.OutputFormat("No region found at {0},{1}", x, y); |
@@ -634,7 +889,8 @@ namespace OpenSim.Services.GridService | |||
634 | ConsoleDisplayList dispList = new ConsoleDisplayList(); | 889 | ConsoleDisplayList dispList = new ConsoleDisplayList(); |
635 | dispList.AddRow("Region Name", r.RegionName); | 890 | dispList.AddRow("Region Name", r.RegionName); |
636 | dispList.AddRow("Region ID", r.RegionID); | 891 | dispList.AddRow("Region ID", r.RegionID); |
637 | dispList.AddRow("Location", string.Format("{0},{1}", r.coordX, r.coordY)); | 892 | dispList.AddRow("Position", string.Format("{0},{1}", r.coordX, r.coordY)); |
893 | dispList.AddRow("Size", string.Format("{0}x{1}", r.sizeX, r.sizeY)); | ||
638 | dispList.AddRow("URI", r.Data["serverURI"]); | 894 | dispList.AddRow("URI", r.Data["serverURI"]); |
639 | dispList.AddRow("Owner ID", r.Data["owner_uuid"]); | 895 | dispList.AddRow("Owner ID", r.Data["owner_uuid"]); |
640 | dispList.AddRow("Flags", flags); | 896 | dispList.AddRow("Flags", flags); |
@@ -651,10 +907,10 @@ namespace OpenSim.Services.GridService | |||
651 | private void OutputRegionsToConsoleSummary(List<RegionData> regions) | 907 | private void OutputRegionsToConsoleSummary(List<RegionData> regions) |
652 | { | 908 | { |
653 | ConsoleDisplayTable dispTable = new ConsoleDisplayTable(); | 909 | ConsoleDisplayTable dispTable = new ConsoleDisplayTable(); |
654 | dispTable.AddColumn("Name", 16); | 910 | dispTable.AddColumn("Name", 44); |
655 | dispTable.AddColumn("ID", 36); | 911 | dispTable.AddColumn("ID", 36); |
656 | dispTable.AddColumn("Position", 11); | 912 | dispTable.AddColumn("Position", 11); |
657 | dispTable.AddColumn("Owner ID", 36); | 913 | dispTable.AddColumn("Size", 11); |
658 | dispTable.AddColumn("Flags", 60); | 914 | dispTable.AddColumn("Flags", 60); |
659 | 915 | ||
660 | foreach (RegionData r in regions) | 916 | foreach (RegionData r in regions) |
@@ -664,7 +920,7 @@ namespace OpenSim.Services.GridService | |||
664 | r.RegionName, | 920 | r.RegionName, |
665 | r.RegionID.ToString(), | 921 | r.RegionID.ToString(), |
666 | string.Format("{0},{1}", r.coordX, r.coordY), | 922 | string.Format("{0},{1}", r.coordX, r.coordY), |
667 | r.Data["owner_uuid"].ToString(), | 923 | string.Format("{0}x{1}", r.sizeX, r.sizeY), |
668 | flags.ToString()); | 924 | flags.ToString()); |
669 | } | 925 | } |
670 | 926 | ||
@@ -716,7 +972,7 @@ namespace OpenSim.Services.GridService | |||
716 | return; | 972 | return; |
717 | } | 973 | } |
718 | 974 | ||
719 | List<RegionData> regions = m_Database.Get(cmd[3], UUID.Zero); | 975 | List<RegionData> regions = m_Database.Get(Util.EscapeForLike(cmd[3]), UUID.Zero); |
720 | if (regions == null || regions.Count < 1) | 976 | if (regions == null || regions.Count < 1) |
721 | { | 977 | { |
722 | MainConsole.Instance.Output("Region not found"); | 978 | MainConsole.Instance.Output("Region not found"); |
@@ -734,5 +990,18 @@ namespace OpenSim.Services.GridService | |||
734 | m_Database.Store(r); | 990 | m_Database.Store(r); |
735 | } | 991 | } |
736 | } | 992 | } |
993 | |||
994 | /// <summary> | ||
995 | /// Gets the grid extra service URls we wish for the region to send in OpenSimExtras to dynamically refresh | ||
996 | /// parameters in the viewer used to access services like map, search and destination guides. | ||
997 | /// <para>see "SimulatorFeaturesModule" </para> | ||
998 | /// </summary> | ||
999 | /// <returns> | ||
1000 | /// The grid extra service URls. | ||
1001 | /// </returns> | ||
1002 | public Dictionary<string,object> GetExtraFeatures() | ||
1003 | { | ||
1004 | return m_ExtraFeatures; | ||
1005 | } | ||
737 | } | 1006 | } |
738 | } | 1007 | } |