Fixed some build warnings in release mode
[amule.git] / src / Statistics.h
blobb4d8f8559d4a09706e35423b28b8d8e1ff9ed8e2
1 //
2 // This file is part of the aMule Project.
3 //
4 // Copyright (c) 2003-2011 aMule Team ( admin@amule.org / http://www.amule.org )
5 // Copyright (c) 2002-2011 Merkur ( devs@emule-project.net / http://www.emule-project.net )
6 // Copyright (c) 2005-2011 Dévai Tamás ( gonosztopi@amule.org )
7 //
8 // Any parts of this program derived from the xMule, lMule or eMule project,
9 // or contributed by third-party developers are copyrighted by their
10 // respective authors.
12 // This program is free software; you can redistribute it and/or modify
13 // it under the terms of the GNU General Public License as published by
14 // the Free Software Foundation; either version 2 of the License, or
15 // (at your option) any later version.
17 // This program is distributed in the hope that it will be useful,
18 // but WITHOUT ANY WARRANTY; without even the implied warranty of
19 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 // GNU General Public License for more details.
22 // You should have received a copy of the GNU General Public License
23 // along with this program; if not, write to the Free Software
24 // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
27 #ifndef STATISTICS_H
28 #define STATISTICS_H
30 #include "Constants.h" // Needed for StatsGraphType
31 #include "StatTree.h" // Needed for CStatTreeItem* classes
33 #include <deque> // Needed for std::deque
35 typedef struct UpdateInfo {
36 double timestamp;
37 float downloads[3];
38 float uploads[3];
39 float connections[3];
40 float kadnodes[3];
41 } GraphUpdateInfo;
43 typedef struct HistoryRecord {
44 double kBytesSent;
45 double kBytesReceived;
46 float kBpsUpCur;
47 float kBpsDownCur;
48 double sTimestamp;
49 uint16 cntDownloads;
50 uint16 cntUploads;
51 uint16 cntConnections;
52 uint16 kadNodesCur;
53 uint64 kadNodesTotal;
54 } HR;
57 #ifndef CLIENT_GUI
59 /**
60 * Counts precise rate/average on added bytes/values.
62 * @note This class is MT-safe.
64 class CPreciseRateCounter {
65 friend class CStatistics; // for playing dirty tricks to compute running average :P
66 public:
68 /**
69 * Constructor
71 * @param timespan Desired timespan for rate calculations.
72 * @param count_average Counts average instead of rate.
74 CPreciseRateCounter(uint32_t timespan, bool count_average = false)
75 : m_timespan(timespan), m_total(0), m_rate(0.0), m_max_rate(0.0), m_tmp_sum(0), m_count_average(count_average)
77 if (!count_average) {
78 uint64_t cur_time = GetTickCount64();
79 uint64_t target_time = cur_time - timespan;
80 while (cur_time > target_time) {
81 m_tick_history.push_front(cur_time);
82 m_byte_history.push_front(0);
83 cur_time -= 100; // default update period
85 m_tick_history.push_front(cur_time);
89 /**
90 * Calculate current rate.
92 * This function should be called reasonably often, to
93 * keep rates up-to-date, and prevent history growing
94 * to the skies.
96 void CalculateRate(uint64_t now);
98 /**
99 * Get current rate.
101 * @return Current rate in bytes/second.
103 double GetRate() { wxMutexLocker lock(m_mutex); return m_rate; };
106 * Gets ever seen maximal rate.
108 * @return The maximal rate which occured.
110 double GetMaxRate() { wxMutexLocker lock(m_mutex); return m_max_rate; }
113 * Sets desired timespan for rate calculations.
115 * If new timespan is greater than the old was, then the change
116 * takes effect with time. The exact time needed for the change
117 * to take effect is new minus old value of the timespan.
119 * If the new timespan is lower than the old, the change takes
120 * effect immediately at the next call to CalculateRate().
122 void SetTimespan(uint32_t timespan) { wxMutexLocker lock(m_mutex); m_timespan = timespan; }
125 * Add bytes to be tracked for rate-counting.
127 void operator+=(uint32_t bytes) { wxMutexLocker lock(m_mutex); m_tmp_sum += bytes; }
129 protected:
131 std::deque<uint32> m_byte_history;
132 std::deque<uint64> m_tick_history;
133 uint32_t m_timespan;
134 uint32_t m_total;
135 double m_rate;
136 double m_max_rate;
137 uint32_t m_tmp_sum;
138 wxMutex m_mutex;
139 bool m_count_average;
143 class CECTag;
146 * Stat tree item for rates/averages.
148 class CStatTreeItemRateCounter : public CStatTreeItemBase, public CPreciseRateCounter {
149 public:
152 * @see CStatTreeItemBase::CStatTreeItemBase, CPreciseRateCounter::CPreciseRateCounter
154 * @param show_maxrate If true, shows max rate instead of current rate.
156 CStatTreeItemRateCounter(const wxString& label, bool show_maxrate, uint32_t timespan, bool count_average = false)
157 : CStatTreeItemBase(label, stNone), CPreciseRateCounter(timespan, count_average), m_show_maxrate(show_maxrate)
160 #ifndef AMULE_DAEMON
162 * @see CStatTreeItemBase::GetDisplayString()
164 virtual wxString GetDisplayString() const;
165 #endif
167 protected:
169 * Add values to EC tag being generated.
171 * @param tag The tag to which values should be added.
173 * @see CStatTreeItemBase::AddECValues
175 virtual void AddECValues(CECTag* tag) const;
177 //! Whether to show max rate instead of actual rate.
178 bool m_show_maxrate;
183 * Stat tree item for Peak Connections.
185 class CStatTreeItemPeakConnections : public CStatTreeItemBase {
186 public:
189 * @see CStatTreeItemBase::CStatTreeItemBase
191 CStatTreeItemPeakConnections(const wxString& label)
192 : CStatTreeItemBase(label)
195 #ifndef AMULE_DAEMON
197 * @see CStatTreeItemBase::GetDisplayString()
199 virtual wxString GetDisplayString() const;
200 #endif
202 protected:
204 * Add values to EC tag being generated.
206 * @param tag The tag to which values should be added.
208 * @see CStatTreeItemBase::AddECValues
210 virtual void AddECValues(CECTag* tag) const;
214 class CUpDownClient;
216 class CStatistics {
217 friend class CStatisticsDlg; // to access CStatistics::GetTreeRoot()
218 public:
219 CStatistics();
220 ~CStatistics();
222 static void Load();
223 static void Save();
225 /* Statistics graph functions */
227 void RecordHistory();
228 unsigned GetHistoryForWeb(unsigned cntPoints, double sStep, double *sStart, uint32 **graphData);
229 unsigned GetHistory(unsigned cntPoints, double sStep, double sFinal, const std::vector<float *> &ppf, StatsGraphType which_graph);
230 GraphUpdateInfo GetPointsForUpdate();
232 /* Statistics tree functions */
234 void UpdateStatsTree();
236 /* Access to the tree */
238 // uptime
239 static uint64 GetUptimeMillis() { return s_uptime->GetTimerValue(); }
240 static uint64 GetUptimeSeconds() { return s_uptime->GetTimerSeconds(); }
241 static uint64 GetStartTime() { return s_uptime->GetTimerStart(); }
243 // Upload
244 static uint64 GetTotalSentBytes() { return s_totalSent; }
245 static uint64 GetSessionSentBytes() { return (*s_sessionUpload); }
246 static void AddUpOverheadFileRequest(uint32 size) { (*s_fileReqUpOverhead) += size; (*s_upOverheadRate) += size; }
247 static void AddUpOverheadSourceExchange(uint32 size){ (*s_sourceXchgUpOverhead) += size; (*s_upOverheadRate) += size; }
248 static void AddUpOverheadServer(uint32 size) { (*s_serverUpOverhead) += size; (*s_upOverheadRate) += size; }
249 static void AddUpOverheadKad(uint32 size) { (*s_kadUpOverhead) += size; (*s_upOverheadRate) += size; }
250 static void AddUpOverheadCrypt(uint32_t size) { (*s_cryptUpOverhead) += size; }
251 static void AddUpOverheadOther(uint32 size) { (*s_totalUpOverhead) += size; (*s_upOverheadRate) += size; }
252 static double GetUpOverheadRate() { return s_upOverheadRate->GetRate(); }
253 static void AddSuccessfulUpload() { ++(*s_totalSuccUploads); }
254 static void AddFailedUpload() { ++(*s_totalFailedUploads); }
255 static void AddUploadTime(uint32 time) { (*s_totalUploadTime) += time; }
256 static void AddUploadingClient() { ++(*s_activeUploads); }
257 static void RemoveUploadingClient() { --(*s_activeUploads); }
258 static uint32 GetActiveUploadsCount() { return (*s_activeUploads); }
259 static void AddWaitingClient() { ++(*s_waitingUploads); }
260 static void RemoveWaitingClient() { --(*s_waitingUploads); }
261 static uint32 GetWaitingUserCount() { return (*s_waitingUploads); }
262 static double GetUploadRate() { return s_uploadrate->GetRate(); }
264 // Download
265 static uint64 GetTotalReceivedBytes() { return s_totalReceived; }
266 static uint64 GetSessionReceivedBytes() { return (*s_sessionDownload); }
267 static void AddDownOverheadFileRequest(uint32 size) { (*s_fileReqDownOverhead) += size; (*s_downOverheadRate) += size; }
268 static void AddDownOverheadSourceExchange(uint32 size){ (*s_sourceXchgDownOverhead) += size; (*s_downOverheadRate) += size; }
269 static void AddDownOverheadServer(uint32 size) { (*s_serverDownOverhead) += size; (*s_downOverheadRate) += size; }
270 static void AddDownOverheadKad(uint32 size) { (*s_kadDownOverhead) += size; (*s_downOverheadRate) += size; }
271 static void AddDownOverheadCrypt(uint32_t size) { (*s_cryptDownOverhead) += size; }
272 static void AddDownOverheadOther(uint32 size) { (*s_totalDownOverhead) += size; (*s_downOverheadRate) += size; }
273 static double GetDownOverheadRate() { return s_downOverheadRate->GetRate(); }
274 static void AddFoundSource() { ++(*s_foundSources); }
275 static void RemoveFoundSource() { --(*s_foundSources); }
276 static uint32 GetFoundSources() { return (*s_foundSources); }
277 static void AddSourceOrigin(unsigned origin);
278 static void RemoveSourceOrigin(unsigned origin);
279 static void AddDownloadingSource() { ++(*s_activeDownloads); }
280 static void RemoveDownloadingSource() { --(*s_activeDownloads); }
281 static uint32 GetDownloadingSources() { return (*s_activeDownloads); }
282 static double GetDownloadRate() { return s_downloadrate->GetRate(); }
284 // Connection
285 static CStatTreeItemTimer* GetServerConnectTimer() { return s_sinceConnected; }
286 static void AddReconnect() { ++(*s_reconnects); }
287 static void AddActiveConnection() { ++(*s_activeConnections); }
288 static void RemoveActiveConnection() { --(*s_activeConnections); }
289 static uint32 GetActiveConnections() { return s_activeConnections->GetValue(); }
290 static uint32 GetPeakConnections() { return s_activeConnections->GetMaxValue(); }
291 static void AddMaxConnectionLimitReached() { ++(*s_limitReached); }
293 // Clients
294 static void AddFilteredClient() { ++(*s_filtered); }
295 static void AddUnknownClient() { ++(*s_unknown); }
296 static void RemoveUnknownClient() { --(*s_unknown); }
297 static void AddKnownClient(CUpDownClient *pClient);
298 static void RemoveKnownClient(uint32 clientSoft, uint32 clientVersion, const wxString& OSInfo);
299 #ifdef __DEBUG__
300 static void SocketAssignedToClient() { ++(*s_hasSocket); }
301 static void SocketUnassignedFromClient() { --(*s_hasSocket); }
302 #endif
303 static uint32 GetBannedCount() { return (*s_banned); }
304 static void AddBannedClient() { ++(*s_banned); }
305 static void RemoveBannedClient() { --(*s_banned); }
307 // Servers
308 static void AddServer() { ++(*s_totalServers); }
309 static void DeleteServer() { ++(*s_deletedServers); --(*s_totalServers); }
310 static void DeleteAllServers() { (*s_deletedServers) += (*s_totalServers); (*s_totalServers) = 0; }
311 static void AddFilteredServer() { ++(*s_filteredServers); }
313 // Shared files
314 static void ClearSharedFilesInfo() { (*s_numberOfShared) = 0; (*s_sizeOfShare) = 0; }
315 static void AddSharedFile(uint64 size) { ++(*s_numberOfShared); (*s_sizeOfShare) += size; }
316 static void RemoveSharedFile(uint64 size) { --(*s_numberOfShared); (*s_sizeOfShare) -= size; }
317 static uint32 GetSharedFileCount() { return (*s_numberOfShared); }
319 // Kad nodes
320 static void AddKadNode() { ++s_kadNodesCur; }
321 static void RemoveKadNode() { --s_kadNodesCur; }
324 // Other
325 static void CalculateRates();
327 static void AddReceivedBytes(uint32 bytes)
329 if (!s_sinceFirstTransfer->IsRunning()) {
330 s_sinceFirstTransfer->StartTimer();
333 (*s_sessionDownload) += bytes;
334 (*s_downloadrate) += bytes;
335 s_totalReceived += bytes;
336 s_statsNeedSave = true;
339 static void AddSentBytes(uint32 bytes)
341 if (!s_sinceFirstTransfer->IsRunning()) {
342 s_sinceFirstTransfer->StartTimer();
345 (*s_sessionUpload) += bytes;
346 (*s_uploadrate) += bytes;
347 s_totalSent += bytes;
348 s_statsNeedSave = true;
351 static void AddDownloadFromSoft(uint8 SoftType, uint32 bytes);
352 static void AddUploadToSoft(uint8 SoftType, uint32 bytes);
354 // EC
355 static CECTag* GetECStatTree(uint8 tree_capping_value) { return s_statTree->CreateECTag(tree_capping_value); }
357 void SetAverageMinutes(uint8 minutes) { average_minutes = minutes; }
359 private:
360 std::list<HR> listHR;
361 typedef std::list<HR>::iterator listPOS;
362 typedef std::list<HR>::reverse_iterator listRPOS;
364 /* Graph-related functions */
366 void ComputeAverages(HR **pphr, listRPOS pos, unsigned cntFilled,
367 double sStep, const std::vector<float *> &ppf, StatsGraphType which_graph);
369 int GetPointsPerRange()
371 return (1280/2) - 80; // This used to be a calc. based on GUI width
374 /* Graphs-related vars */
376 CPreciseRateCounter m_graphRunningAvgDown;
377 CPreciseRateCounter m_graphRunningAvgUp;
378 CPreciseRateCounter m_graphRunningAvgKad;
381 uint8 average_minutes;
382 int nHistRanges;
383 int bitsHistClockMask;
384 int nPointsPerRange;
385 listPOS* aposRecycle;
387 HR hrInit;
389 /* Rate/Average counters */
390 static CPreciseRateCounter* s_upOverheadRate;
391 static CPreciseRateCounter* s_downOverheadRate;
392 static CStatTreeItemRateCounter* s_uploadrate;
393 static CStatTreeItemRateCounter* s_downloadrate;
395 /* Tree-related functions */
397 static void InitStatsTree();
399 static CStatTreeItemBase* GetTreeRoot() { return s_statTree; }
401 /* Tree-related vars */
403 // the tree
404 static CStatTreeItemBase* s_statTree;
406 // Uptime
407 static CStatTreeItemTimer* s_uptime;
409 // Upload
410 static CStatTreeItemUlDlCounter* s_sessionUpload;
411 static CStatTreeItemPacketTotals* s_totalUpOverhead;
412 static CStatTreeItemPackets* s_fileReqUpOverhead;
413 static CStatTreeItemPackets* s_sourceXchgUpOverhead;
414 static CStatTreeItemPackets* s_serverUpOverhead;
415 static CStatTreeItemPackets* s_kadUpOverhead;
416 static CStatTreeItemCounter* s_cryptUpOverhead;
417 static CStatTreeItemNativeCounter* s_activeUploads;
418 static CStatTreeItemNativeCounter* s_waitingUploads;
419 static CStatTreeItemCounter* s_totalSuccUploads;
420 static CStatTreeItemCounter* s_totalFailedUploads;
421 static CStatTreeItemCounter* s_totalUploadTime;
423 // Download
424 static CStatTreeItemUlDlCounter* s_sessionDownload;
425 static CStatTreeItemPacketTotals* s_totalDownOverhead;
426 static CStatTreeItemPackets* s_fileReqDownOverhead;
427 static CStatTreeItemPackets* s_sourceXchgDownOverhead;
428 static CStatTreeItemPackets* s_serverDownOverhead;
429 static CStatTreeItemPackets* s_kadDownOverhead;
430 static CStatTreeItemCounter* s_cryptDownOverhead;
431 static CStatTreeItemNativeCounter* s_foundSources;
432 static CStatTreeItemNativeCounter* s_activeDownloads;
434 // Connection
435 static CStatTreeItemReconnects* s_reconnects;
436 static CStatTreeItemTimer* s_sinceFirstTransfer;
437 static CStatTreeItemTimer* s_sinceConnected;
438 static CStatTreeItemCounterMax* s_activeConnections;
439 static CStatTreeItemMaxConnLimitReached* s_limitReached;
440 static CStatTreeItemSimple* s_avgConnections;
442 // Clients
443 static CStatTreeItemHiddenCounter* s_clients;
444 static CStatTreeItemCounter* s_unknown;
445 //static CStatTreeItem s_lowID;
446 //static CStatTreeItem s_secIdentOnOff;
447 #ifdef __DEBUG__
448 static CStatTreeItemNativeCounter* s_hasSocket;
449 #endif
450 static CStatTreeItemNativeCounter* s_filtered;
451 static CStatTreeItemNativeCounter* s_banned;
453 // Servers
454 static CStatTreeItemSimple* s_workingServers;
455 static CStatTreeItemSimple* s_failedServers;
456 static CStatTreeItemNativeCounter* s_totalServers;
457 static CStatTreeItemNativeCounter* s_deletedServers;
458 static CStatTreeItemNativeCounter* s_filteredServers;
459 static CStatTreeItemSimple* s_usersOnWorking;
460 static CStatTreeItemSimple* s_filesOnWorking;
461 static CStatTreeItemSimple* s_totalUsers;
462 static CStatTreeItemSimple* s_totalFiles;
463 static CStatTreeItemSimple* s_serverOccupation;
465 // Shared files
466 static CStatTreeItemCounter* s_numberOfShared;
467 static CStatTreeItemCounter* s_sizeOfShare;
469 // Kad nodes
470 static uint64_t s_kadNodesTotal;
471 static uint16_t s_kadNodesCur;
473 // Total sent/received bytes
474 static uint64_t s_totalSent;
475 static uint64_t s_totalReceived;
477 static bool s_statsNeedSave;
480 #else /* CLIENT_GUI */
482 class CECPacket;
483 class CRemoteConnect;
485 enum StatDataIndex {
486 sdUpload,
487 sdUpOverhead,
488 sdDownload,
489 sdDownOverhead,
490 sdWaitingClients,
491 sdBannedClients,
492 sdED2KUsers,
493 sdKadUsers,
494 sdED2KFiles,
495 sdKadFiles,
496 sdKadFirewalledUDP,
497 sdKadIndexedSources,
498 sdKadIndexedKeywords,
499 sdKadIndexedNotes,
500 sdKadIndexedLoad,
501 sdKadIPAdress,
502 sdBuddyStatus,
503 sdBuddyIP,
504 sdBuddyPort,
505 sdKadInLanMode,
506 sdTotalSentBytes,
507 sdTotalReceivedBytes,
508 sdSharedFileCount,
510 sdTotalItems
513 class CStatistics {
514 friend class CStatisticsDlg; // to access CStatistics::GetTreeRoot()
516 private:
517 CRemoteConnect &m_conn;
518 static CStatTreeItemBase* s_statTree;
519 static uint64 s_start_time;
520 static uint64 s_statData[sdTotalItems];
521 uint8 average_minutes;
523 public:
524 CStatistics(CRemoteConnect &conn);
525 ~CStatistics();
527 static uint64 GetUptimeMillis();
528 static uint64 GetUptimeSeconds();
530 static uint64 GetTotalSentBytes() { return s_statData[sdTotalSentBytes]; }
531 static double GetUploadRate() { return (double)s_statData[sdUpload]; }
532 static double GetUpOverheadRate() { return (double)s_statData[sdUpOverhead]; }
534 static uint64 GetTotalReceivedBytes() { return s_statData[sdTotalReceivedBytes]; }
535 static double GetDownloadRate() { return (double)s_statData[sdDownload]; }
536 static double GetDownOverheadRate() { return (double)s_statData[sdDownOverhead]; }
538 static uint32 GetWaitingUserCount() { return s_statData[sdWaitingClients]; }
539 static uint32 GetBannedCount() { return s_statData[sdBannedClients]; }
541 static uint32 GetSharedFileCount() { return s_statData[sdSharedFileCount]; }
543 static uint32 GetED2KUsers() { return s_statData[sdED2KUsers]; }
544 static uint32 GetKadUsers() { return s_statData[sdKadUsers]; }
545 static uint32 GetED2KFiles() { return s_statData[sdED2KFiles]; }
546 static uint32 GetKadFiles() { return s_statData[sdKadFiles]; }
548 static bool IsFirewalledKadUDP() { return s_statData[sdKadFirewalledUDP] != 0; }
549 static uint32 GetKadIndexedSources() { return s_statData[sdKadIndexedSources]; }
550 static uint32 GetKadIndexedKeywords() { return s_statData[sdKadIndexedKeywords]; }
551 static uint32 GetKadIndexedNotes() { return s_statData[sdKadIndexedNotes]; }
552 static uint32 GetKadIndexedLoad() { return s_statData[sdKadIndexedLoad]; }
553 static uint32 GetKadIPAdress() { return s_statData[sdKadIPAdress]; }
554 static uint8 GetBuddyStatus() { return s_statData[sdBuddyStatus]; }
555 static uint32 GetBuddyIP() { return s_statData[sdBuddyIP]; }
556 static uint32 GetBuddyPort() { return s_statData[sdBuddyPort]; }
557 static bool IsKadRunningInLanMode() { return s_statData[sdKadInLanMode] != 0; }
559 static void UpdateStats(const CECPacket* stats);
561 void UpdateStatsTree();
562 void RebuildStatTreeRemote(const CECTag *);
563 void SetAverageMinutes(uint8 minutes) { average_minutes = minutes; }
565 private:
566 static CStatTreeItemBase* GetTreeRoot() { return s_statTree; }
569 #endif /* !CLIENT_GUI / CLIENT_GUI */
573 * Shortcut for CStatistics
575 typedef CStatistics theStats;
577 #endif // STATISTICS_H
578 // File_checked_for_headers