/** * Guess some last-action time, likely to be replaced with centralized PlayerData use. * * @param player * @param Timestamp of the moment of calling this. * @param maxAge Maximum age in milliseconds. * @return Return timestamp or Long.MIN_VALUE if not possible or beyond maxAge. */ public static final long guessKeepAliveTime( final Player player, final long now, final long maxAge) { final int tick = TickTask.getTick(); long ref = Long.MIN_VALUE; // Estimate last fight action time (important for gode modes). final FightData fData = FightData.getData(player); ref = Math.max(ref, fData.speedBuckets.lastUpdate()); ref = Math.max(ref, now - 50L * (tick - fData.lastAttackTick)); // Ignore lag. // Health regain (not unimportant). ref = Math.max(ref, fData.regainHealthTime); // Move time. ref = Math.max(ref, CombinedData.getData(player).lastMoveTime); // Inventory. final InventoryData iData = InventoryData.getData(player); ref = Math.max(ref, iData.lastClickTime); ref = Math.max(ref, iData.instantEatInteract); // BlcokBreak/interact. final BlockBreakData bbData = BlockBreakData.getData(player); ref = Math.max(ref, bbData.frequencyBuckets.lastUpdate()); ref = Math.max(ref, bbData.fastBreakfirstDamage); // TODO: More, less ... if (ref > now || ref < now - maxAge) { return Long.MIN_VALUE; } return ref; }
@EventHandler(priority = EventPriority.LOWEST) public void onPlayerJoin(final PlayerJoinEvent event) { final Player player = event.getPlayer(); lastLogout.remove(player.getName()); CombinedData.getData(player).lastJoinTime = System.currentTimeMillis(); addOnlinePlayer(player); }
private boolean checkImprobable(final Player player, final float weight, final long now) { if (!isEnabled(player)) return false; final CombinedData data = CombinedData.getData(player); final CombinedConfig cc = CombinedConfig.getConfig(player); data.improbableCount.add(now, weight); final float shortTerm = data.improbableCount.bucketScore(0); double violation = 0; boolean violated = false; if (shortTerm * 0.8f > cc.improbableLevel / 20.0) { final float lag = cc.lag ? TickTask.getLag(data.improbableCount.bucketDuration(), true) : 1f; if (shortTerm / lag > cc.improbableLevel / 20.0) { violation += shortTerm * 2d / lag; violated = true; } } final double full = data.improbableCount.score(1.0f); if (full > cc.improbableLevel) { final float lag = cc.lag ? TickTask.getLag( data.improbableCount.bucketDuration() * data.improbableCount.numberOfBuckets(), true) : 1f; if (full / lag > cc.improbableLevel) { violation += full / lag; violated = true; } } boolean cancel = false; if (violated) { // Execute actions data.improbableVL += violation / 10.0; cancel = executeActions(player, data.improbableVL, violation / 10.0, cc.improbableActions); } else data.improbableVL *= 0.95; return cancel; }
/** * Quit or kick. * * @param player */ private final void onLeave(final Player player) { final long now = System.currentTimeMillis(); lastLogout.put(player.getName(), now); CombinedData.getData(player).lastLogoutTime = now; }
@Override public ICheckData removeData(final String playerName) { return CombinedData.removeData(playerName); }
@Override public final ICheckData getData(final Player player) { return CombinedData.getData(player); }
/** * Feed the check but no violations processing (convenience method). * * @param player * @param weight * @param now */ public static final void feed(final Player player, final float weight, final long now) { CombinedData.getData(player).improbableCount.add(now, weight); }