diff --git a/src/player_compchecks.c b/src/player_compchecks.c index e1e1f0f27b..29b2170182 100644 --- a/src/player_compchecks.c +++ b/src/player_compchecks.c @@ -597,7 +597,7 @@ struct Thing * find_imp_for_pickup(struct Computer2 *comp, MapSubtlCoord stl_x, { struct Thing* thing = thing_get(i); struct CreatureControl* cctrl = creature_control_get_from_thing(thing); - if (thing_is_invalid(thing) || creature_control_invalid(cctrl)) + if (!thing_is_creature(thing) || creature_control_invalid(cctrl)) { ERRORLOG("Jump to invalid creature detected"); break; @@ -655,6 +655,9 @@ long computer_check_for_pretty(struct Computer2 *comp, struct ComputerCheck * ch if (!computer_able_to_use_power(comp, PwrK_HAND, 1, 1)) { return CTaskRet_Unk4; } + if (is_task_in_progress_using_hand(comp)) { + return CTaskRet_Unk4; + } { long stack_len = dungeon->digger_stack_length; if (stack_len <= check->param1 * dungeon->total_area / 100) { diff --git a/src/player_compevents.c b/src/player_compevents.c index 2b3ca81b84..ad6cf535d1 100644 --- a/src/player_compevents.c +++ b/src/player_compevents.c @@ -170,14 +170,14 @@ long computer_event_battle(struct Computer2 *comp, struct ComputerEvent *cevent, struct Coord3d pos; if (!get_computer_drop_position_near_subtile(&pos, comp->dungeon, coord_subtile(event->mappos_x), coord_subtile(event->mappos_y))) { SYNCDBG(8,"No drop position near (%d,%d) for %s",(int)coord_subtile(event->mappos_x),(int)coord_subtile(event->mappos_y),cevent->name); - return 0; + return CTaskRet_Unk0; } // Check if there are any enemies in the vicinity - no enemies, don't drop creatures struct Thing* enmtng = get_creature_in_range_who_is_enemy_of_able_to_attack_and_not_specdigger(pos.x.val, pos.y.val, 21, comp->dungeon->owner); if (thing_is_invalid(enmtng)) { SYNCDBG(8,"No enemies near %s",cevent->name); - return 0; + return CTaskRet_Unk0; } long creatrs_def = count_creatures_for_defend_pickup(comp); long creatrs_num = creatrs_def * (long)cevent->param1 / 100; @@ -186,11 +186,11 @@ long computer_event_battle(struct Computer2 *comp, struct ComputerEvent *cevent, } if (creatrs_num <= 0) { SYNCDBG(8,"No creatures to drop for %s",cevent->name); - return 0; + return CTaskRet_Unk0; } if (!computer_find_safe_non_solid_block(comp, &pos)) { SYNCDBG(8,"Drop position is solid for %s",cevent->name); - return 0; + return CTaskRet_Unk0; } if (computer_able_to_use_power(comp, PwrK_HAND, 1, creatrs_num)) { @@ -198,9 +198,9 @@ long computer_event_battle(struct Computer2 *comp, struct ComputerEvent *cevent, { if (!create_task_move_creatures_to_defend(comp, &pos, creatrs_num, cevent->param2)) { SYNCDBG(18,"Cannot move to defend for %s",cevent->name); - return 0; + return CTaskRet_Unk0; } - return 1; + return CTaskRet_Unk1; } } if (computer_able_to_use_power(comp, PwrK_CALL2ARMS, 1, 1)) @@ -211,14 +211,14 @@ long computer_event_battle(struct Computer2 *comp, struct ComputerEvent *cevent, { if (!create_task_magic_battle_call_to_arms(comp, &pos, 2500, creatrs_num)) { SYNCDBG(18,"Cannot call to arms for %s",cevent->name); - return 0; + return CTaskRet_Unk0; } - return 1; + return CTaskRet_Unk1; } } } SYNCDBG(18,"No hand nor CTA, giving up with %s",cevent->name); - return 0; + return CTaskRet_Unk0; } long computer_event_find_link(struct Computer2 *comp, struct ComputerEvent *cevent,struct Event *event) @@ -256,7 +256,7 @@ struct Thing *find_creature_in_fight_with_enemy(struct Computer2 *comp) { creatng = thing_get(i); cctrl = creature_control_get_from_thing(creatng); - if (thing_is_invalid(creatng) || creature_control_invalid(cctrl)) + if (!thing_is_creature(creatng) || creature_control_invalid(cctrl)) { ERRORLOG("Jump to invalid creature detected"); break; @@ -284,7 +284,7 @@ struct Thing *find_creature_in_fight_with_enemy(struct Computer2 *comp) { creatng = thing_get(i); cctrl = creature_control_get_from_thing(creatng); - if (thing_is_invalid(creatng) || creature_control_invalid(cctrl)) + if (!thing_is_creature(creatng) || creature_control_invalid(cctrl)) { ERRORLOG("Jump to invalid creature detected"); break; @@ -310,11 +310,11 @@ struct Thing *find_creature_in_fight_with_enemy(struct Computer2 *comp) long computer_event_battle_test(struct Computer2 *comp, struct ComputerEvent *cevent) { if (comp->dungeon->fights_num <= 0) { - return 4; + return CTaskRet_Unk4; } struct Thing* creatng = find_creature_in_fight_with_enemy(comp); if (thing_is_invalid(creatng)) { - return 4; + return CTaskRet_Unk4; } struct Coord3d pos; pos.x.val = creatng->mappos.x.val; @@ -326,19 +326,19 @@ long computer_event_battle_test(struct Computer2 *comp, struct ComputerEvent *ce creatrs_num = 1; } if (creatrs_num <= 0) { - return 4; + return CTaskRet_Unk4; } if (!computer_find_safe_non_solid_block(comp, &pos)) { - return 4; + return CTaskRet_Unk4; } if (computer_able_to_use_power(comp, PwrK_HAND, 1, creatrs_num)) { if (!is_task_in_progress(comp, CTT_MoveCreaturesToDefend)) { if (!create_task_move_creatures_to_defend(comp, &pos, creatrs_num, cevent->param2)) { - return 4; + return CTaskRet_Unk4; } - return 1; + return CTaskRet_Unk1; } } if (computer_able_to_use_power(comp, PwrK_CALL2ARMS, 8, 1)) @@ -348,13 +348,13 @@ long computer_event_battle_test(struct Computer2 *comp, struct ComputerEvent *ce if (check_call_to_arms(comp)) { if (!create_task_magic_battle_call_to_arms(comp, &pos, 2500, creatrs_num)) { - return 4; + return CTaskRet_Unk4; } - return 1; + return CTaskRet_Unk1; } } } - return 4; + return CTaskRet_Unk4; } /** @@ -371,13 +371,13 @@ long computer_event_check_fighters(struct Computer2 *comp, struct ComputerEvent { if (comp->dungeon->fights_num <= 0) { - return 4; + return CTaskRet_Unk4; } if (!(computer_able_to_use_power(comp, PwrK_SPEEDCRTR, cevent->param1, 1) || computer_able_to_use_power(comp, PwrK_PROTECT, cevent->param1, 1) || computer_able_to_use_power(comp, PwrK_REBOUND, cevent->param1, 1) || computer_able_to_use_power(comp, PwrK_FLIGHT, cevent->param1, 1) || computer_able_to_use_power(comp, PwrK_VISION, cevent->param1, 1))) { - return 4; + return CTaskRet_Unk4; } struct Thing* fightng = computer_get_creature_in_fight(comp, PwrK_SPEEDCRTR); if (thing_is_invalid(fightng)) @@ -394,17 +394,20 @@ long computer_event_check_fighters(struct Computer2 *comp, struct ComputerEvent fightng = computer_get_creature_in_fight(comp, PwrK_VISION); if (thing_is_invalid(fightng)) { - return 4; + return CTaskRet_Unk4; } } } } } - if (!create_task_magic_speed_up(comp, fightng, cevent->param1)) + if (!is_task_in_progress(comp, CTT_MagicSpeedUp)) { - return 4; + if (!create_task_magic_speed_up(comp, fightng, cevent->param1)) + { + return CTaskRet_Unk4; + } } - return 1; + return CTaskRet_Unk1; } PowerKind computer_choose_attack_spell(struct Computer2 *comp, struct ComputerEvent *cevent, struct Thing *creatng) @@ -447,26 +450,26 @@ long computer_event_attack_magic_foe(struct Computer2 *comp, struct ComputerEven { struct Dungeon* dungeon = comp->dungeon; if (dungeon->fights_num <= 0) { - return 4; + return CTaskRet_Unk4; } // TODO COMPUTER_PLAYER Do we really only want to help creature with the highest score? struct Thing* fightng = computer_get_creature_in_fight(comp, PwrK_None); if (thing_is_invalid(fightng)) { - return 4; + return CTaskRet_Unk4; } struct CreatureControl* figctrl = creature_control_get_from_thing(fightng); struct Thing* creatng = thing_get(figctrl->combat.battle_enemy_idx); if (!thing_is_creature(creatng) || creature_is_dying(creatng)) { - return 4; + return CTaskRet_Unk4; } if (creatng->owner == fightng->owner) { //TODO: Stop computer from initiating attack event on friendly fights - return 4; + return CTaskRet_Unk4; } PowerKind pwkind = computer_choose_attack_spell(comp, cevent, creatng); if (pwkind == PwrK_None) { - return 4; + return CTaskRet_Unk4; } struct ComputerSpells* caspl = &computer_attack_spells[cevent->param3]; int repeat_num = caspl->repeat_num; @@ -476,17 +479,20 @@ long computer_event_attack_magic_foe(struct Computer2 *comp, struct ComputerEven if (splevel < 0) repeat_num = cevent->param1; int gaction = caspl->gaction; - // Create the new task - if (!create_task_attack_magic(comp, creatng, pwkind, repeat_num, splevel, gaction)) { - return 4; + if (!is_task_in_progress(comp, CTT_AttackMagic)) + { + // Create the new task + if (!create_task_attack_magic(comp, creatng, pwkind, repeat_num, splevel, gaction)) { + return CTaskRet_Unk4; + } } - return 1; + return CTaskRet_Unk1; } long computer_event_check_rooms_full(struct Computer2 *comp, struct ComputerEvent *cevent) { SYNCDBG(18,"Starting"); - long ret = 4; + long ret = CTaskRet_Unk4; TbBool emergency_state = computer_player_in_emergency_state(comp); for (struct ValidRooms* bldroom = valid_rooms_to_build; bldroom->rkind > 0; bldroom++) { @@ -507,8 +513,11 @@ long computer_event_check_rooms_full(struct Computer2 *comp, struct ComputerEven get_room_kind_total_used_and_storage_capacity(dungeon, bldroom->rkind, &total_capacity, &used_capacity, &storaged_capacity); if (storaged_capacity > (used_capacity / 2)) { - create_task_sell_traps_and_doors(comp, storaged_capacity/3*2 ,100000,false); - SYNCDBG(8,"Player %d to sell crates to free up space in %s",(int)comp->dungeon->owner,room_code_name(bldroom->rkind)); + if (!is_task_in_progress(comp, CTT_SellTrapsAndDoors)) + { + create_task_sell_traps_and_doors(comp, storaged_capacity/3*2 ,100000,false); + SYNCDBG(8,"Player %d to sell crates to free up space in %s",(int)comp->dungeon->owner,room_code_name(bldroom->rkind)); + } } } continue; @@ -527,7 +536,7 @@ long computer_event_check_rooms_full(struct Computer2 *comp, struct ComputerEven if (cproc->parent == bldroom->process) { SYNCDBG(8,"Player %d will allow process \"%s\"",(int)comp->dungeon->owner,cproc->name); - ret = 1; + ret = CTaskRet_Unk1; reactivate_build_process(comp, bldroom->rkind); } } @@ -543,40 +552,43 @@ long computer_event_attack_door(struct Computer2* comp, struct ComputerEvent* ce if (!thing_is_deployed_door(thing)) { SYNCDBG(8, "Target %s is not a door", thing_model_name(thing)); - return 0; + return CTaskRet_Unk0; } if (!players_are_enemies(comp->dungeon->owner, thing->owner)) { SYNCDBG(8, "Door owner is no longer an enemy"); - return 0; + return CTaskRet_Unk0; } struct Coord3d freepos; if (!get_computer_drop_position_next_to_subtile(&freepos, comp->dungeon, coord_subtile(event->mappos_x), coord_subtile(event->mappos_y))) { SYNCDBG(18, "No drop position near (%d,%d) for %s", (int)coord_subtile(event->mappos_x), (int)coord_subtile(event->mappos_y), cevent->name); - return 0; + return CTaskRet_Unk0; } if (computer_able_to_use_power(comp, PwrK_HAND, 1, 1)) { - long creatrs_def = count_creatures_for_defend_pickup(comp); - if (creatrs_def < cevent->param1) - { - SYNCDBG(18, "Not enough creatures to drop for event %s", cevent->name); - return 4; - } - struct Thing* creatng = find_creature_for_defend_pickup(comp); - if (creatng == INVALID_THING) - { - SYNCDBG(18, "Invalid creature selected for event %s", cevent->name); - return 4; - } - if(!create_task_move_creature_to_pos(comp, creatng, freepos, CrSt_CreatureDoorCombat)) + if (!is_task_in_progress_using_hand(comp)) { - SYNCDBG(18, "Cannot move to position for event %s", cevent->name); - return 0; + long creatrs_def = count_creatures_for_defend_pickup(comp); + if (creatrs_def < cevent->param1) + { + SYNCDBG(18, "Not enough creatures to drop for event %s", cevent->name); + return CTaskRet_Unk4; + } + struct Thing* creatng = find_creature_for_defend_pickup(comp); + if (thing_is_invalid(creatng)) + { + SYNCDBG(18, "Invalid creature selected for event %s", cevent->name); + return CTaskRet_Unk4; + } + if (!create_task_move_creature_to_pos(comp, creatng, freepos, CrSt_CreatureDoorCombat)) + { + SYNCDBG(18, "Cannot move to position for event %s", cevent->name); + return CTaskRet_Unk0; + } + return CTaskRet_Unk1; } - return 1; } if (computer_able_to_use_power(comp, PwrK_CALL2ARMS, 1, 1)) @@ -592,23 +604,23 @@ long computer_event_attack_door(struct Computer2* comp, struct ComputerEvent* ce if (!create_task_magic_battle_call_to_arms(comp, &freepos, cevent->param2, cevent->param3)) { SYNCDBG(18, "Cannot call to arms for %s", cevent->name); - return 0; + return CTaskRet_Unk0; } - return 1; + return CTaskRet_Unk1; } else { SYNCDBG(8, "Drop position is solid for %s", cevent->name); - return 0; + return CTaskRet_Unk0; } } - return 1; + return CTaskRet_Unk1; } } } SYNCDBG(18, "No hand nor CTA, giving up with %s", cevent->name); - return 0; + return CTaskRet_Unk0; } long computer_event_handle_prisoner(struct Computer2* comp, struct ComputerEvent* cevent, struct Event* event) @@ -634,10 +646,15 @@ long computer_event_handle_prisoner(struct Computer2* comp, struct ComputerEvent { if (!creature_would_benefit_from_healing(creatng)) { + if (!computer_able_to_use_power(comp, PwrK_HAND, 1, 1)) { + return CTaskRet_Unk4; + } + if (is_task_in_progress_using_hand(comp)) { + return CTaskRet_Unk4; + } destroom = find_room_of_role_with_spare_capacity(dungeon->owner, RoRoF_Torture, 1); if (!room_is_invalid(destroom)) { - if (create_task_move_creature_to_subtile(comp, creatng, destroom->central_stl_x, destroom->central_stl_y, CrSt_Torturing)) { return CTaskRet_Unk1; @@ -690,12 +707,7 @@ long computer_event_save_tortured(struct Computer2* comp, struct ComputerEvent* { struct Dungeon* dungeon = comp->dungeon; int health_permil = (cevent->param1 * 10); - - // If we don't have the power to pick up creatures, fail now - if (!computer_able_to_use_power(comp, PwrK_HAND, 1, 1)) { - return 4; - } - + // Do not check for PwrK_HAND here; this would prevent the computer from taking other actions without it! // Do we have a prison to put the unit back into? struct Room* destroom = NULL; TbBool can_return = false; @@ -723,8 +735,7 @@ long computer_event_save_tortured(struct Computer2* comp, struct ComputerEvent* { struct Thing* creatng = thing_get(i); struct CreatureControl* cctrl = creature_control_get_from_thing(creatng); - struct Room* room = get_room_thing_is_on(creatng); - if (thing_is_invalid(creatng) || creature_control_invalid(cctrl)) + if (!thing_is_creature(creatng) || creature_control_invalid(cctrl)) { ERRORLOG("Jump to invalid creature detected"); break; @@ -738,6 +749,7 @@ long computer_event_save_tortured(struct Computer2* comp, struct ComputerEvent* { continue; } + struct Room* room = get_room_thing_is_on(creatng); if (room->owner == creatng->owner) { continue; @@ -766,6 +778,13 @@ long computer_event_save_tortured(struct Computer2* comp, struct ComputerEvent* //move back to prison if (can_return == true) { + // If we don't have the power to pick up creatures, fail now + if (!computer_able_to_use_power(comp, PwrK_HAND, 1, 1)) { + return CTaskRet_Unk4; + } + if (is_task_in_progress_using_hand(comp)) { + return CTaskRet_Unk4; + } if (create_task_move_creature_to_subtile(comp, creatng, destroom->central_stl_x, destroom->central_stl_y, CrSt_CreatureInPrison)) { moved++; @@ -780,13 +799,10 @@ long computer_event_check_imps_in_danger(struct Computer2 *comp, struct Computer { struct Dungeon* dungeon = comp->dungeon; if (dungeon->fights_num <= 0) { - return 4; - } - // If we don't have the power to pick up creatures, fail now - if (!computer_able_to_use_power(comp, PwrK_HAND, 1, 1)) { - return 4; + return CTaskRet_Unk4; } - long result = 4; + // Do not check for PwrK_HAND here; this would prevent the computer from taking other actions without it! + long result = CTaskRet_Unk4; // Search through special diggers unsigned long k = 0; int i = dungeon->digger_list_start; @@ -794,7 +810,7 @@ long computer_event_check_imps_in_danger(struct Computer2 *comp, struct Computer { struct Thing* creatng = thing_get(i); struct CreatureControl* cctrl = creature_control_get_from_thing(creatng); - if (thing_is_invalid(creatng) || creature_control_invalid(cctrl)) + if (!thing_is_creature(creatng) || creature_control_invalid(cctrl)) { ERRORLOG("Jump to invalid creature detected"); break; @@ -806,7 +822,7 @@ long computer_event_check_imps_in_danger(struct Computer2 *comp, struct Computer if (!creature_is_being_unconscious(creatng) && !creature_affected_by_spell(creatng, SplK_Chicken)) { // Small chance to casting invisibility,on imp in battle. - if((CREATURE_RANDOM(creatng, 150) == 1) && computer_able_to_use_power(comp, PwrK_CONCEAL, 8, 1) && !thing_affected_by_spell(creatng, PwrK_CONCEAL)) + if ((CREATURE_RANDOM(creatng, 150) == 1) && computer_able_to_use_power(comp, PwrK_CONCEAL, 8, 1) && !thing_affected_by_spell(creatng, PwrK_CONCEAL)) { magic_use_available_power_on_thing(creatng->owner, PwrK_CONCEAL, 8, 0, 0, creatng, PwMod_Default); } @@ -815,13 +831,17 @@ long computer_event_check_imps_in_danger(struct Computer2 *comp, struct Computer TbBool needs_help; if (get_creature_health_permil(creatng) < 500) { - needs_help = 1; + needs_help = true; } else { needs_help = creature_is_being_attacked_by_enemy_creature_not_digger(creatng); } if (needs_help) { + // PwrK_HAND check should not be needed here, because we've already done that with can_thing_be_picked_up_by_player + if (is_task_in_progress_using_hand(comp)) { + return CTaskRet_Unk4; + } // Move creature to heart, unless it already is near the heart struct Thing* heartng = get_player_soul_container(dungeon->owner); if (get_2d_distance(&creatng->mappos, &heartng->mappos) > subtile_coord(16,0)) @@ -830,7 +850,7 @@ long computer_event_check_imps_in_danger(struct Computer2 *comp, struct Computer heartng->mappos.x.stl.num, heartng->mappos.y.stl.num, CrSt_ImpDoingNothing)) { break; } - result = 1; + result = CTaskRet_Unk1; } } } @@ -891,7 +911,7 @@ long computer_event_breach(struct Computer2 *comp, struct ComputerEvent *cevent, pos.y.val = event->mappos_y; pos.z.val = 0; if ((pos.x.val <= 0) || (pos.y.val <= 0)) { - return 0; + return CTaskRet_Unk0; } long count = count_creatures_for_pickup(comp, &pos, 0, cevent->param2); long i = count * cevent->param1 / 100; @@ -899,15 +919,18 @@ long computer_event_breach(struct Computer2 *comp, struct ComputerEvent *cevent, i = 1; } if (i <= 0) { - return 4; + return CTaskRet_Unk4; } if (!computer_find_safe_non_solid_block(comp, &pos)) { - return 4; + return CTaskRet_Unk4; } - if (!create_task_move_creatures_to_defend(comp, &pos, i, cevent->param2)) { - return 4; + if (!is_task_in_progress(comp, CTT_MoveCreaturesToDefend)) + { + if (!create_task_move_creatures_to_defend(comp, &pos, i, cevent->param2)) { + return CTaskRet_Unk4; + } } - return 1; + return CTaskRet_Unk1; } /******************************************************************************/ diff --git a/src/player_compprocs.c b/src/player_compprocs.c index aee4564978..d7d341b484 100644 --- a/src/player_compprocs.c +++ b/src/player_compprocs.c @@ -761,39 +761,40 @@ TbBool imp_can_be_moved_to_mine(const struct Thing *creatng) long move_imp_to_dig_here(struct Computer2 *comp, struct Coord3d *pos, long max_amount) { - struct Dungeon* dungeon = comp->dungeon; - long amount_did = 0; - - unsigned long k = 0; - int i = dungeon->digger_list_start; - while (i != 0) + if (!is_task_in_progress_using_hand(comp)) { - const struct Thing* creatng = thing_get(i); - TRACE_THING(creatng); - const struct CreatureControl* cctrl = creature_control_get_from_thing(creatng); - if (thing_is_invalid(creatng) || creature_control_invalid(cctrl)) + struct Dungeon* dungeon = comp->dungeon; + unsigned long k = 0; + int i = dungeon->digger_list_start; + while (i != 0) { - ERRORLOG("Jump to invalid creature detected"); - break; - } - i = cctrl->players_next_creature_idx; - // Thing list loop body - if (amount_did >= max_amount) - break; - if (can_thing_be_picked_up_by_player(creatng, dungeon->owner) && imp_can_be_moved_to_dig(creatng)) - { - if (!create_task_move_creature_to_pos(comp, creatng, *pos, CrSt_ImpDigsDirt)) { + const struct Thing* creatng = thing_get(i); + TRACE_THING(creatng); + const struct CreatureControl* cctrl = creature_control_get_from_thing(creatng); + if (!thing_is_creature(creatng) || creature_control_invalid(cctrl)) + { + ERRORLOG("Jump to invalid creature detected"); + break; + } + i = cctrl->players_next_creature_idx; + // Thing list loop body + if (amount_did >= max_amount) + break; + if (can_thing_be_picked_up_by_player(creatng, dungeon->owner) && imp_can_be_moved_to_dig(creatng)) + { + if (!create_task_move_creature_to_pos(comp, creatng, *pos, CrSt_ImpDigsDirt)) { + break; + } + amount_did++; + } + // Thing list loop body ends + k++; + if (k > THINGS_COUNT) + { + ERRORLOG("Infinite loop detected when sweeping things list"); break; } - amount_did++; - } - // Thing list loop body ends - k++; - if (k > THINGS_COUNT) - { - ERRORLOG("Infinite loop detected when sweeping things list"); - break; } } return amount_did; @@ -801,39 +802,40 @@ long move_imp_to_dig_here(struct Computer2 *comp, struct Coord3d *pos, long max_ long move_imp_to_mine_here(struct Computer2 *comp, struct Coord3d *pos, long max_amount) { - struct Dungeon* dungeon = comp->dungeon; - long amount_did = 0; - - unsigned long k = 0; - int i = dungeon->digger_list_start; - while (i != 0) + if (!is_task_in_progress_using_hand(comp)) { - const struct Thing* creatng = thing_get(i); - TRACE_THING(creatng); - const struct CreatureControl* cctrl = creature_control_get_from_thing(creatng); - if (thing_is_invalid(creatng) || creature_control_invalid(cctrl)) + struct Dungeon* dungeon = comp->dungeon; + unsigned long k = 0; + int i = dungeon->digger_list_start; + while (i != 0) { - ERRORLOG("Jump to invalid creature detected"); - break; - } - i = cctrl->players_next_creature_idx; - // Thing list loop body - if (amount_did >= max_amount) - break; - if (can_thing_be_picked_up_by_player(creatng, dungeon->owner) && imp_can_be_moved_to_mine(creatng)) - { - if (!create_task_move_creature_to_pos(comp, creatng, *pos, CrSt_ImpMinesGold)) { + const struct Thing* creatng = thing_get(i); + TRACE_THING(creatng); + const struct CreatureControl* cctrl = creature_control_get_from_thing(creatng); + if (!thing_is_creature(creatng) || creature_control_invalid(cctrl)) + { + ERRORLOG("Jump to invalid creature detected"); + break; + } + i = cctrl->players_next_creature_idx; + // Thing list loop body + if (amount_did >= max_amount) + break; + if (can_thing_be_picked_up_by_player(creatng, dungeon->owner) && imp_can_be_moved_to_mine(creatng)) + { + if (!create_task_move_creature_to_pos(comp, creatng, *pos, CrSt_ImpMinesGold)) { + break; + } + amount_did++; + } + // Thing list loop body ends + k++; + if (k > THINGS_COUNT) + { + ERRORLOG("Infinite loop detected when sweeping things list"); break; } - amount_did++; - } - // Thing list loop body ends - k++; - if (k > THINGS_COUNT) - { - ERRORLOG("Infinite loop detected when sweeping things list"); - break; } } return amount_did;