diff --git a/src/common/gamecode/economy.c b/src/common/gamecode/economy.c index 95f4fe064..f08dccfcc 100644 --- a/src/common/gamecode/economy.c +++ b/src/common/gamecode/economy.c @@ -1624,6 +1624,8 @@ make_cmd(unit * u, struct order * ord) const char *s; const struct locale * lang = u->faction->locale; + if (u->number==NULL) return; + init_tokens(ord); skip_token(); s = getstrtoken(); diff --git a/src/common/gamecode/laws.c b/src/common/gamecode/laws.c index d5b2e3979..0db59f390 100644 --- a/src/common/gamecode/laws.c +++ b/src/common/gamecode/laws.c @@ -338,7 +338,7 @@ age_unit(region * r, unit * u) } } else { ++u->age; - if (u->race->age) { + if (u->number>0 && u->race->age) { u->race->age(u); } } diff --git a/src/common/gamecode/randenc.c b/src/common/gamecode/randenc.c index 728767164..0fa4fc9a8 100644 --- a/src/common/gamecode/randenc.c +++ b/src/common/gamecode/randenc.c @@ -309,6 +309,7 @@ static void get_allies(region * r, unit * u) { unit *newunit = NULL; + assert(u->number); switch (rterrain(r)) { @@ -422,27 +423,24 @@ void encounters(void) { region *r; - unit *u; - int n; - int c; - int i; for (r = regions; r; r = r->next) { if (!fval(r->terrain, SEA_REGION) && fval(r, RF_ENCOUNTER)) { - c = 0; + int c = 0; + unit * u; for (u = r->units; u; u = u->next) { c += u->number; } if (c > 0) { - n = rng_int() % c; - u = r->units; + int i = 0; + int n = rng_int() % c; - for (i = u->number; i < n; i += u->number) { - u = u->next; + for (u = r->units; u; u = u->next) { + if (i+u->number>c) break; } - - encounter(r, u); + assert(u && u->number); + encounter(r, u); } } } @@ -609,12 +607,13 @@ damage_unit(unit *u, const char *dam, boolean physical, boolean magic) int *hp = malloc(u->number * sizeof(int)); int h; int i, dead = 0, hp_rem = 0, heiltrank; + double magres = magic_resistance(u); + assert(u->number); if (fval(u->race, RCF_ILLUSIONARY) || u->race == new_race[RC_SPELL]) { return 0; } - if (u->number==0) return 0; h = u->hp/u->number; /* HP verteilen */ for (i=0; inumber; i++) hp[i] = h; @@ -624,7 +623,7 @@ damage_unit(unit *u, const char *dam, boolean physical, boolean magic) /* Schaden */ for (i=0; inumber; i++) { int damage = dice_rand(dam); - if (magic) damage = (int)(damage * (1.0 - magic_resistance(u))); + if (magic) damage = (int)(damage * (1.0 - magres)); if (physical) damage -= nb_armor(u, i); hp[i] -= damage; } @@ -766,19 +765,21 @@ volcano_outbreak(region *r) for (up=&r->units; *up;) { unit * u = *up; - int dead = damage_unit(u, "4d10", true, false); - if (dead) { - ADDMSG(&u->faction->msgs, msg_message("volcano_dead", - "unit region dead", u, r, dead)); - } - if (!fval(u->faction, FL_DH)) { - fset(u->faction, FL_DH); - if (rn) { - ADDMSG(&u->faction->msgs, msg_message("volcanooutbreak", - "regionv regionn", r, rn)); - } else { - ADDMSG(&u->faction->msgs, msg_message("volcanooutbreaknn", - "region", r)); + if (u->number) { + int dead = damage_unit(u, "4d10", true, false); + if (dead) { + ADDMSG(&u->faction->msgs, msg_message("volcano_dead", + "unit region dead", u, r, dead)); + } + if (!fval(u->faction, FL_DH)) { + fset(u->faction, FL_DH); + if (rn) { + ADDMSG(&u->faction->msgs, msg_message("volcanooutbreak", + "regionv regionn", r, rn)); + } else { + ADDMSG(&u->faction->msgs, msg_message("volcanooutbreaknn", + "region", r)); + } } } if (u==*up) up=&u->next; @@ -805,10 +806,12 @@ volcano_outbreak(region *r) /* Personen bekommen 3W10 Punkte Schaden. */ for (up=&rn->units; *up;) { unit * u = *up; - int dead = damage_unit(u, "3d10", true, false); - if (dead) { - ADDMSG(&u->faction->msgs, msg_message("volcano_dead", - "unit region dead", u, r, dead)); + if (u->number) { + int dead = damage_unit(u, "3d10", true, false); + if (dead) { + ADDMSG(&u->faction->msgs, msg_message("volcano_dead", + "unit region dead", u, r, dead)); + } } if (u==*up) up=&u->next; } diff --git a/src/common/gamecode/study.c b/src/common/gamecode/study.c index 7402041b3..fdebc8909 100644 --- a/src/common/gamecode/study.c +++ b/src/common/gamecode/study.c @@ -446,11 +446,7 @@ learn_cmd(unit * u, order * ord) int p; magic_t mtyp; int l; - int studycost; - - /* lernen nach lehren */ - - int days; + int studycost, days; double multi = 1.0; attrib * a = NULL; teaching_info * teach = NULL; @@ -458,6 +454,7 @@ learn_cmd(unit * u, order * ord) skill_t sk; int maxalchemy = 0; + if (u->number==0) return; if (fval(r->terrain, SEA_REGION)) { /* sonderbehandlung aller die auf Ozeanen lernen können */ if (u->race!=new_race[RC_AQUARIAN] && !(u->race->flags & RCF_SWIM)) { diff --git a/src/common/kernel/battle.c b/src/common/kernel/battle.c index dce9f8a28..15ea60a70 100644 --- a/src/common/kernel/battle.c +++ b/src/common/kernel/battle.c @@ -911,6 +911,7 @@ terminate(troop dt, troop at, int type, const char *damage, boolean missile) boolean magic = false; int da = dice_rand(damage); + assert(du->number>0); #ifdef SHOW_KILLS ++at.fighter->hits; #endif @@ -2914,6 +2915,7 @@ make_fighter(battle * b, unit * u, side * s1, boolean attack) static boolean init = false; unsigned int flags = 0; + assert(u->number); if (fval(u, UFL_PARTEITARNUNG)!=0) flags |= SIDE_STEALTH; #ifdef SIMPLE_COMBAT if (attack) flags |= SIDE_ATTACKER; diff --git a/src/common/kernel/build.c b/src/common/kernel/build.c index ef4d72251..c5f627218 100644 --- a/src/common/kernel/build.c +++ b/src/common/kernel/build.c @@ -452,6 +452,7 @@ build_road(region * r, unit * u, int size, direction_t d) int n, left; region * rn = rconnect(r,d); + assert(u->number); if (!eff_skill(u, SK_ROAD_BUILDING, r)) { cmistake(u, u->thisorder, 103, MSG_PRODUCE); return; @@ -611,6 +612,7 @@ build(unit * u, const construction * ctype, int completed, int want) int made = 0; int basesk, effsk; + assert(u->number); if (want<=0) return 0; if (type==NULL) return 0; if (type->improvement==NULL && completed==type->maxsize) @@ -796,6 +798,7 @@ build_building(unit * u, const building_type * btype, int want, order * ord) order * new_order = NULL; const struct locale * lang = u->faction->locale; + assert(u->number); if (eff_skill(u, SK_BUILDING, r) == 0) { cmistake(u, ord, 101, MSG_PRODUCE); return; diff --git a/src/common/kernel/curse.c b/src/common/kernel/curse.c index abdee24be..35475ce70 100644 --- a/src/common/kernel/curse.c +++ b/src/common/kernel/curse.c @@ -546,7 +546,7 @@ create_curse(unit *magician, attrib **ap, const curse_type *ct, double vigour, /* hier müssen alle c-typen, die auf Einheiten gezaubert werden können, * berücksichtigt werden */ -void +static void do_transfer_curse(curse *c, unit * u, unit * u2, int n) { int flag = c->flag; diff --git a/src/common/kernel/eressea.c b/src/common/kernel/eressea.c index 41cd77f87..ca791182d 100644 --- a/src/common/kernel/eressea.c +++ b/src/common/kernel/eressea.c @@ -881,7 +881,7 @@ scale_number (unit * u, int n) int remain; if (n == u->number) return; - if (n && u->number) { + if (n && u->number>0) { int full; remain = ((u->hp%u->number) * (n % u->number)) % u->number; @@ -894,17 +894,19 @@ scale_number (unit * u, int n) remain = 0; u->hp = 0; } - for (a = a_find(u->attribs, &at_effect);a && a->type==&at_effect;a=a->next) { - effect_data * data = (effect_data *)a->data.v; - int snew = data->value / u->number * n; - if (n) { - remain = data->value - snew / n * u->number; - snew += remain * n / u->number; - remain = (remain * n) % u->number; - if ((rng_int() % u->number) < remain) - ++snew; /* Nachkommastellen */ + if (u->number>0) { + for (a = a_find(u->attribs, &at_effect);a && a->type==&at_effect;a=a->next) { + effect_data * data = (effect_data *)a->data.v; + int snew = data->value / u->number * n; + if (n) { + remain = data->value - snew / n * u->number; + snew += remain * n / u->number; + remain = (remain * n) % u->number; + if ((rng_int() % u->number) < remain) + ++snew; /* Nachkommastellen */ + } + data->value = snew; } - data->value = snew; } if (u->number==0 || n==0) { for (sk = 0; sk < MAXSKILLS; sk++) { diff --git a/src/common/kernel/magic.c b/src/common/kernel/magic.c index b5ce877ed..81f0347f9 100644 --- a/src/common/kernel/magic.c +++ b/src/common/kernel/magic.c @@ -1085,6 +1085,7 @@ magic_resistance(unit *target) /* Bonus durch Rassenmagieresistenz */ double probability = target->race->magres; + assert(target->number>0); /* Magier haben einen Resistenzbonus vom Magietalent * 5%*/ probability += effskill(target, SK_MAGIC)*0.05; diff --git a/src/common/kernel/movement.c b/src/common/kernel/movement.c index 7304b5f49..523d75f3e 100644 --- a/src/common/kernel/movement.c +++ b/src/common/kernel/movement.c @@ -1249,6 +1249,7 @@ movement_speed(unit * u) static boolean init = false; double dk = u->race->speed; + assert(u->number); /* dragons have a fixed speed, and no other effects work on them: */ switch (old_race(u->race)) { case RC_DRAGON: @@ -2051,6 +2052,7 @@ move(unit * u, boolean move_on_land) { region_list * route = NULL; + assert(u->number); if (u->ship && fval(u, UFL_OWNER)) { sail(u, u->thisorder, move_on_land, &route); } else { diff --git a/src/common/kernel/reports.c b/src/common/kernel/reports.c index 35211a605..5e29845d6 100644 --- a/src/common/kernel/reports.c +++ b/src/common/kernel/reports.c @@ -132,6 +132,7 @@ hp_status(const unit * u) void report_item(const unit * owner, const item * i, const faction * viewer, const char ** name, const char ** basename, int * number, boolean singular) { + assert(owner->number); if (owner->faction == viewer) { if (name) *name = locale_string(viewer->locale, resourcename(i->type->rtype, ((i->number!=1 && !singular)?GR_PLURAL:0))); if (basename) *basename = resourcename(i->type->rtype, 0); diff --git a/src/common/kernel/save.c b/src/common/kernel/save.c index a2d2e5eb5..3fb0c0eaa 100644 --- a/src/common/kernel/save.c +++ b/src/common/kernel/save.c @@ -1077,16 +1077,18 @@ readunit(FILE * F) assert(u->race); if (global.data_versionnumber; - int lvl = level(days); - int weeks = lvl + 1 - (days - level_days(lvl))/30; - assert(weeks>0 && weeks<=lvl+1); - if (lvl) { - skill * sv = add_skill(u, sk); - sv->level = sv->old = (unsigned char)lvl; - sv->weeks = (unsigned char)weeks; - } + if (u->number) { + while ((sk = (skill_t) ri(F)) != NOSKILL) { + int days = ri(F) / u->number; + int lvl = level(days); + int weeks = lvl + 1 - (days - level_days(lvl))/30; + assert(weeks>0 && weeks<=lvl+1); + if (lvl) { + skill * sv = add_skill(u, sk); + sv->level = sv->old = (unsigned char)lvl; + sv->weeks = (unsigned char)weeks; + } + } } } else { while ((sk = (skill_t) ri(F)) != NOSKILL) { diff --git a/src/common/kernel/unit.c b/src/common/kernel/unit.c index 9f8f25546..b2b15f9ec 100644 --- a/src/common/kernel/unit.c +++ b/src/common/kernel/unit.c @@ -782,8 +782,8 @@ transfermen(unit * u, unit * u2, int n) int hp = u->hp; region * r = u->region; - if (!n) return; - + if (n==0) return; + assert(n > 0); /* "hat attackiert"-status wird übergeben */ if (u2) { diff --git a/src/common/races/dragons.c b/src/common/races/dragons.c index ad3a9a39d..2185c24fb 100644 --- a/src/common/races/dragons.c +++ b/src/common/races/dragons.c @@ -31,7 +31,7 @@ void age_firedragon(unit *u) { - if (rng_int()%100 < age_chance(u->age, DRAGONAGE, 1)) { + if (u->number>0 && rng_int()%100 < age_chance(u->age, DRAGONAGE, 1)) { double q = (double) u->hp / (double) (unit_max_hp(u) * u->number); u->race = new_race[RC_DRAGON]; u->irace = new_race[RC_DRAGON]; @@ -43,7 +43,7 @@ age_firedragon(unit *u) void age_dragon(unit *u) { - if (rng_int()%100 < age_chance(u->age, WYRMAGE, 1)) { + if (u->number>0 && rng_int()%100 < age_chance(u->age, WYRMAGE, 1)) { double q = (double) u->hp / (double) (unit_max_hp(u) * u->number); u->race = new_race[RC_WYRM]; u->irace = new_race[RC_WYRM]; diff --git a/src/common/spells/spells.c b/src/common/spells/spells.c index 2ca49b5dc..10a2e9d97 100644 --- a/src/common/spells/spells.c +++ b/src/common/spells/spells.c @@ -4708,7 +4708,7 @@ sp_headache(castorder *co) countspells(mage, 1); /* wenn kein Ziel gefunden, Zauber abbrechen */ - if(pa->param[0]->flag == TARGET_NOTFOUND) return 0; + if (target->number==0 || pa->param[0]->flag == TARGET_NOTFOUND) return 0; target = pa->param[0]->data.u; /* Zieleinheit */