aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/OptionalModules/Avatar/Voice/VivoxVoice/VivoxVoiceModule.cs
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/OptionalModules/Avatar/Voice/VivoxVoice/VivoxVoiceModule.cs')
-rw-r--r--OpenSim/Region/OptionalModules/Avatar/Voice/VivoxVoice/VivoxVoiceModule.cs183
1 files changed, 107 insertions, 76 deletions
diff --git a/OpenSim/Region/OptionalModules/Avatar/Voice/VivoxVoice/VivoxVoiceModule.cs b/OpenSim/Region/OptionalModules/Avatar/Voice/VivoxVoice/VivoxVoiceModule.cs
index dd44564..defaa9c 100644
--- a/OpenSim/Region/OptionalModules/Avatar/Voice/VivoxVoice/VivoxVoiceModule.cs
+++ b/OpenSim/Region/OptionalModules/Avatar/Voice/VivoxVoice/VivoxVoiceModule.cs
@@ -114,13 +114,14 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
114 114
115 private static Dictionary<string,string> m_parents = new Dictionary<string,string>(); 115 private static Dictionary<string,string> m_parents = new Dictionary<string,string>();
116 private static bool m_dumpXml; 116 private static bool m_dumpXml;
117 117
118 private IConfig m_config; 118 private IConfig m_config;
119 119
120 private object m_Lock; 120 private object m_Lock;
121 121
122 public void Initialise(IConfigSource config) 122 public void Initialise(IConfigSource config)
123 { 123 {
124 MainConsole.Instance.Commands.AddCommand("vivox", false, "vivox debug", "vivox debug <on>|<off>", "Set vivox debugging", HandleDebug);
124 125
125 m_config = config.Configs["VivoxVoice"]; 126 m_config = config.Configs["VivoxVoice"];
126 127
@@ -152,22 +153,22 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
152 // Validate against constraints and default if necessary 153 // Validate against constraints and default if necessary
153 if (m_vivoxChannelRollOff < CHAN_ROLL_OFF_MIN || m_vivoxChannelRollOff > CHAN_ROLL_OFF_MAX) 154 if (m_vivoxChannelRollOff < CHAN_ROLL_OFF_MIN || m_vivoxChannelRollOff > CHAN_ROLL_OFF_MAX)
154 { 155 {
155 m_log.WarnFormat("[VivoxVoice] Invalid value for roll off ({0}), reset to {1}.", 156 m_log.WarnFormat("[VivoxVoice] Invalid value for roll off ({0}), reset to {1}.",
156 m_vivoxChannelRollOff, CHAN_ROLL_OFF_DEFAULT); 157 m_vivoxChannelRollOff, CHAN_ROLL_OFF_DEFAULT);
157 m_vivoxChannelRollOff = CHAN_ROLL_OFF_DEFAULT; 158 m_vivoxChannelRollOff = CHAN_ROLL_OFF_DEFAULT;
158 } 159 }
159 160
160 if (m_vivoxChannelMaximumRange < CHAN_MAX_RANGE_MIN || m_vivoxChannelMaximumRange > CHAN_MAX_RANGE_MAX) 161 if (m_vivoxChannelMaximumRange < CHAN_MAX_RANGE_MIN || m_vivoxChannelMaximumRange > CHAN_MAX_RANGE_MAX)
161 { 162 {
162 m_log.WarnFormat("[VivoxVoice] Invalid value for maximum range ({0}), reset to {1}.", 163 m_log.WarnFormat("[VivoxVoice] Invalid value for maximum range ({0}), reset to {1}.",
163 m_vivoxChannelMaximumRange, CHAN_MAX_RANGE_DEFAULT); 164 m_vivoxChannelMaximumRange, CHAN_MAX_RANGE_DEFAULT);
164 m_vivoxChannelMaximumRange = CHAN_MAX_RANGE_DEFAULT; 165 m_vivoxChannelMaximumRange = CHAN_MAX_RANGE_DEFAULT;
165 } 166 }
166 167
167 if (m_vivoxChannelClampingDistance < CHAN_CLAMPING_DISTANCE_MIN || 168 if (m_vivoxChannelClampingDistance < CHAN_CLAMPING_DISTANCE_MIN ||
168 m_vivoxChannelClampingDistance > CHAN_CLAMPING_DISTANCE_MAX) 169 m_vivoxChannelClampingDistance > CHAN_CLAMPING_DISTANCE_MAX)
169 { 170 {
170 m_log.WarnFormat("[VivoxVoice] Invalid value for clamping distance ({0}), reset to {1}.", 171 m_log.WarnFormat("[VivoxVoice] Invalid value for clamping distance ({0}), reset to {1}.",
171 m_vivoxChannelClampingDistance, CHAN_CLAMPING_DISTANCE_DEFAULT); 172 m_vivoxChannelClampingDistance, CHAN_CLAMPING_DISTANCE_DEFAULT);
172 m_vivoxChannelClampingDistance = CHAN_CLAMPING_DISTANCE_DEFAULT; 173 m_vivoxChannelClampingDistance = CHAN_CLAMPING_DISTANCE_DEFAULT;
173 } 174 }
@@ -179,7 +180,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
179 case "presentation" : break; 180 case "presentation" : break;
180 case "auditorium" : break; 181 case "auditorium" : break;
181 default : 182 default :
182 m_log.WarnFormat("[VivoxVoice] Invalid value for channel mode ({0}), reset to {1}.", 183 m_log.WarnFormat("[VivoxVoice] Invalid value for channel mode ({0}), reset to {1}.",
183 m_vivoxChannelMode, CHAN_MODE_DEFAULT); 184 m_vivoxChannelMode, CHAN_MODE_DEFAULT);
184 m_vivoxChannelMode = CHAN_MODE_DEFAULT; 185 m_vivoxChannelMode = CHAN_MODE_DEFAULT;
185 break; 186 break;
@@ -190,7 +191,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
190 case "positional" : break; 191 case "positional" : break;
191 case "channel" : break; 192 case "channel" : break;
192 default : 193 default :
193 m_log.WarnFormat("[VivoxVoice] Invalid value for channel type ({0}), reset to {1}.", 194 m_log.WarnFormat("[VivoxVoice] Invalid value for channel type ({0}), reset to {1}.",
194 m_vivoxChannelType, CHAN_TYPE_DEFAULT); 195 m_vivoxChannelType, CHAN_TYPE_DEFAULT);
195 m_vivoxChannelType = CHAN_TYPE_DEFAULT; 196 m_vivoxChannelType = CHAN_TYPE_DEFAULT;
196 break; 197 break;
@@ -229,7 +230,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
229 230
230 public void AddRegion(Scene scene) 231 public void AddRegion(Scene scene)
231 { 232 {
232 if (m_pluginEnabled) 233 if (m_pluginEnabled)
233 { 234 {
234 lock (vlock) 235 lock (vlock)
235 { 236 {
@@ -237,13 +238,13 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
237 238
238 string sceneUUID = scene.RegionInfo.RegionID.ToString(); 239 string sceneUUID = scene.RegionInfo.RegionID.ToString();
239 string sceneName = scene.RegionInfo.RegionName; 240 string sceneName = scene.RegionInfo.RegionName;
240 241
241 // Make sure that all local channels are deleted. 242 // Make sure that all local channels are deleted.
242 // So we have to search for the children, and then do an 243 // So we have to search for the children, and then do an
243 // iteration over the set of chidren identified. 244 // iteration over the set of chidren identified.
244 // This assumes that there is just one directory per 245 // This assumes that there is just one directory per
245 // region. 246 // region.
246 247
247 if (VivoxTryGetDirectory(sceneUUID + "D", out channelId)) 248 if (VivoxTryGetDirectory(sceneUUID + "D", out channelId))
248 { 249 {
249 m_log.DebugFormat("[VivoxVoice]: region {0}: uuid {1}: located directory id {2}", 250 m_log.DebugFormat("[VivoxVoice]: region {0}: uuid {1}: located directory id {2}",
@@ -262,7 +263,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
262 { 263 {
263 if (!IsOK(VivoxDeleteChannel(channelId, id))) 264 if (!IsOK(VivoxDeleteChannel(channelId, id)))
264 m_log.WarnFormat("[VivoxVoice] Channel delete failed {0}:{1}:{2}", i, channelId, id); 265 m_log.WarnFormat("[VivoxVoice] Channel delete failed {0}:{1}:{2}", i, channelId, id);
265 } 266 }
266 } 267 }
267 } 268 }
268 } 269 }
@@ -310,7 +311,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
310 311
311 public void RemoveRegion(Scene scene) 312 public void RemoveRegion(Scene scene)
312 { 313 {
313 if (m_pluginEnabled) 314 if (m_pluginEnabled)
314 { 315 {
315 lock (vlock) 316 lock (vlock)
316 { 317 {
@@ -318,7 +319,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
318 319
319 string sceneUUID = scene.RegionInfo.RegionID.ToString(); 320 string sceneUUID = scene.RegionInfo.RegionID.ToString();
320 string sceneName = scene.RegionInfo.RegionName; 321 string sceneName = scene.RegionInfo.RegionName;
321 322
322 // Make sure that all local channels are deleted. 323 // Make sure that all local channels are deleted.
323 // So we have to search for the children, and then do an 324 // So we have to search for the children, and then do an
324 // iteration over the set of chidren identified. 325 // iteration over the set of chidren identified.
@@ -342,7 +343,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
342 { 343 {
343 if (!IsOK(VivoxDeleteChannel(channelId, id))) 344 if (!IsOK(VivoxDeleteChannel(channelId, id)))
344 m_log.WarnFormat("[VivoxVoice] Channel delete failed {0}:{1}:{2}", i, channelId, id); 345 m_log.WarnFormat("[VivoxVoice] Channel delete failed {0}:{1}:{2}", i, channelId, id);
345 } 346 }
346 } 347 }
347 } 348 }
348 } 349 }
@@ -352,7 +353,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
352 353
353 // Remove the channel umbrella entry 354 // Remove the channel umbrella entry
354 355
355 lock (m_parents) 356 lock (m_parents)
356 { 357 {
357 if (m_parents.ContainsKey(sceneUUID)) 358 if (m_parents.ContainsKey(sceneUUID))
358 { 359 {
@@ -374,7 +375,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
374 VivoxLogout(); 375 VivoxLogout();
375 } 376 }
376 377
377 public Type ReplaceableInterface 378 public Type ReplaceableInterface
378 { 379 {
379 get { return null; } 380 get { return null; }
380 } 381 }
@@ -395,11 +396,11 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
395 // (login, region crossing). We contribute two capabilities to 396 // (login, region crossing). We contribute two capabilities to
396 // the set of capabilities handed back to the client: 397 // the set of capabilities handed back to the client:
397 // ProvisionVoiceAccountRequest and ParcelVoiceInfoRequest. 398 // ProvisionVoiceAccountRequest and ParcelVoiceInfoRequest.
398 // 399 //
399 // ProvisionVoiceAccountRequest allows the client to obtain 400 // ProvisionVoiceAccountRequest allows the client to obtain
400 // the voice account credentials for the avatar it is 401 // the voice account credentials for the avatar it is
401 // controlling (e.g., user name, password, etc). 402 // controlling (e.g., user name, password, etc).
402 // 403 //
403 // ParcelVoiceInfoRequest is invoked whenever the client 404 // ParcelVoiceInfoRequest is invoked whenever the client
404 // changes from one region or parcel to another. 405 // changes from one region or parcel to another.
405 // 406 //
@@ -475,8 +476,8 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
475 avatarName = avatar.Name; 476 avatarName = avatar.Name;
476 477
477 m_log.DebugFormat("[VivoxVoice][PROVISIONVOICE]: scene = {0}, agentID = {1}", scene, agentID); 478 m_log.DebugFormat("[VivoxVoice][PROVISIONVOICE]: scene = {0}, agentID = {1}", scene, agentID);
478 m_log.DebugFormat("[VivoxVoice][PROVISIONVOICE]: request: {0}, path: {1}, param: {2}", 479// m_log.DebugFormat("[VivoxVoice][PROVISIONVOICE]: request: {0}, path: {1}, param: {2}",
479 request, path, param); 480// request, path, param);
480 481
481 XmlElement resp; 482 XmlElement resp;
482 bool retry = false; 483 bool retry = false;
@@ -492,9 +493,9 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
492 493
493 if (XmlFind(resp, "response.level0.status", out code)) 494 if (XmlFind(resp, "response.level0.status", out code))
494 { 495 {
495 if (code != "OK") 496 if (code != "OK")
496 { 497 {
497 if (XmlFind(resp, "response.level0.body.code", out code)) 498 if (XmlFind(resp, "response.level0.body.code", out code))
498 { 499 {
499 // If the request was recognized, then this should be set to something 500 // If the request was recognized, then this should be set to something
500 switch (code) 501 switch (code)
@@ -529,27 +530,27 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
529 switch (code) 530 switch (code)
530 { 531 {
531 case "201" : // Account expired 532 case "201" : // Account expired
532 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Create account information failed : expired credentials", 533 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Create account information failed : expired credentials",
533 avatarName); 534 avatarName);
534 m_adminConnected = false; 535 m_adminConnected = false;
535 retry = DoAdminLogin(); 536 retry = DoAdminLogin();
536 break; 537 break;
537 538
538 case "202" : // Missing credentials 539 case "202" : // Missing credentials
539 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Create account information failed : missing credentials", 540 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Create account information failed : missing credentials",
540 avatarName); 541 avatarName);
541 break; 542 break;
542 543
543 case "212" : // Not authorized 544 case "212" : // Not authorized
544 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Create account information failed : not authorized", 545 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Create account information failed : not authorized",
545 avatarName); 546 avatarName);
546 break; 547 break;
547 548
548 case "300" : // Required parameter missing 549 case "300" : // Required parameter missing
549 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Create account information failed : parameter missing", 550 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Create account information failed : parameter missing",
550 avatarName); 551 avatarName);
551 break; 552 break;
552 553
553 case "400" : // Create failed 554 case "400" : // Create failed
554 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Create account information failed : create failed", 555 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Create account information failed : create failed",
555 avatarName); 556 avatarName);
@@ -557,7 +558,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
557 } 558 }
558 } 559 }
559 break; 560 break;
560 561
561 case "404" : // Failed to retrieve account 562 case "404" : // Failed to retrieve account
562 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Get account information failed : retrieve failed"); 563 m_log.ErrorFormat("[VivoxVoice]: avatar \"{0}\": Get account information failed : retrieve failed");
563 // [AMW] Sleep and retry for a fixed period? Or just abandon? 564 // [AMW] Sleep and retry for a fixed period? Or just abandon?
@@ -574,7 +575,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
574 m_log.DebugFormat("[VivoxVoice][PROVISIONVOICE]: Get Account Request failed for \"{0}\"", avatarName); 575 m_log.DebugFormat("[VivoxVoice][PROVISIONVOICE]: Get Account Request failed for \"{0}\"", avatarName);
575 throw new Exception("Unable to execute request"); 576 throw new Exception("Unable to execute request");
576 } 577 }
577 578
578 // Unconditionally change the password on each request 579 // Unconditionally change the password on each request
579 VivoxPassword(agentname, password); 580 VivoxPassword(agentname, password);
580 581
@@ -583,7 +584,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
583 584
584 string r = LLSDHelpers.SerialiseLLSDReply(voiceAccountResponse); 585 string r = LLSDHelpers.SerialiseLLSDReply(voiceAccountResponse);
585 586
586 m_log.DebugFormat("[VivoxVoice][PROVISIONVOICE]: avatar \"{0}\": {1}", avatarName, r); 587// m_log.DebugFormat("[VivoxVoice][PROVISIONVOICE]: avatar \"{0}\": {1}", avatarName, r);
587 588
588 return r; 589 return r;
589 } 590 }
@@ -612,7 +613,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
612 string avatarName = avatar.Name; 613 string avatarName = avatar.Name;
613 614
614 // - check whether we have a region channel in our cache 615 // - check whether we have a region channel in our cache
615 // - if not: 616 // - if not:
616 // create it and cache it 617 // create it and cache it
617 // - send it to the client 618 // - send it to the client
618 // - send channel_uri: as "sip:regionID@m_sipDomain" 619 // - send channel_uri: as "sip:regionID@m_sipDomain"
@@ -621,7 +622,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
621 LLSDParcelVoiceInfoResponse parcelVoiceInfo; 622 LLSDParcelVoiceInfoResponse parcelVoiceInfo;
622 string channel_uri; 623 string channel_uri;
623 624
624 if (null == scene.LandChannel) 625 if (null == scene.LandChannel)
625 throw new Exception(String.Format("region \"{0}\": avatar \"{1}\": land data not yet available", 626 throw new Exception(String.Format("region \"{0}\": avatar \"{1}\": land data not yet available",
626 scene.RegionInfo.RegionName, avatarName)); 627 scene.RegionInfo.RegionName, avatarName));
627 628
@@ -630,24 +631,28 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
630 // voice, if all do retrieve or obtain the parcel 631 // voice, if all do retrieve or obtain the parcel
631 // voice channel 632 // voice channel
632 LandData land = scene.GetLandData(avatar.AbsolutePosition); 633 LandData land = scene.GetLandData(avatar.AbsolutePosition);
634 if (land == null)
635 {
636 return "<llsd><undef /></llsd>";
637 }
633 638
634 m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": Parcel \"{1}\" ({2}): avatar \"{3}\": request: {4}, path: {5}, param: {6}", 639// m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": Parcel \"{1}\" ({2}): avatar \"{3}\": request: {4}, path: {5}, param: {6}",
635 scene.RegionInfo.RegionName, land.Name, land.LocalID, avatarName, request, path, param); 640// scene.RegionInfo.RegionName, land.Name, land.LocalID, avatarName, request, path, param);
636 // m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: avatar \"{0}\": location: {1} {2} {3}", 641 // m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: avatar \"{0}\": location: {1} {2} {3}",
637 // avatarName, avatar.AbsolutePosition.X, avatar.AbsolutePosition.Y, avatar.AbsolutePosition.Z); 642 // avatarName, avatar.AbsolutePosition.X, avatar.AbsolutePosition.Y, avatar.AbsolutePosition.Z);
638 643
639 // TODO: EstateSettings don't seem to get propagated... 644 // TODO: EstateSettings don't seem to get propagated...
640 if (!scene.RegionInfo.EstateSettings.AllowVoice) 645 if (!scene.RegionInfo.EstateSettings.AllowVoice)
641 { 646 {
642 m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": voice not enabled in estate settings", 647 //m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": voice not enabled in estate settings",
643 scene.RegionInfo.RegionName); 648 // scene.RegionInfo.RegionName);
644 channel_uri = String.Empty; 649 channel_uri = String.Empty;
645 } 650 }
646 651
647 if ((land.Flags & (uint)ParcelFlags.AllowVoiceChat) == 0) 652 if ((land.Flags & (uint)ParcelFlags.AllowVoiceChat) == 0)
648 { 653 {
649 m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": Parcel \"{1}\" ({2}): avatar \"{3}\": voice not enabled for parcel", 654 //m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": Parcel \"{1}\" ({2}): avatar \"{3}\": voice not enabled for parcel",
650 scene.RegionInfo.RegionName, land.Name, land.LocalID, avatarName); 655 // scene.RegionInfo.RegionName, land.Name, land.LocalID, avatarName);
651 channel_uri = String.Empty; 656 channel_uri = String.Empty;
652 } 657 }
653 else 658 else
@@ -662,15 +667,15 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
662 parcelVoiceInfo = new LLSDParcelVoiceInfoResponse(scene.RegionInfo.RegionName, land.LocalID, creds); 667 parcelVoiceInfo = new LLSDParcelVoiceInfoResponse(scene.RegionInfo.RegionName, land.LocalID, creds);
663 string r = LLSDHelpers.SerialiseLLSDReply(parcelVoiceInfo); 668 string r = LLSDHelpers.SerialiseLLSDReply(parcelVoiceInfo);
664 669
665 m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": Parcel \"{1}\" ({2}): avatar \"{3}\": {4}", 670// m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": Parcel \"{1}\" ({2}): avatar \"{3}\": {4}",
666 scene.RegionInfo.RegionName, land.Name, land.LocalID, avatarName, r); 671// scene.RegionInfo.RegionName, land.Name, land.LocalID, avatarName, r);
667 return r; 672 return r;
668 } 673 }
669 catch (Exception e) 674 catch (Exception e)
670 { 675 {
671 m_log.ErrorFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": avatar \"{1}\": {2}, retry later", 676 m_log.ErrorFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": avatar \"{1}\": {2}, retry later",
672 scene.RegionInfo.RegionName, avatarName, e.Message); 677 scene.RegionInfo.RegionName, avatarName, e.Message);
673 m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": avatar \"{1}\": {2} failed", 678 m_log.DebugFormat("[VivoxVoice][PARCELVOICE]: region \"{0}\": avatar \"{1}\": {2} failed",
674 scene.RegionInfo.RegionName, avatarName, e.ToString()); 679 scene.RegionInfo.RegionName, avatarName, e.ToString());
675 680
676 return "<llsd><undef /></llsd>"; 681 return "<llsd><undef /></llsd>";
@@ -690,11 +695,11 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
690 public string ChatSessionRequest(Scene scene, string request, string path, string param, 695 public string ChatSessionRequest(Scene scene, string request, string path, string param,
691 UUID agentID, Caps caps) 696 UUID agentID, Caps caps)
692 { 697 {
693 ScenePresence avatar = scene.GetScenePresence(agentID); 698// ScenePresence avatar = scene.GetScenePresence(agentID);
694 string avatarName = avatar.Name; 699// string avatarName = avatar.Name;
695 700
696 m_log.DebugFormat("[VivoxVoice][CHATSESSION]: avatar \"{0}\": request: {1}, path: {2}, param: {3}", 701// m_log.DebugFormat("[VivoxVoice][CHATSESSION]: avatar \"{0}\": request: {1}, path: {2}, param: {3}",
697 avatarName, request, path, param); 702// avatarName, request, path, param);
698 return "<llsd>true</llsd>"; 703 return "<llsd>true</llsd>";
699 } 704 }
700 705
@@ -716,17 +721,17 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
716 { 721 {
717 landName = String.Format("{0}:{1}", scene.RegionInfo.RegionName, land.Name); 722 landName = String.Format("{0}:{1}", scene.RegionInfo.RegionName, land.Name);
718 landUUID = land.GlobalID.ToString(); 723 landUUID = land.GlobalID.ToString();
719 m_log.DebugFormat("[VivoxVoice]: Region:Parcel \"{0}\": parcel id {1}: using channel name {2}", 724 m_log.DebugFormat("[VivoxVoice]: Region:Parcel \"{0}\": parcel id {1}: using channel name {2}",
720 landName, land.LocalID, landUUID); 725 landName, land.LocalID, landUUID);
721 } 726 }
722 else 727 else
723 { 728 {
724 landName = String.Format("{0}:{1}", scene.RegionInfo.RegionName, scene.RegionInfo.RegionName); 729 landName = String.Format("{0}:{1}", scene.RegionInfo.RegionName, scene.RegionInfo.RegionName);
725 landUUID = scene.RegionInfo.RegionID.ToString(); 730 landUUID = scene.RegionInfo.RegionID.ToString();
726 m_log.DebugFormat("[VivoxVoice]: Region:Parcel \"{0}\": parcel id {1}: using channel name {2}", 731 m_log.DebugFormat("[VivoxVoice]: Region:Parcel \"{0}\": parcel id {1}: using channel name {2}",
727 landName, land.LocalID, landUUID); 732 landName, land.LocalID, landUUID);
728 } 733 }
729 734
730 lock (vlock) 735 lock (vlock)
731 { 736 {
732 // Added by Adam to help debug channel not availible errors. 737 // Added by Adam to help debug channel not availible errors.
@@ -737,7 +742,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
737 else 742 else
738 throw new Exception("vivox channel uri not available"); 743 throw new Exception("vivox channel uri not available");
739 744
740 m_log.DebugFormat("[VivoxVoice]: Region:Parcel \"{0}\": parent channel id {1}: retrieved parcel channel_uri {2} ", 745 m_log.DebugFormat("[VivoxVoice]: Region:Parcel \"{0}\": parent channel id {1}: retrieved parcel channel_uri {2} ",
741 landName, parentId, channelUri); 746 landName, parentId, channelUri);
742 } 747 }
743 748
@@ -767,6 +772,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
767 return VivoxCall(requrl, false); 772 return VivoxCall(requrl, false);
768 } 773 }
769 774
775
770 private static readonly string m_vivoxGetAccountPath = "http://{0}/api2/viv_get_acct.php?auth_token={1}&user_name={2}"; 776 private static readonly string m_vivoxGetAccountPath = "http://{0}/api2/viv_get_acct.php?auth_token={1}&user_name={2}";
771 777
772 /// <summary> 778 /// <summary>
@@ -779,6 +785,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
779 return VivoxCall(requrl, true); 785 return VivoxCall(requrl, true);
780 } 786 }
781 787
788
782 private static readonly string m_vivoxNewAccountPath = "http://{0}/api2/viv_adm_acct_new.php?username={1}&pwd={2}&auth_token={3}"; 789 private static readonly string m_vivoxNewAccountPath = "http://{0}/api2/viv_adm_acct_new.php?username={1}&pwd={2}&auth_token={3}";
783 790
784 /// <summary> 791 /// <summary>
@@ -793,6 +800,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
793 return VivoxCall(requrl, true); 800 return VivoxCall(requrl, true);
794 } 801 }
795 802
803
796 private static readonly string m_vivoxPasswordPath = "http://{0}/api2/viv_adm_password.php?user_name={1}&new_pwd={2}&auth_token={3}"; 804 private static readonly string m_vivoxPasswordPath = "http://{0}/api2/viv_adm_password.php?user_name={1}&new_pwd={2}&auth_token={3}";
797 805
798 /// <summary> 806 /// <summary>
@@ -804,18 +812,19 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
804 return VivoxCall(requrl, true); 812 return VivoxCall(requrl, true);
805 } 813 }
806 814
815
807 private static readonly string m_vivoxChannelPath = "http://{0}/api2/viv_chan_mod.php?mode={1}&chan_name={2}&auth_token={3}"; 816 private static readonly string m_vivoxChannelPath = "http://{0}/api2/viv_chan_mod.php?mode={1}&chan_name={2}&auth_token={3}";
808 817
809 /// <summary> 818 /// <summary>
810 /// Create a channel. 819 /// Create a channel.
811 /// Once again, there a multitude of options possible. In the simplest case 820 /// Once again, there a multitude of options possible. In the simplest case
812 /// we specify only the name and get a non-persistent cannel in return. Non 821 /// we specify only the name and get a non-persistent cannel in return. Non
813 /// persistent means that the channel gets deleted if no-one uses it for 822 /// persistent means that the channel gets deleted if no-one uses it for
814 /// 5 hours. To accomodate future requirements, it may be a good idea to 823 /// 5 hours. To accomodate future requirements, it may be a good idea to
815 /// initially create channels under the umbrella of a parent ID based upon 824 /// initially create channels under the umbrella of a parent ID based upon
816 /// the region name. That way we have a context for side channels, if those 825 /// the region name. That way we have a context for side channels, if those
817 /// are required in a later phase. 826 /// are required in a later phase.
818 /// 827 ///
819 /// In this case the call handles parent and description as optional values. 828 /// In this case the call handles parent and description as optional values.
820 /// </summary> 829 /// </summary>
821 private bool VivoxTryCreateChannel(string parent, string channelId, string description, out string channelUri) 830 private bool VivoxTryCreateChannel(string parent, string channelId, string description, out string channelUri)
@@ -837,7 +846,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
837 requrl = String.Format("{0}&chan_dist_model={1}", requrl, m_vivoxChannelDistanceModel); 846 requrl = String.Format("{0}&chan_dist_model={1}", requrl, m_vivoxChannelDistanceModel);
838 requrl = String.Format("{0}&chan_max_range={1}", requrl, m_vivoxChannelMaximumRange); 847 requrl = String.Format("{0}&chan_max_range={1}", requrl, m_vivoxChannelMaximumRange);
839 requrl = String.Format("{0}&chan_clamping_distance={1}", requrl, m_vivoxChannelClampingDistance); 848 requrl = String.Format("{0}&chan_clamping_distance={1}", requrl, m_vivoxChannelClampingDistance);
840 849
841 XmlElement resp = VivoxCall(requrl, true); 850 XmlElement resp = VivoxCall(requrl, true);
842 if (XmlFind(resp, "response.level0.body.chan_uri", out channelUri)) 851 if (XmlFind(resp, "response.level0.body.chan_uri", out channelUri))
843 return true; 852 return true;
@@ -880,7 +889,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
880 889
881 /// <summary> 890 /// <summary>
882 /// Retrieve a channel. 891 /// Retrieve a channel.
883 /// Once again, there a multitude of options possible. In the simplest case 892 /// Once again, there a multitude of options possible. In the simplest case
884 /// we specify only the name and get a non-persistent cannel in return. Non 893 /// we specify only the name and get a non-persistent cannel in return. Non
885 /// persistent means that the channel gets deleted if no-one uses it for 894 /// persistent means that the channel gets deleted if no-one uses it for
886 /// 5 hours. To accomodate future requirements, it may be a good idea to 895 /// 5 hours. To accomodate future requirements, it may be a good idea to
@@ -889,7 +898,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
889 /// are required in a later phase. 898 /// are required in a later phase.
890 /// In this case the call handles parent and description as optional values. 899 /// In this case the call handles parent and description as optional values.
891 /// </summary> 900 /// </summary>
892 private bool VivoxTryGetChannel(string channelParent, string channelName, 901 private bool VivoxTryGetChannel(string channelParent, string channelName,
893 out string channelId, out string channelUri) 902 out string channelId, out string channelUri)
894 { 903 {
895 string count; 904 string count;
@@ -997,7 +1006,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
997 string type; 1006 string type;
998 1007
999 // skip if not a directory 1008 // skip if not a directory
1000 if (!XmlFind(resp, "response.level0.channel-search.channels.channels.level4.type", i, out type) || 1009 if (!XmlFind(resp, "response.level0.channel-search.channels.channels.level4.type", i, out type) ||
1001 type != "dir") 1010 type != "dir")
1002 continue; 1011 continue;
1003 1012
@@ -1019,7 +1028,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1019 return false; 1028 return false;
1020 } 1029 }
1021 1030
1022 // private static readonly string m_vivoxChannelById = "http://{0}/api2/viv_chan_mod.php?mode={1}&chan_id={2}&auth_token={3}"; 1031 // private static readonly string m_vivoxChannelById = "https://{0}/api2/viv_chan_mod.php?mode={1}&chan_id={2}&auth_token={3}";
1023 1032
1024 // private XmlElement VivoxGetChannelById(string parent, string channelid) 1033 // private XmlElement VivoxGetChannelById(string parent, string channelid)
1025 // { 1034 // {
@@ -1035,7 +1044,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1035 1044
1036 /// <summary> 1045 /// <summary>
1037 /// Delete a channel. 1046 /// Delete a channel.
1038 /// Once again, there a multitude of options possible. In the simplest case 1047 /// Once again, there a multitude of options possible. In the simplest case
1039 /// we specify only the name and get a non-persistent cannel in return. Non 1048 /// we specify only the name and get a non-persistent cannel in return. Non
1040 /// persistent means that the channel gets deleted if no-one uses it for 1049 /// persistent means that the channel gets deleted if no-one uses it for
1041 /// 5 hours. To accomodate future requirements, it may be a good idea to 1050 /// 5 hours. To accomodate future requirements, it may be a good idea to
@@ -1044,6 +1053,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1044 /// are required in a later phase. 1053 /// are required in a later phase.
1045 /// In this case the call handles parent and description as optional values. 1054 /// In this case the call handles parent and description as optional values.
1046 /// </summary> 1055 /// </summary>
1056
1047 private XmlElement VivoxDeleteChannel(string parent, string channelid) 1057 private XmlElement VivoxDeleteChannel(string parent, string channelid)
1048 { 1058 {
1049 string requrl = String.Format(m_vivoxChannelDel, m_vivoxServer, "delete", channelid, m_authToken); 1059 string requrl = String.Format(m_vivoxChannelDel, m_vivoxServer, "delete", channelid, m_authToken);
@@ -1059,6 +1069,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1059 /// <summary> 1069 /// <summary>
1060 /// Return information on channels in the given directory 1070 /// Return information on channels in the given directory
1061 /// </summary> 1071 /// </summary>
1072
1062 private XmlElement VivoxListChildren(string channelid) 1073 private XmlElement VivoxListChildren(string channelid)
1063 { 1074 {
1064 string requrl = String.Format(m_vivoxChannelSearch, m_vivoxServer, channelid, m_authToken); 1075 string requrl = String.Format(m_vivoxChannelSearch, m_vivoxServer, channelid, m_authToken);
@@ -1087,7 +1098,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1087 // return VivoxGetChannelById(null, id); 1098 // return VivoxGetChannelById(null, id);
1088 // } 1099 // }
1089 // } 1100 // }
1090 // } 1101 // }
1091 // } 1102 // }
1092 // } 1103 // }
1093 1104
@@ -1095,12 +1106,12 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1095 // return VivoxGetChannel(null, Guid.NewGuid().ToString()); 1106 // return VivoxGetChannel(null, Guid.NewGuid().ToString());
1096 1107
1097 // } 1108 // }
1098 1109
1099 /// <summary> 1110 /// <summary>
1100 /// This method handles the WEB side of making a request over the 1111 /// This method handles the WEB side of making a request over the
1101 /// Vivox interface. The returned values are tansferred to a has 1112 /// Vivox interface. The returned values are tansferred to a has
1102 /// table which is returned as the result. 1113 /// table which is returned as the result.
1103 /// The outcome of the call can be determined by examining the 1114 /// The outcome of the call can be determined by examining the
1104 /// status value in the hash table. 1115 /// status value in the hash table.
1105 /// </summary> 1116 /// </summary>
1106 private XmlElement VivoxCall(string requrl, bool admin) 1117 private XmlElement VivoxCall(string requrl, bool admin)
@@ -1114,9 +1125,10 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1114 return null; 1125 return null;
1115 1126
1116 doc = new XmlDocument(); 1127 doc = new XmlDocument();
1128 doc.XmlResolver = null;
1117 1129
1118 // Let's serialize all calls to Vivox. Most of these are driven by 1130 // Let's serialize all calls to Vivox. Most of these are driven by
1119 // the clients (CAPs), when the user arrives at the region. We don't 1131 // the clients (CAPs), when the user arrives at the region. We don't
1120 // want to issue many simultaneous http requests to Vivox, because mono 1132 // want to issue many simultaneous http requests to Vivox, because mono
1121 // doesn't like that 1133 // doesn't like that
1122 lock (m_Lock) 1134 lock (m_Lock)
@@ -1124,7 +1136,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1124 try 1136 try
1125 { 1137 {
1126 // Otherwise prepare the request 1138 // Otherwise prepare the request
1127 m_log.DebugFormat("[VivoxVoice] Sending request <{0}>", requrl); 1139 //m_log.DebugFormat("[VivoxVoice] Sending request <{0}>", requrl);
1128 1140
1129 HttpWebRequest req = (HttpWebRequest)WebRequest.Create(requrl); 1141 HttpWebRequest req = (HttpWebRequest)WebRequest.Create(requrl);
1130 1142
@@ -1135,7 +1147,10 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1135 using (HttpWebResponse rsp = (HttpWebResponse)req.GetResponse()) 1147 using (HttpWebResponse rsp = (HttpWebResponse)req.GetResponse())
1136 using (Stream s = rsp.GetResponseStream()) 1148 using (Stream s = rsp.GetResponseStream())
1137 using (XmlTextReader rdr = new XmlTextReader(s)) 1149 using (XmlTextReader rdr = new XmlTextReader(s))
1138 doc.Load(rdr); 1150 {
1151 rdr.ProhibitDtd = true;
1152 doc.Load(rdr);
1153 }
1139 } 1154 }
1140 catch (Exception e) 1155 catch (Exception e)
1141 { 1156 {
@@ -1162,7 +1177,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1162 1177
1163 /// <summary> 1178 /// <summary>
1164 /// Login has been factored in this way because it gets called 1179 /// Login has been factored in this way because it gets called
1165 /// from several places in the module, and we want it to work 1180 /// from several places in the module, and we want it to work
1166 /// the same way each time. 1181 /// the same way each time.
1167 /// </summary> 1182 /// </summary>
1168 private bool DoAdminLogin() 1183 private bool DoAdminLogin()
@@ -1177,15 +1192,15 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1177 XmlElement resp = null; 1192 XmlElement resp = null;
1178 1193
1179 resp = VivoxLogin(m_vivoxAdminUser, m_vivoxAdminPassword); 1194 resp = VivoxLogin(m_vivoxAdminUser, m_vivoxAdminPassword);
1180 1195
1181 if (XmlFind(resp, "response.level0.body.status", out status)) 1196 if (XmlFind(resp, "response.level0.body.status", out status))
1182 { 1197 {
1183 if (status == "Ok") 1198 if (status == "Ok")
1184 { 1199 {
1185 m_log.Info("[VivoxVoice] Admin connection established"); 1200 m_log.Info("[VivoxVoice] Admin connection established");
1186 if (XmlFind(resp, "response.level0.body.auth_token", out m_authToken)) 1201 if (XmlFind(resp, "response.level0.body.auth_token", out m_authToken))
1187 { 1202 {
1188 if (m_dumpXml) m_log.DebugFormat("[VivoxVoice] Auth Token <{0}>", 1203 if (m_dumpXml) m_log.DebugFormat("[VivoxVoice] Auth Token <{0}>",
1189 m_authToken); 1204 m_authToken);
1190 m_adminConnected = true; 1205 m_adminConnected = true;
1191 } 1206 }
@@ -1204,9 +1219,9 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1204 1219
1205 /// <summary> 1220 /// <summary>
1206 /// The XmlScan routine is provided to aid in the 1221 /// The XmlScan routine is provided to aid in the
1207 /// reverse engineering of incompletely 1222 /// reverse engineering of incompletely
1208 /// documented packets returned by the Vivox 1223 /// documented packets returned by the Vivox
1209 /// voice server. It is only called if the 1224 /// voice server. It is only called if the
1210 /// m_dumpXml switch is set. 1225 /// m_dumpXml switch is set.
1211 /// </summary> 1226 /// </summary>
1212 private void XmlScanl(XmlElement e, int index) 1227 private void XmlScanl(XmlElement e, int index)
@@ -1251,7 +1266,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1251 private bool XmlFind(XmlElement root, string tag, int nth, out string result) 1266 private bool XmlFind(XmlElement root, string tag, int nth, out string result)
1252 { 1267 {
1253 if (root == null || tag == null || tag == String.Empty) 1268 if (root == null || tag == null || tag == String.Empty)
1254 { 1269 {
1255 result = String.Empty; 1270 result = String.Empty;
1256 return false; 1271 return false;
1257 } 1272 }
@@ -1262,7 +1277,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1262 { 1277 {
1263 int nth = 0; 1278 int nth = 0;
1264 if (root == null || tag == null || tag == String.Empty) 1279 if (root == null || tag == null || tag == String.Empty)
1265 { 1280 {
1266 result = String.Empty; 1281 result = String.Empty;
1267 return false; 1282 return false;
1268 } 1283 }
@@ -1273,7 +1288,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1273 /// XmlSearch is initially called by XmlFind, and then 1288 /// XmlSearch is initially called by XmlFind, and then
1274 /// recursively called by itself until the document 1289 /// recursively called by itself until the document
1275 /// supplied to XmlFind is either exhausted or the name hierarchy 1290 /// supplied to XmlFind is either exhausted or the name hierarchy
1276 /// is matched. 1291 /// is matched.
1277 /// 1292 ///
1278 /// If the hierarchy is matched, the value is returned in 1293 /// If the hierarchy is matched, the value is returned in
1279 /// result, and true returned as the function's 1294 /// result, and true returned as the function's
@@ -1287,7 +1302,7 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1287 result = String.Empty; 1302 result = String.Empty;
1288 return false; 1303 return false;
1289 } 1304 }
1290 1305
1291 if (tags.Length-index == 1) 1306 if (tags.Length-index == 1)
1292 { 1307 {
1293 if (nth == 0) 1308 if (nth == 0)
@@ -1324,5 +1339,21 @@ namespace OpenSim.Region.OptionalModules.Avatar.Voice.VivoxVoice
1324 result = String.Empty; 1339 result = String.Empty;
1325 return false; 1340 return false;
1326 } 1341 }
1342
1343 private void HandleDebug(string module, string[] cmd)
1344 {
1345 if (cmd.Length < 3)
1346 {
1347 MainConsole.Instance.Output("Error: missing on/off flag");
1348 return;
1349 }
1350
1351 if (cmd[2] == "on")
1352 m_dumpXml = true;
1353 else if (cmd[2] == "off")
1354 m_dumpXml = false;
1355 else
1356 MainConsole.Instance.Output("Error: only on and off are supported");
1357 }
1327 } 1358 }
1328} 1359}