diff --git a/CHANGELOG.md b/CHANGELOG.md
index d08b8527..dc1a0b01 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -26,7 +26,7 @@ This is the rolling changelog for TShock for Terraria. Use past tense when addin
* `GetDataHandlers.SendTileSquare` hook now sends a `TSPlayer` and a `MemoryStream` of raw data. (@hakusaro)
* Added `GetDataHandlers.HealOtherPlayer` hook. (@hakusaro)
* Added `GetDataHandlers.PlaceObject` hook. (@hakusaro)
-
+* `GetDataHandlers.KillMe` now sends a `TSPlayer` and a `PlayerDeathReason`. (@hakusaro)
## TShock 4.3.24
* Updated OpenTerraria API to 1.3.5.3 (@DeathCradle)
diff --git a/TShockAPI/Bouncer.cs b/TShockAPI/Bouncer.cs
index ed1caba1..6fc7f640 100644
--- a/TShockAPI/Bouncer.cs
+++ b/TShockAPI/Bouncer.cs
@@ -29,7 +29,7 @@ using static TShockAPI.GetDataHandlers;
using TerrariaApi.Server;
using Terraria.ObjectData;
using Terraria.ID;
-
+using Terraria.DataStructures;
namespace TShockAPI
{
@@ -42,6 +42,7 @@ namespace TShockAPI
{
// Setup hooks
+ GetDataHandlers.KillMe.Register(OnKillMe);
GetDataHandlers.NewProjectile.Register(OnNewProjectile);
GetDataHandlers.PlaceObject.Register(OnPlaceObject);
GetDataHandlers.SendTileSquare.Register(OnSendTileSquare);
@@ -49,6 +50,37 @@ namespace TShockAPI
GetDataHandlers.TileEdit.Register(OnTileEdit);
}
+ internal void OnKillMe(object sender, GetDataHandlers.KillMeEventArgs args)
+ {
+ short dmg = args.Damage;
+ short id = args.PlayerId;
+ PlayerDeathReason playerDeathReason = args.PlayerDeathReason;
+
+ if (dmg > 20000) //Abnormal values have the potential to cause infinite loops in the server.
+ {
+ TShock.Utils.ForceKick(args.Player, "Crash Exploit Attempt", true);
+ TShock.Log.ConsoleError("Death Exploit Attempt: Damage {0}", dmg);
+ args.Handled = true;
+ return;
+ }
+
+ if (id >= Main.maxPlayers)
+ {
+ args.Handled = true;
+ return;
+ }
+
+ if (playerDeathReason != null)
+ {
+ if (playerDeathReason.GetDeathText(TShock.Players[id].Name).ToString().Length > 500)
+ {
+ TShock.Utils.Kick(TShock.Players[id], "Crash attempt", true);
+ args.Handled = true;
+ return;
+ }
+ }
+ }
+
internal void OnNewProjectile(object sender, GetDataHandlers.NewProjectileEventArgs args)
{
short ident = args.Identity;
diff --git a/TShockAPI/GetDataHandlers.cs b/TShockAPI/GetDataHandlers.cs
index 0d59a7ec..c57ab351 100644
--- a/TShockAPI/GetDataHandlers.cs
+++ b/TShockAPI/GetDataHandlers.cs
@@ -389,6 +389,8 @@ namespace TShockAPI
///
public class KillMeEventArgs : HandledEventArgs
{
+ /// The TSPlayer that triggered the event.
+ public TSPlayer Player { get; set; }
///
/// The Terraria playerID of the player
///
@@ -405,23 +407,27 @@ namespace TShockAPI
/// Player's current pvp setting
///
public bool Pvp { get; set; }
+ /// The reason the player died.
+ public PlayerDeathReason PlayerDeathReason { get; set; }
}
///
/// KillMe - Terraria's crappy way of handling damage from players
///
public static HandlerList KillMe;
- private static bool OnKillMe(byte plr, byte direction, short damage, bool pvp)
+ private static bool OnKillMe(TSPlayer player, byte plr, byte direction, short damage, bool pvp, PlayerDeathReason playerDeathReason)
{
if (KillMe == null)
return false;
var args = new KillMeEventArgs
{
+ Player = player,
PlayerId = plr,
Direction = direction,
Damage = damage,
Pvp = pvp,
+ PlayerDeathReason = playerDeathReason,
};
KillMe.Invoke(null, args);
return args.Handled;
@@ -1341,7 +1347,6 @@ namespace TShockAPI
{ PacketTypes.TogglePvp, HandleTogglePvp },
{ PacketTypes.PlayerTeam, HandlePlayerTeam },
{ PacketTypes.TileKill, HandleTileKill },
- { PacketTypes.PlayerKillMe, HandlePlayerKillMe },
{ PacketTypes.LiquidSet, HandleLiquidSet },
{ PacketTypes.PlayerSpawn, HandleSpawn },
{ PacketTypes.ChestGetContents, HandleChestOpen },
@@ -2315,71 +2320,6 @@ namespace TShockAPI
return false;
}
- private static bool HandlePlayerKillMe(GetDataHandlerArgs args)
- {
- var id = args.Data.ReadInt8();
- var direction = (byte)(args.Data.ReadInt8() - 1);
- var dmg = args.Data.ReadInt16();
- var pvp = args.Data.ReadInt8() == 0;
- var text = args.Data.ReadString();
- if (dmg > 20000) //Abnormal values have the potential to cause infinite loops in the server.
- {
- TShock.Utils.ForceKick(args.Player, "Crash Exploit Attempt", true);
- TShock.Log.ConsoleError("Death Exploit Attempt: Damage {0}", dmg);
- return false;
- }
-
- if (id >= Main.maxPlayers)
- {
- return true;
- }
-
- if (OnKillMe(id, direction, dmg, pvp))
- return true;
-
- if (text.Length > 500)
- {
- TShock.Utils.Kick(TShock.Players[id], "Crash attempt", true);
- return true;
- }
-
- args.Player.Dead = true;
- args.Player.RespawnTimer = TShock.Config.RespawnSeconds;
-
- foreach (NPC npc in Main.npc)
- {
- if (npc.active && (npc.boss || npc.type == 13 || npc.type == 14 || npc.type == 15) &&
- Math.Abs(args.TPlayer.Center.X - npc.Center.X) + Math.Abs(args.TPlayer.Center.Y - npc.Center.Y) < 4000f)
- {
- args.Player.RespawnTimer = TShock.Config.RespawnBossSeconds;
- break;
- }
- }
-
- if (args.TPlayer.difficulty == 2 && (TShock.Config.KickOnHardcoreDeath || TShock.Config.BanOnHardcoreDeath))
- {
- if (TShock.Config.BanOnHardcoreDeath)
- {
- if (!TShock.Utils.Ban(args.Player, TShock.Config.HardcoreBanReason, false, "hardcore-death"))
- TShock.Utils.ForceKick(args.Player, "Death results in a ban, but you are immune to bans.", true);
- }
- else
- {
- TShock.Utils.ForceKick(args.Player, TShock.Config.HardcoreKickReason, true, false);
- }
- }
-
- if (args.TPlayer.difficulty == 2 && Main.ServerSideCharacter && args.Player.IsLoggedIn)
- {
- if (TShock.CharacterDB.RemovePlayer(args.Player.Account.ID))
- {
- TShock.CharacterDB.SeedInitialData(args.Player.Account);
- }
- }
-
- return false;
- }
-
private static bool HandlePlayerKillMeV2(GetDataHandlerArgs args)
{
var id = args.Data.ReadInt8();
@@ -2388,26 +2328,9 @@ namespace TShockAPI
var direction = (byte)(args.Data.ReadInt8() - 1);
BitsByte bits = (BitsByte)args.Data.ReadByte();
bool pvp = bits[0];
- if (dmg > 20000) //Abnormal values have the potential to cause infinite loops in the server.
- {
- TShock.Utils.ForceKick(args.Player, "Crash Exploit Attempt", true);
- TShock.Log.ConsoleError("Death Exploit Attempt: Damage {0}", dmg);
- return false;
- }
- if (id >= Main.maxPlayers)
- {
+ if (OnKillMe(args.Player, id, direction, dmg, pvp, playerDeathReason))
return true;
- }
-
- if (OnKillMe(id, direction, dmg, pvp))
- return true;
-
- if (playerDeathReason.GetDeathText(TShock.Players[id].Name).ToString().Length > 500)
- {
- TShock.Utils.Kick(TShock.Players[id], "Crash attempt", true);
- return true;
- }
args.Player.Dead = true;
args.Player.RespawnTimer = TShock.Config.RespawnSeconds;