Compare commits

..
10 Commits
Author SHA1 Message Date
unknown fa70848c0e testexample unregistered 2020-04-21 16:01:47 +02:00
unknown 0274014768 Packet cancelling and enums added, reflection usage added 2020-04-21 16:01:00 +02:00
unknown 44ebf50956 pom.xml changes 2020-04-21 09:35:11 +02:00
unknown 009fe731a3 ServerTickEvent added 2020-04-20 14:54:41 +02:00
unknown b4c28e53d4 pom.xml errors fixed 2020-04-20 08:16:23 +02:00
unknown 8aa8a99909 Bugs fixed and testexample improved 2020-04-20 08:07:42 +02:00
unknown 2916e57d20 TestExample improved and bugs fixed! 2020-04-20 08:06:34 +02:00
purplex 6d0a4c07c6 Merge pull request #1 from purpdev/dependabot/maven/io.netty-netty-all-4.1.42.Final
Bump netty-all from 4.0.23.Final to 4.1.42.Final
2020-04-18 19:18:50 +02:00
unknown 7a3db02214 TinyProtocol example removed, bugs fixed, testexample is no longer registered 2020-04-17 14:59:05 +02:00
dependabot[bot] 652ba2d41c Bump netty-all from 4.0.23.Final to 4.1.42.Final
Bumps [netty-all](https://github.com/netty/netty) from 4.0.23.Final to 4.1.42.Final.
- [Release notes](https://github.com/netty/netty/releases)
- [Commits](https://github.com/netty/netty/compare/netty-4.0.23.Final...netty-4.1.42.Final)

Signed-off-by: dependabot[bot] <support@github.com>
2020-04-17 12:50:48 +00:00
20 changed files with 443 additions and 213 deletions

No files matched your search

+4 -7
View File
@@ -6,7 +6,7 @@
<groupId>me.retrooper</groupId>
<artifactId>packetevents</artifactId>
<version>1.0-SNAPSHOT</version>
<version>1.0.3</version>
<packaging>jar</packaging>
<name>PacketEvents</name>
@@ -54,10 +54,6 @@
</build>
<repositories>
<repository>
<id>jitpack.io</id>
<url>https://jitpack.io</url>
</repository>
<repository>
<id>spigot-repo</id>
<url>https://hub.spigotmc.org/nexus/content/groups/public/</url>
@@ -73,12 +69,13 @@
<groupId>com.mojang</groupId>
<artifactId>authlib</artifactId>
<version>1.5.21</version>
<scope>compile</scope>
</dependency>
<!-- https://mvnrepository.com/artifact/io.netty/netty-all -->
<dependency>
<groupId>io.netty</groupId>
<artifactId>netty-all</artifactId>
<version>4.0.23.Final</version>
<version>4.1.42.Final</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.bukkit</groupId>
@@ -1,114 +0,0 @@
package com.comphenix.tinyprotocol;
import io.netty.channel.Channel;
import org.bukkit.*;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import org.bukkit.plugin.java.JavaPlugin;
import com.comphenix.tinyprotocol.Reflection.*;
/**
* Represents an example plugin utilizing TinyProtocol
*/
public class ExamplePlugin extends JavaPlugin {
// Chat packets
private FieldAccessor<String> CHAT_MESSAGE = Reflection.getField("{nms}.PacketPlayInChat", String.class, 0);
// Explosion packet
private Class<?> particleClass = Reflection.getClass("{nms}.PacketPlayOutWorldParticles");
private FieldAccessor<String> particleName = Reflection.getField(particleClass, String.class, 0);
private FieldAccessor<Float> particleX = Reflection.getField(particleClass, float.class, 0);
private FieldAccessor<Float> particleY = Reflection.getField(particleClass, float.class, 1);
private FieldAccessor<Float> particleZ = Reflection.getField(particleClass, float.class, 2);
private FieldAccessor<Integer> particleCount = Reflection.getField(particleClass, int.class, 0);
// Server info packet
private Class<?> serverInfoClass = Reflection.getClass("{nms}.PacketStatusOutServerInfo");
private Class<Object> serverPingClass = Reflection.getUntypedClass("{nms}.ServerPing");
private Class<Object> playerSampleClass = Reflection.getUntypedClass("{nms}.ServerPingPlayerSample");
private FieldAccessor<Object> serverPing = Reflection.getField(serverInfoClass, serverPingClass, 0);
private FieldAccessor<Object> playerSample = Reflection.getField(serverPingClass, playerSampleClass, 0);
private ConstructorInvoker playerSampleInvoker = Reflection.getConstructor(playerSampleClass, int.class, int.class);
private TinyProtocol protocol;
@Override
public void onEnable() {
protocol = new TinyProtocol(this) {
@Override
public Object onPacketInAsync(Player sender, Channel channel, Object packet) {
// Cancel chat packets
if (CHAT_MESSAGE.hasField(packet)) {
if (CHAT_MESSAGE.get(packet).contains("dirty")) {
sendExplosion(sender);
return null;
}
}
if (particleName.hasField(packet)) {
System.out.println("Sending particle field:" + packet);
}
return super.onPacketInAsync(sender, channel, packet);
}
@Override
public Object onPacketOutAsync(Player reciever, Channel channel, Object packet) {
if (serverInfoClass.isInstance(packet)) {
Object ping = serverPing.get(packet);
playerSample.set(ping, playerSampleInvoker.invoke(1000, 0));
// Which is equivalent to:
// serverPing.get(packet).setPlayerSample(new ServerPingPlayerSample(1000, 0));
return packet;
}
return super.onPacketOutAsync(reciever, channel, packet);
}
};
}
@Override
public boolean onCommand(CommandSender sender, Command command, String label, String[] args) {
if (sender instanceof Player) {
Player player = (Player) sender;
// Toggle injection
if (protocol.hasInjected(player)) {
protocol.uninjectPlayer(player);
sender.sendMessage(ChatColor.YELLOW + "Player " + player + " has been uninjected.");
} else {
protocol.injectPlayer(player);
sender.sendMessage(ChatColor.DARK_GREEN + "Player " + player + " has been injected.");
}
return true;
} else {
sender.sendMessage(ChatColor.RED + "Can only be invoked by a player.");
}
return false;
}
private void sendExplosion(Player player) {
try {
// Only visible for the client
Object explosionPacket = particleClass.newInstance();
Location loc = player.getLocation();
particleName.set(explosionPacket, "hugeexplosion");
particleX.set(explosionPacket, (float) loc.getX());
particleY.set(explosionPacket, (float) loc.getY());
particleZ.set(explosionPacket, (float) loc.getZ());
particleCount.set(explosionPacket, 1);
// Send the packet to the player
protocol.sendPacket(player, explosionPacket);
} catch (Exception e) {
throw new RuntimeException("Cannot send packet.", e);
}
}
}
@@ -2,8 +2,9 @@ package me.purplex.packetevents;
import com.comphenix.tinyprotocol.*;
import io.netty.channel.Channel;
import me.purplex.packetevents.events.PacketReceiveEvent;
import me.retrooper.packetevents.events.*;
import me.purplex.packetevents.events.packetevent.PacketSendEvent;
import me.purplex.packetevents.events.packetevent.ServerTickEvent;
import me.purplex.packetevents.events.packetevent.PacketReceiveEvent;
import me.purplex.packetevents.example.TestExample;
import org.bukkit.Bukkit;
import org.bukkit.entity.Player;
@@ -16,7 +17,7 @@ public class Main extends JavaPlugin implements Listener {
@Override
public void onEnable() {
Bukkit.getPluginManager().registerEvents(this, this);
PacketEvents.getPacketManager().registerPacketListener(new TestExample());
//PacketEvents.getPacketManager().registerPacketListener(new TestExample());
protocol = new TinyProtocol(this) {
@Override
public Object onPacketInAsync(Player p, Channel channel, Object packet) {
@@ -24,7 +25,11 @@ public class Main extends JavaPlugin implements Listener {
if(p == null) return super.onPacketInAsync(null, channel, packet);
if(channel == null) return super.onPacketInAsync(p, null, packet);
String packetName = packet.getClass().getSimpleName();
PacketEvents.getPacketManager().callPacketReceiveEvent(new PacketReceiveEvent(p, packetName, packet));
PacketReceiveEvent e = new PacketReceiveEvent(p, packetName, packet);
PacketEvents.getPacketManager().callPacketReceiveEvent(e);
if(e.isCancelled()) {
return super.onPacketInAsync(null, null, null);
}
return super.onPacketInAsync(p, channel, packet);
}
@@ -34,11 +39,23 @@ public class Main extends JavaPlugin implements Listener {
if(p == null) return super.onPacketInAsync(null, channel, packet);
if(channel == null) return super.onPacketInAsync(p, null, packet);
String packetName = packet.getClass().getSimpleName();
PacketEvents.getPacketManager().callPacketReceiveEvent(new PacketReceiveEvent(p, packetName, packet));
PacketSendEvent e = new PacketSendEvent(p, packetName, packet);
PacketEvents.getPacketManager().callPacketSendEvent(e);
if(e.isCancelled()) {
return super.onPacketOutAsync(null, null, null);
}
return super.onPacketOutAsync(p, channel, packet);
}
};
Bukkit.getScheduler().scheduleAsyncRepeatingTask(this, new Runnable() {
@Override
public void run() {
long now = System.currentTimeMillis();
PacketEvents.getPacketManager().callServerTickEvent(new ServerTickEvent(now));
}
}, 0L, 1L);
}
@Override
public void onDisable() {
@@ -1,6 +1,6 @@
package me.purplex.packetevents;
import me.purplex.packetevents.events.PacketManager;
import me.purplex.packetevents.events.manager.PacketManager;
public class PacketEvents {
private static PacketManager packetManager;
@@ -0,0 +1,5 @@
package me.purplex.packetevents.enums;
public enum EntityUseAction {
INTERACT, INTERACT_AT, ATTACK, INVALID, WRONG_PACKET;
}
@@ -0,0 +1,21 @@
package me.purplex.packetevents.enums;
public enum PlayerAction {
START_SNEAKING,
STOP_SNEAKING,
STOP_SLEEPING,
START_SPRINTING,
STOP_SPRINTING,
START_RIDING_JUMP,
STOP_RIDING_JUMP,
OPEN_INVENTORY,
START_FALL_FLYING, WRONG_PACKET;
}
@@ -0,0 +1,23 @@
package me.purplex.packetevents.enums;
public enum PlayerDigType {
START_DESTROY_BLOCK,
ABORT_DESTROY_BLOCK,
STOP_DESTROY_BLOCK,
DROP_ALL_ITEMS,
DROP_ITEM,
RELEASE_USE_ITEM,
SWAP_HELD_ITEMS,
WRONG_PACKET;
}
@@ -1,4 +0,0 @@
package me.purplex.packetevents.events;
public interface PacketListener {
}
@@ -1,34 +0,0 @@
package me.purplex.packetevents.events;
import org.bukkit.entity.Player;
public class PacketReceiveEvent extends PacketEvent {
private Player player;
private String name;
private Object packet;
private long timestamp;
public PacketReceiveEvent(Player player, String packetName, Object packet) {
this.player = player;
this.name = packetName;
this.packet = packet;
this.timestamp = (System.nanoTime() / 1000000);
}
public Player getPlayer() {
return this.player;
}
public String getPacketName() {
return this.name;
}
public Object getPacket() {
return this.packet;
}
public long getTimestamp() {
return timestamp;
}
}
@@ -1,35 +0,0 @@
package me.purplex.packetevents.events;
import org.bukkit.entity.Player;
public class PacketSendEvent extends PacketEvent {
private Player player;
private String name;
private Object packet;
private long timestamp;
public PacketSendEvent(Player player, String packetName, Object packet) {
this.player = player;
this.name = packetName;
this.packet = packet;
this.timestamp = (System.nanoTime() / 1000000);
}
public Player getPlayer() {
return this.player;
}
public String getPacketName() {
return this.name;
}
public Object getPacket() {
return this.packet;
}
public long getTimestamp() {
return timestamp;
}
}
@@ -1,4 +1,9 @@
package me.purplex.packetevents.events;
package me.purplex.packetevents.events.eventmanager;
import me.purplex.packetevents.events.packetevent.ServerTickEvent;
import me.purplex.packetevents.events.listener.PacketListener;
import me.purplex.packetevents.events.packetevent.PacketReceiveEvent;
import me.purplex.packetevents.events.packetevent.PacketSendEvent;
import java.util.LinkedList;
@@ -10,4 +15,6 @@ public interface PacketEventManager {
public void registerPacketListener(PacketListener e);
public void callServerTickEvent(ServerTickEvent e);
}
@@ -1,6 +1,4 @@
package me.purplex.packetevents.events;
import org.bukkit.event.EventHandler;
package me.purplex.packetevents.events.handler;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
@@ -0,0 +1,4 @@
package me.purplex.packetevents.events.listener;
public interface PacketListener {
}
@@ -1,4 +1,11 @@
package me.purplex.packetevents.events;
package me.purplex.packetevents.events.manager;
import me.purplex.packetevents.events.packetevent.ServerTickEvent;
import me.purplex.packetevents.events.eventmanager.PacketEventManager;
import me.purplex.packetevents.events.handler.PacketHandler;
import me.purplex.packetevents.events.listener.PacketListener;
import me.purplex.packetevents.events.packetevent.PacketReceiveEvent;
import me.purplex.packetevents.events.packetevent.PacketSendEvent;
import java.lang.reflect.Method;
@@ -44,4 +51,22 @@ public class PacketManager implements PacketEventManager {
public void registerPacketListener(PacketListener e) {
this.packetListeners.add(e);
}
@Override
public void callServerTickEvent(ServerTickEvent e) {
for (PacketListener listener : this.packetListeners) {
Method[] methods = listener.getClass().getMethods();
for (Method m : methods) {
if (m.isAnnotationPresent(PacketHandler.class)) {
if (m.getParameterTypes()[0].getSimpleName().equals(e.getClass().getSimpleName())) {
try {
m.invoke(listener, e);
} catch (Exception ex) {
}
}
}
}
}
}
}
@@ -0,0 +1,148 @@
package me.purplex.packetevents.events.packetevent;
import com.comphenix.tinyprotocol.Reflection;
import com.comphenix.tinyprotocol.Reflection.*;
import me.purplex.packetevents.enums.EntityUseAction;
import me.purplex.packetevents.enums.PlayerAction;
import me.purplex.packetevents.enums.PlayerDigType;
import me.purplex.packetevents.events.PacketEvent;
import org.apache.commons.lang3.reflect.FieldUtils;
import org.bukkit.Bukkit;
import org.bukkit.World;
import org.bukkit.entity.*;
public class PacketReceiveEvent extends PacketEvent {
private Player player;
private String name;
private Object packet;
private long timestamp;
private boolean cancelled;
public PacketReceiveEvent(Player player, String packetName, Object packet) {
this.player = player;
this.name = packetName;
this.packet = packet;
this.timestamp = (System.nanoTime() / 1000000);
this.cancelled = false;
}
public Player getPlayer() {
return this.player;
}
public String getPacketName() {
return this.name;
}
public Object getPacket() {
return this.packet;
}
public long getTimestamp() {
return timestamp;
}
public void setCancelled(boolean cancelled) {
this.cancelled = cancelled;
}
public boolean isCancelled() {
return cancelled;
}
/**
* Get the type of dig
* PacketPlayInBlockDig
* @return
*/
public PlayerDigType getPlayerDigType() {
String c = String.valueOf(Reflection.getMethod(packet.getClass(), "c").invoke(packet));
PlayerDigType type;
try {
type = PlayerDigType.valueOf(c);
} catch (IllegalArgumentException e) {
type = PlayerDigType.WRONG_PACKET;
}
return type;
}
/**
* Get the entity interact action
* PacketPlayInUseEntity
* @return
*/
public EntityUseAction getEntityUseAction() {
Object action = null;
try {
action = FieldUtils.readDeclaredField(packet, "action", true);
} catch (IllegalAccessException e) {
e.printStackTrace();
}
for (EntityUseAction a : EntityUseAction.values()) {
if (a.toString().equalsIgnoreCase(action.toString())) {
return a;
}
}
return EntityUseAction.WRONG_PACKET;
}
/**
* Get the PlayerAction
* PacketPlayInEntityAction
* @return
*/
public PlayerAction getPlayerAction() {
Object animation = null;
try {
animation = FieldUtils.readDeclaredField(packet, "animation", true);
} catch (IllegalAccessException e) {
e.printStackTrace();
}
for (PlayerAction a : PlayerAction.values()) {
if (a.toString().equalsIgnoreCase(animation.toString())) {
return a;
}
}
return PlayerAction.WRONG_PACKET;
}
/**
* Entity you interacted with
* PacketPlayInUseEntity
* @return
*/
public Entity getInteractedEntity() {
try {
FieldAccessor<Integer> field = Reflection.getField(packet.getClass(), int.class, 0);
int id = field.get(packet);
for (Entity e : player.getWorld().getEntities()) {
if (e.getEntityId() == id) {
return e;
}
}
for(World w : Bukkit.getWorlds()) {
for(Entity e : w.getEntities()) {
if(e.getEntityId() == id) {
return e;
}
}
}
} catch (Exception ex) {
}
return null;
}
/**
* Get the string message
* PacketPlayInChat
* @return
*/
public String getChatPacketMessage() {
FieldAccessor<String> field = Reflection.getField(packet.getClass(), String.class, 0);
String message = field.get(packet);
return message;
}
}
@@ -0,0 +1,109 @@
package me.purplex.packetevents.events.packetevent;
import com.comphenix.tinyprotocol.Reflection;
import com.comphenix.tinyprotocol.Reflection.*;
import me.purplex.packetevents.events.PacketEvent;
import org.bukkit.Bukkit;
import org.bukkit.World;
import org.bukkit.entity.Entity;
import org.bukkit.entity.Player;
public class PacketSendEvent extends PacketEvent {
private Player player;
private String name;
private Object packet;
private long timestamp;
private boolean cancelled;
public PacketSendEvent(Player player, String packetName, Object packet) {
this.player = player;
this.name = packetName;
this.packet = packet;
this.timestamp = (System.nanoTime() / 1000000);
this.cancelled = false;
}
public Player getPlayer() {
return this.player;
}
public String getPacketName() {
return this.name;
}
public Object getPacket() {
return this.packet;
}
public long getTimestamp() {
return timestamp;
}
public void setCancelled(boolean cancelled) {
this.cancelled = cancelled;
}
public boolean isCancelled() {
return cancelled;
}
/**
* Get Velocity entity
* PacketPlayOutEntityVelocity
* @return
*/
public Entity getVelocityEntity() {
//WorldServer s;
FieldAccessor<Integer> field = Reflection.getField(packet.getClass(), int.class, 0);
int id = field.get(packet);
for(World w : Bukkit.getWorlds()) {
for(Entity e : w.getEntities()) {
if(e.getEntityId() == id) {
return e;
}
}
}
return null;
}
/**
* Get X velocity
* PacketPlayOutEntityVelocity
* @return x
*/
public double getVelocityX() {
FieldAccessor<Integer> field = Reflection.getField(packet.getClass(), int.class, 1);
int i = field.get(packet);
double x = i / 8000.0;
return x;
}
/**
* Get Y velocity
* PacketPlayOutEntityVelocity
* @return y
*/
public double getVelocityY() {
FieldAccessor<Integer> field = Reflection.getField(packet.getClass(), int.class, 2);
int i = field.get(packet);
double y = i / 8000.0;
return y;
}
/**
* Get Z velocity
* PacketPlayOutEntityVelocity
* @return z
*/
public double getVelocityZ() {
FieldAccessor<Integer> field = Reflection.getField(packet.getClass(), int.class, 3);
int i = field.get(packet);
double z = i / 8000.0;
return z;
}
}
@@ -0,0 +1,19 @@
package me.purplex.packetevents.events.packetevent;
import me.purplex.packetevents.events.PacketEvent;
public class ServerTickEvent extends PacketEvent {
private long timestamp;
public ServerTickEvent(long timestamp) {
this.timestamp = timestamp;
}
public long getTimestamp() {
return timestamp;
}
}
@@ -1,22 +1,64 @@
package me.purplex.packetevents.example;
import me.purplex.packetevents.events.PacketHandler;
import me.purplex.packetevents.events.PacketListener;
import me.purplex.packetevents.events.PacketReceiveEvent;
import me.purplex.packetevents.events.PacketSendEvent;
import me.purplex.packetevents.enums.EntityUseAction;
import me.purplex.packetevents.enums.PlayerAction;
import me.purplex.packetevents.enums.PlayerDigType;
import me.purplex.packetevents.events.packetevent.ServerTickEvent;
import me.purplex.packetevents.events.handler.PacketHandler;
import me.purplex.packetevents.events.listener.PacketListener;
import me.purplex.packetevents.events.packetevent.PacketReceiveEvent;
import me.purplex.packetevents.events.packetevent.PacketSendEvent;
import me.purplex.packetevents.packets.Packet;
import me.retrooper.packetevents.events.*;
import org.bukkit.Bukkit;
import org.bukkit.entity.Entity;
import org.bukkit.entity.Player;
import org.bukkit.inventory.ItemStack;
public class TestExample implements PacketListener {
/**
* How to register a packet listener?
* <p>
* PacketEvents.getPacketManager().registerPacketListener(new TestExample());
*/
private int tick;
@PacketHandler
public void onPacketReceive(PacketReceiveEvent e) {
if (e.getPacketName().equals(Packet.Client.POSITION)) {
e.getPlayer().sendMessage("You sent a position packet!");
//ONLY CLIENT PACKETS ALLOWED HERE!
if (e.getPacketName().equals(Packet.Client.USE_ENTITY)) {
Entity entity = e.getInteractedEntity();
EntityUseAction entityUseAction = e.getEntityUseAction();
e.getPlayer().sendMessage("Dist: " + entity.getLocation().distanceSquared(e.getPlayer().getLocation()));
} else if (e.getPacketName().equals(Packet.Client.ARM_ANIMATION)) {
e.getPlayer().sendMessage("You swung your arm.");
} else if (e.getPacketName().equals(Packet.Client.BLOCK_DIG)) {
PlayerDigType type = e.getPlayerDigType();
} else if (e.getPacketName().equals(Packet.Client.CHAT)) {
String message = e.getChatPacketMessage();
}
}
@PacketHandler
public void onPacketSend(PacketSendEvent e) {
//ONLY SERVER PACKETS ALLOWED HERE!
if (e.getPacketName().equals(Packet.Server.ENTITY_VELOCITY)) {
System.out.println("preee");
Entity entity = e.getVelocityEntity();
System.out.println(entity.getName());
System.out.println(e.getVelocityX());
}
}
@PacketHandler
public void onServerTick(ServerTickEvent e) {
//CALLED EVERY TICK
tick++;
if (tick % 20 == 0) {
for (Player p : Bukkit.getOnlinePlayers()) {
p.sendMessage("One second has passed!");
}
}
}
}
@@ -4,6 +4,8 @@ public abstract class Packet {
public static class Client {
private static final String CLIENT = "PacketPlayIn";
public static final String KEEP_ALIVE = CLIENT + "KeepAlive";
@Deprecated
public static final String FLYING = CLIENT + "Flying";
public static final String POSITION = CLIENT + "Position";
public static final String POSITION_LOOK = CLIENT + "PositionLook";
+1 -1
View File
@@ -1,4 +1,4 @@
name: PacketEvents
version: ${project.version}
main: me.retrooper.packetevents.Main
main: me.purplex.packetevents.Main
authors: [purplex]