From bb495cac6088a7c167f4db7335d9b32365070153 Mon Sep 17 00:00:00 2001 From: Markus Armbruster Date: Sat, 18 Jun 2016 14:57:45 +0200 Subject: [PATCH] budget: Fix military count (but not yet their pay) When we add up military payroll, we discard fractions. Payroll is therefore lower than it should be, but I'm not fixing that now. The number of military budget reports is actually computed from payroll, and therefore also low. The obvious way to fix that would be adding another out parameter to tax() and upd_slmilcosts(). However, budget and the update track cost and count of numerous things (sector products, unit maintenance and building, ...), and it's time for a common way to do that. Create struct budget_item for tracking cost and count, and struct budget nat_budget[MAXNOC] for tracking a nation's budget. Track only military for now; more to follow. This fixes the military count. The cost of military remains low, because we discard fractions exactly as before. Signed-off-by: Markus Armbruster --- include/update.h | 17 ++++++++++++-- src/lib/commands/budg.c | 51 ++++++++++++++++++++-------------------- src/lib/update/main.c | 3 ++- src/lib/update/prepare.c | 37 +++++++++++++++++++---------- tests/update/02-2 | 2 +- tests/update/journal.log | 12 +++++----- 6 files changed, 75 insertions(+), 47 deletions(-) diff --git a/include/update.h b/include/update.h index 7ff03d9e..77a2305d 100644 --- a/include/update.h +++ b/include/update.h @@ -43,7 +43,19 @@ #define SCT_MAINT (SCT_TYPE_MAX + 2) #define SCT_BUDG_MAX SCT_MAINT +struct budg_item { + int money; /* money delta */ + int count; /* #things making/consuming the money */ +}; + +/* A nation's budget for an update */ +struct budget { + /* military payroll */ + struct budg_item mil; +}; + /* main.c */ +extern struct budget nat_budget[MAXNOC]; extern int money[MAXNOC]; extern int pops[MAXNOC]; extern int sea_money[MAXNOC]; @@ -103,10 +115,11 @@ extern int prod_plane(int, int, struct bp *, int); extern void populace(struct sctstr *, int); extern int total_work(int, int, int, int, int, int); /* prepare.c */ -extern void tax(struct sctstr *, int, int *, int *, int *, int *); -extern int upd_slmilcosts(natid, int); extern void prepare_sects(int); +extern void tax(struct sctstr *, int, int *, int *, int *); +extern void upd_slmilcosts(int, natid); extern int bank_income(struct sctstr *, int); +extern void pay_reserve(struct natstr *, int); /* produce.c */ extern int produce(struct natstr *, struct sctstr *, int *); extern int prod_materials_cost(struct pchrstr *, short[], int *); diff --git a/src/lib/commands/budg.c b/src/lib/commands/budg.c index 11c59825..af6957e1 100644 --- a/src/lib/commands/budg.c +++ b/src/lib/commands/budg.c @@ -42,8 +42,8 @@ #include "product.h" #include "update.h" -static void calc_all(int (*p_sect)[2], int *taxes, int *Ncivs, - int *Nuws, int *bars, int *Nbars, int *mil, +static struct budget *calc_all(int (*p_sect)[2], int *taxes, int *Ncivs, + int *Nuws, int *bars, int *Nbars, int *ships, int *sbuild, int *nsbuild, int *smaint, int *units, int *lbuild, int *nlbuild, int *lmaint, int *planes, int *pbuild, int *npbuild, int *pmaint); @@ -54,26 +54,24 @@ budg(void) { int i; int p_sect[SCT_BUDG_MAX+1][2]; - int taxes, Ncivs, Nuws, bars, Nbars, mil; + int taxes, Ncivs, Nuws, bars, Nbars; int ships, sbuild, nsbuild, smaint; int units, lbuild, nlbuild, lmaint; int planes, pbuild, npbuild, pmaint; - int n, etu; + struct budget *budget; int income, expenses; struct natstr *np; char buf[1024]; char in[80]; - etu = etu_per_update; - np = getnatp(player->cnum); player->simulation = 1; - calc_all(p_sect, - &taxes, &Ncivs, &Nuws, &bars, &Nbars, &mil, - &ships, &sbuild, &nsbuild, &smaint, - &units, &lbuild, &nlbuild, &lmaint, - &planes, &pbuild, &npbuild, &pmaint); + budget = calc_all(p_sect, + &taxes, &Ncivs, &Nuws, &bars, &Nbars, + &ships, &sbuild, &nsbuild, &smaint, + &units, &lbuild, &nlbuild, &lmaint, + &planes, &pbuild, &npbuild, &pmaint); player->simulation = 0; income = taxes + bars; @@ -142,12 +140,14 @@ budg(void) buf, p_sect[SCT_MAINT][1]); expenses += p_sect[SCT_MAINT][1]; } - if (mil) { - n = (mil - np->nat_reserve * money_res * etu) / (etu * money_mil); - sprintf(in, "%d mil, %d res", n, np->nat_reserve); - pr("Military payroll\t\t%-32s%8d\n", in, -mil); - expenses -= mil; + if (budget->mil.money) { + snprintf(buf, sizeof(buf), "%d mil, %d res", + budget->mil.count, np->nat_reserve); + pr("Military payroll\t\t%-32s%8d\n", + buf, -budget->mil.money); + expenses -= budget->mil.money; } + pr("Total expenses%s\n", dotsprintf(buf, "%58d", expenses)); if (taxes) { sprintf(in, "%d civ%s, %d uw%s", @@ -171,22 +171,24 @@ budg(void) return RET_OK; } -static void +static struct budget * calc_all(int p_sect[][2], - int *taxes, int *Ncivs, int *Nuws, int *bars, int *Nbars, int *mil, + int *taxes, int *Ncivs, int *Nuws, int *bars, int *Nbars, int *ships, int *sbuild, int *nsbuild, int *smaint, int *units, int *lbuild, int *nlbuild, int *lmaint, int *planes, int *pbuild, int *npbuild, int *pmaint) { + struct budget *budget = &nat_budget[player->cnum]; struct natstr *np; struct bp *bp; int pop = 0; - int n, civ_tax, uw_tax, mil_pay; + int n, civ_tax, uw_tax; struct sctstr *sp; int etu = etu_per_update; + memset(nat_budget, 0, sizeof(nat_budget)); memset(p_sect, 0, sizeof(**p_sect) * (SCT_BUDG_MAX+1) * 2); - *taxes = *Ncivs = *Nuws = *bars = *Nbars = *mil = 0; + *taxes = *Ncivs = *Nuws = *bars = *Nbars = 0; *ships = *sbuild = *nsbuild = *smaint = 0; *units = *lbuild = *nlbuild = *lmaint = 0; *planes = *pbuild = *npbuild = *pmaint = 0; @@ -197,11 +199,10 @@ calc_all(int p_sect[][2], bp_set_from_sect(bp, sp); if (sp->sct_own == player->cnum) { sp->sct_updated = 0; - tax(sp, etu, &pop, &civ_tax, &uw_tax, &mil_pay); + tax(sp, etu, &pop, &civ_tax, &uw_tax); *Ncivs += sp->sct_item[I_CIVIL]; *Nuws += sp->sct_item[I_UW]; *taxes += civ_tax + uw_tax; - *mil += mil_pay; if (sp->sct_type == SCT_BANK) { *bars += bank_income(sp, etu); *Nbars += sp->sct_item[I_BAR]; @@ -209,9 +210,8 @@ calc_all(int p_sect[][2], } } tpops[player->cnum] = pop; - *mil += (int)(np->nat_reserve * money_res * etu); - - *mil += upd_slmilcosts(np->nat_cnum, etu); + upd_slmilcosts(etu, player->cnum); + pay_reserve(np, etu); /* Maintain ships */ sea_money[player->cnum] = 0; @@ -250,6 +250,7 @@ calc_all(int p_sect[][2], lnd_money[player->cnum] = 0; free(bp); + return budget; } static char * diff --git a/src/lib/update/main.c b/src/lib/update/main.c index 2ea9aef2..ceff5c0a 100644 --- a/src/lib/update/main.c +++ b/src/lib/update/main.c @@ -46,6 +46,7 @@ #include "unit.h" #include "update.h" +struct budget nat_budget[MAXNOC]; int money[MAXNOC]; int pops[MAXNOC]; int sea_money[MAXNOC]; @@ -86,6 +87,7 @@ update_main(void) * sector production routine (for producing education, * happiness, and printing out the state of the nation) */ + memset(nat_budget, 0, sizeof(nat_budget)); memset(pops, 0, sizeof(pops)); memset(air_money, 0, sizeof(air_money)); memset(sea_money, 0, sizeof(sea_money)); @@ -111,7 +113,6 @@ update_main(void) if (np->nat_stat == STAT_SANCT) { continue; } - np->nat_money += (int)(np->nat_reserve * money_res * etu); /* maintain units */ prod_ship(etu, i, NULL, 0); diff --git a/src/lib/update/prepare.c b/src/lib/update/prepare.c index ad1d7e04..ae66966c 100644 --- a/src/lib/update/prepare.c +++ b/src/lib/update/prepare.c @@ -51,7 +51,7 @@ prepare_sects(int etu) { struct sctstr *sp; struct natstr *np; - int n, civ_tax, uw_tax, mil_pay; + int n, civ_tax, uw_tax; memset(levels, 0, sizeof(levels)); @@ -95,20 +95,24 @@ prepare_sects(int etu) do_plague(sp, etu); populace(sp, etu); np = getnatp(sp->sct_own); - tax(sp, etu, &pops[sp->sct_own], &civ_tax, &uw_tax, &mil_pay); - np->nat_money += civ_tax + uw_tax + mil_pay; + tax(sp, etu, &pops[sp->sct_own], &civ_tax, &uw_tax); + np->nat_money += civ_tax + uw_tax; if (sp->sct_type == SCT_BANK) np->nat_money += bank_income(sp, etu); } for (n = 0; NULL != (np = getnatp(n)); n++) { - np->nat_money += upd_slmilcosts(np->nat_cnum, etu); + upd_slmilcosts(etu, np->nat_cnum); + pay_reserve(np, etu); + np->nat_money += nat_budget[n].mil.money; } } void -tax(struct sctstr *sp, int etu, int *pop, int *civ_tax, - int *uw_tax, int *mil_pay) +tax(struct sctstr *sp, int etu, int *pop, int *civ_tax, int *uw_tax) { + struct budget *budget = &nat_budget[sp->sct_own]; + int mil_pay; + *civ_tax = (int)(0.5 + sp->sct_item[I_CIVIL] * sp->sct_effic * etu * money_civ / 100); /* @@ -118,7 +122,10 @@ tax(struct sctstr *sp, int etu, int *pop, int *civ_tax, *civ_tax = *civ_tax / 4; *uw_tax = (int)(0.5 + sp->sct_item[I_UW] * sp->sct_effic * etu * money_uw / 100); - *mil_pay = sp->sct_item[I_MILIT] * etu * money_mil; + + mil_pay = sp->sct_item[I_MILIT] * etu * money_mil; + budget->mil.count += sp->sct_item[I_MILIT]; + budget->mil.money += mil_pay; /* * only non-captured civs add to census for nation @@ -127,13 +134,12 @@ tax(struct sctstr *sp, int etu, int *pop, int *civ_tax, *pop += sp->sct_item[I_CIVIL]; } -int -upd_slmilcosts(natid n, int etu) +void +upd_slmilcosts(int etu, natid n) { struct shpstr *sp; struct lndstr *lp; int mil, i; - int mil_pay; mil = 0; @@ -149,8 +155,8 @@ upd_slmilcosts(natid n, int etu) mil += lp->lnd_item[I_MILIT]; } - mil_pay = mil * etu * money_mil; - return mil_pay; + nat_budget[n].mil.count += mil; + nat_budget[n].mil.money += mil * etu * money_mil; } int @@ -158,3 +164,10 @@ bank_income(struct sctstr *sp, int etu) { return (int)(sp->sct_item[I_BAR] * etu * bankint * sp->sct_effic / 100); } + +void +pay_reserve(struct natstr *np, int etu) +{ + nat_budget[np->nat_cnum].mil.money + += (int)(np->nat_reserve * money_res * etu); +} diff --git a/tests/update/02-2 b/tests/update/02-2 index 6360d5d4..c4a57f03 100644 --- a/tests/update/02-2 +++ b/tests/update/02-2 @@ -1,5 +1,5 @@ budget -| BUG: military payroll slightly low, both #mil and $ +| BUG: military payroll slightly low | BUG: expenses ignore going broke | TODO is it accurate? production * diff --git a/tests/update/journal.log b/tests/update/journal.log index cb9bba24..782dfc75 100644 --- a/tests/update/journal.log +++ b/tests/update/journal.log @@ -41,7 +41,7 @@ Play#1 output Play#1 1 Unit maintenance 16 units 510 Play#1 output Play#1 1 Sector building 40 sectors 774 Play#1 output Play#1 1 Sector maintenance 2 sectors 120 - Play#1 output Play#1 1 Military payroll 1155 mil, 0 res 5777 + Play#1 output Play#1 1 Military payroll 1164 mil, 0 res 5777 Play#1 output Play#1 1 Total expenses.....................................................24647 Play#1 output Play#1 1 Income from taxes 26911 civs, 9007 uws +12625 Play#1 output Play#1 1 Total income......................................................+12625 @@ -234,7 +234,7 @@ Play#2 output Play#2 1 Unit maintenance 3 units 90 Play#2 output Play#2 1 Sector building 26 sectors 209 Play#2 output Play#2 1 Sector maintenance 5 sectors 300 - Play#2 output Play#2 1 Military payroll 1898 mil, 1000 res 9994 + Play#2 output Play#2 1 Military payroll 1900 mil, 1000 res 9994 Play#2 output Play#2 1 Total expenses.....................................................12390 Play#2 output Play#2 1 Income from taxes 6800 civs, 4000 uws +1076 Play#2 output Play#2 1 Income from bars 400 bars +2865 @@ -279,7 +279,7 @@ Play#3 input budget Play#3 command budget Play#3 output Play#3 1 Sector Type Production Cost - Play#3 output Play#3 1 Military payroll 169 mil, 0 res 848 + Play#3 output Play#3 1 Military payroll 170 mil, 0 res 848 Play#3 output Play#3 1 Total expenses.......................................................848 Play#3 output Play#3 1 Income from taxes 16549 civs, 150 uws +5540 Play#3 output Play#3 1 Total income.......................................................+5540 @@ -320,7 +320,7 @@ Play#4 output Play#4 1 bank 4 bars 40 Play#4 output Play#4 1 Ship maintenance 10 ships 300 Play#4 output Play#4 1 Unit maintenance 10 units 600 - Play#4 output Play#4 1 Military payroll 1110 mil, 0 res 5552 + Play#4 output Play#4 1 Military payroll 1111 mil, 0 res 5552 Play#4 output Play#4 1 Total expenses......................................................6492 Play#4 output Play#4 1 Income from taxes 23604 civs, 4100 uws +212 Play#4 output Play#4 1 Income from bars 100 bars +1500 @@ -393,7 +393,7 @@ Play#6 output Play#6 1 Plane maintenance 3 planes 147 Play#6 output Play#6 1 Unit maintenance 3 units 90 Play#6 output Play#6 1 Sector maintenance 1 sector 60 - Play#6 output Play#6 1 Military payroll 166 mil, 0 res 831 + Play#6 output Play#6 1 Military payroll 168 mil, 0 res 831 Play#6 output Play#6 1 Total expenses......................................................1668 Play#6 output Play#6 1 Income from taxes 4000 civs, 0 uws +1750 Play#6 output Play#6 1 Total income.......................................................+1750 @@ -424,7 +424,7 @@ Play#7 output Play#7 1 Sector Type Production Cost Play#7 output Play#7 1 Ship maintenance 3 ships 70 Play#7 output Play#7 1 Sector maintenance 1 sector 60 - Play#7 output Play#7 1 Military payroll 158 mil, 0 res 792 + Play#7 output Play#7 1 Military payroll 160 mil, 0 res 792 Play#7 output Play#7 1 Total expenses.......................................................922 Play#7 output Play#7 1 Income from taxes 4000 civs, 0 uws +1750 Play#7 output Play#7 1 Total income.......................................................+1750