Skip to content

Commit 9e79f9d

Browse files
authored
Fix corrupt neutral room list (#4412)
and a recalculation when it corrupts someplace else.
1 parent ee363d7 commit 9e79f9d

File tree

2 files changed

+43
-18
lines changed

2 files changed

+43
-18
lines changed

src/room_data.c

Lines changed: 16 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -3144,25 +3144,24 @@ void kill_room_slab_and_contents(PlayerNumber plyr_idx, MapSlabCoord slb_x, MapS
31443144
void free_room_structure(struct Room *room)
31453145
{
31463146
PlayerNumber owner = room->owner;
3147-
if ( game.neutral_player_num != owner )
3148-
{
3149-
struct Dungeon *dungeon = get_dungeon(owner);
31503147

3151-
if ( room->index == dungeon->room_list_start[room->kind] )
3152-
{
3153-
dungeon->room_list_start[room->kind] = room->next_of_owner;
3154-
struct Room *next_room = room_get(room->next_of_owner);
3155-
next_room->prev_of_owner = 0;
3156-
}
3157-
else
3158-
{
3159-
struct Room *next_room = room_get(room->next_of_owner);
3160-
next_room->prev_of_owner = room->prev_of_owner;
3161-
struct Room *prev_room = room_get(room->prev_of_owner);
3162-
prev_room->next_of_owner = room->next_of_owner;
3163-
}
3164-
--dungeon->room_discrete_count[room->kind];
3148+
struct Dungeon *dungeon = get_dungeon(owner);
3149+
3150+
if ( room->index == dungeon->room_list_start[room->kind] )
3151+
{
3152+
dungeon->room_list_start[room->kind] = room->next_of_owner;
3153+
struct Room *next_room = room_get(room->next_of_owner);
3154+
next_room->prev_of_owner = 0;
3155+
}
3156+
else
3157+
{
3158+
struct Room *next_room = room_get(room->next_of_owner);
3159+
next_room->prev_of_owner = room->prev_of_owner;
3160+
struct Room *prev_room = room_get(room->prev_of_owner);
3161+
prev_room->next_of_owner = room->next_of_owner;
31653162
}
3163+
--dungeon->room_discrete_count[room->kind];
3164+
31663165
remove_room_from_global_list(room);
31673166
delete_room_structure(room);
31683167
}

src/room_list.c

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,31 @@ void clear_rooms(void)
5252
}
5353
}
5454

55+
void recalculate_player_roomlist(PlayerNumber plyr_idx,RoomKind rkind)
56+
{
57+
struct Dungeon* dungeon = get_dungeon(plyr_idx);
58+
59+
RoomIndex last_idx = 0;
60+
61+
for (RoomIndex room_idx = 0; room_idx < ROOMS_COUNT; room_idx++)
62+
{
63+
struct Room* room = &game.rooms[room_idx];
64+
if (!room_is_invalid(room) && (room->owner == plyr_idx) && (room->kind == rkind))
65+
{
66+
if (last_idx != 0)
67+
{
68+
struct Room* last_room = &game.rooms[last_idx];
69+
last_room->prev_of_owner = room->index;
70+
}
71+
72+
room->next_of_owner = last_idx;
73+
dungeon->room_list_start[rkind] = room->index;
74+
last_idx = room->index;
75+
76+
}
77+
}
78+
}
79+
5580
/**
5681
* Counts amount of rooms of specific type owned by specific player.
5782
* @param plyr_idx The player number. Only specific player number is accepted.
@@ -85,7 +110,8 @@ long count_player_rooms_of_type(PlayerNumber plyr_idx, RoomKind rkind)
85110
k++;
86111
if (k > ROOMS_COUNT)
87112
{
88-
ERRORLOG("Infinite loop detected when sweeping rooms list");
113+
ERRORLOG("Infinite loop detected when sweeping rooms list %s for player %d",room_code_name(rkind),(int)plyr_idx);
114+
recalculate_player_roomlist(plyr_idx, rkind);
89115
break;
90116
}
91117
}

0 commit comments

Comments
 (0)