3
0
Mirror von https://github.com/GeyserMC/Geyser.git synchronisiert 2024-11-19 14:30:17 +01:00

Expose emote stuff in API; different secure chat checking

This should fix false flags from secure chat disablers doing funky things.
Dieser Commit ist enthalten in:
Camotoy 2023-04-15 12:54:30 -04:00
Ursprung 0521fba1a8
Commit 48b796d75e
Es konnte kein GPG-Schlüssel zu dieser Signatur gefunden werden
GPG-Schlüssel-ID: 7EEFB66FE798081F
10 geänderte Dateien mit 115 neuen und 54 gelöschten Zeilen

Datei anzeigen

@ -25,11 +25,31 @@
package org.geysermc.geyser.api.connection; package org.geysermc.geyser.api.connection;
import org.checkerframework.checker.index.qual.NonNegative;
import org.checkerframework.checker.nullness.qual.NonNull;
import org.checkerframework.checker.nullness.qual.Nullable;
import org.geysermc.api.connection.Connection; import org.geysermc.api.connection.Connection;
import org.geysermc.geyser.api.command.CommandSource; import org.geysermc.geyser.api.command.CommandSource;
import org.geysermc.geyser.api.entity.type.GeyserEntity;
import org.geysermc.geyser.api.entity.type.player.GeyserPlayerEntity;
import java.util.concurrent.CompletableFuture;
/** /**
* Represents a player connection used in Geyser. * Represents a player connection used in Geyser.
*/ */
public interface GeyserConnection extends Connection, CommandSource { public interface GeyserConnection extends Connection, CommandSource {
/**
* @param javaId the Java entity ID to look up.
* @return a {@link GeyserEntity} if present in this connection's entity tracker.
*/
@NonNull
CompletableFuture<@Nullable GeyserEntity> entityByJavaId(@NonNegative int javaId);
/**
*
* @param emoter the player entity emoting.
* @param emoteId the emote ID to send to the client.
*/
void showEmote(@NonNull GeyserPlayerEntity emoter, @NonNull String emoteId);
} }

Datei anzeigen

@ -1,5 +1,5 @@
/* /*
* Copyright (c) 2019-2022 GeyserMC. http://geysermc.org * Copyright (c) 2019-2023 GeyserMC. http://geysermc.org
* *
* Permission is hereby granted, free of charge, to any person obtaining a copy * Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal * of this software and associated documentation files (the "Software"), to deal
@ -23,22 +23,18 @@
* @link https://github.com/GeyserMC/Geyser * @link https://github.com/GeyserMC/Geyser
*/ */
package org.geysermc.geyser.translator.protocol.java; package org.geysermc.geyser.api.entity.type;
import com.github.steveice10.mc.protocol.packet.ingame.clientbound.ClientboundServerDataPacket; import org.checkerframework.checker.index.qual.NonNegative;
import org.geysermc.geyser.api.util.TriState;
import org.geysermc.geyser.session.GeyserSession;
import org.geysermc.geyser.translator.protocol.PacketTranslator;
import org.geysermc.geyser.translator.protocol.Translator;
@Translator(packet = ClientboundServerDataPacket.class) /**
public class JavaServerDataTranslator extends PacketTranslator<ClientboundServerDataPacket> { * Represents a unique instance of an entity. Each {@link org.geysermc.geyser.api.connection.GeyserConnection}
* have their own sets of entities - no two instances will share the same GeyserEntity instance.
@Override */
public void translate(GeyserSession session, ClientboundServerDataPacket packet) { public interface GeyserEntity {
// We only want to warn about chat maybe not working once /**
if (packet.isEnforcesSecureChat() && session.getWorldCache().getChatWarningSent() == TriState.NOT_SET) { * @return the entity ID that the server has assigned to this entity.
session.getWorldCache().setChatWarningSent(TriState.FALSE); */
} @NonNegative
} int javaId();
} }

Datei anzeigen

@ -0,0 +1,31 @@
/*
* Copyright (c) 2019-2023 GeyserMC. http://geysermc.org
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*
* @author GeyserMC
* @link https://github.com/GeyserMC/Geyser
*/
package org.geysermc.geyser.api.entity.type.player;
import org.geysermc.geyser.api.entity.type.GeyserEntity;
public interface GeyserPlayerEntity extends GeyserEntity {
}

Datei anzeigen

@ -46,6 +46,7 @@ import org.cloudburstmc.protocol.bedrock.packet.MoveEntityAbsolutePacket;
import org.cloudburstmc.protocol.bedrock.packet.MoveEntityDeltaPacket; import org.cloudburstmc.protocol.bedrock.packet.MoveEntityDeltaPacket;
import org.cloudburstmc.protocol.bedrock.packet.RemoveEntityPacket; import org.cloudburstmc.protocol.bedrock.packet.RemoveEntityPacket;
import org.cloudburstmc.protocol.bedrock.packet.SetEntityDataPacket; import org.cloudburstmc.protocol.bedrock.packet.SetEntityDataPacket;
import org.geysermc.geyser.api.entity.type.GeyserEntity;
import org.geysermc.geyser.entity.EntityDefinition; import org.geysermc.geyser.entity.EntityDefinition;
import org.geysermc.geyser.entity.GeyserDirtyMetadata; import org.geysermc.geyser.entity.GeyserDirtyMetadata;
import org.geysermc.geyser.session.GeyserSession; import org.geysermc.geyser.session.GeyserSession;
@ -63,7 +64,7 @@ import java.util.UUID;
@Getter @Getter
@Setter @Setter
public class Entity { public class Entity implements GeyserEntity {
protected final GeyserSession session; protected final GeyserSession session;
protected int entityId; protected int entityId;
@ -509,6 +510,11 @@ public class Entity {
} }
} }
@Override
public int javaId() {
return entityId;
}
public boolean isAlive() { public boolean isAlive() {
return this.valid; return this.valid;
} }

Datei anzeigen

@ -44,6 +44,7 @@ import org.cloudburstmc.protocol.bedrock.data.entity.EntityDataTypes;
import org.cloudburstmc.protocol.bedrock.data.entity.EntityFlag; import org.cloudburstmc.protocol.bedrock.data.entity.EntityFlag;
import org.cloudburstmc.protocol.bedrock.data.entity.EntityLinkData; import org.cloudburstmc.protocol.bedrock.data.entity.EntityLinkData;
import org.cloudburstmc.protocol.bedrock.packet.*; import org.cloudburstmc.protocol.bedrock.packet.*;
import org.geysermc.geyser.api.entity.type.player.GeyserPlayerEntity;
import org.geysermc.geyser.entity.EntityDefinitions; import org.geysermc.geyser.entity.EntityDefinitions;
import org.geysermc.geyser.entity.type.Entity; import org.geysermc.geyser.entity.type.Entity;
import org.geysermc.geyser.entity.type.LivingEntity; import org.geysermc.geyser.entity.type.LivingEntity;
@ -64,7 +65,7 @@ import java.util.UUID;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
@Getter @Setter @Getter @Setter
public class PlayerEntity extends LivingEntity { public class PlayerEntity extends LivingEntity implements GeyserPlayerEntity {
public static final float SNEAKING_POSE_HEIGHT = 1.5f; public static final float SNEAKING_POSE_HEIGHT = 1.5f;
protected static final List<AbilityLayer> BASE_ABILITY_LAYER; protected static final List<AbilityLayer> BASE_ABILITY_LAYER;

Datei anzeigen

@ -63,8 +63,6 @@ import com.github.steveice10.packetlib.tcp.TcpSession;
import com.nimbusds.jwt.SignedJWT; import com.nimbusds.jwt.SignedJWT;
import io.netty.channel.Channel; import io.netty.channel.Channel;
import io.netty.channel.EventLoop; import io.netty.channel.EventLoop;
import it.unimi.dsi.fastutil.ints.Int2IntMap;
import it.unimi.dsi.fastutil.ints.Int2IntOpenHashMap;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap; import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import it.unimi.dsi.fastutil.ints.Int2ObjectOpenHashMap; import it.unimi.dsi.fastutil.ints.Int2ObjectOpenHashMap;
import it.unimi.dsi.fastutil.longs.Long2ObjectMap; import it.unimi.dsi.fastutil.longs.Long2ObjectMap;
@ -75,10 +73,12 @@ import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
import it.unimi.dsi.fastutil.objects.ObjectOpenHashSet; import it.unimi.dsi.fastutil.objects.ObjectOpenHashSet;
import lombok.AccessLevel; import lombok.AccessLevel;
import lombok.Getter; import lombok.Getter;
import lombok.NonNull;
import lombok.Setter; import lombok.Setter;
import lombok.experimental.Accessors; import lombok.experimental.Accessors;
import org.checkerframework.checker.index.qual.NonNegative;
import org.checkerframework.checker.nullness.qual.MonotonicNonNull; import org.checkerframework.checker.nullness.qual.MonotonicNonNull;
import org.checkerframework.checker.nullness.qual.NonNull;
import org.checkerframework.checker.nullness.qual.Nullable;
import org.checkerframework.common.value.qual.IntRange; import org.checkerframework.common.value.qual.IntRange;
import org.cloudburstmc.math.vector.*; import org.cloudburstmc.math.vector.*;
import org.cloudburstmc.nbt.NbtMap; import org.cloudburstmc.nbt.NbtMap;
@ -102,6 +102,8 @@ import org.geysermc.floodgate.util.BedrockData;
import org.geysermc.geyser.Constants; import org.geysermc.geyser.Constants;
import org.geysermc.geyser.GeyserImpl; import org.geysermc.geyser.GeyserImpl;
import org.geysermc.geyser.api.connection.GeyserConnection; import org.geysermc.geyser.api.connection.GeyserConnection;
import org.geysermc.geyser.api.entity.type.GeyserEntity;
import org.geysermc.geyser.api.entity.type.player.GeyserPlayerEntity;
import org.geysermc.geyser.api.network.AuthType; import org.geysermc.geyser.api.network.AuthType;
import org.geysermc.geyser.api.network.RemoteServer; import org.geysermc.geyser.api.network.RemoteServer;
import org.geysermc.geyser.command.GeyserCommandSource; import org.geysermc.geyser.command.GeyserCommandSource;
@ -1921,6 +1923,26 @@ public class GeyserSession implements GeyserConnection, GeyserCommandSource {
return true; return true;
} }
@Override
public @NonNull CompletableFuture<@Nullable GeyserEntity> entityByJavaId(@NonNegative int javaId) {
CompletableFuture<GeyserEntity> future = new CompletableFuture<>();
ensureInEventLoop(() -> future.complete(this.entityCache.getEntityByJavaId(javaId)));
return future;
}
@Override
public void showEmote(@NonNull GeyserPlayerEntity emoter, @NonNull String emoteId) {
Entity entity = (Entity) emoter;
if (entity.getSession() != this) {
throw new IllegalStateException("Given entity must be from this session!");
}
EmotePacket packet = new EmotePacket();
packet.setEmoteId(emoteId);
packet.setRuntimeEntityId(entity.getGeyserId());
sendUpstreamPacket(packet);
}
public void addCommandEnum(String name, String enums) { public void addCommandEnum(String name, String enums) {
softEnumPacket(name, SoftEnumUpdateType.ADD, enums); softEnumPacket(name, SoftEnumUpdateType.ADD, enums);
} }

Datei anzeigen

@ -26,15 +26,13 @@
package org.geysermc.geyser.session.cache; package org.geysermc.geyser.session.cache;
import com.github.steveice10.mc.protocol.data.game.setting.Difficulty; import com.github.steveice10.mc.protocol.data.game.setting.Difficulty;
import org.cloudburstmc.math.vector.Vector3i;
import org.cloudburstmc.protocol.bedrock.packet.SetTitlePacket;
import it.unimi.dsi.fastutil.objects.Object2IntMap; import it.unimi.dsi.fastutil.objects.Object2IntMap;
import it.unimi.dsi.fastutil.objects.Object2IntMaps; import it.unimi.dsi.fastutil.objects.Object2IntMaps;
import it.unimi.dsi.fastutil.objects.Object2IntOpenHashMap; import it.unimi.dsi.fastutil.objects.Object2IntOpenHashMap;
import lombok.Getter; import lombok.Getter;
import lombok.Setter; import lombok.Setter;
import org.checkerframework.checker.nullness.qual.NonNull; import org.cloudburstmc.math.vector.Vector3i;
import org.geysermc.geyser.api.util.TriState; import org.cloudburstmc.protocol.bedrock.packet.SetTitlePacket;
import org.geysermc.geyser.scoreboard.Scoreboard; import org.geysermc.geyser.scoreboard.Scoreboard;
import org.geysermc.geyser.scoreboard.ScoreboardUpdater.ScoreboardSession; import org.geysermc.geyser.scoreboard.ScoreboardUpdater.ScoreboardSession;
import org.geysermc.geyser.session.GeyserSession; import org.geysermc.geyser.session.GeyserSession;
@ -63,17 +61,6 @@ public final class WorldCache {
private int currentSequence; private int currentSequence;
private final Object2IntMap<Vector3i> unverifiedPredictions = new Object2IntOpenHashMap<>(1); private final Object2IntMap<Vector3i> unverifiedPredictions = new Object2IntOpenHashMap<>(1);
/**
* <ul>
* <li>NOT_SET = not yet triggered</li>
* <li>FALSE = enforce-secure-profile is true but player hasn't chatted yet</li>
* <li>TRUE = enforce-secure-profile is enabled, and player has chatted and they have seen our message.</li>
* </ul>
*/
@Getter
@Setter
private @NonNull TriState chatWarningSent = TriState.NOT_SET;
public WorldCache(GeyserSession session) { public WorldCache(GeyserSession session) {
this.session = session; this.session = session;
this.scoreboard = new Scoreboard(session); this.scoreboard = new Scoreboard(session);

Datei anzeigen

@ -26,9 +26,7 @@
package org.geysermc.geyser.translator.protocol.bedrock; package org.geysermc.geyser.translator.protocol.bedrock;
import org.cloudburstmc.protocol.bedrock.packet.TextPacket; import org.cloudburstmc.protocol.bedrock.packet.TextPacket;
import org.geysermc.geyser.api.util.TriState;
import org.geysermc.geyser.session.GeyserSession; import org.geysermc.geyser.session.GeyserSession;
import org.geysermc.geyser.text.GeyserLocale;
import org.geysermc.geyser.translator.protocol.PacketTranslator; import org.geysermc.geyser.translator.protocol.PacketTranslator;
import org.geysermc.geyser.translator.protocol.Translator; import org.geysermc.geyser.translator.protocol.Translator;
import org.geysermc.geyser.translator.text.MessageTranslator; import org.geysermc.geyser.translator.text.MessageTranslator;
@ -49,15 +47,6 @@ public class BedrockTextTranslator extends PacketTranslator<TextPacket> {
return; return;
} }
if (session.getWorldCache().getChatWarningSent() == TriState.FALSE) {
if (Boolean.parseBoolean(System.getProperty("Geyser.PrintSecureChatInformation", "true"))) {
session.sendMessage(GeyserLocale.getPlayerLocaleString("geyser.chat.secure_info_1", session.locale()));
session.sendMessage(GeyserLocale.getPlayerLocaleString("geyser.chat.secure_info_2", session.locale(), "https://geysermc.link/secure-chat"));
}
// Never send this message again for this session.
session.getWorldCache().setChatWarningSent(TriState.TRUE);
}
session.sendChat(message); session.sendChat(message);
} }
} }

Datei anzeigen

@ -29,6 +29,7 @@ import org.cloudburstmc.protocol.bedrock.packet.EmotePacket;
import org.geysermc.geyser.api.event.bedrock.ClientEmoteEvent; import org.geysermc.geyser.api.event.bedrock.ClientEmoteEvent;
import org.geysermc.geyser.configuration.EmoteOffhandWorkaroundOption; import org.geysermc.geyser.configuration.EmoteOffhandWorkaroundOption;
import org.geysermc.geyser.entity.type.Entity; import org.geysermc.geyser.entity.type.Entity;
import org.geysermc.geyser.entity.type.player.PlayerEntity;
import org.geysermc.geyser.session.GeyserSession; import org.geysermc.geyser.session.GeyserSession;
import org.geysermc.geyser.translator.protocol.PacketTranslator; import org.geysermc.geyser.translator.protocol.PacketTranslator;
import org.geysermc.geyser.translator.protocol.Translator; import org.geysermc.geyser.translator.protocol.Translator;
@ -61,7 +62,7 @@ public class BedrockEmoteTranslator extends PacketTranslator<EmotePacket> {
if (otherSession.getEventLoop().inEventLoop()) { if (otherSession.getEventLoop().inEventLoop()) {
playEmote(otherSession, javaId, packet.getEmoteId()); playEmote(otherSession, javaId, packet.getEmoteId());
} else { } else {
session.executeInEventLoop(() -> playEmote(otherSession, javaId, packet.getEmoteId())); otherSession.executeInEventLoop(() -> playEmote(otherSession, javaId, packet.getEmoteId()));
} }
} }
} }
@ -69,10 +70,7 @@ public class BedrockEmoteTranslator extends PacketTranslator<EmotePacket> {
private void playEmote(GeyserSession otherSession, int javaId, String emoteId) { private void playEmote(GeyserSession otherSession, int javaId, String emoteId) {
Entity otherEntity = otherSession.getEntityCache().getEntityByJavaId(javaId); // Must be ran on same thread Entity otherEntity = otherSession.getEntityCache().getEntityByJavaId(javaId); // Must be ran on same thread
if (otherEntity == null) return; if (!(otherEntity instanceof PlayerEntity otherPlayer)) return;
EmotePacket otherEmotePacket = new EmotePacket(); otherSession.showEmote(otherPlayer, emoteId);
otherEmotePacket.setEmoteId(emoteId);
otherEmotePacket.setRuntimeEntityId(otherEntity.getGeyserId());
otherSession.sendUpstreamPacket(otherEmotePacket);
} }
} }

Datei anzeigen

@ -26,8 +26,10 @@
package org.geysermc.geyser.translator.protocol.java; package org.geysermc.geyser.translator.protocol.java;
import com.github.steveice10.mc.protocol.packet.ingame.clientbound.ClientboundSystemChatPacket; import com.github.steveice10.mc.protocol.packet.ingame.clientbound.ClientboundSystemChatPacket;
import net.kyori.adventure.text.TranslatableComponent;
import org.cloudburstmc.protocol.bedrock.packet.TextPacket; import org.cloudburstmc.protocol.bedrock.packet.TextPacket;
import org.geysermc.geyser.session.GeyserSession; import org.geysermc.geyser.session.GeyserSession;
import org.geysermc.geyser.text.GeyserLocale;
import org.geysermc.geyser.translator.protocol.PacketTranslator; import org.geysermc.geyser.translator.protocol.PacketTranslator;
import org.geysermc.geyser.translator.protocol.Translator; import org.geysermc.geyser.translator.protocol.Translator;
import org.geysermc.geyser.translator.text.MessageTranslator; import org.geysermc.geyser.translator.text.MessageTranslator;
@ -37,6 +39,15 @@ public class JavaSystemChatTranslator extends PacketTranslator<ClientboundSystem
@Override @Override
public void translate(GeyserSession session, ClientboundSystemChatPacket packet) { public void translate(GeyserSession session, ClientboundSystemChatPacket packet) {
if (packet.getContent() instanceof TranslatableComponent component && component.key().equals("chat.disabled.missingProfileKey")) {
// We likely got this message as a response to a player trying to chat
// As there SHOULD be no false flags for this, print every time it shows up in chat.
if (Boolean.parseBoolean(System.getProperty("Geyser.PrintSecureChatInformation", "true"))) {
session.sendMessage(GeyserLocale.getPlayerLocaleString("geyser.chat.secure_info_1", session.locale()));
session.sendMessage(GeyserLocale.getPlayerLocaleString("geyser.chat.secure_info_2", session.locale(), "https://geysermc.link/secure-chat"));
}
}
TextPacket textPacket = new TextPacket(); TextPacket textPacket = new TextPacket();
textPacket.setPlatformChatId(""); textPacket.setPlatformChatId("");
textPacket.setSourceName(""); textPacket.setSourceName("");