1 /*
2 *
3 * Dave Ahn
4 *
5 * Leonard/Tom/Dave (LTD) Extended statistics. For detailed info, read
6 * the README.LTD file.
7 *
8 * For inline optimization details, read the README.LTD and
9 * ltd_stats.c files.
10 *
11 * struct ltd_stats is a per-ship statistics group for each player.
12 * This means that the player DB will increase by several factors in
13 * size at the benefit of detailed stats that can be used to analyze
14 * individual play for clued games.
15 *
16 */
17
18 #ifndef __INCLUDED_ltd_stats_h__
19 #define __INCLUDED_ltd_stats_h__
20
21 #include "defs.h" /* We need defines from this file */
22
23 typedef enum {
24
25 LTD_TZONE_0 = 0, /* Zone 0 = backfield */
26 LTD_TZONE_1 = 1, /* Zone 1 = core + 2 open side */
27 LTD_TZONE_2 = 2, /* Zone 2 = front line */
28 LTD_TZONE_3 = 3, /* Zone 3 = enemy front line */
29 LTD_TZONE_4 = 4, /* Zone 4 = enemy core + 2 open side */
30 LTD_TZONE_5 = 5, /* Zone 5 = enemy backfield */
31 LTD_TZONE_6 = 6, /* Zone 6 = 3rd space */
32 LTD_TZONE_7 = 7, /* Zone 7 = unknown/diag */
33 LTD_NUM_TZONES = 8 /* number of zones */
34
35 } LTD_TZONE_T;
36
37 /* XXNOTE: find a better way to do the inlining
38 */
39
40 #ifdef LTD_INLINE
41 #define __LTD_INLINE inline static
42 #else
43 #define __LTD_INLINE
44 #endif
45
46 /* for extende stats, one struct for each ship except GA and AT, which
47 share the same slot */
48
49 typedef enum {
50
51 LTD_TOTAL = 0,
52 LTD_SC = 1,
53 LTD_DD = 2,
54 LTD_CA = 3,
55 LTD_BB = 4,
56 LTD_AS = 5,
57 LTD_SB = 6,
58 LTD_GA = 7,
59 LTD_AT = 7,
60 LTD_NUM_SHIPS = 8
61
62 } LTD_SHIP_T;
63
64
65 #ifdef LTD_PER_RACE
66
67 typedef enum {
68
69 LTD_FED = 0,
70 LTD_ROM = 1,
71 LTD_KLI = 2,
72 LTD_ORI = 3,
73 LTD_NOBODY = 4,
74 LTD_NUM_RACES = 5
75
76 } LTD_RACE_T;
77
78 #else
79
80 typedef enum {
81
82 LTD_FED = 0,
83 LTD_ROM = 0,
84 LTD_KLI = 0,
85 LTD_ORI = 0,
86 LTD_NOBODY = 0,
87 LTD_NUM_RACES = 1
88
89 } LTD_RACE_T;
90
91 #endif /* LTD_PER_RACE */
92
93
94 /* LTD stats structure */
95
96 struct ltd_stats {
97
98 /* How many times have I killed in this ship */
99
100 struct _kills {
101
102 unsigned int total; /* total number of kills ever */
103 double max; /* max kills ever achieved */
104 unsigned int first; /* number of first kills made */
105 unsigned int first_potential; /* first kills that could be
106 converted to carries */
107 unsigned int first_converted; /* first kills that actually were
108 converted to carries */
109 unsigned int second; /* number of second kills made */
110 unsigned int second_potential; /* second kills that could be
111 converted to carries */
112 unsigned int second_converted; /* second kills that actually were
113 converted to carries */
114 unsigned int phasered; /* number of kills made with a
115 phaser death blow */
116 unsigned int torped; /* number of kills made with a
117 torp blow */
118 unsigned int plasmaed; /* number of kills made with a
119 plamsa */
120 #if defined(_64BIT) && defined(linux)
121 } __attribute__((packed)) kills;
122 #else
123 } kills;
124 #endif
125
126 /* How many times have I died in this ship */
127
128 struct _deaths {
129
130 unsigned int total; /* total number of deaths ever */
131 unsigned int potential; /* number of times died as a
132 potential carrier */
133 unsigned int converted; /* number of times died as a
134 a converted carrier */
135 unsigned int dooshed; /* number of times died while ++ */
136 unsigned int phasered; /* number of times died from phaser */
137 unsigned int torped; /* number of times died from torp */
138 unsigned int plasmaed; /* number of times died from plasma */
139 unsigned int acc; /* number of times you died, and
140 someone picked up armies with
141 the kill */
142
143 } deaths;
144
145
146 /* How many planets have I destroyed or taken */
147
148 struct _planets {
149
150 unsigned int taken; /* number of planets taken */
151 unsigned int destroyed; /* number of planets destroyed */
152
153 } planets;
154
155
156 /* How many enemy armies have you bombed */
157
158 struct _bomb {
159
160 unsigned int planets; /* number of planets bombed */
161 unsigned int planets_8; /* number of planets with <= 8
162 armies bombed */
163 unsigned int planets_core; /* number of core planets bombed */
164 unsigned int armies; /* total number of armies bombed */
165 unsigned int armies_8; /* armies bombed where the planet
166 being bombed had <= 8 armies */
167 unsigned int armies_core; /* armies bombed in a core planet */
168
169 } bomb;
170
171
172 /* How many enemy carriers have you killed and armies ogged */
173
174 struct _ogged {
175
176 unsigned int armies; /* number of enemy armies ogged */
177 unsigned int dooshed; /* number of dooshed real carriers */
178 unsigned int converted; /* number of converted enemy
179 carriers */
180 unsigned int potential; /* number of potential enemy
181 carriers */
182 unsigned int bigger_ship; /* number of times a real carrier
183 was in a bigger ship */
184 unsigned int same_ship; /* number of times a real carrier
185 was in the same sized ship */
186 unsigned int smaller_ship; /* number of times a real carrier
187 was in the same sized ship */
188 unsigned int sb_armies; /* number of armies on enemy SB
189 ogged */
190 unsigned int friendly; /* number of friendly carriers
191 you killed */
192 unsigned int friendly_armies; /* number of friendly armies you
193 killed due to blatant stupidity */
194
195 } ogged;
196
197
198 /* How many friendly armies have you carried */
199
200 struct _armies {
201
202 unsigned int total; /* number of friendly armies carried */
203 unsigned int attack; /* armies droped on enemy planets */
204 unsigned int reinforce; /* armies used to reinforce friendly
205 planet < 4 */
206 unsigned int ferries; /* armies ferried to friendly planet
207 >= 4 or SB */
208 unsigned int killed; /* armies killed */
209
210 } armies;
211
212
213 /* How many carries have you made */
214
215 struct _carries {
216
217 unsigned int total; /* number of carries you attempted */
218 unsigned int partial; /* number of times you delivered
219 at least 1 army before dying ++ */
220 unsigned int completed; /* number of times you completed
221 your carry by delivering all
222 the armies */
223 unsigned int attack; /* number of times you dropped on
224 a neutral or enemy planet */
225 unsigned int reinforce; /* number of times you reinforced
226 a friendly planet < 4 */
227 unsigned int ferries; /* number of times you ferried to
228 a friendly planet >= 4 or SB */
229
230 } carries;
231
232
233 /* How much time we spent in relevant roles, modes or space */
234
235 struct _ticks {
236
237 unsigned int total; /* total = green + yellow + red */
238 /* unsigned int green; */ /* time spent in green alert */
239 unsigned int yellow; /* time spent in yellow alert */
240 unsigned int red; /* time spent in red alert */
241
242 unsigned int zone[LTD_NUM_TZONES]; /* time spent in a particular zone */
243
244 unsigned int potential; /* time spent as potential carrier */
245 unsigned int carrier; /* time spent as carrier */
246 unsigned int repair; /* time spent in repair mode */
247
248 } ticks;
249
250 unsigned int damage_repaired; /* total damage repaired */
251
252
253 /* Weapon stats */
254
255 struct _weapons {
256
257 /* phasers */
258
259 struct _phaser {
260
261 unsigned int fired; /* number of times the weapon was
262 fired */
263 unsigned int hit; /* number of times the weapon hit */
264
265 struct _damage {
266
267 unsigned int inflicted; /* damage inflicted with this weapon */
268 unsigned int taken; /* damage taken from this weapon */
269
270 } damage;
271
272 } phaser;
273
274 /* torps */
275
276 struct _torp {
277
278 unsigned int fired; /* number of torps that were fired */
279 unsigned int hit; /* number of torps hit */
280 unsigned int detted; /* number of torps that were detted
281 by enemy */
282 unsigned int selfdetted; /* number of torps self detted */
283 unsigned int wall; /* number of torps that hit the wall */
284
285 struct _damage damage; /* damage inflicted/taken */
286
287 } torps;
288
289
290 /* plasma */
291
292 struct _plasma {
293
294 unsigned int fired; /* number of plasmas that were fired */
295 unsigned int hit; /* number that hit */
296 unsigned int phasered; /* number that were phasered */
297 unsigned int wall; /* number that hit the wall */
298
299 struct _damage damage; /* damage inflicted/taken */
300
301 } plasma;
302
303 /* damage repaired */
304
305 } weapons;
306
307 #if defined(_64BIT) && defined(linux)
308 } __attribute__((packed));
309 #else
310 };
311 #endif
312
313 /* LTD history structure - this is needed to calculate the LTD stats
314 every tick. */
315
316 enum {
317 LTD_NUM_HIST = 5 /* keep track of up to 5 events */
318 };
319
320 struct ltd_history {
321
322 /* kill history */
323
324 struct _kill {
325
326 unsigned int tick; /* tick kill was acquired */
327 char potential; /* kill was retained long enough to
328 become potential or converted
329 carrier */
330 struct player *victim; /* the player that was killed */
331 float before; /* kills i had before this one, perhaps
332 from bombing, etc */
333 int ship; /* ship type of the victim */
334
335 } kills[LTD_NUM_HIST];
336
337 int num_kills; /* number of last_kills */
338
339 char kill_potential; /* i am a potential carrier
340 0 = no
341 1 = potential 1st kill
342 2 = potential 2nd kill
343 3 = converted 1st kill
344 4 = converted 2nd kill */
345
346 /* bombing history */
347
348 unsigned int last_bombed_tick;/* tick i bombed the last planet */
349 short last_bombed_planet; /* last planet that i bombed */
350
351 /* army/carries history */
352
353 short last_beamup_planet;
354 short last_beamdown_planet; /* last planet i beamed up/down armies from
355 value is planet number
356 -1 = SB
357 -2 = no planet */
358
359 int enemy_team; /* the enemy team, for ltd_zone */
360
361 };
362
363
364 /* forward declarations of structs for function prototypes */
365
366 struct player;
367 struct stats;
368 struct planet;
369
370 /* function prototypes for non-inlined functions */
371
372 void ltd_reset(struct player *);
373 void ltd_reset_struct(struct ltd_stats (*) [LTD_NUM_SHIPS]);
374 void ltd_reset_hist(struct player *);
375 int ltd_can_rank(struct player *);
376 void ltd_update_totals(struct player *);
377
378 /* function prototypes for inlined functions */
379
380 __LTD_INLINE float ltd_total_rating(struct player *);
381 __LTD_INLINE float ltd_bombing_rating(struct player *);
382 __LTD_INLINE float ltd_planet_rating(struct player *);
383 __LTD_INLINE float ltd_defense_rating(struct player *);
384 __LTD_INLINE float ltd_offense_rating(struct player *);
385
386 __LTD_INLINE int ltd_kills(struct player *, const LTD_SHIP_T);
387 __LTD_INLINE int ltd_deaths(struct player *, const LTD_SHIP_T);
388 __LTD_INLINE int ltd_armies_bombed(struct player *, const LTD_SHIP_T);
389 __LTD_INLINE int ltd_planets_taken(struct player *, const LTD_SHIP_T);
390 __LTD_INLINE int ltd_ticks(struct player *, const LTD_SHIP_T);
391 __LTD_INLINE int ltd_kills_max(struct player *, const LTD_SHIP_T);
392
393 __LTD_INLINE void ltd_update_ticks(struct player *);
394 __LTD_INLINE void ltd_update_kills(struct player *credit_killer,
395 struct player *actual_killer,
396 struct player *victim);
397 __LTD_INLINE void ltd_update_kills_max(struct player *);
398 __LTD_INLINE void ltd_update_deaths(struct player *victim,
399 struct player *actual_killer);
400 __LTD_INLINE void ltd_update_bomb(struct player *bomber,
401 struct planet *planet_bombed,
402 int armies_bombed);
403 __LTD_INLINE void ltd_update_planets(struct player *taker,
404 struct planet *planet);
405 __LTD_INLINE void ltd_update_armies(struct player *carrier,
406 struct planet *planet);
407 __LTD_INLINE void ltd_update_armies_carried(struct player *carrier,
408 struct player *sb);
409 __LTD_INLINE void ltd_update_armies_ferried(struct player *carrier,
410 struct player *sb);
411 __LTD_INLINE void ltd_update_repaired(struct player *, const int damage);
412
413 __LTD_INLINE void ltd_update_phaser_fired(struct player *shooter);
414 __LTD_INLINE void ltd_update_phaser_hit(struct player *shooter);
415 __LTD_INLINE void ltd_update_phaser_damage(struct player *shooter,
416 struct player *victim,
417 const int damage);
418
419 __LTD_INLINE void ltd_update_torp_fired(struct player *shooter);
420 __LTD_INLINE void ltd_update_torp_hit(struct player *shooter);
421 __LTD_INLINE void ltd_update_torp_detted(struct player *shooter);
422 __LTD_INLINE void ltd_update_torp_selfdetted(struct player *shooter);
423 __LTD_INLINE void ltd_update_torp_wall(struct player *shooter);
424 __LTD_INLINE void ltd_update_torp_damage(struct player *shooter,
425 struct player *victim,
426 const int damage);
427
428 __LTD_INLINE void ltd_update_plasma_fired(struct player *shooter);
429 __LTD_INLINE void ltd_update_plasma_hit(struct player *shooter);
430 __LTD_INLINE void ltd_update_plasma_phasered(struct player *shooter);
431 __LTD_INLINE void ltd_update_plasma_wall(struct player *shooter);
432 __LTD_INLINE void ltd_update_plasma_damage(struct player *shooter,
433 struct player *victim,
434 const int damage);
435
436 /* find a better way to do this inline stuff */
437
438 #ifdef LTD_INLINE /* this stuff is ugly */
439 #define __LTD_INCLUDE_SOURCE
440 #include "ltd_stats.c"
441 #undef __LTD_INCLUDE_SOURCE
442 #endif
443
444
445 #ifdef LTD_PER_RACE
446
ltd_race(const short team)447 static inline LTD_RACE_T ltd_race(const short team) {
448
449 switch(team) {
450
451 case FED: return LTD_FED;
452 case ROM: return LTD_ROM;
453 case KLI: return LTD_KLI;
454 case ORI: return LTD_ORI;
455 default: return LTD_NOBODY;
456
457 }
458
459 }
460
461 #else
462
463 #define ltd_race(XXX) 0
464
465 #endif /* LTD_PER_RACE */
466
467 #endif /* __INCLUDED_ltd_stats_h__ */
468
469