Skip to content

Commit

Permalink
MultiClientingService exclusion config
Browse files Browse the repository at this point in the history
  • Loading branch information
neon-dev committed Nov 24, 2024
1 parent c73eb23 commit f124a5a
Show file tree
Hide file tree
Showing 3 changed files with 30 additions and 3 deletions.
3 changes: 3 additions & 0 deletions game-server/config/main/security.properties
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,9 @@ gameserver.security.survey.delay.minute = 20
# SAME_FACTION - Players are allowed to log in multiple accounts per computer, but only log in characters of the same faction
gameserver.security.multi_clienting.restriction_mode = NONE

# Comma separated list of MAC addresses that are allowed to log in regardless of the configured restrictions.
gameserver.security.multi_clienting.ignored_mac_addresses =

# If multi-clienting is restricted to the same faction, logging in characters of one faction will be denied until all characters of the opposite
# faction have been offline for the specified amount of time.
gameserver.security.multi_clienting.faction_switch_cooldown_minutes = 20
Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
package com.aionemu.gameserver.configs.main;

import java.util.Set;

import com.aionemu.commons.configuration.Property;

public class SecurityConfig {

@Property(key = "gameserver.security.aion.bin.check", defaultValue = "false")
public static boolean AION_BIN_CHECK;

Expand Down Expand Up @@ -70,9 +72,25 @@ public class SecurityConfig {
@Property(key = "gameserver.security.survey.delay.minute", defaultValue = "20")
public static int SURVEY_DELAY;

/**
* Restriction mode for multi-clienting:<br>
* NONE - Players are allowed to log in multiple accounts per computer<br>
* FULL - Players are allowed to log in one account per computer<br>
* SAME_FACTION - Players are allowed to log in multiple accounts per computer, but only log in characters of the same faction<br>
*/
@Property(key = "gameserver.security.multi_clienting.restriction_mode", defaultValue = "NONE")
public static MultiClientingRestrictionMode MULTI_CLIENTING_RESTRICTION_MODE;

/**
* Comma separated list of MAC addresses that are allowed to log in regardless of the configured restrictions.
*/
@Property(key = "gameserver.security.multi_clienting.ignored_mac_addresses", defaultValue = "")
public static Set<String> MULTI_CLIENTING_IGNORED_MAC_ADDRESSES;

/**
* If multi-clienting is restricted to the same faction, logging in characters of one faction will be denied until all characters of the opposite
* faction have been offline for the specified amount of time.
*/
@Property(key = "gameserver.security.multi_clienting.faction_switch_cooldown_minutes", defaultValue = "20")
public static int MULTI_CLIENTING_FACTION_SWITCH_COOLDOWN_MINUTES;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ public class MultiClientingService {
private static final Map<Integer, AccountSession> sessionsByAccountId = new ConcurrentHashMap<>();

public static boolean tryEnterWorld(Player player, AionConnection con) {
if (SecurityConfig.MULTI_CLIENTING_RESTRICTION_MODE == MultiClientingRestrictionMode.FULL) {
if (SecurityConfig.MULTI_CLIENTING_RESTRICTION_MODE == MultiClientingRestrictionMode.FULL && !SecurityConfig.MULTI_CLIENTING_IGNORED_MAC_ADDRESSES.contains(con.getMacAddress())) {
String mac = con.getMacAddress();
String hdd = con.getHddSerial();
String ip = con.getIP();
Expand Down Expand Up @@ -58,10 +58,12 @@ public static void onLeaveWorld(Player player) {
}

public static Integer checkForFactionSwitchCooldownTime(Race race, AionConnection con) {
if (SecurityConfig.MULTI_CLIENTING_IGNORED_MAC_ADDRESSES.contains(con.getMacAddress()))
return null;
Race oppositeRace = race == Race.ELYOS ? Race.ASMODIANS : Race.ELYOS;
long minLastOnlineMillis = System.currentTimeMillis() - Duration.ofMinutes(SecurityConfig.MULTI_CLIENTING_FACTION_SWITCH_COOLDOWN_MINUTES).toMillis();
return sessionsByAccountId.values().stream()
.filter(s -> s.wasPlayingOnSameIpOrMac(oppositeRace, minLastOnlineMillis, con))
.filter(s -> !s.isIgnored() && s.wasPlayingOnSameIpOrMac(oppositeRace, minLastOnlineMillis, con))
.findAny()
.map(s -> s.accountId)
.orElse(null);
Expand All @@ -77,6 +79,10 @@ public AccountSession(int accountId) {
this.accountId = accountId;
}

synchronized boolean isIgnored() {
return !identifiers.isEmpty() && SecurityConfig.MULTI_CLIENTING_IGNORED_MAC_ADDRESSES.contains(identifiers.getFirst().mac);
}

synchronized void putIdentifiers(AionConnection connection) {
Identifiers ids = new Identifiers(connection.getIP(), connection.getMacAddress());
if (!identifiers.contains(ids)) {
Expand Down

0 comments on commit f124a5a

Please sign in to comment.