diff --git a/managed/CounterStrikeSharp.API/Core/API.cs b/managed/CounterStrikeSharp.API/Core/API.cs index e0320288b..40785f520 100644 --- a/managed/CounterStrikeSharp.API/Core/API.cs +++ b/managed/CounterStrikeSharp.API/Core/API.cs @@ -560,6 +560,17 @@ public static void PrintToServerConsole(string msg){ } } + public static void DisconnectClient(int slot, int reason){ + lock (ScriptContext.GlobalScriptContext.Lock) { + ScriptContext.GlobalScriptContext.Reset(); + ScriptContext.GlobalScriptContext.Push(slot); + ScriptContext.GlobalScriptContext.Push(reason); + ScriptContext.GlobalScriptContext.SetIdentifier(0x799EE9C3); + ScriptContext.GlobalScriptContext.Invoke(); + ScriptContext.GlobalScriptContext.CheckErrors(); + } + } + public static IntPtr GetEntityFromIndex(int index){ lock (ScriptContext.GlobalScriptContext.Lock) { ScriptContext.GlobalScriptContext.Reset(); diff --git a/managed/CounterStrikeSharp.API/Core/Model/CCSPlayerController.cs b/managed/CounterStrikeSharp.API/Core/Model/CCSPlayerController.cs index 6967662aa..76700911a 100644 --- a/managed/CounterStrikeSharp.API/Core/Model/CCSPlayerController.cs +++ b/managed/CounterStrikeSharp.API/Core/Model/CCSPlayerController.cs @@ -1,10 +1,10 @@ using System; - using CounterStrikeSharp.API.Modules.Cvars; using CounterStrikeSharp.API.Modules.Entities; using CounterStrikeSharp.API.Modules.Entities.Constants; using CounterStrikeSharp.API.Modules.Memory; using CounterStrikeSharp.API.Modules.Utils; +using CounterStrikeSharp.API.ValveConstants.Protobuf; namespace CounterStrikeSharp.API.Core; @@ -241,6 +241,15 @@ public void ExecuteClientCommand(string command) NativeAPI.IssueClientCommand(Slot, command); } + /// + /// Disconnects a player from the server with the specified reason. + /// + /// + public void Disconnect(NetworkDisconnectionReason reason) + { + NativeAPI.DisconnectClient(Slot, (int)reason); + } + /// /// Issue the specified command directly from the server (mimics the server executing the command with the given player context). /// Works with server commands like `kill`, `explode`, `noclip`, etc. diff --git a/managed/CounterStrikeSharp.API/ValveConstants/Protobuf/NetworkDisconnectionReason.cs b/managed/CounterStrikeSharp.API/ValveConstants/Protobuf/NetworkDisconnectionReason.cs new file mode 100644 index 000000000..d75261329 --- /dev/null +++ b/managed/CounterStrikeSharp.API/ValveConstants/Protobuf/NetworkDisconnectionReason.cs @@ -0,0 +1,126 @@ +namespace CounterStrikeSharp.API.ValveConstants.Protobuf; + +/// +/// Enum derived from `network_connection.proto` +/// +public enum NetworkDisconnectionReason +{ + NETWORK_DISCONNECT_INVALID = 0, + NETWORK_DISCONNECT_SHUTDOWN = 1, + NETWORK_DISCONNECT_DISCONNECT_BY_USER = 2, + NETWORK_DISCONNECT_DISCONNECT_BY_SERVER = 3, + NETWORK_DISCONNECT_LOST = 4, + NETWORK_DISCONNECT_OVERFLOW = 5, + NETWORK_DISCONNECT_STEAM_BANNED = 6, + NETWORK_DISCONNECT_STEAM_INUSE = 7, + NETWORK_DISCONNECT_STEAM_TICKET = 8, + NETWORK_DISCONNECT_STEAM_LOGON = 9, + NETWORK_DISCONNECT_STEAM_AUTHCANCELLED = 10, + NETWORK_DISCONNECT_STEAM_AUTHALREADYUSED = 11, + NETWORK_DISCONNECT_STEAM_AUTHINVALID = 12, + NETWORK_DISCONNECT_STEAM_VACBANSTATE = 13, + NETWORK_DISCONNECT_STEAM_LOGGED_IN_ELSEWHERE = 14, + NETWORK_DISCONNECT_STEAM_VAC_CHECK_TIMEDOUT = 15, + NETWORK_DISCONNECT_STEAM_DROPPED = 16, + NETWORK_DISCONNECT_STEAM_OWNERSHIP = 17, + NETWORK_DISCONNECT_SERVERINFO_OVERFLOW = 18, + NETWORK_DISCONNECT_TICKMSG_OVERFLOW = 19, + NETWORK_DISCONNECT_STRINGTABLEMSG_OVERFLOW = 20, + NETWORK_DISCONNECT_DELTAENTMSG_OVERFLOW = 21, + NETWORK_DISCONNECT_TEMPENTMSG_OVERFLOW = 22, + NETWORK_DISCONNECT_SOUNDSMSG_OVERFLOW = 23, + NETWORK_DISCONNECT_SNAPSHOTOVERFLOW = 24, + NETWORK_DISCONNECT_SNAPSHOTERROR = 25, + NETWORK_DISCONNECT_RELIABLEOVERFLOW = 26, + NETWORK_DISCONNECT_BADDELTATICK = 27, + NETWORK_DISCONNECT_NOMORESPLITS = 28, + NETWORK_DISCONNECT_TIMEDOUT = 29, + NETWORK_DISCONNECT_DISCONNECTED = 30, + NETWORK_DISCONNECT_LEAVINGSPLIT = 31, + NETWORK_DISCONNECT_DIFFERENTCLASSTABLES = 32, + NETWORK_DISCONNECT_BADRELAYPASSWORD = 33, + NETWORK_DISCONNECT_BADSPECTATORPASSWORD = 34, + NETWORK_DISCONNECT_HLTVRESTRICTED = 35, + NETWORK_DISCONNECT_NOSPECTATORS = 36, + NETWORK_DISCONNECT_HLTVUNAVAILABLE = 37, + NETWORK_DISCONNECT_HLTVSTOP = 38, + NETWORK_DISCONNECT_KICKED = 39, + NETWORK_DISCONNECT_BANADDED = 40, + NETWORK_DISCONNECT_KICKBANADDED = 41, + NETWORK_DISCONNECT_HLTVDIRECT = 42, + NETWORK_DISCONNECT_PURESERVER_CLIENTEXTRA = 43, + NETWORK_DISCONNECT_PURESERVER_MISMATCH = 44, + NETWORK_DISCONNECT_USERCMD = 45, + NETWORK_DISCONNECT_REJECTED_BY_GAME = 46, + NETWORK_DISCONNECT_MESSAGE_PARSE_ERROR = 47, + NETWORK_DISCONNECT_INVALID_MESSAGE_ERROR = 48, + NETWORK_DISCONNECT_BAD_SERVER_PASSWORD = 49, + NETWORK_DISCONNECT_DIRECT_CONNECT_RESERVATION = 50, + NETWORK_DISCONNECT_CONNECTION_FAILURE = 51, + NETWORK_DISCONNECT_NO_PEER_GROUP_HANDLERS = 52, + NETWORK_DISCONNECT_RECONNECTION = 53, + NETWORK_DISCONNECT_LOOPSHUTDOWN = 54, + NETWORK_DISCONNECT_LOOPDEACTIVATE = 55, + NETWORK_DISCONNECT_HOST_ENDGAME = 56, + NETWORK_DISCONNECT_LOOP_LEVELLOAD_ACTIVATE = 57, + NETWORK_DISCONNECT_CREATE_SERVER_FAILED = 58, + NETWORK_DISCONNECT_EXITING = 59, + NETWORK_DISCONNECT_REQUEST_HOSTSTATE_IDLE = 60, + NETWORK_DISCONNECT_REQUEST_HOSTSTATE_HLTVRELAY = 61, + NETWORK_DISCONNECT_CLIENT_CONSISTENCY_FAIL = 62, + NETWORK_DISCONNECT_CLIENT_UNABLE_TO_CRC_MAP = 63, + NETWORK_DISCONNECT_CLIENT_NO_MAP = 64, + NETWORK_DISCONNECT_CLIENT_DIFFERENT_MAP = 65, + NETWORK_DISCONNECT_SERVER_REQUIRES_STEAM = 66, + NETWORK_DISCONNECT_STEAM_DENY_MISC = 67, + NETWORK_DISCONNECT_STEAM_DENY_BAD_ANTI_CHEAT = 68, + NETWORK_DISCONNECT_SERVER_SHUTDOWN = 69, + NETWORK_DISCONNECT_REPLAY_INCOMPATIBLE = 71, + NETWORK_DISCONNECT_CONNECT_REQUEST_TIMEDOUT = 72, + NETWORK_DISCONNECT_SERVER_INCOMPATIBLE = 73, + NETWORK_DISCONNECT_LOCALPROBLEM_MANYRELAYS = 74, + NETWORK_DISCONNECT_LOCALPROBLEM_HOSTEDSERVERPRIMARYRELAY = 75, + NETWORK_DISCONNECT_LOCALPROBLEM_NETWORKCONFIG = 76, + NETWORK_DISCONNECT_LOCALPROBLEM_OTHER = 77, + NETWORK_DISCONNECT_REMOTE_TIMEOUT = 79, + NETWORK_DISCONNECT_REMOTE_TIMEOUT_CONNECTING = 80, + NETWORK_DISCONNECT_REMOTE_OTHER = 81, + NETWORK_DISCONNECT_REMOTE_BADCRYPT = 82, + NETWORK_DISCONNECT_REMOTE_CERTNOTTRUSTED = 83, + NETWORK_DISCONNECT_UNUSUAL = 84, + NETWORK_DISCONNECT_INTERNAL_ERROR = 85, + NETWORK_DISCONNECT_REJECT_BADCHALLENGE = 128, + NETWORK_DISCONNECT_REJECT_NOLOBBY = 129, + NETWORK_DISCONNECT_REJECT_BACKGROUND_MAP = 130, + NETWORK_DISCONNECT_REJECT_SINGLE_PLAYER = 131, + NETWORK_DISCONNECT_REJECT_HIDDEN_GAME = 132, + NETWORK_DISCONNECT_REJECT_LANRESTRICT = 133, + NETWORK_DISCONNECT_REJECT_BADPASSWORD = 134, + NETWORK_DISCONNECT_REJECT_SERVERFULL = 135, + NETWORK_DISCONNECT_REJECT_INVALIDRESERVATION = 136, + NETWORK_DISCONNECT_REJECT_FAILEDCHANNEL = 137, + NETWORK_DISCONNECT_REJECT_CONNECT_FROM_LOBBY = 138, + NETWORK_DISCONNECT_REJECT_RESERVED_FOR_LOBBY = 139, + NETWORK_DISCONNECT_REJECT_INVALIDKEYLENGTH = 140, + NETWORK_DISCONNECT_REJECT_OLDPROTOCOL = 141, + NETWORK_DISCONNECT_REJECT_NEWPROTOCOL = 142, + NETWORK_DISCONNECT_REJECT_INVALIDCONNECTION = 143, + NETWORK_DISCONNECT_REJECT_INVALIDCERTLEN = 144, + NETWORK_DISCONNECT_REJECT_INVALIDSTEAMCERTLEN = 145, + NETWORK_DISCONNECT_REJECT_STEAM = 146, + NETWORK_DISCONNECT_REJECT_SERVERAUTHDISABLED = 147, + NETWORK_DISCONNECT_REJECT_SERVERCDKEYAUTHINVALID = 148, + NETWORK_DISCONNECT_REJECT_BANNED = 149, + NETWORK_DISCONNECT_KICKED_TEAMKILLING = 150, + NETWORK_DISCONNECT_KICKED_TK_START = 151, + NETWORK_DISCONNECT_KICKED_UNTRUSTEDACCOUNT = 152, + NETWORK_DISCONNECT_KICKED_CONVICTEDACCOUNT = 153, + NETWORK_DISCONNECT_KICKED_COMPETITIVECOOLDOWN = 154, + NETWORK_DISCONNECT_KICKED_TEAMHURTING = 155, + NETWORK_DISCONNECT_KICKED_HOSTAGEKILLING = 156, + NETWORK_DISCONNECT_KICKED_VOTEDOFF = 157, + NETWORK_DISCONNECT_KICKED_IDLE = 158, + NETWORK_DISCONNECT_KICKED_SUICIDE = 159, + NETWORK_DISCONNECT_KICKED_NOSTEAMLOGIN = 160, + NETWORK_DISCONNECT_KICKED_NOSTEAMTICKET = 161 +} diff --git a/src/scripting/natives/natives_engine.cpp b/src/scripting/natives/natives_engine.cpp index 488425cd7..04b250d69 100644 --- a/src/scripting/natives/natives_engine.cpp +++ b/src/scripting/natives/natives_engine.cpp @@ -224,6 +224,20 @@ void PrintToServerConsole(ScriptContext& scriptContext) META_CONPRINT(message); } +void DisconnectClient(ScriptContext& scriptContext) +{ + auto slot = scriptContext.GetArgument(0); + auto disconnectReason = scriptContext.GetArgument(1); + + if (!ENetworkDisconnectionReason_IsValid(disconnectReason)) + { + scriptContext.ThrowNativeError("Invalid disconnect reason"); + return; + } + + globals::engineServer2->DisconnectClient(slot, disconnectReason); +} + REGISTER_NATIVES(engine, { ScriptEngine::RegisterNativeHandler("GET_GAME_DIRECTORY", GetGameDirectory); ScriptEngine::RegisterNativeHandler("GET_MAP_NAME", GetMapName); @@ -248,5 +262,6 @@ REGISTER_NATIVES(engine, { ScriptEngine::RegisterNativeHandler("GET_VALVE_INTERFACE", GetValveInterface); ScriptEngine::RegisterNativeHandler("GET_COMMAND_PARAM_VALUE", GetCommandParamValue); ScriptEngine::RegisterNativeHandler("PRINT_TO_SERVER_CONSOLE", PrintToServerConsole); + ScriptEngine::RegisterNativeHandler("DISCONNECT_CLIENT", DisconnectClient); }) } // namespace counterstrikesharp diff --git a/src/scripting/natives/natives_engine.yaml b/src/scripting/natives/natives_engine.yaml index dcc6ac22b..1718a69e1 100644 --- a/src/scripting/natives/natives_engine.yaml +++ b/src/scripting/natives/natives_engine.yaml @@ -25,4 +25,5 @@ QUEUE_TASK_FOR_FRAME: tick:int, callback:func -> void QUEUE_TASK_FOR_NEXT_WORLD_UPDATE: callback:func -> void GET_VALVE_INTERFACE: interfaceType:int, interfaceName:string -> pointer GET_COMMAND_PARAM_VALUE: param:string, dataType:DataType_t, defaultValue:any -> any -PRINT_TO_SERVER_CONSOLE: msg:string -> void \ No newline at end of file +PRINT_TO_SERVER_CONSOLE: msg:string -> void +DISCONNECT_CLIENT: slot:int, reason:int -> void