diff options
Diffstat (limited to 'OpenSim/Framework/Servers/HttpServer/BaseHttpServer.cs')
-rw-r--r-- | OpenSim/Framework/Servers/HttpServer/BaseHttpServer.cs | 274 |
1 files changed, 98 insertions, 176 deletions
diff --git a/OpenSim/Framework/Servers/HttpServer/BaseHttpServer.cs b/OpenSim/Framework/Servers/HttpServer/BaseHttpServer.cs index 3198891..788a0b9 100644 --- a/OpenSim/Framework/Servers/HttpServer/BaseHttpServer.cs +++ b/OpenSim/Framework/Servers/HttpServer/BaseHttpServer.cs | |||
@@ -54,23 +54,8 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
54 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); | 54 | private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); |
55 | private HttpServerLogWriter httpserverlog = new HttpServerLogWriter(); | 55 | private HttpServerLogWriter httpserverlog = new HttpServerLogWriter(); |
56 | 56 | ||
57 | /// <summary> | ||
58 | /// Gets or sets the debug level. | ||
59 | /// </summary> | ||
60 | /// <value> | ||
61 | /// See MainServer.DebugLevel. | ||
62 | /// </value> | ||
63 | public int DebugLevel { get; set; } | 57 | public int DebugLevel { get; set; } |
64 | 58 | ||
65 | /// <summary> | ||
66 | /// Request number for diagnostic purposes. | ||
67 | /// </summary> | ||
68 | /// <remarks> | ||
69 | /// This is an internal number. In some debug situations an external number may also be supplied in the | ||
70 | /// opensim-request-id header but we are not currently logging this. | ||
71 | /// </remarks> | ||
72 | public int RequestNumber { get; private set; } | ||
73 | |||
74 | private volatile int NotSocketErrors = 0; | 59 | private volatile int NotSocketErrors = 0; |
75 | public volatile bool HTTPDRunning = false; | 60 | public volatile bool HTTPDRunning = false; |
76 | 61 | ||
@@ -82,7 +67,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
82 | protected Dictionary<string, LLSDMethod> m_llsdHandlers = new Dictionary<string, LLSDMethod>(); | 67 | protected Dictionary<string, LLSDMethod> m_llsdHandlers = new Dictionary<string, LLSDMethod>(); |
83 | protected Dictionary<string, IRequestHandler> m_streamHandlers = new Dictionary<string, IRequestHandler>(); | 68 | protected Dictionary<string, IRequestHandler> m_streamHandlers = new Dictionary<string, IRequestHandler>(); |
84 | protected Dictionary<string, GenericHTTPMethod> m_HTTPHandlers = new Dictionary<string, GenericHTTPMethod>(); | 69 | protected Dictionary<string, GenericHTTPMethod> m_HTTPHandlers = new Dictionary<string, GenericHTTPMethod>(); |
85 | // protected Dictionary<string, IHttpAgentHandler> m_agentHandlers = new Dictionary<string, IHttpAgentHandler>(); | 70 | protected Dictionary<string, IHttpAgentHandler> m_agentHandlers = new Dictionary<string, IHttpAgentHandler>(); |
86 | protected Dictionary<string, PollServiceEventArgs> m_pollHandlers = | 71 | protected Dictionary<string, PollServiceEventArgs> m_pollHandlers = |
87 | new Dictionary<string, PollServiceEventArgs>(); | 72 | new Dictionary<string, PollServiceEventArgs>(); |
88 | 73 | ||
@@ -260,29 +245,29 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
260 | return new List<string>(m_pollHandlers.Keys); | 245 | return new List<string>(m_pollHandlers.Keys); |
261 | } | 246 | } |
262 | 247 | ||
263 | // // Note that the agent string is provided simply to differentiate | 248 | // Note that the agent string is provided simply to differentiate |
264 | // // the handlers - it is NOT required to be an actual agent header | 249 | // the handlers - it is NOT required to be an actual agent header |
265 | // // value. | 250 | // value. |
266 | // public bool AddAgentHandler(string agent, IHttpAgentHandler handler) | 251 | public bool AddAgentHandler(string agent, IHttpAgentHandler handler) |
267 | // { | 252 | { |
268 | // lock (m_agentHandlers) | 253 | lock (m_agentHandlers) |
269 | // { | 254 | { |
270 | // if (!m_agentHandlers.ContainsKey(agent)) | 255 | if (!m_agentHandlers.ContainsKey(agent)) |
271 | // { | 256 | { |
272 | // m_agentHandlers.Add(agent, handler); | 257 | m_agentHandlers.Add(agent, handler); |
273 | // return true; | 258 | return true; |
274 | // } | 259 | } |
275 | // } | 260 | } |
276 | // | 261 | |
277 | // //must already have a handler for that path so return false | 262 | //must already have a handler for that path so return false |
278 | // return false; | 263 | return false; |
279 | // } | 264 | } |
280 | // | 265 | |
281 | // public List<string> GetAgentHandlerKeys() | 266 | public List<string> GetAgentHandlerKeys() |
282 | // { | 267 | { |
283 | // lock (m_agentHandlers) | 268 | lock (m_agentHandlers) |
284 | // return new List<string>(m_agentHandlers.Keys); | 269 | return new List<string>(m_agentHandlers.Keys); |
285 | // } | 270 | } |
286 | 271 | ||
287 | public bool AddLLSDHandler(string path, LLSDMethod handler) | 272 | public bool AddLLSDHandler(string path, LLSDMethod handler) |
288 | { | 273 | { |
@@ -311,8 +296,6 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
311 | 296 | ||
312 | private void OnRequest(object source, RequestEventArgs args) | 297 | private void OnRequest(object source, RequestEventArgs args) |
313 | { | 298 | { |
314 | RequestNumber++; | ||
315 | |||
316 | try | 299 | try |
317 | { | 300 | { |
318 | IHttpClientContext context = (IHttpClientContext)source; | 301 | IHttpClientContext context = (IHttpClientContext)source; |
@@ -423,6 +406,7 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
423 | string requestMethod = request.HttpMethod; | 406 | string requestMethod = request.HttpMethod; |
424 | string uriString = request.RawUrl; | 407 | string uriString = request.RawUrl; |
425 | 408 | ||
409 | // string reqnum = "unknown"; | ||
426 | int requestStartTick = Environment.TickCount; | 410 | int requestStartTick = Environment.TickCount; |
427 | 411 | ||
428 | // Will be adjusted later on. | 412 | // Will be adjusted later on. |
@@ -439,22 +423,22 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
439 | 423 | ||
440 | Thread.CurrentThread.CurrentCulture = new CultureInfo("en-US", true); | 424 | Thread.CurrentThread.CurrentCulture = new CultureInfo("en-US", true); |
441 | 425 | ||
442 | // // This is the REST agent interface. We require an agent to properly identify | 426 | // This is the REST agent interface. We require an agent to properly identify |
443 | // // itself. If the REST handler recognizes the prefix it will attempt to | 427 | // itself. If the REST handler recognizes the prefix it will attempt to |
444 | // // satisfy the request. If it is not recognizable, and no damage has occurred | 428 | // satisfy the request. If it is not recognizable, and no damage has occurred |
445 | // // the request can be passed through to the other handlers. This is a low | 429 | // the request can be passed through to the other handlers. This is a low |
446 | // // probability event; if a request is matched it is normally expected to be | 430 | // probability event; if a request is matched it is normally expected to be |
447 | // // handled | 431 | // handled |
448 | // IHttpAgentHandler agentHandler; | 432 | IHttpAgentHandler agentHandler; |
449 | // | 433 | |
450 | // if (TryGetAgentHandler(request, response, out agentHandler)) | 434 | if (TryGetAgentHandler(request, response, out agentHandler)) |
451 | // { | 435 | { |
452 | // if (HandleAgentRequest(agentHandler, request, response)) | 436 | if (HandleAgentRequest(agentHandler, request, response)) |
453 | // { | 437 | { |
454 | // requestEndTick = Environment.TickCount; | 438 | requestEndTick = Environment.TickCount; |
455 | // return; | 439 | return; |
456 | // } | 440 | } |
457 | // } | 441 | } |
458 | 442 | ||
459 | //response.KeepAlive = true; | 443 | //response.KeepAlive = true; |
460 | response.SendChunked = false; | 444 | response.SendChunked = false; |
@@ -466,7 +450,9 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
466 | if (TryGetStreamHandler(handlerKey, out requestHandler)) | 450 | if (TryGetStreamHandler(handlerKey, out requestHandler)) |
467 | { | 451 | { |
468 | if (DebugLevel >= 3) | 452 | if (DebugLevel >= 3) |
469 | LogIncomingToStreamHandler(request, requestHandler); | 453 | m_log.DebugFormat( |
454 | "[BASE HTTP SERVER]: Found stream handler for {0} {1} {2} {3}", | ||
455 | request.HttpMethod, request.Url.PathAndQuery, requestHandler.Name, requestHandler.Description); | ||
470 | 456 | ||
471 | response.ContentType = requestHandler.ContentType; // Lets do this defaulting before in case handler has varying content type. | 457 | response.ContentType = requestHandler.ContentType; // Lets do this defaulting before in case handler has varying content type. |
472 | 458 | ||
@@ -543,8 +529,11 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
543 | { | 529 | { |
544 | case null: | 530 | case null: |
545 | case "text/html": | 531 | case "text/html": |
532 | |||
546 | if (DebugLevel >= 3) | 533 | if (DebugLevel >= 3) |
547 | LogIncomingToContentTypeHandler(request); | 534 | m_log.DebugFormat( |
535 | "[BASE HTTP SERVER]: Found a {0} content type handler for {1} {2}", | ||
536 | request.ContentType, request.HttpMethod, request.Url.PathAndQuery); | ||
548 | 537 | ||
549 | buffer = HandleHTTPRequest(request, response); | 538 | buffer = HandleHTTPRequest(request, response); |
550 | break; | 539 | break; |
@@ -552,8 +541,11 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
552 | case "application/llsd+xml": | 541 | case "application/llsd+xml": |
553 | case "application/xml+llsd": | 542 | case "application/xml+llsd": |
554 | case "application/llsd+json": | 543 | case "application/llsd+json": |
544 | |||
555 | if (DebugLevel >= 3) | 545 | if (DebugLevel >= 3) |
556 | LogIncomingToContentTypeHandler(request); | 546 | m_log.DebugFormat( |
547 | "[BASE HTTP SERVER]: Found a {0} content type handler for {1} {2}", | ||
548 | request.ContentType, request.HttpMethod, request.Url.PathAndQuery); | ||
557 | 549 | ||
558 | buffer = HandleLLSDRequests(request, response); | 550 | buffer = HandleLLSDRequests(request, response); |
559 | break; | 551 | break; |
@@ -572,7 +564,9 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
572 | if (DoWeHaveALLSDHandler(request.RawUrl)) | 564 | if (DoWeHaveALLSDHandler(request.RawUrl)) |
573 | { | 565 | { |
574 | if (DebugLevel >= 3) | 566 | if (DebugLevel >= 3) |
575 | LogIncomingToContentTypeHandler(request); | 567 | m_log.DebugFormat( |
568 | "[BASE HTTP SERVER]: Found a {0} content type handler for {1} {2}", | ||
569 | request.ContentType, request.HttpMethod, request.Url.PathAndQuery); | ||
576 | 570 | ||
577 | buffer = HandleLLSDRequests(request, response); | 571 | buffer = HandleLLSDRequests(request, response); |
578 | } | 572 | } |
@@ -580,14 +574,18 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
580 | else if (DoWeHaveAHTTPHandler(request.RawUrl)) | 574 | else if (DoWeHaveAHTTPHandler(request.RawUrl)) |
581 | { | 575 | { |
582 | if (DebugLevel >= 3) | 576 | if (DebugLevel >= 3) |
583 | LogIncomingToContentTypeHandler(request); | 577 | m_log.DebugFormat( |
578 | "[BASE HTTP SERVER]: Found a {0} content type handler for {1} {2}", | ||
579 | request.ContentType, request.HttpMethod, request.Url.PathAndQuery); | ||
584 | 580 | ||
585 | buffer = HandleHTTPRequest(request, response); | 581 | buffer = HandleHTTPRequest(request, response); |
586 | } | 582 | } |
587 | else | 583 | else |
588 | { | 584 | { |
589 | if (DebugLevel >= 3) | 585 | if (DebugLevel >= 3) |
590 | LogIncomingToXmlRpcHandler(request); | 586 | m_log.DebugFormat( |
587 | "[BASE HTTP SERVER]: Assuming a generic XMLRPC request for {0} {1}", | ||
588 | request.HttpMethod, request.Url.PathAndQuery); | ||
591 | 589 | ||
592 | // generic login request. | 590 | // generic login request. |
593 | buffer = HandleXmlRpcRequests(request, response); | 591 | buffer = HandleXmlRpcRequests(request, response); |
@@ -631,11 +629,11 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
631 | } | 629 | } |
632 | catch (IOException e) | 630 | catch (IOException e) |
633 | { | 631 | { |
634 | m_log.Error(String.Format("[BASE HTTP SERVER]: HandleRequest() threw {0} ", e.StackTrace), e); | 632 | m_log.Error(String.Format("[BASE HTTP SERVER]: HandleRequest() threw {0} ", e.Message), e); |
635 | } | 633 | } |
636 | catch (Exception e) | 634 | catch (Exception e) |
637 | { | 635 | { |
638 | m_log.Error(String.Format("[BASE HTTP SERVER]: HandleRequest() threw {0} ", e.StackTrace), e); | 636 | m_log.Error(String.Format("[BASE HTTP SERVER]: HandleRequest() threw {0} ", e.Message), e); |
639 | SendHTML500(response); | 637 | SendHTML500(response); |
640 | } | 638 | } |
641 | finally | 639 | finally |
@@ -646,93 +644,17 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
646 | if (tickdiff > 3000 && (requestHandler == null || requestHandler.Name == null || requestHandler.Name != "GetTexture")) | 644 | if (tickdiff > 3000 && (requestHandler == null || requestHandler.Name == null || requestHandler.Name != "GetTexture")) |
647 | { | 645 | { |
648 | m_log.InfoFormat( | 646 | m_log.InfoFormat( |
649 | "[BASE HTTP SERVER]: Slow handling of {0} {1} {2} {3} {4} from {5} took {6}ms", | 647 | "[BASE HTTP SERVER]: Slow handling of {0} {1} {2} {3} from {4} took {5}ms", |
650 | RequestNumber, | ||
651 | requestMethod, | 648 | requestMethod, |
652 | uriString, | 649 | uriString, |
653 | requestHandler != null ? requestHandler.Name : "", | 650 | requestHandler != null ? requestHandler.Name : "", |
654 | requestHandler != null ? requestHandler.Description : "", | 651 | requestHandler != null ? requestHandler.Description : "", |
655 | request.RemoteIPEndPoint, | 652 | request.RemoteIPEndPoint.ToString(), |
656 | tickdiff); | ||
657 | } | ||
658 | else if (DebugLevel >= 4) | ||
659 | { | ||
660 | m_log.DebugFormat( | ||
661 | "[BASE HTTP SERVER]: HTTP IN {0} :{1} took {2}ms", | ||
662 | RequestNumber, | ||
663 | Port, | ||
664 | tickdiff); | 653 | tickdiff); |
665 | } | 654 | } |
666 | } | 655 | } |
667 | } | 656 | } |
668 | 657 | ||
669 | private void LogIncomingToStreamHandler(OSHttpRequest request, IRequestHandler requestHandler) | ||
670 | { | ||
671 | m_log.DebugFormat( | ||
672 | "[BASE HTTP SERVER]: HTTP IN {0} :{1} stream handler {2} {3} {4} {5} from {6}", | ||
673 | RequestNumber, | ||
674 | Port, | ||
675 | request.HttpMethod, | ||
676 | request.Url.PathAndQuery, | ||
677 | requestHandler.Name, | ||
678 | requestHandler.Description, | ||
679 | request.RemoteIPEndPoint); | ||
680 | |||
681 | if (DebugLevel >= 5) | ||
682 | LogIncomingInDetail(request); | ||
683 | } | ||
684 | |||
685 | private void LogIncomingToContentTypeHandler(OSHttpRequest request) | ||
686 | { | ||
687 | m_log.DebugFormat( | ||
688 | "[BASE HTTP SERVER]: HTTP IN {0} :{1} {2} content type handler {3} {4} from {5}", | ||
689 | RequestNumber, | ||
690 | Port, | ||
691 | (request.ContentType == null || request.ContentType == "") ? "not set" : request.ContentType, | ||
692 | request.HttpMethod, | ||
693 | request.Url.PathAndQuery, | ||
694 | request.RemoteIPEndPoint); | ||
695 | |||
696 | if (DebugLevel >= 5) | ||
697 | LogIncomingInDetail(request); | ||
698 | } | ||
699 | |||
700 | private void LogIncomingToXmlRpcHandler(OSHttpRequest request) | ||
701 | { | ||
702 | m_log.DebugFormat( | ||
703 | "[BASE HTTP SERVER]: HTTP IN {0} :{1} assumed generic XMLRPC request {2} {3} from {4}", | ||
704 | RequestNumber, | ||
705 | Port, | ||
706 | request.HttpMethod, | ||
707 | request.Url.PathAndQuery, | ||
708 | request.RemoteIPEndPoint); | ||
709 | |||
710 | if (DebugLevel >= 5) | ||
711 | LogIncomingInDetail(request); | ||
712 | } | ||
713 | |||
714 | private void LogIncomingInDetail(OSHttpRequest request) | ||
715 | { | ||
716 | using (StreamReader reader = new StreamReader(Util.Copy(request.InputStream), Encoding.UTF8)) | ||
717 | { | ||
718 | string output; | ||
719 | |||
720 | if (DebugLevel == 5) | ||
721 | { | ||
722 | const int sampleLength = 80; | ||
723 | char[] sampleChars = new char[sampleLength]; | ||
724 | reader.Read(sampleChars, 0, sampleLength); | ||
725 | output = new string(sampleChars); | ||
726 | } | ||
727 | else | ||
728 | { | ||
729 | output = reader.ReadToEnd(); | ||
730 | } | ||
731 | |||
732 | m_log.DebugFormat("[BASE HTTP SERVER]: {0}...", output.Replace("\n", @"\n")); | ||
733 | } | ||
734 | } | ||
735 | |||
736 | private bool TryGetStreamHandler(string handlerKey, out IRequestHandler streamHandler) | 658 | private bool TryGetStreamHandler(string handlerKey, out IRequestHandler streamHandler) |
737 | { | 659 | { |
738 | string bestMatch = null; | 660 | string bestMatch = null; |
@@ -825,24 +747,24 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
825 | } | 747 | } |
826 | } | 748 | } |
827 | 749 | ||
828 | // private bool TryGetAgentHandler(OSHttpRequest request, OSHttpResponse response, out IHttpAgentHandler agentHandler) | 750 | private bool TryGetAgentHandler(OSHttpRequest request, OSHttpResponse response, out IHttpAgentHandler agentHandler) |
829 | // { | 751 | { |
830 | // agentHandler = null; | 752 | agentHandler = null; |
831 | // | 753 | |
832 | // lock (m_agentHandlers) | 754 | lock (m_agentHandlers) |
833 | // { | 755 | { |
834 | // foreach (IHttpAgentHandler handler in m_agentHandlers.Values) | 756 | foreach (IHttpAgentHandler handler in m_agentHandlers.Values) |
835 | // { | 757 | { |
836 | // if (handler.Match(request, response)) | 758 | if (handler.Match(request, response)) |
837 | // { | 759 | { |
838 | // agentHandler = handler; | 760 | agentHandler = handler; |
839 | // return true; | 761 | return true; |
840 | // } | 762 | } |
841 | // } | 763 | } |
842 | // } | 764 | } |
843 | // | 765 | |
844 | // return false; | 766 | return false; |
845 | // } | 767 | } |
846 | 768 | ||
847 | /// <summary> | 769 | /// <summary> |
848 | /// Try all the registered xmlrpc handlers when an xmlrpc request is received. | 770 | /// Try all the registered xmlrpc handlers when an xmlrpc request is received. |
@@ -1815,21 +1737,21 @@ namespace OpenSim.Framework.Servers.HttpServer | |||
1815 | m_pollHandlers.Remove(path); | 1737 | m_pollHandlers.Remove(path); |
1816 | } | 1738 | } |
1817 | 1739 | ||
1818 | // public bool RemoveAgentHandler(string agent, IHttpAgentHandler handler) | 1740 | public bool RemoveAgentHandler(string agent, IHttpAgentHandler handler) |
1819 | // { | 1741 | { |
1820 | // lock (m_agentHandlers) | 1742 | lock (m_agentHandlers) |
1821 | // { | 1743 | { |
1822 | // IHttpAgentHandler foundHandler; | 1744 | IHttpAgentHandler foundHandler; |
1823 | // | 1745 | |
1824 | // if (m_agentHandlers.TryGetValue(agent, out foundHandler) && foundHandler == handler) | 1746 | if (m_agentHandlers.TryGetValue(agent, out foundHandler) && foundHandler == handler) |
1825 | // { | 1747 | { |
1826 | // m_agentHandlers.Remove(agent); | 1748 | m_agentHandlers.Remove(agent); |
1827 | // return true; | 1749 | return true; |
1828 | // } | 1750 | } |
1829 | // } | 1751 | } |
1830 | // | 1752 | |
1831 | // return false; | 1753 | return false; |
1832 | // } | 1754 | } |
1833 | 1755 | ||
1834 | public void RemoveXmlRPCHandler(string method) | 1756 | public void RemoveXmlRPCHandler(string method) |
1835 | { | 1757 | { |