diff options
Diffstat (limited to 'OpenSim')
3 files changed, 153 insertions, 5 deletions
diff --git a/OpenSim/Framework/Communications/Limit/RepeatLimitStrategy.cs b/OpenSim/Framework/Communications/Limit/RepeatLimitStrategy.cs index 82122fc..85ff2bd 100644 --- a/OpenSim/Framework/Communications/Limit/RepeatLimitStrategy.cs +++ b/OpenSim/Framework/Communications/Limit/RepeatLimitStrategy.cs | |||
@@ -80,7 +80,7 @@ namespace OpenSim.Framework.Communications.Limit | |||
80 | /// </summary> | 80 | /// </summary> |
81 | public bool IsFirstRefusal(TId id) | 81 | public bool IsFirstRefusal(TId id) |
82 | { | 82 | { |
83 | if (m_maxRequests + 1 == requestCounts[id]) | 83 | if (requestCounts.ContainsKey(id) && m_maxRequests + 1 == requestCounts[id]) |
84 | { | 84 | { |
85 | return true; | 85 | return true; |
86 | } | 86 | } |
diff --git a/OpenSim/Framework/Communications/Limit/TimeLimitStrategy.cs b/OpenSim/Framework/Communications/Limit/TimeLimitStrategy.cs new file mode 100755 index 0000000..b2b4f14 --- /dev/null +++ b/OpenSim/Framework/Communications/Limit/TimeLimitStrategy.cs | |||
@@ -0,0 +1,140 @@ | |||
1 | /* | ||
2 | * Copyright (c) Contributors, http://opensimulator.org/ | ||
3 | * See CONTRIBUTORS.TXT for a full list of copyright holders. | ||
4 | * | ||
5 | * Redistribution and use in source and binary forms, with or without | ||
6 | * modification, are permitted provided that the following conditions are met: | ||
7 | * * Redistributions of source code must retain the above copyright | ||
8 | * notice, this list of conditions and the following disclaimer. | ||
9 | * * Redistributions in binary form must reproduce the above copyright | ||
10 | * notice, this list of conditions and the following disclaimer in the | ||
11 | * documentation and/or other materials provided with the distribution. | ||
12 | * * Neither the name of the OpenSim Project nor the | ||
13 | * names of its contributors may be used to endorse or promote products | ||
14 | * derived from this software without specific prior written permission. | ||
15 | * | ||
16 | * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY | ||
17 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | ||
18 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
19 | * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY | ||
20 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | ||
21 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
22 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | ||
23 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ||
24 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
25 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
26 | */ | ||
27 | |||
28 | using System; | ||
29 | using System.Collections.Generic; | ||
30 | |||
31 | namespace OpenSim.Framework.Communications.Limit | ||
32 | { | ||
33 | /// <summary> | ||
34 | /// Limit requests by discarding repeat attempts that occur within a given time period | ||
35 | /// | ||
36 | /// XXX Don't use this for limiting texture downloading, at least not until we better handle multiple requests | ||
37 | /// for the same texture at different resolutions. | ||
38 | /// </summary> | ||
39 | public class TimeLimitStrategy<TId> : IRequestLimitStrategy<TId> | ||
40 | { | ||
41 | /// <summary> | ||
42 | /// Record the time at which an asset request occurs. | ||
43 | /// </summary> | ||
44 | private readonly Dictionary<TId, Request> requests = new Dictionary<TId, Request>(); | ||
45 | |||
46 | /// <summary> | ||
47 | /// The minimum time period between which requests for the same data will be serviced. | ||
48 | /// </summary> | ||
49 | private readonly TimeSpan m_repeatPeriod; | ||
50 | public TimeSpan RepeatPeriod | ||
51 | { | ||
52 | get { return m_repeatPeriod; } | ||
53 | } | ||
54 | |||
55 | /// <summary></summary> | ||
56 | /// <param name="repeatPeriod"></param> | ||
57 | public TimeLimitStrategy(TimeSpan repeatPeriod) | ||
58 | { | ||
59 | m_repeatPeriod = repeatPeriod; | ||
60 | } | ||
61 | |||
62 | /// <summary> | ||
63 | /// <see cref="IRequestLimitStrategy"/> | ||
64 | /// </summary> | ||
65 | public bool AllowRequest(TId id) | ||
66 | { | ||
67 | if (IsMonitoringRequests(id)) | ||
68 | { | ||
69 | DateTime now = DateTime.Now; | ||
70 | TimeSpan elapsed = now - requests[id].Time; | ||
71 | |||
72 | if (elapsed < RepeatPeriod) | ||
73 | { | ||
74 | requests[id].Refusals += 1; | ||
75 | return false; | ||
76 | } | ||
77 | |||
78 | requests[id].Time = now; | ||
79 | } | ||
80 | |||
81 | return true; | ||
82 | } | ||
83 | |||
84 | /// <summary> | ||
85 | /// <see cref="IRequestLimitStrategy"/> | ||
86 | /// </summary> | ||
87 | public bool IsFirstRefusal(TId id) | ||
88 | { | ||
89 | if (IsMonitoringRequests(id)) | ||
90 | { | ||
91 | if (1 == requests[id].Refusals) | ||
92 | { | ||
93 | return true; | ||
94 | } | ||
95 | } | ||
96 | |||
97 | return false; | ||
98 | } | ||
99 | |||
100 | /// <summary> | ||
101 | /// <see cref="IRequestLimitStrategy"/> | ||
102 | /// </summary> | ||
103 | public void MonitorRequests(TId id) | ||
104 | { | ||
105 | if (!IsMonitoringRequests(id)) | ||
106 | { | ||
107 | requests.Add(id, new Request(System.DateTime.Now)); | ||
108 | } | ||
109 | } | ||
110 | |||
111 | /// <summary> | ||
112 | /// <see cref="IRequestLimitStrategy"/> | ||
113 | /// </summary> | ||
114 | public bool IsMonitoringRequests(TId id) | ||
115 | { | ||
116 | return requests.ContainsKey(id); | ||
117 | } | ||
118 | } | ||
119 | |||
120 | /// <summary> | ||
121 | /// Private request details. | ||
122 | /// </summary> | ||
123 | class Request | ||
124 | { | ||
125 | /// <summary> | ||
126 | /// Time of last request | ||
127 | /// </summary> | ||
128 | public DateTime Time; | ||
129 | |||
130 | /// <summary> | ||
131 | /// Number of refusals associated with this request | ||
132 | /// </summary> | ||
133 | public int Refusals; | ||
134 | |||
135 | public Request(DateTime time) | ||
136 | { | ||
137 | Time = time; | ||
138 | } | ||
139 | } | ||
140 | } | ||
diff --git a/OpenSim/Region/Environment/Modules/UserTextureDownloadService.cs b/OpenSim/Region/Environment/Modules/UserTextureDownloadService.cs index 62904d8..f0a2517 100644 --- a/OpenSim/Region/Environment/Modules/UserTextureDownloadService.cs +++ b/OpenSim/Region/Environment/Modules/UserTextureDownloadService.cs | |||
@@ -50,12 +50,16 @@ namespace OpenSim.Region.Environment.Modules | |||
50 | = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); | 50 | = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); |
51 | 51 | ||
52 | /// <summary> | 52 | /// <summary> |
53 | /// We will allow the client to request the same texture n times before dropping further requests | 53 | /// We will allow the client to request the same missing texture n times before dropping further requests |
54 | /// | ||
55 | /// This number includes repeated requests for the same texture at different resolutions (which we don't | ||
56 | /// currently handle properly as far as I know). However, this situation should be handled in a more | ||
57 | /// sophisticated way. | ||
54 | /// </summary> | 58 | /// </summary> |
55 | private static readonly int MAX_ALLOWED_TEXTURE_REQUESTS = 5; | 59 | private static readonly int MAX_ALLOWED_TEXTURE_REQUESTS = 5; |
56 | 60 | ||
57 | /// <summary> | 61 | /// <summary> |
58 | /// We're going to limit repeated requests for the same missing texture. | 62 | /// We're going to limit requests for the same missing texture. |
59 | /// XXX This is really a temporary solution to deal with the situation where a client continually requests | 63 | /// XXX This is really a temporary solution to deal with the situation where a client continually requests |
60 | /// the same missing textures | 64 | /// the same missing textures |
61 | /// </summary> | 65 | /// </summary> |
@@ -63,10 +67,10 @@ namespace OpenSim.Region.Environment.Modules | |||
63 | = new RepeatLimitStrategy<LLUUID>(MAX_ALLOWED_TEXTURE_REQUESTS); | 67 | = new RepeatLimitStrategy<LLUUID>(MAX_ALLOWED_TEXTURE_REQUESTS); |
64 | 68 | ||
65 | /// <summary> | 69 | /// <summary> |
66 | /// XXX Also going to limit repeated requests for found textures. | 70 | /// XXX Also going to limit requests for found textures. |
67 | /// </summary> | 71 | /// </summary> |
68 | private readonly IRequestLimitStrategy<LLUUID> foundTextureLimitStrategy | 72 | private readonly IRequestLimitStrategy<LLUUID> foundTextureLimitStrategy |
69 | = new RepeatLimitStrategy<LLUUID>(MAX_ALLOWED_TEXTURE_REQUESTS); | 73 | = new RepeatLimitStrategy<LLUUID>(MAX_ALLOWED_TEXTURE_REQUESTS); |
70 | 74 | ||
71 | /// <summary> | 75 | /// <summary> |
72 | /// Holds texture senders before they have received the appropriate texture from the asset cache. | 76 | /// Holds texture senders before they have received the appropriate texture from the asset cache. |
@@ -115,6 +119,10 @@ namespace OpenSim.Region.Environment.Modules | |||
115 | { | 119 | { |
116 | if (!foundTextureLimitStrategy.AllowRequest(e.RequestedAssetID)) | 120 | if (!foundTextureLimitStrategy.AllowRequest(e.RequestedAssetID)) |
117 | { | 121 | { |
122 | // m_log.DebugFormat( | ||
123 | // "[USER TEXTURE DOWNLOAD SERVICE]: Refusing request for {0} from client {1}", | ||
124 | // e.RequestedAssetID, m_client.AgentId); | ||
125 | |||
118 | return; | 126 | return; |
119 | } | 127 | } |
120 | else if (!missingTextureLimitStrategy.AllowRequest(e.RequestedAssetID)) | 128 | else if (!missingTextureLimitStrategy.AllowRequest(e.RequestedAssetID)) |