diff options
Diffstat (limited to 'OpenSim/Framework/Servers')
27 files changed, 951 insertions, 513 deletions
diff --git a/OpenSim/Framework/Servers/BaseOpenSimServer.cs b/OpenSim/Framework/Servers/BaseOpenSimServer.cs index 5ce978e..81dd357 100644 --- a/OpenSim/Framework/Servers/BaseOpenSimServer.cs +++ b/OpenSim/Framework/Servers/BaseOpenSimServer.cs | |||
@@ -65,11 +65,12 @@ namespace OpenSim.Framework.Servers | |||
65 | /// This will control a periodic log printout of the current 'show stats' (if they are active) for this | 65 | /// This will control a periodic log printout of the current 'show stats' (if they are active) for this |
66 | /// server. | 66 | /// server. |
67 | /// </summary> | 67 | /// </summary> |
68 | |||
68 | private int m_periodDiagnosticTimerMS = 60 * 60 * 1000; | 69 | private int m_periodDiagnosticTimerMS = 60 * 60 * 1000; |
69 | private Timer m_periodicDiagnosticsTimer = new Timer(60 * 60 * 1000); | 70 | private Timer m_periodicDiagnosticsTimer = new Timer(60 * 60 * 1000); |
70 | 71 | ||
71 | /// <summary> | 72 | /// <summary> |
72 | /// Random uuid for private data | 73 | /// Random uuid for private data |
73 | /// </summary> | 74 | /// </summary> |
74 | protected string m_osSecret = String.Empty; | 75 | protected string m_osSecret = String.Empty; |
75 | 76 | ||
@@ -83,9 +84,8 @@ namespace OpenSim.Framework.Servers | |||
83 | { | 84 | { |
84 | // Random uuid for private data | 85 | // Random uuid for private data |
85 | m_osSecret = UUID.Random().ToString(); | 86 | m_osSecret = UUID.Random().ToString(); |
86 | |||
87 | } | 87 | } |
88 | 88 | ||
89 | /// <summary> | 89 | /// <summary> |
90 | /// Must be overriden by child classes for their own server specific startup behaviour. | 90 | /// Must be overriden by child classes for their own server specific startup behaviour. |
91 | /// </summary> | 91 | /// </summary> |
@@ -104,26 +104,33 @@ namespace OpenSim.Framework.Servers | |||
104 | m_periodicDiagnosticsTimer.Interval = m_periodDiagnosticTimerMS; | 104 | m_periodicDiagnosticsTimer.Interval = m_periodDiagnosticTimerMS; |
105 | m_periodicDiagnosticsTimer.Enabled = true; | 105 | m_periodicDiagnosticsTimer.Enabled = true; |
106 | } | 106 | } |
107 | } | 107 | } |
108 | 108 | ||
109 | protected override void ShutdownSpecific() | 109 | protected override void ShutdownSpecific() |
110 | { | 110 | { |
111 | m_log.Info("[SHUTDOWN]: Shutdown processing on main thread complete. Exiting..."); | 111 | Watchdog.Enabled = false; |
112 | base.ShutdownSpecific(); | ||
113 | |||
114 | MainServer.Stop(); | ||
115 | |||
116 | Thread.Sleep(5000); | ||
117 | Util.StopThreadPool(); | ||
118 | WorkManager.Stop(); | ||
112 | 119 | ||
120 | Thread.Sleep(1000); | ||
113 | RemovePIDFile(); | 121 | RemovePIDFile(); |
114 | 122 | ||
115 | base.ShutdownSpecific(); | 123 | m_log.Info("[SHUTDOWN]: Shutdown processing on main thread complete. Exiting..."); |
116 | 124 | ||
117 | if (!SuppressExit) | 125 | if (!SuppressExit) |
118 | System.Diagnostics.Process.GetCurrentProcess().Kill(); | 126 | Environment.Exit(0); |
119 | //// Environment.Exit(0); | ||
120 | } | 127 | } |
121 | 128 | ||
122 | /// <summary> | 129 | /// <summary> |
123 | /// Provides a list of help topics that are available. Overriding classes should append their topics to the | 130 | /// Provides a list of help topics that are available. Overriding classes should append their topics to the |
124 | /// information returned when the base method is called. | 131 | /// information returned when the base method is called. |
125 | /// </summary> | 132 | /// </summary> |
126 | /// | 133 | /// |
127 | /// <returns> | 134 | /// <returns> |
128 | /// A list of strings that represent different help topics on which more information is available | 135 | /// A list of strings that represent different help topics on which more information is available |
129 | /// </returns> | 136 | /// </returns> |
@@ -147,20 +154,38 @@ namespace OpenSim.Framework.Servers | |||
147 | /// Performs initialisation of the scene, such as loading configuration from disk. | 154 | /// Performs initialisation of the scene, such as loading configuration from disk. |
148 | /// </summary> | 155 | /// </summary> |
149 | public virtual void Startup() | 156 | public virtual void Startup() |
150 | { | 157 | { |
151 | StartupSpecific(); | 158 | m_log.Info("[STARTUP]: Beginning startup processing"); |
152 | 159 | ||
160 | m_log.Info("[STARTUP]: version: " + m_version + Environment.NewLine); | ||
161 | // clr version potentially is more confusing than helpful, since it doesn't tell us if we're running under Mono/MS .NET and | ||
162 | // the clr version number doesn't match the project version number under Mono. | ||
163 | //m_log.Info("[STARTUP]: Virtual machine runtime version: " + Environment.Version + Environment.NewLine); | ||
164 | m_log.InfoFormat( | ||
165 | "[STARTUP]: Operating system version: {0}, .NET platform {1}, {2}-bit\n", | ||
166 | Environment.OSVersion, Environment.OSVersion.Platform, Util.Is64BitProcess() ? "64" : "32"); | ||
167 | |||
168 | try | ||
169 | { | ||
170 | StartupSpecific(); | ||
171 | } | ||
172 | catch(Exception e) | ||
173 | { | ||
174 | m_log.Fatal("Fatal error: " + e.ToString()); | ||
175 | Environment.Exit(1); | ||
176 | } | ||
177 | |||
153 | TimeSpan timeTaken = DateTime.Now - m_startuptime; | 178 | TimeSpan timeTaken = DateTime.Now - m_startuptime; |
154 | 179 | ||
155 | MainConsole.Instance.OutputFormat( | 180 | // MainConsole.Instance.OutputFormat( |
156 | "PLEASE WAIT FOR LOGINS TO BE ENABLED ON REGIONS ONCE SCRIPTS HAVE STARTED. Non-script portion of startup took {0}m {1}s.", | 181 | // "PLEASE WAIT FOR LOGINS TO BE ENABLED ON REGIONS ONCE SCRIPTS HAVE STARTED. Non-script portion of startup took {0}m {1}s.", |
157 | timeTaken.Minutes, timeTaken.Seconds); | 182 | // timeTaken.Minutes, timeTaken.Seconds); |
158 | } | 183 | } |
159 | 184 | ||
160 | public string osSecret | 185 | public string osSecret |
161 | { | 186 | { |
162 | // Secret uuid for the simulator | 187 | // Secret uuid for the simulator |
163 | get { return m_osSecret; } | 188 | get { return m_osSecret; } |
164 | } | 189 | } |
165 | 190 | ||
166 | public string StatReport(IOSHttpRequest httpRequest) | 191 | public string StatReport(IOSHttpRequest httpRequest) |
@@ -169,8 +194,8 @@ namespace OpenSim.Framework.Servers | |||
169 | if (httpRequest.Query.ContainsKey("callback")) | 194 | if (httpRequest.Query.ContainsKey("callback")) |
170 | { | 195 | { |
171 | return httpRequest.Query["callback"].ToString() + "(" + StatsManager.SimExtraStats.XReport((DateTime.Now - m_startuptime).ToString() , m_version) + ");"; | 196 | return httpRequest.Query["callback"].ToString() + "(" + StatsManager.SimExtraStats.XReport((DateTime.Now - m_startuptime).ToString() , m_version) + ");"; |
172 | } | 197 | } |
173 | else | 198 | else |
174 | { | 199 | { |
175 | return StatsManager.SimExtraStats.XReport((DateTime.Now - m_startuptime).ToString() , m_version); | 200 | return StatsManager.SimExtraStats.XReport((DateTime.Now - m_startuptime).ToString() , m_version); |
176 | } | 201 | } |
diff --git a/OpenSim/Framework/Servers/HttpServer/BaseHttpServer.cs b/OpenSim/Framework/Servers/HttpServer/BaseHttpServer.cs index f252bd5..f4ba02f 100644 --- a/OpenSim/Framework/Servers/HttpServer/BaseHttpServer.cs +++ b/OpenSim/Framework/Servers/HttpServer/BaseHttpServer.cs | |||
@@ -58,7 +58,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
58 | 58 | ||
59 | /// <summary> | 59 | /// <summary> |
60 | /// This is a pending websocket request before it got an sucessful upgrade response. | 60 | /// This is a pending websocket request before it got an sucessful upgrade response. |
61 | /// The consumer must call handler.HandshakeAndUpgrade() to signal to the handler to | 61 | /// The consumer must call handler.HandshakeAndUpgrade() to signal to the handler to |
62 | /// start the connection and optionally provide an origin authentication method. | 62 | /// start the connection and optionally provide an origin authentication method. |
63 | /// </summary> | 63 | /// </summary> |
64 | /// <param name="servicepath"></param> | 64 | /// <param name="servicepath"></param> |
@@ -104,7 +104,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
104 | new Dictionary<string, PollServiceEventArgs>(); | 104 | new Dictionary<string, PollServiceEventArgs>(); |
105 | 105 | ||
106 | protected Dictionary<string, WebSocketRequestDelegate> m_WebSocketHandlers = | 106 | protected Dictionary<string, WebSocketRequestDelegate> m_WebSocketHandlers = |
107 | new Dictionary<string, WebSocketRequestDelegate>(); | 107 | new Dictionary<string, WebSocketRequestDelegate>(); |
108 | 108 | ||
109 | protected uint m_port; | 109 | protected uint m_port; |
110 | protected uint m_sslport; | 110 | protected uint m_sslport; |
@@ -253,7 +253,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
253 | return new List<string>(m_rpcHandlers.Keys); | 253 | return new List<string>(m_rpcHandlers.Keys); |
254 | } | 254 | } |
255 | 255 | ||
256 | // JsonRPC | 256 | // JsonRPC |
257 | public bool AddJsonRPCHandler(string method, JsonRPCMethod handler) | 257 | public bool AddJsonRPCHandler(string method, JsonRPCMethod handler) |
258 | { | 258 | { |
259 | lock(jsonRpcHandlers) | 259 | lock(jsonRpcHandlers) |
@@ -399,10 +399,10 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
399 | 399 | ||
400 | Stream requestStream = req.InputStream; | 400 | Stream requestStream = req.InputStream; |
401 | 401 | ||
402 | string requestBody; | ||
402 | Encoding encoding = Encoding.UTF8; | 403 | Encoding encoding = Encoding.UTF8; |
403 | StreamReader reader = new StreamReader(requestStream, encoding); | 404 | using(StreamReader reader = new StreamReader(requestStream, encoding)) |
404 | 405 | requestBody = reader.ReadToEnd(); | |
405 | string requestBody = reader.ReadToEnd(); | ||
406 | 406 | ||
407 | Hashtable keysvals = new Hashtable(); | 407 | Hashtable keysvals = new Hashtable(); |
408 | Hashtable headervals = new Hashtable(); | 408 | Hashtable headervals = new Hashtable(); |
@@ -458,10 +458,11 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
458 | dWebSocketRequestDelegate(req.Url.AbsolutePath, new WebSocketHttpServerHandler(req, context, 8192)); | 458 | dWebSocketRequestDelegate(req.Url.AbsolutePath, new WebSocketHttpServerHandler(req, context, 8192)); |
459 | return; | 459 | return; |
460 | } | 460 | } |
461 | 461 | ||
462 | OSHttpResponse resp = new OSHttpResponse(new HttpResponse(context, request),context); | 462 | OSHttpResponse resp = new OSHttpResponse(new HttpResponse(context, request),context); |
463 | resp.ReuseContext = true; | 463 | resp.ReuseContext = true; |
464 | HandleRequest(req, resp); | 464 | // resp.ReuseContext = false; |
465 | HandleRequest(req, resp); | ||
465 | 466 | ||
466 | // !!!HACK ALERT!!! | 467 | // !!!HACK ALERT!!! |
467 | // There seems to be a bug in the underlying http code that makes subsequent requests | 468 | // There seems to be a bug in the underlying http code that makes subsequent requests |
@@ -552,7 +553,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
552 | LogIncomingToStreamHandler(request, requestHandler); | 553 | LogIncomingToStreamHandler(request, requestHandler); |
553 | 554 | ||
554 | response.ContentType = requestHandler.ContentType; // Lets do this defaulting before in case handler has varying content type. | 555 | response.ContentType = requestHandler.ContentType; // Lets do this defaulting before in case handler has varying content type. |
555 | 556 | ||
556 | if (requestHandler is IStreamedRequestHandler) | 557 | if (requestHandler is IStreamedRequestHandler) |
557 | { | 558 | { |
558 | IStreamedRequestHandler streamedRequestHandler = requestHandler as IStreamedRequestHandler; | 559 | IStreamedRequestHandler streamedRequestHandler = requestHandler as IStreamedRequestHandler; |
@@ -565,13 +566,10 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
565 | IGenericHTTPHandler HTTPRequestHandler = requestHandler as IGenericHTTPHandler; | 566 | IGenericHTTPHandler HTTPRequestHandler = requestHandler as IGenericHTTPHandler; |
566 | Stream requestStream = request.InputStream; | 567 | Stream requestStream = request.InputStream; |
567 | 568 | ||
569 | string requestBody; | ||
568 | Encoding encoding = Encoding.UTF8; | 570 | Encoding encoding = Encoding.UTF8; |
569 | StreamReader reader = new StreamReader(requestStream, encoding); | 571 | using(StreamReader reader = new StreamReader(requestStream, encoding)) |
570 | 572 | requestBody = reader.ReadToEnd(); | |
571 | string requestBody = reader.ReadToEnd(); | ||
572 | |||
573 | reader.Close(); | ||
574 | //requestStream.Close(); | ||
575 | 573 | ||
576 | Hashtable keysvals = new Hashtable(); | 574 | Hashtable keysvals = new Hashtable(); |
577 | Hashtable headervals = new Hashtable(); | 575 | Hashtable headervals = new Hashtable(); |
@@ -628,16 +626,16 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
628 | case "text/html": | 626 | case "text/html": |
629 | if (DebugLevel >= 3) | 627 | if (DebugLevel >= 3) |
630 | LogIncomingToContentTypeHandler(request); | 628 | LogIncomingToContentTypeHandler(request); |
631 | 629 | ||
632 | buffer = HandleHTTPRequest(request, response); | 630 | buffer = HandleHTTPRequest(request, response); |
633 | break; | 631 | break; |
634 | 632 | ||
635 | case "application/llsd+xml": | 633 | case "application/llsd+xml": |
636 | case "application/xml+llsd": | 634 | case "application/xml+llsd": |
637 | case "application/llsd+json": | 635 | case "application/llsd+json": |
638 | if (DebugLevel >= 3) | 636 | if (DebugLevel >= 3) |
639 | LogIncomingToContentTypeHandler(request); | 637 | LogIncomingToContentTypeHandler(request); |
640 | 638 | ||
641 | buffer = HandleLLSDRequests(request, response); | 639 | buffer = HandleLLSDRequests(request, response); |
642 | break; | 640 | break; |
643 | 641 | ||
@@ -647,7 +645,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
647 | 645 | ||
648 | buffer = HandleJsonRpcRequests(request, response); | 646 | buffer = HandleJsonRpcRequests(request, response); |
649 | break; | 647 | break; |
650 | 648 | ||
651 | case "text/xml": | 649 | case "text/xml": |
652 | case "application/xml": | 650 | case "application/xml": |
653 | case "application/json": | 651 | case "application/json": |
@@ -664,7 +662,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
664 | { | 662 | { |
665 | if (DebugLevel >= 3) | 663 | if (DebugLevel >= 3) |
666 | LogIncomingToContentTypeHandler(request); | 664 | LogIncomingToContentTypeHandler(request); |
667 | 665 | ||
668 | buffer = HandleLLSDRequests(request, response); | 666 | buffer = HandleLLSDRequests(request, response); |
669 | } | 667 | } |
670 | // m_log.DebugFormat("[BASE HTTP SERVER]: Checking for HTTP Handler for request {0}", request.RawUrl); | 668 | // m_log.DebugFormat("[BASE HTTP SERVER]: Checking for HTTP Handler for request {0}", request.RawUrl); |
@@ -672,23 +670,24 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
672 | { | 670 | { |
673 | if (DebugLevel >= 3) | 671 | if (DebugLevel >= 3) |
674 | LogIncomingToContentTypeHandler(request); | 672 | LogIncomingToContentTypeHandler(request); |
675 | 673 | ||
676 | buffer = HandleHTTPRequest(request, response); | 674 | buffer = HandleHTTPRequest(request, response); |
677 | } | 675 | } |
678 | else | 676 | else |
679 | { | 677 | { |
680 | if (DebugLevel >= 3) | 678 | if (DebugLevel >= 3) |
681 | LogIncomingToXmlRpcHandler(request); | 679 | LogIncomingToXmlRpcHandler(request); |
682 | 680 | ||
683 | // generic login request. | 681 | // generic login request. |
684 | buffer = HandleXmlRpcRequests(request, response); | 682 | buffer = HandleXmlRpcRequests(request, response); |
685 | } | 683 | } |
686 | 684 | ||
687 | break; | 685 | break; |
688 | } | 686 | } |
689 | } | 687 | } |
690 | 688 | ||
691 | request.InputStream.Close(); | 689 | if(request.InputStream.CanRead) |
690 | request.InputStream.Dispose(); | ||
692 | 691 | ||
693 | if (buffer != null) | 692 | if (buffer != null) |
694 | { | 693 | { |
@@ -759,7 +758,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
759 | // Every month or so this will wrap and give bad numbers, not really a problem | 758 | // Every month or so this will wrap and give bad numbers, not really a problem |
760 | // since its just for reporting | 759 | // since its just for reporting |
761 | int tickdiff = requestEndTick - requestStartTick; | 760 | int tickdiff = requestEndTick - requestStartTick; |
762 | if (tickdiff > 3000 && requestHandler != null && requestHandler.Name != "GetTexture") | 761 | if (tickdiff > 3000 && (requestHandler == null || requestHandler.Name == null || requestHandler.Name != "GetTexture")) |
763 | { | 762 | { |
764 | m_log.InfoFormat( | 763 | m_log.InfoFormat( |
765 | "[LOGHTTP] Slow handling of {0} {1} {2} {3} {4} from {5} took {6}ms", | 764 | "[LOGHTTP] Slow handling of {0} {1} {2} {3} {4} from {5} took {6}ms", |
@@ -970,7 +969,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
970 | // private bool TryGetAgentHandler(OSHttpRequest request, OSHttpResponse response, out IHttpAgentHandler agentHandler) | 969 | // private bool TryGetAgentHandler(OSHttpRequest request, OSHttpResponse response, out IHttpAgentHandler agentHandler) |
971 | // { | 970 | // { |
972 | // agentHandler = null; | 971 | // agentHandler = null; |
973 | // | 972 | // |
974 | // lock (m_agentHandlers) | 973 | // lock (m_agentHandlers) |
975 | // { | 974 | // { |
976 | // foreach (IHttpAgentHandler handler in m_agentHandlers.Values) | 975 | // foreach (IHttpAgentHandler handler in m_agentHandlers.Values) |
@@ -996,7 +995,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
996 | { | 995 | { |
997 | String requestBody; | 996 | String requestBody; |
998 | 997 | ||
999 | Stream requestStream = request.InputStream; | 998 | Stream requestStream = Util.Copy(request.InputStream); |
1000 | Stream innerStream = null; | 999 | Stream innerStream = null; |
1001 | try | 1000 | try |
1002 | { | 1001 | { |
@@ -1007,9 +1006,8 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1007 | } | 1006 | } |
1008 | 1007 | ||
1009 | using (StreamReader reader = new StreamReader(requestStream, Encoding.UTF8)) | 1008 | using (StreamReader reader = new StreamReader(requestStream, Encoding.UTF8)) |
1010 | { | ||
1011 | requestBody = reader.ReadToEnd(); | 1009 | requestBody = reader.ReadToEnd(); |
1012 | } | 1010 | |
1013 | } | 1011 | } |
1014 | finally | 1012 | finally |
1015 | { | 1013 | { |
@@ -1024,6 +1022,19 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1024 | string responseString = String.Empty; | 1022 | string responseString = String.Empty; |
1025 | XmlRpcRequest xmlRprcRequest = null; | 1023 | XmlRpcRequest xmlRprcRequest = null; |
1026 | 1024 | ||
1025 | bool gridproxy = false; | ||
1026 | if (requestBody.Contains("encoding=\"utf-8")) | ||
1027 | { | ||
1028 | int channelindx = -1; | ||
1029 | int optionsindx = requestBody.IndexOf(">options<"); | ||
1030 | if(optionsindx >0) | ||
1031 | { | ||
1032 | channelindx = requestBody.IndexOf(">channel<"); | ||
1033 | if (optionsindx < channelindx) | ||
1034 | gridproxy = true; | ||
1035 | } | ||
1036 | } | ||
1037 | |||
1027 | try | 1038 | try |
1028 | { | 1039 | { |
1029 | xmlRprcRequest = (XmlRpcRequest) (new XmlRpcRequestDeserializer()).Deserialize(requestBody); | 1040 | xmlRprcRequest = (XmlRpcRequest) (new XmlRpcRequestDeserializer()).Deserialize(requestBody); |
@@ -1081,6 +1092,8 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1081 | } | 1092 | } |
1082 | xmlRprcRequest.Params.Add(request.Headers.Get(xff)); // Param[3] | 1093 | xmlRprcRequest.Params.Add(request.Headers.Get(xff)); // Param[3] |
1083 | 1094 | ||
1095 | if (gridproxy) | ||
1096 | xmlRprcRequest.Params.Add("gridproxy"); // Param[4] | ||
1084 | try | 1097 | try |
1085 | { | 1098 | { |
1086 | xmlRpcResponse = method(xmlRprcRequest, request.RemoteIPEndPoint); | 1099 | xmlRpcResponse = method(xmlRprcRequest, request.RemoteIPEndPoint); |
@@ -1154,7 +1167,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1154 | return buffer; | 1167 | return buffer; |
1155 | } | 1168 | } |
1156 | 1169 | ||
1157 | // JsonRpc (v2.0 only) | 1170 | // JsonRpc (v2.0 only) |
1158 | // Batch requests not yet supported | 1171 | // Batch requests not yet supported |
1159 | private byte[] HandleJsonRpcRequests(OSHttpRequest request, OSHttpResponse response) | 1172 | private byte[] HandleJsonRpcRequests(OSHttpRequest request, OSHttpResponse response) |
1160 | { | 1173 | { |
@@ -1171,7 +1184,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1171 | jsonRpcResponse.Error.Code = ErrorCode.InternalError; | 1184 | jsonRpcResponse.Error.Code = ErrorCode.InternalError; |
1172 | jsonRpcResponse.Error.Message = e.Message; | 1185 | jsonRpcResponse.Error.Message = e.Message; |
1173 | } | 1186 | } |
1174 | 1187 | ||
1175 | requestStream.Close(); | 1188 | requestStream.Close(); |
1176 | 1189 | ||
1177 | if (jsonRpcRequest != null) | 1190 | if (jsonRpcRequest != null) |
@@ -1236,7 +1249,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1236 | string responseData = string.Empty; | 1249 | string responseData = string.Empty; |
1237 | 1250 | ||
1238 | responseData = jsonRpcResponse.Serialize(); | 1251 | responseData = jsonRpcResponse.Serialize(); |
1239 | 1252 | ||
1240 | byte[] buffer = Encoding.UTF8.GetBytes(responseData); | 1253 | byte[] buffer = Encoding.UTF8.GetBytes(responseData); |
1241 | return buffer; | 1254 | return buffer; |
1242 | } | 1255 | } |
@@ -1246,12 +1259,10 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1246 | //m_log.Warn("[BASE HTTP SERVER]: We've figured out it's a LLSD Request"); | 1259 | //m_log.Warn("[BASE HTTP SERVER]: We've figured out it's a LLSD Request"); |
1247 | Stream requestStream = request.InputStream; | 1260 | Stream requestStream = request.InputStream; |
1248 | 1261 | ||
1262 | string requestBody; | ||
1249 | Encoding encoding = Encoding.UTF8; | 1263 | Encoding encoding = Encoding.UTF8; |
1250 | StreamReader reader = new StreamReader(requestStream, encoding); | 1264 | using(StreamReader reader = new StreamReader(requestStream, encoding)) |
1251 | 1265 | requestBody= reader.ReadToEnd(); | |
1252 | string requestBody = reader.ReadToEnd(); | ||
1253 | reader.Close(); | ||
1254 | requestStream.Close(); | ||
1255 | 1266 | ||
1256 | //m_log.DebugFormat("[OGP]: {0}:{1}", request.RawUrl, requestBody); | 1267 | //m_log.DebugFormat("[OGP]: {0}:{1}", request.RawUrl, requestBody); |
1257 | response.KeepAlive = true; | 1268 | response.KeepAlive = true; |
@@ -1516,7 +1527,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1516 | } | 1527 | } |
1517 | } | 1528 | } |
1518 | } | 1529 | } |
1519 | 1530 | ||
1520 | if (String.IsNullOrEmpty(bestMatch)) | 1531 | if (String.IsNullOrEmpty(bestMatch)) |
1521 | { | 1532 | { |
1522 | llsdHandler = null; | 1533 | llsdHandler = null; |
@@ -1575,15 +1586,10 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1575 | byte[] buffer; | 1586 | byte[] buffer; |
1576 | 1587 | ||
1577 | Stream requestStream = request.InputStream; | 1588 | Stream requestStream = request.InputStream; |
1578 | 1589 | string requestBody; | |
1579 | Encoding encoding = Encoding.UTF8; | 1590 | Encoding encoding = Encoding.UTF8; |
1580 | StreamReader reader = new StreamReader(requestStream, encoding); | 1591 | using(StreamReader reader = new StreamReader(requestStream, encoding)) |
1581 | 1592 | requestBody = reader.ReadToEnd(); | |
1582 | string requestBody = reader.ReadToEnd(); | ||
1583 | // avoid warning for now | ||
1584 | reader.ReadToEnd(); | ||
1585 | reader.Close(); | ||
1586 | requestStream.Close(); | ||
1587 | 1593 | ||
1588 | Hashtable keysvals = new Hashtable(); | 1594 | Hashtable keysvals = new Hashtable(); |
1589 | Hashtable headervals = new Hashtable(); | 1595 | Hashtable headervals = new Hashtable(); |
@@ -1732,10 +1738,40 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1732 | 1738 | ||
1733 | internal byte[] DoHTTPGruntWork(Hashtable responsedata, OSHttpResponse response) | 1739 | internal byte[] DoHTTPGruntWork(Hashtable responsedata, OSHttpResponse response) |
1734 | { | 1740 | { |
1735 | //m_log.Info("[BASE HTTP SERVER]: Doing HTTP Grunt work with response"); | 1741 | int responsecode; |
1736 | int responsecode = (int)responsedata["int_response_code"]; | 1742 | string responseString = String.Empty; |
1737 | string responseString = (string)responsedata["str_response_string"]; | 1743 | byte[] responseData = null; |
1738 | string contentType = (string)responsedata["content_type"]; | 1744 | string contentType; |
1745 | |||
1746 | if (responsedata == null) | ||
1747 | { | ||
1748 | responsecode = 500; | ||
1749 | responseString = "No response could be obtained"; | ||
1750 | contentType = "text/plain"; | ||
1751 | responsedata = new Hashtable(); | ||
1752 | } | ||
1753 | else | ||
1754 | { | ||
1755 | try | ||
1756 | { | ||
1757 | //m_log.Info("[BASE HTTP SERVER]: Doing HTTP Grunt work with response"); | ||
1758 | responsecode = (int)responsedata["int_response_code"]; | ||
1759 | if (responsedata["bin_response_data"] != null) | ||
1760 | responseData = (byte[])responsedata["bin_response_data"]; | ||
1761 | else | ||
1762 | responseString = (string)responsedata["str_response_string"]; | ||
1763 | contentType = (string)responsedata["content_type"]; | ||
1764 | if (responseString == null) | ||
1765 | responseString = String.Empty; | ||
1766 | } | ||
1767 | catch | ||
1768 | { | ||
1769 | responsecode = 500; | ||
1770 | responseString = "No response could be obtained"; | ||
1771 | contentType = "text/plain"; | ||
1772 | responsedata = new Hashtable(); | ||
1773 | } | ||
1774 | } | ||
1739 | 1775 | ||
1740 | if (responsedata.ContainsKey("error_status_text")) | 1776 | if (responsedata.ContainsKey("error_status_text")) |
1741 | { | 1777 | { |
@@ -1745,16 +1781,19 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1745 | { | 1781 | { |
1746 | response.ProtocolVersion = (string)responsedata["http_protocol_version"]; | 1782 | response.ProtocolVersion = (string)responsedata["http_protocol_version"]; |
1747 | } | 1783 | } |
1748 | 1784 | /* | |
1749 | if (responsedata.ContainsKey("keepalive")) | 1785 | if (responsedata.ContainsKey("keepalive")) |
1750 | { | 1786 | { |
1751 | bool keepalive = (bool)responsedata["keepalive"]; | 1787 | bool keepalive = (bool)responsedata["keepalive"]; |
1752 | response.KeepAlive = keepalive; | 1788 | response.KeepAlive = keepalive; |
1753 | |||
1754 | } | 1789 | } |
1755 | 1790 | ||
1756 | if (responsedata.ContainsKey("reusecontext")) | 1791 | if (responsedata.ContainsKey("reusecontext")) |
1757 | response.ReuseContext = (bool) responsedata["reusecontext"]; | 1792 | response.ReuseContext = (bool) responsedata["reusecontext"]; |
1793 | */ | ||
1794 | // disable this things | ||
1795 | response.KeepAlive = false; | ||
1796 | response.ReuseContext = false; | ||
1758 | 1797 | ||
1759 | // Cross-Origin Resource Sharing with simple requests | 1798 | // Cross-Origin Resource Sharing with simple requests |
1760 | if (responsedata.ContainsKey("access_control_allow_origin")) | 1799 | if (responsedata.ContainsKey("access_control_allow_origin")) |
@@ -1768,8 +1807,11 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1768 | contentType = "text/html"; | 1807 | contentType = "text/html"; |
1769 | } | 1808 | } |
1770 | 1809 | ||
1810 | |||
1811 | |||
1771 | // The client ignores anything but 200 here for web login, so ensure that this is 200 for that | 1812 | // The client ignores anything but 200 here for web login, so ensure that this is 200 for that |
1772 | 1813 | ||
1814 | |||
1773 | response.StatusCode = responsecode; | 1815 | response.StatusCode = responsecode; |
1774 | 1816 | ||
1775 | if (responsecode == (int)OSHttpStatusCode.RedirectMovedPermanently) | 1817 | if (responsecode == (int)OSHttpStatusCode.RedirectMovedPermanently) |
@@ -1780,25 +1822,40 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1780 | 1822 | ||
1781 | response.AddHeader("Content-Type", contentType); | 1823 | response.AddHeader("Content-Type", contentType); |
1782 | 1824 | ||
1825 | if (responsedata.ContainsKey("headers")) | ||
1826 | { | ||
1827 | Hashtable headerdata = (Hashtable)responsedata["headers"]; | ||
1828 | |||
1829 | foreach (string header in headerdata.Keys) | ||
1830 | response.AddHeader(header, headerdata[header].ToString()); | ||
1831 | } | ||
1832 | |||
1783 | byte[] buffer; | 1833 | byte[] buffer; |
1784 | 1834 | ||
1785 | if (!(contentType.Contains("image") | 1835 | if (responseData != null) |
1786 | || contentType.Contains("x-shockwave-flash") | ||
1787 | || contentType.Contains("application/x-oar") | ||
1788 | || contentType.Contains("application/vnd.ll.mesh"))) | ||
1789 | { | 1836 | { |
1790 | // Text | 1837 | buffer = responseData; |
1791 | buffer = Encoding.UTF8.GetBytes(responseString); | ||
1792 | } | 1838 | } |
1793 | else | 1839 | else |
1794 | { | 1840 | { |
1795 | // Binary! | 1841 | if (!(contentType.Contains("image") |
1796 | buffer = Convert.FromBase64String(responseString); | 1842 | || contentType.Contains("x-shockwave-flash") |
1797 | } | 1843 | || contentType.Contains("application/x-oar") |
1844 | || contentType.Contains("application/vnd.ll.mesh"))) | ||
1845 | { | ||
1846 | // Text | ||
1847 | buffer = Encoding.UTF8.GetBytes(responseString); | ||
1848 | } | ||
1849 | else | ||
1850 | { | ||
1851 | // Binary! | ||
1852 | buffer = Convert.FromBase64String(responseString); | ||
1853 | } | ||
1798 | 1854 | ||
1799 | response.SendChunked = false; | 1855 | response.SendChunked = false; |
1800 | response.ContentLength64 = buffer.Length; | 1856 | response.ContentLength64 = buffer.Length; |
1801 | response.ContentEncoding = Encoding.UTF8; | 1857 | response.ContentEncoding = Encoding.UTF8; |
1858 | } | ||
1802 | 1859 | ||
1803 | return buffer; | 1860 | return buffer; |
1804 | } | 1861 | } |
@@ -1831,8 +1888,8 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1831 | response.SendChunked = false; | 1888 | response.SendChunked = false; |
1832 | response.ContentLength64 = buffer.Length; | 1889 | response.ContentLength64 = buffer.Length; |
1833 | response.ContentEncoding = Encoding.UTF8; | 1890 | response.ContentEncoding = Encoding.UTF8; |
1834 | 1891 | ||
1835 | 1892 | ||
1836 | return buffer; | 1893 | return buffer; |
1837 | } | 1894 | } |
1838 | 1895 | ||
@@ -1886,7 +1943,8 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1886 | m_httpListener2.Start(64); | 1943 | m_httpListener2.Start(64); |
1887 | 1944 | ||
1888 | // Long Poll Service Manager with 3 worker threads a 25 second timeout for no events | 1945 | // Long Poll Service Manager with 3 worker threads a 25 second timeout for no events |
1889 | PollServiceRequestManager = new PollServiceRequestManager(this, performPollResponsesAsync, 3, 25000); | 1946 | |
1947 | PollServiceRequestManager = new PollServiceRequestManager(this, performPollResponsesAsync, 2, 25000); | ||
1890 | PollServiceRequestManager.Start(); | 1948 | PollServiceRequestManager.Start(); |
1891 | 1949 | ||
1892 | HTTPDRunning = true; | 1950 | HTTPDRunning = true; |
@@ -1908,7 +1966,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1908 | throw e; | 1966 | throw e; |
1909 | } | 1967 | } |
1910 | 1968 | ||
1911 | m_requestsProcessedStat | 1969 | m_requestsProcessedStat |
1912 | = new Stat( | 1970 | = new Stat( |
1913 | "HTTPRequestsServed", | 1971 | "HTTPRequestsServed", |
1914 | "Number of inbound HTTP requests processed", | 1972 | "Number of inbound HTTP requests processed", |
@@ -1920,7 +1978,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1920 | MeasuresOfInterest.AverageChangeOverTime, | 1978 | MeasuresOfInterest.AverageChangeOverTime, |
1921 | stat => stat.Value = RequestNumber, | 1979 | stat => stat.Value = RequestNumber, |
1922 | StatVerbosity.Debug); | 1980 | StatVerbosity.Debug); |
1923 | 1981 | ||
1924 | StatsManager.RegisterStat(m_requestsProcessedStat); | 1982 | StatsManager.RegisterStat(m_requestsProcessedStat); |
1925 | } | 1983 | } |
1926 | 1984 | ||
@@ -1937,7 +1995,9 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1937 | 1995 | ||
1938 | public void httpServerException(object source, Exception exception) | 1996 | public void httpServerException(object source, Exception exception) |
1939 | { | 1997 | { |
1940 | m_log.Error(String.Format("[BASE HTTP SERVER]: {0} had an exception: {1} ", source.ToString(), exception.Message), exception); | 1998 | if (source.ToString() == "HttpServer.HttpListener" && exception.ToString().StartsWith("Mono.Security.Protocol.Tls.TlsException")) |
1999 | return; | ||
2000 | m_log.ErrorFormat("[BASE HTTP SERVER]: {0} had an exception {1}", source.ToString(), exception.ToString()); | ||
1941 | /* | 2001 | /* |
1942 | if (HTTPDRunning)// && NotSocketErrors > 5) | 2002 | if (HTTPDRunning)// && NotSocketErrors > 5) |
1943 | { | 2003 | { |
@@ -1957,7 +2017,8 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1957 | 2017 | ||
1958 | try | 2018 | try |
1959 | { | 2019 | { |
1960 | PollServiceRequestManager.Stop(); | 2020 | if(PollServiceRequestManager != null) |
2021 | PollServiceRequestManager.Stop(); | ||
1961 | 2022 | ||
1962 | m_httpListener2.ExceptionThrown -= httpServerException; | 2023 | m_httpListener2.ExceptionThrown -= httpServerException; |
1963 | //m_httpListener2.DisconnectHandler = null; | 2024 | //m_httpListener2.DisconnectHandler = null; |
@@ -1984,6 +2045,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1984 | 2045 | ||
1985 | public void RemoveHTTPHandler(string httpMethod, string path) | 2046 | public void RemoveHTTPHandler(string httpMethod, string path) |
1986 | { | 2047 | { |
2048 | if (path == null) return; // Caps module isn't loaded, tries to remove handler where path = null | ||
1987 | lock (m_HTTPHandlers) | 2049 | lock (m_HTTPHandlers) |
1988 | { | 2050 | { |
1989 | if (httpMethod != null && httpMethod.Length == 0) | 2051 | if (httpMethod != null && httpMethod.Length == 0) |
diff --git a/OpenSim/Framework/Servers/HttpServer/BaseRequestHandler.cs b/OpenSim/Framework/Servers/HttpServer/BaseRequestHandler.cs index d4a1ec3..01d95e9 100644 --- a/OpenSim/Framework/Servers/HttpServer/BaseRequestHandler.cs +++ b/OpenSim/Framework/Servers/HttpServer/BaseRequestHandler.cs | |||
@@ -69,13 +69,13 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
69 | { | 69 | { |
70 | StatsManager.RegisterStat( | 70 | StatsManager.RegisterStat( |
71 | new Stat( | 71 | new Stat( |
72 | "requests", | 72 | "requests", |
73 | "requests", | 73 | "requests", |
74 | "Number of requests received by this service endpoint", | 74 | "Number of requests received by this service endpoint", |
75 | "requests", | 75 | "requests", |
76 | "service", | 76 | "service", |
77 | string.Format("{0}:{1}", httpMethod, path), | 77 | string.Format("{0}:{1}", httpMethod, path), |
78 | StatType.Pull, | 78 | StatType.Pull, |
79 | MeasuresOfInterest.AverageChangeOverTime, | 79 | MeasuresOfInterest.AverageChangeOverTime, |
80 | s => s.Value = RequestsReceived, | 80 | s => s.Value = RequestsReceived, |
81 | StatVerbosity.Debug)); | 81 | StatVerbosity.Debug)); |
diff --git a/OpenSim/Framework/Servers/HttpServer/BaseStreamHandler.cs b/OpenSim/Framework/Servers/HttpServer/BaseStreamHandler.cs index 41aa19b..7fc9f0b 100644 --- a/OpenSim/Framework/Servers/HttpServer/BaseStreamHandler.cs +++ b/OpenSim/Framework/Servers/HttpServer/BaseStreamHandler.cs | |||
@@ -47,7 +47,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
47 | : base(httpMethod, path, name, description) {} | 47 | : base(httpMethod, path, name, description) {} |
48 | 48 | ||
49 | protected BaseStreamHandler(string httpMethod, string path, IServiceAuth auth) | 49 | protected BaseStreamHandler(string httpMethod, string path, IServiceAuth auth) |
50 | : base(httpMethod, path, null, null) | 50 | : base(httpMethod, path, null, null) |
51 | { | 51 | { |
52 | m_Auth = auth; | 52 | m_Auth = auth; |
53 | } | 53 | } |
@@ -62,7 +62,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
62 | HttpStatusCode statusCode; | 62 | HttpStatusCode statusCode; |
63 | 63 | ||
64 | if (!m_Auth.Authenticate(httpRequest.Headers, httpResponse.AddHeader, out statusCode)) | 64 | if (!m_Auth.Authenticate(httpRequest.Headers, httpResponse.AddHeader, out statusCode)) |
65 | { | 65 | { |
66 | httpResponse.StatusCode = (int)statusCode; | 66 | httpResponse.StatusCode = (int)statusCode; |
67 | httpResponse.ContentType = "text/plain"; | 67 | httpResponse.ContentType = "text/plain"; |
68 | return new byte[0]; | 68 | return new byte[0]; |
diff --git a/OpenSim/Framework/Servers/HttpServer/BaseStreamHandlerBasicDOSProtector.cs b/OpenSim/Framework/Servers/HttpServer/BaseStreamHandlerBasicDOSProtector.cs index 1b88545..9619e03 100644 --- a/OpenSim/Framework/Servers/HttpServer/BaseStreamHandlerBasicDOSProtector.cs +++ b/OpenSim/Framework/Servers/HttpServer/BaseStreamHandlerBasicDOSProtector.cs | |||
@@ -37,7 +37,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
37 | /// </remarks> | 37 | /// </remarks> |
38 | public abstract class BaseStreamHandlerBasicDOSProtector : BaseRequestHandler, IStreamedRequestHandler | 38 | public abstract class BaseStreamHandlerBasicDOSProtector : BaseRequestHandler, IStreamedRequestHandler |
39 | { | 39 | { |
40 | 40 | ||
41 | private readonly BasicDosProtectorOptions _options; | 41 | private readonly BasicDosProtectorOptions _options; |
42 | private readonly BasicDOSProtector _dosProtector; | 42 | private readonly BasicDOSProtector _dosProtector; |
43 | 43 | ||
@@ -63,7 +63,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
63 | result = ThrottledRequest(path, request, httpRequest, httpResponse); | 63 | result = ThrottledRequest(path, request, httpRequest, httpResponse); |
64 | if (_options.MaxConcurrentSessions > 0) | 64 | if (_options.MaxConcurrentSessions > 0) |
65 | _dosProtector.ProcessEnd(clientstring, endpoint); | 65 | _dosProtector.ProcessEnd(clientstring, endpoint); |
66 | 66 | ||
67 | RequestsHandled++; | 67 | RequestsHandled++; |
68 | 68 | ||
69 | return result; | 69 | return result; |
@@ -81,7 +81,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
81 | return new byte[0]; | 81 | return new byte[0]; |
82 | } | 82 | } |
83 | 83 | ||
84 | 84 | ||
85 | private string GetRemoteAddr(IOSHttpRequest httpRequest) | 85 | private string GetRemoteAddr(IOSHttpRequest httpRequest) |
86 | { | 86 | { |
87 | string remoteaddr = string.Empty; | 87 | string remoteaddr = string.Empty; |
@@ -101,7 +101,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
101 | clientstring = GetRemoteAddr(httpRequest); | 101 | clientstring = GetRemoteAddr(httpRequest); |
102 | 102 | ||
103 | return clientstring; | 103 | return clientstring; |
104 | 104 | ||
105 | } | 105 | } |
106 | } | 106 | } |
107 | } | 107 | } |
diff --git a/OpenSim/Framework/Servers/HttpServer/GenericHTTPBasicDOSProtector.cs b/OpenSim/Framework/Servers/HttpServer/GenericHTTPBasicDOSProtector.cs index cd4b8ff..98d33e4 100644 --- a/OpenSim/Framework/Servers/HttpServer/GenericHTTPBasicDOSProtector.cs +++ b/OpenSim/Framework/Servers/HttpServer/GenericHTTPBasicDOSProtector.cs | |||
@@ -33,7 +33,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
33 | { | 33 | { |
34 | private readonly GenericHTTPMethod _normalMethod; | 34 | private readonly GenericHTTPMethod _normalMethod; |
35 | private readonly GenericHTTPMethod _throttledMethod; | 35 | private readonly GenericHTTPMethod _throttledMethod; |
36 | 36 | ||
37 | private readonly BasicDosProtectorOptions _options; | 37 | private readonly BasicDosProtectorOptions _options; |
38 | private readonly BasicDOSProtector _dosProtector; | 38 | private readonly BasicDOSProtector _dosProtector; |
39 | 39 | ||
@@ -41,7 +41,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
41 | { | 41 | { |
42 | _normalMethod = normalMethod; | 42 | _normalMethod = normalMethod; |
43 | _throttledMethod = throttledMethod; | 43 | _throttledMethod = throttledMethod; |
44 | 44 | ||
45 | _options = options; | 45 | _options = options; |
46 | _dosProtector = new BasicDOSProtector(_options); | 46 | _dosProtector = new BasicDOSProtector(_options); |
47 | } | 47 | } |
@@ -60,7 +60,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
60 | 60 | ||
61 | return process; | 61 | return process; |
62 | } | 62 | } |
63 | 63 | ||
64 | private string GetRemoteAddr(Hashtable request) | 64 | private string GetRemoteAddr(Hashtable request) |
65 | { | 65 | { |
66 | string remoteaddr = ""; | 66 | string remoteaddr = ""; |
diff --git a/OpenSim/Framework/Servers/HttpServer/Interfaces/IHttpServer.cs b/OpenSim/Framework/Servers/HttpServer/Interfaces/IHttpServer.cs index d162bc1..3a04074 100644 --- a/OpenSim/Framework/Servers/HttpServer/Interfaces/IHttpServer.cs +++ b/OpenSim/Framework/Servers/HttpServer/Interfaces/IHttpServer.cs | |||
@@ -45,26 +45,26 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
45 | // // the handlers - it is NOT required to be an actual agent header | 45 | // // the handlers - it is NOT required to be an actual agent header |
46 | // // value. | 46 | // // value. |
47 | // bool AddAgentHandler(string agent, IHttpAgentHandler handler); | 47 | // bool AddAgentHandler(string agent, IHttpAgentHandler handler); |
48 | 48 | ||
49 | /// <summary> | 49 | /// <summary> |
50 | /// Add a handler for an HTTP request. | 50 | /// Add a handler for an HTTP request. |
51 | /// </summary> | 51 | /// </summary> |
52 | /// <remarks> | 52 | /// <remarks> |
53 | /// This handler can actually be invoked either as | 53 | /// This handler can actually be invoked either as |
54 | /// | 54 | /// |
55 | /// http://<hostname>:<port>/?method=<methodName> | 55 | /// http://<hostname>:<port>/?method=<methodName> |
56 | /// | 56 | /// |
57 | /// or | 57 | /// or |
58 | /// | 58 | /// |
59 | /// http://<hostname>:<port><method> | 59 | /// http://<hostname>:<port><method> |
60 | /// | 60 | /// |
61 | /// if the method name starts with a slash. For example, AddHTTPHandler("/object/", ...) on a standalone region | 61 | /// if the method name starts with a slash. For example, AddHTTPHandler("/object/", ...) on a standalone region |
62 | /// server will register a handler that can be invoked with either | 62 | /// server will register a handler that can be invoked with either |
63 | /// | 63 | /// |
64 | /// http://localhost:9000/?method=/object/ | 64 | /// http://localhost:9000/?method=/object/ |
65 | /// | 65 | /// |
66 | /// or | 66 | /// or |
67 | /// | 67 | /// |
68 | /// http://localhost:9000/object/ | 68 | /// http://localhost:9000/object/ |
69 | /// | 69 | /// |
70 | /// In addition, the handler invoked by the HTTP server for any request is the one when best matches the request | 70 | /// In addition, the handler invoked by the HTTP server for any request is the one when best matches the request |
@@ -87,7 +87,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
87 | /// <param name="handler">handle the LLSD response</param> | 87 | /// <param name="handler">handle the LLSD response</param> |
88 | /// <returns></returns> | 88 | /// <returns></returns> |
89 | bool AddLLSDHandler(string path, LLSDMethod handler); | 89 | bool AddLLSDHandler(string path, LLSDMethod handler); |
90 | 90 | ||
91 | /// <summary> | 91 | /// <summary> |
92 | /// Add a stream handler to the http server. If the handler already exists, then nothing happens. | 92 | /// Add a stream handler to the http server. If the handler already exists, then nothing happens. |
93 | /// </summary> | 93 | /// </summary> |
@@ -98,7 +98,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
98 | bool AddXmlRPCHandler(string method, XmlRpcMethod handler, bool keepAlive); | 98 | bool AddXmlRPCHandler(string method, XmlRpcMethod handler, bool keepAlive); |
99 | 99 | ||
100 | bool AddJsonRPCHandler(string method, JsonRPCMethod handler); | 100 | bool AddJsonRPCHandler(string method, JsonRPCMethod handler); |
101 | 101 | ||
102 | /// <summary> | 102 | /// <summary> |
103 | /// Websocket HTTP server handlers. | 103 | /// Websocket HTTP server handlers. |
104 | /// </summary> | 104 | /// </summary> |
@@ -108,7 +108,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
108 | 108 | ||
109 | 109 | ||
110 | void RemoveWebSocketHandler(string servicepath); | 110 | void RemoveWebSocketHandler(string servicepath); |
111 | 111 | ||
112 | /// <summary> | 112 | /// <summary> |
113 | /// Gets the XML RPC handler for given method name | 113 | /// Gets the XML RPC handler for given method name |
114 | /// </summary> | 114 | /// </summary> |
@@ -125,7 +125,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
125 | // /// <param name="handler"></param> | 125 | // /// <param name="handler"></param> |
126 | // /// <returns></returns> | 126 | // /// <returns></returns> |
127 | // bool RemoveAgentHandler(string agent, IHttpAgentHandler handler); | 127 | // bool RemoveAgentHandler(string agent, IHttpAgentHandler handler); |
128 | 128 | ||
129 | /// <summary> | 129 | /// <summary> |
130 | /// Remove an HTTP handler | 130 | /// Remove an HTTP handler |
131 | /// </summary> | 131 | /// </summary> |
@@ -134,15 +134,15 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
134 | void RemoveHTTPHandler(string httpMethod, string path); | 134 | void RemoveHTTPHandler(string httpMethod, string path); |
135 | 135 | ||
136 | void RemovePollServiceHTTPHandler(string httpMethod, string path); | 136 | void RemovePollServiceHTTPHandler(string httpMethod, string path); |
137 | 137 | ||
138 | bool RemoveLLSDHandler(string path, LLSDMethod handler); | 138 | bool RemoveLLSDHandler(string path, LLSDMethod handler); |
139 | 139 | ||
140 | void RemoveStreamHandler(string httpMethod, string path); | 140 | void RemoveStreamHandler(string httpMethod, string path); |
141 | 141 | ||
142 | void RemoveXmlRPCHandler(string method); | 142 | void RemoveXmlRPCHandler(string method); |
143 | 143 | ||
144 | void RemoveJsonRPCHandler(string method); | 144 | void RemoveJsonRPCHandler(string method); |
145 | 145 | ||
146 | string GetHTTP404(string host); | 146 | string GetHTTP404(string host); |
147 | 147 | ||
148 | string GetHTTP500(); | 148 | string GetHTTP500(); |
diff --git a/OpenSim/Framework/Servers/HttpServer/Interfaces/IStreamHandler.cs b/OpenSim/Framework/Servers/HttpServer/Interfaces/IStreamHandler.cs index b8541cb..62d92fb 100644 --- a/OpenSim/Framework/Servers/HttpServer/Interfaces/IStreamHandler.cs +++ b/OpenSim/Framework/Servers/HttpServer/Interfaces/IStreamHandler.cs | |||
@@ -83,7 +83,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
83 | { | 83 | { |
84 | void Handle(string path, Stream request, Stream response, IOSHttpRequest httpReqbuest, IOSHttpResponse httpResponse); | 84 | void Handle(string path, Stream request, Stream response, IOSHttpRequest httpReqbuest, IOSHttpResponse httpResponse); |
85 | } | 85 | } |
86 | 86 | ||
87 | public interface IGenericHTTPHandler : IRequestHandler | 87 | public interface IGenericHTTPHandler : IRequestHandler |
88 | { | 88 | { |
89 | Hashtable Handle(string path, Hashtable request); | 89 | Hashtable Handle(string path, Hashtable request); |
diff --git a/OpenSim/Framework/Servers/HttpServer/JsonRpcRequestManager.cs b/OpenSim/Framework/Servers/HttpServer/JsonRpcRequestManager.cs index 2fe1a7d..411ee31 100644 --- a/OpenSim/Framework/Servers/HttpServer/JsonRpcRequestManager.cs +++ b/OpenSim/Framework/Servers/HttpServer/JsonRpcRequestManager.cs | |||
@@ -43,7 +43,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
43 | public class JsonRpcRequestManager | 43 | public class JsonRpcRequestManager |
44 | { | 44 | { |
45 | static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); | 45 | static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); |
46 | 46 | ||
47 | public JsonRpcRequestManager() | 47 | public JsonRpcRequestManager() |
48 | { | 48 | { |
49 | } | 49 | } |
@@ -77,6 +77,9 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
77 | if (parameters == null) | 77 | if (parameters == null) |
78 | throw new ArgumentNullException("parameters"); | 78 | throw new ArgumentNullException("parameters"); |
79 | 79 | ||
80 | if(string.IsNullOrWhiteSpace(uri)) | ||
81 | return false; | ||
82 | |||
80 | OSDMap request = new OSDMap(); | 83 | OSDMap request = new OSDMap(); |
81 | request.Add("jsonrpc", OSD.FromString("2.0")); | 84 | request.Add("jsonrpc", OSD.FromString("2.0")); |
82 | request.Add("id", OSD.FromString(jsonId)); | 85 | request.Add("id", OSD.FromString(jsonId)); |
@@ -185,6 +188,6 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
185 | 188 | ||
186 | return true; | 189 | return true; |
187 | } | 190 | } |
188 | 191 | ||
189 | } | 192 | } |
190 | } | 193 | } |
diff --git a/OpenSim/Framework/Servers/HttpServer/JsonRpcResponse.cs b/OpenSim/Framework/Servers/HttpServer/JsonRpcResponse.cs index 2c50587..91d284b 100644 --- a/OpenSim/Framework/Servers/HttpServer/JsonRpcResponse.cs +++ b/OpenSim/Framework/Servers/HttpServer/JsonRpcResponse.cs | |||
@@ -144,7 +144,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
144 | { | 144 | { |
145 | 145 | ||
146 | } | 146 | } |
147 | return result; | 147 | return result; |
148 | } | 148 | } |
149 | } | 149 | } |
150 | } | 150 | } |
diff --git a/OpenSim/Framework/Servers/HttpServer/OSHttpRequest.cs b/OpenSim/Framework/Servers/HttpServer/OSHttpRequest.cs index 05ec6dc..1a6b8cf 100644 --- a/OpenSim/Framework/Servers/HttpServer/OSHttpRequest.cs +++ b/OpenSim/Framework/Servers/HttpServer/OSHttpRequest.cs | |||
@@ -155,11 +155,11 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
155 | private string _userAgent; | 155 | private string _userAgent; |
156 | 156 | ||
157 | internal IHttpRequest IHttpRequest | 157 | internal IHttpRequest IHttpRequest |
158 | { | 158 | { |
159 | get { return _request; } | 159 | get { return _request; } |
160 | } | 160 | } |
161 | 161 | ||
162 | internal IHttpClientContext IHttpClientContext | 162 | internal IHttpClientContext IHttpClientContext |
163 | { | 163 | { |
164 | get { return _context; } | 164 | get { return _context; } |
165 | } | 165 | } |
@@ -192,19 +192,19 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
192 | // ignore | 192 | // ignore |
193 | } | 193 | } |
194 | } | 194 | } |
195 | 195 | ||
196 | if (null != req.Headers["content-type"]) | 196 | if (null != req.Headers["content-type"]) |
197 | _contentType = _request.Headers["content-type"]; | 197 | _contentType = _request.Headers["content-type"]; |
198 | if (null != req.Headers["user-agent"]) | 198 | if (null != req.Headers["user-agent"]) |
199 | _userAgent = req.Headers["user-agent"]; | 199 | _userAgent = req.Headers["user-agent"]; |
200 | 200 | ||
201 | if (null != req.Headers["remote_addr"]) | 201 | if (null != req.Headers["remote_addr"]) |
202 | { | 202 | { |
203 | try | 203 | try |
204 | { | 204 | { |
205 | IPAddress addr = IPAddress.Parse(req.Headers["remote_addr"]); | 205 | IPAddress addr = IPAddress.Parse(req.Headers["remote_addr"]); |
206 | // sometimes req.Headers["remote_port"] returns a comma separated list, so use | 206 | // sometimes req.Headers["remote_port"] returns a comma separated list, so use |
207 | // the first one in the list and log it | 207 | // the first one in the list and log it |
208 | string[] strPorts = req.Headers["remote_port"].Split(new char[] { ',' }); | 208 | string[] strPorts = req.Headers["remote_port"].Split(new char[] { ',' }); |
209 | if (strPorts.Length > 1) | 209 | if (strPorts.Length > 1) |
210 | { | 210 | { |
@@ -216,7 +216,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
216 | } | 216 | } |
217 | catch (FormatException) | 217 | catch (FormatException) |
218 | { | 218 | { |
219 | _log.ErrorFormat("[OSHttpRequest]: format exception on addr/port {0}:{1}, ignoring", | 219 | _log.ErrorFormat("[OSHttpRequest]: format exception on addr/port {0}:{1}, ignoring", |
220 | req.Headers["remote_addr"], req.Headers["remote_port"]); | 220 | req.Headers["remote_addr"], req.Headers["remote_port"]); |
221 | } | 221 | } |
222 | } | 222 | } |
diff --git a/OpenSim/Framework/Servers/HttpServer/OSHttpResponse.cs b/OpenSim/Framework/Servers/HttpServer/OSHttpResponse.cs index 89fb5d4..d7744fc 100644 --- a/OpenSim/Framework/Servers/HttpServer/OSHttpResponse.cs +++ b/OpenSim/Framework/Servers/HttpServer/OSHttpResponse.cs | |||
@@ -115,7 +115,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
115 | 115 | ||
116 | public bool KeepAlive | 116 | public bool KeepAlive |
117 | { | 117 | { |
118 | get | 118 | get |
119 | { | 119 | { |
120 | return _httpResponse.Connection == ConnectionType.KeepAlive; | 120 | return _httpResponse.Connection == ConnectionType.KeepAlive; |
121 | } | 121 | } |
@@ -148,6 +148,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
148 | _httpResponse.Connection = ConnectionType.Close; | 148 | _httpResponse.Connection = ConnectionType.Close; |
149 | _httpResponse.KeepAlive = 0; | 149 | _httpResponse.KeepAlive = 0; |
150 | } | 150 | } |
151 | |||
151 | else | 152 | else |
152 | { | 153 | { |
153 | _httpResponse.Connection = ConnectionType.KeepAlive; | 154 | _httpResponse.Connection = ConnectionType.KeepAlive; |
@@ -320,6 +321,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
320 | public void Send() | 321 | public void Send() |
321 | { | 322 | { |
322 | _httpResponse.Body.Flush(); | 323 | _httpResponse.Body.Flush(); |
324 | |||
323 | _httpResponse.Send(); | 325 | _httpResponse.Send(); |
324 | } | 326 | } |
325 | 327 | ||
diff --git a/OpenSim/Framework/Servers/HttpServer/OSHttpStatusCodes.cs b/OpenSim/Framework/Servers/HttpServer/OSHttpStatusCodes.cs index a736c8b..88e3068 100644 --- a/OpenSim/Framework/Servers/HttpServer/OSHttpStatusCodes.cs +++ b/OpenSim/Framework/Servers/HttpServer/OSHttpStatusCodes.cs | |||
@@ -91,7 +91,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
91 | /// 300 Redirect: different presentation forms available, take a pick | 91 | /// 300 Redirect: different presentation forms available, take a pick |
92 | /// </summary> | 92 | /// </summary> |
93 | RedirectMultipleChoices = 300, | 93 | RedirectMultipleChoices = 300, |
94 | 94 | ||
95 | /// <summary> | 95 | /// <summary> |
96 | /// 301 Redirect: requested resource has moved and now lives somewhere else | 96 | /// 301 Redirect: requested resource has moved and now lives somewhere else |
97 | /// </summary> | 97 | /// </summary> |
diff --git a/OpenSim/Framework/Servers/HttpServer/PollServiceEventArgs.cs b/OpenSim/Framework/Servers/HttpServer/PollServiceEventArgs.cs index 9477100..7150aad 100644 --- a/OpenSim/Framework/Servers/HttpServer/PollServiceEventArgs.cs +++ b/OpenSim/Framework/Servers/HttpServer/PollServiceEventArgs.cs | |||
@@ -46,13 +46,15 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
46 | public RequestMethod Request; | 46 | public RequestMethod Request; |
47 | public UUID Id; | 47 | public UUID Id; |
48 | public int TimeOutms; | 48 | public int TimeOutms; |
49 | public EventType Type; | 49 | public EventType Type; |
50 | 50 | ||
51 | public enum EventType : int | 51 | public enum EventType : int |
52 | { | 52 | { |
53 | LongPoll = 0, | 53 | Poll = 0, |
54 | LslHttp = 1, | 54 | LslHttp = 1, |
55 | Inventory = 2 | 55 | Inventory = 2, |
56 | Texture = 3, | ||
57 | Mesh = 4 | ||
56 | } | 58 | } |
57 | 59 | ||
58 | public string Url { get; set; } | 60 | public string Url { get; set; } |
@@ -80,7 +82,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
80 | NoEvents = pNoEvents; | 82 | NoEvents = pNoEvents; |
81 | Id = pId; | 83 | Id = pId; |
82 | TimeOutms = pTimeOutms; | 84 | TimeOutms = pTimeOutms; |
83 | Type = EventType.LongPoll; | 85 | Type = EventType.Poll; |
84 | } | 86 | } |
85 | } | 87 | } |
86 | } | 88 | } |
diff --git a/OpenSim/Framework/Servers/HttpServer/PollServiceHttpRequest.cs b/OpenSim/Framework/Servers/HttpServer/PollServiceHttpRequest.cs index caf0e98..fefcb20 100644 --- a/OpenSim/Framework/Servers/HttpServer/PollServiceHttpRequest.cs +++ b/OpenSim/Framework/Servers/HttpServer/PollServiceHttpRequest.cs | |||
@@ -27,6 +27,7 @@ | |||
27 | 27 | ||
28 | using System; | 28 | using System; |
29 | using System.Collections; | 29 | using System.Collections; |
30 | using System.Collections.Generic; | ||
30 | using System.Reflection; | 31 | using System.Reflection; |
31 | using System.Text; | 32 | using System.Text; |
32 | using HttpServer; | 33 | using HttpServer; |
@@ -44,6 +45,24 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
44 | public readonly IHttpRequest Request; | 45 | public readonly IHttpRequest Request; |
45 | public readonly int RequestTime; | 46 | public readonly int RequestTime; |
46 | public readonly UUID RequestID; | 47 | public readonly UUID RequestID; |
48 | public int contextHash; | ||
49 | |||
50 | private void GenContextHash() | ||
51 | { | ||
52 | Random rnd = new Random(); | ||
53 | contextHash = 0; | ||
54 | if (Request.Headers["remote_addr"] != null) | ||
55 | contextHash = (Request.Headers["remote_addr"]).GetHashCode() << 16; | ||
56 | else | ||
57 | contextHash = rnd.Next() << 16; | ||
58 | if (Request.Headers["remote_port"] != null) | ||
59 | { | ||
60 | string[] strPorts = Request.Headers["remote_port"].Split(new char[] { ',' }); | ||
61 | contextHash += Int32.Parse(strPorts[0]); | ||
62 | } | ||
63 | else | ||
64 | contextHash += rnd.Next() & 0xffff; | ||
65 | } | ||
47 | 66 | ||
48 | public PollServiceHttpRequest( | 67 | public PollServiceHttpRequest( |
49 | PollServiceEventArgs pPollServiceArgs, IHttpClientContext pHttpContext, IHttpRequest pRequest) | 68 | PollServiceEventArgs pPollServiceArgs, IHttpClientContext pHttpContext, IHttpRequest pRequest) |
@@ -53,6 +72,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
53 | Request = pRequest; | 72 | Request = pRequest; |
54 | RequestTime = System.Environment.TickCount; | 73 | RequestTime = System.Environment.TickCount; |
55 | RequestID = UUID.Random(); | 74 | RequestID = UUID.Random(); |
75 | GenContextHash(); | ||
56 | } | 76 | } |
57 | 77 | ||
58 | internal void DoHTTPGruntWork(BaseHttpServer server, Hashtable responsedata) | 78 | internal void DoHTTPGruntWork(BaseHttpServer server, Hashtable responsedata) |
@@ -62,36 +82,69 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
62 | 82 | ||
63 | byte[] buffer = server.DoHTTPGruntWork(responsedata, response); | 83 | byte[] buffer = server.DoHTTPGruntWork(responsedata, response); |
64 | 84 | ||
85 | if(Request.Body.CanRead) | ||
86 | Request.Body.Dispose(); | ||
87 | |||
65 | response.SendChunked = false; | 88 | response.SendChunked = false; |
66 | response.ContentLength64 = buffer.Length; | 89 | response.ContentLength64 = buffer.Length; |
67 | response.ContentEncoding = Encoding.UTF8; | 90 | response.ContentEncoding = Encoding.UTF8; |
91 | response.ReuseContext = false; | ||
68 | 92 | ||
69 | try | 93 | try |
70 | { | 94 | { |
71 | response.OutputStream.Write(buffer, 0, buffer.Length); | 95 | response.OutputStream.Write(buffer, 0, buffer.Length); |
96 | response.OutputStream.Flush(); | ||
97 | response.Send(); | ||
98 | buffer = null; | ||
72 | } | 99 | } |
73 | catch (Exception ex) | 100 | catch (Exception ex) |
74 | { | 101 | { |
75 | m_log.Warn("[POLL SERVICE WORKER THREAD]: Error ", ex); | 102 | m_log.Warn("[POLL SERVICE WORKER THREAD]: Error ", ex); |
76 | } | 103 | } |
77 | finally | 104 | |
105 | PollServiceArgs.RequestsHandled++; | ||
106 | } | ||
107 | |||
108 | internal void DoHTTPstop(BaseHttpServer server) | ||
109 | { | ||
110 | OSHttpResponse response | ||
111 | = new OSHttpResponse(new HttpResponse(HttpContext, Request), HttpContext); | ||
112 | |||
113 | if(Request.Body.CanRead) | ||
114 | Request.Body.Dispose(); | ||
115 | |||
116 | response.SendChunked = false; | ||
117 | response.ContentLength64 = 0; | ||
118 | response.ContentEncoding = Encoding.UTF8; | ||
119 | response.ReuseContext = false; | ||
120 | response.KeepAlive = false; | ||
121 | response.SendChunked = false; | ||
122 | response.StatusCode = 503; | ||
123 | |||
124 | try | ||
78 | { | 125 | { |
79 | //response.OutputStream.Close(); | 126 | response.OutputStream.Flush(); |
80 | try | 127 | response.Send(); |
81 | { | ||
82 | response.OutputStream.Flush(); | ||
83 | response.Send(); | ||
84 | |||
85 | //if (!response.KeepAlive && response.ReuseContext) | ||
86 | // response.FreeContext(); | ||
87 | } | ||
88 | catch (Exception e) | ||
89 | { | ||
90 | m_log.Warn("[POLL SERVICE WORKER THREAD]: Error ", e); | ||
91 | } | ||
92 | |||
93 | PollServiceArgs.RequestsHandled++; | ||
94 | } | 128 | } |
129 | catch (Exception e) | ||
130 | { | ||
131 | } | ||
132 | } | ||
133 | } | ||
134 | |||
135 | class PollServiceHttpRequestComparer : IEqualityComparer<PollServiceHttpRequest> | ||
136 | { | ||
137 | public bool Equals(PollServiceHttpRequest b1, PollServiceHttpRequest b2) | ||
138 | { | ||
139 | if (b1.contextHash != b2.contextHash) | ||
140 | return false; | ||
141 | bool b = Object.ReferenceEquals(b1.HttpContext, b2.HttpContext); | ||
142 | return b; | ||
143 | } | ||
144 | |||
145 | public int GetHashCode(PollServiceHttpRequest b2) | ||
146 | { | ||
147 | return (int)b2.contextHash; | ||
95 | } | 148 | } |
96 | } | 149 | } |
97 | } \ No newline at end of file | 150 | } \ No newline at end of file |
diff --git a/OpenSim/Framework/Servers/HttpServer/PollServiceRequestManager.cs b/OpenSim/Framework/Servers/HttpServer/PollServiceRequestManager.cs index 28bba70..c6a3e65 100644 --- a/OpenSim/Framework/Servers/HttpServer/PollServiceRequestManager.cs +++ b/OpenSim/Framework/Servers/HttpServer/PollServiceRequestManager.cs | |||
@@ -44,200 +44,183 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
44 | { | 44 | { |
45 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); | 45 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); |
46 | 46 | ||
47 | /// <summary> | ||
48 | /// Is the poll service request manager running? | ||
49 | /// </summary> | ||
50 | /// <remarks> | ||
51 | /// Can be running either synchronously or asynchronously | ||
52 | /// </remarks> | ||
53 | public bool IsRunning { get; private set; } | ||
54 | |||
55 | /// <summary> | ||
56 | /// Is the poll service performing responses asynchronously (with its own threads) or synchronously (via | ||
57 | /// external calls)? | ||
58 | /// </summary> | ||
59 | public bool PerformResponsesAsync { get; private set; } | ||
60 | |||
61 | /// <summary> | ||
62 | /// Number of responses actually processed and sent to viewer (or aborted due to error). | ||
63 | /// </summary> | ||
64 | public int ResponsesProcessed { get; private set; } | ||
65 | |||
66 | private readonly BaseHttpServer m_server; | 47 | private readonly BaseHttpServer m_server; |
67 | 48 | ||
49 | private Dictionary<PollServiceHttpRequest, Queue<PollServiceHttpRequest>> m_bycontext; | ||
68 | private BlockingQueue<PollServiceHttpRequest> m_requests = new BlockingQueue<PollServiceHttpRequest>(); | 50 | private BlockingQueue<PollServiceHttpRequest> m_requests = new BlockingQueue<PollServiceHttpRequest>(); |
69 | private static List<PollServiceHttpRequest> m_longPollRequests = new List<PollServiceHttpRequest>(); | 51 | private static Queue<PollServiceHttpRequest> m_retryRequests = new Queue<PollServiceHttpRequest>(); |
70 | 52 | ||
71 | private uint m_WorkerThreadCount = 0; | 53 | private uint m_WorkerThreadCount = 0; |
72 | private Thread[] m_workerThreads; | 54 | private Thread[] m_workerThreads; |
55 | private Thread m_retrysThread; | ||
73 | 56 | ||
74 | private SmartThreadPool m_threadPool = new SmartThreadPool(20000, 12, 2); | 57 | private bool m_running = false; |
75 | 58 | ||
76 | // private int m_timeout = 1000; // increase timeout 250; now use the event one | 59 | private SmartThreadPool m_threadPool; |
77 | 60 | ||
78 | public PollServiceRequestManager( | 61 | public PollServiceRequestManager( |
79 | BaseHttpServer pSrv, bool performResponsesAsync, uint pWorkerThreadCount, int pTimeout) | 62 | BaseHttpServer pSrv, bool performResponsesAsync, uint pWorkerThreadCount, int pTimeout) |
80 | { | 63 | { |
81 | m_server = pSrv; | 64 | m_server = pSrv; |
82 | PerformResponsesAsync = performResponsesAsync; | ||
83 | m_WorkerThreadCount = pWorkerThreadCount; | 65 | m_WorkerThreadCount = pWorkerThreadCount; |
84 | m_workerThreads = new Thread[m_WorkerThreadCount]; | 66 | m_workerThreads = new Thread[m_WorkerThreadCount]; |
85 | 67 | ||
86 | StatsManager.RegisterStat( | 68 | PollServiceHttpRequestComparer preqCp = new PollServiceHttpRequestComparer(); |
87 | new Stat( | 69 | m_bycontext = new Dictionary<PollServiceHttpRequest, Queue<PollServiceHttpRequest>>(preqCp); |
88 | "QueuedPollResponses", | 70 | |
89 | "Number of poll responses queued for processing.", | 71 | STPStartInfo startInfo = new STPStartInfo(); |
90 | "", | 72 | startInfo.IdleTimeout = 30000; |
91 | "", | 73 | startInfo.MaxWorkerThreads = 20; |
92 | "httpserver", | 74 | startInfo.MinWorkerThreads = 1; |
93 | m_server.Port.ToString(), | 75 | startInfo.ThreadPriority = ThreadPriority.Normal; |
94 | StatType.Pull, | 76 | startInfo.StartSuspended = true; |
95 | MeasuresOfInterest.AverageChangeOverTime, | 77 | startInfo.ThreadPoolName = "PoolService"; |
96 | stat => stat.Value = m_requests.Count(), | 78 | |
97 | StatVerbosity.Debug)); | 79 | m_threadPool = new SmartThreadPool(startInfo); |
98 | |||
99 | StatsManager.RegisterStat( | ||
100 | new Stat( | ||
101 | "ProcessedPollResponses", | ||
102 | "Number of poll responses processed.", | ||
103 | "", | ||
104 | "", | ||
105 | "httpserver", | ||
106 | m_server.Port.ToString(), | ||
107 | StatType.Pull, | ||
108 | MeasuresOfInterest.AverageChangeOverTime, | ||
109 | stat => stat.Value = ResponsesProcessed, | ||
110 | StatVerbosity.Debug)); | ||
111 | } | 80 | } |
112 | 81 | ||
113 | public void Start() | 82 | public void Start() |
114 | { | 83 | { |
115 | IsRunning = true; | 84 | m_running = true; |
116 | 85 | m_threadPool.Start(); | |
117 | if (PerformResponsesAsync) | 86 | //startup worker threads |
87 | for (uint i = 0; i < m_WorkerThreadCount; i++) | ||
118 | { | 88 | { |
119 | //startup worker threads | 89 | m_workerThreads[i] |
120 | for (uint i = 0; i < m_WorkerThreadCount; i++) | 90 | = WorkManager.StartThread( |
121 | { | 91 | PoolWorkerJob, |
122 | m_workerThreads[i] | 92 | string.Format("PollServiceWorkerThread {0}:{1}", i, m_server.Port), |
123 | = WorkManager.StartThread( | 93 | ThreadPriority.Normal, |
124 | PoolWorkerJob, | 94 | true, |
125 | string.Format("PollServiceWorkerThread{0}:{1}", i, m_server.Port), | 95 | false, |
126 | ThreadPriority.Normal, | 96 | null, |
127 | false, | 97 | int.MaxValue); |
128 | false, | ||
129 | null, | ||
130 | int.MaxValue); | ||
131 | } | ||
132 | |||
133 | WorkManager.StartThread( | ||
134 | this.CheckLongPollThreads, | ||
135 | string.Format("LongPollServiceWatcherThread:{0}", m_server.Port), | ||
136 | ThreadPriority.Normal, | ||
137 | false, | ||
138 | true, | ||
139 | null, | ||
140 | 1000 * 60 * 10); | ||
141 | } | 98 | } |
99 | |||
100 | m_retrysThread = WorkManager.StartThread( | ||
101 | this.CheckRetries, | ||
102 | string.Format("PollServiceWatcherThread:{0}", m_server.Port), | ||
103 | ThreadPriority.Normal, | ||
104 | true, | ||
105 | true, | ||
106 | null, | ||
107 | 1000 * 60 * 10); | ||
108 | |||
109 | |||
142 | } | 110 | } |
143 | 111 | ||
144 | private void ReQueueEvent(PollServiceHttpRequest req) | 112 | private void ReQueueEvent(PollServiceHttpRequest req) |
145 | { | 113 | { |
146 | if (IsRunning) | 114 | if (m_running) |
147 | { | 115 | { |
148 | // delay the enqueueing for 100ms. There's no need to have the event | 116 | lock (m_retryRequests) |
149 | // actively on the queue | 117 | m_retryRequests.Enqueue(req); |
150 | Timer t = new Timer(self => { | ||
151 | ((Timer)self).Dispose(); | ||
152 | m_requests.Enqueue(req); | ||
153 | }); | ||
154 | |||
155 | t.Change(100, Timeout.Infinite); | ||
156 | |||
157 | } | 118 | } |
158 | } | 119 | } |
159 | 120 | ||
160 | public void Enqueue(PollServiceHttpRequest req) | 121 | public void Enqueue(PollServiceHttpRequest req) |
161 | { | 122 | { |
162 | if (IsRunning) | 123 | lock (m_bycontext) |
163 | { | 124 | { |
164 | if (req.PollServiceArgs.Type == PollServiceEventArgs.EventType.LongPoll) | 125 | Queue<PollServiceHttpRequest> ctxQeueue; |
126 | if (m_bycontext.TryGetValue(req, out ctxQeueue)) | ||
165 | { | 127 | { |
166 | lock (m_longPollRequests) | 128 | ctxQeueue.Enqueue(req); |
167 | m_longPollRequests.Add(req); | ||
168 | } | 129 | } |
169 | else | 130 | else |
170 | m_requests.Enqueue(req); | 131 | { |
132 | ctxQeueue = new Queue<PollServiceHttpRequest>(); | ||
133 | m_bycontext[req] = ctxQeueue; | ||
134 | EnqueueInt(req); | ||
135 | } | ||
171 | } | 136 | } |
172 | } | 137 | } |
173 | 138 | ||
174 | private void CheckLongPollThreads() | 139 | public void byContextDequeue(PollServiceHttpRequest req) |
175 | { | 140 | { |
176 | // The only purpose of this thread is to check the EQs for events. | 141 | Queue<PollServiceHttpRequest> ctxQeueue; |
177 | // If there are events, that thread will be placed in the "ready-to-serve" queue, m_requests. | 142 | lock (m_bycontext) |
178 | // If there are no events, that thread will be back to its "waiting" queue, m_longPollRequests. | ||
179 | // All other types of tasks (Inventory handlers, http-in, etc) don't have the long-poll nature, | ||
180 | // so if they aren't ready to be served by a worker thread (no events), they are placed | ||
181 | // directly back in the "ready-to-serve" queue by the worker thread. | ||
182 | while (IsRunning) | ||
183 | { | 143 | { |
184 | Thread.Sleep(500); | 144 | if (m_bycontext.TryGetValue(req, out ctxQeueue)) |
185 | Watchdog.UpdateThread(); | ||
186 | |||
187 | // List<PollServiceHttpRequest> not_ready = new List<PollServiceHttpRequest>(); | ||
188 | lock (m_longPollRequests) | ||
189 | { | 145 | { |
190 | if (m_longPollRequests.Count > 0 && IsRunning) | 146 | if (ctxQeueue.Count > 0) |
147 | { | ||
148 | PollServiceHttpRequest newreq = ctxQeueue.Dequeue(); | ||
149 | EnqueueInt(newreq); | ||
150 | } | ||
151 | else | ||
191 | { | 152 | { |
192 | List<PollServiceHttpRequest> ready = m_longPollRequests.FindAll(req => | 153 | m_bycontext.Remove(req); |
193 | (req.PollServiceArgs.HasEvents(req.RequestID, req.PollServiceArgs.Id) || // there are events in this EQ | 154 | } |
194 | (Environment.TickCount - req.RequestTime) > req.PollServiceArgs.TimeOutms) // no events, but timeout | 155 | } |
195 | ); | 156 | } |
157 | } | ||
196 | 158 | ||
197 | ready.ForEach(req => | 159 | public void EnqueueInt(PollServiceHttpRequest req) |
198 | { | 160 | { |
199 | m_requests.Enqueue(req); | 161 | if (m_running) |
200 | m_longPollRequests.Remove(req); | 162 | m_requests.Enqueue(req); |
201 | }); | 163 | } |
202 | 164 | ||
203 | } | 165 | private void CheckRetries() |
166 | { | ||
167 | while (m_running) | ||
204 | 168 | ||
169 | { | ||
170 | Thread.Sleep(100); // let the world move .. back to faster rate | ||
171 | Watchdog.UpdateThread(); | ||
172 | lock (m_retryRequests) | ||
173 | { | ||
174 | while (m_retryRequests.Count > 0 && m_running) | ||
175 | m_requests.Enqueue(m_retryRequests.Dequeue()); | ||
205 | } | 176 | } |
206 | } | 177 | } |
207 | } | 178 | } |
208 | 179 | ||
209 | public void Stop() | 180 | public void Stop() |
210 | { | 181 | { |
211 | IsRunning = false; | 182 | m_running = false; |
212 | // m_timeout = -10000; // cause all to expire | 183 | |
213 | Thread.Sleep(1000); // let the world move | 184 | Thread.Sleep(100); // let the world move |
214 | 185 | ||
215 | foreach (Thread t in m_workerThreads) | 186 | foreach (Thread t in m_workerThreads) |
216 | Watchdog.AbortThread(t.ManagedThreadId); | 187 | Watchdog.AbortThread(t.ManagedThreadId); |
217 | 188 | ||
218 | PollServiceHttpRequest wreq; | 189 | m_threadPool.Shutdown(); |
190 | |||
191 | // any entry in m_bycontext should have a active request on the other queues | ||
192 | // so just delete contents to easy GC | ||
193 | foreach (Queue<PollServiceHttpRequest> qu in m_bycontext.Values) | ||
194 | qu.Clear(); | ||
195 | m_bycontext.Clear(); | ||
219 | 196 | ||
220 | lock (m_longPollRequests) | 197 | try |
198 | { | ||
199 | foreach (PollServiceHttpRequest req in m_retryRequests) | ||
200 | { | ||
201 | req.DoHTTPstop(m_server); | ||
202 | } | ||
203 | } | ||
204 | catch | ||
221 | { | 205 | { |
222 | if (m_longPollRequests.Count > 0 && IsRunning) | ||
223 | m_longPollRequests.ForEach(req => m_requests.Enqueue(req)); | ||
224 | } | 206 | } |
225 | 207 | ||
208 | PollServiceHttpRequest wreq; | ||
209 | |||
210 | m_retryRequests.Clear(); | ||
211 | |||
226 | while (m_requests.Count() > 0) | 212 | while (m_requests.Count() > 0) |
227 | { | 213 | { |
228 | try | 214 | try |
229 | { | 215 | { |
230 | wreq = m_requests.Dequeue(0); | 216 | wreq = m_requests.Dequeue(0); |
231 | ResponsesProcessed++; | 217 | wreq.DoHTTPstop(m_server); |
232 | wreq.DoHTTPGruntWork( | ||
233 | m_server, wreq.PollServiceArgs.NoEvents(wreq.RequestID, wreq.PollServiceArgs.Id)); | ||
234 | } | 218 | } |
235 | catch | 219 | catch |
236 | { | 220 | { |
237 | } | 221 | } |
238 | } | 222 | } |
239 | 223 | ||
240 | m_longPollRequests.Clear(); | ||
241 | m_requests.Clear(); | 224 | m_requests.Clear(); |
242 | } | 225 | } |
243 | 226 | ||
@@ -245,87 +228,69 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
245 | 228 | ||
246 | private void PoolWorkerJob() | 229 | private void PoolWorkerJob() |
247 | { | 230 | { |
248 | while (IsRunning) | 231 | while (m_running) |
249 | { | 232 | { |
233 | PollServiceHttpRequest req = m_requests.Dequeue(4500); | ||
250 | Watchdog.UpdateThread(); | 234 | Watchdog.UpdateThread(); |
251 | WaitPerformResponse(); | 235 | if (req != null) |
252 | } | ||
253 | } | ||
254 | |||
255 | public void WaitPerformResponse() | ||
256 | { | ||
257 | PollServiceHttpRequest req = m_requests.Dequeue(5000); | ||
258 | // m_log.DebugFormat("[YYY]: Dequeued {0}", (req == null ? "null" : req.PollServiceArgs.Type.ToString())); | ||
259 | |||
260 | if (req != null) | ||
261 | { | ||
262 | try | ||
263 | { | 236 | { |
264 | if (req.PollServiceArgs.HasEvents(req.RequestID, req.PollServiceArgs.Id)) | 237 | try |
265 | { | 238 | { |
266 | Hashtable responsedata = req.PollServiceArgs.GetEvents(req.RequestID, req.PollServiceArgs.Id); | 239 | if (req.PollServiceArgs.HasEvents(req.RequestID, req.PollServiceArgs.Id)) |
267 | |||
268 | if (responsedata == null) | ||
269 | return; | ||
270 | |||
271 | // This is the event queue. | ||
272 | // Even if we're not running we can still perform responses by explicit request. | ||
273 | if (req.PollServiceArgs.Type == PollServiceEventArgs.EventType.LongPoll | ||
274 | || !PerformResponsesAsync) | ||
275 | { | ||
276 | try | ||
277 | { | ||
278 | ResponsesProcessed++; | ||
279 | req.DoHTTPGruntWork(m_server, responsedata); | ||
280 | } | ||
281 | catch (ObjectDisposedException e) // Browser aborted before we could read body, server closed the stream | ||
282 | { | ||
283 | // Ignore it, no need to reply | ||
284 | m_log.Error(e); | ||
285 | } | ||
286 | } | ||
287 | else | ||
288 | { | 240 | { |
241 | Hashtable responsedata = req.PollServiceArgs.GetEvents(req.RequestID, req.PollServiceArgs.Id); | ||
242 | |||
289 | m_threadPool.QueueWorkItem(x => | 243 | m_threadPool.QueueWorkItem(x => |
290 | { | 244 | { |
291 | try | 245 | try |
292 | { | 246 | { |
293 | ResponsesProcessed++; | ||
294 | req.DoHTTPGruntWork(m_server, responsedata); | 247 | req.DoHTTPGruntWork(m_server, responsedata); |
295 | } | 248 | } |
296 | catch (ObjectDisposedException e) // Browser aborted before we could read body, server closed the stream | 249 | catch (ObjectDisposedException) |
297 | { | 250 | { |
298 | // Ignore it, no need to reply | ||
299 | m_log.Error(e); | ||
300 | } | 251 | } |
301 | catch (Exception e) | 252 | finally |
302 | { | 253 | { |
303 | m_log.Error(e); | 254 | byContextDequeue(req); |
304 | } | 255 | } |
305 | |||
306 | return null; | 256 | return null; |
307 | }, null); | 257 | }, null); |
308 | } | 258 | } |
309 | } | ||
310 | else | ||
311 | { | ||
312 | if ((Environment.TickCount - req.RequestTime) > req.PollServiceArgs.TimeOutms) | ||
313 | { | ||
314 | ResponsesProcessed++; | ||
315 | req.DoHTTPGruntWork( | ||
316 | m_server, req.PollServiceArgs.NoEvents(req.RequestID, req.PollServiceArgs.Id)); | ||
317 | } | ||
318 | else | 259 | else |
319 | { | 260 | { |
320 | ReQueueEvent(req); | 261 | if ((Environment.TickCount - req.RequestTime) > req.PollServiceArgs.TimeOutms) |
262 | { | ||
263 | m_threadPool.QueueWorkItem(x => | ||
264 | { | ||
265 | try | ||
266 | { | ||
267 | req.DoHTTPGruntWork(m_server, | ||
268 | req.PollServiceArgs.NoEvents(req.RequestID, req.PollServiceArgs.Id)); | ||
269 | } | ||
270 | catch (ObjectDisposedException) | ||
271 | { | ||
272 | // Ignore it, no need to reply | ||
273 | } | ||
274 | finally | ||
275 | { | ||
276 | byContextDequeue(req); | ||
277 | } | ||
278 | return null; | ||
279 | }, null); | ||
280 | } | ||
281 | else | ||
282 | { | ||
283 | ReQueueEvent(req); | ||
284 | } | ||
321 | } | 285 | } |
322 | } | 286 | } |
323 | } | 287 | catch (Exception e) |
324 | catch (Exception e) | 288 | { |
325 | { | 289 | m_log.ErrorFormat("Exception in poll service thread: " + e.ToString()); |
326 | m_log.ErrorFormat("Exception in poll service thread: " + e.ToString()); | 290 | } |
327 | } | 291 | } |
328 | } | 292 | } |
329 | } | 293 | } |
294 | |||
330 | } | 295 | } |
331 | } \ No newline at end of file | 296 | } |
diff --git a/OpenSim/Framework/Servers/HttpServer/Properties/AssemblyInfo.cs b/OpenSim/Framework/Servers/HttpServer/Properties/AssemblyInfo.cs index 5e630dc..9b663ba 100644 --- a/OpenSim/Framework/Servers/HttpServer/Properties/AssemblyInfo.cs +++ b/OpenSim/Framework/Servers/HttpServer/Properties/AssemblyInfo.cs | |||
@@ -2,7 +2,7 @@ | |||
2 | using System.Runtime.CompilerServices; | 2 | using System.Runtime.CompilerServices; |
3 | using System.Runtime.InteropServices; | 3 | using System.Runtime.InteropServices; |
4 | 4 | ||
5 | // General Information about an assembly is controlled through the following | 5 | // General Information about an assembly is controlled through the following |
6 | // set of attributes. Change these attribute values to modify the information | 6 | // set of attributes. Change these attribute values to modify the information |
7 | // associated with an assembly. | 7 | // associated with an assembly. |
8 | [assembly: AssemblyTitle("OpenSim.Framework.Servers.HttpServer")] | 8 | [assembly: AssemblyTitle("OpenSim.Framework.Servers.HttpServer")] |
@@ -14,8 +14,8 @@ using System.Runtime.InteropServices; | |||
14 | [assembly: AssemblyTrademark("")] | 14 | [assembly: AssemblyTrademark("")] |
15 | [assembly: AssemblyCulture("")] | 15 | [assembly: AssemblyCulture("")] |
16 | 16 | ||
17 | // Setting ComVisible to false makes the types in this assembly not visible | 17 | // Setting ComVisible to false makes the types in this assembly not visible |
18 | // to COM components. If you need to access a type in this assembly from | 18 | // to COM components. If you need to access a type in this assembly from |
19 | // COM, set the ComVisible attribute to true on that type. | 19 | // COM, set the ComVisible attribute to true on that type. |
20 | [assembly: ComVisible(false)] | 20 | [assembly: ComVisible(false)] |
21 | 21 | ||
@@ -25,9 +25,9 @@ using System.Runtime.InteropServices; | |||
25 | // Version information for an assembly consists of the following four values: | 25 | // Version information for an assembly consists of the following four values: |
26 | // | 26 | // |
27 | // Major Version | 27 | // Major Version |
28 | // Minor Version | 28 | // Minor Version |
29 | // Build Number | 29 | // Build Number |
30 | // Revision | 30 | // Revision |
31 | // | 31 | // |
32 | [assembly: AssemblyVersion("0.8.3.*")] | 32 | [assembly: AssemblyVersion(OpenSim.VersionInfo.AssemblyVersionNumber)] |
33 | 33 | ||
diff --git a/OpenSim/Framework/Servers/HttpServer/RestDeserialiseHandler.cs b/OpenSim/Framework/Servers/HttpServer/RestDeserialiseHandler.cs index bd55657..67fc14e 100644 --- a/OpenSim/Framework/Servers/HttpServer/RestDeserialiseHandler.cs +++ b/OpenSim/Framework/Servers/HttpServer/RestDeserialiseHandler.cs | |||
@@ -54,6 +54,8 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
54 | TRequest deserial; | 54 | TRequest deserial; |
55 | using (XmlTextReader xmlReader = new XmlTextReader(request)) | 55 | using (XmlTextReader xmlReader = new XmlTextReader(request)) |
56 | { | 56 | { |
57 | xmlReader.ProhibitDtd = true; | ||
58 | |||
57 | XmlSerializer deserializer = new XmlSerializer(typeof (TRequest)); | 59 | XmlSerializer deserializer = new XmlSerializer(typeof (TRequest)); |
58 | deserial = (TRequest) deserializer.Deserialize(xmlReader); | 60 | deserial = (TRequest) deserializer.Deserialize(xmlReader); |
59 | } | 61 | } |
diff --git a/OpenSim/Framework/Servers/HttpServer/RestSessionService.cs b/OpenSim/Framework/Servers/HttpServer/RestSessionService.cs index ad69cd2..158befa 100644 --- a/OpenSim/Framework/Servers/HttpServer/RestSessionService.cs +++ b/OpenSim/Framework/Servers/HttpServer/RestSessionService.cs | |||
@@ -210,6 +210,8 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
210 | { | 210 | { |
211 | try | 211 | try |
212 | { | 212 | { |
213 | xmlReader.ProhibitDtd = true; | ||
214 | |||
213 | XmlSerializer deserializer = new XmlSerializer(typeof(RestSessionObject<TRequest>)); | 215 | XmlSerializer deserializer = new XmlSerializer(typeof(RestSessionObject<TRequest>)); |
214 | deserial = (RestSessionObject<TRequest>)deserializer.Deserialize(xmlReader); | 216 | deserial = (RestSessionObject<TRequest>)deserializer.Deserialize(xmlReader); |
215 | } | 217 | } |
@@ -269,6 +271,8 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
269 | { | 271 | { |
270 | try | 272 | try |
271 | { | 273 | { |
274 | xmlReader.ProhibitDtd = true; | ||
275 | |||
272 | XmlSerializer deserializer = new XmlSerializer(typeof(TRequest)); | 276 | XmlSerializer deserializer = new XmlSerializer(typeof(TRequest)); |
273 | deserial = (TRequest)deserializer.Deserialize(xmlReader); | 277 | deserial = (TRequest)deserializer.Deserialize(xmlReader); |
274 | } | 278 | } |
@@ -291,5 +295,5 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
291 | serializer.Serialize(xmlWriter, response); | 295 | serializer.Serialize(xmlWriter, response); |
292 | } | 296 | } |
293 | } | 297 | } |
294 | } | 298 | } |
295 | } \ No newline at end of file | 299 | } \ No newline at end of file |
diff --git a/OpenSim/Framework/Servers/HttpServer/RestStreamHandler.cs b/OpenSim/Framework/Servers/HttpServer/RestStreamHandler.cs index 0305dee..dfc2715 100644 --- a/OpenSim/Framework/Servers/HttpServer/RestStreamHandler.cs +++ b/OpenSim/Framework/Servers/HttpServer/RestStreamHandler.cs | |||
@@ -50,11 +50,10 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
50 | 50 | ||
51 | protected override byte[] ProcessRequest(string path, Stream request, IOSHttpRequest httpRequest, IOSHttpResponse httpResponse) | 51 | protected override byte[] ProcessRequest(string path, Stream request, IOSHttpRequest httpRequest, IOSHttpResponse httpResponse) |
52 | { | 52 | { |
53 | string requestBody; | ||
53 | Encoding encoding = Encoding.UTF8; | 54 | Encoding encoding = Encoding.UTF8; |
54 | StreamReader streamReader = new StreamReader(request, encoding); | 55 | using(StreamReader streamReader = new StreamReader(request,encoding)) |
55 | 56 | requestBody = streamReader.ReadToEnd(); | |
56 | string requestBody = streamReader.ReadToEnd(); | ||
57 | streamReader.Close(); | ||
58 | 57 | ||
59 | string param = GetParam(path); | 58 | string param = GetParam(path); |
60 | string responseString = m_restMethod(requestBody, path, param, httpRequest, httpResponse); | 59 | string responseString = m_restMethod(requestBody, path, param, httpRequest, httpResponse); |
diff --git a/OpenSim/Framework/Servers/HttpServer/WebsocketServerHandler.cs b/OpenSim/Framework/Servers/HttpServer/WebsocketServerHandler.cs index c2925e3..c8af90f 100644 --- a/OpenSim/Framework/Servers/HttpServer/WebsocketServerHandler.cs +++ b/OpenSim/Framework/Servers/HttpServer/WebsocketServerHandler.cs | |||
@@ -75,7 +75,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
75 | public event PongDelegate OnPong; | 75 | public event PongDelegate OnPong; |
76 | 76 | ||
77 | /// <summary> | 77 | /// <summary> |
78 | /// This is a regular HTTP Request... This may be removed in the future. | 78 | /// This is a regular HTTP Request... This may be removed in the future. |
79 | /// </summary> | 79 | /// </summary> |
80 | // public event RegularHttpRequestDelegate OnRegularHttpRequest; | 80 | // public event RegularHttpRequestDelegate OnRegularHttpRequest; |
81 | 81 | ||
@@ -93,9 +93,9 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
93 | /// When the websocket is closed, this will be fired. | 93 | /// When the websocket is closed, this will be fired. |
94 | /// </summary> | 94 | /// </summary> |
95 | public event CloseDelegate OnClose; | 95 | public event CloseDelegate OnClose; |
96 | 96 | ||
97 | /// <summary> | 97 | /// <summary> |
98 | /// Set this delegate to allow your module to validate the origin of the | 98 | /// Set this delegate to allow your module to validate the origin of the |
99 | /// Websocket request. Primary line of defense against cross site scripting | 99 | /// Websocket request. Primary line of defense against cross site scripting |
100 | /// </summary> | 100 | /// </summary> |
101 | public ValidateHandshake HandshakeValidateMethodOverride = null; | 101 | public ValidateHandshake HandshakeValidateMethodOverride = null; |
@@ -181,7 +181,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
181 | { | 181 | { |
182 | throw new InvalidOperationException("The socket has been shutdown"); | 182 | throw new InvalidOperationException("The socket has been shutdown"); |
183 | } | 183 | } |
184 | } | 184 | } |
185 | set | 185 | set |
186 | { | 186 | { |
187 | if (_networkContext != null && _networkContext.Socket != null) | 187 | if (_networkContext != null && _networkContext.Socket != null) |
@@ -194,8 +194,8 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
194 | } | 194 | } |
195 | 195 | ||
196 | /// <summary> | 196 | /// <summary> |
197 | /// This triggers the websocket to start the upgrade process... | 197 | /// This triggers the websocket to start the upgrade process... |
198 | /// This is a Generalized Networking 'common sense' helper method. Some people expect to call Start() instead | 198 | /// This is a Generalized Networking 'common sense' helper method. Some people expect to call Start() instead |
199 | /// of the more context appropriate HandshakeAndUpgrade() | 199 | /// of the more context appropriate HandshakeAndUpgrade() |
200 | /// </summary> | 200 | /// </summary> |
201 | public void Start() | 201 | public void Start() |
@@ -261,7 +261,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
261 | acceptKey = GenerateAcceptKey(websocketKey); | 261 | acceptKey = GenerateAcceptKey(websocketKey); |
262 | string rawaccept = string.Format(HandshakeAcceptText, acceptKey); | 262 | string rawaccept = string.Format(HandshakeAcceptText, acceptKey); |
263 | SendUpgradeSuccess(rawaccept); | 263 | SendUpgradeSuccess(rawaccept); |
264 | 264 | ||
265 | 265 | ||
266 | } | 266 | } |
267 | else | 267 | else |
@@ -282,7 +282,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
282 | } | 282 | } |
283 | 283 | ||
284 | /// <summary> | 284 | /// <summary> |
285 | /// Generates a handshake response key string based on the client's | 285 | /// Generates a handshake response key string based on the client's |
286 | /// provided key to prove to the client that we're allowing the Websocket | 286 | /// provided key to prove to the client that we're allowing the Websocket |
287 | /// upgrade of our own free will and we were not coerced into doing it. | 287 | /// upgrade of our own free will and we were not coerced into doing it. |
288 | /// </summary> | 288 | /// </summary> |
@@ -298,7 +298,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
298 | SHA1 hashobj = SHA1.Create(); | 298 | SHA1 hashobj = SHA1.Create(); |
299 | string ret = Convert.ToBase64String(hashobj.ComputeHash(Encoding.UTF8.GetBytes(acceptkey))); | 299 | string ret = Convert.ToBase64String(hashobj.ComputeHash(Encoding.UTF8.GetBytes(acceptkey))); |
300 | hashobj.Clear(); | 300 | hashobj.Clear(); |
301 | 301 | ||
302 | return ret; | 302 | return ret; |
303 | } | 303 | } |
304 | 304 | ||
@@ -310,11 +310,11 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
310 | { | 310 | { |
311 | // Create a new websocket state so we can keep track of data in between network reads. | 311 | // Create a new websocket state so we can keep track of data in between network reads. |
312 | WebSocketState socketState = new WebSocketState() { ReceivedBytes = new List<byte>(), Header = WebsocketFrameHeader.HeaderDefault(), FrameComplete = true}; | 312 | WebSocketState socketState = new WebSocketState() { ReceivedBytes = new List<byte>(), Header = WebsocketFrameHeader.HeaderDefault(), FrameComplete = true}; |
313 | 313 | ||
314 | byte[] bhandshakeResponse = Encoding.UTF8.GetBytes(pHandshakeResponse); | 314 | byte[] bhandshakeResponse = Encoding.UTF8.GetBytes(pHandshakeResponse); |
315 | 315 | ||
316 | 316 | ||
317 | 317 | ||
318 | 318 | ||
319 | try | 319 | try |
320 | { | 320 | { |
@@ -324,7 +324,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
324 | } | 324 | } |
325 | // Begin reading the TCP stream before writing the Upgrade success message to the other side of the stream. | 325 | // Begin reading the TCP stream before writing the Upgrade success message to the other side of the stream. |
326 | _networkContext.Stream.BeginRead(_buffer, 0, _bufferLength, OnReceive, socketState); | 326 | _networkContext.Stream.BeginRead(_buffer, 0, _bufferLength, OnReceive, socketState); |
327 | 327 | ||
328 | // Write the upgrade handshake success message | 328 | // Write the upgrade handshake success message |
329 | _networkContext.Stream.Write(bhandshakeResponse, 0, bhandshakeResponse.Length); | 329 | _networkContext.Stream.Write(bhandshakeResponse, 0, bhandshakeResponse.Length); |
330 | _networkContext.Stream.Flush(); | 330 | _networkContext.Stream.Flush(); |
@@ -345,7 +345,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
345 | catch (ObjectDisposedException) | 345 | catch (ObjectDisposedException) |
346 | { | 346 | { |
347 | Close(string.Empty); | 347 | Close(string.Empty); |
348 | } | 348 | } |
349 | } | 349 | } |
350 | 350 | ||
351 | /// <summary> | 351 | /// <summary> |
@@ -369,7 +369,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
369 | 369 | ||
370 | /// <summary> | 370 | /// <summary> |
371 | /// This is our ugly Async OnReceive event handler. | 371 | /// This is our ugly Async OnReceive event handler. |
372 | /// This chunks the input stream based on the length of the provided buffer and processes out | 372 | /// This chunks the input stream based on the length of the provided buffer and processes out |
373 | /// as many frames as it can. It then moves the unprocessed data to the beginning of the buffer. | 373 | /// as many frames as it can. It then moves the unprocessed data to the beginning of the buffer. |
374 | /// </summary> | 374 | /// </summary> |
375 | /// <param name="ar">Our Async State from beginread</param> | 375 | /// <param name="ar">Our Async State from beginread</param> |
@@ -390,7 +390,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
390 | 390 | ||
391 | if (_bufferPosition > _bufferLength) | 391 | if (_bufferPosition > _bufferLength) |
392 | { | 392 | { |
393 | // Message too big for chunksize.. not sure how this happened... | 393 | // Message too big for chunksize.. not sure how this happened... |
394 | //Close(string.Empty); | 394 | //Close(string.Empty); |
395 | } | 395 | } |
396 | 396 | ||
@@ -413,7 +413,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
413 | if (pheader.PayloadLen > (ulong) _maxPayloadBytes) | 413 | if (pheader.PayloadLen > (ulong) _maxPayloadBytes) |
414 | { | 414 | { |
415 | Close("Invalid Payload size"); | 415 | Close("Invalid Payload size"); |
416 | 416 | ||
417 | return; | 417 | return; |
418 | } | 418 | } |
419 | if (pheader.PayloadLen > 0) | 419 | if (pheader.PayloadLen > 0) |
@@ -487,7 +487,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
487 | _socketState.ReceivedBytes.Clear(); | 487 | _socketState.ReceivedBytes.Clear(); |
488 | _socketState.ExpectedBytes = 0; | 488 | _socketState.ExpectedBytes = 0; |
489 | // do some processing | 489 | // do some processing |
490 | } | 490 | } |
491 | } | 491 | } |
492 | } | 492 | } |
493 | if (offset > 0) | 493 | if (offset > 0) |
@@ -504,7 +504,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
504 | } | 504 | } |
505 | else | 505 | else |
506 | { | 506 | { |
507 | // We can't read the stream anymore... | 507 | // We can't read the stream anymore... |
508 | } | 508 | } |
509 | } | 509 | } |
510 | catch (IOException) | 510 | catch (IOException) |
@@ -533,7 +533,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
533 | textMessageFrame.Header.Opcode = WebSocketReader.OpCode.Text; | 533 | textMessageFrame.Header.Opcode = WebSocketReader.OpCode.Text; |
534 | textMessageFrame.Header.IsEnd = true; | 534 | textMessageFrame.Header.IsEnd = true; |
535 | SendSocket(textMessageFrame.ToBytes()); | 535 | SendSocket(textMessageFrame.ToBytes()); |
536 | 536 | ||
537 | } | 537 | } |
538 | 538 | ||
539 | public void SendData(byte[] data) | 539 | public void SendData(byte[] data) |
@@ -657,7 +657,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
657 | SendSocket(pongFrame.ToBytes()); | 657 | SendSocket(pongFrame.ToBytes()); |
658 | break; | 658 | break; |
659 | case WebSocketReader.OpCode.Pong: | 659 | case WebSocketReader.OpCode.Pong: |
660 | 660 | ||
661 | PongDelegate pongD = OnPong; | 661 | PongDelegate pongD = OnPong; |
662 | if (pongD != null) | 662 | if (pongD != null) |
663 | { | 663 | { |
@@ -701,7 +701,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
701 | { | 701 | { |
702 | textD(this, new WebsocketTextEventArgs() { Data = Encoding.UTF8.GetString(psocketState.ReceivedBytes.ToArray()) }); | 702 | textD(this, new WebsocketTextEventArgs() { Data = Encoding.UTF8.GetString(psocketState.ReceivedBytes.ToArray()) }); |
703 | } | 703 | } |
704 | 704 | ||
705 | // Send Done Event! | 705 | // Send Done Event! |
706 | } | 706 | } |
707 | break; | 707 | break; |
@@ -719,7 +719,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
719 | { | 719 | { |
720 | if (psocketState.ContinuationFrame.Header.Opcode == WebSocketReader.OpCode.Text) | 720 | if (psocketState.ContinuationFrame.Header.Opcode == WebSocketReader.OpCode.Text) |
721 | { | 721 | { |
722 | // Send Done event | 722 | // Send Done event |
723 | TextDelegate textD = OnText; | 723 | TextDelegate textD = OnText; |
724 | if (textD != null) | 724 | if (textD != null) |
725 | { | 725 | { |
@@ -744,9 +744,9 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
744 | break; | 744 | break; |
745 | case WebSocketReader.OpCode.Close: | 745 | case WebSocketReader.OpCode.Close: |
746 | Close(string.Empty); | 746 | Close(string.Empty); |
747 | 747 | ||
748 | break; | 748 | break; |
749 | 749 | ||
750 | } | 750 | } |
751 | psocketState.Header.SetDefault(); | 751 | psocketState.Header.SetDefault(); |
752 | psocketState.ReceivedBytes.Clear(); | 752 | psocketState.ReceivedBytes.Clear(); |
@@ -837,12 +837,12 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
837 | } | 837 | } |
838 | 838 | ||
839 | /// <summary> | 839 | /// <summary> |
840 | /// Attempts to read a header off the provided buffer. Returns true, exports a WebSocketFrameheader, | 840 | /// Attempts to read a header off the provided buffer. Returns true, exports a WebSocketFrameheader, |
841 | /// and an int to move the buffer forward when it reads a header. False when it can't read a header | 841 | /// and an int to move the buffer forward when it reads a header. False when it can't read a header |
842 | /// </summary> | 842 | /// </summary> |
843 | /// <param name="pBuffer">Bytes read from the stream</param> | 843 | /// <param name="pBuffer">Bytes read from the stream</param> |
844 | /// <param name="pOffset">Starting place in the stream to begin trying to read from</param> | 844 | /// <param name="pOffset">Starting place in the stream to begin trying to read from</param> |
845 | /// <param name="length">Lenth in the stream to try and read from. Provided for cases where the | 845 | /// <param name="length">Lenth in the stream to try and read from. Provided for cases where the |
846 | /// buffer's length is larger then the data in it</param> | 846 | /// buffer's length is larger then the data in it</param> |
847 | /// <param name="oHeader">Outputs the read WebSocket frame header</param> | 847 | /// <param name="oHeader">Outputs the read WebSocket frame header</param> |
848 | /// <param name="moveBuffer">Informs the calling stream to move the buffer forward</param> | 848 | /// <param name="moveBuffer">Informs the calling stream to move the buffer forward</param> |
@@ -897,7 +897,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
897 | oHeader.PayloadLen = BitConverter.ToUInt16(pBuffer, pOffset + index); | 897 | oHeader.PayloadLen = BitConverter.ToUInt16(pBuffer, pOffset + index); |
898 | index += 2; | 898 | index += 2; |
899 | break; | 899 | break; |
900 | case 127: // we got more this is a bigger frame | 900 | case 127: // we got more this is a bigger frame |
901 | // 8 bytes - uint64 - most significant bit 0 network byte order | 901 | // 8 bytes - uint64 - most significant bit 0 network byte order |
902 | minumheadersize += 8; | 902 | minumheadersize += 8; |
903 | if (length < minumheadersize) | 903 | if (length < minumheadersize) |
@@ -909,7 +909,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
909 | oHeader.PayloadLen = BitConverter.ToUInt64(pBuffer, pOffset + index); | 909 | oHeader.PayloadLen = BitConverter.ToUInt64(pBuffer, pOffset + index); |
910 | index += 8; | 910 | index += 8; |
911 | break; | 911 | break; |
912 | 912 | ||
913 | } | 913 | } |
914 | //oHeader.PayloadLeft = oHeader.PayloadLen; // Start the count in case it's chunked over the network. This is different then frame fragmentation | 914 | //oHeader.PayloadLeft = oHeader.PayloadLen; // Start the count in case it's chunked over the network. This is different then frame fragmentation |
915 | if (oHeader.IsMasked) | 915 | if (oHeader.IsMasked) |
@@ -937,9 +937,9 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
937 | /* | 937 | /* |
938 | * RFC6455 | 938 | * RFC6455 |
939 | nib 0 1 2 3 4 5 6 7 | 939 | nib 0 1 2 3 4 5 6 7 |
940 | byt 0 1 2 3 | 940 | byt 0 1 2 3 |
941 | dec 0 1 2 3 | 941 | dec 0 1 2 3 |
942 | 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 | 942 | 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
943 | +-+-+-+-+-------+-+-------------+-------------------------------+ | 943 | +-+-+-+-+-------+-+-------------+-------------------------------+ |
944 | |F|R|R|R| opcode|M| Payload len | Extended payload length | | 944 | |F|R|R|R| opcode|M| Payload len | Extended payload length | |
945 | |I|S|S|S| (4) |A| (7) | (16/64) + | 945 | |I|S|S|S| (4) |A| (7) | (16/64) + |
@@ -963,7 +963,7 @@ dec 0 1 2 3 | |||
963 | public static readonly WebSocketFrame DefaultFrame = new WebSocketFrame(){Header = new WebsocketFrameHeader(),WebSocketPayload = new byte[0]}; | 963 | public static readonly WebSocketFrame DefaultFrame = new WebSocketFrame(){Header = new WebsocketFrameHeader(),WebSocketPayload = new byte[0]}; |
964 | public WebsocketFrameHeader Header; | 964 | public WebsocketFrameHeader Header; |
965 | public byte[] WebSocketPayload; | 965 | public byte[] WebSocketPayload; |
966 | 966 | ||
967 | public byte[] ToBytes() | 967 | public byte[] ToBytes() |
968 | { | 968 | { |
969 | Header.PayloadLen = (ulong)WebSocketPayload.Length; | 969 | Header.PayloadLen = (ulong)WebSocketPayload.Length; |
@@ -991,7 +991,7 @@ dec 0 1 2 3 | |||
991 | public int Mask; | 991 | public int Mask; |
992 | /* | 992 | /* |
993 | byt 0 1 2 3 | 993 | byt 0 1 2 3 |
994 | 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 | 994 | 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
995 | +---------------+---------------+---------------+---------------+ | 995 | +---------------+---------------+---------------+---------------+ |
996 | | Octal 1 | Octal 2 | Octal 3 | Octal 4 | | 996 | | Octal 1 | Octal 2 | Octal 3 | Octal 4 | |
997 | +---------------+---------------+---------------+---------------+ | 997 | +---------------+---------------+---------------+---------------+ |
@@ -1002,11 +1002,11 @@ byt 0 1 2 3 | |||
1002 | 1002 | ||
1003 | public UInt64 PayloadLen; | 1003 | public UInt64 PayloadLen; |
1004 | //public UInt64 PayloadLeft; | 1004 | //public UInt64 PayloadLeft; |
1005 | // Payload is X + Y | 1005 | // Payload is X + Y |
1006 | //public UInt64 ExtensionDataLength; | 1006 | //public UInt64 ExtensionDataLength; |
1007 | //public UInt64 ApplicationDataLength; | 1007 | //public UInt64 ApplicationDataLength; |
1008 | public static readonly WebsocketFrameHeader ZeroHeader = WebsocketFrameHeader.HeaderDefault(); | 1008 | public static readonly WebsocketFrameHeader ZeroHeader = WebsocketFrameHeader.HeaderDefault(); |
1009 | 1009 | ||
1010 | public void SetDefault() | 1010 | public void SetDefault() |
1011 | { | 1011 | { |
1012 | 1012 | ||
@@ -1025,16 +1025,16 @@ byt 0 1 2 3 | |||
1025 | /// <summary> | 1025 | /// <summary> |
1026 | /// Returns a byte array representing the Frame header | 1026 | /// Returns a byte array representing the Frame header |
1027 | /// </summary> | 1027 | /// </summary> |
1028 | /// <param name="payload">This is the frame data payload. The header describes the size of the payload. | 1028 | /// <param name="payload">This is the frame data payload. The header describes the size of the payload. |
1029 | /// If payload is null, a Zero sized payload is assumed</param> | 1029 | /// If payload is null, a Zero sized payload is assumed</param> |
1030 | /// <returns>Returns a byte array representing the frame header</returns> | 1030 | /// <returns>Returns a byte array representing the frame header</returns> |
1031 | public byte[] ToBytes(byte[] payload) | 1031 | public byte[] ToBytes(byte[] payload) |
1032 | { | 1032 | { |
1033 | List<byte> result = new List<byte>(); | 1033 | List<byte> result = new List<byte>(); |
1034 | 1034 | ||
1035 | // Squeeze in our opcode and our ending bit. | 1035 | // Squeeze in our opcode and our ending bit. |
1036 | result.Add((byte)((byte)Opcode | (IsEnd?0x80:0x00) )); | 1036 | result.Add((byte)((byte)Opcode | (IsEnd?0x80:0x00) )); |
1037 | 1037 | ||
1038 | // Again with the three different byte interpretations of size.. | 1038 | // Again with the three different byte interpretations of size.. |
1039 | 1039 | ||
1040 | //bytesize | 1040 | //bytesize |
@@ -1056,7 +1056,7 @@ byt 0 1 2 3 | |||
1056 | Array.Reverse(payloadLengthByte); | 1056 | Array.Reverse(payloadLengthByte); |
1057 | result.AddRange(payloadLengthByte); | 1057 | result.AddRange(payloadLengthByte); |
1058 | } | 1058 | } |
1059 | 1059 | ||
1060 | // Only add a payload if it's not null | 1060 | // Only add a payload if it's not null |
1061 | if (payload != null) | 1061 | if (payload != null) |
1062 | { | 1062 | { |
@@ -1155,5 +1155,5 @@ byt 0 1 2 3 | |||
1155 | 1155 | ||
1156 | } | 1156 | } |
1157 | 1157 | ||
1158 | 1158 | ||
1159 | } | 1159 | } |
diff --git a/OpenSim/Framework/Servers/HttpServer/XmlRpcBasicDOSProtector.cs b/OpenSim/Framework/Servers/HttpServer/XmlRpcBasicDOSProtector.cs index f212208..6b2c0ab 100644 --- a/OpenSim/Framework/Servers/HttpServer/XmlRpcBasicDOSProtector.cs +++ b/OpenSim/Framework/Servers/HttpServer/XmlRpcBasicDOSProtector.cs | |||
@@ -36,7 +36,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
36 | { | 36 | { |
37 | private readonly XmlRpcMethod _normalMethod; | 37 | private readonly XmlRpcMethod _normalMethod; |
38 | private readonly XmlRpcMethod _throttledMethod; | 38 | private readonly XmlRpcMethod _throttledMethod; |
39 | 39 | ||
40 | private readonly BasicDosProtectorOptions _options; | 40 | private readonly BasicDosProtectorOptions _options; |
41 | private readonly BasicDOSProtector _dosProtector; | 41 | private readonly BasicDOSProtector _dosProtector; |
42 | 42 | ||
@@ -44,7 +44,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
44 | { | 44 | { |
45 | _normalMethod = normalMethod; | 45 | _normalMethod = normalMethod; |
46 | _throttledMethod = throttledMethod; | 46 | _throttledMethod = throttledMethod; |
47 | 47 | ||
48 | _options = options; | 48 | _options = options; |
49 | _dosProtector = new BasicDOSProtector(_options); | 49 | _dosProtector = new BasicDOSProtector(_options); |
50 | 50 | ||
@@ -87,5 +87,5 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
87 | 87 | ||
88 | } | 88 | } |
89 | 89 | ||
90 | 90 | ||
91 | } | 91 | } |
diff --git a/OpenSim/Framework/Servers/MainServer.cs b/OpenSim/Framework/Servers/MainServer.cs index 57931d4..9b1d906 100644 --- a/OpenSim/Framework/Servers/MainServer.cs +++ b/OpenSim/Framework/Servers/MainServer.cs | |||
@@ -223,11 +223,11 @@ namespace OpenSim.Framework.Servers | |||
223 | { | 223 | { |
224 | handlers.AppendFormat( | 224 | handlers.AppendFormat( |
225 | "Registered HTTP Handlers for server at {0}:{1}\n", httpServer.ListenIPAddress, httpServer.Port); | 225 | "Registered HTTP Handlers for server at {0}:{1}\n", httpServer.ListenIPAddress, httpServer.Port); |
226 | 226 | ||
227 | handlers.AppendFormat("* XMLRPC:\n"); | 227 | handlers.AppendFormat("* XMLRPC:\n"); |
228 | foreach (String s in httpServer.GetXmlRpcHandlerKeys()) | 228 | foreach (String s in httpServer.GetXmlRpcHandlerKeys()) |
229 | handlers.AppendFormat("\t{0}\n", s); | 229 | handlers.AppendFormat("\t{0}\n", s); |
230 | 230 | ||
231 | handlers.AppendFormat("* HTTP:\n"); | 231 | handlers.AppendFormat("* HTTP:\n"); |
232 | foreach (String s in httpServer.GetHTTPHandlerKeys()) | 232 | foreach (String s in httpServer.GetHTTPHandlerKeys()) |
233 | handlers.AppendFormat("\t{0}\n", s); | 233 | handlers.AppendFormat("\t{0}\n", s); |
@@ -235,19 +235,19 @@ namespace OpenSim.Framework.Servers | |||
235 | handlers.AppendFormat("* HTTP (poll):\n"); | 235 | handlers.AppendFormat("* HTTP (poll):\n"); |
236 | foreach (String s in httpServer.GetPollServiceHandlerKeys()) | 236 | foreach (String s in httpServer.GetPollServiceHandlerKeys()) |
237 | handlers.AppendFormat("\t{0}\n", s); | 237 | handlers.AppendFormat("\t{0}\n", s); |
238 | 238 | ||
239 | handlers.AppendFormat("* JSONRPC:\n"); | 239 | handlers.AppendFormat("* JSONRPC:\n"); |
240 | foreach (String s in httpServer.GetJsonRpcHandlerKeys()) | 240 | foreach (String s in httpServer.GetJsonRpcHandlerKeys()) |
241 | handlers.AppendFormat("\t{0}\n", s); | 241 | handlers.AppendFormat("\t{0}\n", s); |
242 | 242 | ||
243 | // handlers.AppendFormat("* Agent:\n"); | 243 | // handlers.AppendFormat("* Agent:\n"); |
244 | // foreach (String s in httpServer.GetAgentHandlerKeys()) | 244 | // foreach (String s in httpServer.GetAgentHandlerKeys()) |
245 | // handlers.AppendFormat("\t{0}\n", s); | 245 | // handlers.AppendFormat("\t{0}\n", s); |
246 | 246 | ||
247 | handlers.AppendFormat("* LLSD:\n"); | 247 | handlers.AppendFormat("* LLSD:\n"); |
248 | foreach (String s in httpServer.GetLLSDHandlerKeys()) | 248 | foreach (String s in httpServer.GetLLSDHandlerKeys()) |
249 | handlers.AppendFormat("\t{0}\n", s); | 249 | handlers.AppendFormat("\t{0}\n", s); |
250 | 250 | ||
251 | handlers.AppendFormat("* StreamHandlers ({0}):\n", httpServer.GetStreamHandlerKeys().Count); | 251 | handlers.AppendFormat("* StreamHandlers ({0}):\n", httpServer.GetStreamHandlerKeys().Count); |
252 | foreach (String s in httpServer.GetStreamHandlerKeys()) | 252 | foreach (String s in httpServer.GetStreamHandlerKeys()) |
253 | handlers.AppendFormat("\t{0}\n", s); | 253 | handlers.AppendFormat("\t{0}\n", s); |
@@ -334,7 +334,7 @@ namespace OpenSim.Framework.Servers | |||
334 | { | 334 | { |
335 | if (port == 0) | 335 | if (port == 0) |
336 | return Instance; | 336 | return Instance; |
337 | 337 | ||
338 | if (instance != null && port == Instance.Port) | 338 | if (instance != null && port == Instance.Port) |
339 | return Instance; | 339 | return Instance; |
340 | 340 | ||
@@ -353,5 +353,17 @@ namespace OpenSim.Framework.Servers | |||
353 | return m_Servers[port]; | 353 | return m_Servers[port]; |
354 | } | 354 | } |
355 | } | 355 | } |
356 | |||
357 | public static void Stop() | ||
358 | { | ||
359 | lock (m_Servers) | ||
360 | { | ||
361 | foreach (BaseHttpServer httpServer in m_Servers.Values) | ||
362 | { | ||
363 | httpServer.Stop(); | ||
364 | } | ||
365 | } | ||
366 | } | ||
367 | |||
356 | } | 368 | } |
357 | } \ No newline at end of file | 369 | } \ No newline at end of file |
diff --git a/OpenSim/Framework/Servers/Properties/AssemblyInfo.cs b/OpenSim/Framework/Servers/Properties/AssemblyInfo.cs index 792c62e..4469e7c 100644 --- a/OpenSim/Framework/Servers/Properties/AssemblyInfo.cs +++ b/OpenSim/Framework/Servers/Properties/AssemblyInfo.cs | |||
@@ -2,7 +2,7 @@ | |||
2 | using System.Runtime.CompilerServices; | 2 | using System.Runtime.CompilerServices; |
3 | using System.Runtime.InteropServices; | 3 | using System.Runtime.InteropServices; |
4 | 4 | ||
5 | // General Information about an assembly is controlled through the following | 5 | // General Information about an assembly is controlled through the following |
6 | // set of attributes. Change these attribute values to modify the information | 6 | // set of attributes. Change these attribute values to modify the information |
7 | // associated with an assembly. | 7 | // associated with an assembly. |
8 | [assembly: AssemblyTitle("OpenSim.Framework.Servers")] | 8 | [assembly: AssemblyTitle("OpenSim.Framework.Servers")] |
@@ -14,8 +14,8 @@ using System.Runtime.InteropServices; | |||
14 | [assembly: AssemblyTrademark("")] | 14 | [assembly: AssemblyTrademark("")] |
15 | [assembly: AssemblyCulture("")] | 15 | [assembly: AssemblyCulture("")] |
16 | 16 | ||
17 | // Setting ComVisible to false makes the types in this assembly not visible | 17 | // Setting ComVisible to false makes the types in this assembly not visible |
18 | // to COM components. If you need to access a type in this assembly from | 18 | // to COM components. If you need to access a type in this assembly from |
19 | // COM, set the ComVisible attribute to true on that type. | 19 | // COM, set the ComVisible attribute to true on that type. |
20 | [assembly: ComVisible(false)] | 20 | [assembly: ComVisible(false)] |
21 | 21 | ||
@@ -25,7 +25,7 @@ using System.Runtime.InteropServices; | |||
25 | // Version information for an assembly consists of the following four values: | 25 | // Version information for an assembly consists of the following four values: |
26 | // | 26 | // |
27 | // Major Version | 27 | // Major Version |
28 | // Minor Version | 28 | // Minor Version |
29 | // Build Number | 29 | // Build Number |
30 | // Revision | 30 | // Revision |
31 | // | 31 | // |
diff --git a/OpenSim/Framework/Servers/ServerBase.cs b/OpenSim/Framework/Servers/ServerBase.cs index 07a09e6..3c2dce8 100644 --- a/OpenSim/Framework/Servers/ServerBase.cs +++ b/OpenSim/Framework/Servers/ServerBase.cs | |||
@@ -56,7 +56,8 @@ namespace OpenSim.Framework.Servers | |||
56 | protected ICommandConsole m_console; | 56 | protected ICommandConsole m_console; |
57 | 57 | ||
58 | protected OpenSimAppender m_consoleAppender; | 58 | protected OpenSimAppender m_consoleAppender; |
59 | protected FileAppender m_logFileAppender; | 59 | protected FileAppender m_logFileAppender; |
60 | protected FileAppender m_statsLogFileAppender; | ||
60 | 61 | ||
61 | protected DateTime m_startuptime; | 62 | protected DateTime m_startuptime; |
62 | protected string m_startupDirectory = Environment.CurrentDirectory; | 63 | protected string m_startupDirectory = Environment.CurrentDirectory; |
@@ -81,7 +82,7 @@ namespace OpenSim.Framework.Servers | |||
81 | { | 82 | { |
82 | if (File.Exists(path)) | 83 | if (File.Exists(path)) |
83 | m_log.ErrorFormat( | 84 | m_log.ErrorFormat( |
84 | "[SERVER BASE]: Previous pid file {0} still exists on startup. Possibly previously unclean shutdown.", | 85 | "[SERVER BASE]: Previous pid file {0} still exists on startup. Possibly previously unclean shutdown.", |
85 | path); | 86 | path); |
86 | 87 | ||
87 | try | 88 | try |
@@ -103,7 +104,7 @@ namespace OpenSim.Framework.Servers | |||
103 | m_log.Warn(string.Format("[SERVER BASE]: Could not create PID file at {0} ", path), e); | 104 | m_log.Warn(string.Format("[SERVER BASE]: Could not create PID file at {0} ", path), e); |
104 | } | 105 | } |
105 | } | 106 | } |
106 | 107 | ||
107 | protected void RemovePIDFile() | 108 | protected void RemovePIDFile() |
108 | { | 109 | { |
109 | if (m_pidFile != String.Empty) | 110 | if (m_pidFile != String.Empty) |
@@ -156,6 +157,10 @@ namespace OpenSim.Framework.Servers | |||
156 | { | 157 | { |
157 | m_logFileAppender = (FileAppender)appender; | 158 | m_logFileAppender = (FileAppender)appender; |
158 | } | 159 | } |
160 | else if (appender.Name == "StatsLogFileAppender") | ||
161 | { | ||
162 | m_statsLogFileAppender = (FileAppender)appender; | ||
163 | } | ||
159 | } | 164 | } |
160 | 165 | ||
161 | if (null == m_consoleAppender) | 166 | if (null == m_consoleAppender) |
@@ -166,11 +171,11 @@ namespace OpenSim.Framework.Servers | |||
166 | { | 171 | { |
167 | // FIXME: This should be done through an interface rather than casting. | 172 | // FIXME: This should be done through an interface rather than casting. |
168 | m_consoleAppender.Console = (ConsoleBase)m_console; | 173 | m_consoleAppender.Console = (ConsoleBase)m_console; |
169 | 174 | ||
170 | // If there is no threshold set then the threshold is effectively everything. | 175 | // If there is no threshold set then the threshold is effectively everything. |
171 | if (null == m_consoleAppender.Threshold) | 176 | if (null == m_consoleAppender.Threshold) |
172 | m_consoleAppender.Threshold = Level.All; | 177 | m_consoleAppender.Threshold = Level.All; |
173 | 178 | ||
174 | Notice(String.Format("Console log level is {0}", m_consoleAppender.Threshold)); | 179 | Notice(String.Format("Console log level is {0}", m_consoleAppender.Threshold)); |
175 | } | 180 | } |
176 | 181 | ||
@@ -185,6 +190,18 @@ namespace OpenSim.Framework.Servers | |||
185 | 190 | ||
186 | m_log.InfoFormat("[SERVER BASE]: Logging started to file {0}", m_logFileAppender.File); | 191 | m_log.InfoFormat("[SERVER BASE]: Logging started to file {0}", m_logFileAppender.File); |
187 | } | 192 | } |
193 | |||
194 | if (m_statsLogFileAppender != null && startupConfig != null) | ||
195 | { | ||
196 | string cfgStatsFileName = startupConfig.GetString("StatsLogFile", null); | ||
197 | if (cfgStatsFileName != null) | ||
198 | { | ||
199 | m_statsLogFileAppender.File = cfgStatsFileName; | ||
200 | m_statsLogFileAppender.ActivateOptions(); | ||
201 | } | ||
202 | |||
203 | m_log.InfoFormat("[SERVER BASE]: Stats Logging started to file {0}", m_statsLogFileAppender.File); | ||
204 | } | ||
188 | } | 205 | } |
189 | 206 | ||
190 | /// <summary> | 207 | /// <summary> |
@@ -205,11 +222,11 @@ namespace OpenSim.Framework.Servers | |||
205 | "General", false, "show uptime", "show uptime", "Show server uptime", HandleShow); | 222 | "General", false, "show uptime", "show uptime", "Show server uptime", HandleShow); |
206 | 223 | ||
207 | m_console.Commands.AddCommand( | 224 | m_console.Commands.AddCommand( |
208 | "General", false, "get log level", "get log level", "Get the current console logging level", | 225 | "General", false, "get log level", "get log level", "Get the current console logging level", |
209 | (mod, cmd) => ShowLogLevel()); | 226 | (mod, cmd) => ShowLogLevel()); |
210 | 227 | ||
211 | m_console.Commands.AddCommand( | 228 | m_console.Commands.AddCommand( |
212 | "General", false, "set log level", "set log level <level>", | 229 | "General", false, "set log level", "set log level <level>", |
213 | "Set the console logging level for this session.", HandleSetLogLevel); | 230 | "Set the console logging level for this session.", HandleSetLogLevel); |
214 | 231 | ||
215 | m_console.Commands.AddCommand( | 232 | m_console.Commands.AddCommand( |
@@ -222,14 +239,14 @@ namespace OpenSim.Framework.Servers | |||
222 | "config get [<section>] [<key>]", | 239 | "config get [<section>] [<key>]", |
223 | "Synonym for config show", | 240 | "Synonym for config show", |
224 | HandleConfig); | 241 | HandleConfig); |
225 | 242 | ||
226 | m_console.Commands.AddCommand( | 243 | m_console.Commands.AddCommand( |
227 | "General", false, "config show", | 244 | "General", false, "config show", |
228 | "config show [<section>] [<key>]", | 245 | "config show [<section>] [<key>]", |
229 | "Show config information", | 246 | "Show config information", |
230 | "If neither section nor field are specified, then the whole current configuration is printed." + Environment.NewLine | 247 | "If neither section nor field are specified, then the whole current configuration is printed." + Environment.NewLine |
231 | + "If a section is given but not a field, then all fields in that section are printed.", | 248 | + "If a section is given but not a field, then all fields in that section are printed.", |
232 | HandleConfig); | 249 | HandleConfig); |
233 | 250 | ||
234 | m_console.Commands.AddCommand( | 251 | m_console.Commands.AddCommand( |
235 | "General", false, "config save", | 252 | "General", false, "config save", |
@@ -258,18 +275,6 @@ namespace OpenSim.Framework.Servers | |||
258 | (string module, string[] args) => Notice(GetThreadsReport())); | 275 | (string module, string[] args) => Notice(GetThreadsReport())); |
259 | 276 | ||
260 | m_console.Commands.AddCommand ( | 277 | m_console.Commands.AddCommand ( |
261 | "Debug", false, "debug comms set", | ||
262 | "debug comms set serialosdreq true|false", | ||
263 | "Set comms parameters. For debug purposes.", | ||
264 | HandleDebugCommsSet); | ||
265 | |||
266 | m_console.Commands.AddCommand ( | ||
267 | "Debug", false, "debug comms status", | ||
268 | "debug comms status", | ||
269 | "Show current debug comms parameters.", | ||
270 | HandleDebugCommsStatus); | ||
271 | |||
272 | m_console.Commands.AddCommand ( | ||
273 | "Debug", false, "debug threadpool set", | 278 | "Debug", false, "debug threadpool set", |
274 | "debug threadpool set worker|iocp min|max <n>", | 279 | "debug threadpool set worker|iocp min|max <n>", |
275 | "Set threadpool parameters. For debug purposes.", | 280 | "Set threadpool parameters. For debug purposes.", |
@@ -280,7 +285,7 @@ namespace OpenSim.Framework.Servers | |||
280 | "debug threadpool status", | 285 | "debug threadpool status", |
281 | "Show current debug threadpool parameters.", | 286 | "Show current debug threadpool parameters.", |
282 | HandleDebugThreadpoolStatus); | 287 | HandleDebugThreadpoolStatus); |
283 | 288 | ||
284 | m_console.Commands.AddCommand( | 289 | m_console.Commands.AddCommand( |
285 | "Debug", false, "debug threadpool level", | 290 | "Debug", false, "debug threadpool level", |
286 | "debug threadpool level 0.." + Util.MAX_THREADPOOL_LEVEL, | 291 | "debug threadpool level 0.." + Util.MAX_THREADPOOL_LEVEL, |
@@ -326,47 +331,13 @@ namespace OpenSim.Framework.Servers | |||
326 | 331 | ||
327 | public void RegisterCommonComponents(IConfigSource configSource) | 332 | public void RegisterCommonComponents(IConfigSource configSource) |
328 | { | 333 | { |
329 | IConfig networkConfig = configSource.Configs["Network"]; | 334 | // IConfig networkConfig = configSource.Configs["Network"]; |
330 | 335 | ||
331 | if (networkConfig != null) | ||
332 | { | ||
333 | WebUtil.SerializeOSDRequestsPerEndpoint = networkConfig.GetBoolean("SerializeOSDRequests", false); | ||
334 | } | ||
335 | |||
336 | m_serverStatsCollector = new ServerStatsCollector(); | 336 | m_serverStatsCollector = new ServerStatsCollector(); |
337 | m_serverStatsCollector.Initialise(configSource); | 337 | m_serverStatsCollector.Initialise(configSource); |
338 | m_serverStatsCollector.Start(); | 338 | m_serverStatsCollector.Start(); |
339 | } | 339 | } |
340 | 340 | ||
341 | private void HandleDebugCommsStatus(string module, string[] args) | ||
342 | { | ||
343 | Notice("serialosdreq is {0}", WebUtil.SerializeOSDRequestsPerEndpoint); | ||
344 | } | ||
345 | |||
346 | private void HandleDebugCommsSet(string module, string[] args) | ||
347 | { | ||
348 | if (args.Length != 5) | ||
349 | { | ||
350 | Notice("Usage: debug comms set serialosdreq true|false"); | ||
351 | return; | ||
352 | } | ||
353 | |||
354 | if (args[3] != "serialosdreq") | ||
355 | { | ||
356 | Notice("Usage: debug comms set serialosdreq true|false"); | ||
357 | return; | ||
358 | } | ||
359 | |||
360 | bool setSerializeOsdRequests; | ||
361 | |||
362 | if (!ConsoleUtil.TryParseConsoleBool(m_console, args[4], out setSerializeOsdRequests)) | ||
363 | return; | ||
364 | |||
365 | WebUtil.SerializeOSDRequestsPerEndpoint = setSerializeOsdRequests; | ||
366 | |||
367 | Notice("serialosdreq is now {0}", setSerializeOsdRequests); | ||
368 | } | ||
369 | |||
370 | private void HandleShowThreadpoolCallsActive(string module, string[] args) | 341 | private void HandleShowThreadpoolCallsActive(string module, string[] args) |
371 | { | 342 | { |
372 | List<KeyValuePair<string, int>> calls = Util.GetFireAndForgetCallsInProgress().ToList(); | 343 | List<KeyValuePair<string, int>> calls = Util.GetFireAndForgetCallsInProgress().ToList(); |
@@ -432,7 +403,7 @@ namespace OpenSim.Framework.Servers | |||
432 | 403 | ||
433 | ThreadPool.GetAvailableThreads(out workerThreads, out iocpThreads); | 404 | ThreadPool.GetAvailableThreads(out workerThreads, out iocpThreads); |
434 | Notice("Available worker threads: {0}", workerThreads); | 405 | Notice("Available worker threads: {0}", workerThreads); |
435 | Notice("Available IOCP threads: {0}", iocpThreads); | 406 | Notice("Available IOCP threads: {0}", iocpThreads); |
436 | } | 407 | } |
437 | 408 | ||
438 | private void HandleDebugThreadpoolSet(string module, string[] args) | 409 | private void HandleDebugThreadpoolSet(string module, string[] args) |
@@ -488,7 +459,7 @@ namespace OpenSim.Framework.Servers | |||
488 | fail = true; | 459 | fail = true; |
489 | } | 460 | } |
490 | } | 461 | } |
491 | 462 | ||
492 | if (fail) | 463 | if (fail) |
493 | { | 464 | { |
494 | Notice("ERROR: Could not set {0} {1} threads to {2}", poolType, bound, newThreads); | 465 | Notice("ERROR: Could not set {0} {1} threads to {2}", poolType, bound, newThreads); |
@@ -582,7 +553,7 @@ namespace OpenSim.Framework.Servers | |||
582 | if (cmdparams.Length > 0) | 553 | if (cmdparams.Length > 0) |
583 | { | 554 | { |
584 | string firstParam = cmdparams[0].ToLower(); | 555 | string firstParam = cmdparams[0].ToLower(); |
585 | 556 | ||
586 | switch (firstParam) | 557 | switch (firstParam) |
587 | { | 558 | { |
588 | case "set": | 559 | case "set": |
@@ -633,12 +604,12 @@ namespace OpenSim.Framework.Servers | |||
633 | { | 604 | { |
634 | Notice("[{0}]", config.Name); | 605 | Notice("[{0}]", config.Name); |
635 | foreach (string key in config.GetKeys()) | 606 | foreach (string key in config.GetKeys()) |
636 | Notice(" {0} = {1}", key, config.GetString(key)); | 607 | Notice(" {0} = {1}", key, config.GetString(key)); |
637 | } | 608 | } |
638 | else | 609 | else |
639 | { | 610 | { |
640 | Notice( | 611 | Notice( |
641 | "config get {0} {1} : {2}", | 612 | "config get {0} {1} : {2}", |
642 | cmdparams[1], cmdparams[2], config.GetString(cmdparams[2])); | 613 | cmdparams[1], cmdparams[2], config.GetString(cmdparams[2])); |
643 | } | 614 | } |
644 | } | 615 | } |
@@ -692,10 +663,10 @@ namespace OpenSim.Framework.Servers | |||
692 | } | 663 | } |
693 | 664 | ||
694 | string rawLevel = cmd[3]; | 665 | string rawLevel = cmd[3]; |
695 | 666 | ||
696 | ILoggerRepository repository = LogManager.GetRepository(); | 667 | ILoggerRepository repository = LogManager.GetRepository(); |
697 | Level consoleLevel = repository.LevelMap[rawLevel]; | 668 | Level consoleLevel = repository.LevelMap[rawLevel]; |
698 | 669 | ||
699 | if (consoleLevel != null) | 670 | if (consoleLevel != null) |
700 | m_consoleAppender.Threshold = consoleLevel; | 671 | m_consoleAppender.Threshold = consoleLevel; |
701 | else | 672 | else |
@@ -770,9 +741,9 @@ namespace OpenSim.Framework.Servers | |||
770 | protected void ShowInfo() | 741 | protected void ShowInfo() |
771 | { | 742 | { |
772 | Notice(GetVersionText()); | 743 | Notice(GetVersionText()); |
773 | Notice("Startup directory: " + m_startupDirectory); | 744 | Notice("Startup directory: " + m_startupDirectory); |
774 | if (null != m_consoleAppender) | 745 | if (null != m_consoleAppender) |
775 | Notice(String.Format("Console log level: {0}", m_consoleAppender.Threshold)); | 746 | Notice(String.Format("Console log level: {0}", m_consoleAppender.Threshold)); |
776 | } | 747 | } |
777 | 748 | ||
778 | /// <summary> | 749 | /// <summary> |
@@ -842,7 +813,7 @@ namespace OpenSim.Framework.Servers | |||
842 | { | 813 | { |
843 | StreamReader RevisionFile = File.OpenText(svnRevisionFileName); | 814 | StreamReader RevisionFile = File.OpenText(svnRevisionFileName); |
844 | buildVersion = RevisionFile.ReadLine(); | 815 | buildVersion = RevisionFile.ReadLine(); |
845 | buildVersion.Trim(); | 816 | buildVersion = buildVersion.Trim(); |
846 | RevisionFile.Close(); | 817 | RevisionFile.Close(); |
847 | } | 818 | } |
848 | 819 | ||
@@ -871,9 +842,9 @@ namespace OpenSim.Framework.Servers | |||
871 | } | 842 | } |
872 | } | 843 | } |
873 | 844 | ||
874 | protected string GetVersionText() | 845 | public string GetVersionText() |
875 | { | 846 | { |
876 | return String.Format("Version: {0} (SIMULATION/{1} - SIMULATION/{2})", | 847 | return String.Format("Version: {0} (SIMULATION/{1} - SIMULATION/{2})", |
877 | m_version, VersionInfo.SimulationServiceVersionSupportedMin, VersionInfo.SimulationServiceVersionSupportedMax); | 848 | m_version, VersionInfo.SimulationServiceVersionSupportedMin, VersionInfo.SimulationServiceVersionSupportedMax); |
878 | } | 849 | } |
879 | 850 | ||
@@ -898,7 +869,7 @@ namespace OpenSim.Framework.Servers | |||
898 | foreach (Watchdog.ThreadWatchdogInfo twi in threads) | 869 | foreach (Watchdog.ThreadWatchdogInfo twi in threads) |
899 | { | 870 | { |
900 | Thread t = twi.Thread; | 871 | Thread t = twi.Thread; |
901 | 872 | ||
902 | sb.AppendFormat( | 873 | sb.AppendFormat( |
903 | reportFormat, | 874 | reportFormat, |
904 | t.ManagedThreadId, | 875 | t.ManagedThreadId, |
@@ -911,16 +882,12 @@ namespace OpenSim.Framework.Servers | |||
911 | sb.Append("\n"); | 882 | sb.Append("\n"); |
912 | } | 883 | } |
913 | 884 | ||
914 | sb.Append("\n"); | 885 | sb.Append(GetThreadPoolReport()); |
915 | 886 | ||
916 | // For some reason mono 2.6.7 returns an empty threads set! Not going to confuse people by reporting | 887 | sb.Append("\n"); |
917 | // zero active threads. | ||
918 | int totalThreads = Process.GetCurrentProcess().Threads.Count; | 888 | int totalThreads = Process.GetCurrentProcess().Threads.Count; |
919 | if (totalThreads > 0) | 889 | if (totalThreads > 0) |
920 | sb.AppendFormat("Total threads active: {0}\n\n", totalThreads); | 890 | sb.AppendFormat("Total process threads active: {0}\n\n", totalThreads); |
921 | |||
922 | sb.Append("Main threadpool (excluding script engine pools)\n"); | ||
923 | sb.Append(GetThreadPoolReport()); | ||
924 | 891 | ||
925 | return sb.ToString(); | 892 | return sb.ToString(); |
926 | } | 893 | } |
@@ -931,15 +898,46 @@ namespace OpenSim.Framework.Servers | |||
931 | /// <returns></returns> | 898 | /// <returns></returns> |
932 | public static string GetThreadPoolReport() | 899 | public static string GetThreadPoolReport() |
933 | { | 900 | { |
901 | |||
902 | StringBuilder sb = new StringBuilder(); | ||
903 | |||
904 | // framework pool is alwasy active | ||
905 | int maxWorkers; | ||
906 | int minWorkers; | ||
907 | int curWorkers; | ||
908 | int maxComp; | ||
909 | int minComp; | ||
910 | int curComp; | ||
911 | |||
912 | try | ||
913 | { | ||
914 | ThreadPool.GetMaxThreads(out maxWorkers, out maxComp); | ||
915 | ThreadPool.GetMinThreads(out minWorkers, out minComp); | ||
916 | ThreadPool.GetAvailableThreads(out curWorkers, out curComp); | ||
917 | curWorkers = maxWorkers - curWorkers; | ||
918 | curComp = maxComp - curComp; | ||
919 | |||
920 | sb.Append("\nFramework main threadpool \n"); | ||
921 | sb.AppendFormat("workers: {0} ({1} / {2})\n", curWorkers, maxWorkers, minWorkers); | ||
922 | sb.AppendFormat("Completion: {0} ({1} / {2})\n", curComp, maxComp, minComp); | ||
923 | } | ||
924 | catch { } | ||
925 | |||
926 | if ( | ||
927 | Util.FireAndForgetMethod == FireAndForgetMethod.QueueUserWorkItem | ||
928 | || Util.FireAndForgetMethod == FireAndForgetMethod.UnsafeQueueUserWorkItem) | ||
929 | { | ||
930 | sb.AppendFormat("\nThread pool used: Framework main threadpool\n"); | ||
931 | return sb.ToString(); | ||
932 | } | ||
933 | |||
934 | string threadPoolUsed = null; | 934 | string threadPoolUsed = null; |
935 | int maxThreads = 0; | 935 | int maxThreads = 0; |
936 | int minThreads = 0; | 936 | int minThreads = 0; |
937 | int allocatedThreads = 0; | 937 | int allocatedThreads = 0; |
938 | int inUseThreads = 0; | 938 | int inUseThreads = 0; |
939 | int waitingCallbacks = 0; | 939 | int waitingCallbacks = 0; |
940 | int completionPortThreads = 0; | ||
941 | 940 | ||
942 | StringBuilder sb = new StringBuilder(); | ||
943 | if (Util.FireAndForgetMethod == FireAndForgetMethod.SmartThreadPool) | 941 | if (Util.FireAndForgetMethod == FireAndForgetMethod.SmartThreadPool) |
944 | { | 942 | { |
945 | STPInfo stpi = Util.GetSmartThreadPoolInfo(); | 943 | STPInfo stpi = Util.GetSmartThreadPoolInfo(); |
@@ -955,22 +953,10 @@ namespace OpenSim.Framework.Servers | |||
955 | waitingCallbacks = stpi.WaitingCallbacks; | 953 | waitingCallbacks = stpi.WaitingCallbacks; |
956 | } | 954 | } |
957 | } | 955 | } |
958 | else if ( | 956 | |
959 | Util.FireAndForgetMethod == FireAndForgetMethod.QueueUserWorkItem | ||
960 | || Util.FireAndForgetMethod == FireAndForgetMethod.UnsafeQueueUserWorkItem) | ||
961 | { | ||
962 | threadPoolUsed = "BuiltInThreadPool"; | ||
963 | ThreadPool.GetMaxThreads(out maxThreads, out completionPortThreads); | ||
964 | ThreadPool.GetMinThreads(out minThreads, out completionPortThreads); | ||
965 | int availableThreads; | ||
966 | ThreadPool.GetAvailableThreads(out availableThreads, out completionPortThreads); | ||
967 | inUseThreads = maxThreads - availableThreads; | ||
968 | allocatedThreads = -1; | ||
969 | waitingCallbacks = -1; | ||
970 | } | ||
971 | |||
972 | if (threadPoolUsed != null) | 957 | if (threadPoolUsed != null) |
973 | { | 958 | { |
959 | sb.Append("\nThreadpool (excluding script engine pools)\n"); | ||
974 | sb.AppendFormat("Thread pool used : {0}\n", threadPoolUsed); | 960 | sb.AppendFormat("Thread pool used : {0}\n", threadPoolUsed); |
975 | sb.AppendFormat("Max threads : {0}\n", maxThreads); | 961 | sb.AppendFormat("Max threads : {0}\n", maxThreads); |
976 | sb.AppendFormat("Min threads : {0}\n", minThreads); | 962 | sb.AppendFormat("Min threads : {0}\n", minThreads); |
@@ -1005,7 +991,7 @@ namespace OpenSim.Framework.Servers | |||
1005 | MainConsole.Instance.OutputFormat("Aborted thread with id {0}", threadId); | 991 | MainConsole.Instance.OutputFormat("Aborted thread with id {0}", threadId); |
1006 | else | 992 | else |
1007 | MainConsole.Instance.OutputFormat("ERROR - Thread with id {0} not found in managed threads", threadId); | 993 | MainConsole.Instance.OutputFormat("ERROR - Thread with id {0} not found in managed threads", threadId); |
1008 | } | 994 | } |
1009 | 995 | ||
1010 | /// <summary> | 996 | /// <summary> |
1011 | /// Console output is only possible if a console has been established. | 997 | /// Console output is only possible if a console has been established. |
@@ -1020,13 +1006,13 @@ namespace OpenSim.Framework.Servers | |||
1020 | m_console.Output(msg); | 1006 | m_console.Output(msg); |
1021 | } | 1007 | } |
1022 | } | 1008 | } |
1023 | 1009 | ||
1024 | /// <summary> | 1010 | /// <summary> |
1025 | /// Console output is only possible if a console has been established. | 1011 | /// Console output is only possible if a console has been established. |
1026 | /// That is something that cannot be determined within this class. So | 1012 | /// That is something that cannot be determined within this class. So |
1027 | /// all attempts to use the console MUST be verified. | 1013 | /// all attempts to use the console MUST be verified. |
1028 | /// </summary> | 1014 | /// </summary> |
1029 | /// <param name="format"></param> | 1015 | /// <param name="format"></param> |
1030 | /// <param name="components"></param> | 1016 | /// <param name="components"></param> |
1031 | protected void Notice(string format, params object[] components) | 1017 | protected void Notice(string format, params object[] components) |
1032 | { | 1018 | { |
diff --git a/OpenSim/Framework/Servers/Tests/OSHttpTests.cs b/OpenSim/Framework/Servers/Tests/OSHttpTests.cs index 5c0e0df..e5f7043 100644 --- a/OpenSim/Framework/Servers/Tests/OSHttpTests.cs +++ b/OpenSim/Framework/Servers/Tests/OSHttpTests.cs | |||
@@ -39,9 +39,331 @@ using OpenSim.Tests.Common; | |||
39 | 39 | ||
40 | namespace OpenSim.Framework.Servers.Tests | 40 | namespace OpenSim.Framework.Servers.Tests |
41 | { | 41 | { |
42 | /* | ||
43 | |||
42 | [TestFixture] | 44 | [TestFixture] |
43 | public class OSHttpTests : OpenSimTestCase | 45 | public class OSHttpTests : OpenSimTestCase |
44 | { | 46 | { |
47 | // we need an IHttpClientContext for our tests | ||
48 | public class TestHttpClientContext: IHttpClientContext | ||
49 | { | ||
50 | private bool _secured; | ||
51 | public bool IsSecured | ||
52 | { | ||
53 | get { return _secured; } | ||
54 | } | ||
55 | public bool Secured | ||
56 | { | ||
57 | get { return _secured; } | ||
58 | } | ||
59 | |||
60 | public TestHttpClientContext(bool secured) | ||
61 | { | ||
62 | _secured = secured; | ||
63 | } | ||
64 | |||
65 | public void Disconnect(SocketError error) {} | ||
66 | public void Respond(string httpVersion, HttpStatusCode statusCode, string reason, string body) {} | ||
67 | public void Respond(string httpVersion, HttpStatusCode statusCode, string reason) {} | ||
68 | public void Respond(string body) {} | ||
69 | public void Send(byte[] buffer) {} | ||
70 | public void Send(byte[] buffer, int offset, int size) {} | ||
71 | public void Respond(string httpVersion, HttpStatusCode statusCode, string reason, string body, string contentType) {} | ||
72 | public void Close() { } | ||
73 | public bool EndWhenDone { get { return false;} set { return;}} | ||
74 | |||
75 | public HTTPNetworkContext GiveMeTheNetworkStreamIKnowWhatImDoing() | ||
76 | { | ||
77 | return new HTTPNetworkContext(); | ||
78 | } | ||
79 | |||
80 | public event EventHandler<DisconnectedEventArgs> Disconnected = delegate { }; | ||
81 | /// <summary> | ||
82 | /// A request have been received in the context. | ||
83 | /// </summary> | ||
84 | public event EventHandler<RequestEventArgs> RequestReceived = delegate { }; | ||
85 | |||
86 | public bool CanSend { get { return true; } } | ||
87 | public string RemoteEndPoint { get { return ""; } } | ||
88 | public string RemoteEndPointAddress { get { return ""; } } | ||
89 | public string RemoteEndPointPort { get { return ""; } } | ||
90 | } | ||
91 | |||
92 | public class TestHttpRequest: IHttpRequest | ||
93 | { | ||
94 | private string _uriPath; | ||
95 | public bool BodyIsComplete | ||
96 | { | ||
97 | get { return true; } | ||
98 | } | ||
99 | public string[] AcceptTypes | ||
100 | { | ||
101 | get {return _acceptTypes; } | ||
102 | } | ||
103 | private string[] _acceptTypes; | ||
104 | public Stream Body | ||
105 | { | ||
106 | get { return _body; } | ||
107 | set { _body = value;} | ||
108 | } | ||
109 | private Stream _body; | ||
110 | public ConnectionType Connection | ||
111 | { | ||
112 | get { return _connection; } | ||
113 | set { _connection = value; } | ||
114 | } | ||
115 | private ConnectionType _connection; | ||
116 | public int ContentLength | ||
117 | { | ||
118 | get { return _contentLength; } | ||
119 | set { _contentLength = value; } | ||
120 | } | ||
121 | private int _contentLength; | ||
122 | public NameValueCollection Headers | ||
123 | { | ||
124 | get { return _headers; } | ||
125 | } | ||
126 | private NameValueCollection _headers = new NameValueCollection(); | ||
127 | public string HttpVersion | ||
128 | { | ||
129 | get { return _httpVersion; } | ||
130 | set { _httpVersion = value; } | ||
131 | } | ||
132 | private string _httpVersion = null; | ||
133 | public string Method | ||
134 | { | ||
135 | get { return _method; } | ||
136 | set { _method = value; } | ||
137 | } | ||
138 | private string _method = null; | ||
139 | public HttpInput QueryString | ||
140 | { | ||
141 | get { return _queryString; } | ||
142 | } | ||
143 | private HttpInput _queryString = null; | ||
144 | public Uri Uri | ||
145 | { | ||
146 | get { return _uri; } | ||
147 | set { _uri = value; } | ||
148 | } | ||
149 | private Uri _uri = null; | ||
150 | public string[] UriParts | ||
151 | { | ||
152 | get { return _uri.Segments; } | ||
153 | } | ||
154 | public HttpParam Param | ||
155 | { | ||
156 | get { return null; } | ||
157 | } | ||
158 | public HttpForm Form | ||
159 | { | ||
160 | get { return null; } | ||
161 | } | ||
162 | public bool IsAjax | ||
163 | { | ||
164 | get { return false; } | ||
165 | } | ||
166 | public RequestCookies Cookies | ||
167 | { | ||
168 | get { return null; } | ||
169 | } | ||
170 | |||
171 | public TestHttpRequest() {} | ||
172 | |||
173 | public TestHttpRequest(string contentEncoding, string contentType, string userAgent, | ||
174 | string remoteAddr, string remotePort, string[] acceptTypes, | ||
175 | ConnectionType connectionType, int contentLength, Uri uri) | ||
176 | { | ||
177 | _headers["content-encoding"] = contentEncoding; | ||
178 | _headers["content-type"] = contentType; | ||
179 | _headers["user-agent"] = userAgent; | ||
180 | _headers["remote_addr"] = remoteAddr; | ||
181 | _headers["remote_port"] = remotePort; | ||
182 | |||
183 | _acceptTypes = acceptTypes; | ||
184 | _connection = connectionType; | ||
185 | _contentLength = contentLength; | ||
186 | _uri = uri; | ||
187 | } | ||
188 | |||
189 | public void DecodeBody(FormDecoderProvider providers) {} | ||
190 | public void SetCookies(RequestCookies cookies) {} | ||
191 | public void AddHeader(string name, string value) | ||
192 | { | ||
193 | _headers.Add(name, value); | ||
194 | } | ||
195 | public int AddToBody(byte[] bytes, int offset, int length) | ||
196 | { | ||
197 | return 0; | ||
198 | } | ||
199 | public void Clear() {} | ||
200 | |||
201 | public object Clone() | ||
202 | { | ||
203 | TestHttpRequest clone = new TestHttpRequest(); | ||
204 | clone._acceptTypes = _acceptTypes; | ||
205 | clone._connection = _connection; | ||
206 | clone._contentLength = _contentLength; | ||
207 | clone._uri = _uri; | ||
208 | clone._headers = new NameValueCollection(_headers); | ||
209 | |||
210 | return clone; | ||
211 | } | ||
212 | public IHttpResponse CreateResponse(IHttpClientContext context) | ||
213 | { | ||
214 | return new HttpResponse(context, this); | ||
215 | } | ||
216 | /// <summary> | ||
217 | /// Path and query (will be merged with the host header) and put in Uri | ||
218 | /// </summary> | ||
219 | /// <see cref="Uri"/> | ||
220 | public string UriPath | ||
221 | { | ||
222 | get { return _uriPath; } | ||
223 | set | ||
224 | { | ||
225 | _uriPath = value; | ||
226 | |||
227 | } | ||
228 | } | ||
229 | |||
230 | } | ||
231 | |||
232 | public class TestHttpResponse: IHttpResponse | ||
233 | { | ||
234 | public Stream Body | ||
235 | { | ||
236 | get { return _body; } | ||
237 | |||
238 | set { _body = value; } | ||
239 | } | ||
240 | private Stream _body; | ||
241 | |||
242 | public string ProtocolVersion | ||
243 | { | ||
244 | get { return _protocolVersion; } | ||
245 | set { _protocolVersion = value; } | ||
246 | } | ||
247 | private string _protocolVersion; | ||
248 | |||
249 | public bool Chunked | ||
250 | { | ||
251 | get { return _chunked; } | ||
252 | |||
253 | set { _chunked = value; } | ||
254 | } | ||
255 | private bool _chunked; | ||
256 | |||
257 | public ConnectionType Connection | ||
258 | { | ||
259 | get { return _connection; } | ||
260 | |||
261 | set { _connection = value; } | ||
262 | } | ||
263 | private ConnectionType _connection; | ||
264 | |||
265 | public Encoding Encoding | ||
266 | { | ||
267 | get { return _encoding; } | ||
268 | |||
269 | set { _encoding = value; } | ||
270 | } | ||
271 | private Encoding _encoding; | ||
272 | |||
273 | public int KeepAlive | ||
274 | { | ||
275 | get { return _keepAlive; } | ||
276 | |||
277 | set { _keepAlive = value; } | ||
278 | } | ||
279 | private int _keepAlive; | ||
280 | |||
281 | public HttpStatusCode Status | ||
282 | { | ||
283 | get { return _status; } | ||
284 | |||
285 | set { _status = value; } | ||
286 | } | ||
287 | private HttpStatusCode _status; | ||
288 | |||
289 | public string Reason | ||
290 | { | ||
291 | get { return _reason; } | ||
292 | |||
293 | set { _reason = value; } | ||
294 | } | ||
295 | private string _reason; | ||
296 | |||
297 | public long ContentLength | ||
298 | { | ||
299 | get { return _contentLength; } | ||
300 | |||
301 | set { _contentLength = value; } | ||
302 | } | ||
303 | private long _contentLength; | ||
304 | |||
305 | public string ContentType | ||
306 | { | ||
307 | get { return _contentType; } | ||
308 | |||
309 | set { _contentType = value; } | ||
310 | } | ||
311 | private string _contentType; | ||
312 | |||
313 | public bool HeadersSent | ||
314 | { | ||
315 | get { return _headersSent; } | ||
316 | } | ||
317 | private bool _headersSent; | ||
318 | |||
319 | public bool Sent | ||
320 | { | ||
321 | get { return _sent; } | ||
322 | } | ||
323 | private bool _sent; | ||
324 | |||
325 | public ResponseCookies Cookies | ||
326 | { | ||
327 | get { return _cookies; } | ||
328 | } | ||
329 | private ResponseCookies _cookies = null; | ||
330 | |||
331 | public TestHttpResponse() | ||
332 | { | ||
333 | _headersSent = false; | ||
334 | _sent = false; | ||
335 | } | ||
336 | |||
337 | public void AddHeader(string name, string value) {} | ||
338 | public void Send() | ||
339 | { | ||
340 | if (!_headersSent) SendHeaders(); | ||
341 | if (_sent) throw new InvalidOperationException("stuff already sent"); | ||
342 | _sent = true; | ||
343 | } | ||
344 | |||
345 | public void SendBody(byte[] buffer, int offset, int count) | ||
346 | { | ||
347 | if (!_headersSent) SendHeaders(); | ||
348 | _sent = true; | ||
349 | } | ||
350 | public void SendBody(byte[] buffer) | ||
351 | { | ||
352 | if (!_headersSent) SendHeaders(); | ||
353 | _sent = true; | ||
354 | } | ||
355 | |||
356 | public void SendHeaders() | ||
357 | { | ||
358 | if (_headersSent) throw new InvalidOperationException("headers already sent"); | ||
359 | _headersSent = true; | ||
360 | } | ||
361 | |||
362 | public void Redirect(Uri uri) {} | ||
363 | public void Redirect(string url) {} | ||
364 | } | ||
365 | |||
366 | |||
45 | public OSHttpRequest req0; | 367 | public OSHttpRequest req0; |
46 | public OSHttpRequest req1; | 368 | public OSHttpRequest req1; |
47 | 369 | ||
@@ -52,22 +374,22 @@ namespace OpenSim.Framework.Servers.Tests | |||
52 | [TestFixtureSetUp] | 374 | [TestFixtureSetUp] |
53 | public void Init() | 375 | public void Init() |
54 | { | 376 | { |
55 | TestHttpRequest threq0 = new TestHttpRequest("utf-8", "text/xml", "OpenSim Test Agent", "192.168.0.1", "4711", | 377 | TestHttpRequest threq0 = new TestHttpRequest("utf-8", "text/xml", "OpenSim Test Agent", "192.168.0.1", "4711", |
56 | new string[] {"text/xml"}, | 378 | new string[] {"text/xml"}, |
57 | ConnectionType.KeepAlive, 4711, | 379 | ConnectionType.KeepAlive, 4711, |
58 | new Uri("http://127.0.0.1/admin/inventory/Dr+Who/Tardis")); | 380 | new Uri("http://127.0.0.1/admin/inventory/Dr+Who/Tardis")); |
59 | threq0.Method = "GET"; | 381 | threq0.Method = "GET"; |
60 | threq0.HttpVersion = HttpHelper.HTTP10; | 382 | threq0.HttpVersion = HttpHelper.HTTP10; |
61 | 383 | ||
62 | TestHttpRequest threq1 = new TestHttpRequest("utf-8", "text/xml", "OpenSim Test Agent", "192.168.0.1", "4711", | 384 | TestHttpRequest threq1 = new TestHttpRequest("utf-8", "text/xml", "OpenSim Test Agent", "192.168.0.1", "4711", |
63 | new string[] {"text/xml"}, | 385 | new string[] {"text/xml"}, |
64 | ConnectionType.KeepAlive, 4711, | 386 | ConnectionType.KeepAlive, 4711, |
65 | new Uri("http://127.0.0.1/admin/inventory/Dr+Who/Tardis?a=0&b=1&c=2")); | 387 | new Uri("http://127.0.0.1/admin/inventory/Dr+Who/Tardis?a=0&b=1&c=2")); |
66 | threq1.Method = "POST"; | 388 | threq1.Method = "POST"; |
67 | threq1.HttpVersion = HttpHelper.HTTP11; | 389 | threq1.HttpVersion = HttpHelper.HTTP11; |
68 | threq1.Headers["x-wuff"] = "wuffwuff"; | 390 | threq1.Headers["x-wuff"] = "wuffwuff"; |
69 | threq1.Headers["www-authenticate"] = "go away"; | 391 | threq1.Headers["www-authenticate"] = "go away"; |
70 | 392 | ||
71 | req0 = new OSHttpRequest(new TestHttpClientContext(false), threq0); | 393 | req0 = new OSHttpRequest(new TestHttpClientContext(false), threq0); |
72 | req1 = new OSHttpRequest(new TestHttpClientContext(false), threq1); | 394 | req1 = new OSHttpRequest(new TestHttpClientContext(false), threq1); |
73 | 395 | ||
@@ -113,4 +435,5 @@ namespace OpenSim.Framework.Servers.Tests | |||
113 | Assert.That(rsp0.ContentType, Is.EqualTo("text/xml")); | 435 | Assert.That(rsp0.ContentType, Is.EqualTo("text/xml")); |
114 | } | 436 | } |
115 | } | 437 | } |
116 | } \ No newline at end of file | 438 | */ |
439 | } | ||
diff --git a/OpenSim/Framework/Servers/Tests/VersionInfoTests.cs b/OpenSim/Framework/Servers/Tests/VersionInfoTests.cs index 2d72cb8..480f2bb 100644 --- a/OpenSim/Framework/Servers/Tests/VersionInfoTests.cs +++ b/OpenSim/Framework/Servers/Tests/VersionInfoTests.cs | |||
@@ -47,7 +47,7 @@ namespace OpenSim.Framework.Servers.Tests | |||
47 | { | 47 | { |
48 | foreach (VersionInfo.Flavour flavour in Enum.GetValues(typeof(VersionInfo.Flavour))) | 48 | foreach (VersionInfo.Flavour flavour in Enum.GetValues(typeof(VersionInfo.Flavour))) |
49 | { | 49 | { |
50 | Assert.AreEqual(VersionInfo.VERSIONINFO_VERSION_LENGTH, VersionInfo.GetVersionString("0.0.0", "0", flavour).Length, "0.0.0/" + flavour + " failed"); | 50 | Assert.AreEqual(VersionInfo.VERSIONINFO_VERSION_LENGTH, VersionInfo.GetVersionString("0.0.0", flavour).Length, "0.0.0/" + flavour + " failed"); |
51 | } | 51 | } |
52 | } | 52 | } |
53 | } | 53 | } |