# HG changeset patch # User smatz # Date 2009-05-13 21:38:23 # Node ID 7e0b37f9045166206ecb1ec700cf0327c071cd0f # Parent 7c734e0358af6579a07153bea9b1d8a8788010e7 (svn r16302) -Codechange: remove Vehicle::AllocateList diff --git a/src/articulated_vehicles.cpp b/src/articulated_vehicles.cpp --- a/src/articulated_vehicles.cpp +++ b/src/articulated_vehicles.cpp @@ -283,10 +283,10 @@ void CheckConsistencyOfArticulatedVehicl } } -void AddArticulatedParts(Vehicle **vl, VehicleType type) +void AddArticulatedParts(Vehicle *first, VehicleType type) { - const Vehicle *v = vl[0]; - Vehicle *u = vl[0]; + const Vehicle *v = first; + Vehicle *u = first; if (!HasBit(EngInfo(v->engine_type)->callbackmask, CBM_VEHICLE_ARTIC_ENGINE)) return; @@ -294,23 +294,20 @@ void AddArticulatedParts(Vehicle **vl, V uint16 callback = GetVehicleCallback(CBID_VEHICLE_ARTIC_ENGINE, i, 0, v->engine_type, v); if (callback == CALLBACK_FAILED || GB(callback, 0, 8) == 0xFF) return; - /* Attempt to use pre-allocated vehicles until they run out. This can happen - * if the callback returns different values depending on the cargo type. */ - u->SetNext(vl[i]); - if (u->Next() == NULL) return; - - Vehicle *previous = u; - u = u->Next(); + /* In the (very rare) case the GRF reported wrong number of articulated parts + * and we run out of available vehicles, bail out. */ + if (!Vehicle::CanAllocateItem()) return; EngineID engine_type = GetNewEngineID(GetEngineGRF(v->engine_type), type, GB(callback, 0, 7)); bool flip_image = HasBit(callback, 7); + Vehicle *previous = u; const Engine *e_artic = GetEngine(engine_type); switch (type) { default: NOT_REACHED(); case VEH_TRAIN: - u = new (u) Train(); + u = new Train(); u->subtype = 0; previous->SetNext(u); u->u.rail.track = v->u.rail.track; @@ -330,7 +327,7 @@ void AddArticulatedParts(Vehicle **vl, V break; case VEH_ROAD: - u = new (u) RoadVehicle(); + u = new RoadVehicle(); u->subtype = 0; previous->SetNext(u); u->u.road.first_engine = v->engine_type; diff --git a/src/articulated_vehicles.h b/src/articulated_vehicles.h --- a/src/articulated_vehicles.h +++ b/src/articulated_vehicles.h @@ -10,7 +10,7 @@ uint CountArticulatedParts(EngineID engine_type, bool purchase_window); uint16 *GetCapacityOfArticulatedParts(EngineID engine, VehicleType type); -void AddArticulatedParts(Vehicle **vl, VehicleType type); +void AddArticulatedParts(Vehicle *first, VehicleType type); uint32 GetUnionOfArticulatedRefitMasks(EngineID engine, VehicleType type, bool include_initial_cargo_type); uint32 GetIntersectionOfArticulatedRefitMasks(EngineID engine, VehicleType type, bool include_initial_cargo_type); bool IsArticulatedVehicleCarryingDifferentCargos(const Vehicle *v, CargoID *cargo_type); diff --git a/src/roadveh_cmd.cpp b/src/roadveh_cmd.cpp --- a/src/roadveh_cmd.cpp +++ b/src/roadveh_cmd.cpp @@ -160,9 +160,6 @@ void RoadVehUpdateCache(Vehicle *v) */ CommandCost CmdBuildRoadVeh(TileIndex tile, DoCommandFlag flags, uint32 p1, uint32 p2, const char *text) { - Vehicle *v; - UnitID unit_num; - if (!IsEngineBuildable(p1, VEH_ROAD, _current_company)) return_cmd_error(STR_ROAD_VEHICLE_NOT_AVAILABLE); const Engine *e = GetEngine(p1); @@ -181,47 +178,40 @@ CommandCost CmdBuildRoadVeh(TileIndex ti uint num_vehicles = 1 + CountArticulatedParts(p1, false); - /* Allow for the front and the articulated parts, plus one to "terminate" the list. */ - Vehicle **vl = AllocaM(Vehicle*, num_vehicles + 1); - memset(vl, 0, sizeof(*vl) * (num_vehicles + 1)); - - if (!Vehicle::AllocateList(vl, num_vehicles)) { + /* Allow for the front and the articulated parts */ + if (!Vehicle::CanAllocateItem(num_vehicles)) { return_cmd_error(STR_ERROR_TOO_MANY_VEHICLES_IN_GAME); } - v = vl[0]; - /* find the first free roadveh id */ - unit_num = (flags & DC_AUTOREPLACE) ? 0 : GetFreeUnitNumber(VEH_ROAD); - if (unit_num > _settings_game.vehicle.max_roadveh) + UnitID unit_num = (flags & DC_AUTOREPLACE) ? 0 : GetFreeUnitNumber(VEH_ROAD); + if (unit_num > _settings_game.vehicle.max_roadveh) { return_cmd_error(STR_ERROR_TOO_MANY_VEHICLES_IN_GAME); + } if (flags & DC_EXEC) { - int x; - int y; - const RoadVehicleInfo *rvi = RoadVehInfo(p1); - v = new (v) RoadVehicle(); + Vehicle *v = new RoadVehicle(); v->unitnumber = unit_num; v->direction = DiagDirToDir(GetRoadDepotDirection(tile)); v->owner = _current_company; v->tile = tile; - x = TileX(tile) * TILE_SIZE + TILE_SIZE / 2; - y = TileY(tile) * TILE_SIZE + TILE_SIZE / 2; + int x = TileX(tile) * TILE_SIZE + TILE_SIZE / 2; + int y = TileY(tile) * TILE_SIZE + TILE_SIZE / 2; v->x_pos = x; v->y_pos = y; v->z_pos = GetSlopeZ(x, y); - v->running_ticks = 0; +// v->running_ticks = 0; v->u.road.state = RVSB_IN_DEPOT; v->vehstatus = VS_HIDDEN | VS_STOPPED | VS_DEFPAL; v->spritenum = rvi->image_index; v->cargo_type = e->GetDefaultCargoType(); - v->cargo_subtype = 0; +// v->cargo_subtype = 0; v->cargo_cap = rvi->capacity; // v->cargo_count = 0; v->value = cost.GetCost(); @@ -230,7 +220,7 @@ CommandCost CmdBuildRoadVeh(TileIndex ti // v->load_unload_time_rem = 0; // v->progress = 0; -// v->u.road.overtaking = 0; +// v->u.road.overtaking = 0; v->last_station_visited = INVALID_STATION; v->max_speed = rvi->max_speed; @@ -261,7 +251,7 @@ CommandCost CmdBuildRoadVeh(TileIndex ti v->cargo_cap = rvi->capacity; - AddArticulatedParts(vl, VEH_ROAD); + AddArticulatedParts(v, VEH_ROAD); /* Call various callbacks after the whole consist has been constructed */ for (Vehicle *u = v; u != NULL; u = u->Next()) { diff --git a/src/train_cmd.cpp b/src/train_cmd.cpp --- a/src/train_cmd.cpp +++ b/src/train_cmd.cpp @@ -641,31 +641,28 @@ static CommandCost CmdBuildRailWagon(Eng uint num_vehicles = 1 + CountArticulatedParts(engine, false); - /* Allow for the wagon and the articulated parts, plus one to "terminate" the list. */ - Vehicle **vl = AllocaM(Vehicle*, num_vehicles + 1); - memset(vl, 0, sizeof(*vl) * (num_vehicles + 1)); - - if (!Vehicle::AllocateList(vl, num_vehicles)) { + /* Allow for the wagon and the articulated parts */ + if (!Vehicle::CanAllocateItem(num_vehicles)) { return_cmd_error(STR_ERROR_TOO_MANY_VEHICLES_IN_GAME); } if (flags & DC_EXEC) { - Vehicle *v = vl[0]; - v->spritenum = rvi->image_index; - Vehicle *u = NULL; Vehicle *w; FOR_ALL_VEHICLES(w) { + /* do not connect new wagon with crashed/flooded consists */ if (w->type == VEH_TRAIN && w->tile == tile && - IsFreeWagon(w) && w->engine_type == engine && - !HASBITS(w->vehstatus, VS_CRASHED)) { /// do not connect new wagon with crashed/flooded consists + IsFreeWagon(w) && w->engine_type == engine && + !HASBITS(w->vehstatus, VS_CRASHED)) { u = GetLastVehicleInChain(w); break; } } - v = new (v) Train(); + Vehicle *v = new Train(); + v->spritenum = rvi->image_index; + v->engine_type = engine; DiagDirection dir = GetRailDepotDirection(tile); @@ -707,7 +704,7 @@ static CommandCost CmdBuildRailWagon(Eng v->group_id = DEFAULT_GROUP; - AddArticulatedParts(vl, VEH_TRAIN); + AddArticulatedParts(v, VEH_TRAIN); _new_vehicle_id = v->index; @@ -743,9 +740,11 @@ static void NormalizeTrainVehInDepot(con } } -static void AddRearEngineToMultiheadedTrain(Vehicle *v, Vehicle *u) +static void AddRearEngineToMultiheadedTrain(Vehicle *v) { - u = new (u) Train(); + Vehicle *u = new Train(); + v->value >>= 1; + u->value = v->value; u->direction = v->direction; u->owner = v->owner; u->tile = v->tile; @@ -755,20 +754,23 @@ static void AddRearEngineToMultiheadedTr u->u.rail.track = TRACK_BIT_DEPOT; u->vehstatus = v->vehstatus & ~VS_STOPPED; // u->subtype = 0; - SetMultiheaded(u); u->spritenum = v->spritenum + 1; u->cargo_type = v->cargo_type; u->cargo_subtype = v->cargo_subtype; u->cargo_cap = v->cargo_cap; u->u.rail.railtype = v->u.rail.railtype; - v->SetNext(u); u->engine_type = v->engine_type; u->build_year = v->build_year; - v->value >>= 1; - u->value = v->value; u->cur_image = 0xAC2; u->random_bits = VehicleRandomBits(); + SetMultiheaded(v); + SetMultiheaded(u); + v->SetNext(u); VehicleMove(u, false); + + /* Now we need to link the front and rear engines together */ + v->u.rail.other_multiheaded_part = u; + u->u.rail.other_multiheaded_part = v; } /** Build a railroad vehicle. @@ -806,16 +808,11 @@ CommandCost CmdBuildRailVehicle(TileInde * We need to see if the engine got power on the tile to avoid eletric engines in non-electric depots */ if (!HasPowerOnRail(rvi->railtype, GetRailType(tile))) return CMD_ERROR; - /* Allow for the dual-heads and the articulated parts, plus one to "terminate" the list. */ - Vehicle **vl = AllocaM(Vehicle*, num_vehicles + 1); - memset(vl, 0, sizeof(*vl) * (num_vehicles + 1)); - - if (!Vehicle::AllocateList(vl, num_vehicles)) { + /* Allow for the dual-heads and the articulated parts */ + if (!Vehicle::CanAllocateItem(num_vehicles)) { return_cmd_error(STR_ERROR_TOO_MANY_VEHICLES_IN_GAME); } - Vehicle *v = vl[0]; - UnitID unit_num = (flags & DC_AUTOREPLACE) ? 0 : GetFreeUnitNumber(VEH_TRAIN); if (unit_num > _settings_game.vehicle.max_trains) { return_cmd_error(STR_ERROR_TOO_MANY_VEHICLES_IN_GAME); @@ -826,7 +823,7 @@ CommandCost CmdBuildRailVehicle(TileInde int x = TileX(tile) * TILE_SIZE + _vehicle_initial_x_fract[dir]; int y = TileY(tile) * TILE_SIZE + _vehicle_initial_y_fract[dir]; - v = new (v) Train(); + Vehicle *v = new Train(); v->unitnumber = unit_num; v->direction = DiagDirToDir(dir); v->tile = tile; @@ -874,16 +871,9 @@ CommandCost CmdBuildRailVehicle(TileInde VehicleMove(v, false); if (rvi->railveh_type == RAILVEH_MULTIHEAD) { - SetMultiheaded(v); - AddRearEngineToMultiheadedTrain(vl[0], vl[1]); - /* Now we need to link the front and rear engines together - * other_multiheaded_part is the pointer that links to the other half of the engine - * vl[0] is the front and vl[1] is the rear - */ - vl[0]->u.rail.other_multiheaded_part = vl[1]; - vl[1]->u.rail.other_multiheaded_part = vl[0]; + AddRearEngineToMultiheadedTrain(v); } else { - AddArticulatedParts(vl, VEH_TRAIN); + AddArticulatedParts(v, VEH_TRAIN); } TrainConsistChanged(v, false); diff --git a/src/vehicle.cpp b/src/vehicle.cpp --- a/src/vehicle.cpp +++ b/src/vehicle.cpp @@ -206,22 +206,6 @@ byte VehicleRandomBits() return GB(Random(), 0, 8); } - -/* static */ bool Vehicle::AllocateList(Vehicle **vl, int num) -{ - if (!Vehicle::CanAllocateItem(num)) return false; - if (vl == NULL) return true; - - uint counter = _Vehicle_pool.first_free_index; - - for (int i = 0; i != num; i++) { - vl[i] = new (AllocateRaw(counter)) InvalidVehicle(); - counter++; - } - - return true; -} - /* Size of the hash, 6 = 64 x 64, 7 = 128 x 128. Larger sizes will (in theory) reduce hash * lookup times at the expense of memory usage. */ const int HASH_BITS = 7; diff --git a/src/vehicle_base.h b/src/vehicle_base.h --- a/src/vehicle_base.h +++ b/src/vehicle_base.h @@ -327,14 +327,6 @@ public: uint32 cached_var42; ///< Cache for NewGRF var 42 uint32 cached_var43; ///< Cache for NewGRF var 43 - /** - * Allocates a lot of vehicles. - * @param vl pointer to an array of vehicles to get allocated. Can be NULL if the vehicles aren't needed (makes it test only) - * @param num number of vehicles to allocate room for - * @return true if there is room to allocate all the vehicles - */ - static bool AllocateList(Vehicle **vl, int num); - /** Create a new vehicle */ Vehicle();