diff options
Diffstat (limited to '')
-rw-r--r-- | OpenSim/Region/UserStatistics/ActiveConnectionsAJAX.cs | 185 |
1 files changed, 185 insertions, 0 deletions
diff --git a/OpenSim/Region/UserStatistics/ActiveConnectionsAJAX.cs b/OpenSim/Region/UserStatistics/ActiveConnectionsAJAX.cs new file mode 100644 index 0000000..2dcd2b8 --- /dev/null +++ b/OpenSim/Region/UserStatistics/ActiveConnectionsAJAX.cs | |||
@@ -0,0 +1,185 @@ | |||
1 | using System; | ||
2 | using System.Collections; | ||
3 | using System.Collections.Generic; | ||
4 | using System.Reflection; | ||
5 | using System.Text; | ||
6 | using Mono.Data.SqliteClient; | ||
7 | using OpenMetaverse; | ||
8 | using OpenSim.Region.Environment.Scenes; | ||
9 | using OpenSim.Framework.Statistics; | ||
10 | |||
11 | namespace OpenSim.Region.UserStatistics | ||
12 | { | ||
13 | public class ActiveConnectionsAJAX : IStatsController | ||
14 | { | ||
15 | #region IStatsController Members | ||
16 | |||
17 | public Hashtable ProcessModel(Hashtable pParams) | ||
18 | { | ||
19 | |||
20 | List<Scene> m_scene = (List<Scene>)pParams["Scenes"]; | ||
21 | |||
22 | Hashtable nh = new Hashtable(); | ||
23 | nh.Add("hdata", m_scene); | ||
24 | |||
25 | return nh; | ||
26 | } | ||
27 | |||
28 | public string RenderView(Hashtable pModelResult) | ||
29 | { | ||
30 | List<Scene> all_scenes = (List<Scene>) pModelResult["hdata"]; | ||
31 | |||
32 | StringBuilder output = new StringBuilder(); | ||
33 | HTMLUtil.OL_O(ref output, ""); | ||
34 | foreach (Scene scene in all_scenes) | ||
35 | { | ||
36 | List<ScenePresence> avatarInScene = scene.GetScenePresences(); | ||
37 | |||
38 | HTMLUtil.LI_O(ref output, ""); | ||
39 | output.Append(scene.RegionInfo.RegionName); | ||
40 | HTMLUtil.OL_O(ref output, ""); | ||
41 | foreach (ScenePresence av in avatarInScene) | ||
42 | { | ||
43 | Dictionary<string,string> queues = new Dictionary<string, string>(); | ||
44 | if (av.ControllingClient is IStatsCollector) | ||
45 | { | ||
46 | IStatsCollector isClient = (IStatsCollector) av.ControllingClient; | ||
47 | queues = decodeQueueReport(isClient.Report()); | ||
48 | } | ||
49 | HTMLUtil.LI_O(ref output, ""); | ||
50 | output.Append(av.Name); | ||
51 | output.Append(" "); | ||
52 | output.Append((av.IsChildAgent ? "Child" : "Root")); | ||
53 | |||
54 | Dictionary<string, int> throttles = DecodeClientThrottles(av.ControllingClient.GetThrottlesPacked(1)); | ||
55 | |||
56 | HTMLUtil.UL_O(ref output, ""); | ||
57 | foreach (string throttlename in throttles.Keys) | ||
58 | { | ||
59 | HTMLUtil.LI_O(ref output, ""); | ||
60 | output.Append(throttlename); | ||
61 | output.Append(":"); | ||
62 | output.Append(throttles[throttlename].ToString()); | ||
63 | if (queues.ContainsKey(throttlename)) | ||
64 | { | ||
65 | output.Append("/"); | ||
66 | output.Append(queues[throttlename]); | ||
67 | } | ||
68 | HTMLUtil.LI_C(ref output); | ||
69 | } | ||
70 | if (queues.ContainsKey("Incoming") && queues.ContainsKey("Outgoing")) | ||
71 | { | ||
72 | HTMLUtil.LI_O(ref output, "red"); | ||
73 | output.Append("SEND:"); | ||
74 | output.Append(queues["Outgoing"]); | ||
75 | output.Append("/"); | ||
76 | output.Append(queues["Incoming"]); | ||
77 | HTMLUtil.LI_C(ref output); | ||
78 | } | ||
79 | |||
80 | HTMLUtil.UL_C(ref output); | ||
81 | HTMLUtil.LI_C(ref output); | ||
82 | } | ||
83 | HTMLUtil.OL_C(ref output); | ||
84 | } | ||
85 | HTMLUtil.OL_C(ref output); | ||
86 | return output.ToString(); | ||
87 | } | ||
88 | |||
89 | public Dictionary<string, int> DecodeClientThrottles(byte[] throttle) | ||
90 | { | ||
91 | Dictionary<string, int> returndict = new Dictionary<string, int>(); | ||
92 | // From mantis http://opensimulator.org/mantis/view.php?id=1374 | ||
93 | // it appears that sometimes we are receiving empty throttle byte arrays. | ||
94 | // TODO: Investigate this behaviour | ||
95 | if (throttle.Length == 0) | ||
96 | { | ||
97 | return new Dictionary<string, int>(); | ||
98 | } | ||
99 | |||
100 | int tResend = -1; | ||
101 | int tLand = -1; | ||
102 | int tWind = -1; | ||
103 | int tCloud = -1; | ||
104 | int tTask = -1; | ||
105 | int tTexture = -1; | ||
106 | int tAsset = -1; | ||
107 | int tall = -1; | ||
108 | const int singlefloat = 4; | ||
109 | |||
110 | //Agent Throttle Block contains 7 single floatingpoint values. | ||
111 | int j = 0; | ||
112 | |||
113 | // Some Systems may be big endian... | ||
114 | // it might be smart to do this check more often... | ||
115 | if (!BitConverter.IsLittleEndian) | ||
116 | for (int i = 0; i < 7; i++) | ||
117 | Array.Reverse(throttle, j + i * singlefloat, singlefloat); | ||
118 | |||
119 | // values gotten from OpenMetaverse.org/wiki/Throttle. Thanks MW_ | ||
120 | // bytes | ||
121 | // Convert to integer, since.. the full fp space isn't used. | ||
122 | tResend = (int)BitConverter.ToSingle(throttle, j); | ||
123 | returndict.Add("Resend", tResend); | ||
124 | j += singlefloat; | ||
125 | tLand = (int)BitConverter.ToSingle(throttle, j); | ||
126 | returndict.Add("Land", tLand); | ||
127 | j += singlefloat; | ||
128 | tWind = (int)BitConverter.ToSingle(throttle, j); | ||
129 | returndict.Add("Wind", tWind); | ||
130 | j += singlefloat; | ||
131 | tCloud = (int)BitConverter.ToSingle(throttle, j); | ||
132 | returndict.Add("Cloud", tCloud); | ||
133 | j += singlefloat; | ||
134 | tTask = (int)BitConverter.ToSingle(throttle, j); | ||
135 | returndict.Add("Task", tTask); | ||
136 | j += singlefloat; | ||
137 | tTexture = (int)BitConverter.ToSingle(throttle, j); | ||
138 | returndict.Add("Texture", tTexture); | ||
139 | j += singlefloat; | ||
140 | tAsset = (int)BitConverter.ToSingle(throttle, j); | ||
141 | returndict.Add("Asset", tAsset); | ||
142 | |||
143 | tall = tResend + tLand + tWind + tCloud + tTask + tTexture + tAsset; | ||
144 | returndict.Add("All", tall); | ||
145 | |||
146 | return returndict; | ||
147 | } | ||
148 | public Dictionary<string,string> decodeQueueReport(string rep) | ||
149 | { | ||
150 | Dictionary<string, string> returndic = new Dictionary<string, string>(); | ||
151 | if (rep.Length == 79) | ||
152 | { | ||
153 | int pos = 1; | ||
154 | returndic.Add("All", rep.Substring((6 * pos), 8)); pos++; | ||
155 | returndic.Add("Incoming", rep.Substring((7 * pos), 8)); pos++; | ||
156 | returndic.Add("Outgoing", rep.Substring((7 * pos) , 8)); pos++; | ||
157 | returndic.Add("Resend", rep.Substring((7 * pos) , 8)); pos++; | ||
158 | returndic.Add("Land", rep.Substring((7 * pos) , 8)); pos++; | ||
159 | returndic.Add("Wind", rep.Substring((7 * pos) , 8)); pos++; | ||
160 | returndic.Add("Cloud", rep.Substring((7 * pos) , 8)); pos++; | ||
161 | returndic.Add("Task", rep.Substring((7 * pos) , 8)); pos++; | ||
162 | returndic.Add("Texture", rep.Substring((7 * pos), 8)); pos++; | ||
163 | returndic.Add("Asset", rep.Substring((7 * pos), 8)); | ||
164 | /* | ||
165 | * return string.Format("{0,7} {1,7} {2,7} {3,7} {4,7} {5,7} {6,7} {7,7} {8,7} {9,7}", | ||
166 | SendQueue.Count(), | ||
167 | IncomingPacketQueue.Count, | ||
168 | OutgoingPacketQueue.Count, | ||
169 | ResendOutgoingPacketQueue.Count, | ||
170 | LandOutgoingPacketQueue.Count, | ||
171 | WindOutgoingPacketQueue.Count, | ||
172 | CloudOutgoingPacketQueue.Count, | ||
173 | TaskOutgoingPacketQueue.Count, | ||
174 | TextureOutgoingPacketQueue.Count, | ||
175 | AssetOutgoingPacketQueue.Count); | ||
176 | */ | ||
177 | } | ||
178 | |||
179 | |||
180 | |||
181 | return returndic; | ||
182 | } | ||
183 | #endregion | ||
184 | } | ||
185 | } | ||