diff options
author | gareth | 2007-03-22 10:11:15 +0000 |
---|---|---|
committer | gareth | 2007-03-22 10:11:15 +0000 |
commit | 7daa3955bc3a1918e40962851f9e8d38597a245e (patch) | |
tree | bee3e1372a7eed0c1b220a8a49f7bee7d29a6b91 /OpenSim.RegionServer | |
parent | Load XML for neighbourinfo from grid (diff) | |
download | opensim-SC_OLD-7daa3955bc3a1918e40962851f9e8d38597a245e.zip opensim-SC_OLD-7daa3955bc3a1918e40962851f9e8d38597a245e.tar.gz opensim-SC_OLD-7daa3955bc3a1918e40962851f9e8d38597a245e.tar.bz2 opensim-SC_OLD-7daa3955bc3a1918e40962851f9e8d38597a245e.tar.xz |
brought zircon branch into trunk
Diffstat (limited to 'OpenSim.RegionServer')
24 files changed, 4442 insertions, 0 deletions
diff --git a/OpenSim.RegionServer/Assets/AssetCache.cs b/OpenSim.RegionServer/Assets/AssetCache.cs new file mode 100644 index 0000000..f7f2e10 --- /dev/null +++ b/OpenSim.RegionServer/Assets/AssetCache.cs | |||
@@ -0,0 +1,589 @@ | |||
1 | /* | ||
2 | * Copyright (c) OpenSim project, http://sim.opensecondlife.org/ | ||
3 | * | ||
4 | * Redistribution and use in source and binary forms, with or without | ||
5 | * modification, are permitted provided that the following conditions are met: | ||
6 | * * Redistributions of source code must retain the above copyright | ||
7 | * notice, this list of conditions and the following disclaimer. | ||
8 | * * Redistributions in binary form must reproduce the above copyright | ||
9 | * notice, this list of conditions and the following disclaimer in the | ||
10 | * documentation and/or other materials provided with the distribution. | ||
11 | * * Neither the name of the <organization> nor the | ||
12 | * names of its contributors may be used to endorse or promote products | ||
13 | * derived from this software without specific prior written permission. | ||
14 | * | ||
15 | * THIS SOFTWARE IS PROVIDED BY <copyright holder> ``AS IS'' AND ANY | ||
16 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
17 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
18 | * DISCLAIMED. IN NO EVENT SHALL <copyright holder> BE LIABLE FOR ANY | ||
19 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
20 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
21 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
22 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
23 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
24 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
25 | * | ||
26 | */ | ||
27 | |||
28 | using System; | ||
29 | using System.Collections.Generic; | ||
30 | using System.Threading; | ||
31 | using libsecondlife; | ||
32 | using libsecondlife.Packets; | ||
33 | using OpenSim; | ||
34 | using OpenSim.Framework.Interfaces; | ||
35 | using OpenSim.Framework.Assets; | ||
36 | using OpenSim.Framework.Utilities; | ||
37 | |||
38 | namespace OpenSim.Assets | ||
39 | { | ||
40 | /// <summary> | ||
41 | /// Manages local cache of assets and their sending to viewers. | ||
42 | /// </summary> | ||
43 | public class AssetCache : IAssetReceiver | ||
44 | { | ||
45 | public Dictionary<libsecondlife.LLUUID, AssetInfo> Assets; | ||
46 | public Dictionary<libsecondlife.LLUUID, TextureImage> Textures; | ||
47 | |||
48 | public List<AssetRequest> AssetRequests = new List<AssetRequest>(); //assets ready to be sent to viewers | ||
49 | public List<AssetRequest> TextureRequests = new List<AssetRequest>(); //textures ready to be sent | ||
50 | |||
51 | public Dictionary<LLUUID, AssetRequest> RequestedAssets = new Dictionary<LLUUID, AssetRequest>(); //Assets requested from the asset server | ||
52 | public Dictionary<LLUUID, AssetRequest> RequestedTextures = new Dictionary<LLUUID, AssetRequest>(); //Textures requested from the asset server | ||
53 | |||
54 | //private Dictionary<libsecondlife.LLUUID, AssetBase> IncomingAssets; | ||
55 | |||
56 | private IAssetServer _assetServer; | ||
57 | private Thread _assetCacheThread; | ||
58 | private LLUUID[] textureList = new LLUUID[2]; | ||
59 | |||
60 | /// <summary> | ||
61 | /// | ||
62 | /// </summary> | ||
63 | public AssetCache(IAssetServer assetServer) | ||
64 | { | ||
65 | Console.WriteLine("Creating Asset cache"); | ||
66 | _assetServer = assetServer; | ||
67 | _assetServer.SetReceiver(this); | ||
68 | Assets = new Dictionary<libsecondlife.LLUUID, AssetInfo>(); | ||
69 | Textures = new Dictionary<libsecondlife.LLUUID, TextureImage>(); | ||
70 | //IncomingAssets = new Dictionary<libsecondlife.LLUUID, AssetBase>(); | ||
71 | this._assetCacheThread = new Thread(new ThreadStart(RunAssetManager)); | ||
72 | this._assetCacheThread.IsBackground = true; | ||
73 | this._assetCacheThread.Start(); | ||
74 | |||
75 | } | ||
76 | |||
77 | /// <summary> | ||
78 | /// | ||
79 | /// </summary> | ||
80 | public void RunAssetManager() | ||
81 | { | ||
82 | while (true) | ||
83 | { | ||
84 | try | ||
85 | { | ||
86 | //Console.WriteLine("Asset cache loop"); | ||
87 | this.ProcessAssetQueue(); | ||
88 | this.ProcessTextureQueue(); | ||
89 | Thread.Sleep(500); | ||
90 | } | ||
91 | catch (Exception e) | ||
92 | { | ||
93 | Console.WriteLine(e.Message); | ||
94 | } | ||
95 | } | ||
96 | } | ||
97 | |||
98 | public void LoadDefaultTextureSet() | ||
99 | { | ||
100 | //hack: so we can give each user a set of textures | ||
101 | textureList[0] = new LLUUID("00000000-0000-0000-9999-000000000001"); | ||
102 | textureList[1] = new LLUUID("00000000-0000-0000-9999-000000000002"); | ||
103 | for (int i = 0; i < textureList.Length; i++) | ||
104 | { | ||
105 | this._assetServer.RequestAsset(textureList[i], true); | ||
106 | } | ||
107 | |||
108 | } | ||
109 | |||
110 | public AssetBase[] CreateNewInventorySet(LLUUID agentID) | ||
111 | { | ||
112 | AssetBase[] inventorySet = new AssetBase[this.textureList.Length]; | ||
113 | for (int i = 0; i < textureList.Length; i++) | ||
114 | { | ||
115 | if (this.Textures.ContainsKey(textureList[i])) | ||
116 | { | ||
117 | inventorySet[i] = this.CloneImage(agentID, this.Textures[textureList[i]]); | ||
118 | TextureImage image = new TextureImage(inventorySet[i]); | ||
119 | this.Textures.Add(image.FullID, image); | ||
120 | this._assetServer.UploadNewAsset(image); //save the asset to the asset server | ||
121 | } | ||
122 | } | ||
123 | return inventorySet; | ||
124 | } | ||
125 | |||
126 | /// <summary> | ||
127 | /// | ||
128 | /// </summary> | ||
129 | private void ProcessTextureQueue() | ||
130 | { | ||
131 | if (this.TextureRequests.Count == 0) | ||
132 | { | ||
133 | //no requests waiting | ||
134 | return; | ||
135 | } | ||
136 | int num; | ||
137 | |||
138 | if (this.TextureRequests.Count < 5) | ||
139 | { | ||
140 | //lower than 5 so do all of them | ||
141 | num = this.TextureRequests.Count; | ||
142 | } | ||
143 | else | ||
144 | { | ||
145 | num = 5; | ||
146 | } | ||
147 | AssetRequest req; | ||
148 | Console.WriteLine("processing texture requests ( " + num + " )"); | ||
149 | for (int i = 0; i < num; i++) | ||
150 | { | ||
151 | req = (AssetRequest)this.TextureRequests[i]; | ||
152 | if (req.PacketCounter != req.NumPackets) | ||
153 | { | ||
154 | // if (req.ImageInfo.FullID == new LLUUID("00000000-0000-0000-5005-000000000005")) | ||
155 | Console.WriteLine("sending base texture ( " + req.ImageInfo.FullID + " ) in " + req.NumPackets + "number of packets"); | ||
156 | |||
157 | if (req.PacketCounter == 0) | ||
158 | { | ||
159 | //first time for this request so send imagedata packet | ||
160 | if (req.NumPackets == 1) | ||
161 | { | ||
162 | //only one packet so send whole file | ||
163 | ImageDataPacket im = new ImageDataPacket(); | ||
164 | im.ImageID.Packets = 1; | ||
165 | im.ImageID.ID = req.ImageInfo.FullID; | ||
166 | im.ImageID.Size = (uint)req.ImageInfo.Data.Length; | ||
167 | im.ImageData.Data = req.ImageInfo.Data; | ||
168 | im.ImageID.Codec = 2; | ||
169 | req.RequestUser.OutPacket(im); | ||
170 | req.PacketCounter++; | ||
171 | //req.ImageInfo.l= time; | ||
172 | //System.Console.WriteLine("sent texture: "+req.image_info.FullID); | ||
173 | } | ||
174 | else | ||
175 | { | ||
176 | //more than one packet so split file up | ||
177 | ImageDataPacket im = new ImageDataPacket(); | ||
178 | im.ImageID.Packets = (ushort)req.NumPackets; | ||
179 | im.ImageID.ID = req.ImageInfo.FullID; | ||
180 | im.ImageID.Size = (uint)req.ImageInfo.Data.Length; | ||
181 | im.ImageData.Data = new byte[600]; | ||
182 | Array.Copy(req.ImageInfo.Data, 0, im.ImageData.Data, 0, 600); | ||
183 | im.ImageID.Codec = 2; | ||
184 | req.RequestUser.OutPacket(im); | ||
185 | req.PacketCounter++; | ||
186 | //req.ImageInfo.last_used = time; | ||
187 | //System.Console.WriteLine("sent first packet of texture: | ||
188 | } | ||
189 | } | ||
190 | else | ||
191 | { | ||
192 | //send imagepacket | ||
193 | //more than one packet so split file up | ||
194 | ImagePacketPacket im = new ImagePacketPacket(); | ||
195 | im.ImageID.Packet = (ushort)req.PacketCounter; | ||
196 | im.ImageID.ID = req.ImageInfo.FullID; | ||
197 | int size = req.ImageInfo.Data.Length - 600 - 1000 * (req.PacketCounter - 1); | ||
198 | if (size > 1000) size = 1000; | ||
199 | im.ImageData.Data = new byte[size]; | ||
200 | Array.Copy(req.ImageInfo.Data, 600 + 1000 * (req.PacketCounter - 1), im.ImageData.Data, 0, size); | ||
201 | req.RequestUser.OutPacket(im); | ||
202 | req.PacketCounter++; | ||
203 | //req.ImageInfo.last_used = time; | ||
204 | //System.Console.WriteLine("sent a packet of texture: "+req.image_info.FullID); | ||
205 | } | ||
206 | } | ||
207 | } | ||
208 | |||
209 | //remove requests that have been completed | ||
210 | int count = 0; | ||
211 | for (int i = 0; i < num; i++) | ||
212 | { | ||
213 | if (this.TextureRequests.Count > count) | ||
214 | { | ||
215 | req = (AssetRequest)this.TextureRequests[count]; | ||
216 | if (req.PacketCounter == req.NumPackets) | ||
217 | { | ||
218 | this.TextureRequests.Remove(req); | ||
219 | } | ||
220 | else | ||
221 | { | ||
222 | count++; | ||
223 | } | ||
224 | } | ||
225 | } | ||
226 | |||
227 | } | ||
228 | public void AssetReceived(AssetBase asset, bool IsTexture) | ||
229 | { | ||
230 | Console.WriteLine("received asset from asset server ( " + asset.FullID + " )"); | ||
231 | if (asset.FullID != LLUUID.Zero) // if it is set to zero then the asset wasn't found by the server | ||
232 | { | ||
233 | //check if it is a texture or not | ||
234 | //then add to the correct cache list | ||
235 | //then check for waiting requests for this asset/texture (in the Requested lists) | ||
236 | //and move those requests into the Requests list. | ||
237 | if (IsTexture) | ||
238 | { | ||
239 | TextureImage image = new TextureImage(asset); | ||
240 | this.Textures.Add(image.FullID, image); | ||
241 | if (this.RequestedTextures.ContainsKey(image.FullID)) | ||
242 | { | ||
243 | AssetRequest req = this.RequestedTextures[image.FullID]; | ||
244 | req.ImageInfo = image; | ||
245 | if (image.Data.LongLength > 600) | ||
246 | { | ||
247 | //over 600 bytes so split up file | ||
248 | req.NumPackets = 1 + (int)(image.Data.Length - 600 + 999) / 1000; | ||
249 | } | ||
250 | else | ||
251 | { | ||
252 | req.NumPackets = 1; | ||
253 | } | ||
254 | this.RequestedTextures.Remove(image.FullID); | ||
255 | this.TextureRequests.Add(req); | ||
256 | } | ||
257 | } | ||
258 | else | ||
259 | { | ||
260 | AssetInfo assetInf = new AssetInfo(asset); | ||
261 | this.Assets.Add(assetInf.FullID, assetInf); | ||
262 | if (this.RequestedAssets.ContainsKey(assetInf.FullID)) | ||
263 | { | ||
264 | AssetRequest req = this.RequestedAssets[assetInf.FullID]; | ||
265 | req.AssetInf = assetInf; | ||
266 | if (assetInf.Data.LongLength > 600) | ||
267 | { | ||
268 | //over 600 bytes so split up file | ||
269 | req.NumPackets = 1 + (int)(assetInf.Data.Length - 600 + 999) / 1000; | ||
270 | } | ||
271 | else | ||
272 | { | ||
273 | req.NumPackets = 1; | ||
274 | } | ||
275 | this.RequestedAssets.Remove(assetInf.FullID); | ||
276 | this.AssetRequests.Add(req); | ||
277 | } | ||
278 | } | ||
279 | } | ||
280 | } | ||
281 | |||
282 | public void AssetNotFound(AssetBase asset) | ||
283 | { | ||
284 | //the asset server had no knowledge of requested asset | ||
285 | |||
286 | } | ||
287 | |||
288 | #region Assets | ||
289 | /// <summary> | ||
290 | /// | ||
291 | /// </summary> | ||
292 | /// <param name="userInfo"></param> | ||
293 | /// <param name="transferRequest"></param> | ||
294 | public void AddAssetRequest(SimClient userInfo, TransferRequestPacket transferRequest) | ||
295 | { | ||
296 | LLUUID requestID = new LLUUID(transferRequest.TransferInfo.Params, 0); | ||
297 | //check to see if asset is in local cache, if not we need to request it from asset server. | ||
298 | if (!this.Assets.ContainsKey(requestID)) | ||
299 | { | ||
300 | //not found asset | ||
301 | // so request from asset server | ||
302 | if (!this.RequestedAssets.ContainsKey(requestID)) | ||
303 | { | ||
304 | AssetRequest request = new AssetRequest(); | ||
305 | request.RequestUser = userInfo; | ||
306 | request.RequestAssetID = requestID; | ||
307 | request.TransferRequestID = transferRequest.TransferInfo.TransferID; | ||
308 | this.RequestedAssets.Add(requestID, request); | ||
309 | this._assetServer.RequestAsset(requestID, false); | ||
310 | } | ||
311 | return; | ||
312 | } | ||
313 | //it is in our cache | ||
314 | AssetInfo asset = this.Assets[requestID]; | ||
315 | |||
316 | //work out how many packets it should be sent in | ||
317 | // and add to the AssetRequests list | ||
318 | AssetRequest req = new AssetRequest(); | ||
319 | req.RequestUser = userInfo; | ||
320 | req.RequestAssetID = requestID; | ||
321 | req.TransferRequestID = transferRequest.TransferInfo.TransferID; | ||
322 | req.AssetInf = asset; | ||
323 | |||
324 | if (asset.Data.LongLength > 600) | ||
325 | { | ||
326 | //over 600 bytes so split up file | ||
327 | req.NumPackets = 1 + (int)(asset.Data.Length - 600 + 999) / 1000; | ||
328 | } | ||
329 | else | ||
330 | { | ||
331 | req.NumPackets = 1; | ||
332 | } | ||
333 | |||
334 | this.AssetRequests.Add(req); | ||
335 | } | ||
336 | |||
337 | /// <summary> | ||
338 | /// | ||
339 | /// </summary> | ||
340 | private void ProcessAssetQueue() | ||
341 | { | ||
342 | if (this.AssetRequests.Count == 0) | ||
343 | { | ||
344 | //no requests waiting | ||
345 | return; | ||
346 | } | ||
347 | int num; | ||
348 | |||
349 | if (this.AssetRequests.Count < 5) | ||
350 | { | ||
351 | //lower than 5 so do all of them | ||
352 | num = this.AssetRequests.Count; | ||
353 | } | ||
354 | else | ||
355 | { | ||
356 | num = 5; | ||
357 | } | ||
358 | AssetRequest req; | ||
359 | for (int i = 0; i < num; i++) | ||
360 | { | ||
361 | req = (AssetRequest)this.AssetRequests[i]; | ||
362 | |||
363 | TransferInfoPacket Transfer = new TransferInfoPacket(); | ||
364 | Transfer.TransferInfo.ChannelType = 2; | ||
365 | Transfer.TransferInfo.Status = 0; | ||
366 | Transfer.TransferInfo.TargetType = 0; | ||
367 | Transfer.TransferInfo.Params = req.RequestAssetID.GetBytes(); | ||
368 | Transfer.TransferInfo.Size = (int)req.AssetInf.Data.Length; | ||
369 | Transfer.TransferInfo.TransferID = req.TransferRequestID; | ||
370 | req.RequestUser.OutPacket(Transfer); | ||
371 | |||
372 | if (req.NumPackets == 1) | ||
373 | { | ||
374 | TransferPacketPacket TransferPacket = new TransferPacketPacket(); | ||
375 | TransferPacket.TransferData.Packet = 0; | ||
376 | TransferPacket.TransferData.ChannelType = 2; | ||
377 | TransferPacket.TransferData.TransferID = req.TransferRequestID; | ||
378 | TransferPacket.TransferData.Data = req.AssetInf.Data; | ||
379 | TransferPacket.TransferData.Status = 1; | ||
380 | req.RequestUser.OutPacket(TransferPacket); | ||
381 | } | ||
382 | else | ||
383 | { | ||
384 | //more than one packet so split file up , for now it can't be bigger than 2000 bytes | ||
385 | TransferPacketPacket TransferPacket = new TransferPacketPacket(); | ||
386 | TransferPacket.TransferData.Packet = 0; | ||
387 | TransferPacket.TransferData.ChannelType = 2; | ||
388 | TransferPacket.TransferData.TransferID = req.TransferRequestID; | ||
389 | byte[] chunk = new byte[1000]; | ||
390 | Array.Copy(req.AssetInf.Data, chunk, 1000); | ||
391 | TransferPacket.TransferData.Data = chunk; | ||
392 | TransferPacket.TransferData.Status = 0; | ||
393 | req.RequestUser.OutPacket(TransferPacket); | ||
394 | |||
395 | TransferPacket = new TransferPacketPacket(); | ||
396 | TransferPacket.TransferData.Packet = 1; | ||
397 | TransferPacket.TransferData.ChannelType = 2; | ||
398 | TransferPacket.TransferData.TransferID = req.TransferRequestID; | ||
399 | byte[] chunk1 = new byte[(req.AssetInf.Data.Length - 1000)]; | ||
400 | Array.Copy(req.AssetInf.Data, 1000, chunk1, 0, chunk1.Length); | ||
401 | TransferPacket.TransferData.Data = chunk1; | ||
402 | TransferPacket.TransferData.Status = 1; | ||
403 | req.RequestUser.OutPacket(TransferPacket); | ||
404 | } | ||
405 | |||
406 | } | ||
407 | |||
408 | //remove requests that have been completed | ||
409 | for (int i = 0; i < num; i++) | ||
410 | { | ||
411 | this.AssetRequests.RemoveAt(0); | ||
412 | } | ||
413 | |||
414 | } | ||
415 | |||
416 | public AssetInfo CloneAsset(LLUUID newOwner, AssetInfo sourceAsset) | ||
417 | { | ||
418 | AssetInfo newAsset = new AssetInfo(); | ||
419 | newAsset.Data = new byte[sourceAsset.Data.Length]; | ||
420 | Array.Copy(sourceAsset.Data, newAsset.Data, sourceAsset.Data.Length); | ||
421 | newAsset.FullID = LLUUID.Random(); | ||
422 | newAsset.Type = sourceAsset.Type; | ||
423 | newAsset.InvType = sourceAsset.InvType; | ||
424 | return (newAsset); | ||
425 | } | ||
426 | #endregion | ||
427 | |||
428 | #region Textures | ||
429 | /// <summary> | ||
430 | /// | ||
431 | /// </summary> | ||
432 | /// <param name="userInfo"></param> | ||
433 | /// <param name="imageID"></param> | ||
434 | public void AddTextureRequest(SimClient userInfo, LLUUID imageID) | ||
435 | { | ||
436 | if (imageID == new LLUUID("00000000-0000-0000-5005-000000000005")) | ||
437 | Console.WriteLine("request base prim texture "); | ||
438 | |||
439 | //check to see if texture is in local cache, if not request from asset server | ||
440 | if (!this.Textures.ContainsKey(imageID)) | ||
441 | { | ||
442 | if (!this.RequestedTextures.ContainsKey(imageID)) | ||
443 | { | ||
444 | //not is cache so request from asset server | ||
445 | AssetRequest request = new AssetRequest(); | ||
446 | request.RequestUser = userInfo; | ||
447 | request.RequestAssetID = imageID; | ||
448 | request.IsTextureRequest = true; | ||
449 | this.RequestedTextures.Add(imageID, request); | ||
450 | this._assetServer.RequestAsset(imageID, true); | ||
451 | } | ||
452 | return; | ||
453 | } | ||
454 | |||
455 | TextureImage imag = this.Textures[imageID]; | ||
456 | AssetRequest req = new AssetRequest(); | ||
457 | req.RequestUser = userInfo; | ||
458 | req.RequestAssetID = imageID; | ||
459 | req.IsTextureRequest = true; | ||
460 | req.ImageInfo = imag; | ||
461 | |||
462 | if (imag.Data.LongLength > 600) | ||
463 | { | ||
464 | //over 600 bytes so split up file | ||
465 | req.NumPackets = 1 + (int)(imag.Data.Length - 600 + 999) / 1000; | ||
466 | } | ||
467 | else | ||
468 | { | ||
469 | req.NumPackets = 1; | ||
470 | } | ||
471 | |||
472 | this.TextureRequests.Add(req); | ||
473 | } | ||
474 | |||
475 | public TextureImage CloneImage(LLUUID newOwner, TextureImage source) | ||
476 | { | ||
477 | TextureImage newImage = new TextureImage(); | ||
478 | newImage.Data = new byte[source.Data.Length]; | ||
479 | Array.Copy(source.Data, newImage.Data, source.Data.Length); | ||
480 | //newImage.filename = source.filename; | ||
481 | newImage.FullID = LLUUID.Random(); | ||
482 | newImage.Name = source.Name; | ||
483 | return (newImage); | ||
484 | } | ||
485 | #endregion | ||
486 | |||
487 | #region viewer asset uploading | ||
488 | public AssetBase UploadPacket(AssetUploadRequestPacket pack, LLUUID assetID) | ||
489 | { | ||
490 | |||
491 | AssetBase asset = null; | ||
492 | if (pack.AssetBlock.Type == 0) | ||
493 | { | ||
494 | if (pack.AssetBlock.AssetData.Length > 0) | ||
495 | { | ||
496 | //first packet for transaction | ||
497 | asset = new AssetBase(); | ||
498 | asset.FullID = assetID; | ||
499 | asset.Type = pack.AssetBlock.Type; | ||
500 | asset.InvType = asset.Type; | ||
501 | asset.Name = "UploadedTexture" + Util.RandomClass.Next(1, 1000).ToString("000"); | ||
502 | asset.Data = pack.AssetBlock.AssetData; | ||
503 | this._assetServer.UploadNewAsset(asset); | ||
504 | TextureImage image = new TextureImage(asset); | ||
505 | this.Textures.Add(image.FullID, image); | ||
506 | } | ||
507 | } | ||
508 | |||
509 | return asset; | ||
510 | } | ||
511 | |||
512 | /* | ||
513 | public AssetBase TransactionComplete(LLUUID transactionID) | ||
514 | { | ||
515 | AssetBase asset = null; | ||
516 | if(this.IncomingAssets.ContainsKey(transactionID)) | ||
517 | { | ||
518 | // not the first packet of this transaction | ||
519 | asset = this.IncomingAssets[transactionID]; | ||
520 | if(asset.Type == 0) | ||
521 | { | ||
522 | TextureImage image = new TextureImage(asset); | ||
523 | this.Textures.Add(image.FullID, image); | ||
524 | } | ||
525 | } | ||
526 | return asset; | ||
527 | }*/ | ||
528 | |||
529 | #endregion | ||
530 | |||
531 | } | ||
532 | |||
533 | public class AssetRequest | ||
534 | { | ||
535 | public SimClient RequestUser; | ||
536 | public LLUUID RequestAssetID; | ||
537 | public AssetInfo AssetInf; | ||
538 | public TextureImage ImageInfo; | ||
539 | public LLUUID TransferRequestID; | ||
540 | public long DataPointer = 0; | ||
541 | public int NumPackets = 0; | ||
542 | public int PacketCounter = 0; | ||
543 | public bool IsTextureRequest; | ||
544 | //public bool AssetInCache; | ||
545 | //public int TimeRequested; | ||
546 | |||
547 | public AssetRequest() | ||
548 | { | ||
549 | |||
550 | } | ||
551 | } | ||
552 | |||
553 | public class AssetInfo : AssetBase | ||
554 | { | ||
555 | public AssetInfo() | ||
556 | { | ||
557 | |||
558 | } | ||
559 | |||
560 | public AssetInfo(AssetBase aBase) | ||
561 | { | ||
562 | Data = aBase.Data; | ||
563 | FullID = aBase.FullID; | ||
564 | Type = aBase.Type; | ||
565 | InvType = aBase.InvType; | ||
566 | Name = aBase.Name; | ||
567 | Description = aBase.Description; | ||
568 | } | ||
569 | } | ||
570 | |||
571 | public class TextureImage : AssetBase | ||
572 | { | ||
573 | public TextureImage() | ||
574 | { | ||
575 | |||
576 | } | ||
577 | |||
578 | public TextureImage(AssetBase aBase) | ||
579 | { | ||
580 | Data = aBase.Data; | ||
581 | FullID = aBase.FullID; | ||
582 | Type = aBase.Type; | ||
583 | InvType = aBase.InvType; | ||
584 | Name = aBase.Name; | ||
585 | Description = aBase.Description; | ||
586 | } | ||
587 | } | ||
588 | |||
589 | } | ||
diff --git a/OpenSim.RegionServer/Assets/InventoryCache.cs b/OpenSim.RegionServer/Assets/InventoryCache.cs new file mode 100644 index 0000000..0788db2 --- /dev/null +++ b/OpenSim.RegionServer/Assets/InventoryCache.cs | |||
@@ -0,0 +1,199 @@ | |||
1 | /* | ||
2 | * Copyright (c) OpenSim project, http://sim.opensecondlife.org/ | ||
3 | * | ||
4 | * Redistribution and use in source and binary forms, with or without | ||
5 | * modification, are permitted provided that the following conditions are met: | ||
6 | * * Redistributions of source code must retain the above copyright | ||
7 | * notice, this list of conditions and the following disclaimer. | ||
8 | * * Redistributions in binary form must reproduce the above copyright | ||
9 | * notice, this list of conditions and the following disclaimer in the | ||
10 | * documentation and/or other materials provided with the distribution. | ||
11 | * * Neither the name of the <organization> nor the | ||
12 | * names of its contributors may be used to endorse or promote products | ||
13 | * derived from this software without specific prior written permission. | ||
14 | * | ||
15 | * THIS SOFTWARE IS PROVIDED BY <copyright holder> ``AS IS'' AND ANY | ||
16 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
17 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
18 | * DISCLAIMED. IN NO EVENT SHALL <copyright holder> BE LIABLE FOR ANY | ||
19 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
20 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
21 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
22 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
23 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
24 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
25 | * | ||
26 | */ | ||
27 | |||
28 | using System; | ||
29 | using System.Collections.Generic; | ||
30 | using libsecondlife; | ||
31 | using OpenSim; | ||
32 | using libsecondlife.Packets; | ||
33 | //using OpenSim.GridServers; | ||
34 | using OpenSim.Framework.Inventory; | ||
35 | using OpenSim.Framework.Assets; | ||
36 | |||
37 | namespace OpenSim.Assets | ||
38 | { | ||
39 | /// <summary> | ||
40 | /// Description of InventoryManager. | ||
41 | /// </summary> | ||
42 | public class InventoryCache | ||
43 | { | ||
44 | private Dictionary<LLUUID, AgentInventory> _agentsInventory; | ||
45 | private List<UserServerRequest> _serverRequests; //list of requests made to user server. | ||
46 | private System.Text.Encoding _enc = System.Text.Encoding.ASCII; | ||
47 | private const uint FULL_MASK_PERMISSIONS = 2147483647; | ||
48 | |||
49 | public InventoryCache() | ||
50 | { | ||
51 | _agentsInventory = new Dictionary<LLUUID, AgentInventory>(); | ||
52 | _serverRequests = new List<UserServerRequest>(); | ||
53 | } | ||
54 | |||
55 | public void AddNewAgentsInventory(AgentInventory agentInventory) | ||
56 | { | ||
57 | this._agentsInventory.Add(agentInventory.AgentID, agentInventory); | ||
58 | } | ||
59 | |||
60 | public void ClientLeaving(LLUUID clientID) | ||
61 | { | ||
62 | if (this._agentsInventory.ContainsKey(clientID)) | ||
63 | { | ||
64 | this._agentsInventory.Remove(clientID); | ||
65 | } | ||
66 | |||
67 | } | ||
68 | public bool CreateNewInventoryFolder(SimClient remoteClient, LLUUID folderID) | ||
69 | { | ||
70 | bool res = false; | ||
71 | if (folderID != LLUUID.Zero) //don't create a folder with a zero id | ||
72 | { | ||
73 | if (this._agentsInventory.ContainsKey(remoteClient.AgentID)) | ||
74 | { | ||
75 | res = this._agentsInventory[remoteClient.AgentID].CreateNewFolder(folderID); | ||
76 | } | ||
77 | } | ||
78 | return res; | ||
79 | } | ||
80 | |||
81 | public LLUUID AddNewInventoryItem(SimClient remoteClient, LLUUID folderID, OpenSim.Framework.Assets.AssetBase asset) | ||
82 | { | ||
83 | LLUUID newItem = null; | ||
84 | if (this._agentsInventory.ContainsKey(remoteClient.AgentID)) | ||
85 | { | ||
86 | newItem = this._agentsInventory[remoteClient.AgentID].AddToInventory(folderID, asset); | ||
87 | } | ||
88 | |||
89 | return newItem; | ||
90 | } | ||
91 | |||
92 | public void FetchInventoryDescendents(SimClient userInfo, FetchInventoryDescendentsPacket FetchDescend) | ||
93 | { | ||
94 | if (this._agentsInventory.ContainsKey(userInfo.AgentID)) | ||
95 | { | ||
96 | AgentInventory agentInventory = this._agentsInventory[userInfo.AgentID]; | ||
97 | if (FetchDescend.InventoryData.FetchItems) | ||
98 | { | ||
99 | if (agentInventory.InventoryFolders.ContainsKey(FetchDescend.InventoryData.FolderID)) | ||
100 | { | ||
101 | InventoryFolder Folder = agentInventory.InventoryFolders[FetchDescend.InventoryData.FolderID]; | ||
102 | InventoryDescendentsPacket Descend = new InventoryDescendentsPacket(); | ||
103 | Descend.AgentData.AgentID = userInfo.AgentID; | ||
104 | Descend.AgentData.OwnerID = Folder.OwnerID; | ||
105 | Descend.AgentData.FolderID = FetchDescend.InventoryData.FolderID; | ||
106 | Descend.AgentData.Descendents = Folder.Items.Count; | ||
107 | Descend.AgentData.Version = Folder.Items.Count; | ||
108 | |||
109 | |||
110 | Descend.ItemData = new InventoryDescendentsPacket.ItemDataBlock[Folder.Items.Count]; | ||
111 | for (int i = 0; i < Folder.Items.Count; i++) | ||
112 | { | ||
113 | |||
114 | InventoryItem Item = Folder.Items[i]; | ||
115 | Descend.ItemData[i] = new InventoryDescendentsPacket.ItemDataBlock(); | ||
116 | Descend.ItemData[i].ItemID = Item.ItemID; | ||
117 | Descend.ItemData[i].AssetID = Item.AssetID; | ||
118 | Descend.ItemData[i].CreatorID = Item.CreatorID; | ||
119 | Descend.ItemData[i].BaseMask = FULL_MASK_PERMISSIONS; | ||
120 | Descend.ItemData[i].CreationDate = 1000; | ||
121 | Descend.ItemData[i].Description = _enc.GetBytes(Item.Description + "\0"); | ||
122 | Descend.ItemData[i].EveryoneMask = FULL_MASK_PERMISSIONS; | ||
123 | Descend.ItemData[i].Flags = 1; | ||
124 | Descend.ItemData[i].FolderID = Item.FolderID; | ||
125 | Descend.ItemData[i].GroupID = new LLUUID("00000000-0000-0000-0000-000000000000"); | ||
126 | Descend.ItemData[i].GroupMask = FULL_MASK_PERMISSIONS; | ||
127 | Descend.ItemData[i].InvType = Item.InvType; | ||
128 | Descend.ItemData[i].Name = _enc.GetBytes(Item.Name + "\0"); | ||
129 | Descend.ItemData[i].NextOwnerMask = FULL_MASK_PERMISSIONS; | ||
130 | Descend.ItemData[i].OwnerID = Item.OwnerID; | ||
131 | Descend.ItemData[i].OwnerMask = FULL_MASK_PERMISSIONS; | ||
132 | Descend.ItemData[i].SalePrice = 100; | ||
133 | Descend.ItemData[i].SaleType = 0; | ||
134 | Descend.ItemData[i].Type = Item.Type; | ||
135 | Descend.ItemData[i].CRC = libsecondlife.Helpers.InventoryCRC(1000, 0, Descend.ItemData[i].InvType, Descend.ItemData[i].Type, Descend.ItemData[i].AssetID, Descend.ItemData[i].GroupID, 100, Descend.ItemData[i].OwnerID, Descend.ItemData[i].CreatorID, Descend.ItemData[i].ItemID, Descend.ItemData[i].FolderID, FULL_MASK_PERMISSIONS, 1, FULL_MASK_PERMISSIONS, FULL_MASK_PERMISSIONS, FULL_MASK_PERMISSIONS); | ||
136 | } | ||
137 | userInfo.OutPacket(Descend); | ||
138 | |||
139 | } | ||
140 | } | ||
141 | else | ||
142 | { | ||
143 | Console.WriteLine("fetch subfolders"); | ||
144 | } | ||
145 | } | ||
146 | } | ||
147 | |||
148 | public void FetchInventory(SimClient userInfo, FetchInventoryPacket FetchItems) | ||
149 | { | ||
150 | if (this._agentsInventory.ContainsKey(userInfo.AgentID)) | ||
151 | { | ||
152 | AgentInventory agentInventory = this._agentsInventory[userInfo.AgentID]; | ||
153 | |||
154 | for (int i = 0; i < FetchItems.InventoryData.Length; i++) | ||
155 | { | ||
156 | if (agentInventory.InventoryItems.ContainsKey(FetchItems.InventoryData[i].ItemID)) | ||
157 | { | ||
158 | InventoryItem Item = agentInventory.InventoryItems[FetchItems.InventoryData[i].ItemID]; | ||
159 | FetchInventoryReplyPacket InventoryReply = new FetchInventoryReplyPacket(); | ||
160 | InventoryReply.AgentData.AgentID = userInfo.AgentID; | ||
161 | InventoryReply.InventoryData = new FetchInventoryReplyPacket.InventoryDataBlock[1]; | ||
162 | InventoryReply.InventoryData[0] = new FetchInventoryReplyPacket.InventoryDataBlock(); | ||
163 | InventoryReply.InventoryData[0].ItemID = Item.ItemID; | ||
164 | InventoryReply.InventoryData[0].AssetID = Item.AssetID; | ||
165 | InventoryReply.InventoryData[0].CreatorID = Item.CreatorID; | ||
166 | InventoryReply.InventoryData[0].BaseMask = FULL_MASK_PERMISSIONS; | ||
167 | InventoryReply.InventoryData[0].CreationDate = 1000; | ||
168 | InventoryReply.InventoryData[0].Description = _enc.GetBytes(Item.Description + "\0"); | ||
169 | InventoryReply.InventoryData[0].EveryoneMask = FULL_MASK_PERMISSIONS; | ||
170 | InventoryReply.InventoryData[0].Flags = 1; | ||
171 | InventoryReply.InventoryData[0].FolderID = Item.FolderID; | ||
172 | InventoryReply.InventoryData[0].GroupID = new LLUUID("00000000-0000-0000-0000-000000000000"); | ||
173 | InventoryReply.InventoryData[0].GroupMask = FULL_MASK_PERMISSIONS; | ||
174 | InventoryReply.InventoryData[0].InvType = Item.InvType; | ||
175 | InventoryReply.InventoryData[0].Name = _enc.GetBytes(Item.Name + "\0"); | ||
176 | InventoryReply.InventoryData[0].NextOwnerMask = FULL_MASK_PERMISSIONS; | ||
177 | InventoryReply.InventoryData[0].OwnerID = Item.OwnerID; | ||
178 | InventoryReply.InventoryData[0].OwnerMask = FULL_MASK_PERMISSIONS; | ||
179 | InventoryReply.InventoryData[0].SalePrice = 100; | ||
180 | InventoryReply.InventoryData[0].SaleType = 0; | ||
181 | InventoryReply.InventoryData[0].Type = Item.Type; | ||
182 | InventoryReply.InventoryData[0].CRC = libsecondlife.Helpers.InventoryCRC(1000, 0, InventoryReply.InventoryData[0].InvType, InventoryReply.InventoryData[0].Type, InventoryReply.InventoryData[0].AssetID, InventoryReply.InventoryData[0].GroupID, 100, InventoryReply.InventoryData[0].OwnerID, InventoryReply.InventoryData[0].CreatorID, InventoryReply.InventoryData[0].ItemID, InventoryReply.InventoryData[0].FolderID, FULL_MASK_PERMISSIONS, 1, FULL_MASK_PERMISSIONS, FULL_MASK_PERMISSIONS, FULL_MASK_PERMISSIONS); | ||
183 | userInfo.OutPacket(InventoryReply); | ||
184 | } | ||
185 | } | ||
186 | } | ||
187 | } | ||
188 | } | ||
189 | |||
190 | |||
191 | |||
192 | public class UserServerRequest | ||
193 | { | ||
194 | public UserServerRequest() | ||
195 | { | ||
196 | |||
197 | } | ||
198 | } | ||
199 | } | ||
diff --git a/OpenSim.RegionServer/CAPS/SimHttp.cs b/OpenSim.RegionServer/CAPS/SimHttp.cs new file mode 100644 index 0000000..f5a8705 --- /dev/null +++ b/OpenSim.RegionServer/CAPS/SimHttp.cs | |||
@@ -0,0 +1,175 @@ | |||
1 | /* | ||
2 | Copyright (c) OpenSimCAPS project, http://osgrid.org/ | ||
3 | |||
4 | |||
5 | * All rights reserved. | ||
6 | * | ||
7 | * Redistribution and use in source and binary forms, with or without | ||
8 | * modification, are permitted provided that the following conditions are met: | ||
9 | * * Redistributions of source code must retain the above copyright | ||
10 | * notice, this list of conditions and the following disclaimer. | ||
11 | * * Redistributions in binary form must reproduce the above copyright | ||
12 | * notice, this list of conditions and the following disclaimer in the | ||
13 | * documentation and/or other materials provided with the distribution. | ||
14 | * * Neither the name of the <organization> nor the | ||
15 | * names of its contributors may be used to endorse or promote products | ||
16 | * derived from this software without specific prior written permission. | ||
17 | * | ||
18 | * THIS SOFTWARE IS PROVIDED BY <copyright holder> ``AS IS'' AND ANY | ||
19 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
20 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
21 | * DISCLAIMED. IN NO EVENT SHALL <copyright holder> BE LIABLE FOR ANY | ||
22 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
23 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
24 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
25 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
26 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
27 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
28 | */ | ||
29 | |||
30 | using System; | ||
31 | using System.Text; | ||
32 | using Nwc.XmlRpc; | ||
33 | using System.Threading; | ||
34 | using System.Text.RegularExpressions; | ||
35 | using System.Net; | ||
36 | using System.IO; | ||
37 | using System.Collections; | ||
38 | using System.Collections.Generic; | ||
39 | using libsecondlife; | ||
40 | using OpenSim.Framework.Console; | ||
41 | using OpenSim.Framework.Interfaces; | ||
42 | |||
43 | namespace OpenSim.CAPS | ||
44 | { | ||
45 | // Dummy HTTP server, does nothing useful for now | ||
46 | |||
47 | public class SimCAPSHTTPServer | ||
48 | { | ||
49 | public Thread HTTPD; | ||
50 | public HttpListener Listener; | ||
51 | |||
52 | public SimCAPSHTTPServer() | ||
53 | { | ||
54 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Starting up HTTP Server"); | ||
55 | HTTPD = new Thread(new ThreadStart(StartHTTP)); | ||
56 | HTTPD.Start(); | ||
57 | } | ||
58 | |||
59 | public void StartHTTP() | ||
60 | { | ||
61 | try | ||
62 | { | ||
63 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("SimHttp.cs:StartHTTP() - Spawned main thread OK"); | ||
64 | Listener = new HttpListener(); | ||
65 | |||
66 | Listener.Prefixes.Add("http://+:" + OpenSimRoot.Instance.Cfg.IPListenPort + "/"); | ||
67 | Listener.Start(); | ||
68 | |||
69 | HttpListenerContext context; | ||
70 | while (true) | ||
71 | { | ||
72 | context = Listener.GetContext(); | ||
73 | ThreadPool.QueueUserWorkItem(new WaitCallback(HandleRequest), context); | ||
74 | } | ||
75 | } | ||
76 | catch (Exception e) | ||
77 | { | ||
78 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine(e.Message); | ||
79 | } | ||
80 | } | ||
81 | |||
82 | static string ParseXMLRPC(string requestBody) | ||
83 | { | ||
84 | try | ||
85 | { | ||
86 | XmlRpcRequest request = (XmlRpcRequest)(new XmlRpcRequestDeserializer()).Deserialize(requestBody); | ||
87 | |||
88 | Hashtable requestData = (Hashtable)request.Params[0]; | ||
89 | switch (request.MethodName) | ||
90 | { | ||
91 | case "expect_user": | ||
92 | AgentCircuitData agent_data = new AgentCircuitData(); | ||
93 | agent_data.SessionID = new LLUUID((string)requestData["session_id"]); | ||
94 | agent_data.SecureSessionID = new LLUUID((string)requestData["secure_session_id"]); | ||
95 | agent_data.firstname = (string)requestData["firstname"]; | ||
96 | agent_data.lastname = (string)requestData["lastname"]; | ||
97 | agent_data.AgentID = new LLUUID((string)requestData["agent_id"]); | ||
98 | agent_data.circuitcode = Convert.ToUInt32(requestData["circuit_code"]); | ||
99 | if (OpenSimRoot.Instance.GridServers.GridServer.GetName() == "Remote") | ||
100 | { | ||
101 | ((RemoteGridBase)OpenSimRoot.Instance.GridServers.GridServer).agentcircuits.Add((uint)agent_data.circuitcode, agent_data); | ||
102 | } | ||
103 | return "<?xml version=\"1.0\"?><methodResponse><params /></methodResponse>"; | ||
104 | break; | ||
105 | } | ||
106 | } | ||
107 | catch (Exception e) | ||
108 | { | ||
109 | Console.WriteLine(e.ToString()); | ||
110 | } | ||
111 | return ""; | ||
112 | } | ||
113 | |||
114 | static string ParseREST(string requestBody, string requestURL) | ||
115 | { | ||
116 | return ""; | ||
117 | } | ||
118 | |||
119 | static string ParseLLSDXML(string requestBody) | ||
120 | { | ||
121 | // dummy function for now - IMPLEMENT ME! | ||
122 | return ""; | ||
123 | } | ||
124 | |||
125 | static void HandleRequest(Object stateinfo) | ||
126 | { | ||
127 | HttpListenerContext context = (HttpListenerContext)stateinfo; | ||
128 | |||
129 | HttpListenerRequest request = context.Request; | ||
130 | HttpListenerResponse response = context.Response; | ||
131 | |||
132 | response.KeepAlive = false; | ||
133 | response.SendChunked = false; | ||
134 | |||
135 | System.IO.Stream body = request.InputStream; | ||
136 | System.Text.Encoding encoding = System.Text.Encoding.UTF8; | ||
137 | System.IO.StreamReader reader = new System.IO.StreamReader(body, encoding); | ||
138 | |||
139 | string requestBody = reader.ReadToEnd(); | ||
140 | body.Close(); | ||
141 | reader.Close(); | ||
142 | |||
143 | string responseString = ""; | ||
144 | switch (request.ContentType) | ||
145 | { | ||
146 | case "text/xml": | ||
147 | // must be XML-RPC, so pass to the XML-RPC parser | ||
148 | |||
149 | responseString = ParseXMLRPC(requestBody); | ||
150 | response.AddHeader("Content-type", "text/xml"); | ||
151 | break; | ||
152 | |||
153 | case "application/xml": | ||
154 | // probably LLSD we hope, otherwise it should be ignored by the parser | ||
155 | responseString = ParseLLSDXML(requestBody); | ||
156 | response.AddHeader("Content-type", "application/xml"); | ||
157 | break; | ||
158 | |||
159 | case null: | ||
160 | // must be REST or invalid crap, so pass to the REST parser | ||
161 | responseString = ParseREST(request.Url.OriginalString, requestBody); | ||
162 | break; | ||
163 | } | ||
164 | |||
165 | byte[] buffer = System.Text.Encoding.UTF8.GetBytes(responseString); | ||
166 | System.IO.Stream output = response.OutputStream; | ||
167 | response.SendChunked = false; | ||
168 | response.ContentLength64 = buffer.Length; | ||
169 | output.Write(buffer, 0, buffer.Length); | ||
170 | output.Close(); | ||
171 | } | ||
172 | } | ||
173 | |||
174 | |||
175 | } | ||
diff --git a/OpenSim.RegionServer/Grid.cs b/OpenSim.RegionServer/Grid.cs new file mode 100644 index 0000000..b0df6a8 --- /dev/null +++ b/OpenSim.RegionServer/Grid.cs | |||
@@ -0,0 +1,89 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Text; | ||
4 | using System.Reflection; | ||
5 | using OpenSim.Framework.Interfaces; | ||
6 | using OpenSim.UserServer; | ||
7 | |||
8 | namespace OpenSim | ||
9 | { | ||
10 | public class Grid | ||
11 | { | ||
12 | public IAssetServer AssetServer; | ||
13 | public IGridServer GridServer; | ||
14 | public string AssetDll = ""; | ||
15 | public string GridDll = ""; | ||
16 | |||
17 | public Grid() | ||
18 | { | ||
19 | } | ||
20 | |||
21 | public virtual void Initialise() | ||
22 | { | ||
23 | //load the dlls | ||
24 | this.AssetServer = this.LoadAssetDll(this.AssetDll); | ||
25 | this.GridServer = this.LoadGridDll(this.GridDll); | ||
26 | } | ||
27 | public virtual void Close() | ||
28 | { | ||
29 | this.AssetServer.Close(); | ||
30 | this.GridServer.Close(); | ||
31 | } | ||
32 | |||
33 | private IAssetServer LoadAssetDll(string dllName) | ||
34 | { | ||
35 | Assembly pluginAssembly = Assembly.LoadFrom(dllName); | ||
36 | IAssetServer server = null; | ||
37 | |||
38 | foreach (Type pluginType in pluginAssembly.GetTypes()) | ||
39 | { | ||
40 | if (pluginType.IsPublic) | ||
41 | { | ||
42 | if (!pluginType.IsAbstract) | ||
43 | { | ||
44 | Type typeInterface = pluginType.GetInterface("IAssetPlugin", true); | ||
45 | |||
46 | if (typeInterface != null) | ||
47 | { | ||
48 | IAssetPlugin plug = (IAssetPlugin)Activator.CreateInstance(pluginAssembly.GetType(pluginType.ToString())); | ||
49 | server = plug.GetAssetServer(); | ||
50 | break; | ||
51 | } | ||
52 | |||
53 | typeInterface = null; | ||
54 | } | ||
55 | } | ||
56 | } | ||
57 | pluginAssembly = null; | ||
58 | return server; | ||
59 | } | ||
60 | |||
61 | private IGridServer LoadGridDll(string dllName) | ||
62 | { | ||
63 | Assembly pluginAssembly = Assembly.LoadFrom(dllName); | ||
64 | IGridServer server = null; | ||
65 | |||
66 | foreach (Type pluginType in pluginAssembly.GetTypes()) | ||
67 | { | ||
68 | if (pluginType.IsPublic) | ||
69 | { | ||
70 | if (!pluginType.IsAbstract) | ||
71 | { | ||
72 | Type typeInterface = pluginType.GetInterface("IGridPlugin", true); | ||
73 | |||
74 | if (typeInterface != null) | ||
75 | { | ||
76 | IGridPlugin plug = (IGridPlugin)Activator.CreateInstance(pluginAssembly.GetType(pluginType.ToString())); | ||
77 | server = plug.GetGridServer(); | ||
78 | break; | ||
79 | } | ||
80 | |||
81 | typeInterface = null; | ||
82 | } | ||
83 | } | ||
84 | } | ||
85 | pluginAssembly = null; | ||
86 | return server; | ||
87 | } | ||
88 | } | ||
89 | } | ||
diff --git a/OpenSim.RegionServer/OpenSim.RegionServer.csproj b/OpenSim.RegionServer/OpenSim.RegionServer.csproj new file mode 100644 index 0000000..ebf2f87 --- /dev/null +++ b/OpenSim.RegionServer/OpenSim.RegionServer.csproj | |||
@@ -0,0 +1,169 @@ | |||
1 | <Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> | ||
2 | <PropertyGroup> | ||
3 | <ProjectType>Local</ProjectType> | ||
4 | <ProductVersion>8.0.50727</ProductVersion> | ||
5 | <SchemaVersion>2.0</SchemaVersion> | ||
6 | <ProjectGuid>{B48F0D82-2DE5-42B0-9F1D-0F4353FA243A}</ProjectGuid> | ||
7 | <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration> | ||
8 | <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform> | ||
9 | <ApplicationIcon></ApplicationIcon> | ||
10 | <AssemblyKeyContainerName> | ||
11 | </AssemblyKeyContainerName> | ||
12 | <AssemblyName>OpenSim.RegionServer</AssemblyName> | ||
13 | <DefaultClientScript>JScript</DefaultClientScript> | ||
14 | <DefaultHTMLPageLayout>Grid</DefaultHTMLPageLayout> | ||
15 | <DefaultTargetSchema>IE50</DefaultTargetSchema> | ||
16 | <DelaySign>false</DelaySign> | ||
17 | <OutputType>Exe</OutputType> | ||
18 | <AppDesignerFolder></AppDesignerFolder> | ||
19 | <RootNamespace>OpenSim.RegionServer</RootNamespace> | ||
20 | <StartupObject>OpenSim.RegionServer</StartupObject> | ||
21 | <FileUpgradeFlags> | ||
22 | </FileUpgradeFlags> | ||
23 | </PropertyGroup> | ||
24 | <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' "> | ||
25 | <AllowUnsafeBlocks>False</AllowUnsafeBlocks> | ||
26 | <BaseAddress>285212672</BaseAddress> | ||
27 | <CheckForOverflowUnderflow>False</CheckForOverflowUnderflow> | ||
28 | <ConfigurationOverrideFile> | ||
29 | </ConfigurationOverrideFile> | ||
30 | <DefineConstants>TRACE;DEBUG</DefineConstants> | ||
31 | <DocumentationFile></DocumentationFile> | ||
32 | <DebugSymbols>True</DebugSymbols> | ||
33 | <FileAlignment>4096</FileAlignment> | ||
34 | <Optimize>False</Optimize> | ||
35 | <OutputPath>..\bin\</OutputPath> | ||
36 | <RegisterForComInterop>False</RegisterForComInterop> | ||
37 | <RemoveIntegerChecks>False</RemoveIntegerChecks> | ||
38 | <TreatWarningsAsErrors>False</TreatWarningsAsErrors> | ||
39 | <WarningLevel>4</WarningLevel> | ||
40 | <NoWarn></NoWarn> | ||
41 | </PropertyGroup> | ||
42 | <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' "> | ||
43 | <AllowUnsafeBlocks>False</AllowUnsafeBlocks> | ||
44 | <BaseAddress>285212672</BaseAddress> | ||
45 | <CheckForOverflowUnderflow>False</CheckForOverflowUnderflow> | ||
46 | <ConfigurationOverrideFile> | ||
47 | </ConfigurationOverrideFile> | ||
48 | <DefineConstants>TRACE</DefineConstants> | ||
49 | <DocumentationFile></DocumentationFile> | ||
50 | <DebugSymbols>False</DebugSymbols> | ||
51 | <FileAlignment>4096</FileAlignment> | ||
52 | <Optimize>True</Optimize> | ||
53 | <OutputPath>..\bin\</OutputPath> | ||
54 | <RegisterForComInterop>False</RegisterForComInterop> | ||
55 | <RemoveIntegerChecks>False</RemoveIntegerChecks> | ||
56 | <TreatWarningsAsErrors>False</TreatWarningsAsErrors> | ||
57 | <WarningLevel>4</WarningLevel> | ||
58 | <NoWarn></NoWarn> | ||
59 | </PropertyGroup> | ||
60 | <ItemGroup> | ||
61 | <Reference Include="System" > | ||
62 | <HintPath>\System.dll</HintPath> | ||
63 | </Reference> | ||
64 | <Reference Include="System.Xml.dll" > | ||
65 | <HintPath>\System.Xml.dll.dll</HintPath> | ||
66 | </Reference> | ||
67 | <Reference Include="libsecondlife.dll" > | ||
68 | <HintPath>\libsecondlife.dll.dll</HintPath> | ||
69 | </Reference> | ||
70 | <Reference Include="Axiom.MathLib.dll" > | ||
71 | <HintPath>\Axiom.MathLib.dll.dll</HintPath> | ||
72 | </Reference> | ||
73 | <Reference Include="Db4objects.Db4o.dll" > | ||
74 | <HintPath>\Db4objects.Db4o.dll.dll</HintPath> | ||
75 | </Reference> | ||
76 | </ItemGroup> | ||
77 | <ItemGroup> | ||
78 | <ProjectReference Include="..\OpenSim.Framework.Console\OpenSim.Framework.Console.csproj"> | ||
79 | <Name>OpenSim.Framework.Console</Name> | ||
80 | <Project>{C8405E1A-EC19-48B6-9C8C-CA03624B9916}</Project> | ||
81 | <Package>{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}</Package> | ||
82 | </ProjectReference> | ||
83 | <ProjectReference Include="..\OpenSim.Physics\Manager\OpenSim.Physics.Manager.csproj"> | ||
84 | <Name>OpenSim.Physics.Manager</Name> | ||
85 | <Project>{58360A80-9333-4E0F-8F83-3CF937E51633}</Project> | ||
86 | <Package>{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}</Package> | ||
87 | </ProjectReference> | ||
88 | <ProjectReference Include="..\OpenSim.Framework\OpenSim.Framework.csproj"> | ||
89 | <Name>OpenSim.Framework</Name> | ||
90 | <Project>{1D2865A9-CF8E-45F7-B96D-91ED128A32CF}</Project> | ||
91 | <Package>{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}</Package> | ||
92 | </ProjectReference> | ||
93 | </ItemGroup> | ||
94 | <ItemGroup> | ||
95 | <Compile Include="Grid.cs"> | ||
96 | <SubType>Code</SubType> | ||
97 | </Compile> | ||
98 | <Compile Include="OpenSimApplication.cs"> | ||
99 | <SubType>Code</SubType> | ||
100 | </Compile> | ||
101 | <Compile Include="OpenSimMain.cs"> | ||
102 | <SubType>Code</SubType> | ||
103 | </Compile> | ||
104 | <Compile Include="OpenSimRoot.cs"> | ||
105 | <SubType>Code</SubType> | ||
106 | </Compile> | ||
107 | <Compile Include="QueItem.cs"> | ||
108 | <SubType>Code</SubType> | ||
109 | </Compile> | ||
110 | <Compile Include="SimClient.cs"> | ||
111 | <SubType>Code</SubType> | ||
112 | </Compile> | ||
113 | <Compile Include="SimConsole.cs"> | ||
114 | <SubType>Code</SubType> | ||
115 | </Compile> | ||
116 | <Compile Include="VersionInfo.cs"> | ||
117 | <SubType>Code</SubType> | ||
118 | </Compile> | ||
119 | <Compile Include="Assets\AssetCache.cs"> | ||
120 | <SubType>Code</SubType> | ||
121 | </Compile> | ||
122 | <Compile Include="Assets\InventoryCache.cs"> | ||
123 | <SubType>Code</SubType> | ||
124 | </Compile> | ||
125 | <Compile Include="CAPS\SimHttp.cs"> | ||
126 | <SubType>Code</SubType> | ||
127 | </Compile> | ||
128 | <Compile Include="types\Mesh.cs"> | ||
129 | <SubType>Code</SubType> | ||
130 | </Compile> | ||
131 | <Compile Include="types\Triangle.cs"> | ||
132 | <SubType>Code</SubType> | ||
133 | </Compile> | ||
134 | <Compile Include="UserServer\LocalUserProfileManager.cs"> | ||
135 | <SubType>Code</SubType> | ||
136 | </Compile> | ||
137 | <Compile Include="UserServer\LoginServer.cs"> | ||
138 | <SubType>Code</SubType> | ||
139 | </Compile> | ||
140 | <Compile Include="world\Avatar.cs"> | ||
141 | <SubType>Code</SubType> | ||
142 | </Compile> | ||
143 | <Compile Include="world\Entity.cs"> | ||
144 | <SubType>Code</SubType> | ||
145 | </Compile> | ||
146 | <Compile Include="world\Primitive.cs"> | ||
147 | <SubType>Code</SubType> | ||
148 | </Compile> | ||
149 | <Compile Include="world\ScriptEngine.cs"> | ||
150 | <SubType>Code</SubType> | ||
151 | </Compile> | ||
152 | <Compile Include="world\SurfacePatch.cs"> | ||
153 | <SubType>Code</SubType> | ||
154 | </Compile> | ||
155 | <Compile Include="world\World.cs"> | ||
156 | <SubType>Code</SubType> | ||
157 | </Compile> | ||
158 | <Compile Include="world\scripting\IScript.cs"> | ||
159 | <SubType>Code</SubType> | ||
160 | </Compile> | ||
161 | </ItemGroup> | ||
162 | <Import Project="$(MSBuildBinPath)\Microsoft.CSHARP.Targets" /> | ||
163 | <PropertyGroup> | ||
164 | <PreBuildEvent> | ||
165 | </PreBuildEvent> | ||
166 | <PostBuildEvent> | ||
167 | </PostBuildEvent> | ||
168 | </PropertyGroup> | ||
169 | </Project> | ||
diff --git a/OpenSim.RegionServer/OpenSim.RegionServer.exe.build b/OpenSim.RegionServer/OpenSim.RegionServer.exe.build new file mode 100644 index 0000000..c65f751 --- /dev/null +++ b/OpenSim.RegionServer/OpenSim.RegionServer.exe.build | |||
@@ -0,0 +1,67 @@ | |||
1 | <?xml version="1.0" ?> | ||
2 | <project name="OpenSim.RegionServer" default="build"> | ||
3 | <target name="build"> | ||
4 | <echo message="Build Directory is ${project::get-base-directory()}/${build.dir}" /> | ||
5 | <mkdir dir="${project::get-base-directory()}/${build.dir}" /> | ||
6 | <copy todir="${project::get-base-directory()}/${build.dir}"> | ||
7 | <fileset basedir="${project::get-base-directory()}"> | ||
8 | </fileset> | ||
9 | </copy> | ||
10 | <csc target="exe" debug="${build.debug}" unsafe="False" define="TRACE;DEBUG" output="${project::get-base-directory()}/${build.dir}/${project::get-name()}.exe"> | ||
11 | <resources prefix="OpenSim.RegionServer" dynamicprefix="true" > | ||
12 | </resources> | ||
13 | <sources failonempty="true"> | ||
14 | <include name="Grid.cs" /> | ||
15 | <include name="OpenSimApplication.cs" /> | ||
16 | <include name="OpenSimMain.cs" /> | ||
17 | <include name="OpenSimRoot.cs" /> | ||
18 | <include name="QueItem.cs" /> | ||
19 | <include name="SimClient.cs" /> | ||
20 | <include name="SimConsole.cs" /> | ||
21 | <include name="VersionInfo.cs" /> | ||
22 | <include name="Assets/AssetCache.cs" /> | ||
23 | <include name="Assets/InventoryCache.cs" /> | ||
24 | <include name="CAPS/SimHttp.cs" /> | ||
25 | <include name="types/Mesh.cs" /> | ||
26 | <include name="types/Triangle.cs" /> | ||
27 | <include name="UserServer/LocalUserProfileManager.cs" /> | ||
28 | <include name="UserServer/LoginServer.cs" /> | ||
29 | <include name="world/Avatar.cs" /> | ||
30 | <include name="world/Entity.cs" /> | ||
31 | <include name="world/Primitive.cs" /> | ||
32 | <include name="world/ScriptEngine.cs" /> | ||
33 | <include name="world/SurfacePatch.cs" /> | ||
34 | <include name="world/World.cs" /> | ||
35 | <include name="world/scripting/IScript.cs" /> | ||
36 | </sources> | ||
37 | <references basedir="${project::get-base-directory()}"> | ||
38 | <lib> | ||
39 | <include name="${project::get-base-directory()}" /> | ||
40 | <include name="${project::get-base-directory()}/${build.dir}" /> | ||
41 | </lib> | ||
42 | <include name="System.dll" /> | ||
43 | <include name="System.Xml.dll.dll" /> | ||
44 | <include name="../bin/libsecondlife.dll" /> | ||
45 | <include name="../bin/Axiom.MathLib.dll" /> | ||
46 | <include name="../bin/Db4objects.Db4o.dll" /> | ||
47 | <include name="../OpenSim.Framework.Console/${build.dir}/OpenSim.Framework.Console.dll" /> | ||
48 | <include name="../OpenSim.Physics/Manager/${build.dir}/OpenSim.Physics.Manager.dll" /> | ||
49 | <include name="../OpenSim.Framework/${build.dir}/OpenSim.Framework.dll" /> | ||
50 | </references> | ||
51 | </csc> | ||
52 | <echo message="Copying from [${project::get-base-directory()}/${build.dir}/] to [${project::get-base-directory()}/../bin/" /> | ||
53 | <mkdir dir="${project::get-base-directory()}/../bin/"/> | ||
54 | <copy todir="${project::get-base-directory()}/../bin/"> | ||
55 | <fileset basedir="${project::get-base-directory()}/${build.dir}/" > | ||
56 | <include name="*.dll"/> | ||
57 | <include name="*.exe"/> | ||
58 | </fileset> | ||
59 | </copy> | ||
60 | </target> | ||
61 | <target name="clean"> | ||
62 | <delete dir="${bin.dir}" failonerror="false" /> | ||
63 | <delete dir="${obj.dir}" failonerror="false" /> | ||
64 | </target> | ||
65 | <target name="doc" description="Creates documentation."> | ||
66 | </target> | ||
67 | </project> | ||
diff --git a/OpenSim.RegionServer/OpenSimApplication.cs b/OpenSim.RegionServer/OpenSimApplication.cs new file mode 100644 index 0000000..abfdf45 --- /dev/null +++ b/OpenSim.RegionServer/OpenSimApplication.cs | |||
@@ -0,0 +1,16 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Text; | ||
4 | using System.Net; | ||
5 | using System.Net.Sockets; | ||
6 | |||
7 | namespace OpenSim | ||
8 | { | ||
9 | public abstract class OpenSimApplication | ||
10 | { | ||
11 | public abstract void StartUp(); | ||
12 | public abstract void Shutdown(); | ||
13 | public abstract void SendPacketTo(byte[] buffer, int size, SocketFlags flags, uint circuitcode);// EndPoint packetSender); | ||
14 | public abstract void RemoveClientCircuit(uint circuitcode); | ||
15 | } | ||
16 | } | ||
diff --git a/OpenSim.RegionServer/OpenSimMain.cs b/OpenSim.RegionServer/OpenSimMain.cs new file mode 100644 index 0000000..b2bc0b3 --- /dev/null +++ b/OpenSim.RegionServer/OpenSimMain.cs | |||
@@ -0,0 +1,320 @@ | |||
1 | /* | ||
2 | Copyright (c) OpenSim project, http://osgrid.org/ | ||
3 | |||
4 | * All rights reserved. | ||
5 | * | ||
6 | * Redistribution and use in source and binary forms, with or without | ||
7 | * modification, are permitted provided that the following conditions are met: | ||
8 | * * Redistributions of source code must retain the above copyright | ||
9 | * notice, this list of conditions and the following disclaimer. | ||
10 | * * Redistributions in binary form must reproduce the above copyright | ||
11 | * notice, this list of conditions and the following disclaimer in the | ||
12 | * documentation and/or other materials provided with the distribution. | ||
13 | * * Neither the name of the <organization> nor the | ||
14 | * names of its contributors may be used to endorse or promote products | ||
15 | * derived from this software without specific prior written permission. | ||
16 | * | ||
17 | * THIS SOFTWARE IS PROVIDED BY <copyright holder> ``AS IS'' AND ANY | ||
18 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
19 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
20 | * DISCLAIMED. IN NO EVENT SHALL <copyright holder> BE LIABLE FOR ANY | ||
21 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
22 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
23 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
24 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
25 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
26 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
27 | */ | ||
28 | |||
29 | using System; | ||
30 | using System.Text; | ||
31 | using System.IO; | ||
32 | using System.Threading; | ||
33 | using System.Net; | ||
34 | using System.Net.Sockets; | ||
35 | using System.Timers; | ||
36 | using System.Reflection; | ||
37 | using System.Collections; | ||
38 | using System.Collections.Generic; | ||
39 | using libsecondlife; | ||
40 | using libsecondlife.Packets; | ||
41 | using OpenSim.world; | ||
42 | using OpenSim.Framework.Interfaces; | ||
43 | using OpenSim.UserServer; | ||
44 | using OpenSim.Assets; | ||
45 | using OpenSim.CAPS; | ||
46 | using OpenSim.Framework.Console; | ||
47 | using OpenSim.Physics.Manager; | ||
48 | |||
49 | namespace OpenSim | ||
50 | { | ||
51 | /// <summary> | ||
52 | /// | ||
53 | /// </summary> | ||
54 | public class OpenSimMain : OpenSimApplication | ||
55 | { | ||
56 | private Dictionary<EndPoint, uint> clientCircuits = new Dictionary<EndPoint, uint>(); | ||
57 | private PhysicsManager physManager; | ||
58 | |||
59 | public Socket Server; | ||
60 | private IPEndPoint ServerIncoming; | ||
61 | private byte[] RecvBuffer = new byte[4096]; | ||
62 | private byte[] ZeroBuffer = new byte[8192]; | ||
63 | private IPEndPoint ipeSender; | ||
64 | private EndPoint epSender; | ||
65 | private AsyncCallback ReceivedData; | ||
66 | |||
67 | private System.Timers.Timer timer1 = new System.Timers.Timer(); | ||
68 | private string ConfigDll = "OpenSim.Config.SimConfigDb4o.dll"; | ||
69 | private string _physicsEngine = "basicphysics"; | ||
70 | public bool sandbox = false; | ||
71 | public bool loginserver = false; | ||
72 | |||
73 | [STAThread] | ||
74 | public static void Main(string[] args) | ||
75 | { | ||
76 | Console.WriteLine("OpenSim " + VersionInfo.Version + "\n"); | ||
77 | Console.WriteLine("Starting...\n"); | ||
78 | OpenSim.Framework.Console.MainConsole.Instance = new SimConsole(OpenSim.Framework.Console.ConsoleBase.ConsoleType.Local, "", 0); | ||
79 | |||
80 | //OpenSimRoot.instance = new OpenSimRoot(); | ||
81 | OpenSimMain sim = new OpenSimMain(); | ||
82 | OpenSimRoot.Instance.Application = sim; | ||
83 | |||
84 | sim.sandbox = false; | ||
85 | sim.loginserver = false; | ||
86 | sim._physicsEngine = "basicphysics"; | ||
87 | |||
88 | for (int i = 0; i < args.Length; i++) | ||
89 | { | ||
90 | if (args[i] == "-sandbox") | ||
91 | { | ||
92 | sim.sandbox = true; | ||
93 | OpenSimRoot.Instance.Sandbox = true; | ||
94 | } | ||
95 | |||
96 | if (args[i] == "-loginserver") | ||
97 | { | ||
98 | sim.loginserver = true; | ||
99 | } | ||
100 | if (args[i] == "-realphysx") | ||
101 | { | ||
102 | sim._physicsEngine = "RealPhysX"; | ||
103 | OpenSim.world.Avatar.PhysicsEngineFlying = true; | ||
104 | } | ||
105 | } | ||
106 | |||
107 | |||
108 | OpenSimRoot.Instance.GridServers = new Grid(); | ||
109 | if (sim.sandbox) | ||
110 | { | ||
111 | OpenSimRoot.Instance.GridServers.AssetDll = "OpenSim.GridInterfaces.Local.dll"; | ||
112 | OpenSimRoot.Instance.GridServers.GridDll = "OpenSim.GridInterfaces.Local.dll"; | ||
113 | OpenSimRoot.Instance.GridServers.Initialise(); | ||
114 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Starting in Sandbox mode"); | ||
115 | } | ||
116 | else | ||
117 | { | ||
118 | OpenSimRoot.Instance.GridServers.AssetDll = "OpenSim.GridInterfaces.Remote.dll"; | ||
119 | OpenSimRoot.Instance.GridServers.GridDll = "OpenSim.GridInterfaces.Remote.dll"; | ||
120 | OpenSimRoot.Instance.GridServers.Initialise(); | ||
121 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Starting in Grid mode"); | ||
122 | } | ||
123 | |||
124 | if (sim.loginserver && sim.sandbox) | ||
125 | { | ||
126 | LoginServer loginServer = new LoginServer(OpenSimRoot.Instance.GridServers.GridServer); | ||
127 | loginServer.Startup(); | ||
128 | } | ||
129 | |||
130 | OpenSimRoot.Instance.StartUp(); | ||
131 | |||
132 | while (true) | ||
133 | { | ||
134 | OpenSim.Framework.Console.MainConsole.Instance.MainConsolePrompt(); | ||
135 | } | ||
136 | } | ||
137 | |||
138 | private OpenSimMain() | ||
139 | { | ||
140 | } | ||
141 | |||
142 | public override void StartUp() | ||
143 | { | ||
144 | OpenSimRoot.Instance.startuptime = DateTime.Now; | ||
145 | |||
146 | OpenSimRoot.Instance.AssetCache = new AssetCache(OpenSimRoot.Instance.GridServers.AssetServer); | ||
147 | OpenSimRoot.Instance.InventoryCache = new InventoryCache(); | ||
148 | |||
149 | // We check our local database first, then the grid for config options | ||
150 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:Startup() - Loading configuration"); | ||
151 | OpenSimRoot.Instance.Cfg = this.LoadConfigDll(this.ConfigDll); | ||
152 | OpenSimRoot.Instance.Cfg.InitConfig(this.sandbox); | ||
153 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:Startup() - Contacting gridserver"); | ||
154 | OpenSimRoot.Instance.Cfg.LoadFromGrid(); | ||
155 | |||
156 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:Startup() - We are " + OpenSimRoot.Instance.Cfg.RegionName + " at " + OpenSimRoot.Instance.Cfg.RegionLocX.ToString() + "," + OpenSimRoot.Instance.Cfg.RegionLocY.ToString()); | ||
157 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Initialising world"); | ||
158 | OpenSimRoot.Instance.LocalWorld = new World(); | ||
159 | OpenSimRoot.Instance.LocalWorld.LandMap = OpenSimRoot.Instance.Cfg.LoadWorld(); | ||
160 | |||
161 | this.physManager = new OpenSim.Physics.Manager.PhysicsManager(); | ||
162 | this.physManager.LoadPlugins(); | ||
163 | |||
164 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:Startup() - Starting up messaging system"); | ||
165 | OpenSimRoot.Instance.LocalWorld.PhysScene = this.physManager.GetPhysicsScene(this._physicsEngine); //should be reading from the config file what physics engine to use | ||
166 | OpenSimRoot.Instance.LocalWorld.PhysScene.SetTerrain(OpenSimRoot.Instance.LocalWorld.LandMap); | ||
167 | |||
168 | OpenSimRoot.Instance.GridServers.AssetServer.SetServerInfo(OpenSimRoot.Instance.Cfg.AssetURL, OpenSimRoot.Instance.Cfg.AssetSendKey); | ||
169 | OpenSimRoot.Instance.GridServers.GridServer.SetServerInfo(OpenSimRoot.Instance.Cfg.GridURL, OpenSimRoot.Instance.Cfg.GridSendKey, OpenSimRoot.Instance.Cfg.GridRecvKey); | ||
170 | |||
171 | OpenSimRoot.Instance.LocalWorld.LoadStorageDLL("OpenSim.Storage.LocalStorageDb4o.dll"); //all these dll names shouldn't be hard coded. | ||
172 | OpenSimRoot.Instance.LocalWorld.LoadPrimsFromStorage(); | ||
173 | |||
174 | if (this.sandbox) | ||
175 | { | ||
176 | OpenSimRoot.Instance.AssetCache.LoadDefaultTextureSet(); | ||
177 | } | ||
178 | |||
179 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:Startup() - Starting CAPS HTTP server"); | ||
180 | OpenSimRoot.Instance.HttpServer = new SimCAPSHTTPServer(); | ||
181 | |||
182 | timer1.Enabled = true; | ||
183 | timer1.Interval = 100; | ||
184 | timer1.Elapsed += new ElapsedEventHandler(this.Timer1Tick); | ||
185 | |||
186 | MainServerListener(); | ||
187 | } | ||
188 | |||
189 | private SimConfig LoadConfigDll(string dllName) | ||
190 | { | ||
191 | Assembly pluginAssembly = Assembly.LoadFrom(dllName); | ||
192 | SimConfig config = null; | ||
193 | |||
194 | foreach (Type pluginType in pluginAssembly.GetTypes()) | ||
195 | { | ||
196 | if (pluginType.IsPublic) | ||
197 | { | ||
198 | if (!pluginType.IsAbstract) | ||
199 | { | ||
200 | Type typeInterface = pluginType.GetInterface("ISimConfig", true); | ||
201 | |||
202 | if (typeInterface != null) | ||
203 | { | ||
204 | ISimConfig plug = (ISimConfig)Activator.CreateInstance(pluginAssembly.GetType(pluginType.ToString())); | ||
205 | config = plug.GetConfigObject(); | ||
206 | break; | ||
207 | } | ||
208 | |||
209 | typeInterface = null; | ||
210 | } | ||
211 | } | ||
212 | } | ||
213 | pluginAssembly = null; | ||
214 | return config; | ||
215 | } | ||
216 | |||
217 | private void OnReceivedData(IAsyncResult result) | ||
218 | { | ||
219 | ipeSender = new IPEndPoint(IPAddress.Any, 0); | ||
220 | epSender = (EndPoint)ipeSender; | ||
221 | Packet packet = null; | ||
222 | int numBytes = Server.EndReceiveFrom(result, ref epSender); | ||
223 | int packetEnd = numBytes - 1; | ||
224 | packet = Packet.BuildPacket(RecvBuffer, ref packetEnd, ZeroBuffer); | ||
225 | |||
226 | // This is either a new client or a packet to send to an old one | ||
227 | // if (OpenSimRoot.Instance.ClientThreads.ContainsKey(epSender)) | ||
228 | |||
229 | // do we already have a circuit for this endpoint | ||
230 | if(this.clientCircuits.ContainsKey(epSender)) | ||
231 | { | ||
232 | OpenSimRoot.Instance.ClientThreads[this.clientCircuits[epSender]].InPacket(packet); | ||
233 | } | ||
234 | else if (packet.Type == PacketType.UseCircuitCode) | ||
235 | { // new client | ||
236 | UseCircuitCodePacket useCircuit = (UseCircuitCodePacket)packet; | ||
237 | this.clientCircuits.Add(epSender, useCircuit.CircuitCode.Code); | ||
238 | SimClient newuser = new SimClient(epSender, useCircuit); | ||
239 | //OpenSimRoot.Instance.ClientThreads.Add(epSender, newuser); | ||
240 | OpenSimRoot.Instance.ClientThreads.Add(useCircuit.CircuitCode.Code, newuser); | ||
241 | } | ||
242 | else | ||
243 | { // invalid client | ||
244 | Console.Error.WriteLine("Main.cs:OnReceivedData() - WARNING: Got a packet from an invalid client - " + epSender.ToString()); | ||
245 | } | ||
246 | Server.BeginReceiveFrom(RecvBuffer, 0, RecvBuffer.Length, SocketFlags.None, ref epSender, ReceivedData, null); | ||
247 | } | ||
248 | |||
249 | private void MainServerListener() | ||
250 | { | ||
251 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:MainServerListener() - New thread started"); | ||
252 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:MainServerListener() - Opening UDP socket on " + OpenSimRoot.Instance.Cfg.IPListenAddr + ":" + OpenSimRoot.Instance.Cfg.IPListenPort); | ||
253 | |||
254 | ServerIncoming = new IPEndPoint(IPAddress.Any, OpenSimRoot.Instance.Cfg.IPListenPort); | ||
255 | Server = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp); | ||
256 | Server.Bind(ServerIncoming); | ||
257 | |||
258 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:MainServerListener() - UDP socket bound, getting ready to listen"); | ||
259 | |||
260 | ipeSender = new IPEndPoint(IPAddress.Any, 0); | ||
261 | epSender = (EndPoint)ipeSender; | ||
262 | ReceivedData = new AsyncCallback(this.OnReceivedData); | ||
263 | Server.BeginReceiveFrom(RecvBuffer, 0, RecvBuffer.Length, SocketFlags.None, ref epSender, ReceivedData, null); | ||
264 | |||
265 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:MainServerListener() - Listening..."); | ||
266 | |||
267 | } | ||
268 | |||
269 | public override void SendPacketTo(byte[] buffer, int size, SocketFlags flags, uint circuitcode )//EndPoint packetSender) | ||
270 | { | ||
271 | // find the endpoint for this circuit | ||
272 | EndPoint sendto = null; | ||
273 | foreach(KeyValuePair<EndPoint, uint> p in this.clientCircuits) | ||
274 | { | ||
275 | if (p.Value == circuitcode) | ||
276 | { | ||
277 | sendto = p.Key; | ||
278 | break; | ||
279 | } | ||
280 | } | ||
281 | if (sendto != null) | ||
282 | { | ||
283 | //we found the endpoint so send the packet to it | ||
284 | this.Server.SendTo(buffer, size, flags, sendto); | ||
285 | } | ||
286 | } | ||
287 | |||
288 | public override void RemoveClientCircuit(uint circuitcode) | ||
289 | { | ||
290 | foreach (KeyValuePair<EndPoint, uint> p in this.clientCircuits) | ||
291 | { | ||
292 | if (p.Value == circuitcode) | ||
293 | { | ||
294 | this.clientCircuits.Remove(p.Key); | ||
295 | break; | ||
296 | } | ||
297 | } | ||
298 | } | ||
299 | |||
300 | public override void Shutdown() | ||
301 | { | ||
302 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:Shutdown() - Closing all threads"); | ||
303 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:Shutdown() - Killing listener thread"); | ||
304 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:Shutdown() - Killing clients"); | ||
305 | // IMPLEMENT THIS | ||
306 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Main.cs:Shutdown() - Closing console and terminating"); | ||
307 | OpenSimRoot.Instance.LocalWorld.Close(); | ||
308 | OpenSimRoot.Instance.GridServers.Close(); | ||
309 | OpenSim.Framework.Console.MainConsole.Instance.Close(); | ||
310 | Environment.Exit(0); | ||
311 | } | ||
312 | |||
313 | void Timer1Tick(object sender, System.EventArgs e) | ||
314 | { | ||
315 | OpenSimRoot.Instance.LocalWorld.Update(); | ||
316 | } | ||
317 | } | ||
318 | |||
319 | |||
320 | } | ||
diff --git a/OpenSim.RegionServer/OpenSimRoot.cs b/OpenSim.RegionServer/OpenSimRoot.cs new file mode 100644 index 0000000..3361e5d --- /dev/null +++ b/OpenSim.RegionServer/OpenSimRoot.cs | |||
@@ -0,0 +1,63 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Text; | ||
4 | using System.Net; | ||
5 | //using System.Net.Sockets; | ||
6 | using libsecondlife; | ||
7 | using libsecondlife.Packets; | ||
8 | using OpenSim.world; | ||
9 | using OpenSim.Framework.Interfaces; | ||
10 | using OpenSim.UserServer; | ||
11 | using OpenSim.Assets; | ||
12 | using OpenSim.CAPS; | ||
13 | using OpenSim.Framework.Console; | ||
14 | using OpenSim.Physics.Manager; | ||
15 | |||
16 | namespace OpenSim | ||
17 | { | ||
18 | public sealed class OpenSimRoot | ||
19 | { | ||
20 | private static OpenSimRoot instance = new OpenSimRoot(); | ||
21 | |||
22 | public static OpenSimRoot Instance | ||
23 | { | ||
24 | get | ||
25 | { | ||
26 | return instance; | ||
27 | } | ||
28 | } | ||
29 | |||
30 | private OpenSimRoot() | ||
31 | { | ||
32 | |||
33 | } | ||
34 | |||
35 | public World LocalWorld; | ||
36 | public Grid GridServers; | ||
37 | public SimConfig Cfg; | ||
38 | public SimCAPSHTTPServer HttpServer; | ||
39 | public AssetCache AssetCache; | ||
40 | public InventoryCache InventoryCache; | ||
41 | //public Dictionary<EndPoint, SimClient> ClientThreads = new Dictionary<EndPoint, SimClient>(); | ||
42 | public Dictionary<uint, SimClient> ClientThreads = new Dictionary<uint, SimClient>(); | ||
43 | public DateTime startuptime; | ||
44 | public OpenSimApplication Application; | ||
45 | public bool Sandbox = false; | ||
46 | |||
47 | public void StartUp() | ||
48 | { | ||
49 | if (this.Application != null) | ||
50 | { | ||
51 | this.Application.StartUp(); | ||
52 | } | ||
53 | } | ||
54 | |||
55 | public void Shutdown() | ||
56 | { | ||
57 | if (this.Application != null) | ||
58 | { | ||
59 | this.Application.Shutdown(); | ||
60 | } | ||
61 | } | ||
62 | } | ||
63 | } | ||
diff --git a/OpenSim.RegionServer/QueItem.cs b/OpenSim.RegionServer/QueItem.cs new file mode 100644 index 0000000..747e026 --- /dev/null +++ b/OpenSim.RegionServer/QueItem.cs | |||
@@ -0,0 +1,18 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Text; | ||
4 | using libsecondlife.Packets; | ||
5 | |||
6 | namespace OpenSim | ||
7 | { | ||
8 | public class QueItem | ||
9 | { | ||
10 | public QueItem() | ||
11 | { | ||
12 | } | ||
13 | |||
14 | public Packet Packet; | ||
15 | public bool Incoming; | ||
16 | } | ||
17 | |||
18 | } | ||
diff --git a/OpenSim.RegionServer/SimClient.cs b/OpenSim.RegionServer/SimClient.cs new file mode 100644 index 0000000..210e0d9 --- /dev/null +++ b/OpenSim.RegionServer/SimClient.cs | |||
@@ -0,0 +1,621 @@ | |||
1 | /* | ||
2 | Copyright (c) OpenSim project, http://osgrid.org/ | ||
3 | * | ||
4 | * Redistribution and use in source and binary forms, with or without | ||
5 | * modification, are permitted provided that the following conditions are met: | ||
6 | * * Redistributions of source code must retain the above copyright | ||
7 | * notice, this list of conditions and the following disclaimer. | ||
8 | * * Redistributions in binary form must reproduce the above copyright | ||
9 | * notice, this list of conditions and the following disclaimer in the | ||
10 | * documentation and/or other materials provided with the distribution. | ||
11 | * * Neither the name of the <organization> nor the | ||
12 | * names of its contributors may be used to endorse or promote products | ||
13 | * derived from this software without specific prior written permission. | ||
14 | * | ||
15 | * THIS SOFTWARE IS PROVIDED BY <copyright holder> ``AS IS'' AND ANY | ||
16 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
17 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
18 | * DISCLAIMED. IN NO EVENT SHALL <copyright holder> BE LIABLE FOR ANY | ||
19 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
20 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
21 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
22 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
23 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
24 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
25 | */ | ||
26 | |||
27 | using System; | ||
28 | using System.Collections; | ||
29 | using System.Collections.Generic; | ||
30 | using libsecondlife; | ||
31 | using libsecondlife.Packets; | ||
32 | using System.Net; | ||
33 | using System.Net.Sockets; | ||
34 | using System.IO; | ||
35 | using System.Threading; | ||
36 | using System.Timers; | ||
37 | using OpenSim.Framework.Interfaces; | ||
38 | using OpenSim.Framework.Assets; | ||
39 | using OpenSim.Framework.Inventory; | ||
40 | using OpenSim.Framework.Utilities; | ||
41 | using OpenSim.world; | ||
42 | using OpenSim.Assets; | ||
43 | |||
44 | namespace OpenSim | ||
45 | { | ||
46 | /// <summary> | ||
47 | /// Handles new client connections | ||
48 | /// Constructor takes a single Packet and authenticates everything | ||
49 | /// </summary> | ||
50 | public class SimClient | ||
51 | { | ||
52 | |||
53 | public LLUUID AgentID; | ||
54 | public LLUUID SessionID; | ||
55 | public LLUUID SecureSessionID = LLUUID.Zero; | ||
56 | public uint CircuitCode; | ||
57 | public world.Avatar ClientAvatar; | ||
58 | private UseCircuitCodePacket cirpack; | ||
59 | private Thread ClientThread; | ||
60 | public EndPoint userEP; | ||
61 | private BlockingQueue<QueItem> PacketQueue; | ||
62 | private Dictionary<uint, uint> PendingAcks = new Dictionary<uint, uint>(); | ||
63 | private Dictionary<uint, Packet> NeedAck = new Dictionary<uint, Packet>(); | ||
64 | //private Dictionary<LLUUID, AssetBase> UploadedAssets = new Dictionary<LLUUID, AssetBase>(); | ||
65 | private System.Timers.Timer AckTimer; | ||
66 | private uint Sequence = 0; | ||
67 | private object SequenceLock = new object(); | ||
68 | private const int MAX_APPENDED_ACKS = 10; | ||
69 | private const int RESEND_TIMEOUT = 4000; | ||
70 | private const int MAX_SEQUENCE = 0xFFFFFF; | ||
71 | private LLUUID newAssetFolder = LLUUID.Zero; | ||
72 | private bool debug = false; | ||
73 | |||
74 | private void ack_pack(Packet Pack) | ||
75 | { | ||
76 | //libsecondlife.Packets.PacketAckPacket ack_it = new PacketAckPacket(); | ||
77 | //ack_it.Packets = new PacketAckPacket.PacketsBlock[1]; | ||
78 | //ack_it.Packets[0] = new PacketAckPacket.PacketsBlock(); | ||
79 | //ack_it.Packets[0].ID = Pack.Header.ID; | ||
80 | //ack_it.Header.Reliable = false; | ||
81 | |||
82 | //OutPacket(ack_it); | ||
83 | |||
84 | if (Pack.Header.Reliable) | ||
85 | { | ||
86 | lock (PendingAcks) | ||
87 | { | ||
88 | uint sequence = (uint)Pack.Header.Sequence; | ||
89 | if (!PendingAcks.ContainsKey(sequence)) { PendingAcks[sequence] = sequence; } | ||
90 | } | ||
91 | } | ||
92 | } | ||
93 | |||
94 | protected virtual void ProcessInPacket(Packet Pack) | ||
95 | { | ||
96 | ack_pack(Pack); | ||
97 | if (debug) | ||
98 | { | ||
99 | if (Pack.Type != PacketType.AgentUpdate) | ||
100 | { | ||
101 | Console.WriteLine(Pack.Type.ToString()); | ||
102 | } | ||
103 | } | ||
104 | switch (Pack.Type) | ||
105 | { | ||
106 | case PacketType.CompleteAgentMovement: | ||
107 | ClientAvatar.CompleteMovement(OpenSimRoot.Instance.LocalWorld); | ||
108 | ClientAvatar.SendInitialPosition(); | ||
109 | break; | ||
110 | case PacketType.RegionHandshakeReply: | ||
111 | OpenSimRoot.Instance.LocalWorld.SendLayerData(this); | ||
112 | break; | ||
113 | case PacketType.AgentWearablesRequest: | ||
114 | ClientAvatar.SendInitialAppearance(); | ||
115 | foreach (SimClient client in OpenSimRoot.Instance.ClientThreads.Values) | ||
116 | { | ||
117 | if (client.AgentID != this.AgentID) | ||
118 | { | ||
119 | ObjectUpdatePacket objupdate = client.ClientAvatar.CreateUpdatePacket(); | ||
120 | this.OutPacket(objupdate); | ||
121 | client.ClientAvatar.SendAppearanceToOtherAgent(this); | ||
122 | } | ||
123 | } | ||
124 | OpenSimRoot.Instance.LocalWorld.GetInitialPrims(this); | ||
125 | break; | ||
126 | case PacketType.ObjectAdd: | ||
127 | OpenSimRoot.Instance.LocalWorld.AddNewPrim((ObjectAddPacket)Pack, this); | ||
128 | break; | ||
129 | case PacketType.ObjectLink: | ||
130 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine(Pack.ToString()); | ||
131 | break; | ||
132 | case PacketType.ObjectScale: | ||
133 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine(Pack.ToString()); | ||
134 | break; | ||
135 | case PacketType.ObjectShape: | ||
136 | ObjectShapePacket shape = (ObjectShapePacket)Pack; | ||
137 | for (int i = 0; i < shape.ObjectData.Length; i++) | ||
138 | { | ||
139 | foreach (Entity ent in OpenSimRoot.Instance.LocalWorld.Entities.Values) | ||
140 | { | ||
141 | if (ent.localid == shape.ObjectData[i].ObjectLocalID) | ||
142 | { | ||
143 | ((OpenSim.world.Primitive)ent).UpdateShape(shape.ObjectData[i]); | ||
144 | } | ||
145 | } | ||
146 | } | ||
147 | break; | ||
148 | case PacketType.MultipleObjectUpdate: | ||
149 | MultipleObjectUpdatePacket multipleupdate = (MultipleObjectUpdatePacket)Pack; | ||
150 | |||
151 | for (int i = 0; i < multipleupdate.ObjectData.Length; i++) | ||
152 | { | ||
153 | if (multipleupdate.ObjectData[i].Type == 9) //change position | ||
154 | { | ||
155 | libsecondlife.LLVector3 pos = new LLVector3(multipleupdate.ObjectData[i].Data, 0); | ||
156 | foreach (Entity ent in OpenSimRoot.Instance.LocalWorld.Entities.Values) | ||
157 | { | ||
158 | if (ent.localid == multipleupdate.ObjectData[i].ObjectLocalID) | ||
159 | { | ||
160 | ((OpenSim.world.Primitive)ent).UpdatePosition(pos); | ||
161 | |||
162 | } | ||
163 | } | ||
164 | |||
165 | //should update stored position of the prim | ||
166 | } | ||
167 | else if (multipleupdate.ObjectData[i].Type == 10)//rotation | ||
168 | { | ||
169 | libsecondlife.LLQuaternion rot = new LLQuaternion(multipleupdate.ObjectData[i].Data, 0, true); | ||
170 | foreach (Entity ent in OpenSimRoot.Instance.LocalWorld.Entities.Values) | ||
171 | { | ||
172 | if (ent.localid == multipleupdate.ObjectData[i].ObjectLocalID) | ||
173 | { | ||
174 | ent.rotation = new Axiom.MathLib.Quaternion(rot.W, rot.X, rot.Y, rot.W); | ||
175 | ((OpenSim.world.Primitive)ent).UpdateFlag = true; | ||
176 | } | ||
177 | } | ||
178 | } | ||
179 | else if (multipleupdate.ObjectData[i].Type == 13)//scale | ||
180 | { | ||
181 | |||
182 | libsecondlife.LLVector3 scale = new LLVector3(multipleupdate.ObjectData[i].Data, 12); | ||
183 | foreach (Entity ent in OpenSimRoot.Instance.LocalWorld.Entities.Values) | ||
184 | { | ||
185 | if (ent.localid == multipleupdate.ObjectData[i].ObjectLocalID) | ||
186 | { | ||
187 | ((OpenSim.world.Primitive)ent).Scale = scale; | ||
188 | } | ||
189 | } | ||
190 | } | ||
191 | } | ||
192 | break; | ||
193 | case PacketType.RequestImage: | ||
194 | RequestImagePacket imageRequest = (RequestImagePacket)Pack; | ||
195 | for (int i = 0; i < imageRequest.RequestImage.Length; i++) | ||
196 | { | ||
197 | OpenSimRoot.Instance.AssetCache.AddTextureRequest(this, imageRequest.RequestImage[i].Image); | ||
198 | } | ||
199 | break; | ||
200 | case PacketType.TransferRequest: | ||
201 | //Console.WriteLine("OpenSimClient.cs:ProcessInPacket() - Got transfer request"); | ||
202 | TransferRequestPacket transfer = (TransferRequestPacket)Pack; | ||
203 | OpenSimRoot.Instance.AssetCache.AddAssetRequest(this, transfer); | ||
204 | break; | ||
205 | case PacketType.AgentUpdate: | ||
206 | ClientAvatar.HandleUpdate((AgentUpdatePacket)Pack); | ||
207 | break; | ||
208 | case PacketType.LogoutRequest: | ||
209 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("OpenSimClient.cs:ProcessInPacket() - Got a logout request"); | ||
210 | //send reply to let the client logout | ||
211 | LogoutReplyPacket logReply = new LogoutReplyPacket(); | ||
212 | logReply.AgentData.AgentID = this.AgentID; | ||
213 | logReply.AgentData.SessionID = this.SessionID; | ||
214 | logReply.InventoryData = new LogoutReplyPacket.InventoryDataBlock[1]; | ||
215 | logReply.InventoryData[0] = new LogoutReplyPacket.InventoryDataBlock(); | ||
216 | logReply.InventoryData[0].ItemID = LLUUID.Zero; | ||
217 | OutPacket(logReply); | ||
218 | //tell all clients to kill our object | ||
219 | KillObjectPacket kill = new KillObjectPacket(); | ||
220 | kill.ObjectData = new KillObjectPacket.ObjectDataBlock[1]; | ||
221 | kill.ObjectData[0] = new KillObjectPacket.ObjectDataBlock(); | ||
222 | kill.ObjectData[0].ID = this.ClientAvatar.localid; | ||
223 | foreach (SimClient client in OpenSimRoot.Instance.ClientThreads.Values) | ||
224 | { | ||
225 | client.OutPacket(kill); | ||
226 | } | ||
227 | OpenSimRoot.Instance.GridServers.GridServer.LogoutSession(this.SessionID, this.AgentID, this.CircuitCode); | ||
228 | lock (OpenSimRoot.Instance.LocalWorld.Entities) | ||
229 | { | ||
230 | OpenSimRoot.Instance.LocalWorld.Entities.Remove(this.AgentID); | ||
231 | } | ||
232 | //need to do other cleaning up here too | ||
233 | OpenSimRoot.Instance.ClientThreads.Remove(this.CircuitCode); //this.userEP); | ||
234 | OpenSimRoot.Instance.Application.RemoveClientCircuit(this.CircuitCode); | ||
235 | this.ClientThread.Abort(); | ||
236 | break; | ||
237 | case PacketType.ChatFromViewer: | ||
238 | ChatFromViewerPacket inchatpack = (ChatFromViewerPacket)Pack; | ||
239 | if (Helpers.FieldToString(inchatpack.ChatData.Message) == "") break; | ||
240 | |||
241 | System.Text.Encoding _enc = System.Text.Encoding.ASCII; | ||
242 | libsecondlife.Packets.ChatFromSimulatorPacket reply = new ChatFromSimulatorPacket(); | ||
243 | reply.ChatData.Audible = 1; | ||
244 | reply.ChatData.Message = inchatpack.ChatData.Message; | ||
245 | reply.ChatData.ChatType = 1; | ||
246 | reply.ChatData.SourceType = 1; | ||
247 | reply.ChatData.Position = this.ClientAvatar.position; | ||
248 | reply.ChatData.FromName = _enc.GetBytes(this.ClientAvatar.firstname + " " + this.ClientAvatar.lastname + "\0"); | ||
249 | reply.ChatData.OwnerID = this.AgentID; | ||
250 | reply.ChatData.SourceID = this.AgentID; | ||
251 | foreach (SimClient client in OpenSimRoot.Instance.ClientThreads.Values) | ||
252 | { | ||
253 | client.OutPacket(reply); | ||
254 | } | ||
255 | break; | ||
256 | case PacketType.ObjectImage: | ||
257 | ObjectImagePacket imagePack = (ObjectImagePacket)Pack; | ||
258 | for (int i = 0; i < imagePack.ObjectData.Length; i++) | ||
259 | { | ||
260 | foreach (Entity ent in OpenSimRoot.Instance.LocalWorld.Entities.Values) | ||
261 | { | ||
262 | if (ent.localid == imagePack.ObjectData[i].ObjectLocalID) | ||
263 | { | ||
264 | ((OpenSim.world.Primitive)ent).UpdateTexture(imagePack.ObjectData[i].TextureEntry); | ||
265 | } | ||
266 | } | ||
267 | } | ||
268 | break; | ||
269 | case PacketType.ObjectFlagUpdate: | ||
270 | ObjectFlagUpdatePacket flags = (ObjectFlagUpdatePacket)Pack; | ||
271 | foreach (Entity ent in OpenSimRoot.Instance.LocalWorld.Entities.Values) | ||
272 | { | ||
273 | if (ent.localid == flags.AgentData.ObjectLocalID) | ||
274 | { | ||
275 | ((OpenSim.world.Primitive)ent).UpdateObjectFlags(flags); | ||
276 | } | ||
277 | } | ||
278 | |||
279 | break; | ||
280 | case PacketType.AssetUploadRequest: | ||
281 | AssetUploadRequestPacket request = (AssetUploadRequestPacket)Pack; | ||
282 | Console.WriteLine("upload request "+ request.AssetBlock.TransactionID); | ||
283 | AssetBase newAsset = OpenSimRoot.Instance.AssetCache.UploadPacket(request, LLUUID.Random()); | ||
284 | if (newAsset != null) | ||
285 | { | ||
286 | OpenSimRoot.Instance.InventoryCache.AddNewInventoryItem(this, this.newAssetFolder, newAsset); | ||
287 | } | ||
288 | Console.WriteLine(request.ToString()); | ||
289 | Console.WriteLine("combined uuid is " + request.AssetBlock.TransactionID.Combine(this.SecureSessionID).ToStringHyphenated()); | ||
290 | |||
291 | AssetUploadCompletePacket response = new AssetUploadCompletePacket(); | ||
292 | response.AssetBlock.Type =request.AssetBlock.Type; | ||
293 | response.AssetBlock.Success = true; | ||
294 | response.AssetBlock.UUID = request.AssetBlock.TransactionID.Combine(this.SecureSessionID); | ||
295 | |||
296 | this.OutPacket(response); | ||
297 | break; | ||
298 | case PacketType.CreateInventoryFolder: | ||
299 | //Console.WriteLine(Pack.ToString()); | ||
300 | break; | ||
301 | case PacketType.CreateInventoryItem: | ||
302 | //Console.WriteLine(Pack.ToString()); | ||
303 | break; | ||
304 | case PacketType.FetchInventory: | ||
305 | Console.WriteLine("fetch item packet"); | ||
306 | FetchInventoryPacket FetchInventory = (FetchInventoryPacket)Pack; | ||
307 | OpenSimRoot.Instance.InventoryCache.FetchInventory(this, FetchInventory); | ||
308 | break; | ||
309 | case PacketType.FetchInventoryDescendents: | ||
310 | FetchInventoryDescendentsPacket Fetch = (FetchInventoryDescendentsPacket)Pack; | ||
311 | OpenSimRoot.Instance.InventoryCache.FetchInventoryDescendents(this, Fetch); | ||
312 | break; | ||
313 | } | ||
314 | } | ||
315 | |||
316 | private void ResendUnacked() | ||
317 | { | ||
318 | int now = Environment.TickCount; | ||
319 | |||
320 | lock (NeedAck) | ||
321 | { | ||
322 | foreach (Packet packet in NeedAck.Values) | ||
323 | { | ||
324 | if ((now - packet.TickCount > RESEND_TIMEOUT) && (!packet.Header.Resent)) | ||
325 | { | ||
326 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Resending " + packet.Type.ToString() + " packet, " + | ||
327 | (now - packet.TickCount) + "ms have passed"); | ||
328 | |||
329 | packet.Header.Resent = true; | ||
330 | OutPacket(packet); | ||
331 | } | ||
332 | } | ||
333 | } | ||
334 | } | ||
335 | |||
336 | private void SendAcks() | ||
337 | { | ||
338 | lock (PendingAcks) | ||
339 | { | ||
340 | if (PendingAcks.Count > 0) | ||
341 | { | ||
342 | if (PendingAcks.Count > 250) | ||
343 | { | ||
344 | // FIXME: Handle the odd case where we have too many pending ACKs queued up | ||
345 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Too many ACKs queued up!"); | ||
346 | return; | ||
347 | } | ||
348 | |||
349 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Sending PacketAck"); | ||
350 | |||
351 | |||
352 | int i = 0; | ||
353 | PacketAckPacket acks = new PacketAckPacket(); | ||
354 | acks.Packets = new PacketAckPacket.PacketsBlock[PendingAcks.Count]; | ||
355 | |||
356 | foreach (uint ack in PendingAcks.Values) | ||
357 | { | ||
358 | acks.Packets[i] = new PacketAckPacket.PacketsBlock(); | ||
359 | acks.Packets[i].ID = ack; | ||
360 | i++; | ||
361 | } | ||
362 | |||
363 | acks.Header.Reliable = false; | ||
364 | OutPacket(acks); | ||
365 | |||
366 | PendingAcks.Clear(); | ||
367 | } | ||
368 | } | ||
369 | } | ||
370 | |||
371 | private void AckTimer_Elapsed(object sender, ElapsedEventArgs ea) | ||
372 | { | ||
373 | SendAcks(); | ||
374 | ResendUnacked(); | ||
375 | } | ||
376 | |||
377 | protected virtual void ProcessOutPacket(Packet Pack) | ||
378 | { | ||
379 | |||
380 | // Keep track of when this packet was sent out | ||
381 | Pack.TickCount = Environment.TickCount; | ||
382 | |||
383 | if (!Pack.Header.Resent) | ||
384 | { | ||
385 | // Set the sequence number | ||
386 | lock (SequenceLock) | ||
387 | { | ||
388 | if (Sequence >= MAX_SEQUENCE) | ||
389 | Sequence = 1; | ||
390 | else | ||
391 | Sequence++; | ||
392 | Pack.Header.Sequence = Sequence; | ||
393 | } | ||
394 | |||
395 | if (Pack.Header.Reliable) //DIRTY HACK | ||
396 | { | ||
397 | lock (NeedAck) | ||
398 | { | ||
399 | if (!NeedAck.ContainsKey(Pack.Header.Sequence)) | ||
400 | { | ||
401 | NeedAck.Add(Pack.Header.Sequence, Pack); | ||
402 | } | ||
403 | else | ||
404 | { | ||
405 | // Client.Log("Attempted to add a duplicate sequence number (" + | ||
406 | // packet.Header.Sequence + ") to the NeedAck dictionary for packet type " + | ||
407 | // packet.Type.ToString(), Helpers.LogLevel.Warning); | ||
408 | } | ||
409 | } | ||
410 | |||
411 | // Don't append ACKs to resent packets, in case that's what was causing the | ||
412 | // delivery to fail | ||
413 | if (!Pack.Header.Resent) | ||
414 | { | ||
415 | // Append any ACKs that need to be sent out to this packet | ||
416 | lock (PendingAcks) | ||
417 | { | ||
418 | if (PendingAcks.Count > 0 && PendingAcks.Count < MAX_APPENDED_ACKS && | ||
419 | Pack.Type != PacketType.PacketAck && | ||
420 | Pack.Type != PacketType.LogoutRequest) | ||
421 | { | ||
422 | Pack.Header.AckList = new uint[PendingAcks.Count]; | ||
423 | int i = 0; | ||
424 | |||
425 | foreach (uint ack in PendingAcks.Values) | ||
426 | { | ||
427 | Pack.Header.AckList[i] = ack; | ||
428 | i++; | ||
429 | } | ||
430 | |||
431 | PendingAcks.Clear(); | ||
432 | Pack.Header.AppendedAcks = true; | ||
433 | } | ||
434 | } | ||
435 | } | ||
436 | } | ||
437 | } | ||
438 | |||
439 | //ServerConsole.MainConsole.Instance.WriteLine("OUT: \n" + Pack.ToString()); | ||
440 | |||
441 | byte[] ZeroOutBuffer = new byte[4096]; | ||
442 | byte[] sendbuffer; | ||
443 | sendbuffer = Pack.ToBytes(); | ||
444 | |||
445 | try | ||
446 | { | ||
447 | if (Pack.Header.Zerocoded) | ||
448 | { | ||
449 | int packetsize = Helpers.ZeroEncode(sendbuffer, sendbuffer.Length, ZeroOutBuffer); | ||
450 | OpenSimRoot.Instance.Application.SendPacketTo(ZeroOutBuffer, packetsize, SocketFlags.None, CircuitCode);//userEP); | ||
451 | } | ||
452 | else | ||
453 | { | ||
454 | OpenSimRoot.Instance.Application.SendPacketTo(sendbuffer, sendbuffer.Length, SocketFlags.None, CircuitCode); //userEP); | ||
455 | } | ||
456 | } | ||
457 | catch (Exception) | ||
458 | { | ||
459 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("OpenSimClient.cs:ProcessOutPacket() - WARNING: Socket exception occurred on connection " + userEP.ToString() + " - killing thread"); | ||
460 | ClientThread.Abort(); | ||
461 | } | ||
462 | |||
463 | } | ||
464 | |||
465 | public virtual void InPacket(Packet NewPack) | ||
466 | { | ||
467 | // Handle appended ACKs | ||
468 | if (NewPack.Header.AppendedAcks) | ||
469 | { | ||
470 | lock (NeedAck) | ||
471 | { | ||
472 | foreach (uint ack in NewPack.Header.AckList) | ||
473 | { | ||
474 | NeedAck.Remove(ack); | ||
475 | } | ||
476 | } | ||
477 | } | ||
478 | |||
479 | // Handle PacketAck packets | ||
480 | if (NewPack.Type == PacketType.PacketAck) | ||
481 | { | ||
482 | PacketAckPacket ackPacket = (PacketAckPacket)NewPack; | ||
483 | |||
484 | lock (NeedAck) | ||
485 | { | ||
486 | foreach (PacketAckPacket.PacketsBlock block in ackPacket.Packets) | ||
487 | { | ||
488 | NeedAck.Remove(block.ID); | ||
489 | } | ||
490 | } | ||
491 | } | ||
492 | else if ((NewPack.Type == PacketType.StartPingCheck)) | ||
493 | { | ||
494 | //reply to pingcheck | ||
495 | libsecondlife.Packets.StartPingCheckPacket startPing = (libsecondlife.Packets.StartPingCheckPacket)NewPack; | ||
496 | libsecondlife.Packets.CompletePingCheckPacket endPing = new CompletePingCheckPacket(); | ||
497 | endPing.PingID.PingID = startPing.PingID.PingID; | ||
498 | OutPacket(endPing); | ||
499 | } | ||
500 | else | ||
501 | { | ||
502 | QueItem item = new QueItem(); | ||
503 | item.Packet = NewPack; | ||
504 | item.Incoming = true; | ||
505 | this.PacketQueue.Enqueue(item); | ||
506 | } | ||
507 | |||
508 | } | ||
509 | |||
510 | public virtual void OutPacket(Packet NewPack) | ||
511 | { | ||
512 | QueItem item = new QueItem(); | ||
513 | item.Packet = NewPack; | ||
514 | item.Incoming = false; | ||
515 | this.PacketQueue.Enqueue(item); | ||
516 | } | ||
517 | |||
518 | public SimClient(EndPoint remoteEP, UseCircuitCodePacket initialcirpack) | ||
519 | { | ||
520 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("OpenSimClient.cs - Started up new client thread to handle incoming request"); | ||
521 | cirpack = initialcirpack; | ||
522 | userEP = remoteEP; | ||
523 | PacketQueue = new BlockingQueue<QueItem>(); | ||
524 | AckTimer = new System.Timers.Timer(500); | ||
525 | AckTimer.Elapsed += new ElapsedEventHandler(AckTimer_Elapsed); | ||
526 | AckTimer.Start(); | ||
527 | |||
528 | ClientThread = new Thread(new ThreadStart(AuthUser)); | ||
529 | ClientThread.IsBackground = true; | ||
530 | ClientThread.Start(); | ||
531 | } | ||
532 | |||
533 | protected virtual void ClientLoop() | ||
534 | { | ||
535 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("OpenSimClient.cs:ClientLoop() - Entered loop"); | ||
536 | while (true) | ||
537 | { | ||
538 | QueItem nextPacket = PacketQueue.Dequeue(); | ||
539 | if (nextPacket.Incoming) | ||
540 | { | ||
541 | //is a incoming packet | ||
542 | ProcessInPacket(nextPacket.Packet); | ||
543 | } | ||
544 | else | ||
545 | { | ||
546 | //is a out going packet | ||
547 | ProcessOutPacket(nextPacket.Packet); | ||
548 | } | ||
549 | } | ||
550 | } | ||
551 | |||
552 | protected virtual void InitNewClient() | ||
553 | { | ||
554 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("OpenSimClient.cs:InitNewClient() - Adding viewer agent to world"); | ||
555 | OpenSimRoot.Instance.LocalWorld.AddViewerAgent(this); | ||
556 | world.Entity tempent = OpenSimRoot.Instance.LocalWorld.Entities[this.AgentID]; | ||
557 | this.ClientAvatar = (world.Avatar)tempent; | ||
558 | } | ||
559 | |||
560 | protected virtual void AuthUser() | ||
561 | { | ||
562 | AuthenticateResponse sessionInfo = OpenSimRoot.Instance.GridServers.GridServer.AuthenticateSession(cirpack.CircuitCode.SessionID, cirpack.CircuitCode.ID, cirpack.CircuitCode.Code); | ||
563 | if (!sessionInfo.Authorised) | ||
564 | { | ||
565 | //session/circuit not authorised | ||
566 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("OpenSimClient.cs:AuthUser() - New user request denied to " + userEP.ToString()); | ||
567 | ClientThread.Abort(); | ||
568 | } | ||
569 | else | ||
570 | { | ||
571 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("OpenSimClient.cs:AuthUser() - Got authenticated connection from " + userEP.ToString()); | ||
572 | //session is authorised | ||
573 | this.AgentID = cirpack.CircuitCode.ID; | ||
574 | this.SessionID = cirpack.CircuitCode.SessionID; | ||
575 | this.CircuitCode = cirpack.CircuitCode.Code; | ||
576 | InitNewClient(); //shouldn't be called here as we might be a child agent and not want a full avatar | ||
577 | this.ClientAvatar.firstname = sessionInfo.LoginInfo.First; | ||
578 | this.ClientAvatar.lastname = sessionInfo.LoginInfo.Last; | ||
579 | if (sessionInfo.LoginInfo.SecureSession != LLUUID.Zero) | ||
580 | { | ||
581 | this.SecureSessionID = sessionInfo.LoginInfo.SecureSession; | ||
582 | } | ||
583 | |||
584 | // Create Inventory, currently only works for sandbox mode | ||
585 | if (OpenSimRoot.Instance.Sandbox) | ||
586 | { | ||
587 | if (sessionInfo.LoginInfo.InventoryFolder != null) | ||
588 | { | ||
589 | this.CreateInventory(sessionInfo.LoginInfo.InventoryFolder); | ||
590 | if (sessionInfo.LoginInfo.BaseFolder != null) | ||
591 | { | ||
592 | OpenSimRoot.Instance.InventoryCache.CreateNewInventoryFolder(this, sessionInfo.LoginInfo.BaseFolder); | ||
593 | this.newAssetFolder = sessionInfo.LoginInfo.BaseFolder; | ||
594 | AssetBase[] inventorySet = OpenSimRoot.Instance.AssetCache.CreateNewInventorySet(this.AgentID); | ||
595 | if (inventorySet != null) | ||
596 | { | ||
597 | for (int i = 0; i < inventorySet.Length; i++) | ||
598 | { | ||
599 | if (inventorySet[i] != null) | ||
600 | { | ||
601 | OpenSimRoot.Instance.InventoryCache.AddNewInventoryItem(this, sessionInfo.LoginInfo.BaseFolder, inventorySet[i]); | ||
602 | } | ||
603 | } | ||
604 | } | ||
605 | } | ||
606 | } | ||
607 | } | ||
608 | |||
609 | ClientLoop(); | ||
610 | } | ||
611 | } | ||
612 | |||
613 | private void CreateInventory(LLUUID baseFolder) | ||
614 | { | ||
615 | AgentInventory inventory = new AgentInventory(); | ||
616 | inventory.AgentID = this.AgentID; | ||
617 | OpenSimRoot.Instance.InventoryCache.AddNewAgentsInventory(inventory); | ||
618 | OpenSimRoot.Instance.InventoryCache.CreateNewInventoryFolder(this, baseFolder); | ||
619 | } | ||
620 | } | ||
621 | } | ||
diff --git a/OpenSim.RegionServer/SimConsole.cs b/OpenSim.RegionServer/SimConsole.cs new file mode 100644 index 0000000..d6d5e44 --- /dev/null +++ b/OpenSim.RegionServer/SimConsole.cs | |||
@@ -0,0 +1,211 @@ | |||
1 | /* | ||
2 | * Copyright (c) OpenSim project, http://sim.opensecondlife.org/ | ||
3 | * | ||
4 | * Redistribution and use in source and binary forms, with or without | ||
5 | * modification, are permitted provided that the following conditions are met: | ||
6 | * * Redistributions of source code must retain the above copyright | ||
7 | * notice, this list of conditions and the following disclaimer. | ||
8 | * * Redistributions in binary form must reproduce the above copyright | ||
9 | * notice, this list of conditions and the following disclaimer in the | ||
10 | * documentation and/or other materials provided with the distribution. | ||
11 | * * Neither the name of the <organization> nor the | ||
12 | * names of its contributors may be used to endorse or promote products | ||
13 | * derived from this software without specific prior written permission. | ||
14 | * | ||
15 | * THIS SOFTWARE IS PROVIDED BY <copyright holder> ``AS IS'' AND ANY | ||
16 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
17 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
18 | * DISCLAIMED. IN NO EVENT SHALL <copyright holder> BE LIABLE FOR ANY | ||
19 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
20 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
21 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
22 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
23 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
24 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
25 | * | ||
26 | */ | ||
27 | |||
28 | using System; | ||
29 | using System.Collections; | ||
30 | using System.Collections.Generic; | ||
31 | using System.Threading; | ||
32 | using System.IO; | ||
33 | using System.Net; | ||
34 | using libsecondlife; | ||
35 | using libsecondlife.Packets; | ||
36 | using OpenSim.Framework.Console; | ||
37 | |||
38 | namespace OpenSim | ||
39 | { | ||
40 | /// <summary> | ||
41 | /// Description of ServerConsole. | ||
42 | /// </summary> | ||
43 | public class SimConsole : ConsoleBase | ||
44 | { | ||
45 | |||
46 | private ConsoleType ConsType; | ||
47 | StreamWriter Log; | ||
48 | |||
49 | |||
50 | // STUPID HACK ALERT!!!! STUPID HACK ALERT!!!!! | ||
51 | // constype - the type of console to use (see enum ConsoleType) | ||
52 | // sparam - depending on the console type: | ||
53 | // TCP - the IP to bind to (127.0.0.1 if blank) | ||
54 | // Local - param ignored | ||
55 | // SimChat - the AgentID of this sim's admin | ||
56 | // and for the iparam: | ||
57 | // TCP - the port to bind to | ||
58 | // Local - param ignored | ||
59 | // SimChat - the chat channel to accept commands from | ||
60 | public SimConsole(ConsoleType constype, string sparam, int iparam) { | ||
61 | ConsType = constype; | ||
62 | switch(constype) { | ||
63 | case ConsoleType.Local: | ||
64 | |||
65 | Console.WriteLine("ServerConsole.cs - creating new local console"); | ||
66 | Console.WriteLine("Logs will be saved to current directory in opensim-console.log"); | ||
67 | Log=File.AppendText("opensim-console.log"); | ||
68 | Log.WriteLine("========================================================================"); | ||
69 | //Log.WriteLine("OpenSim " + VersionInfo.Version + " Started at " + DateTime.Now.ToString()); | ||
70 | break; | ||
71 | case ConsoleType.TCP: | ||
72 | break; | ||
73 | case ConsoleType.SimChat: | ||
74 | break; | ||
75 | |||
76 | default: | ||
77 | Console.WriteLine("ServerConsole.cs - what are you smoking? that isn't a valid console type!"); | ||
78 | break; | ||
79 | } | ||
80 | } | ||
81 | |||
82 | public override void Close() { | ||
83 | Log.WriteLine("OpenSim shutdown at " + DateTime.Now.ToString()); | ||
84 | Log.Close(); | ||
85 | } | ||
86 | |||
87 | public override void Write(string format, params object[] args) | ||
88 | { | ||
89 | Log.Write(format, args); | ||
90 | Console.Write(format, args); | ||
91 | return; | ||
92 | } | ||
93 | |||
94 | public override void WriteLine(string format, params object[] args) | ||
95 | { | ||
96 | Log.WriteLine(format, args); | ||
97 | Console.WriteLine(format, args); | ||
98 | return; | ||
99 | } | ||
100 | |||
101 | public override string ReadLine() | ||
102 | { | ||
103 | string TempStr=Console.ReadLine(); | ||
104 | Log.WriteLine(TempStr); | ||
105 | return TempStr; | ||
106 | } | ||
107 | |||
108 | public override int Read() { | ||
109 | int TempInt= Console.Read(); | ||
110 | Log.Write((char)TempInt); | ||
111 | return TempInt; | ||
112 | } | ||
113 | |||
114 | // Displays a command prompt and waits for the user to enter a string, then returns that string | ||
115 | public override string CmdPrompt(string prompt) { | ||
116 | this.Write(prompt); | ||
117 | return this.ReadLine(); | ||
118 | } | ||
119 | |||
120 | // Displays a command prompt and returns a default value if the user simply presses enter | ||
121 | public override string CmdPrompt(string prompt, string defaultresponse) { | ||
122 | string temp=CmdPrompt(prompt); | ||
123 | if(temp=="") { | ||
124 | return defaultresponse; | ||
125 | } else { | ||
126 | return temp; | ||
127 | } | ||
128 | } | ||
129 | |||
130 | // Displays a command prompt and returns a default value, user may only enter 1 of 2 options | ||
131 | public override string CmdPrompt(string prompt, string defaultresponse, string OptionA, string OptionB) { | ||
132 | bool itisdone=false; | ||
133 | string temp=CmdPrompt(prompt,defaultresponse); | ||
134 | while(itisdone==false) { | ||
135 | if((temp==OptionA) || (temp==OptionB)) { | ||
136 | itisdone=true; | ||
137 | } else { | ||
138 | this.WriteLine("Valid options are " + OptionA + " or " + OptionB); | ||
139 | temp=CmdPrompt(prompt,defaultresponse); | ||
140 | } | ||
141 | } | ||
142 | return temp; | ||
143 | } | ||
144 | |||
145 | // Runs a command with a number of parameters | ||
146 | public override Object RunCmd(string Cmd, string[] cmdparams) { | ||
147 | switch(Cmd) { | ||
148 | case "help": | ||
149 | this.WriteLine("show users - show info about connected users"); | ||
150 | this.WriteLine("shutdown - disconnect all clients and shutdown"); | ||
151 | this.WriteLine("regenerate - regenerate the sim's terrain"); | ||
152 | break; | ||
153 | |||
154 | case "show": | ||
155 | ShowCommands(cmdparams[0]); | ||
156 | break; | ||
157 | |||
158 | case "regenerate": | ||
159 | OpenSimRoot.Instance.LocalWorld.RegenerateTerrain(); | ||
160 | break; | ||
161 | |||
162 | case "shutdown": | ||
163 | OpenSimRoot.Instance.Shutdown(); | ||
164 | break; | ||
165 | } | ||
166 | return null; | ||
167 | } | ||
168 | |||
169 | // Shows data about something | ||
170 | public override void ShowCommands(string ShowWhat) { | ||
171 | switch(ShowWhat) { | ||
172 | case "uptime": | ||
173 | this.WriteLine("OpenSim has been running since " + OpenSimRoot.Instance.startuptime.ToString()); | ||
174 | this.WriteLine("That is " + (DateTime.Now-OpenSimRoot.Instance.startuptime).ToString()); | ||
175 | break; | ||
176 | case "users": | ||
177 | OpenSim.world.Avatar TempAv; | ||
178 | this.WriteLine(String.Format("{0,-16}{1,-16}{2,-25}{3,-25}{4,-16}{5,-16}","Firstname", "Lastname","Agent ID", "Session ID", "Circuit", "IP")); | ||
179 | foreach (libsecondlife.LLUUID UUID in OpenSimRoot.Instance.LocalWorld.Entities.Keys) { | ||
180 | if(OpenSimRoot.Instance.LocalWorld.Entities[UUID].ToString()== "OpenSim.world.Avatar") | ||
181 | { | ||
182 | TempAv=(OpenSim.world.Avatar)OpenSimRoot.Instance.LocalWorld.Entities[UUID]; | ||
183 | this.WriteLine(String.Format("{0,-16}{1,-16}{2,-25}{3,-25}{4,-16},{5,-16}",TempAv.firstname, TempAv.lastname,UUID, TempAv.ControllingClient.SessionID, TempAv.ControllingClient.CircuitCode, TempAv.ControllingClient.userEP.ToString())); | ||
184 | } | ||
185 | } | ||
186 | break; | ||
187 | } | ||
188 | } | ||
189 | |||
190 | // Displays a prompt to the user and then runs the command they entered | ||
191 | public override void MainConsolePrompt() { | ||
192 | string[] tempstrarray; | ||
193 | string tempstr = this.CmdPrompt("OpenSim-" + OpenSimRoot.Instance.Cfg.RegionHandle.ToString() + " # "); | ||
194 | tempstrarray = tempstr.Split(' '); | ||
195 | string cmd=tempstrarray[0]; | ||
196 | Array.Reverse(tempstrarray); | ||
197 | Array.Resize<string>(ref tempstrarray,tempstrarray.Length-1); | ||
198 | Array.Reverse(tempstrarray); | ||
199 | string[] cmdparams=(string[])tempstrarray; | ||
200 | RunCmd(cmd,cmdparams); | ||
201 | } | ||
202 | |||
203 | |||
204 | public override void SetStatus(string status) | ||
205 | { | ||
206 | Console.Write( status + "\r" ); | ||
207 | } | ||
208 | } | ||
209 | } | ||
210 | |||
211 | |||
diff --git a/OpenSim.RegionServer/UserServer/LocalUserProfileManager.cs b/OpenSim.RegionServer/UserServer/LocalUserProfileManager.cs new file mode 100644 index 0000000..83e340b --- /dev/null +++ b/OpenSim.RegionServer/UserServer/LocalUserProfileManager.cs | |||
@@ -0,0 +1,76 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Collections; | ||
4 | using System.Text; | ||
5 | using OpenSim.Framework.User; | ||
6 | using OpenSim.Framework.Grid; | ||
7 | using OpenSim.Framework.Inventory; | ||
8 | using OpenSim.Framework.Interfaces; | ||
9 | using libsecondlife; | ||
10 | |||
11 | namespace OpenSim.UserServer | ||
12 | { | ||
13 | class LocalUserProfileManager : UserProfileManager | ||
14 | { | ||
15 | private IGridServer _gridServer; | ||
16 | |||
17 | public LocalUserProfileManager(IGridServer gridServer) | ||
18 | { | ||
19 | _gridServer = gridServer; | ||
20 | } | ||
21 | |||
22 | public override void InitUserProfiles() | ||
23 | { | ||
24 | // TODO: need to load from database | ||
25 | } | ||
26 | |||
27 | public override void CustomiseResponse(ref System.Collections.Hashtable response, UserProfile theUser) | ||
28 | { | ||
29 | uint circode = (uint)response["circuit_code"]; | ||
30 | theUser.AddSimCircuit(circode, LLUUID.Random()); | ||
31 | response["home"] = "{'region_handle':[r" + (997 * 256).ToString() + ",r" + (996 * 256).ToString() + "], 'position':[r" + theUser.homepos.X.ToString() + ",r" + theUser.homepos.Y.ToString() + ",r" + theUser.homepos.Z.ToString() + "], 'look_at':[r" + theUser.homelookat.X.ToString() + ",r" + theUser.homelookat.Y.ToString() + ",r" + theUser.homelookat.Z.ToString() + "]}"; | ||
32 | response["sim_port"] = OpenSimRoot.Instance.Cfg.IPListenPort; | ||
33 | response["sim_ip"] = OpenSimRoot.Instance.Cfg.IPListenAddr; | ||
34 | response["region_y"] = (Int32)996 * 256; | ||
35 | response["region_x"] = (Int32)997* 256; | ||
36 | |||
37 | string first; | ||
38 | string last; | ||
39 | if (response.Contains("first")) | ||
40 | { | ||
41 | first = (string)response["first"]; | ||
42 | } | ||
43 | else | ||
44 | { | ||
45 | first = "test"; | ||
46 | } | ||
47 | |||
48 | if (response.Contains("last")) | ||
49 | { | ||
50 | last = (string)response["last"]; | ||
51 | } | ||
52 | else | ||
53 | { | ||
54 | last = "User"; | ||
55 | } | ||
56 | |||
57 | ArrayList InventoryList = (ArrayList)response["inventory-skeleton"]; | ||
58 | Hashtable Inventory1 = (Hashtable)InventoryList[0]; | ||
59 | |||
60 | Login _login = new Login(); | ||
61 | //copy data to login object | ||
62 | _login.First = first; | ||
63 | _login.Last = last; | ||
64 | _login.Agent = new LLUUID((string)response["agent_id"]) ; | ||
65 | _login.Session = new LLUUID((string)response["session_id"]); | ||
66 | _login.BaseFolder = null; | ||
67 | _login.InventoryFolder = new LLUUID((string)Inventory1["folder_id"]); | ||
68 | |||
69 | //working on local computer if so lets add to the gridserver's list of sessions? | ||
70 | if (OpenSimRoot.Instance.GridServers.GridServer.GetName() == "Local") | ||
71 | { | ||
72 | ((LocalGridBase)this._gridServer).AddNewSession(_login); | ||
73 | } | ||
74 | } | ||
75 | } | ||
76 | } | ||
diff --git a/OpenSim.RegionServer/UserServer/LoginServer.cs b/OpenSim.RegionServer/UserServer/LoginServer.cs new file mode 100644 index 0000000..86b098a --- /dev/null +++ b/OpenSim.RegionServer/UserServer/LoginServer.cs | |||
@@ -0,0 +1,414 @@ | |||
1 | /* | ||
2 | * Copyright (c) OpenSim project, http://sim.opensecondlife.org/ | ||
3 | * | ||
4 | * Redistribution and use in source and binary forms, with or without | ||
5 | * modification, are permitted provided that the following conditions are met: | ||
6 | * * Redistributions of source code must retain the above copyright | ||
7 | * notice, this list of conditions and the following disclaimer. | ||
8 | * * Redistributions in binary form must reproduce the above copyright | ||
9 | * notice, this list of conditions and the following disclaimer in the | ||
10 | * documentation and/or other materials provided with the distribution. | ||
11 | * * Neither the name of the <organization> nor the | ||
12 | * names of its contributors may be used to endorse or promote products | ||
13 | * derived from this software without specific prior written permission. | ||
14 | * | ||
15 | * THIS SOFTWARE IS PROVIDED BY <copyright holder> ``AS IS'' AND ANY | ||
16 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
17 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
18 | * DISCLAIMED. IN NO EVENT SHALL <copyright holder> BE LIABLE FOR ANY | ||
19 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
20 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
21 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
22 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
23 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
24 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
25 | * | ||
26 | */ | ||
27 | |||
28 | using Nwc.XmlRpc; | ||
29 | using System; | ||
30 | using System.IO; | ||
31 | using System.Net; | ||
32 | using System.Net.Sockets; | ||
33 | using System.Text; | ||
34 | using System.Text.RegularExpressions; | ||
35 | using System.Threading; | ||
36 | using System.Collections; | ||
37 | using System.Security.Cryptography; | ||
38 | using System.Xml; | ||
39 | using libsecondlife; | ||
40 | using OpenSim; | ||
41 | using OpenSim.Framework.Interfaces; | ||
42 | using OpenSim.Framework.Grid; | ||
43 | using OpenSim.Framework.Inventory; | ||
44 | using OpenSim.Framework.User; | ||
45 | using OpenSim.Framework.Utilities; | ||
46 | |||
47 | namespace OpenSim.UserServer | ||
48 | { | ||
49 | |||
50 | /// <summary> | ||
51 | /// When running in local (default) mode , handles client logins. | ||
52 | /// </summary> | ||
53 | public class LoginServer : LoginService , IUserServer | ||
54 | { | ||
55 | private IGridServer _gridServer; | ||
56 | private ushort _loginPort = 8080; | ||
57 | public IPAddress clientAddress = IPAddress.Loopback; | ||
58 | public IPAddress remoteAddress = IPAddress.Any; | ||
59 | private Socket loginServer; | ||
60 | private int NumClients; | ||
61 | private string _defaultResponse; | ||
62 | private bool userAccounts = false; | ||
63 | private string _mpasswd; | ||
64 | private bool _needPasswd = false; | ||
65 | private LocalUserProfileManager userManager; | ||
66 | |||
67 | public LoginServer(IGridServer gridServer) | ||
68 | { | ||
69 | _gridServer = gridServer; | ||
70 | } | ||
71 | |||
72 | // InitializeLogin: initialize the login | ||
73 | private void InitializeLogin() | ||
74 | { | ||
75 | this._needPasswd = false; | ||
76 | //read in default response string | ||
77 | StreamReader SR; | ||
78 | string lines; | ||
79 | SR = File.OpenText("new-login.dat"); | ||
80 | |||
81 | //lines=SR.ReadLine(); | ||
82 | |||
83 | while (!SR.EndOfStream) | ||
84 | { | ||
85 | lines = SR.ReadLine(); | ||
86 | _defaultResponse += lines; | ||
87 | //lines = SR.ReadLine(); | ||
88 | } | ||
89 | SR.Close(); | ||
90 | this._mpasswd = EncodePassword("testpass"); | ||
91 | |||
92 | userManager = new LocalUserProfileManager(this._gridServer); | ||
93 | userManager.InitUserProfiles(); | ||
94 | userManager.SetKeys("", "", "", "Welcome to OpenSim"); | ||
95 | |||
96 | loginServer = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); | ||
97 | loginServer.Bind(new IPEndPoint(remoteAddress, _loginPort)); | ||
98 | loginServer.Listen(1); | ||
99 | } | ||
100 | |||
101 | public void Startup() | ||
102 | { | ||
103 | this.InitializeLogin(); | ||
104 | Thread runLoginProxy = new Thread(new ThreadStart(RunLogin)); | ||
105 | runLoginProxy.IsBackground = true; | ||
106 | runLoginProxy.Start(); | ||
107 | } | ||
108 | |||
109 | private void RunLogin() | ||
110 | { | ||
111 | Console.WriteLine("Starting Login Server"); | ||
112 | try | ||
113 | { | ||
114 | for (; ; ) | ||
115 | { | ||
116 | Socket client = loginServer.Accept(); | ||
117 | IPEndPoint clientEndPoint = (IPEndPoint)client.RemoteEndPoint; | ||
118 | |||
119 | |||
120 | NetworkStream networkStream = new NetworkStream(client); | ||
121 | StreamReader networkReader = new StreamReader(networkStream); | ||
122 | StreamWriter networkWriter = new StreamWriter(networkStream); | ||
123 | |||
124 | try | ||
125 | { | ||
126 | LoginRequest(networkReader, networkWriter); | ||
127 | } | ||
128 | catch (Exception e) | ||
129 | { | ||
130 | Console.WriteLine(e.Message); | ||
131 | } | ||
132 | |||
133 | networkWriter.Close(); | ||
134 | networkReader.Close(); | ||
135 | networkStream.Close(); | ||
136 | |||
137 | client.Close(); | ||
138 | |||
139 | // send any packets queued for injection | ||
140 | |||
141 | } | ||
142 | } | ||
143 | catch (Exception e) | ||
144 | { | ||
145 | Console.WriteLine(e.Message); | ||
146 | Console.WriteLine(e.StackTrace); | ||
147 | } | ||
148 | } | ||
149 | |||
150 | // ProxyLogin: proxy a login request | ||
151 | private void LoginRequest(StreamReader reader, StreamWriter writer) | ||
152 | { | ||
153 | lock (this) | ||
154 | { | ||
155 | string line; | ||
156 | int contentLength = 0; | ||
157 | // read HTTP header | ||
158 | do | ||
159 | { | ||
160 | // read one line of the header | ||
161 | line = reader.ReadLine(); | ||
162 | |||
163 | // check for premature EOF | ||
164 | if (line == null) | ||
165 | throw new Exception("EOF in client HTTP header"); | ||
166 | |||
167 | // look for Content-Length | ||
168 | Match match = (new Regex(@"Content-Length: (\d+)$")).Match(line); | ||
169 | if (match.Success) | ||
170 | contentLength = Convert.ToInt32(match.Groups[1].Captures[0].ToString()); | ||
171 | } while (line != ""); | ||
172 | |||
173 | // read the HTTP body into a buffer | ||
174 | char[] content = new char[contentLength]; | ||
175 | reader.Read(content, 0, contentLength); | ||
176 | |||
177 | if (this.userAccounts) | ||
178 | { | ||
179 | //ask the UserProfile Manager to process the request | ||
180 | string reply = this.userManager.ParseXMLRPC(new String(content)); | ||
181 | // forward the XML-RPC response to the client | ||
182 | writer.WriteLine("HTTP/1.0 200 OK"); | ||
183 | writer.WriteLine("Content-type: text/xml"); | ||
184 | writer.WriteLine(); | ||
185 | writer.WriteLine(reply); | ||
186 | } | ||
187 | else | ||
188 | { | ||
189 | //handle ourselves | ||
190 | XmlRpcRequest request = (XmlRpcRequest)(new XmlRpcRequestDeserializer()).Deserialize(new String(content)); | ||
191 | if (request.MethodName == "login_to_simulator") | ||
192 | { | ||
193 | this.ProcessXmlRequest(request, writer); | ||
194 | } | ||
195 | else | ||
196 | { | ||
197 | XmlRpcResponse PresenceErrorResp = new XmlRpcResponse(); | ||
198 | Hashtable PresenceErrorRespData = new Hashtable(); | ||
199 | PresenceErrorRespData["reason"] = "XmlRequest"; ; | ||
200 | PresenceErrorRespData["message"] = "Unknown Rpc request"; | ||
201 | PresenceErrorRespData["login"] = "false"; | ||
202 | PresenceErrorResp.Value = PresenceErrorRespData; | ||
203 | string reply = Regex.Replace(XmlRpcResponseSerializer.Singleton.Serialize(PresenceErrorResp), " encoding=\"utf-16\"", ""); | ||
204 | writer.WriteLine("HTTP/1.0 200 OK"); | ||
205 | writer.WriteLine("Content-type: text/xml"); | ||
206 | writer.WriteLine(); | ||
207 | writer.WriteLine(reply); | ||
208 | } | ||
209 | } | ||
210 | } | ||
211 | } | ||
212 | |||
213 | public bool ProcessXmlRequest(XmlRpcRequest request, StreamWriter writer) | ||
214 | { | ||
215 | Hashtable requestData = (Hashtable)request.Params[0]; | ||
216 | string first; | ||
217 | string last; | ||
218 | string passwd; | ||
219 | LLUUID Agent; | ||
220 | LLUUID Session; | ||
221 | |||
222 | //get login name | ||
223 | if (requestData.Contains("first")) | ||
224 | { | ||
225 | first = (string)requestData["first"]; | ||
226 | } | ||
227 | else | ||
228 | { | ||
229 | first = "test"; | ||
230 | } | ||
231 | |||
232 | if (requestData.Contains("last")) | ||
233 | { | ||
234 | last = (string)requestData["last"]; | ||
235 | } | ||
236 | else | ||
237 | { | ||
238 | last = "User" + NumClients.ToString(); | ||
239 | } | ||
240 | |||
241 | if (requestData.Contains("passwd")) | ||
242 | { | ||
243 | passwd = (string)requestData["passwd"]; | ||
244 | } | ||
245 | else | ||
246 | { | ||
247 | passwd = "notfound"; | ||
248 | } | ||
249 | |||
250 | if (!Authenticate(first, last, passwd)) | ||
251 | { | ||
252 | XmlRpcResponse PresenceErrorResp = new XmlRpcResponse(); | ||
253 | Hashtable PresenceErrorRespData = new Hashtable(); | ||
254 | PresenceErrorRespData["reason"] = "key"; ; | ||
255 | PresenceErrorRespData["message"] = "You have entered an invalid name/password combination. Check Caps/lock."; | ||
256 | PresenceErrorRespData["login"] = "false"; | ||
257 | PresenceErrorResp.Value = PresenceErrorRespData; | ||
258 | string reply = Regex.Replace(XmlRpcResponseSerializer.Singleton.Serialize(PresenceErrorResp), " encoding=\"utf-16\"", ""); | ||
259 | writer.WriteLine("HTTP/1.0 200 OK"); | ||
260 | writer.WriteLine("Content-type: text/xml"); | ||
261 | writer.WriteLine(); | ||
262 | writer.WriteLine(reply); | ||
263 | return false; | ||
264 | } | ||
265 | |||
266 | NumClients++; | ||
267 | |||
268 | //create a agent and session LLUUID | ||
269 | Agent = GetAgentId(first, last); | ||
270 | int SessionRand = Util.RandomClass.Next(1, 999); | ||
271 | Session = new LLUUID("aaaabbbb-0200-" + SessionRand.ToString("0000") + "-8664-58f53e442797"); | ||
272 | LLUUID secureSess = LLUUID.Random(); | ||
273 | //create some login info | ||
274 | Hashtable LoginFlagsHash = new Hashtable(); | ||
275 | LoginFlagsHash["daylight_savings"] = "N"; | ||
276 | LoginFlagsHash["stipend_since_login"] = "N"; | ||
277 | LoginFlagsHash["gendered"] = "Y"; | ||
278 | LoginFlagsHash["ever_logged_in"] = "Y"; | ||
279 | ArrayList LoginFlags = new ArrayList(); | ||
280 | LoginFlags.Add(LoginFlagsHash); | ||
281 | |||
282 | Hashtable GlobalT = new Hashtable(); | ||
283 | GlobalT["sun_texture_id"] = "cce0f112-878f-4586-a2e2-a8f104bba271"; | ||
284 | GlobalT["cloud_texture_id"] = "fc4b9f0b-d008-45c6-96a4-01dd947ac621"; | ||
285 | GlobalT["moon_texture_id"] = "fc4b9f0b-d008-45c6-96a4-01dd947ac621"; | ||
286 | ArrayList GlobalTextures = new ArrayList(); | ||
287 | GlobalTextures.Add(GlobalT); | ||
288 | |||
289 | XmlRpcResponse response = (XmlRpcResponse)(new XmlRpcResponseDeserializer()).Deserialize(this._defaultResponse); | ||
290 | Hashtable responseData = (Hashtable)response.Value; | ||
291 | |||
292 | responseData["sim_port"] = OpenSimRoot.Instance.Cfg.IPListenPort; | ||
293 | responseData["sim_ip"] = OpenSimRoot.Instance.Cfg.IPListenAddr; | ||
294 | responseData["agent_id"] = Agent.ToStringHyphenated(); | ||
295 | responseData["session_id"] = Session.ToStringHyphenated(); | ||
296 | responseData["secure_session_id"]= secureSess.ToStringHyphenated(); | ||
297 | responseData["circuit_code"] = (Int32)(Util.RandomClass.Next()); | ||
298 | responseData["seconds_since_epoch"] = (Int32)(DateTime.UtcNow - new DateTime(1970, 1, 1)).TotalSeconds; | ||
299 | responseData["login-flags"] = LoginFlags; | ||
300 | responseData["global-textures"] = GlobalTextures; | ||
301 | |||
302 | //inventory | ||
303 | ArrayList InventoryList = (ArrayList)responseData["inventory-skeleton"]; | ||
304 | Hashtable Inventory1 = (Hashtable)InventoryList[0]; | ||
305 | Hashtable Inventory2 = (Hashtable)InventoryList[1]; | ||
306 | LLUUID BaseFolderID = LLUUID.Random(); | ||
307 | LLUUID InventoryFolderID = LLUUID.Random(); | ||
308 | Inventory2["name"] = "Base"; | ||
309 | Inventory2["folder_id"] = BaseFolderID.ToStringHyphenated(); | ||
310 | Inventory2["type_default"] = 0; | ||
311 | Inventory1["folder_id"] = InventoryFolderID.ToStringHyphenated(); | ||
312 | |||
313 | ArrayList InventoryRoot = (ArrayList)responseData["inventory-root"]; | ||
314 | Hashtable Inventoryroot = (Hashtable)InventoryRoot[0]; | ||
315 | Inventoryroot["folder_id"] = InventoryFolderID.ToStringHyphenated(); | ||
316 | |||
317 | CustomiseLoginResponse(responseData, first, last); | ||
318 | |||
319 | Login _login = new Login(); | ||
320 | //copy data to login object | ||
321 | _login.First = first; | ||
322 | _login.Last = last; | ||
323 | _login.Agent = Agent; | ||
324 | _login.Session = Session; | ||
325 | _login.SecureSession = secureSess; | ||
326 | _login.BaseFolder = BaseFolderID; | ||
327 | _login.InventoryFolder = InventoryFolderID; | ||
328 | |||
329 | //working on local computer if so lets add to the gridserver's list of sessions? | ||
330 | if (OpenSimRoot.Instance.GridServers.GridServer.GetName() == "Local") | ||
331 | { | ||
332 | ((LocalGridBase)this._gridServer).AddNewSession(_login); | ||
333 | } | ||
334 | |||
335 | // forward the XML-RPC response to the client | ||
336 | writer.WriteLine("HTTP/1.0 200 OK"); | ||
337 | writer.WriteLine("Content-type: text/xml"); | ||
338 | writer.WriteLine(); | ||
339 | |||
340 | XmlTextWriter responseWriter = new XmlTextWriter(writer); | ||
341 | XmlRpcResponseSerializer.Singleton.Serialize(responseWriter, response); | ||
342 | responseWriter.Close(); | ||
343 | |||
344 | return true; | ||
345 | } | ||
346 | |||
347 | protected virtual void CustomiseLoginResponse(Hashtable responseData, string first, string last) | ||
348 | { | ||
349 | } | ||
350 | |||
351 | protected virtual LLUUID GetAgentId(string firstName, string lastName) | ||
352 | { | ||
353 | LLUUID Agent; | ||
354 | int AgentRand = Util.RandomClass.Next(1, 9999); | ||
355 | Agent = new LLUUID("99998888-0100-" + AgentRand.ToString("0000") + "-8ec1-0b1d5cd6aead"); | ||
356 | return Agent; | ||
357 | } | ||
358 | |||
359 | protected virtual bool Authenticate(string first, string last, string passwd) | ||
360 | { | ||
361 | if (this._needPasswd) | ||
362 | { | ||
363 | //every user needs the password to login | ||
364 | string encodedPass = passwd.Remove(0, 3); //remove $1$ | ||
365 | if (encodedPass == this._mpasswd) | ||
366 | { | ||
367 | return true; | ||
368 | } | ||
369 | else | ||
370 | { | ||
371 | return false; | ||
372 | } | ||
373 | } | ||
374 | else | ||
375 | { | ||
376 | //do not need password to login | ||
377 | return true; | ||
378 | } | ||
379 | } | ||
380 | |||
381 | private static string EncodePassword(string passwd) | ||
382 | { | ||
383 | Byte[] originalBytes; | ||
384 | Byte[] encodedBytes; | ||
385 | MD5 md5; | ||
386 | |||
387 | md5 = new MD5CryptoServiceProvider(); | ||
388 | originalBytes = ASCIIEncoding.Default.GetBytes(passwd); | ||
389 | encodedBytes = md5.ComputeHash(originalBytes); | ||
390 | |||
391 | return Regex.Replace(BitConverter.ToString(encodedBytes), "-", "").ToLower(); | ||
392 | } | ||
393 | |||
394 | //IUserServer implementation | ||
395 | public AgentInventory RequestAgentsInventory(LLUUID agentID) | ||
396 | { | ||
397 | AgentInventory aInventory = null; | ||
398 | if (this.userAccounts) | ||
399 | { | ||
400 | aInventory = this.userManager.GetUsersInventory(agentID); | ||
401 | } | ||
402 | |||
403 | return aInventory; | ||
404 | } | ||
405 | |||
406 | public void SetServerInfo(string ServerUrl, string SendKey, string RecvKey) | ||
407 | { | ||
408 | |||
409 | } | ||
410 | |||
411 | } | ||
412 | |||
413 | |||
414 | } | ||
diff --git a/OpenSim.RegionServer/VersionInfo.cs b/OpenSim.RegionServer/VersionInfo.cs new file mode 100644 index 0000000..39767df --- /dev/null +++ b/OpenSim.RegionServer/VersionInfo.cs | |||
@@ -0,0 +1,37 @@ | |||
1 | /* | ||
2 | Copyright (c) OpenSim project, http://osgrid.org/ | ||
3 | * | ||
4 | * Redistribution and use in source and binary forms, with or without | ||
5 | * modification, are permitted provided that the following conditions are met: | ||
6 | * * Redistributions of source code must retain the above copyright | ||
7 | * notice, this list of conditions and the following disclaimer. | ||
8 | * * Redistributions in binary form must reproduce the above copyright | ||
9 | * notice, this list of conditions and the following disclaimer in the | ||
10 | * documentation and/or other materials provided with the distribution. | ||
11 | * * Neither the name of the <organization> nor the | ||
12 | * names of its contributors may be used to endorse or promote products | ||
13 | * derived from this software without specific prior written permission. | ||
14 | * | ||
15 | * THIS SOFTWARE IS PROVIDED BY <copyright holder> ``AS IS'' AND ANY | ||
16 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
17 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
18 | * DISCLAIMED. IN NO EVENT SHALL <copyright holder> BE LIABLE FOR ANY | ||
19 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
20 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
21 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
22 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
23 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
24 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
25 | */ | ||
26 | |||
27 | using System; | ||
28 | |||
29 | namespace OpenSim | ||
30 | { | ||
31 | /// <summary> | ||
32 | /// </summary> | ||
33 | public class VersionInfo | ||
34 | { | ||
35 | public static string Version = "0.1, Build 1173843165, Revision 193:206M"; | ||
36 | } | ||
37 | } | ||
diff --git a/OpenSim.RegionServer/types/Mesh.cs b/OpenSim.RegionServer/types/Mesh.cs new file mode 100644 index 0000000..3e00c91 --- /dev/null +++ b/OpenSim.RegionServer/types/Mesh.cs | |||
@@ -0,0 +1,28 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Text; | ||
4 | |||
5 | namespace OpenSim.types | ||
6 | { | ||
7 | // TODO: This will need some performance tuning no doubt. | ||
8 | public class Mesh | ||
9 | { | ||
10 | public List<Triangle> mesh; | ||
11 | |||
12 | public Mesh() | ||
13 | { | ||
14 | mesh = new List<Triangle>(); | ||
15 | } | ||
16 | |||
17 | public void AddTri(Triangle tri) | ||
18 | { | ||
19 | mesh.Add(tri); | ||
20 | } | ||
21 | |||
22 | public static Mesh operator +(Mesh a, Mesh b) | ||
23 | { | ||
24 | a.mesh.AddRange(b.mesh); | ||
25 | return a; | ||
26 | } | ||
27 | } | ||
28 | } | ||
diff --git a/OpenSim.RegionServer/types/Triangle.cs b/OpenSim.RegionServer/types/Triangle.cs new file mode 100644 index 0000000..8dfea6e --- /dev/null +++ b/OpenSim.RegionServer/types/Triangle.cs | |||
@@ -0,0 +1,28 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Text; | ||
4 | using Axiom.MathLib; | ||
5 | |||
6 | namespace OpenSim.types | ||
7 | { | ||
8 | public class Triangle | ||
9 | { | ||
10 | Vector3 a; | ||
11 | Vector3 b; | ||
12 | Vector3 c; | ||
13 | |||
14 | public Triangle() | ||
15 | { | ||
16 | a = new Vector3(); | ||
17 | b = new Vector3(); | ||
18 | c = new Vector3(); | ||
19 | } | ||
20 | |||
21 | public Triangle(Vector3 A, Vector3 B, Vector3 C) | ||
22 | { | ||
23 | a = A; | ||
24 | b = B; | ||
25 | c = C; | ||
26 | } | ||
27 | } | ||
28 | } | ||
diff --git a/OpenSim.RegionServer/world/Avatar.cs b/OpenSim.RegionServer/world/Avatar.cs new file mode 100644 index 0000000..b4a3b82 --- /dev/null +++ b/OpenSim.RegionServer/world/Avatar.cs | |||
@@ -0,0 +1,501 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.IO; | ||
4 | using System.Text; | ||
5 | using libsecondlife; | ||
6 | using libsecondlife.Packets; | ||
7 | using OpenSim.Physics.Manager; | ||
8 | using Axiom.MathLib; | ||
9 | |||
10 | namespace OpenSim.world | ||
11 | { | ||
12 | public class Avatar : Entity | ||
13 | { | ||
14 | public static bool PhysicsEngineFlying = false; | ||
15 | public string firstname; | ||
16 | public string lastname; | ||
17 | public SimClient ControllingClient; | ||
18 | private PhysicsActor _physActor; | ||
19 | private static libsecondlife.Packets.ObjectUpdatePacket.ObjectDataBlock AvatarTemplate; | ||
20 | private bool updateflag = false; | ||
21 | private byte movementflag = 0; | ||
22 | private List<NewForce> forcesList = new List<NewForce>(); | ||
23 | private short _updateCount = 0; | ||
24 | private Axiom.MathLib.Quaternion bodyRot; | ||
25 | |||
26 | public Avatar(SimClient TheClient) | ||
27 | { | ||
28 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Avatar.cs - Loading details from grid (DUMMY)"); | ||
29 | ControllingClient = TheClient; | ||
30 | localid = 8880000 + (OpenSimRoot.Instance.LocalWorld._localNumber++); | ||
31 | position = new LLVector3(100.0f, 100.0f, 30.0f); | ||
32 | position.Z = OpenSimRoot.Instance.LocalWorld.LandMap[(int)position.Y * 256 + (int)position.X] + 1; | ||
33 | } | ||
34 | |||
35 | public PhysicsActor PhysActor | ||
36 | { | ||
37 | set | ||
38 | { | ||
39 | this._physActor = value; | ||
40 | } | ||
41 | } | ||
42 | |||
43 | public override void addForces() | ||
44 | { | ||
45 | lock (this.forcesList) | ||
46 | { | ||
47 | if (this.forcesList.Count > 0) | ||
48 | { | ||
49 | for (int i = 0; i < this.forcesList.Count; i++) | ||
50 | { | ||
51 | NewForce force = this.forcesList[i]; | ||
52 | PhysicsVector phyVector = new PhysicsVector(force.X, force.Y, force.Z); | ||
53 | this._physActor.Velocity = phyVector; | ||
54 | this.updateflag = true; | ||
55 | this.velocity = new LLVector3(force.X, force.Y, force.Z); //shouldn't really be doing this | ||
56 | // but as we are setting the velocity (rather than using real forces) at the moment it is okay. | ||
57 | } | ||
58 | for (int i = 0; i < this.forcesList.Count; i++) | ||
59 | { | ||
60 | this.forcesList.RemoveAt(0); | ||
61 | } | ||
62 | } | ||
63 | } | ||
64 | } | ||
65 | |||
66 | public override void update() | ||
67 | { | ||
68 | |||
69 | if (this.updateflag) | ||
70 | { | ||
71 | //need to send movement info | ||
72 | //so create the improvedterseobjectupdate packet | ||
73 | //use CreateTerseBlock() | ||
74 | ImprovedTerseObjectUpdatePacket.ObjectDataBlock terseBlock = CreateTerseBlock(); | ||
75 | ImprovedTerseObjectUpdatePacket terse = new ImprovedTerseObjectUpdatePacket(); | ||
76 | terse.RegionData.RegionHandle = OpenSimRoot.Instance.Cfg.RegionHandle; // FIXME | ||
77 | terse.RegionData.TimeDilation = 64096; | ||
78 | terse.ObjectData = new ImprovedTerseObjectUpdatePacket.ObjectDataBlock[1]; | ||
79 | terse.ObjectData[0] = terseBlock; | ||
80 | foreach (SimClient client in OpenSimRoot.Instance.ClientThreads.Values) | ||
81 | { | ||
82 | client.OutPacket(terse); | ||
83 | } | ||
84 | |||
85 | updateflag = false; | ||
86 | //this._updateCount = 0; | ||
87 | } | ||
88 | else | ||
89 | { | ||
90 | //if((movementflag & 1) !=0) | ||
91 | //{ | ||
92 | _updateCount++; | ||
93 | if (((!PhysicsEngineFlying) && (_updateCount > 3)) || (_updateCount > 0)) | ||
94 | { | ||
95 | //It has been a while since last update was sent so lets send one. | ||
96 | ImprovedTerseObjectUpdatePacket.ObjectDataBlock terseBlock = CreateTerseBlock(); | ||
97 | ImprovedTerseObjectUpdatePacket terse = new ImprovedTerseObjectUpdatePacket(); | ||
98 | terse.RegionData.RegionHandle = OpenSimRoot.Instance.Cfg.RegionHandle; // FIXME | ||
99 | terse.RegionData.TimeDilation = 64096; | ||
100 | terse.ObjectData = new ImprovedTerseObjectUpdatePacket.ObjectDataBlock[1]; | ||
101 | terse.ObjectData[0] = terseBlock; | ||
102 | foreach (SimClient client in OpenSimRoot.Instance.ClientThreads.Values) | ||
103 | { | ||
104 | client.OutPacket(terse); | ||
105 | } | ||
106 | _updateCount = 0; | ||
107 | } | ||
108 | //} | ||
109 | } | ||
110 | } | ||
111 | |||
112 | public static void SetupTemplate(string name) | ||
113 | { | ||
114 | int i = 0; | ||
115 | FileInfo fInfo = new FileInfo(name); | ||
116 | long numBytes = fInfo.Length; | ||
117 | FileStream fStream = new FileStream(name, FileMode.Open, FileAccess.Read); | ||
118 | BinaryReader br = new BinaryReader(fStream); | ||
119 | byte[] data1 = br.ReadBytes((int)numBytes); | ||
120 | br.Close(); | ||
121 | fStream.Close(); | ||
122 | |||
123 | libsecondlife.Packets.ObjectUpdatePacket.ObjectDataBlock objdata = new libsecondlife.Packets.ObjectUpdatePacket.ObjectDataBlock(data1, ref i); | ||
124 | |||
125 | System.Text.Encoding enc = System.Text.Encoding.ASCII; | ||
126 | libsecondlife.LLVector3 pos = new LLVector3(objdata.ObjectData, 16); | ||
127 | pos.X = 100f; | ||
128 | objdata.ID = 8880000; | ||
129 | objdata.NameValue = enc.GetBytes("FirstName STRING RW SV Test \nLastName STRING RW SV User \0"); | ||
130 | libsecondlife.LLVector3 pos2 = new LLVector3(100f, 100f, 23f); | ||
131 | //objdata.FullID=user.AgentID; | ||
132 | byte[] pb = pos.GetBytes(); | ||
133 | Array.Copy(pb, 0, objdata.ObjectData, 16, pb.Length); | ||
134 | |||
135 | Avatar.AvatarTemplate = objdata; | ||
136 | } | ||
137 | |||
138 | public void CompleteMovement(World RegionInfo) | ||
139 | { | ||
140 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Avatar.cs:CompleteMovement() - Constructing AgentMovementComplete packet"); | ||
141 | AgentMovementCompletePacket mov = new AgentMovementCompletePacket(); | ||
142 | mov.AgentData.SessionID = this.ControllingClient.SessionID; | ||
143 | mov.AgentData.AgentID = this.ControllingClient.AgentID; | ||
144 | mov.Data.RegionHandle = OpenSimRoot.Instance.Cfg.RegionHandle; | ||
145 | // TODO - dynamicalise this stuff | ||
146 | mov.Data.Timestamp = 1172750370; | ||
147 | mov.Data.Position = new LLVector3(100f, 100f, 23f); | ||
148 | mov.Data.LookAt = new LLVector3(0.99f, 0.042f, 0); | ||
149 | |||
150 | ControllingClient.OutPacket(mov); | ||
151 | } | ||
152 | |||
153 | public void SendInitialPosition() | ||
154 | { | ||
155 | |||
156 | System.Text.Encoding _enc = System.Text.Encoding.ASCII; | ||
157 | //send a objectupdate packet with information about the clients avatar | ||
158 | ObjectUpdatePacket objupdate = new ObjectUpdatePacket(); | ||
159 | objupdate.RegionData.RegionHandle = OpenSimRoot.Instance.Cfg.RegionHandle; | ||
160 | objupdate.RegionData.TimeDilation = 64096; | ||
161 | objupdate.ObjectData = new libsecondlife.Packets.ObjectUpdatePacket.ObjectDataBlock[1]; | ||
162 | |||
163 | objupdate.ObjectData[0] = AvatarTemplate; | ||
164 | //give this avatar object a local id and assign the user a name | ||
165 | objupdate.ObjectData[0].ID = this.localid; | ||
166 | this.uuid = objupdate.ObjectData[0].FullID = ControllingClient.AgentID; | ||
167 | objupdate.ObjectData[0].NameValue = _enc.GetBytes("FirstName STRING RW SV " + firstname + "\nLastName STRING RW SV " + lastname + " \0"); | ||
168 | |||
169 | libsecondlife.LLVector3 pos2 = new LLVector3((float)this.position.X, (float)this.position.Y, (float)this.position.Z); | ||
170 | |||
171 | byte[] pb = pos2.GetBytes(); | ||
172 | |||
173 | Array.Copy(pb, 0, objupdate.ObjectData[0].ObjectData, 16, pb.Length); | ||
174 | OpenSimRoot.Instance.LocalWorld._localNumber++; | ||
175 | |||
176 | foreach (SimClient client in OpenSimRoot.Instance.ClientThreads.Values) | ||
177 | { | ||
178 | client.OutPacket(objupdate); | ||
179 | if (client.AgentID != ControllingClient.AgentID) | ||
180 | { | ||
181 | SendAppearanceToOtherAgent(client); | ||
182 | } | ||
183 | } | ||
184 | //this.ControllingClient.OutPacket(objupdate); | ||
185 | } | ||
186 | |||
187 | public void SendInitialAppearance() | ||
188 | { | ||
189 | AgentWearablesUpdatePacket aw = new AgentWearablesUpdatePacket(); | ||
190 | aw.AgentData.AgentID = this.ControllingClient.AgentID; | ||
191 | aw.AgentData.SerialNum = 0; | ||
192 | aw.AgentData.SessionID = ControllingClient.SessionID; | ||
193 | |||
194 | aw.WearableData = new AgentWearablesUpdatePacket.WearableDataBlock[13]; | ||
195 | AgentWearablesUpdatePacket.WearableDataBlock awb = new AgentWearablesUpdatePacket.WearableDataBlock(); | ||
196 | awb.WearableType = (byte)0; | ||
197 | awb.AssetID = new LLUUID("66c41e39-38f9-f75a-024e-585989bfab73"); | ||
198 | awb.ItemID = LLUUID.Random(); | ||
199 | aw.WearableData[0] = awb; | ||
200 | |||
201 | for (int i = 1; i < 13; i++) | ||
202 | { | ||
203 | awb = new AgentWearablesUpdatePacket.WearableDataBlock(); | ||
204 | awb.WearableType = (byte)i; | ||
205 | awb.AssetID = new LLUUID("00000000-0000-0000-0000-000000000000"); | ||
206 | awb.ItemID = new LLUUID("00000000-0000-0000-0000-000000000000"); | ||
207 | aw.WearableData[i] = awb; | ||
208 | } | ||
209 | |||
210 | ControllingClient.OutPacket(aw); | ||
211 | } | ||
212 | |||
213 | public ObjectUpdatePacket CreateUpdatePacket() | ||
214 | { | ||
215 | System.Text.Encoding _enc = System.Text.Encoding.ASCII; | ||
216 | //send a objectupdate packet with information about the clients avatar | ||
217 | ObjectUpdatePacket objupdate = new ObjectUpdatePacket(); | ||
218 | objupdate.RegionData.RegionHandle = OpenSimRoot.Instance.Cfg.RegionHandle; | ||
219 | objupdate.RegionData.TimeDilation = 64096; | ||
220 | objupdate.ObjectData = new libsecondlife.Packets.ObjectUpdatePacket.ObjectDataBlock[1]; | ||
221 | |||
222 | objupdate.ObjectData[0] = AvatarTemplate; | ||
223 | //give this avatar object a local id and assign the user a name | ||
224 | objupdate.ObjectData[0].ID = this.localid; | ||
225 | objupdate.ObjectData[0].FullID = ControllingClient.AgentID; | ||
226 | objupdate.ObjectData[0].NameValue = _enc.GetBytes("FirstName STRING RW SV " + firstname + "\nLastName STRING RW SV " + lastname + " \0"); | ||
227 | |||
228 | libsecondlife.LLVector3 pos2 = new LLVector3((float)this._physActor.Position.X, (float)this._physActor.Position.Y, (float)this._physActor.Position.Z); | ||
229 | |||
230 | byte[] pb = pos2.GetBytes(); | ||
231 | |||
232 | Array.Copy(pb, 0, objupdate.ObjectData[0].ObjectData, 16, pb.Length); | ||
233 | return objupdate; | ||
234 | } | ||
235 | |||
236 | public void SendAppearanceToOtherAgent(SimClient userInfo) | ||
237 | { | ||
238 | AvatarAppearancePacket avp = new AvatarAppearancePacket(); | ||
239 | |||
240 | |||
241 | avp.VisualParam = new AvatarAppearancePacket.VisualParamBlock[218]; | ||
242 | //avp.ObjectData.TextureEntry=this.avatar_template.TextureEntry;// br.ReadBytes((int)numBytes); | ||
243 | |||
244 | LLObject.TextureEntry ntex = new LLObject.TextureEntry(new LLUUID("00000000-0000-0000-0000-000000000005")); | ||
245 | avp.ObjectData.TextureEntry = ntex.ToBytes(); | ||
246 | |||
247 | AvatarAppearancePacket.VisualParamBlock avblock = null; | ||
248 | for (int i = 0; i < 218; i++) | ||
249 | { | ||
250 | avblock = new AvatarAppearancePacket.VisualParamBlock(); | ||
251 | avblock.ParamValue = (byte)100; | ||
252 | avp.VisualParam[i] = avblock; | ||
253 | } | ||
254 | |||
255 | avp.Sender.IsTrial = false; | ||
256 | avp.Sender.ID = ControllingClient.AgentID; | ||
257 | userInfo.OutPacket(avp); | ||
258 | |||
259 | } | ||
260 | |||
261 | public void HandleUpdate(AgentUpdatePacket pack) | ||
262 | { | ||
263 | if (((uint)pack.AgentData.ControlFlags & (uint)MainAvatar.AgentUpdateFlags.AGENT_CONTROL_FLY) != 0) | ||
264 | { | ||
265 | this._physActor.Flying = true; | ||
266 | } | ||
267 | else | ||
268 | { | ||
269 | this._physActor.Flying = false; | ||
270 | } | ||
271 | if (((uint)pack.AgentData.ControlFlags & (uint)MainAvatar.AgentUpdateFlags.AGENT_CONTROL_AT_POS) != 0) | ||
272 | { | ||
273 | Axiom.MathLib.Quaternion q = new Axiom.MathLib.Quaternion(pack.AgentData.BodyRotation.W, pack.AgentData.BodyRotation.X, pack.AgentData.BodyRotation.Y, pack.AgentData.BodyRotation.Z); | ||
274 | if (((movementflag & 1) == 0) || (q != this.bodyRot)) | ||
275 | { | ||
276 | //we should add a new force to the list | ||
277 | // but for now we will deal with velocities | ||
278 | NewForce newVelocity = new NewForce(); | ||
279 | Axiom.MathLib.Vector3 v3 = new Axiom.MathLib.Vector3(1, 0, 0); | ||
280 | Axiom.MathLib.Vector3 direc = q * v3; | ||
281 | direc.Normalize(); | ||
282 | |||
283 | //work out velocity for sim physics system | ||
284 | direc = direc * ((0.03f) * 128f); | ||
285 | if (this._physActor.Flying) | ||
286 | direc *= 2; | ||
287 | |||
288 | newVelocity.X = direc.x; | ||
289 | newVelocity.Y = direc.y; | ||
290 | newVelocity.Z = direc.z; | ||
291 | this.forcesList.Add(newVelocity); | ||
292 | movementflag = 1; | ||
293 | this.bodyRot = q; | ||
294 | } | ||
295 | } | ||
296 | else if ((((uint)pack.AgentData.ControlFlags & (uint)MainAvatar.AgentUpdateFlags.AGENT_CONTROL_UP_POS) != 0) && (PhysicsEngineFlying)) | ||
297 | { | ||
298 | if (((movementflag & 2) == 0) && this._physActor.Flying) | ||
299 | { | ||
300 | //we should add a new force to the list | ||
301 | // but for now we will deal with velocities | ||
302 | NewForce newVelocity = new NewForce(); | ||
303 | Axiom.MathLib.Vector3 v3 = new Axiom.MathLib.Vector3(0, 0, 1); | ||
304 | Axiom.MathLib.Vector3 direc = v3; | ||
305 | direc.Normalize(); | ||
306 | |||
307 | //work out velocity for sim physics system | ||
308 | direc = direc * ((0.03f) * 128f * 2); | ||
309 | newVelocity.X = direc.x; | ||
310 | newVelocity.Y = direc.y; | ||
311 | newVelocity.Z = direc.z; | ||
312 | this.forcesList.Add(newVelocity); | ||
313 | movementflag = 2; | ||
314 | } | ||
315 | } | ||
316 | else if ((((uint)pack.AgentData.ControlFlags & (uint)MainAvatar.AgentUpdateFlags.AGENT_CONTROL_UP_NEG) != 0) && (PhysicsEngineFlying)) | ||
317 | { | ||
318 | if (((movementflag & 4) == 0) && this._physActor.Flying) | ||
319 | { | ||
320 | //we should add a new force to the list | ||
321 | // but for now we will deal with velocities | ||
322 | NewForce newVelocity = new NewForce(); | ||
323 | Axiom.MathLib.Vector3 v3 = new Axiom.MathLib.Vector3(0, 0, -1); | ||
324 | //Axiom.MathLib.Quaternion q = new Axiom.MathLib.Quaternion(pack.AgentData.BodyRotation.W, pack.AgentData.BodyRotation.X, pack.AgentData.BodyRotation.Y, pack.AgentData.BodyRotation.Z); | ||
325 | Axiom.MathLib.Vector3 direc = v3; | ||
326 | direc.Normalize(); | ||
327 | |||
328 | //work out velocity for sim physics system | ||
329 | direc = direc * ((0.03f) * 128f * 2); | ||
330 | newVelocity.X = direc.x; | ||
331 | newVelocity.Y = direc.y; | ||
332 | newVelocity.Z = direc.z; | ||
333 | this.forcesList.Add(newVelocity); | ||
334 | movementflag = 4; | ||
335 | } | ||
336 | } | ||
337 | else if (((uint)pack.AgentData.ControlFlags & (uint)MainAvatar.AgentUpdateFlags.AGENT_CONTROL_AT_NEG) != 0) | ||
338 | { | ||
339 | Axiom.MathLib.Quaternion q = new Axiom.MathLib.Quaternion(pack.AgentData.BodyRotation.W, pack.AgentData.BodyRotation.X, pack.AgentData.BodyRotation.Y, pack.AgentData.BodyRotation.Z); | ||
340 | if (((movementflag & 8) == 0) || (q != this.bodyRot)) | ||
341 | { | ||
342 | //we should add a new force to the list | ||
343 | // but for now we will deal with velocities | ||
344 | NewForce newVelocity = new NewForce(); | ||
345 | Axiom.MathLib.Vector3 v3 = new Axiom.MathLib.Vector3(-1, 0, 0); | ||
346 | Axiom.MathLib.Vector3 direc = q * v3; | ||
347 | direc.Normalize(); | ||
348 | |||
349 | //work out velocity for sim physics system | ||
350 | direc = direc * ((0.03f) * 128f); | ||
351 | if (this._physActor.Flying) | ||
352 | direc *= 2; | ||
353 | |||
354 | newVelocity.X = direc.x; | ||
355 | newVelocity.Y = direc.y; | ||
356 | newVelocity.Z = direc.z; | ||
357 | this.forcesList.Add(newVelocity); | ||
358 | movementflag = 8; | ||
359 | this.bodyRot = q; | ||
360 | } | ||
361 | } | ||
362 | else | ||
363 | { | ||
364 | if ((movementflag) != 0) | ||
365 | { | ||
366 | NewForce newVelocity = new NewForce(); | ||
367 | newVelocity.X = 0; | ||
368 | newVelocity.Y = 0; | ||
369 | newVelocity.Z = 0; | ||
370 | this.forcesList.Add(newVelocity); | ||
371 | movementflag = 0; | ||
372 | } | ||
373 | } | ||
374 | } | ||
375 | |||
376 | //should be moved somewhere else | ||
377 | public void SendRegionHandshake(World RegionInfo) | ||
378 | { | ||
379 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Avatar.cs:SendRegionHandshake() - Creating empty RegionHandshake packet"); | ||
380 | System.Text.Encoding _enc = System.Text.Encoding.ASCII; | ||
381 | RegionHandshakePacket handshake = new RegionHandshakePacket(); | ||
382 | |||
383 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Avatar.cs:SendRegionhandshake() - Filling in RegionHandshake details"); | ||
384 | handshake.RegionInfo.BillableFactor = 0; | ||
385 | handshake.RegionInfo.IsEstateManager = false; | ||
386 | handshake.RegionInfo.TerrainHeightRange00 = 60; | ||
387 | handshake.RegionInfo.TerrainHeightRange01 = 60; | ||
388 | handshake.RegionInfo.TerrainHeightRange10 = 60; | ||
389 | handshake.RegionInfo.TerrainHeightRange11 = 60; | ||
390 | handshake.RegionInfo.TerrainStartHeight00 = 10; | ||
391 | handshake.RegionInfo.TerrainStartHeight01 = 10; | ||
392 | handshake.RegionInfo.TerrainStartHeight10 = 10; | ||
393 | handshake.RegionInfo.TerrainStartHeight11 = 10; | ||
394 | handshake.RegionInfo.SimAccess = 13; | ||
395 | handshake.RegionInfo.WaterHeight = 20; | ||
396 | handshake.RegionInfo.RegionFlags = 72458694; | ||
397 | handshake.RegionInfo.SimName = _enc.GetBytes(OpenSimRoot.Instance.Cfg.RegionName + "\0"); | ||
398 | handshake.RegionInfo.SimOwner = new LLUUID("00000000-0000-0000-0000-000000000000"); | ||
399 | handshake.RegionInfo.TerrainBase0 = new LLUUID("b8d3965a-ad78-bf43-699b-bff8eca6c975"); | ||
400 | handshake.RegionInfo.TerrainBase1 = new LLUUID("abb783e6-3e93-26c0-248a-247666855da3"); | ||
401 | handshake.RegionInfo.TerrainBase2 = new LLUUID("179cdabd-398a-9b6b-1391-4dc333ba321f"); | ||
402 | handshake.RegionInfo.TerrainBase3 = new LLUUID("beb169c7-11ea-fff2-efe5-0f24dc881df2"); | ||
403 | handshake.RegionInfo.TerrainDetail0 = new LLUUID("00000000-0000-0000-0000-000000000000"); | ||
404 | handshake.RegionInfo.TerrainDetail1 = new LLUUID("00000000-0000-0000-0000-000000000000"); | ||
405 | handshake.RegionInfo.TerrainDetail2 = new LLUUID("00000000-0000-0000-0000-000000000000"); | ||
406 | handshake.RegionInfo.TerrainDetail3 = new LLUUID("00000000-0000-0000-0000-000000000000"); | ||
407 | handshake.RegionInfo.CacheID = new LLUUID("545ec0a5-5751-1026-8a0b-216e38a7ab37"); | ||
408 | |||
409 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Avatar.cs:SendRegionHandshake() - Sending RegionHandshake packet"); | ||
410 | this.ControllingClient.OutPacket(handshake); | ||
411 | } | ||
412 | |||
413 | public ImprovedTerseObjectUpdatePacket.ObjectDataBlock CreateTerseBlock() | ||
414 | { | ||
415 | byte[] bytes = new byte[60]; | ||
416 | int i = 0; | ||
417 | ImprovedTerseObjectUpdatePacket.ObjectDataBlock dat = new ImprovedTerseObjectUpdatePacket.ObjectDataBlock(); | ||
418 | |||
419 | dat.TextureEntry = AvatarTemplate.TextureEntry; | ||
420 | libsecondlife.LLVector3 pos2 = new LLVector3(this._physActor.Position.X, this._physActor.Position.Y, this._physActor.Position.Z); | ||
421 | |||
422 | uint ID = this.localid; | ||
423 | |||
424 | bytes[i++] = (byte)(ID % 256); | ||
425 | bytes[i++] = (byte)((ID >> 8) % 256); | ||
426 | bytes[i++] = (byte)((ID >> 16) % 256); | ||
427 | bytes[i++] = (byte)((ID >> 24) % 256); | ||
428 | bytes[i++] = 0; | ||
429 | bytes[i++] = 1; | ||
430 | i += 14; | ||
431 | bytes[i++] = 128; | ||
432 | bytes[i++] = 63; | ||
433 | |||
434 | byte[] pb = pos2.GetBytes(); | ||
435 | Array.Copy(pb, 0, bytes, i, pb.Length); | ||
436 | i += 12; | ||
437 | ushort InternVelocityX; | ||
438 | ushort InternVelocityY; | ||
439 | ushort InternVelocityZ; | ||
440 | |||
441 | Axiom.MathLib.Vector3 internDirec = new Axiom.MathLib.Vector3(this._physActor.Velocity.X, this._physActor.Velocity.Y, this._physActor.Velocity.Z); | ||
442 | internDirec = internDirec / 128.0f; | ||
443 | internDirec.x += 1; | ||
444 | internDirec.y += 1; | ||
445 | internDirec.z += 1; | ||
446 | |||
447 | InternVelocityX = (ushort)(32768 * internDirec.x); | ||
448 | InternVelocityY = (ushort)(32768 * internDirec.y); | ||
449 | InternVelocityZ = (ushort)(32768 * internDirec.z); | ||
450 | |||
451 | ushort ac = 32767; | ||
452 | bytes[i++] = (byte)(InternVelocityX % 256); | ||
453 | bytes[i++] = (byte)((InternVelocityX >> 8) % 256); | ||
454 | bytes[i++] = (byte)(InternVelocityY % 256); | ||
455 | bytes[i++] = (byte)((InternVelocityY >> 8) % 256); | ||
456 | bytes[i++] = (byte)(InternVelocityZ % 256); | ||
457 | bytes[i++] = (byte)((InternVelocityZ >> 8) % 256); | ||
458 | |||
459 | //accel | ||
460 | bytes[i++] = (byte)(ac % 256); | ||
461 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
462 | bytes[i++] = (byte)(ac % 256); | ||
463 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
464 | bytes[i++] = (byte)(ac % 256); | ||
465 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
466 | |||
467 | //rot | ||
468 | bytes[i++] = (byte)(ac % 256); | ||
469 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
470 | bytes[i++] = (byte)(ac % 256); | ||
471 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
472 | bytes[i++] = (byte)(ac % 256); | ||
473 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
474 | bytes[i++] = (byte)(ac % 256); | ||
475 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
476 | |||
477 | //rotation vel | ||
478 | bytes[i++] = (byte)(ac % 256); | ||
479 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
480 | bytes[i++] = (byte)(ac % 256); | ||
481 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
482 | bytes[i++] = (byte)(ac % 256); | ||
483 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
484 | |||
485 | dat.Data = bytes; | ||
486 | return (dat); | ||
487 | } | ||
488 | } | ||
489 | |||
490 | public class NewForce | ||
491 | { | ||
492 | public float X; | ||
493 | public float Y; | ||
494 | public float Z; | ||
495 | |||
496 | public NewForce() | ||
497 | { | ||
498 | |||
499 | } | ||
500 | } | ||
501 | } | ||
diff --git a/OpenSim.RegionServer/world/Entity.cs b/OpenSim.RegionServer/world/Entity.cs new file mode 100644 index 0000000..780f3a0 --- /dev/null +++ b/OpenSim.RegionServer/world/Entity.cs | |||
@@ -0,0 +1,67 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Text; | ||
4 | using Axiom.MathLib; | ||
5 | using OpenSim.types; | ||
6 | using libsecondlife; | ||
7 | |||
8 | namespace OpenSim.world | ||
9 | { | ||
10 | public class Entity | ||
11 | { | ||
12 | public libsecondlife.LLUUID uuid; | ||
13 | public uint localid; | ||
14 | public LLVector3 position; | ||
15 | public LLVector3 velocity; | ||
16 | public Quaternion rotation; | ||
17 | protected string name; | ||
18 | protected List<Entity> children; | ||
19 | |||
20 | public Entity() | ||
21 | { | ||
22 | uuid = new libsecondlife.LLUUID(); | ||
23 | localid = 0; | ||
24 | position = new LLVector3(); | ||
25 | velocity = new LLVector3(); | ||
26 | rotation = new Quaternion(); | ||
27 | name = "(basic entity)"; | ||
28 | children = new List<Entity>(); | ||
29 | } | ||
30 | public virtual void addForces() | ||
31 | { | ||
32 | foreach (Entity child in children) | ||
33 | { | ||
34 | child.addForces(); | ||
35 | } | ||
36 | } | ||
37 | public virtual void update() { | ||
38 | // Do any per-frame updates needed that are applicable to every type of entity | ||
39 | foreach (Entity child in children) | ||
40 | { | ||
41 | child.update(); | ||
42 | } | ||
43 | } | ||
44 | |||
45 | public virtual string getName() | ||
46 | { | ||
47 | return name; | ||
48 | } | ||
49 | |||
50 | public virtual Mesh getMesh() | ||
51 | { | ||
52 | Mesh mesh = new Mesh(); | ||
53 | |||
54 | foreach (Entity child in children) | ||
55 | { | ||
56 | mesh += child.getMesh(); | ||
57 | } | ||
58 | |||
59 | return mesh; | ||
60 | } | ||
61 | |||
62 | public virtual void BackUp() | ||
63 | { | ||
64 | |||
65 | } | ||
66 | } | ||
67 | } | ||
diff --git a/OpenSim.RegionServer/world/Primitive.cs b/OpenSim.RegionServer/world/Primitive.cs new file mode 100644 index 0000000..b190d81 --- /dev/null +++ b/OpenSim.RegionServer/world/Primitive.cs | |||
@@ -0,0 +1,485 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Text; | ||
4 | using OpenSim.types; | ||
5 | using libsecondlife; | ||
6 | using libsecondlife.Packets; | ||
7 | using OpenSim.Framework.Interfaces; | ||
8 | using OpenSim.Physics.Manager; | ||
9 | using OpenSim.Framework.Assets; | ||
10 | |||
11 | namespace OpenSim.world | ||
12 | { | ||
13 | public class Primitive : Entity | ||
14 | { | ||
15 | protected float mesh_cutbegin; | ||
16 | protected float mesh_cutend; | ||
17 | protected PrimData primData; | ||
18 | protected bool newPrimFlag = false; | ||
19 | protected bool updateFlag = false; | ||
20 | protected bool dirtyFlag = false; | ||
21 | private ObjectUpdatePacket OurPacket; | ||
22 | private PhysicsActor _physActor; | ||
23 | private bool physicsEnabled = false; | ||
24 | private bool physicstest = false; //just added for testing | ||
25 | |||
26 | public bool PhysicsEnabled | ||
27 | { | ||
28 | get | ||
29 | { | ||
30 | return physicsEnabled; | ||
31 | } | ||
32 | set | ||
33 | { | ||
34 | physicsEnabled = value; | ||
35 | } | ||
36 | } | ||
37 | public bool UpdateFlag | ||
38 | { | ||
39 | get | ||
40 | { | ||
41 | return updateFlag; | ||
42 | } | ||
43 | set | ||
44 | { | ||
45 | updateFlag = value; | ||
46 | } | ||
47 | } | ||
48 | public LLVector3 Scale | ||
49 | { | ||
50 | set | ||
51 | { | ||
52 | this.primData.Scale = value; | ||
53 | this.dirtyFlag = true; | ||
54 | } | ||
55 | get | ||
56 | { | ||
57 | return this.primData.Scale; | ||
58 | } | ||
59 | } | ||
60 | public PhysicsActor PhysActor | ||
61 | { | ||
62 | set | ||
63 | { | ||
64 | this._physActor = value; | ||
65 | } | ||
66 | } | ||
67 | |||
68 | public Primitive() | ||
69 | { | ||
70 | mesh_cutbegin = 0.0f; | ||
71 | mesh_cutend = 1.0f; | ||
72 | } | ||
73 | |||
74 | public override Mesh getMesh() | ||
75 | { | ||
76 | Mesh mesh = new Mesh(); | ||
77 | Triangle tri = new Triangle( | ||
78 | new Axiom.MathLib.Vector3(0.0f, 1.0f, 1.0f), | ||
79 | new Axiom.MathLib.Vector3(1.0f, 0.0f, 1.0f), | ||
80 | new Axiom.MathLib.Vector3(1.0f, 1.0f, 0.0f)); | ||
81 | |||
82 | mesh.AddTri(tri); | ||
83 | mesh += base.getMesh(); | ||
84 | |||
85 | return mesh; | ||
86 | } | ||
87 | |||
88 | public void UpdatePosition(LLVector3 pos) | ||
89 | { | ||
90 | this.position = pos; | ||
91 | if (this._physActor != null) // && this.physicsEnabled) | ||
92 | { | ||
93 | this._physActor.Position = new PhysicsVector(pos.X, pos.Y, pos.Z); | ||
94 | } | ||
95 | this.updateFlag = true; | ||
96 | } | ||
97 | |||
98 | public override void update() | ||
99 | { | ||
100 | if (this.newPrimFlag) | ||
101 | { | ||
102 | foreach (SimClient client in OpenSimRoot.Instance.ClientThreads.Values) | ||
103 | { | ||
104 | client.OutPacket(OurPacket); | ||
105 | } | ||
106 | this.newPrimFlag = false; | ||
107 | } | ||
108 | else if (this.updateFlag) | ||
109 | { | ||
110 | ImprovedTerseObjectUpdatePacket terse = new ImprovedTerseObjectUpdatePacket(); | ||
111 | terse.RegionData.RegionHandle = OpenSimRoot.Instance.Cfg.RegionHandle; // FIXME | ||
112 | terse.RegionData.TimeDilation = 64096; | ||
113 | terse.ObjectData = new ImprovedTerseObjectUpdatePacket.ObjectDataBlock[1]; | ||
114 | terse.ObjectData[0] = this.CreateImprovedBlock(); | ||
115 | foreach (SimClient client in OpenSimRoot.Instance.ClientThreads.Values) | ||
116 | { | ||
117 | client.OutPacket(terse); | ||
118 | } | ||
119 | this.updateFlag = false; | ||
120 | } | ||
121 | else if (this.dirtyFlag) | ||
122 | { | ||
123 | foreach (SimClient client in OpenSimRoot.Instance.ClientThreads.Values) | ||
124 | { | ||
125 | UpdateClient(client); | ||
126 | } | ||
127 | this.dirtyFlag = false; | ||
128 | } | ||
129 | else | ||
130 | { | ||
131 | if (this._physActor != null && this.physicsEnabled) | ||
132 | { | ||
133 | ImprovedTerseObjectUpdatePacket terse = new ImprovedTerseObjectUpdatePacket(); | ||
134 | terse.RegionData.RegionHandle = OpenSimRoot.Instance.Cfg.RegionHandle; // FIXME | ||
135 | terse.RegionData.TimeDilation = 64096; | ||
136 | terse.ObjectData = new ImprovedTerseObjectUpdatePacket.ObjectDataBlock[1]; | ||
137 | terse.ObjectData[0] = this.CreateImprovedBlock(); | ||
138 | foreach (SimClient client in OpenSimRoot.Instance.ClientThreads.Values) | ||
139 | { | ||
140 | client.OutPacket(terse); | ||
141 | } | ||
142 | } | ||
143 | } | ||
144 | |||
145 | if (this.physicstest) | ||
146 | { | ||
147 | LLVector3 pos = this.position; | ||
148 | pos.Z += 0.0001f; | ||
149 | this.UpdatePosition(pos); | ||
150 | this.physicstest = false; | ||
151 | } | ||
152 | } | ||
153 | |||
154 | public void UpdateClient(SimClient RemoteClient) | ||
155 | { | ||
156 | |||
157 | LLVector3 lPos; | ||
158 | if (this._physActor != null && this.physicsEnabled) | ||
159 | { | ||
160 | PhysicsVector pPos = this._physActor.Position; | ||
161 | lPos = new LLVector3(pPos.X, pPos.Y, pPos.Z); | ||
162 | } | ||
163 | else | ||
164 | { | ||
165 | lPos = this.position; | ||
166 | } | ||
167 | byte[] pb = lPos.GetBytes(); | ||
168 | Array.Copy(pb, 0, OurPacket.ObjectData[0].ObjectData, 0, pb.Length); | ||
169 | |||
170 | // OurPacket should be update with the follwing in updateShape() rather than having to do it here | ||
171 | OurPacket.ObjectData[0].OwnerID = this.primData.OwnerID; | ||
172 | OurPacket.ObjectData[0].PCode = this.primData.PCode; | ||
173 | OurPacket.ObjectData[0].PathBegin = this.primData.PathBegin; | ||
174 | OurPacket.ObjectData[0].PathEnd = this.primData.PathEnd; | ||
175 | OurPacket.ObjectData[0].PathScaleX = this.primData.PathScaleX; | ||
176 | OurPacket.ObjectData[0].PathScaleY = this.primData.PathScaleY; | ||
177 | OurPacket.ObjectData[0].PathShearX = this.primData.PathShearX; | ||
178 | OurPacket.ObjectData[0].PathShearY = this.primData.PathShearY; | ||
179 | OurPacket.ObjectData[0].PathSkew = this.primData.PathSkew; | ||
180 | OurPacket.ObjectData[0].ProfileBegin = this.primData.ProfileBegin; | ||
181 | OurPacket.ObjectData[0].ProfileEnd = this.primData.ProfileEnd; | ||
182 | OurPacket.ObjectData[0].Scale = this.primData.Scale; | ||
183 | OurPacket.ObjectData[0].PathCurve = this.primData.PathCurve; | ||
184 | OurPacket.ObjectData[0].ProfileCurve = this.primData.ProfileCurve; | ||
185 | OurPacket.ObjectData[0].ParentID = 0; | ||
186 | OurPacket.ObjectData[0].ProfileHollow = this.primData.ProfileHollow; | ||
187 | //finish off copying rest of shape data | ||
188 | OurPacket.ObjectData[0].PathRadiusOffset = this.primData.PathRadiusOffset; | ||
189 | OurPacket.ObjectData[0].PathRevolutions = this.primData.PathRevolutions; | ||
190 | OurPacket.ObjectData[0].PathTaperX = this.primData.PathTaperX; | ||
191 | OurPacket.ObjectData[0].PathTaperY = this.primData.PathTaperY; | ||
192 | OurPacket.ObjectData[0].PathTwist = this.primData.PathTwist; | ||
193 | OurPacket.ObjectData[0].PathTwistBegin = this.primData.PathTwistBegin; | ||
194 | |||
195 | RemoteClient.OutPacket(OurPacket); | ||
196 | } | ||
197 | |||
198 | public void UpdateShape(ObjectShapePacket.ObjectDataBlock addPacket) | ||
199 | { | ||
200 | this.primData.PathBegin = addPacket.PathBegin; | ||
201 | this.primData.PathEnd = addPacket.PathEnd; | ||
202 | this.primData.PathScaleX = addPacket.PathScaleX; | ||
203 | this.primData.PathScaleY = addPacket.PathScaleY; | ||
204 | this.primData.PathShearX = addPacket.PathShearX; | ||
205 | this.primData.PathShearY = addPacket.PathShearY; | ||
206 | this.primData.PathSkew = addPacket.PathSkew; | ||
207 | this.primData.ProfileBegin = addPacket.ProfileBegin; | ||
208 | this.primData.ProfileEnd = addPacket.ProfileEnd; | ||
209 | this.primData.PathCurve = addPacket.PathCurve; | ||
210 | this.primData.ProfileCurve = addPacket.ProfileCurve; | ||
211 | this.primData.ProfileHollow = addPacket.ProfileHollow; | ||
212 | this.primData.PathRadiusOffset = addPacket.PathRadiusOffset; | ||
213 | this.primData.PathRevolutions = addPacket.PathRevolutions; | ||
214 | this.primData.PathTaperX = addPacket.PathTaperX; | ||
215 | this.primData.PathTaperY = addPacket.PathTaperY; | ||
216 | this.primData.PathTwist = addPacket.PathTwist; | ||
217 | this.primData.PathTwistBegin = addPacket.PathTwistBegin; | ||
218 | this.dirtyFlag = true; | ||
219 | } | ||
220 | |||
221 | public void UpdateTexture(byte[] tex) | ||
222 | { | ||
223 | this.primData.Texture = this.OurPacket.ObjectData[0].TextureEntry = tex; | ||
224 | this.dirtyFlag = true; | ||
225 | } | ||
226 | |||
227 | public void UpdateObjectFlags(ObjectFlagUpdatePacket pack) | ||
228 | { | ||
229 | if (this._physActor != null) | ||
230 | { | ||
231 | if (this._physActor.Kinematic == pack.AgentData.UsePhysics) | ||
232 | { | ||
233 | this._physActor.Kinematic = !pack.AgentData.UsePhysics; //if Usephysics = true, then Kinematic should = false | ||
234 | } | ||
235 | this.physicsEnabled = pack.AgentData.UsePhysics; | ||
236 | if (this._physActor.Kinematic == false) | ||
237 | { | ||
238 | LLVector3 pos = this.position; | ||
239 | this.UpdatePosition(pos); | ||
240 | pos.Z += 0.000001f; | ||
241 | this.UpdatePosition(pos); | ||
242 | this.physicstest = true; | ||
243 | } | ||
244 | else | ||
245 | { | ||
246 | PhysicsVector vec = this._physActor.Position; | ||
247 | LLVector3 pos = new LLVector3(vec.X, vec.Y, vec.Z); | ||
248 | this.position = pos; | ||
249 | this.updateFlag = true; | ||
250 | } | ||
251 | } | ||
252 | } | ||
253 | |||
254 | public void CreateFromPacket(ObjectAddPacket addPacket, LLUUID agentID, uint localID) | ||
255 | { | ||
256 | ObjectUpdatePacket objupdate = new ObjectUpdatePacket(); | ||
257 | objupdate.RegionData.RegionHandle = OpenSimRoot.Instance.Cfg.RegionHandle; | ||
258 | objupdate.RegionData.TimeDilation = 64096; | ||
259 | |||
260 | objupdate.ObjectData = new libsecondlife.Packets.ObjectUpdatePacket.ObjectDataBlock[1]; | ||
261 | PrimData PData = new PrimData(); | ||
262 | this.primData = PData; | ||
263 | objupdate.ObjectData[0] = new ObjectUpdatePacket.ObjectDataBlock(); | ||
264 | objupdate.ObjectData[0].PSBlock = new byte[0]; | ||
265 | objupdate.ObjectData[0].ExtraParams = new byte[1]; | ||
266 | objupdate.ObjectData[0].MediaURL = new byte[0]; | ||
267 | objupdate.ObjectData[0].NameValue = new byte[0]; | ||
268 | objupdate.ObjectData[0].Text = new byte[0]; | ||
269 | objupdate.ObjectData[0].TextColor = new byte[4]; | ||
270 | objupdate.ObjectData[0].JointAxisOrAnchor = new LLVector3(0, 0, 0); | ||
271 | objupdate.ObjectData[0].JointPivot = new LLVector3(0, 0, 0); | ||
272 | objupdate.ObjectData[0].Material = 3; | ||
273 | objupdate.ObjectData[0].UpdateFlags = 32 + 65536 + 131072 + 256 + 4 + 8 + 2048 + 524288 + 268435456; | ||
274 | objupdate.ObjectData[0].TextureAnim = new byte[0]; | ||
275 | objupdate.ObjectData[0].Sound = LLUUID.Zero; | ||
276 | LLObject.TextureEntry ntex = new LLObject.TextureEntry(new LLUUID("00000000-0000-0000-5005-000000000005")); | ||
277 | objupdate.ObjectData[0].TextureEntry = ntex.ToBytes(); | ||
278 | objupdate.ObjectData[0].State = 0; | ||
279 | objupdate.ObjectData[0].Data = new byte[0]; | ||
280 | PData.OwnerID = objupdate.ObjectData[0].OwnerID = agentID; | ||
281 | PData.PCode = objupdate.ObjectData[0].PCode = addPacket.ObjectData.PCode; | ||
282 | PData.PathBegin = objupdate.ObjectData[0].PathBegin = addPacket.ObjectData.PathBegin; | ||
283 | PData.PathEnd = objupdate.ObjectData[0].PathEnd = addPacket.ObjectData.PathEnd; | ||
284 | PData.PathScaleX = objupdate.ObjectData[0].PathScaleX = addPacket.ObjectData.PathScaleX; | ||
285 | PData.PathScaleY = objupdate.ObjectData[0].PathScaleY = addPacket.ObjectData.PathScaleY; | ||
286 | PData.PathShearX = objupdate.ObjectData[0].PathShearX = addPacket.ObjectData.PathShearX; | ||
287 | PData.PathShearY = objupdate.ObjectData[0].PathShearY = addPacket.ObjectData.PathShearY; | ||
288 | PData.PathSkew = objupdate.ObjectData[0].PathSkew = addPacket.ObjectData.PathSkew; | ||
289 | PData.ProfileBegin = objupdate.ObjectData[0].ProfileBegin = addPacket.ObjectData.ProfileBegin; | ||
290 | PData.ProfileEnd = objupdate.ObjectData[0].ProfileEnd = addPacket.ObjectData.ProfileEnd; | ||
291 | PData.Scale = objupdate.ObjectData[0].Scale = addPacket.ObjectData.Scale; | ||
292 | PData.PathCurve = objupdate.ObjectData[0].PathCurve = addPacket.ObjectData.PathCurve; | ||
293 | PData.ProfileCurve = objupdate.ObjectData[0].ProfileCurve = addPacket.ObjectData.ProfileCurve; | ||
294 | PData.ParentID = objupdate.ObjectData[0].ParentID = 0; | ||
295 | PData.ProfileHollow = objupdate.ObjectData[0].ProfileHollow = addPacket.ObjectData.ProfileHollow; | ||
296 | |||
297 | PData.PathRadiusOffset = objupdate.ObjectData[0].PathRadiusOffset = addPacket.ObjectData.PathRadiusOffset; | ||
298 | PData.PathRevolutions = objupdate.ObjectData[0].PathRevolutions = addPacket.ObjectData.PathRevolutions; | ||
299 | PData.PathTaperX = objupdate.ObjectData[0].PathTaperX = addPacket.ObjectData.PathTaperX; | ||
300 | PData.PathTaperY = objupdate.ObjectData[0].PathTaperY = addPacket.ObjectData.PathTaperY; | ||
301 | PData.PathTwist = objupdate.ObjectData[0].PathTwist = addPacket.ObjectData.PathTwist; | ||
302 | PData.PathTwistBegin = objupdate.ObjectData[0].PathTwistBegin = addPacket.ObjectData.PathTwistBegin; | ||
303 | |||
304 | objupdate.ObjectData[0].ID = (uint)(localID); | ||
305 | objupdate.ObjectData[0].FullID = new LLUUID("edba7151-5857-acc5-b30b-f01efef" + (localID - 702000).ToString("00000")); | ||
306 | objupdate.ObjectData[0].ObjectData = new byte[60]; | ||
307 | objupdate.ObjectData[0].ObjectData[46] = 128; | ||
308 | objupdate.ObjectData[0].ObjectData[47] = 63; | ||
309 | LLVector3 pos1 = addPacket.ObjectData.RayEnd; | ||
310 | //update position | ||
311 | byte[] pb = pos1.GetBytes(); | ||
312 | Array.Copy(pb, 0, objupdate.ObjectData[0].ObjectData, 0, pb.Length); | ||
313 | |||
314 | this.newPrimFlag = true; | ||
315 | this.uuid = objupdate.ObjectData[0].FullID; | ||
316 | this.localid = objupdate.ObjectData[0].ID; | ||
317 | this.position = pos1; | ||
318 | this.OurPacket = objupdate; | ||
319 | } | ||
320 | |||
321 | public void CreateFromStorage(PrimData store) | ||
322 | { | ||
323 | //need to clean this up as it shares a lot of code with CreateFromPacket() | ||
324 | ObjectUpdatePacket objupdate = new ObjectUpdatePacket(); | ||
325 | objupdate.RegionData.RegionHandle = OpenSimRoot.Instance.Cfg.RegionHandle; | ||
326 | objupdate.RegionData.TimeDilation = 64096; | ||
327 | objupdate.ObjectData = new libsecondlife.Packets.ObjectUpdatePacket.ObjectDataBlock[1]; | ||
328 | |||
329 | this.primData = store; | ||
330 | objupdate.ObjectData[0] = new ObjectUpdatePacket.ObjectDataBlock(); | ||
331 | objupdate.ObjectData[0].PSBlock = new byte[0]; | ||
332 | objupdate.ObjectData[0].ExtraParams = new byte[1]; | ||
333 | objupdate.ObjectData[0].MediaURL = new byte[0]; | ||
334 | objupdate.ObjectData[0].NameValue = new byte[0]; | ||
335 | objupdate.ObjectData[0].Text = new byte[0]; | ||
336 | objupdate.ObjectData[0].TextColor = new byte[4]; | ||
337 | objupdate.ObjectData[0].JointAxisOrAnchor = new LLVector3(0, 0, 0); | ||
338 | objupdate.ObjectData[0].JointPivot = new LLVector3(0, 0, 0); | ||
339 | objupdate.ObjectData[0].Material = 3; | ||
340 | objupdate.ObjectData[0].UpdateFlags = 32 + 65536 + 131072 + 256 + 4 + 8 + 2048 + 524288 + 268435456; | ||
341 | objupdate.ObjectData[0].TextureAnim = new byte[0]; | ||
342 | objupdate.ObjectData[0].Sound = LLUUID.Zero; | ||
343 | |||
344 | if (store.Texture == null) | ||
345 | { | ||
346 | LLObject.TextureEntry ntex = new LLObject.TextureEntry(new LLUUID("00000000-0000-0000-5005-000000000005")); | ||
347 | objupdate.ObjectData[0].TextureEntry = ntex.ToBytes(); | ||
348 | } | ||
349 | else | ||
350 | { | ||
351 | objupdate.ObjectData[0].TextureEntry = store.Texture; | ||
352 | } | ||
353 | |||
354 | objupdate.ObjectData[0].State = 0; | ||
355 | objupdate.ObjectData[0].Data = new byte[0]; | ||
356 | objupdate.ObjectData[0].OwnerID = this.primData.OwnerID; | ||
357 | objupdate.ObjectData[0].PCode = this.primData.PCode; | ||
358 | objupdate.ObjectData[0].PathBegin = this.primData.PathBegin; | ||
359 | objupdate.ObjectData[0].PathEnd = this.primData.PathEnd; | ||
360 | objupdate.ObjectData[0].PathScaleX = this.primData.PathScaleX; | ||
361 | objupdate.ObjectData[0].PathScaleY = this.primData.PathScaleY; | ||
362 | objupdate.ObjectData[0].PathShearX = this.primData.PathShearX; | ||
363 | objupdate.ObjectData[0].PathShearY = this.primData.PathShearY; | ||
364 | objupdate.ObjectData[0].PathSkew = this.primData.PathSkew; | ||
365 | objupdate.ObjectData[0].ProfileBegin = this.primData.ProfileBegin; | ||
366 | objupdate.ObjectData[0].ProfileEnd = this.primData.ProfileEnd; | ||
367 | objupdate.ObjectData[0].Scale = this.primData.Scale; | ||
368 | objupdate.ObjectData[0].PathCurve = this.primData.PathCurve; | ||
369 | objupdate.ObjectData[0].ProfileCurve = this.primData.ProfileCurve; | ||
370 | objupdate.ObjectData[0].ParentID = 0; | ||
371 | objupdate.ObjectData[0].ProfileHollow = this.primData.ProfileHollow; | ||
372 | //finish off copying rest of shape data | ||
373 | objupdate.ObjectData[0].PathRadiusOffset = this.primData.PathRadiusOffset; | ||
374 | objupdate.ObjectData[0].PathRevolutions = this.primData.PathRevolutions; | ||
375 | objupdate.ObjectData[0].PathTaperX = this.primData.PathTaperX; | ||
376 | objupdate.ObjectData[0].PathTaperY = this.primData.PathTaperY; | ||
377 | objupdate.ObjectData[0].PathTwist = this.primData.PathTwist; | ||
378 | objupdate.ObjectData[0].PathTwistBegin = this.primData.PathTwistBegin; | ||
379 | |||
380 | objupdate.ObjectData[0].ID = (uint)store.LocalID; | ||
381 | objupdate.ObjectData[0].FullID = store.FullID; | ||
382 | |||
383 | objupdate.ObjectData[0].ObjectData = new byte[60]; | ||
384 | objupdate.ObjectData[0].ObjectData[46] = 128; | ||
385 | objupdate.ObjectData[0].ObjectData[47] = 63; | ||
386 | LLVector3 pos1 = store.Position; | ||
387 | //update position | ||
388 | byte[] pb = pos1.GetBytes(); | ||
389 | Array.Copy(pb, 0, objupdate.ObjectData[0].ObjectData, 0, pb.Length); | ||
390 | |||
391 | this.uuid = objupdate.ObjectData[0].FullID; | ||
392 | this.localid = objupdate.ObjectData[0].ID; | ||
393 | this.position = pos1; | ||
394 | this.OurPacket = objupdate; | ||
395 | |||
396 | } | ||
397 | public ImprovedTerseObjectUpdatePacket.ObjectDataBlock CreateImprovedBlock() | ||
398 | { | ||
399 | uint ID = this.localid; | ||
400 | byte[] bytes = new byte[60]; | ||
401 | |||
402 | int i = 0; | ||
403 | ImprovedTerseObjectUpdatePacket.ObjectDataBlock dat = new ImprovedTerseObjectUpdatePacket.ObjectDataBlock(); | ||
404 | dat.TextureEntry = this.OurPacket.ObjectData[0].TextureEntry; | ||
405 | |||
406 | bytes[i++] = (byte)(ID % 256); | ||
407 | bytes[i++] = (byte)((ID >> 8) % 256); | ||
408 | bytes[i++] = (byte)((ID >> 16) % 256); | ||
409 | bytes[i++] = (byte)((ID >> 24) % 256); | ||
410 | bytes[i++] = 0; | ||
411 | bytes[i++] = 0; | ||
412 | |||
413 | LLVector3 lPos; | ||
414 | Axiom.MathLib.Quaternion lRot; | ||
415 | if (this._physActor != null && this.physicsEnabled) | ||
416 | { | ||
417 | PhysicsVector pPos = this._physActor.Position; | ||
418 | lPos = new LLVector3(pPos.X, pPos.Y, pPos.Z); | ||
419 | lRot = this._physActor.Orientation; | ||
420 | } | ||
421 | else | ||
422 | { | ||
423 | lPos = this.position; | ||
424 | lRot = this.rotation; | ||
425 | } | ||
426 | byte[] pb = lPos.GetBytes(); | ||
427 | Array.Copy(pb, 0, bytes, i, pb.Length); | ||
428 | i += 12; | ||
429 | ushort ac = 32767; | ||
430 | |||
431 | //vel | ||
432 | bytes[i++] = (byte)(ac % 256); | ||
433 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
434 | bytes[i++] = (byte)(ac % 256); | ||
435 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
436 | bytes[i++] = (byte)(ac % 256); | ||
437 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
438 | |||
439 | //accel | ||
440 | bytes[i++] = (byte)(ac % 256); | ||
441 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
442 | bytes[i++] = (byte)(ac % 256); | ||
443 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
444 | bytes[i++] = (byte)(ac % 256); | ||
445 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
446 | |||
447 | ushort rw, rx, ry, rz; | ||
448 | rw = (ushort)(32768 * (lRot.w + 1)); | ||
449 | rx = (ushort)(32768 * (lRot.x + 1)); | ||
450 | ry = (ushort)(32768 * (lRot.y + 1)); | ||
451 | rz = (ushort)(32768 * (lRot.z + 1)); | ||
452 | |||
453 | //rot | ||
454 | bytes[i++] = (byte)(rx % 256); | ||
455 | bytes[i++] = (byte)((rx >> 8) % 256); | ||
456 | bytes[i++] = (byte)(ry % 256); | ||
457 | bytes[i++] = (byte)((ry >> 8) % 256); | ||
458 | bytes[i++] = (byte)(rz % 256); | ||
459 | bytes[i++] = (byte)((rz >> 8) % 256); | ||
460 | bytes[i++] = (byte)(rw % 256); | ||
461 | bytes[i++] = (byte)((rw >> 8) % 256); | ||
462 | |||
463 | //rotation vel | ||
464 | bytes[i++] = (byte)(ac % 256); | ||
465 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
466 | bytes[i++] = (byte)(ac % 256); | ||
467 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
468 | bytes[i++] = (byte)(ac % 256); | ||
469 | bytes[i++] = (byte)((ac >> 8) % 256); | ||
470 | |||
471 | dat.Data = bytes; | ||
472 | return dat; | ||
473 | } | ||
474 | |||
475 | public override void BackUp() | ||
476 | { | ||
477 | this.primData.FullID = this.uuid; | ||
478 | this.primData.LocalID = this.localid; | ||
479 | this.primData.Position = this.position; | ||
480 | this.primData.Rotation = new LLQuaternion(this.rotation.x, this.rotation.y, this.rotation.z, this.rotation.w); | ||
481 | OpenSimRoot.Instance.LocalWorld.localStorage.StorePrim(this.primData); | ||
482 | } | ||
483 | } | ||
484 | |||
485 | } | ||
diff --git a/OpenSim.RegionServer/world/ScriptEngine.cs b/OpenSim.RegionServer/world/ScriptEngine.cs new file mode 100644 index 0000000..f20a08e --- /dev/null +++ b/OpenSim.RegionServer/world/ScriptEngine.cs | |||
@@ -0,0 +1,18 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Text; | ||
4 | |||
5 | namespace OpenSim.world | ||
6 | { | ||
7 | public class ScriptEngine | ||
8 | { | ||
9 | public ScriptEngine(World env) | ||
10 | { | ||
11 | } | ||
12 | |||
13 | public void LoadScript() | ||
14 | { | ||
15 | |||
16 | } | ||
17 | } | ||
18 | } | ||
diff --git a/OpenSim.RegionServer/world/SurfacePatch.cs b/OpenSim.RegionServer/world/SurfacePatch.cs new file mode 100644 index 0000000..71e4116 --- /dev/null +++ b/OpenSim.RegionServer/world/SurfacePatch.cs | |||
@@ -0,0 +1,22 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Text; | ||
4 | |||
5 | namespace OpenSim.world | ||
6 | { | ||
7 | public class SurfacePatch | ||
8 | { | ||
9 | public float[] HeightMap; | ||
10 | |||
11 | public SurfacePatch() { | ||
12 | HeightMap = new float[16*16]; | ||
13 | |||
14 | int xinc; | ||
15 | int yinc; | ||
16 | for(xinc=0; xinc<16; xinc++) for(yinc=0; yinc<16; yinc++) { | ||
17 | HeightMap[xinc+(yinc*16)]=100.0f; | ||
18 | } | ||
19 | |||
20 | } | ||
21 | } | ||
22 | } | ||
diff --git a/OpenSim.RegionServer/world/World.cs b/OpenSim.RegionServer/world/World.cs new file mode 100644 index 0000000..ba99233 --- /dev/null +++ b/OpenSim.RegionServer/world/World.cs | |||
@@ -0,0 +1,213 @@ | |||
1 | using System; | ||
2 | using libsecondlife; | ||
3 | using libsecondlife.Packets; | ||
4 | using System.Collections.Generic; | ||
5 | using System.Text; | ||
6 | using System.Reflection; | ||
7 | using System.IO; | ||
8 | using OpenSim.Physics.Manager; | ||
9 | using OpenSim.Framework.Interfaces; | ||
10 | using OpenSim.Framework.Assets; | ||
11 | using OpenSim.Framework.Terrain; | ||
12 | |||
13 | namespace OpenSim.world | ||
14 | { | ||
15 | public class World : ILocalStorageReceiver | ||
16 | { | ||
17 | public Dictionary<libsecondlife.LLUUID, Entity> Entities; | ||
18 | public float[] LandMap; | ||
19 | public ScriptEngine Scripts; | ||
20 | public uint _localNumber=0; | ||
21 | private PhysicsScene phyScene; | ||
22 | private float timeStep= 0.1f; | ||
23 | private libsecondlife.TerrainManager TerrainManager; | ||
24 | public ILocalStorage localStorage; | ||
25 | private Random Rand = new Random(); | ||
26 | private uint _primCount = 702000; | ||
27 | private int storageCount; | ||
28 | |||
29 | public World() | ||
30 | { | ||
31 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs - creating new entitities instance"); | ||
32 | Entities = new Dictionary<libsecondlife.LLUUID, Entity>(); | ||
33 | |||
34 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs - creating LandMap"); | ||
35 | TerrainManager = new TerrainManager(new SecondLife()); | ||
36 | Avatar.SetupTemplate("avatar-template.dat"); | ||
37 | // ServerConsole.MainConsole.Instance.WriteLine("World.cs - Creating script engine instance"); | ||
38 | // Initialise this only after the world has loaded | ||
39 | // Scripts = new ScriptEngine(this); | ||
40 | } | ||
41 | |||
42 | public PhysicsScene PhysScene | ||
43 | { | ||
44 | set | ||
45 | { | ||
46 | this.phyScene = value; | ||
47 | } | ||
48 | get | ||
49 | { | ||
50 | return(this.phyScene); | ||
51 | } | ||
52 | } | ||
53 | |||
54 | public void Update() | ||
55 | { | ||
56 | if(this.phyScene.IsThreaded) | ||
57 | { | ||
58 | this.phyScene.GetResults(); | ||
59 | |||
60 | } | ||
61 | |||
62 | foreach (libsecondlife.LLUUID UUID in Entities.Keys) | ||
63 | { | ||
64 | Entities[UUID].addForces(); | ||
65 | } | ||
66 | |||
67 | this.phyScene.Simulate(timeStep); | ||
68 | |||
69 | foreach (libsecondlife.LLUUID UUID in Entities.Keys) | ||
70 | { | ||
71 | Entities[UUID].update(); | ||
72 | } | ||
73 | |||
74 | //backup world data | ||
75 | this.storageCount++; | ||
76 | if(storageCount> 1200) //set to how often you want to backup | ||
77 | { | ||
78 | this.Backup(); | ||
79 | storageCount =0; | ||
80 | } | ||
81 | } | ||
82 | |||
83 | public bool LoadStorageDLL(string dllName) | ||
84 | { | ||
85 | Assembly pluginAssembly = Assembly.LoadFrom(dllName); | ||
86 | ILocalStorage store = null; | ||
87 | |||
88 | foreach (Type pluginType in pluginAssembly.GetTypes()) | ||
89 | { | ||
90 | if (pluginType.IsPublic) | ||
91 | { | ||
92 | if (!pluginType.IsAbstract) | ||
93 | { | ||
94 | Type typeInterface = pluginType.GetInterface("ILocalStorage", true); | ||
95 | |||
96 | if (typeInterface != null) | ||
97 | { | ||
98 | ILocalStorage plug = (ILocalStorage)Activator.CreateInstance(pluginAssembly.GetType(pluginType.ToString())); | ||
99 | store = plug; | ||
100 | break; | ||
101 | } | ||
102 | |||
103 | typeInterface = null; | ||
104 | } | ||
105 | } | ||
106 | } | ||
107 | pluginAssembly = null; | ||
108 | this.localStorage = store; | ||
109 | return(store == null); | ||
110 | } | ||
111 | |||
112 | public void RegenerateTerrain() | ||
113 | { | ||
114 | HeightmapGenHills hills = new HeightmapGenHills(); | ||
115 | this.LandMap = hills.GenerateHeightmap(200, 4.0f, 80.0f, false); | ||
116 | this.phyScene.SetTerrain(this.LandMap); | ||
117 | OpenSimRoot.Instance.Cfg.SaveMap(this.LandMap); | ||
118 | |||
119 | foreach(SimClient client in OpenSimRoot.Instance.ClientThreads.Values) { | ||
120 | this.SendLayerData(client); | ||
121 | } | ||
122 | } | ||
123 | public void LoadPrimsFromStorage() | ||
124 | { | ||
125 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs: LoadPrimsFromStorage() - Loading primitives"); | ||
126 | this.localStorage.LoadPrimitives(this); | ||
127 | } | ||
128 | |||
129 | public void PrimFromStorage(PrimData prim) | ||
130 | { | ||
131 | if(prim.LocalID >= this._primCount) | ||
132 | { | ||
133 | _primCount = prim.LocalID + 1; | ||
134 | } | ||
135 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs: PrimFromStorage() - Reloading prim (localId "+ prim.LocalID+ " ) from storage"); | ||
136 | Primitive nPrim = new Primitive(); | ||
137 | nPrim.CreateFromStorage(prim); | ||
138 | this.Entities.Add(nPrim.uuid, nPrim); | ||
139 | } | ||
140 | |||
141 | public void Close() | ||
142 | { | ||
143 | this.localStorage.ShutDown(); | ||
144 | } | ||
145 | |||
146 | public void SendLayerData(SimClient RemoteClient) { | ||
147 | int[] patches = new int[4]; | ||
148 | |||
149 | for (int y = 0; y < 16; y++) | ||
150 | { | ||
151 | for (int x = 0; x < 16; x = x + 4) | ||
152 | { | ||
153 | patches[0] = x + 0 + y * 16; | ||
154 | patches[1] = x + 1 + y * 16; | ||
155 | patches[2] = x + 2 + y * 16; | ||
156 | patches[3] = x + 3 + y * 16; | ||
157 | |||
158 | Packet layerpack = TerrainManager.CreateLandPacket(LandMap, patches); | ||
159 | RemoteClient.OutPacket(layerpack); | ||
160 | } | ||
161 | } | ||
162 | } | ||
163 | |||
164 | public void GetInitialPrims(SimClient RemoteClient) | ||
165 | { | ||
166 | foreach (libsecondlife.LLUUID UUID in Entities.Keys) | ||
167 | { | ||
168 | if(Entities[UUID].ToString()== "OpenSim.world.Primitive") | ||
169 | { | ||
170 | ((OpenSim.world.Primitive)Entities[UUID]).UpdateClient(RemoteClient); | ||
171 | } | ||
172 | } | ||
173 | } | ||
174 | |||
175 | public void AddViewerAgent(SimClient AgentClient) { | ||
176 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs:AddViewerAgent() - Creating new avatar for remote viewer agent"); | ||
177 | Avatar NewAvatar = new Avatar(AgentClient); | ||
178 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs:AddViewerAgent() - Adding new avatar to world"); | ||
179 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs:AddViewerAgent() - Starting RegionHandshake "); | ||
180 | NewAvatar.SendRegionHandshake(this); | ||
181 | PhysicsVector pVec = new PhysicsVector(NewAvatar.position.X, NewAvatar.position.Y, NewAvatar.position.Z); | ||
182 | NewAvatar.PhysActor = this.phyScene.AddAvatar(pVec); | ||
183 | this.Entities.Add(AgentClient.AgentID, NewAvatar); | ||
184 | } | ||
185 | |||
186 | public void AddNewPrim(ObjectAddPacket addPacket, SimClient AgentClient) | ||
187 | { | ||
188 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs: AddNewPrim() - Creating new prim"); | ||
189 | Primitive prim = new Primitive(); | ||
190 | prim.CreateFromPacket(addPacket, AgentClient.AgentID, this._primCount); | ||
191 | PhysicsVector pVec = new PhysicsVector(prim.position.X, prim.position.Y, prim.position.Z); | ||
192 | PhysicsVector pSize = new PhysicsVector( 0.255f, 0.255f, 0.255f); | ||
193 | if(OpenSim.world.Avatar.PhysicsEngineFlying) | ||
194 | { | ||
195 | prim.PhysActor = this.phyScene.AddPrim(pVec, pSize ); | ||
196 | } | ||
197 | //prim.PhysicsEnabled = true; | ||
198 | this.Entities.Add(prim.uuid, prim); | ||
199 | this._primCount++; | ||
200 | } | ||
201 | |||
202 | public bool Backup() { | ||
203 | |||
204 | OpenSim.Framework.Console.MainConsole.Instance.WriteLine("World.cs: Backup() - Backing up Primitives"); | ||
205 | foreach (libsecondlife.LLUUID UUID in Entities.Keys) | ||
206 | { | ||
207 | Entities[UUID].BackUp(); | ||
208 | } | ||
209 | return true; | ||
210 | } | ||
211 | |||
212 | } | ||
213 | } | ||
diff --git a/OpenSim.RegionServer/world/scripting/IScript.cs b/OpenSim.RegionServer/world/scripting/IScript.cs new file mode 100644 index 0000000..550594d --- /dev/null +++ b/OpenSim.RegionServer/world/scripting/IScript.cs | |||
@@ -0,0 +1,16 @@ | |||
1 | using System; | ||
2 | using System.Collections.Generic; | ||
3 | using System.Text; | ||
4 | |||
5 | namespace OpenSim.world.scripting | ||
6 | { | ||
7 | public interface IScriptHost { | ||
8 | bool Register(IScript iscript); | ||
9 | } | ||
10 | public interface IScript | ||
11 | { | ||
12 | string Name{get;set;} | ||
13 | IScriptHost Host{get;set;} | ||
14 | void Show(); | ||
15 | } | ||
16 | } | ||