aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Communications
diff options
context:
space:
mode:
authorJustin Clarke Casey2008-09-12 20:12:03 +0000
committerJustin Clarke Casey2008-09-12 20:12:03 +0000
commit52a4c4d82f9c5b808e6c61fd51c1c70e42865565 (patch)
treef63a4ea443597b2d79ad6c2b7acff058c4437425 /OpenSim/Region/Communications
parentremove hidden faces inside prim meshes to improve memory use and startup time (diff)
downloadopensim-SC-52a4c4d82f9c5b808e6c61fd51c1c70e42865565.zip
opensim-SC-52a4c4d82f9c5b808e6c61fd51c1c70e42865565.tar.gz
opensim-SC-52a4c4d82f9c5b808e6c61fd51c1c70e42865565.tar.bz2
opensim-SC-52a4c4d82f9c5b808e6c61fd51c1c70e42865565.tar.xz
* Check in first part of http://opensimulator.org/mantis/view.php?id=2073
* This patch aims to introduce look at direction persistence between logins. It won't be active until the second part of the patch is committed in about two weeks time. At this point, region servers that haven't upgraded past this revision may run into problems * This checkin upgrades the user database. As always, we recommend you have backups in case something goes wrong. * Many thanks to tyre for this patch.
Diffstat (limited to 'OpenSim/Region/Communications')
-rw-r--r--OpenSim/Region/Communications/Local/LocalLoginService.cs257
-rw-r--r--OpenSim/Region/Communications/OGS1/OGS1UserServices.cs35
2 files changed, 154 insertions, 138 deletions
diff --git a/OpenSim/Region/Communications/Local/LocalLoginService.cs b/OpenSim/Region/Communications/Local/LocalLoginService.cs
index 93a1e46..2f7fdb7 100644
--- a/OpenSim/Region/Communications/Local/LocalLoginService.cs
+++ b/OpenSim/Region/Communications/Local/LocalLoginService.cs
@@ -41,8 +41,7 @@ namespace OpenSim.Region.Communications.Local
41 41
42 public class LocalLoginService : LoginService 42 public class LocalLoginService : LoginService
43 { 43 {
44 private static readonly ILog m_log 44 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
45 = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
46 45
47 private CommunicationsLocal m_Parent; 46 private CommunicationsLocal m_Parent;
48 47
@@ -120,167 +119,167 @@ namespace OpenSim.Region.Communications.Local
120 } 119 }
121 } 120 }
122 121
123 private Regex reURI = new Regex(@"^uri:(?<region>[^&]+)&(?<x>\d+)&(?<y>\d+)&(?<z>\d+)$"); 122 /// <summary>
124 123 /// Customises the login response and fills in missing values.
124 /// </summary>
125 /// <param name="response">The existing response</param>
126 /// <param name="theUser">The user profile</param>
127 /// <param name="startLocationRequest">The requested start location</param>
125 public override bool CustomiseResponse(LoginResponse response, UserProfileData theUser, string startLocationRequest) 128 public override bool CustomiseResponse(LoginResponse response, UserProfileData theUser, string startLocationRequest)
126 { 129 {
127 ulong currentRegion = 0; 130 // HomeLocation
128 131 RegionInfo homeInfo = null;
129 uint locX = 0; 132 // use the homeRegionID if it is stored already. If not, use the regionHandle as before
130 uint locY = 0; 133 if (theUser.HomeRegionID != UUID.Zero)
131 uint locZ = 0; 134 homeInfo = m_Parent.GridService.RequestNeighbourInfo(theUser.HomeRegionID);
132 bool specificStartLocation = false; 135 else
136 homeInfo = m_Parent.GridService.RequestNeighbourInfo(theUser.HomeRegion);
137 if (homeInfo != null)
138 {
139 response.Home =
140 string.Format(
141 "{{'region_handle':[r{0},r{1}], 'position':[r{2},r{3},r{4}], 'look_at':[r{5},r{6},r{7}]}}",
142 (homeInfo.RegionLocX*Constants.RegionSize),
143 (homeInfo.RegionLocY*Constants.RegionSize),
144 theUser.HomeLocation.X, theUser.HomeLocation.Y, theUser.HomeLocation.Z,
145 theUser.HomeLookAt.X, theUser.HomeLookAt.Y, theUser.HomeLookAt.Z);
146 }
147 else
148 {
149 // Emergency mode: Home-region isn't available, so we can't request the region info.
150 // Use the stored home regionHandle instead.
151 // NOTE: If the home-region moves, this will be wrong until the users update their user-profile again
152 ulong regionX = theUser.HomeRegion >> 32;
153 ulong regionY = theUser.HomeRegion & 0xffffffff;
154 response.Home =
155 string.Format(
156 "{{'region_handle':[r{0},r{1}], 'position':[r{2},r{3},r{4}], 'look_at':[r{5},r{6},r{7}]}}",
157 regionX, regionY,
158 theUser.HomeLocation.X, theUser.HomeLocation.Y, theUser.HomeLocation.Z,
159 theUser.HomeLookAt.X, theUser.HomeLookAt.Y, theUser.HomeLookAt.Z);
160 m_log.InfoFormat("[LOGIN] Home region of user {0} {1} is not available; using computed region position {2} {3}",
161 theUser.FirstName, theUser.SurName,
162 regionX, regionY);
163 }
133 164
134 // get start location 165 // StartLocation
135 if (startLocationRequest == "last") 166 RegionInfo regionInfo = null;
167 if (startLocationRequest == "home")
136 { 168 {
137 currentRegion = theUser.CurrentAgent.Handle; 169 regionInfo = homeInfo;
138 locX = (UInt32)theUser.CurrentAgent.Position.X; 170 theUser.CurrentAgent.Position = theUser.HomeLocation;
139 locY = (UInt32)theUser.CurrentAgent.Position.Y; 171 response.LookAt = "[r" + theUser.HomeLookAt.X.ToString() + ",r" + theUser.HomeLookAt.Y.ToString() + ",r" + theUser.HomeLookAt.Z.ToString() + "]";
140 locZ = (UInt32)theUser.CurrentAgent.Position.Z;
141 response.StartLocation = "last";
142 specificStartLocation = true;
143 } 172 }
144 else if (startLocationRequest == "home") 173 else if (startLocationRequest == "last")
145 { 174 {
146 currentRegion = theUser.HomeRegion; 175 regionInfo = m_Parent.GridService.RequestNeighbourInfo(theUser.CurrentAgent.Region);
147 response.StartLocation = "home"; 176 response.LookAt = "[r" + theUser.CurrentAgent.LookAt.X.ToString() + ",r" + theUser.CurrentAgent.LookAt.Y.ToString() + ",r" + theUser.CurrentAgent.LookAt.Z.ToString() + "]";
148 } 177 }
149 else 178 else
150 { 179 {
151 // use last location as default 180 Regex reURI = new Regex(@"^uri:(?<region>[^&]+)&(?<x>\d+)&(?<y>\d+)&(?<z>\d+)$");
152 currentRegion = theUser.CurrentAgent.Handle;
153
154 Match uriMatch = reURI.Match(startLocationRequest); 181 Match uriMatch = reURI.Match(startLocationRequest);
155 if (null == uriMatch) 182 if (uriMatch == null)
156 { 183 {
157 m_log.InfoFormat("[LOGIN]: Got Custom Login URL {0}, but can't process it", startLocationRequest); 184 m_log.InfoFormat("[LOGIN]: Got Custom Login URL {0}, but can't process it", startLocationRequest);
158 } 185 }
159 else 186 else
160 { 187 {
161 string region = uriMatch.Groups["region"].ToString(); 188 string region = uriMatch.Groups["region"].ToString();
162 189 regionInfo = m_Parent.GridService.RequestClosestRegion(region);
163 RegionInfo r = m_Parent.GridService.RequestClosestRegion(region); 190 if (regionInfo == null)
164 if (null == r)
165 { 191 {
166 m_log.InfoFormat("[LOGIN]: Got Custom Login URL {0}, can't locate region {1}", 192 m_log.InfoFormat("[LOGIN]: Got Custom Login URL {0}, can't locate region {1}", startLocationRequest, region);
167 startLocationRequest, region);
168 } 193 }
169 else 194 else
170 { 195 {
171 currentRegion = r.RegionHandle; 196 theUser.CurrentAgent.Position = new Vector3(float.Parse(uriMatch.Groups["x"].Value),
172 locX = UInt32.Parse(uriMatch.Groups["x"].ToString()); 197 float.Parse(uriMatch.Groups["y"].Value), float.Parse(uriMatch.Groups["x"].Value));
173 locY = UInt32.Parse(uriMatch.Groups["y"].ToString());
174 locZ = UInt32.Parse(uriMatch.Groups["z"].ToString());
175 // can be: last, home, safe, url
176 response.StartLocation = "url";
177 specificStartLocation = true;
178 } 198 }
179 } 199 }
200 response.LookAt = "[r0,r1,r0]";
201 // can be: last, home, safe, url
202 response.StartLocation = "url";
180 } 203 }
181 204
182 RegionInfo homeReg = m_Parent.GridService.RequestNeighbourInfo(theUser.HomeRegion); 205 if ((regionInfo != null) && (PrepareLoginToRegion(regionInfo, theUser, response)))
183 RegionInfo reg = m_Parent.GridService.RequestNeighbourInfo(currentRegion);
184
185 if ((homeReg != null) || (reg != null))
186 { 206 {
187 if (homeReg != null) 207 return true;
188 { 208 }
189 response.Home = "{'region_handle':[r" +
190 (homeReg.RegionLocX * Constants.RegionSize).ToString() + ",r" +
191 (homeReg.RegionLocY * Constants.RegionSize).ToString() + "], " +
192 "'position':[r" +
193 theUser.HomeLocation.X.ToString() + ",r" +
194 theUser.HomeLocation.Y.ToString() + ",r" +
195 theUser.HomeLocation.Z.ToString() + "], " +
196 "'look_at':[r" +
197 theUser.HomeLocation.X.ToString() + ",r" +
198 theUser.HomeLocation.Y.ToString() + ",r" +
199 theUser.HomeLocation.Z.ToString() + "]}";
200 }
201 else
202 {
203 m_log.Warn("[LOGIN]: Your home region doesn't exist");
204 response.Home = "{'region_handle':[r" +
205 (reg.RegionLocX * Constants.RegionSize).ToString() + ",r" +
206 (reg.RegionLocY * Constants.RegionSize).ToString() + "], " +
207 "'position':[r" +
208 theUser.HomeLocation.X.ToString() + ",r" +
209 theUser.HomeLocation.Y.ToString() + ",r" +
210 theUser.HomeLocation.Z.ToString() + "], " +
211 "'look_at':[r" +
212 theUser.HomeLocation.X.ToString() + ",r" +
213 theUser.HomeLocation.Y.ToString() + ",r" +
214 theUser.HomeLocation.Z.ToString() + "]}";
215 }
216 string capsPath = Util.GetRandomCapsPath();
217 response.SimAddress = reg.ExternalEndPoint.Address.ToString();
218 response.SimPort = (uint) reg.ExternalEndPoint.Port;
219 response.RegionX = reg.RegionLocX;
220 response.RegionY = reg.RegionLocY;
221
222 m_log.DebugFormat(
223 "[CAPS][LOGIN]: RegionX {0} RegionY {0}", response.RegionX, response.RegionY);
224
225 response.SeedCapability = "http://" + reg.ExternalHostName + ":" +
226 serversInfo.HttpListenerPort.ToString() + "/CAPS/" + capsPath + "0000/";
227
228 m_log.DebugFormat(
229 "[CAPS]: Sending new CAPS seed url {0} to client {1}",
230 response.SeedCapability, response.AgentID);
231
232 theUser.CurrentAgent.Region = reg.RegionID;
233 theUser.CurrentAgent.Handle = reg.RegionHandle;
234
235 // LoginResponse.BuddyList buddyList = new LoginResponse.BuddyList();
236
237 response.BuddList = ConvertFriendListItem(m_userManager.GetUserFriendList(theUser.ID));
238
239 Login _login = new Login();
240 //copy data to login object
241 _login.First = response.Firstname;
242 _login.Last = response.Lastname;
243 _login.Agent = response.AgentID;
244 _login.Session = response.SessionID;
245 _login.SecureSession = response.SecureSessionID;
246 _login.CircuitCode = (uint) response.CircuitCode;
247 if (specificStartLocation)
248 _login.StartPos = new Vector3(locX, locY, locZ);
249 else
250 _login.StartPos = new Vector3(128, 128, 128);
251 _login.CapsPath = capsPath;
252 209
253 m_log.InfoFormat( 210 // StartLocation not available, send him to a nearby region instead
254 "[LOGIN]: Telling region {0} @ {1},{2} ({3}:{4}) to expect user connection", 211 // regionInfo = m_Parent.GridService.RequestClosestRegion("");
255 reg.RegionName, response.RegionX, response.RegionY, response.SimAddress, response.SimPort); 212 //m_log.InfoFormat("[LOGIN]: StartLocation not available sending to region {0}", regionInfo.regionName);
256 213
257 handlerLoginToRegion = OnLoginToRegion; 214 // Send him to default region instead
258 if (handlerLoginToRegion != null) 215 ulong defaultHandle = (((ulong)defaultHomeX * Constants.RegionSize) << 32) |
259 { 216 ((ulong)defaultHomeY * Constants.RegionSize);
260 handlerLoginToRegion(currentRegion, _login); 217
261 } 218 if ((regionInfo != null) && (defaultHandle == regionInfo.RegionHandle))
262 }
263 else
264 { 219 {
265 m_log.Warn("[LOGIN]: Not found region " + currentRegion); 220 m_log.ErrorFormat("[LOGIN]: Not trying the default region since this is the same as the selected region");
266 return false; 221 return false;
267 } 222 }
268 223
269 return true; 224 m_log.Error("[LOGIN]: Sending user to default region " + defaultHandle + " instead");
225 regionInfo = m_Parent.GridService.RequestNeighbourInfo(defaultHandle);
226
227 // Customise the response
228 //response.Home =
229 // string.Format(
230 // "{{'region_handle':[r{0},r{1}], 'position':[r{2},r{3},r{4}], 'look_at':[r{5},r{6},r{7}]}}",
231 // (SimInfo.regionLocX * Constants.RegionSize),
232 // (SimInfo.regionLocY*Constants.RegionSize),
233 // theUser.HomeLocation.X, theUser.HomeLocation.Y, theUser.HomeLocation.Z,
234 // theUser.HomeLookAt.X, theUser.HomeLookAt.Y, theUser.HomeLookAt.Z);
235 theUser.CurrentAgent.Position = new Vector3(128,128,0);
236 response.StartLocation = "safe";
237
238 return PrepareLoginToRegion(regionInfo, theUser, response);
270 } 239 }
271 240
272 private LoginResponse.BuddyList ConvertFriendListItem(List<FriendListItem> LFL) 241 /// <summary>
242 /// Prepare a login to the given region. This involves both telling the region to expect a connection
243 /// and appropriately customising the response to the user.
244 /// </summary>
245 /// <param name="sim"></param>
246 /// <param name="user"></param>
247 /// <param name="response"></param>
248 /// <returns>true if the region was successfully contacted, false otherwise</returns>
249 private bool PrepareLoginToRegion(RegionInfo regionInfo, UserProfileData user, LoginResponse response)
273 { 250 {
274 LoginResponse.BuddyList buddylistreturn = new LoginResponse.BuddyList(); 251 response.SimAddress = regionInfo.ExternalEndPoint.Address.ToString();
275 foreach (FriendListItem fl in LFL) 252 response.SimPort = (uint)regionInfo.ExternalEndPoint.Port;
276 { 253 response.RegionX = regionInfo.RegionLocX;
277 LoginResponse.BuddyList.BuddyInfo buddyitem = new LoginResponse.BuddyList.BuddyInfo(fl.Friend); 254 response.RegionY = regionInfo.RegionLocY;
278 buddyitem.BuddyID = fl.Friend; 255
279 buddyitem.BuddyRightsHave = (int)fl.FriendListOwnerPerms; 256 string capsPath = Util.GetRandomCapsPath();
280 buddyitem.BuddyRightsGiven = (int)fl.FriendPerms; 257 response.SeedCapability = regionInfo.ServerURI + "/CAPS/" + capsPath + "0000/";
281 buddylistreturn.AddNewBuddy(buddyitem); 258
282 } 259 // Notify the target of an incoming user
283 return buddylistreturn; 260 m_log.InfoFormat(
261 "[LOGIN]: Telling {0} @ {1},{2} ({3}) to prepare for client connection",
262 regionInfo.RegionName, response.RegionX, response.RegionY, regionInfo.ServerURI);
263 // Update agent with target sim
264 user.CurrentAgent.Region = regionInfo.RegionID;
265 user.CurrentAgent.Handle = regionInfo.RegionHandle;
266 // Prepare notification
267 Login loginParams = new Login();
268 loginParams.Session = user.CurrentAgent.SessionID.ToString();
269 loginParams.SecureSession = user.CurrentAgent.SecureSessionID.ToString();
270 loginParams.First = user.FirstName;
271 loginParams.Last = user.SurName;
272 loginParams.Agent = user.ID.ToString();
273 loginParams.CircuitCode = Convert.ToUInt32(response.CircuitCode);
274 loginParams.StartPos = user.CurrentAgent.Position;
275 loginParams.CapsPath = capsPath;
276
277 handlerLoginToRegion = OnLoginToRegion;
278 if (handlerLoginToRegion == null)
279 return false;
280
281 handlerLoginToRegion(user.CurrentAgent.Handle, loginParams);
282 return true;
284 } 283 }
285 284
286 // See LoginService 285 // See LoginService
diff --git a/OpenSim/Region/Communications/OGS1/OGS1UserServices.cs b/OpenSim/Region/Communications/OGS1/OGS1UserServices.cs
index 36a82a8..b8268eb 100644
--- a/OpenSim/Region/Communications/OGS1/OGS1UserServices.cs
+++ b/OpenSim/Region/Communications/OGS1/OGS1UserServices.cs
@@ -235,19 +235,22 @@ namespace OpenSim.Region.Communications.OGS1
235 /// Logs off a user on the user server 235 /// Logs off a user on the user server
236 /// </summary> 236 /// </summary>
237 /// <param name="UserID">UUID of the user</param> 237 /// <param name="UserID">UUID of the user</param>
238 /// <param name="regionData">UUID of the Region</param> 238 /// <param name="regionID">UUID of the Region</param>
239 /// <param name="posx">final position x</param> 239 /// <param name="regionhandle">regionhandle</param>
240 /// <param name="posy">final position y</param> 240 /// <param name="position">final position</param>
241 /// <param name="posz">final position z</param> 241 /// <param name="lookat">final lookat</param>
242 public void LogOffUser(UUID userid, UUID regionid, ulong regionhandle, float posx, float posy, float posz) 242 public void LogOffUser(UUID userid, UUID regionid, ulong regionhandle, Vector3 position, Vector3 lookat)
243 { 243 {
244 Hashtable param = new Hashtable(); 244 Hashtable param = new Hashtable();
245 param["avatar_uuid"] = userid.Guid.ToString(); 245 param["avatar_uuid"] = userid.Guid.ToString();
246 param["region_uuid"] = regionid.Guid.ToString(); 246 param["region_uuid"] = regionid.Guid.ToString();
247 param["region_handle"] = regionhandle.ToString(); 247 param["region_handle"] = regionhandle.ToString();
248 param["region_pos_x"] = posx.ToString(); 248 param["region_pos_x"] = position.X.ToString();
249 param["region_pos_y"] = posy.ToString(); 249 param["region_pos_y"] = position.Y.ToString();
250 param["region_pos_z"] = posz.ToString(); 250 param["region_pos_z"] = position.Z.ToString();
251 param["lookat_x"] = lookat.X.ToString();
252 param["lookat_y"] = lookat.Y.ToString();
253 param["lookat_z"] = lookat.Z.ToString();
251 254
252 IList parameters = new ArrayList(); 255 IList parameters = new ArrayList();
253 parameters.Add(param); 256 parameters.Add(param);
@@ -263,6 +266,20 @@ namespace OpenSim.Region.Communications.OGS1
263 } 266 }
264 } 267 }
265 268
269 /// <summary>
270 /// Logs off a user on the user server (deprecated as of 2008-08-27)
271 /// </summary>
272 /// <param name="UserID">UUID of the user</param>
273 /// <param name="regionID">UUID of the Region</param>
274 /// <param name="regionhandle">regionhandle</param>
275 /// <param name="posx">final position x</param>
276 /// <param name="posy">final position y</param>
277 /// <param name="posz">final position z</param>
278 public void LogOffUser(UUID userid, UUID regionid, ulong regionhandle, float posx, float posy, float posz)
279 {
280 LogOffUser(userid, regionid, regionhandle, new Vector3(posx, posy, posz), new Vector3());
281 }
282
266 public UserProfileData GetUserProfile(string firstName, string lastName) 283 public UserProfileData GetUserProfile(string firstName, string lastName)
267 { 284 {
268 return GetUserProfile(firstName + " " + lastName); 285 return GetUserProfile(firstName + " " + lastName);
@@ -672,7 +689,7 @@ namespace OpenSim.Region.Communications.OGS1
672 } 689 }
673 } 690 }
674 /// <summary> 691 /// <summary>
675 /// Returns a list of FriendsListItems that describe the friends and permissions in the friend relationship for LLUUID friendslistowner 692 /// Returns a list of FriendsListItems that describe the friends and permissions in the friend relationship for UUID friendslistowner
676 /// </summary> 693 /// </summary>
677 /// <param name="friendlistowner">The agent that we're retreiving the friends Data.</param> 694 /// <param name="friendlistowner">The agent that we're retreiving the friends Data.</param>
678 public List<FriendListItem> GetUserFriendList(UUID friendlistowner) 695 public List<FriendListItem> GetUserFriendList(UUID friendlistowner)