diff options
Diffstat (limited to 'OpenSim/Region/ClientStack/Linden')
4 files changed, 78 insertions, 51 deletions
diff --git a/OpenSim/Region/ClientStack/Linden/UDP/LLUDPServer.cs b/OpenSim/Region/ClientStack/Linden/UDP/LLUDPServer.cs index 415a22e..aa10301 100644 --- a/OpenSim/Region/ClientStack/Linden/UDP/LLUDPServer.cs +++ b/OpenSim/Region/ClientStack/Linden/UDP/LLUDPServer.cs | |||
@@ -447,7 +447,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
447 | // = new TokenBucket( | 447 | // = new TokenBucket( |
448 | // string.Format("server throttle bucket for {0}", Scene.Name), null, sceneThrottleBps); | 448 | // string.Format("server throttle bucket for {0}", Scene.Name), null, sceneThrottleBps); |
449 | 449 | ||
450 | Throttle = new TokenBucket("server throttle bucket", null, sceneThrottleBps, sceneThrottleBps); | 450 | Throttle = new TokenBucket("server throttle bucket", null, 0, sceneThrottleBps); |
451 | 451 | ||
452 | ThrottleRates = new ThrottleRates(configSource); | 452 | ThrottleRates = new ThrottleRates(configSource); |
453 | 453 | ||
diff --git a/OpenSim/Region/ClientStack/Linden/UDP/LLUDPServerCommands.cs b/OpenSim/Region/ClientStack/Linden/UDP/LLUDPServerCommands.cs index 60b93ac..e0398d5 100644 --- a/OpenSim/Region/ClientStack/Linden/UDP/LLUDPServerCommands.cs +++ b/OpenSim/Region/ClientStack/Linden/UDP/LLUDPServerCommands.cs | |||
@@ -512,7 +512,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
512 | if (!ConsoleUtil.TryParseConsoleInt(MainConsole.Instance, rawValue, out newValue)) | 512 | if (!ConsoleUtil.TryParseConsoleInt(MainConsole.Instance, rawValue, out newValue)) |
513 | return; | 513 | return; |
514 | 514 | ||
515 | m_udpServer.Throttle.RequestedDripRate = newValue * 1000 / 8; | 515 | m_udpServer.Throttle.MaxDripRate = newValue * 1000 / 8; |
516 | } | 516 | } |
517 | else if (param == "max-new-client-throttle") | 517 | else if (param == "max-new-client-throttle") |
518 | { | 518 | { |
diff --git a/OpenSim/Region/ClientStack/Linden/UDP/Tests/ThrottleTests.cs b/OpenSim/Region/ClientStack/Linden/UDP/Tests/ThrottleTests.cs index 0d39c1d..912c994 100644 --- a/OpenSim/Region/ClientStack/Linden/UDP/Tests/ThrottleTests.cs +++ b/OpenSim/Region/ClientStack/Linden/UDP/Tests/ThrottleTests.cs | |||
@@ -57,51 +57,71 @@ namespace OpenSim.Region.ClientStack.LindenUDP.Tests | |||
57 | [Test] | 57 | [Test] |
58 | public void TestSetRequestDripRate() | 58 | public void TestSetRequestDripRate() |
59 | { | 59 | { |
60 | TestHelpers.InMethod(); | ||
61 | |||
60 | TokenBucket tb = new TokenBucket("tb", null, 5000, 0); | 62 | TokenBucket tb = new TokenBucket("tb", null, 5000, 0); |
61 | AssertRates(tb, 5000, 5000, 5000, 0); | 63 | AssertRates(tb, 5000, 0, 5000, 0); |
62 | 64 | ||
63 | tb.RequestedDripRate = 4000; | 65 | tb.RequestedDripRate = 4000; |
64 | AssertRates(tb, 4000, 4000, 4000, 0); | 66 | AssertRates(tb, 4000, 0, 4000, 0); |
65 | 67 | ||
66 | tb.RequestedDripRate = 6000; | 68 | tb.RequestedDripRate = 6000; |
67 | AssertRates(tb, 6000, 6000, 6000, 0); | 69 | AssertRates(tb, 6000, 0, 6000, 0); |
68 | } | 70 | } |
69 | 71 | ||
70 | [Test] | 72 | [Test] |
71 | public void TestSetRequestDripRateWithMax() | 73 | public void TestSetRequestDripRateWithMax() |
72 | { | 74 | { |
75 | TestHelpers.InMethod(); | ||
76 | |||
73 | TokenBucket tb = new TokenBucket("tb", null, 5000, 10000); | 77 | TokenBucket tb = new TokenBucket("tb", null, 5000, 10000); |
74 | AssertRates(tb, 5000, 5000, 5000, 10000); | 78 | AssertRates(tb, 5000, 0, 5000, 10000); |
75 | 79 | ||
76 | tb.RequestedDripRate = 4000; | 80 | tb.RequestedDripRate = 4000; |
77 | AssertRates(tb, 4000, 4000, 4000, 10000); | 81 | AssertRates(tb, 4000, 0, 4000, 10000); |
78 | 82 | ||
79 | tb.RequestedDripRate = 6000; | 83 | tb.RequestedDripRate = 6000; |
80 | AssertRates(tb, 6000, 6000, 6000, 10000); | 84 | AssertRates(tb, 6000, 0, 6000, 10000); |
81 | 85 | ||
82 | tb.RequestedDripRate = 12000; | 86 | tb.RequestedDripRate = 12000; |
83 | AssertRates(tb, 10000, 10000, 10000, 10000); | 87 | AssertRates(tb, 10000, 0, 10000, 10000); |
84 | } | 88 | } |
85 | 89 | ||
86 | [Test] | 90 | [Test] |
87 | public void TestSetRequestDripRateWithChildren() | 91 | public void TestSetRequestDripRateWithChildren() |
88 | { | 92 | { |
93 | TestHelpers.InMethod(); | ||
94 | |||
89 | TokenBucket tbParent = new TokenBucket("tbParent", null, 0, 0); | 95 | TokenBucket tbParent = new TokenBucket("tbParent", null, 0, 0); |
90 | TokenBucket tbChild1 = new TokenBucket("tbChild1", tbParent, 3000, 0); | 96 | TokenBucket tbChild1 = new TokenBucket("tbChild1", tbParent, 3000, 0); |
91 | TokenBucket tbChild2 = new TokenBucket("tbChild2", tbParent, 5000, 0); | 97 | TokenBucket tbChild2 = new TokenBucket("tbChild2", tbParent, 5000, 0); |
92 | 98 | ||
93 | AssertRates(tbParent, 8000, 8000, 8000, 0); | 99 | AssertRates(tbParent, 8000, 8000, 8000, 0); |
94 | AssertRates(tbChild1, 3000, 3000, 3000, 0); | 100 | AssertRates(tbChild1, 3000, 0, 3000, 0); |
95 | AssertRates(tbChild2, 5000, 5000, 5000, 0); | 101 | AssertRates(tbChild2, 5000, 0, 5000, 0); |
102 | |||
103 | // Test: Setting a parent request greater than total children requests. | ||
104 | tbParent.RequestedDripRate = 10000; | ||
105 | |||
106 | AssertRates(tbParent, 10000, 8000, 8000, 0); | ||
107 | AssertRates(tbChild1, 3000, 0, 3000, 0); | ||
108 | AssertRates(tbChild2, 5000, 0, 5000, 0); | ||
109 | |||
110 | // Test: Setting a parent request lower than total children requests. | ||
111 | tbParent.RequestedDripRate = 6000; | ||
112 | |||
113 | AssertRates(tbParent, 6000, 8000, 6000, 0); | ||
114 | AssertRates(tbChild1, 3000, 0, 6000 / 8 * 3, 0); | ||
115 | AssertRates(tbChild2, 5000, 0, 6000 / 8 * 5, 0); | ||
96 | } | 116 | } |
97 | 117 | ||
98 | private void AssertRates( | 118 | private void AssertRates( |
99 | TokenBucket tb, double requestedDripRate, double totalDripRequest, double dripRate, double maxDripRate) | 119 | TokenBucket tb, double requestedDripRate, double totalDripRequest, double dripRate, double maxDripRate) |
100 | { | 120 | { |
101 | Assert.AreEqual((int)requestedDripRate, tb.RequestedDripRate); | 121 | Assert.AreEqual((int)requestedDripRate, tb.RequestedDripRate, "Requested drip rate"); |
102 | Assert.AreEqual((int)totalDripRequest, tb.TotalDripRequest); | 122 | Assert.AreEqual((int)totalDripRequest, tb.TotalDripRequest, "Total drip request"); |
103 | Assert.AreEqual((int)dripRate, tb.DripRate); | 123 | Assert.AreEqual((int)dripRate, tb.DripRate, "Drip rate"); |
104 | Assert.AreEqual((int)maxDripRate, tb.MaxDripRate); | 124 | Assert.AreEqual((int)maxDripRate, tb.MaxDripRate, "Max drip rate"); |
105 | } | 125 | } |
106 | 126 | ||
107 | [Test] | 127 | [Test] |
@@ -360,16 +380,16 @@ namespace OpenSim.Region.ClientStack.LindenUDP.Tests | |||
360 | // "Resend={0}, Land={1}, Wind={2}, Cloud={3}, Task={4}, Texture={5}, Asset={6}, TOTAL = {7}", | 380 | // "Resend={0}, Land={1}, Wind={2}, Cloud={3}, Task={4}, Texture={5}, Asset={6}, TOTAL = {7}", |
361 | // ci.resendThrottle, ci.landThrottle, ci.windThrottle, ci.cloudThrottle, ci.taskThrottle, ci.textureThrottle, ci.assetThrottle, ci.totalThrottle); | 381 | // ci.resendThrottle, ci.landThrottle, ci.windThrottle, ci.cloudThrottle, ci.taskThrottle, ci.textureThrottle, ci.assetThrottle, ci.totalThrottle); |
362 | 382 | ||
363 | Assert.AreEqual((int)resendBytes, ci.resendThrottle); | 383 | Assert.AreEqual((int)resendBytes, ci.resendThrottle, "Resend"); |
364 | Assert.AreEqual((int)landBytes, ci.landThrottle); | 384 | Assert.AreEqual((int)landBytes, ci.landThrottle, "Land"); |
365 | Assert.AreEqual((int)windBytes, ci.windThrottle); | 385 | Assert.AreEqual((int)windBytes, ci.windThrottle, "Wind"); |
366 | Assert.AreEqual((int)cloudBytes, ci.cloudThrottle); | 386 | Assert.AreEqual((int)cloudBytes, ci.cloudThrottle, "Cloud"); |
367 | Assert.AreEqual((int)taskBytes, ci.taskThrottle); | 387 | Assert.AreEqual((int)taskBytes, ci.taskThrottle, "Task"); |
368 | Assert.AreEqual((int)textureBytes, ci.textureThrottle); | 388 | Assert.AreEqual((int)textureBytes, ci.textureThrottle, "Texture"); |
369 | Assert.AreEqual((int)assetBytes, ci.assetThrottle); | 389 | Assert.AreEqual((int)assetBytes, ci.assetThrottle, "Asset"); |
370 | Assert.AreEqual((int)totalBytes, ci.totalThrottle); | 390 | Assert.AreEqual((int)totalBytes, ci.totalThrottle, "Total"); |
371 | Assert.AreEqual((int)targetBytes, ci.targetThrottle); | 391 | Assert.AreEqual((int)targetBytes, ci.targetThrottle, "Target"); |
372 | Assert.AreEqual((int)maxBytes, ci.maxThrottle); | 392 | Assert.AreEqual((int)maxBytes, ci.maxThrottle, "Max"); |
373 | } | 393 | } |
374 | 394 | ||
375 | private void SetThrottles( | 395 | private void SetThrottles( |
diff --git a/OpenSim/Region/ClientStack/Linden/UDP/TokenBucket.cs b/OpenSim/Region/ClientStack/Linden/UDP/TokenBucket.cs index e0633d3..ab8d268 100644 --- a/OpenSim/Region/ClientStack/Linden/UDP/TokenBucket.cs +++ b/OpenSim/Region/ClientStack/Linden/UDP/TokenBucket.cs | |||
@@ -110,14 +110,19 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
110 | } | 110 | } |
111 | 111 | ||
112 | /// <summary> | 112 | /// <summary> |
113 | /// The speed limit of this bucket in bytes per second. This is the | 113 | /// The requested drip rate for this particular bucket. |
114 | /// number of tokens that are added to the bucket per quantum | ||
115 | /// </summary> | 114 | /// </summary> |
116 | /// <remarks> | 115 | /// <remarks> |
117 | /// RequestedDripRate can never be above MaxDripRate. | 116 | /// 0 then TotalDripRequest is used instead. |
118 | /// Tokens are added to the bucket any time | 117 | /// Can never be above MaxDripRate. |
118 | /// Tokens are added to the bucket at any time | ||
119 | /// <seealso cref="RemoveTokens"/> is called, at the granularity of | 119 | /// <seealso cref="RemoveTokens"/> is called, at the granularity of |
120 | /// the system tick interval (typically around 15-22ms)</remarks> | 120 | /// the system tick interval (typically around 15-22ms) |
121 | /// FIXME: It is extremely confusing to be able to set a RequestedDripRate of 0 and then receive a positive | ||
122 | /// number on get if TotalDripRequest is sent. This also stops us being able to retrieve the fact that | ||
123 | /// RequestedDripRate is set to 0. Really, this should always return m_dripRate and then we can get | ||
124 | /// (m_dripRate == 0 ? TotalDripRequest : m_dripRate) on some other properties. | ||
125 | /// </remarks> | ||
121 | protected Int64 m_dripRate; | 126 | protected Int64 m_dripRate; |
122 | public virtual Int64 RequestedDripRate | 127 | public virtual Int64 RequestedDripRate |
123 | { | 128 | { |
@@ -131,7 +136,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
131 | else | 136 | else |
132 | m_dripRate = value; | 137 | m_dripRate = value; |
133 | 138 | ||
134 | TotalDripRequest = m_dripRate; | ||
135 | m_burstRate = (Int64)((double)m_dripRate * m_quantumsPerBurst); | 139 | m_burstRate = (Int64)((double)m_dripRate * m_quantumsPerBurst); |
136 | 140 | ||
137 | if (Parent != null) | 141 | if (Parent != null) |
@@ -142,15 +146,31 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
142 | /// <summary> | 146 | /// <summary> |
143 | /// Gets the drip rate. | 147 | /// Gets the drip rate. |
144 | /// </summary> | 148 | /// </summary> |
145 | /// <value>DripRate can never be above max.</value> | 149 | /// <value> |
150 | /// DripRate can never be above max drip rate or below min drip rate. | ||
151 | /// If we are a child bucket then the drip rate return is modifed by the total load on the capacity of the | ||
152 | /// parent bucket. | ||
153 | /// </value> | ||
146 | public virtual Int64 DripRate | 154 | public virtual Int64 DripRate |
147 | { | 155 | { |
148 | get | 156 | get |
149 | { | 157 | { |
158 | double rate; | ||
159 | |||
160 | // FIXME: This doesn't properly work if we have a parent and children and a requested drip rate set | ||
161 | // on ourselves which is not equal to the child drip rates. | ||
150 | if (Parent == null) | 162 | if (Parent == null) |
151 | return Math.Min(RequestedDripRate, TotalDripRequest); | 163 | { |
152 | 164 | if (TotalDripRequest > 0) | |
153 | double rate = (double)RequestedDripRate * Parent.DripRateModifier(); | 165 | rate = Math.Min(RequestedDripRate, TotalDripRequest); |
166 | else | ||
167 | rate = RequestedDripRate; | ||
168 | } | ||
169 | else | ||
170 | { | ||
171 | rate = (double)RequestedDripRate * Parent.DripRateModifier(); | ||
172 | } | ||
173 | |||
154 | if (rate < m_minimumDripRate) | 174 | if (rate < m_minimumDripRate) |
155 | rate = m_minimumDripRate; | 175 | rate = m_minimumDripRate; |
156 | else if (MaxDripRate > 0 && rate > MaxDripRate) | 176 | else if (MaxDripRate > 0 && rate > MaxDripRate) |
@@ -163,18 +183,10 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
163 | // <summary> | 183 | // <summary> |
164 | // The maximum rate for flow control. Drip rate can never be greater than this. | 184 | // The maximum rate for flow control. Drip rate can never be greater than this. |
165 | // </summary> | 185 | // </summary> |
166 | // protected Int64 m_maxDripRate; | ||
167 | // public Int64 MaxDripRate | ||
168 | // { | ||
169 | // get { return m_maxDripRate; } | ||
170 | // //get { return (m_maxDripRate == 0 ? TotalDripRequest : m_maxDripRate); } | ||
171 | // set { m_maxDripRate = (value == 0 ? 0 : Math.Max(value, m_minimumFlow)); } | ||
172 | // } | ||
173 | public Int64 MaxDripRate { get; set; } | 186 | public Int64 MaxDripRate { get; set; } |
174 | 187 | ||
175 | /// <summary> | 188 | /// <summary> |
176 | /// The current total of the requested maximum burst rates of | 189 | /// The current total of the requested maximum burst rates of children buckets. |
177 | /// this bucket's children buckets. | ||
178 | /// </summary> | 190 | /// </summary> |
179 | public Int64 TotalDripRequest { get; protected set; } | 191 | public Int64 TotalDripRequest { get; protected set; } |
180 | 192 | ||
@@ -197,8 +209,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
197 | Parent = parent; | 209 | Parent = parent; |
198 | RequestedDripRate = dripRate; | 210 | RequestedDripRate = dripRate; |
199 | MaxDripRate = maxDripRate; | 211 | MaxDripRate = maxDripRate; |
200 | // TotalDripRequest = dripRate; // this will be overwritten when a child node registers | ||
201 | // MaxBurst = (Int64)((double)dripRate * m_quantumsPerBurst); | ||
202 | m_lastDrip = Util.EnvironmentTickCount(); | 212 | m_lastDrip = Util.EnvironmentTickCount(); |
203 | } | 213 | } |
204 | 214 | ||
@@ -243,7 +253,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
243 | lock (m_children) | 253 | lock (m_children) |
244 | { | 254 | { |
245 | m_children[child] = request; | 255 | m_children[child] = request; |
246 | // TotalDripRequest = m_children.Values.Sum(); | ||
247 | 256 | ||
248 | TotalDripRequest = 0; | 257 | TotalDripRequest = 0; |
249 | foreach (KeyValuePair<TokenBucket, Int64> cref in m_children) | 258 | foreach (KeyValuePair<TokenBucket, Int64> cref in m_children) |
@@ -255,12 +264,11 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
255 | { | 264 | { |
256 | Int64 effectiveDripRate; | 265 | Int64 effectiveDripRate; |
257 | 266 | ||
258 | if (MaxDripRate > 0) | 267 | if (RequestedDripRate > 0) |
259 | effectiveDripRate = Math.Min(MaxDripRate, TotalDripRequest); | 268 | effectiveDripRate = Math.Min(RequestedDripRate, TotalDripRequest); |
260 | else | 269 | else |
261 | effectiveDripRate = TotalDripRequest; | 270 | effectiveDripRate = TotalDripRequest; |
262 | 271 | ||
263 | //Parent.RegisterRequest(this, Math.Min(RequestedDripRate, TotalDripRequest)); | ||
264 | Parent.RegisterRequest(this, effectiveDripRate); | 272 | Parent.RegisterRequest(this, effectiveDripRate); |
265 | } | 273 | } |
266 | } | 274 | } |
@@ -274,7 +282,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
274 | lock (m_children) | 282 | lock (m_children) |
275 | { | 283 | { |
276 | m_children.Remove(child); | 284 | m_children.Remove(child); |
277 | // m_totalDripRequest = m_children.Values.Sum(); | ||
278 | 285 | ||
279 | TotalDripRequest = 0; | 286 | TotalDripRequest = 0; |
280 | foreach (KeyValuePair<TokenBucket, Int64> cref in m_children) | 287 | foreach (KeyValuePair<TokenBucket, Int64> cref in m_children) |