|
@@ -189,96 +189,98 @@ static void UpdateCurrencies()
|
|
|
/* Up to revision 1413 the invisible tiles at the southern border have not been
|
|
|
* MP_VOID, even though they should have. This is fixed by this function
|
|
|
*/
|
|
|
static void UpdateVoidTiles()
|
|
|
{
|
|
|
uint i;
|
|
|
|
|
|
for (i = 0; i < MapMaxY(); ++i) MakeVoid(i * MapSizeX() + MapMaxX());
|
|
|
for (i = 0; i < MapSizeX(); ++i) MakeVoid(MapSizeX() * MapMaxY() + i);
|
|
|
}
|
|
|
|
|
|
static inline RailType UpdateRailType(RailType rt, RailType min)
|
|
|
{
|
|
|
return rt >= min ? (RailType)(rt + 1): rt;
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* Initialization of the windows and several kinds of caches.
|
|
|
* This is not done directly in AfterLoadGame because these
|
|
|
* functions require that all saveload conversions have been
|
|
|
* done. As people tend to add savegame conversion stuff after
|
|
|
* the intialization of the windows and caches quite some bugs
|
|
|
* had been made.
|
|
|
* Moving this out of there is both cleaner and less bug-prone.
|
|
|
*/
|
|
|
static void InitializeWindowsAndCaches()
|
|
|
{
|
|
|
/* Initialize windows */
|
|
|
ResetWindowSystem();
|
|
|
SetupColoursAndInitialWindow();
|
|
|
|
|
|
ResetViewportAfterLoadGame();
|
|
|
|
|
|
/* Update coordinates of the signs. */
|
|
|
UpdateAllStationVirtCoords();
|
|
|
UpdateAllSignVirtCoords();
|
|
|
UpdateAllTownVirtCoords();
|
|
|
|
|
|
Company *c;
|
|
|
FOR_ALL_COMPANIES(c) {
|
|
|
/* For each company, verify (while loading a scenario) that the inauguration date is the current year and set it
|
|
|
* accordingly if it is not the case. No need to set it on companies that are not been used already,
|
|
|
* thus the MIN_YEAR (which is really nothing more than Zero, initialized value) test */
|
|
|
if (_file_to_saveload.filetype == FT_SCENARIO && c->inaugurated_year != MIN_YEAR) {
|
|
|
c->inaugurated_year = _cur_year;
|
|
|
}
|
|
|
}
|
|
|
|
|
|
RecomputePrices();
|
|
|
|
|
|
SetCachedEngineCounts();
|
|
|
|
|
|
Station::RecomputeIndustriesNearForAll();
|
|
|
RebuildSubsidisedSourceAndDestinationCache();
|
|
|
|
|
|
/* Towns have a noise controlled number of airports system
|
|
|
* So each airport's noise value must be added to the town->noise_reached value
|
|
|
* Reset each town's noise_reached value to '0' before. */
|
|
|
UpdateAirportsNoise();
|
|
|
|
|
|
CheckTrainsLengths();
|
|
|
}
|
|
|
|
|
|
typedef void (CDECL *SignalHandlerPointer)(int);
|
|
|
static SignalHandlerPointer _prev_segfault = NULL;
|
|
|
static SignalHandlerPointer _prev_abort = NULL;
|
|
|
static SignalHandlerPointer _prev_fpe = NULL;
|
|
|
|
|
|
static void CDECL HandleSavegameLoadCrash(int signum);
|
|
|
|
|
|
/**
|
|
|
* Replaces signal handlers of SIGSEGV and SIGABRT
|
|
|
* and stores pointers to original handlers in memory.
|
|
|
*/
|
|
|
static void SetSignalHandlers()
|
|
|
{
|
|
|
_prev_segfault = signal(SIGSEGV, HandleSavegameLoadCrash);
|
|
|
_prev_abort = signal(SIGABRT, HandleSavegameLoadCrash);
|
|
|
_prev_fpe = signal(SIGFPE, HandleSavegameLoadCrash);
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* Resets signal handlers back to original handlers.
|
|
|
*/
|
|
|
static void ResetSignalHandlers()
|
|
|
{
|
|
|
signal(SIGSEGV, _prev_segfault);
|
|
|
signal(SIGABRT, _prev_abort);
|
|
|
signal(SIGFPE, _prev_fpe);
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
* Try to find the overridden GRF identifier of the given GRF.
|
|
|
* @param c the GRF to get the 'previous' version of.
|
|
|
* @return the GRF identifier or \a c if none could be found.
|
|
|
*/
|
|
|
static const GRFIdentifier *GetOverriddenIdentifier(const GRFConfig *c)
|
|
|
{
|
|
@@ -485,99 +487,96 @@ bool AfterLoadGame()
|
|
|
/* the same applies to Company::location_of_HQ */
|
|
|
Company *c;
|
|
|
FOR_ALL_COMPANIES(c) {
|
|
|
if (c->location_of_HQ == 0 || (CheckSavegameVersion(4) && c->location_of_HQ == 0xFFFF)) {
|
|
|
c->location_of_HQ = INVALID_TILE;
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
|
|
|
/* convert road side to my format. */
|
|
|
if (_settings_game.vehicle.road_side) _settings_game.vehicle.road_side = 1;
|
|
|
|
|
|
/* Check if all NewGRFs are present, we are very strict in MP mode */
|
|
|
GRFListCompatibility gcf_res = IsGoodGRFConfigList();
|
|
|
if (_networking && gcf_res != GLC_ALL_GOOD) {
|
|
|
SetSaveLoadError(STR_NETWORK_ERROR_CLIENT_NEWGRF_MISMATCH);
|
|
|
/* Restore the signals */
|
|
|
ResetSignalHandlers();
|
|
|
return false;
|
|
|
}
|
|
|
|
|
|
switch (gcf_res) {
|
|
|
case GLC_COMPATIBLE: _switch_mode_errorstr = STR_NEWGRF_COMPATIBLE_LOAD_WARNING; break;
|
|
|
case GLC_NOT_FOUND: _switch_mode_errorstr = STR_NEWGRF_DISABLED_WARNING; _pause_mode = PM_PAUSED_ERROR; break;
|
|
|
default: break;
|
|
|
}
|
|
|
|
|
|
/* Update current year
|
|
|
* must be done before loading sprites as some newgrfs check it */
|
|
|
SetDate(_date);
|
|
|
|
|
|
/* Force dynamic engines off when loading older savegames */
|
|
|
if (CheckSavegameVersion(95)) _settings_game.vehicle.dynamic_engines = 0;
|
|
|
|
|
|
/* Load the sprites */
|
|
|
GfxLoadSprites();
|
|
|
LoadStringWidthTable();
|
|
|
|
|
|
/* Copy temporary data to Engine pool */
|
|
|
CopyTempEngineData();
|
|
|
|
|
|
/* Connect front and rear engines of multiheaded trains and converts
|
|
|
* subtype to the new format */
|
|
|
if (CheckSavegameVersionOldStyle(17, 1)) ConvertOldMultiheadToNew();
|
|
|
|
|
|
/* Connect front and rear engines of multiheaded trains */
|
|
|
ConnectMultiheadedTrains();
|
|
|
|
|
|
/* reinit the landscape variables (landscape might have changed) */
|
|
|
InitializeLandscapeVariables(true);
|
|
|
|
|
|
/* Update all vehicles */
|
|
|
AfterLoadVehicles(true);
|
|
|
|
|
|
/* Make sure there is an AI attached to an AI company */
|
|
|
{
|
|
|
Company *c;
|
|
|
FOR_ALL_COMPANIES(c) {
|
|
|
if (c->is_ai && c->ai_instance == NULL) AI::StartNew(c->index);
|
|
|
}
|
|
|
}
|
|
|
|
|
|
/* make sure there is a town in the game */
|
|
|
if (_game_mode == GM_NORMAL && !ClosestTownFromTile(0, UINT_MAX)) {
|
|
|
SetSaveLoadError(STR_ERROR_NO_TOWN_IN_SCENARIO);
|
|
|
/* Restore the signals */
|
|
|
ResetSignalHandlers();
|
|
|
return false;
|
|
|
}
|
|
|
|
|
|
/* The void tiles on the southern border used to belong to a wrong class (pre 4.3).
|
|
|
* This problem appears in savegame version 21 too, see r3455. But after loading the
|
|
|
* savegame and saving again, the buggy map array could be converted to new savegame
|
|
|
* version. It didn't show up before r12070. */
|
|
|
if (CheckSavegameVersion(87)) UpdateVoidTiles();
|
|
|
|
|
|
/* If Load Scenario / New (Scenario) Game is used,
|
|
|
* a company does not exist yet. So create one here.
|
|
|
* 1 exeption: network-games. Those can have 0 companies
|
|
|
* But this exeption is not true for non dedicated network_servers! */
|
|
|
if (!Company::IsValidID(COMPANY_FIRST) && (!_networking || (_networking && _network_server && !_network_dedicated)))
|
|
|
DoStartupNewCompany(false);
|
|
|
|
|
|
/* Fix the cache for cargo payments. */
|
|
|
CargoPayment *cp;
|
|
|
FOR_ALL_CARGO_PAYMENTS(cp) {
|
|
|
cp->front->cargo_payment = cp;
|
|
|
cp->current_station = cp->front->last_station_visited;
|
|
|
}
|
|
|
|
|
|
if (CheckSavegameVersion(72)) {
|
|
|
/* Locks/shiplifts in very old savegames had OWNER_WATER as owner */
|
|
|
for (TileIndex t = 0; t < MapSize(); t++) {
|
|
|
switch (GetTileType(t)) {
|
|
|
default: break;
|
|
|
|
|
|
case MP_WATER:
|
|
|
if (GetWaterTileType(t) == WATER_TILE_LOCK && GetTileOwner(t) == OWNER_WATER) SetTileOwner(t, OWNER_NONE);
|
|
|
break;
|
|
@@ -1884,85 +1883,103 @@ bool AfterLoadGame()
|
|
|
if (wp->facilities & FACIL_TRAIN) {
|
|
|
wp->train_station.tile = wp->xy;
|
|
|
wp->train_station.w = 1;
|
|
|
wp->train_station.h = 1;
|
|
|
} else {;
|
|
|
wp->train_station.tile = INVALID_TILE;
|
|
|
wp->train_station.w = 0;
|
|
|
wp->train_station.h = 0;
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
|
|
|
if (CheckSavegameVersion(125)) {
|
|
|
/* Convert old subsidies */
|
|
|
Subsidy *s;
|
|
|
FOR_ALL_SUBSIDIES(s) {
|
|
|
/* Convert only nonawarded subsidies. The original source and destination town/industry
|
|
|
* can't be determined anymore for awarded subsidies, so invalidate them. */
|
|
|
if (s->remaining < 12) {
|
|
|
s->remaining = 12 - s->remaining; // convert "age" to "remaining"
|
|
|
s->awarded = INVALID_COMPANY; // not awarded to anyone
|
|
|
const CargoSpec *cs = CargoSpec::Get(s->cargo_type);
|
|
|
switch (cs->town_effect) {
|
|
|
case TE_PASSENGERS:
|
|
|
case TE_MAIL:
|
|
|
/* Town -> Town */
|
|
|
s->src_type = s->dst_type = ST_TOWN;
|
|
|
if (Town::IsValidID(s->src) && Town::IsValidID(s->dst)) continue;
|
|
|
break;
|
|
|
case TE_GOODS:
|
|
|
case TE_FOOD:
|
|
|
/* Industry -> Town */
|
|
|
s->src_type = ST_INDUSTRY;
|
|
|
s->dst_type = ST_TOWN;
|
|
|
if (Industry::IsValidID(s->src) && Town::IsValidID(s->dst)) continue;
|
|
|
break;
|
|
|
default:
|
|
|
/* Industry -> Industry */
|
|
|
s->src_type = s->dst_type = ST_INDUSTRY;
|
|
|
if (Industry::IsValidID(s->src) && Industry::IsValidID(s->dst)) continue;
|
|
|
break;
|
|
|
}
|
|
|
}
|
|
|
/* Awarded subsidy or invalid source/destination, invalidate */
|
|
|
delete s;
|
|
|
}
|
|
|
}
|
|
|
|
|
|
if (CheckSavegameVersion(126)) {
|
|
|
/* Recompute inflation based on old unround loan limit
|
|
|
* Note: Max loan is 500000. With an inflation of 4% across 170 years
|
|
|
* that results in a max loan of about 0.7 * 2^31.
|
|
|
* So taking the 16 bit fractional part into account there are plenty of bits left
|
|
|
* for unmodified savegames ...
|
|
|
*/
|
|
|
uint64 aimed_inflation = (_economy.old_max_loan_unround << 16 | _economy.old_max_loan_unround_fract) / _settings_game.difficulty.max_loan;
|
|
|
|
|
|
/* ... well, just clamp it then. */
|
|
|
if (aimed_inflation > MAX_INFLATION) aimed_inflation = MAX_INFLATION;
|
|
|
|
|
|
/* Simulate the inflation, so we also get the payment inflation */
|
|
|
while (_economy.inflation_prices < aimed_inflation) {
|
|
|
AddInflation(false);
|
|
|
}
|
|
|
}
|
|
|
|
|
|
AfterLoadLabelMaps();
|
|
|
|
|
|
GamelogPrintDebug(1);
|
|
|
|
|
|
InitializeWindowsAndCaches();
|
|
|
/* Restore the signals */
|
|
|
ResetSignalHandlers();
|
|
|
return true;
|
|
|
}
|
|
|
|
|
|
/** Reload all NewGRF files during a running game. This is a cut-down
|
|
|
* version of AfterLoadGame().
|
|
|
* XXX - We need to reset the vehicle position hash because with a non-empty
|
|
|
* hash AfterLoadVehicles() will loop infinitely. We need AfterLoadVehicles()
|
|
|
* to recalculate vehicle data as some NewGRF vehicle sets could have been
|
|
|
* removed or added and changed statistics */
|
|
|
void ReloadNewGRFData()
|
|
|
{
|
|
|
/* reload grf data */
|
|
|
GfxLoadSprites();
|
|
|
LoadStringWidthTable();
|
|
|
ResetEconomy();
|
|
|
RecomputePrices();
|
|
|
/* reload vehicles */
|
|
|
ResetVehiclePosHash();
|
|
|
AfterLoadVehicles(false);
|
|
|
StartupEngines();
|
|
|
SetCachedEngineCounts();
|
|
|
/* update station graphics */
|
|
|
AfterLoadStations();
|
|
|
/* Check and update house and town values */
|
|
|
UpdateHousesAndTowns();
|
|
|
/* Update livery selection windows */
|
|
|
for (CompanyID i = COMPANY_FIRST; i < MAX_COMPANIES; i++) InvalidateWindowData(WC_COMPANY_COLOUR, i);
|
|
|
/* redraw the whole screen */
|
|
|
MarkWholeScreenDirty();
|
|
|
CheckTrainsLengths();
|
|
|
}
|