54 #include "table/strings.h" 
   75 static inline int32 
BigMulS(const int32 a, const int32 b, const uint8 shift)
 
   77   return (int32)((int64)a * (int64)b >> shift);
 
  101 Money _additional_cash_required;
 
  102 static PriceMultipliers _price_base_multiplier;
 
  120   FOR_ALL_STATIONS(st) {
 
  124   Money value = num * _price[PR_STATION_VALUE] * 25;
 
  128     if (v->
owner != owner) 
continue;
 
  134       value += v->
value * 3 >> 1;
 
  158   memset(_score_part[owner], 0, 
sizeof(_score_part[owner]));
 
  163     Money min_profit = 0;
 
  164     bool min_profit_first = 
true;
 
  168       if (v->
owner != owner) 
continue;
 
  175             min_profit_first = 
false;
 
  183     _score_part[owner][SCORE_VEHICLES] = num;
 
  185     if (min_profit > 0) {
 
  186       _score_part[owner][SCORE_MIN_PROFIT] = 
ClampToI32(min_profit);
 
  195     FOR_ALL_STATIONS(st) {
 
  197       if (st->
owner == owner && (st->time_since_load <= 20 || st->time_since_unload <= 20)) num += 
CountBits((byte)st->
facilities);
 
  199     _score_part[owner][SCORE_STATIONS] = num;
 
  213       } 
while (++cee, --numec);
 
  215       if (min_income > 0) {
 
  216         _score_part[owner][SCORE_MIN_INCOME] = 
ClampToI32(min_income);
 
  219       _score_part[owner][SCORE_MAX_INCOME] = 
ClampToI32(max_income);
 
  231       } 
while (++cee, --numec);
 
  233       _score_part[owner][SCORE_DELIVERED] = 
ClampToI32(total_delivered);
 
  263       s = 
Clamp(_score_part[owner][i], 0, _score_info[i].needed) * _score_info[i].
score / _score_info[i].
needed;
 
  265       total_score += _score_info[i].
score;
 
  295 #ifdef ENABLE_NETWORK 
  305     FOR_ALL_COMPANIES(c) {
 
  306       if (c->
index != old_owner) {
 
  317   assert(old_owner != new_owner);
 
  324     FOR_ALL_COMPANIES(c) {
 
  325       for (i = 0; i < 4; i++) {
 
  339     for (i = 0; i < 4; i++) {
 
  360   FOR_ALL_SUBSIDIES(s) {
 
  406           if (v->
Previous() == NULL) 
delete v;
 
  420     RemoveAllGroupsForCompany(old_owner);
 
  424       if (g->
owner == old_owner) g->
owner = new_owner;
 
  456         if (!v->ServiceIntervalIsCustom()) {
 
  466         v->
owner = new_owner;
 
  524   FOR_ALL_STATIONS(st) {
 
  525     if (st->
owner == old_owner) {
 
  535     if (wp->
owner == old_owner) {
 
  548     if (g->
company == old_owner) 
delete g;
 
  555   FOR_ALL_STORY_PAGES(sp) {
 
  556     if (sp->
company == old_owner) 
delete sp;
 
  600       SetDParam(0, STR_NEWS_COMPANY_IN_TROUBLE_TITLE);
 
  601       SetDParam(1, STR_NEWS_COMPANY_IN_TROUBLE_DESCRIPTION);
 
  603       AddCompanyNewsItem(STR_MESSAGE_NEWS_FORMAT, cni);
 
  614       c->bankrupt_value = val;
 
  619       assert(c->bankrupt_value > 0);
 
  663     FOR_ALL_STATIONS(st) {
 
  670     FOR_ALL_COMPANIES(c) {
 
  692   FOR_ALL_COMPANIES(c) {
 
  699   FOR_ALL_COMPANIES(c) {
 
  767   for (
Price i = PR_BEGIN; i < PR_END; i++) {
 
  772     switch (_price_base_specs[i].category) {
 
  784       case 0: price *= 6; 
break;
 
  785       case 1: price *= 8; 
break; 
 
  786       case 2: price *= 9; 
break;
 
  787       default: NOT_REACHED();
 
  794     int shift = _price_base_multiplier[i] - 16 - 3;
 
  807       price = 
Clamp(_price_base_specs[i].start_price, -1, 1);
 
  817   FOR_ALL_CARGOSPECS(cs) {
 
  818     cs->current_payment = ((int64)cs->initial_payment * _economy.
inflation_payment) >> 16;
 
  834   FOR_ALL_COMPANIES(c) {
 
  862 static void HandleEconomyFluctuations()
 
  869     _economy.
fluct = -12;
 
  875   if (_economy.
fluct == 0) {
 
  876     _economy.
fluct = -(int)
GB(Random(), 0, 2);
 
  878   } 
else if (_economy.
fluct == -12) {
 
  879     _economy.
fluct = 
GB(Random(), 0, 8) + 312;
 
  890   memset(_price_base_multiplier, 0, 
sizeof(_price_base_multiplier));
 
  902   assert(price < PR_END);
 
  927 void StartupEconomy()
 
  932   _economy.
fluct = 
GB(Random(), 0, 8) + 168;
 
  961   if (index >= PR_END) 
return 0;
 
  963   Money cost = _price[index] * cost_factor;
 
  975 Money GetTransportedGoodsIncome(uint num_pieces, uint dist, byte transit_days, 
CargoID cargo_type)
 
  985     uint32 var18 = 
min(dist, 0xFFFF) | (
min(num_pieces, 0xFF) << 16) | (transit_days << 24);
 
  988       int result = 
GB(callback, 0, 14);
 
  991       if (
HasBit(callback, 14)) result -= 0x4000;
 
  996       return result * num_pieces * cs->current_payment / 8192;
 
 1000   static const int MIN_TIME_FACTOR = 31;
 
 1001   static const int MAX_TIME_FACTOR = 255;
 
 1003   const int days1 = cs->transit_days[0];
 
 1004   const int days2 = cs->transit_days[1];
 
 1005   const int days_over_days1 = 
max(   transit_days - days1, 0);
 
 1006   const int days_over_days2 = 
max(days_over_days1 - days2, 0);
 
 1018   const int time_factor = 
max(MAX_TIME_FACTOR - days_over_days1 - days_over_days2, MIN_TIME_FACTOR);
 
 1020   return BigMulS(dist * time_factor * num_pieces, cs->current_payment, 21);
 
 1048     if (ind->
index == source) 
continue;
 
 1061     _cargo_delivery_destinations.
Include(ind);
 
 1065     num_pieces -= amount;
 
 1087   assert(num_pieces > 0);
 
 1112   Money profit = GetTransportedGoodsIncome(accepted, 
DistanceManhattan(source_tile, st->
xy), days_in_transit, cargo_type);
 
 1120       case 0:  profit += profit >> 1; 
break;
 
 1121       case 1:  profit *= 2; 
break;
 
 1122       case 2:  profit *= 3; 
break;
 
 1123       default: profit *= 4; 
break;
 
 1152       if (cargo_waiting == 0) 
continue;
 
 1171   current_station(front->last_station_visited)
 
 1175 CargoPayment::~CargoPayment()
 
 1189     SndPlayVehicleFx(SND_14_CASHTILL, this->
front);
 
 1194         this->front->z_pos, this->visual_transfer, -this->visual_profit);
 
 1197         this->front->z_pos, -this->visual_profit);
 
 1200   cur_company.Restore();
 
 1210   if (this->
owner == NULL) {
 
 1230   Money profit = GetTransportedGoodsIncome(
 
 1251   curr_station->loading_vehicles.push_back(front_v);
 
 1269     for (
Vehicle *v = front_v; v != NULL; v = v->
Next()) {
 
 1271       if (v->cargo_cap > 0 && v->cargo.TotalCount() > 0) {
 
 1292   uint load_amount = e->info.load_amount;
 
 1296   if (air_mail) load_amount = 
CeilDiv(load_amount, 4);
 
 1300     if (e->
GetGRF() != NULL && e->
GetGRF()->grf_version >= 8) {
 
 1308       if (e->
GetGRF()->grf_version < 8) cb_load_amount = 
GB(cb_load_amount, 0, 8);
 
 1309       if (cb_load_amount >= 0x100) {
 
 1311       } 
else if (cb_load_amount != 0) {
 
 1312         load_amount = cb_load_amount;
 
 1321   return max(1u, load_amount);
 
 1333 template<
class Taction>
 
 1336   for (
Vehicle *w = v; w != NULL;
 
 1338     if (!action(w)) 
return false;
 
 1341       if (train->
IsMultiheaded() && !action(train->other_multiheaded_part)) 
return false;
 
 1378     consist_capleft(consist_capleft), refit_mask(refit_mask) {}
 
 1439     consist_capleft(consist_capleft), st(st), next_station(next_station), do_reserve(do_reserve) {}
 
 1473   uint32 refit_mask = v->
GetEngine()->info.refit_mask;
 
 1479   if (is_auto_refit) {
 
 1483     FOR_EACH_SET_CARGO_ID(cid, refit_mask) {
 
 1495             (consist_capleft[cid] == consist_capleft[new_cid] &&
 
 1504   if (new_cid < NUM_CARGO && new_cid != v_start->cargo_type) {
 
 1526     st(st), next_station(next_station) {}
 
 1532           &v->
cargo, st->
xy, *next_station);
 
 1555     assert(v->cargo_cap >= v->cargo.RemainingCount());
 
 1560     if (!v->IsArticulatedPart() &&
 
 1566     if (consist_capleft == NULL || v->cargo_cap == 0) 
continue;
 
 1567     (*consist_capleft)[v->cargo_type] += v->cargo_cap - v->cargo.RemainingCount();
 
 1585       ticks += (overhang * ticks) / 8;
 
 1624   int new_load_unload_ticks = 0;
 
 1625   bool dirty_vehicle = 
false;
 
 1626   bool dirty_station = 
false;
 
 1628   bool completely_emptied = 
true;
 
 1629   bool anything_unloaded  = 
false;
 
 1630   bool anything_loaded    = 
false;
 
 1631   uint32 full_load_amount = 0;
 
 1632   uint32 cargo_not_full   = 0;
 
 1633   uint32 cargo_full       = 0;
 
 1634   uint32 reservation_left = 0;
 
 1640   uint artic_part = 0; 
 
 1641   for (
Vehicle *v = front; v != NULL; v = v->
Next()) {
 
 1643     if (v->cargo_cap == 0) 
continue;
 
 1651       uint cargo_count = v->
cargo.UnloadCount();
 
 1653       bool remaining = 
false; 
 
 1655       assert(payment != NULL);
 
 1666           if (v->cargo_cap < new_remaining) {
 
 1668             v->cargo.Return(new_remaining - v->cargo_cap, &ge->
cargo, INVALID_STATION);
 
 1679           anything_unloaded = 
true;
 
 1685         dirty_station = 
true;
 
 1695       amount_unloaded = v->cargo.Unload(amount_unloaded, &ge->
cargo, payment);
 
 1696       remaining = v->cargo.UnloadCount() > 0;
 
 1697       if (amount_unloaded > 0) {
 
 1698         dirty_vehicle = 
true;
 
 1699         anything_unloaded = 
true;
 
 1700         new_load_unload_ticks += amount_unloaded;
 
 1703         st->time_since_unload = 0;
 
 1707         completely_emptied = 
false;
 
 1722       ge = &st->
goods[v->cargo_type];
 
 1726     v->refit_cap = v->cargo_cap;
 
 1730     switch (front->
type) {
 
 1744       default: NOT_REACHED();
 
 1752     assert(v->cargo_cap >= v->cargo.StoredCount());
 
 1755     uint cap_left = v->cargo_cap - v->cargo.StoredCount();
 
 1758       if (v->cargo.StoredCount() == 0) TriggerVehicle(v, VEHICLE_TRIGGER_NEW_CARGO);
 
 1760       uint loaded = ge->
cargo.
Load(cap_left, &v->cargo, st->
xy, next_station);
 
 1764         SetBit(reservation_left, v->cargo_type);
 
 1768       if (loaded == cap_left) {
 
 1769         SetBit(full_load_amount, v->cargo_type);
 
 1771         ClrBit(full_load_amount, v->cargo_type);
 
 1782         completely_emptied = 
false;
 
 1783         anything_loaded = 
true;
 
 1785         st->time_since_load = 0;
 
 1786         st->last_vehicle_type = v->type;
 
 1794         new_load_unload_ticks += loaded;
 
 1796         dirty_vehicle = dirty_station = 
true;
 
 1800     if (v->cargo.StoredCount() >= v->cargo_cap) {
 
 1801       SetBit(cargo_full, v->cargo_type);
 
 1803       SetBit(cargo_not_full, v->cargo_type);
 
 1807   if (anything_loaded || anything_unloaded) {
 
 1815   completely_emptied &= anything_unloaded;
 
 1817   if (!anything_unloaded) 
delete payment;
 
 1820   if (anything_loaded || anything_unloaded) {
 
 1824       const uint gradual_loading_wait_time[] = { 40, 20, 10, 20 };
 
 1826       new_load_unload_ticks = gradual_loading_wait_time[front->
type];
 
 1838     bool finished_loading = 
true;
 
 1844             (cargo_not_full && (cargo_full & ~cargo_not_full) == 0)) { 
 
 1845           finished_loading = 
false;
 
 1847       } 
else if (cargo_not_full != 0) {
 
 1848         finished_loading = 
false;
 
 1869     StringID percent_up_down = STR_NULL;
 
 1878   if (completely_emptied) {
 
 1881     dirty_vehicle = 
true;
 
 1882     TriggerVehicle(front, VEHICLE_TRIGGER_EMPTY);
 
 1885   if (dirty_vehicle) {
 
 1890   if (dirty_station) {
 
 1905   if (st->loading_vehicles.empty()) 
return;
 
 1908   std::list<Vehicle *>::iterator iter;
 
 1911   for (iter = st->loading_vehicles.begin(); iter != st->loading_vehicles.end(); ++iter) {
 
 1927   if (last_loading == NULL) 
return;
 
 1929   for (iter = st->loading_vehicles.begin(); iter != st->loading_vehicles.end(); ++iter) {
 
 1932     if (v == last_loading) 
break;
 
 1936   const Industry * 
const *isend = _cargo_delivery_destinations.
End();
 
 1937   for (
Industry **iid = _cargo_delivery_destinations.
Begin(); iid != isend; iid++) {
 
 1940   _cargo_delivery_destinations.
Clear();
 
 1954   HandleEconomyFluctuations();
 
 1957 static void DoAcquireCompany(
Company *c)
 
 1964   SetDParam(0, STR_NEWS_COMPANY_MERGER_TITLE);
 
 1965   SetDParam(1, c->bankrupt_value == 0 ? STR_NEWS_MERGER_TAKEOVER_TITLE : STR_NEWS_COMPANY_MERGER_DESCRIPTION);
 
 1969   AddCompanyNewsItem(STR_MESSAGE_NEWS_FORMAT, cni);
 
 1975   if (c->bankrupt_value == 0) {
 
 1991 extern int GetAmountOwnedBy(
const Company *c, 
Owner owner);
 
 2019     if (!c->
is_ai) 
return cost; 
 
 2034         c->bankrupt_value = 0;
 
 2035         DoAcquireCompany(c);
 
 2071   cost = -(cost - (cost >> 7));
 
 2117     DoAcquireCompany(c);