mirror of https://github.com/OpenRCT2/OpenRCT2.git
Merge pull request #5557 from IntelOrca/feature/server-logging
Add logging for user actions in multiplayer
This commit is contained in:
commit
d3fc1d9e1e
|
@ -4373,6 +4373,42 @@ STR_6061 :{SMALLFONT}{BLACK}Show animated money effect{NEWLINE}when guests ma
|
|||
STR_6062 :{OUTLINE}{GREEN}+ {CURRENCY2DP}
|
||||
STR_6063 :{OUTLINE}{RED}- {CURRENCY2DP}
|
||||
STR_6064 :Own all land
|
||||
STR_6065 :Log user actions
|
||||
STR_6066 :{SMALLFONT}{BLACK}Logs all user actions to files in your user directory.
|
||||
STR_6067 :Server started.
|
||||
STR_6068 :Server shutdown.
|
||||
STR_6069 :{STRING} was kicked from the server by {STRING}.
|
||||
STR_6070 :{STRING} was set to group '{STRING}' by {STRING}.
|
||||
STR_6071 :{STRING} created new player group '{STRING}'.
|
||||
STR_6072 :{STRING} deleted player group '{String}'.
|
||||
STR_6073 :{STRING} edited permissions for player group '{String}'.
|
||||
STR_6074 :{STRING} changed player group name from '{String}' to '{String}'.
|
||||
STR_6075 :{STRING} changed the default player group to '{String}'.
|
||||
STR_6076 :{STRING} used/toggled cheat '{STRING}'.
|
||||
STR_6077 :Add Money
|
||||
STR_6078 :{STRING} created ride '{STRING}'.
|
||||
STR_6079 :{STRING} demolished ride '{STRING}'.
|
||||
STR_6080 :{STRING} changed the appearance of ride '{STRING}'.
|
||||
STR_6081 :{STRING} changed the status of ride '{STRING}' to closed.
|
||||
STR_6082 :{STRING} changed the status of ride '{STRING}' to open.
|
||||
STR_6083 :{STRING} changed the status of ride '{STRING}' to testing.
|
||||
STR_6084 :{STRING} changed the vehicle settings of ride '{STRING}'.
|
||||
STR_6085 :{STRING} changed the ride settings of ride '{STRING}'.
|
||||
STR_6086 :{STRING} renamed the ride '{STRING}' to '{STRING}'.
|
||||
STR_6087 :{STRING} changed the price of ride '{STRING}' to {STRING}
|
||||
STR_6088 :{STRING} changed the secondary price of ride '{STRING}' to {STRING}
|
||||
STR_6089 :{STRING} renamed the park from '{STRING}' to '{STRING}'.
|
||||
STR_6090 :{STRING} opened the park.
|
||||
STR_6091 :{STRING} closed the park.
|
||||
STR_6092 :{STRING} changed the park entrance fee to {STRING}
|
||||
STR_6093 :{STRING} placed new scenery.
|
||||
STR_6094 :{STRING} removed scenery.
|
||||
STR_6095 :{STRING} edited scenery.
|
||||
STR_6096 :{STRING} set sign name to '{STRING}'.
|
||||
STR_6097 :{STRING} placed a track of ride '{STRING}'.
|
||||
STR_6098 :{STRING} removed a track of ride.
|
||||
STR_6099 :You connected to the server.
|
||||
STR_6100 :You disconnected from the server.
|
||||
|
||||
#############
|
||||
# Scenarios #
|
||||
|
|
|
@ -49,6 +49,7 @@ extern "C"
|
|||
#include "intro.h"
|
||||
#include "localisation/localisation.h"
|
||||
#include "network/http.h"
|
||||
#include "network/network.h"
|
||||
#include "object_list.h"
|
||||
#include "rct1.h"
|
||||
#include "rct2.h"
|
||||
|
@ -218,6 +219,7 @@ namespace OpenRCT2
|
|||
}
|
||||
|
||||
http_init();
|
||||
network_set_env(_env);
|
||||
theme_manager_initialise();
|
||||
|
||||
rct2_interop_setup_hooks();
|
||||
|
|
|
@ -19,13 +19,14 @@
|
|||
#include "editor.h"
|
||||
#include "game.h"
|
||||
#include "interface/window.h"
|
||||
#include "localisation/date.h"
|
||||
#include "localisation/localisation.h"
|
||||
#include "management/finance.h"
|
||||
#include "network/network.h"
|
||||
#include "util/util.h"
|
||||
#include "world/Climate.h"
|
||||
#include "world/footpath.h"
|
||||
#include "world/map.h"
|
||||
#include "world/park.h"
|
||||
#include "world/scenery.h"
|
||||
#include "world/sprite.h"
|
||||
|
||||
|
@ -569,3 +570,209 @@ void cheats_reset()
|
|||
gCheatsDisablePlantAging = false;
|
||||
gCheatsAllowArbitraryRideTypeChanges = false;
|
||||
}
|
||||
|
||||
//Generates the string to print for the server log when a cheat is used.
|
||||
const char* cheats_get_cheat_string(int cheat, int edx, int edi) {
|
||||
switch (cheat) {
|
||||
case CHEAT_SANDBOXMODE:
|
||||
if (gCheatsSandboxMode) {
|
||||
return language_get_string(STR_CHEAT_SANDBOX_MODE_DISABLE);
|
||||
} else {
|
||||
return language_get_string(STR_CHEAT_SANDBOX_MODE);
|
||||
}
|
||||
case CHEAT_DISABLECLEARANCECHECKS: return language_get_string(STR_DISABLE_CLEARANCE_CHECKS);
|
||||
case CHEAT_DISABLESUPPORTLIMITS: return language_get_string(STR_DISABLE_SUPPORT_LIMITS);
|
||||
case CHEAT_SHOWALLOPERATINGMODES: return language_get_string(STR_CHEAT_SHOW_ALL_OPERATING_MODES);
|
||||
case CHEAT_SHOWVEHICLESFROMOTHERTRACKTYPES: return language_get_string(STR_CHEAT_SHOW_VEHICLES_FROM_OTHER_TRACK_TYPES);
|
||||
case CHEAT_FASTLIFTHILL: return language_get_string(STR_CHEAT_UNLOCK_OPERATING_LIMITS);
|
||||
case CHEAT_DISABLEBRAKESFAILURE: return language_get_string(STR_CHEAT_DISABLE_BRAKES_FAILURE);
|
||||
case CHEAT_DISABLEALLBREAKDOWNS: return language_get_string(STR_CHEAT_DISABLE_BREAKDOWNS);
|
||||
case CHEAT_DISABLETRAINLENGTHLIMIT: return language_get_string(STR_CHEAT_DISABLE_TRAIN_LENGTH_LIMIT);
|
||||
case CHEAT_ENABLECHAINLIFTONALLTRACK: return language_get_string(STR_CHEAT_ENABLE_CHAIN_LIFT_ON_ALL_TRACK);
|
||||
case CHEAT_UNLOCKALLPRICES: return language_get_string(STR_CHEAT_UNLOCK_PRICES);
|
||||
case CHEAT_BUILDINPAUSEMODE: return language_get_string(STR_CHEAT_BUILD_IN_PAUSE_MODE);
|
||||
case CHEAT_IGNORERIDEINTENSITY: return language_get_string(STR_CHEAT_IGNORE_INTENSITY);
|
||||
case CHEAT_DISABLEVANDALISM: return language_get_string(STR_CHEAT_DISABLE_VANDALISM);
|
||||
case CHEAT_DISABLELITTERING: return language_get_string(STR_CHEAT_DISABLE_LITTERING);
|
||||
case CHEAT_ADDMONEY: return language_get_string(STR_LOG_CHEAT_ADD_MONEY);
|
||||
case CHEAT_CLEARLOAN: return language_get_string(STR_CHEAT_CLEAR_LOAN);
|
||||
case CHEAT_SETGUESTPARAMETER:
|
||||
{
|
||||
static char cheat_string[128];
|
||||
safe_strcpy(cheat_string, language_get_string(STR_CHEAT_SET_GUESTS_PARAMETERS), 128);
|
||||
safe_strcat(cheat_string, " ", 128);
|
||||
switch (edx) {
|
||||
case GUEST_PARAMETER_HAPPINESS:
|
||||
safe_strcat(cheat_string, language_get_string(STR_CHEAT_GUEST_HAPPINESS), 128);
|
||||
safe_strcat(cheat_string, " ", 128);
|
||||
if (edi == 255) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MAX), 128);
|
||||
} else if (edi == 0) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MIN), 128);
|
||||
}
|
||||
break;
|
||||
case GUEST_PARAMETER_ENERGY:
|
||||
safe_strcat(cheat_string, language_get_string(STR_CHEAT_GUEST_ENERGY), 128);
|
||||
safe_strcat(cheat_string, " ", 128);
|
||||
if (edi == 127) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MAX), 128);
|
||||
} else if (edi == 0) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MIN), 128);
|
||||
}
|
||||
break;
|
||||
case GUEST_PARAMETER_HUNGER:
|
||||
safe_strcat(cheat_string, language_get_string(STR_CHEAT_GUEST_HUNGER), 128);
|
||||
safe_strcat(cheat_string, " ", 128);
|
||||
if (edi == 255) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MIN), 128);
|
||||
} else if (edi == 0) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MAX), 128);
|
||||
}
|
||||
break;
|
||||
case GUEST_PARAMETER_THIRST:
|
||||
safe_strcat(cheat_string, language_get_string(STR_CHEAT_GUEST_THIRST), 128);
|
||||
safe_strcat(cheat_string, " ", 128);
|
||||
if (edi == 255) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MIN), 128);
|
||||
} else if (edi == 0) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MAX), 128);
|
||||
}
|
||||
break;
|
||||
case GUEST_PARAMETER_NAUSEA:
|
||||
safe_strcat(cheat_string, language_get_string(STR_CHEAT_GUEST_NAUSEA), 128);
|
||||
safe_strcat(cheat_string, " ", 128);
|
||||
if (edi == 255) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MAX), 128);
|
||||
} else if (edi == 0) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MIN), 128);
|
||||
}
|
||||
break;
|
||||
case GUEST_PARAMETER_NAUSEA_TOLERANCE:
|
||||
safe_strcat(cheat_string, language_get_string(STR_CHEAT_GUEST_NAUSEA_TOLERANCE), 128);
|
||||
safe_strcat(cheat_string, " ", 128);
|
||||
if (edi == PEEP_NAUSEA_TOLERANCE_HIGH) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MAX), 128);
|
||||
} else if (edi == PEEP_NAUSEA_TOLERANCE_NONE) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MIN), 128);
|
||||
}
|
||||
break;
|
||||
case GUEST_PARAMETER_BATHROOM:
|
||||
safe_strcat(cheat_string, language_get_string(STR_CHEAT_GUEST_BATHROOM), 128);
|
||||
safe_strcat(cheat_string, " ", 128);
|
||||
if (edi == 255) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MAX), 128);
|
||||
} else if (edi == 0) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_MIN), 128);
|
||||
}
|
||||
break;
|
||||
case GUEST_PARAMETER_PREFERRED_RIDE_INTENSITY:
|
||||
safe_strcat(cheat_string, language_get_string(STR_CHEAT_GUEST_PREFERRED_INTENSITY), 128);
|
||||
safe_strcat(cheat_string, " ", 128);
|
||||
if (edi == 1) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_CHEAT_MORE_THAN_1), 128);
|
||||
} else if (edi == 0) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_CHEAT_LESS_THAN_15), 128);
|
||||
}
|
||||
break;
|
||||
}
|
||||
return cheat_string;
|
||||
}
|
||||
case CHEAT_GENERATEGUESTS: return language_get_string(STR_CHEAT_LARGE_TRAM_GUESTS);
|
||||
case CHEAT_REMOVEALLGUESTS: return language_get_string(STR_CHEAT_REMOVE_ALL_GUESTS);
|
||||
case CHEAT_EXPLODEGUESTS: return language_get_string(STR_CHEAT_EXPLODE);
|
||||
case CHEAT_GIVEALLGUESTS:
|
||||
{
|
||||
static char cheat_string[64];
|
||||
safe_strcpy(cheat_string, language_get_string(STR_CHEAT_GIVE_ALL_GUESTS), 64);
|
||||
safe_strcat(cheat_string, " ", 64);
|
||||
switch (edx) {
|
||||
case OBJECT_MONEY:
|
||||
{
|
||||
char money[16];
|
||||
set_format_arg(0, money32, CHEATS_GIVE_GUESTS_MONEY);
|
||||
format_string(money, 16, STR_CHEAT_CURRENCY_FORMAT, gCommonFormatArgs);
|
||||
safe_strcat(cheat_string, money, 64);
|
||||
break;
|
||||
}
|
||||
case OBJECT_PARK_MAP: safe_strcat(cheat_string, language_get_string(STR_SHOP_ITEM_PLURAL_PARK_MAP), 64); break;
|
||||
case OBJECT_BALLOON: safe_strcat(cheat_string, language_get_string(STR_SHOP_ITEM_PLURAL_BALLOON), 64); break;
|
||||
case OBJECT_UMBRELLA: safe_strcat(cheat_string, language_get_string(STR_SHOP_ITEM_PLURAL_UMBRELLA), 64); break;
|
||||
}
|
||||
return cheat_string;
|
||||
}
|
||||
case CHEAT_SETGRASSLENGTH:
|
||||
if (edx == 0) {
|
||||
return language_get_string(STR_CHEAT_MOWED_GRASS);
|
||||
} else if (edx == 1) {
|
||||
return language_get_string(STR_CHEAT_CLEAR_GRASS);
|
||||
}
|
||||
case CHEAT_WATERPLANTS: return language_get_string(STR_CHEAT_WATER_PLANTS);
|
||||
case CHEAT_FIXVANDALISM: return language_get_string(STR_CHEAT_FIX_VANDALISM);
|
||||
case CHEAT_REMOVELITTER: return language_get_string(STR_CHEAT_REMOVE_LITTER);
|
||||
case CHEAT_DISABLEPLANTAGING: return language_get_string(STR_CHEAT_DISABLE_PLANT_AGING);
|
||||
case CHEAT_SETSTAFFSPEED:
|
||||
{
|
||||
static char cheat_string[64];
|
||||
safe_strcpy(cheat_string, language_get_string(STR_CHEAT_STAFF_SPEED), 64);
|
||||
safe_strcat(cheat_string, " ", 64);
|
||||
if (edx == CHEATS_STAFF_FAST_SPEED) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_FAST), 64);
|
||||
} else if (edx == CHEATS_STAFF_NORMAL_SPEED) {
|
||||
safe_strcat(cheat_string, language_get_string(STR_NORMAL), 64);
|
||||
}
|
||||
return cheat_string;
|
||||
}
|
||||
case CHEAT_RENEWRIDES: return language_get_string(STR_CHEAT_RENEW_RIDES);
|
||||
case CHEAT_MAKEDESTRUCTIBLE: return language_get_string(STR_CHEAT_MAKE_DESTRUCTABLE);
|
||||
case CHEAT_FIXRIDES: return language_get_string(STR_CHEAT_FIX_ALL_RIDES);
|
||||
case CHEAT_RESETCRASHSTATUS: return language_get_string(STR_CHEAT_RESET_CRASH_STATUS);
|
||||
case CHEAT_10MINUTEINSPECTIONS: return language_get_string(STR_CHEAT_10_MINUTE_INSPECTIONS);
|
||||
case CHEAT_WINSCENARIO: return language_get_string(STR_CHEAT_WIN_SCENARIO);
|
||||
case CHEAT_FORCEWEATHER:
|
||||
{
|
||||
static char cheat_string[64];
|
||||
safe_strcpy(cheat_string, language_get_string(STR_FORCE_WEATHER), 64);
|
||||
safe_strcat(cheat_string, " ", 64);
|
||||
switch (edx) {
|
||||
case 0: safe_strcat(cheat_string, language_get_string(STR_SUNNY), 64); break;
|
||||
case 1: safe_strcat(cheat_string, language_get_string(STR_PARTIALLY_CLOUDY), 64); break;
|
||||
case 2: safe_strcat(cheat_string, language_get_string(STR_CLOUDY), 64); break;
|
||||
case 3: safe_strcat(cheat_string, language_get_string(STR_RAIN), 64); break;
|
||||
case 4: safe_strcat(cheat_string, language_get_string(STR_HEAVY_RAIN), 64); break;
|
||||
case 5: safe_strcat(cheat_string, language_get_string(STR_THUNDERSTORM), 64); break;
|
||||
}
|
||||
return cheat_string;
|
||||
}
|
||||
case CHEAT_FREEZECLIMATE:
|
||||
if (gCheatsFreezeClimate) {
|
||||
return language_get_string(STR_CHEAT_UNFREEZE_CLIMATE);
|
||||
} else {
|
||||
return language_get_string(STR_CHEAT_FREEZE_CLIMATE);
|
||||
}
|
||||
case CHEAT_NEVERENDINGMARKETING: return language_get_string(STR_CHEAT_NEVERENDING_MARKETING);
|
||||
case CHEAT_OPENCLOSEPARK:
|
||||
if (park_is_open()) {
|
||||
return language_get_string(STR_CHEAT_CLOSE_PARK);
|
||||
} else {
|
||||
return language_get_string(STR_CHEAT_OPEN_PARK);
|
||||
}
|
||||
case CHEAT_HAVEFUN: return language_get_string(STR_CHEAT_HAVE_FUN);
|
||||
case CHEAT_SETFORCEDPARKRATING:
|
||||
{
|
||||
static char cheat_string[64];
|
||||
safe_strcpy(cheat_string, language_get_string(STR_FORCE_PARK_RATING), 64);
|
||||
safe_strcat(cheat_string, " ", 64);
|
||||
|
||||
char buffer[8];
|
||||
snprintf(buffer, sizeof(buffer), "%d", park_rating_spinner_value);
|
||||
char* park_rating = buffer;
|
||||
safe_strcat(cheat_string, park_rating, 64);
|
||||
|
||||
return cheat_string;
|
||||
}
|
||||
case CHEAT_RESETDATE: return language_get_string(STR_CHEAT_RESET_DATE);
|
||||
case CHEAT_ALLOW_ARBITRARY_RIDE_TYPE_CHANGES: return language_get_string(STR_CHEAT_ALLOW_ARBITRARY_RIDE_TYPE_CHANGES);
|
||||
}
|
||||
|
||||
return "";
|
||||
}
|
||||
|
|
|
@ -107,7 +107,10 @@ enum {
|
|||
};
|
||||
|
||||
#define CHEATS_MONEY_INCREMENT MONEY(5000,00)
|
||||
#define CHEATS_GIVE_GUESTS_MONEY MONEY(1000,00)
|
||||
#define CHEATS_TRAM_INCREMENT 250
|
||||
#define CHEATS_STAFF_FAST_SPEED 0xFF
|
||||
#define CHEATS_STAFF_NORMAL_SPEED 0x60
|
||||
|
||||
extern sint32 park_rating_spinner_value;
|
||||
|
||||
|
@ -115,4 +118,6 @@ void game_command_cheat(sint32* eax, sint32* ebx, sint32* ecx, sint32* edx, sint
|
|||
|
||||
void cheats_reset();
|
||||
|
||||
const char* cheats_get_cheat_string(int cheat, int edx, int edi);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -359,6 +359,7 @@ namespace Config
|
|||
model->provider_website = reader->GetCString("provider_website", nullptr);
|
||||
model->known_keys_only = reader->GetBoolean("known_keys_only", false);
|
||||
model->log_chat = reader->GetBoolean("log_chat", false);
|
||||
model->log_server_actions = reader->GetBoolean("log_server_actions", false);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -382,6 +383,7 @@ namespace Config
|
|||
writer->WriteString("provider_website", model->provider_website);
|
||||
writer->WriteBoolean("known_keys_only", model->known_keys_only);
|
||||
writer->WriteBoolean("log_chat", model->log_chat);
|
||||
writer->WriteBoolean("log_server_actions", model->log_server_actions);
|
||||
}
|
||||
|
||||
static void ReadNotifications(IIniReader * reader)
|
||||
|
|
|
@ -152,6 +152,7 @@ typedef struct NetworkConfiguration
|
|||
utf8 * provider_website;
|
||||
bool known_keys_only;
|
||||
bool log_chat;
|
||||
bool log_server_actions;
|
||||
} NetworkConfiguration;
|
||||
|
||||
typedef struct NotificationConfiguration
|
||||
|
|
|
@ -512,6 +512,13 @@ sint32 game_do_command_p(sint32 command, sint32 *eax, sint32 *ebx, sint32 *ecx,
|
|||
game_command_playerid = network_get_current_player_id();
|
||||
}
|
||||
|
||||
// Log certain commands if we are in multiplayer and logging is enabled
|
||||
bool serverLog = (network_get_mode() == NETWORK_MODE_SERVER) && gGameCommandNestLevel == 1 && gConfigNetwork.log_server_actions;
|
||||
bool clientLog = (network_get_mode() == NETWORK_MODE_CLIENT) && (flags & GAME_COMMAND_FLAG_NETWORKED) && gGameCommandNestLevel == 1 && gConfigNetwork.log_server_actions;
|
||||
if (serverLog || clientLog) {
|
||||
game_log_multiplayer_command(command, eax, ebx, ecx, edx, edi, ebp);
|
||||
}
|
||||
|
||||
*ebx &= ~GAME_COMMAND_FLAG_APPLY;
|
||||
|
||||
// First call for validity and price check
|
||||
|
@ -611,6 +618,228 @@ sint32 game_do_command_p(sint32 command, sint32 *eax, sint32 *ebx, sint32 *ecx,
|
|||
return MONEY32_UNDEFINED;
|
||||
}
|
||||
|
||||
void game_log_multiplayer_command(int command, int *eax, int* ebx, int* ecx, int* edx, int* edi, int* ebp)
|
||||
{
|
||||
// Get player name
|
||||
int player_index = network_get_player_index(game_command_playerid);
|
||||
const char* player_name = network_get_player_name(player_index);
|
||||
|
||||
char log_msg[256];
|
||||
if (command == GAME_COMMAND_CHEAT) {
|
||||
// Get cheat name
|
||||
const char* cheat = cheats_get_cheat_string(*ecx, *edx, *edi);
|
||||
char* args[2] = {
|
||||
(char *)player_name,
|
||||
(char *)cheat
|
||||
};
|
||||
format_string(log_msg, 256, STR_LOG_CHEAT_USED, args);
|
||||
network_append_server_log(log_msg);
|
||||
} else if (command == GAME_COMMAND_CREATE_RIDE && *ebp == 1) { // ebp is 1 if the command comes from ride_create method in ride.c, other calls send ride_entry instead of ride and wont work
|
||||
// Get ride name
|
||||
rct_ride* ride = get_ride(*edx);
|
||||
char ride_name[128];
|
||||
format_string(ride_name, 128, ride->name, &ride->name_arguments);
|
||||
|
||||
char* args[2] = {
|
||||
(char *)player_name,
|
||||
ride_name
|
||||
};
|
||||
|
||||
format_string(log_msg, 256, STR_LOG_CREATE_RIDE, args);
|
||||
network_append_server_log(log_msg);
|
||||
} else if (command == GAME_COMMAND_DEMOLISH_RIDE && (*ebp == 1 || *ebp == 0)) { // ebp is 1 if command comes from ride window prompt, so we don't log "demolishing" ride previews
|
||||
// Get ride name
|
||||
rct_ride* ride = get_ride(*edx);
|
||||
char ride_name[128];
|
||||
format_string(ride_name, 128, ride->name, &ride->name_arguments);
|
||||
|
||||
char* args[2] = {
|
||||
(char *) player_name,
|
||||
ride_name
|
||||
};
|
||||
|
||||
format_string(log_msg, 256, STR_LOG_DEMOLISH_RIDE, args);
|
||||
network_append_server_log(log_msg);
|
||||
} else if (command == GAME_COMMAND_SET_RIDE_APPEARANCE || command == GAME_COMMAND_SET_RIDE_VEHICLES || command == GAME_COMMAND_SET_RIDE_SETTING) {
|
||||
// Get ride name
|
||||
int ride_index = *edx & 0xFF;
|
||||
rct_ride* ride = get_ride(ride_index);
|
||||
char ride_name[128];
|
||||
format_string(ride_name, 128, ride->name, &ride->name_arguments);
|
||||
|
||||
char* args[2] = {
|
||||
(char *) player_name,
|
||||
ride_name
|
||||
};
|
||||
|
||||
switch (command) {
|
||||
case GAME_COMMAND_SET_RIDE_APPEARANCE: format_string(log_msg, 256, STR_LOG_RIDE_APPEARANCE, args); break;
|
||||
case GAME_COMMAND_SET_RIDE_VEHICLES: format_string(log_msg, 256, STR_LOG_RIDE_VEHICLES, args); break;
|
||||
case GAME_COMMAND_SET_RIDE_SETTING: format_string(log_msg, 256, STR_LOG_RIDE_SETTINGS, args); break;
|
||||
}
|
||||
|
||||
network_append_server_log(log_msg);
|
||||
} else if (command == GAME_COMMAND_SET_RIDE_STATUS) {
|
||||
// Get ride name
|
||||
int ride_index = *edx & 0xFF;
|
||||
rct_ride* ride = get_ride(ride_index);
|
||||
char ride_name[128];
|
||||
format_string(ride_name, 128, ride->name, &ride->name_arguments);
|
||||
|
||||
char* args[2] = {
|
||||
(char *) player_name,
|
||||
ride_name
|
||||
};
|
||||
|
||||
int status = *edx >> 8;
|
||||
switch (status) {
|
||||
case 0: format_string(log_msg, 256, STR_LOG_RIDE_STATUS_CLOSED, args); break;
|
||||
case 1: format_string(log_msg, 256, STR_LOG_RIDE_STATUS_OPEN, args); break;
|
||||
case 2: format_string(log_msg, 256, STR_LOG_RIDE_STATUS_TESTING, args); break;
|
||||
}
|
||||
|
||||
network_append_server_log(log_msg);
|
||||
} else if (command == GAME_COMMAND_SET_RIDE_PRICE) {
|
||||
// Get ride name
|
||||
int ride_index = *edx & 0xFF;
|
||||
rct_ride* ride = get_ride(ride_index);
|
||||
char ride_name[128];
|
||||
format_string(ride_name, 128, ride->name, &ride->name_arguments);
|
||||
|
||||
// Format price
|
||||
int price_args[1] = {*edi};
|
||||
char price_str[16];
|
||||
format_string(price_str, 16, STR_BOTTOM_TOOLBAR_CASH, price_args);
|
||||
|
||||
// Log change in primary or secondary price
|
||||
char* args[3] = {
|
||||
(char *) player_name,
|
||||
ride_name,
|
||||
price_str
|
||||
};
|
||||
|
||||
if (*edx >> 8 == 0) {
|
||||
format_string(log_msg, 256, STR_LOG_RIDE_PRICE, args);
|
||||
} else if (*edx >> 8 == 1) {
|
||||
format_string(log_msg, 256, STR_LOG_RIDE_SECONDARY_PRICE, args);
|
||||
}
|
||||
|
||||
network_append_server_log(log_msg);
|
||||
} else if (command == GAME_COMMAND_SET_PARK_OPEN) {
|
||||
// Log change in park open/close
|
||||
char* args[1] = {
|
||||
(char *) player_name
|
||||
};
|
||||
|
||||
if (*edx >> 8 == 0) {
|
||||
format_string(log_msg, 256, STR_LOG_PARK_OPEN, args);
|
||||
} else if (*edx >> 8 == 1) {
|
||||
format_string(log_msg, 256, STR_LOG_PARK_CLOSED, args);
|
||||
}
|
||||
|
||||
network_append_server_log(log_msg);
|
||||
} else if (command == GAME_COMMAND_SET_PARK_ENTRANCE_FEE) {
|
||||
// Format price
|
||||
int price_args[1] = {*edi};
|
||||
char price_str[16];
|
||||
format_string(price_str, 16, STR_BOTTOM_TOOLBAR_CASH, price_args);
|
||||
|
||||
// Log change in park entrance fee
|
||||
char* args[2] = {
|
||||
(char *) player_name,
|
||||
price_str
|
||||
};
|
||||
|
||||
format_string(log_msg, 256, STR_LOG_PARK_ENTRANCE_FEE, args);
|
||||
network_append_server_log(log_msg);
|
||||
} else if (command == GAME_COMMAND_PLACE_SCENERY || command == GAME_COMMAND_PLACE_WALL ||
|
||||
command == GAME_COMMAND_PLACE_LARGE_SCENERY || command == GAME_COMMAND_PLACE_BANNER) {
|
||||
uint8 flags = *ebx & 0xFF;
|
||||
if (flags & GAME_COMMAND_FLAG_GHOST) {
|
||||
// Don't log ghost previews being removed
|
||||
return;
|
||||
}
|
||||
|
||||
// Log placing scenery
|
||||
char* args[1] = {
|
||||
(char *)player_name
|
||||
};
|
||||
|
||||
format_string(log_msg, 256, STR_LOG_PLACE_SCENERY, args);
|
||||
network_append_server_log(log_msg);
|
||||
} else if (command == GAME_COMMAND_REMOVE_SCENERY || command == GAME_COMMAND_REMOVE_WALL ||
|
||||
command == GAME_COMMAND_REMOVE_LARGE_SCENERY || command == GAME_COMMAND_REMOVE_BANNER) {
|
||||
uint8 flags = *ebx & 0xFF;
|
||||
if (flags & GAME_COMMAND_FLAG_GHOST) {
|
||||
// Don't log ghost previews being removed
|
||||
return;
|
||||
}
|
||||
|
||||
// Log removing scenery
|
||||
char* args[1] = {
|
||||
(char *)player_name
|
||||
};
|
||||
|
||||
format_string(log_msg, 256, STR_LOG_REMOVE_SCENERY, args);
|
||||
network_append_server_log(log_msg);
|
||||
} else if (command == GAME_COMMAND_SET_SCENERY_COLOUR || command == GAME_COMMAND_SET_WALL_COLOUR ||
|
||||
command == GAME_COMMAND_SET_LARGE_SCENERY_COLOUR || command == GAME_COMMAND_SET_BANNER_COLOUR ||
|
||||
command == GAME_COMMAND_SET_BANNER_NAME || command == GAME_COMMAND_SET_SIGN_NAME ||
|
||||
command == GAME_COMMAND_SET_BANNER_STYLE || command == GAME_COMMAND_SET_SIGN_STYLE) {
|
||||
// Log editing scenery
|
||||
char* args[1] = {
|
||||
(char *)player_name
|
||||
};
|
||||
|
||||
format_string(log_msg, 256, STR_LOG_EDIT_SCENERY, args);
|
||||
network_append_server_log(log_msg);
|
||||
if (command == GAME_COMMAND_SET_BANNER_NAME || command == GAME_COMMAND_SET_SIGN_NAME) {
|
||||
static char banner_name[128];
|
||||
|
||||
memset(banner_name, ' ', sizeof(banner_name));
|
||||
int nameChunkIndex = *eax & 0xFFFF;
|
||||
|
||||
int nameChunkOffset = nameChunkIndex - 1;
|
||||
if (nameChunkOffset < 0)
|
||||
nameChunkOffset = 2;
|
||||
nameChunkOffset *= 12;
|
||||
nameChunkOffset = min(nameChunkOffset, countof(banner_name) - 12);
|
||||
memcpy(banner_name + nameChunkOffset + 0, edx, 4);
|
||||
memcpy(banner_name + nameChunkOffset + 4, ebp, 4);
|
||||
memcpy(banner_name + nameChunkOffset + 8, edi, 4);
|
||||
banner_name[sizeof(banner_name) - 1] = '\0';
|
||||
char* args_sign[2] = {
|
||||
(char *)player_name,
|
||||
(char *)banner_name
|
||||
};
|
||||
|
||||
format_string(log_msg, 256, STR_LOG_SET_SIGN_NAME, args_sign);
|
||||
network_append_server_log(log_msg);
|
||||
}
|
||||
} else if (command == GAME_COMMAND_PLACE_TRACK) {
|
||||
// Get ride name
|
||||
int ride_index = *edx & 0xFF;
|
||||
rct_ride* ride = get_ride(ride_index);
|
||||
char ride_name[128];
|
||||
format_string(ride_name, 128, ride->name, &ride->name_arguments);
|
||||
|
||||
char* args[2] = {
|
||||
(char *) player_name,
|
||||
ride_name
|
||||
};
|
||||
|
||||
format_string(log_msg, 256, STR_LOG_PLACE_TRACK, args);
|
||||
network_append_server_log(log_msg);
|
||||
} else if (command == GAME_COMMAND_REMOVE_TRACK) {
|
||||
char* args[1] = {
|
||||
(char *) player_name
|
||||
};
|
||||
|
||||
format_string(log_msg, 256, STR_LOG_REMOVE_TRACK, args);
|
||||
network_append_server_log(log_msg);
|
||||
}
|
||||
}
|
||||
|
||||
void pause_toggle()
|
||||
{
|
||||
gGamePaused ^= GAME_PAUSED_NORMAL;
|
||||
|
|
|
@ -166,6 +166,8 @@ void update_palette_effects();
|
|||
sint32 game_do_command(sint32 eax, sint32 ebx, sint32 ecx, sint32 edx, sint32 esi, sint32 edi, sint32 ebp);
|
||||
sint32 game_do_command_p(sint32 command, sint32 *eax, sint32 *ebx, sint32 *ecx, sint32 *edx, sint32 *esi, sint32 *edi, sint32 *ebp);
|
||||
|
||||
void game_log_multiplayer_command(int command, int *eax, int* ebx, int* ecx, int* edx, int* edi, int* ebp);
|
||||
|
||||
void game_load_or_quit_no_save_prompt();
|
||||
bool game_load_sv6_path(const char * path);
|
||||
bool game_load_save(const utf8 *path);
|
||||
|
|
|
@ -3728,6 +3728,43 @@ enum {
|
|||
|
||||
STR_CHEAT_OWN_ALL_LAND = 6064,
|
||||
|
||||
STR_LOG_SERVER_ACTIONS = 6065,
|
||||
STR_LOG_SERVER_ACTIONS_TIP = 6066,
|
||||
STR_LOG_SERVER_STARTED = 6067,
|
||||
STR_LOG_SERVER_STOPPED = 6068,
|
||||
STR_LOG_PLAYER_KICKED = 6069,
|
||||
STR_LOG_SET_PLAYER_GROUP = 6070,
|
||||
STR_LOG_ADD_PLAYER_GROUP = 6071,
|
||||
STR_LOG_REMOVE_PLAYER_GROUP = 6072,
|
||||
STR_LOG_EDIT_PLAYER_GROUP_PERMISSIONS = 6073,
|
||||
STR_LOG_EDIT_PLAYER_GROUP_NAME = 6074,
|
||||
STR_LOG_EDIT_DEFAULT_PLAYER_GROUP = 6075,
|
||||
STR_LOG_CHEAT_USED = 6076,
|
||||
STR_LOG_CHEAT_ADD_MONEY = 6077,
|
||||
STR_LOG_CREATE_RIDE = 6078,
|
||||
STR_LOG_DEMOLISH_RIDE = 6079,
|
||||
STR_LOG_RIDE_APPEARANCE = 6080,
|
||||
STR_LOG_RIDE_STATUS_CLOSED = 6081,
|
||||
STR_LOG_RIDE_STATUS_OPEN = 6082,
|
||||
STR_LOG_RIDE_STATUS_TESTING = 6083,
|
||||
STR_LOG_RIDE_VEHICLES = 6084,
|
||||
STR_LOG_RIDE_SETTINGS = 6085,
|
||||
STR_LOG_RIDE_NAME = 6086,
|
||||
STR_LOG_RIDE_PRICE = 6087,
|
||||
STR_LOG_RIDE_SECONDARY_PRICE = 6088,
|
||||
STR_LOG_PARK_NAME = 6089,
|
||||
STR_LOG_PARK_CLOSED = 6090,
|
||||
STR_LOG_PARK_OPEN = 6091,
|
||||
STR_LOG_PARK_ENTRANCE_FEE = 6092,
|
||||
STR_LOG_PLACE_SCENERY = 6093,
|
||||
STR_LOG_REMOVE_SCENERY = 6094,
|
||||
STR_LOG_EDIT_SCENERY = 6095,
|
||||
STR_LOG_SET_SIGN_NAME = 6096,
|
||||
STR_LOG_PLACE_TRACK = 6097,
|
||||
STR_LOG_REMOVE_TRACK = 6098,
|
||||
STR_LOG_CLIENT_STARTED = 6099,
|
||||
STR_LOG_CLIENT_STOPPED = 6100,
|
||||
|
||||
// Have to include resource strings (from scenarios and objects) for the time being now that language is partially working
|
||||
STR_COUNT = 32768
|
||||
};
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
|
||||
#include "../core/Guard.hpp"
|
||||
#include "../OpenRCT2.h"
|
||||
#include "../PlatformEnvironment.h"
|
||||
|
||||
extern "C" {
|
||||
#include "../platform/platform.h"
|
||||
|
@ -125,6 +126,11 @@ Network::~Network()
|
|||
Close();
|
||||
}
|
||||
|
||||
void Network::SetEnvironment(IPlatformEnvironment * env)
|
||||
{
|
||||
_env = env;
|
||||
}
|
||||
|
||||
bool Network::Init()
|
||||
{
|
||||
if (!InitialiseWSA()) {
|
||||
|
@ -170,6 +176,9 @@ void Network::Close()
|
|||
_advertiser = nullptr;
|
||||
}
|
||||
|
||||
CloseChatLog();
|
||||
CloseServerLog();
|
||||
|
||||
mode = NETWORK_MODE_NONE;
|
||||
status = NETWORK_STATUS_NONE;
|
||||
_lastConnectStatus = SOCKET_STATUS_CLOSED;
|
||||
|
@ -185,7 +194,6 @@ void Network::Close()
|
|||
|
||||
DisposeWSA();
|
||||
|
||||
CloseChatLog();
|
||||
gfx_invalidate_screen();
|
||||
|
||||
_requireClose = false;
|
||||
|
@ -210,6 +218,7 @@ bool Network::BeginClient(const char* host, uint16 port)
|
|||
_lastConnectStatus = SOCKET_STATUS_CLOSED;
|
||||
|
||||
BeginChatLog();
|
||||
BeginServerLog();
|
||||
|
||||
utf8 keyPath[MAX_PATH];
|
||||
network_get_private_key_path(keyPath, sizeof(keyPath), gConfigNetwork.player_name);
|
||||
|
@ -313,6 +322,7 @@ bool Network::BeginServer(uint16 port, const char* address)
|
|||
cheats_reset();
|
||||
LoadGroups();
|
||||
BeginChatLog();
|
||||
BeginServerLog();
|
||||
|
||||
NetworkPlayer *player = AddPlayer(gConfigNetwork.player_name, "");
|
||||
player->Flags |= NETWORK_PLAYER_FLAG_ISSERVER;
|
||||
|
@ -823,62 +833,97 @@ void Network::LoadGroups()
|
|||
group_list.at(0)->ActionsAllowed.fill(0xFF);
|
||||
}
|
||||
|
||||
void Network::BeginChatLog()
|
||||
std::string Network::BeginLog(const std::string &directory, const std::string &filenameFormat)
|
||||
{
|
||||
utf8 filename[32];
|
||||
utf8 filename[256];
|
||||
time_t timer;
|
||||
struct tm * tmInfo;
|
||||
time(&timer);
|
||||
tmInfo = localtime(&timer);
|
||||
strftime(filename, sizeof(filename), "%Y%m%d-%H%M%S.txt", tmInfo);
|
||||
|
||||
utf8 path[MAX_PATH];
|
||||
platform_get_user_directory(path, "chatlogs", sizeof(path));
|
||||
Path::Append(path, sizeof(path), filename);
|
||||
|
||||
_chatLogPath = std::string(path);
|
||||
}
|
||||
|
||||
void Network::AppendChatLog(const utf8 *text)
|
||||
{
|
||||
if (!gConfigNetwork.log_chat) {
|
||||
return;
|
||||
auto tmInfo = localtime(&timer);
|
||||
if (strftime(filename, sizeof(filename), filenameFormat.c_str(), tmInfo) == 0) {
|
||||
throw std::runtime_error("strftime failed");
|
||||
}
|
||||
|
||||
const utf8 *chatLogPath = _chatLogPath.c_str();
|
||||
return Path::Combine(directory, filename);
|
||||
}
|
||||
|
||||
utf8 directory[MAX_PATH];
|
||||
Path::GetDirectory(directory, sizeof(directory), chatLogPath);
|
||||
if (platform_ensure_directory_exists(directory)) {
|
||||
void Network::AppendLog(const std::string &logPath, const std::string &s)
|
||||
{
|
||||
std::string directory = Path::GetDirectory(logPath);
|
||||
if (platform_ensure_directory_exists(directory.c_str())) {
|
||||
try
|
||||
{
|
||||
_chatLogStream = new FileStream(chatLogPath, FILE_MODE_APPEND);
|
||||
auto fs = FileStream(logPath, FILE_MODE_APPEND);
|
||||
|
||||
utf8 buffer[256];
|
||||
time_t timer;
|
||||
struct tm * tmInfo;
|
||||
time(&timer);
|
||||
tmInfo = localtime(&timer);
|
||||
strftime(buffer, sizeof(buffer), "[%Y/%m/%d %H:%M:%S] ", tmInfo);
|
||||
|
||||
String::Append(buffer, sizeof(buffer), text);
|
||||
auto tmInfo = localtime(&timer);
|
||||
if (strftime(buffer, sizeof(buffer), "[%Y/%m/%d %H:%M:%S] ", tmInfo) != 0) {
|
||||
String::Append(buffer, sizeof(buffer), s.c_str());
|
||||
utf8_remove_formatting(buffer, false);
|
||||
String::Append(buffer, sizeof(buffer), PLATFORM_NEWLINE);
|
||||
|
||||
_chatLogStream->Write(buffer, strlen(buffer));
|
||||
delete _chatLogStream;
|
||||
_chatLogStream = nullptr;
|
||||
fs.Write(buffer, strlen(buffer));
|
||||
}
|
||||
catch (const Exception &)
|
||||
}
|
||||
catch (const Exception &ex)
|
||||
{
|
||||
log_error("%s", ex.GetMessage());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Network::BeginChatLog()
|
||||
{
|
||||
auto directory = _env->GetDirectoryPath(DIRBASE::USER, DIRID::LOG_CHAT);
|
||||
_chatLogPath = BeginLog(directory, _chatLogFilenameFormat);
|
||||
}
|
||||
|
||||
void Network::AppendChatLog(const std::string &s)
|
||||
{
|
||||
if (gConfigNetwork.log_chat) {
|
||||
AppendLog(_chatLogPath, s);
|
||||
}
|
||||
}
|
||||
|
||||
void Network::CloseChatLog()
|
||||
{
|
||||
}
|
||||
|
||||
void Network::BeginServerLog()
|
||||
{
|
||||
auto directory = _env->GetDirectoryPath(DIRBASE::USER, DIRID::LOG_SERVER);
|
||||
_serverLogPath = BeginLog(directory, (ServerName + _serverLogFilenameFormat));
|
||||
|
||||
// Log server start event
|
||||
utf8 logMessage[256];
|
||||
if (GetMode() == NETWORK_MODE_CLIENT) {
|
||||
format_string(logMessage, sizeof(logMessage), STR_LOG_CLIENT_STARTED, NULL);
|
||||
} else if (GetMode() == NETWORK_MODE_SERVER) {
|
||||
format_string(logMessage, sizeof(logMessage), STR_LOG_SERVER_STARTED, NULL);
|
||||
}
|
||||
AppendServerLog(logMessage);
|
||||
}
|
||||
|
||||
void Network::AppendServerLog(const std::string &s)
|
||||
{
|
||||
if (gConfigNetwork.log_server_actions) {
|
||||
AppendLog(_serverLogPath.c_str(), s);
|
||||
}
|
||||
}
|
||||
|
||||
void Network::CloseServerLog()
|
||||
{
|
||||
// Log server stopped event
|
||||
char logMessage[256];
|
||||
if (GetMode() == NETWORK_MODE_CLIENT) {
|
||||
format_string(logMessage, sizeof(logMessage), STR_LOG_CLIENT_STOPPED, NULL);
|
||||
} else if (GetMode() == NETWORK_MODE_SERVER) {
|
||||
format_string(logMessage, sizeof(logMessage), STR_LOG_SERVER_STOPPED, NULL);
|
||||
}
|
||||
AppendServerLog(logMessage);
|
||||
}
|
||||
|
||||
void Network::Client_Send_TOKEN()
|
||||
{
|
||||
log_verbose("requesting token");
|
||||
|
@ -1292,6 +1337,9 @@ void Network::AddClient(ITcpSocket * socket)
|
|||
{
|
||||
auto connection = std::unique_ptr<NetworkConnection>(new NetworkConnection); // change to make_unique in c++14
|
||||
connection->Socket = socket;
|
||||
char addr[128];
|
||||
snprintf(addr, sizeof(addr), "Client joined from %s", socket->GetHostName());
|
||||
AppendServerLog(addr);
|
||||
client_connection_list.push_back(std::move(connection));
|
||||
}
|
||||
|
||||
|
@ -1317,6 +1365,9 @@ void Network::RemoveClient(std::unique_ptr<NetworkConnection>& connection)
|
|||
game_do_command(pickup_peep->sprite_index, GAME_COMMAND_FLAG_APPLY, 1, 0, pickup_peep->type == PEEP_TYPE_GUEST ? GAME_COMMAND_PICKUP_GUEST : GAME_COMMAND_PICKUP_STAFF, network_get_pickup_peep_old_x(connection_player->Id), 0);
|
||||
}
|
||||
gNetwork.Server_Send_EVENT_PLAYER_DISCONNECTED((char*)connection_player->Name.c_str(), connection->GetLastDisconnectReason());
|
||||
|
||||
// Log player disconnected event
|
||||
AppendServerLog(text);
|
||||
}
|
||||
player_list.erase(std::remove_if(player_list.begin(), player_list.end(), [connection_player](std::unique_ptr<NetworkPlayer>& player){
|
||||
return player.get() == connection_player;
|
||||
|
@ -1516,6 +1567,9 @@ void Network::Server_Client_Joined(const char* name, const std::string &keyhash,
|
|||
IObjectManager * objManager = GetObjectManager();
|
||||
auto objects = objManager->GetPackableObjects();
|
||||
Server_Send_OBJECTS(connection, objects);
|
||||
|
||||
// Log player joining event
|
||||
AppendServerLog(text);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2138,9 +2192,9 @@ void Network::Client_Handle_GAMEINFO(NetworkConnection& connection, NetworkPacke
|
|||
network_chat_show_server_greeting();
|
||||
}
|
||||
|
||||
sint32 network_init()
|
||||
void network_set_env(void * env)
|
||||
{
|
||||
return gNetwork.Init();
|
||||
gNetwork.SetEnvironment((IPlatformEnvironment *)env);
|
||||
}
|
||||
|
||||
void network_close()
|
||||
|
@ -2375,6 +2429,18 @@ void game_command_set_player_group(sint32* eax, sint32* ebx, sint32* ecx, sint32
|
|||
}
|
||||
|
||||
window_invalidate_by_number(WC_PLAYER, playerid);
|
||||
|
||||
// Log set player group event
|
||||
NetworkPlayer* game_command_player = gNetwork.GetPlayerByID(game_command_playerid);
|
||||
NetworkGroup* new_player_group = gNetwork.GetGroupByID(groupid);
|
||||
char log_msg[256];
|
||||
const char * args[3] = {
|
||||
(char *) player->Name.c_str(),
|
||||
(char *) new_player_group->GetName().c_str(),
|
||||
(char *) game_command_player->Name.c_str()
|
||||
};
|
||||
format_string(log_msg, 256, STR_LOG_SET_PLAYER_GROUP, args);
|
||||
network_append_server_log(log_msg);
|
||||
}
|
||||
*ebx = 0;
|
||||
}
|
||||
|
@ -2385,9 +2451,6 @@ void game_command_modify_groups(sint32 *eax, sint32 *ebx, sint32 *ecx, sint32 *e
|
|||
uint8 groupid = (uint8)(*eax >> 8);
|
||||
uint8 nameChunkIndex = (uint8)(*eax >> 16);
|
||||
|
||||
char oldName[128] = { 0 };
|
||||
static char newName[128];
|
||||
|
||||
switch (action)
|
||||
{
|
||||
case 0:{ // add group
|
||||
|
@ -2399,6 +2462,16 @@ void game_command_modify_groups(sint32 *eax, sint32 *ebx, sint32 *ecx, sint32 *e
|
|||
*ebx = MONEY32_UNDEFINED;
|
||||
return;
|
||||
}
|
||||
|
||||
// Log add player group event
|
||||
NetworkPlayer* game_command_player = gNetwork.GetPlayerByID(game_command_playerid);
|
||||
char log_msg[256];
|
||||
const char * args[2] = {
|
||||
(char *) game_command_player->Name.c_str(),
|
||||
(char *) newgroup->GetName().c_str()
|
||||
};
|
||||
format_string(log_msg, 256, STR_LOG_ADD_PLAYER_GROUP, args);
|
||||
network_append_server_log(log_msg);
|
||||
}
|
||||
}break;
|
||||
case 1:{ // remove group
|
||||
|
@ -2417,6 +2490,18 @@ void game_command_modify_groups(sint32 *eax, sint32 *ebx, sint32 *ecx, sint32 *e
|
|||
}
|
||||
}
|
||||
if (*ebx & GAME_COMMAND_FLAG_APPLY) {
|
||||
// Log remove player group event
|
||||
NetworkPlayer* game_command_player = gNetwork.GetPlayerByID(game_command_playerid);
|
||||
NetworkGroup* group = gNetwork.GetGroupByID(groupid);
|
||||
char* groupName = (char *)group->GetName().c_str();
|
||||
char log_msg[256];
|
||||
const char * args[2] = {
|
||||
(char *) game_command_player->Name.c_str(),
|
||||
groupName
|
||||
};
|
||||
format_string(log_msg, 256, STR_LOG_REMOVE_PLAYER_GROUP, args);
|
||||
network_append_server_log(log_msg);
|
||||
|
||||
gNetwork.RemoveGroup(groupid);
|
||||
}
|
||||
}break;
|
||||
|
@ -2456,9 +2541,22 @@ void game_command_modify_groups(sint32 *eax, sint32 *ebx, sint32 *ecx, sint32 *e
|
|||
group->ToggleActionPermission(index);
|
||||
}
|
||||
}
|
||||
|
||||
// Log edit player group permissions event
|
||||
char log_msg[256];
|
||||
const char * args[2] = {
|
||||
(char *) player->Name.c_str(),
|
||||
(char *) group->GetName().c_str()
|
||||
};
|
||||
format_string(log_msg, 256, STR_LOG_EDIT_PLAYER_GROUP_PERMISSIONS, args);
|
||||
network_append_server_log(log_msg);
|
||||
}
|
||||
}break;
|
||||
case 3:{ // set group name
|
||||
NetworkGroup* group = gNetwork.GetGroupByID(groupid);
|
||||
const char * oldName = group->GetName().c_str();
|
||||
static char newName[128];
|
||||
|
||||
size_t nameChunkOffset = nameChunkIndex - 1;
|
||||
if (nameChunkIndex == 0)
|
||||
nameChunkOffset = 2;
|
||||
|
@ -2486,8 +2584,18 @@ void game_command_modify_groups(sint32 *eax, sint32 *ebx, sint32 *ecx, sint32 *e
|
|||
}
|
||||
|
||||
if (*ebx & GAME_COMMAND_FLAG_APPLY) {
|
||||
NetworkGroup* group = gNetwork.GetGroupByID(groupid);
|
||||
if (group) {
|
||||
// Log edit player group name event
|
||||
NetworkPlayer* player = gNetwork.GetPlayerByID(game_command_playerid);
|
||||
char log_msg[256];
|
||||
const char * args[3] = {
|
||||
(char *) player->Name.c_str(),
|
||||
oldName,
|
||||
newName
|
||||
};
|
||||
format_string(log_msg, 256, STR_LOG_EDIT_PLAYER_GROUP_NAME, args);
|
||||
network_append_server_log(log_msg);
|
||||
|
||||
group->SetName(newName);
|
||||
}
|
||||
}
|
||||
|
@ -2501,6 +2609,17 @@ void game_command_modify_groups(sint32 *eax, sint32 *ebx, sint32 *ecx, sint32 *e
|
|||
}
|
||||
if (*ebx & GAME_COMMAND_FLAG_APPLY) {
|
||||
gNetwork.SetDefaultGroup(groupid);
|
||||
|
||||
// Log edit default player group event
|
||||
NetworkPlayer* player = gNetwork.GetPlayerByID(game_command_playerid);
|
||||
NetworkGroup* group = gNetwork.GetGroupByID(groupid);
|
||||
char log_msg[256];
|
||||
const char * args[2] = {
|
||||
(char *) player->Name.c_str(),
|
||||
(char *) group->GetName().c_str()
|
||||
};
|
||||
format_string(log_msg, 256, STR_LOG_EDIT_DEFAULT_PLAYER_GROUP, args);
|
||||
network_append_server_log(log_msg);
|
||||
}
|
||||
}break;
|
||||
}
|
||||
|
@ -2529,6 +2648,16 @@ void game_command_kick_player(sint32 *eax, sint32 *ebx, sint32 *ecx, sint32 *edx
|
|||
networkUserManager->RemoveUser(player->KeyHash);
|
||||
networkUserManager->Save();
|
||||
}
|
||||
|
||||
// Log kick player event
|
||||
NetworkPlayer* kicker = gNetwork.GetPlayerByID(game_command_playerid);
|
||||
char log_msg[256];
|
||||
const char * args[2] = {
|
||||
(char *) player->Name.c_str(),
|
||||
(char *) kicker->Name.c_str(),
|
||||
};
|
||||
format_string(log_msg, 256, STR_LOG_PLAYER_KICKED, args);
|
||||
network_append_server_log(log_msg);
|
||||
}
|
||||
*ebx = 0;
|
||||
}
|
||||
|
@ -2657,6 +2786,11 @@ void network_append_chat_log(const utf8 *text)
|
|||
gNetwork.AppendChatLog(text);
|
||||
}
|
||||
|
||||
void network_append_server_log(const utf8 *text)
|
||||
{
|
||||
gNetwork.AppendServerLog(text);
|
||||
}
|
||||
|
||||
static void network_get_keys_directory(utf8 *buffer, size_t bufferSize)
|
||||
{
|
||||
platform_get_user_directory(buffer, "keys", bufferSize);
|
||||
|
@ -2729,11 +2863,13 @@ sint32 network_get_pickup_peep_old_x(uint8 playerid) { return _pickup_peep_old_x
|
|||
void network_send_chat(const char* text) {}
|
||||
void network_send_password(const char* password) {}
|
||||
void network_close() {}
|
||||
void network_set_env(void * env) {}
|
||||
void network_shutdown_client() {}
|
||||
void network_set_password(const char* password) {}
|
||||
uint8 network_get_current_player_id() { return 0; }
|
||||
sint32 network_get_current_player_group_index() { return 0; }
|
||||
void network_append_chat_log(const utf8 *text) { }
|
||||
void network_append_server_log(const utf8 *text) { }
|
||||
const utf8 * network_get_server_name() { return nullptr; }
|
||||
const utf8 * network_get_server_description() { return nullptr; }
|
||||
const utf8 * network_get_server_greeting() { return nullptr; }
|
||||
|
|
|
@ -85,6 +85,7 @@ enum {
|
|||
NETWORK_TICK_FLAG_CHECKSUMS = 1 << 0,
|
||||
};
|
||||
|
||||
interface IPlatformEnvironment;
|
||||
struct ObjectRepositoryItem;
|
||||
|
||||
class Network
|
||||
|
@ -92,6 +93,7 @@ class Network
|
|||
public:
|
||||
Network();
|
||||
~Network();
|
||||
void SetEnvironment(IPlatformEnvironment * env);
|
||||
bool Init();
|
||||
void Close();
|
||||
bool BeginClient(const char* host, uint16 port);
|
||||
|
@ -120,10 +122,17 @@ public:
|
|||
void SaveGroups();
|
||||
void LoadGroups();
|
||||
|
||||
std::string BeginLog(const std::string &directory, const std::string &filenameFormat);
|
||||
void AppendLog(const std::string &logPath, const std::string &s);
|
||||
|
||||
void BeginChatLog();
|
||||
void AppendChatLog(const utf8 *text);
|
||||
void AppendChatLog(const std::string &s);
|
||||
void CloseChatLog();
|
||||
|
||||
void BeginServerLog();
|
||||
void AppendServerLog(const std::string &s);
|
||||
void CloseServerLog();
|
||||
|
||||
void Client_Send_TOKEN();
|
||||
void Client_Send_AUTH(const char* name, const char* password, const char *pubkey, const char *sig, size_t sigsize);
|
||||
void Client_Send_AUTH(const char* name, const char* password, const char *pubkey);
|
||||
|
@ -217,9 +226,12 @@ private:
|
|||
INetworkServerAdvertiser * _advertiser = nullptr;
|
||||
uint32 server_connect_time = 0;
|
||||
uint8 default_group = 0;
|
||||
IStream * _chatLogStream = nullptr;
|
||||
std::string _chatLogPath;
|
||||
uint32 game_commands_processed_this_tick = 0;
|
||||
std::string _chatLogPath;
|
||||
std::string _chatLogFilenameFormat = "%Y%m%d-%H%M%S.txt";
|
||||
std::string _serverLogPath;
|
||||
std::string _serverLogFilenameFormat = "-%Y%m%d-%H%M%S.txt";
|
||||
IPlatformEnvironment * _env;
|
||||
|
||||
void UpdateServer();
|
||||
void UpdateClient();
|
||||
|
@ -262,7 +274,7 @@ private:
|
|||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif // __cplusplus
|
||||
sint32 network_init();
|
||||
void network_set_env(void * env);
|
||||
void network_close();
|
||||
void network_shutdown_client();
|
||||
sint32 network_begin_client(const char *host, sint32 port);
|
||||
|
@ -316,6 +328,7 @@ void network_set_password(const char* password);
|
|||
|
||||
void network_print_error();
|
||||
void network_append_chat_log(const utf8 *text);
|
||||
void network_append_server_log(const utf8 *text);
|
||||
const utf8 * network_get_server_name();
|
||||
const utf8 * network_get_server_description();
|
||||
const utf8 * network_get_server_greeting();
|
||||
|
|
|
@ -5594,6 +5594,22 @@ void game_command_set_ride_name(sint32 *eax, sint32 *ebx, sint32 *ecx, sint32 *e
|
|||
}
|
||||
|
||||
if (*ebx & GAME_COMMAND_FLAG_APPLY) {
|
||||
// Log ride rename command if we are in multiplayer and logging is enabled
|
||||
if ((network_get_mode() == NETWORK_MODE_CLIENT || network_get_mode() == NETWORK_MODE_SERVER) && gConfigNetwork.log_server_actions) {
|
||||
// Get player name
|
||||
int player_index = network_get_player_index(game_command_playerid);
|
||||
const char* player_name = network_get_player_name(player_index);
|
||||
|
||||
char log_msg[256];
|
||||
char* args[3] = {
|
||||
(char *) player_name,
|
||||
oldName,
|
||||
newName
|
||||
};
|
||||
format_string(log_msg, 256, STR_LOG_RIDE_NAME, args);
|
||||
network_append_server_log(log_msg);
|
||||
}
|
||||
|
||||
if (ride->overall_view != (uint16)-1) {
|
||||
rct_xyz16 coord;
|
||||
coord.x = (ride->overall_view & 0xFF) * 32 + 16;
|
||||
|
@ -6158,6 +6174,10 @@ foundRideEntry:
|
|||
ride_set_vehicle_colours_to_random_preset(ride, 0xFF & (*outRideColour >> 8));
|
||||
window_invalidate_by_class(WC_RIDE_LIST);
|
||||
|
||||
// Log ride creation
|
||||
int ebp = 1;
|
||||
game_log_multiplayer_command(GAME_COMMAND_CREATE_RIDE, 0, 0, 0, &rideIndex, 0, &ebp);
|
||||
|
||||
gCommandExpenditureType = RCT_EXPENDITURE_TYPE_RIDE_CONSTRUCTION;
|
||||
gCommandPosition.x = 0x8000;
|
||||
return 0;
|
||||
|
|
|
@ -746,10 +746,10 @@ static void window_cheats_misc_mouseup(rct_window *w, rct_widgetindex widgetInde
|
|||
game_do_command(0, GAME_COMMAND_FLAG_APPLY, CHEAT_RESETDATE, 0, GAME_COMMAND_CHEAT, 0, 0);
|
||||
break;
|
||||
case WIDX_FAST_STAFF:
|
||||
game_do_command(0, GAME_COMMAND_FLAG_APPLY, CHEAT_SETSTAFFSPEED, 0xFF, GAME_COMMAND_CHEAT, 0, 0);
|
||||
game_do_command(0, GAME_COMMAND_FLAG_APPLY, CHEAT_SETSTAFFSPEED, CHEATS_STAFF_FAST_SPEED, GAME_COMMAND_CHEAT, 0, 0);
|
||||
break;
|
||||
case WIDX_NORMAL_STAFF:
|
||||
game_do_command(0, GAME_COMMAND_FLAG_APPLY, CHEAT_SETSTAFFSPEED, 0x60, GAME_COMMAND_CHEAT, 0, 0);
|
||||
game_do_command(0, GAME_COMMAND_FLAG_APPLY, CHEAT_SETSTAFFSPEED, CHEATS_STAFF_NORMAL_SPEED, GAME_COMMAND_CHEAT, 0, 0);
|
||||
break;
|
||||
case WIDX_PARK_PARAMETERS:
|
||||
window_editor_scenario_options_open();
|
||||
|
|
|
@ -105,7 +105,7 @@ static void window_ride_demolish_mouseup(rct_window *w, rct_widgetindex widgetIn
|
|||
switch (widgetIndex) {
|
||||
case WIDX_DEMOLISH:
|
||||
gGameCommandErrorTitle = STR_CANT_DEMOLISH_RIDE;
|
||||
game_do_command(0, 1, 0, w->number, GAME_COMMAND_DEMOLISH_RIDE, 0, 0);
|
||||
game_do_command(0, 1, 0, w->number, GAME_COMMAND_DEMOLISH_RIDE, 0, 1); // Set ebp to 1 to be used to log demolish from window prompt
|
||||
break;
|
||||
case WIDX_CANCEL:
|
||||
case WIDX_CLOSE:
|
||||
|
|
|
@ -52,6 +52,7 @@ enum WINDOW_MULTIPLAYER_WIDGET_IDX {
|
|||
WIDX_PERMISSIONS_LIST,
|
||||
|
||||
WIDX_LOG_CHAT_CHECKBOX = 8,
|
||||
WIDX_LOG_SERVER_ACTIONS_CHECKBOX,
|
||||
WIDX_KNOWN_KEYS_ONLY_CHECKBOX,
|
||||
};
|
||||
|
||||
|
@ -92,7 +93,8 @@ static rct_widget window_multiplayer_groups_widgets[] = {
|
|||
static rct_widget window_multiplayer_options_widgets[] = {
|
||||
MAIN_MULTIPLAYER_WIDGETS,
|
||||
{ WWT_CHECKBOX, 1, 3, 297, 50, 61, STR_LOG_CHAT, STR_LOG_CHAT_TIP },
|
||||
{ WWT_CHECKBOX, 1, 3, 297, 64, 75, STR_ALLOW_KNOWN_KEYS_ONLY, STR_ALLOW_KNOWN_KEYS_ONLY_TIP },
|
||||
{ WWT_CHECKBOX, 1, 3, 297, 64, 75, STR_LOG_SERVER_ACTIONS, STR_LOG_SERVER_ACTIONS_TIP },
|
||||
{ WWT_CHECKBOX, 1, 3, 297, 78, 89, STR_ALLOW_KNOWN_KEYS_ONLY, STR_ALLOW_KNOWN_KEYS_ONLY_TIP },
|
||||
{ WIDGETS_END }
|
||||
};
|
||||
|
||||
|
@ -107,7 +109,7 @@ const uint64 window_multiplayer_page_enabled_widgets[] = {
|
|||
(1 << WIDX_CLOSE) | (1 << WIDX_TAB1) | (1 << WIDX_TAB2) | (1 << WIDX_TAB3) | (1 << WIDX_TAB4),
|
||||
(1 << WIDX_CLOSE) | (1 << WIDX_TAB1) | (1 << WIDX_TAB2) | (1 << WIDX_TAB3) | (1 << WIDX_TAB4),
|
||||
(1 << WIDX_CLOSE) | (1 << WIDX_TAB1) | (1 << WIDX_TAB2) | (1 << WIDX_TAB3) | (1 << WIDX_TAB4) | (1 << WIDX_DEFAULT_GROUP) | (1 << WIDX_DEFAULT_GROUP_DROPDOWN) | (1 << WIDX_ADD_GROUP) | (1 << WIDX_REMOVE_GROUP) | (1 << WIDX_RENAME_GROUP) | (1 << WIDX_SELECTED_GROUP) | (1 << WIDX_SELECTED_GROUP_DROPDOWN),
|
||||
(1 << WIDX_CLOSE) | (1 << WIDX_TAB1) | (1 << WIDX_TAB2) | (1 << WIDX_TAB3) | (1 << WIDX_TAB4) | (1 << WIDX_LOG_CHAT_CHECKBOX) | (1 << WIDX_KNOWN_KEYS_ONLY_CHECKBOX),
|
||||
(1 << WIDX_CLOSE) | (1 << WIDX_TAB1) | (1 << WIDX_TAB2) | (1 << WIDX_TAB3) | (1 << WIDX_TAB4) | (1 << WIDX_LOG_CHAT_CHECKBOX) | (1 << WIDX_LOG_SERVER_ACTIONS_CHECKBOX) | (1 << WIDX_KNOWN_KEYS_ONLY_CHECKBOX),
|
||||
};
|
||||
|
||||
static uint8 _selectedGroup = 0;
|
||||
|
@ -918,6 +920,10 @@ static void window_multiplayer_options_mouseup(rct_window *w, rct_widgetindex wi
|
|||
gConfigNetwork.log_chat = !gConfigNetwork.log_chat;
|
||||
config_save_default();
|
||||
break;
|
||||
case WIDX_LOG_SERVER_ACTIONS_CHECKBOX:
|
||||
gConfigNetwork.log_server_actions = !gConfigNetwork.log_server_actions;
|
||||
config_save_default();
|
||||
break;
|
||||
case WIDX_KNOWN_KEYS_ONLY_CHECKBOX:
|
||||
gConfigNetwork.known_keys_only = !gConfigNetwork.known_keys_only;
|
||||
config_save_default();
|
||||
|
@ -947,6 +953,7 @@ static void window_multiplayer_options_invalidate(rct_window *w)
|
|||
}
|
||||
|
||||
widget_set_checkbox_value(w, WIDX_LOG_CHAT_CHECKBOX, gConfigNetwork.log_chat);
|
||||
widget_set_checkbox_value(w, WIDX_LOG_SERVER_ACTIONS_CHECKBOX, gConfigNetwork.log_server_actions);
|
||||
widget_set_checkbox_value(w, WIDX_KNOWN_KEYS_ONLY_CHECKBOX, gConfigNetwork.known_keys_only);
|
||||
}
|
||||
|
||||
|
|
|
@ -25,6 +25,7 @@
|
|||
#include "../management/marketing.h"
|
||||
#include "../management/news_item.h"
|
||||
#include "../management/research.h"
|
||||
#include "../network/network.h"
|
||||
#include "../peep/peep.h"
|
||||
#include "../peep/staff.h"
|
||||
#include "../rct2.h"
|
||||
|
@ -840,6 +841,22 @@ void game_command_set_park_name(sint32 *eax, sint32 *ebx, sint32 *ecx, sint32 *e
|
|||
}
|
||||
|
||||
if (*ebx & GAME_COMMAND_FLAG_APPLY) {
|
||||
// Log park rename command if we are in multiplayer and logging is enabled
|
||||
if ((network_get_mode() == NETWORK_MODE_CLIENT || network_get_mode() == NETWORK_MODE_SERVER) && gConfigNetwork.log_server_actions) {
|
||||
// Get player name
|
||||
int player_index = network_get_player_index(game_command_playerid);
|
||||
const char* player_name = network_get_player_name(player_index);
|
||||
|
||||
char log_msg[256];
|
||||
char* args[3] = {
|
||||
(char *) player_name,
|
||||
oldName,
|
||||
newName
|
||||
};
|
||||
format_string(log_msg, 256, STR_LOG_PARK_NAME, args);
|
||||
network_append_server_log(log_msg);
|
||||
}
|
||||
|
||||
// Free the old ride name
|
||||
user_string_free(gParkName);
|
||||
gParkName = newUserStringId;
|
||||
|
|
Loading…
Reference in New Issue