aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/ClientStack/Linden/UDP
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/ClientStack/Linden/UDP')
-rw-r--r--OpenSim/Region/ClientStack/Linden/UDP/J2KImage.cs35
-rw-r--r--OpenSim/Region/ClientStack/Linden/UDP/LLImageManager.cs31
-rw-r--r--OpenSim/Region/ClientStack/Linden/UDP/Tests/LLImageManagerTests.cs110
3 files changed, 143 insertions, 33 deletions
diff --git a/OpenSim/Region/ClientStack/Linden/UDP/J2KImage.cs b/OpenSim/Region/ClientStack/Linden/UDP/J2KImage.cs
index bbd2c43..afbe56b 100644
--- a/OpenSim/Region/ClientStack/Linden/UDP/J2KImage.cs
+++ b/OpenSim/Region/ClientStack/Linden/UDP/J2KImage.cs
@@ -45,6 +45,15 @@ namespace OpenSim.Region.ClientStack.LindenUDP
45 private const int IMAGE_PACKET_SIZE = 1000; 45 private const int IMAGE_PACKET_SIZE = 1000;
46 private const int FIRST_PACKET_SIZE = 600; 46 private const int FIRST_PACKET_SIZE = 600;
47 47
48 /// <summary>
49 /// If we've requested an asset but not received it in this ticks timeframe, then allow a duplicate
50 /// request from the client to trigger a fresh asset request.
51 /// </summary>
52 /// <remarks>
53 /// There are 10,000 ticks in a millisecond
54 /// </remarks>
55 private const int ASSET_REQUEST_TIMEOUT = 100000000;
56
48 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); 57 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
49 58
50 public uint LastSequence; 59 public uint LastSequence;
@@ -57,8 +66,22 @@ namespace OpenSim.Region.ClientStack.LindenUDP
57 public UUID AgentID; 66 public UUID AgentID;
58 public IInventoryAccessModule InventoryAccessModule; 67 public IInventoryAccessModule InventoryAccessModule;
59 private OpenJPEG.J2KLayerInfo[] m_layers; 68 private OpenJPEG.J2KLayerInfo[] m_layers;
69
70 /// <summary>
71 /// Has this request decoded the asset data?
72 /// </summary>
60 public bool IsDecoded { get; private set; } 73 public bool IsDecoded { get; private set; }
74
75 /// <summary>
76 /// Has this request received the required asset data?
77 /// </summary>
61 public bool HasAsset { get; private set; } 78 public bool HasAsset { get; private set; }
79
80 /// <summary>
81 /// Time in milliseconds at which the asset was requested.
82 /// </summary>
83 public long AssetRequestTime { get; private set; }
84
62 public C5.IPriorityQueueHandle<J2KImage> PriorityQueueHandle; 85 public C5.IPriorityQueueHandle<J2KImage> PriorityQueueHandle;
63 86
64 private uint m_currentPacket; 87 private uint m_currentPacket;
@@ -123,10 +146,15 @@ namespace OpenSim.Region.ClientStack.LindenUDP
123 { 146 {
124 if (!HasAsset) 147 if (!HasAsset)
125 { 148 {
126 if (!m_assetRequested) 149 if (!m_assetRequested || DateTime.UtcNow.Ticks > AssetRequestTime + ASSET_REQUEST_TIMEOUT)
127 { 150 {
151// m_log.DebugFormat(
152// "[J2KIMAGE]: Requesting asset {0} from request in packet {1}, already requested? {2}, due to timeout? {3}",
153// TextureID, LastSequence, m_assetRequested, DateTime.UtcNow.Ticks > AssetRequestTime + ASSET_REQUEST_TIMEOUT);
154
128 m_assetRequested = true; 155 m_assetRequested = true;
129// m_log.DebugFormat("[J2KIMAGE]: Requesting asset {0}", TextureID); 156 AssetRequestTime = DateTime.UtcNow.Ticks;
157
130 AssetService.Get(TextureID.ToString(), this, AssetReceived); 158 AssetService.Get(TextureID.ToString(), this, AssetReceived);
131 } 159 }
132 } 160 }
@@ -377,6 +405,9 @@ namespace OpenSim.Region.ClientStack.LindenUDP
377 405
378 private void AssetReceived(string id, Object sender, AssetBase asset) 406 private void AssetReceived(string id, Object sender, AssetBase asset)
379 { 407 {
408// m_log.DebugFormat(
409// "[J2KIMAGE]: Received asset {0} ({1} bytes)", id, asset != null ? asset.Data.Length.ToString() : "n/a");
410
380 UUID assetID = UUID.Zero; 411 UUID assetID = UUID.Zero;
381 if (asset != null) 412 if (asset != null)
382 { 413 {
diff --git a/OpenSim/Region/ClientStack/Linden/UDP/LLImageManager.cs b/OpenSim/Region/ClientStack/Linden/UDP/LLImageManager.cs
index 7bfb844..073c357 100644
--- a/OpenSim/Region/ClientStack/Linden/UDP/LLImageManager.cs
+++ b/OpenSim/Region/ClientStack/Linden/UDP/LLImageManager.cs
@@ -55,18 +55,29 @@ namespace OpenSim.Region.ClientStack.LindenUDP
55 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); 55 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
56 private bool m_shuttingdown; 56 private bool m_shuttingdown;
57 private AssetBase m_missingImage; 57 private AssetBase m_missingImage;
58 private IClientAPI m_client; //Client we're assigned to 58 private IAssetService m_assetCache;
59 private IAssetService m_assetCache; //Asset Cache 59 private IJ2KDecoder m_j2kDecodeModule;
60 private IJ2KDecoder m_j2kDecodeModule; //Our J2K module 60
61 /// <summary>
62 /// Priority queue for determining which image to send first.
63 /// </summary>
61 private C5.IntervalHeap<J2KImage> m_priorityQueue = new C5.IntervalHeap<J2KImage>(10, new J2KImageComparer()); 64 private C5.IntervalHeap<J2KImage> m_priorityQueue = new C5.IntervalHeap<J2KImage>(10, new J2KImageComparer());
65
66 /// <summary>
67 /// Used to control thread access to the priority queue.
68 /// </summary>
62 private object m_syncRoot = new object(); 69 private object m_syncRoot = new object();
63 70
64 public IClientAPI Client { get { return m_client; } } 71 /// <summary>
72 /// Client served by this image manager
73 /// </summary>
74 public IClientAPI Client { get; private set; }
75
65 public AssetBase MissingImage { get { return m_missingImage; } } 76 public AssetBase MissingImage { get { return m_missingImage; } }
66 77
67 public LLImageManager(IClientAPI client, IAssetService pAssetCache, IJ2KDecoder pJ2kDecodeModule) 78 public LLImageManager(IClientAPI client, IAssetService pAssetCache, IJ2KDecoder pJ2kDecodeModule)
68 { 79 {
69 m_client = client; 80 Client = client;
70 m_assetCache = pAssetCache; 81 m_assetCache = pAssetCache;
71 82
72 if (pAssetCache != null) 83 if (pAssetCache != null)
@@ -111,8 +122,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP
111// "[LL IMAGE MANAGER]: Received duplicate of existing request for {0}, start packet {1} from {2}", 122// "[LL IMAGE MANAGER]: Received duplicate of existing request for {0}, start packet {1} from {2}",
112// newRequest.RequestedAssetID, newRequest.PacketNumber, m_client.Name); 123// newRequest.RequestedAssetID, newRequest.PacketNumber, m_client.Name);
113 124
114 //m_log.DebugFormat("[TEX]: (UPD) ID={0}: D={1}, S={2}, P={3}", 125// m_log.DebugFormat("[TEX]: (UPD) ID={0}: D={1}, S={2}, P={3}",
115 // newRequest.RequestedAssetID, newRequest.DiscardLevel, newRequest.PacketNumber, newRequest.Priority); 126// newRequest.RequestedAssetID, newRequest.DiscardLevel, newRequest.PacketNumber, newRequest.Priority);
116 127
117 //Check the packet sequence to make sure this isn't older than 128 //Check the packet sequence to make sure this isn't older than
118 //one we've already received 129 //one we've already received
@@ -178,8 +189,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP
178 imgrequest = new J2KImage(this); 189 imgrequest = new J2KImage(this);
179 imgrequest.J2KDecoder = m_j2kDecodeModule; 190 imgrequest.J2KDecoder = m_j2kDecodeModule;
180 imgrequest.AssetService = m_assetCache; 191 imgrequest.AssetService = m_assetCache;
181 imgrequest.AgentID = m_client.AgentId; 192 imgrequest.AgentID = Client.AgentId;
182 imgrequest.InventoryAccessModule = m_client.Scene.RequestModuleInterface<IInventoryAccessModule>(); 193 imgrequest.InventoryAccessModule = Client.Scene.RequestModuleInterface<IInventoryAccessModule>();
183 imgrequest.DiscardLevel = newRequest.DiscardLevel; 194 imgrequest.DiscardLevel = newRequest.DiscardLevel;
184 imgrequest.StartPacket = Math.Max(1, newRequest.PacketNumber); 195 imgrequest.StartPacket = Math.Max(1, newRequest.PacketNumber);
185 imgrequest.Priority = newRequest.Priority; 196 imgrequest.Priority = newRequest.Priority;
@@ -210,7 +221,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP
210 if (image.IsDecoded) 221 if (image.IsDecoded)
211 { 222 {
212 int sent; 223 int sent;
213 bool imageDone = image.SendPackets(m_client, packetsToSend - packetsSent, out sent); 224 bool imageDone = image.SendPackets(Client, packetsToSend - packetsSent, out sent);
214 packetsSent += sent; 225 packetsSent += sent;
215 226
216 // If the send is complete, destroy any knowledge of this transfer 227 // If the send is complete, destroy any knowledge of this transfer
diff --git a/OpenSim/Region/ClientStack/Linden/UDP/Tests/LLImageManagerTests.cs b/OpenSim/Region/ClientStack/Linden/UDP/Tests/LLImageManagerTests.cs
index bdc9c7d..1b68d68 100644
--- a/OpenSim/Region/ClientStack/Linden/UDP/Tests/LLImageManagerTests.cs
+++ b/OpenSim/Region/ClientStack/Linden/UDP/Tests/LLImageManagerTests.cs
@@ -45,24 +45,14 @@ namespace OpenSim.Region.ClientStack.LindenUDP.Tests
45 [TestFixture] 45 [TestFixture]
46 public class LLImageManagerTests 46 public class LLImageManagerTests
47 { 47 {
48 [Test] 48 private AssetBase m_testImageAsset;
49 public void TestRequestAndSendImage() 49 private Scene scene;
50 { 50 private LLImageManager llim;
51 TestHelpers.InMethod(); 51 private TestClient tc;
52// XmlConfigurator.Configure();
53
54 UUID imageId = TestHelpers.ParseTail(0x1);
55 string creatorId = TestHelpers.ParseTail(0x2).ToString();
56 UUID userId = TestHelpers.ParseTail(0x3);
57
58 J2KDecoderModule j2kdm = new J2KDecoderModule();
59
60 Scene scene = SceneHelpers.SetupScene();
61 SceneHelpers.SetupSceneModules(scene, j2kdm);
62
63 TestClient tc = new TestClient(SceneHelpers.GenerateAgentData(userId), scene);
64 LLImageManager llim = new LLImageManager(tc, scene.AssetService, j2kdm);
65 52
53 [TestFixtureSetUp]
54 public void FixtureInit()
55 {
66 using ( 56 using (
67 Stream resource 57 Stream resource
68 = GetType().Assembly.GetManifestResourceStream( 58 = GetType().Assembly.GetManifestResourceStream(
@@ -70,14 +60,42 @@ namespace OpenSim.Region.ClientStack.LindenUDP.Tests
70 { 60 {
71 using (BinaryReader br = new BinaryReader(resource)) 61 using (BinaryReader br = new BinaryReader(resource))
72 { 62 {
73 AssetBase asset = new AssetBase(imageId, "Test Image", (sbyte)AssetType.Texture, creatorId); 63 m_testImageAsset
74 asset.Data = br.ReadBytes(99999999); 64 = new AssetBase(
75 scene.AssetService.Store(asset); 65 TestHelpers.ParseTail(0x1),
66 "Test Image",
67 (sbyte)AssetType.Texture,
68 TestHelpers.ParseTail(0x2).ToString());
69
70 m_testImageAsset.Data = br.ReadBytes(99999999);
76 } 71 }
77 } 72 }
73 }
74
75 [SetUp]
76 public void SetUp()
77 {
78 UUID userId = TestHelpers.ParseTail(0x3);
79
80 J2KDecoderModule j2kdm = new J2KDecoderModule();
81
82 scene = SceneHelpers.SetupScene();
83 SceneHelpers.SetupSceneModules(scene, j2kdm);
84
85 tc = new TestClient(SceneHelpers.GenerateAgentData(userId), scene);
86 llim = new LLImageManager(tc, scene.AssetService, j2kdm);
87 }
88
89 [Test]
90 public void TestSendImage()
91 {
92 TestHelpers.InMethod();
93// XmlConfigurator.Configure();
94
95 scene.AssetService.Store(m_testImageAsset);
78 96
79 TextureRequestArgs args = new TextureRequestArgs(); 97 TextureRequestArgs args = new TextureRequestArgs();
80 args.RequestedAssetID = TestHelpers.ParseTail(0x1); 98 args.RequestedAssetID = m_testImageAsset.FullID;
81 args.DiscardLevel = 0; 99 args.DiscardLevel = 0;
82 args.PacketNumber = 1; 100 args.PacketNumber = 1;
83 args.Priority = 5; 101 args.Priority = 5;
@@ -88,5 +106,55 @@ namespace OpenSim.Region.ClientStack.LindenUDP.Tests
88 106
89 Assert.That(tc.SentImageDataPackets.Count, Is.EqualTo(1)); 107 Assert.That(tc.SentImageDataPackets.Count, Is.EqualTo(1));
90 } 108 }
109
110 [Test]
111 public void TestDiscardImage()
112 {
113 TestHelpers.InMethod();
114// XmlConfigurator.Configure();
115
116 scene.AssetService.Store(m_testImageAsset);
117
118 TextureRequestArgs args = new TextureRequestArgs();
119 args.RequestedAssetID = m_testImageAsset.FullID;
120 args.DiscardLevel = 0;
121 args.PacketNumber = 1;
122 args.Priority = 5;
123 args.requestSequence = 1;
124 llim.EnqueueReq(args);
125
126 // Now create a discard request
127 TextureRequestArgs discardArgs = new TextureRequestArgs();
128 discardArgs.RequestedAssetID = m_testImageAsset.FullID;
129 discardArgs.DiscardLevel = -1;
130 discardArgs.PacketNumber = 1;
131 discardArgs.Priority = 0;
132 discardArgs.requestSequence = 2;
133 llim.EnqueueReq(discardArgs);
134
135 llim.ProcessImageQueue(20);
136
137 Assert.That(tc.SentImageDataPackets.Count, Is.EqualTo(0));
138 }
139
140 [Test]
141 public void TestMissingImage()
142 {
143 TestHelpers.InMethod();
144// XmlConfigurator.Configure();
145
146 TextureRequestArgs args = new TextureRequestArgs();
147 args.RequestedAssetID = m_testImageAsset.FullID;
148 args.DiscardLevel = 0;
149 args.PacketNumber = 1;
150 args.Priority = 5;
151 args.requestSequence = 1;
152
153 llim.EnqueueReq(args);
154 llim.ProcessImageQueue(20);
155
156 Assert.That(tc.SentImageDataPackets.Count, Is.EqualTo(0));
157 Assert.That(tc.SentImageNotInDatabasePackets.Count, Is.EqualTo(1));
158 }
91 } 159 }
92} \ No newline at end of file 160} \ No newline at end of file