FS2_Open
Open source remastering of the Freespace 2 engine
multi_rate.cpp
Go to the documentation of this file.
1 /*
2  * Copyright (C) Volition, Inc. 1999. All rights reserved.
3  *
4  * All source code herein is the property of Volition, Inc. You may not sell
5  * or otherwise commercially exploit the source or things you created based on the
6  * source.
7  *
8 */
9 
10 
11 
12 
13 // -----------------------------------------------------------------------------------------------------------------------
14 // MULTI RATE DEFINES/VARS
15 //
16 
17 #include "network/multi_rate.h"
18 
19 #ifdef MULTI_RATE
20 
21 #include "io/timer.h"
22 #include "globalincs/alphacolors.h"
23 
24 
25 
26 // how many records in the past we'll keep track of
27 #define NUM_UPDATE_RECORDS 5
28 
29 // rate monitoring info
30 typedef struct mr_info {
31  // type
32  char type[MAX_RATE_TYPE_LEN+1];
33 
34  // all time info
35  int total_bytes; // total bytes alltime
36 
37  // per second info
38  int stamp_second; // stamp for one second
39  int bytes_second; // how many bytes we've sent in the last second
40  int records_second[NUM_UPDATE_RECORDS]; // records
41  int records_second_count; // how many records we have
42  float avg_second; // avg bytes/sec
43 
44  // per frame info
45  int bytes_frame; // how many bytes we've sent this frame
46  int records_frame[NUM_UPDATE_RECORDS]; // records
47  int records_frame_count; // how many records we have
48  float avg_frame; // avg bytes/frame
49 } mr_info;
50 
51 
52 // all records
53 mr_info Multi_rate[MAX_RATE_PLAYERS][MAX_RATE_TYPES];
54 
55 
56 // -----------------------------------------------------------------------------------------------------------------------
57 // MULTI RATE FUNCTIONS
58 //
59 
60 // notify of a player join
61 void multi_rate_reset(int np_index)
62 {
63  int idx;
64 
65  // sanity checks
66  if((np_index < 0) || (np_index >= MAX_RATE_PLAYERS)){
67  return;
68  }
69 
70  // blast the index clear
71  for(idx=0; idx<MAX_RATE_TYPES; idx++){
72  memset(&Multi_rate[np_index][idx], 0, sizeof(mr_info));
73  Multi_rate[np_index][idx].stamp_second = -1;
74  }
75 }
76 
77 // add data of the specified type to datarate processing, returns 0 on fail (if we ran out of types, etc, etc)
78 int multi_rate_add(int np_index, char *type, int size)
79 {
80  int idx;
81  mr_info *m;
82  // sanity checks
83  if((np_index < 0) || (np_index >= MAX_RATE_PLAYERS)){
84  return 0;
85  }
86  if((type == NULL) || (strlen(type) <= 0)){
87  return 0;
88  }
89 
90  // see if the type already exists
91  for(idx=0; idx<MAX_RATE_TYPES; idx++){
92  // empty slot
93  if(strlen(Multi_rate[np_index][idx].type) <= 0){
94  break;
95  }
96  // existing
97  else if(!stricmp(Multi_rate[np_index][idx].type, type)){
98  break;
99  }
100  }
101 
102  // if we couldn't find a slot
103  if(idx >= MAX_RATE_TYPES){
104  return 0;
105  }
106 
107  // otherwise add the data
108  m = &Multi_rate[np_index][idx];
109 
110  // type string
111  strcpy_s(m->type, type);
112 
113  // alltime
114  m->total_bytes += size;
115 
116  // per-second
117  m->bytes_second += size;
118 
119  // per-frame
120  m->bytes_frame += size;
121 
122  // success
123  return 1;
124 }
125 
126 // process
127 #define R_AVG(ct, ar, avg) do {int av_idx; float av_sum = 0.0f; if(ct == 0){ avg = 0;} else { for(av_idx=0; av_idx<ct; av_idx++){ av_sum += (float)ar[av_idx]; } avg = av_sum / (float)ct; } }while(0)
128 void multi_rate_process()
129 {
130  int idx, s_idx;
131  mr_info *m;
132 
133  // process all active players
134  for(idx=0; idx<MAX_RATE_PLAYERS; idx++){
135  for(s_idx=0; s_idx<MAX_RATE_TYPES; s_idx++){
136  m = &Multi_rate[idx][s_idx];
137 
138  // invalid entries
139  if(strlen(m->type) <= 0){
140  continue;
141  }
142 
143  // process alltime
144  if(m->stamp_second == -1){
145  m->stamp_second = timestamp(1000);
146  } else if(timestamp_elapsed(m->stamp_second)){
147  // if we've reached max records
148  if(m->records_second_count >= NUM_UPDATE_RECORDS){
149  memmove(m->records_second, m->records_second+1, sizeof(int) * (NUM_UPDATE_RECORDS - 1));
150  m->records_second[NUM_UPDATE_RECORDS-1] = m->bytes_second;
151  }
152  // haven't reached max records
153  else {
154  m->records_second[m->records_second_count++] = m->bytes_second;
155  }
156 
157  // recalculate the average
158  R_AVG(m->records_second_count, m->records_second, m->avg_second);
159 
160  // reset bytes/second and timestamp
161  m->bytes_second = 0;
162  m->stamp_second = timestamp(1000);
163  }
164 
165  // process per-frame
166  // if we've reached max records
167  if(m->records_frame_count >= NUM_UPDATE_RECORDS){
168  memmove(m->records_frame, m->records_frame+1, sizeof(int) * (NUM_UPDATE_RECORDS - 1));
169  m->records_frame[NUM_UPDATE_RECORDS-1] = m->bytes_frame;
170  }
171  // haven't reached max records
172  else {
173  m->records_frame[m->records_frame_count++] = m->bytes_frame;
174  }
175 
176  // recalculate the average
177  R_AVG(m->records_frame_count, m->records_frame, m->avg_frame);
178 
179  // reset bytes/frame
180  m->bytes_frame = 0;
181  }
182  }
183 }
184 
185 // display
186 void multi_rate_display(int np_index, int x, int y)
187 {
188  int idx;
189  mr_info *m;
190  int line_height = gr_get_font_height() + 1;
191 
192  // sanity checks
193  if((np_index < 0) || (np_index >= MAX_RATE_PLAYERS)){
194  return;
195  }
196 
197  // get info
198  for(idx=0; idx<MAX_RATE_TYPES; idx++){
199  m = &Multi_rate[np_index][idx];
200 
201  // if we have a 0 length string, we're done
202  if(strlen(m->type) <= 0){
203  break;
204  }
205 
206  // display
208  gr_printf_no_resize(x, y, "%s %d (%d/s) (%f/f)", m->type, m->total_bytes, (int)m->avg_second, m->avg_frame);
209  y += line_height;
210  }
211 }
212 
213 #endif
int timestamp(int delta_ms)
Definition: timer.cpp:226
#define MAX_RATE_PLAYERS
Definition: multi_rate.h:25
color Color_red
Definition: alphacolors.cpp:34
void gr_set_color_fast(color *dst)
Definition: 2d.cpp:1197
GLsizeiptr size
Definition: Glext.h:5496
GLenum type
Definition: Gl.h:1492
#define MAX_RATE_TYPES
Definition: multi_rate.h:26
void multi_rate_reset(int np_index)
int idx
Definition: multiui.cpp:761
GLint GLint GLint GLint GLint x
Definition: Glext.h:5182
int multi_rate_add(int np_index, char *type, int size)
int gr_get_font_height()
Definition: font.cpp:187
#define timestamp_elapsed(stamp)
Definition: timer.h:102
const GLfloat * m
Definition: Glext.h:10319
#define MAX_RATE_TYPE_LEN
Definition: multi_rate.h:24
void _cdecl gr_printf_no_resize(int x, int y, const char *format,...)
Definition: font.cpp:342
void multi_rate_display(int np_index, int x, int y)
void multi_rate_process()
#define stricmp(s1, s2)
Definition: config.h:271
GLint y
Definition: Gl.h:1505
#define strcpy_s(...)
Definition: safe_strings.h:67