aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/CoreModules/Scripting
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/CoreModules/Scripting')
-rw-r--r--OpenSim/Region/CoreModules/Scripting/HttpRequest/ScriptsHttpRequests.cs31
-rw-r--r--OpenSim/Region/CoreModules/Scripting/LSLHttp/UrlModule.cs388
-rw-r--r--OpenSim/Region/CoreModules/Scripting/WorldComm/WorldCommModule.cs75
3 files changed, 262 insertions, 232 deletions
diff --git a/OpenSim/Region/CoreModules/Scripting/HttpRequest/ScriptsHttpRequests.cs b/OpenSim/Region/CoreModules/Scripting/HttpRequest/ScriptsHttpRequests.cs
index d328eb3..9dac6b9 100644
--- a/OpenSim/Region/CoreModules/Scripting/HttpRequest/ScriptsHttpRequests.cs
+++ b/OpenSim/Region/CoreModules/Scripting/HttpRequest/ScriptsHttpRequests.cs
@@ -382,6 +382,10 @@ namespace OpenSim.Region.CoreModules.Scripting.HttpRequest
382 try 382 try
383 { 383 {
384 Request = (HttpWebRequest) WebRequest.Create(Url); 384 Request = (HttpWebRequest) WebRequest.Create(Url);
385
386 //This works around some buggy HTTP Servers like Lighttpd
387 Request.ServicePoint.Expect100Continue = false;
388
385 Request.Method = HttpMethod; 389 Request.Method = HttpMethod;
386 Request.ContentType = HttpMIMEType; 390 Request.ContentType = HttpMIMEType;
387 391
@@ -458,15 +462,36 @@ namespace OpenSim.Region.CoreModules.Scripting.HttpRequest
458 462
459 // continue building the string 463 // continue building the string
460 sb.Append(tempString); 464 sb.Append(tempString);
465 if (sb.Length > 2048)
466 break;
461 } 467 }
462 } while (count > 0); // any more data to read? 468 } while (count > 0); // any more data to read?
463 469
464 ResponseBody = sb.ToString(); 470 ResponseBody = sb.ToString().Replace("\r", "");
465 } 471 }
466 catch (Exception e) 472 catch (Exception e)
467 { 473 {
468 Status = (int)OSHttpStatusCode.ClientErrorJoker; 474 if (e is WebException && ((WebException)e).Status == WebExceptionStatus.ProtocolError)
469 ResponseBody = e.Message; 475 {
476 HttpWebResponse webRsp = (HttpWebResponse)((WebException)e).Response;
477 Status = (int)webRsp.StatusCode;
478 try
479 {
480 using (Stream responseStream = webRsp.GetResponseStream())
481 {
482 ResponseBody = responseStream.GetStreamString();
483 }
484 }
485 catch
486 {
487 ResponseBody = webRsp.StatusDescription;
488 }
489 }
490 else
491 {
492 Status = (int)OSHttpStatusCode.ClientErrorJoker;
493 ResponseBody = e.Message;
494 }
470 495
471 _finished = true; 496 _finished = true;
472 return; 497 return;
diff --git a/OpenSim/Region/CoreModules/Scripting/LSLHttp/UrlModule.cs b/OpenSim/Region/CoreModules/Scripting/LSLHttp/UrlModule.cs
index 05d54f0..e0e358a 100644
--- a/OpenSim/Region/CoreModules/Scripting/LSLHttp/UrlModule.cs
+++ b/OpenSim/Region/CoreModules/Scripting/LSLHttp/UrlModule.cs
@@ -41,39 +41,13 @@ using OpenSim.Region.Framework.Scenes;
41 41
42namespace OpenSim.Region.CoreModules.Scripting.LSLHttp 42namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
43{ 43{
44 /// <summary>
45 /// Data describing an external URL set up by a script.
46 /// </summary>
47 public class UrlData 44 public class UrlData
48 { 45 {
49 /// <summary>
50 /// Scene object part hosting the script
51 /// </summary>
52 public UUID hostID; 46 public UUID hostID;
53
54 /// <summary>
55 /// The item ID of the script that requested the URL.
56 /// </summary>
57 public UUID itemID; 47 public UUID itemID;
58
59 /// <summary>
60 /// The script engine that runs the script.
61 /// </summary>
62 public IScriptModule engine; 48 public IScriptModule engine;
63
64 /// <summary>
65 /// The generated URL.
66 /// </summary>
67 public string url; 49 public string url;
68
69 /// <summary>
70 /// The random UUID component of the generated URL.
71 /// </summary>
72 public UUID urlcode; 50 public UUID urlcode;
73
74 /// <summary>
75 /// The external requests currently being processed or awaiting retrieval for this URL.
76 /// </summary>
77 public Dictionary<UUID, RequestData> requests; 51 public Dictionary<UUID, RequestData> requests;
78 } 52 }
79 53
@@ -87,37 +61,26 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
87 //public ManualResetEvent ev; 61 //public ManualResetEvent ev;
88 public bool requestDone; 62 public bool requestDone;
89 public int startTime; 63 public int startTime;
64 public bool responseSent;
90 public string uri; 65 public string uri;
91 } 66 }
92 67
93 /// <summary>
94 /// This module provides external URLs for in-world scripts.
95 /// </summary>
96 public class UrlModule : ISharedRegionModule, IUrlModule 68 public class UrlModule : ISharedRegionModule, IUrlModule
97 { 69 {
98 private static readonly ILog m_log = 70 private static readonly ILog m_log =
99 LogManager.GetLogger( 71 LogManager.GetLogger(
100 MethodBase.GetCurrentMethod().DeclaringType); 72 MethodBase.GetCurrentMethod().DeclaringType);
101 73
102 /// <summary> 74 private Dictionary<UUID, UrlData> m_RequestMap =
103 /// Indexs the URL request metadata (which script requested it, outstanding requests, etc.) by the request ID 75 new Dictionary<UUID, UrlData>();
104 /// randomly generated when a request is received for this URL.
105 /// </summary>
106 /// <remarks>
107 /// Manipulation or retrieval from this dictionary must be locked on m_UrlMap to preserve consistency with
108 /// m_UrlMap
109 /// </remarks>
110 private Dictionary<UUID, UrlData> m_RequestMap = new Dictionary<UUID, UrlData>();
111 76
112 /// <summary> 77 private Dictionary<string, UrlData> m_UrlMap =
113 /// Indexs the URL request metadata (which script requested it, outstanding requests, etc.) by the full URL 78 new Dictionary<string, UrlData>();
114 /// </summary>
115 private Dictionary<string, UrlData> m_UrlMap = new Dictionary<string, UrlData>();
116 79
117 /// <summary> 80 /// <summary>
118 /// Maximum number of external urls that can be set up by this module. 81 /// Maximum number of external urls that can be set up by this module.
119 /// </summary> 82 /// </summary>
120 private int m_TotalUrls = 100; 83 private int m_TotalUrls = 15000;
121 84
122 private uint https_port = 0; 85 private uint https_port = 0;
123 private IHttpServer m_HttpServer = null; 86 private IHttpServer m_HttpServer = null;
@@ -143,9 +106,10 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
143 { 106 {
144 m_ExternalHostNameForLSL = config.Configs["Network"].GetString("ExternalHostNameForLSL", System.Environment.MachineName); 107 m_ExternalHostNameForLSL = config.Configs["Network"].GetString("ExternalHostNameForLSL", System.Environment.MachineName);
145 bool ssl_enabled = config.Configs["Network"].GetBoolean("https_listener",false); 108 bool ssl_enabled = config.Configs["Network"].GetBoolean("https_listener",false);
146
147 if (ssl_enabled) 109 if (ssl_enabled)
110 {
148 https_port = (uint) config.Configs["Network"].GetInt("https_port",0); 111 https_port = (uint) config.Configs["Network"].GetInt("https_port",0);
112 }
149 113
150 IConfig llFunctionsConfig = config.Configs["LL-Functions"]; 114 IConfig llFunctionsConfig = config.Configs["LL-Functions"];
151 115
@@ -206,7 +170,7 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
206 engine.PostScriptEvent(itemID, "http_request", new Object[] { urlcode.ToString(), "URL_REQUEST_DENIED", "" }); 170 engine.PostScriptEvent(itemID, "http_request", new Object[] { urlcode.ToString(), "URL_REQUEST_DENIED", "" });
207 return urlcode; 171 return urlcode;
208 } 172 }
209 string url = "http://" + m_ExternalHostNameForLSL + ":" + m_HttpServer.Port.ToString() + "/lslhttp/" + urlcode.ToString() + "/"; 173 string url = "http://" + m_ExternalHostNameForLSL + ":" + m_HttpServer.Port.ToString() + "/lslhttp/" + urlcode.ToString();
210 174
211 UrlData urlData = new UrlData(); 175 UrlData urlData = new UrlData();
212 urlData.hostID = host.UUID; 176 urlData.hostID = host.UUID;
@@ -215,14 +179,14 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
215 urlData.url = url; 179 urlData.url = url;
216 urlData.urlcode = urlcode; 180 urlData.urlcode = urlcode;
217 urlData.requests = new Dictionary<UUID, RequestData>(); 181 urlData.requests = new Dictionary<UUID, RequestData>();
218 182
219 m_UrlMap[url] = urlData; 183 m_UrlMap[url] = urlData;
220 184
221 string uri = "/lslhttp/" + urlcode.ToString() + "/"; 185 string uri = "/lslhttp/" + urlcode.ToString();
222 186
223 m_HttpServer.AddPollServiceHTTPHandler( 187 PollServiceEventArgs args = new PollServiceEventArgs(HttpRequestHandler, HasEvents, GetEvents, NoEvents, urlcode, 25000);
224 uri, 188 args.Type = PollServiceEventArgs.EventType.LslHttp;
225 new PollServiceEventArgs(HttpRequestHandler, HasEvents, GetEvents, NoEvents, urlcode)); 189 m_HttpServer.AddPollServiceHTTPHandler(uri, args);
226 190
227 m_log.DebugFormat( 191 m_log.DebugFormat(
228 "[URL MODULE]: Set up incoming request url {0} for {1} in {2} {3}", 192 "[URL MODULE]: Set up incoming request url {0} for {1} in {2} {3}",
@@ -251,7 +215,7 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
251 engine.PostScriptEvent(itemID, "http_request", new Object[] { urlcode.ToString(), "URL_REQUEST_DENIED", "" }); 215 engine.PostScriptEvent(itemID, "http_request", new Object[] { urlcode.ToString(), "URL_REQUEST_DENIED", "" });
252 return urlcode; 216 return urlcode;
253 } 217 }
254 string url = "https://" + m_ExternalHostNameForLSL + ":" + m_HttpsServer.Port.ToString() + "/lslhttps/" + urlcode.ToString() + "/"; 218 string url = "https://" + m_ExternalHostNameForLSL + ":" + m_HttpsServer.Port.ToString() + "/lslhttps/" + urlcode.ToString();
255 219
256 UrlData urlData = new UrlData(); 220 UrlData urlData = new UrlData();
257 urlData.hostID = host.UUID; 221 urlData.hostID = host.UUID;
@@ -261,13 +225,14 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
261 urlData.urlcode = urlcode; 225 urlData.urlcode = urlcode;
262 urlData.requests = new Dictionary<UUID, RequestData>(); 226 urlData.requests = new Dictionary<UUID, RequestData>();
263 227
228
264 m_UrlMap[url] = urlData; 229 m_UrlMap[url] = urlData;
265 230
266 string uri = "/lslhttps/" + urlcode.ToString() + "/"; 231 string uri = "/lslhttps/" + urlcode.ToString();
267 232
268 m_HttpsServer.AddPollServiceHTTPHandler( 233 PollServiceEventArgs args = new PollServiceEventArgs(HttpRequestHandler, HasEvents, GetEvents, NoEvents, urlcode, 25000);
269 uri, 234 args.Type = PollServiceEventArgs.EventType.LslHttp;
270 new PollServiceEventArgs(HttpRequestHandler, HasEvents, GetEvents, NoEvents, urlcode)); 235 m_HttpsServer.AddPollServiceHTTPHandler(uri, args);
271 236
272 m_log.DebugFormat( 237 m_log.DebugFormat(
273 "[URL MODULE]: Set up incoming secure request url {0} for {1} in {2} {3}", 238 "[URL MODULE]: Set up incoming secure request url {0} for {1} in {2} {3}",
@@ -290,12 +255,15 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
290 return; 255 return;
291 } 256 }
292 257
293 foreach (UUID req in data.requests.Keys) 258 lock (m_RequestMap)
294 m_RequestMap.Remove(req); 259 {
295 260 foreach (UUID req in data.requests.Keys)
296 m_log.DebugFormat( 261 m_RequestMap.Remove(req);
297 "[URL MODULE]: Releasing url {0} for {1} in {2}", 262 }
298 url, data.itemID, data.hostID); 263
264// m_log.DebugFormat(
265// "[URL MODULE]: Releasing url {0} for {1} in {2}",
266// url, data.itemID, data.hostID);
299 267
300 RemoveUrl(data); 268 RemoveUrl(data);
301 m_UrlMap.Remove(url); 269 m_UrlMap.Remove(url);
@@ -304,15 +272,19 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
304 272
305 public void HttpResponse(UUID request, int status, string body) 273 public void HttpResponse(UUID request, int status, string body)
306 { 274 {
307 lock (m_UrlMap) 275 lock (m_RequestMap)
308 { 276 {
309 if (m_RequestMap.ContainsKey(request)) 277 if (m_RequestMap.ContainsKey(request))
310 { 278 {
311 UrlData urlData = m_RequestMap[request]; 279 UrlData urlData = m_RequestMap[request];
312 urlData.requests[request].responseCode = status; 280 if (!urlData.requests[request].responseSent)
313 urlData.requests[request].responseBody = body; 281 {
314 //urlData.requests[request].ev.Set(); 282 urlData.requests[request].responseCode = status;
315 urlData.requests[request].requestDone =true; 283 urlData.requests[request].responseBody = body;
284 //urlData.requests[request].ev.Set();
285 urlData.requests[request].requestDone = true;
286 urlData.requests[request].responseSent = true;
287 }
316 } 288 }
317 else 289 else
318 { 290 {
@@ -323,7 +295,7 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
323 295
324 public string GetHttpHeader(UUID requestId, string header) 296 public string GetHttpHeader(UUID requestId, string header)
325 { 297 {
326 lock (m_UrlMap) 298 lock (m_RequestMap)
327 { 299 {
328 if (m_RequestMap.ContainsKey(requestId)) 300 if (m_RequestMap.ContainsKey(requestId))
329 { 301 {
@@ -337,14 +309,12 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
337 m_log.Warn("[HttpRequestHandler] There was no http-in request with id " + requestId); 309 m_log.Warn("[HttpRequestHandler] There was no http-in request with id " + requestId);
338 } 310 }
339 } 311 }
340
341 return String.Empty; 312 return String.Empty;
342 } 313 }
343 314
344 public int GetFreeUrls() 315 public int GetFreeUrls()
345 { 316 {
346 lock (m_UrlMap) 317 return m_TotalUrls - m_UrlMap.Count;
347 return m_TotalUrls - m_UrlMap.Count;
348 } 318 }
349 319
350 public void ScriptRemoved(UUID itemID) 320 public void ScriptRemoved(UUID itemID)
@@ -361,8 +331,11 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
361 { 331 {
362 RemoveUrl(url.Value); 332 RemoveUrl(url.Value);
363 removeURLs.Add(url.Key); 333 removeURLs.Add(url.Key);
364 foreach (UUID req in url.Value.requests.Keys) 334 lock (m_RequestMap)
365 m_RequestMap.Remove(req); 335 {
336 foreach (UUID req in url.Value.requests.Keys)
337 m_RequestMap.Remove(req);
338 }
366 } 339 }
367 } 340 }
368 341
@@ -383,9 +356,11 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
383 { 356 {
384 RemoveUrl(url.Value); 357 RemoveUrl(url.Value);
385 removeURLs.Add(url.Key); 358 removeURLs.Add(url.Key);
386 359 lock (m_RequestMap)
387 foreach (UUID req in url.Value.requests.Keys) 360 {
388 m_RequestMap.Remove(req); 361 foreach (UUID req in url.Value.requests.Keys)
362 m_RequestMap.Remove(req);
363 }
389 } 364 }
390 } 365 }
391 366
@@ -394,122 +369,125 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
394 } 369 }
395 } 370 }
396 371
372
397 private void RemoveUrl(UrlData data) 373 private void RemoveUrl(UrlData data)
398 { 374 {
399 m_HttpServer.RemoveHTTPHandler("", "/lslhttp/" + data.urlcode.ToString() + "/"); 375 m_HttpServer.RemoveHTTPHandler("", "/lslhttp/"+data.urlcode.ToString()+"/");
400 } 376 }
401 377
402 private Hashtable NoEvents(UUID requestID, UUID sessionID) 378 private Hashtable NoEvents(UUID requestID, UUID sessionID)
403 { 379 {
404 Hashtable response = new Hashtable(); 380 Hashtable response = new Hashtable();
405 UrlData urlData; 381 UrlData url;
406 382 int startTime = 0;
407 lock (m_UrlMap) 383 lock (m_RequestMap)
408 { 384 {
409 // We need to return a 404 here in case the request URL was removed at exactly the same time that a
410 // request was made. In this case, the request thread can outrace llRemoveURL() and still be polling
411 // for the request ID.
412 if (!m_RequestMap.ContainsKey(requestID)) 385 if (!m_RequestMap.ContainsKey(requestID))
413 {
414 response["int_response_code"] = 404;
415 response["str_response_string"] = "";
416 response["keepalive"] = false;
417 response["reusecontext"] = false;
418
419 return response; 386 return response;
420 } 387 url = m_RequestMap[requestID];
388 startTime = url.requests[requestID].startTime;
389 }
421 390
422 urlData = m_RequestMap[requestID]; 391 if (System.Environment.TickCount - startTime > 25000)
392 {
393 response["int_response_code"] = 500;
394 response["str_response_string"] = "Script timeout";
395 response["content_type"] = "text/plain";
396 response["keepalive"] = false;
397 response["reusecontext"] = false;
423 398
424 if (System.Environment.TickCount - urlData.requests[requestID].startTime > 25000) 399 //remove from map
400 lock (url.requests)
401 {
402 url.requests.Remove(requestID);
403 }
404 lock (m_RequestMap)
425 { 405 {
426 response["int_response_code"] = 500;
427 response["str_response_string"] = "Script timeout";
428 response["content_type"] = "text/plain";
429 response["keepalive"] = false;
430 response["reusecontext"] = false;
431
432 //remove from map
433 urlData.requests.Remove(requestID);
434 m_RequestMap.Remove(requestID); 406 m_RequestMap.Remove(requestID);
435
436 return response;
437 } 407 }
408
409 return response;
438 } 410 }
439 411
412
440 return response; 413 return response;
441 } 414 }
442 415
443 private bool HasEvents(UUID requestID, UUID sessionID) 416 private bool HasEvents(UUID requestID, UUID sessionID)
444 { 417 {
445 lock (m_UrlMap) 418 UrlData url=null;
419
420 lock (m_RequestMap)
446 { 421 {
447 // We return true here because an external URL request that happened at the same time as an llRemoveURL()
448 // can still make it through to HttpRequestHandler(). That will return without setting up a request
449 // when it detects that the URL has been removed. The poller, however, will continue to ask for
450 // events for that request, so here we will signal that there are events and in GetEvents we will
451 // return a 404.
452 if (!m_RequestMap.ContainsKey(requestID)) 422 if (!m_RequestMap.ContainsKey(requestID))
453 { 423 {
454 return true; 424 return false;
455 } 425 }
456 426 url = m_RequestMap[requestID];
457 UrlData urlData = m_RequestMap[requestID]; 427 }
458 428 lock (url.requests)
459 if (!urlData.requests.ContainsKey(requestID)) 429 {
430 if (!url.requests.ContainsKey(requestID))
460 { 431 {
461 return true; 432 return false;
462 } 433 }
463 434 else
464 // Trigger return of timeout response.
465 if (System.Environment.TickCount - urlData.requests[requestID].startTime > 25000)
466 { 435 {
467 return true; 436 if (System.Environment.TickCount - url.requests[requestID].startTime > 25000)
437 {
438 return true;
439 }
440 if (url.requests[requestID].requestDone)
441 return true;
442 else
443 return false;
468 } 444 }
469
470 return urlData.requests[requestID].requestDone;
471 } 445 }
472 } 446 }
473
474 private Hashtable GetEvents(UUID requestID, UUID sessionID, string request) 447 private Hashtable GetEvents(UUID requestID, UUID sessionID, string request)
475 { 448 {
476 Hashtable response; 449 UrlData url = null;
450 RequestData requestData = null;
477 451
478 lock (m_UrlMap) 452 lock (m_RequestMap)
479 { 453 {
480 UrlData url = null;
481 RequestData requestData = null;
482
483 if (!m_RequestMap.ContainsKey(requestID)) 454 if (!m_RequestMap.ContainsKey(requestID))
484 return NoEvents(requestID, sessionID); 455 return NoEvents(requestID,sessionID);
485
486 url = m_RequestMap[requestID]; 456 url = m_RequestMap[requestID];
457 }
458 lock (url.requests)
459 {
487 requestData = url.requests[requestID]; 460 requestData = url.requests[requestID];
461 }
462
463 if (!requestData.requestDone)
464 return NoEvents(requestID,sessionID);
465
466 Hashtable response = new Hashtable();
488 467
489 if (!requestData.requestDone) 468 if (System.Environment.TickCount - requestData.startTime > 25000)
490 return NoEvents(requestID, sessionID); 469 {
491 470 response["int_response_code"] = 500;
492 response = new Hashtable(); 471 response["str_response_string"] = "Script timeout";
493
494 if (System.Environment.TickCount - requestData.startTime > 25000)
495 {
496 response["int_response_code"] = 500;
497 response["str_response_string"] = "Script timeout";
498 response["content_type"] = "text/plain";
499 response["keepalive"] = false;
500 response["reusecontext"] = false;
501 return response;
502 }
503
504 //put response
505 response["int_response_code"] = requestData.responseCode;
506 response["str_response_string"] = requestData.responseBody;
507 response["content_type"] = "text/plain"; 472 response["content_type"] = "text/plain";
508 response["keepalive"] = false; 473 response["keepalive"] = false;
509 response["reusecontext"] = false; 474 response["reusecontext"] = false;
510 475 return response;
511 //remove from map 476 }
477 //put response
478 response["int_response_code"] = requestData.responseCode;
479 response["str_response_string"] = requestData.responseBody;
480 response["content_type"] = "text/plain";
481 response["keepalive"] = false;
482 response["reusecontext"] = false;
483
484 //remove from map
485 lock (url.requests)
486 {
512 url.requests.Remove(requestID); 487 url.requests.Remove(requestID);
488 }
489 lock (m_RequestMap)
490 {
513 m_RequestMap.Remove(requestID); 491 m_RequestMap.Remove(requestID);
514 } 492 }
515 493
@@ -518,41 +496,45 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
518 496
519 public void HttpRequestHandler(UUID requestID, Hashtable request) 497 public void HttpRequestHandler(UUID requestID, Hashtable request)
520 { 498 {
521 string uri = request["uri"].ToString(); 499 lock (request)
522 bool is_ssl = uri.Contains("lslhttps");
523
524 try
525 { 500 {
526 Hashtable headers = (Hashtable)request["headers"]; 501 string uri = request["uri"].ToString();
527 502 bool is_ssl = uri.Contains("lslhttps");
528// string uri_full = "http://" + m_ExternalHostNameForLSL + ":" + m_HttpServer.Port.ToString() + uri;// "/lslhttp/" + urlcode.ToString() + "/";
529 503
530 int pos1 = uri.IndexOf("/");// /lslhttp 504 try
531 int pos2 = uri.IndexOf("/", pos1 + 1);// /lslhttp/
532 int pos3 = uri.IndexOf("/", pos2 + 1);// /lslhttp/<UUID>/
533 string uri_tmp = uri.Substring(0, pos3 + 1);
534 //HTTP server code doesn't provide us with QueryStrings
535 string pathInfo;
536 string queryString;
537 queryString = "";
538
539 pathInfo = uri.Substring(pos3);
540
541 UrlData urlData = null;
542
543 lock (m_UrlMap)
544 { 505 {
545 string url; 506 Hashtable headers = (Hashtable)request["headers"];
507
508// string uri_full = "http://" + m_ExternalHostNameForLSL + ":" + m_HttpServer.Port.ToString() + uri;// "/lslhttp/" + urlcode.ToString() + "/";
546 509
547 if (is_ssl) 510 int pos1 = uri.IndexOf("/");// /lslhttp
548 url = "https://" + m_ExternalHostNameForLSL + ":" + m_HttpsServer.Port.ToString() + uri_tmp; 511 int pos2 = uri.IndexOf("/", pos1 + 1);// /lslhttp/
512 int pos3 = pos2 + 37; // /lslhttp/urlcode
513 string uri_tmp = uri.Substring(0, pos3);
514 //HTTP server code doesn't provide us with QueryStrings
515 string pathInfo;
516 string queryString;
517 queryString = "";
518
519 pathInfo = uri.Substring(pos3);
520
521 UrlData url = null;
522 string urlkey;
523 if (!is_ssl)
524 urlkey = "http://" + m_ExternalHostNameForLSL + ":" + m_HttpServer.Port.ToString() + uri_tmp;
525 //m_UrlMap[];
549 else 526 else
550 url = "http://" + m_ExternalHostNameForLSL + ":" + m_HttpServer.Port.ToString() + uri_tmp; 527 urlkey = "https://" + m_ExternalHostNameForLSL + ":" + m_HttpsServer.Port.ToString() + uri_tmp;
551 528
552 // Avoid a race - the request URL may have been released via llRequestUrl() whilst this 529 if (m_UrlMap.ContainsKey(urlkey))
553 // request was being processed. 530 {
554 if (!m_UrlMap.TryGetValue(url, out urlData)) 531 url = m_UrlMap[urlkey];
532 }
533 else
534 {
535 //m_log.Warn("[HttpRequestHandler]: http-in request failed; no such url: "+urlkey.ToString());
555 return; 536 return;
537 }
556 538
557 //for llGetHttpHeader support we need to store original URI here 539 //for llGetHttpHeader support we need to store original URI here
558 //to make x-path-info / x-query-string / x-script-url / x-remote-ip headers 540 //to make x-path-info / x-query-string / x-script-url / x-remote-ip headers
@@ -572,7 +554,6 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
572 string value = (string)header.Value; 554 string value = (string)header.Value;
573 requestData.headers.Add(key, value); 555 requestData.headers.Add(key, value);
574 } 556 }
575
576 foreach (DictionaryEntry de in request) 557 foreach (DictionaryEntry de in request)
577 { 558 {
578 if (de.Key.ToString() == "querystringkeys") 559 if (de.Key.ToString() == "querystringkeys")
@@ -583,13 +564,21 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
583 if (request.ContainsKey(key)) 564 if (request.ContainsKey(key))
584 { 565 {
585 string val = (String)request[key]; 566 string val = (String)request[key];
586 queryString = queryString + key + "=" + val + "&"; 567 if (key != "")
568 {
569 queryString = queryString + key + "=" + val + "&";
570 }
571 else
572 {
573 queryString = queryString + val + "&";
574 }
587 } 575 }
588 } 576 }
589
590 if (queryString.Length > 1) 577 if (queryString.Length > 1)
591 queryString = queryString.Substring(0, queryString.Length - 1); 578 queryString = queryString.Substring(0, queryString.Length - 1);
579
592 } 580 }
581
593 } 582 }
594 583
595 //if this machine is behind DNAT/port forwarding, currently this is being 584 //if this machine is behind DNAT/port forwarding, currently this is being
@@ -597,23 +586,34 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
597 requestData.headers["x-remote-ip"] = requestData.headers["remote_addr"]; 586 requestData.headers["x-remote-ip"] = requestData.headers["remote_addr"];
598 requestData.headers["x-path-info"] = pathInfo; 587 requestData.headers["x-path-info"] = pathInfo;
599 requestData.headers["x-query-string"] = queryString; 588 requestData.headers["x-query-string"] = queryString;
600 requestData.headers["x-script-url"] = urlData.url; 589 requestData.headers["x-script-url"] = url.url;
601 590
602 urlData.requests.Add(requestID, requestData); 591 //requestData.ev = new ManualResetEvent(false);
603 m_RequestMap.Add(requestID, urlData); 592 lock (url.requests)
604 } 593 {
594 url.requests.Add(requestID, requestData);
595 }
596 lock (m_RequestMap)
597 {
598 //add to request map
599 m_RequestMap.Add(requestID, url);
600 }
605 601
606 urlData.engine.PostScriptEvent( 602 url.engine.PostScriptEvent(url.itemID, "http_request", new Object[] { requestID.ToString(), request["http-method"].ToString(), request["body"].ToString() });
607 urlData.itemID, 603
608 "http_request", 604 //send initial response?
609 new Object[] { requestID.ToString(), request["http-method"].ToString(), request["body"].ToString() }); 605// Hashtable response = new Hashtable();
610 } 606
611 catch (Exception we) 607 return;
612 { 608
613 //Hashtable response = new Hashtable(); 609 }
614 m_log.Warn("[HttpRequestHandler]: http-in request failed"); 610 catch (Exception we)
615 m_log.Warn(we.Message); 611 {
616 m_log.Warn(we.StackTrace); 612 //Hashtable response = new Hashtable();
613 m_log.Warn("[HttpRequestHandler]: http-in request failed");
614 m_log.Warn(we.Message);
615 m_log.Warn(we.StackTrace);
616 }
617 } 617 }
618 } 618 }
619 619
@@ -622,4 +622,4 @@ namespace OpenSim.Region.CoreModules.Scripting.LSLHttp
622 ScriptRemoved(itemID); 622 ScriptRemoved(itemID);
623 } 623 }
624 } 624 }
625} \ No newline at end of file 625}
diff --git a/OpenSim/Region/CoreModules/Scripting/WorldComm/WorldCommModule.cs b/OpenSim/Region/CoreModules/Scripting/WorldComm/WorldCommModule.cs
index 8358bc0..07bb291 100644
--- a/OpenSim/Region/CoreModules/Scripting/WorldComm/WorldCommModule.cs
+++ b/OpenSim/Region/CoreModules/Scripting/WorldComm/WorldCommModule.cs
@@ -90,6 +90,8 @@ namespace OpenSim.Region.CoreModules.Scripting.WorldComm
90 // private static readonly ILog m_log = 90 // private static readonly ILog m_log =
91 // LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); 91 // LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
92 92
93 private const int DEBUG_CHANNEL = 2147483647;
94
93 private ListenerManager m_listenerManager; 95 private ListenerManager m_listenerManager;
94 private Queue m_pending; 96 private Queue m_pending;
95 private Queue m_pendingQ; 97 private Queue m_pendingQ;
@@ -308,56 +310,59 @@ namespace OpenSim.Region.CoreModules.Scripting.WorldComm
308 /// <param name='msg'> 310 /// <param name='msg'>
309 /// Message. 311 /// Message.
310 /// </param> 312 /// </param>
311 public void DeliverMessageTo(UUID target, int channel, Vector3 pos, string name, UUID id, string msg) 313 public bool DeliverMessageTo(UUID target, int channel, Vector3 pos, string name, UUID id, string msg, out string error)
312 { 314 {
315 error = null;
316
317 if (channel == DEBUG_CHANNEL)
318 return true;
319
313 // Is id an avatar? 320 // Is id an avatar?
314 ScenePresence sp = m_scene.GetScenePresence(target); 321 ScenePresence sp = m_scene.GetScenePresence(target);
315 322
316 if (sp != null) 323 if (sp != null)
317 { 324 {
318 // ignore if a child agent this is restricted to inside one region 325 // Send message to avatar
319 if (sp.IsChildAgent)
320 return;
321
322 // Send message to the avatar.
323 // Channel zero only goes to the avatar
324 // non zero channel messages only go to the attachments
325 if (channel == 0) 326 if (channel == 0)
326 { 327 {
327 m_scene.SimChatToAgent(target, Utils.StringToBytes(msg), pos, name, id, false); 328 // Channel 0 goes to viewer ONLY
328 } 329 m_scene.SimChat(Utils.StringToBytes(msg), ChatTypeEnum.Broadcast, 0, pos, name, id, false, false, target);
329 else 330 return true;
330 { 331 }
331 List<SceneObjectGroup> attachments = sp.GetAttachments();
332 if (attachments.Count == 0)
333 return;
334 332
335 // Get uuid of attachments 333 List<SceneObjectGroup> attachments = sp.GetAttachments();
336 List<UUID> targets = new List<UUID>();
337 foreach (SceneObjectGroup sog in attachments)
338 {
339 if (!sog.IsDeleted)
340 targets.Add(sog.UUID);
341 }
342 334
343 // Need to check each attachment 335 if (attachments.Count == 0)
344 foreach (ListenerInfo li in m_listenerManager.GetListeners(UUID.Zero, channel, name, id, msg)) 336 return true;
345 {
346 if (li.GetHostID().Equals(id))
347 continue;
348 337
349 if (m_scene.GetSceneObjectPart(li.GetHostID()) == null) 338 // Get uuid of attachments
350 continue; 339 List<UUID> targets = new List<UUID>();
340 foreach (SceneObjectGroup sog in attachments)
341 {
342 if (!sog.IsDeleted)
343 targets.Add(sog.UUID);
344 }
351 345
352 if (targets.Contains(li.GetHostID())) 346 // Need to check each attachment
353 QueueMessage(new ListenerInfo(li, name, id, msg)); 347 foreach (ListenerInfo li in m_listenerManager.GetListeners(UUID.Zero, channel, name, id, msg))
354 } 348 {
349 if (li.GetHostID().Equals(id))
350 continue;
351
352 if (m_scene.GetSceneObjectPart(li.GetHostID()) == null)
353 continue;
354
355 if (targets.Contains(li.GetHostID()))
356 QueueMessage(new ListenerInfo(li, name, id, msg));
355 } 357 }
356 358
357 return; 359 return true;
358 } 360 }
359 361
360 // No avatar found so look for an object 362 SceneObjectPart part = m_scene.GetSceneObjectPart(target);
363 if (part == null) // Not even an object
364 return true; // No error
365
361 foreach (ListenerInfo li in m_listenerManager.GetListeners(UUID.Zero, channel, name, id, msg)) 366 foreach (ListenerInfo li in m_listenerManager.GetListeners(UUID.Zero, channel, name, id, msg))
362 { 367 {
363 // Dont process if this message is from yourself! 368 // Dont process if this message is from yourself!
@@ -375,7 +380,7 @@ namespace OpenSim.Region.CoreModules.Scripting.WorldComm
375 } 380 }
376 } 381 }
377 382
378 return; 383 return true;
379 } 384 }
380 385
381 protected void QueueMessage(ListenerInfo li) 386 protected void QueueMessage(ListenerInfo li)