/// <summary> /// Remove an item from one of the queues. Specifically, it removes the /// oldest item from the next queue in order to provide fair access to /// all of the queues /// </summary> public bool TryDequeue(out EntityUpdate value, out Int32 timeinqueue) { // If there is anything in imediate queues, return it first no // matter what else. Breaks fairness. But very useful. for (int iq = 0; iq < NumberOfImmediateQueues; iq++) { if (m_heaps[iq].Count > 0) { MinHeapItem item = m_heaps[iq].RemoveMin(); m_lookupTable.Remove(item.Value.Entity.LocalId); timeinqueue = Util.EnvironmentTickCountSubtract(item.EntryTime); value = item.Value; return true; } } // To get the fair queing, we cycle through each of the // queues when finding an element to dequeue. // We pull (NumberOfQueues - QueueIndex) items from each queue in order // to give lower numbered queues a higher priority and higher percentage // of the bandwidth. // Check for more items to be pulled from the current queue if (m_heaps[m_nextQueue].Count > 0 && m_countFromQueue > 0) { m_countFromQueue--; MinHeapItem item = m_heaps[m_nextQueue].RemoveMin(); m_lookupTable.Remove(item.Value.Entity.LocalId); timeinqueue = Util.EnvironmentTickCountSubtract(item.EntryTime); value = item.Value; return true; } // Find the next non-immediate queue with updates in it for (uint i = NumberOfImmediateQueues; i < NumberOfQueues; ++i) { m_nextQueue++; if(m_nextQueue >= NumberOfQueues) m_nextQueue = NumberOfImmediateQueues; m_countFromQueue = m_queueCounts[m_nextQueue]; if (m_heaps[m_nextQueue].Count > 0) { m_countFromQueue--; MinHeapItem item = m_heaps[m_nextQueue].RemoveMin(); m_lookupTable.Remove(item.Value.Entity.LocalId); timeinqueue = Util.EnvironmentTickCountSubtract(item.EntryTime); value = item.Value; return true; } } timeinqueue = 0; value = default(EntityUpdate); return false; }
/// <summary> /// Process the velocity of this context /// </summary> /// <param name="key"></param> /// <param name="endpoint"></param> /// <returns></returns> public bool Process(string key, string endpoint) { if (_options.MaxRequestsInTimeframe < 1 || _options.RequestTimeSpan.TotalMilliseconds < 1) { return(true); } string clientstring = key; _blockLockSlim.EnterReadLock(); if (_tempBlocked.ContainsKey(clientstring)) { _blockLockSlim.ExitReadLock(); if (_options.ThrottledAction == ThrottleAction.DoThrottledMethod) { return(false); } else { throw new System.Security.SecurityException("Throttled"); } } _blockLockSlim.ExitReadLock(); lock (_generalRequestTimes) _generalRequestTimes.Put(Util.EnvironmentTickCount()); if (_options.MaxConcurrentSessions > 0) { int sessionscount = 0; _sessionLockSlim.EnterReadLock(); if (_sessions.ContainsKey(key)) { sessionscount = _sessions[key]; } _sessionLockSlim.ExitReadLock(); if (sessionscount > _options.MaxConcurrentSessions) { // Add to blocking and cleanup methods lock (_deeperInspection) { _blockLockSlim.EnterWriteLock(); if (!_tempBlocked.ContainsKey(clientstring)) { _tempBlocked.Add(clientstring, Util.EnvironmentTickCount() + (int)_options.ForgetTimeSpan.TotalMilliseconds); _forgetTimer.Enabled = true; m_log.WarnFormat("[{0}]: client: {1} is blocked for {2} milliseconds based on concurrency, X-ForwardedForAllowed status is {3}, endpoint:{4}", _options.ReportingName, clientstring, _options.ForgetTimeSpan.TotalMilliseconds, _options.AllowXForwardedFor, endpoint); } else { _tempBlocked[clientstring] = Util.EnvironmentTickCount() + (int)_options.ForgetTimeSpan.TotalMilliseconds; } _blockLockSlim.ExitWriteLock(); } } else { ProcessConcurrency(key, endpoint); } } if (_generalRequestTimes.Size == _generalRequestTimes.Capacity && (Util.EnvironmentTickCountSubtract(Util.EnvironmentTickCount(), _generalRequestTimes.Get()) < _options.RequestTimeSpan.TotalMilliseconds)) { //Trigger deeper inspection if (DeeperInspection(key, endpoint)) { return(true); } if (_options.ThrottledAction == ThrottleAction.DoThrottledMethod) { return(false); } else { throw new System.Security.SecurityException("Throttled"); } } return(true); }
public static void MakeRequest <TRequest, TResponse>(string verb, string requestUrl, TRequest obj, Action <TResponse> action, int maxConnections) { int reqnum = WebUtil.RequestNumber++; if (m_log.IsDebugEnabled) { m_log.DebugFormat( "[WEB UTIL]: HTTP OUT {0} AsynchronousRequestObject {1} {2}", reqnum, verb, requestUrl); } int tickstart = Util.EnvironmentTickCount(); int tickdata = 0; Type type = typeof(TRequest); WebRequest request = WebRequest.Create(requestUrl); HttpWebRequest ht = (HttpWebRequest)request; if (maxConnections > 0 && ht.ServicePoint.ConnectionLimit < maxConnections) { ht.ServicePoint.ConnectionLimit = maxConnections; } WebResponse response = null; TResponse deserial = default(TResponse); XmlSerializer deserializer = new XmlSerializer(typeof(TResponse)); request.Method = verb; MemoryStream buffer = null; if (verb == "POST") { request.ContentType = "text/xml"; buffer = new MemoryStream(); XmlWriterSettings settings = new XmlWriterSettings(); settings.Encoding = Encoding.UTF8; using (XmlWriter writer = XmlWriter.Create(buffer, settings)) { XmlSerializer serializer = new XmlSerializer(type); serializer.Serialize(writer, obj); writer.Flush(); } int length = (int)buffer.Length; request.ContentLength = length; request.BeginGetRequestStream(delegate(IAsyncResult res) { Stream requestStream = request.EndGetRequestStream(res); requestStream.Write(buffer.ToArray(), 0, length); requestStream.Close(); // capture how much time was spent writing tickdata = Util.EnvironmentTickCountSubtract(tickstart); request.BeginGetResponse(delegate(IAsyncResult ar) { response = request.EndGetResponse(ar); Stream respStream = null; try { respStream = response.GetResponseStream(); deserial = (TResponse)deserializer.Deserialize( respStream); } catch (System.InvalidOperationException) { } finally { // Let's not close this //buffer.Close(); respStream.Close(); response.Close(); } action(deserial); }, null); }, null); } else { request.BeginGetResponse(delegate(IAsyncResult res2) { try { // If the server returns a 404, this appears to trigger a System.Net.WebException even though that isn't // documented in MSDN response = request.EndGetResponse(res2); Stream respStream = null; try { respStream = response.GetResponseStream(); deserial = (TResponse)deserializer.Deserialize(respStream); } catch (System.InvalidOperationException) { } finally { respStream.Close(); response.Close(); } } catch (WebException e) { if (e.Status == WebExceptionStatus.ProtocolError) { if (e.Response is HttpWebResponse) { using (HttpWebResponse httpResponse = (HttpWebResponse)e.Response) { if (httpResponse.StatusCode != HttpStatusCode.NotFound) { // We don't appear to be handling any other status codes, so log these feailures to that // people don't spend unnecessary hours hunting phantom bugs. m_log.DebugFormat( "[ASYNC REQUEST]: Request {0} {1} failed with unexpected status code {2}", verb, requestUrl, httpResponse.StatusCode); } } } } else { m_log.ErrorFormat( "[ASYNC REQUEST]: Request {0} {1} failed with status {2} and message {3}", verb, requestUrl, e.Status, e.Message); } } catch (Exception e) { m_log.ErrorFormat( "[ASYNC REQUEST]: Request {0} {1} failed with exception {2}{3}", verb, requestUrl, e.Message, e.StackTrace); } // m_log.DebugFormat("[ASYNC REQUEST]: Received {0}", deserial.ToString()); try { action(deserial); } catch (Exception e) { m_log.ErrorFormat( "[ASYNC REQUEST]: Request {0} {1} callback failed with exception {2}{3}", verb, requestUrl, e.Message, e.StackTrace); } }, null); } int tickdiff = Util.EnvironmentTickCountSubtract(tickstart); if (tickdiff > WebUtil.LongCallTime) { string originalRequest = null; if (buffer != null) { originalRequest = Encoding.UTF8.GetString(buffer.ToArray()); if (originalRequest.Length > WebUtil.MaxRequestDiagLength) { originalRequest = originalRequest.Remove(WebUtil.MaxRequestDiagLength); } } m_log.InfoFormat( "[ASYNC REQUEST]: Slow request {0} {1} {2} took {3}ms, {4}ms writing, {5}", reqnum, verb, requestUrl, tickdiff, tickdata, originalRequest); } else if (m_log.IsDebugEnabled) { m_log.DebugFormat( "[WEB UTIL]: HTTP OUT {0} took {1}ms, {2}ms writing", reqnum, tickdiff, tickdata); } }
/// <summary> /// Perform a synchronous REST request. /// </summary> /// <param name="verb"></param> /// <param name="requestUrl"></param> /// <param name="obj"> </param> /// <param name="timeoutsecs"> </param> /// <returns></returns> /// /// <exception cref="System.Net.WebException">Thrown if we encounter a network issue while posting /// the request. You'll want to make sure you deal with this as they're not uncommon</exception> public static string MakeRequest(string verb, string requestUrl, string obj, int timeoutsecs) { int reqnum = WebUtil.RequestNumber++; if (m_log.IsDebugEnabled) { m_log.DebugFormat( "[WEB UTIL]: HTTP OUT {0} SynchronousRestForms {1} {2}", reqnum, verb, requestUrl); } int tickstart = Util.EnvironmentTickCount(); int tickdata = 0; WebRequest request = WebRequest.Create(requestUrl); request.Method = verb; if (timeoutsecs > 0) { request.Timeout = timeoutsecs * 1000; } string respstring = String.Empty; using (MemoryStream buffer = new MemoryStream()) { if ((verb == "POST") || (verb == "PUT")) { request.ContentType = "application/x-www-form-urlencoded"; int length = 0; using (StreamWriter writer = new StreamWriter(buffer)) { writer.Write(obj); writer.Flush(); } length = (int)obj.Length; request.ContentLength = length; // if (m_log.IsDebugEnabled) // WebUtil.LogOutgoingDetail(buffer); Stream requestStream = null; try { requestStream = request.GetRequestStream(); requestStream.Write(buffer.ToArray(), 0, length); } catch (Exception e) { m_log.DebugFormat( "[FORMS]: exception occured {0} {1}: {2}{3}", verb, requestUrl, e.Message, e.StackTrace); } finally { if (requestStream != null) { requestStream.Close(); } // capture how much time was spent writing tickdata = Util.EnvironmentTickCountSubtract(tickstart); } } try { using (WebResponse resp = request.GetResponse()) { if (resp.ContentLength != 0) { Stream respStream = null; try { using (respStream = resp.GetResponseStream()) using (StreamReader reader = new StreamReader(respStream)) respstring = reader.ReadToEnd(); } catch (Exception e) { m_log.DebugFormat( "[FORMS]: Exception occured on receiving {0} {1}: {2}{3}", verb, requestUrl, e.Message, e.StackTrace); } finally { if (respStream != null) { respStream.Close(); } } } } } catch (System.InvalidOperationException) { // This is what happens when there is invalid XML m_log.DebugFormat("[FORMS]: InvalidOperationException on receiving {0} {1}", verb, requestUrl); } } int tickdiff = Util.EnvironmentTickCountSubtract(tickstart); if (tickdiff > WebUtil.LongCallTime) { m_log.InfoFormat( "[FORMS]: Slow request {0} {1} {2} took {3}ms, {4}ms writing, {5}", reqnum, verb, requestUrl, tickdiff, tickdata, obj.Length > WebUtil.MaxRequestDiagLength ? obj.Remove(WebUtil.MaxRequestDiagLength) : obj); } else if (m_log.IsDebugEnabled) { m_log.DebugFormat( "[WEB UTIL]: HTTP OUT {0} took {1}ms, {2}ms writing", reqnum, tickdiff, tickdata); } return(respstring); }
private static OSDMap ServiceFormRequestWorker(string url, NameValueCollection data, int timeout) { int reqnum = RequestNumber++; string method = (data != null && data["RequestMethod"] != null) ? data["RequestMethod"] : "unknown"; if (m_log.IsDebugEnabled) { m_log.DebugFormat( "[WEB UTIL]: HTTP OUT {0} ServiceForm {1} {2} (timeout {3})", reqnum, method, url, timeout); } string errorMessage = "unknown error"; int tickstart = Util.EnvironmentTickCount(); int tickdata = 0; string queryString = null; try { HttpWebRequest request = (HttpWebRequest)HttpWebRequest.Create(url); request.Method = "POST"; request.Timeout = timeout; request.KeepAlive = false; request.MaximumAutomaticRedirections = 10; request.ReadWriteTimeout = timeout / 4; request.Headers[OSHeaderRequestID] = reqnum.ToString(); if (data != null) { queryString = BuildQueryString(data); byte[] buffer = System.Text.Encoding.UTF8.GetBytes(queryString); request.ContentLength = buffer.Length; request.ContentType = "application/x-www-form-urlencoded"; using (Stream requestStream = request.GetRequestStream()) requestStream.Write(buffer, 0, buffer.Length); } // capture how much time was spent writing, this may seem silly // but with the number concurrent requests, this often blocks tickdata = Util.EnvironmentTickCountSubtract(tickstart); using (WebResponse response = request.GetResponse()) { using (Stream responseStream = response.GetResponseStream()) { string responseStr = null; responseStr = responseStream.GetStreamString(); OSD responseOSD = OSDParser.Deserialize(responseStr); if (responseOSD.Type == OSDType.Map) { return((OSDMap)responseOSD); } } } } catch (WebException we) { errorMessage = we.Message; if (we.Status == WebExceptionStatus.ProtocolError) { using (HttpWebResponse webResponse = (HttpWebResponse)we.Response) errorMessage = String.Format("[{0}] {1}", webResponse.StatusCode, webResponse.StatusDescription); } } catch (Exception ex) { errorMessage = ex.Message; } finally { int tickdiff = Util.EnvironmentTickCountSubtract(tickstart); if (tickdiff > LongCallTime) { m_log.InfoFormat( "[WEB UTIL]: Slow ServiceForm request {0} {1} {2} took {3}ms, {4}ms writing, {5}", reqnum, method, url, tickdiff, tickdata, queryString != null ? (queryString.Length > MaxRequestDiagLength) ? queryString.Remove(MaxRequestDiagLength) : queryString : ""); } else if (m_log.IsDebugEnabled) { m_log.DebugFormat( "[WEB UTIL]: HTTP OUT {0} took {1}ms, {2}ms writing", reqnum, tickdiff, tickdata); } } m_log.WarnFormat("[WEB UTIL]: ServiceForm request {0} {1} {2} failed: {2}", reqnum, method, url, errorMessage); return(ErrorResponseMap(errorMessage)); }
private static OSDMap ServiceOSDRequestWorker(string url, OSDMap data, string method, int timeout, bool compressed) { int reqnum = RequestNumber++; if (m_log.IsDebugEnabled) { m_log.DebugFormat( "[WEB UTIL]: HTTP OUT {0} ServiceOSD {1} {2} (timeout {3}, compressed {4})", reqnum, method, url, timeout, compressed); } string errorMessage = "unknown error"; int tickstart = Util.EnvironmentTickCount(); int tickdata = 0; string strBuffer = null; try { HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url); request.Method = method; request.Timeout = timeout; request.KeepAlive = false; request.MaximumAutomaticRedirections = 10; request.ReadWriteTimeout = timeout / 4; request.Headers[OSHeaderRequestID] = reqnum.ToString(); // If there is some input, write it into the request if (data != null) { strBuffer = OSDParser.SerializeJsonString(data); byte[] buffer = System.Text.Encoding.UTF8.GetBytes(strBuffer); if (compressed) { request.ContentType = "application/x-gzip"; using (MemoryStream ms = new MemoryStream()) { using (GZipStream comp = new GZipStream(ms, CompressionMode.Compress)) { comp.Write(buffer, 0, buffer.Length); // We need to close the gzip stream before we write it anywhere // because apparently something important related to gzip compression // gets written on the strteam upon Dispose() } byte[] buf = ms.ToArray(); request.ContentLength = buf.Length; //Count bytes to send using (Stream requestStream = request.GetRequestStream()) requestStream.Write(buf, 0, (int)buf.Length); } } else { request.ContentType = "application/json"; request.ContentLength = buffer.Length; //Count bytes to send using (Stream requestStream = request.GetRequestStream()) requestStream.Write(buffer, 0, buffer.Length); //Send it } } // capture how much time was spent writing, this may seem silly // but with the number concurrent requests, this often blocks tickdata = Util.EnvironmentTickCountSubtract(tickstart); using (WebResponse response = request.GetResponse()) { using (Stream responseStream = response.GetResponseStream()) { string responseStr = null; responseStr = responseStream.GetStreamString(); // m_log.DebugFormat("[WEB UTIL]: <{0}> response is <{1}>",reqnum,responseStr); return(CanonicalizeResults(responseStr)); } } } catch (WebException we) { errorMessage = we.Message; if (we.Status == WebExceptionStatus.ProtocolError) { using (HttpWebResponse webResponse = (HttpWebResponse)we.Response) errorMessage = String.Format("[{0}] {1}", webResponse.StatusCode, webResponse.StatusDescription); } } catch (Exception ex) { errorMessage = ex.Message; } finally { int tickdiff = Util.EnvironmentTickCountSubtract(tickstart); if (tickdiff > LongCallTime) { m_log.InfoFormat( "[WEB UTIL]: Slow ServiceOSD request {0} {1} {2} took {3}ms, {4}ms writing, {5}", reqnum, method, url, tickdiff, tickdata, strBuffer); } else if (m_log.IsDebugEnabled) { m_log.DebugFormat( "[WEB UTIL]: HTTP OUT {0} took {1}ms, {2}ms writing", reqnum, tickdiff, tickdata); } } m_log.DebugFormat( "[WEB UTIL]: ServiceOSD request {0} {1} {2} FAILED: {3}", reqnum, url, method, errorMessage); return(ErrorResponseMap(errorMessage)); }
public static TResponse MakeRequest <TRequest, TResponse>(string verb, string requestUrl, TRequest obj, int pTimeout, int maxConnections) { int reqnum = WebUtil.RequestNumber++; if (m_log.IsDebugEnabled) { m_log.DebugFormat( "[WEB UTIL]: HTTP OUT {0} SynchronousRestObject {1} {2}", reqnum, verb, requestUrl); } int tickstart = Util.EnvironmentTickCount(); int tickdata = 0; Type type = typeof(TRequest); TResponse deserial = default(TResponse); WebRequest request = WebRequest.Create(requestUrl); HttpWebRequest ht = (HttpWebRequest)request; if (maxConnections > 0 && ht.ServicePoint.ConnectionLimit < maxConnections) { ht.ServicePoint.ConnectionLimit = maxConnections; } request.Method = verb; MemoryStream buffer = null; if ((verb == "POST") || (verb == "PUT")) { request.ContentType = "text/xml"; buffer = new MemoryStream(); XmlWriterSettings settings = new XmlWriterSettings(); settings.Encoding = Encoding.UTF8; using (XmlWriter writer = XmlWriter.Create(buffer, settings)) { XmlSerializer serializer = new XmlSerializer(type); serializer.Serialize(writer, obj); writer.Flush(); } int length = (int)buffer.Length; request.ContentLength = length; Stream requestStream = null; try { requestStream = request.GetRequestStream(); requestStream.Write(buffer.ToArray(), 0, length); } catch (Exception e) { m_log.DebugFormat( "[SynchronousRestObjectRequester]: Exception in making request {0} {1}: {2}{3}", verb, requestUrl, e.Message, e.StackTrace); return(deserial); } finally { if (requestStream != null) { requestStream.Close(); } // capture how much time was spent writing tickdata = Util.EnvironmentTickCountSubtract(tickstart); } } try { using (HttpWebResponse resp = (HttpWebResponse)request.GetResponse()) { if (resp.ContentLength != 0) { using (Stream respStream = resp.GetResponseStream()) { XmlSerializer deserializer = new XmlSerializer(typeof(TResponse)); deserial = (TResponse)deserializer.Deserialize(respStream); } } else { m_log.DebugFormat( "[SynchronousRestObjectRequester]: Oops! no content found in response stream from {0} {1}", verb, requestUrl); } } } catch (WebException e) { using (HttpWebResponse hwr = (HttpWebResponse)e.Response) { if (hwr != null && hwr.StatusCode == HttpStatusCode.NotFound) { return(deserial); } else { m_log.ErrorFormat( "[SynchronousRestObjectRequester]: WebException for {0} {1} {2}: {3} {4}", verb, requestUrl, typeof(TResponse).ToString(), e.Message, e.StackTrace); } } } catch (System.InvalidOperationException) { // This is what happens when there is invalid XML m_log.DebugFormat( "[SynchronousRestObjectRequester]: Invalid XML from {0} {1} {2}", verb, requestUrl, typeof(TResponse).ToString()); } catch (Exception e) { m_log.DebugFormat( "[SynchronousRestObjectRequester]: Exception on response from {0} {1}: {2}{3}", verb, requestUrl, e.Message, e.StackTrace); } int tickdiff = Util.EnvironmentTickCountSubtract(tickstart); if (tickdiff > WebUtil.LongCallTime) { string originalRequest = null; if (buffer != null) { originalRequest = Encoding.UTF8.GetString(buffer.ToArray()); if (originalRequest.Length > WebUtil.MaxRequestDiagLength) { originalRequest = originalRequest.Remove(WebUtil.MaxRequestDiagLength); } } m_log.InfoFormat( "[SynchronousRestObjectRequester]: Slow request {0} {1} {2} took {3}ms, {4}ms writing, {5}", reqnum, verb, requestUrl, tickdiff, tickdata, originalRequest); } else if (m_log.IsDebugEnabled) { m_log.DebugFormat( "[WEB UTIL]: HTTP OUT {0} took {1}ms, {2}ms writing", reqnum, tickdiff, tickdata); } return(deserial); }
public void SaveLastMapUUID(UUID mapUUID) { lastMapUUID = mapUUID; lastMapRefresh = Util.UnixTimeSinceEpoch().ToString(); }
private void ReadNiniConfig(IConfigSource source, string name) { bool creatingNew = false; if (source.Configs.Count == 0) { MainConsole.Instance.Output("=====================================\n"); MainConsole.Instance.Output("We are now going to ask a couple of questions about your region.\n"); MainConsole.Instance.Output("You can press 'enter' without typing anything to use the default\n"); MainConsole.Instance.Output("the default is displayed between [ ] brackets.\n"); MainConsole.Instance.Output("=====================================\n"); if (name == String.Empty) { while (name.Trim() == string.Empty) { name = MainConsole.Instance.Prompt("New region name", name); if (name.Trim() == string.Empty) { MainConsole.Instance.Output("Cannot interactively create region with no name"); } } } source.AddConfig(name); creatingNew = true; } if (name == String.Empty) { name = source.Configs[0].Name; } if (source.Configs[name] == null) { source.AddConfig(name); } RegionName = name; IConfig config = source.Configs[name]; // Track all of the keys in this config and remove as they are processed // The remaining keys will be added to generic key-value storage for // whoever might need it HashSet <String> allKeys = new HashSet <String>(); foreach (string s in config.GetKeys()) { allKeys.Add(s); } // RegionUUID // allKeys.Remove("RegionUUID"); string regionUUID = config.GetString("RegionUUID", string.Empty); if (!UUID.TryParse(regionUUID.Trim(), out RegionID)) { UUID newID = UUID.Random(); while (RegionID == UUID.Zero) { regionUUID = MainConsole.Instance.Prompt("RegionUUID", newID.ToString()); if (!UUID.TryParse(regionUUID.Trim(), out RegionID)) { MainConsole.Instance.Output("RegionUUID must be a valid UUID"); } } config.Set("RegionUUID", regionUUID); } originRegionID = RegionID; // What IS this?! (Needed for RegionCombinerModule?) // Location // allKeys.Remove("Location"); string location = config.GetString("Location", String.Empty); if (location == String.Empty) { location = MainConsole.Instance.Prompt("Region Location", "1000,1000"); config.Set("Location", location); } string[] locationElements = location.Split(new char[] { ',' }); RegionLocX = Convert.ToUInt32(locationElements[0]); RegionLocY = Convert.ToUInt32(locationElements[1]); // Region size // Default to legacy region size if not specified. allKeys.Remove("SizeX"); string configSizeX = config.GetString("SizeX", Constants.RegionSize.ToString()); config.Set("SizeX", configSizeX); RegionSizeX = Convert.ToUInt32(configSizeX); allKeys.Remove("SizeY"); string configSizeY = config.GetString("SizeY", Constants.RegionSize.ToString()); config.Set("SizeY", configSizeX); RegionSizeY = Convert.ToUInt32(configSizeY); allKeys.Remove("SizeZ"); string configSizeZ = config.GetString("SizeZ", Constants.RegionHeight.ToString()); config.Set("SizeZ", configSizeX); RegionSizeZ = Convert.ToUInt32(configSizeZ); DoRegionSizeSanityChecks(); // InternalAddress // IPAddress address; allKeys.Remove("InternalAddress"); if (config.Contains("InternalAddress")) { address = IPAddress.Parse(config.GetString("InternalAddress", String.Empty)); } else { address = IPAddress.Parse(MainConsole.Instance.Prompt("Internal IP address", "0.0.0.0")); config.Set("InternalAddress", address.ToString()); } // InternalPort // int port; allKeys.Remove("InternalPort"); if (config.Contains("InternalPort")) { port = config.GetInt("InternalPort", 9000); } else { port = Convert.ToInt32(MainConsole.Instance.Prompt("Internal port", "9000")); config.Set("InternalPort", port); } m_internalEndPoint = new IPEndPoint(address, port); // ResolveAddress // allKeys.Remove("ResolveAddress"); if (config.Contains("ResolveAddress")) { m_resolveAddress = config.GetBoolean("ResolveAddress", false); } else { if (creatingNew) { m_resolveAddress = Convert.ToBoolean(MainConsole.Instance.Prompt("Resolve hostname to IP on start (for running inside Docker)", "False")); } config.Set("ResolveAddress", m_resolveAddress.ToString()); } // ExternalHostName // allKeys.Remove("ExternalHostName"); string externalName; if (config.Contains("ExternalHostName")) { externalName = config.GetString("ExternalHostName", "SYSTEMIP"); } else { externalName = MainConsole.Instance.Prompt("External host name", "SYSTEMIP"); config.Set("ExternalHostName", externalName); } if (externalName == "SYSTEMIP") { m_externalHostName = Util.GetLocalHost().ToString(); m_log.InfoFormat( "[REGIONINFO]: Resolving SYSTEMIP to {0} for external hostname of region {1}", m_externalHostName, name); } else if (!m_resolveAddress) { m_externalHostName = externalName; } else { IPAddress[] addrs = Dns.GetHostAddresses(externalName); if (addrs.Length != 1) // If it is ambiguous or not resolveable, use it literally { m_externalHostName = externalName; } else { m_externalHostName = addrs[0].ToString(); } } // RegionType m_regionType = config.GetString("RegionType", String.Empty); allKeys.Remove("RegionType"); // Get Default Landing Location (Defaults to 128,128) string temp_location = config.GetString("DefaultLanding", "<128, 128, 30>"); Vector3 temp_vector; if (Vector3.TryParse(temp_location, out temp_vector)) { DefaultLandingPoint = temp_vector; } else { m_log.ErrorFormat("[RegionInfo]: Unable to parse DefaultLanding for '{0}'. The value given was '{1}'", RegionName, temp_location); } allKeys.Remove("DefaultLanding"); DoDefaultLandingSanityChecks(); #region Access Restrictions m_disallowResidents = config.GetBoolean("DisallowResidents", false); allKeys.Remove("DisallowResidents"); m_disallowForeigners = config.GetBoolean("DisallowForeigners", false); allKeys.Remove("DisallowForeigners"); #endregion #region Prim and map stuff m_nonphysPrimMin = config.GetFloat("NonPhysicalPrimMin", 0); allKeys.Remove("NonPhysicalPrimMin"); m_nonphysPrimMax = config.GetInt("NonPhysicalPrimMax", 0); allKeys.Remove("NonPhysicalPrimMax"); m_physPrimMin = config.GetFloat("PhysicalPrimMin", 0); allKeys.Remove("PhysicalPrimMin"); m_physPrimMax = config.GetInt("PhysicalPrimMax", 0); allKeys.Remove("PhysicalPrimMax"); m_clampPrimSize = config.GetBoolean("ClampPrimSize", false); allKeys.Remove("ClampPrimSize"); m_objectCapacity = config.GetInt("MaxPrims", m_objectCapacity); allKeys.Remove("MaxPrims"); m_maxPrimsPerUser = config.GetInt("MaxPrimsPerUser", -1); allKeys.Remove("MaxPrimsPerUser"); m_linksetCapacity = config.GetInt("LinksetPrims", 0); allKeys.Remove("LinksetPrims"); allKeys.Remove("MaptileStaticUUID"); string mapTileStaticUUID = config.GetString("MaptileStaticUUID", UUID.Zero.ToString()); if (UUID.TryParse(mapTileStaticUUID.Trim(), out m_maptileStaticUUID)) { config.Set("MaptileStaticUUID", m_maptileStaticUUID.ToString()); } MaptileStaticFile = config.GetString("MaptileStaticFile", String.Empty); allKeys.Remove("MaptileStaticFile"); #endregion AgentCapacity = config.GetInt("MaxAgents", 100); allKeys.Remove("MaxAgents"); // Multi-tenancy // ScopeID = new UUID(config.GetString("ScopeID", UUID.Zero.ToString())); allKeys.Remove("ScopeID"); foreach (String s in allKeys) { SetExtraSetting(s, config.GetString(s)); } }